tor-commits
Threads by month
- ----- 2025 -----
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2024 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2023 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2022 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2021 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2020 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2019 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2018 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2017 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2016 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2015 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2014 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2013 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2012 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2011 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- 1 participants
- 213855 discussions

12 Jan '12
commit 580931f412cd3284053f62b88df60f668f42ad26
Author: Karsten Loesing <karsten.loesing(a)gmx.net>
Date: Thu Jan 12 16:34:27 2012 +0100
Change a query in the database importer.
---
.../cron/RelayDescriptorDatabaseImporter.java | 5 +++--
1 files changed, 3 insertions(+), 2 deletions(-)
diff --git a/src/org/torproject/ernie/cron/RelayDescriptorDatabaseImporter.java b/src/org/torproject/ernie/cron/RelayDescriptorDatabaseImporter.java
index 4a9f97c..deefc10 100644
--- a/src/org/torproject/ernie/cron/RelayDescriptorDatabaseImporter.java
+++ b/src/org/torproject/ernie/cron/RelayDescriptorDatabaseImporter.java
@@ -244,7 +244,8 @@ public final class RelayDescriptorDatabaseImporter {
this.psSs = conn.prepareStatement("SELECT COUNT(*) "
+ "FROM statusentry WHERE validafter = ?");
this.psRs = conn.prepareStatement("SELECT COUNT(*) "
- + "FROM statusentry WHERE validafter = ? AND descriptor = ?");
+ + "FROM statusentry WHERE validafter = ? AND "
+ + "fingerprint = ?");
this.psDs = conn.prepareStatement("SELECT COUNT(*) "
+ "FROM descriptor WHERE descriptor = ?");
this.psEs = conn.prepareStatement("SELECT COUNT(*) "
@@ -362,7 +363,7 @@ public final class RelayDescriptorDatabaseImporter {
if (separateStatusEntryCheckNecessary ||
insertedStatusEntries.contains(fingerprint)) {
this.psRs.setTimestamp(1, validAfterTimestamp, cal);
- this.psRs.setString(2, descriptor);
+ this.psRs.setString(2, fingerprint);
ResultSet rs = psRs.executeQuery();
rs.next();
if (rs.getInt(1) > 0) {
1
0

[metrics-web/master] Tweak refresh functions to use partitioned table.
by karsten@torproject.org 12 Jan '12
by karsten@torproject.org 12 Jan '12
12 Jan '12
commit 13857257ac1df8c4b4d9bc00e0164b5731289762
Author: Karsten Loesing <karsten.loesing(a)gmx.net>
Date: Thu Jan 12 14:54:16 2012 +0100
Tweak refresh functions to use partitioned table.
---
db/tordir.sql | 162 ++++++++++++++++++++++++++++++++++++++-------------------
1 files changed, 109 insertions(+), 53 deletions(-)
diff --git a/db/tordir.sql b/db/tordir.sql
index fbb1341..bc93b45 100644
--- a/db/tordir.sql
+++ b/db/tordir.sql
@@ -438,11 +438,18 @@ $$ LANGUAGE plpgsql;
-- FUNCTION refresh_network_size()
CREATE OR REPLACE FUNCTION refresh_network_size() RETURNS INTEGER AS $$
+ DECLARE
+ min_date TIMESTAMP WITHOUT TIME ZONE;
+ max_date TIMESTAMP WITHOUT TIME ZONE;
BEGIN
+ min_date := (SELECT MIN(date) FROM updates);
+ max_date := (SELECT MAX(date) + 1 FROM updates);
+
DELETE FROM network_size
WHERE date IN (SELECT date FROM updates);
+ EXECUTE '
INSERT INTO network_size
(date, avg_running, avg_exit, avg_guard, avg_fast, avg_stable)
SELECT date,
@@ -460,12 +467,12 @@ CREATE OR REPLACE FUNCTION refresh_network_size() RETURNS INTEGER AS $$
COUNT(NULLIF(isstable, FALSE)) AS isstable
FROM statusentry
WHERE isrunning = TRUE
- AND DATE(validafter) >= (SELECT MIN(date) FROM updates)
- AND DATE(validafter) <= (SELECT MAX(date) FROM updates)
+ AND validafter >= ''' || min_date || '''
+ AND validafter < ''' || max_date || '''
AND DATE(validafter) IN (SELECT date FROM updates)
GROUP BY DATE(validafter)
) b
- NATURAL JOIN relay_statuses_per_day;
+ NATURAL JOIN relay_statuses_per_day';
RETURN 1;
END;
@@ -473,11 +480,18 @@ $$ LANGUAGE plpgsql;
-- FUNCTION refresh_network_size_hour()
CREATE OR REPLACE FUNCTION refresh_network_size_hour() RETURNS INTEGER AS $$
+ DECLARE
+ min_date TIMESTAMP WITHOUT TIME ZONE;
+ max_date TIMESTAMP WITHOUT TIME ZONE;
BEGIN
+ min_date := (SELECT MIN(date) FROM updates);
+ max_date := (SELECT MAX(date) + 1 FROM updates);
+
DELETE FROM network_size_hour
WHERE DATE(validafter) IN (SELECT date FROM updates);
+ EXECUTE '
INSERT INTO network_size_hour
(validafter, avg_running, avg_exit, avg_guard, avg_fast, avg_stable)
SELECT validafter, COUNT(*) AS avg_running,
@@ -487,10 +501,10 @@ CREATE OR REPLACE FUNCTION refresh_network_size_hour() RETURNS INTEGER AS $$
COUNT(NULLIF(isstable, FALSE)) AS avg_stable
FROM statusentry
WHERE isrunning = TRUE
- AND DATE(validafter) >= (SELECT MIN(date) FROM updates)
- AND DATE(validafter) <= (SELECT MAX(date) FROM updates)
+ AND validafter >= ''' || min_date || '''
+ AND validafter < ''' || max_date || '''
AND DATE(validafter) IN (SELECT date FROM updates)
- GROUP BY validafter;
+ GROUP BY validafter';
RETURN 1;
END;
@@ -498,27 +512,34 @@ $$ LANGUAGE plpgsql;
-- FUNCTION refresh_relay_countries()
CREATE OR REPLACE FUNCTION refresh_relay_countries() RETURNS INTEGER AS $$
+ DECLARE
+ min_date TIMESTAMP WITHOUT TIME ZONE;
+ max_date TIMESTAMP WITHOUT TIME ZONE;
BEGIN
+ min_date := (SELECT MIN(date) FROM updates);
+ max_date := (SELECT MAX(date) + 1 FROM updates);
+
DELETE FROM relay_countries
WHERE date IN (SELECT date FROM updates);
+ EXECUTE '
INSERT INTO relay_countries
(date, country, relays)
SELECT date, country, relays / count AS relays
FROM (
SELECT DATE(validafter),
- COALESCE(lower((geoip_lookup(address)).country), 'zz')
+ COALESCE(lower((geoip_lookup(address)).country), ''zz'')
AS country,
COUNT(*) AS relays
FROM statusentry
WHERE isrunning = TRUE
- AND DATE(validafter) >= (SELECT MIN(date) FROM updates)
- AND DATE(validafter) <= (SELECT MAX(date) FROM updates)
+ AND validafter >= ''' || min_date || '''
+ AND validafter < ''' || max_date || '''
AND DATE(validafter) IN (SELECT date FROM updates)
GROUP BY 1, 2
) b
- NATURAL JOIN relay_statuses_per_day;
+ NATURAL JOIN relay_statuses_per_day';
RETURN 1;
END;
@@ -526,11 +547,18 @@ $$ LANGUAGE plpgsql;
-- FUNCTION refresh_relay_platforms()
CREATE OR REPLACE FUNCTION refresh_relay_platforms() RETURNS INTEGER AS $$
+ DECLARE
+ min_date TIMESTAMP WITHOUT TIME ZONE;
+ max_date TIMESTAMP WITHOUT TIME ZONE;
BEGIN
+ min_date := (SELECT MIN(date) FROM updates);
+ max_date := (SELECT MAX(date) + 1 FROM updates);
+
DELETE FROM relay_platforms
WHERE date IN (SELECT date FROM updates);
+ EXECUTE '
INSERT INTO relay_platforms
(date, avg_linux, avg_darwin, avg_bsd, avg_windows, avg_other)
SELECT date,
@@ -541,29 +569,29 @@ CREATE OR REPLACE FUNCTION refresh_relay_platforms() RETURNS INTEGER AS $$
other / count AS avg_other
FROM (
SELECT DATE(validafter) AS date,
- SUM(CASE WHEN platform LIKE '%Linux%' THEN 1 ELSE 0 END)
+ SUM(CASE WHEN platform LIKE ''%Linux%'' THEN 1 ELSE 0 END)
AS linux,
- SUM(CASE WHEN platform LIKE '%Darwin%' THEN 1 ELSE 0 END)
+ SUM(CASE WHEN platform LIKE ''%Darwin%'' THEN 1 ELSE 0 END)
AS darwin,
- SUM(CASE WHEN platform LIKE '%BSD%' THEN 1 ELSE 0 END)
+ SUM(CASE WHEN platform LIKE ''%BSD%'' THEN 1 ELSE 0 END)
AS bsd,
- SUM(CASE WHEN platform LIKE '%Windows%' THEN 1 ELSE 0 END)
+ SUM(CASE WHEN platform LIKE ''%Windows%'' THEN 1 ELSE 0 END)
AS windows,
- SUM(CASE WHEN platform NOT LIKE '%Windows%'
- AND platform NOT LIKE '%Darwin%'
- AND platform NOT LIKE '%BSD%'
- AND platform NOT LIKE '%Linux%' THEN 1 ELSE 0 END)
+ SUM(CASE WHEN platform NOT LIKE ''%Windows%''
+ AND platform NOT LIKE ''%Darwin%''
+ AND platform NOT LIKE ''%BSD%''
+ AND platform NOT LIKE ''%Linux%'' THEN 1 ELSE 0 END)
AS other
FROM descriptor
RIGHT JOIN statusentry
ON statusentry.descriptor = descriptor.descriptor
WHERE isrunning = TRUE
- AND DATE(validafter) >= (SELECT MIN(date) FROM updates)
- AND DATE(validafter) <= (SELECT MAX(date) FROM updates)
+ AND validafter >= ''' || min_date || '''
+ AND validafter < ''' || max_date || '''
AND DATE(validafter) IN (SELECT date FROM updates)
GROUP BY DATE(validafter)
) b
- NATURAL JOIN relay_statuses_per_day;
+ NATURAL JOIN relay_statuses_per_day';
RETURN 1;
END;
@@ -571,11 +599,18 @@ $$ LANGUAGE plpgsql;
-- FUNCTION refresh_relay_versions()
CREATE OR REPLACE FUNCTION refresh_relay_versions() RETURNS INTEGER AS $$
+ DECLARE
+ min_date TIMESTAMP WITHOUT TIME ZONE;
+ max_date TIMESTAMP WITHOUT TIME ZONE;
BEGIN
+ min_date := (SELECT MIN(date) FROM updates);
+ max_date := (SELECT MAX(date) + 1 FROM updates);
+
DELETE FROM relay_versions
WHERE date IN (SELECT date FROM updates);
+ EXECUTE '
INSERT INTO relay_versions
(date, version, relays)
SELECT date, version, relays / count AS relays
@@ -586,12 +621,12 @@ CREATE OR REPLACE FUNCTION refresh_relay_versions() RETURNS INTEGER AS $$
ON descriptor.descriptor = statusentry.descriptor
WHERE isrunning = TRUE
AND platform IS NOT NULL
- AND DATE(validafter) >= (SELECT MIN(date) FROM updates)
- AND DATE(validafter) <= (SELECT MAX(date) FROM updates)
+ AND validafter >= ''' || min_date || '''
+ AND validafter < ''' || max_date || '''
AND DATE(validafter) IN (SELECT date FROM updates)
GROUP BY 1, 2
) b
- NATURAL JOIN relay_statuses_per_day;
+ NATURAL JOIN relay_statuses_per_day';
RETURN 1;
END;
@@ -600,11 +635,18 @@ $$ LANGUAGE plpgsql;
-- FUNCTION refresh_total_bandwidth()
-- This keeps the table total_bandwidth up-to-date when necessary.
CREATE OR REPLACE FUNCTION refresh_total_bandwidth() RETURNS INTEGER AS $$
+ DECLARE
+ min_date TIMESTAMP WITHOUT TIME ZONE;
+ max_date TIMESTAMP WITHOUT TIME ZONE;
BEGIN
+ min_date := (SELECT MIN(date) FROM updates);
+ max_date := (SELECT MAX(date) + 1 FROM updates);
+
DELETE FROM total_bandwidth
WHERE date IN (SELECT date FROM updates);
+ EXECUTE '
INSERT INTO total_bandwidth
(bwavg, bwburst, bwobserved, bwadvertised, date)
SELECT (SUM(bandwidthavg)
@@ -621,16 +663,14 @@ CREATE OR REPLACE FUNCTION refresh_total_bandwidth() RETURNS INTEGER AS $$
JOIN relay_statuses_per_day
ON DATE(validafter) = relay_statuses_per_day.date
WHERE isrunning = TRUE
- AND DATE(validafter) >= (SELECT MIN(date) FROM updates)
- AND DATE(validafter) <= (SELECT MAX(date) FROM updates)
+ AND validafter >= ''' || min_date || '''
+ AND validafter < ''' || max_date || '''
AND DATE(validafter) IN (SELECT date FROM updates)
- AND DATE(relay_statuses_per_day.date) >=
- (SELECT MIN(date) FROM updates)
- AND DATE(relay_statuses_per_day.date) <=
- (SELECT MAX(date) FROM updates)
+ AND relay_statuses_per_day.date >= ''' || min_date || '''
+ AND relay_statuses_per_day.date < ''' || max_date || '''
AND DATE(relay_statuses_per_day.date) IN
(SELECT date FROM updates)
- GROUP BY DATE(validafter), relay_statuses_per_day.count;
+ GROUP BY DATE(validafter), relay_statuses_per_day.count';
RETURN 1;
END;
@@ -651,8 +691,16 @@ CREATE OR REPLACE FUNCTION refresh_total_bwhist() RETURNS INTEGER AS $$
$$ LANGUAGE plpgsql;
CREATE OR REPLACE FUNCTION refresh_bwhist_flags() RETURNS INTEGER AS $$
- BEGIN
+ DECLARE
+ min_date TIMESTAMP WITHOUT TIME ZONE;
+ max_date TIMESTAMP WITHOUT TIME ZONE;
+ BEGIN
+
+ min_date := (SELECT MIN(date) FROM updates);
+ max_date := (SELECT MAX(date) + 1 FROM updates);
+
DELETE FROM bwhist_flags WHERE date IN (SELECT date FROM updates);
+ EXECUTE '
INSERT INTO bwhist_flags (date, isexit, isguard, read, written)
SELECT a.date, isexit, isguard, SUM(read_sum) as read,
SUM(written_sum) AS written
@@ -663,14 +711,14 @@ CREATE OR REPLACE FUNCTION refresh_bwhist_flags() RETURNS INTEGER AS $$
BOOL_OR(isguard) AS isguard
FROM statusentry
WHERE isrunning = TRUE
- AND DATE(validafter) >= (SELECT MIN(date) FROM updates)
- AND DATE(validafter) <= (SELECT MAX(date) FROM updates)
+ AND validafter >= ''' || min_date || '''
+ AND validafter < ''' || max_date || '''
AND DATE(validafter) IN (SELECT date FROM updates)
GROUP BY 1, 2) a
JOIN bwhist
ON a.date = bwhist.date
AND a.fingerprint = bwhist.fingerprint
- GROUP BY 1, 2, 3;
+ GROUP BY 1, 2, 3';
RETURN 1;
END;
$$ LANGUAGE plpgsql;
@@ -680,11 +728,19 @@ $$ LANGUAGE plpgsql;
-- directory request statistics of directory mirrors with bandwidth
-- histories.
CREATE OR REPLACE FUNCTION refresh_user_stats() RETURNS INTEGER AS $$
- BEGIN
+ DECLARE
+ min_date TIMESTAMP WITHOUT TIME ZONE;
+ max_date TIMESTAMP WITHOUT TIME ZONE;
+ BEGIN
+
+ min_date := (SELECT MIN(date) FROM updates);
+ max_date := (SELECT MAX(date) + 1 FROM updates);
+
-- Start by deleting user statistics of the dates we're about to
-- regenerate.
DELETE FROM user_stats WHERE date IN (SELECT date FROM updates);
-- Now insert new user statistics.
+ EXECUTE '
INSERT INTO user_stats (date, country, r, dw, dr, drw, drr, bw, br, bwd,
brd, bwr, brr, bwdr, brdr, bwp, brp, bwn, brn)
SELECT
@@ -692,7 +748,7 @@ CREATE OR REPLACE FUNCTION refresh_user_stats() RETURNS INTEGER AS $$
dirreq_stats_by_country.date AS date,
dirreq_stats_by_country.country AS country,
dirreq_stats_by_country.r AS r,
- -- In order to weight the reported directory requests, we're
+ -- In order to weight the reported directory requests, we are
-- counting bytes of relays (except directory authorities)
-- matching certain criteria: whether or not they are reporting
-- directory requests, whether or not they are reporting
@@ -759,14 +815,14 @@ CREATE OR REPLACE FUNCTION refresh_user_stats() RETURNS INTEGER AS $$
) dirreq_stats_split
GROUP BY 1, 2, 3
) dirreq_stats_by_date
- -- We're only interested in requests by directory mirrors, not
+ -- We are only interested in requests by directory mirrors, not
-- directory authorities, so we exclude all relays with the Authority
-- flag.
RIGHT JOIN (
SELECT fingerprint, DATE(validafter) AS date
FROM statusentry
- WHERE DATE(validafter) >= (SELECT MIN(date) FROM updates)
- AND DATE(validafter) <= (SELECT MAX(date) FROM updates)
+ WHERE validafter >= ''' || min_date || '''
+ AND validafter < ''' || max_date || '''
AND DATE(validafter) IN (SELECT date FROM updates)
AND isauthority IS FALSE
GROUP BY 1, 2
@@ -782,8 +838,8 @@ CREATE OR REPLACE FUNCTION refresh_user_stats() RETURNS INTEGER AS $$
SELECT fingerprint, date, read_sum AS read, written_sum AS written,
dirread_sum AS dirread, dirwritten_sum AS dirwritten
FROM bwhist
- WHERE date >= (SELECT MIN(date) FROM updates)
- AND date <= (SELECT MAX(date) FROM updates)
+ WHERE date >= ''' || min_date || '''
+ AND date < ''' || max_date || '''
AND date IN (SELECT date FROM updates)
) bwhist_by_relay
ON dirreq_stats_by_country.date = bwhist_by_relay.date
@@ -794,8 +850,8 @@ CREATE OR REPLACE FUNCTION refresh_user_stats() RETURNS INTEGER AS $$
SUM(CASE WHEN dirport > 0 THEN 1 ELSE NULL END) AS opendirport,
SUM(CASE WHEN isauthority IS TRUE THEN 1 ELSE NULL END) AS authority
FROM statusentry
- WHERE DATE(validafter) >= (SELECT MIN(date) FROM updates)
- AND DATE(validafter) <= (SELECT MAX(date) FROM updates)
+ WHERE validafter >= ''' || min_date || '''
+ AND validafter < ''' || max_date || '''
AND DATE(validafter) IN (SELECT date FROM updates)
GROUP BY 1, 2
) statusentry_by_relay
@@ -805,23 +861,23 @@ CREATE OR REPLACE FUNCTION refresh_user_stats() RETURNS INTEGER AS $$
-- For each relay, tell if it has reported directory request
-- statistics on a given date. Again, we have to take into account
-- that statistics intervals cover more than one calendar date in most
- -- cases. The exact number of requests isn't relevant here, but only
+ -- cases. The exact number of requests is not relevant here, but only
-- whether the relay reported directory requests or not.
SELECT fingerprint, date, 1 AS requests
FROM (
SELECT LOWER(source) AS fingerprint, DATE(statsend) AS date
FROM dirreq_stats
- WHERE DATE(statsend) >= (SELECT MIN(date) FROM updates)
- AND DATE(statsend) <= (SELECT MAX(date) FROM updates)
+ WHERE DATE(statsend) >= ''' || min_date || '''
+ AND DATE(statsend) < ''' || max_date || '''
AND DATE(statsend) IN (SELECT date FROM updates)
- AND country = 'zy'
+ AND country = ''zy''
UNION
SELECT LOWER(source) AS fingerprint, DATE(statsend) - 1 AS date
FROM dirreq_stats
- WHERE DATE(statsend) - 1 >= (SELECT MIN(date) FROM updates)
- AND DATE(statsend) - 1 <= (SELECT MAX(date) FROM updates)
- AND DATE(statsend) - 1 IN (SELECT date FROM updates)
- AND country = 'zy'
+ WHERE DATE(statsend) - 1 >= ''' || min_date || '''
+ AND DATE(statsend) - 1 < ''' || max_date || '''
+ AND DATE(statsend) IN (SELECT date FROM updates)
+ AND country = ''zy''
AND EXTRACT(EPOCH FROM DATE(statsend)) -
EXTRACT(EPOCH FROM statsend) + seconds > 0
) dirreq_stats_split
@@ -832,7 +888,7 @@ CREATE OR REPLACE FUNCTION refresh_user_stats() RETURNS INTEGER AS $$
WHERE dirreq_stats_by_country.country IS NOT NULL
-- Group by date, country, and total reported directory requests,
-- summing up the bandwidth histories.
- GROUP BY 1, 2, 3;
+ GROUP BY 1, 2, 3';
RETURN 1;
END;
$$ LANGUAGE plpgsql;
1
0

12 Jan '12
commit d5ffbee290e55423e143e6eb558f2647e28b5d6a
Author: Karsten Loesing <karsten.loesing(a)gmx.net>
Date: Thu Jan 12 09:29:11 2012 +0100
Implement bridge network status parsing.
---
.../impl/BridgeDescriptorReaderImpl.java | 85 ++++++++++++++++++--
.../descriptor/impl/BridgeNetworkStatusImpl.java | 75 +++++++++++++++++
.../torproject/descriptor/impl/DescriptorImpl.java | 30 +++++++
3 files changed, 183 insertions(+), 7 deletions(-)
diff --git a/src/org/torproject/descriptor/impl/BridgeDescriptorReaderImpl.java b/src/org/torproject/descriptor/impl/BridgeDescriptorReaderImpl.java
index 09f422c..04e5d2a 100644
--- a/src/org/torproject/descriptor/impl/BridgeDescriptorReaderImpl.java
+++ b/src/org/torproject/descriptor/impl/BridgeDescriptorReaderImpl.java
@@ -2,34 +2,105 @@
* See LICENSE for licensing information */
package org.torproject.descriptor.impl;
+import java.io.BufferedInputStream;
+import java.io.ByteArrayOutputStream;
import java.io.File;
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.Arrays;
import java.util.Iterator;
+import java.util.List;
import java.util.Map;
import java.util.Set;
+import java.util.Stack;
+import org.torproject.descriptor.Descriptor;
import org.torproject.descriptor.DescriptorFile;
import org.torproject.descriptor.BridgeDescriptorReader;
-public class BridgeDescriptorReaderImpl implements BridgeDescriptorReader {
+public class BridgeDescriptorReaderImpl
+ implements BridgeDescriptorReader {
+ private List<File> directories = new ArrayList<File>();
public void addDirectory(File directory) {
- /* TODO Implement me. */
+ this.directories.add(directory);
}
public void setExcludeFile(File fileToExclude) {
+ throw new UnsupportedOperationException("Not implemented yet.");
/* TODO Implement me. */
}
public void setExcludeFiles(Set<File> filesToExclude) {
+ throw new UnsupportedOperationException("Not implemented yet.");
/* TODO Implement me. */
}
- public void setInitialCacheLimit(long cacheLimitBytes) {
- /* TODO Implement me. */
+ public Iterator<DescriptorFile> readDescriptors() {
+ BlockingIteratorImpl<DescriptorFile> descriptorQueue =
+ new BlockingIteratorImpl<DescriptorFile>();
+ DescriptorReader reader = new DescriptorReader(this.directories,
+ descriptorQueue);
+ new Thread(reader).start();
+ return descriptorQueue;
}
- public Iterator<DescriptorFile> readDescriptors() {
- /* TODO Implement me. */
- return new BlockingIteratorImpl<DescriptorFile>();
+ private static class DescriptorReader implements Runnable {
+ private List<File> directories;
+ private BlockingIteratorImpl<DescriptorFile> descriptorQueue;
+ private DescriptorReader(List<File> directories,
+ BlockingIteratorImpl<DescriptorFile> descriptorQueue) {
+ this.directories = directories;
+ this.descriptorQueue = descriptorQueue;
+ }
+ public void run() {
+ for (File directory : this.directories) {
+ try {
+ Stack<File> files = new Stack<File>();
+ files.add(directory);
+ while (!files.isEmpty()) {
+ File file = files.pop();
+ if (file.isDirectory()) {
+ files.addAll(Arrays.asList(file.listFiles()));
+ } else {
+ try {
+ List<Descriptor> parsedDescriptors = this.readFile(file);
+ DescriptorFileImpl descriptorFile =
+ new DescriptorFileImpl();
+ descriptorFile.setDirectory(directory);
+ descriptorFile.setFile(file);
+ descriptorFile.setLastModified(file.lastModified());
+ descriptorFile.setDescriptors(parsedDescriptors);
+ this.descriptorQueue.add(descriptorFile);
+ } catch (DescriptorParseException e) {
+ /* TODO Handle me. */
+ }
+ }
+ }
+ } catch (IOException e) {
+ System.err.println("Error while reading descriptors in '"
+ + directory.getAbsolutePath() + "'.");
+ /* TODO Handle this exception somehow. */
+ } finally {
+ this.descriptorQueue.setOutOfDescriptors();
+ }
+ }
+ }
+ private List<Descriptor> readFile(File file) throws IOException,
+ DescriptorParseException {
+ FileInputStream fis = new FileInputStream(file);
+ BufferedInputStream bis = new BufferedInputStream(fis);
+ ByteArrayOutputStream baos = new ByteArrayOutputStream();
+ int len;
+ byte[] data = new byte[1024];
+ while ((len = bis.read(data, 0, 1024)) >= 0) {
+ baos.write(data, 0, len);
+ }
+ bis.close();
+ byte[] rawDescriptorBytes = baos.toByteArray();
+ return DescriptorImpl.parseBridgeDescriptors(rawDescriptorBytes,
+ file.getName());
+ }
}
}
diff --git a/src/org/torproject/descriptor/impl/BridgeNetworkStatusImpl.java b/src/org/torproject/descriptor/impl/BridgeNetworkStatusImpl.java
new file mode 100644
index 0000000..714f6ae
--- /dev/null
+++ b/src/org/torproject/descriptor/impl/BridgeNetworkStatusImpl.java
@@ -0,0 +1,75 @@
+/* Copyright 2012 The Tor Project
+ * See LICENSE for licensing information */
+package org.torproject.descriptor.impl;
+
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.TimeZone;
+import org.torproject.descriptor.BridgeNetworkStatus;
+
+/* Contains a bridge network status. */
+public class BridgeNetworkStatusImpl extends NetworkStatusImpl
+ implements BridgeNetworkStatus {
+
+ protected BridgeNetworkStatusImpl(byte[] statusBytes,
+ String fileName) throws DescriptorParseException {
+ super(statusBytes);
+ this.setPublishedMillisFromFileName(fileName);
+ }
+
+ private static SimpleDateFormat fileNameFormat = new SimpleDateFormat(
+ "yyyyMMdd-HHmmss");
+ static {
+ fileNameFormat.setLenient(false);
+ fileNameFormat.setTimeZone(TimeZone.getTimeZone("UTC"));
+ }
+
+ private void setPublishedMillisFromFileName(String fileName)
+ throws DescriptorParseException {
+ if (fileName.length() ==
+ "20000101-000000-4A0CCD2DDC7995083D73F5D667100C8A5831F16D".
+ length()) {
+ String publishedString = fileName.substring(0,
+ "yyyyMMdd-HHmmss".length());
+ try {
+ this.publishedMillis = fileNameFormat.parse(publishedString).
+ getTime();
+ } catch (ParseException e) {
+ }
+ }
+ if (this.publishedMillis == 0L) {
+ throw new DescriptorParseException("Unrecognized bridge network "
+ + "status file name '" + fileName + "'.");
+ }
+ }
+
+ protected void parseHeader(byte[] headerBytes)
+ throws DescriptorParseException {
+ throw new DescriptorParseException("No directory header expected in "
+ + "bridge network status.");
+ }
+
+ protected void parseDirSource(byte[] dirSourceBytes)
+ throws DescriptorParseException {
+ throw new DescriptorParseException("No directory source expected in "
+ + "bridge network status.");
+ }
+
+ protected void parseFooter(byte[] footerBytes)
+ throws DescriptorParseException {
+ throw new DescriptorParseException("No directory footer expected in "
+ + "bridge network status.");
+ }
+
+ protected void parseDirectorySignature(byte[] directorySignatureBytes)
+ throws DescriptorParseException {
+ throw new DescriptorParseException("No directory signature expected "
+ + "in bridge network status.");
+ }
+
+ private long publishedMillis;
+ public long getPublishedMillis() {
+ return this.publishedMillis;
+ }
+}
+
diff --git a/src/org/torproject/descriptor/impl/DescriptorImpl.java b/src/org/torproject/descriptor/impl/DescriptorImpl.java
index cade4cf..24c1fe9 100644
--- a/src/org/torproject/descriptor/impl/DescriptorImpl.java
+++ b/src/org/torproject/descriptor/impl/DescriptorImpl.java
@@ -51,6 +51,36 @@ public abstract class DescriptorImpl implements Descriptor {
return parsedDescriptors;
}
+ protected static List<Descriptor> parseBridgeDescriptors(
+ byte[] rawDescriptorBytes, String fileName)
+ throws DescriptorParseException {
+ List<Descriptor> parsedDescriptors = new ArrayList<Descriptor>();
+ byte[] first100Chars = new byte[Math.min(100,
+ rawDescriptorBytes.length)];
+ System.arraycopy(rawDescriptorBytes, 0, first100Chars, 0,
+ first100Chars.length);
+ String firstLines = new String(first100Chars);
+ if (firstLines.startsWith("r ")) {
+ parsedDescriptors.add(new BridgeNetworkStatusImpl(
+ rawDescriptorBytes, fileName));
+ } else if (firstLines.startsWith("router ") ||
+ firstLines.contains("\nrouter ")) {
+ /* TODO Implement me.
+ parsedDescriptors.addAll(BridgeServerDescriptorImpl.
+ parseDescriptors(rawDescriptorBytes)); */
+ } else if (firstLines.startsWith("extra-info ") ||
+ firstLines.contains("\nextra-info ")) {
+ /* TODO Implement me.
+ parsedDescriptors.addAll(BridgeExtraInfoDescriptorImpl.
+ parseDescriptors(rawDescriptorBytes)); */
+ } else {
+ throw new DescriptorParseException("Could not detect bridge "
+ + "descriptor type in descriptor starting with '" + firstLines
+ + "'.");
+ }
+ return parsedDescriptors;
+ }
+
protected static List<byte[]> splitRawDescriptorBytes(
byte[] rawDescriptorBytes, String startToken) {
List<byte[]> rawDescriptors = new ArrayList<byte[]>();
1
0

[metrics-lib/master] Use a single relay and bridge descriptor implementation.
by karsten@torproject.org 12 Jan '12
by karsten@torproject.org 12 Jan '12
12 Jan '12
commit ef6de2f9ad26fb064844d3c6edccf6ce7a829faf
Author: Karsten Loesing <karsten.loesing(a)gmx.net>
Date: Thu Jan 12 09:59:32 2012 +0100
Use a single relay and bridge descriptor implementation.
Relay and bridge server and extra-info descriptors are similar enough to
implement them in a single class each. It should be clear from the
descriptor source (relay or bridge reader) whether the descriptor was
published by a relay or a bridge.
---
.../descriptor/BridgeExtraInfoDescriptor.java | 7 -
.../descriptor/BridgeServerDescriptor.java | 7 -
.../torproject/descriptor/ExtraInfoDescriptor.java | 211 ++++
.../descriptor/RelayExtraInfoDescriptor.java | 211 ----
.../descriptor/RelayServerDescriptor.java | 110 --
.../torproject/descriptor/ServerDescriptor.java | 110 ++
.../torproject/descriptor/impl/DescriptorImpl.java | 4 +-
.../descriptor/impl/ExtraInfoDescriptorImpl.java | 574 +++++++++++
.../impl/RelayExtraInfoDescriptorImpl.java | 574 -----------
.../descriptor/impl/RelayServerDescriptorImpl.java | 532 ----------
.../descriptor/impl/ServerDescriptorImpl.java | 532 ++++++++++
.../impl/RelayServerDescriptorImplTest.java | 1080 --------------------
.../descriptor/impl/ServerDescriptorImplTest.java | 1080 ++++++++++++++++++++
13 files changed, 2509 insertions(+), 2523 deletions(-)
diff --git a/src/org/torproject/descriptor/BridgeExtraInfoDescriptor.java b/src/org/torproject/descriptor/BridgeExtraInfoDescriptor.java
deleted file mode 100644
index ed0238d..0000000
--- a/src/org/torproject/descriptor/BridgeExtraInfoDescriptor.java
+++ /dev/null
@@ -1,7 +0,0 @@
-/* Copyright 2011, 2012 The Tor Project
- * See LICENSE for licensing information */
-package org.torproject.descriptor;
-
-public interface BridgeExtraInfoDescriptor extends Descriptor {
-}
-
diff --git a/src/org/torproject/descriptor/BridgeServerDescriptor.java b/src/org/torproject/descriptor/BridgeServerDescriptor.java
deleted file mode 100644
index ec759b1..0000000
--- a/src/org/torproject/descriptor/BridgeServerDescriptor.java
+++ /dev/null
@@ -1,7 +0,0 @@
-/* Copyright 2011, 2012 The Tor Project
- * See LICENSE for licensing information */
-package org.torproject.descriptor;
-
-public interface BridgeServerDescriptor extends Descriptor {
-}
-
diff --git a/src/org/torproject/descriptor/ExtraInfoDescriptor.java b/src/org/torproject/descriptor/ExtraInfoDescriptor.java
new file mode 100644
index 0000000..bd4bcd8
--- /dev/null
+++ b/src/org/torproject/descriptor/ExtraInfoDescriptor.java
@@ -0,0 +1,211 @@
+/* Copyright 2012 The Tor Project
+ * See LICENSE for licensing information */
+package org.torproject.descriptor;
+
+import java.util.List;
+import java.util.SortedMap;
+
+public interface ExtraInfoDescriptor extends Descriptor {
+
+ /* Return the relay's nickname. */
+ public String getNickname();
+
+ /* Return the relay's fingerprint. */
+ public String getFingerprint();
+
+ /* Return the publication time of this descriptor. */
+ public long getPublishedMillis();
+
+ /* Return the read history contained in this descriptor, or null if no
+ * read history is contained. */
+ public BandwidthHistory getReadHistory();
+
+ /* Return the write history contained in this descriptor, or null if no
+ * read history is contained. */
+ public BandwidthHistory getWriteHistory();
+
+ /* Return the SHA1 digest of the GeoIP database used by this relay, or
+ * null if no GeoIP database digest is included. */
+ public String getGeoipDbDigest();
+
+ /* Return the end of the included directory request statistics interval,
+ * or -1 if no directory request statistics are included. */
+ public long getDirreqStatsEndMillis();
+
+ /* Return the interval length of the included directory request
+ * statistics, or -1 if no directory request statistics are included. */
+ public long getDirreqStatsIntervalLength();
+
+ /* Return statistics on unique IP addresses requesting v2 network
+ * statuses with map keys being country codes and map values being
+ * numbers of unique IP addresses rounded up to the nearest multiple of
+ * 8, or null if no such statistics are included. */
+ public SortedMap<String, Integer> getDirreqV2Ips();
+
+ /* Return statistics on unique IP addresses requesting v3 network status
+ * consensuses with map keys being country codes and map values being
+ * numbers of unique IP addresses rounded up to the nearest multiple of
+ * 8, or null if no such statistics are included. */
+ public SortedMap<String, Integer> getDirreqV3Ips();
+
+ /* Return statistics on directory requests for v2 network statuses with
+ * map keys being country codes and map values being request numbers
+ * rounded up to the nearest multiple of 8, or null if no such
+ * statistics are included. */
+ public SortedMap<String, Integer> getDirreqV2Reqs();
+
+ /* Return statistics on directory requests for v3 network status
+ * consensuses with map keys being country codes and map values being
+ * request numbers rounded up to the nearest multiple of 8, or null if
+ * no such statistics are included. */
+ public SortedMap<String, Integer> getDirreqV3Reqs();
+
+ /* Return the share of requests for v2 network statuses that the
+ * directory expects to receive from clients, or -1.0 if no such
+ * statistics are included. */
+ public double getDirreqV2Share();
+
+ /* Return the share of requests for v3 network status consensuses that
+ * the directory expects to receive from clients, or -1.0 if no such
+ * statistics are included. */
+ public double getDirreqV3Share();
+
+ /* Return statistics on directory request responses for v2 network
+ * statuses with map keys being response strings and map values being
+ * response numbers rounded up to the nearest multiple of 4, or null if
+ * no such statistics are included. */
+ public SortedMap<String, Integer> getDirreqV2Resp();
+
+ /* Return statistics on directory request responses for v3 network
+ * status consensuses with map keys being response strings and map
+ * values being response numbers rounded up to the nearest multiple of
+ * 4, or null if no such statistics are included. */
+ public SortedMap<String, Integer> getDirreqV3Resp();
+
+ /* Return statistics on direct directory requests asking for v2 network
+ * statuses with map keys being statistic keys and map values being
+ * statistic values, or null if no such statistics are included. */
+ public SortedMap<String, Integer> getDirreqV2DirectDl();
+
+ /* Return statistics on direct directory requests asking for v3 network
+ * status consensuses with map keys being statistic keys and map
+ * values being statistic values, or null if no such statistics are
+ * included. */
+ public SortedMap<String, Integer> getDirreqV3DirectDl();
+
+ /* Return statistics on tunneled directory requests asking for v2
+ * network statuses with map keys being statistic keys and map values
+ * being statistic values, or null if no such statistics are
+ * included. */
+ public SortedMap<String, Integer> getDirreqV2TunneledDl();
+
+ /* Return statistics on tunneled directory requests asking for v3
+ * network status consensuses with map keys being statistic keys and map
+ * values being statistic values, or null if no such statistics are
+ * included. */
+ public SortedMap<String, Integer> getDirreqV3TunneledDl();
+
+ /* Return the directory request read history contained in this
+ * descriptor, or null if no directory request read history is
+ * contained. */
+ public BandwidthHistory getDirreqReadHistory();
+
+ /* Return the directory request write history contained in this
+ * descriptor, or null if no directory request write history is
+ * contained. */
+ public BandwidthHistory getDirreqWriteHistory();
+
+ /* Return the end of the included entry statistics interval, or -1 if no
+ * entry statistics are included. */
+ public long getEntryStatsEndMillis();
+
+ /* Return the interval length of the included entry statistics, or -1 if
+ * no entry statistics are included. */
+ public long getEntryStatsIntervalLength();
+
+ /* Return statistics on client IP addresses with map keys being country
+ * codes and map values being the number of unique IP addresses that
+ * have connected from that country rounded up to the nearest multiple
+ * of 8, or null if no entry statistics are included. */
+ public SortedMap<String, Integer> getEntryIps();
+
+ /* Return the end of the included cell statistics interval, or -1 if no
+ * cell statistics are included. */
+ public long getCellStatsEndMillis();
+
+ /* Return the interval length of the included cell statistics, or -1 if
+ * no cell statistics are included. */
+ public long getCellStatsIntervalLength();
+
+ /* Return the mean number of processed cells per circuit by circuit
+ * deciles. */
+ public List<Integer> getCellProcessedCells();
+
+ /* Return the mean number of cells contained in circuit queues by
+ * circuit deciles. */
+ public List<Integer> getCellQueueCells();
+
+ /* Return the mean times in milliseconds that cells spend in circuit
+ * queues by circuit deciles. */
+ public List<Integer> getCellTimeInQueue();
+
+ /* Return the mean number of circuits included in any of the cell
+ * statistics deciles, or -1 if no cell statistics are included. */
+ public int getCellCircuitsPerDecile();
+
+ /* Return the end of the included statistics interval on bi-directional
+ * connection usage, or -1 if no such statistics are included. */
+ public long getConnBiDirectStatsEndMillis();
+
+ /* Return the interval length of the included statistics on
+ * bi-directional connection usage, or -1 if no such statistics are
+ * included. */
+ public long getConnBiDirectIntervalLength();
+
+ /* Return the number of connections on which this relay read and wrote
+ * less than 2 KiB/s in a 10-second interval, or -1 if no statistics on
+ * bi-directional connection usage are included. */
+ public int getConnBiDirectBelow();
+
+ /* Return the number of connections on which this relay read and wrote
+ * at least 2 KiB/s in a 10-second interval and at least 10 times more
+ * in read direction than in write direction, or -1 if no statistics on
+ * bi-directional connection usage are included. */
+ public int getConnBiDirectRead();
+
+ /* Return the number of connections on which this relay read and wrote
+ * at least 2 KiB/s in a 10-second interval and at least 10 times more
+ * in write direction than in read direction, or -1 if no statistics on
+ * bi-directional connection usage are included. */
+ public int getConnBiDirectWrite();
+
+ /* Return the number of connections on which this relay read and wrote
+ * at least 2 KiB/s in a 10-second interval but not 10 times more in
+ * either direction, or -1 if no statistics on bi-directional connection
+ * usage are included. */
+ public int getConnBiDirectBoth();
+
+ /* Return the end of the included exit statistics interval, or -1 if no
+ * exit statistics are included. */
+ public long getExitStatsEndMillis();
+
+ /* Return the interval length of the included exit statistics, or -1 if
+ * no exit statistics are included. */
+ public long getExitStatsIntervalLength();
+
+ /* Return statistics on KiB written by port with map keys being ports
+ * and map values being KiB rounded up to the next full KiB, or null if
+ * no exit statistics are included. */
+ public SortedMap<Integer, Integer> getExitKibibytesWritten();
+
+ /* Return statistics on KiB read by port with map keys being ports and
+ * map values being KiB rounded up to the next full KiB, or null if no
+ * exit statistics are included. */
+ public SortedMap<Integer, Integer> getExitKibibytesRead();
+
+ /* Return statistics on opened exit streams with map keys being ports
+ * and map values being the number of opened streams, rounded up to the
+ * nearest multiple of 4, or null if no exit statistics are included. */
+ public SortedMap<Integer, Integer> getExitStreamsOpened();
+}
+
diff --git a/src/org/torproject/descriptor/RelayExtraInfoDescriptor.java b/src/org/torproject/descriptor/RelayExtraInfoDescriptor.java
deleted file mode 100644
index 853a60a..0000000
--- a/src/org/torproject/descriptor/RelayExtraInfoDescriptor.java
+++ /dev/null
@@ -1,211 +0,0 @@
-/* Copyright 2012 The Tor Project
- * See LICENSE for licensing information */
-package org.torproject.descriptor;
-
-import java.util.List;
-import java.util.SortedMap;
-
-public interface RelayExtraInfoDescriptor extends Descriptor {
-
- /* Return the relay's nickname. */
- public String getNickname();
-
- /* Return the relay's fingerprint. */
- public String getFingerprint();
-
- /* Return the publication time of this descriptor. */
- public long getPublishedMillis();
-
- /* Return the read history contained in this descriptor, or null if no
- * read history is contained. */
- public BandwidthHistory getReadHistory();
-
- /* Return the write history contained in this descriptor, or null if no
- * read history is contained. */
- public BandwidthHistory getWriteHistory();
-
- /* Return the SHA1 digest of the GeoIP database used by this relay, or
- * null if no GeoIP database digest is included. */
- public String getGeoipDbDigest();
-
- /* Return the end of the included directory request statistics interval,
- * or -1 if no directory request statistics are included. */
- public long getDirreqStatsEndMillis();
-
- /* Return the interval length of the included directory request
- * statistics, or -1 if no directory request statistics are included. */
- public long getDirreqStatsIntervalLength();
-
- /* Return statistics on unique IP addresses requesting v2 network
- * statuses with map keys being country codes and map values being
- * numbers of unique IP addresses rounded up to the nearest multiple of
- * 8, or null if no such statistics are included. */
- public SortedMap<String, Integer> getDirreqV2Ips();
-
- /* Return statistics on unique IP addresses requesting v3 network status
- * consensuses with map keys being country codes and map values being
- * numbers of unique IP addresses rounded up to the nearest multiple of
- * 8, or null if no such statistics are included. */
- public SortedMap<String, Integer> getDirreqV3Ips();
-
- /* Return statistics on directory requests for v2 network statuses with
- * map keys being country codes and map values being request numbers
- * rounded up to the nearest multiple of 8, or null if no such
- * statistics are included. */
- public SortedMap<String, Integer> getDirreqV2Reqs();
-
- /* Return statistics on directory requests for v3 network status
- * consensuses with map keys being country codes and map values being
- * request numbers rounded up to the nearest multiple of 8, or null if
- * no such statistics are included. */
- public SortedMap<String, Integer> getDirreqV3Reqs();
-
- /* Return the share of requests for v2 network statuses that the
- * directory expects to receive from clients, or -1.0 if no such
- * statistics are included. */
- public double getDirreqV2Share();
-
- /* Return the share of requests for v3 network status consensuses that
- * the directory expects to receive from clients, or -1.0 if no such
- * statistics are included. */
- public double getDirreqV3Share();
-
- /* Return statistics on directory request responses for v2 network
- * statuses with map keys being response strings and map values being
- * response numbers rounded up to the nearest multiple of 4, or null if
- * no such statistics are included. */
- public SortedMap<String, Integer> getDirreqV2Resp();
-
- /* Return statistics on directory request responses for v3 network
- * status consensuses with map keys being response strings and map
- * values being response numbers rounded up to the nearest multiple of
- * 4, or null if no such statistics are included. */
- public SortedMap<String, Integer> getDirreqV3Resp();
-
- /* Return statistics on direct directory requests asking for v2 network
- * statuses with map keys being statistic keys and map values being
- * statistic values, or null if no such statistics are included. */
- public SortedMap<String, Integer> getDirreqV2DirectDl();
-
- /* Return statistics on direct directory requests asking for v3 network
- * status consensuses with map keys being statistic keys and map
- * values being statistic values, or null if no such statistics are
- * included. */
- public SortedMap<String, Integer> getDirreqV3DirectDl();
-
- /* Return statistics on tunneled directory requests asking for v2
- * network statuses with map keys being statistic keys and map values
- * being statistic values, or null if no such statistics are
- * included. */
- public SortedMap<String, Integer> getDirreqV2TunneledDl();
-
- /* Return statistics on tunneled directory requests asking for v3
- * network status consensuses with map keys being statistic keys and map
- * values being statistic values, or null if no such statistics are
- * included. */
- public SortedMap<String, Integer> getDirreqV3TunneledDl();
-
- /* Return the directory request read history contained in this
- * descriptor, or null if no directory request read history is
- * contained. */
- public BandwidthHistory getDirreqReadHistory();
-
- /* Return the directory request write history contained in this
- * descriptor, or null if no directory request write history is
- * contained. */
- public BandwidthHistory getDirreqWriteHistory();
-
- /* Return the end of the included entry statistics interval, or -1 if no
- * entry statistics are included. */
- public long getEntryStatsEndMillis();
-
- /* Return the interval length of the included entry statistics, or -1 if
- * no entry statistics are included. */
- public long getEntryStatsIntervalLength();
-
- /* Return statistics on client IP addresses with map keys being country
- * codes and map values being the number of unique IP addresses that
- * have connected from that country rounded up to the nearest multiple
- * of 8, or null if no entry statistics are included. */
- public SortedMap<String, Integer> getEntryIps();
-
- /* Return the end of the included cell statistics interval, or -1 if no
- * cell statistics are included. */
- public long getCellStatsEndMillis();
-
- /* Return the interval length of the included cell statistics, or -1 if
- * no cell statistics are included. */
- public long getCellStatsIntervalLength();
-
- /* Return the mean number of processed cells per circuit by circuit
- * deciles. */
- public List<Integer> getCellProcessedCells();
-
- /* Return the mean number of cells contained in circuit queues by
- * circuit deciles. */
- public List<Integer> getCellQueueCells();
-
- /* Return the mean times in milliseconds that cells spend in circuit
- * queues by circuit deciles. */
- public List<Integer> getCellTimeInQueue();
-
- /* Return the mean number of circuits included in any of the cell
- * statistics deciles, or -1 if no cell statistics are included. */
- public int getCellCircuitsPerDecile();
-
- /* Return the end of the included statistics interval on bi-directional
- * connection usage, or -1 if no such statistics are included. */
- public long getConnBiDirectStatsEndMillis();
-
- /* Return the interval length of the included statistics on
- * bi-directional connection usage, or -1 if no such statistics are
- * included. */
- public long getConnBiDirectIntervalLength();
-
- /* Return the number of connections on which this relay read and wrote
- * less than 2 KiB/s in a 10-second interval, or -1 if no statistics on
- * bi-directional connection usage are included. */
- public int getConnBiDirectBelow();
-
- /* Return the number of connections on which this relay read and wrote
- * at least 2 KiB/s in a 10-second interval and at least 10 times more
- * in read direction than in write direction, or -1 if no statistics on
- * bi-directional connection usage are included. */
- public int getConnBiDirectRead();
-
- /* Return the number of connections on which this relay read and wrote
- * at least 2 KiB/s in a 10-second interval and at least 10 times more
- * in write direction than in read direction, or -1 if no statistics on
- * bi-directional connection usage are included. */
- public int getConnBiDirectWrite();
-
- /* Return the number of connections on which this relay read and wrote
- * at least 2 KiB/s in a 10-second interval but not 10 times more in
- * either direction, or -1 if no statistics on bi-directional connection
- * usage are included. */
- public int getConnBiDirectBoth();
-
- /* Return the end of the included exit statistics interval, or -1 if no
- * exit statistics are included. */
- public long getExitStatsEndMillis();
-
- /* Return the interval length of the included exit statistics, or -1 if
- * no exit statistics are included. */
- public long getExitStatsIntervalLength();
-
- /* Return statistics on KiB written by port with map keys being ports
- * and map values being KiB rounded up to the next full KiB, or null if
- * no exit statistics are included. */
- public SortedMap<Integer, Integer> getExitKibibytesWritten();
-
- /* Return statistics on KiB read by port with map keys being ports and
- * map values being KiB rounded up to the next full KiB, or null if no
- * exit statistics are included. */
- public SortedMap<Integer, Integer> getExitKibibytesRead();
-
- /* Return statistics on opened exit streams with map keys being ports
- * and map values being the number of opened streams, rounded up to the
- * nearest multiple of 4, or null if no exit statistics are included. */
- public SortedMap<Integer, Integer> getExitStreamsOpened();
-}
-
diff --git a/src/org/torproject/descriptor/RelayServerDescriptor.java b/src/org/torproject/descriptor/RelayServerDescriptor.java
deleted file mode 100644
index 2f48def..0000000
--- a/src/org/torproject/descriptor/RelayServerDescriptor.java
+++ /dev/null
@@ -1,110 +0,0 @@
-/* Copyright 2011, 2012 The Tor Project
- * See LICENSE for licensing information */
-package org.torproject.descriptor;
-
-import java.util.List;
-
-/* Contains a relay server descriptor. */
-public interface RelayServerDescriptor extends Descriptor {
-
- /* Return the relay's nickname. */
- public String getNickname();
-
- /* Return the relay's IPv4 address in dotted-quad format. */
- public String getAddress();
-
- /* Return the relay's OR port. */
- public int getOrPort();
-
- /* Return the relay's SOCKS port which should always be 0. */
- public int getSocksPort();
-
- /* Return the relay's directory port. */
- public int getDirPort();
-
- /* Return the average bandwidth in bytes per second that the relay is
- * willing to sustain over long periods. */
- public int getBandwidthRate();
-
- /* Return the burst bandwidth in bytes per second that the relay is
- * willing to sustain in very short intervals. */
- public int getBandwidthBurst();
-
- /* Return the observed bandwidth in bytes per second as an estimate of
- * the capacity that the relay can handle. */
- public int getBandwidthObserved();
-
- /* Return the platform string containing the Tor software version and
- * the operating system. */
- public String getPlatform();
-
- /* Return the time when this descriptor and the corresponding extra-info
- * document was generated. */
- public long getPublishedMillis();
-
- /* Return the relay fingerprint, or null if this descriptor does not
- * contain a fingerprint line. */
- public String getFingerprint();
-
- /* Return whether the relay was hibernating when this descriptor was
- * published. */
- public boolean isHibernating();
-
- /* Return the number of seconds that this relay has been running, or -1
- * if the descriptor does not contain an uptime line. */
- public int getUptime();
-
- /* Return the relay's exit policy consisting of one or more accept or
- * reject lines. */
- public List<String> getExitPolicyLines();
-
- /* Return the contact information for this relay, or null if no contact
- * information is included in the descriptor. */
- public String getContact();
-
- /* Return the nicknames or ($-prefixed) fingerprints contained in the
- * family line of this relay, or null if the descriptor does not contain
- * a family line. */
- public List<String> getFamilyEntries();
-
- /* Return the relay's read history. (Current Tor versions include their
- * bandwidth histories in their extra-info descriptors, not in their
- * server descriptors.) */
- public BandwidthHistory getReadHistory();
-
- /* Return the relay's write history. (Current Tor versions include
- * their bandwidth histories in their extra-info descriptors, not in
- * their server descriptors.) */
- public BandwidthHistory getWriteHistory();
-
- /* Return true if the relay uses the enhanced DNS logic, or false if
- * doesn't use it or doesn't include an eventdns line in its
- * descriptor. */
- public boolean getUsesEnhancedDnsLogic();
-
- /* Return whether this relay is a directory cache that provides
- * extra-info descriptors. */
- public boolean getCachesExtraInfo();
-
- /* Return the digest of the relay's extra-info descriptor, or null if
- * the relay did not upload a corresponding extra-info descriptor. */
- public String getExtraInfoDigest();
-
- /* Return the hidden service descriptor version(s) that this relay
- * stores and serves, or null if it doesn't store and serve any hidden
- * service descriptors. */
- public List<Integer> getHiddenServiceDirVersions();
-
- /* Return the list of link protocol versions that this relay
- * supports. */
- public List<Integer> getLinkProtocolVersions();
-
- /* Return the list of circuit protocol versions that this relay
- * supports. */
- public List<Integer> getCircuitProtocolVersions();
-
- /* Return whether this relay allows single-hop circuits to make exit
- * connections. */
- public boolean getAllowSingleHopExits();
-}
-
diff --git a/src/org/torproject/descriptor/ServerDescriptor.java b/src/org/torproject/descriptor/ServerDescriptor.java
new file mode 100644
index 0000000..98a0f02
--- /dev/null
+++ b/src/org/torproject/descriptor/ServerDescriptor.java
@@ -0,0 +1,110 @@
+/* Copyright 2011, 2012 The Tor Project
+ * See LICENSE for licensing information */
+package org.torproject.descriptor;
+
+import java.util.List;
+
+/* Contains a relay server descriptor. */
+public interface ServerDescriptor extends Descriptor {
+
+ /* Return the relay's nickname. */
+ public String getNickname();
+
+ /* Return the relay's IPv4 address in dotted-quad format. */
+ public String getAddress();
+
+ /* Return the relay's OR port. */
+ public int getOrPort();
+
+ /* Return the relay's SOCKS port which should always be 0. */
+ public int getSocksPort();
+
+ /* Return the relay's directory port. */
+ public int getDirPort();
+
+ /* Return the average bandwidth in bytes per second that the relay is
+ * willing to sustain over long periods. */
+ public int getBandwidthRate();
+
+ /* Return the burst bandwidth in bytes per second that the relay is
+ * willing to sustain in very short intervals. */
+ public int getBandwidthBurst();
+
+ /* Return the observed bandwidth in bytes per second as an estimate of
+ * the capacity that the relay can handle. */
+ public int getBandwidthObserved();
+
+ /* Return the platform string containing the Tor software version and
+ * the operating system. */
+ public String getPlatform();
+
+ /* Return the time when this descriptor and the corresponding extra-info
+ * document was generated. */
+ public long getPublishedMillis();
+
+ /* Return the relay fingerprint, or null if this descriptor does not
+ * contain a fingerprint line. */
+ public String getFingerprint();
+
+ /* Return whether the relay was hibernating when this descriptor was
+ * published. */
+ public boolean isHibernating();
+
+ /* Return the number of seconds that this relay has been running, or -1
+ * if the descriptor does not contain an uptime line. */
+ public int getUptime();
+
+ /* Return the relay's exit policy consisting of one or more accept or
+ * reject lines. */
+ public List<String> getExitPolicyLines();
+
+ /* Return the contact information for this relay, or null if no contact
+ * information is included in the descriptor. */
+ public String getContact();
+
+ /* Return the nicknames or ($-prefixed) fingerprints contained in the
+ * family line of this relay, or null if the descriptor does not contain
+ * a family line. */
+ public List<String> getFamilyEntries();
+
+ /* Return the relay's read history. (Current Tor versions include their
+ * bandwidth histories in their extra-info descriptors, not in their
+ * server descriptors.) */
+ public BandwidthHistory getReadHistory();
+
+ /* Return the relay's write history. (Current Tor versions include
+ * their bandwidth histories in their extra-info descriptors, not in
+ * their server descriptors.) */
+ public BandwidthHistory getWriteHistory();
+
+ /* Return true if the relay uses the enhanced DNS logic, or false if
+ * doesn't use it or doesn't include an eventdns line in its
+ * descriptor. */
+ public boolean getUsesEnhancedDnsLogic();
+
+ /* Return whether this relay is a directory cache that provides
+ * extra-info descriptors. */
+ public boolean getCachesExtraInfo();
+
+ /* Return the digest of the relay's extra-info descriptor, or null if
+ * the relay did not upload a corresponding extra-info descriptor. */
+ public String getExtraInfoDigest();
+
+ /* Return the hidden service descriptor version(s) that this relay
+ * stores and serves, or null if it doesn't store and serve any hidden
+ * service descriptors. */
+ public List<Integer> getHiddenServiceDirVersions();
+
+ /* Return the list of link protocol versions that this relay
+ * supports. */
+ public List<Integer> getLinkProtocolVersions();
+
+ /* Return the list of circuit protocol versions that this relay
+ * supports. */
+ public List<Integer> getCircuitProtocolVersions();
+
+ /* Return whether this relay allows single-hop circuits to make exit
+ * connections. */
+ public boolean getAllowSingleHopExits();
+}
+
diff --git a/src/org/torproject/descriptor/impl/DescriptorImpl.java b/src/org/torproject/descriptor/impl/DescriptorImpl.java
index 24c1fe9..259a1de 100644
--- a/src/org/torproject/descriptor/impl/DescriptorImpl.java
+++ b/src/org/torproject/descriptor/impl/DescriptorImpl.java
@@ -37,11 +37,11 @@ public abstract class DescriptorImpl implements Descriptor {
}
} else if (firstLines.startsWith("router ") ||
firstLines.contains("\nrouter ")) {
- parsedDescriptors.addAll(RelayServerDescriptorImpl.
+ parsedDescriptors.addAll(ServerDescriptorImpl.
parseDescriptors(rawDescriptorBytes));
} else if (firstLines.startsWith("extra-info ") ||
firstLines.contains("\nextra-info ")) {
- parsedDescriptors.addAll(RelayExtraInfoDescriptorImpl.
+ parsedDescriptors.addAll(ExtraInfoDescriptorImpl.
parseDescriptors(rawDescriptorBytes));
} else {
throw new DescriptorParseException("Could not detect relay "
diff --git a/src/org/torproject/descriptor/impl/ExtraInfoDescriptorImpl.java b/src/org/torproject/descriptor/impl/ExtraInfoDescriptorImpl.java
new file mode 100644
index 0000000..6dae9eb
--- /dev/null
+++ b/src/org/torproject/descriptor/impl/ExtraInfoDescriptorImpl.java
@@ -0,0 +1,574 @@
+/* Copyright 2012 The Tor Project
+ * See LICENSE for licensing information */
+package org.torproject.descriptor.impl;
+
+import java.io.BufferedReader;
+import java.io.IOException;
+import java.io.StringReader;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+import java.util.SortedMap;
+import org.torproject.descriptor.ExtraInfoDescriptor;
+import org.torproject.descriptor.BandwidthHistory;
+
+/* TODO Implement methods to parse the various statistics (other than
+ * bandwidth histories. */
+/* TODO Write a test class. */
+public class ExtraInfoDescriptorImpl extends DescriptorImpl
+ implements ExtraInfoDescriptor {
+
+ protected static List<ExtraInfoDescriptor> parseDescriptors(
+ byte[] descriptorsBytes) {
+ List<ExtraInfoDescriptor> parsedDescriptors =
+ new ArrayList<ExtraInfoDescriptor>();
+ List<byte[]> splitDescriptorsBytes =
+ DescriptorImpl.splitRawDescriptorBytes(descriptorsBytes,
+ "extra-info ");
+ try {
+ for (byte[] descriptorBytes : splitDescriptorsBytes) {
+ ExtraInfoDescriptor parsedDescriptor =
+ new ExtraInfoDescriptorImpl(descriptorBytes);
+ parsedDescriptors.add(parsedDescriptor);
+ }
+ } catch (DescriptorParseException e) {
+ /* TODO Handle this error somehow. */
+ System.err.println("Failed to parse descriptor. Skipping.");
+ e.printStackTrace();
+ }
+ return parsedDescriptors;
+ }
+
+ protected ExtraInfoDescriptorImpl(byte[] descriptorBytes)
+ throws DescriptorParseException {
+ super(descriptorBytes);
+ this.parseDescriptorBytes();
+ Set<String> exactlyOnceKeywords = new HashSet<String>(Arrays.asList((
+ "extra-info,published,router-signature").split(",")));
+ this.checkExactlyOnceKeywords(exactlyOnceKeywords);
+ Set<String> atMostOnceKeywords = new HashSet<String>(Arrays.asList((
+ "read-history,write-history,geoip-db-digest,dirreq-stats-end,"
+ + "dirreq-v2-ips,dirreq-v3-ips,dirreq-v2-reqs,dirreq-v3-reqs,"
+ + "dirreq-v2-share,dirreq-v3-share,dirreq-v2-resp,dirreq-v3-resp,"
+ + "dirreq-v2-direct-dl,dirreq-v3-direct-dl,dirreq-v2-tunneled-dl,"
+ + "dirreq-v3-tunneled-dl,dirreq-read-history,"
+ + "dirreq-write-history,entry-stats-end,entry-ips,cell-stats-end,"
+ + "cell-processed-cells,cell-queued-cells,cell-time-in-queue,"
+ + "cell-circuits-per-decile,conn-bi-direct,exit-stats-end,"
+ + "exit-kibibytes-written,exit-kibibytes-read,"
+ + "exit-streams-opened").split(",")));
+ this.checkAtMostOnceKeywords(atMostOnceKeywords);
+ /* TODO Add more checks to see that only statistics details lines are
+ * included with corresponding statistics interval lines. */
+ this.checkFirstKeyword("extra-info");
+ this.checkLastKeyword("router-signature");
+ return;
+ }
+
+ private void parseDescriptorBytes() throws DescriptorParseException {
+ try {
+ BufferedReader br = new BufferedReader(new StringReader(
+ new String(this.rawDescriptorBytes)));
+ String line;
+ boolean skipCrypto = false;
+ while ((line = br.readLine()) != null) {
+ String lineNoOpt = line.startsWith("opt ") ?
+ line.substring("opt ".length()) : line;
+ String[] partsNoOpt = lineNoOpt.split(" ");
+ String keyword = partsNoOpt[0];
+ if (keyword.equals("extra-info")) {
+ this.parseExtraInfoLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("published")) {
+ this.parsePublishedLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("read-history")) {
+ this.parseReadHistoryLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("write-history")) {
+ this.parseWriteHistoryLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("geoip-db-digest")) {
+ this.parseGeoipDbDigestLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("geoip-start-time")) {
+ this.parseGeoipStartTimeLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("geoip-client-origins")) {
+ this.parseGeoipClientOriginsLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-stats-end")) {
+ this.parseDirreqStatsEndLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-v2-ips")) {
+ this.parseDirreqV2IpsLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-v3-ips")) {
+ this.parseDirreqV3IpsLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-v2-reqs")) {
+ this.parseDirreqV2ReqsLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-v3-reqs")) {
+ this.parseDirreqV3ReqsLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-v2-share")) {
+ this.parseDirreqV2ShareLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-v3-share")) {
+ this.parseDirreqV3ShareLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-v2-resp")) {
+ this.parseDirreqV2RespLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-v3-resp")) {
+ this.parseDirreqV3RespLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-v2-direct-dl")) {
+ this.parseDirreqV2DirectDlLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-v3-direct-dl")) {
+ this.parseDirreqV3DirectDlLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-v2-tunneled-dl")) {
+ this.parseDirreqV2TunneledDlLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-v3-tunneled-dl")) {
+ this.parseDirreqV3TunneledDlLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-read-history")) {
+ this.parseDirreqReadHistoryLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("dirreq-write-history")) {
+ this.parseDirreqWriteHistoryLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("entry-stats-end")) {
+ this.parseEntryStatsEndLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("entry-ips")) {
+ this.parseEntryIpsLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("cell-stats-end")) {
+ this.parseCellStatsEndLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("cell-processed-cells")) {
+ this.parseCellProcessedCellsLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("cell-queued-cells")) {
+ this.parseCellQueuedCellsLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("cell-time-in-queue")) {
+ this.parseCellTimeInQueueLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("cell-circuits-per-decile")) {
+ this.parseCellCircuitsPerDecileLine(line, lineNoOpt,
+ partsNoOpt);
+ } else if (keyword.equals("conn-bi-direct")) {
+ this.parseConnBiDirectLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("exit-stats-end")) {
+ this.parseExitStatsEndLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("exit-kibibytes-written")) {
+ this.parseExitKibibytesWrittenLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("exit-kibibytes-read")) {
+ this.parseExitKibibytesReadLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("exit-streams-opened")) {
+ this.parseExitStreamsOpenedLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("router-signature")) {
+ this.parseRouterSignatureLine(line, lineNoOpt, partsNoOpt);
+ } else if (line.startsWith("-----BEGIN")) {
+ skipCrypto = true;
+ } else if (line.startsWith("-----END")) {
+ skipCrypto = false;
+ } else if (!skipCrypto) {
+ /* TODO Is throwing an exception the right thing to do here?
+ * This is probably fine for development, but once the library
+ * is in production use, this seems annoying. In theory,
+ * dir-spec.txt says that unknown lines should be ignored. This
+ * also applies to the other descriptors. */
+ throw new DescriptorParseException("Unrecognized line '" + line
+ + "'.");
+ }
+ }
+ } catch (IOException e) {
+ throw new RuntimeException("Internal error: Ran into an "
+ + "IOException while parsing a String in memory. Something's "
+ + "really wrong.", e);
+ }
+ }
+
+ private void parseExtraInfoLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (partsNoOpt.length != 3) {
+ throw new DescriptorParseException("Illegal line '" + line
+ + "' in extra-info descriptor.");
+ }
+ this.nickname = ParseHelper.parseNickname(line, partsNoOpt[1]);
+ this.fingerprint = ParseHelper.parseTwentyByteHexString(line,
+ partsNoOpt[2]);
+ }
+
+ private void parsePublishedLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ this.publishedMillis = ParseHelper.parseTimestampAtIndex(line,
+ partsNoOpt, 1, 2);
+ }
+
+ private void parseReadHistoryLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ this.readHistory = new BandwidthHistoryImpl(line, lineNoOpt,
+ partsNoOpt);
+ }
+
+ private void parseWriteHistoryLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ this.writeHistory = new BandwidthHistoryImpl(line, lineNoOpt,
+ partsNoOpt);
+ }
+
+ private void parseGeoipDbDigestLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseGeoipStartTimeLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseGeoipClientOriginsLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqStatsEndLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqV2IpsLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqV3IpsLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqV2ReqsLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqV3ReqsLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqV2ShareLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqV3ShareLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqV2RespLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqV3RespLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqV2DirectDlLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqV3DirectDlLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqV2TunneledDlLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqV3TunneledDlLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseDirreqReadHistoryLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ this.dirreqReadHistory = new BandwidthHistoryImpl(line, lineNoOpt,
+ partsNoOpt);
+ }
+
+ private void parseDirreqWriteHistoryLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ this.dirreqWriteHistory = new BandwidthHistoryImpl(line, lineNoOpt,
+ partsNoOpt);
+ }
+
+ private void parseEntryStatsEndLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseEntryIpsLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseCellStatsEndLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseCellProcessedCellsLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseCellQueuedCellsLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseCellTimeInQueueLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseCellCircuitsPerDecileLine(String line,
+ String lineNoOpt, String[] partsNoOpt)
+ throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseConnBiDirectLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseExitStatsEndLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseExitKibibytesWrittenLine(String line,
+ String lineNoOpt, String[] partsNoOpt)
+ throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseExitKibibytesReadLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseExitStreamsOpenedLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseRouterSignatureLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (!lineNoOpt.equals("router-signature")) {
+ throw new DescriptorParseException("Illegal line '" + line + "'.");
+ }
+ /* Not parsing crypto parts (yet). */
+ }
+
+ private String nickname;
+ public String getNickname() {
+ return this.nickname;
+ }
+
+ private String fingerprint;
+ public String getFingerprint() {
+ return this.fingerprint;
+ }
+
+ private long publishedMillis;
+ public long getPublishedMillis() {
+ return this.publishedMillis;
+ }
+
+ private BandwidthHistory readHistory;
+ public BandwidthHistory getReadHistory() {
+ return this.readHistory;
+ }
+
+ private BandwidthHistory writeHistory;
+ public BandwidthHistory getWriteHistory() {
+ return this.writeHistory;
+ }
+
+ public String getGeoipDbDigest() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public long getDirreqStatsEndMillis() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public long getDirreqStatsIntervalLength() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<String, Integer> getDirreqV2Ips() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<String, Integer> getDirreqV3Ips() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<String, Integer> getDirreqV2Reqs() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<String, Integer> getDirreqV3Reqs() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public double getDirreqV2Share() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public double getDirreqV3Share() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<String, Integer> getDirreqV2Resp() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<String, Integer> getDirreqV3Resp() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<String, Integer> getDirreqV2DirectDl() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<String, Integer> getDirreqV3DirectDl() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<String, Integer> getDirreqV2TunneledDl() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<String, Integer> getDirreqV3TunneledDl() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ private BandwidthHistory dirreqReadHistory;
+ public BandwidthHistory getDirreqReadHistory() {
+ return this.dirreqReadHistory;
+ }
+
+ private BandwidthHistory dirreqWriteHistory;
+ public BandwidthHistory getDirreqWriteHistory() {
+ return this.dirreqWriteHistory;
+ }
+
+ public long getEntryStatsEndMillis() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public long getEntryStatsIntervalLength() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<String, Integer> getEntryIps() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public long getCellStatsEndMillis() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public long getCellStatsIntervalLength() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public List<Integer> getCellProcessedCells() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public List<Integer> getCellQueueCells() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public List<Integer> getCellTimeInQueue() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public int getCellCircuitsPerDecile() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public long getConnBiDirectStatsEndMillis() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public long getConnBiDirectIntervalLength() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public int getConnBiDirectBelow() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public int getConnBiDirectRead() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public int getConnBiDirectWrite() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public int getConnBiDirectBoth() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public long getExitStatsEndMillis() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public long getExitStatsIntervalLength() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<Integer, Integer> getExitKibibytesWritten() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<Integer, Integer> getExitKibibytesRead() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+
+ public SortedMap<Integer, Integer> getExitStreamsOpened() {
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException();
+ }
+}
+
diff --git a/src/org/torproject/descriptor/impl/RelayExtraInfoDescriptorImpl.java b/src/org/torproject/descriptor/impl/RelayExtraInfoDescriptorImpl.java
deleted file mode 100644
index a07caec..0000000
--- a/src/org/torproject/descriptor/impl/RelayExtraInfoDescriptorImpl.java
+++ /dev/null
@@ -1,574 +0,0 @@
-/* Copyright 2012 The Tor Project
- * See LICENSE for licensing information */
-package org.torproject.descriptor.impl;
-
-import java.io.BufferedReader;
-import java.io.IOException;
-import java.io.StringReader;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
-import java.util.SortedMap;
-import org.torproject.descriptor.RelayExtraInfoDescriptor;
-import org.torproject.descriptor.BandwidthHistory;
-
-/* TODO Implement methods to parse the various statistics (other than
- * bandwidth histories. */
-/* TODO Write a test class. */
-public class RelayExtraInfoDescriptorImpl extends DescriptorImpl
- implements RelayExtraInfoDescriptor {
-
- protected static List<RelayExtraInfoDescriptor> parseDescriptors(
- byte[] descriptorsBytes) {
- List<RelayExtraInfoDescriptor> parsedDescriptors =
- new ArrayList<RelayExtraInfoDescriptor>();
- List<byte[]> splitDescriptorsBytes =
- DescriptorImpl.splitRawDescriptorBytes(descriptorsBytes,
- "extra-info ");
- try {
- for (byte[] descriptorBytes : splitDescriptorsBytes) {
- RelayExtraInfoDescriptor parsedDescriptor =
- new RelayExtraInfoDescriptorImpl(descriptorBytes);
- parsedDescriptors.add(parsedDescriptor);
- }
- } catch (DescriptorParseException e) {
- /* TODO Handle this error somehow. */
- System.err.println("Failed to parse descriptor. Skipping.");
- e.printStackTrace();
- }
- return parsedDescriptors;
- }
-
- protected RelayExtraInfoDescriptorImpl(byte[] descriptorBytes)
- throws DescriptorParseException {
- super(descriptorBytes);
- this.parseDescriptorBytes();
- Set<String> exactlyOnceKeywords = new HashSet<String>(Arrays.asList((
- "extra-info,published,router-signature").split(",")));
- this.checkExactlyOnceKeywords(exactlyOnceKeywords);
- Set<String> atMostOnceKeywords = new HashSet<String>(Arrays.asList((
- "read-history,write-history,geoip-db-digest,dirreq-stats-end,"
- + "dirreq-v2-ips,dirreq-v3-ips,dirreq-v2-reqs,dirreq-v3-reqs,"
- + "dirreq-v2-share,dirreq-v3-share,dirreq-v2-resp,dirreq-v3-resp,"
- + "dirreq-v2-direct-dl,dirreq-v3-direct-dl,dirreq-v2-tunneled-dl,"
- + "dirreq-v3-tunneled-dl,dirreq-read-history,"
- + "dirreq-write-history,entry-stats-end,entry-ips,cell-stats-end,"
- + "cell-processed-cells,cell-queued-cells,cell-time-in-queue,"
- + "cell-circuits-per-decile,conn-bi-direct,exit-stats-end,"
- + "exit-kibibytes-written,exit-kibibytes-read,"
- + "exit-streams-opened").split(",")));
- this.checkAtMostOnceKeywords(atMostOnceKeywords);
- /* TODO Add more checks to see that only statistics details lines are
- * included with corresponding statistics interval lines. */
- this.checkFirstKeyword("extra-info");
- this.checkLastKeyword("router-signature");
- return;
- }
-
- private void parseDescriptorBytes() throws DescriptorParseException {
- try {
- BufferedReader br = new BufferedReader(new StringReader(
- new String(this.rawDescriptorBytes)));
- String line;
- boolean skipCrypto = false;
- while ((line = br.readLine()) != null) {
- String lineNoOpt = line.startsWith("opt ") ?
- line.substring("opt ".length()) : line;
- String[] partsNoOpt = lineNoOpt.split(" ");
- String keyword = partsNoOpt[0];
- if (keyword.equals("extra-info")) {
- this.parseExtraInfoLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("published")) {
- this.parsePublishedLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("read-history")) {
- this.parseReadHistoryLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("write-history")) {
- this.parseWriteHistoryLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("geoip-db-digest")) {
- this.parseGeoipDbDigestLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("geoip-start-time")) {
- this.parseGeoipStartTimeLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("geoip-client-origins")) {
- this.parseGeoipClientOriginsLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-stats-end")) {
- this.parseDirreqStatsEndLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-v2-ips")) {
- this.parseDirreqV2IpsLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-v3-ips")) {
- this.parseDirreqV3IpsLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-v2-reqs")) {
- this.parseDirreqV2ReqsLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-v3-reqs")) {
- this.parseDirreqV3ReqsLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-v2-share")) {
- this.parseDirreqV2ShareLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-v3-share")) {
- this.parseDirreqV3ShareLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-v2-resp")) {
- this.parseDirreqV2RespLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-v3-resp")) {
- this.parseDirreqV3RespLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-v2-direct-dl")) {
- this.parseDirreqV2DirectDlLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-v3-direct-dl")) {
- this.parseDirreqV3DirectDlLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-v2-tunneled-dl")) {
- this.parseDirreqV2TunneledDlLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-v3-tunneled-dl")) {
- this.parseDirreqV3TunneledDlLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-read-history")) {
- this.parseDirreqReadHistoryLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("dirreq-write-history")) {
- this.parseDirreqWriteHistoryLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("entry-stats-end")) {
- this.parseEntryStatsEndLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("entry-ips")) {
- this.parseEntryIpsLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("cell-stats-end")) {
- this.parseCellStatsEndLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("cell-processed-cells")) {
- this.parseCellProcessedCellsLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("cell-queued-cells")) {
- this.parseCellQueuedCellsLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("cell-time-in-queue")) {
- this.parseCellTimeInQueueLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("cell-circuits-per-decile")) {
- this.parseCellCircuitsPerDecileLine(line, lineNoOpt,
- partsNoOpt);
- } else if (keyword.equals("conn-bi-direct")) {
- this.parseConnBiDirectLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("exit-stats-end")) {
- this.parseExitStatsEndLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("exit-kibibytes-written")) {
- this.parseExitKibibytesWrittenLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("exit-kibibytes-read")) {
- this.parseExitKibibytesReadLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("exit-streams-opened")) {
- this.parseExitStreamsOpenedLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("router-signature")) {
- this.parseRouterSignatureLine(line, lineNoOpt, partsNoOpt);
- } else if (line.startsWith("-----BEGIN")) {
- skipCrypto = true;
- } else if (line.startsWith("-----END")) {
- skipCrypto = false;
- } else if (!skipCrypto) {
- /* TODO Is throwing an exception the right thing to do here?
- * This is probably fine for development, but once the library
- * is in production use, this seems annoying. In theory,
- * dir-spec.txt says that unknown lines should be ignored. This
- * also applies to the other descriptors. */
- throw new DescriptorParseException("Unrecognized line '" + line
- + "'.");
- }
- }
- } catch (IOException e) {
- throw new RuntimeException("Internal error: Ran into an "
- + "IOException while parsing a String in memory. Something's "
- + "really wrong.", e);
- }
- }
-
- private void parseExtraInfoLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (partsNoOpt.length != 3) {
- throw new DescriptorParseException("Illegal line '" + line
- + "' in extra-info descriptor.");
- }
- this.nickname = ParseHelper.parseNickname(line, partsNoOpt[1]);
- this.fingerprint = ParseHelper.parseTwentyByteHexString(line,
- partsNoOpt[2]);
- }
-
- private void parsePublishedLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- this.publishedMillis = ParseHelper.parseTimestampAtIndex(line,
- partsNoOpt, 1, 2);
- }
-
- private void parseReadHistoryLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- this.readHistory = new BandwidthHistoryImpl(line, lineNoOpt,
- partsNoOpt);
- }
-
- private void parseWriteHistoryLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- this.writeHistory = new BandwidthHistoryImpl(line, lineNoOpt,
- partsNoOpt);
- }
-
- private void parseGeoipDbDigestLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseGeoipStartTimeLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseGeoipClientOriginsLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqStatsEndLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqV2IpsLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqV3IpsLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqV2ReqsLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqV3ReqsLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqV2ShareLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqV3ShareLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqV2RespLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqV3RespLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqV2DirectDlLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqV3DirectDlLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqV2TunneledDlLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqV3TunneledDlLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseDirreqReadHistoryLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- this.dirreqReadHistory = new BandwidthHistoryImpl(line, lineNoOpt,
- partsNoOpt);
- }
-
- private void parseDirreqWriteHistoryLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- this.dirreqWriteHistory = new BandwidthHistoryImpl(line, lineNoOpt,
- partsNoOpt);
- }
-
- private void parseEntryStatsEndLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseEntryIpsLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseCellStatsEndLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseCellProcessedCellsLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseCellQueuedCellsLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseCellTimeInQueueLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseCellCircuitsPerDecileLine(String line,
- String lineNoOpt, String[] partsNoOpt)
- throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseConnBiDirectLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseExitStatsEndLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseExitKibibytesWrittenLine(String line,
- String lineNoOpt, String[] partsNoOpt)
- throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseExitKibibytesReadLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseExitStreamsOpenedLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* TODO Implement me. */
- }
-
- private void parseRouterSignatureLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (!lineNoOpt.equals("router-signature")) {
- throw new DescriptorParseException("Illegal line '" + line + "'.");
- }
- /* Not parsing crypto parts (yet). */
- }
-
- private String nickname;
- public String getNickname() {
- return this.nickname;
- }
-
- private String fingerprint;
- public String getFingerprint() {
- return this.fingerprint;
- }
-
- private long publishedMillis;
- public long getPublishedMillis() {
- return this.publishedMillis;
- }
-
- private BandwidthHistory readHistory;
- public BandwidthHistory getReadHistory() {
- return this.readHistory;
- }
-
- private BandwidthHistory writeHistory;
- public BandwidthHistory getWriteHistory() {
- return this.writeHistory;
- }
-
- public String getGeoipDbDigest() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public long getDirreqStatsEndMillis() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public long getDirreqStatsIntervalLength() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<String, Integer> getDirreqV2Ips() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<String, Integer> getDirreqV3Ips() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<String, Integer> getDirreqV2Reqs() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<String, Integer> getDirreqV3Reqs() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public double getDirreqV2Share() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public double getDirreqV3Share() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<String, Integer> getDirreqV2Resp() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<String, Integer> getDirreqV3Resp() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<String, Integer> getDirreqV2DirectDl() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<String, Integer> getDirreqV3DirectDl() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<String, Integer> getDirreqV2TunneledDl() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<String, Integer> getDirreqV3TunneledDl() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- private BandwidthHistory dirreqReadHistory;
- public BandwidthHistory getDirreqReadHistory() {
- return this.dirreqReadHistory;
- }
-
- private BandwidthHistory dirreqWriteHistory;
- public BandwidthHistory getDirreqWriteHistory() {
- return this.dirreqWriteHistory;
- }
-
- public long getEntryStatsEndMillis() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public long getEntryStatsIntervalLength() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<String, Integer> getEntryIps() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public long getCellStatsEndMillis() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public long getCellStatsIntervalLength() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public List<Integer> getCellProcessedCells() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public List<Integer> getCellQueueCells() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public List<Integer> getCellTimeInQueue() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public int getCellCircuitsPerDecile() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public long getConnBiDirectStatsEndMillis() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public long getConnBiDirectIntervalLength() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public int getConnBiDirectBelow() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public int getConnBiDirectRead() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public int getConnBiDirectWrite() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public int getConnBiDirectBoth() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public long getExitStatsEndMillis() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public long getExitStatsIntervalLength() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<Integer, Integer> getExitKibibytesWritten() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<Integer, Integer> getExitKibibytesRead() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-
- public SortedMap<Integer, Integer> getExitStreamsOpened() {
- /* TODO Implement me. */
- throw new UnsupportedOperationException();
- }
-}
-
diff --git a/src/org/torproject/descriptor/impl/RelayServerDescriptorImpl.java b/src/org/torproject/descriptor/impl/RelayServerDescriptorImpl.java
deleted file mode 100644
index 472a2bc..0000000
--- a/src/org/torproject/descriptor/impl/RelayServerDescriptorImpl.java
+++ /dev/null
@@ -1,532 +0,0 @@
-/* Copyright 2012 The Tor Project
- * See LICENSE for licensing information */
-package org.torproject.descriptor.impl;
-
-import java.io.BufferedReader;
-import java.io.IOException;
-import java.io.StringReader;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
-import org.torproject.descriptor.RelayServerDescriptor;
-import org.torproject.descriptor.BandwidthHistory;
-
-/* Contains a relay server descriptor. */
-public class RelayServerDescriptorImpl extends DescriptorImpl
- implements RelayServerDescriptor {
-
- protected static List<RelayServerDescriptor> parseDescriptors(
- byte[] descriptorsBytes) {
- List<RelayServerDescriptor> parsedDescriptors =
- new ArrayList<RelayServerDescriptor>();
- List<byte[]> splitDescriptorsBytes =
- DescriptorImpl.splitRawDescriptorBytes(descriptorsBytes,
- "router ");
- try {
- for (byte[] descriptorBytes : splitDescriptorsBytes) {
- RelayServerDescriptor parsedDescriptor =
- new RelayServerDescriptorImpl(descriptorBytes);
- parsedDescriptors.add(parsedDescriptor);
- }
- } catch (DescriptorParseException e) {
- /* TODO Handle this error somehow. */
- System.err.println("Failed to parse descriptor. Skipping.");
- e.printStackTrace();
- }
- return parsedDescriptors;
- }
-
- protected RelayServerDescriptorImpl(byte[] descriptorBytes)
- throws DescriptorParseException {
- super(descriptorBytes);
- this.parseDescriptorBytes();
- Set<String> exactlyOnceKeywords = new HashSet<String>(Arrays.asList((
- "router,bandwidth,published,onion-key,signing-key,"
- + "router-signature").split(",")));
- this.checkExactlyOnceKeywords(exactlyOnceKeywords);
- Set<String> atMostOnceKeywords = new HashSet<String>(Arrays.asList((
- "platform,fingerprint,hibernating,uptime,contact,family,"
- + "read-history,write-history,eventdns,caches-extra-info,"
- + "extra-info-digest,hidden-service-dir,protocols,"
- + "allow-single-hop-exits").split(",")));
- this.checkAtMostOnceKeywords(atMostOnceKeywords);
- this.checkFirstKeyword("router");
- this.checkLastKeyword("router-signature");
- if (this.getKeywordCount("accept") == 0 &&
- this.getKeywordCount("reject") == 0) {
- throw new DescriptorParseException("Either keyword 'accept' or "
- + "'reject' must be contained at least once.");
- }
- return;
- }
-
- private void parseDescriptorBytes() throws DescriptorParseException {
- try {
- BufferedReader br = new BufferedReader(new StringReader(
- new String(this.rawDescriptorBytes)));
- String line;
- boolean skipCrypto = false;
- while ((line = br.readLine()) != null) {
- if (line.startsWith("@")) {
- continue;
- }
- String lineNoOpt = line.startsWith("opt ") ?
- line.substring("opt ".length()) : line;
- String[] partsNoOpt = lineNoOpt.split(" ");
- String keyword = partsNoOpt[0];
- if (keyword.equals("router")) {
- this.parseRouterLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("bandwidth")) {
- this.parseBandwidthLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("platform")) {
- this.parsePlatformLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("published")) {
- this.parsePublishedLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("fingerprint")) {
- this.parseFingerprintLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("hibernating")) {
- this.parseHibernatingLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("uptime")) {
- this.parseUptimeLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("onion-key")) {
- this.parseOnionKeyLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("signing-key")) {
- this.parseSigningKeyLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("accept")) {
- this.parseAcceptLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("reject")) {
- this.parseRejectLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("router-signature")) {
- this.parseRouterSignatureLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("contact")) {
- this.parseContactLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("family")) {
- this.parseFamilyLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("read-history")) {
- this.parseReadHistoryLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("write-history")) {
- this.parseWriteHistoryLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("eventdns")) {
- this.parseEventdnsLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("caches-extra-info")) {
- this.parseCachesExtraInfoLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("extra-info-digest")) {
- this.parseExtraInfoDigestLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("hidden-service-dir")) {
- this.parseHiddenServiceDirLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("protocols")) {
- this.parseProtocolsLine(line, lineNoOpt, partsNoOpt);
- } else if (keyword.equals("allow-single-hop-exits")) {
- this.parseAllowSingleHopExitsLine(line, lineNoOpt, partsNoOpt);
- } else if (line.startsWith("-----BEGIN")) {
- skipCrypto = true;
- } else if (line.startsWith("-----END")) {
- skipCrypto = false;
- } else if (!skipCrypto) {
- /* TODO Is throwing an exception the right thing to do here?
- * This is probably fine for development, but once the library
- * is in production use, this seems annoying. In theory,
- * dir-spec.txt says that unknown lines should be ignored. This
- * also applies to the other descriptors. */
- throw new DescriptorParseException("Unrecognized line '" + line
- + "'.");
- }
- }
- } catch (IOException e) {
- throw new RuntimeException("Internal error: Ran into an "
- + "IOException while parsing a String in memory. Something's "
- + "really wrong.", e);
- }
- }
-
- private void parseRouterLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (partsNoOpt.length != 6) {
- throw new DescriptorParseException("Illegal line '" + line
- + "' in server descriptor.");
- }
- this.nickname = ParseHelper.parseNickname(line, partsNoOpt[1]);
- this.address = ParseHelper.parseIpv4Address(line, partsNoOpt[2]);
- this.orPort = ParseHelper.parsePort(line, partsNoOpt[3]);
- this.socksPort = ParseHelper.parsePort(line, partsNoOpt[4]);
- this.dirPort = ParseHelper.parsePort(line, partsNoOpt[5]);
- }
-
- private void parseBandwidthLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (partsNoOpt.length != 4) {
- throw new DescriptorParseException("Wrong number of values in line "
- + "'" + line + "'.");
- }
- boolean isValid = false;
- try {
- this.bandwidthRate = Integer.parseInt(partsNoOpt[1]);
- this.bandwidthBurst = Integer.parseInt(partsNoOpt[2]);
- this.bandwidthObserved = Integer.parseInt(partsNoOpt[3]);
- if (this.bandwidthRate >= 0 && this.bandwidthBurst >= 0 &&
- this.bandwidthObserved >= 0) {
- isValid = true;
- }
- } catch (NumberFormatException e) {
- /* Handle below. */
- }
- if (!isValid) {
- throw new DescriptorParseException("Illegal values in line '" + line
- + "'.");
- }
- }
-
- private void parsePlatformLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (lineNoOpt.length() > "platform ".length()) {
- this.platform = lineNoOpt.substring("platform ".length());
- } else {
- this.platform = "";
- }
- }
-
- private void parsePublishedLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- this.publishedMillis = ParseHelper.parseTimestampAtIndex(line,
- partsNoOpt, 1, 2);
- }
-
- private void parseFingerprintLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (lineNoOpt.length() != "fingerprint".length() + 5 * 10) {
- throw new DescriptorParseException("Illegal line '" + line + "'.");
- }
- this.fingerprint = ParseHelper.parseTwentyByteHexString(line,
- lineNoOpt.substring("fingerprint ".length()).replaceAll(" ", ""));
- }
-
- private void parseHibernatingLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (partsNoOpt.length != 2) {
- throw new DescriptorParseException("Illegal line '" + line + "'.");
- }
- if (partsNoOpt[1].equals("1")) {
- this.hibernating = true;
- } else if (partsNoOpt[1].equals("0")) {
- this.hibernating = false;
- } else {
- throw new DescriptorParseException("Illegal line '" + line + "'.");
- }
- }
-
- private void parseUptimeLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (partsNoOpt.length != 2) {
- throw new DescriptorParseException("Wrong number of values in line "
- + "'" + line + "'.");
- }
- boolean isValid = false;
- try {
- this.uptime = Integer.parseInt(partsNoOpt[1]);
- if (this.uptime >= 0) {
- isValid = true;
- }
- } catch (NumberFormatException e) {
- /* Handle below. */
- }
- if (!isValid) {
- throw new DescriptorParseException("Illegal value in line '" + line
- + "'.");
- }
- }
-
- private void parseOnionKeyLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* Not parsing crypto parts (yet). */
- }
-
- private void parseSigningKeyLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- /* Not parsing crypto parts (yet). */
- }
-
- private void parseAcceptLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- this.parseExitPolicyLine(line, lineNoOpt, partsNoOpt);
- }
-
- private void parseRejectLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- this.parseExitPolicyLine(line, lineNoOpt, partsNoOpt);
- }
-
- private void parseExitPolicyLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (partsNoOpt.length != 2) {
- throw new DescriptorParseException("Illegal line '" + line + "'.");
- }
- ParseHelper.parseExitPattern(line, partsNoOpt[1]);
- this.exitPolicyLines.add(lineNoOpt);
- }
-
- private void parseRouterSignatureLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (!lineNoOpt.equals("router-signature")) {
- throw new DescriptorParseException("Illegal line '" + line + "'.");
- }
- /* Not parsing crypto parts (yet). */
- }
-
- private void parseContactLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (lineNoOpt.length() > "contact ".length()) {
- this.contact = lineNoOpt.substring("contact ".length());
- } else {
- this.contact = "";
- }
- }
-
- private void parseFamilyLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- this.familyEntries = new ArrayList<String>();
- for (int i = 1; i < partsNoOpt.length; i++) {
- if (partsNoOpt[i].startsWith("$")) {
- this.familyEntries.add("$"
- + ParseHelper.parseTwentyByteHexString(line,
- partsNoOpt[i].substring(1)));
- } else {
- this.familyEntries.add(ParseHelper.parseNickname(line,
- partsNoOpt[i]));
- }
- }
- }
-
- private void parseReadHistoryLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- this.readHistory = new BandwidthHistoryImpl(line, lineNoOpt,
- partsNoOpt);
- }
-
- private void parseWriteHistoryLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- this.writeHistory = new BandwidthHistoryImpl(line, lineNoOpt,
- partsNoOpt);
- }
-
- private void parseEventdnsLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (partsNoOpt.length != 2) {
- throw new DescriptorParseException("Illegal line '" + line + "'.");
- }
- if (partsNoOpt[1].equals("true")) {
- this.usesEnhancedDnsLogic = true;
- } else if (partsNoOpt[1].equals("false")) {
- this.usesEnhancedDnsLogic = false;
- } else {
- throw new DescriptorParseException("Illegal line '" + line + "'.");
- }
- }
-
- private void parseCachesExtraInfoLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (!lineNoOpt.equals("caches-extra-info")) {
- throw new DescriptorParseException("Illegal line '" + line + "'.");
- }
- this.cachesExtraInfo = true;
- }
-
- private void parseExtraInfoDigestLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (partsNoOpt.length != 2) {
- throw new DescriptorParseException("Illegal line '" + line + "'.");
- }
- this.extraInfoDigest = ParseHelper.parseTwentyByteHexString(line,
- partsNoOpt[1]);
- }
-
- private void parseHiddenServiceDirLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- this.hiddenServiceDirVersions = new ArrayList<Integer>();
- if (partsNoOpt.length == 1) {
- this.hiddenServiceDirVersions.add(2);
- } else {
- try {
- for (int i = 1; i < partsNoOpt.length; i++) {
- this.hiddenServiceDirVersions.add(Integer.parseInt(
- partsNoOpt[i]));
- }
- } catch (NumberFormatException e) {
- throw new DescriptorParseException("Illegal value in line '"
- + line + "'.");
- }
- }
- }
-
- private void parseProtocolsLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- List<String> partsList = Arrays.asList(partsNoOpt);
- boolean isValid = true;
- this.linkProtocolVersions = new ArrayList<Integer>();
- this.circuitProtocolVersions = new ArrayList<Integer>();
- List<Integer> protocolVersions = null;
- for (int i = 1; i < partsNoOpt.length; i++) {
- String part = partsNoOpt[i];
- if (part.equals("Link")) {
- protocolVersions = this.linkProtocolVersions;
- } else if (part.equals("Circuit")) {
- protocolVersions = this.circuitProtocolVersions;
- } else if (protocolVersions == null) {
- isValid = false;
- break;
- } else {
- try {
- protocolVersions.add(Integer.parseInt(part));
- } catch (NumberFormatException e) {
- isValid = false;
- break;
- }
- }
- }
- if (protocolVersions != this.circuitProtocolVersions) {
- isValid = false;
- }
- if (!isValid) {
- throw new DescriptorParseException("Illegal line '" + line + "'.");
- }
- }
-
- private void parseAllowSingleHopExitsLine(String line, String lineNoOpt,
- String[] partsNoOpt) throws DescriptorParseException {
- if (!lineNoOpt.equals("allow-single-hop-exits")) {
- throw new DescriptorParseException("Illegal line '" + line + "'.");
- }
- this.allowSingleHopExits = true;
- }
-
- private String nickname;
- public String getNickname() {
- return this.nickname;
- }
-
- private String address;
- public String getAddress() {
- return this.address;
- }
-
- private int orPort;
- public int getOrPort() {
- return this.orPort;
- }
-
- private int socksPort;
- public int getSocksPort() {
- return this.socksPort;
- }
-
- private int dirPort;
- public int getDirPort() {
- return this.dirPort;
- }
-
- private int bandwidthRate;
- public int getBandwidthRate() {
- return this.bandwidthRate;
- }
-
- private int bandwidthBurst;
- public int getBandwidthBurst() {
- return this.bandwidthBurst;
- }
-
- private int bandwidthObserved;
- public int getBandwidthObserved() {
- return this.bandwidthObserved;
- }
-
- private String platform;
- public String getPlatform() {
- return this.platform;
- }
-
- private long publishedMillis;
- public long getPublishedMillis() {
- return this.publishedMillis;
- }
-
- private String fingerprint;
- public String getFingerprint() {
- return this.fingerprint;
- }
-
- private boolean hibernating;
- public boolean isHibernating() {
- return this.hibernating;
- }
-
- private int uptime = -1;
- public int getUptime() {
- return this.uptime;
- }
-
- private List<String> exitPolicyLines = new ArrayList<String>();
- public List<String> getExitPolicyLines() {
- return new ArrayList<String>(this.exitPolicyLines);
- }
-
- private String contact;
- public String getContact() {
- return this.contact;
- }
-
- private List<String> familyEntries;
- public List<String> getFamilyEntries() {
- return this.familyEntries == null ? null :
- new ArrayList<String>(this.familyEntries);
- }
-
- private BandwidthHistory readHistory;
- public BandwidthHistory getReadHistory() {
- return this.readHistory;
- }
-
- private BandwidthHistory writeHistory;
- public BandwidthHistory getWriteHistory() {
- return this.writeHistory;
- }
-
- private boolean usesEnhancedDnsLogic;
- public boolean getUsesEnhancedDnsLogic() {
- return this.usesEnhancedDnsLogic;
- }
-
- private boolean cachesExtraInfo;
- public boolean getCachesExtraInfo() {
- return this.cachesExtraInfo;
- }
-
- private String extraInfoDigest;
- public String getExtraInfoDigest() {
- return this.extraInfoDigest;
- }
-
- private List<Integer> hiddenServiceDirVersions;
- public List<Integer> getHiddenServiceDirVersions() {
- return this.hiddenServiceDirVersions == null ? null :
- new ArrayList<Integer>(this.hiddenServiceDirVersions);
- }
-
- private List<Integer> linkProtocolVersions;
- public List<Integer> getLinkProtocolVersions() {
- return this.linkProtocolVersions == null ? null :
- new ArrayList<Integer>(this.linkProtocolVersions);
- }
-
- private List<Integer> circuitProtocolVersions;
- public List<Integer> getCircuitProtocolVersions() {
- return this.circuitProtocolVersions == null ? null :
- new ArrayList<Integer>(this.circuitProtocolVersions);
- }
-
- private boolean allowSingleHopExits;
- public boolean getAllowSingleHopExits() {
- return this.allowSingleHopExits;
- }
-}
-
diff --git a/src/org/torproject/descriptor/impl/ServerDescriptorImpl.java b/src/org/torproject/descriptor/impl/ServerDescriptorImpl.java
new file mode 100644
index 0000000..878955e
--- /dev/null
+++ b/src/org/torproject/descriptor/impl/ServerDescriptorImpl.java
@@ -0,0 +1,532 @@
+/* Copyright 2012 The Tor Project
+ * See LICENSE for licensing information */
+package org.torproject.descriptor.impl;
+
+import java.io.BufferedReader;
+import java.io.IOException;
+import java.io.StringReader;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+import org.torproject.descriptor.ServerDescriptor;
+import org.torproject.descriptor.BandwidthHistory;
+
+/* Contains a relay server descriptor. */
+public class ServerDescriptorImpl extends DescriptorImpl
+ implements ServerDescriptor {
+
+ protected static List<ServerDescriptor> parseDescriptors(
+ byte[] descriptorsBytes) {
+ List<ServerDescriptor> parsedDescriptors =
+ new ArrayList<ServerDescriptor>();
+ List<byte[]> splitDescriptorsBytes =
+ DescriptorImpl.splitRawDescriptorBytes(descriptorsBytes,
+ "router ");
+ try {
+ for (byte[] descriptorBytes : splitDescriptorsBytes) {
+ ServerDescriptor parsedDescriptor =
+ new ServerDescriptorImpl(descriptorBytes);
+ parsedDescriptors.add(parsedDescriptor);
+ }
+ } catch (DescriptorParseException e) {
+ /* TODO Handle this error somehow. */
+ System.err.println("Failed to parse descriptor. Skipping.");
+ e.printStackTrace();
+ }
+ return parsedDescriptors;
+ }
+
+ protected ServerDescriptorImpl(byte[] descriptorBytes)
+ throws DescriptorParseException {
+ super(descriptorBytes);
+ this.parseDescriptorBytes();
+ Set<String> exactlyOnceKeywords = new HashSet<String>(Arrays.asList((
+ "router,bandwidth,published,onion-key,signing-key,"
+ + "router-signature").split(",")));
+ this.checkExactlyOnceKeywords(exactlyOnceKeywords);
+ Set<String> atMostOnceKeywords = new HashSet<String>(Arrays.asList((
+ "platform,fingerprint,hibernating,uptime,contact,family,"
+ + "read-history,write-history,eventdns,caches-extra-info,"
+ + "extra-info-digest,hidden-service-dir,protocols,"
+ + "allow-single-hop-exits").split(",")));
+ this.checkAtMostOnceKeywords(atMostOnceKeywords);
+ this.checkFirstKeyword("router");
+ this.checkLastKeyword("router-signature");
+ if (this.getKeywordCount("accept") == 0 &&
+ this.getKeywordCount("reject") == 0) {
+ throw new DescriptorParseException("Either keyword 'accept' or "
+ + "'reject' must be contained at least once.");
+ }
+ return;
+ }
+
+ private void parseDescriptorBytes() throws DescriptorParseException {
+ try {
+ BufferedReader br = new BufferedReader(new StringReader(
+ new String(this.rawDescriptorBytes)));
+ String line;
+ boolean skipCrypto = false;
+ while ((line = br.readLine()) != null) {
+ if (line.startsWith("@")) {
+ continue;
+ }
+ String lineNoOpt = line.startsWith("opt ") ?
+ line.substring("opt ".length()) : line;
+ String[] partsNoOpt = lineNoOpt.split(" ");
+ String keyword = partsNoOpt[0];
+ if (keyword.equals("router")) {
+ this.parseRouterLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("bandwidth")) {
+ this.parseBandwidthLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("platform")) {
+ this.parsePlatformLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("published")) {
+ this.parsePublishedLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("fingerprint")) {
+ this.parseFingerprintLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("hibernating")) {
+ this.parseHibernatingLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("uptime")) {
+ this.parseUptimeLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("onion-key")) {
+ this.parseOnionKeyLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("signing-key")) {
+ this.parseSigningKeyLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("accept")) {
+ this.parseAcceptLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("reject")) {
+ this.parseRejectLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("router-signature")) {
+ this.parseRouterSignatureLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("contact")) {
+ this.parseContactLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("family")) {
+ this.parseFamilyLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("read-history")) {
+ this.parseReadHistoryLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("write-history")) {
+ this.parseWriteHistoryLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("eventdns")) {
+ this.parseEventdnsLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("caches-extra-info")) {
+ this.parseCachesExtraInfoLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("extra-info-digest")) {
+ this.parseExtraInfoDigestLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("hidden-service-dir")) {
+ this.parseHiddenServiceDirLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("protocols")) {
+ this.parseProtocolsLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("allow-single-hop-exits")) {
+ this.parseAllowSingleHopExitsLine(line, lineNoOpt, partsNoOpt);
+ } else if (line.startsWith("-----BEGIN")) {
+ skipCrypto = true;
+ } else if (line.startsWith("-----END")) {
+ skipCrypto = false;
+ } else if (!skipCrypto) {
+ /* TODO Is throwing an exception the right thing to do here?
+ * This is probably fine for development, but once the library
+ * is in production use, this seems annoying. In theory,
+ * dir-spec.txt says that unknown lines should be ignored. This
+ * also applies to the other descriptors. */
+ throw new DescriptorParseException("Unrecognized line '" + line
+ + "'.");
+ }
+ }
+ } catch (IOException e) {
+ throw new RuntimeException("Internal error: Ran into an "
+ + "IOException while parsing a String in memory. Something's "
+ + "really wrong.", e);
+ }
+ }
+
+ private void parseRouterLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (partsNoOpt.length != 6) {
+ throw new DescriptorParseException("Illegal line '" + line
+ + "' in server descriptor.");
+ }
+ this.nickname = ParseHelper.parseNickname(line, partsNoOpt[1]);
+ this.address = ParseHelper.parseIpv4Address(line, partsNoOpt[2]);
+ this.orPort = ParseHelper.parsePort(line, partsNoOpt[3]);
+ this.socksPort = ParseHelper.parsePort(line, partsNoOpt[4]);
+ this.dirPort = ParseHelper.parsePort(line, partsNoOpt[5]);
+ }
+
+ private void parseBandwidthLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (partsNoOpt.length != 4) {
+ throw new DescriptorParseException("Wrong number of values in line "
+ + "'" + line + "'.");
+ }
+ boolean isValid = false;
+ try {
+ this.bandwidthRate = Integer.parseInt(partsNoOpt[1]);
+ this.bandwidthBurst = Integer.parseInt(partsNoOpt[2]);
+ this.bandwidthObserved = Integer.parseInt(partsNoOpt[3]);
+ if (this.bandwidthRate >= 0 && this.bandwidthBurst >= 0 &&
+ this.bandwidthObserved >= 0) {
+ isValid = true;
+ }
+ } catch (NumberFormatException e) {
+ /* Handle below. */
+ }
+ if (!isValid) {
+ throw new DescriptorParseException("Illegal values in line '" + line
+ + "'.");
+ }
+ }
+
+ private void parsePlatformLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (lineNoOpt.length() > "platform ".length()) {
+ this.platform = lineNoOpt.substring("platform ".length());
+ } else {
+ this.platform = "";
+ }
+ }
+
+ private void parsePublishedLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ this.publishedMillis = ParseHelper.parseTimestampAtIndex(line,
+ partsNoOpt, 1, 2);
+ }
+
+ private void parseFingerprintLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (lineNoOpt.length() != "fingerprint".length() + 5 * 10) {
+ throw new DescriptorParseException("Illegal line '" + line + "'.");
+ }
+ this.fingerprint = ParseHelper.parseTwentyByteHexString(line,
+ lineNoOpt.substring("fingerprint ".length()).replaceAll(" ", ""));
+ }
+
+ private void parseHibernatingLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (partsNoOpt.length != 2) {
+ throw new DescriptorParseException("Illegal line '" + line + "'.");
+ }
+ if (partsNoOpt[1].equals("1")) {
+ this.hibernating = true;
+ } else if (partsNoOpt[1].equals("0")) {
+ this.hibernating = false;
+ } else {
+ throw new DescriptorParseException("Illegal line '" + line + "'.");
+ }
+ }
+
+ private void parseUptimeLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (partsNoOpt.length != 2) {
+ throw new DescriptorParseException("Wrong number of values in line "
+ + "'" + line + "'.");
+ }
+ boolean isValid = false;
+ try {
+ this.uptime = Integer.parseInt(partsNoOpt[1]);
+ if (this.uptime >= 0) {
+ isValid = true;
+ }
+ } catch (NumberFormatException e) {
+ /* Handle below. */
+ }
+ if (!isValid) {
+ throw new DescriptorParseException("Illegal value in line '" + line
+ + "'.");
+ }
+ }
+
+ private void parseOnionKeyLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* Not parsing crypto parts (yet). */
+ }
+
+ private void parseSigningKeyLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* Not parsing crypto parts (yet). */
+ }
+
+ private void parseAcceptLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ this.parseExitPolicyLine(line, lineNoOpt, partsNoOpt);
+ }
+
+ private void parseRejectLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ this.parseExitPolicyLine(line, lineNoOpt, partsNoOpt);
+ }
+
+ private void parseExitPolicyLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (partsNoOpt.length != 2) {
+ throw new DescriptorParseException("Illegal line '" + line + "'.");
+ }
+ ParseHelper.parseExitPattern(line, partsNoOpt[1]);
+ this.exitPolicyLines.add(lineNoOpt);
+ }
+
+ private void parseRouterSignatureLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (!lineNoOpt.equals("router-signature")) {
+ throw new DescriptorParseException("Illegal line '" + line + "'.");
+ }
+ /* Not parsing crypto parts (yet). */
+ }
+
+ private void parseContactLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (lineNoOpt.length() > "contact ".length()) {
+ this.contact = lineNoOpt.substring("contact ".length());
+ } else {
+ this.contact = "";
+ }
+ }
+
+ private void parseFamilyLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ this.familyEntries = new ArrayList<String>();
+ for (int i = 1; i < partsNoOpt.length; i++) {
+ if (partsNoOpt[i].startsWith("$")) {
+ this.familyEntries.add("$"
+ + ParseHelper.parseTwentyByteHexString(line,
+ partsNoOpt[i].substring(1)));
+ } else {
+ this.familyEntries.add(ParseHelper.parseNickname(line,
+ partsNoOpt[i]));
+ }
+ }
+ }
+
+ private void parseReadHistoryLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ this.readHistory = new BandwidthHistoryImpl(line, lineNoOpt,
+ partsNoOpt);
+ }
+
+ private void parseWriteHistoryLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ this.writeHistory = new BandwidthHistoryImpl(line, lineNoOpt,
+ partsNoOpt);
+ }
+
+ private void parseEventdnsLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (partsNoOpt.length != 2) {
+ throw new DescriptorParseException("Illegal line '" + line + "'.");
+ }
+ if (partsNoOpt[1].equals("true")) {
+ this.usesEnhancedDnsLogic = true;
+ } else if (partsNoOpt[1].equals("false")) {
+ this.usesEnhancedDnsLogic = false;
+ } else {
+ throw new DescriptorParseException("Illegal line '" + line + "'.");
+ }
+ }
+
+ private void parseCachesExtraInfoLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (!lineNoOpt.equals("caches-extra-info")) {
+ throw new DescriptorParseException("Illegal line '" + line + "'.");
+ }
+ this.cachesExtraInfo = true;
+ }
+
+ private void parseExtraInfoDigestLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (partsNoOpt.length != 2) {
+ throw new DescriptorParseException("Illegal line '" + line + "'.");
+ }
+ this.extraInfoDigest = ParseHelper.parseTwentyByteHexString(line,
+ partsNoOpt[1]);
+ }
+
+ private void parseHiddenServiceDirLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ this.hiddenServiceDirVersions = new ArrayList<Integer>();
+ if (partsNoOpt.length == 1) {
+ this.hiddenServiceDirVersions.add(2);
+ } else {
+ try {
+ for (int i = 1; i < partsNoOpt.length; i++) {
+ this.hiddenServiceDirVersions.add(Integer.parseInt(
+ partsNoOpt[i]));
+ }
+ } catch (NumberFormatException e) {
+ throw new DescriptorParseException("Illegal value in line '"
+ + line + "'.");
+ }
+ }
+ }
+
+ private void parseProtocolsLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ List<String> partsList = Arrays.asList(partsNoOpt);
+ boolean isValid = true;
+ this.linkProtocolVersions = new ArrayList<Integer>();
+ this.circuitProtocolVersions = new ArrayList<Integer>();
+ List<Integer> protocolVersions = null;
+ for (int i = 1; i < partsNoOpt.length; i++) {
+ String part = partsNoOpt[i];
+ if (part.equals("Link")) {
+ protocolVersions = this.linkProtocolVersions;
+ } else if (part.equals("Circuit")) {
+ protocolVersions = this.circuitProtocolVersions;
+ } else if (protocolVersions == null) {
+ isValid = false;
+ break;
+ } else {
+ try {
+ protocolVersions.add(Integer.parseInt(part));
+ } catch (NumberFormatException e) {
+ isValid = false;
+ break;
+ }
+ }
+ }
+ if (protocolVersions != this.circuitProtocolVersions) {
+ isValid = false;
+ }
+ if (!isValid) {
+ throw new DescriptorParseException("Illegal line '" + line + "'.");
+ }
+ }
+
+ private void parseAllowSingleHopExitsLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ if (!lineNoOpt.equals("allow-single-hop-exits")) {
+ throw new DescriptorParseException("Illegal line '" + line + "'.");
+ }
+ this.allowSingleHopExits = true;
+ }
+
+ private String nickname;
+ public String getNickname() {
+ return this.nickname;
+ }
+
+ private String address;
+ public String getAddress() {
+ return this.address;
+ }
+
+ private int orPort;
+ public int getOrPort() {
+ return this.orPort;
+ }
+
+ private int socksPort;
+ public int getSocksPort() {
+ return this.socksPort;
+ }
+
+ private int dirPort;
+ public int getDirPort() {
+ return this.dirPort;
+ }
+
+ private int bandwidthRate;
+ public int getBandwidthRate() {
+ return this.bandwidthRate;
+ }
+
+ private int bandwidthBurst;
+ public int getBandwidthBurst() {
+ return this.bandwidthBurst;
+ }
+
+ private int bandwidthObserved;
+ public int getBandwidthObserved() {
+ return this.bandwidthObserved;
+ }
+
+ private String platform;
+ public String getPlatform() {
+ return this.platform;
+ }
+
+ private long publishedMillis;
+ public long getPublishedMillis() {
+ return this.publishedMillis;
+ }
+
+ private String fingerprint;
+ public String getFingerprint() {
+ return this.fingerprint;
+ }
+
+ private boolean hibernating;
+ public boolean isHibernating() {
+ return this.hibernating;
+ }
+
+ private int uptime = -1;
+ public int getUptime() {
+ return this.uptime;
+ }
+
+ private List<String> exitPolicyLines = new ArrayList<String>();
+ public List<String> getExitPolicyLines() {
+ return new ArrayList<String>(this.exitPolicyLines);
+ }
+
+ private String contact;
+ public String getContact() {
+ return this.contact;
+ }
+
+ private List<String> familyEntries;
+ public List<String> getFamilyEntries() {
+ return this.familyEntries == null ? null :
+ new ArrayList<String>(this.familyEntries);
+ }
+
+ private BandwidthHistory readHistory;
+ public BandwidthHistory getReadHistory() {
+ return this.readHistory;
+ }
+
+ private BandwidthHistory writeHistory;
+ public BandwidthHistory getWriteHistory() {
+ return this.writeHistory;
+ }
+
+ private boolean usesEnhancedDnsLogic;
+ public boolean getUsesEnhancedDnsLogic() {
+ return this.usesEnhancedDnsLogic;
+ }
+
+ private boolean cachesExtraInfo;
+ public boolean getCachesExtraInfo() {
+ return this.cachesExtraInfo;
+ }
+
+ private String extraInfoDigest;
+ public String getExtraInfoDigest() {
+ return this.extraInfoDigest;
+ }
+
+ private List<Integer> hiddenServiceDirVersions;
+ public List<Integer> getHiddenServiceDirVersions() {
+ return this.hiddenServiceDirVersions == null ? null :
+ new ArrayList<Integer>(this.hiddenServiceDirVersions);
+ }
+
+ private List<Integer> linkProtocolVersions;
+ public List<Integer> getLinkProtocolVersions() {
+ return this.linkProtocolVersions == null ? null :
+ new ArrayList<Integer>(this.linkProtocolVersions);
+ }
+
+ private List<Integer> circuitProtocolVersions;
+ public List<Integer> getCircuitProtocolVersions() {
+ return this.circuitProtocolVersions == null ? null :
+ new ArrayList<Integer>(this.circuitProtocolVersions);
+ }
+
+ private boolean allowSingleHopExits;
+ public boolean getAllowSingleHopExits() {
+ return this.allowSingleHopExits;
+ }
+}
+
diff --git a/test/org/torproject/descriptor/impl/RelayServerDescriptorImplTest.java b/test/org/torproject/descriptor/impl/RelayServerDescriptorImplTest.java
deleted file mode 100644
index f806502..0000000
--- a/test/org/torproject/descriptor/impl/RelayServerDescriptorImplTest.java
+++ /dev/null
@@ -1,1080 +0,0 @@
-/* Copyright 2012 The Tor Project
- * See LICENSE for licensing information */
-package org.torproject.descriptor.impl;
-
-import org.torproject.descriptor.BandwidthHistory;
-import org.torproject.descriptor.RelayServerDescriptor;
-
-import java.util.*;
-
-import org.junit.*;
-import org.junit.rules.*;
-import static org.junit.Assert.*;
-
-/* Test parsing of relay server descriptors. */
-public class RelayServerDescriptorImplTest {
-
- /* Helper class to build a descriptor based on default data and
- * modifications requested by test methods. */
- private static class DescriptorBuilder {
- private String routerLine = "router saberrider2008 94.134.192.243 "
- + "9001 0 0";
- private static RelayServerDescriptor createWithRouterLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.routerLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String bandwidthLine = "bandwidth 51200 51200 53470";
- private static RelayServerDescriptor createWithBandwidthLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.bandwidthLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String platformLine = "platform Tor 0.2.2.35 "
- + "(git-b04388f9e7546a9f) on Linux i686";
- private static RelayServerDescriptor createWithPlatformLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.platformLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String publishedLine = "published 2012-01-01 04:03:19";
- private static RelayServerDescriptor createWithPublishedLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.publishedLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String fingerprintLine = "opt fingerprint D873 3048 FC8E "
- + "C910 2466 AD8F 3098 622B F1BF 71FD";
- private static RelayServerDescriptor createWithFingerprintLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.fingerprintLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String hibernatingLine = null;
- private static RelayServerDescriptor createWithHibernatingLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.hibernatingLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String uptimeLine = "uptime 48";
- private static RelayServerDescriptor createWithUptimeLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.uptimeLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String onionKeyLines = "onion-key\n"
- + "-----BEGIN RSA PUBLIC KEY-----\n"
- + "MIGJAoGBAKM+iiHhO6eHsvd6Xjws9z9EQB1V/Bpuy5ciGJ1U4V9SeiKooSo5Bp"
- + "PL\no3XT+6PIgzl3R6uycjS3Ejk47vLEJdcVTm/VG6E0ppu3olIynCI4QryfCE"
- + "uC3cTF\n9wE4WXY4nX7w0RTN18UVLxrt1A9PP0cobFNiPs9rzJCbKFfacOkpAg"
- + "MBAAE=\n"
- + "-----END RSA PUBLIC KEY-----";
- private static RelayServerDescriptor createWithOnionKeyLines(
- String lines) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.onionKeyLines = lines;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String signingKeyLines = "signing-key\n"
- + "-----BEGIN RSA PUBLIC KEY-----\n"
- + "MIGJAoGBALMm3r3QDh482Ewe6Ub9wvRIfmEkoNX6q5cEAtQRNHSDcNx41gjELb"
- + "cl\nEniVMParBYACKfOxkS+mTTnIRDKVNEJTsDOwryNrc4X9JnPc/nn6ymYPiN"
- + "DhUROG\n8URDIhQoixcUeyyrVB8sxliSstKimulGnB7xpjYOlO8JKaHLNL4TAg"
- + "MBAAE=\n"
- + "-----END RSA PUBLIC KEY-----";
- private static RelayServerDescriptor createWithSigningKeyLines(
- String lines) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.signingKeyLines = lines;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String exitPolicyLines = "reject *:*";
- private static RelayServerDescriptor createWithExitPolicyLines(
- String lines) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.exitPolicyLines = lines;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String contactLine = "contact Random Person <nobody AT "
- + "example dot com>";
- private static RelayServerDescriptor createWithContactLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.contactLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String familyLine = null;
- private static RelayServerDescriptor createWithFamilyLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.familyLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String readHistoryLine = null;
- private static RelayServerDescriptor createWithReadHistoryLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.readHistoryLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String writeHistoryLine = null;
- private static RelayServerDescriptor createWithWriteHistoryLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.writeHistoryLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String eventdnsLine = null;
- private static RelayServerDescriptor createWithEventdnsLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.eventdnsLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String cachesExtraInfoLine = null;
- private static RelayServerDescriptor createWithCachesExtraInfoLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.cachesExtraInfoLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String extraInfoDigestLine = "opt extra-info-digest "
- + "1469D1550738A25B1E7B47CDDBCD7B2899F51B74";
- private static RelayServerDescriptor createWithExtraInfoDigestLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.extraInfoDigestLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String hiddenServiceDirLine = "opt hidden-service-dir";
- private static RelayServerDescriptor createWithHiddenServiceDirLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.hiddenServiceDirLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String protocolsLine = "opt protocols Link 1 2 Circuit 1";
- private static RelayServerDescriptor createWithProtocolsLine(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.protocolsLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String allowSingleHopExitsLine = null;
- private static RelayServerDescriptor
- createWithAllowSingleHopExitsLine(String line)
- throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.allowSingleHopExitsLine = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private String routerSignatureLines = "router-signature\n"
- + "-----BEGIN SIGNATURE-----\n"
- + "o4j+kH8UQfjBwepUnr99v0ebN8RpzHJ/lqYsTojXHy9kMr1RNI9IDeSzA7PSqT"
- + "uV\n4PL8QsGtlfwthtIoZpB2srZeyN/mcpA9fa1JXUrt/UN9K/+32Cyaad7h0n"
- + "HE6Xfb\njqpXDpnBpvk4zjmzjjKYnIsUWTnADmu0fo3xTRqXi7g=\n"
- + "-----END SIGNATURE-----";
- private static RelayServerDescriptor createWithRouterSignatureLines(
- String line) throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- db.routerSignatureLines = line;
- return new RelayServerDescriptorImpl(db.buildDescriptor());
- }
- private byte[] buildDescriptor() {
- StringBuilder sb = new StringBuilder();
- if (this.routerLine != null) {
- sb.append(this.routerLine + "\n");
- }
- if (this.bandwidthLine != null) {
- sb.append(this.bandwidthLine + "\n");
- }
- if (this.platformLine != null) {
- sb.append(this.platformLine + "\n");
- }
- if (this.publishedLine != null) {
- sb.append(this.publishedLine + "\n");
- }
- if (this.fingerprintLine != null) {
- sb.append(this.fingerprintLine + "\n");
- }
- if (this.hibernatingLine != null) {
- sb.append(this.hibernatingLine + "\n");
- }
- if (this.uptimeLine != null) {
- sb.append(this.uptimeLine + "\n");
- }
- if (this.onionKeyLines != null) {
- sb.append(this.onionKeyLines + "\n");
- }
- if (this.signingKeyLines != null) {
- sb.append(this.signingKeyLines + "\n");
- }
- if (this.exitPolicyLines != null) {
- sb.append(this.exitPolicyLines + "\n");
- }
- if (this.contactLine != null) {
- sb.append(this.contactLine + "\n");
- }
- if (this.familyLine != null) {
- sb.append(this.familyLine + "\n");
- }
- if (this.readHistoryLine != null) {
- sb.append(this.readHistoryLine + "\n");
- }
- if (this.writeHistoryLine != null) {
- sb.append(this.writeHistoryLine + "\n");
- }
- if (this.eventdnsLine != null) {
- sb.append(this.eventdnsLine + "\n");
- }
- if (this.cachesExtraInfoLine != null) {
- sb.append(this.cachesExtraInfoLine + "\n");
- }
- if (this.extraInfoDigestLine != null) {
- sb.append(this.extraInfoDigestLine + "\n");
- }
- if (this.hiddenServiceDirLine != null) {
- sb.append(this.hiddenServiceDirLine + "\n");
- }
- if (this.protocolsLine != null) {
- sb.append(this.protocolsLine + "\n");
- }
- if (this.allowSingleHopExitsLine != null) {
- sb.append(this.allowSingleHopExitsLine + "\n");
- }
- if (this.routerSignatureLines != null) {
- sb.append(this.routerSignatureLines + "\n");
- }
- return sb.toString().getBytes();
- }
- }
-
- @Test()
- public void testSampleDescriptor() throws DescriptorParseException {
- DescriptorBuilder db = new DescriptorBuilder();
- RelayServerDescriptor descriptor =
- new RelayServerDescriptorImpl(db.buildDescriptor());
- assertEquals("saberrider2008", descriptor.getNickname());
- assertEquals("94.134.192.243", descriptor.getAddress());
- assertEquals(9001, (int) descriptor.getOrPort());
- assertEquals(0, (int) descriptor.getSocksPort());
- assertEquals(0, (int) descriptor.getDirPort());
- assertEquals("Tor 0.2.2.35 (git-b04388f9e7546a9f) on Linux i686",
- descriptor.getPlatform());
- assertEquals(Arrays.asList(new Integer[] {1, 2}),
- descriptor.getLinkProtocolVersions());
- assertEquals(Arrays.asList(new Integer[] {1}),
- descriptor.getCircuitProtocolVersions());
- assertEquals(1325390599000L, descriptor.getPublishedMillis());
- assertEquals("D8733048FC8EC9102466AD8F3098622BF1BF71FD",
- descriptor.getFingerprint());
- assertEquals(48, (int) descriptor.getUptime());
- assertEquals(51200, (int) descriptor.getBandwidthRate());
- assertEquals(51200, (int) descriptor.getBandwidthBurst());
- assertEquals(53470, (int) descriptor.getBandwidthObserved());
- assertEquals("1469D1550738A25B1E7B47CDDBCD7B2899F51B74",
- descriptor.getExtraInfoDigest());
- assertEquals(Arrays.asList(new Integer[] {2}),
- descriptor.getHiddenServiceDirVersions());
- assertEquals("Random Person <nobody AT example dot com>",
- descriptor.getContact());
- assertEquals(Arrays.asList(new String[] {"reject *:*"}),
- descriptor.getExitPolicyLines());
- assertFalse(descriptor.isHibernating());
- assertNull(descriptor.getFamilyEntries());
- assertNull(descriptor.getReadHistory());
- assertNull(descriptor.getWriteHistory());
- assertFalse(descriptor.getUsesEnhancedDnsLogic());
- assertFalse(descriptor.getCachesExtraInfo());
- assertFalse(descriptor.getAllowSingleHopExits());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testRouterLineMissing() throws DescriptorParseException {
- DescriptorBuilder.createWithRouterLine(null);
- }
-
- @Test()
- public void testRouterOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithRouterLine("opt router saberrider2008 "
- + "94.134.192.243 9001 0 0");
- assertEquals("saberrider2008", descriptor.getNickname());
- assertEquals("94.134.192.243", descriptor.getAddress());
- assertEquals(9001, (int) descriptor.getOrPort());
- assertEquals(0, (int) descriptor.getSocksPort());
- assertEquals(0, (int) descriptor.getDirPort());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testRouterLinePrecedingHibernatingLine()
- throws DescriptorParseException {
- DescriptorBuilder.createWithRouterLine("hibernating 1\nrouter "
- + "saberrider2008 94.134.192.243 9001 0 0");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testNicknameMissing() throws DescriptorParseException {
- DescriptorBuilder.createWithRouterLine("router 94.134.192.243 9001 "
- + "0 0");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testNicknameInvalidChar() throws DescriptorParseException {
- DescriptorBuilder.createWithRouterLine("router $aberrider2008 "
- + "94.134.192.243 9001 0 0");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testNicknameTooLong() throws DescriptorParseException {
- DescriptorBuilder.createWithRouterLine("router "
- + "saberrider2008ReallyLongNickname 94.134.192.243 9001 0 0");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testAddress24() throws DescriptorParseException {
- DescriptorBuilder.createWithRouterLine("router saberrider2008 "
- + "94.134.192/24 9001 0 0");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testAddress294() throws DescriptorParseException {
- DescriptorBuilder.createWithRouterLine("router saberrider2008 "
- + "294.134.192.243 9001 0 0");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testAddressMissing() throws DescriptorParseException {
- DescriptorBuilder.createWithRouterLine("router saberrider2008 9001 "
- + "0 0");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testOrPort99001() throws DescriptorParseException {
- DescriptorBuilder.createWithRouterLine("router saberrider2008 "
- + "94.134.192.243 99001 0 0");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testOrPortMissing() throws DescriptorParseException {
- DescriptorBuilder.createWithRouterLine("router saberrider2008 "
- + "94.134.192.243 0 0");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testOrPortOne() throws DescriptorParseException {
- DescriptorBuilder.createWithRouterLine("router saberrider2008 "
- + "94.134.192.243 one 0 0");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testOrPortNewline() throws DescriptorParseException {
- DescriptorBuilder.createWithRouterLine("router saberrider2008 "
- + "94.134.192.243 0\n 0 0");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testDirPortMissing() throws DescriptorParseException {
- DescriptorBuilder.createWithRouterLine("router saberrider2008 "
- + "94.134.192.243 9001 0 ");
- }
-
- @Test()
- public void testPlatformMissing() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithPlatformLine(null);
- assertNull(descriptor.getPlatform());
- }
-
- @Test()
- public void testPlatformOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithPlatformLine("opt platform Tor 0.2.2.35 "
- + "(git-b04388f9e7546a9f) on Linux i686");
- assertEquals("Tor 0.2.2.35 (git-b04388f9e7546a9f) on Linux i686",
- descriptor.getPlatform());
- }
-
- @Test()
- public void testPlatformNoSpace() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithPlatformLine("platform");
- assertEquals("", descriptor.getPlatform());
- }
-
- @Test()
- public void testPlatformSpace() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithPlatformLine("platform ");
- assertEquals("", descriptor.getPlatform());
- }
-
- @Test()
- public void testProtocolsNoOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithProtocolsLine("protocols Link 1 2 Circuit 1");
- assertEquals(Arrays.asList(new Integer[] {1, 2}),
- descriptor.getLinkProtocolVersions());
- assertEquals(Arrays.asList(new Integer[] {1}),
- descriptor.getCircuitProtocolVersions());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testProtocolsAB() throws DescriptorParseException {
- DescriptorBuilder.createWithProtocolsLine("opt protocols Link A B "
- + "Circuit 1");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testProtocolsNoCircuitVersions()
- throws DescriptorParseException {
- DescriptorBuilder.createWithProtocolsLine("opt protocols Link 1 2");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testPublishedMissing() throws DescriptorParseException {
- DescriptorBuilder.createWithPublishedLine(null);
- }
-
- @Test()
- public void testPublishedOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithPublishedLine("opt published 2012-01-01 04:03:19");
- assertEquals(1325390599000L, descriptor.getPublishedMillis());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testPublished3012() throws DescriptorParseException {
- DescriptorBuilder.createWithPublishedLine("published 3012-01-01 "
- + "04:03:19");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testPublished1912() throws DescriptorParseException {
- DescriptorBuilder.createWithPublishedLine("published 1912-01-01 "
- + "04:03:19");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testPublishedFeb31() throws DescriptorParseException {
- DescriptorBuilder.createWithPublishedLine("published 2012-02-31 "
- + "04:03:19");
- }
-
- @Test()
- public void testFingerprintNoOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithFingerprintLine("fingerprint D873 3048 FC8E C910 2466 "
- + "AD8F 3098 622B F1BF 71FD");
- assertEquals("D8733048FC8EC9102466AD8F3098622BF1BF71FD",
- descriptor.getFingerprint());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testFingerprintG() throws DescriptorParseException {
- DescriptorBuilder.createWithFingerprintLine("opt fingerprint G873 "
- + "3048 FC8E C910 2466 AD8F 3098 622B F1BF 71FD");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testFingerprintTooShort() throws DescriptorParseException {
- DescriptorBuilder.createWithFingerprintLine("opt fingerprint D873 "
- + "3048 FC8E C910 2466 AD8F 3098 622B F1BF");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testFingerprintTooLong() throws DescriptorParseException {
- DescriptorBuilder.createWithFingerprintLine("opt fingerprint D873 "
- + "3048 FC8E C910 2466 AD8F 3098 622B F1BF 71FD D873");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testFingerprintNoSpaces() throws DescriptorParseException {
- DescriptorBuilder.createWithFingerprintLine("opt fingerprint "
- + "D8733048FC8EC9102466AD8F3098622BF1BF71FD");
- }
-
- @Test()
- public void testUptimeMissing() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithUptimeLine(null);
- assertEquals(-1, (int) descriptor.getUptime());
- }
-
- @Test()
- public void testUptimeOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithUptimeLine("opt uptime 48");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testUptimeFourtyEight() throws DescriptorParseException {
- DescriptorBuilder.createWithUptimeLine("uptime fourty-eight");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testUptimeMinusOne() throws DescriptorParseException {
- DescriptorBuilder.createWithUptimeLine("uptime -1");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testUptimeSpace() throws DescriptorParseException {
- DescriptorBuilder.createWithUptimeLine("uptime ");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testUptimeNoSpace() throws DescriptorParseException {
- DescriptorBuilder.createWithUptimeLine("uptime");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testUptimeFourEight() throws DescriptorParseException {
- DescriptorBuilder.createWithUptimeLine("uptime 4 8");
- }
-
- @Test()
- public void testBandwidthOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithBandwidthLine("opt bandwidth 51200 51200 53470");
- assertEquals(51200, (int) descriptor.getBandwidthRate());
- assertEquals(51200, (int) descriptor.getBandwidthBurst());
- assertEquals(53470, (int) descriptor.getBandwidthObserved());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testBandwidthMissing() throws DescriptorParseException {
- DescriptorBuilder.createWithBandwidthLine(null);
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testBandwidthTwoValues() throws DescriptorParseException {
- DescriptorBuilder.createWithBandwidthLine("bandwidth 51200 51200");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testBandwidthFourValues() throws DescriptorParseException {
- DescriptorBuilder.createWithBandwidthLine("bandwidth 51200 51200 "
- + "53470 53470");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testBandwidthMinusOneTwoThree()
- throws DescriptorParseException {
- DescriptorBuilder.createWithBandwidthLine("bandwidth -1 -2 -3");
- }
-
- @Test()
- public void testExtraInfoDigestNoOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithExtraInfoDigestLine("extra-info-digest "
- + "1469D1550738A25B1E7B47CDDBCD7B2899F51B74");
- assertEquals("1469D1550738A25B1E7B47CDDBCD7B2899F51B74",
- descriptor.getExtraInfoDigest());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testExtraInfoDigestNoSpace()
- throws DescriptorParseException {
- DescriptorBuilder.createWithExtraInfoDigestLine("opt "
- + "extra-info-digest");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testExtraInfoDigestTooShort()
- throws DescriptorParseException {
- DescriptorBuilder.createWithExtraInfoDigestLine("opt "
- + "extra-info-digest 1469D1550738A25B1E7B47CDDBCD7B2899F5");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testExtraInfoDigestTooLong()
- throws DescriptorParseException {
- DescriptorBuilder.createWithExtraInfoDigestLine("opt "
- + "extra-info-digest "
- + "1469D1550738A25B1E7B47CDDBCD7B2899F51B741469");
- }
-
- @Test()
- public void testExtraInfoDigestMissing()
- throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithExtraInfoDigestLine(null);
- assertNull(descriptor.getExtraInfoDigest());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testOnionKeyMissing() throws DescriptorParseException {
- DescriptorBuilder.createWithOnionKeyLines(null);
- }
-
- @Test()
- public void testOnionKeyOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithOnionKeyLines("opt onion-key\n"
- + "-----BEGIN RSA PUBLIC KEY-----\n"
- + "MIGJAoGBAKM+iiHhO6eHsvd6Xjws9z9EQB1V/Bpuy5ciGJ1U4V9SeiKooSo5Bp"
- + "PL\no3XT+6PIgzl3R6uycjS3Ejk47vLEJdcVTm/VG6E0ppu3olIynCI4QryfCE"
- + "uC3cTF\n9wE4WXY4nX7w0RTN18UVLxrt1A9PP0cobFNiPs9rzJCbKFfacOkpAg"
- + "MBAAE=\n"
- + "-----END RSA PUBLIC KEY-----");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testSigningKeyMissing() throws DescriptorParseException {
- DescriptorBuilder.createWithSigningKeyLines(null);
- }
-
- @Test()
- public void testSigningKeyOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithSigningKeyLines("opt signing-key\n"
- + "-----BEGIN RSA PUBLIC KEY-----\n"
- + "MIGJAoGBALMm3r3QDh482Ewe6Ub9wvRIfmEkoNX6q5cEAtQRNHSDcNx41gjELb"
- + "cl\nEniVMParBYACKfOxkS+mTTnIRDKVNEJTsDOwryNrc4X9JnPc/nn6ymYPiN"
- + "DhUROG\n8URDIhQoixcUeyyrVB8sxliSstKimulGnB7xpjYOlO8JKaHLNL4TAg"
- + "MBAAE=\n"
- + "-----END RSA PUBLIC KEY-----");
- }
-
- @Test()
- public void testHiddenServiceDirMissing()
- throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithHiddenServiceDirLine(null);
- assertNull(descriptor.getHiddenServiceDirVersions());
- }
-
- @Test()
- public void testHiddenServiceDirNoOpt()
- throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithHiddenServiceDirLine("hidden-service-dir");
- assertEquals(Arrays.asList(new Integer[] {2}),
- descriptor.getHiddenServiceDirVersions());
- }
-
- @Test()
- public void testHiddenServiceDirVersions2And3()
- throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithHiddenServiceDirLine("hidden-service-dir 2 3");
- assertEquals(Arrays.asList(new Integer[] {2, 3}),
- descriptor.getHiddenServiceDirVersions());
- }
-
- @Test()
- public void testContactMissing() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithContactLine(null);
- assertNull(descriptor.getContact());
- }
-
- @Test()
- public void testContactOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithContactLine("opt contact Random Person");
- assertEquals("Random Person", descriptor.getContact());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testContactDuplicate() throws DescriptorParseException {
- DescriptorBuilder.createWithContactLine("contact Random "
- + "Person\ncontact Random Person");
- }
-
- @Test()
- public void testContactNoSpace() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithContactLine("contact");
- assertEquals("", descriptor.getContact());
- }
-
- @Test()
- public void testExitPolicyRejectAllAcceptAll()
- throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithExitPolicyLines("reject *:*\naccept *:*");
- assertEquals(Arrays.asList(new String[] {"reject *:*", "accept *:*"}),
- descriptor.getExitPolicyLines());
- }
-
- @Test()
- public void testExitPolicyOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithExitPolicyLines("opt reject *:*");
- assertEquals(Arrays.asList(new String[] {"reject *:*"}),
- descriptor.getExitPolicyLines());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testExitPolicyNoPort() throws DescriptorParseException {
- DescriptorBuilder.createWithExitPolicyLines("reject *");
- }
-
- @Test()
- public void testExitPolicyAccept80RejectAll()
- throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithExitPolicyLines("accept *:80\nreject *:*");
- assertEquals(Arrays.asList(new String[] {"accept *:80",
- "reject *:*"}), descriptor.getExitPolicyLines());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testExitPolicyReject321() throws DescriptorParseException {
- DescriptorBuilder.createWithExitPolicyLines("reject "
- + "123.123.123.321:80");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testExitPolicyRejectPort66666()
- throws DescriptorParseException {
- DescriptorBuilder.createWithExitPolicyLines("reject *:66666");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testExitPolicyProjectAll() throws DescriptorParseException {
- DescriptorBuilder.createWithExitPolicyLines("project *:*");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testExitPolicyMissing() throws DescriptorParseException {
- DescriptorBuilder.createWithExitPolicyLines(null);
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testRouterSignatureMissing()
- throws DescriptorParseException {
- DescriptorBuilder.createWithRouterSignatureLines(null);
- }
-
- @Test()
- public void testRouterSignatureOpt()
- throws DescriptorParseException {
- DescriptorBuilder.createWithRouterSignatureLines("opt "
- + "router-signature\n"
- + "-----BEGIN SIGNATURE-----\n"
- + "crypto lines are ignored anyway\n"
- + "-----END SIGNATURE-----");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testRouterSignatureNotLastLine()
- throws DescriptorParseException {
- DescriptorBuilder.createWithRouterSignatureLines("router-signature\n"
- + "-----BEGIN SIGNATURE-----\n"
- + "o4j+kH8UQfjBwepUnr99v0ebN8RpzHJ/lqYsTojXHy9kMr1RNI9IDeSzA7PSqT"
- + "uV\n4PL8QsGtlfwthtIoZpB2srZeyN/mcpA9fa1JXUrt/UN9K/+32Cyaad7h0n"
- + "HE6Xfb\njqpXDpnBpvk4zjmzjjKYnIsUWTnADmu0fo3xTRqXi7g=\n"
- + "-----END SIGNATURE-----\ncontact me");
- }
-
- @Test()
- public void testHibernatingOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithHibernatingLine("opt hibernating 1");
- assertTrue(descriptor.isHibernating());
- }
-
- @Test()
- public void testHibernatingFalse() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithHibernatingLine("hibernating 0");
- assertFalse(descriptor.isHibernating());
- }
-
- @Test()
- public void testHibernatingTrue() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithHibernatingLine("hibernating 1");
- assertTrue(descriptor.isHibernating());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testHibernatingYep() throws DescriptorParseException {
- DescriptorBuilder.createWithHibernatingLine("hibernating yep");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testHibernatingNoSpace() throws DescriptorParseException {
- DescriptorBuilder.createWithHibernatingLine("hibernating");
- }
-
- @Test()
- public void testFamilyOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithFamilyLine("opt family saberrider2008");
- assertEquals(Arrays.asList(new String[] {"saberrider2008"}),
- descriptor.getFamilyEntries());
- }
-
- @Test()
- public void testFamilyFingerprint() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithFamilyLine("family "
- + "$D8733048FC8EC9102466AD8F3098622BF1BF71FD");
- assertEquals(Arrays.asList(new String[] {
- "$D8733048FC8EC9102466AD8F3098622BF1BF71FD"}),
- descriptor.getFamilyEntries());
- }
-
- @Test()
- public void testFamilyNickname() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithFamilyLine("family saberrider2008");
- assertEquals(Arrays.asList(new String[] {"saberrider2008"}),
- descriptor.getFamilyEntries());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testFamilyDuplicate() throws DescriptorParseException {
- DescriptorBuilder.createWithFamilyLine("family "
- + "saberrider2008\nfamily saberrider2008");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testFamilyNicknamePrefix() throws DescriptorParseException {
- DescriptorBuilder.createWithFamilyLine("family $saberrider2008");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testFamilyFingerprintNoPrefix()
- throws DescriptorParseException {
- DescriptorBuilder.createWithFamilyLine("family "
- + "D8733048FC8EC9102466AD8F3098622BF1BF71FD");
- }
-
- @Test()
- public void testWriteHistory() throws DescriptorParseException {
- String writeHistoryLine = "write-history 2012-01-01 03:51:44 (900 s) "
- + "4345856,261120,7591936,1748992";
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithWriteHistoryLine(writeHistoryLine);
- assertNotNull(descriptor.getWriteHistory());
- BandwidthHistory parsedWriteHistory = descriptor.getWriteHistory();
- assertEquals(writeHistoryLine, parsedWriteHistory.getLine());
- assertEquals(1325389904000L, (long) parsedWriteHistory.
- getHistoryEndMillis());
- assertEquals(900L, (long) parsedWriteHistory.getIntervalLength());
- SortedMap<Long, Long> bandwidthValues = parsedWriteHistory.
- getBandwidthValues();
- assertEquals(4345856L, (long) bandwidthValues.remove(1325387204000L));
- assertEquals(261120L, (long) bandwidthValues.remove(1325388104000L));
- assertEquals(7591936L, (long) bandwidthValues.remove(1325389004000L));
- assertEquals(1748992L, (long) bandwidthValues.remove(1325389904000L));
- assertTrue(bandwidthValues.isEmpty());
- }
-
- @Test()
- public void testWriteHistoryOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithWriteHistoryLine("opt write-history 2012-01-01 "
- + "03:51:44 (900 s) 4345856,261120,7591936,1748992");
- assertNotNull(descriptor.getWriteHistory());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testWriteHistory3012() throws DescriptorParseException {
- DescriptorBuilder.createWithWriteHistoryLine("write-history "
- + "3012-01-01 03:51:44 (900 s) 4345856,261120,7591936,1748992");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testWriteHistoryNoSeconds()
- throws DescriptorParseException {
- DescriptorBuilder.createWithWriteHistoryLine("write-history "
- + "2012-01-01 03:51 (900 s) 4345856,261120,7591936,1748992");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testWriteHistoryNoParathenses()
- throws DescriptorParseException {
- DescriptorBuilder.createWithWriteHistoryLine("write-history "
- + "2012-01-01 03:51:44 900 s 4345856,261120,7591936,1748992");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testWriteHistoryNoSpaceSeconds()
- throws DescriptorParseException {
- DescriptorBuilder.createWithWriteHistoryLine("write-history "
- + "2012-01-01 03:51:44 (900s) 4345856,261120,7591936,1748992");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testWriteHistoryTrailingComma()
- throws DescriptorParseException {
- DescriptorBuilder.createWithWriteHistoryLine("write-history "
- + "2012-01-01 03:51:44 (900 s) 4345856,261120,7591936,");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testWriteHistoryOneTwoThree()
- throws DescriptorParseException {
- DescriptorBuilder.createWithWriteHistoryLine("write-history "
- + "2012-01-01 03:51:44 (900 s) one,two,three");
- }
-
- @Test()
- public void testWriteHistoryNoValuesSpace()
- throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithWriteHistoryLine("write-history 2012-01-01 03:51:44 "
- + "(900 s) ");
- assertEquals(900, (long) descriptor.getWriteHistory().
- getIntervalLength());
- assertTrue(descriptor.getWriteHistory().getBandwidthValues().
- isEmpty());
- }
-
- @Test()
- public void testWriteHistoryNoValuesNoSpace()
- throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithWriteHistoryLine("write-history 2012-01-01 03:51:44 "
- + "(900 s)");
- assertEquals(900, (long) descriptor.getWriteHistory().
- getIntervalLength());
- assertTrue(descriptor.getWriteHistory().getBandwidthValues().
- isEmpty());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testWriteHistoryNoS() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithWriteHistoryLine("write-history 2012-01-01 03:51:44 "
- + "(900 ");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testWriteHistoryTrailingNumber()
- throws DescriptorParseException {
- DescriptorBuilder.createWithWriteHistoryLine("write-history "
- + "2012-01-01 03:51:44 (900 s) 4345856 1");
- }
-
- @Test()
- public void testWriteHistory1800Seconds()
- throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithWriteHistoryLine("write-history 2012-01-01 03:51:44 "
- + "(1800 s) 4345856");
- assertEquals(1800L, (long) descriptor.getWriteHistory().
- getIntervalLength());
- }
-
- @Test()
- public void testReadHistory() throws DescriptorParseException {
- String readHistoryLine = "read-history 2012-01-01 03:51:44 (900 s) "
- + "4268032,139264,7797760,1415168";
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithReadHistoryLine(readHistoryLine);
- assertNotNull(descriptor.getReadHistory());
- BandwidthHistory parsedReadHistory = descriptor.getReadHistory();
- assertEquals(readHistoryLine, parsedReadHistory.getLine());
- assertEquals(1325389904000L, (long) parsedReadHistory.
- getHistoryEndMillis());
- assertEquals(900L, (long) parsedReadHistory.getIntervalLength());
- SortedMap<Long, Long> bandwidthValues = parsedReadHistory.
- getBandwidthValues();
- assertEquals(4268032L, (long) bandwidthValues.remove(1325387204000L));
- assertEquals(139264L, (long) bandwidthValues.remove(1325388104000L));
- assertEquals(7797760L, (long) bandwidthValues.remove(1325389004000L));
- assertEquals(1415168L, (long) bandwidthValues.remove(1325389904000L));
- assertTrue(bandwidthValues.isEmpty());
- }
-
- /* TODO There are some old server descriptors with " read-history"
- * lines. Find out if these were spec-compliant and if other lines may
- * start with leading spaces, too. */
- @Test(expected = DescriptorParseException.class)
- public void testReadHistoryLeadingSpace()
- throws DescriptorParseException {
- String readHistoryLine = " read-history 2012-01-01 03:51:44 (900 s) "
- + "4268032,139264,7797760,1415168";
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithReadHistoryLine(readHistoryLine);
- }
-
- @Test()
- public void testEventdnsOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithEventdnsLine("opt eventdns true");
- assertTrue(descriptor.getUsesEnhancedDnsLogic());
- }
-
- @Test()
- public void testEventdnsTrue() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithEventdnsLine("eventdns true");
- assertTrue(descriptor.getUsesEnhancedDnsLogic());
- }
-
- @Test()
- public void testEventdnsFalse() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithEventdnsLine("eventdns false");
- assertFalse(descriptor.getUsesEnhancedDnsLogic());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testEventdns1() throws DescriptorParseException {
- DescriptorBuilder.createWithEventdnsLine("eventdns 1");
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testEventdnsNo() throws DescriptorParseException {
- DescriptorBuilder.createWithEventdnsLine("eventdns no");
- }
-
- @Test()
- public void testCachesExtraInfoOpt() throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithCachesExtraInfoLine("opt caches-extra-info");
- assertTrue(descriptor.getCachesExtraInfo());
- }
-
- @Test()
- public void testCachesExtraInfoNoSpace()
- throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithCachesExtraInfoLine("caches-extra-info");
- assertTrue(descriptor.getCachesExtraInfo());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testCachesExtraInfoTrue() throws DescriptorParseException {
- DescriptorBuilder.createWithCachesExtraInfoLine("caches-extra-info "
- + "true");
- }
-
- @Test()
- public void testAllowSingleHopExitsOpt()
- throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithCachesExtraInfoLine("opt allow-single-hop-exits");
- assertTrue(descriptor.getAllowSingleHopExits());
- }
-
- @Test()
- public void testAllowSingleHopExitsNoSpace()
- throws DescriptorParseException {
- RelayServerDescriptor descriptor = DescriptorBuilder.
- createWithCachesExtraInfoLine("allow-single-hop-exits");
- assertTrue(descriptor.getAllowSingleHopExits());
- }
-
- @Test(expected = DescriptorParseException.class)
- public void testAllowSingleHopExitsTrue()
- throws DescriptorParseException {
- DescriptorBuilder.createWithCachesExtraInfoLine(
- "allow-single-hop-exits true");
- }
-}
-
diff --git a/test/org/torproject/descriptor/impl/ServerDescriptorImplTest.java b/test/org/torproject/descriptor/impl/ServerDescriptorImplTest.java
new file mode 100644
index 0000000..c0721f5
--- /dev/null
+++ b/test/org/torproject/descriptor/impl/ServerDescriptorImplTest.java
@@ -0,0 +1,1080 @@
+/* Copyright 2012 The Tor Project
+ * See LICENSE for licensing information */
+package org.torproject.descriptor.impl;
+
+import org.torproject.descriptor.BandwidthHistory;
+import org.torproject.descriptor.ServerDescriptor;
+
+import java.util.*;
+
+import org.junit.*;
+import org.junit.rules.*;
+import static org.junit.Assert.*;
+
+/* Test parsing of relay server descriptors. */
+public class ServerDescriptorImplTest {
+
+ /* Helper class to build a descriptor based on default data and
+ * modifications requested by test methods. */
+ private static class DescriptorBuilder {
+ private String routerLine = "router saberrider2008 94.134.192.243 "
+ + "9001 0 0";
+ private static ServerDescriptor createWithRouterLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.routerLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String bandwidthLine = "bandwidth 51200 51200 53470";
+ private static ServerDescriptor createWithBandwidthLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.bandwidthLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String platformLine = "platform Tor 0.2.2.35 "
+ + "(git-b04388f9e7546a9f) on Linux i686";
+ private static ServerDescriptor createWithPlatformLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.platformLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String publishedLine = "published 2012-01-01 04:03:19";
+ private static ServerDescriptor createWithPublishedLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.publishedLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String fingerprintLine = "opt fingerprint D873 3048 FC8E "
+ + "C910 2466 AD8F 3098 622B F1BF 71FD";
+ private static ServerDescriptor createWithFingerprintLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.fingerprintLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String hibernatingLine = null;
+ private static ServerDescriptor createWithHibernatingLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.hibernatingLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String uptimeLine = "uptime 48";
+ private static ServerDescriptor createWithUptimeLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.uptimeLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String onionKeyLines = "onion-key\n"
+ + "-----BEGIN RSA PUBLIC KEY-----\n"
+ + "MIGJAoGBAKM+iiHhO6eHsvd6Xjws9z9EQB1V/Bpuy5ciGJ1U4V9SeiKooSo5Bp"
+ + "PL\no3XT+6PIgzl3R6uycjS3Ejk47vLEJdcVTm/VG6E0ppu3olIynCI4QryfCE"
+ + "uC3cTF\n9wE4WXY4nX7w0RTN18UVLxrt1A9PP0cobFNiPs9rzJCbKFfacOkpAg"
+ + "MBAAE=\n"
+ + "-----END RSA PUBLIC KEY-----";
+ private static ServerDescriptor createWithOnionKeyLines(
+ String lines) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.onionKeyLines = lines;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String signingKeyLines = "signing-key\n"
+ + "-----BEGIN RSA PUBLIC KEY-----\n"
+ + "MIGJAoGBALMm3r3QDh482Ewe6Ub9wvRIfmEkoNX6q5cEAtQRNHSDcNx41gjELb"
+ + "cl\nEniVMParBYACKfOxkS+mTTnIRDKVNEJTsDOwryNrc4X9JnPc/nn6ymYPiN"
+ + "DhUROG\n8URDIhQoixcUeyyrVB8sxliSstKimulGnB7xpjYOlO8JKaHLNL4TAg"
+ + "MBAAE=\n"
+ + "-----END RSA PUBLIC KEY-----";
+ private static ServerDescriptor createWithSigningKeyLines(
+ String lines) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.signingKeyLines = lines;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String exitPolicyLines = "reject *:*";
+ private static ServerDescriptor createWithExitPolicyLines(
+ String lines) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.exitPolicyLines = lines;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String contactLine = "contact Random Person <nobody AT "
+ + "example dot com>";
+ private static ServerDescriptor createWithContactLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.contactLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String familyLine = null;
+ private static ServerDescriptor createWithFamilyLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.familyLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String readHistoryLine = null;
+ private static ServerDescriptor createWithReadHistoryLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.readHistoryLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String writeHistoryLine = null;
+ private static ServerDescriptor createWithWriteHistoryLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.writeHistoryLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String eventdnsLine = null;
+ private static ServerDescriptor createWithEventdnsLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.eventdnsLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String cachesExtraInfoLine = null;
+ private static ServerDescriptor createWithCachesExtraInfoLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.cachesExtraInfoLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String extraInfoDigestLine = "opt extra-info-digest "
+ + "1469D1550738A25B1E7B47CDDBCD7B2899F51B74";
+ private static ServerDescriptor createWithExtraInfoDigestLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.extraInfoDigestLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String hiddenServiceDirLine = "opt hidden-service-dir";
+ private static ServerDescriptor createWithHiddenServiceDirLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.hiddenServiceDirLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String protocolsLine = "opt protocols Link 1 2 Circuit 1";
+ private static ServerDescriptor createWithProtocolsLine(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.protocolsLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String allowSingleHopExitsLine = null;
+ private static ServerDescriptor
+ createWithAllowSingleHopExitsLine(String line)
+ throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.allowSingleHopExitsLine = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private String routerSignatureLines = "router-signature\n"
+ + "-----BEGIN SIGNATURE-----\n"
+ + "o4j+kH8UQfjBwepUnr99v0ebN8RpzHJ/lqYsTojXHy9kMr1RNI9IDeSzA7PSqT"
+ + "uV\n4PL8QsGtlfwthtIoZpB2srZeyN/mcpA9fa1JXUrt/UN9K/+32Cyaad7h0n"
+ + "HE6Xfb\njqpXDpnBpvk4zjmzjjKYnIsUWTnADmu0fo3xTRqXi7g=\n"
+ + "-----END SIGNATURE-----";
+ private static ServerDescriptor createWithRouterSignatureLines(
+ String line) throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ db.routerSignatureLines = line;
+ return new ServerDescriptorImpl(db.buildDescriptor());
+ }
+ private byte[] buildDescriptor() {
+ StringBuilder sb = new StringBuilder();
+ if (this.routerLine != null) {
+ sb.append(this.routerLine + "\n");
+ }
+ if (this.bandwidthLine != null) {
+ sb.append(this.bandwidthLine + "\n");
+ }
+ if (this.platformLine != null) {
+ sb.append(this.platformLine + "\n");
+ }
+ if (this.publishedLine != null) {
+ sb.append(this.publishedLine + "\n");
+ }
+ if (this.fingerprintLine != null) {
+ sb.append(this.fingerprintLine + "\n");
+ }
+ if (this.hibernatingLine != null) {
+ sb.append(this.hibernatingLine + "\n");
+ }
+ if (this.uptimeLine != null) {
+ sb.append(this.uptimeLine + "\n");
+ }
+ if (this.onionKeyLines != null) {
+ sb.append(this.onionKeyLines + "\n");
+ }
+ if (this.signingKeyLines != null) {
+ sb.append(this.signingKeyLines + "\n");
+ }
+ if (this.exitPolicyLines != null) {
+ sb.append(this.exitPolicyLines + "\n");
+ }
+ if (this.contactLine != null) {
+ sb.append(this.contactLine + "\n");
+ }
+ if (this.familyLine != null) {
+ sb.append(this.familyLine + "\n");
+ }
+ if (this.readHistoryLine != null) {
+ sb.append(this.readHistoryLine + "\n");
+ }
+ if (this.writeHistoryLine != null) {
+ sb.append(this.writeHistoryLine + "\n");
+ }
+ if (this.eventdnsLine != null) {
+ sb.append(this.eventdnsLine + "\n");
+ }
+ if (this.cachesExtraInfoLine != null) {
+ sb.append(this.cachesExtraInfoLine + "\n");
+ }
+ if (this.extraInfoDigestLine != null) {
+ sb.append(this.extraInfoDigestLine + "\n");
+ }
+ if (this.hiddenServiceDirLine != null) {
+ sb.append(this.hiddenServiceDirLine + "\n");
+ }
+ if (this.protocolsLine != null) {
+ sb.append(this.protocolsLine + "\n");
+ }
+ if (this.allowSingleHopExitsLine != null) {
+ sb.append(this.allowSingleHopExitsLine + "\n");
+ }
+ if (this.routerSignatureLines != null) {
+ sb.append(this.routerSignatureLines + "\n");
+ }
+ return sb.toString().getBytes();
+ }
+ }
+
+ @Test()
+ public void testSampleDescriptor() throws DescriptorParseException {
+ DescriptorBuilder db = new DescriptorBuilder();
+ ServerDescriptor descriptor =
+ new ServerDescriptorImpl(db.buildDescriptor());
+ assertEquals("saberrider2008", descriptor.getNickname());
+ assertEquals("94.134.192.243", descriptor.getAddress());
+ assertEquals(9001, (int) descriptor.getOrPort());
+ assertEquals(0, (int) descriptor.getSocksPort());
+ assertEquals(0, (int) descriptor.getDirPort());
+ assertEquals("Tor 0.2.2.35 (git-b04388f9e7546a9f) on Linux i686",
+ descriptor.getPlatform());
+ assertEquals(Arrays.asList(new Integer[] {1, 2}),
+ descriptor.getLinkProtocolVersions());
+ assertEquals(Arrays.asList(new Integer[] {1}),
+ descriptor.getCircuitProtocolVersions());
+ assertEquals(1325390599000L, descriptor.getPublishedMillis());
+ assertEquals("D8733048FC8EC9102466AD8F3098622BF1BF71FD",
+ descriptor.getFingerprint());
+ assertEquals(48, (int) descriptor.getUptime());
+ assertEquals(51200, (int) descriptor.getBandwidthRate());
+ assertEquals(51200, (int) descriptor.getBandwidthBurst());
+ assertEquals(53470, (int) descriptor.getBandwidthObserved());
+ assertEquals("1469D1550738A25B1E7B47CDDBCD7B2899F51B74",
+ descriptor.getExtraInfoDigest());
+ assertEquals(Arrays.asList(new Integer[] {2}),
+ descriptor.getHiddenServiceDirVersions());
+ assertEquals("Random Person <nobody AT example dot com>",
+ descriptor.getContact());
+ assertEquals(Arrays.asList(new String[] {"reject *:*"}),
+ descriptor.getExitPolicyLines());
+ assertFalse(descriptor.isHibernating());
+ assertNull(descriptor.getFamilyEntries());
+ assertNull(descriptor.getReadHistory());
+ assertNull(descriptor.getWriteHistory());
+ assertFalse(descriptor.getUsesEnhancedDnsLogic());
+ assertFalse(descriptor.getCachesExtraInfo());
+ assertFalse(descriptor.getAllowSingleHopExits());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testRouterLineMissing() throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterLine(null);
+ }
+
+ @Test()
+ public void testRouterOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithRouterLine("opt router saberrider2008 "
+ + "94.134.192.243 9001 0 0");
+ assertEquals("saberrider2008", descriptor.getNickname());
+ assertEquals("94.134.192.243", descriptor.getAddress());
+ assertEquals(9001, (int) descriptor.getOrPort());
+ assertEquals(0, (int) descriptor.getSocksPort());
+ assertEquals(0, (int) descriptor.getDirPort());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testRouterLinePrecedingHibernatingLine()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterLine("hibernating 1\nrouter "
+ + "saberrider2008 94.134.192.243 9001 0 0");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testNicknameMissing() throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterLine("router 94.134.192.243 9001 "
+ + "0 0");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testNicknameInvalidChar() throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterLine("router $aberrider2008 "
+ + "94.134.192.243 9001 0 0");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testNicknameTooLong() throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterLine("router "
+ + "saberrider2008ReallyLongNickname 94.134.192.243 9001 0 0");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testAddress24() throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterLine("router saberrider2008 "
+ + "94.134.192/24 9001 0 0");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testAddress294() throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterLine("router saberrider2008 "
+ + "294.134.192.243 9001 0 0");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testAddressMissing() throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterLine("router saberrider2008 9001 "
+ + "0 0");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testOrPort99001() throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterLine("router saberrider2008 "
+ + "94.134.192.243 99001 0 0");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testOrPortMissing() throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterLine("router saberrider2008 "
+ + "94.134.192.243 0 0");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testOrPortOne() throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterLine("router saberrider2008 "
+ + "94.134.192.243 one 0 0");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testOrPortNewline() throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterLine("router saberrider2008 "
+ + "94.134.192.243 0\n 0 0");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testDirPortMissing() throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterLine("router saberrider2008 "
+ + "94.134.192.243 9001 0 ");
+ }
+
+ @Test()
+ public void testPlatformMissing() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithPlatformLine(null);
+ assertNull(descriptor.getPlatform());
+ }
+
+ @Test()
+ public void testPlatformOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithPlatformLine("opt platform Tor 0.2.2.35 "
+ + "(git-b04388f9e7546a9f) on Linux i686");
+ assertEquals("Tor 0.2.2.35 (git-b04388f9e7546a9f) on Linux i686",
+ descriptor.getPlatform());
+ }
+
+ @Test()
+ public void testPlatformNoSpace() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithPlatformLine("platform");
+ assertEquals("", descriptor.getPlatform());
+ }
+
+ @Test()
+ public void testPlatformSpace() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithPlatformLine("platform ");
+ assertEquals("", descriptor.getPlatform());
+ }
+
+ @Test()
+ public void testProtocolsNoOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithProtocolsLine("protocols Link 1 2 Circuit 1");
+ assertEquals(Arrays.asList(new Integer[] {1, 2}),
+ descriptor.getLinkProtocolVersions());
+ assertEquals(Arrays.asList(new Integer[] {1}),
+ descriptor.getCircuitProtocolVersions());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testProtocolsAB() throws DescriptorParseException {
+ DescriptorBuilder.createWithProtocolsLine("opt protocols Link A B "
+ + "Circuit 1");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testProtocolsNoCircuitVersions()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithProtocolsLine("opt protocols Link 1 2");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testPublishedMissing() throws DescriptorParseException {
+ DescriptorBuilder.createWithPublishedLine(null);
+ }
+
+ @Test()
+ public void testPublishedOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithPublishedLine("opt published 2012-01-01 04:03:19");
+ assertEquals(1325390599000L, descriptor.getPublishedMillis());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testPublished3012() throws DescriptorParseException {
+ DescriptorBuilder.createWithPublishedLine("published 3012-01-01 "
+ + "04:03:19");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testPublished1912() throws DescriptorParseException {
+ DescriptorBuilder.createWithPublishedLine("published 1912-01-01 "
+ + "04:03:19");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testPublishedFeb31() throws DescriptorParseException {
+ DescriptorBuilder.createWithPublishedLine("published 2012-02-31 "
+ + "04:03:19");
+ }
+
+ @Test()
+ public void testFingerprintNoOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithFingerprintLine("fingerprint D873 3048 FC8E C910 2466 "
+ + "AD8F 3098 622B F1BF 71FD");
+ assertEquals("D8733048FC8EC9102466AD8F3098622BF1BF71FD",
+ descriptor.getFingerprint());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testFingerprintG() throws DescriptorParseException {
+ DescriptorBuilder.createWithFingerprintLine("opt fingerprint G873 "
+ + "3048 FC8E C910 2466 AD8F 3098 622B F1BF 71FD");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testFingerprintTooShort() throws DescriptorParseException {
+ DescriptorBuilder.createWithFingerprintLine("opt fingerprint D873 "
+ + "3048 FC8E C910 2466 AD8F 3098 622B F1BF");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testFingerprintTooLong() throws DescriptorParseException {
+ DescriptorBuilder.createWithFingerprintLine("opt fingerprint D873 "
+ + "3048 FC8E C910 2466 AD8F 3098 622B F1BF 71FD D873");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testFingerprintNoSpaces() throws DescriptorParseException {
+ DescriptorBuilder.createWithFingerprintLine("opt fingerprint "
+ + "D8733048FC8EC9102466AD8F3098622BF1BF71FD");
+ }
+
+ @Test()
+ public void testUptimeMissing() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithUptimeLine(null);
+ assertEquals(-1, (int) descriptor.getUptime());
+ }
+
+ @Test()
+ public void testUptimeOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithUptimeLine("opt uptime 48");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testUptimeFourtyEight() throws DescriptorParseException {
+ DescriptorBuilder.createWithUptimeLine("uptime fourty-eight");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testUptimeMinusOne() throws DescriptorParseException {
+ DescriptorBuilder.createWithUptimeLine("uptime -1");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testUptimeSpace() throws DescriptorParseException {
+ DescriptorBuilder.createWithUptimeLine("uptime ");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testUptimeNoSpace() throws DescriptorParseException {
+ DescriptorBuilder.createWithUptimeLine("uptime");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testUptimeFourEight() throws DescriptorParseException {
+ DescriptorBuilder.createWithUptimeLine("uptime 4 8");
+ }
+
+ @Test()
+ public void testBandwidthOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithBandwidthLine("opt bandwidth 51200 51200 53470");
+ assertEquals(51200, (int) descriptor.getBandwidthRate());
+ assertEquals(51200, (int) descriptor.getBandwidthBurst());
+ assertEquals(53470, (int) descriptor.getBandwidthObserved());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testBandwidthMissing() throws DescriptorParseException {
+ DescriptorBuilder.createWithBandwidthLine(null);
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testBandwidthTwoValues() throws DescriptorParseException {
+ DescriptorBuilder.createWithBandwidthLine("bandwidth 51200 51200");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testBandwidthFourValues() throws DescriptorParseException {
+ DescriptorBuilder.createWithBandwidthLine("bandwidth 51200 51200 "
+ + "53470 53470");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testBandwidthMinusOneTwoThree()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithBandwidthLine("bandwidth -1 -2 -3");
+ }
+
+ @Test()
+ public void testExtraInfoDigestNoOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithExtraInfoDigestLine("extra-info-digest "
+ + "1469D1550738A25B1E7B47CDDBCD7B2899F51B74");
+ assertEquals("1469D1550738A25B1E7B47CDDBCD7B2899F51B74",
+ descriptor.getExtraInfoDigest());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testExtraInfoDigestNoSpace()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithExtraInfoDigestLine("opt "
+ + "extra-info-digest");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testExtraInfoDigestTooShort()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithExtraInfoDigestLine("opt "
+ + "extra-info-digest 1469D1550738A25B1E7B47CDDBCD7B2899F5");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testExtraInfoDigestTooLong()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithExtraInfoDigestLine("opt "
+ + "extra-info-digest "
+ + "1469D1550738A25B1E7B47CDDBCD7B2899F51B741469");
+ }
+
+ @Test()
+ public void testExtraInfoDigestMissing()
+ throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithExtraInfoDigestLine(null);
+ assertNull(descriptor.getExtraInfoDigest());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testOnionKeyMissing() throws DescriptorParseException {
+ DescriptorBuilder.createWithOnionKeyLines(null);
+ }
+
+ @Test()
+ public void testOnionKeyOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithOnionKeyLines("opt onion-key\n"
+ + "-----BEGIN RSA PUBLIC KEY-----\n"
+ + "MIGJAoGBAKM+iiHhO6eHsvd6Xjws9z9EQB1V/Bpuy5ciGJ1U4V9SeiKooSo5Bp"
+ + "PL\no3XT+6PIgzl3R6uycjS3Ejk47vLEJdcVTm/VG6E0ppu3olIynCI4QryfCE"
+ + "uC3cTF\n9wE4WXY4nX7w0RTN18UVLxrt1A9PP0cobFNiPs9rzJCbKFfacOkpAg"
+ + "MBAAE=\n"
+ + "-----END RSA PUBLIC KEY-----");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testSigningKeyMissing() throws DescriptorParseException {
+ DescriptorBuilder.createWithSigningKeyLines(null);
+ }
+
+ @Test()
+ public void testSigningKeyOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithSigningKeyLines("opt signing-key\n"
+ + "-----BEGIN RSA PUBLIC KEY-----\n"
+ + "MIGJAoGBALMm3r3QDh482Ewe6Ub9wvRIfmEkoNX6q5cEAtQRNHSDcNx41gjELb"
+ + "cl\nEniVMParBYACKfOxkS+mTTnIRDKVNEJTsDOwryNrc4X9JnPc/nn6ymYPiN"
+ + "DhUROG\n8URDIhQoixcUeyyrVB8sxliSstKimulGnB7xpjYOlO8JKaHLNL4TAg"
+ + "MBAAE=\n"
+ + "-----END RSA PUBLIC KEY-----");
+ }
+
+ @Test()
+ public void testHiddenServiceDirMissing()
+ throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithHiddenServiceDirLine(null);
+ assertNull(descriptor.getHiddenServiceDirVersions());
+ }
+
+ @Test()
+ public void testHiddenServiceDirNoOpt()
+ throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithHiddenServiceDirLine("hidden-service-dir");
+ assertEquals(Arrays.asList(new Integer[] {2}),
+ descriptor.getHiddenServiceDirVersions());
+ }
+
+ @Test()
+ public void testHiddenServiceDirVersions2And3()
+ throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithHiddenServiceDirLine("hidden-service-dir 2 3");
+ assertEquals(Arrays.asList(new Integer[] {2, 3}),
+ descriptor.getHiddenServiceDirVersions());
+ }
+
+ @Test()
+ public void testContactMissing() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithContactLine(null);
+ assertNull(descriptor.getContact());
+ }
+
+ @Test()
+ public void testContactOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithContactLine("opt contact Random Person");
+ assertEquals("Random Person", descriptor.getContact());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testContactDuplicate() throws DescriptorParseException {
+ DescriptorBuilder.createWithContactLine("contact Random "
+ + "Person\ncontact Random Person");
+ }
+
+ @Test()
+ public void testContactNoSpace() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithContactLine("contact");
+ assertEquals("", descriptor.getContact());
+ }
+
+ @Test()
+ public void testExitPolicyRejectAllAcceptAll()
+ throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithExitPolicyLines("reject *:*\naccept *:*");
+ assertEquals(Arrays.asList(new String[] {"reject *:*", "accept *:*"}),
+ descriptor.getExitPolicyLines());
+ }
+
+ @Test()
+ public void testExitPolicyOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithExitPolicyLines("opt reject *:*");
+ assertEquals(Arrays.asList(new String[] {"reject *:*"}),
+ descriptor.getExitPolicyLines());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testExitPolicyNoPort() throws DescriptorParseException {
+ DescriptorBuilder.createWithExitPolicyLines("reject *");
+ }
+
+ @Test()
+ public void testExitPolicyAccept80RejectAll()
+ throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithExitPolicyLines("accept *:80\nreject *:*");
+ assertEquals(Arrays.asList(new String[] {"accept *:80",
+ "reject *:*"}), descriptor.getExitPolicyLines());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testExitPolicyReject321() throws DescriptorParseException {
+ DescriptorBuilder.createWithExitPolicyLines("reject "
+ + "123.123.123.321:80");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testExitPolicyRejectPort66666()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithExitPolicyLines("reject *:66666");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testExitPolicyProjectAll() throws DescriptorParseException {
+ DescriptorBuilder.createWithExitPolicyLines("project *:*");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testExitPolicyMissing() throws DescriptorParseException {
+ DescriptorBuilder.createWithExitPolicyLines(null);
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testRouterSignatureMissing()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterSignatureLines(null);
+ }
+
+ @Test()
+ public void testRouterSignatureOpt()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterSignatureLines("opt "
+ + "router-signature\n"
+ + "-----BEGIN SIGNATURE-----\n"
+ + "crypto lines are ignored anyway\n"
+ + "-----END SIGNATURE-----");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testRouterSignatureNotLastLine()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithRouterSignatureLines("router-signature\n"
+ + "-----BEGIN SIGNATURE-----\n"
+ + "o4j+kH8UQfjBwepUnr99v0ebN8RpzHJ/lqYsTojXHy9kMr1RNI9IDeSzA7PSqT"
+ + "uV\n4PL8QsGtlfwthtIoZpB2srZeyN/mcpA9fa1JXUrt/UN9K/+32Cyaad7h0n"
+ + "HE6Xfb\njqpXDpnBpvk4zjmzjjKYnIsUWTnADmu0fo3xTRqXi7g=\n"
+ + "-----END SIGNATURE-----\ncontact me");
+ }
+
+ @Test()
+ public void testHibernatingOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithHibernatingLine("opt hibernating 1");
+ assertTrue(descriptor.isHibernating());
+ }
+
+ @Test()
+ public void testHibernatingFalse() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithHibernatingLine("hibernating 0");
+ assertFalse(descriptor.isHibernating());
+ }
+
+ @Test()
+ public void testHibernatingTrue() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithHibernatingLine("hibernating 1");
+ assertTrue(descriptor.isHibernating());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testHibernatingYep() throws DescriptorParseException {
+ DescriptorBuilder.createWithHibernatingLine("hibernating yep");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testHibernatingNoSpace() throws DescriptorParseException {
+ DescriptorBuilder.createWithHibernatingLine("hibernating");
+ }
+
+ @Test()
+ public void testFamilyOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithFamilyLine("opt family saberrider2008");
+ assertEquals(Arrays.asList(new String[] {"saberrider2008"}),
+ descriptor.getFamilyEntries());
+ }
+
+ @Test()
+ public void testFamilyFingerprint() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithFamilyLine("family "
+ + "$D8733048FC8EC9102466AD8F3098622BF1BF71FD");
+ assertEquals(Arrays.asList(new String[] {
+ "$D8733048FC8EC9102466AD8F3098622BF1BF71FD"}),
+ descriptor.getFamilyEntries());
+ }
+
+ @Test()
+ public void testFamilyNickname() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithFamilyLine("family saberrider2008");
+ assertEquals(Arrays.asList(new String[] {"saberrider2008"}),
+ descriptor.getFamilyEntries());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testFamilyDuplicate() throws DescriptorParseException {
+ DescriptorBuilder.createWithFamilyLine("family "
+ + "saberrider2008\nfamily saberrider2008");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testFamilyNicknamePrefix() throws DescriptorParseException {
+ DescriptorBuilder.createWithFamilyLine("family $saberrider2008");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testFamilyFingerprintNoPrefix()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithFamilyLine("family "
+ + "D8733048FC8EC9102466AD8F3098622BF1BF71FD");
+ }
+
+ @Test()
+ public void testWriteHistory() throws DescriptorParseException {
+ String writeHistoryLine = "write-history 2012-01-01 03:51:44 (900 s) "
+ + "4345856,261120,7591936,1748992";
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithWriteHistoryLine(writeHistoryLine);
+ assertNotNull(descriptor.getWriteHistory());
+ BandwidthHistory parsedWriteHistory = descriptor.getWriteHistory();
+ assertEquals(writeHistoryLine, parsedWriteHistory.getLine());
+ assertEquals(1325389904000L, (long) parsedWriteHistory.
+ getHistoryEndMillis());
+ assertEquals(900L, (long) parsedWriteHistory.getIntervalLength());
+ SortedMap<Long, Long> bandwidthValues = parsedWriteHistory.
+ getBandwidthValues();
+ assertEquals(4345856L, (long) bandwidthValues.remove(1325387204000L));
+ assertEquals(261120L, (long) bandwidthValues.remove(1325388104000L));
+ assertEquals(7591936L, (long) bandwidthValues.remove(1325389004000L));
+ assertEquals(1748992L, (long) bandwidthValues.remove(1325389904000L));
+ assertTrue(bandwidthValues.isEmpty());
+ }
+
+ @Test()
+ public void testWriteHistoryOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithWriteHistoryLine("opt write-history 2012-01-01 "
+ + "03:51:44 (900 s) 4345856,261120,7591936,1748992");
+ assertNotNull(descriptor.getWriteHistory());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testWriteHistory3012() throws DescriptorParseException {
+ DescriptorBuilder.createWithWriteHistoryLine("write-history "
+ + "3012-01-01 03:51:44 (900 s) 4345856,261120,7591936,1748992");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testWriteHistoryNoSeconds()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithWriteHistoryLine("write-history "
+ + "2012-01-01 03:51 (900 s) 4345856,261120,7591936,1748992");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testWriteHistoryNoParathenses()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithWriteHistoryLine("write-history "
+ + "2012-01-01 03:51:44 900 s 4345856,261120,7591936,1748992");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testWriteHistoryNoSpaceSeconds()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithWriteHistoryLine("write-history "
+ + "2012-01-01 03:51:44 (900s) 4345856,261120,7591936,1748992");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testWriteHistoryTrailingComma()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithWriteHistoryLine("write-history "
+ + "2012-01-01 03:51:44 (900 s) 4345856,261120,7591936,");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testWriteHistoryOneTwoThree()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithWriteHistoryLine("write-history "
+ + "2012-01-01 03:51:44 (900 s) one,two,three");
+ }
+
+ @Test()
+ public void testWriteHistoryNoValuesSpace()
+ throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithWriteHistoryLine("write-history 2012-01-01 03:51:44 "
+ + "(900 s) ");
+ assertEquals(900, (long) descriptor.getWriteHistory().
+ getIntervalLength());
+ assertTrue(descriptor.getWriteHistory().getBandwidthValues().
+ isEmpty());
+ }
+
+ @Test()
+ public void testWriteHistoryNoValuesNoSpace()
+ throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithWriteHistoryLine("write-history 2012-01-01 03:51:44 "
+ + "(900 s)");
+ assertEquals(900, (long) descriptor.getWriteHistory().
+ getIntervalLength());
+ assertTrue(descriptor.getWriteHistory().getBandwidthValues().
+ isEmpty());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testWriteHistoryNoS() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithWriteHistoryLine("write-history 2012-01-01 03:51:44 "
+ + "(900 ");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testWriteHistoryTrailingNumber()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithWriteHistoryLine("write-history "
+ + "2012-01-01 03:51:44 (900 s) 4345856 1");
+ }
+
+ @Test()
+ public void testWriteHistory1800Seconds()
+ throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithWriteHistoryLine("write-history 2012-01-01 03:51:44 "
+ + "(1800 s) 4345856");
+ assertEquals(1800L, (long) descriptor.getWriteHistory().
+ getIntervalLength());
+ }
+
+ @Test()
+ public void testReadHistory() throws DescriptorParseException {
+ String readHistoryLine = "read-history 2012-01-01 03:51:44 (900 s) "
+ + "4268032,139264,7797760,1415168";
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithReadHistoryLine(readHistoryLine);
+ assertNotNull(descriptor.getReadHistory());
+ BandwidthHistory parsedReadHistory = descriptor.getReadHistory();
+ assertEquals(readHistoryLine, parsedReadHistory.getLine());
+ assertEquals(1325389904000L, (long) parsedReadHistory.
+ getHistoryEndMillis());
+ assertEquals(900L, (long) parsedReadHistory.getIntervalLength());
+ SortedMap<Long, Long> bandwidthValues = parsedReadHistory.
+ getBandwidthValues();
+ assertEquals(4268032L, (long) bandwidthValues.remove(1325387204000L));
+ assertEquals(139264L, (long) bandwidthValues.remove(1325388104000L));
+ assertEquals(7797760L, (long) bandwidthValues.remove(1325389004000L));
+ assertEquals(1415168L, (long) bandwidthValues.remove(1325389904000L));
+ assertTrue(bandwidthValues.isEmpty());
+ }
+
+ /* TODO There are some old server descriptors with " read-history"
+ * lines. Find out if these were spec-compliant and if other lines may
+ * start with leading spaces, too. */
+ @Test(expected = DescriptorParseException.class)
+ public void testReadHistoryLeadingSpace()
+ throws DescriptorParseException {
+ String readHistoryLine = " read-history 2012-01-01 03:51:44 (900 s) "
+ + "4268032,139264,7797760,1415168";
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithReadHistoryLine(readHistoryLine);
+ }
+
+ @Test()
+ public void testEventdnsOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithEventdnsLine("opt eventdns true");
+ assertTrue(descriptor.getUsesEnhancedDnsLogic());
+ }
+
+ @Test()
+ public void testEventdnsTrue() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithEventdnsLine("eventdns true");
+ assertTrue(descriptor.getUsesEnhancedDnsLogic());
+ }
+
+ @Test()
+ public void testEventdnsFalse() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithEventdnsLine("eventdns false");
+ assertFalse(descriptor.getUsesEnhancedDnsLogic());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testEventdns1() throws DescriptorParseException {
+ DescriptorBuilder.createWithEventdnsLine("eventdns 1");
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testEventdnsNo() throws DescriptorParseException {
+ DescriptorBuilder.createWithEventdnsLine("eventdns no");
+ }
+
+ @Test()
+ public void testCachesExtraInfoOpt() throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithCachesExtraInfoLine("opt caches-extra-info");
+ assertTrue(descriptor.getCachesExtraInfo());
+ }
+
+ @Test()
+ public void testCachesExtraInfoNoSpace()
+ throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithCachesExtraInfoLine("caches-extra-info");
+ assertTrue(descriptor.getCachesExtraInfo());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testCachesExtraInfoTrue() throws DescriptorParseException {
+ DescriptorBuilder.createWithCachesExtraInfoLine("caches-extra-info "
+ + "true");
+ }
+
+ @Test()
+ public void testAllowSingleHopExitsOpt()
+ throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithCachesExtraInfoLine("opt allow-single-hop-exits");
+ assertTrue(descriptor.getAllowSingleHopExits());
+ }
+
+ @Test()
+ public void testAllowSingleHopExitsNoSpace()
+ throws DescriptorParseException {
+ ServerDescriptor descriptor = DescriptorBuilder.
+ createWithCachesExtraInfoLine("allow-single-hop-exits");
+ assertTrue(descriptor.getAllowSingleHopExits());
+ }
+
+ @Test(expected = DescriptorParseException.class)
+ public void testAllowSingleHopExitsTrue()
+ throws DescriptorParseException {
+ DescriptorBuilder.createWithCachesExtraInfoLine(
+ "allow-single-hop-exits true");
+ }
+}
+
1
0

12 Jan '12
commit ad10cd9ac88dac0de65c336448b5b639292ee6d0
Author: Karsten Loesing <karsten.loesing(a)gmx.net>
Date: Thu Jan 12 10:21:16 2012 +0100
Enable bridge descriptor parsing.
---
.../torproject/descriptor/impl/DescriptorImpl.java | 10 ++++------
.../descriptor/impl/ExtraInfoDescriptorImpl.java | 20 +++++++++++++++++---
.../descriptor/impl/ServerDescriptorImpl.java | 9 ++++-----
.../impl/RelayNetworkStatusVoteImplTest.java | 2 +-
.../descriptor/impl/ServerDescriptorImplTest.java | 16 ----------------
5 files changed, 26 insertions(+), 31 deletions(-)
diff --git a/src/org/torproject/descriptor/impl/DescriptorImpl.java b/src/org/torproject/descriptor/impl/DescriptorImpl.java
index 259a1de..233b2df 100644
--- a/src/org/torproject/descriptor/impl/DescriptorImpl.java
+++ b/src/org/torproject/descriptor/impl/DescriptorImpl.java
@@ -65,14 +65,12 @@ public abstract class DescriptorImpl implements Descriptor {
rawDescriptorBytes, fileName));
} else if (firstLines.startsWith("router ") ||
firstLines.contains("\nrouter ")) {
- /* TODO Implement me.
- parsedDescriptors.addAll(BridgeServerDescriptorImpl.
- parseDescriptors(rawDescriptorBytes)); */
+ parsedDescriptors.addAll(ServerDescriptorImpl.
+ parseDescriptors(rawDescriptorBytes));
} else if (firstLines.startsWith("extra-info ") ||
firstLines.contains("\nextra-info ")) {
- /* TODO Implement me.
- parsedDescriptors.addAll(BridgeExtraInfoDescriptorImpl.
- parseDescriptors(rawDescriptorBytes)); */
+ parsedDescriptors.addAll(ExtraInfoDescriptorImpl.
+ parseDescriptors(rawDescriptorBytes));
} else {
throw new DescriptorParseException("Could not detect bridge "
+ "descriptor type in descriptor starting with '" + firstLines
diff --git a/src/org/torproject/descriptor/impl/ExtraInfoDescriptorImpl.java b/src/org/torproject/descriptor/impl/ExtraInfoDescriptorImpl.java
index 6dae9eb..dc9f521 100644
--- a/src/org/torproject/descriptor/impl/ExtraInfoDescriptorImpl.java
+++ b/src/org/torproject/descriptor/impl/ExtraInfoDescriptorImpl.java
@@ -46,7 +46,7 @@ public class ExtraInfoDescriptorImpl extends DescriptorImpl
super(descriptorBytes);
this.parseDescriptorBytes();
Set<String> exactlyOnceKeywords = new HashSet<String>(Arrays.asList((
- "extra-info,published,router-signature").split(",")));
+ "extra-info,published").split(",")));
this.checkExactlyOnceKeywords(exactlyOnceKeywords);
Set<String> atMostOnceKeywords = new HashSet<String>(Arrays.asList((
"read-history,write-history,geoip-db-digest,dirreq-stats-end,"
@@ -58,12 +58,12 @@ public class ExtraInfoDescriptorImpl extends DescriptorImpl
+ "cell-processed-cells,cell-queued-cells,cell-time-in-queue,"
+ "cell-circuits-per-decile,conn-bi-direct,exit-stats-end,"
+ "exit-kibibytes-written,exit-kibibytes-read,"
- + "exit-streams-opened").split(",")));
+ + "exit-streams-opened,bridge-stats-end,bridge-stats-ips,"
+ + "router-signature").split(",")));
this.checkAtMostOnceKeywords(atMostOnceKeywords);
/* TODO Add more checks to see that only statistics details lines are
* included with corresponding statistics interval lines. */
this.checkFirstKeyword("extra-info");
- this.checkLastKeyword("router-signature");
return;
}
@@ -147,6 +147,10 @@ public class ExtraInfoDescriptorImpl extends DescriptorImpl
this.parseExitKibibytesReadLine(line, lineNoOpt, partsNoOpt);
} else if (keyword.equals("exit-streams-opened")) {
this.parseExitStreamsOpenedLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("bridge-stats-end")) {
+ this.parseBridgeStatsEndLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("bridge-ips")) {
+ this.parseBridgeStatsIpsLine(line, lineNoOpt, partsNoOpt);
} else if (keyword.equals("router-signature")) {
this.parseRouterSignatureLine(line, lineNoOpt, partsNoOpt);
} else if (line.startsWith("-----BEGIN")) {
@@ -353,6 +357,16 @@ public class ExtraInfoDescriptorImpl extends DescriptorImpl
/* TODO Implement me. */
}
+ private void parseBridgeStatsEndLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseBridgeStatsIpsLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
private void parseRouterSignatureLine(String line, String lineNoOpt,
String[] partsNoOpt) throws DescriptorParseException {
if (!lineNoOpt.equals("router-signature")) {
diff --git a/src/org/torproject/descriptor/impl/ServerDescriptorImpl.java b/src/org/torproject/descriptor/impl/ServerDescriptorImpl.java
index 878955e..411e8c9 100644
--- a/src/org/torproject/descriptor/impl/ServerDescriptorImpl.java
+++ b/src/org/torproject/descriptor/impl/ServerDescriptorImpl.java
@@ -42,18 +42,17 @@ public class ServerDescriptorImpl extends DescriptorImpl
throws DescriptorParseException {
super(descriptorBytes);
this.parseDescriptorBytes();
- Set<String> exactlyOnceKeywords = new HashSet<String>(Arrays.asList((
- "router,bandwidth,published,onion-key,signing-key,"
- + "router-signature").split(",")));
+ Set<String> exactlyOnceKeywords = new HashSet<String>(Arrays.asList(
+ "router,bandwidth,published".split(",")));
this.checkExactlyOnceKeywords(exactlyOnceKeywords);
Set<String> atMostOnceKeywords = new HashSet<String>(Arrays.asList((
"platform,fingerprint,hibernating,uptime,contact,family,"
+ "read-history,write-history,eventdns,caches-extra-info,"
+ "extra-info-digest,hidden-service-dir,protocols,"
- + "allow-single-hop-exits").split(",")));
+ + "allow-single-hop-exits,onion-key,signing-key,"
+ + "router-signature").split(",")));
this.checkAtMostOnceKeywords(atMostOnceKeywords);
this.checkFirstKeyword("router");
- this.checkLastKeyword("router-signature");
if (this.getKeywordCount("accept") == 0 &&
this.getKeywordCount("reject") == 0) {
throw new DescriptorParseException("Either keyword 'accept' or "
diff --git a/test/org/torproject/descriptor/impl/RelayNetworkStatusVoteImplTest.java b/test/org/torproject/descriptor/impl/RelayNetworkStatusVoteImplTest.java
index 7618fff..ffacc9f 100644
--- a/test/org/torproject/descriptor/impl/RelayNetworkStatusVoteImplTest.java
+++ b/test/org/torproject/descriptor/impl/RelayNetworkStatusVoteImplTest.java
@@ -687,7 +687,7 @@ public class RelayNetworkStatusVoteImplTest {
+ "208.83.223.34 443 80");
}
- @Test(expected = DescriptorParseException.class)
+ @Test()
public void testFingerprintLowerCase() throws DescriptorParseException {
VoteBuilder.createWithDirSourceLine("dir-source urras "
+ "80550987e1d626e3eba5e5e75a458de0626d088c 208.83.223.34 "
diff --git a/test/org/torproject/descriptor/impl/ServerDescriptorImplTest.java b/test/org/torproject/descriptor/impl/ServerDescriptorImplTest.java
index c0721f5..f699694 100644
--- a/test/org/torproject/descriptor/impl/ServerDescriptorImplTest.java
+++ b/test/org/torproject/descriptor/impl/ServerDescriptorImplTest.java
@@ -609,11 +609,6 @@ public class ServerDescriptorImplTest {
assertNull(descriptor.getExtraInfoDigest());
}
- @Test(expected = DescriptorParseException.class)
- public void testOnionKeyMissing() throws DescriptorParseException {
- DescriptorBuilder.createWithOnionKeyLines(null);
- }
-
@Test()
public void testOnionKeyOpt() throws DescriptorParseException {
ServerDescriptor descriptor = DescriptorBuilder.
@@ -626,11 +621,6 @@ public class ServerDescriptorImplTest {
+ "-----END RSA PUBLIC KEY-----");
}
- @Test(expected = DescriptorParseException.class)
- public void testSigningKeyMissing() throws DescriptorParseException {
- DescriptorBuilder.createWithSigningKeyLines(null);
- }
-
@Test()
public void testSigningKeyOpt() throws DescriptorParseException {
ServerDescriptor descriptor = DescriptorBuilder.
@@ -749,12 +739,6 @@ public class ServerDescriptorImplTest {
DescriptorBuilder.createWithExitPolicyLines(null);
}
- @Test(expected = DescriptorParseException.class)
- public void testRouterSignatureMissing()
- throws DescriptorParseException {
- DescriptorBuilder.createWithRouterSignatureLines(null);
- }
-
@Test()
public void testRouterSignatureOpt()
throws DescriptorParseException {
1
0

[metrics-lib/master] Recognize geoip-* lines in extra-info descriptors.
by karsten@torproject.org 12 Jan '12
by karsten@torproject.org 12 Jan '12
12 Jan '12
commit a994451ca0f0d93408b63332193794340c452b10
Author: Karsten Loesing <karsten.loesing(a)gmx.net>
Date: Thu Jan 12 08:13:18 2012 +0100
Recognize geoip-* lines in extra-info descriptors.
---
.../impl/RelayExtraInfoDescriptorImpl.java | 14 ++++++++++++++
1 files changed, 14 insertions(+), 0 deletions(-)
diff --git a/src/org/torproject/descriptor/impl/RelayExtraInfoDescriptorImpl.java b/src/org/torproject/descriptor/impl/RelayExtraInfoDescriptorImpl.java
index 61e5f0f..a07caec 100644
--- a/src/org/torproject/descriptor/impl/RelayExtraInfoDescriptorImpl.java
+++ b/src/org/torproject/descriptor/impl/RelayExtraInfoDescriptorImpl.java
@@ -88,6 +88,10 @@ public class RelayExtraInfoDescriptorImpl extends DescriptorImpl
this.parseWriteHistoryLine(line, lineNoOpt, partsNoOpt);
} else if (keyword.equals("geoip-db-digest")) {
this.parseGeoipDbDigestLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("geoip-start-time")) {
+ this.parseGeoipStartTimeLine(line, lineNoOpt, partsNoOpt);
+ } else if (keyword.equals("geoip-client-origins")) {
+ this.parseGeoipClientOriginsLine(line, lineNoOpt, partsNoOpt);
} else if (keyword.equals("dirreq-stats-end")) {
this.parseDirreqStatsEndLine(line, lineNoOpt, partsNoOpt);
} else if (keyword.equals("dirreq-v2-ips")) {
@@ -200,6 +204,16 @@ public class RelayExtraInfoDescriptorImpl extends DescriptorImpl
/* TODO Implement me. */
}
+ private void parseGeoipStartTimeLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
+ private void parseGeoipClientOriginsLine(String line, String lineNoOpt,
+ String[] partsNoOpt) throws DescriptorParseException {
+ /* TODO Implement me. */
+ }
+
private void parseDirreqStatsEndLine(String line, String lineNoOpt,
String[] partsNoOpt) throws DescriptorParseException {
/* TODO Implement me. */
1
0
commit 411cf8f71455926db119259545ac8d5c80a5fb58
Author: Nick Mathewson <nickm(a)torproject.org>
Date: Wed Jan 11 15:41:46 2012 -0500
Make openssl 0.9.8l log message accurate
fixes 4837
---
changes/bug4837 | 4 ++++
src/common/tortls.c | 6 ++++--
2 files changed, 8 insertions(+), 2 deletions(-)
diff --git a/changes/bug4837 b/changes/bug4837
new file mode 100644
index 0000000..16a61d1
--- /dev/null
+++ b/changes/bug4837
@@ -0,0 +1,4 @@
+ o Minor bugfixes:
+ - Fix the log message describing how we work around discovering
+ that our version is the ill-fated OpenSSL 0.9.8l. Fixes bug
+ 4837; bugfix on 0.2.2.9-alpha.
diff --git a/src/common/tortls.c b/src/common/tortls.c
index 28bb3f9..908337f 100644
--- a/src/common/tortls.c
+++ b/src/common/tortls.c
@@ -475,8 +475,10 @@ tor_tls_init(void)
* a test of intelligence and determination.
*/
if (version > OPENSSL_V(0,9,8,'k') && version <= OPENSSL_V(0,9,8,'l')) {
- log_notice(LD_GENERAL, "OpenSSL %s looks like version 0.9.8l; "
- "I will try SSL3_FLAGS to enable renegotation.",
+ log_notice(LD_GENERAL, "OpenSSL %s looks like version 0.9.8l, but "
+ "some vendors have backported renegotiation code from "
+ "0.9.8m without updating the version number. "
+ "I will try SSL3_FLAGS and SSL_OP to enable renegotation.",
SSLeay_version(SSLEAY_VERSION));
use_unsafe_renegotiation_flag = 1;
use_unsafe_renegotiation_op = 1;
1
0

11 Jan '12
commit 0ffb7cb470ecc0310ba1f98ef47934f68a126e17
Author: Translation commit bot <translation(a)torproject.org>
Date: Wed Jan 11 19:15:16 2012 +0000
Update translations for vidalia
---
ca/qt_ca.po | 84 ++++++++++++++++++++++++++++++++--------------------------
1 files changed, 46 insertions(+), 38 deletions(-)
diff --git a/ca/qt_ca.po b/ca/qt_ca.po
index 87bc48c..ec991de 100644
--- a/ca/qt_ca.po
+++ b/ca/qt_ca.po
@@ -7,7 +7,7 @@ msgstr ""
"Project-Id-Version: The Tor Project\n"
"Report-Msgid-Bugs-To: https://trac.torproject.org/projects/tor\n"
"POT-Creation-Date: 2008-08-20 03:25+0000\n"
-"PO-Revision-Date: 2012-01-11 18:43+0000\n"
+"PO-Revision-Date: 2012-01-11 18:49+0000\n"
"Last-Translator: Gerard Farràs Ballabriga <>\n"
"Language-Team: none\n"
"MIME-Version: 1.0\n"
@@ -30,12 +30,12 @@ msgstr "L'executable '%1' requereix Qt %2 i s'ha trobat Qt %3."
#: qmessagebox.h:321
msgctxt "QApplication"
msgid "Incompatible Qt Library Error"
-msgstr ""
+msgstr "Error d'incompatibilitat amb la llibreria Qt"
#: qapplication.cpp:2095
msgctxt "QApplication"
msgid "QT_LAYOUT_DIRECTION"
-msgstr ""
+msgstr "QT_LAYOUT_DIRECTION"
#: qaccessibleobject.cpp:350
msgctxt "QApplication"
@@ -245,27 +245,27 @@ msgstr "Enrere"
#: ui_qfiledialog.h:274
msgctxt "QFileDialog"
msgid "Parent Directory"
-msgstr ""
+msgstr "Directori superior"
#: ui_qfiledialog.h:284
msgctxt "QFileDialog"
msgid "List View"
-msgstr ""
+msgstr "Vista com a llistat"
#: ui_qfiledialog.h:289
msgctxt "QFileDialog"
msgid "Detail View"
-msgstr ""
+msgstr "Vista en detall"
#: ui_qfiledialog.h:292
msgctxt "QFileDialog"
msgid "Files of type:"
-msgstr ""
+msgstr "Tipus de fitxers:"
#: qfiledialog.cpp:883
msgctxt "QFileDialog"
msgid "Directory:"
-msgstr ""
+msgstr "Directori:"
#: qfiledialog.cpp:2476
msgctxt "QFileDialog"
@@ -274,6 +274,10 @@ msgid ""
"Directory not found.\n"
"Please verify the correct directory name was given."
msgstr ""
+"%1\n"
+"\n"
+"Directori no trobat.\n"
+"Si us plau, verifiqueu que s'ha proporcionat un nom de directori correcte."
#: qfiledialog.cpp:2281
msgctxt "QFileDialog"
@@ -281,96 +285,98 @@ msgid ""
"'%1' is write protected.\n"
"Do you want to delete it anyway?"
msgstr ""
+"'%1' està protegit per escriptura.\n"
+"El desitgeu suprimir igualment?"
#: qfiledialog.cpp:2286
msgctxt "QFileDialog"
msgid "Are sure you want to delete '%1'?"
-msgstr ""
+msgstr "Esteu segur que desitgeu suprimir '%1'?"
#: qfiledialog.cpp:2299
msgctxt "QFileDialog"
msgid "Could not delete directory."
-msgstr ""
+msgstr "Podria no suprimir aquest directori."
#: qfiledialog_win.cpp:128
msgctxt "QFileDialog"
msgid "All Files (*.*)"
-msgstr ""
+msgstr "Tots els fitxers (*.*)"
#: qfiledialog.cpp:437
msgctxt "QFileDialog"
msgid "Save As"
-msgstr ""
+msgstr "Desa com a"
#: qfileiconprovider.cpp:379
msgctxt "QFileDialog"
msgid "Drive"
-msgstr ""
+msgstr "Unitat"
#: qfileiconprovider.cpp:383
msgctxt "QFileDialog"
msgid "File"
-msgstr ""
+msgstr "Fitxer"
#: qfileiconprovider.cpp:412
msgctxt "QFileDialog"
msgid "Unknown"
-msgstr ""
+msgstr "Desconegut"
#: qfiledialog.cpp:439
msgctxt "QFileDialog"
msgid "Find Directory"
-msgstr ""
+msgstr "Cerca directori"
#: qfiledialog.cpp:458
msgctxt "QFileDialog"
msgid "Show "
-msgstr ""
+msgstr "Mostra"
#: ui_qfiledialog.h:269
msgctxt "QFileDialog"
msgid "Forward"
-msgstr ""
+msgstr "Reenvia"
#: qfiledialog.cpp:2137
msgctxt "QFileDialog"
msgid "New Folder"
-msgstr ""
+msgstr "Nova carpeta"
#: qfiledialog.cpp:465
msgctxt "QFileDialog"
msgid "&New Folder"
-msgstr ""
+msgstr "&Nova carpeta"
#: qfiledialog.cpp:917
msgctxt "QFileDialog"
msgid "&Choose"
-msgstr ""
+msgstr "&Escolliu"
#: qsidebar.cpp:388
msgctxt "QFileDialog"
msgid "Remove"
-msgstr ""
+msgstr "Suprimeix"
#: qfiledialog.cpp:886
msgctxt "QFileDialog"
msgid "File &name:"
-msgstr ""
+msgstr "Nom de fitxer:"
#: ui_qfiledialog.h:261
msgctxt "QFileDialog"
msgid "Look in:"
-msgstr ""
+msgstr "Mira a:"
#: ui_qfiledialog.h:279
msgctxt "QFileDialog"
msgid "Create New Folder"
-msgstr ""
+msgstr "Crea nova carpeta"
#: qfilesystemmodel.cpp:761
msgctxt "QFileSystemModel"
msgid "Invalid filename"
-msgstr ""
+msgstr "Nom de fitxer invàlid"
#: qfilesystemmodel.cpp:763
msgctxt "QFileSystemModel"
@@ -378,65 +384,67 @@ msgid ""
"<b>The name \"%1\" can not be used.</b><p>Try using another name, with fewer"
" characters or no punctuations marks."
msgstr ""
+"<b>No es pot utilitzar el nom \"%1\".</b><p>Intenteu utilitzar un altre nom,"
+" amb menys caracters o sense marques de puntuació."
#: qfilesystemmodel.cpp:832
msgctxt "QFileSystemModel"
msgid "Name"
-msgstr ""
+msgstr "Nom"
#: qfilesystemmodel.cpp:834
msgctxt "QFileSystemModel"
msgid "Size"
-msgstr ""
+msgstr "Mida"
#: qfilesystemmodel.cpp:838
msgctxt "QFileSystemModel"
msgid "Kind"
-msgstr ""
+msgstr "Tipus"
#: qfilesystemmodel.cpp:840
msgctxt "QFileSystemModel"
msgid "Type"
-msgstr ""
+msgstr "Tipus"
#: qfilesystemmodel.cpp:847
msgctxt "QFileSystemModel"
msgid "Date Modified"
-msgstr ""
+msgstr "Data de modificació"
#: qfilesystemmodel_p.h:198
msgctxt "QFileSystemModel"
msgid "My Computer"
-msgstr ""
+msgstr "El meu ordinador"
#: qfilesystemmodel_p.h:200
msgctxt "QFileSystemModel"
msgid "Computer"
-msgstr ""
+msgstr "Ordinador"
#: qfilesystemmodel.cpp:677
msgctxt "QFileSystemModel"
msgid "%1 TB"
-msgstr ""
+msgstr "%1 TB"
#: qfilesystemmodel.cpp:679
msgctxt "QFileSystemModel"
msgid "%1 GB"
-msgstr ""
+msgstr "%1 GB"
#: qfilesystemmodel.cpp:681
msgctxt "QFileSystemModel"
msgid "%1 MB"
-msgstr ""
+msgstr "%1 MB"
#: qfilesystemmodel.cpp:683
msgctxt "QFileSystemModel"
msgid "%1 KB"
-msgstr ""
+msgstr "%1 KB"
#: qfilesystemmodel.cpp:684
msgctxt "QFileSystemModel"
msgid "%1 bytes"
-msgstr ""
+msgstr "%1 bytes"
1
0

11 Jan '12
commit 2b140dfe716a9f0b1414281ee77a947affa89052
Author: Translation commit bot <translation(a)torproject.org>
Date: Wed Jan 11 18:45:16 2012 +0000
Update translations for vidalia
---
ca/qt_ca.po | 7 +++--
ca/vidalia_ca.po | 66 +++++++++++++++++++++++++++++++++++++++++++++--------
2 files changed, 60 insertions(+), 13 deletions(-)
diff --git a/ca/qt_ca.po b/ca/qt_ca.po
index a73f11e..87bc48c 100644
--- a/ca/qt_ca.po
+++ b/ca/qt_ca.po
@@ -1,13 +1,14 @@
#
# Translators:
+# Gerard Farràs Ballabriga <>, 2012.
# runasand <runa.sandvik(a)gmail.com>, 2011.
msgid ""
msgstr ""
"Project-Id-Version: The Tor Project\n"
"Report-Msgid-Bugs-To: https://trac.torproject.org/projects/tor\n"
"POT-Creation-Date: 2008-08-20 03:25+0000\n"
-"PO-Revision-Date: 2010-12-05 19:59+0000\n"
-"Last-Translator: Automatically generated\n"
+"PO-Revision-Date: 2012-01-11 18:43+0000\n"
+"Last-Translator: Gerard Farràs Ballabriga <>\n"
"Language-Team: none\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
@@ -24,7 +25,7 @@ msgstr "Activa"
#: qmessagebox.h:319
msgctxt "QApplication"
msgid "Executable '%1' requires Qt %2, found Qt %3."
-msgstr ""
+msgstr "L'executable '%1' requereix Qt %2 i s'ha trobat Qt %3."
#: qmessagebox.h:321
msgctxt "QApplication"
diff --git a/ca/vidalia_ca.po b/ca/vidalia_ca.po
index 168460d..9d32a7a 100755
--- a/ca/vidalia_ca.po
+++ b/ca/vidalia_ca.po
@@ -6,7 +6,7 @@ msgstr ""
"Project-Id-Version: The Tor Project\n"
"Report-Msgid-Bugs-To: https://trac.torproject.org/projects/tor\n"
"POT-Creation-Date: 2011-09-07 14:40+0000\n"
-"PO-Revision-Date: 2012-01-11 17:58+0000\n"
+"PO-Revision-Date: 2012-01-11 18:40+0000\n"
"Last-Translator: Gerard Farràs Ballabriga <>\n"
"Language-Team: translations(a)vidalia-project.net\n"
"MIME-Version: 1.0\n"
@@ -3284,6 +3284,9 @@ msgid ""
"software, which may contain important security, reliability and performance "
"fixes."
msgstr ""
+"Esteu executant la versió \"%1\" del Tor, la qual ja no està suportada. Si "
+"us plau, actualitzeu-vos a la versió més recent, que conté correccions "
+"relacionades amb la seguretat, la fiabilitat i el rendiment. "
msgctxt "StatusEventWidget"
msgid ""
@@ -3292,30 +3295,38 @@ msgid ""
"version of the software, which may contain important security, reliability "
"and performance fixes."
msgstr ""
+"Esteu executant la versió \"%1\" del Tor, que probablement ja no funciona "
+"amb la xarxa de Tor actual. Si us plau, actualitze-vos a la versió més "
+"recent, que conté correccions relacionades amb la seguretat, la fibilitat i "
+"el rendiment."
msgctxt "StatusEventWidget"
msgid "Your Tor Software is Out-of-date"
-msgstr ""
+msgstr "El seu Tor està desactualitzat"
msgctxt "StatusEventWidget"
msgid "Connected to the Tor Network"
-msgstr ""
+msgstr "S'ha connectat a la xarxa Tor"
msgctxt "StatusEventWidget"
msgid ""
"We were able to successfully establish a connection to the Tor network. You "
"can now configure your applications to use the Internet anonymously."
msgstr ""
+"Estem en condicions de connectar-nos correctament a la xarxa Tor. Ara, podeu"
+" configurar aplicacions per tal d'utilitzar Internet de manera anònima."
msgctxt "StatusEventWidget"
msgid "Tor Software Error"
-msgstr ""
+msgstr "Error del Tor"
msgctxt "StatusEventWidget"
msgid ""
"The Tor software encountered an internal bug. Please report the following "
"error message to the Tor developers at bugs.torproject.org: \"%1\""
msgstr ""
+"El Tor ha topat amb un error de programació. Si us plau, informeu als "
+"desenvolupadors de l'error següent a bugs.torproject.org: \"%1\""
msgctxt "StatusEventWidget"
msgid ""
@@ -3324,6 +3335,10 @@ msgid ""
"will not be able to function. Please verify your computer displays the "
"correct time."
msgstr ""
+"El Tor ha determinat que el rellotge del seu sistema està establert %1 "
+"seconds en el passat que el de la font de \"%2\". Si l'hora del seu rellotge"
+" no és correcta, el Tor no podrà funcionar correctament. Si us plau, "
+"verifiqueu que el seu sistema tingui l'hrora correcta."
msgctxt "StatusEventWidget"
msgid ""
@@ -3332,10 +3347,14 @@ msgid ""
"will not be able to function. Please verify your computer displays the "
"correct time."
msgstr ""
+"El Tor ha determinat que el rellotge del seu sistema està establert %1 "
+"seconds en el futur que el de la font de \"%2\". Si l'hora del seu rellotge "
+"no és correcta, el Tor no podrà funcionar correctament. Si us plau, "
+"verifiqueu que el seu sistema tingui l'hrora correcta."
msgctxt "StatusEventWidget"
msgid "Your Computer's Clock is Potentially Incorrect"
-msgstr ""
+msgstr "L'hora del seu sistema és potencialment incorrecta"
msgctxt "StatusEventWidget"
msgid ""
@@ -3344,6 +3363,10 @@ msgid ""
"information over the Tor network is dangerous and not recommended. For your "
"protection, Tor has automatically closed this connection."
msgstr ""
+"Una de les aplicacions del seu sistema ha intentat realitzar una connexió no"
+" xifrada al Tor a través del port %1. Enviar informació en clar a través de "
+"la xarxa Tor és perillós i no està recomanat. Per la seva protecció, el Tor "
+"ha tancat de manera automàtica aquesta connexió."
msgctxt "StatusEventWidget"
msgid ""
@@ -3351,10 +3374,13 @@ msgid ""
"unencrypted connection through Tor to port %1. Sending unencrypted "
"information over the Tor network is dangerous and not recommended."
msgstr ""
+"Una de les aplicacions del seu sistema ha intentat realitzar una connexió no"
+" xifrada al Tor a través del port %1. Enviar informació en clar a través de "
+"la xarxa Tor és perillós i no està recomanat. "
msgctxt "StatusEventWidget"
msgid "Potentially Dangerous Connection!"
-msgstr ""
+msgstr "Connexió potencialment perillosa!"
msgctxt "StatusEventWidget"
msgid ""
@@ -3363,10 +3389,15 @@ msgid ""
"ensure you configure your applications to use only SOCKS4a or SOCKS5 with "
"remote hostname resolution."
msgstr ""
+"Una de les vostres aplicacions ha establert una connexió a través del Tor a "
+"\"%1\" utilitzant un protocol que podria proporcionar informació sobre la "
+"seva destinació. Si us plau, assegureu-vos que heu configurat les vostres "
+"aplicacions per tal d'utilitzar solament SOCKS4 i SOCKS5 amb resolució "
+"d'objectiu remot."
msgctxt "StatusEventWidget"
msgid "Unknown SOCKS Protocol"
-msgstr ""
+msgstr "Protocol SOCKS desconegut"
msgctxt "StatusEventWidget"
msgid ""
@@ -3374,10 +3405,14 @@ msgid ""
" protocol that Tor does not understand. Please ensure you configure your "
"applications to use only SOCKS4a or SOCKS5 with remote hostname resolution."
msgstr ""
+"Una de les vostres aplicacions ha establert una connexió a través del Tor "
+"emprant un protocol que aquest no compren. Si us plau, assegureu-vos que heu"
+" configurat les vostres aplicacions per tal d'utilitzar solament SOCKS4 i "
+"SOCKS5 amb resolució d'objectiu remot."
msgctxt "StatusEventWidget"
msgid "Invalid Destination Hostname"
-msgstr ""
+msgstr "Destinació d'objectiu invàlida"
msgctxt "StatusEventWidget"
msgid ""
@@ -3385,10 +3420,13 @@ msgid ""
"\"%1\", which Tor does not recognize as a valid hostname. Please check your "
"application's configuration."
msgstr ""
+"Una de les vostres aplicacions ha intentat establir una connexió via el Tor "
+"a \"%1\", que aquest no reconeix com a objectiu vàlid. Si us plau, reviseu "
+"la configuració de la seva aplicació."
msgctxt "StatusEventWidget"
msgid "External IP Address Changed"
-msgstr ""
+msgstr "L'adreça IP externa s'ha canviat"
msgctxt "StatusEventWidget"
msgid ""
@@ -3399,7 +3437,7 @@ msgstr ""
msgctxt "StatusEventWidget"
msgid "DNS Hijacking Detected"
-msgstr ""
+msgstr "Detecció de DNS Hijacking"
msgctxt "StatusEventWidget"
msgid ""
@@ -3407,6 +3445,10 @@ msgid ""
" that do not exist. Some ISPs and other DNS providers, such as OpenDNS, are "
"known to do this in order to display their own search or advertising pages."
msgstr ""
+"El Tor ha detectat que el seu proveïdor de DNS està proveïnt de respostes "
+"falses per dominis que no existeixen. És conegut que alguns ISPs i d'altres "
+"proveïdors de DNS, com per exemple, OpenDNS, fan això per tal de mostrar les"
+" seves pròpies pàgines de cerca o de publicitat."
msgctxt "StatusEventWidget"
msgid ""
@@ -3414,6 +3456,10 @@ msgid ""
"known domains. Since clients rely on Tor network relays to provide accurate "
"DNS repsonses, your relay will not be configured as an exit relay."
msgstr ""
+"El Tor ha detectat que el seu proveïdor de DNS està proveïnt de respostes "
+"falses per a dominis reconeguts. Since clients rely on Tor network relays to"
+" provide accurate DNS repsonses, your relay will not be configured as an "
+"exit relay."
msgctxt "StatusEventWidget"
msgid "Checking Server Port Reachability"
1
0

11 Jan '12
commit 13c3975bc3585847dd204d074a66394786bf2007
Author: Damian Johnson <atagar(a)torproject.org>
Date: Wed Jan 11 10:20:30 2012 -0800
Testing argument to run with a tor binary
Adding a '--tor PATH' argument so the caller can select the tor binary they
want to run against.
---
run_tests.py | 12 ++++++++++--
stem/process.py | 8 ++++++--
test/runner.py | 12 +++++++-----
3 files changed, 23 insertions(+), 9 deletions(-)
diff --git a/run_tests.py b/run_tests.py
index 1b252df..f458a80 100755
--- a/run_tests.py
+++ b/run_tests.py
@@ -33,7 +33,7 @@ import stem.util.log as log
import stem.util.term as term
OPT = "uic:t:l:h"
-OPT_EXPANDED = ["unit", "integ", "config=", "targets=", "log=", "help"]
+OPT_EXPANDED = ["unit", "integ", "config=", "targets=", "log=", "tor=", "help"]
DIVIDER = "=" * 70
# Tests are ordered by the dependencies so the lowest level tests come first.
@@ -86,6 +86,7 @@ Runs tests for the stem library.
-t, --target TARGET comma separated list of extra targets for integ tests
-l, --log RUNLEVEL includes logging output with test results, runlevels:
TRACE, DEBUG, INFO, NOTICE, WARN, ERROR
+ --tor PATH custom tor binary to run testing against
-h, --help presents this help
Integration targets:
@@ -123,6 +124,7 @@ if __name__ == '__main__':
config_path = None
test_config = stem.util.conf.get_config("test")
logging_runlevel = None
+ tor_cmd = "tor"
# parses user input, noting any issues
try:
@@ -158,6 +160,12 @@ if __name__ == '__main__':
print "'%s' isn't a logging runlevel, use one of the following instead:" % arg
print " TRACE, DEBUG, INFO, NOTICE, WARN, ERROR"
sys.exit(1)
+ elif opt in ("--tor"):
+ if not os.path.exists(arg):
+ print "Unable to start tor, '%s' does not exists." % arg
+ sys.exit(1)
+
+ tor_cmd = arg
elif opt in ("-h", "--help"):
# Prints usage information and quits. This includes a listing of the
# valid integration targets.
@@ -260,7 +268,7 @@ if __name__ == '__main__':
for connection_type in connection_types:
try:
- integ_runner.start(connection_type = connection_type)
+ integ_runner.start(tor_cmd, connection_type = connection_type)
print term.format("Running tests...", term.Color.BLUE, term.Attr.BOLD)
print
diff --git a/stem/process.py b/stem/process.py
index 0bb9740..2b00117 100644
--- a/stem/process.py
+++ b/stem/process.py
@@ -13,7 +13,7 @@ import subprocess
# number of seconds before we time out our attempt to start a tor instance
DEFAULT_INIT_TIMEOUT = 90
-def launch_tor(torrc_path, completion_percent = 100, init_msg_handler = None, timeout = DEFAULT_INIT_TIMEOUT):
+def launch_tor(tor_cmd = "tor", torrc_path = None, completion_percent = 100, init_msg_handler = None, timeout = DEFAULT_INIT_TIMEOUT):
"""
Initializes a tor process. This blocks until initialization completes or we
error out.
@@ -24,6 +24,7 @@ def launch_tor(torrc_path, completion_percent = 100, init_msg_handler = None, ti
to get stuck, taking well over the default timeout.
Arguments:
+ tor_cmd (str) - command for starting tor
torrc_path (str) - location of the torrc for us to use
completion_percent (int) - percent of bootstrap completion at which
this'll return
@@ -45,7 +46,10 @@ def launch_tor(torrc_path, completion_percent = 100, init_msg_handler = None, ti
raise OSError("torrc doesn't exist (%s)" % torrc_path)
# starts a tor subprocess, raising an OSError if it fails
- tor_process = subprocess.Popen(["tor", "-f", torrc_path], stdout = subprocess.PIPE, stderr = subprocess.PIPE)
+ runtime_args = [tor_cmd]
+ if torrc_path: runtime_args += ["-f", torrc_path]
+
+ tor_process = subprocess.Popen(runtime_args, stdout = subprocess.PIPE, stderr = subprocess.PIPE)
if timeout:
def timeout_handler(signum, frame):
diff --git a/test/runner.py b/test/runner.py
index 10c4699..cfe6dbb 100644
--- a/test/runner.py
+++ b/test/runner.py
@@ -139,12 +139,13 @@ class Runner:
self._connection_type = None
self._tor_process = None
- def start(self, connection_type = DEFAULT_TOR_CONNECTION, quiet = False):
+ def start(self, tor_cmd, connection_type = DEFAULT_TOR_CONNECTION, quiet = False):
"""
Makes temporary testing resources and starts tor, blocking until it
completes.
Arguments:
+ tor_cmd (str) - command to start tor with
connection_type (TorConnection) - method for controllers to authenticate
to tor
quiet (bool) - if False then this prints status information as we start
@@ -190,7 +191,7 @@ class Runner:
try:
self._tor_cwd = os.getcwd()
self._run_setup(quiet)
- self._start_tor(quiet)
+ self._start_tor(tor_cmd, quiet)
# revert our cwd back to normal
if self._config["test.integ.target.relative_data_dir"]:
@@ -478,13 +479,14 @@ class Runner:
_print_status("failed (%s)\n\n" % exc, ERROR_ATTR, quiet)
raise OSError(exc)
- def _start_tor(self, quiet):
+ def _start_tor(self, tor_cmd, quiet):
"""
Initializes a tor process. This blocks until initialization completes or we
error out.
Arguments:
- quiet (bool) - prints status information to stdout if False
+ tor_cmd (str) - command to start tor with
+ quiet (bool) - prints status information to stdout if False
Raises:
OSError if we either fail to create the tor process or reached a timeout
@@ -503,7 +505,7 @@ class Runner:
print_init_line = lambda line: _print_status(" %s\n" % line, SUBSTATUS_ATTR, quiet)
torrc_dst = os.path.join(self._test_dir, "torrc")
- self._tor_process = stem.process.launch_tor(torrc_dst, complete_percent, print_init_line)
+ self._tor_process = stem.process.launch_tor(tor_cmd, torrc_dst, complete_percent, print_init_line)
runtime = time.time() - start_time
_print_status(" done (%i seconds)\n\n" % runtime, STATUS_ATTR, quiet)
1
0