tor-commits
Threads by month
- ----- 2025 -----
- 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
February 2012
- 21 participants
- 991 discussions

02 Feb '12
commit 445595ed4c5c82c7d39856f73076fe55bc1c28c5
Author: Translation commit bot <translation(a)torproject.org>
Date: Thu Feb 2 20:15:02 2012 +0000
Update translations for bridgedb
---
eo/bridgedb.po | 14 ++++++++++++--
1 files changed, 12 insertions(+), 2 deletions(-)
diff --git a/eo/bridgedb.po b/eo/bridgedb.po
index fe1873d..c0983de 100644
--- a/eo/bridgedb.po
+++ b/eo/bridgedb.po
@@ -3,14 +3,15 @@
# This file is distributed under the same license as the PACKAGE package.
#
# Translators:
+# <eeemsi(a)googlemail.com>, 2012.
# trio <trio(a)esperanto.org>, 2011.
msgid ""
msgstr ""
"Project-Id-Version: The Tor Project\n"
"Report-Msgid-Bugs-To: https://trac.torproject.org/projects/tor\n"
"POT-Creation-Date: 2011-01-01 07:48-0800\n"
-"PO-Revision-Date: 2011-03-22 16:45+0000\n"
-"Last-Translator: trio <trio(a)esperanto.org>\n"
+"PO-Revision-Date: 2012-02-02 20:10+0000\n"
+"Last-Translator: identity <eeemsi(a)googlemail.com>\n"
"Language-Team: LANGUAGE <LL(a)li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
@@ -59,6 +60,11 @@ msgid ""
"lots of bridge addresses, you must send this request from an email address at\n"
"one of the following domains:"
msgstr ""
+"Alia vojo por trovi adreson de publika ponto estas sendi retposxtmesagxon al"
+" bridges(a)torproject.org kun nur la linio \"get bridges\" en la korpo de la "
+"mesagxo. Tamen, por malfaciligi la malkovro de multon da pontoj al "
+"atakantoj, vi devas sendi la peton el retposxtadreso cxe unu el la sekvaj "
+"retregionoj:"
#: lib/bridgedb/I18n.py:41
msgid "[This is an automated message; please do not reply.]"
@@ -71,6 +77,10 @@ msgid ""
"will change every few days, so check back periodically if you need more\n"
"bridge addresses."
msgstr ""
+"Alia vojo por trovi adreson de publika ponto estas viziti "
+"https://bridges.torproject.org/. La respondoj, kiujn vi ricevos de tiu "
+"pagxo, sxangxigxas preskaux tage, do kontrolu ofte se vi bezonas pliajn "
+"pontadresojn."
#: lib/bridgedb/I18n.py:48
msgid "(no bridges currently available)"
1
0

02 Feb '12
commit 73541d23c78cbdd4a200f9c00962459182655d95
Author: Translation commit bot <translation(a)torproject.org>
Date: Thu Feb 2 15:45:16 2012 +0000
Update translations for vidalia
---
pt_BR/qt_pt_BR.po | 53 +++++++++++++++++++++++++++--------------------------
1 files changed, 27 insertions(+), 26 deletions(-)
diff --git a/pt_BR/qt_pt_BR.po b/pt_BR/qt_pt_BR.po
index bba6fe3..0c69e51 100644
--- a/pt_BR/qt_pt_BR.po
+++ b/pt_BR/qt_pt_BR.po
@@ -1,14 +1,15 @@
#
# Translators:
# <amimyself(a)live.co.uk>, 2011.
+# Filipe <nfscp(a)walla.com>, 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: 2011-09-01 02:56+0000\n"
-"Last-Translator: translator420 <amimyself(a)live.co.uk>\n"
+"PO-Revision-Date: 2012-02-02 15:27+0000\n"
+"Last-Translator: Filipe <nfscp(a)walla.com>\n"
"Language-Team: none\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
@@ -20,7 +21,7 @@ msgstr ""
#: qaccessibleobject.cpp:348
msgctxt "QApplication"
msgid "Activate"
-msgstr "Ativar"
+msgstr "Activar"
#: qmessagebox.h:319
msgctxt "QApplication"
@@ -35,12 +36,12 @@ msgstr "Biblioteca Qt incompatível"
#: qapplication.cpp:2095
msgctxt "QApplication"
msgid "QT_LAYOUT_DIRECTION"
-msgstr "Direção_de_Layout_QT"
+msgstr "Direcção_de_Layout_QT"
#: qaccessibleobject.cpp:350
msgctxt "QApplication"
msgid "Activates the program's main window"
-msgstr "Ativa a janela principal do programa"
+msgstr "Activa a janela principal do programa"
#: qmessagebox.cpp:2104
msgctxt "QDialogButtonBox"
@@ -50,7 +51,7 @@ msgstr "OK"
#: qdialogbuttonbox.cpp:528
msgctxt "QDialogButtonBox"
msgid "Save"
-msgstr "Salvar"
+msgstr "Gravar"
#: qdialogbuttonbox.cpp:531
msgctxt "QDialogButtonBox"
@@ -85,7 +86,7 @@ msgstr "Ajuda"
#: qdialogbuttonbox.cpp:550
msgctxt "QDialogButtonBox"
msgid "Don't Save"
-msgstr "Não salvar"
+msgstr "Não gravar"
#: qdialogbuttonbox.cpp:554
msgctxt "QDialogButtonBox"
@@ -115,7 +116,7 @@ msgstr "Não a Todas"
#: qdialogbuttonbox.cpp:569
msgctxt "QDialogButtonBox"
msgid "Save All"
-msgstr "Salvar Tudo"
+msgstr "Gravar Tudo"
#: qdialogbuttonbox.cpp:572
msgctxt "QDialogButtonBox"
@@ -140,7 +141,7 @@ msgstr "Restaurar padrão"
#: qdialogbuttonbox.cpp:552
msgctxt "QDialogButtonBox"
msgid "Close without Saving"
-msgstr "Fechar sem salvar"
+msgstr "Fechar sem gravar"
#: qdialogbuttonbox.cpp:525
msgctxt "QDialogButtonBox"
@@ -180,7 +181,7 @@ msgstr "Todos arquivos (*)"
#: qfiledialog.cpp:881
msgctxt "QFileDialog"
msgid "Directories"
-msgstr "Diretórios"
+msgstr "Directórios"
#: qfiledialog.cpp:2408
msgctxt "QFileDialog"
@@ -190,7 +191,7 @@ msgstr "&Abrir"
#: qfiledialog.cpp:919
msgctxt "QFileDialog"
msgid "&Save"
-msgstr "&Salvar"
+msgstr "&Gravar"
#: qfiledialog.cpp:435
msgctxt "QFileDialog"
@@ -215,12 +216,12 @@ msgid ""
msgstr ""
"%1\n"
"Arquivo não encontrado.\n"
-"Por favor verifique se o nome do arquivo foi corretamente informado."
+"Por favor verifique se o nome do arquivo foi correctamente introduzido."
#: qdirmodel.cpp:833
msgctxt "QFileDialog"
msgid "My Computer"
-msgstr "Meu Computador"
+msgstr "O Meu Computador"
#: qfiledialog.cpp:462
msgctxt "QFileDialog"
@@ -230,7 +231,7 @@ msgstr "&Renomear"
#: qfiledialog.cpp:463
msgctxt "QFileDialog"
msgid "&Delete"
-msgstr "&Deletar"
+msgstr "&Apagar"
#: qfiledialog.cpp:464
msgctxt "QFileDialog"
@@ -245,7 +246,7 @@ msgstr "Voltar"
#: ui_qfiledialog.h:274
msgctxt "QFileDialog"
msgid "Parent Directory"
-msgstr "Diretório Acima"
+msgstr "Directório Acima"
#: ui_qfiledialog.h:284
msgctxt "QFileDialog"
@@ -265,7 +266,7 @@ msgstr "Arquivos do tipo:"
#: qfiledialog.cpp:883
msgctxt "QFileDialog"
msgid "Directory:"
-msgstr "Diretório:"
+msgstr "Directório:"
#: qfiledialog.cpp:2476
msgctxt "QFileDialog"
@@ -275,8 +276,8 @@ msgid ""
"Please verify the correct directory name was given."
msgstr ""
"%1\n"
-"Diretório não encontrado.\n"
-"Por favor verifique se o nome do diretório foi corretamente informado."
+"Directório não encontrado.\n"
+"Por favor verifique se o nome do directório foi corretamente introduzido."
#: qfiledialog.cpp:2281
msgctxt "QFileDialog"
@@ -285,17 +286,17 @@ msgid ""
"Do you want to delete it anyway?"
msgstr ""
"'%1' é protegido contra cópia.\n"
-"Você quer deletá-lo ainda assim?"
+"Você quer realmente apagá-lo ?"
#: qfiledialog.cpp:2286
msgctxt "QFileDialog"
msgid "Are sure you want to delete '%1'?"
-msgstr "Tem certeza de que deseja deletar '%1'?"
+msgstr "Tem certeza de que deseja apagar '%1'?"
#: qfiledialog.cpp:2299
msgctxt "QFileDialog"
msgid "Could not delete directory."
-msgstr "Não foi possível deletar o diretório."
+msgstr "Não foi possível apagar o diretório."
#: qfiledialog_win.cpp:128
msgctxt "QFileDialog"
@@ -305,7 +306,7 @@ msgstr "Todos Arquivos (*.*)"
#: qfiledialog.cpp:437
msgctxt "QFileDialog"
msgid "Save As"
-msgstr "Salvar Como"
+msgstr "Gravar Como"
#: qfileiconprovider.cpp:379
msgctxt "QFileDialog"
@@ -325,7 +326,7 @@ msgstr "Desconhecido"
#: qfiledialog.cpp:439
msgctxt "QFileDialog"
msgid "Find Directory"
-msgstr "Encontrar Diretório"
+msgstr "Encontrar Directório"
#: qfiledialog.cpp:458
msgctxt "QFileDialog"
@@ -383,8 +384,8 @@ msgid ""
"<b>The name \"%1\" can not be used.</b><p>Try using another name, with fewer"
" characters or no punctuations marks."
msgstr ""
-"<b>O nome \"%1\" não pode ser usado.</b><p>Tente um nome com menos letras ou"
-" sem pontuação."
+"<b>O nome \"%1\" não pode ser usado.</b><p>Tente um nome com menos "
+"caracteres ou sem pontuação."
#: qfilesystemmodel.cpp:832
msgctxt "QFileSystemModel"
@@ -414,7 +415,7 @@ msgstr "Última modificação"
#: qfilesystemmodel_p.h:198
msgctxt "QFileSystemModel"
msgid "My Computer"
-msgstr "Meu computador"
+msgstr "O Meu computador"
#: qfilesystemmodel_p.h:200
msgctxt "QFileSystemModel"
1
0

02 Feb '12
commit fd35c54bf02cfec331a0cf785dbfa20105f163fe
Author: Translation commit bot <translation(a)torproject.org>
Date: Thu Feb 2 10:45:17 2012 +0000
Update translations for vidalia
---
sk/vidalia_sk.po | 122 +++++++++++++++++++++++++++---------------------------
1 files changed, 61 insertions(+), 61 deletions(-)
diff --git a/sk/vidalia_sk.po b/sk/vidalia_sk.po
index 4d3f73a..c34eb9f 100644
--- a/sk/vidalia_sk.po
+++ b/sk/vidalia_sk.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: 2011-09-07 14:40+0000\n"
-"PO-Revision-Date: 2012-02-02 10:14+0000\n"
+"PO-Revision-Date: 2012-02-02 10:33+0000\n"
"Last-Translator: martinstrucel <martin.strucel(a)gmail.com>\n"
"Language-Team: translations(a)vidalia-project.net\n"
"MIME-Version: 1.0\n"
@@ -1756,23 +1756,23 @@ msgstr "Požiadavka na odovzdanie informácie"
msgctxt "MainWindow"
msgid "Loading relay information"
-msgstr ""
+msgstr "Nahrávanie informácie"
msgctxt "MainWindow"
msgid "Connecting to the Tor network"
-msgstr ""
+msgstr "Pripájanie do Tor siete"
msgctxt "MainWindow"
msgid "Establishing a Tor circuit"
-msgstr ""
+msgstr "Nastavuje sa Tor okruh"
msgctxt "MainWindow"
msgid "Connected to the Tor network!"
-msgstr ""
+msgstr "Pripojené do siete Tor!"
msgctxt "MainWindow"
msgid "Unrecognized startup status"
-msgstr ""
+msgstr "Nerozpoznaný stav štartovania"
msgctxt "MainWindow"
msgid "miscellaneous"
@@ -2484,7 +2484,7 @@ msgstr "Zavriem mapu siete"
msgctxt "NetViewer"
msgid "Esc"
-msgstr ""
+msgstr "Esc"
msgctxt "NetViewer"
msgid "Zoom In"
@@ -2496,7 +2496,7 @@ msgstr "Priblížim mapu siete"
msgctxt "NetViewer"
msgid "+"
-msgstr ""
+msgstr "+"
msgctxt "NetViewer"
msgid "Zoom Out"
@@ -2508,7 +2508,7 @@ msgstr "Oddialim mapu siete"
msgctxt "NetViewer"
msgid "-"
-msgstr ""
+msgstr "-"
msgctxt "NetViewer"
msgid "Zoom To Fit"
@@ -2520,43 +2520,43 @@ msgstr "Priblížim, aby sa zmestili všetky aktuálne zobrazené okruhy"
msgctxt "NetViewer"
msgid "Ctrl+Z"
-msgstr ""
+msgstr "Ctrl+Z"
msgctxt "NetViewer"
msgid "Relay Not Found"
-msgstr ""
+msgstr "Prenos nebol nájdený"
msgctxt "NetViewer"
msgid "No details on the selected relay are available."
-msgstr ""
+msgstr "Podrobnosti pre daný prenos neboli nájdené."
msgctxt "NetViewer"
msgid "Unknown"
-msgstr ""
+msgstr "Neznáme"
msgctxt "NetViewer"
msgid "Full Screen"
-msgstr ""
+msgstr "Celá obrazovka"
msgctxt "NetViewer"
msgid "View the network map as a full screen window"
-msgstr ""
+msgstr "Zobraziť mapu siete v okne na celú obrazovku"
msgctxt "NetViewer"
msgid "Ctrl+F"
-msgstr ""
+msgstr "Ctrl+F"
msgctxt "NetworkPage"
msgid "Invalid Bridge"
-msgstr ""
+msgstr "Nesprávny most"
msgctxt "NetworkPage"
msgid "The specified bridge identifier is not valid."
-msgstr ""
+msgstr "Zadaný identifikátor mosta nie je platný."
msgctxt "NetworkPage"
msgid "Copy (Ctrl+C)"
-msgstr ""
+msgstr "Kopírovať (Ctrl+C)"
msgctxt "NetworkPage"
msgid ""
@@ -2596,7 +2596,7 @@ msgstr "Heslo?"
msgctxt "NetworkPage"
msgid "Port:"
-msgstr ""
+msgstr "Port:"
msgctxt "NetworkPage"
msgid "Check to only connect to relays using ports allowed by your firewall"
@@ -2614,11 +2614,11 @@ msgstr "Nastavenie firewallu"
msgctxt "NetworkPage"
msgid "Allowed Ports:"
-msgstr ""
+msgstr "Povolené porty:"
msgctxt "NetworkPage"
msgid "80, 443"
-msgstr ""
+msgstr "80, 443"
msgctxt "NetworkPage"
msgid ""
@@ -2698,83 +2698,83 @@ msgstr ""
msgctxt "Policy"
msgid "accept"
-msgstr ""
+msgstr "akceptovať"
msgctxt "Policy"
msgid "reject"
-msgstr ""
+msgstr "zamietnúť"
msgctxt "RouterDescriptor"
msgid "Online"
-msgstr ""
+msgstr "Zapojený"
msgctxt "RouterDescriptor"
msgid "Hibernating"
-msgstr ""
+msgstr "Hybernácia"
msgctxt "RouterDescriptor"
msgid "Offline"
-msgstr ""
+msgstr "Odpojený"
msgctxt "RouterDescriptorView"
msgid "Location:"
-msgstr ""
+msgstr "Lokalita:"
msgctxt "RouterDescriptorView"
msgid "IP Address:"
-msgstr ""
+msgstr "IP adresa:"
msgctxt "RouterDescriptorView"
msgid "Platform:"
-msgstr ""
+msgstr "Platforma:"
msgctxt "RouterDescriptorView"
msgid "Bandwidth:"
-msgstr ""
+msgstr "Šírka pásma:"
msgctxt "RouterDescriptorView"
msgid "Uptime:"
-msgstr ""
+msgstr "Čas chodu:"
msgctxt "RouterDescriptorView"
msgid "Last Updated:"
-msgstr ""
+msgstr "Naposledy aktualizované:"
msgctxt "RouterDescriptorView"
msgid "Copy"
-msgstr ""
+msgstr "Kopírovať"
msgctxt "RouterInfoDialog"
msgid "Hibernating"
-msgstr ""
+msgstr "Hybernovať"
msgctxt "RouterInfoDialog"
msgid "Online"
-msgstr ""
+msgstr "Zapojený"
msgctxt "RouterInfoDialog"
msgid "Offline"
-msgstr ""
+msgstr "Odpojený"
msgctxt "RouterInfoDialog"
msgid "Unknown"
-msgstr ""
+msgstr "Neznámy"
msgctxt "RouterInfoDialog"
msgid "Relay Details"
-msgstr ""
+msgstr "Podrobnosti o prenose"
msgctxt "RouterInfoDialog"
msgid "Summary"
-msgstr ""
+msgstr "Zhrnutie"
msgctxt "RouterInfoDialog"
msgid "Name:"
-msgstr ""
+msgstr "Meno:"
msgctxt "RouterInfoDialog"
msgid "Status:"
-msgstr ""
+msgstr "Stav:"
msgctxt "RouterInfoDialog"
msgid "Location:"
@@ -2932,27 +2932,27 @@ msgstr ""
msgctxt "ServerPage"
msgid "Cable/DSL 256 Kbps"
-msgstr ""
+msgstr "Cable/DSL 256 Kbps"
msgctxt "ServerPage"
msgid "Cable/DSL 512 Kbps"
-msgstr ""
+msgstr "Cable/DSL 512 Kbps"
msgctxt "ServerPage"
msgid "Cable/DSL 768 Kbps"
-msgstr ""
+msgstr "Cable/DSL 768 Kbps"
msgctxt "ServerPage"
msgid "T1/Cable/DSL 1.5 Mbps"
-msgstr ""
+msgstr "T1/Cable/DSL 1.5 Mbps"
msgctxt "ServerPage"
msgid "> 1.5 Mbps"
-msgstr ""
+msgstr "> 1.5 Mbps"
msgctxt "ServerPage"
msgid "Custom"
-msgstr ""
+msgstr "Vlastné"
msgctxt "ServerPage"
msgid "Select the entry that most closely resembles your Internet connection"
@@ -2972,7 +2972,7 @@ msgstr ""
msgctxt "ServerPage"
msgid "KB/s"
-msgstr ""
+msgstr "KB/s"
msgctxt "ServerPage"
msgid "Maximum Rate"
@@ -2994,19 +2994,19 @@ msgstr ""
msgctxt "ServerPage"
msgid "Ports 6660 - 6669 and 6697"
-msgstr ""
+msgstr "Porty 6660 - 6669 a 6697"
msgctxt "ServerPage"
msgid "Internet Relay Chat (IRC)"
-msgstr ""
+msgstr "Internet Relay Chat (IRC)"
msgctxt "ServerPage"
msgid "Ports 110, 143, 993 and 995"
-msgstr ""
+msgstr "Porty 110, 143, 993 a 995"
msgctxt "ServerPage"
msgid "Retrieve Mail (POP, IMAP)"
-msgstr ""
+msgstr "Príjem emailov (POP, IMAP)"
msgctxt "ServerPage"
msgid "Ports unspecified by other checkboxes"
@@ -3018,27 +3018,27 @@ msgstr ""
msgctxt "ServerPage"
msgid "Ports 706, 1863, 5050, 5190, 5222, 5223, 8300 and 8888"
-msgstr ""
+msgstr "Porty 706, 1863, 5050, 5190, 5222, 5223, 8300 a 8888"
msgctxt "ServerPage"
msgid "Instant Messaging (IM)"
-msgstr ""
+msgstr "Instant Messaging (IM)"
msgctxt "ServerPage"
msgid "Port 443"
-msgstr ""
+msgstr "Port 443"
msgctxt "ServerPage"
msgid "Secure Websites (SSL)"
-msgstr ""
+msgstr "Bezpečné webstránky (SSL)"
msgctxt "ServerPage"
msgid "Port 80"
-msgstr ""
+msgstr "Port 80"
msgctxt "ServerPage"
msgid "Websites"
-msgstr ""
+msgstr "Webstránky"
msgctxt "ServerPage"
msgid "Show help topic on exit policies"
@@ -3142,11 +3142,11 @@ msgstr ""
msgctxt "ServicePage"
msgid "Error"
-msgstr ""
+msgstr "Chyba"
msgctxt "ServicePage"
msgid "Please select a Service."
-msgstr ""
+msgstr "Prosím vyberte službu"
msgctxt "ServicePage"
msgid "Select Service Directory"
1
0

02 Feb '12
commit a863f79f7352067dc4057f433bdecc64202dc5be
Author: Translation commit bot <translation(a)torproject.org>
Date: Thu Feb 2 10:15:15 2012 +0000
Update translations for vidalia
---
sk/vidalia_sk.po | 340 +++++++++++++++++++++++++++---------------------------
1 files changed, 170 insertions(+), 170 deletions(-)
diff --git a/sk/vidalia_sk.po b/sk/vidalia_sk.po
index a319e00..4d3f73a 100644
--- a/sk/vidalia_sk.po
+++ b/sk/vidalia_sk.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: 2011-09-07 14:40+0000\n"
-"PO-Revision-Date: 2012-02-02 09:45+0000\n"
+"PO-Revision-Date: 2012-02-02 10:14+0000\n"
"Last-Translator: martinstrucel <martin.strucel(a)gmail.com>\n"
"Language-Team: translations(a)vidalia-project.net\n"
"MIME-Version: 1.0\n"
@@ -498,419 +498,419 @@ msgstr "Armenia"
msgctxt "CountryInfo"
msgid "Australia"
-msgstr ""
+msgstr "Australia"
msgctxt "CountryInfo"
msgid "Azerbaijan"
-msgstr ""
+msgstr "Azerbaijan"
msgctxt "CountryInfo"
msgid "Bahamas"
-msgstr ""
+msgstr "Bahamas"
msgctxt "CountryInfo"
msgid "Bangladesh"
-msgstr ""
+msgstr "Bangladesh"
msgctxt "CountryInfo"
msgid "Barbados"
-msgstr ""
+msgstr "Barbados"
msgctxt "CountryInfo"
msgid "Belarus"
-msgstr ""
+msgstr "Belarus"
msgctxt "CountryInfo"
msgid "Belgium"
-msgstr ""
+msgstr "Belgium"
msgctxt "CountryInfo"
msgid "Belize"
-msgstr ""
+msgstr "Belize"
msgctxt "CountryInfo"
msgid "Bhutan"
-msgstr ""
+msgstr "Bhutan"
msgctxt "CountryInfo"
msgid "Bolivia"
-msgstr ""
+msgstr "Bolivia"
msgctxt "CountryInfo"
msgid "Bosnia & Herzegovina"
-msgstr ""
+msgstr "Bosnia & Herzegovina"
msgctxt "CountryInfo"
msgid "Botswana"
-msgstr ""
+msgstr "Botswana"
msgctxt "CountryInfo"
msgid "Brazil"
-msgstr ""
+msgstr "Brazil"
msgctxt "CountryInfo"
msgid "Brunei Darussalam"
-msgstr ""
+msgstr "Brunei Darussalam"
msgctxt "CountryInfo"
msgid "Bulgaria"
-msgstr ""
+msgstr "Bulgaria"
msgctxt "CountryInfo"
msgid "Burkina Faso"
-msgstr ""
+msgstr "Burkina Faso"
msgctxt "CountryInfo"
msgid "Burundi"
-msgstr ""
+msgstr "Burundi"
msgctxt "CountryInfo"
msgid "Cambodia"
-msgstr ""
+msgstr "Cambodia"
msgctxt "CountryInfo"
msgid "Cameroon"
-msgstr ""
+msgstr "Cameroon"
msgctxt "CountryInfo"
msgid "Canada"
-msgstr ""
+msgstr "Canada"
msgctxt "CountryInfo"
msgid "Cape Verde"
-msgstr ""
+msgstr "Cape Verde"
msgctxt "CountryInfo"
msgid "Central African Republic"
-msgstr ""
+msgstr "Central African Republic"
msgctxt "CountryInfo"
msgid "Chad"
-msgstr ""
+msgstr "Chad"
msgctxt "CountryInfo"
msgid "Chile"
-msgstr ""
+msgstr "Chile"
msgctxt "CountryInfo"
msgid "China"
-msgstr ""
+msgstr "China"
msgctxt "CountryInfo"
msgid "Colombia"
-msgstr ""
+msgstr "Colombia"
msgctxt "CountryInfo"
msgid "Comoros"
-msgstr ""
+msgstr "Comoros"
msgctxt "CountryInfo"
msgid "Congo, The Democratic Republic of the"
-msgstr ""
+msgstr "Congo, The Democratic Republic of the"
msgctxt "CountryInfo"
msgid "Congo"
-msgstr ""
+msgstr "Congo"
msgctxt "CountryInfo"
msgid "Costa Rica"
-msgstr ""
+msgstr "Costa Rica"
msgctxt "CountryInfo"
msgid "Cote dâIvoire"
-msgstr ""
+msgstr "Cote dâIvoire"
msgctxt "CountryInfo"
msgid "Croatia"
-msgstr ""
+msgstr "Croatia"
msgctxt "CountryInfo"
msgid "Cuba"
-msgstr ""
+msgstr "Cuba"
msgctxt "CountryInfo"
msgid "Cyprus"
-msgstr ""
+msgstr "Cyprus"
msgctxt "CountryInfo"
msgid "Czech Republic"
-msgstr ""
+msgstr "Czech Republic"
msgctxt "CountryInfo"
msgid "Denmark"
-msgstr ""
+msgstr "Denmark"
msgctxt "CountryInfo"
msgid "Djibouti"
-msgstr ""
+msgstr "Djibouti"
msgctxt "CountryInfo"
msgid "Dominica"
-msgstr ""
+msgstr "Dominica"
msgctxt "CountryInfo"
msgid "Dominican Republic"
-msgstr ""
+msgstr "Dominican Republic"
msgctxt "CountryInfo"
msgid "Ecuador"
-msgstr ""
+msgstr "Ecuador"
msgctxt "CountryInfo"
msgid "Egypt"
-msgstr ""
+msgstr "Egypt"
msgctxt "CountryInfo"
msgid "El Salvador"
-msgstr ""
+msgstr "El Salvador"
msgctxt "CountryInfo"
msgid "Equatorial Guinea"
-msgstr ""
+msgstr "Equatorial Guinea"
msgctxt "CountryInfo"
msgid "Eritrea"
-msgstr ""
+msgstr "Eritrea"
msgctxt "CountryInfo"
msgid "Estonia"
-msgstr ""
+msgstr "Estonia"
msgctxt "CountryInfo"
msgid "France"
-msgstr ""
+msgstr "France"
msgctxt "CountryInfo"
msgid "Gabon"
-msgstr ""
+msgstr "Gabon"
msgctxt "CountryInfo"
msgid "Gambia"
-msgstr ""
+msgstr "Gambia"
msgctxt "CountryInfo"
msgid "Georgia"
-msgstr ""
+msgstr "Georgia"
msgctxt "CountryInfo"
msgid "Germany"
-msgstr ""
+msgstr "Germany"
msgctxt "CountryInfo"
msgid "Ghana"
-msgstr ""
+msgstr "Ghana"
msgctxt "CountryInfo"
msgid "Grenada"
-msgstr ""
+msgstr "Grenada"
msgctxt "CountryInfo"
msgid "Guatemala"
-msgstr ""
+msgstr "Guatemala"
msgctxt "CountryInfo"
msgid "Guinea"
-msgstr ""
+msgstr "Guinea"
msgctxt "CountryInfo"
msgid "Guinea-Bissau"
-msgstr ""
+msgstr "Guinea-Bissau"
msgctxt "CountryInfo"
msgid "Guyana"
-msgstr ""
+msgstr "Guyana"
msgctxt "CountryInfo"
msgid "Hong Kong"
-msgstr ""
+msgstr "Hong Kong"
msgctxt "CountryInfo"
msgid "Haiti"
-msgstr ""
+msgstr "Haiti"
msgctxt "CountryInfo"
msgid "Honduras"
-msgstr ""
+msgstr "Honduras"
msgctxt "CountryInfo"
msgid "Israel"
-msgstr ""
+msgstr "Israel"
msgctxt "CountryInfo"
msgid "Italy"
-msgstr ""
+msgstr "Italy"
msgctxt "CountryInfo"
msgid "Jamaica"
-msgstr ""
+msgstr "Jamaica"
msgctxt "CountryInfo"
msgid "Japan"
-msgstr ""
+msgstr "Japan"
msgctxt "CountryInfo"
msgid "Jordan"
-msgstr ""
+msgstr "Jordan"
msgctxt "CountryInfo"
msgid "Kazakhstan"
-msgstr ""
+msgstr "Kazakhstan"
msgctxt "CountryInfo"
msgid "Kenya"
-msgstr ""
+msgstr "Kenya"
msgctxt "CountryInfo"
msgid "Kiribati"
-msgstr ""
+msgstr "Kiribati"
msgctxt "CountryInfo"
msgid "Kuwait"
-msgstr ""
+msgstr "Kuwait"
msgctxt "CountryInfo"
msgid "Kyrgyzstan"
-msgstr ""
+msgstr "Kyrgyzstan"
msgctxt "CountryInfo"
msgid "Laos"
-msgstr ""
+msgstr "Laos"
msgctxt "CountryInfo"
msgid "Latvia"
-msgstr ""
+msgstr "Latvia"
msgctxt "CountryInfo"
msgid "Lebanon"
-msgstr ""
+msgstr "Lebanon"
msgctxt "CountryInfo"
msgid "Lesotho"
-msgstr ""
+msgstr "Lesotho"
msgctxt "CountryInfo"
msgid "Liberia"
-msgstr ""
+msgstr "Liberia"
msgctxt "CountryInfo"
msgid "Liechtenstein"
-msgstr ""
+msgstr "Liechtenstein"
msgctxt "CountryInfo"
msgid "Lithuania"
-msgstr ""
+msgstr "Lithuania"
msgctxt "CountryInfo"
msgid "Luxembourg"
-msgstr ""
+msgstr "Luxembourg"
msgctxt "CountryInfo"
msgid "Macedonia"
-msgstr ""
+msgstr "Macedonia"
msgctxt "CountryInfo"
msgid "Madagascar"
-msgstr ""
+msgstr "Madagascar"
msgctxt "CountryInfo"
msgid "Malawi"
-msgstr ""
+msgstr "Malawi"
msgctxt "CountryInfo"
msgid "Malaysia"
-msgstr ""
+msgstr "Malaysia"
msgctxt "CountryInfo"
msgid "Mali"
-msgstr ""
+msgstr "Mali"
msgctxt "CountryInfo"
msgid "Malta"
-msgstr ""
+msgstr "Malta"
msgctxt "CountryInfo"
msgid "Marshall Islands"
-msgstr ""
+msgstr "Marshall Islands"
msgctxt "CountryInfo"
msgid "Mauritania"
-msgstr ""
+msgstr "Mauritania"
msgctxt "CountryInfo"
msgid "Mauritius"
-msgstr ""
+msgstr "Mauritius"
msgctxt "CountryInfo"
msgid "Micronesia"
-msgstr ""
+msgstr "Micronesia"
msgctxt "CountryInfo"
msgid "Moldova"
-msgstr ""
+msgstr "Moldova"
msgctxt "CountryInfo"
msgid "Monaco"
-msgstr ""
+msgstr "Monaco"
msgctxt "CountryInfo"
msgid "Mongolia"
-msgstr ""
+msgstr "Mongolia"
msgctxt "CountryInfo"
msgid "Montenegro"
-msgstr ""
+msgstr "Montenegro"
msgctxt "CountryInfo"
msgid "Morocco"
-msgstr ""
+msgstr "Morocco"
msgctxt "CountryInfo"
msgid "Mozambique"
-msgstr ""
+msgstr "Mozambique"
msgctxt "CountryInfo"
msgid "Namibia"
-msgstr ""
+msgstr "Namibia"
msgctxt "CountryInfo"
msgid "Nauru"
-msgstr ""
+msgstr "Nauru"
msgctxt "CountryInfo"
msgid "Nepal"
-msgstr ""
+msgstr "Nepal"
msgctxt "CountryInfo"
msgid "Netherlands"
-msgstr ""
+msgstr "Netherlands"
msgctxt "CountryInfo"
msgid "New Zealand"
-msgstr ""
+msgstr "New Zealand"
msgctxt "CountryInfo"
msgid "Nicaragua"
-msgstr ""
+msgstr "Nicaragua"
msgctxt "CountryInfo"
msgid "Niger"
-msgstr ""
+msgstr "Niger"
msgctxt "CountryInfo"
msgid "Nigeria"
-msgstr ""
+msgstr "Nigeria"
msgctxt "CountryInfo"
msgid "Norway"
-msgstr ""
+msgstr "Norway"
msgctxt "CountryInfo"
msgid "Oman"
-msgstr ""
+msgstr "Oman"
msgctxt "CountryInfo"
msgid "Pakistan"
-msgstr ""
+msgstr "Pakistan"
msgctxt "CountryInfo"
msgid "Palau"
@@ -954,43 +954,43 @@ msgstr ""
msgctxt "CountryInfo"
msgid "Romania"
-msgstr ""
+msgstr "Romania"
msgctxt "CountryInfo"
msgid "Russia"
-msgstr ""
+msgstr "Russia"
msgctxt "CountryInfo"
msgid "Rwanda"
-msgstr ""
+msgstr "Rwanda"
msgctxt "CountryInfo"
msgid "Saint Kitts & Nevis"
-msgstr ""
+msgstr "Saint Kitts & Nevis"
msgctxt "CountryInfo"
msgid "Saint Lucia"
-msgstr ""
+msgstr "Saint Lucia"
msgctxt "CountryInfo"
msgid "Saint Vincent & the Grenadines"
-msgstr ""
+msgstr "Saint Vincent & the Grenadines"
msgctxt "CountryInfo"
msgid "Samoa"
-msgstr ""
+msgstr "Samoa"
msgctxt "CountryInfo"
msgid "San Marino"
-msgstr ""
+msgstr "San Marino"
msgctxt "CountryInfo"
msgid "Sao Tome & Principe"
-msgstr ""
+msgstr "Sao Tome & Principe"
msgctxt "CountryInfo"
msgid "Saudi Arabia"
-msgstr ""
+msgstr "Saudi Arabia"
msgctxt "CountryInfo"
msgid "Senegal"
@@ -1034,43 +1034,43 @@ msgstr ""
msgctxt "CountryInfo"
msgid "Spain"
-msgstr ""
+msgstr "Spain"
msgctxt "CountryInfo"
msgid "Sri Lanka"
-msgstr ""
+msgstr "Sri Lanka"
msgctxt "CountryInfo"
msgid "Sudan"
-msgstr ""
+msgstr "Sudan"
msgctxt "CountryInfo"
msgid "Suriname"
-msgstr ""
+msgstr "Suriname"
msgctxt "CountryInfo"
msgid "Swaziland"
-msgstr ""
+msgstr "Swaziland"
msgctxt "CountryInfo"
msgid "Sweden"
-msgstr ""
+msgstr "Sweden"
msgctxt "CountryInfo"
msgid "Switzerland"
-msgstr ""
+msgstr "Switzerland"
msgctxt "CountryInfo"
msgid "Syria"
-msgstr ""
+msgstr "Syria"
msgctxt "CountryInfo"
msgid "Tajikistan"
-msgstr ""
+msgstr "Tajikistan"
msgctxt "CountryInfo"
msgid "Tanzania"
-msgstr ""
+msgstr "Tanzania"
msgctxt "CountryInfo"
msgid "Thailand"
@@ -1198,75 +1198,75 @@ msgstr ""
msgctxt "CountryInfo"
msgid "Fiji"
-msgstr ""
+msgstr "Fiji"
msgctxt "CountryInfo"
msgid "Finland"
-msgstr ""
+msgstr "Finland"
msgctxt "CountryInfo"
msgid "Greece"
-msgstr ""
+msgstr "Greece"
msgctxt "CountryInfo"
msgid "Guam"
-msgstr ""
+msgstr "Guam"
msgctxt "CountryInfo"
msgid "Hungary"
-msgstr ""
+msgstr "Hungary"
msgctxt "CountryInfo"
msgid "Iceland"
-msgstr ""
+msgstr "Iceland"
msgctxt "CountryInfo"
msgid "India"
-msgstr ""
+msgstr "India"
msgctxt "CountryInfo"
msgid "Indonesia"
-msgstr ""
+msgstr "Indonesia"
msgctxt "CountryInfo"
msgid "Iran"
-msgstr ""
+msgstr "Iran"
msgctxt "CountryInfo"
msgid "Iraq"
-msgstr ""
+msgstr "Iraq"
msgctxt "CountryInfo"
msgid "Ireland"
-msgstr ""
+msgstr "Ireland"
msgctxt "CountryInfo"
msgid "Korea, North"
-msgstr ""
+msgstr "Korea, North"
msgctxt "CountryInfo"
msgid "Korea, South"
-msgstr ""
+msgstr "Korea, South"
msgctxt "CountryInfo"
msgid "Libya"
-msgstr ""
+msgstr "Libya"
msgctxt "CountryInfo"
msgid "Maldives"
-msgstr ""
+msgstr "Maldives"
msgctxt "CountryInfo"
msgid "Mexico"
-msgstr ""
+msgstr "Mexico"
msgctxt "CountryInfo"
msgid "Myanmar"
-msgstr ""
+msgstr "Myanmar"
msgctxt "CountryInfo"
msgid "Taiwan"
-msgstr ""
+msgstr "Taiwan"
msgctxt "CrashReportDialog"
msgid "Submit a Crash Report"
@@ -1354,7 +1354,7 @@ msgstr "Spustiť program Tora zo spustením Vidalia"
msgctxt "GeneralPage"
msgid "Tor"
-msgstr ""
+msgstr "Tor"
msgctxt "GeneralPage"
msgid "Proxy Application (optional)"
@@ -1382,19 +1382,19 @@ msgstr "Skontrolovať"
msgctxt "GraphFrame"
msgid "%1 KB/s"
-msgstr ""
+msgstr "%1 KB/s"
msgctxt "GraphFrame"
msgid "%1 KB"
-msgstr ""
+msgstr "%1 KB"
msgctxt "GraphFrame"
msgid "%1 MB"
-msgstr ""
+msgstr "%1 MB"
msgctxt "GraphFrame"
msgid "%1 GB"
-msgstr ""
+msgstr "%1 GB"
msgctxt "GraphFrame"
msgid "Recv:"
@@ -1438,7 +1438,7 @@ msgstr "Prejdem na predchádzajúcu stránku (Backspace)"
msgctxt "HelpBrowser"
msgid "Backspace"
-msgstr ""
+msgstr "Backspace"
msgctxt "HelpBrowser"
msgid "Forward"
@@ -1450,11 +1450,11 @@ msgstr "Prejdem na ďalšiu stránku (Shift+Backspace)"
msgctxt "HelpBrowser"
msgid "Shift+Backspace"
-msgstr ""
+msgstr "Shift+Backspace"
msgctxt "HelpBrowser"
msgid "Home"
-msgstr ""
+msgstr "Home"
msgctxt "HelpBrowser"
msgid "Move to the Home page (Ctrl+H)"
@@ -1462,7 +1462,7 @@ msgstr "Prejdem na domovskú stránku (Ctrl+H)"
msgctxt "HelpBrowser"
msgid "Ctrl+H"
-msgstr ""
+msgstr "Ctrl+H"
msgctxt "HelpBrowser"
msgid "Find"
@@ -1474,7 +1474,7 @@ msgstr "Vyhľadám slová alebo frázy na aktuálnej stránke (Ctrl+F)"
msgctxt "HelpBrowser"
msgid "Ctrl+F"
-msgstr ""
+msgstr "Ctrl+F"
msgctxt "HelpBrowser"
msgid "Close"
@@ -1486,7 +1486,7 @@ msgstr "Zavriem pomoc Vidalia"
msgctxt "HelpBrowser"
msgid "Esc"
-msgstr ""
+msgstr "Esc"
msgctxt "HelpBrowser"
msgid "Find:"
@@ -1584,7 +1584,7 @@ msgstr "Ladiť"
msgctxt "LogEvent"
msgid "Info"
-msgstr ""
+msgstr "Info"
msgctxt "LogEvent"
msgid "Notice"
@@ -1668,39 +1668,39 @@ msgstr "Nová identita"
msgctxt "MainWindow"
msgid "Ctrl+T"
-msgstr ""
+msgstr "Ctrl+T"
msgctxt "MainWindow"
msgid "Ctrl+B"
-msgstr ""
+msgstr "Ctrl+B"
msgctxt "MainWindow"
msgid "Ctrl+L"
-msgstr ""
+msgstr "Ctrl+L"
msgctxt "MainWindow"
msgid "Ctrl+N"
-msgstr ""
+msgstr "Ctrl+N"
msgctxt "MainWindow"
msgid "Ctrl+?"
-msgstr ""
+msgstr "Ctrl+?"
msgctxt "MainWindow"
msgid "Ctrl+I"
-msgstr ""
+msgstr "Ctrl+I"
msgctxt "MainWindow"
msgid "Ctrl+P"
-msgstr ""
+msgstr "Ctrl+P"
msgctxt "MainWindow"
msgid "Tor"
-msgstr ""
+msgstr "Tor"
msgctxt "MainWindow"
msgid "View"
-msgstr ""
+msgstr "Zobraziť"
msgctxt "MainWindow"
msgid "Vidalia Help"
@@ -1732,27 +1732,27 @@ msgstr "Ľutujeme ale Vidalia sa nepodarilo spustiť nastavený proxy server"
msgctxt "MainWindow"
msgid "Connecting to a relay directory"
-msgstr ""
+msgstr "Pripájanie k prenosu adresára"
msgctxt "MainWindow"
msgid "Establishing an encrypted directory connection"
-msgstr ""
+msgstr "Establishing an encrypted directory connection"
msgctxt "MainWindow"
msgid "Retrieving network status"
-msgstr ""
+msgstr "Príjem stavu siete"
msgctxt "MainWindow"
msgid "Loading network status"
-msgstr ""
+msgstr "Nahrávanie stavu siete"
msgctxt "MainWindow"
msgid "Loading authority certificates"
-msgstr ""
+msgstr "Nahrávanie autorizačných certifikátov"
msgctxt "MainWindow"
msgid "Requesting relay information"
-msgstr ""
+msgstr "Požiadavka na odovzdanie informácie"
msgctxt "MainWindow"
msgid "Loading relay information"
1
0

02 Feb '12
commit cde34bb784f1f538bd76fec7e734c376b3c4b700
Author: Translation commit bot <translation(a)torproject.org>
Date: Thu Feb 2 09:45:17 2012 +0000
Update translations for vidalia
---
sk/vidalia_sk.po | 17 +++++++++--------
1 files changed, 9 insertions(+), 8 deletions(-)
diff --git a/sk/vidalia_sk.po b/sk/vidalia_sk.po
index c706cd2..a319e00 100644
--- a/sk/vidalia_sk.po
+++ b/sk/vidalia_sk.po
@@ -1,13 +1,14 @@
#
# Translators:
+# <martin.strucel(a)gmail.com>, 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: 2011-09-07 14:40+0000\n"
-"PO-Revision-Date: 2012-01-07 16:59+0000\n"
-"Last-Translator: brahma <brahma(a)zoznam.sk>\n"
+"PO-Revision-Date: 2012-02-02 09:45+0000\n"
+"Last-Translator: martinstrucel <martin.strucel(a)gmail.com>\n"
"Language-Team: translations(a)vidalia-project.net\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
@@ -473,27 +474,27 @@ msgstr "Neplatná riadiaca odpoveď. [%1]"
msgctxt "CountryInfo"
msgid "Afghanistan"
-msgstr ""
+msgstr "Afghanistan"
msgctxt "CountryInfo"
msgid "Andorra"
-msgstr ""
+msgstr "Andorra"
msgctxt "CountryInfo"
msgid "Angola"
-msgstr ""
+msgstr "Angola"
msgctxt "CountryInfo"
msgid "Antigua & Barbuda"
-msgstr ""
+msgstr "Antigua & Barbuda"
msgctxt "CountryInfo"
msgid "Argentina"
-msgstr ""
+msgstr "Argentina"
msgctxt "CountryInfo"
msgid "Armenia"
-msgstr ""
+msgstr "Armenia"
msgctxt "CountryInfo"
msgid "Australia"
1
0
commit 1aaaa0e19a0038dc368915b2c24a350391c02fa2
Author: Translation commit bot <translation(a)torproject.org>
Date: Thu Feb 2 08:15:04 2012 +0000
Update translations for tsum
---
fi/tsum.po | 9 +++++++--
1 files changed, 7 insertions(+), 2 deletions(-)
diff --git a/fi/tsum.po b/fi/tsum.po
index d00e07c..f44d146 100644
--- a/fi/tsum.po
+++ b/fi/tsum.po
@@ -3,13 +3,14 @@
# This file is distributed under the same license as the PACKAGE package.
#
# Translators:
+# <jukka.mieskonen(a)suomi24.fi>, 2012.
msgid ""
msgstr ""
"Project-Id-Version: The Tor Project\n"
"Report-Msgid-Bugs-To: https://trac.torproject.org/projects/tor\n"
"POT-Creation-Date: 2011-11-05 17:16+0000\n"
-"PO-Revision-Date: 2011-10-12 13:07+0000\n"
-"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
+"PO-Revision-Date: 2012-02-02 08:06+0000\n"
+"Last-Translator: com234 <jukka.mieskonen(a)suomi24.fi>\n"
"Language-Team: LANGUAGE <LL(a)li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
@@ -46,6 +47,8 @@ msgid ""
"How Tor works\n"
"-------------\n"
msgstr ""
+"Kuinka Tor toimii\n"
+"-------------------\n"
#. type: Plain text
#: en/tsum.text:19
@@ -93,6 +96,8 @@ msgid ""
"How to download Tor\n"
"-------------------\n"
msgstr ""
+"Kuinka ladata Tor\n"
+"--------------------\n"
#. type: Plain text
#: en/tsum.text:44
1
0
commit cc1b9bad55736de995128bb626645a860495f38e
Author: Karsten Loesing <karsten.loesing(a)gmx.net>
Date: Thu Feb 2 08:17:43 2012 +0100
Rename metrics-lib downloader.
---
src/org/torproject/doctor/Downloader.java | 4 ++--
1 files changed, 2 insertions(+), 2 deletions(-)
diff --git a/src/org/torproject/doctor/Downloader.java b/src/org/torproject/doctor/Downloader.java
index da86e23..6dff6d8 100644
--- a/src/org/torproject/doctor/Downloader.java
+++ b/src/org/torproject/doctor/Downloader.java
@@ -14,8 +14,8 @@ public class Downloader {
/* Create a descriptor downloader instance that will do all the hard
* download work for us. */
- RelayDescriptorDownloader downloader =
- DescriptorSourceFactory.createRelayDescriptorDownloader();
+ DescriptorDownloader downloader =
+ DescriptorSourceFactory.createDescriptorDownloader();
/* Configure the currently known directory authorities. */
downloader.addDirectoryAuthority("gabelmoo", "212.112.245.170", 80);
1
0

02 Feb '12
commit 550c43e842403d1b6d57a90a9b270eeb0e913dab
Author: Karsten Loesing <karsten.loesing(a)gmx.net>
Date: Thu Feb 2 07:55:17 2012 +0100
Rename some copied-and-pasted variables.
---
.../descriptor/impl/NetworkStatusImpl.java | 6 +++---
1 files changed, 3 insertions(+), 3 deletions(-)
diff --git a/src/org/torproject/descriptor/impl/NetworkStatusImpl.java b/src/org/torproject/descriptor/impl/NetworkStatusImpl.java
index fcbd8f6..febe31a 100644
--- a/src/org/torproject/descriptor/impl/NetworkStatusImpl.java
+++ b/src/org/torproject/descriptor/impl/NetworkStatusImpl.java
@@ -181,13 +181,13 @@ public abstract class NetworkStatusImpl extends DescriptorImpl {
NetworkStatusEntryImpl statusEntry = new NetworkStatusEntryImpl(
statusEntryBytes, this.failUnrecognizedDescriptorLines);
this.statusEntries.put(statusEntry.getFingerprint(), statusEntry);
- List<String> unrecognizedDirSourceLines = statusEntry.
+ List<String> unrecognizedStatusEntryLines = statusEntry.
getAndClearUnrecognizedLines();
- if (unrecognizedDirSourceLines != null) {
+ if (unrecognizedStatusEntryLines != null) {
if (this.unrecognizedLines == null) {
this.unrecognizedLines = new ArrayList<String>();
}
- this.unrecognizedLines.addAll(unrecognizedDirSourceLines);
+ this.unrecognizedLines.addAll(unrecognizedStatusEntryLines);
}
}
1
0

02 Feb '12
commit 5c1494966f2af90f4bdb024c3c561cccad23b24e
Author: Karsten Loesing <karsten.loesing(a)gmx.net>
Date: Thu Feb 2 08:11:15 2012 +0100
Add support for parsing exit lists.
---
src/org/torproject/descriptor/ExitList.java | 16 ++
src/org/torproject/descriptor/ExitListEntry.java | 25 +++
.../torproject/descriptor/impl/DescriptorImpl.java | 3 +
.../descriptor/impl/ExitListEntryImpl.java | 170 ++++++++++++++++++++
.../torproject/descriptor/impl/ExitListImpl.java | 121 ++++++++++++++
5 files changed, 335 insertions(+), 0 deletions(-)
diff --git a/src/org/torproject/descriptor/ExitList.java b/src/org/torproject/descriptor/ExitList.java
new file mode 100644
index 0000000..5372b8b
--- /dev/null
+++ b/src/org/torproject/descriptor/ExitList.java
@@ -0,0 +1,16 @@
+/* Copyright 2012 The Tor Project
+ * See LICENSE for licensing information */
+package org.torproject.descriptor;
+
+import java.util.Set;
+
+/* Exit list containing all known exit scan results at a given time. */
+public interface ExitList extends Descriptor {
+
+ /* Return the publication time of the exit list. */
+ public long getPublishedMillis();
+
+ /* Return the unordered set of exit scan results. */
+ public Set<ExitListEntry> getExitListEntries();
+}
+
diff --git a/src/org/torproject/descriptor/ExitListEntry.java b/src/org/torproject/descriptor/ExitListEntry.java
new file mode 100644
index 0000000..74438de
--- /dev/null
+++ b/src/org/torproject/descriptor/ExitListEntry.java
@@ -0,0 +1,25 @@
+/* Copyright 2012 The Tor Project
+ * See LICENSE for licensing information */
+package org.torproject.descriptor;
+
+/* Exit list entry containing results from a single exit scan. */
+public interface ExitListEntry {
+
+ /* Return the scanned relay's fingerprint. */
+ public String getFingerprint();
+
+ /* Return the publication time of the scanned relay's last known
+ * descriptor. */
+ public long getPublishedMillis();
+
+ /* Return the publication time of the network status that this scan was
+ * based on. */
+ public long getLastStatusMillis();
+
+ /* Return the IP address that was determined in the scan. */
+ public String getExitAddress();
+
+ /* Return the scan time. */
+ public long getScanMillis();
+}
+
diff --git a/src/org/torproject/descriptor/impl/DescriptorImpl.java b/src/org/torproject/descriptor/impl/DescriptorImpl.java
index 7db8aaf..e173612 100644
--- a/src/org/torproject/descriptor/impl/DescriptorImpl.java
+++ b/src/org/torproject/descriptor/impl/DescriptorImpl.java
@@ -63,6 +63,9 @@ public abstract class DescriptorImpl implements Descriptor {
failUnrecognizedDescriptorLines));
} else if (firstLines.startsWith("dir-key-certificate-version ")) {
/* TODO Implement parsing of directory certificates. */
+ } else if (firstLines.startsWith("ExitNode ")) {
+ parsedDescriptors.add(new ExitListImpl(rawDescriptorBytes, fileName,
+ failUnrecognizedDescriptorLines));
} else {
throw new DescriptorParseException("Could not detect descriptor "
+ "type in descriptor starting with '" + firstLines + "'.");
diff --git a/src/org/torproject/descriptor/impl/ExitListEntryImpl.java b/src/org/torproject/descriptor/impl/ExitListEntryImpl.java
new file mode 100644
index 0000000..b3ed8f1
--- /dev/null
+++ b/src/org/torproject/descriptor/impl/ExitListEntryImpl.java
@@ -0,0 +1,170 @@
+/* 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.List;
+import java.util.SortedSet;
+import java.util.TreeSet;
+
+import org.torproject.descriptor.ExitListEntry;
+
+public class ExitListEntryImpl implements ExitListEntry {
+
+ private byte[] exitListEntryBytes;
+ public byte[] getExitListEntryBytes() {
+ return this.exitListEntryBytes;
+ }
+
+ private boolean failUnrecognizedDescriptorLines;
+ private List<String> unrecognizedLines;
+ protected List<String> getAndClearUnrecognizedLines() {
+ List<String> lines = this.unrecognizedLines;
+ this.unrecognizedLines = null;
+ return lines;
+ }
+
+ protected ExitListEntryImpl(byte[] exitListEntryBytes,
+ boolean failUnrecognizedDescriptorLines)
+ throws DescriptorParseException {
+ this.exitListEntryBytes = exitListEntryBytes;
+ this.failUnrecognizedDescriptorLines =
+ failUnrecognizedDescriptorLines;
+ this.initializeKeywords();
+ this.parseExitListEntryBytes();
+ this.checkKeywords();
+ }
+
+ private SortedSet<String> exactlyOnceKeywords;
+ private void initializeKeywords() {
+ this.exactlyOnceKeywords = new TreeSet<String>();
+ this.exactlyOnceKeywords.add("ExitNode");
+ this.exactlyOnceKeywords.add("Published");
+ this.exactlyOnceKeywords.add("LastStatus");
+ this.exactlyOnceKeywords.add("ExitAddress");
+ }
+
+ private void parsedExactlyOnceKeyword(String keyword)
+ throws DescriptorParseException {
+ if (!this.exactlyOnceKeywords.contains(keyword)) {
+ throw new DescriptorParseException("Duplicate '" + keyword
+ + "' line in exit list entry.");
+ }
+ this.exactlyOnceKeywords.remove(keyword);
+ }
+
+ private void checkKeywords() throws DescriptorParseException {
+ for (String missingKeyword : this.exactlyOnceKeywords) {
+ throw new DescriptorParseException("Missing '" + missingKeyword
+ + "' line in exit list entry.");
+ }
+ }
+
+ private void parseExitListEntryBytes()
+ throws DescriptorParseException {
+ try {
+ BufferedReader br = new BufferedReader(new StringReader(
+ new String(this.exitListEntryBytes)));
+ String line;
+ while ((line = br.readLine()) != null) {
+ String[] parts = line.split(" ");
+ String keyword = parts[0];
+ if (keyword.equals("ExitNode")) {
+ this.parseExitNodeLine(line, parts);
+ } else if (keyword.equals("Published")) {
+ this.parsePublishedLine(line, parts);
+ } else if (keyword.equals("LastStatus")) {
+ this.parseLastStatusLine(line, parts);
+ } else if (keyword.equals("ExitAddress")) {
+ this.parseExitAddressLine(line, parts);
+ } else if (this.failUnrecognizedDescriptorLines) {
+ throw new DescriptorParseException("Unrecognized line '" + line
+ + "' in exit list entry.");
+ } else {
+ if (this.unrecognizedLines == null) {
+ this.unrecognizedLines = new ArrayList<String>();
+ }
+ this.unrecognizedLines.add(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 parseExitNodeLine(String line, String[] parts)
+ throws DescriptorParseException {
+ if (parts.length != 2) {
+ throw new DescriptorParseException("Invalid line '" + line + "' in "
+ + "exit list entry.");
+ }
+ this.parsedExactlyOnceKeyword(parts[0]);
+ this.fingerprint = ParseHelper.parseTwentyByteHexString(line,
+ parts[1]);
+ }
+
+ private void parsePublishedLine(String line, String[] parts)
+ throws DescriptorParseException {
+ if (parts.length != 3) {
+ throw new DescriptorParseException("Invalid line '" + line + "' in "
+ + "exit list entry.");
+ }
+ this.parsedExactlyOnceKeyword(parts[0]);
+ this.publishedMillis = ParseHelper.parseTimestampAtIndex(line, parts,
+ 1, 2);
+ }
+
+ private void parseLastStatusLine(String line, String[] parts)
+ throws DescriptorParseException {
+ if (parts.length != 3) {
+ throw new DescriptorParseException("Invalid line '" + line + "' in "
+ + "exit list entry.");
+ }
+ this.parsedExactlyOnceKeyword(parts[0]);
+ this.lastStatusMillis = ParseHelper.parseTimestampAtIndex(line, parts,
+ 1, 2);
+ }
+
+ private void parseExitAddressLine(String line, String[] parts)
+ throws DescriptorParseException {
+ if (parts.length != 4) {
+ throw new DescriptorParseException("Invalid line '" + line + "' in "
+ + "exit list entry.");
+ }
+ this.parsedExactlyOnceKeyword(parts[0]);
+ this.exitAddress = ParseHelper.parseIpv4Address(line, parts[1]);
+ this.scanMillis = ParseHelper.parseTimestampAtIndex(line, parts,
+ 2, 3);
+ }
+
+ private String fingerprint;
+ public String getFingerprint() {
+ return this.fingerprint;
+ }
+
+ private long publishedMillis;
+ public long getPublishedMillis() {
+ return this.publishedMillis;
+ }
+
+ private long lastStatusMillis;
+ public long getLastStatusMillis() {
+ return this.lastStatusMillis;
+ }
+
+ private String exitAddress;
+ public String getExitAddress() {
+ return this.exitAddress;
+ }
+
+ private long scanMillis;
+ public long getScanMillis() {
+ return this.scanMillis;
+ }
+}
+
diff --git a/src/org/torproject/descriptor/impl/ExitListImpl.java b/src/org/torproject/descriptor/impl/ExitListImpl.java
new file mode 100644
index 0000000..4861fa0
--- /dev/null
+++ b/src/org/torproject/descriptor/impl/ExitListImpl.java
@@ -0,0 +1,121 @@
+/* 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.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.ArrayList;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+import java.util.TimeZone;
+
+import org.torproject.descriptor.ExitList;
+import org.torproject.descriptor.ExitListEntry;
+
+/* TODO Add test class. */
+public class ExitListImpl extends DescriptorImpl implements ExitList {
+
+ protected ExitListImpl(byte[] rawDescriptorBytes, String fileName,
+ boolean failUnrecognizedDescriptorLines)
+ throws DescriptorParseException {
+ super(rawDescriptorBytes, failUnrecognizedDescriptorLines);
+ this.setPublishedMillisFromFileName(fileName);
+ this.splitAndParseExitListEntries(rawDescriptorBytes);
+ }
+
+ private void setPublishedMillisFromFileName(String fileName)
+ throws DescriptorParseException {
+ if (fileName.length() == "2012-02-01-04-06-24".length()) {
+ try {
+ SimpleDateFormat fileNameFormat = new SimpleDateFormat(
+ "yyyy-MM-dd-HH-mm-ss");
+ fileNameFormat.setLenient(false);
+ fileNameFormat.setTimeZone(TimeZone.getTimeZone("UTC"));
+ this.publishedMillis = fileNameFormat.parse(fileName).getTime();
+ } catch (ParseException e) {
+ /* Handle below. */
+ }
+ }
+ if (this.publishedMillis == 0L) {
+ throw new DescriptorParseException("Unrecognized exit list file "
+ + "name '" + fileName + "'.");
+ }
+ }
+
+ private void splitAndParseExitListEntries(byte[] rawDescriptorBytes)
+ throws DescriptorParseException {
+ if (this.rawDescriptorBytes.length == 0) {
+ throw new DescriptorParseException("Descriptor is empty.");
+ }
+ String descriptorString = new String(rawDescriptorBytes);
+ if (descriptorString.startsWith("\n") ||
+ descriptorString.contains("\n\n")) {
+ throw new DescriptorParseException("Empty lines are not allowed.");
+ }
+ try {
+ BufferedReader br = new BufferedReader(new StringReader(
+ descriptorString));
+ String line;
+ StringBuilder sb = new StringBuilder();
+ while ((line = br.readLine()) != null) {
+ String[] parts = line.split(" ");
+ String keyword = parts[0];
+ if (keyword.equals("ExitNode")) {
+ sb = new StringBuilder();
+ sb.append(line + "\n");
+ } else if (keyword.equals("Published")) {
+ sb.append(line + "\n");
+ } else if (keyword.equals("LastStatus")) {
+ sb.append(line + "\n");
+ } else if (keyword.equals("ExitAddress")) {
+ String exitListEntryString = sb.toString() + line + "\n";
+ byte[] exitListEntryBytes = exitListEntryString.getBytes();
+ this.parseExitListEntry(exitListEntryBytes);
+ } else if (this.failUnrecognizedDescriptorLines) {
+ throw new DescriptorParseException("Unrecognized line '" + line
+ + "' in exit list.");
+ } else {
+ if (this.unrecognizedLines == null) {
+ this.unrecognizedLines = new ArrayList<String>();
+ }
+ this.unrecognizedLines.add(line);
+ }
+ }
+ } catch (IOException e) {
+ throw new RuntimeException("Internal error: Ran into an "
+ + "IOException while parsing a String in memory. Something's "
+ + "really wrong.", e);
+ }
+ }
+
+ protected void parseExitListEntry(byte[] exitListEntryBytes)
+ throws DescriptorParseException {
+ ExitListEntryImpl exitListEntry = new ExitListEntryImpl(
+ exitListEntryBytes, this.failUnrecognizedDescriptorLines);
+ this.exitListEntries.add(exitListEntry);
+ List<String> unrecognizedExitListEntryLines = exitListEntry.
+ getAndClearUnrecognizedLines();
+ if (unrecognizedExitListEntryLines != null) {
+ if (this.unrecognizedLines == null) {
+ this.unrecognizedLines = new ArrayList<String>();
+ }
+ this.unrecognizedLines.addAll(unrecognizedExitListEntryLines);
+ }
+ }
+
+ private long publishedMillis;
+ public long getPublishedMillis() {
+ return this.publishedMillis;
+ }
+
+ private Set<ExitListEntry> exitListEntries =
+ new HashSet<ExitListEntry>();
+ public Set<ExitListEntry> getExitListEntries() {
+ return new HashSet<ExitListEntry>(this.exitListEntries);
+ }
+}
+
1
0

[metrics-lib/master] Use a single interface for reading descriptors.
by karsten@torproject.org 02 Feb '12
by karsten@torproject.org 02 Feb '12
02 Feb '12
commit b2ad143c2a79e335f0ff7648b1dcd5fc157af63c
Author: Karsten Loesing <karsten.loesing(a)gmx.net>
Date: Thu Feb 2 08:08:07 2012 +0100
Use a single interface for reading descriptors.
---
.../descriptor/BridgeDescriptorReader.java | 34 ---
.../descriptor/BridgePoolAssignmentReader.java | 34 ---
.../descriptor/DescriptorDownloader.java | 109 ++++++++
.../torproject/descriptor/DescriptorReader.java | 34 +++
.../descriptor/DescriptorSourceFactory.java | 28 +--
.../descriptor/RelayDescriptorDownloader.java | 109 --------
.../descriptor/RelayDescriptorReader.java | 35 ---
.../descriptor/impl/DescriptorDownloaderImpl.java | 265 ++++++++++++++++++++
.../descriptor/impl/DescriptorReaderImpl.java | 194 ++++++++++++++
.../impl/RelayDescriptorDownloaderImpl.java | 265 --------------------
.../impl/RelayOrBridgeDescriptorReaderImpl.java | 198 ---------------
11 files changed, 610 insertions(+), 695 deletions(-)
diff --git a/src/org/torproject/descriptor/BridgeDescriptorReader.java b/src/org/torproject/descriptor/BridgeDescriptorReader.java
deleted file mode 100644
index d827124..0000000
--- a/src/org/torproject/descriptor/BridgeDescriptorReader.java
+++ /dev/null
@@ -1,34 +0,0 @@
-/* Copyright 2011, 2012 The Tor Project
- * See LICENSE for licensing information */
-package org.torproject.descriptor;
-
-import java.io.File;
-import java.util.Iterator;
-
-/* Read bridge descriptors from one or more local directories. */
-public interface BridgeDescriptorReader {
-
- /* Add a local directory to read bridge descriptors from. */
- public void addDirectory(File directory);
-
- /* Exclude files that are contained in the given history file and that
- * haven't changed since they were last read. Add reads from the
- * current run to the history file. Remove files that don't exist
- * anymore from the history file. Lines in the history file contain the
- * last modified timestamp and the absolute path of a file. */
- public void setExcludeFiles(File historyFile);
-
- /* Fail descriptor parsing when encountering an unrecognized line. This
- * is not set by default, because the Tor specifications allow for new
- * lines to be added that shall be ignored by older Tor versions. But
- * some applications may want to handle unrecognized descriptor lines
- * explicitly. */
- public void setFailUnrecognizedDescriptorLines();
-
- /* Read the previously configured bridge descriptors and make them
- * available via the returned blocking iterator. Whenever the reader
- * runs out of descriptors and expects to provide more shortly after, it
- * blocks the caller. This method can only be run once. */
- public Iterator<DescriptorFile> readDescriptors();
-}
-
diff --git a/src/org/torproject/descriptor/BridgePoolAssignmentReader.java b/src/org/torproject/descriptor/BridgePoolAssignmentReader.java
deleted file mode 100644
index 13c8ae3..0000000
--- a/src/org/torproject/descriptor/BridgePoolAssignmentReader.java
+++ /dev/null
@@ -1,34 +0,0 @@
-/* Copyright 2011, 2012 The Tor Project
- * See LICENSE for licensing information */
-package org.torproject.descriptor;
-
-import java.io.File;
-import java.util.Iterator;
-
-/* Read bridge pool assignments from one or more local directories. */
-public interface BridgePoolAssignmentReader {
-
- /* Add a local directory to read bridge pool assignments from. */
- public void addDirectory(File directory);
-
- /* Exclude files that are contained in the given history file and that
- * haven't changed since they were last read. Add reads from the
- * current run to the history file. Remove files that don't exist
- * anymore from the history file. Lines in the history file contain the
- * last modified timestamp and the absolute path of a file. */
- public void setExcludeFiles(File historyFile);
-
- /* Fail descriptor parsing when encountering an unrecognized line. This
- * is not set by default, because the Tor specifications allow for new
- * lines to be added that shall be ignored by older Tor versions. But
- * some applications may want to handle unrecognized descriptor lines
- * explicitly. */
- public void setFailUnrecognizedDescriptorLines();
-
- /* Read the previously configured bridge pool assignments and make them
- * available via the returned blocking iterator. Whenever the reader
- * runs out of descriptors and expects to provide more shortly after, it
- * blocks the caller. This method can only be run once. */
- public Iterator<DescriptorFile> readDescriptors();
-}
-
diff --git a/src/org/torproject/descriptor/DescriptorDownloader.java b/src/org/torproject/descriptor/DescriptorDownloader.java
new file mode 100644
index 0000000..5665e1f
--- /dev/null
+++ b/src/org/torproject/descriptor/DescriptorDownloader.java
@@ -0,0 +1,109 @@
+/* Copyright 2011, 2012 The Tor Project
+ * See LICENSE for licensing information */
+package org.torproject.descriptor;
+
+import java.util.Iterator;
+import java.util.Set;
+
+/* Download relay descriptors from directory mirrors or authorities. */
+public interface DescriptorDownloader {
+
+ /* Add a directory authority to download descriptors from. A directory
+ * authority is only required for downloading network status vote and
+ * will be used when no directory mirrors are available. */
+ public void addDirectoryAuthority(String nickname, String ip,
+ int dirPort);
+
+ /* Add a directory mirror to download descriptors from. Directory
+ * mirrors are preferred when downloading descriptors, except for
+ * network status votes which are only available on directory
+ * authorities. */
+ public void addDirectoryMirror(String nickname, String ip, int dirPort);
+
+ /* Include the current network status consensus in the downloads. */
+ public void setIncludeCurrentConsensus();
+
+ /* Include the current network status consensus in the downloads, and
+ * attempt to download it from all directory authorities. The primary
+ * purpose of doing this is to compare different consensuses and
+ * download characteristics to each other. Typically, downloading from
+ * a single directory mirror or authority is sufficient. */
+ public void setIncludeCurrentConsensusFromAllDirectoryAuthorities();
+
+ /* Include the current network status votes referenced from a previously
+ * downloaded consensus in the downloads. This requires downloading the
+ * current consensus from at least one directory mirror or authority. */
+ public void setIncludeCurrentReferencedVotes();
+
+ /* Include the current network status vote published by the given
+ * directory authority in the downloads. This requires downloading from
+ * at least one directory authority. */
+ public void setIncludeCurrentVote(String fingerprint);
+
+ /* Include the current network status votes published by the given
+ * directory authorities in the downloads. This requires downloading
+ * from at least one directory authority. */
+ public void setIncludeCurrentVotes(Set<String> fingerprints);
+
+ /* Include all server descriptors referenced from a previously
+ * downloaded network status consensus in the downloads. */
+ public void setIncludeReferencedServerDescriptors();
+
+ /* Exclude the server descriptor with the given identifier from the
+ * downloads even if it's referenced from a consensus and we're supposed
+ * to download all referenced server descriptors. */
+ public void setExcludeServerDescriptor(String identifier);
+
+ /* Exclude the server descriptors with the given identifiers from the
+ * downloads even if they are referenced from a consensus and we're
+ * supposed to download all referenced server descriptors. */
+ public void setExcludeServerDescriptors(Set<String> identifier);
+
+ /* Include all extra-info descriptors referenced from previously
+ * downloaded server descriptors in the downloads. */
+ public void setIncludeReferencedExtraInfoDescriptors();
+
+ /* Exclude the extra-info descriptor with the given identifier from the
+ * downloads even if it's referenced from a server descriptor and we're
+ * supposed to download all referenced extra-info descriptors. */
+ public void setExcludeExtraInfoDescriptor(String identifier);
+
+ /* Exclude the extra-info descriptors with the given identifiers from
+ * the downloads even if they are referenced from server descriptors
+ * and we're supposed to download all referenced extra-info
+ * descriptors. */
+ public void setExcludeExtraInfoDescriptors(Set<String> identifiers);
+
+ /* Define a connect timeout for a single request. If a timeout expires,
+ * no further requests will be sent to the directory authority or
+ * mirror. Setting this value to 0 disables the connect timeout.
+ * Default value is 1 minute (60 * 1000). */
+ public void setConnectTimeout(long connectTimeoutMillis);
+
+ /* Define a read timeout for a single request. If a timeout expires,
+ * no further requests will be sent to the directory authority or
+ * mirror. Setting this value to 0 disables the read timeout.
+ * Default value is 1 minute (60 * 1000). */
+ public void setReadTimeout(long readTimeoutMillis);
+
+ /* Define a global timeout for all requests. Once this timeout expires,
+ * all running requests are aborted and no further requests are made.
+ * Setting this value to 0 disables the global timeout. Default is 1
+ * hour (60 * 60 * 1000). */
+ public void setGlobalTimeout(long globalTimeoutMillis);
+
+ /* Fail descriptor parsing when encountering an unrecognized line. This
+ * is not set by default, because the Tor specifications allow for new
+ * lines to be added that shall be ignored by older Tor versions. But
+ * some applications may want to handle unrecognized descriptor lines
+ * explicitly. */
+ public void setFailUnrecognizedDescriptorLines();
+
+ /* Download the previously configured relay descriptors and make them
+ * available via the returned blocking iterator. Whenever the
+ * downloader runs out of descriptors and expects to provide more
+ * shortly after, it blocks the caller. This method can only be run
+ * once. */
+ public Iterator<DescriptorRequest> downloadDescriptors();
+}
+
diff --git a/src/org/torproject/descriptor/DescriptorReader.java b/src/org/torproject/descriptor/DescriptorReader.java
new file mode 100644
index 0000000..1d46a79
--- /dev/null
+++ b/src/org/torproject/descriptor/DescriptorReader.java
@@ -0,0 +1,34 @@
+/* Copyright 2011, 2012 The Tor Project
+ * See LICENSE for licensing information */
+package org.torproject.descriptor;
+
+import java.io.File;
+import java.util.Iterator;
+
+/* Read descriptors from one or more local directories. */
+public interface DescriptorReader {
+
+ /* Add a local directory to read descriptors from. */
+ public void addDirectory(File directory);
+
+ /* Exclude files that are contained in the given history file and that
+ * haven't changed since they were last read. Add reads from the
+ * current run to the history file. Remove files that don't exist
+ * anymore from the history file. Lines in the history file contain the
+ * last modified timestamp and the absolute path of a file. */
+ public void setExcludeFiles(File historyFile);
+
+ /* Fail descriptor parsing when encountering an unrecognized line. This
+ * is not set by default, because the Tor specifications allow for new
+ * lines to be added that shall be ignored by older Tor versions. But
+ * some applications may want to handle unrecognized descriptor lines
+ * explicitly. */
+ public void setFailUnrecognizedDescriptorLines();
+
+ /* Read the previously configured descriptors and make them available
+ * via the returned blocking iterator. Whenever the reader runs out of
+ * descriptors and expects to provide more shortly after, it blocks the
+ * caller. This method can only be run once. */
+ public Iterator<DescriptorFile> readDescriptors();
+}
+
diff --git a/src/org/torproject/descriptor/DescriptorSourceFactory.java b/src/org/torproject/descriptor/DescriptorSourceFactory.java
index ed2790a..102bfce 100644
--- a/src/org/torproject/descriptor/DescriptorSourceFactory.java
+++ b/src/org/torproject/descriptor/DescriptorSourceFactory.java
@@ -2,32 +2,20 @@
* See LICENSE for licensing information */
package org.torproject.descriptor;
-import org.torproject.descriptor.impl.RelayDescriptorDownloaderImpl;
-import org.torproject.descriptor.impl.RelayOrBridgeDescriptorReaderImpl;
+import org.torproject.descriptor.impl.DescriptorDownloaderImpl;
+import org.torproject.descriptor.impl.DescriptorReaderImpl;
/* Create descriptor source instances. */
public class DescriptorSourceFactory {
- /* Create a relay descriptor reader. */
- public static RelayDescriptorReader createRelayDescriptorReader() {
- return new RelayOrBridgeDescriptorReaderImpl();
+ /* Create a descriptor reader. */
+ public static DescriptorReader createDescriptorReader() {
+ return new DescriptorReaderImpl();
}
- /* Create a relay descriptor downloader. */
- public static RelayDescriptorDownloader
- createRelayDescriptorDownloader() {
- return new RelayDescriptorDownloaderImpl();
- }
-
- /* Create a bridge descriptor reader. */
- public static BridgeDescriptorReader createBridgeDescriptorReader() {
- return new RelayOrBridgeDescriptorReaderImpl();
- }
-
- /* Create a bridge pool assignment reader. */
- public static BridgePoolAssignmentReader
- createBridgePoolAssignmentReader() {
- return new RelayOrBridgeDescriptorReaderImpl();
+ /* Create a descriptor downloader. */
+ public static DescriptorDownloader createDescriptorDownloader() {
+ return new DescriptorDownloaderImpl();
}
}
diff --git a/src/org/torproject/descriptor/RelayDescriptorDownloader.java b/src/org/torproject/descriptor/RelayDescriptorDownloader.java
deleted file mode 100644
index 29171d3..0000000
--- a/src/org/torproject/descriptor/RelayDescriptorDownloader.java
+++ /dev/null
@@ -1,109 +0,0 @@
-/* Copyright 2011, 2012 The Tor Project
- * See LICENSE for licensing information */
-package org.torproject.descriptor;
-
-import java.util.Iterator;
-import java.util.Set;
-
-/* Download relay descriptors from directory mirrors or authorities. */
-public interface RelayDescriptorDownloader {
-
- /* Add a directory authority to download descriptors from. A directory
- * authority is only required for downloading network status vote and
- * will be used when no directory mirrors are available. */
- public void addDirectoryAuthority(String nickname, String ip,
- int dirPort);
-
- /* Add a directory mirror to download descriptors from. Directory
- * mirrors are preferred when downloading descriptors, except for
- * network status votes which are only available on directory
- * authorities. */
- public void addDirectoryMirror(String nickname, String ip, int dirPort);
-
- /* Include the current network status consensus in the downloads. */
- public void setIncludeCurrentConsensus();
-
- /* Include the current network status consensus in the downloads, and
- * attempt to download it from all directory authorities. The primary
- * purpose of doing this is to compare different consensuses and
- * download characteristics to each other. Typically, downloading from
- * a single directory mirror or authority is sufficient. */
- public void setIncludeCurrentConsensusFromAllDirectoryAuthorities();
-
- /* Include the current network status votes referenced from a previously
- * downloaded consensus in the downloads. This requires downloading the
- * current consensus from at least one directory mirror or authority. */
- public void setIncludeCurrentReferencedVotes();
-
- /* Include the current network status vote published by the given
- * directory authority in the downloads. This requires downloading from
- * at least one directory authority. */
- public void setIncludeCurrentVote(String fingerprint);
-
- /* Include the current network status votes published by the given
- * directory authorities in the downloads. This requires downloading
- * from at least one directory authority. */
- public void setIncludeCurrentVotes(Set<String> fingerprints);
-
- /* Include all server descriptors referenced from a previously
- * downloaded network status consensus in the downloads. */
- public void setIncludeReferencedServerDescriptors();
-
- /* Exclude the server descriptor with the given identifier from the
- * downloads even if it's referenced from a consensus and we're supposed
- * to download all referenced server descriptors. */
- public void setExcludeServerDescriptor(String identifier);
-
- /* Exclude the server descriptors with the given identifiers from the
- * downloads even if they are referenced from a consensus and we're
- * supposed to download all referenced server descriptors. */
- public void setExcludeServerDescriptors(Set<String> identifier);
-
- /* Include all extra-info descriptors referenced from previously
- * downloaded server descriptors in the downloads. */
- public void setIncludeReferencedExtraInfoDescriptors();
-
- /* Exclude the extra-info descriptor with the given identifier from the
- * downloads even if it's referenced from a server descriptor and we're
- * supposed to download all referenced extra-info descriptors. */
- public void setExcludeExtraInfoDescriptor(String identifier);
-
- /* Exclude the extra-info descriptors with the given identifiers from
- * the downloads even if they are referenced from server descriptors
- * and we're supposed to download all referenced extra-info
- * descriptors. */
- public void setExcludeExtraInfoDescriptors(Set<String> identifiers);
-
- /* Define a connect timeout for a single request. If a timeout expires,
- * no further requests will be sent to the directory authority or
- * mirror. Setting this value to 0 disables the connect timeout.
- * Default value is 1 minute (60 * 1000). */
- public void setConnectTimeout(long connectTimeoutMillis);
-
- /* Define a read timeout for a single request. If a timeout expires,
- * no further requests will be sent to the directory authority or
- * mirror. Setting this value to 0 disables the read timeout.
- * Default value is 1 minute (60 * 1000). */
- public void setReadTimeout(long readTimeoutMillis);
-
- /* Define a global timeout for all requests. Once this timeout expires,
- * all running requests are aborted and no further requests are made.
- * Setting this value to 0 disables the global timeout. Default is 1
- * hour (60 * 60 * 1000). */
- public void setGlobalTimeout(long globalTimeoutMillis);
-
- /* Fail descriptor parsing when encountering an unrecognized line. This
- * is not set by default, because the Tor specifications allow for new
- * lines to be added that shall be ignored by older Tor versions. But
- * some applications may want to handle unrecognized descriptor lines
- * explicitly. */
- public void setFailUnrecognizedDescriptorLines();
-
- /* Download the previously configured relay descriptors and make them
- * available via the returned blocking iterator. Whenever the
- * downloader runs out of descriptors and expects to provide more
- * shortly after, it blocks the caller. This method can only be run
- * once. */
- public Iterator<DescriptorRequest> downloadDescriptors();
-}
-
diff --git a/src/org/torproject/descriptor/RelayDescriptorReader.java b/src/org/torproject/descriptor/RelayDescriptorReader.java
deleted file mode 100644
index 142f79c..0000000
--- a/src/org/torproject/descriptor/RelayDescriptorReader.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/* Copyright 2011, 2012 The Tor Project
- * See LICENSE for licensing information */
-package org.torproject.descriptor;
-
-import java.io.File;
-import java.util.Iterator;
-
-/* Read relay descriptors from one or more local directories. */
-public interface RelayDescriptorReader {
-
- /* Add a local directory to read relay descriptors from. */
- public void addDirectory(File directory);
-
- /* Exclude files that are contained in the given history file and that
- * haven't changed since they were last read. Add reads from the
- * current run to the history file. Remove files that don't exist
- * anymore from the history file. Lines in the history file contain the
- * last modified timestamp and the absolute path of a file. */
- public void setExcludeFiles(File historyFile);
-
- /* Fail descriptor parsing when encountering an unrecognized line. This
- * is not set by default, because the Tor specifications allow for new
- * lines to be added that shall be ignored by older Tor versions. But
- * some applications may want to handle unrecognized descriptor lines
- * explicitly. */
- public void setFailUnrecognizedDescriptorLines();
-
- /* Read the previously configured relay descriptors and make them
- * available via the returned blocking iterator. Whenever the reader
- * runs out of descriptors and expects to provide more shortly after, it
- * blocks the caller. This method can only be run once. */
- public Iterator<DescriptorFile> readDescriptors();
-
-}
-
diff --git a/src/org/torproject/descriptor/impl/DescriptorDownloaderImpl.java b/src/org/torproject/descriptor/impl/DescriptorDownloaderImpl.java
new file mode 100644
index 0000000..3c093d1
--- /dev/null
+++ b/src/org/torproject/descriptor/impl/DescriptorDownloaderImpl.java
@@ -0,0 +1,265 @@
+/* Copyright 2011, 2012 The Tor Project
+ * See LICENSE for licensing information */
+package org.torproject.descriptor.impl;
+
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.Set;
+import java.util.SortedMap;
+import java.util.TreeMap;
+
+import org.torproject.descriptor.DescriptorRequest;
+import org.torproject.descriptor.DescriptorDownloader;
+
+public class DescriptorDownloaderImpl
+ implements DescriptorDownloader {
+
+ private boolean hasStartedDownloading = false;
+
+ private SortedMap<String, DirectoryDownloader> directoryAuthorities =
+ new TreeMap<String, DirectoryDownloader>();
+ public void addDirectoryAuthority(String nickname, String ip,
+ int dirPort) {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ this.checkDirectoryParameters(nickname, ip, dirPort);
+ DirectoryDownloader directoryAuthority = new DirectoryDownloader(
+ nickname, ip, dirPort);
+ this.directoryAuthorities.put(nickname, directoryAuthority);
+ }
+
+ private SortedMap<String, DirectoryDownloader> directoryMirrors =
+ new TreeMap<String, DirectoryDownloader>();
+ public void addDirectoryMirror(String nickname, String ip,
+ int dirPort) {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ this.checkDirectoryParameters(nickname, ip, dirPort);
+ DirectoryDownloader directoryMirror = new DirectoryDownloader(
+ nickname, ip, dirPort);
+ this.directoryMirrors.put(nickname, directoryMirror);
+ /* TODO Implement prioritizing mirrors for non-vote downloads. */
+ throw new UnsupportedOperationException("Prioritizing directory "
+ + "mirrors over directory authorities is not implemented yet. "
+ + "Until it is, configuring directory mirrors is misleading and "
+ + "therefore not supported.");
+ }
+
+ private void checkDirectoryParameters(String nickname, String ip,
+ int dirPort) {
+ if (nickname == null || nickname.length() < 1) {
+ throw new IllegalArgumentException("'" + nickname + "' is not a "
+ + "valid nickname.");
+ }
+ if (ip == null || ip.length() < 7 || ip.split("\\.").length != 4) {
+ throw new IllegalArgumentException("'" + ip + "' is not a valid IP "
+ + "address.");
+ }
+ if (dirPort < 1 || dirPort > 65535) {
+ throw new IllegalArgumentException(String.valueOf(dirPort) + " is "
+ + "not a valid DirPort.");
+ }
+ /* TODO Relax the requirement for directory nicknames to be unique.
+ * In theory, we can identify them by ip+port. */
+ if (this.directoryAuthorities.containsKey(nickname) ||
+ this.directoryMirrors.containsKey(nickname)) {
+ throw new IllegalArgumentException("Directory nicknames must be "
+ + "unique.");
+ }
+ }
+
+ private boolean downloadConsensus = false;
+ public void setIncludeCurrentConsensus() {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ this.downloadConsensus = true;
+ }
+
+ private boolean downloadConsensusFromAllAuthorities = false;
+ public void setIncludeCurrentConsensusFromAllDirectoryAuthorities() {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ this.downloadConsensusFromAllAuthorities = true;
+ }
+
+ private boolean includeCurrentReferencedVotes = false;
+ public void setIncludeCurrentReferencedVotes() {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ this.includeCurrentReferencedVotes = true;
+ }
+
+ private Set<String> downloadVotes = new HashSet<String>();
+ public void setIncludeCurrentVote(String fingerprint) {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ this.checkVoteFingerprint(fingerprint);
+ this.downloadVotes.add(fingerprint);
+ }
+
+ public void setIncludeCurrentVotes(Set<String> fingerprints) {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ if (fingerprints == null) {
+ throw new IllegalArgumentException("Set of fingerprints must not "
+ + "be null.");
+ }
+ for (String fingerprint : fingerprints) {
+ this.checkVoteFingerprint(fingerprint);
+ }
+ for (String fingerprint : fingerprints) {
+ this.setIncludeCurrentVote(fingerprint);
+ }
+ }
+
+ private void checkVoteFingerprint(String fingerprint) {
+ if (fingerprint == null || fingerprint.length() != 40) {
+ throw new IllegalArgumentException("'" + fingerprint + "' is not a "
+ + "valid fingerprint.");
+ }
+ }
+
+ public void setIncludeReferencedServerDescriptors() {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException("Downloading server "
+ + "descriptors is not implemented yet.");
+ }
+
+ public void setExcludeServerDescriptor(String identifier) {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException("Downloading server "
+ + "descriptors is not implemented yet.");
+ }
+
+ public void setExcludeServerDescriptors(Set<String> identifier) {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException("Downloading server "
+ + "descriptors is not implemented yet.");
+ }
+
+ public void setIncludeReferencedExtraInfoDescriptors() {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException("Downloading extra-info "
+ + "descriptors is not implemented yet.");
+ }
+
+ public void setExcludeExtraInfoDescriptor(String identifier) {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException("Downloading extra-info "
+ + "descriptors is not implemented yet.");
+ }
+
+ public void setExcludeExtraInfoDescriptors(Set<String> identifiers) {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ /* TODO Implement me. */
+ throw new UnsupportedOperationException("Downloading extra-info "
+ + "descriptors is not implemented yet.");
+ }
+
+ private long readTimeoutMillis = 60L * 1000L;
+ public void setReadTimeout(long readTimeoutMillis) {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ if (readTimeoutMillis < 0L) {
+ throw new IllegalArgumentException("Read timeout value "
+ + String.valueOf(readTimeoutMillis) + " may not be "
+ + "negative.");
+ }
+ this.readTimeoutMillis = readTimeoutMillis;
+ }
+
+ private long connectTimeoutMillis = 60L * 1000L;
+ public void setConnectTimeout(long connectTimeoutMillis) {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ if (connectTimeoutMillis < 0L) {
+ throw new IllegalArgumentException("Connect timeout value "
+ + String.valueOf(connectTimeoutMillis) + " may not be "
+ + "negative.");
+ }
+ this.connectTimeoutMillis = connectTimeoutMillis;
+ }
+
+ private long globalTimeoutMillis = 60L * 60L * 1000L;
+ public void setGlobalTimeout(long globalTimeoutMillis) {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ if (globalTimeoutMillis < 0L) {
+ throw new IllegalArgumentException("Global timeout value "
+ + String.valueOf(globalTimeoutMillis) + " may not be "
+ + "negative.");
+ }
+ this.globalTimeoutMillis = globalTimeoutMillis;
+ }
+
+ private boolean failUnrecognizedDescriptorLines = false;
+ public void setFailUnrecognizedDescriptorLines() {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to download.");
+ }
+ this.failUnrecognizedDescriptorLines = true;
+ }
+
+ public Iterator<DescriptorRequest> downloadDescriptors() {
+ if (this.hasStartedDownloading) {
+ throw new IllegalStateException("Initiating downloads is only "
+ + "permitted once.");
+ }
+ this.hasStartedDownloading = true;
+ DownloadCoordinatorImpl downloadCoordinator =
+ new DownloadCoordinatorImpl(this.directoryAuthorities,
+ this.directoryMirrors, this.downloadConsensus,
+ this.downloadConsensusFromAllAuthorities, this.downloadVotes,
+ this.includeCurrentReferencedVotes, this.connectTimeoutMillis,
+ this.readTimeoutMillis, this.globalTimeoutMillis,
+ this.failUnrecognizedDescriptorLines);
+ Iterator<DescriptorRequest> descriptorQueue = downloadCoordinator.
+ getDescriptorQueue();
+ return descriptorQueue;
+ }
+}
+
diff --git a/src/org/torproject/descriptor/impl/DescriptorReaderImpl.java b/src/org/torproject/descriptor/impl/DescriptorReaderImpl.java
new file mode 100644
index 0000000..c22cbe8
--- /dev/null
+++ b/src/org/torproject/descriptor/impl/DescriptorReaderImpl.java
@@ -0,0 +1,194 @@
+/* Copyright 2011, 2012 The Tor Project
+ * See LICENSE for licensing information */
+package org.torproject.descriptor.impl;
+
+import java.io.BufferedInputStream;
+import java.io.BufferedReader;
+import java.io.BufferedWriter;
+import java.io.ByteArrayOutputStream;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileReader;
+import java.io.FileWriter;
+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.SortedMap;
+import java.util.Stack;
+import java.util.TreeMap;
+
+import org.torproject.descriptor.Descriptor;
+import org.torproject.descriptor.DescriptorFile;
+import org.torproject.descriptor.DescriptorReader;
+
+public class DescriptorReaderImpl implements DescriptorReader {
+
+ private boolean hasStartedReading = false;
+
+ private List<File> directories = new ArrayList<File>();
+ public void addDirectory(File directory) {
+ if (this.hasStartedReading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to read.");
+ }
+ this.directories.add(directory);
+ }
+
+ private File historyFile;
+ public void setExcludeFiles(File historyFile) {
+ if (this.hasStartedReading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to read.");
+ }
+ this.historyFile = historyFile;
+ }
+
+ private boolean failUnrecognizedDescriptorLines = false;
+ public void setFailUnrecognizedDescriptorLines() {
+ if (this.hasStartedReading) {
+ throw new IllegalStateException("Reconfiguration is not permitted "
+ + "after starting to read.");
+ }
+ this.failUnrecognizedDescriptorLines = true;
+ }
+
+ public Iterator<DescriptorFile> readDescriptors() {
+ if (this.hasStartedReading) {
+ throw new IllegalStateException("Initiating reading is only "
+ + "permitted once.");
+ }
+ this.hasStartedReading = true;
+ BlockingIteratorImpl<DescriptorFile> descriptorQueue =
+ new BlockingIteratorImpl<DescriptorFile>();
+ DescriptorReaderRunnable reader = new DescriptorReaderRunnable(
+ this.directories, descriptorQueue, this.historyFile,
+ this.failUnrecognizedDescriptorLines);
+ new Thread(reader).start();
+ return descriptorQueue;
+ }
+
+ private static class DescriptorReaderRunnable implements Runnable {
+ private List<File> directories;
+ private BlockingIteratorImpl<DescriptorFile> descriptorQueue;
+ private File historyFile;
+ private boolean failUnrecognizedDescriptorLines;
+ private DescriptorReaderRunnable(List<File> directories,
+ BlockingIteratorImpl<DescriptorFile> descriptorQueue,
+ File historyFile, boolean failUnrecognizedDescriptorLines) {
+ this.directories = directories;
+ this.descriptorQueue = descriptorQueue;
+ this.historyFile = historyFile;
+ this.failUnrecognizedDescriptorLines =
+ failUnrecognizedDescriptorLines;
+ }
+ public void run() {
+ this.readOldHistory();
+ this.readDescriptors();
+ this.writeNewHistory();
+ }
+ private SortedMap<String, Long>
+ oldHistory = new TreeMap<String, Long>(),
+ newHistory = new TreeMap<String, Long>();
+ private void readOldHistory() {
+ if (this.historyFile == null) {
+ return;
+ }
+ try {
+ BufferedReader br = new BufferedReader(new FileReader(
+ this.historyFile));
+ String line;
+ while ((line = br.readLine()) != null) {
+ if (!line.contains(" ")) {
+ /* TODO Handle this problem? */
+ continue;
+ }
+ long lastModifiedMillis = Long.parseLong(line.substring(0,
+ line.indexOf(" ")));
+ String absolutePath = line.substring(line.indexOf(" ") + 1);
+ this.oldHistory.put(absolutePath, lastModifiedMillis);
+ }
+ br.close();
+ } catch (IOException e) {
+ /* TODO Handle this exception. */
+ } catch (NumberFormatException e) {
+ /* TODO Handle this exception. */
+ }
+ }
+ private void writeNewHistory() {
+ if (this.historyFile == null) {
+ return;
+ }
+ try {
+ if (this.historyFile.getParentFile() != null) {
+ this.historyFile.getParentFile().mkdirs();
+ }
+ BufferedWriter bw = new BufferedWriter(new FileWriter(
+ this.historyFile));
+ for (Map.Entry<String, Long> e : this.newHistory.entrySet()) {
+ String absolutePath = e.getKey();
+ long lastModifiedMillis = e.getValue();
+ bw.write(String.valueOf(lastModifiedMillis) + " " + absolutePath
+ + "\n");
+ }
+ bw.close();
+ } catch (IOException e) {
+ /* TODO Handle this exception. */
+ }
+ }
+ private void readDescriptors() {
+ for (File directory : this.directories) {
+ Stack<File> files = new Stack<File>();
+ files.add(directory);
+ boolean abortReading = false;
+ while (!abortReading && !files.isEmpty()) {
+ File file = files.pop();
+ if (file.isDirectory()) {
+ files.addAll(Arrays.asList(file.listFiles()));
+ } else {
+ String absolutePath = file.getAbsolutePath();
+ long lastModifiedMillis = file.lastModified();
+ this.newHistory.put(absolutePath, lastModifiedMillis);
+ if (this.oldHistory.containsKey(absolutePath) &&
+ this.oldHistory.get(absolutePath) == lastModifiedMillis) {
+ continue;
+ }
+ DescriptorFileImpl descriptorFile = new DescriptorFileImpl();
+ try {
+ descriptorFile.setDirectory(directory);
+ descriptorFile.setFile(file);
+ descriptorFile.setLastModified(lastModifiedMillis);
+ descriptorFile.setDescriptors(this.readFile(file));
+ } catch (DescriptorParseException e) {
+ descriptorFile.setException(e);
+ } catch (IOException e) {
+ descriptorFile.setException(e);
+ abortReading = true;
+ }
+ this.descriptorQueue.add(descriptorFile);
+ }
+ }
+ }
+ 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.parseRelayOrBridgeDescriptors(
+ rawDescriptorBytes, file.getName(),
+ this.failUnrecognizedDescriptorLines);
+ }
+ }
+}
+
diff --git a/src/org/torproject/descriptor/impl/RelayDescriptorDownloaderImpl.java b/src/org/torproject/descriptor/impl/RelayDescriptorDownloaderImpl.java
deleted file mode 100644
index 6993509..0000000
--- a/src/org/torproject/descriptor/impl/RelayDescriptorDownloaderImpl.java
+++ /dev/null
@@ -1,265 +0,0 @@
-/* Copyright 2011, 2012 The Tor Project
- * See LICENSE for licensing information */
-package org.torproject.descriptor.impl;
-
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.Set;
-import java.util.SortedMap;
-import java.util.TreeMap;
-
-import org.torproject.descriptor.DescriptorRequest;
-import org.torproject.descriptor.RelayDescriptorDownloader;
-
-public class RelayDescriptorDownloaderImpl
- implements RelayDescriptorDownloader {
-
- private boolean hasStartedDownloading = false;
-
- private SortedMap<String, DirectoryDownloader> directoryAuthorities =
- new TreeMap<String, DirectoryDownloader>();
- public void addDirectoryAuthority(String nickname, String ip,
- int dirPort) {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- this.checkDirectoryParameters(nickname, ip, dirPort);
- DirectoryDownloader directoryAuthority = new DirectoryDownloader(
- nickname, ip, dirPort);
- this.directoryAuthorities.put(nickname, directoryAuthority);
- }
-
- private SortedMap<String, DirectoryDownloader> directoryMirrors =
- new TreeMap<String, DirectoryDownloader>();
- public void addDirectoryMirror(String nickname, String ip,
- int dirPort) {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- this.checkDirectoryParameters(nickname, ip, dirPort);
- DirectoryDownloader directoryMirror = new DirectoryDownloader(
- nickname, ip, dirPort);
- this.directoryMirrors.put(nickname, directoryMirror);
- /* TODO Implement prioritizing mirrors for non-vote downloads. */
- throw new UnsupportedOperationException("Prioritizing directory "
- + "mirrors over directory authorities is not implemented yet. "
- + "Until it is, configuring directory mirrors is misleading and "
- + "therefore not supported.");
- }
-
- private void checkDirectoryParameters(String nickname, String ip,
- int dirPort) {
- if (nickname == null || nickname.length() < 1) {
- throw new IllegalArgumentException("'" + nickname + "' is not a "
- + "valid nickname.");
- }
- if (ip == null || ip.length() < 7 || ip.split("\\.").length != 4) {
- throw new IllegalArgumentException("'" + ip + "' is not a valid IP "
- + "address.");
- }
- if (dirPort < 1 || dirPort > 65535) {
- throw new IllegalArgumentException(String.valueOf(dirPort) + " is "
- + "not a valid DirPort.");
- }
- /* TODO Relax the requirement for directory nicknames to be unique.
- * In theory, we can identify them by ip+port. */
- if (this.directoryAuthorities.containsKey(nickname) ||
- this.directoryMirrors.containsKey(nickname)) {
- throw new IllegalArgumentException("Directory nicknames must be "
- + "unique.");
- }
- }
-
- private boolean downloadConsensus = false;
- public void setIncludeCurrentConsensus() {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- this.downloadConsensus = true;
- }
-
- private boolean downloadConsensusFromAllAuthorities = false;
- public void setIncludeCurrentConsensusFromAllDirectoryAuthorities() {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- this.downloadConsensusFromAllAuthorities = true;
- }
-
- private boolean includeCurrentReferencedVotes = false;
- public void setIncludeCurrentReferencedVotes() {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- this.includeCurrentReferencedVotes = true;
- }
-
- private Set<String> downloadVotes = new HashSet<String>();
- public void setIncludeCurrentVote(String fingerprint) {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- this.checkVoteFingerprint(fingerprint);
- this.downloadVotes.add(fingerprint);
- }
-
- public void setIncludeCurrentVotes(Set<String> fingerprints) {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- if (fingerprints == null) {
- throw new IllegalArgumentException("Set of fingerprints must not "
- + "be null.");
- }
- for (String fingerprint : fingerprints) {
- this.checkVoteFingerprint(fingerprint);
- }
- for (String fingerprint : fingerprints) {
- this.setIncludeCurrentVote(fingerprint);
- }
- }
-
- private void checkVoteFingerprint(String fingerprint) {
- if (fingerprint == null || fingerprint.length() != 40) {
- throw new IllegalArgumentException("'" + fingerprint + "' is not a "
- + "valid fingerprint.");
- }
- }
-
- public void setIncludeReferencedServerDescriptors() {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- /* TODO Implement me. */
- throw new UnsupportedOperationException("Downloading server "
- + "descriptors is not implemented yet.");
- }
-
- public void setExcludeServerDescriptor(String identifier) {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- /* TODO Implement me. */
- throw new UnsupportedOperationException("Downloading server "
- + "descriptors is not implemented yet.");
- }
-
- public void setExcludeServerDescriptors(Set<String> identifier) {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- /* TODO Implement me. */
- throw new UnsupportedOperationException("Downloading server "
- + "descriptors is not implemented yet.");
- }
-
- public void setIncludeReferencedExtraInfoDescriptors() {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- /* TODO Implement me. */
- throw new UnsupportedOperationException("Downloading extra-info "
- + "descriptors is not implemented yet.");
- }
-
- public void setExcludeExtraInfoDescriptor(String identifier) {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- /* TODO Implement me. */
- throw new UnsupportedOperationException("Downloading extra-info "
- + "descriptors is not implemented yet.");
- }
-
- public void setExcludeExtraInfoDescriptors(Set<String> identifiers) {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- /* TODO Implement me. */
- throw new UnsupportedOperationException("Downloading extra-info "
- + "descriptors is not implemented yet.");
- }
-
- private long readTimeoutMillis = 60L * 1000L;
- public void setReadTimeout(long readTimeoutMillis) {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- if (readTimeoutMillis < 0L) {
- throw new IllegalArgumentException("Read timeout value "
- + String.valueOf(readTimeoutMillis) + " may not be "
- + "negative.");
- }
- this.readTimeoutMillis = readTimeoutMillis;
- }
-
- private long connectTimeoutMillis = 60L * 1000L;
- public void setConnectTimeout(long connectTimeoutMillis) {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- if (connectTimeoutMillis < 0L) {
- throw new IllegalArgumentException("Connect timeout value "
- + String.valueOf(connectTimeoutMillis) + " may not be "
- + "negative.");
- }
- this.connectTimeoutMillis = connectTimeoutMillis;
- }
-
- private long globalTimeoutMillis = 60L * 60L * 1000L;
- public void setGlobalTimeout(long globalTimeoutMillis) {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- if (globalTimeoutMillis < 0L) {
- throw new IllegalArgumentException("Global timeout value "
- + String.valueOf(globalTimeoutMillis) + " may not be "
- + "negative.");
- }
- this.globalTimeoutMillis = globalTimeoutMillis;
- }
-
- private boolean failUnrecognizedDescriptorLines = false;
- public void setFailUnrecognizedDescriptorLines() {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to download.");
- }
- this.failUnrecognizedDescriptorLines = true;
- }
-
- public Iterator<DescriptorRequest> downloadDescriptors() {
- if (this.hasStartedDownloading) {
- throw new IllegalStateException("Initiating downloads is only "
- + "permitted once.");
- }
- this.hasStartedDownloading = true;
- DownloadCoordinatorImpl downloadCoordinator =
- new DownloadCoordinatorImpl(this.directoryAuthorities,
- this.directoryMirrors, this.downloadConsensus,
- this.downloadConsensusFromAllAuthorities, this.downloadVotes,
- this.includeCurrentReferencedVotes, this.connectTimeoutMillis,
- this.readTimeoutMillis, this.globalTimeoutMillis,
- this.failUnrecognizedDescriptorLines);
- Iterator<DescriptorRequest> descriptorQueue = downloadCoordinator.
- getDescriptorQueue();
- return descriptorQueue;
- }
-}
-
diff --git a/src/org/torproject/descriptor/impl/RelayOrBridgeDescriptorReaderImpl.java b/src/org/torproject/descriptor/impl/RelayOrBridgeDescriptorReaderImpl.java
deleted file mode 100644
index 60c1e36..0000000
--- a/src/org/torproject/descriptor/impl/RelayOrBridgeDescriptorReaderImpl.java
+++ /dev/null
@@ -1,198 +0,0 @@
-/* Copyright 2011, 2012 The Tor Project
- * See LICENSE for licensing information */
-package org.torproject.descriptor.impl;
-
-import java.io.BufferedInputStream;
-import java.io.BufferedReader;
-import java.io.BufferedWriter;
-import java.io.ByteArrayOutputStream;
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.FileReader;
-import java.io.FileWriter;
-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.SortedMap;
-import java.util.Stack;
-import java.util.TreeMap;
-
-import org.torproject.descriptor.BridgeDescriptorReader;
-import org.torproject.descriptor.BridgePoolAssignmentReader;
-import org.torproject.descriptor.Descriptor;
-import org.torproject.descriptor.DescriptorFile;
-import org.torproject.descriptor.RelayDescriptorReader;
-
-public class RelayOrBridgeDescriptorReaderImpl
- implements RelayDescriptorReader, BridgeDescriptorReader,
- BridgePoolAssignmentReader {
-
- private boolean hasStartedReading = false;
-
- private List<File> directories = new ArrayList<File>();
- public void addDirectory(File directory) {
- if (this.hasStartedReading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to read.");
- }
- this.directories.add(directory);
- }
-
- private File historyFile;
- public void setExcludeFiles(File historyFile) {
- if (this.hasStartedReading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to read.");
- }
- this.historyFile = historyFile;
- }
-
- private boolean failUnrecognizedDescriptorLines = false;
- public void setFailUnrecognizedDescriptorLines() {
- if (this.hasStartedReading) {
- throw new IllegalStateException("Reconfiguration is not permitted "
- + "after starting to read.");
- }
- this.failUnrecognizedDescriptorLines = true;
- }
-
- public Iterator<DescriptorFile> readDescriptors() {
- if (this.hasStartedReading) {
- throw new IllegalStateException("Initiating reading is only "
- + "permitted once.");
- }
- this.hasStartedReading = true;
- BlockingIteratorImpl<DescriptorFile> descriptorQueue =
- new BlockingIteratorImpl<DescriptorFile>();
- DescriptorReader reader = new DescriptorReader(this.directories,
- descriptorQueue, this.historyFile,
- this.failUnrecognizedDescriptorLines);
- new Thread(reader).start();
- return descriptorQueue;
- }
-
- private static class DescriptorReader implements Runnable {
- private List<File> directories;
- private BlockingIteratorImpl<DescriptorFile> descriptorQueue;
- private File historyFile;
- private boolean failUnrecognizedDescriptorLines;
- private DescriptorReader(List<File> directories,
- BlockingIteratorImpl<DescriptorFile> descriptorQueue,
- File historyFile, boolean failUnrecognizedDescriptorLines) {
- this.directories = directories;
- this.descriptorQueue = descriptorQueue;
- this.historyFile = historyFile;
- this.failUnrecognizedDescriptorLines =
- failUnrecognizedDescriptorLines;
- }
- public void run() {
- this.readOldHistory();
- this.readDescriptors();
- this.writeNewHistory();
- }
- private SortedMap<String, Long>
- oldHistory = new TreeMap<String, Long>(),
- newHistory = new TreeMap<String, Long>();
- private void readOldHistory() {
- if (this.historyFile == null) {
- return;
- }
- try {
- BufferedReader br = new BufferedReader(new FileReader(
- this.historyFile));
- String line;
- while ((line = br.readLine()) != null) {
- if (!line.contains(" ")) {
- /* TODO Handle this problem? */
- continue;
- }
- long lastModifiedMillis = Long.parseLong(line.substring(0,
- line.indexOf(" ")));
- String absolutePath = line.substring(line.indexOf(" ") + 1);
- this.oldHistory.put(absolutePath, lastModifiedMillis);
- }
- br.close();
- } catch (IOException e) {
- /* TODO Handle this exception. */
- } catch (NumberFormatException e) {
- /* TODO Handle this exception. */
- }
- }
- private void writeNewHistory() {
- if (this.historyFile == null) {
- return;
- }
- try {
- if (this.historyFile.getParentFile() != null) {
- this.historyFile.getParentFile().mkdirs();
- }
- BufferedWriter bw = new BufferedWriter(new FileWriter(
- this.historyFile));
- for (Map.Entry<String, Long> e : this.newHistory.entrySet()) {
- String absolutePath = e.getKey();
- long lastModifiedMillis = e.getValue();
- bw.write(String.valueOf(lastModifiedMillis) + " " + absolutePath
- + "\n");
- }
- bw.close();
- } catch (IOException e) {
- /* TODO Handle this exception. */
- }
- }
- private void readDescriptors() {
- for (File directory : this.directories) {
- Stack<File> files = new Stack<File>();
- files.add(directory);
- boolean abortReading = false;
- while (!abortReading && !files.isEmpty()) {
- File file = files.pop();
- if (file.isDirectory()) {
- files.addAll(Arrays.asList(file.listFiles()));
- } else {
- String absolutePath = file.getAbsolutePath();
- long lastModifiedMillis = file.lastModified();
- this.newHistory.put(absolutePath, lastModifiedMillis);
- if (this.oldHistory.containsKey(absolutePath) &&
- this.oldHistory.get(absolutePath) == lastModifiedMillis) {
- continue;
- }
- DescriptorFileImpl descriptorFile = new DescriptorFileImpl();
- try {
- descriptorFile.setDirectory(directory);
- descriptorFile.setFile(file);
- descriptorFile.setLastModified(lastModifiedMillis);
- descriptorFile.setDescriptors(this.readFile(file));
- } catch (DescriptorParseException e) {
- descriptorFile.setException(e);
- } catch (IOException e) {
- descriptorFile.setException(e);
- abortReading = true;
- }
- this.descriptorQueue.add(descriptorFile);
- }
- }
- }
- 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.parseRelayOrBridgeDescriptors(
- rawDescriptorBytes, file.getName(),
- this.failUnrecognizedDescriptorLines);
- }
- }
-}
-
1
0