From 45be6747c9a90dd2a00a7bff5dc68574c5a04384 Mon Sep 17 00:00:00 2001 From: acidvegas Date: Sun, 7 May 2023 13:44:21 -0400 Subject: [PATCH] Initial commit --- .BANNER | 19 + .gitignore | 19 + .mailmap | 50 + CMakeLists.txt | 559 + Config | 417 + Config.exe | Bin 0 -> 18944 bytes README.md | 46 + cmake/Anope.cmake | 555 + cmake/FindGettext.cmake | 26 + cmake/NSIS.template.in | 825 ++ cmake/ReadFile.cmake | 5 + data/CMakeLists.txt | 4 + data/botserv.conf | 132 + data/chanserv.conf | 472 + data/global.conf | 20 + data/hostserv.conf | 49 + data/nickserv.conf | 178 + data/operserv.conf | 148 + data/services.conf | 132 + docs/ASTYLE | 1 + docs/BUGS | 1 + docs/C++CASTING | 111 + docs/CMakeLists.txt | 15 + docs/CODING | 239 + docs/COPYING | 347 + docs/Changes | 412 + docs/Changes.conf | 220 + docs/DEFCON | 93 + docs/EVENTS | 34 + docs/FAQ | 10 + docs/INSTALL | 135 + docs/INSTALL.fr | 149 + docs/LANGUAGE | 53 + docs/MODULES | 128 + docs/NEWS | 6 + docs/README | 258 + docs/REDIS | 160 + docs/TOOLS | 25 + docs/WIN32.txt | 161 + docs/XMLRPC/XMLRPC | 29 + docs/XMLRPC/xmlrpc.php | 145 + extras | 168 + include/CMakeLists.txt | 64 + include/access.h | 174 + include/account.h | 290 + include/anope.h | 791 + include/base.h | 143 + include/bots.h | 135 + include/channels.h | 310 + include/commands.h | 187 + include/config.h | 184 + include/defs.h | 53 + include/extensible.h | 263 + include/hashcomp.h | 199 + include/language.h | 127 + include/lists.h | 94 + include/logger.h | 144 + include/mail.h | 56 + include/memo.h | 55 + include/messages.h | 173 + include/modes.h | 422 + include/module.h | 54 + include/modules.h | 1239 ++ include/modules/bs_badwords.h | 70 + include/modules/bs_kick.h | 44 + include/modules/cs_entrymsg.h | 34 + include/modules/cs_log.h | 42 + include/modules/cs_mode.h | 89 + include/modules/dns.h | 178 + include/modules/encryption.h | 35 + include/modules/httpd.h | 243 + include/modules/ldap.h | 171 + include/modules/ns_cert.h | 70 + include/modules/os_forbid.h | 55 + include/modules/os_ignore.h | 43 + include/modules/os_news.h | 52 + include/modules/os_session.h | 94 + include/modules/pseudoclients/chanserv.h | 25 + include/modules/pseudoclients/global.h | 30 + include/modules/pseudoclients/memoserv.h | 41 + include/modules/pseudoclients/nickserv.h | 24 + include/modules/redis.h | 74 + include/modules/sasl.h | 139 + include/modules/set_misc.h | 17 + include/modules/sql.h | 216 + include/modules/ssl.h | 15 + include/modules/suspend.h | 19 + include/modules/xmlrpc.h | 47 + include/opertype.h | 127 + include/protocol.h | 318 + include/pstdint.h | 800 + include/regchannel.h | 252 + include/regexpr.h | 45 + include/serialize.h | 335 + include/servers.h | 187 + include/service.h | 173 + include/services.h | 68 + include/socketengine.h | 50 + include/sockets.h | 511 + include/sysconf.h.cmake | 47 + include/threadengine.h | 120 + include/timers.h | 131 + include/uplink.h | 53 + include/users.h | 374 + include/version.cpp | 188 + include/xline.h | 184 + language/CMakeLists.txt | 37 + language/anope.ca_ES.po | 11920 +++++++++++++++ language/anope.de_DE.po | 11638 +++++++++++++++ language/anope.el_GR.po | 11858 +++++++++++++++ language/anope.en_US.po | 11070 ++++++++++++++ language/anope.es_ES.po | 11198 ++++++++++++++ language/anope.fr_FR.po | 11321 +++++++++++++++ language/anope.hu_HU.po | 11829 +++++++++++++++ language/anope.it_IT.po | 11224 ++++++++++++++ language/anope.nl_NL.po | 11212 ++++++++++++++ language/anope.pl_PL.po | 11060 ++++++++++++++ language/anope.pt_PT.po | 11801 +++++++++++++++ language/anope.ru_RU.po | 12087 ++++++++++++++++ language/anope.tr_TR.po | 11767 +++++++++++++++ language/update.sh | 16 + modules/CMakeLists.txt | 169 + modules/bs_autoassign.cpp | 36 + modules/commands/bs_assign.cpp | 256 + modules/commands/bs_badwords.cpp | 469 + modules/commands/bs_bot.cpp | 385 + modules/commands/bs_botlist.cpp | 82 + modules/commands/bs_control.cpp | 146 + modules/commands/bs_info.cpp | 134 + modules/commands/bs_kick.cpp | 1474 ++ modules/commands/bs_set.cpp | 228 + modules/commands/cs_access.cpp | 917 ++ modules/commands/cs_akick.cpp | 584 + modules/commands/cs_ban.cpp | 251 + modules/commands/cs_clone.cpp | 261 + modules/commands/cs_drop.cpp | 95 + modules/commands/cs_enforce.cpp | 292 + modules/commands/cs_entrymsg.cpp | 289 + modules/commands/cs_flags.cpp | 504 + modules/commands/cs_getkey.cpp | 73 + modules/commands/cs_info.cpp | 98 + modules/commands/cs_invite.cpp | 111 + modules/commands/cs_kick.cpp | 147 + modules/commands/cs_list.cpp | 266 + modules/commands/cs_log.cpp | 399 + modules/commands/cs_mode.cpp | 1069 ++ modules/commands/cs_register.cpp | 124 + modules/commands/cs_seen.cpp | 460 + modules/commands/cs_set.cpp | 1311 ++ modules/commands/cs_set_misc.cpp | 219 + modules/commands/cs_status.cpp | 125 + modules/commands/cs_suspend.cpp | 285 + modules/commands/cs_sync.cpp | 66 + modules/commands/cs_topic.cpp | 270 + modules/commands/cs_unban.cpp | 130 + modules/commands/cs_updown.cpp | 243 + modules/commands/cs_xop.cpp | 627 + modules/commands/gl_global.cpp | 66 + modules/commands/greet.cpp | 216 + modules/commands/help.cpp | 205 + modules/commands/hs_del.cpp | 113 + modules/commands/hs_group.cpp | 117 + modules/commands/hs_list.cpp | 160 + modules/commands/hs_off.cpp | 69 + modules/commands/hs_on.cpp | 75 + modules/commands/hs_request.cpp | 394 + modules/commands/hs_set.cpp | 229 + modules/commands/ms_cancel.cpp | 101 + modules/commands/ms_check.cpp | 87 + modules/commands/ms_del.cpp | 159 + modules/commands/ms_ignore.cpp | 132 + modules/commands/ms_info.cpp | 231 + modules/commands/ms_list.cpp | 164 + modules/commands/ms_read.cpp | 224 + modules/commands/ms_rsend.cpp | 104 + modules/commands/ms_send.cpp | 88 + modules/commands/ms_sendall.cpp | 70 + modules/commands/ms_set.cpp | 315 + modules/commands/ms_staff.cpp | 67 + modules/commands/ns_access.cpp | 206 + modules/commands/ns_ajoin.cpp | 405 + modules/commands/ns_alist.cpp | 149 + modules/commands/ns_cert.cpp | 407 + modules/commands/ns_drop.cpp | 86 + modules/commands/ns_getemail.cpp | 74 + modules/commands/ns_getpass.cpp | 74 + modules/commands/ns_group.cpp | 396 + modules/commands/ns_identify.cpp | 128 + modules/commands/ns_info.cpp | 283 + modules/commands/ns_list.cpp | 301 + modules/commands/ns_logout.cpp | 91 + modules/commands/ns_recover.cpp | 298 + modules/commands/ns_register.cpp | 438 + modules/commands/ns_resetpass.cpp | 144 + modules/commands/ns_set.cpp | 1350 ++ modules/commands/ns_set_misc.cpp | 234 + modules/commands/ns_status.cpp | 87 + modules/commands/ns_suspend.cpp | 288 + modules/commands/ns_update.cpp | 62 + modules/commands/os_akill.cpp | 483 + modules/commands/os_chankill.cpp | 119 + modules/commands/os_config.cpp | 150 + modules/commands/os_defcon.cpp | 603 + modules/commands/os_dns.cpp | 948 ++ modules/commands/os_forbid.cpp | 571 + modules/commands/os_ignore.cpp | 416 + modules/commands/os_info.cpp | 290 + modules/commands/os_jupe.cpp | 80 + modules/commands/os_kick.cpp | 84 + modules/commands/os_kill.cpp | 67 + modules/commands/os_list.cpp | 276 + modules/commands/os_login.cpp | 132 + modules/commands/os_logsearch.cpp | 185 + modules/commands/os_mode.cpp | 192 + modules/commands/os_modinfo.cpp | 214 + modules/commands/os_module.cpp | 188 + modules/commands/os_news.cpp | 464 + modules/commands/os_noop.cpp | 100 + modules/commands/os_oline.cpp | 78 + modules/commands/os_oper.cpp | 292 + modules/commands/os_reload.cpp | 67 + modules/commands/os_session.cpp | 737 + modules/commands/os_set.cpp | 267 + modules/commands/os_shutdown.cpp | 108 + modules/commands/os_stats.cpp | 276 + modules/commands/os_svs.cpp | 178 + modules/commands/os_sxline.cpp | 732 + modules/commands/os_update.cpp | 52 + modules/cs_statusupdate.cpp | 65 + modules/database/db_flatfile.cpp | 411 + modules/database/db_old.cpp | 1360 ++ modules/database/db_redis.cpp | 668 + modules/database/db_sql.cpp | 268 + modules/database/db_sql_live.cpp | 264 + modules/encryption/enc_bcrypt.cpp | 964 ++ modules/encryption/enc_md5.cpp | 395 + modules/encryption/enc_none.cpp | 69 + modules/encryption/enc_old.cpp | 110 + modules/encryption/enc_sha1.cpp | 252 + modules/encryption/enc_sha256.cpp | 334 + modules/extra/CMakeLists.txt | 3 + modules/extra/m_ldap.cpp | 626 + modules/extra/m_ldap_authentication.cpp | 304 + modules/extra/m_ldap_oper.cpp | 138 + modules/extra/m_mysql.cpp | 555 + modules/extra/m_regex_pcre.cpp | 83 + modules/extra/m_regex_pcre2.cpp | 93 + modules/extra/m_regex_posix.cpp | 84 + modules/extra/m_regex_tre.cpp | 85 + modules/extra/m_sql_authentication.cpp | 148 + modules/extra/m_sql_log.cpp | 108 + modules/extra/m_sql_oper.cpp | 180 + modules/extra/m_sqlite.cpp | 334 + modules/extra/m_ssl_gnutls.cpp | 656 + modules/extra/m_ssl_openssl.cpp | 422 + modules/extra/stats/cs_fantasy_stats.cpp | 176 + modules/extra/stats/cs_fantasy_top.cpp | 188 + modules/extra/stats/irc2sql/CMakeLists.txt | 1 + modules/extra/stats/irc2sql/irc2sql.cpp | 327 + modules/extra/stats/irc2sql/irc2sql.h | 84 + modules/extra/stats/irc2sql/tables.cpp | 343 + modules/extra/stats/irc2sql/utils.cpp | 68 + modules/extra/stats/m_chanstats.cpp | 655 + modules/fantasy.cpp | 218 + modules/m_dns.cpp | 1125 ++ modules/m_dnsbl.cpp | 198 + modules/m_helpchan.cpp | 32 + modules/m_httpd.cpp | 472 + modules/m_proxyscan.cpp | 378 + modules/m_redis.cpp | 625 + modules/m_rewrite.cpp | 187 + modules/m_sasl.cpp | 357 + modules/m_xmlrpc.cpp | 228 + modules/m_xmlrpc_main.cpp | 310 + modules/ns_maxemail.cpp | 114 + modules/protocol/bahamut.cpp | 570 + modules/protocol/charybdis.cpp | 427 + modules/protocol/hybrid.cpp | 875 ++ modules/protocol/inspircd12.cpp | 1400 ++ modules/protocol/inspircd20.cpp | 1106 ++ modules/protocol/inspircd3.cpp | 1987 +++ modules/protocol/ngircd.cpp | 679 + modules/protocol/plexus.cpp | 451 + modules/protocol/ratbox.cpp | 373 + modules/protocol/unreal.cpp | 1340 ++ modules/protocol/unreal4.cpp | 1741 +++ modules/pseudoclients/botserv.cpp | 214 + modules/pseudoclients/chanserv.cpp | 480 + modules/pseudoclients/global.cpp | 100 + modules/pseudoclients/hostserv.cpp | 130 + modules/pseudoclients/memoserv.cpp | 233 + modules/pseudoclients/nickserv.cpp | 567 + modules/pseudoclients/operserv.cpp | 298 + modules/third/README | 2 + modules/third/language/CMakeLists.txt | 38 + modules/third/language/README | 1 + modules/third/language/update.sh | 14 + modules/webcpanel/CMakeLists.txt | 5 + modules/webcpanel/pages/chanserv/access.cpp | 127 + modules/webcpanel/pages/chanserv/access.h | 26 + modules/webcpanel/pages/chanserv/akick.cpp | 93 + modules/webcpanel/pages/chanserv/akick.h | 26 + modules/webcpanel/pages/chanserv/drop.cpp | 58 + modules/webcpanel/pages/chanserv/drop.h | 25 + modules/webcpanel/pages/chanserv/info.cpp | 27 + modules/webcpanel/pages/chanserv/info.h | 24 + modules/webcpanel/pages/chanserv/modes.cpp | 111 + modules/webcpanel/pages/chanserv/modes.h | 26 + modules/webcpanel/pages/chanserv/set.cpp | 154 + modules/webcpanel/pages/chanserv/set.h | 26 + modules/webcpanel/pages/chanserv/utils.cpp | 44 + modules/webcpanel/pages/chanserv/utils.h | 18 + modules/webcpanel/pages/confirm.cpp | 31 + modules/webcpanel/pages/confirm.h | 21 + modules/webcpanel/pages/hostserv/request.cpp | 36 + modules/webcpanel/pages/hostserv/request.h | 24 + modules/webcpanel/pages/index.cpp | 137 + modules/webcpanel/pages/index.h | 26 + modules/webcpanel/pages/logout.cpp | 22 + modules/webcpanel/pages/logout.h | 19 + modules/webcpanel/pages/memoserv/memos.cpp | 114 + modules/webcpanel/pages/memoserv/memos.h | 24 + modules/webcpanel/pages/nickserv/access.cpp | 39 + modules/webcpanel/pages/nickserv/access.h | 24 + modules/webcpanel/pages/nickserv/alist.cpp | 57 + modules/webcpanel/pages/nickserv/alist.h | 24 + modules/webcpanel/pages/nickserv/cert.cpp | 42 + modules/webcpanel/pages/nickserv/cert.h | 24 + modules/webcpanel/pages/nickserv/confirm.cpp | 26 + modules/webcpanel/pages/nickserv/confirm.h | 24 + modules/webcpanel/pages/nickserv/info.cpp | 117 + modules/webcpanel/pages/nickserv/info.h | 24 + modules/webcpanel/pages/operserv/akill.cpp | 63 + modules/webcpanel/pages/operserv/akill.h | 24 + modules/webcpanel/pages/register.cpp | 23 + modules/webcpanel/pages/register.h | 21 + modules/webcpanel/static_fileserver.cpp | 41 + modules/webcpanel/static_fileserver.h | 18 + modules/webcpanel/template_fileserver.cpp | 267 + modules/webcpanel/template_fileserver.h | 26 + .../templates/default/chanserv/access.html | 77 + .../templates/default/chanserv/akick.html | 61 + .../templates/default/chanserv/chanlist.html | 17 + .../templates/default/chanserv/drop.html | 32 + .../templates/default/chanserv/main.html | 3 + .../templates/default/chanserv/modes.html | 56 + .../templates/default/chanserv/set.html | 93 + .../webcpanel/templates/default/confirm.html | 51 + modules/webcpanel/templates/default/cubes.png | Bin 0 -> 723 bytes .../webcpanel/templates/default/favicon.ico | Bin 0 -> 3774 bytes .../webcpanel/templates/default/footer.html | 14 + .../webcpanel/templates/default/header.html | 64 + .../templates/default/hostserv/request.html | 45 + .../webcpanel/templates/default/login.html | 55 + modules/webcpanel/templates/default/logo.png | Bin 0 -> 19247 bytes .../templates/default/memoserv/memos.html | 112 + .../templates/default/nickserv/access.html | 42 + .../templates/default/nickserv/alist.html | 23 + .../templates/default/nickserv/cert.html | 42 + .../templates/default/nickserv/confirm.html | 29 + .../templates/default/nickserv/info.html | 72 + .../templates/default/operserv/akill.html | 77 + .../webcpanel/templates/default/register.html | 65 + modules/webcpanel/templates/default/style.css | 166 + modules/webcpanel/webcpanel.cpp | 324 + modules/webcpanel/webcpanel.h | 182 + src/CMakeLists.txt | 116 + src/access.cpp | 475 + src/account.cpp | 91 + src/base.cpp | 48 + src/base64.cpp | 163 + src/bots.cpp | 277 + src/channels.cpp | 961 ++ src/command.cpp | 314 + src/config.cpp | 947 ++ src/extensible.cpp | 71 + src/hashcomp.cpp | 163 + src/init.cpp | 567 + src/language.cpp | 127 + src/logger.cpp | 418 + src/mail.cpp | 164 + src/main.cpp | 218 + src/memos.cpp | 140 + src/messages.cpp | 502 + src/misc.cpp | 765 + src/modes.cpp | 896 ++ src/module.cpp | 129 + src/modulemanager.cpp | 526 + src/nickalias.cpp | 216 + src/nickcore.cpp | 318 + src/opertype.cpp | 147 + src/pipeengine.cpp | 80 + src/process.cpp | 182 + src/protocol.cpp | 516 + src/regchannel.cpp | 694 + src/serialize.cpp | 177 + src/servers.cpp | 360 + src/siphash.cpp | 139 + src/socket_clients.cpp | 98 + src/socket_transport.cpp | 198 + src/socketengines/socketengine_epoll.cpp | 121 + src/socketengines/socketengine_kqueue.cpp | 123 + src/socketengines/socketengine_poll.cpp | 148 + src/socketengines/socketengine_select.cpp | 148 + src/sockets.cpp | 611 + src/threadengine.cpp | 136 + src/timers.cpp | 126 + src/tools/CMakeLists.txt | 52 + src/tools/anoperc.in | 137 + src/tools/anopesmtp.cpp | 535 + src/tools/geoipupdate.sh | 81 + src/uplink.cpp | 212 + src/users.cpp | 846 ++ src/version.sh | 6 + src/win32/Config.cs | 363 + src/win32/anope-icon.ico | Bin 0 -> 3774 bytes src/win32/anope.bat | 3 + src/win32/anope_windows.h | 81 + src/win32/dir/dir.cpp | 48 + src/win32/dir/dir.h | 27 + src/win32/dl/dl.cpp | 33 + src/win32/dl/dl.h | 14 + src/win32/pipe/pipe.cpp | 61 + src/win32/pipe/pipe.h | 9 + src/win32/pthread/pthread.cpp | 119 + src/win32/pthread/pthread.h | 35 + src/win32/resource.h | 28 + src/win32/sigaction/sigaction.cpp | 31 + src/win32/sigaction/sigaction.h | 28 + src/win32/socket.cpp | 153 + src/win32/socket.h | 32 + src/win32/win32.rc.cmake | 92 + src/win32/win32_memory.cpp | 64 + src/win32/windows.cpp | 261 + src/xline.cpp | 469 + 435 files changed, 245769 insertions(+) create mode 100644 .BANNER create mode 100644 .gitignore create mode 100644 .mailmap create mode 100644 CMakeLists.txt create mode 100755 Config create mode 100644 Config.exe create mode 100644 README.md create mode 100644 cmake/Anope.cmake create mode 100644 cmake/FindGettext.cmake create mode 100644 cmake/NSIS.template.in create mode 100644 cmake/ReadFile.cmake create mode 100644 data/CMakeLists.txt create mode 100644 data/botserv.conf create mode 100644 data/chanserv.conf create mode 100644 data/global.conf create mode 100644 data/hostserv.conf create mode 100644 data/nickserv.conf create mode 100644 data/operserv.conf create mode 100644 data/services.conf create mode 100644 docs/ASTYLE create mode 100644 docs/BUGS create mode 100644 docs/C++CASTING create mode 100644 docs/CMakeLists.txt create mode 100644 docs/CODING create mode 100644 docs/COPYING create mode 100644 docs/Changes create mode 100644 docs/Changes.conf create mode 100644 docs/DEFCON create mode 100644 docs/EVENTS create mode 100644 docs/FAQ create mode 100644 docs/INSTALL create mode 100644 docs/INSTALL.fr create mode 100644 docs/LANGUAGE create mode 100644 docs/MODULES create mode 100644 docs/NEWS create mode 100644 docs/README create mode 100644 docs/REDIS create mode 100644 docs/TOOLS create mode 100644 docs/WIN32.txt create mode 100644 docs/XMLRPC/XMLRPC create mode 100644 docs/XMLRPC/xmlrpc.php create mode 100755 extras create mode 100644 include/CMakeLists.txt create mode 100644 include/access.h create mode 100644 include/account.h create mode 100644 include/anope.h create mode 100644 include/base.h create mode 100644 include/bots.h create mode 100644 include/channels.h create mode 100644 include/commands.h create mode 100644 include/config.h create mode 100644 include/defs.h create mode 100644 include/extensible.h create mode 100644 include/hashcomp.h create mode 100644 include/language.h create mode 100644 include/lists.h create mode 100644 include/logger.h create mode 100644 include/mail.h create mode 100644 include/memo.h create mode 100644 include/messages.h create mode 100644 include/modes.h create mode 100644 include/module.h create mode 100644 include/modules.h create mode 100644 include/modules/bs_badwords.h create mode 100644 include/modules/bs_kick.h create mode 100644 include/modules/cs_entrymsg.h create mode 100644 include/modules/cs_log.h create mode 100644 include/modules/cs_mode.h create mode 100644 include/modules/dns.h create mode 100644 include/modules/encryption.h create mode 100644 include/modules/httpd.h create mode 100644 include/modules/ldap.h create mode 100644 include/modules/ns_cert.h create mode 100644 include/modules/os_forbid.h create mode 100644 include/modules/os_ignore.h create mode 100644 include/modules/os_news.h create mode 100644 include/modules/os_session.h create mode 100644 include/modules/pseudoclients/chanserv.h create mode 100644 include/modules/pseudoclients/global.h create mode 100644 include/modules/pseudoclients/memoserv.h create mode 100644 include/modules/pseudoclients/nickserv.h create mode 100644 include/modules/redis.h create mode 100644 include/modules/sasl.h create mode 100644 include/modules/set_misc.h create mode 100644 include/modules/sql.h create mode 100644 include/modules/ssl.h create mode 100644 include/modules/suspend.h create mode 100644 include/modules/xmlrpc.h create mode 100644 include/opertype.h create mode 100644 include/protocol.h create mode 100644 include/pstdint.h create mode 100644 include/regchannel.h create mode 100644 include/regexpr.h create mode 100644 include/serialize.h create mode 100644 include/servers.h create mode 100644 include/service.h create mode 100644 include/services.h create mode 100644 include/socketengine.h create mode 100644 include/sockets.h create mode 100644 include/sysconf.h.cmake create mode 100644 include/threadengine.h create mode 100644 include/timers.h create mode 100644 include/uplink.h create mode 100644 include/users.h create mode 100644 include/version.cpp create mode 100644 include/xline.h create mode 100644 language/CMakeLists.txt create mode 100644 language/anope.ca_ES.po create mode 100644 language/anope.de_DE.po create mode 100644 language/anope.el_GR.po create mode 100644 language/anope.en_US.po create mode 100644 language/anope.es_ES.po create mode 100644 language/anope.fr_FR.po create mode 100644 language/anope.hu_HU.po create mode 100644 language/anope.it_IT.po create mode 100644 language/anope.nl_NL.po create mode 100644 language/anope.pl_PL.po create mode 100644 language/anope.pt_PT.po create mode 100644 language/anope.ru_RU.po create mode 100644 language/anope.tr_TR.po create mode 100755 language/update.sh create mode 100644 modules/CMakeLists.txt create mode 100644 modules/bs_autoassign.cpp create mode 100644 modules/commands/bs_assign.cpp create mode 100644 modules/commands/bs_badwords.cpp create mode 100644 modules/commands/bs_bot.cpp create mode 100644 modules/commands/bs_botlist.cpp create mode 100644 modules/commands/bs_control.cpp create mode 100644 modules/commands/bs_info.cpp create mode 100644 modules/commands/bs_kick.cpp create mode 100644 modules/commands/bs_set.cpp create mode 100644 modules/commands/cs_access.cpp create mode 100644 modules/commands/cs_akick.cpp create mode 100644 modules/commands/cs_ban.cpp create mode 100644 modules/commands/cs_clone.cpp create mode 100644 modules/commands/cs_drop.cpp create mode 100644 modules/commands/cs_enforce.cpp create mode 100644 modules/commands/cs_entrymsg.cpp create mode 100644 modules/commands/cs_flags.cpp create mode 100644 modules/commands/cs_getkey.cpp create mode 100644 modules/commands/cs_info.cpp create mode 100644 modules/commands/cs_invite.cpp create mode 100644 modules/commands/cs_kick.cpp create mode 100644 modules/commands/cs_list.cpp create mode 100644 modules/commands/cs_log.cpp create mode 100644 modules/commands/cs_mode.cpp create mode 100644 modules/commands/cs_register.cpp create mode 100644 modules/commands/cs_seen.cpp create mode 100644 modules/commands/cs_set.cpp create mode 100644 modules/commands/cs_set_misc.cpp create mode 100644 modules/commands/cs_status.cpp create mode 100644 modules/commands/cs_suspend.cpp create mode 100644 modules/commands/cs_sync.cpp create mode 100644 modules/commands/cs_topic.cpp create mode 100644 modules/commands/cs_unban.cpp create mode 100644 modules/commands/cs_updown.cpp create mode 100644 modules/commands/cs_xop.cpp create mode 100644 modules/commands/gl_global.cpp create mode 100644 modules/commands/greet.cpp create mode 100644 modules/commands/help.cpp create mode 100644 modules/commands/hs_del.cpp create mode 100644 modules/commands/hs_group.cpp create mode 100644 modules/commands/hs_list.cpp create mode 100644 modules/commands/hs_off.cpp create mode 100644 modules/commands/hs_on.cpp create mode 100644 modules/commands/hs_request.cpp create mode 100644 modules/commands/hs_set.cpp create mode 100644 modules/commands/ms_cancel.cpp create mode 100644 modules/commands/ms_check.cpp create mode 100644 modules/commands/ms_del.cpp create mode 100644 modules/commands/ms_ignore.cpp create mode 100644 modules/commands/ms_info.cpp create mode 100644 modules/commands/ms_list.cpp create mode 100644 modules/commands/ms_read.cpp create mode 100644 modules/commands/ms_rsend.cpp create mode 100644 modules/commands/ms_send.cpp create mode 100644 modules/commands/ms_sendall.cpp create mode 100644 modules/commands/ms_set.cpp create mode 100644 modules/commands/ms_staff.cpp create mode 100644 modules/commands/ns_access.cpp create mode 100644 modules/commands/ns_ajoin.cpp create mode 100644 modules/commands/ns_alist.cpp create mode 100644 modules/commands/ns_cert.cpp create mode 100644 modules/commands/ns_drop.cpp create mode 100644 modules/commands/ns_getemail.cpp create mode 100644 modules/commands/ns_getpass.cpp create mode 100644 modules/commands/ns_group.cpp create mode 100644 modules/commands/ns_identify.cpp create mode 100644 modules/commands/ns_info.cpp create mode 100644 modules/commands/ns_list.cpp create mode 100644 modules/commands/ns_logout.cpp create mode 100644 modules/commands/ns_recover.cpp create mode 100644 modules/commands/ns_register.cpp create mode 100644 modules/commands/ns_resetpass.cpp create mode 100644 modules/commands/ns_set.cpp create mode 100644 modules/commands/ns_set_misc.cpp create mode 100644 modules/commands/ns_status.cpp create mode 100644 modules/commands/ns_suspend.cpp create mode 100644 modules/commands/ns_update.cpp create mode 100644 modules/commands/os_akill.cpp create mode 100644 modules/commands/os_chankill.cpp create mode 100644 modules/commands/os_config.cpp create mode 100644 modules/commands/os_defcon.cpp create mode 100644 modules/commands/os_dns.cpp create mode 100644 modules/commands/os_forbid.cpp create mode 100644 modules/commands/os_ignore.cpp create mode 100644 modules/commands/os_info.cpp create mode 100644 modules/commands/os_jupe.cpp create mode 100644 modules/commands/os_kick.cpp create mode 100644 modules/commands/os_kill.cpp create mode 100644 modules/commands/os_list.cpp create mode 100644 modules/commands/os_login.cpp create mode 100644 modules/commands/os_logsearch.cpp create mode 100644 modules/commands/os_mode.cpp create mode 100644 modules/commands/os_modinfo.cpp create mode 100644 modules/commands/os_module.cpp create mode 100644 modules/commands/os_news.cpp create mode 100644 modules/commands/os_noop.cpp create mode 100644 modules/commands/os_oline.cpp create mode 100644 modules/commands/os_oper.cpp create mode 100644 modules/commands/os_reload.cpp create mode 100644 modules/commands/os_session.cpp create mode 100644 modules/commands/os_set.cpp create mode 100644 modules/commands/os_shutdown.cpp create mode 100644 modules/commands/os_stats.cpp create mode 100644 modules/commands/os_svs.cpp create mode 100644 modules/commands/os_sxline.cpp create mode 100644 modules/commands/os_update.cpp create mode 100644 modules/cs_statusupdate.cpp create mode 100644 modules/database/db_flatfile.cpp create mode 100644 modules/database/db_old.cpp create mode 100644 modules/database/db_redis.cpp create mode 100644 modules/database/db_sql.cpp create mode 100644 modules/database/db_sql_live.cpp create mode 100644 modules/encryption/enc_bcrypt.cpp create mode 100644 modules/encryption/enc_md5.cpp create mode 100644 modules/encryption/enc_none.cpp create mode 100644 modules/encryption/enc_old.cpp create mode 100644 modules/encryption/enc_sha1.cpp create mode 100644 modules/encryption/enc_sha256.cpp create mode 100644 modules/extra/CMakeLists.txt create mode 100644 modules/extra/m_ldap.cpp create mode 100644 modules/extra/m_ldap_authentication.cpp create mode 100644 modules/extra/m_ldap_oper.cpp create mode 100644 modules/extra/m_mysql.cpp create mode 100644 modules/extra/m_regex_pcre.cpp create mode 100644 modules/extra/m_regex_pcre2.cpp create mode 100644 modules/extra/m_regex_posix.cpp create mode 100644 modules/extra/m_regex_tre.cpp create mode 100644 modules/extra/m_sql_authentication.cpp create mode 100644 modules/extra/m_sql_log.cpp create mode 100644 modules/extra/m_sql_oper.cpp create mode 100644 modules/extra/m_sqlite.cpp create mode 100644 modules/extra/m_ssl_gnutls.cpp create mode 100644 modules/extra/m_ssl_openssl.cpp create mode 100644 modules/extra/stats/cs_fantasy_stats.cpp create mode 100644 modules/extra/stats/cs_fantasy_top.cpp create mode 100644 modules/extra/stats/irc2sql/CMakeLists.txt create mode 100644 modules/extra/stats/irc2sql/irc2sql.cpp create mode 100644 modules/extra/stats/irc2sql/irc2sql.h create mode 100644 modules/extra/stats/irc2sql/tables.cpp create mode 100644 modules/extra/stats/irc2sql/utils.cpp create mode 100644 modules/extra/stats/m_chanstats.cpp create mode 100644 modules/fantasy.cpp create mode 100644 modules/m_dns.cpp create mode 100644 modules/m_dnsbl.cpp create mode 100644 modules/m_helpchan.cpp create mode 100644 modules/m_httpd.cpp create mode 100644 modules/m_proxyscan.cpp create mode 100644 modules/m_redis.cpp create mode 100644 modules/m_rewrite.cpp create mode 100644 modules/m_sasl.cpp create mode 100644 modules/m_xmlrpc.cpp create mode 100644 modules/m_xmlrpc_main.cpp create mode 100644 modules/ns_maxemail.cpp create mode 100644 modules/protocol/bahamut.cpp create mode 100644 modules/protocol/charybdis.cpp create mode 100644 modules/protocol/hybrid.cpp create mode 100644 modules/protocol/inspircd12.cpp create mode 100644 modules/protocol/inspircd20.cpp create mode 100644 modules/protocol/inspircd3.cpp create mode 100644 modules/protocol/ngircd.cpp create mode 100644 modules/protocol/plexus.cpp create mode 100644 modules/protocol/ratbox.cpp create mode 100644 modules/protocol/unreal.cpp create mode 100644 modules/protocol/unreal4.cpp create mode 100644 modules/pseudoclients/botserv.cpp create mode 100644 modules/pseudoclients/chanserv.cpp create mode 100644 modules/pseudoclients/global.cpp create mode 100644 modules/pseudoclients/hostserv.cpp create mode 100644 modules/pseudoclients/memoserv.cpp create mode 100644 modules/pseudoclients/nickserv.cpp create mode 100644 modules/pseudoclients/operserv.cpp create mode 100644 modules/third/README create mode 100644 modules/third/language/CMakeLists.txt create mode 100644 modules/third/language/README create mode 100755 modules/third/language/update.sh create mode 100644 modules/webcpanel/CMakeLists.txt create mode 100644 modules/webcpanel/pages/chanserv/access.cpp create mode 100644 modules/webcpanel/pages/chanserv/access.h create mode 100644 modules/webcpanel/pages/chanserv/akick.cpp create mode 100644 modules/webcpanel/pages/chanserv/akick.h create mode 100644 modules/webcpanel/pages/chanserv/drop.cpp create mode 100644 modules/webcpanel/pages/chanserv/drop.h create mode 100644 modules/webcpanel/pages/chanserv/info.cpp create mode 100644 modules/webcpanel/pages/chanserv/info.h create mode 100644 modules/webcpanel/pages/chanserv/modes.cpp create mode 100644 modules/webcpanel/pages/chanserv/modes.h create mode 100644 modules/webcpanel/pages/chanserv/set.cpp create mode 100644 modules/webcpanel/pages/chanserv/set.h create mode 100644 modules/webcpanel/pages/chanserv/utils.cpp create mode 100644 modules/webcpanel/pages/chanserv/utils.h create mode 100644 modules/webcpanel/pages/confirm.cpp create mode 100644 modules/webcpanel/pages/confirm.h create mode 100644 modules/webcpanel/pages/hostserv/request.cpp create mode 100644 modules/webcpanel/pages/hostserv/request.h create mode 100644 modules/webcpanel/pages/index.cpp create mode 100644 modules/webcpanel/pages/index.h create mode 100644 modules/webcpanel/pages/logout.cpp create mode 100644 modules/webcpanel/pages/logout.h create mode 100644 modules/webcpanel/pages/memoserv/memos.cpp create mode 100644 modules/webcpanel/pages/memoserv/memos.h create mode 100644 modules/webcpanel/pages/nickserv/access.cpp create mode 100644 modules/webcpanel/pages/nickserv/access.h create mode 100644 modules/webcpanel/pages/nickserv/alist.cpp create mode 100644 modules/webcpanel/pages/nickserv/alist.h create mode 100644 modules/webcpanel/pages/nickserv/cert.cpp create mode 100644 modules/webcpanel/pages/nickserv/cert.h create mode 100644 modules/webcpanel/pages/nickserv/confirm.cpp create mode 100644 modules/webcpanel/pages/nickserv/confirm.h create mode 100644 modules/webcpanel/pages/nickserv/info.cpp create mode 100644 modules/webcpanel/pages/nickserv/info.h create mode 100644 modules/webcpanel/pages/operserv/akill.cpp create mode 100644 modules/webcpanel/pages/operserv/akill.h create mode 100644 modules/webcpanel/pages/register.cpp create mode 100644 modules/webcpanel/pages/register.h create mode 100644 modules/webcpanel/static_fileserver.cpp create mode 100644 modules/webcpanel/static_fileserver.h create mode 100644 modules/webcpanel/template_fileserver.cpp create mode 100644 modules/webcpanel/template_fileserver.h create mode 100644 modules/webcpanel/templates/default/chanserv/access.html create mode 100644 modules/webcpanel/templates/default/chanserv/akick.html create mode 100644 modules/webcpanel/templates/default/chanserv/chanlist.html create mode 100644 modules/webcpanel/templates/default/chanserv/drop.html create mode 100644 modules/webcpanel/templates/default/chanserv/main.html create mode 100644 modules/webcpanel/templates/default/chanserv/modes.html create mode 100644 modules/webcpanel/templates/default/chanserv/set.html create mode 100644 modules/webcpanel/templates/default/confirm.html create mode 100644 modules/webcpanel/templates/default/cubes.png create mode 100644 modules/webcpanel/templates/default/favicon.ico create mode 100644 modules/webcpanel/templates/default/footer.html create mode 100644 modules/webcpanel/templates/default/header.html create mode 100644 modules/webcpanel/templates/default/hostserv/request.html create mode 100644 modules/webcpanel/templates/default/login.html create mode 100644 modules/webcpanel/templates/default/logo.png create mode 100644 modules/webcpanel/templates/default/memoserv/memos.html create mode 100644 modules/webcpanel/templates/default/nickserv/access.html create mode 100644 modules/webcpanel/templates/default/nickserv/alist.html create mode 100644 modules/webcpanel/templates/default/nickserv/cert.html create mode 100644 modules/webcpanel/templates/default/nickserv/confirm.html create mode 100644 modules/webcpanel/templates/default/nickserv/info.html create mode 100644 modules/webcpanel/templates/default/operserv/akill.html create mode 100644 modules/webcpanel/templates/default/register.html create mode 100644 modules/webcpanel/templates/default/style.css create mode 100644 modules/webcpanel/webcpanel.cpp create mode 100644 modules/webcpanel/webcpanel.h create mode 100644 src/CMakeLists.txt create mode 100644 src/access.cpp create mode 100644 src/account.cpp create mode 100644 src/base.cpp create mode 100644 src/base64.cpp create mode 100644 src/bots.cpp create mode 100644 src/channels.cpp create mode 100644 src/command.cpp create mode 100644 src/config.cpp create mode 100644 src/extensible.cpp create mode 100644 src/hashcomp.cpp create mode 100644 src/init.cpp create mode 100644 src/language.cpp create mode 100644 src/logger.cpp create mode 100644 src/mail.cpp create mode 100644 src/main.cpp create mode 100644 src/memos.cpp create mode 100644 src/messages.cpp create mode 100644 src/misc.cpp create mode 100644 src/modes.cpp create mode 100644 src/module.cpp create mode 100644 src/modulemanager.cpp create mode 100644 src/nickalias.cpp create mode 100644 src/nickcore.cpp create mode 100644 src/opertype.cpp create mode 100644 src/pipeengine.cpp create mode 100644 src/process.cpp create mode 100644 src/protocol.cpp create mode 100644 src/regchannel.cpp create mode 100644 src/serialize.cpp create mode 100644 src/servers.cpp create mode 100644 src/siphash.cpp create mode 100644 src/socket_clients.cpp create mode 100644 src/socket_transport.cpp create mode 100644 src/socketengines/socketengine_epoll.cpp create mode 100644 src/socketengines/socketengine_kqueue.cpp create mode 100644 src/socketengines/socketengine_poll.cpp create mode 100644 src/socketengines/socketengine_select.cpp create mode 100644 src/sockets.cpp create mode 100644 src/threadengine.cpp create mode 100644 src/timers.cpp create mode 100644 src/tools/CMakeLists.txt create mode 100644 src/tools/anoperc.in create mode 100644 src/tools/anopesmtp.cpp create mode 100755 src/tools/geoipupdate.sh create mode 100644 src/uplink.cpp create mode 100644 src/users.cpp create mode 100644 src/version.sh create mode 100644 src/win32/Config.cs create mode 100644 src/win32/anope-icon.ico create mode 100644 src/win32/anope.bat create mode 100644 src/win32/anope_windows.h create mode 100644 src/win32/dir/dir.cpp create mode 100644 src/win32/dir/dir.h create mode 100644 src/win32/dl/dl.cpp create mode 100644 src/win32/dl/dl.h create mode 100644 src/win32/pipe/pipe.cpp create mode 100644 src/win32/pipe/pipe.h create mode 100644 src/win32/pthread/pthread.cpp create mode 100644 src/win32/pthread/pthread.h create mode 100644 src/win32/resource.h create mode 100644 src/win32/sigaction/sigaction.cpp create mode 100644 src/win32/sigaction/sigaction.h create mode 100644 src/win32/socket.cpp create mode 100644 src/win32/socket.h create mode 100644 src/win32/win32.rc.cmake create mode 100644 src/win32/win32_memory.cpp create mode 100644 src/win32/windows.cpp create mode 100644 src/xline.cpp diff --git a/.BANNER b/.BANNER new file mode 100644 index 0000000..bae644c --- /dev/null +++ b/.BANNER @@ -0,0 +1,19 @@ + ___ + / _ \ https://www.anope.org/ + | /_\ | _ __ _ _ _ _ ___ + | _ || '_ \/ _ \/ _ \ / _ \ + | | | || | | |_| |_| | __/ + |_| |_||_| |_\___/| _/ \___| + | | + |_| IRC Services + CURVER +This program will help you to compile your Services, and ask you +questions regarding the compile-time settings of it during the +process. For more options type SOURCE_DIR/Config --help + +Anope is a set of Services for IRC networks that allows users to +manage their nicks and channels in a secure and efficient way, +and administrators to manage their network with powerful tools. + +For all your Anope needs please visit our portal at +https://www.anope.org/ diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..03a3a02 --- /dev/null +++ b/.gitignore @@ -0,0 +1,19 @@ +build/ +config.cache +include/sysconf.h +modules/m_ldap.cpp +modules/m_ldap_authentication.cpp +modules/m_ldap_oper.cpp +modules/m_mysql.cpp +modules/m_regex_pcre.cpp +modules/m_regex_pcre2.cpp +modules/m_regex_posix.cpp +modules/m_regex_tre.cpp +modules/m_sql_authentication.cpp +modules/m_sql_log.cpp +modules/m_sql_oper.cpp +modules/m_sqlite.cpp +modules/m_ssl_gnutls.cpp +modules/m_ssl_openssl.cpp +modules/stats +run/ diff --git a/.mailmap b/.mailmap new file mode 100644 index 0000000..caa688a --- /dev/null +++ b/.mailmap @@ -0,0 +1,50 @@ +(svnadmin) +Adam +Adam +Adam +Adam +Adam +Adam Kramer +Alvaro Toledo +Attila Molnar +Björn Stiddien +Charles Kingsley +Charles Kingsley +Cronus +Daniel Engel +David Robson +David Robson +Dennis Friis +Fabio Scotoni +Florian Schulze +Gabriel Acevedo H. +Harakiri +Jan Milants +Jan Milants +Jan Milants +Jens Voss +Jens Voss +Jens Voss +Jens Voss Jens Voß +Lee Holmes +Lee Holmes +Mark Summers +Matt Schatz +Matt Ullman +Michael Hazell +Michael Wobst +Michael Wobst +Michael Wobst +Naram Qashat +Naram Qashat +Naram Qashat +Pieter Bootsma +Robby +Robby +Robin Burchell +Robin Burchell +Sadie Powell Peter Powell +Sebastian Barfurth +Sebastian V. +Sebastian V. +Trystan S. Lee diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 0000000..518c198 --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,559 @@ +# This usage of CMake requires at least version 2.4 (checks are made to determine what to use when certain versions lack functions) +cmake_minimum_required(VERSION 2.4 FATAL_ERROR) +if(COMMAND cmake_policy) + cmake_policy(SET CMP0003 NEW) + if(POLICY CMP0026) + cmake_policy(SET CMP0026 OLD) + endif(POLICY CMP0026) + if(POLICY CMP0007) + cmake_policy(SET CMP0007 OLD) + endif(POLICY CMP0007) +endif(COMMAND cmake_policy) + +# Set the project as C++ primarily, but have C enabled for the checks required later +project(Anope CXX) +enable_language(C) + +# Detect the version of CMake for the later conditional checks +execute_process(COMMAND ${CMAKE_COMMAND} --version OUTPUT_VARIABLE VERSION OUTPUT_STRIP_TRAILING_WHITESPACE) +string(REGEX REPLACE "cmake version 2\\.(.*)" "\\1" ONLY_VERSION "${VERSION}") +string(REGEX MATCH "-patch .*$" HAS_PATCH "${ONLY_VERSION}") +if(HAS_PATCH) + string(REGEX REPLACE "(.*)-patch .*" "\\1" MINOR_VERSION "${ONLY_VERSION}") + string(REGEX REPLACE ".*-patch (.*)" "\\1" PATCH_VERSION "${ONLY_VERSION}") +else(HAS_PATCH) + string(REGEX MATCH "\\." HAS_DOT "${ONLY_VERSION}") + if(HAS_DOT) + string(REGEX REPLACE "(.*)\\..*" "\\1" MINOR_VERSION "${ONLY_VERSION}") + string(REGEX REPLACE ".*\\.(.*)" "\\1" PATCH_VERSION "${ONLY_VERSION}") + else(HAS_DOT) + string(REGEX REPLACE "(.*)-beta" "\\1" MINOR_VERSION "${ONLY_VERSION}") + if(MINOR_VERSION STREQUAL "4-1\n") + set(PATCH_VERSION 1) + else(MINOR_VERSION STREQUAL "4-1\n") + set(PATCH_VERSION 0) + endif(MINOR_VERSION STREQUAL "4-1\n") + set(MINOR_VERSION 4) + endif(HAS_DOT) +endif(HAS_PATCH) + +# Detect is we are using CMake 2.6 or better, these versions include functions that require less work than CMake 2.4 does +if(MINOR_VERSION GREATER 5) + set(CMAKE26_OR_BETTER TRUE) + set(CMAKE248_OR_BETTER TRUE) + set(CMAKE244_OR_BETTER TRUE) + set(CMAKE242_OR_BETTER TRUE) +else(MINOR_VERSION GREATER 5) + set(CMAKE26_OR_BETTER FALSE) + # Also detect if we are using CMake 2.4.8 or better, the FIND sub-command of list() is nonexistent in earlier versions + if(PATCH_VERSION GREATER 7) + set(CMAKE248_OR_BETTER TRUE) + set(CMAKE244_OR_BETTER TRUE) + set(CMAKE242_OR_BETTER TRUE) + else(PATCH_VERSION GREATER 7) + set(CMAKE248_OR_BETTER FALSE) + # Also detect if we are using CMake 2.4.4 or better, the CheckCXXCompilerFlag module and SORT sub-command of list() are nonexistent in earlier versions + if(PATCH_VERSION GREATER 3) + set(CMAKE244_OR_BETTER TRUE) + set(CMAKE242_OR_BETTER TRUE) + else(PATCH_VERSION GREATER 3) + set(CMAKE244_OR_BETTER FALSE) + # ALSO detect if we are using CMake 2.4.2 or better, the APPEND sub-command of list() is nonexistent in earlier versions + if(PATCH_VERSION GREATER 1) + set(CMAKE242_OR_BETTER TRUE) + else(PATCH_VERSION GREATER 1) + set(CMAKE242_OR_BETTER FALSE) + endif(PATCH_VERSION GREATER 1) + endif(PATCH_VERSION GREATER 3) + endif(PATCH_VERSION GREATER 7) +endif(MINOR_VERSION GREATER 5) + +# Override the module include path to include our directory, for our Anope.cmake, as well as we are using our own version of the NSIS template +set(CMAKE_MODULE_PATH ${Anope_SOURCE_DIR}/cmake) + +include(Anope) + +# Force the locale to C for later uses of things like gcc so the messages come up in English, not the user's default language +set(ENV{LC_ALL} C) + +# Start with empty defaults for library and include directories, to be used by GNU compilers only +set(DEFAULT_LIBRARY_DIRS) +set(DEFAULT_INCLUDE_DIRS) + +# Check that we aren't running on an ancient broken GCC +if(CMAKE_COMPILER_IS_GNUCXX) + execute_process(COMMAND ${CMAKE_CXX_COMPILER} -dumpversion OUTPUT_VARIABLE GCC_FULL_VERSION OUTPUT_STRIP_TRAILING_WHITESPACE) + string(REGEX REPLACE "^(\\d+\\.\\d+)" "\\1" GCC_VERSION ${GCC_FULL_VERSION}) + if(GCC_VERSION LESS 4.2) + message(FATAL_ERROR "Your compiler is too old to build Anope. Upgrade to GCC 4.2 or newer!") + endif(GCC_VERSION LESS 4.2) + if(GCC_VERSION GREATER 6.0 OR GCC_VERSION EQUAL 6.0) + set(CXXFLAGS "${CXXFLAGS} -fno-delete-null-pointer-checks") + endif(GCC_VERSION GREATER 6.0 OR GCC_VERSION EQUAL 6.0) +endif(CMAKE_COMPILER_IS_GNUCXX) + +# If we are using a GNU compiler (have to use CXX because it seems to fail on C), we will be able to determine it's default paths for libraries and includes +if(CMAKE_COMPILER_IS_GNUCXX OR "${CMAKE_CXX_COMPILER_ID}" MATCHES "Clang$") + # First look for the compiler's default library directories + execute_process(COMMAND ${CMAKE_C_COMPILER} -print-search-dirs OUTPUT_VARIABLE LINES OUTPUT_STRIP_TRAILING_WHITESPACE) + # Find only the part after "libraries: " + string(REGEX REPLACE ".*\nlibraries: (.*)$" "\\1" LINE "${LINES}") + # Replace the colons in the list with semicolons (only when not on MinGW, which uses semicolons already), and if on MinGW, just copy the line + if(NOT MINGW) + string(REGEX REPLACE ":" ";" LIBRARIES ${LINE}) + else(NOT MINGW) + set(LIBRARIES "${LINE}") + endif(NOT MINGW) + # Iterate through the libraries + foreach(LIBRARY ${LIBRARIES}) + # Check if the first character is an equal sign, and skip that library directory as it is (I believe) the primary default and shows up later in the list anyways + string(SUBSTRING ${LIBRARY} 0 1 FIRST_CHAR) + if(NOT FIRST_CHAR STREQUAL "=") + # If the directory had no = in front of it, make sure it's absolute and add it to the list of default library directories + get_filename_component(LIBRARY ${LIBRARY} ABSOLUTE) + append_to_list(DEFAULT_LIBRARY_DIRS ${LIBRARY}) + endif(NOT FIRST_CHAR STREQUAL "=") + endforeach(LIBRARY) + # Remove duplicate entries from the list + if(DEFAULT_LIBRARY_DIRS) + remove_list_duplicates(DEFAULT_LIBRARY_DIRS) + endif(DEFAULT_LIBRARY_DIRS) + # Create a temporary file to test for the default include directories + FILE(WRITE empty.cpp "") + # Next, we look for the compiler's default include directories + # Run the command to find the default include directories + execute_process(COMMAND ${CMAKE_C_COMPILER} -v -x c++ -E ${CMAKE_CURRENT_SOURCE_DIR}/empty.cpp ERROR_VARIABLE LINES OUTPUT_QUIET ERROR_STRIP_TRAILING_WHITESPACE) + # Remove the empty file, it is no longer needed + FILE(REMOVE empty.cpp) + # Convert the new lines to semicolons + string(REGEX REPLACE "\n" ";" LINES ${LINES}) + # Temporary variable saying if we are in the search list or not + set(IN_SEARCH_LIST FALSE) + # Iterate through the lines + foreach(LINE ${LINES}) + # If the line has the following on it, the next lines will contain directory names + if(LINE STREQUAL "#include <...> search starts here:") + set(IN_SEARCH TRUE) + else(LINE STREQUAL "#include <...> search starts here:") + # If the line has the following on it, we hit the end of the list + if(LINE STREQUAL "End of search list.") + set(IN_SEARCH FALSE) + else(LINE STREQUAL "End of search list.") + # If we are within the block between the above two lines... + if(IN_SEARCH) + # Get everything but the first character of the line + string(LENGTH ${LINE} LINE_LENGTH) + math(EXPR LINE_LENGTH "${LINE_LENGTH} - 1") + string(SUBSTRING ${LINE} 1 ${LINE_LENGTH} INCLUDE) + # For systems like Mac OS X, look for include paths that say " (framework directory)" at the end of them and strip that off + string(REGEX REPLACE " \\(framework directory\\)$" "" INCLUDE ${INCLUDE}) + # Convert the path to an absolute one, just in case it wasn't + get_filename_component(INCLUDE ${INCLUDE} ABSOLUTE) + # Add that directory to the list of default include directories + append_to_list(DEFAULT_INCLUDE_DIRS ${INCLUDE}) + endif(IN_SEARCH) + endif(LINE STREQUAL "End of search list.") + endif(LINE STREQUAL "#include <...> search starts here:") + endforeach(LINE) + # Remove duplicate entries from the list + if(DEFAULT_INCLUDE_DIRS) + remove_list_duplicates(DEFAULT_INCLUDE_DIRS) + endif(DEFAULT_INCLUDE_DIRS) +endif(CMAKE_COMPILER_IS_GNUCXX OR "${CMAKE_CXX_COMPILER_ID}" MATCHES "Clang$") + +# If we are using Visual Studio, locate the path of the Windows Server 2008 SDK or Windows Server 2003 Platform SDK, depending on which is installed +if(MSVC) + # If the path comes up as "/registry" from any of these, the path wasn't found, otherwise, we'll set WSDK_PATH to the corresponding path + # Look for the 2008 SDK under HKLM first + get_filename_component(WSDK2008_PATH "[HKEY_LOCAL_MACHINE\\SOFTWARE\\Microsoft\\Microsoft SDKs\\Windows;CurrentInstallFolder]" ABSOLUTE CACHE) + if(WSDK2008_PATH STREQUAL "/registry") + # If not found, look for the 2003 SDK under HKLM + get_filename_component(WSDK2003_PATH "[HKEY_LOCAL_MACHINE\\SOFTWARE\\Microsoft\\MicrosoftSDK\\InstalledSDKs\\D2FF9F89-8AA2-4373-8A31-C838BF4DBBE1;Install Dir]" ABSOLUTE CACHE) + if(WSDK2003_PATH STREQUAL "/registry") + # If not found, look for the 2008 SDK under HKCU + get_filename_component(WSDK2008_PATH "[HKEY_CURRENT_USER\\SOFTWARE\\Microsoft\\Microsoft SDKs\\Windows;CurrentInstallFolder]" ABSOLUTE CACHE) + if(WSDK2008_PATH STREQUAL "/registry") + # If not found, look for the 2003 SDK under HKCU + get_filename_component(WSDK2003_PATH "[HKEY_CURRENT_USER\\SOFTWARE\\Microsoft\\MicrosoftSDK\\InstalledSDKs\\D2FF9F89-8AA2-4373-8A31-C838BF4DBBE1;Install Dir]" ABSOLUTE CACHE) + if(WSDK2003_PATH STREQUAL "/registry") + # The SDK was never found, set the path to nothing + set(WSDK_PATH "") + else(WSDK2003_PATH STREQUAL "/registry") + set(WSDK_PATH "${WSDK2003_PATH}") + endif(WSDK2003_PATH STREQUAL "/registry") + else(WSDK2008_PATH STREQUAL "/registry") + set(WSDK_PATH "${WSDK2008_PATH}") + endif(WSDK2008_PATH STREQUAL "/registry") + else(WSDK2003_PATH STREQUAL "/registry") + set(WSDK_PATH "${WSDK2003_PATH}") + endif(WSDK2003_PATH STREQUAL "/registry") + else(WSDK2008_PATH STREQUAL "/registry") + set(WSDK_PATH "${WSDK2008_PATH}") + endif(WSDK2008_PATH STREQUAL "/registry") +endif(MSVC) + +# If the user specifies -DCMAKE_BUILD_TYPE on the command line, take their definition +# and dump it in the cache along with proper documentation, otherwise set CMAKE_BUILD_TYPE +# to Debug +# Only do this if not using Visual Studio +if(NOT MSVC) + if(CMAKE_BUILD_TYPE) + set(CMAKE_BUILD_TYPE ${CMAKE_BUILD_TYPE} CACHE STRING "Choose the type of build, options are: None(CMAKE_CXX_FLAGS or CMAKE_C_FLAGS used) Debug Release RelWithDebInfo MinSizeRel.") + else(CMAKE_BUILD_TYPE) + set(CMAKE_BUILD_TYPE DEBUG CACHE STRING "Choose the type of build, options are: None(CMAKE_CXX_FLAGS or CMAKE_C_FLAGS used) Debug Release RelWithDebInfo MinSizeRel.") + endif(CMAKE_BUILD_TYPE) +endif(NOT MSVC) + +# If running under MinGW, we have to force the resource compiler settings (hopefully this will be fixed in a later version of CMake) +if(MINGW) + set(CMAKE_RC_COMPILER_INIT windres) + enable_language(RC) + set(CMAKE_RC_COMPILE_OBJECT " -o ") +endif(MINGW) + +# Include the checking functions used later in this CMakeLists.txt +include(CheckFunctionExists) +include(CheckIncludeFile) +include(CheckTypeSize) +include(CheckLibraryExists) +if(CMAKE244_OR_BETTER) + include(CheckCXXCompilerFlag) +else(CMAKE244_OR_BETTER) + include(TestCXXAcceptsFlag) +endif(CMAKE244_OR_BETTER) + +# If extra include directories were specified, tell cmake about them. +if(EXTRA_INCLUDE) + include_directories(${EXTRA_INCLUDE}) +endif(EXTRA_INCLUDE) + +# If extra library directories were specified, tell cmake about them. +if(EXTRA_LIBS) + link_directories(${EXTRA_LIBS}) +endif(EXTRA_LIBS) + +# Find gettext +find_package(Gettext) + +option(USE_PCH "Use precompiled headers" OFF) + +# Use the following directories as includes +# Note that it is important the binary include directory comes before the +# source include directory so the precompiled headers work correctly. +include_directories(${Anope_BINARY_DIR}/include ${Anope_SOURCE_DIR}/include ${Anope_BINARY_DIR}/language ${Anope_SOURCE_DIR}/modules/pseudoclients) + +# Pass on REPRODUCIBLE_BUILD +if(REPRODUCIBLE_BUILD) + add_definitions(-DREPRODUCIBLE_BUILD) +endif(REPRODUCIBLE_BUILD) + +# If using Windows, always add the _WIN32 define +if(WIN32) + add_definitions(-D_WIN32) + # And include the windows specific folder for our anope_windows.h + include_directories(${Anope_SOURCE_DIR}/src/win32) +endif(WIN32) + +# If using Visual Studio, set the C++ flags accordingly +if(MSVC) + # Remove the default exception handling flags, also remove default warning level flag + string(REPLACE "/EHsc " "" CMAKE_CXX_FLAGS ${CMAKE_CXX_FLAGS}) + string(REPLACE "/GX " "" CMAKE_CXX_FLAGS ${CMAKE_CXX_FLAGS}) + string(REPLACE "/W3 " "" CMAKE_CXX_FLAGS ${CMAKE_CXX_FLAGS}) + # Set the compile flags to have warnings on the max setting (but disable a few annoying ones), exception handling turned on, the proper defines + set(CXXFLAGS "${CXXFLAGS} /W4 /wd4100 /wd4127 /wd4250 /wd4251 /wd4355 /wd4706 /wd4800 /wd4996 /EHs") + add_definitions(-DMSVCPP -D_CRT_SECURE_NO_WARNINGS) +# Otherwise, we're not using Visual Studio +else(MSVC) + # Set the compile flags to have all warnings on (including shadowed variables) + set(CXXFLAGS "${CXXFLAGS} -Wall -Wshadow") + # If on a *nix system, also set the compile flags to remove GNU extensions (favor ISO C++) as well as reject non-ISO C++ code, also remove all leading underscores in exported symbols (only on GNU compiler) + if(UNIX) + set(CXXFLAGS "${CXXFLAGS} -ansi -pedantic ${CMAKE_CXX_FLAGS}") + if (CMAKE_CXX_COMPILER_ID STREQUAL "GNU") + set(CXXFLAGS "${CXXFLAGS} -Wno-long-long -fno-leading-underscore") + endif(CMAKE_CXX_COMPILER_ID STREQUAL "GNU") + # If we aren't on a *nix system, we are using MinGW + else(UNIX) + # Also, if we are building under MinGW, add another define for MinGW + if(MINGW) + add_definitions(-DMINGW) + endif(MINGW) + endif(UNIX) +endif(MSVC) + +# If CMake has found that the given system requires a special library for dl* calls, include it with the linker flags +if(CMAKE_DL_LIBS) + append_to_list(LINK_LIBS ${CMAKE_DL_LIBS}) +endif(CMAKE_DL_LIBS) + +# Under MinGW, the -shared flag isn't properly set in the module-specific linker flags, add it from the C flags for shared libraries +if(MINGW) + set(CMAKE_MODULE_LINKER_FLAGS "${CMAKE_MODULE_LINKER_FLAGS} ${CMAKE_SHARED_LIBRARY_CREATE_C_FLAGS}") +endif(MINGW) + +if(NOT PROGRAM_NAME) + # Under Windows, we set the executable name for Anope to be anope + if(WIN32) + set(PROGRAM_NAME anope) + # Under *nix, we set the executable name for Anope to be services + else(WIN32) + set(PROGRAM_NAME services) + endif(WIN32) +endif(NOT PROGRAM_NAME) + +# If we are not using Visual Studio, we'll run the following checks +if(NOT MSVC) + # Check if the C++ compiler can accept the -pipe flag, and add it to the compile flags if it works + if(CMAKE244_OR_BETTER) + # If using CMake 2.4.4 or better, we can use check_cxx_compiler_flag + check_cxx_compiler_flag(-pipe HAVE_PIPE_FLAG) + else(CMAKE244_OR_BETTER) + # If using CMake 2.4.3 or older, we will use check_cxx_accepts_flags instead + check_cxx_accepts_flag(-pipe HAVE_PIPE_FLAG) + endif(CMAKE244_OR_BETTER) + # If the flag was accepted, add it to the list of flags + if(HAVE_PIPE_FLAG) + set(CXXFLAGS "${CXXFLAGS} -pipe") + endif(HAVE_PIPE_FLAG) + + # The following are additional library checks, they are not required for Windows + if(NOT WIN32) + # Check if socket is within the socket library (if the library exists), and add it to the linker flags if needed + check_library_exists(socket socket "" HAVE_SOCKET_LIB) + if(HAVE_SOCKET_LIB) + append_to_list(LINK_LIBS socket) + endif(HAVE_SOCKET_LIB) + # Check if inet_addr is within the nsl library (if the library exists), and add it to the linker flags if needed + check_library_exists(nsl inet_addr "" HAVE_NSL_LIB) + if(HAVE_NSL_LIB) + append_to_list(LINK_LIBS nsl) + endif(HAVE_NSL_LIB) + # Check if pthread_create is within the pthread library (if the library exists), and add it to the linker flags if needed + check_library_exists(pthread pthread_create "" HAVE_PTHREAD) + if(HAVE_PTHREAD) + if(NOT APPLE) + set(LDFLAGS "${LDFLAGS} -pthread") + endif(NOT APPLE) + else(HAVE_PTHREAD) + message(FATAL_ERROR "The pthread library is required to build Anope") + endif(HAVE_PTHREAD) + endif(NOT WIN32) +endif(NOT MSVC) + +# If DEFUMASK wasn't passed to CMake, set a default depending on if RUNGROUP was passed in or not +if(NOT DEFUMASK) + if(RUNGROUP) + set(DEFUMASK "007") + else(RUNGROUP) + set(DEFUMASK "077") + endif(RUNGROUP) +endif(NOT DEFUMASK) + +# Set the DEBUG_BUILD for sysconf.h +if(CMAKE_BUILD_TYPE STREQUAL "DEBUG" OR CMAKE_BUILD_TYPE STREQUAL "RELWITHDEBINFO") + set(DEBUG_BUILD TRUE) +endif(CMAKE_BUILD_TYPE STREQUAL "DEBUG" OR CMAKE_BUILD_TYPE STREQUAL "RELWITHDEBINFO") + +# Check for the existence of the following include files +check_include_file(cstdint HAVE_CSTDINT) +check_include_file(stdint.h HAVE_STDINT_H) +check_include_file(strings.h HAVE_STRINGS_H) + +# Check for the existence of the following functions +check_function_exists(strcasecmp HAVE_STRCASECMP) +check_function_exists(stricmp HAVE_STRICMP) +check_function_exists(umask HAVE_UMASK) +check_function_exists(epoll_wait HAVE_EPOLL) +check_function_exists(poll HAVE_POLL) +check_function_exists(kqueue HAVE_KQUEUE) + +# Strip the leading and trailing spaces from the compile flags +if(CXXFLAGS) + strip_string(${CXXFLAGS} CXXFLAGS) +endif(CXXFLAGS) +# Strip the leading and trailing spaces from the linker flags +if(LDFLAGS) + strip_string(${LDFLAGS} LDFLAGS) +endif(LDFLAGS) + +# Search for the following programs +find_program(GREP grep) +find_program(SH sh) +find_program(CHGRP chgrp) +find_program(CHMOD chmod) + +# If a INSTDIR was passed in to CMake, use it as the install prefix, otherwise set the default install prefix to the services directory under the user's home directory +if(INSTDIR) + set(CMAKE_INSTALL_PREFIX "${INSTDIR}") +elseif(NOT CMAKE_INSTALL_PREFIX) + set(CMAKE_INSTALL_PREFIX "$ENV{HOME}/services") +endif(INSTDIR) + +# Set default paths for various directories if not already defined +if(NOT BIN_DIR) + set(BIN_DIR "bin") +endif(NOT BIN_DIR) +if(NOT DB_DIR) + set(DB_DIR "data") +endif(NOT DB_DIR) +if(NOT DOC_DIR) + set(DOC_DIR "doc") +endif(NOT DOC_DIR) +if(NOT CONF_DIR) + set(CONF_DIR "conf") +endif(NOT CONF_DIR) +if(NOT LIB_DIR) + set(LIB_DIR "lib") +endif(NOT LIB_DIR) +if(NOT LOCALE_DIR) + set(LOCALE_DIR "locale") +endif(NOT LOCALE_DIR) +if(NOT LOGS_DIR) + set(LOGS_DIR "logs") +endif(NOT LOGS_DIR) + +# Version number processing +# Find all lines in src/version.sh that start with VERSION_ +read_from_file(${Anope_SOURCE_DIR}/src/version.sh "^VERSION_" VERSIONS) +# Iterate through the strings found +foreach(VERSION_STR ${VERSIONS}) + string(REGEX REPLACE "^VERSION_([A-Z]+)=\"?([^\"]*)\"?$" "\\1;\\2" VERSION_OUT ${VERSION_STR}) + # Depends on CMP0007 OLD + list(LENGTH VERSION_OUT VERSION_LEN) + list(GET VERSION_OUT 0 VERSION_TYPE) + if(${VERSION_LEN} GREATER 1) + list(GET VERSION_OUT 1 VERSION_DATA) + set(VERSION_${VERSION_TYPE} ${VERSION_DATA}) + endif(${VERSION_LEN} GREATER 1) +endforeach(VERSION_STR ${VERSIONS}) + +# Default build version to 0 +set(VERSION_BUILD 0) + +# Only change the build number if version.h exists +if(EXISTS "${Anope_SOURCE_DIR}/include/version.h") + # Attempt to read the build number from include/version.h + read_from_file(${Anope_SOURCE_DIR}/include/version.h "^#define VERSION_BUILD" VERSIONS) + foreach(VERSION_STR ${VERSIONS}) + # Get the length of the string + string(LENGTH ${VERSION_STR} VERSION_LEN) + # Subtract 22 from the string's length + math(EXPR VERSION_NUM_LEN "${VERSION_LEN} - 22") + # Extract the value from the string + string(SUBSTRING ${VERSION_STR} 22 ${VERSION_NUM_LEN} VERSION) + # Set VERSION_BUILD correctly + set(VERSION_BUILD ${VERSION}) + endforeach(VERSION_STR ${VERSIONS}) +endif(EXISTS "${Anope_SOURCE_DIR}/include/version.h") + +# Set the version variables based on what was found above +set(VERSION_COMMA "${VERSION_MAJOR},${VERSION_MINOR},${VERSION_PATCH},${VERSION_BUILD}") +set(VERSION_DOTTED_NOBUILD "${VERSION_MAJOR}.${VERSION_MINOR}.${VERSION_PATCH}") +set(VERSION_DOTTED "${VERSION_DOTTED_NOBUILD}.${VERSION_BUILD}") +set(VERSION_FULL "${VERSION_DOTTED}${VERSION_EXTRA}") +set(VERSION_FULL_NOBUILD "${VERSION_DOTTED_NOBUILD}${VERSION_EXTRA}") + +# Only do the following for Windows +if(WIN32) + # Generate the win32.rc file using the above variables + configure_file(${Anope_SOURCE_DIR}/src/win32/win32.rc.cmake ${Anope_BINARY_DIR}/src/win32/win32.rc) +endif(WIN32) + +# Add the initial files to ignore which will be ignored regardless of if you are building in-source or out-of-source +add_to_cpack_ignored_files(".git\;config.cache\;CMakeFiles\;sysconf.h$\;build" TRUE) +# Add the files we don't want the periods converted for +add_to_cpack_ignored_files(".\\\\\\\\.so$;.\\\\\\\\.o$;.\\\\\\\\.s$;${Anope_SOURCE_DIR}/Makefile$") +# If the two directories are the same, we are building in-source, thus we need to ignore more files from the build +if(${Anope_SOURCE_DIR} STREQUAL ${Anope_BINARY_DIR}) + # Add the files that need their periods converted + add_to_cpack_ignored_files("Makefile\;cmake_install.cmake\;sysconf.h$\;CMakeCache.txt\;install_manifest.txt" TRUE) + # Add the files we don't want the periods converted for + add_to_cpack_ignored_files(".\\\\\\\\.so$;CPack.;anope-${VERSION_FULL_NOBUILD}-source\\\\\\\\..") + # If using Visual Studio, add these files as well + if(MSVC) + add_to_cpack_ignored_files(".vcproj$\;.sln$\;.ncb$\;.suo$\;.dir$\;.ilk$\;.exp$\;.pdb$\;.lib$\;/debug$;/release$;/relwithdebinfo$;/minsizerel$" TRUE) + endif(MSVC) +endif(${Anope_SOURCE_DIR} STREQUAL ${Anope_BINARY_DIR}) + +# Go into the following directories and run their CMakeLists.txt as well +add_subdirectory(data) +add_subdirectory(docs) +add_subdirectory(language) +add_subdirectory(src) +add_subdirectory(modules) +add_subdirectory(include) + +# Get the filename of the Anope binary, to use later +get_target_property(SERVICES_BINARY ${PROGRAM_NAME} LOCATION) +get_filename_component(SERVICES_BINARY ${SERVICES_BINARY} NAME) + +# At install time, create the following additional directories +install(CODE "file(MAKE_DIRECTORY \"\$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${DB_DIR}/backups\")") +install(CODE "file(MAKE_DIRECTORY \"\$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${LOGS_DIR}\")") +if(WIN32) + install(CODE "file(MAKE_DIRECTORY \"\$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${DB_DIR}/runtime\")") +endif(WIN32) +# On non-Windows platforms, if RUNGROUP is set, change the permissions of the below directories, as well as the group of the data directory +if(NOT WIN32 AND RUNGROUP) + install(CODE "execute_process(COMMAND ${CHMOD} 2775 \"\$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/\${DB_DIR}/backups\")") + install(CODE "execute_process(COMMAND ${CHMOD} 2775 \"\$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/\${LOGS_DIR}\")") + install(CODE "execute_process(COMMAND ${CHGRP} -R ${RUNGROUP} \"\$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}\")") +endif(NOT WIN32 AND RUNGROUP) +# On Windows platforms, install extra files +if(WIN32) + install(FILES ${Anope_SOURCE_DIR}/src/win32/anope.bat + DESTINATION ${BIN_DIR} + ) + + # Package any DLLs in src/win/ + file(GLOB EXTRA_DLLS RELATIVE ${CMAKE_CURRENT_SOURCE_DIR} "${Anope_SOURCE_DIR}/src/win32/*.dll") + install(FILES ${EXTRA_DLLS} DESTINATION ${BIN_DIR}) +endif(WIN32) + +install(CODE "file(REMOVE_RECURSE \"$ENV{DESTDIR}${CMAKE_INSTALL_PREFIX}/${LIB_DIR}/modules\")") + +# Only process the CPack section if we have CPack +if(EXISTS "${CMAKE_ROOT}/Modules/CPack.cmake") + # Various options for CPack + set(CPACK_PACKAGE_NAME "Anope IRC Services") + set(CPACK_PACKAGE_VENDOR "Anope Team") + set(CPACK_PACKAGE_VERSION_MAJOR ${VERSION_MAJOR}) + set(CPACK_PACKAGE_VERSION_MINOR ${VERSION_MINOR}) + set(CPACK_PACKAGE_VERSION_PATCH "${VERSION_PATCH}${VERSION_EXTRA}") + set(CPACK_PACKAGE_FILE_NAME "anope-${VERSION_FULL_NOBUILD}") + set(CPACK_RESOURCE_FILE_LICENSE "${Anope_SOURCE_DIR}/docs/COPYING") + # The following doesn't actually do anything. :( + #set(CPACK_RESOURCE_FILE_README "${Anope_SOURCE_DIR}/docs/README") + # The following is primarily for NSIS + if(WIN32) + # By default, do not warn when built on machines using only VS Express: + IF(NOT DEFINED CMAKE_INSTALL_SYSTEM_RUNTIME_LIBS_NO_WARNINGS) + SET(CMAKE_INSTALL_SYSTEM_RUNTIME_LIBS_NO_WARNINGS ON) + ENDIF(NOT DEFINED CMAKE_INSTALL_SYSTEM_RUNTIME_LIBS_NO_WARNINGS) + # Also for Windows, include installing the MSVCRT library + include(InstallRequiredSystemLibraries) + set(CPACK_GENERATOR "NSIS") + set(CPACK_PACKAGE_INSTALL_DIRECTORY "Anope") + set(CPACK_PACKAGE_EXECUTABLES "") + set(CPACK_NSIS_MENU_LINKS + "bin\\\\${SERVICES_BINARY}" "Anope IRC Services" + "bin\\\\anope.bat\\\" \\\"-debug -nofork" "Anope IRC Services (Debug and Window Logging)" + "bin\\\\anope.bat\\\" \\\"-nofork" "Anope IRC Services (Window Logging)" + "bin\\\\anope.bat\\\" \\\"-nothird" "Anope IRC Services (No Third Party Modules)" + "https://www.anope.org/" "Anope Web Site" + ) + # The following doesn't work, but a bug report has been filed about it + #set(CPACK_CREATE_DESKTOP_LINK_${SERVICES_BINARY} TRUE) + set(CPACK_NSIS_MUI_ICON "${Anope_SOURCE_DIR}/src\\\\win32\\\\anope-icon.ico") + set(CPACK_NSIS_MUI_UNIICON "${Anope_SOURCE_DIR}/src\\\\win32\\\\anope-icon.ico") + set(CPACK_NSIS_INSTALLED_ICON_NAME "${SERVICES_BINARY}") + set(CPACK_NSIS_URL_INFO_ABOUT "https://www.anope.org/") + set(CPACK_NSIS_COMPRESSOR "/SOLID lzma") + endif(WIN32) + set(CPACK_SOURCE_PACKAGE_FILE_NAME "anope-${VERSION_FULL_NOBUILD}-source") + set(CPACK_SOURCE_GENERATOR "TGZ") + set(CPACK_SOURCE_IGNORE_FILES "$ENV{CPACK_IGNORED_FILES}") + set(CPACK_MONOLITHIC_INSTALL TRUE) + include(CPack) +endif(EXISTS "${CMAKE_ROOT}/Modules/CPack.cmake") diff --git a/Config b/Config new file mode 100755 index 0000000..86efef6 --- /dev/null +++ b/Config @@ -0,0 +1,417 @@ +#!/bin/sh +# +# Configuration script for Services. +# +# Anope (C) 2003-2022 Anope Team +# Contact us at team@anope.org +# +# This program is free but copyrighted software; see the file COPYING for +# details. +# +# Based on the original code of Epona by PegSoft. +# Based on the original code of Services by Andy Church. +# +########################################################################### + +echo2 () { + $ECHO2 "$*$ECHO2SUF" # these are defined later +} + +exists () { # because some shells don't have test -e + if [ -f $1 -o -d $1 -o -p $1 -o -c $1 -o -b $1 ] ; then + return 0 + else + return 1 + fi +} + +Load_Cache () { + if [ -f $SOURCE_DIR/config.cache -a -r $SOURCE_DIR/config.cache -a ! "$IGNORE_CACHE" ] ; then + echo "Using defaults from config.cache. To ignore, $SOURCE_DIR/Config -nocache" + echo "" + . $SOURCE_DIR/config.cache + CAN_QUICK="yes" + else + CAN_QUICK="no" + fi +} + +Run_Build_System () { + WITH_INST="" + WITH_RUN="" + WITH_PERM="" + EXTRA_INCLUDE="" + EXTRA_LIBS="" + GEN_TYPE="" + + if [ "$INSTDIR" != "" ] ; then + WITH_INST="-DINSTDIR:STRING=$INSTDIR" + fi + + if [ "$RUNGROUP" != "" ] ; then + WITH_RUN="-DRUNGROUP:STRING=$RUNGROUP" + fi + + if [ "$UMASK" != "" ] ; then + WITH_PERM="-DDEFUMASK:STRING=$UMASK" + fi + + if [ "$DEBUG" = "yes" ] ; then + BUILD_TYPE="-DCMAKE_BUILD_TYPE:STRING=DEBUG" + else + BUILD_TYPE="-DCMAKE_BUILD_TYPE:STRING=RELEASE" + fi + + if [ "$USE_PCH" = "yes" ] ; then + PCH="-DUSE_PCH:BOOLEAN=ON" + else + PCH="-DUSE_PCH:BOOLEAN=OFF" + fi + + if [ "$EXTRA_INCLUDE_DIRS" != "" ] ; then + EXTRA_INCLUDE="-DEXTRA_INCLUDE:STRING=$EXTRA_INCLUDE_DIRS" + fi + + if [ "$EXTRA_LIB_DIRS" != "" ] ; then + EXTRA_LIBS="-DEXTRA_LIBS:STRING=$EXTRA_LIB_DIRS" + fi + + case `uname -s` in + MINGW*) + GEN_TYPE="-G\"MSYS Makefiles\"" + ;; + esac + + if [ "$SOURCE_DIR" = "." ] ; then + pwdsave=`pwd` + test -d build || mkdir build + cd "build" + REAL_SOURCE_DIR=".." + else + REAL_SOURCE_DIR="$SOURCE_DIR" + fi + + echo "cmake $GEN_TYPE $WITH_INST $WITH_RUN $WITH_PERM $BUILD_TYPE $PCH $EXTRA_INCLUDE $EXTRA_LIBS $EXTRA_CONFIG_ARGS $REAL_SOURCE_DIR" + + cmake $GEN_TYPE $WITH_INST $WITH_RUN $WITH_PERM $BUILD_TYPE $PCH $EXTRA_INCLUDE $EXTRA_LIBS $EXTRA_CONFIG_ARGS $REAL_SOURCE_DIR + if [ $? -ne 0 ]; then + echo "You should fix these issues and then run ./Config -quick to rerun CMake." + exit 1 + fi + + echo "" + if [ "$SOURCE_DIR" = "." ] ; then + echo "Now cd build, then run make to build Anope." + cd "$pwdsave" + else + echo "Now run make to build Anope." + fi +} + +ECHO2SUF='' +if [ "`echo -n a ; echo -n b`" = "ab" ] ; then + ECHO2='echo -n' +elif [ "`echo 'a\c' ; echo 'b\c'`" = "ab" ] ; then + ECHO2='echo' ; ECHO2SUF='\c' +elif [ "`printf 'a' 2>&1 ; printf 'b' 2>&1`" = "ab" ] ; then + ECHO2='printf "%s"' +else + # oh well... + ECHO2='echo' +fi +export ECHO2 ECHO2SUF + +########################################################################### +# Init values +########################################################################### + +INSTDIR=$HOME/services +RUNGROUP= +UMASK= +DEBUG="no" +USE_PCH="no" +EXTRA_INCLUDE_DIRS= +EXTRA_LIB_DIRS= +EXTRA_CONFIG_ARGS= +CAN_QUICK="no" +SOURCE_DIR=`dirname $0` + +########################################################################### +# Check out the options +########################################################################### + +while [ $# -ge 1 ] ; do + if [ $1 = "--help" ] ; then + echo "Config utility for Anope" + echo "------------------------" + echo "Syntax: ./Config [options]" + echo "-nocache Ignore settings saved in config.cache" + echo "-nointro Skip intro (disclaimer, etc)" + echo "-quick Skip questions, go straight to cmake" + exit 0 + elif [ $1 = "-devel" ] ; then + DEBUG="yes" + INSTDIR="$PWD/run" + elif [ $1 = "-nocache" ] ; then + IGNORE_CACHE="1" + elif [ $1 = "-nointro" ] ; then + NO_INTRO="1" + elif [ $1 = "-quick" -o $1 = "-q" ] ; then + Load_Cache + if [ "$CAN_QUICK" = "yes" ] ; then + Run_Build_System + else + echo "" + echo "Can't find cache file (config.cache), aborting..." + fi + exit 0 + fi + shift 1 +done + +########################################################################### +# Check for CMake and (optionally) install it +########################################################################### + +cmake --version 2>&1 > /dev/null +if [ $? -ne 0 ] ; then + clear + echo "Anope requires CMake 2.4 or newer, which can be downloaded at https://cmake.org/ or through your system's package manager." + echo "If you have installed CMake already, ensure it is in your PATH environment variable." + exit 0 +fi + +########################################################################### + +if [ ! "$NO_INTRO" ] ; then + case `uname -s` in + MINGW*) + PAGER=less + ;; + *) + PAGER=more + clear + ;; + esac + . $SOURCE_DIR/src/version.sh + cat $SOURCE_DIR/.BANNER | sed "s/CURVER/$VERSION_MAJOR.$VERSION_MINOR.$VERSION_PATCH$VERSION_EXTRA/" | sed "s@SOURCE_DIR@$SOURCE_DIR@" | $PAGER + echo "" +else + echo "" +fi + +echo "Beginning Services configuration." +echo "" + +########################################################################### +# Load the cache +########################################################################### + +if [ ! "$IGNORE_CACHE" ] ; then + Load_Cache +fi + +# Ask the user anything we need to know ahead of time. + +export ok INPUT + +#### + +ok=0 +echo "In what directory should Anope be installed?" +while [ $ok -eq 0 ] ; do + echo2 "[$INSTDIR] " + if read INPUT ; then : ; else echo "" ; exit 1 ; fi + if [ ! "$INPUT" ] ; then + INPUT=$INSTDIR + fi + if [ ! -d "$INPUT" ] ; then + if exists "$INPUT" ; then + echo "$INPUT exists, but is not a directory!" + else + echo "$INPUT does not exist. Create it?" + echo2 "[y] " + read YN + if [ "$YN" != "n" ] ; then + if mkdir -p $INPUT ; then + ok=1 + fi + fi + fi + elif exists "$INPUT/include/services.h" ; then + echo "You cannot use the Services source directory as a target directory." + else + ok=1 + fi +done +INSTDIR=$INPUT +echo "" + +#### + +OLD_RUNGROUP="$RUNGROUP" +if [ "$RUNGROUP" ] ; then + echo "Which group should all Services data files be owned by? (If Services" + echo "should not force files to be owned by a particular group, type \"none\"" + echo "(without the quotes) and press Return.)" +else + echo "Which group should all Services data files be owned by? (If Services" + echo "should not force files to be owned by a particular group, just press" + echo "Return.)" +fi +echo2 "[$RUNGROUP] " +if read INPUT ; then : ; else echo "" ; exit 1 ; fi +if [ "$INPUT" ] ; then + if [ "$INPUT" = "none" ] ; then + RUNGROUP="" + else + RUNGROUP="$INPUT" + fi +fi +echo "" + +#### + +if [ ! "$UMASK" -o "$RUNGROUP" != "$OLD_RUNGROUP" ] ; then + if [ "$RUNGROUP" ] ; then + UMASK=007 + else + UMASK=077 + fi +fi + +ok=0 +echo "What should the default umask for data files be (in octal)?" +echo "(077 = only accessible by owner; 007 = accessible by owner and group)" +while [ $ok -eq 0 ] ; do + echo2 "[$UMASK] " + if read INPUT ; then : ; else echo "" ; exit 1 ; fi + if [ ! "$INPUT" ] ; then + INPUT=$UMASK + fi + if [ `echo "$INPUT" | grep -c '[^0-7]'` -gt 0 ] ; then + echo "$UMASK is not a valid octal number!" + else + if [ "`echo $INPUT | cut -c1`" != "0" ] ; then + INPUT=0$INPUT + fi + ok=1 + fi +done +UMASK=$INPUT +echo "" + +#### + +TEMP_YN="n" +if [ "$DEBUG" = "yes" ] ; then + TEMP_YN="y" +fi +echo "Would you like to build a debug version of Anope?" +echo2 "[$TEMP_YN] " +read YN +if [ "$YN" ] ; then + if [ "$YN" = "y" ] ; then + DEBUG="yes" + else + DEBUG="no" + fi +fi +echo "" + +#### + +TEMP_YN="n" +if [ "$USE_PCH" = "yes" ] ; then + TEMP_YN="y" +fi +echo "Do you want to build using precompiled headers? This can speed up" +echo "the build, but uses more disk space." +echo2 "[$TEMP_YN] " +read YN +if [ "$YN" ] ; then + if [ "$YN" = "y" ] ; then + USE_PCH="yes" + else + USE_PCH="no" + fi +fi +echo "" + +#### + +echo "Are there any extra include directories you wish to use?" +echo "You may only need to do this if CMake is unable to locate" +echo "missing dependencies without hints." +echo "Separate directories with semicolons." +echo "If you need no extra include directories, enter NONE in all caps." +echo2 "[$EXTRA_INCLUDE_DIRS] " +if read INPUT ; then : ; else echo "" ; exit 1 ; fi +if [ "$INPUT" ] ; then + if [ "$INPUT" = "NONE" ] ; then + EXTRA_INCLUDE_DIRS="" + else + EXTRA_INCLUDE_DIRS=$INPUT + fi +fi +echo "" + +#### + +echo "Are there any extra library directories you wish to use?" +echo "You may only need to do this if CMake is unable to locate" +echo "missing dependencies without hints." +echo "Separate directories with semicolons." +echo "If you need no extra library directories, enter NONE in all caps." +echo2 "[$EXTRA_LIB_DIRS] " +if read INPUT ; then : ; else echo "" ; exit 1 ; fi +if [ "$INPUT" ] ; then + if [ "$INPUT" = "NONE" ] ; then + EXTRA_LIB_DIRS="" + else + EXTRA_LIB_DIRS=$INPUT + fi +fi +echo "" + +#### + +echo "Are there any extra arguments you wish to pass to CMake?" +echo "If you need no extra arguments to CMake, enter NONE in all caps." +echo2 "[$EXTRA_CONFIG_ARGS] " +if read INPUT ; then : ; else echo "" ; exit 1 ; fi +if [ "$INPUT" ] ; then + if [ "$INPUT" = "NONE" ] ; then + EXTRA_CONFIG_ARGS="" + else + EXTRA_CONFIG_ARGS=$INPUT + fi +fi +echo "" + +#### + +################################################################################ +# Store values +################################################################################ + +echo2 "Saving configuration results in config.cache... " + +cat <$SOURCE_DIR/config.cache +INSTDIR="$INSTDIR" +RUNGROUP="$RUNGROUP" +UMASK=$UMASK +DEBUG="$DEBUG" +USE_PCH="$USE_PCH" +EXTRA_INCLUDE_DIRS="$EXTRA_INCLUDE_DIRS" +EXTRA_LIB_DIRS="$EXTRA_LIB_DIRS" +EXTRA_CONFIG_ARGS="$EXTRA_CONFIG_ARGS" +EOT +echo "done." + + +################################################################################ +# Build the build system string +################################################################################ + +Run_Build_System diff --git a/Config.exe b/Config.exe new file mode 100644 index 0000000000000000000000000000000000000000..d61814427eb4b0b28a0054c33aa57538b70ba92b GIT binary patch literal 18944 zcmeHPd3;pWz5m^l$;@Oz25u%KAPLL_!9Yk@Ris7;!-PADWU~it+m#=FStByEB52l*6ktUR(uu?wy&0#Df34&+Eq< z?pc24cYf!$pL6fbFzOY^qN}gc7CWo$ zBcbJLxkM8H8KR&k)uRsLJ`*={7epl#-)Kqxxu$Kn0p}}=re8!fNd8OLc2}X$2lI&L zbNfu9vH}~JS#=W)$m}0(J4ocs!1bbkN=CmjX{<@2KeG}A#-yw^-{{FJ2(BuvgcU(g z@^&T~g}5i-&bX#SA(fU9Gl3|1?ZzO}%3KiL=|nS7^|*qpS6qxLD4U+GASw#1-R`N~~|zH)MprD2#q z8?(T^PGsd_#(H#JWpGemSvCrv`-*7c0fFfOx9+aUwZ;Rd42=4~ZopF*@J@XT4Co%+ zyCs)ABdScu;Tzy7^qMe;FVEvG`mPC1d;wREwTkCrqR$~WKzDUxZP(Pzppj#p*L&Qr zyUM_iyBkDZ<*Re7%lpLuORn<8Io3~mW8`2BsKix1HOIQIuR+M_Dj$|(J=1&8gPG8Q zi*yJP@akUOb4B!kixn{~_u#>UMS<+Sxuc2p!cPL(<x$DueLH>j|E zHP-hXXoDZUx4IJuL7$J@*6ZM7J!{2;dokb(2CxPyJXW4Y?d93h(&UT>09()U_cLC> z*bZPN16WiApuL0K1qU=Zi^pxkDSWht#%c&{fq>Y!m4lopFabP5Hqe3Z z<$7j;11V?_^%=N-h|joHVDZ|a4qiG3)? zp4i8Tue@Gy!YZ-RxaliDPQh6-Hk_Nj^5F{33bNtc^p(5IsXzwOunBH@TiF?Q{Sk}F zno(gi5VFeP8DKqtkwEs;`!Se+5`DhjxS;Dp7^%Rz0rJVf8sN2_#!OSks1rKpkhkb^ zIEWU=(Q^t%thhnXG4nBAv?UW<<$w#f4A%2dUM!UH28atx*}> zA#Q78Mt7)9&_+JWZB=EAmKA{pg0Ri11@x$IyhL9#hXxS$E)yG~Po+ECcnEeG=EU(p zw4ZkWP8$j@ld&CxkZ@J_KnoZWWkWF=e!mW##8J#El1Py`jG^2>rr<`QS)v-k9IhHZ zci9NEay@1c)c}tfLY0>&MHz6HPbIH863tNo7owDPTH!^a#KJzxu}89<5ufhXv(2M< zj6CKj)NB}@b06t$b2I>f+;TlXx9k{hdUTH>1V9-B81s$21M_na6e385Iq9Hm3ff^N7Y)Pm%kV%&Slkai&4Yr7q+z8U?#d!aWsjWvgrmFWWj5`U-Ok2Z+=@H&7oq z?J=G%3b$CFfQQtUg^`L=$eUE!Uf@xN!Zy+@ zya4advv}nBLq~GU%X#E&XQU!u^5}G-cHZOzOhyz9pt1_kHF4(gm0{cVbwdL#-qqcC zo{FK?7ns&7O-TYpiolfK2opfU(mm9kqY}diG}C#)HqJQ!s-|tuiI_FIFyQi5WVut! zjiWMb18zXaxpY^#W-nPl*3Q)YA}A@2{7YVzXIe8Rkct4fq?PMM3Xxuo&hpF-@@INv zZD!}4yo`}WgVLQqc45Fh^+Tu!v5la>iO+Vn0tAGMy_r>-qq{kytWoxaes_^ z2s`o#jOQ&omib`b>X33$v=m=FejLU}>t1=tqP-&#W!B?BbE4{a3@dA?<@qQ><;Uq> z>nkQEhk5&QG%%Q~QTaVNrg9wp)FEysCSy%-=I%ytxl*Zs8N{IphbZ^d^D~eTimvh` zR=bUfW(I+`K%Lo`Ht)^l_5EPM9xlm&Y?Sqb1)o<~vLX1WCb^Nh5lO*^Qyn|mS6^Wd zv+hobXcY&X6N^mc)?DthY&dGQqK%_i92KcdZ*}r8OV#)Abr{aEQ6FYh7R~PO=RONz z_oo%0&+OX$CiLyVk|D*%d^afy?0(V<3au?XO_BvIpVFOAMyYJ86*BOjV|=-+#OGGI zjn8exK^kB7E!SY%Ipp!!!DnVIFNWl~Zp5+?L>w1x%i*krQ0Oe3ADH=yf5zrVW8APL49%Ilb zktr_44Ismvp|bC=-tzQ3)~g$5cz-$Re(Y%W-u|)(d>}^hesNrpbm&6)95QyeC_51| zfjFaK?hH*ny{Tux&MB1>Dko2vJQ0HPVK|0zBdjrUJ<+GA+ab=#hNKmZwuaBg$#rg1b1f{)hRnj6o7TsCP8xlmh+_O-J8q%5D6kXL2- zu7n&da)g^s6r(_IgGdS=eTdRcUkRQ&K8r_>%UY||(08%Co374c%Db{|&vMiIfV(Nr z#gOA&+^$B+yvYJ3*Mn#<{<39H$8#>uN_eE^vO$(jvRoz0Zps7v5|j&qOy^3v2JTwnUc8QQogLQZ;6EQY~=S(P{LlHWB#ywGEgn#2~zbP&6ls&A_h~TLGCPeuj2~ zxE1ZC;@2owi2DFZXuIeHY86k(6*o{+QjXGf;!U*gl;tzBd|hN8lr8c>$8fr5bewgX*bgE zvu2^(3kpA{kFw@!V@Pw&1%9z>KIp6vi_oslDh0Pky9UvHQpWpezUzCE!kLWY8iIC% zXqJ$eEE8Ie%qK(whl}H+GG{5mIBa)<9Ym7)o zGTaz57KD?nR2xqu!?D=RsD(k(>cV)^3fIOXv5qDK(1ZfiMH|zdYOAHA&4?!xv^ZhZ z&kL_KXhugg)-=;->}a8yRwJ@NUu3R_5CO2A6YOh(&`${Mq+JsLBt z2E*!%MvMd$!hmoRH=2MUY!%d)u^8+KQi;krM%=KX z5#UQe*y=iS5*7$s$;6TU9I(eEq3y(}Mi(S$kA))!RW~(Ji;-MW%f7>n zc}5};Zh;-8J5|n%hFjuhA{mV&Xn|!y&k0GqHr{Mf0{9D!Ch1gw#+$-c(=5w^Df=3k z-;r$ZNXj8NR70x~izzQPBrNT2_Bu)mTUo4m!;&02E7|mzX$PbhuY<16oG2A*Pvc5j zh>=eTC!o%x(L}T2aBwTkzBk86X7m`Xro*z}{WQ<)H0t?XE(3XD4c>6m%y80J1aFei z#mPv$xtjGGN&Cz~quDkRRVNZgTVt$Ct|9{yyKxH0bn8saWY>_<3T9G~S|7$D%s>2& zU4>U+w}TO-4S0wRTAQfvh{fhxOIjgXLp$3xMI+skQ)(;&+^0vSv?ihhaVP_kJY58% z;H6;~QD_}rU7thCC_*O1sTo?6Yfd3%);o0n$33y@{vt#|v=#2;MbU$-A%bQ@#kPM{RVpGH}h(AOIO37b%3|ausaLfMX&~)H*k?$ z*pfP24SjHIGJ`=tEQxGMND}AGf`bDdnrblFHT+)1p-8O_8RnVv`! zdH#|7X;lrN6$iyIt&u!bBBnFftpulQq+Cm}p0WmWm7wKBMg>|Xbme5>Aox*#wa_h( zDJ>*Gfi0@?GuxcC&$)x0k)i$PWvxN2!dOYr<9KrZ8es1zxKcEn(K1ktVuc8_6-JBg zZON!(E+Tk-&>|H$qjNYYk5QUrSP)stp~)ERDNb-CB#joy0YfcGy#*FizM}Gk6aSjt zTRRRUEr|w;r}@ybxu+F5IkpmeM>XD=enR9 z_Q?ihOP*T;N-OOBZF~wx!Vm25J7f}tvFmOF^HEf7)qFGO~tBLr&Cj4q@&x;~Kky7{=69FdIj!;aQdubkc19Bv218sIq&i0JO z9H$d(93dBl8QBCJ6iRWcQ_5A`q-A3x^898{je`>>5O_tFh>u=Oot?zlQTmtG*+e-& zl#{T&7h$%M;!tk>3J2_W)Ml0Tgt6C(Xh;iBP~-1OKe9vXG7_!QBJeW zG4slL;g+L&N7nQf)H8i?^5-?wp6c+f^sT~3>6IZ(QU(=hG04F|%=%ag`Nv}%Y1TYa zU*$cTeTMy)kHb9=X^xLpgSt97oZNH0^H)~O=y!~&ayYZh`ws61D)%XcbCzX?W_M$^ zW^8s9&Pq|V*;tNyt_Flph>l8>LQjTz&j3E}qU;>J3cF}bw%9?`KB0nA#edon)GnN9 z3gsZ|vYbzpi>SG*U^XOYGhT}^(_zgrsDl)@*x?=inQvZ^d1SX>*W=(xz*IhjG|%Jx z-=W-}9vnIxK76|2{f7@=EG_Gab<9b`aWp={ad>fF=J7K0R^krAHO8Q1E;!tKCZ9%N z@V?gn>}8nEoc9d6w5HiHzKNwdF=VDu;DQEfr>uiT->2Kg{-Jcw8X5(mXK^!{UvRc&t1sBN~t*>%9q%=`ax_L$7I zIpBK+a>hExe*I&PdRS2pBm5|+9!Kc-3i+bXdHuHnA)fgHa2gH-{9=%ybI5s-7Q_R6 z?|IIPxPE73@hdl;<-Au>uO@rrmy(uU3VYF*3anU~@oW%GJ*hYkVF`?bmsw1e6P0?M zxkA3^RIlMyfcrCOfqWwADak^>>Tp*>Lf+K1>Tg0N{dyA=h<1eT@_n}Q#`+)bzUQIS z%$t5n-h0+AJALSseU}KgU$}*fG~vf5sRFl#j^B%h9}Ufqk4U{Geke(E1vSm$T`)bA^@hxgOwNd^V@ggP8teT%G~> z$AUstewE)Z=ljtw5o!ie{%Nc%D2ntmKsi8=TgwkaY0NaUo|VOQdcFn;g@|~!3;d2 z6*Z=X4`Sp8aq`nd!>DYE@%ISui-A!ToGx467XJ03Z8os4Kw5bm`olA5}A8@1<+SL#Ir9R-i*hgISxR?qqyHcGrU{F8sAmD2v z;ERQ`ub@Tv-az`A5XNsZSSb6Nit+a{=*<-P>Ji@bHQ;Ss@6S$nE0~SvD!v|aeR!Y` z2Kfz_yb%0{us>76PM3$8*>bDLXU5o|`QX9V(ZsVBVcX=VQS}VzyvmRWbcgF^@T!43 zeh;7yDTh+(mN*mext;o(f=zq^2#kX@HAtXd-prK84n7m|d)&-*g20`Cl#|BodDviH zCSXfW-~2t-T;Q`b>U|}jK4Z`qzppodUjrGPH|oxtZKhKud8z|Wi=4rD?Rdy!uGITo zq9E|5OZxL|I7`m-9a*^d_3KQL^6;U<#Nmoxpe147%p+7^GO-S-VF~rlfZu5FA@yI) zQ*y~T05(+IRoY=*@?3q2F#im$tOF(&m;HdJV8`@fh9M-bSzd zW*a@R<#PH}_gZ@KjvHv}%CqQ~>(|iMc${uPmjCSIkMX;(gY?3qkJ7I%IGgs~dlNl= z-DPy(tFP#(+inBR7JA|K>**%Tq@S%>Lyuj1DebyuBYphA2lV-;pVA#0H`4ZGk`5d= zK-Zsj7X1YGm!E%5_gsB7-G9Y}^aseW=eIY~8xQUTZ_RZ3MHkU8y1VJ+JAX>AJ^L)} zdte9s@|-pF%3a&&$?LD62Y+}GJ$vuHbPGP}zI9zE{rBFz^yy#!N;fCk>E_N(di$l9 z=pfeGwQU>i!~FeUeo23M`DOa-lTYZOD=(%!fA|C43|`;cw~uzLT}w|wcRNvk0vh*R zdLF&;&@GVhX2|#hdVI$Y`o-D~+Wni~&ci*KuFFc!m zzJ5LZ^)G*+TUICNAJEsYAoBxTw$Sy_R(ko#C+WFgY^Enb>*M#|r$6qvmhQj&0($+y z9rT~KTu1x=`A^#39;c`8yptZg=_Yy~>%8*RQ}pJa|4d)};~(_Z{{8geri*AtR~Kzt zwTfPS`f0im^*{dhH+pvGkLlN!UP?b-o21*$UQPc6+3w!hO}AfsG2MCDWwdkMI@-~( zir#whMSA|WE%YFGy6fWg^x_jwz!p(@==$qv=hmIY~H*d}a$jv4m1&*1+Y z1FY9C_=Y{d`0O+Kl5fNS`w{ym`vB{oZOw7TvBEygad+5P;IJ_zVnN0pcNjB;c|`aV z$4)yE{3$}$j|9JL*^%IvgZh!+i=&SSUrb~4!{%RXkm!etFK$ujhlwwax6u#5--#!P zLoWxrH~&8q#XHhteYJYnOH97GFPuzRCcc=HIg)PQv}uFh=~ewS{*7W)3T5W@F->-7 z`DGBNOW!2sbTUMoYP<32Vo(ZQTwL&-6E~@DtJwO}khoNA6Ji)3%bf}0QU`tdY7yG< zlhF05zg&buAuKUzo?qMmP?O^5v}+x7z3|7~p>so_>pB1_*gQsbV?t7(>Gth z9Es@;{#93pLV;@nlR`i8fL$SmGdf>YHivQnHJ9g1n;U8dpH-pICjI*pue?AZqnsy> zmv$bDqv+%=hrGUFV2CG+khn}2F~%N!xe!;N{-F>B7&#gXIPQn;;!tQJfEz=X=n>KRnA5|=aky944W%Xt%JDpLiMQ-fqzz|8L9;Px_*)XK^a5Sfvs1gD4W6ab-jiI zCXGK~A|#tU<=9Z@I5n;xKUF_Llqf3$^d0^ILisp*P_L-K3b-oqQ>Z>K8IPp414bA% zn$eFb6Jz>B=bvfd8lK|FJt7FdEFIY=wtkc%kMFr1rsRx5w-Ccx1s1FNz#r?f@b3 zdSS~hru2DbWg_DYbnxIK{C`v6!oxFH2kd&kU4P!I-e>ondY9erwrf)L0a{FKUXPL!v7_`oA4p1h_l7VK2t*sm&`SUI6I zXv8CC6TZD%Rl0c5?24(S!G!$Ycg&0%Ri#}3BsUX>}x${MF~feK?hy`O@R+WYmwee1KrD2r@ zJEGMQ{@#66X>&N1Fl?bDk@0 ) +# +# A macro to handle stripping the leading and trailing spaces from a string, +# uses string(STRIP) if using CMake 2.6.x or better, otherwise uses +# string(REGEX REPLACE). +############################################################################### +macro(strip_string INPUT_STRING OUTPUT_STRING) + if(CMAKE26_OR_BETTER) + # For CMake 2.6.x or better, we can just use the STRIP sub-command of string() + string(STRIP ${INPUT_STRING} ${OUTPUT_STRING}) + else(CMAKE26_OR_BETTER) + # For CMake 2.4.x, we will have to use the REGEX REPLACE sub-command of string() instead + # First check if the input string is empty or not + if (${INPUT_STRING} STREQUAL "") + set(${OUTPUT_STRING} "") + else(${INPUT_STRING} STREQUAL "") + # Determine if the string is entirely empty or not + string(REGEX MATCH "^[ \t]*$" EMPTY_STRING "${INPUT_STRING}") + if(EMPTY_STRING) + set(${OUTPUT_STRING} "") + else(EMPTY_STRING) + # We detect if there is any leading whitespace and remove any if there is + string(SUBSTRING "${INPUT_STRING}" 0 1 FIRST_CHAR) + if(FIRST_CHAR STREQUAL " " OR FIRST_CHAR STREQUAL "\t") + string(REGEX REPLACE "^[ \t]+" "" TEMP_STRING "${INPUT_STRING}") + else(FIRST_CHAR STREQUAL " " OR FIRST_CHAR STREQUAL "\t") + set(TEMP_STRING "${INPUT_STRING}") + endif(FIRST_CHAR STREQUAL " " OR FIRST_CHAR STREQUAL "\t") + # Next we detect if there is any trailing whitespace and remove any if there is + string(LENGTH "${TEMP_STRING}" STRING_LEN) + math(EXPR STRING_LEN "${STRING_LEN} - 1") + string(SUBSTRING "${TEMP_STRING}" ${STRING_LEN} 1 LAST_CHAR) + if(LAST_CHAR STREQUAL " " OR LAST_CHAR STREQUAL "\t") + string(REGEX REPLACE "[ \t]+$" "" ${OUTPUT_STRING} "${TEMP_STRING}") + else(LAST_CHAR STREQUAL " " OR LAST_CHAR STREQUAL "\t") + set(${OUTPUT_STRING} "${TEMP_STRING}") + endif(LAST_CHAR STREQUAL " " OR LAST_CHAR STREQUAL "\t") + endif(EMPTY_STRING) + endif(${INPUT_STRING} STREQUAL "") + endif(CMAKE26_OR_BETTER) +endmacro(strip_string) + +############################################################################### +# append_to_list( ...) +# +# A macro to handle appending to lists, uses list(APPEND) if using CMake 2.4.2 +# or better, otherwise uses set() instead. +############################################################################### +macro(append_to_list LIST) + if(CMAKE242_OR_BETTER) + # For CMake 2.4.2 or better, we can just use the APPEND sub-command of list() + list(APPEND ${LIST} ${ARGN}) + else(CMAKE242_OR_BETTER) + # For CMake 2.4.x before 2.4.2, we have to do this manually use set() instead + set(${LIST} ${${LIST}} ${ARGN}) + endif(CMAKE242_OR_BETTER) +endmacro(append_to_list) + +############################################################################### +# find_in_list( ) +# +# A macro to handle searching within a list, will store the result in the +# given , uses list(FIND) if using CMake 2.6.x or better +# (or CMake 2.4.8 or better), otherwise it iterates through the list to find +# the item. +############################################################################### +macro(find_in_list LIST ITEM_TO_FIND FOUND) + if(CMAKE248_OR_BETTER) + # For CMake 2.4.8 or better, we can use the FIND sub-command of list() + list(FIND ${LIST} ${ITEM_TO_FIND} ITEM_FOUND) + else(CMAKE248_OR_BETTER) + # For CMake 2.4.x before 2.4.8, we have to do this ourselves (NOTE: This is very slow due to a lack of break() as well) + # Firstly we set the position to -1 indicating nothing found, we also use a temporary position + set(ITEM_FOUND -1) + set(POS 0) + # Iterate through the list + foreach(ITEM ${${LIST}}) + # If the item we are looking at is the item we are trying to find, set that we've found the item + if(${ITEM} STREQUAL ${ITEM_TO_FIND}) + set(ITEM_FOUND ${POS}) + endif(${ITEM} STREQUAL ${ITEM_TO_FIND}) + # Increase the position value by 1 + math(EXPR POS "${POS} + 1") + endforeach(ITEM) + endif(CMAKE248_OR_BETTER) + # Set the given FOUND variable to the result + set(${FOUND} ${ITEM_FOUND}) +endmacro(find_in_list) + +############################################################################### +# remove_list_duplicates() +# +# A macro to handle removing duplicates from a list, uses +# list(REMOVE_DUPLICATES) if using CMake 2.6.x or better, otherwise it uses +# a slower method of creating a temporary list and only adding to it when +# a duplicate item hasn't been found. +############################################################################### +macro(remove_list_duplicates LIST) + if(CMAKE26_OR_BETTER) + # For CMake 2.6.x or better, this can be done automatically + list(REMOVE_DUPLICATES ${LIST}) + else(CMAKE26_OR_BETTER) + # For CMake 2.4.x, we have to do this ourselves, firstly we'll clear a temporary list + set(NEW_LIST) + # Iterate through the old list + foreach(ITEM ${${LIST}}) + # Check if the item is in the new list + find_in_list(NEW_LIST ${ITEM} FOUND_ITEM) + if(FOUND_ITEM EQUAL -1) + # If the item was not found, append it to the list + append_to_list(NEW_LIST ${ITEM}) + endif(FOUND_ITEM EQUAL -1) + endforeach(ITEM) + # Replace the old list with the new list + set(${LIST} ${NEW_LIST}) + endif(CMAKE26_OR_BETTER) +endmacro(remove_list_duplicates) + +############################################################################### +# remove_item_from_list( ) +# +# A macro to handle removing a value from a list, uses list(REMOVE_ITEM) in +# both cases, but can remove the value itself using CMake 2.4.2 or better, +# while older versions use a slower method of iterating the list to find the +# index of the value to remove. +############################################################################### +macro(remove_item_from_list LIST VALUE) + if(CMAKE242_OR_BETTER) + # For CMake 2.4.2 or better, this can be done automatically + list(REMOVE_ITEM ${LIST} ${VALUE}) + else(CMAKE242_OR_BETTER) + # For CMake 2.4.x before 2.4.2, we have to do this ourselves, firstly we set the index and a variable to indicate if the item was found + set(INDEX 0) + set(FOUND FALSE) + # Iterate through the old list + foreach(ITEM ${${LIST}}) + # If the item hasn't been found yet, but the current item is the same, remove it + if(NOT FOUND) + if(ITEM STREQUAL ${VALUE}) + set(FOUND TRUE) + list(REMOVE_ITEM ${LIST} ${INDEX}) + endif(ITEM STREQUAL ${VALUE}) + endif(NOT FOUND) + # Increase the index value by 1 + math(EXPR INDEX "${INDEX} + 1") + endforeach(ITEM) + endif(CMAKE242_OR_BETTER) +endmacro(remove_item_from_list) + +############################################################################### +# sort_list() +# +# A macro to handle sorting a list, uses list(SORT) if using CMake 2.4.4 or +# better, otherwise it uses a slower method of creating a temporary list and +# adding elements in alphabetical order. +############################################################################### +macro(sort_list LIST) + if(CMAKE244_OR_BETTER) + # For CMake 2.4.4 or better, this can be done automatically + list(SORT ${LIST}) + else(CMAKE244_OR_BETTER) + # For CMake 2.4.x before 2.4.4, we have to do this ourselves, firstly we'll create a temporary list + set(NEW_LIST) + # Iterate through the old list + foreach(ITEM ${${LIST}}) + # Temporary index position for the new list, as well as temporary value to store if the item was ever found + set(INDEX 0) + set(FOUND FALSE) + # Iterate through the new list + foreach(NEW_ITEM ${NEW_LIST}) + # Compare the items, only if nothing was found before + if(NOT FOUND) + if(NEW_ITEM STRGREATER "${ITEM}") + set(FOUND TRUE) + list(INSERT NEW_LIST ${INDEX} ${ITEM}) + endif(NEW_ITEM STRGREATER "${ITEM}") + endif(NOT FOUND) + # Increase the index value by 1 + math(EXPR INDEX "${INDEX} + 1") + endforeach(NEW_ITEM) + # If the item was never found, just append it to the end + if(NOT FOUND) + append_to_list(NEW_LIST ${ITEM}) + endif(NOT FOUND) + endforeach(ITEM) + # Replace the old list with the new list + set(${LIST} ${NEW_LIST}) + endif(CMAKE244_OR_BETTER) +endmacro(sort_list) + +############################################################################### +# read_from_file( ) +# +# A macro to handle reading specific lines from a file, uses file(STRINGS) if +# using CMake 2.6.x or better, otherwise we read in the entire file and +# perform a string(REGEX MATCH) on each line of the file instead. This +# macro can also be used to read in all the lines of a file if REGEX is set +# to "". +############################################################################### +macro(read_from_file FILE REGEX STRINGS) + if(CMAKE26_OR_BETTER) + # For CMake 2.6.x or better, we can just use the STRINGS sub-command to get the lines that match the given regular expression (if one is given, otherwise get all lines) + if(REGEX STREQUAL "") + file(STRINGS ${FILE} RESULT) + else(REGEX STREQUAL "") + file(STRINGS ${FILE} RESULT REGEX ${REGEX}) + endif(REGEX STREQUAL "") + else(CMAKE26_OR_BETTER) + # For CMake 2.4.x, we need to do this manually, firstly we read the file in + execute_process(COMMAND ${CMAKE_COMMAND} -DFILE:STRING=${FILE} -P ${Anope_SOURCE_DIR}/cmake/ReadFile.cmake ERROR_VARIABLE ALL_STRINGS) + # Next we replace all newlines with semicolons + string(REGEX REPLACE "\n" ";" ALL_STRINGS ${ALL_STRINGS}) + if(REGEX STREQUAL "") + # For no regular expression, just set the result to all the lines + set(RESULT ${ALL_STRINGS}) + else(REGEX STREQUAL "") + # Clear the result list + set(RESULT) + # Iterate through all the lines of the file + foreach(STRING ${ALL_STRINGS}) + # Check for a match against the given regular expression + string(REGEX MATCH ${REGEX} STRING_MATCH ${STRING}) + # If we had a match, append the match to the list + if(STRING_MATCH) + append_to_list(RESULT ${STRING}) + endif(STRING_MATCH) + endforeach(STRING) + endif(REGEX STREQUAL "") + endif(CMAKE26_OR_BETTER) + # Set the given STRINGS variable to the result + set(${STRINGS} ${RESULT}) +endmacro(read_from_file) + +############################################################################### +# extract_include_filename( []) +# +# This macro will take a #include line and extract the filename. +############################################################################### +macro(extract_include_filename INCLUDE FILENAME) + # Strip the leading and trailing spaces from the include line + strip_string(${INCLUDE} INCLUDE_STRIPPED) + # Make sure to only do the following if there is a string + if(INCLUDE_STRIPPED STREQUAL "") + set(FILE "") + else(INCLUDE_STRIPPED STREQUAL "") + # Extract the filename including the quotes or angle brackets + string(REGEX REPLACE "^.*([\"<].*[\">]).*$" "\\1" FILE "${INCLUDE_STRIPPED}") + # If an optional 3rd argument is given, we'll store if the quote style was quoted or angle bracketed + if(${ARGC} GREATER 2) + string(SUBSTRING ${FILE} 0 1 QUOTE) + if(QUOTE STREQUAL "<") + set(${ARGV2} "angle brackets") + else(QUOTE STREQUAL "<") + set(${ARGV2} "quotes") + endif(QUOTE STREQUAL "<") + endif(${ARGC} GREATER 2) + # Now remove the quotes or angle brackets + string(REGEX REPLACE "^[\"<](.*)[\">]$" "\\1" FILE "${FILE}") + endif(INCLUDE_STRIPPED STREQUAL "") + # Set the filename to the the given variable + set(${FILENAME} "${FILE}") +endmacro(extract_include_filename) + +############################################################################### +# find_includes( ) +# +# This macro will search through a file for #include lines, regardless of +# whitespace, but only returns the lines that are valid for the current +# platform CMake is running on. +############################################################################### +macro(find_includes SRC INCLUDES) + # Read all lines from the file that start with #, regardless of whitespace before the # + read_from_file(${SRC} "^[ \t]*#.*$" LINES) + # Set that any #include lines found are valid, and create temporary variables for the last found #ifdef/#ifndef + set(VALID_LINE TRUE) + set(LAST_DEF) + set(LAST_CHECK) + # Create an empty include list + set(INCLUDES_LIST) + # Iterate through all the # lines + foreach(LINE ${LINES}) + # Search for #ifdef, #ifndef, #else, #endif, and #include + string(REGEX MATCH "^[ \t]*#[ \t]*ifdef[ \t]*.*$" FOUND_IFDEF ${LINE}) + string(REGEX MATCH "^[ \t]*#[ \t]*ifndef[ \t]*.*$" FOUND_IFNDEF ${LINE}) + string(REGEX MATCH "^[ \t]*#[ \t]*else.*$" FOUND_ELSE ${LINE}) + string(REGEX MATCH "^[ \t]*#[ \t]*endif.*$" FOUND_ENDIF ${LINE}) + string(REGEX MATCH "^[ \t]*#[ \t]*include[ \t]*[\"<].*[\">][\ t]*.*$" FOUND_INCLUDE ${LINE}) + # If we found a #ifdef on the line, extract the data after the #ifdef and set if the lines after it are valid based on the variables in CMake + if(FOUND_IFDEF) + # Extract the define + string(REGEX REPLACE "^[ \t]*#[ \t]*ifdef[ \t]*(.*)$" "\\1" DEFINE ${LINE}) + # Replace _WIN32 with WIN32, so we can check if the WIN32 variable of CMake is set instead of _WIN32 + if(DEFINE STREQUAL "_WIN32") + set(DEFINE WIN32) + endif(DEFINE STREQUAL "_WIN32") + # Set the last define to this one, and set the last check to true, so when #else is encountered, we can do an opposing check + set(LAST_DEF ${DEFINE}) + set(LAST_CHECK TRUE) + # If the define is true (it either exists or is a non-false result), the lines following will be checked, otherwise they will be skipped + if(${DEFINE}) + set(VALID_LINE TRUE) + else(${DEFINE}) + set(VALID_LINE FALSE) + endif(${DEFINE}) + else(FOUND_IFDEF) + # If we found a #ifndef on the line, the same thing as #ifdef is done, except with the checks in the opposite direction + if(FOUND_IFNDEF) + # Extract the define + string(REGEX REPLACE "^[ \t]*#[ \t]*ifndef[ \t]*(.*)$" "\\1" DEFINE ${LINE}) + # Replace _WIN32 with WIN32, so we can check if the WIN32 variable of CMake is set instead of _WIN32 + if(DEFINE STREQUAL "_WIN32") + set(DEFINE WIN32) + endif(DEFINE STREQUAL "_WIN32") + # Set the last define to this one, and set the last check to false, so when #else is encountered, we can do an opposing check + set(LAST_DEF ${DEFINE}) + set(LAST_CHECK FALSE) + # If the define is not true (it either doesn't exists or is a false result), the lines following will be checked, otherwise they will be skipped + if(${DEFINE}) + set(VALID_LINE FALSE) + else(${DEFINE}) + set(VALUE_LINE TRUE) + endif(${DEFINE}) + else(FOUND_IFNDEF) + # If we found a #else on the line, we check the last define in the opposite direction + if(FOUND_ELSE) + # When LAST_CHECK is true, we were inside a #ifdef, now act as if we are entering a #ifndef section by doing an opposing check + if(LAST_CHECK) + if(${LAST_DEF}) + set(VALID_LINE FALSE) + else(${LAST_DEF}) + set(VALID_LINE TRUE) + endif(${LAST_DEF}) + # When LAST_CHECK is false, we were inside a #ifndef, now act as if we are entering a #ifdef section by doing an opposing check + else(LAST_CHECK) + if(${LAST_DEF}) + set(VALID_LINE TRUE) + else(${LAST_DEF}) + set(VALID_LINE FALSE) + endif(${LAST_DEF}) + endif(LAST_CHECK) + else(FOUND_ELSE) + # If we found a #endif on the line, we'll assume everything following the line is valid until we meet another one of the above lines + if(FOUND_ENDIF) + set(VALID_LINE TRUE) + else(FOUND_ENDIF) + # If we found a #include on the line, add the entire line to the list of includes unless the line isn't valid + if(FOUND_INCLUDE) + if(VALID_LINE) + append_to_list(INCLUDES_LIST "${LINE}") + endif(VALID_LINE) + endif(FOUND_INCLUDE) + endif(FOUND_ENDIF) + endif(FOUND_ELSE) + endif(FOUND_IFNDEF) + endif(FOUND_IFDEF) + endforeach(LINE) + set(${INCLUDES} ${INCLUDES_LIST}) +endmacro(find_includes) + +############################################################################### +# calculate_depends( []) +# +# This macro is used in most of the src (sub)directories to calculate the +# header file dependencies for the given source file. +############################################################################### +macro(calculate_depends SRC) + # Temporarily set that we didn't get a 3rd argument before we actually check if we did get one or not + set(CHECK_ANGLE_INCLUDES FALSE) + # Check for a third argument + if(${ARGC} GREATER 1) + set(CHECK_ANGLE_INCLUDES TRUE) + endif(${ARGC} GREATER 1) + # Find all the lines in the given source file that have any form of #include on them, regardless of whitespace, but only if they are valid for the platform we are on + find_includes(${SRC} INCLUDES) + # Reset the list of headers to empty + set(HEADERS) + # Iterate through the strings containing #include (if any) + foreach(INCLUDE ${INCLUDES}) + # Extract the filename from the #include line + extract_include_filename(${INCLUDE} FILENAME QUOTE_TYPE) + if(QUOTE_TYPE STREQUAL "angle brackets") + # The following checks will only be done if there was a request for angle includes to be checked + if(CHECK_ANGLE_INCLUDES) + # Find the path of the include file + if(DEFAULT_INCLUDE_DIRS OR WSDK_PATH OR DEFINED $ENV{VCINSTALLDIR}) + find_path(FOUND_${FILENAME}_INCLUDE NAMES ${FILENAME} PATHS ${DEFAULT_INCLUDE_DIRS} ${WSDK_PATH}/include $ENV{VCINSTALLDIR}/include ${EXTRA_INCLUDE}) + else(DEFAULT_INCLUDE_DIRS OR WSDK_PATH OR DEFINED $ENV{VCINSTALLDIR}) + find_path(FOUND_${FILENAME}_INCLUDE NAMES ${FILENAME} ${EXTRA_INCLUDE}) + endif(DEFAULT_INCLUDE_DIRS OR WSDK_PATH OR DEFINED $ENV{VCINSTALLDIR}) + # If the include file was found, add it's path to the list of include paths, but only if it doesn't already exist and isn't in the defaults for the compiler + if(FOUND_${FILENAME}_INCLUDE) + # This used to be find_in_list, but it was changed to this loop to do a find on each default include directory, this fixes Mac OS X trying to get it's framework directories in here + set(FOUND_IN_DEFAULTS -1) + foreach(DEFAULT_INCLUDE_DIR ${DEFAULT_INCLUDE_DIRS}) + string(REGEX REPLACE "\\+" "\\\\+" DEFAULT_INCLUDE_DIR ${DEFAULT_INCLUDE_DIR}) + string(REGEX MATCH ${DEFAULT_INCLUDE_DIR} FOUND_DEFAULT ${FOUND_${FILENAME}_INCLUDE}) + if(FOUND_DEFAULT) + set(FOUND_IN_DEFAULTS 0) + endif(FOUND_DEFAULT) + endforeach(DEFAULT_INCLUDE_DIR) + if(FOUND_IN_DEFAULTS EQUAL -1) + find_in_list(${ARGV1} "${FOUND_${FILENAME}_INCLUDE}" FOUND_IN_INCLUDES) + if(FOUND_IN_INCLUDES EQUAL -1) + append_to_list(${ARGV1} "${FOUND_${FILENAME}_INCLUDE}") + endif(FOUND_IN_INCLUDES EQUAL -1) + endif(FOUND_IN_DEFAULTS EQUAL -1) + else(FOUND_${FILENAME}_INCLUDE) + # XXX + if(NOT ${FILENAME} STREQUAL "libintl.h") + message(FATAL_ERROR "${SRC} needs header file ${FILENAME} but we were unable to locate that header file! Check that the header file is within the search path of your OS.") + endif(NOT ${FILENAME} STREQUAL "libintl.h") + endif(FOUND_${FILENAME}_INCLUDE) + endif(CHECK_ANGLE_INCLUDES) + endif(QUOTE_TYPE STREQUAL "angle brackets") + endforeach(INCLUDE) +endmacro(calculate_depends) + +############################################################################### +# calculate_libraries( ) +# +# This macro is used in most of the module (sub)directories to calculate the +# library dependencies for the given source file. +############################################################################### +macro(calculate_libraries SRC SRC_LDFLAGS EXTRA_DEPENDS) + # Set up a temporary LDFLAGS for this file + set(THIS_LDFLAGS "${LDFLAGS}") + # Reset extra dependencies + set(EXTRA_DEPENDENCIES) + # Reset library paths + set(LIBRARY_PATHS) + # Reset libraries + set(LIBRARIES) + # Check to see if there are any lines matching: /* RequiredLibraries: [something] */ + if(WIN32) + read_from_file(${SRC} "/\\\\*[ \t]*RequiredWindowsLibraries:[ \t]*.*[ \t]*\\\\*/" REQUIRED_LIBRARIES) + else(WIN32) + read_from_file(${SRC} "/\\\\*[ \t]*RequiredLibraries:[ \t]*.*[ \t]*\\\\*/" REQUIRED_LIBRARIES) + endif(WIN32) + # Iterate through those lines + foreach(REQUIRED_LIBRARY ${REQUIRED_LIBRARIES}) + # Strip off the /* RequiredLibraries: and */ from the line + string(REGEX REPLACE "/\\*[ \t]*Required.*Libraries:[ \t]*([^ \t]*)[ \t]*\\*/" "\\1" REQUIRED_LIBRARY ${REQUIRED_LIBRARY}) + # Replace all commas with semicolons + string(REGEX REPLACE "," ";" REQUIRED_LIBRARY ${REQUIRED_LIBRARY}) + # Iterate through the libraries given + foreach(LIBRARY ${REQUIRED_LIBRARY}) + # If the library has multiple names extract the alternate. + unset(LIBRARY_ALT) + if (${LIBRARY} MATCHES "^.+\\|.+$") + string(REGEX REPLACE ".+\\|(.*)" "\\1" LIBRARY_ALT ${LIBRARY}) + string(REGEX REPLACE "(.+)\\|.*" "\\1" LIBRARY ${LIBRARY}) + endif(${LIBRARY} MATCHES "^.+\\|.+$") + # Locate the library to see if it exists + if(DEFAULT_LIBRARY_DIRS OR WSDK_PATH OR DEFINED $ENV{VCINSTALLDIR}) + find_library(FOUND_${LIBRARY}_LIBRARY NAMES ${LIBRARY} ${LIBRARY_ALT} PATHS ${DEFAULT_LIBRARY_DIRS} ${WSDK_PATH}/lib $ENV{VCINSTALLDIR}/lib ${EXTRA_INCLUDE} ${EXTRA_LIBS}) + else(DEFAULT_LIBRARY_DIRS OR WSDK_PATH OR DEFINED $ENV{VCINSTALLDIR}) + find_library(FOUND_${LIBRARY}_LIBRARY NAMES ${LIBRARY} ${LIBRARY_ALT} PATHS ${EXTRA_INCLUDE} ${EXTRA_LIBS} NO_DEFAULT_PATH) + find_library(FOUND_${LIBRARY}_LIBRARY NAMES ${LIBRARY} ${LIBRARY_ALT} PATHS ${EXTRA_INCLUDE} ${EXTRA_LIBS}) + endif(DEFAULT_LIBRARY_DIRS OR WSDK_PATH OR DEFINED $ENV{VCINSTALLDIR}) + # If the library was found, we will add it to the linker flags + if(FOUND_${LIBRARY}_LIBRARY) + if(MSVC) + # For Visual Studio, instead of editing the linker flags, we'll add the library to a separate list of extra dependencies + append_to_list(EXTRA_DEPENDENCIES "${FOUND_${LIBRARY}_LIBRARY}") + else(MSVC) + # Get the path only of the library, to add it to library paths. + get_filename_component(LIBRARY_PATH ${FOUND_${LIBRARY}_LIBRARY} PATH) + append_to_list(LIBRARY_PATHS "${LIBRARY_PATH}") + # Extract the library short name, add it to the library path + get_filename_component(LIBRARY_NAME ${FOUND_${LIBRARY}_LIBRARY} NAME_WE) + string(REGEX REPLACE "^lib" "" LIBRARY_NAME ${LIBRARY_NAME}) + append_to_list(LIBRARIES ${LIBRARY_NAME}) + endif(MSVC) + else(FOUND_${LIBRARY}_LIBRARY) + # In the case of the library not being found, we fatally error so CMake stops trying to generate + message(FATAL_ERROR "${SRC} needs library ${LIBRARY} but we were unable to locate that library! Check that the library is within the search path of your OS.") + endif(FOUND_${LIBRARY}_LIBRARY) + endforeach(LIBRARY) + endforeach(REQUIRED_LIBRARY) + # Remove duplicates from the library paths + if(LIBRARY_PATHS) + remove_list_duplicates(LIBRARY_PATHS) + endif(LIBRARY_PATHS) + # Remove diplicates from the libraries + if(LIBRARIES) + remove_list_duplicates(LIBRARIES) + endif(LIBRARIES) + # Iterate through library paths and add them to the linker flags + foreach(LIBRARY_PATH ${LIBRARY_PATHS}) + find_in_list(DEFAULT_LIBRARY_DIRS "${LIBRARY_PATH}" FOUND_IN_DEFAULTS) + if(FOUND_IN_DEFAULTS EQUAL -1) + set(THIS_LDFLAGS "${THIS_LDFLAGS} -L${LIBRARY_PATH}") + endif(FOUND_IN_DEFAULTS EQUAL -1) + endforeach(LIBRARY_PATH) + # Iterate through libraries and add them to the linker flags + foreach(LIBRARY ${LIBRARIES}) + append_to_list(EXTRA_DEPENDENCIES "${LIBRARY}") + endforeach(LIBRARY) + set(${SRC_LDFLAGS} "${THIS_LDFLAGS}") + set(${EXTRA_DEPENDS} "${EXTRA_DEPENDENCIES}") +endmacro(calculate_libraries) + +############################################################################### +# check_functions( ) +# +# This macro is used in most of the module (sub)directories to calculate the +# function dependencies for the given source file. +############################################################################### +macro(check_functions SRC SUCCESS) + # Default to true + set(${SUCCESS} TRUE) + # Check to see if there are any lines matching: /* RequiredFunctions: [something] */ + read_from_file(${SRC} "/\\\\*[ \t]*RequiredFunctions:[ \t]*.*[ \t]*\\\\*/" REQUIRED_FUNCTIONS) + # Iterate through those lines + foreach(REQUIRED_FUNCTION ${REQUIRED_FUNCTIONS}) + # Strip off the /* RequiredFunctions: and */ from the line + string(REGEX REPLACE "/\\*[ \t]*RequiredFunctions:[ \t]*([^ \t]*)[ \t]*\\*/" "\\1" REQUIRED_FUNCTION ${REQUIRED_FUNCTION}) + # Replace all commas with semicolons + string(REGEX REPLACE "," ";" REQUIRED_FUNCTION ${REQUIRED_FUNCTION}) + # Iterate through the functions given + foreach(FUNCTION ${REQUIRED_FUNCTION}) + # Check if the function exists + check_function_exists(${REQUIRED_FUNCTION} HAVE_${REQUIRED_FUNCTION}) + # If we don't have the function warn the user and set SUCCESS to FALSE + if(NOT HAVE_${REQUIRED_FUNCTION}) + message("${SRC} needs function ${REQUIRED_FUNCTION} but we were unable to locate that function!") + set(${SUCCESS} FALSE) + endif(NOT HAVE_${REQUIRED_FUNCTION}) + endforeach(FUNCTION) + endforeach(REQUIRED_FUNCTION) +endmacro(check_functions) + +############################################################################### +# add_to_cpack_ignored_files( [TRUE]) +# +# A macro to update the environment variable CPACK_IGNORED_FILES which +# contains a list of files for CPack to ignore. If the optional 2nd argument +# of TRUE is given, periods will be converted to \\. for CPack. +############################################################################### +macro(add_to_cpack_ignored_files ITEM) + # Temporary copy of the orignal item + set(REAL_ITEM "${ITEM}") + # If we have 2+ arguments, assume that the second one was something like TRUE (doesn't matter really) and convert periods so they will be \\. for CPack + if(${ARGC} GREATER 1) + string(REPLACE "." "\\\\." REAL_ITEM ${REAL_ITEM}) + endif(${ARGC} GREATER 1) + # If the environment variable is already defined, just tack the item to the end + if(DEFINED ENV{CPACK_IGNORED_FILES}) + set(ENV{CPACK_IGNORED_FILES} "$ENV{CPACK_IGNORED_FILES};${REAL_ITEM}") + # Otherwise set the environment variable to the item + else(DEFINED ENV{CPACK_IGNORED_FILES}) + set(ENV{CPACK_IGNORED_FILES} "${REAL_ITEM}") + endif(DEFINED ENV{CPACK_IGNORED_FILES}) +endmacro(add_to_cpack_ignored_files) diff --git a/cmake/FindGettext.cmake b/cmake/FindGettext.cmake new file mode 100644 index 0000000..975294d --- /dev/null +++ b/cmake/FindGettext.cmake @@ -0,0 +1,26 @@ +# Find the header files, libs, and executables for gettext +if(NOT WIN32) + find_path(GETTEXT_INCLUDE libintl.h /usr/include /usr/local/include ${EXTRA_INCLUDE}) + find_library(GETTEXT_LIBRARY intl PATHS /usr/lib /usr/lib64 ${EXTRA_LIBS}) + find_program(GETTEXT_MSGFMT msgfmt PATHS /usr/bin/ /usr/local/bin ${EXTRA_INCLUDE}) + if(GETTEXT_INCLUDE AND GETTEXT_MSGFMT) + set(GETTEXT_FOUND TRUE) + if(GETTEXT_LIBRARY) + set(GETTEXT_LIBRARIES ${GETTEXT_LIBRARY}) + endif(GETTEXT_LIBRARY) + endif(GETTEXT_INCLUDE AND GETTEXT_MSGFMT) +else(NOT WIN32) + find_path(GETTEXT_INCLUDE libintl.h ${DEFAULT_INCLUDE_DIRS} ${WSDK_PATH}/include $ENV{VCINSTALLDIR}/include gettext/include ${EXTRA_INCLUDE}) + find_library(GETTEXT_LIBRARY libintl PATHS ${DEFAULT_LIBRARY_DIRS} ${WSDK_PATH}/lib $ENV{VCINSTALLDIR}/lib gettext/lib ${EXTRA_LIBS}) + find_program(GETTEXT_MSGFMT msgfmt PATHS ${DEFAULT_INCLUDE_DIRS} ${WSDK_PATH}/bin $ENV{VCINSTALLDIR}/bin gettext/bin ${EXTRA_INCLUDE}) + if(GETTEXT_INCLUDE AND GETTEXT_LIBRARY AND GETTEXT_MSGFMT) + set(GETTEXT_FOUND TRUE) + set(GETTEXT_LIBRARIES ${GETTEXT_LIBRARY}) + endif(GETTEXT_INCLUDE AND GETTEXT_LIBRARY AND GETTEXT_MSGFMT) +endif(NOT WIN32) + +# If we found everything we need set variables correctly for lang/CMakeLists.txt to use +if(GETTEXT_FOUND) + include_directories("${GETTEXT_INCLUDE}") + set(GETTEXT_MSGFMT_EXECUTABLE ${GETTEXT_MSGFMT}) +endif(GETTEXT_FOUND) diff --git a/cmake/NSIS.template.in b/cmake/NSIS.template.in new file mode 100644 index 0000000..1b0e06c --- /dev/null +++ b/cmake/NSIS.template.in @@ -0,0 +1,825 @@ +; CPack install script designed for a nmake build + +;-------------------------------- +; You must define these values + + !define VERSION "@CPACK_PACKAGE_VERSION@" + !define INST_DIR "@CPACK_TEMPORARY_DIRECTORY@" + +;-------------------------------- +;Variables + + Var MUI_TEMP + Var STARTMENU_FOLDER + Var SV_ALLUSERS + Var START_MENU + Var DO_NOT_ADD_TO_PATH + Var ADD_TO_PATH_ALL_USERS + Var ADD_TO_PATH_CURRENT_USER + Var INSTALL_DESKTOP + +;-------------------------------- +;Include Modern UI + + !include "MUI2.nsh" + + ;Default installation folder + InstallDir "$PROGRAMFILES\@CPACK_PACKAGE_INSTALL_DIRECTORY@" + +;-------------------------------- +;General + + ;Name and file + Name "@CPACK_PACKAGE_NAME@ @CPACK_PACKAGE_VERSION@" + OutFile "@CPACK_TOPLEVEL_DIRECTORY@/@CPACK_OUTPUT_FILE_NAME@" + + ;Set compression + SetCompressor @CPACK_NSIS_COMPRESSOR@ + +@CPACK_NSIS_DEFINES@ + + !include Sections.nsh + +;--- Component support macros: --- +; The code for the add/remove functionality is from: +; http://nsis.sourceforge.net/Add/Remove_Functionality +; It has been modified slightly and extended to provide +; inter-component dependencies. +Var AR_SecFlags +Var AR_RegFlags +@CPACK_NSIS_SECTION_SELECTED_VARS@ + +; Loads the "selected" flag for the section named SecName into the +; variable VarName. +!macro LoadSectionSelectedIntoVar SecName VarName + SectionGetFlags ${${SecName}} $${VarName} + IntOp $${VarName} $${VarName} & ${SF_SELECTED} ;Turn off all other bits +!macroend + +; Loads the value of a variable... can we get around this? +!macro LoadVar VarName + IntOp $R0 0 + $${VarName} +!macroend + +; Sets the value of a variable +!macro StoreVar VarName IntValue + IntOp $${VarName} 0 + ${IntValue} +!macroend + +!macro InitSection SecName + ; This macro reads component installed flag from the registry and + ;changes checked state of the section on the components page. + ;Input: section index constant name specified in Section command. + + ClearErrors + ;Reading component status from registry + ReadRegDWORD $AR_RegFlags HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\@CPACK_PACKAGE_NAME@\Components\${SecName}" "Installed" + IfErrors "default_${SecName}" + ;Status will stay default if registry value not found + ;(component was never installed) + IntOp $AR_RegFlags $AR_RegFlags & ${SF_SELECTED} ;Turn off all other bits + SectionGetFlags ${${SecName}} $AR_SecFlags ;Reading default section flags + IntOp $AR_SecFlags $AR_SecFlags & 0xFFFE ;Turn lowest (enabled) bit off + IntOp $AR_SecFlags $AR_RegFlags | $AR_SecFlags ;Change lowest bit + + ; Note whether this component was installed before + !insertmacro StoreVar ${SecName}_was_installed $AR_RegFlags + IntOp $R0 $AR_RegFlags & $AR_RegFlags + + ;Writing modified flags + SectionSetFlags ${${SecName}} $AR_SecFlags + + "default_${SecName}:" + !insertmacro LoadSectionSelectedIntoVar ${SecName} ${SecName}_selected +!macroend + +!macro FinishSection SecName + ; This macro reads section flag set by user and removes the section + ;if it is not selected. + ;Then it writes component installed flag to registry + ;Input: section index constant name specified in Section command. + + SectionGetFlags ${${SecName}} $AR_SecFlags ;Reading section flags + ;Checking lowest bit: + IntOp $AR_SecFlags $AR_SecFlags & ${SF_SELECTED} + IntCmp $AR_SecFlags 1 "leave_${SecName}" + ;Section is not selected: + ;Calling Section uninstall macro and writing zero installed flag + !insertmacro "Remove_${${SecName}}" + WriteRegDWORD HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\@CPACK_PACKAGE_NAME@\Components\${SecName}" \ + "Installed" 0 + Goto "exit_${SecName}" + + "leave_${SecName}:" + ;Section is selected: + WriteRegDWORD HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\@CPACK_PACKAGE_NAME@\Components\${SecName}" \ + "Installed" 1 + + "exit_${SecName}:" +!macroend + +!macro RemoveSection_CPack SecName + ; This macro is used to call section's Remove_... macro + ;from the uninstaller. + ;Input: section index constant name specified in Section command. + + !insertmacro "Remove_${${SecName}}" +!macroend + +; Determine whether the selection of SecName changed +!macro MaybeSelectionChanged SecName + !insertmacro LoadVar ${SecName}_selected + SectionGetFlags ${${SecName}} $R1 + IntOp $R1 $R1 & ${SF_SELECTED} ;Turn off all other bits + + ; See if the status has changed: + IntCmp $R0 $R1 "${SecName}_unchanged" + !insertmacro LoadSectionSelectedIntoVar ${SecName} ${SecName}_selected + + IntCmp $R1 ${SF_SELECTED} "${SecName}_was_selected" + !insertmacro "Deselect_required_by_${SecName}" + goto "${SecName}_unchanged" + + "${SecName}_was_selected:" + !insertmacro "Select_${SecName}_depends" + + "${SecName}_unchanged:" +!macroend +;--- End of Add/Remove macros --- + +;-------------------------------- +;Interface Settings + + !define MUI_ABORTWARNING + +;---------------------------------------- +; based upon a script of "Written by KiCHiK 2003-01-18 05:57:02" +;---------------------------------------- +!verbose 3 +!include "WinMessages.NSH" +!verbose 4 + +;==================================================== +; get_NT_environment +; Returns: the selected environment +; Output : head of the stack +;==================================================== +!macro select_NT_profile UN +Function ${UN}select_NT_profile + StrCmp $ADD_TO_PATH_ALL_USERS "1" 0 environment_single + DetailPrint "Selected environment for all users" + Push "all" + Return + environment_single: + DetailPrint "Selected environment for current user only." + Push "current" + Return +FunctionEnd +!macroend +!insertmacro select_NT_profile "" +!insertmacro select_NT_profile "un." +;---------------------------------------------------- +!define NT_current_env 'HKCU "Environment"' +!define NT_all_env 'HKLM "SYSTEM\CurrentControlSet\Control\Session Manager\Environment"' + +!ifndef WriteEnvStr_RegKey + !ifdef ALL_USERS + !define WriteEnvStr_RegKey \ + 'HKLM "SYSTEM\CurrentControlSet\Control\Session Manager\Environment"' + !else + !define WriteEnvStr_RegKey 'HKCU "Environment"' + !endif +!endif + +; AddToPath - Adds the given dir to the search path. +; Input - head of the stack +; Note - Win9x systems requires reboot + +Function AddToPath + Exch $0 + Push $1 + Push $2 + Push $3 + + # don't add if the path doesn't exist + IfFileExists "$0\*.*" "" AddToPath_done + + ReadEnvStr $1 PATH + Push "$1;" + Push "$0;" + Call StrStr + Pop $2 + StrCmp $2 "" "" AddToPath_done + Push "$1;" + Push "$0\;" + Call StrStr + Pop $2 + StrCmp $2 "" "" AddToPath_done + GetFullPathName /SHORT $3 $0 + Push "$1;" + Push "$3;" + Call StrStr + Pop $2 + StrCmp $2 "" "" AddToPath_done + Push "$1;" + Push "$3\;" + Call StrStr + Pop $2 + StrCmp $2 "" "" AddToPath_done + + Call IsNT + Pop $1 + StrCmp $1 1 AddToPath_NT + ; Not on NT + StrCpy $1 $WINDIR 2 + FileOpen $1 "$1\autoexec.bat" a + FileSeek $1 -1 END + FileReadByte $1 $2 + IntCmp $2 26 0 +2 +2 # DOS EOF + FileSeek $1 -1 END # write over EOF + FileWrite $1 "$\r$\nSET PATH=%PATH%;$3$\r$\n" + FileClose $1 + SetRebootFlag true + Goto AddToPath_done + + AddToPath_NT: + ReadRegStr $1 ${WriteEnvStr_RegKey} "PATH" + StrCmp $1 "" AddToPath_NTdoIt + Push $1 + Call Trim + Pop $1 + StrCpy $0 "$1;$0" + AddToPath_NTdoIt: + WriteRegExpandStr ${WriteEnvStr_RegKey} "PATH" $0 + SendMessage ${HWND_BROADCAST} ${WM_WININICHANGE} 0 "STR:Environment" /TIMEOUT=5000 + + AddToPath_done: + Pop $3 + Pop $2 + Pop $1 + Pop $0 +FunctionEnd + + +; RemoveFromPath - Remove a given dir from the path +; Input: head of the stack + +Function un.RemoveFromPath + Exch $0 + Push $1 + Push $2 + Push $3 + Push $4 + Push $5 + Push $6 + + IntFmt $6 "%c" 26 # DOS EOF + + Call un.IsNT + Pop $1 + StrCmp $1 1 unRemoveFromPath_NT + ; Not on NT + StrCpy $1 $WINDIR 2 + FileOpen $1 "$1\autoexec.bat" r + GetTempFileName $4 + FileOpen $2 $4 w + GetFullPathName /SHORT $0 $0 + StrCpy $0 "SET PATH=%PATH%;$0" + Goto unRemoveFromPath_dosLoop + + unRemoveFromPath_dosLoop: + FileRead $1 $3 + StrCpy $5 $3 1 -1 # read last char + StrCmp $5 $6 0 +2 # if DOS EOF + StrCpy $3 $3 -1 # remove DOS EOF so we can compare + StrCmp $3 "$0$\r$\n" unRemoveFromPath_dosLoopRemoveLine + StrCmp $3 "$0$\n" unRemoveFromPath_dosLoopRemoveLine + StrCmp $3 "$0" unRemoveFromPath_dosLoopRemoveLine + StrCmp $3 "" unRemoveFromPath_dosLoopEnd + FileWrite $2 $3 + Goto unRemoveFromPath_dosLoop + unRemoveFromPath_dosLoopRemoveLine: + SetRebootFlag true + Goto unRemoveFromPath_dosLoop + + unRemoveFromPath_dosLoopEnd: + FileClose $2 + FileClose $1 + StrCpy $1 $WINDIR 2 + Delete "$1\autoexec.bat" + CopyFiles /SILENT $4 "$1\autoexec.bat" + Delete $4 + Goto unRemoveFromPath_done + + unRemoveFromPath_NT: + ReadRegStr $1 ${WriteEnvStr_RegKey} "PATH" + StrCpy $5 $1 1 -1 # copy last char + StrCmp $5 ";" +2 # if last char != ; + StrCpy $1 "$1;" # append ; + Push $1 + Push "$0;" + Call un.StrStr ; Find `$0;` in $1 + Pop $2 ; pos of our dir + StrCmp $2 "" unRemoveFromPath_done + ; else, it is in path + # $0 - path to add + # $1 - path var + StrLen $3 "$0;" + StrLen $4 $2 + StrCpy $5 $1 -$4 # $5 is now the part before the path to remove + StrCpy $6 $2 "" $3 # $6 is now the part after the path to remove + StrCpy $3 $5$6 + + StrCpy $5 $3 1 -1 # copy last char + StrCmp $5 ";" 0 +2 # if last char == ; + StrCpy $3 $3 -1 # remove last char + + WriteRegExpandStr ${WriteEnvStr_RegKey} "PATH" $3 + SendMessage ${HWND_BROADCAST} ${WM_WININICHANGE} 0 "STR:Environment" /TIMEOUT=5000 + + unRemoveFromPath_done: + Pop $6 + Pop $5 + Pop $4 + Pop $3 + Pop $2 + Pop $1 + Pop $0 +FunctionEnd + +;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; +; Uninstall stuff +;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; + +########################################### +# Utility Functions # +########################################### + +;==================================================== +; IsNT - Returns 1 if the current system is NT, 0 +; otherwise. +; Output: head of the stack +;==================================================== +; IsNT +; no input +; output, top of the stack = 1 if NT or 0 if not +; +; Usage: +; Call IsNT +; Pop $R0 +; ($R0 at this point is 1 or 0) + +!macro IsNT un +Function ${un}IsNT + Push $0 + ReadRegStr $0 HKLM "SOFTWARE\Microsoft\Windows NT\CurrentVersion" CurrentVersion + StrCmp $0 "" 0 IsNT_yes + ; we are not NT. + Pop $0 + Push 0 + Return + + IsNT_yes: + ; NT!!! + Pop $0 + Push 1 +FunctionEnd +!macroend +!insertmacro IsNT "" +!insertmacro IsNT "un." + +; StrStr +; input, top of stack = string to search for +; top of stack-1 = string to search in +; output, top of stack (replaces with the portion of the string remaining) +; modifies no other variables. +; +; Usage: +; Push "this is a long ass string" +; Push "ass" +; Call StrStr +; Pop $R0 +; ($R0 at this point is "ass string") + +!macro StrStr un +Function ${un}StrStr +Exch $R1 ; st=haystack,old$R1, $R1=needle + Exch ; st=old$R1,haystack + Exch $R2 ; st=old$R1,old$R2, $R2=haystack + Push $R3 + Push $R4 + Push $R5 + StrLen $R3 $R1 + StrCpy $R4 0 + ; $R1=needle + ; $R2=haystack + ; $R3=len(needle) + ; $R4=cnt + ; $R5=tmp + loop: + StrCpy $R5 $R2 $R3 $R4 + StrCmp $R5 $R1 done + StrCmp $R5 "" done + IntOp $R4 $R4 + 1 + Goto loop +done: + StrCpy $R1 $R2 "" $R4 + Pop $R5 + Pop $R4 + Pop $R3 + Pop $R2 + Exch $R1 +FunctionEnd +!macroend +!insertmacro StrStr "" +!insertmacro StrStr "un." + +Function Trim ; Added by Pelaca + Exch $R1 + Push $R2 +Loop: + StrCpy $R2 "$R1" 1 -1 + StrCmp "$R2" " " RTrim + StrCmp "$R2" "$\n" RTrim + StrCmp "$R2" "$\r" RTrim + StrCmp "$R2" ";" RTrim + GoTo Done +RTrim: + StrCpy $R1 "$R1" -1 + Goto Loop +Done: + Pop $R2 + Exch $R1 +FunctionEnd + +Function ConditionalAddToRegistry + Pop $0 + Pop $1 + StrCmp "$0" "" ConditionalAddToRegistry_EmptyString + WriteRegStr SHCTX "Software\Microsoft\Windows\CurrentVersion\Uninstall\@CPACK_PACKAGE_NAME@" \ + "$1" "$0" + ;MessageBox MB_OK "Set Registry: '$1' to '$0'" + DetailPrint "Set install registry entry: '$1' to '$0'" + ConditionalAddToRegistry_EmptyString: +FunctionEnd + +;-------------------------------- + +!ifdef CPACK_USES_DOWNLOAD +Function DownloadFile + IfFileExists $INSTDIR\* +2 + CreateDirectory $INSTDIR + Pop $0 + + ; Skip if already downloaded + IfFileExists $INSTDIR\$0 0 +2 + Return + + StrCpy $1 "@CPACK_DOWNLOAD_SITE@" + + try_again: + NSISdl::download "$1/$0" "$INSTDIR\$0" + + Pop $1 + StrCmp $1 "success" success + StrCmp $1 "Cancelled" cancel + MessageBox MB_OK "Download failed: $1" + cancel: + Return + success: +FunctionEnd +!endif + +;-------------------------------- +; Installation types +@CPACK_NSIS_INSTALLATION_TYPES@ + +;-------------------------------- +; Component sections +@CPACK_NSIS_COMPONENT_SECTIONS@ + +;-------------------------------- +; Define some macro setting for the gui +@CPACK_NSIS_INSTALLER_MUI_ICON_CODE@ +@CPACK_NSIS_INSTALLER_ICON_CODE@ +@CPACK_NSIS_INSTALLER_MUI_COMPONENTS_DESC@ + +;-------------------------------- +;Pages + !define MUI_LANGDLL_REGISTRY_ROOT "SHCTX" + !define MUI_LANGDLL_REGISTRY_KEY "Software\Microsoft\Windows\CurrentVersion\Uninstall\@CPACK_PACKAGE_NAME@" + !define MUI_LANGDLL_REGISTRY_VALUENAME "NSIS:Language" + + !insertmacro MUI_PAGE_WELCOME + + !insertmacro MUI_PAGE_LICENSE "@CPACK_RESOURCE_FILE_LICENSE@" + !insertmacro MUI_PAGE_DIRECTORY + + ;Start Menu Folder Page Configuration + !define MUI_STARTMENUPAGE_REGISTRY_ROOT "SHCTX" + !define MUI_STARTMENUPAGE_REGISTRY_KEY "Software\@CPACK_PACKAGE_VENDOR@\@CPACK_PACKAGE_INSTALL_REGISTRY_KEY@" + !define MUI_STARTMENUPAGE_REGISTRY_VALUENAME "Start Menu Folder" + !insertmacro MUI_PAGE_STARTMENU Application $STARTMENU_FOLDER + + @CPACK_NSIS_PAGE_COMPONENTS@ + + !insertmacro MUI_PAGE_INSTFILES + + !define MUI_FINISHPAGE_SHOWREADME "$INSTDIR\doc\README.txt" + !insertmacro MUI_PAGE_FINISH + + !insertmacro MUI_UNPAGE_CONFIRM + !insertmacro MUI_UNPAGE_INSTFILES + +;-------------------------------- +;Languages + + !insertmacro MUI_LANGUAGE "Dutch" + !insertmacro MUI_LANGUAGE "English" + !insertmacro MUI_LANGUAGE "French" + !insertmacro MUI_LANGUAGE "German" + !insertmacro MUI_LANGUAGE "Italian" + !insertmacro MUI_LANGUAGE "Portuguese" + !insertmacro MUI_LANGUAGE "Spanish" + +;-------------------------------- +;Installer Sections + +Section "-Core installation" + ;Use the entire tree produced by the INSTALL target. Keep the + ;list of directories here in sync with the RMDir commands below. + SetOutPath "$INSTDIR" + @CPACK_NSIS_FULL_INSTALL@ + + ;Store installation folder + WriteRegStr SHCTX "Software\@CPACK_PACKAGE_VENDOR@\@CPACK_PACKAGE_INSTALL_REGISTRY_KEY@" "" $INSTDIR + + ;Create uninstaller + WriteUninstaller "$INSTDIR\Uninstall.exe" + Push "DisplayName" + Push "@CPACK_NSIS_DISPLAY_NAME@" + Call ConditionalAddToRegistry + Push "DisplayVersion" + Push "@CPACK_PACKAGE_VERSION@" + Call ConditionalAddToRegistry + Push "Publisher" + Push "@CPACK_PACKAGE_VENDOR@" + Call ConditionalAddToRegistry + Push "UninstallString" + Push "$INSTDIR\Uninstall.exe" + Call ConditionalAddToRegistry + Push "NoRepair" + Push "1" + Call ConditionalAddToRegistry + + !ifdef CPACK_NSIS_ADD_REMOVE + ;Create add/remove functionality + Push "ModifyPath" + Push "$INSTDIR\AddRemove.exe" + Call ConditionalAddToRegistry + !else + Push "NoModify" + Push "1" + Call ConditionalAddToRegistry + !endif + + ; Optional registration + Push "DisplayIcon" + Push "$INSTDIR\@CPACK_NSIS_INSTALLED_ICON_NAME@" + Call ConditionalAddToRegistry + Push "HelpLink" + Push "@CPACK_NSIS_HELP_LINK@" + Call ConditionalAddToRegistry + Push "URLInfoAbout" + Push "@CPACK_NSIS_URL_INFO_ABOUT@" + Call ConditionalAddToRegistry + Push "Contact" + Push "@CPACK_NSIS_CONTACT@" + Call ConditionalAddToRegistry + !insertmacro MUI_STARTMENU_WRITE_BEGIN Application + + ;Create shortcuts + CreateDirectory "$SMPROGRAMS\$STARTMENU_FOLDER" +@CPACK_NSIS_CREATE_ICONS@ +@CPACK_NSIS_CREATE_ICONS_EXTRA@ + CreateShortCut "$SMPROGRAMS\$STARTMENU_FOLDER\Uninstall.lnk" "$INSTDIR\Uninstall.exe" + + ; Write special uninstall registry entries + Push "StartMenu" + Push "$STARTMENU_FOLDER" + Call ConditionalAddToRegistry + Push "DoNotAddToPath" + Push "$DO_NOT_ADD_TO_PATH" + Call ConditionalAddToRegistry + Push "AddToPathAllUsers" + Push "$ADD_TO_PATH_ALL_USERS" + Call ConditionalAddToRegistry + Push "AddToPathCurrentUser" + Push "$ADD_TO_PATH_CURRENT_USER" + Call ConditionalAddToRegistry + Push "InstallToDesktop" + Push "$INSTALL_DESKTOP" + Call ConditionalAddToRegistry + +@CPACK_NSIS_EXTRA_INSTALL_COMMANDS@ + + !insertmacro MUI_STARTMENU_WRITE_END + +SectionEnd + +;-------------------------------- +; determine admin versus local install +Function un.onInit + + ClearErrors + UserInfo::GetName + IfErrors noLM + Pop $0 + UserInfo::GetAccountType + Pop $1 + StrCmp $1 "Admin" 0 +3 + SetShellVarContext all + ;MessageBox MB_OK 'User "$0" is in the Admin group' + Goto done + StrCmp $1 "Power" 0 +3 + SetShellVarContext all + ;MessageBox MB_OK 'User "$0" is in the Power Users group' + Goto done + + noLM: + ;Get installation folder from registry if available + + done: + + !insertmacro MUI_UNGETLANGUAGE +FunctionEnd + +;--- Add/Remove callback functions: --- +!macro SectionList MacroName + ;This macro used to perform operation on multiple sections. + ;List all of your components in following manner here. +@CPACK_NSIS_COMPONENT_SECTION_LIST@ +!macroend + +Section -FinishComponents + ;Removes unselected components and writes component status to registry + !insertmacro SectionList "FinishSection" + +!ifdef CPACK_NSIS_ADD_REMOVE + ; Get the name of the installer executable + System::Call 'kernel32::GetModuleFileNameA(i 0, t .R0, i 1024) i r1' + StrCpy $R3 $R0 + + ; Strip off the last 13 characters, to see if we have AddRemove.exe + StrLen $R1 $R0 + IntOp $R1 $R0 - 13 + StrCpy $R2 $R0 13 $R1 + StrCmp $R2 "AddRemove.exe" addremove_installed + + ; We're not running AddRemove.exe, so install it + CopyFiles $R3 $INSTDIR\AddRemove.exe + + addremove_installed: +!endif +SectionEnd +;--- End of Add/Remove callback functions --- + +;-------------------------------- +; Component dependencies +Function .onSelChange + !insertmacro SectionList MaybeSelectionChanged +FunctionEnd + +;-------------------------------- +;Uninstaller Section + +Section "Uninstall" + ReadRegStr $START_MENU SHCTX \ + "Software\Microsoft\Windows\CurrentVersion\Uninstall\@CPACK_PACKAGE_NAME@" "StartMenu" + ;MessageBox MB_OK "Start menu is in: $START_MENU" + ReadRegStr $DO_NOT_ADD_TO_PATH SHCTX \ + "Software\Microsoft\Windows\CurrentVersion\Uninstall\@CPACK_PACKAGE_NAME@" "DoNotAddToPath" + ReadRegStr $ADD_TO_PATH_ALL_USERS SHCTX \ + "Software\Microsoft\Windows\CurrentVersion\Uninstall\@CPACK_PACKAGE_NAME@" "AddToPathAllUsers" + ReadRegStr $ADD_TO_PATH_CURRENT_USER SHCTX \ + "Software\Microsoft\Windows\CurrentVersion\Uninstall\@CPACK_PACKAGE_NAME@" "AddToPathCurrentUser" + ;MessageBox MB_OK "Add to path: $DO_NOT_ADD_TO_PATH all users: $ADD_TO_PATH_ALL_USERS" + ReadRegStr $INSTALL_DESKTOP SHCTX \ + "Software\Microsoft\Windows\CurrentVersion\Uninstall\@CPACK_PACKAGE_NAME@" "InstallToDesktop" + ;MessageBox MB_OK "Install to desktop: $INSTALL_DESKTOP " + +@CPACK_NSIS_EXTRA_UNINSTALL_COMMANDS@ + + ;Remove files we installed. + ;Keep the list of directories here in sync with the File commands above. +@CPACK_NSIS_DELETE_FILES@ +@CPACK_NSIS_DELETE_DIRECTORIES@ + +!ifdef CPACK_NSIS_ADD_REMOVE + ;Remove the add/remove program + Delete "$INSTDIR\AddRemove.exe" +!endif + + ;Remove the uninstaller itself. + Delete "$INSTDIR\Uninstall.exe" + DeleteRegKey SHCTX "Software\Microsoft\Windows\CurrentVersion\Uninstall\@CPACK_PACKAGE_NAME@" + + ;Remove the installation directory if it is empty. + RMDir "$INSTDIR" + + ; Remove the registry entries. + DeleteRegKey SHCTX "Software\@CPACK_PACKAGE_VENDOR@\@CPACK_PACKAGE_INSTALL_REGISTRY_KEY@" + + ; Removes all optional components + !insertmacro SectionList "RemoveSection_CPack" + + !insertmacro MUI_STARTMENU_GETFOLDER Application $MUI_TEMP + + Delete "$SMPROGRAMS\$MUI_TEMP\Uninstall.lnk" +@CPACK_NSIS_DELETE_ICONS@ +@CPACK_NSIS_DELETE_ICONS_EXTRA@ + + ;Delete empty start menu parent directories + StrCpy $MUI_TEMP "$SMPROGRAMS\$MUI_TEMP" + + startMenuDeleteLoop: + ClearErrors + RMDir $MUI_TEMP + GetFullPathName $MUI_TEMP "$MUI_TEMP\.." + + IfErrors startMenuDeleteLoopDone + + StrCmp "$MUI_TEMP" "$SMPROGRAMS" startMenuDeleteLoopDone startMenuDeleteLoop + startMenuDeleteLoopDone: + + ; If the user changed the shortcut, then uninstall may not work. This should + ; try to fix it. + StrCpy $MUI_TEMP "$START_MENU" + Delete "$SMPROGRAMS\$MUI_TEMP\Uninstall.lnk" +@CPACK_NSIS_DELETE_ICONS_EXTRA@ + + ;Delete empty start menu parent directories + StrCpy $MUI_TEMP "$SMPROGRAMS\$MUI_TEMP" + + secondStartMenuDeleteLoop: + ClearErrors + RMDir $MUI_TEMP + GetFullPathName $MUI_TEMP "$MUI_TEMP\.." + + IfErrors secondStartMenuDeleteLoopDone + + StrCmp "$MUI_TEMP" "$SMPROGRAMS" secondStartMenuDeleteLoopDone secondStartMenuDeleteLoop + secondStartMenuDeleteLoopDone: + + DeleteRegKey /ifempty SHCTX "Software\@CPACK_PACKAGE_VENDOR@\@CPACK_PACKAGE_INSTALL_REGISTRY_KEY@" + + Push $INSTDIR\bin + StrCmp $DO_NOT_ADD_TO_PATH_ "1" doNotRemoveFromPath 0 + Call un.RemoveFromPath + doNotRemoveFromPath: +SectionEnd + +;-------------------------------- +; determine admin versus local install +; Is install for "AllUsers" or "JustMe"? +; Default to "JustMe" - set to "AllUsers" if admin or on Win9x +; This function is used for the very first "custom page" of the installer. +; This custom page does not show up visibly, but it executes prior to the +; first visible page and sets up $INSTDIR properly... +; Choose different default installation folder based on SV_ALLUSERS... +; "Program Files" for AllUsers, "My Documents" for JustMe... + +Function .onInit + !insertmacro MUI_LANGDLL_DISPLAY + ; Reads components status for registry + !insertmacro SectionList "InitSection" + + StrCpy $SV_ALLUSERS "JustMe" + StrCpy $INSTDIR "$DOCUMENTS\@CPACK_PACKAGE_INSTALL_DIRECTORY@" + + ClearErrors + UserInfo::GetName + IfErrors noLM + Pop $0 + UserInfo::GetAccountType + Pop $1 + StrCmp $1 "Admin" 0 +3 + SetShellVarContext all + ;MessageBox MB_OK 'User "$0" is in the Admin group' + StrCpy $SV_ALLUSERS "AllUsers" + Goto done + StrCmp $1 "Power" 0 +3 + SetShellVarContext all + ;MessageBox MB_OK 'User "$0" is in the Power Users group' + StrCpy $SV_ALLUSERS "AllUsers" + Goto done + + noLM: + StrCpy $SV_ALLUSERS "AllUsers" + ;Get installation folder from registry if available + + done: + StrCmp $SV_ALLUSERS "AllUsers" 0 +2 + StrCpy $INSTDIR "$PROGRAMFILES\@CPACK_PACKAGE_INSTALL_DIRECTORY@" + +FunctionEnd diff --git a/cmake/ReadFile.cmake b/cmake/ReadFile.cmake new file mode 100644 index 0000000..be60f1f --- /dev/null +++ b/cmake/ReadFile.cmake @@ -0,0 +1,5 @@ +# This file is external to the read_from_file macro in Anope.cmake in order to +# get around a possible memory leak in older versions of CMake. + +file(READ "${FILE}" RESULT) +message("${RESULT}") diff --git a/data/CMakeLists.txt b/data/CMakeLists.txt new file mode 100644 index 0000000..a021558 --- /dev/null +++ b/data/CMakeLists.txt @@ -0,0 +1,4 @@ +set(DATA botserv.conf chanserv.conf global.conf hostserv.conf nickserv.conf operserv.conf services.conf) +install(FILES ${DATA} + DESTINATION ${CONF_DIR} +) diff --git a/data/botserv.conf b/data/botserv.conf new file mode 100644 index 0000000..3f4822d --- /dev/null +++ b/data/botserv.conf @@ -0,0 +1,132 @@ +service { + nick = "BotServ" + user = "services" + host = "services.host" + gecos = "Bot Service" + #channels = "@#services,#mychan" +} + +module { + name = "botserv" + client = "BotServ" + defaults = "dontkickops fantasy greet" + minusers = 1 + botmodes = "o" +} + +command { service = "BotServ"; name = "HELP"; command = "generic/help"; } + +module { name = "bs_assign" } +command { service = "BotServ"; name = "ASSIGN"; command = "botserv/assign"; } +command { service = "BotServ"; name = "UNASSIGN"; command = "botserv/unassign"; } +command { service = "BotServ"; name = "SET NOBOT"; command = "botserv/set/nobot"; permission = "botserv/set/nobot"; } + +module { + name = "bs_autoassign" + bot = "ChanServ" +} + +module { + name = "bs_badwords" + badwordsmax = 32 +} +command { service = "BotServ"; name = "BADWORDS"; command = "botserv/badwords"; } + +module { name = "bs_bot" } +command { service = "BotServ"; name = "BOT"; command = "botserv/bot"; permission = "botserv/bot"; } + +module { name = "bs_botlist" } +command { service = "BotServ"; name = "BOTLIST"; command = "botserv/botlist"; } + +module { name = "bs_control" } +command { service = "BotServ"; name = "ACT"; command = "botserv/act"; } +command { service = "BotServ"; name = "SAY"; command = "botserv/say"; } + +module { name = "bs_info" } +command { service = "BotServ"; name = "INFO"; command = "botserv/info"; } + +module { + name = "bs_kick" + keepdata = 10m + gentlebadwordreason = yes +} +command { service = "BotServ"; name = "KICK"; command = "botserv/kick"; } +command { service = "BotServ"; name = "KICK AMSG"; command = "botserv/kick/amsg"; } +command { service = "BotServ"; name = "KICK BADWORDS"; command = "botserv/kick/badwords"; } +command { service = "BotServ"; name = "KICK BOLDS"; command = "botserv/kick/bolds"; } +command { service = "BotServ"; name = "KICK CAPS"; command = "botserv/kick/caps"; } +command { service = "BotServ"; name = "KICK COLORS"; command = "botserv/kick/colors"; } +command { service = "BotServ"; name = "KICK FLOOD"; command = "botserv/kick/flood"; } +command { service = "BotServ"; name = "KICK ITALICS"; command = "botserv/kick/italics"; } +command { service = "BotServ"; name = "KICK REPEAT"; command = "botserv/kick/repeat"; } +command { service = "BotServ"; name = "KICK REVERSES"; command = "botserv/kick/reverses"; } +command { service = "BotServ"; name = "KICK UNDERLINES"; command = "botserv/kick/underlines"; } + +command { service = "BotServ"; name = "SET DONTKICKOPS"; command = "botserv/set/dontkickops"; } +command { service = "BotServ"; name = "SET DONTKICKVOICES"; command = "botserv/set/dontkickvoices"; } + +module { name = "bs_set" } +command { service = "BotServ"; name = "SET"; command = "botserv/set"; } +command { service = "BotServ"; name = "SET BANEXPIRE"; command = "botserv/set/banexpire"; } +command { service = "BotServ"; name = "SET PRIVATE"; command = "botserv/set/private"; permission = "botserv/set/private"; } + +module { name = "greet" } +command { service = "BotServ"; name = "SET GREET"; command = "botserv/set/greet"; } +command { service = "NickServ"; name = "SET GREET"; command = "nickserv/set/greet"; } +command { service = "NickServ"; name = "SASET GREET"; command = "nickserv/saset/greet"; permission = "nickserv/saset/greet"; } + +privilege { + name = "GREET" + rank = 40 + level = 5 + flag = "g" + xop = "AOP" +} + +module { + name = "fantasy" +} +command { service = "BotServ"; name = "SET FANTASY"; command = "botserv/set/fantasy"; } + +fantasy { name = "ACCESS"; command = "chanserv/access"; } +fantasy { name = "AKICK"; command = "chanserv/akick"; } +fantasy { name = "AOP"; command = "chanserv/xop"; } +fantasy { name = "BAN"; command = "chanserv/ban"; } +fantasy { name = "CLONE"; command = "chanserv/clone"; } +fantasy { name = "DEHALFOP"; command = "chanserv/modes"; } +fantasy { name = "DEOP"; command = "chanserv/modes"; } +fantasy { name = "DEOWNER"; command = "chanserv/modes"; } +fantasy { name = "DEPROTECT"; command = "chanserv/modes"; } +fantasy { name = "DEVOICE"; command = "chanserv/modes"; } +fantasy { name = "DOWN"; command = "chanserv/down"; } +fantasy { name = "ENFORCE"; command = "chanserv/enforce"; } +fantasy { name = "ENTRYMSG"; command = "chanserv/entrymsg"; } +fantasy { name = "FLAGS"; command = "chanserv/flags"; } +fantasy { name = "HALFOP"; command = "chanserv/modes"; } +fantasy { name = "HELP"; command = "generic/help"; prepend_channel = false; } +fantasy { name = "HOP"; command = "chanserv/xop"; } +fantasy { name = "INFO"; command = "chanserv/info"; prepend_channel = false; } +fantasy { name = "INVITE"; command = "chanserv/invite"; } +fantasy { name = "K"; command = "chanserv/kick"; } +fantasy { name = "KB"; command = "chanserv/ban"; } +fantasy { name = "KICK"; command = "chanserv/kick"; } +fantasy { name = "LEVELS"; command = "chanserv/levels"; } +fantasy { name = "LIST"; command = "chanserv/list"; prepend_channel = false; } +fantasy { name = "LOG"; command = "chanserv/log"; } +fantasy { name = "MODE"; command = "chanserv/mode"; } +fantasy { name = "MUTE"; command = "chanserv/ban"; kick = no; mode = "QUIET"; } +fantasy { name = "OP"; command = "chanserv/modes"; } +fantasy { name = "OWNER"; command = "chanserv/modes"; } +fantasy { name = "PROTECT"; command = "chanserv/modes"; } +fantasy { name = "QOP"; command = "chanserv/xop"; } +fantasy { name = "SEEN"; command = "chanserv/seen"; prepend_channel = false; } +fantasy { name = "SOP"; command = "chanserv/xop"; } +fantasy { name = "STATUS"; command = "chanserv/status"; } +fantasy { name = "SUSPEND"; command = "chanserv/suspend"; permission = "chanserv/suspend"; } +fantasy { name = "SYNC"; command = "chanserv/sync"; } +fantasy { name = "TOPIC"; command = "chanserv/topic"; } +fantasy { name = "UNBAN"; command = "chanserv/unban"; } +fantasy { name = "UNSUSPEND"; command = "chanserv/unsuspend"; permission = "chanserv/suspend"; } +fantasy { name = "UP"; command = "chanserv/up"; } +fantasy { name = "VOICE"; command = "chanserv/modes"; } +fantasy { name = "VOP"; command = "chanserv/xop"; } \ No newline at end of file diff --git a/data/chanserv.conf b/data/chanserv.conf new file mode 100644 index 0000000..31bfa8b --- /dev/null +++ b/data/chanserv.conf @@ -0,0 +1,472 @@ +service { + nick = "ChanServ" + user = "services" + host = "services.host" + gecos = "Channel Registration Service" + #channels = "@#services,#mychan" +} + +module { + name = "chanserv" + client = "ChanServ" + defaults = "keeptopic peace cs_secure secureops securefounder cs_keep_modes" + maxregistered = 5 + expire = 7d + accessmax = 100 + inhabit = 15s + nomlock = "CnLpPs" + reasonmax = 100 + signkickformat = "%m (%n)" + disallow_hostmask_access = true + disallow_channel_access = true + always_lower_ts = false +} + +privilege { + name = "ACCESS_CHANGE" + rank = 360 # 0 ? + level = 10000 # 10 ? + flag = "f" + xop = "QOP" # SOP? +} + +privilege { + name = "ACCESS_LIST" + rank = 10 + level = 3 + flag = "f" + xop = "VOP" +} + +privilege { + name = "AKICK" + rank = 250 + level = 10 + flag = "K" + xop = "SOP" +} + +privilege { + name = "ASSIGN" + rank = 270 + level = "founder" + flag = "s" + xop = "QOP" +} + +privilege { + name = "AUTOHALFOP" + rank = 100 + level = 4 + flag = "H" + xop = "HOP" +} + +privilege { + name = "AUTOOP" + rank = 210 + level = 5 + flag = "O" + xop = "AOP" +} + +privilege { + name = "AUTOOWNER" + rank = 330 + level = 9999 + flag = "Q" + xop = "QOP" +} + +privilege { + name = "AUTOPROTECT" + rank = 240 + level = 10 + flag = "A" + xop = "SOP" +} + +privilege { + name = "AUTOVOICE" + rank = 50 + level = 3 + flag = "V" + xop = "VOP" +} + +privilege { + name = "BADWORDS" + rank = 260 + level = 10 + flag = "K" + xop = "SOP" +} + +privilege { + name = "BAN" + rank = 150 + level = 4 + flag = "b" + xop = "HOP" +} + +privilege { + name = "FANTASIA" + rank = 30 + level = 3 + flag = "c" + xop = "VOP" +} + +privilege { + name = "FOUNDER" + rank = 360 + level = 10000 + flag = "F" + xop = "QOP" +} + +privilege { + name = "GETKEY" + rank = 180 + level = 5 + flag = "G" + xop = "AOP" +} + +privilege { + name = "HALFOP" + rank = 120 + level = 5 + flag = "h" + xop = "AOP" +} + +privilege { + name = "HALFOPME" + rank = 110 + level = 4 + flag = "h" + xop = "HOP" +} + +privilege { + name = "INFO" + rank = 80 + level = 9999 + flag = "I" + xop = "QOP" +} + +privilege { + name = "INVITE" + rank = 190 + level = 5 + flag = "i" + xop = "AOP" +} + +privilege { + name = "KICK" + rank = 130 + level = 4 + flag = "k" + xop = "HOP" +} + +privilege { + name = "MEMO" + rank = 280 + level = 10 + flag = "m" + xop = "SOP" +} + +privilege { + name = "MODE" + rank = 170 + level = 9999 + flag = "s" + xop = "QOP" +} + +privilege { + name = "NOKICK" + rank = 20 + level = 1 + flag = "N" + xop = "VOP" +} + +privilege { + name = "OP" + rank = 230 + level = 5 + flag = "o" + xop = "SOP" +} + +privilege { + name = "OPME" + rank = 220 + level = 5 + flag = "o" + xop = "AOP" +} + +privilege { + name = "OWNER" + rank = 350 + level = "founder" + flag = "q" + xop = "QOP" +} + +privilege { + name = "OWNERME" + rank = 340 + level = 9999 + flag = "q" + xop = "QOP" +} + +privilege { + name = "PROTECT" + rank = 310 + level = 9999 + flag = "a" + xop = "QOP" +} + +privilege { + name = "PROTECTME" + rank = 300 + level = 10 + flag = "a" + xop = "SOP" +} + +privilege { + name = "SAY" + rank = 90 + level = 5 + flag = "B" + xop = "AOP" +} + +privilege { + name = "SET" + rank = 320 + level = 9999 + flag = "s" + xop = "QOP" +} + +privilege { + name = "SIGNKICK" + rank = 140 + level = 9999 + flag = "K" + xop = "QOP" +} + +privilege { + name = "TOPIC" + rank = 160 + level = 5 + flag = "t" + xop = "AOP" +} + +privilege { + name = "UNBAN" + rank = 200 + level = 4 + flag = "u" + xop = "HOP" +} + +privilege { + name = "VOICE" + rank = 70 + level = 4 + flag = "v" + xop = "HOP" +} + +privilege { + name = "VOICEME" + rank = 60 + level = 3 + flag = "v" + xop = "VOP" +} + +command_group { + name = "chanserv/access" + description = _("Used to manage the list of privileged users") +} + +command_group { + name = "chanserv/status" + description = _("Used to modify the channel status of you or other users") +} + +command_group { + name = "chanserv/management" + description = _("Used to manage channels") +} + +command_group { + name = "chanserv/admin" + description = _("Services Operator commands") +} + +command { service = "ChanServ"; name = "HELP"; command = "generic/help"; } + +module { + name = "cs_akick" + autokickmax = 32 + autokickreason = "8,4 E N T E R T H E V O I D " + +} +command { service = "ChanServ"; name = "AKICK"; command = "chanserv/akick"; group = "chanserv/management"; } + +module { name = "cs_ban" } +command { service = "ChanServ"; name = "BAN"; command = "chanserv/ban"; } + +module { name = "cs_clone" } +command { service = "ChanServ"; name = "CLONE"; command = "chanserv/clone"; group = "chanserv/management"; } + +module { name = "cs_drop" } +command { service = "ChanServ"; name = "DROP"; command = "chanserv/drop"; } + +module { name = "cs_enforce" } +command { service = "ChanServ"; name = "ENFORCE"; command = "chanserv/enforce"; group = "chanserv/management"; } + +module { + name = "cs_entrymsg" + maxentries = 5 +} +command { service = "ChanServ"; name = "ENTRYMSG"; command = "chanserv/entrymsg"; group = "chanserv/management"; } + +module { name = "cs_flags" } +command { service = "ChanServ"; name = "FLAGS"; command = "chanserv/flags"; group = "chanserv/access"; } + +#module { name = "cs_getkey" } +#command { service = "ChanServ"; name = "GETKEY"; command = "chanserv/getkey"; } + +module { name = "cs_info" } +command { service = "ChanServ"; name = "INFO"; command = "chanserv/info"; } + +module { name = "cs_invite" } +command { service = "ChanServ"; name = "INVITE"; command = "chanserv/invite"; } + +module { name = "cs_kick" } +command { service = "ChanServ"; name = "KICK"; command = "chanserv/kick"; } + +module { + name = "cs_list" + listmax = 50 +} +command { service = "ChanServ"; name = "LIST"; command = "chanserv/list"; } + +command { service = "ChanServ"; name = "SET PRIVATE"; command = "chanserv/set/private"; } + + +module { + name = "cs_log" +} +command { service = "ChanServ"; name = "LOG"; command = "chanserv/log"; group = "chanserv/management"; } + +module { + name = "cs_mode" + mlock = "+nst" + max = 100 +} +command { service = "ChanServ"; name = "MODE"; command = "chanserv/mode"; group = "chanserv/management"; } + +command { service = "ChanServ"; name = "OWNER"; command = "chanserv/modes"; group = "chanserv/status"; set = "OWNER" } +command { service = "ChanServ"; name = "DEOWNER"; command = "chanserv/modes"; group = "chanserv/status"; unset = "OWNER" } + +command { service = "ChanServ"; name = "PROTECT"; command = "chanserv/modes"; group = "chanserv/status"; set = "PROTECT" } +command { service = "ChanServ"; name = "DEPROTECT"; command = "chanserv/modes"; group = "chanserv/status"; unset = "PROTECT" } + +command { service = "ChanServ"; name = "OP"; command = "chanserv/modes"; group = "chanserv/status"; set = "OP" } +command { service = "ChanServ"; name = "DEOP"; command = "chanserv/modes"; group = "chanserv/status"; unset = "OP" } + +command { service = "ChanServ"; name = "HALFOP"; command = "chanserv/modes"; group = "chanserv/status"; set = "HALFOP" } +command { service = "ChanServ"; name = "DEHALFOP"; command = "chanserv/modes"; group = "chanserv/status"; unset = "HALFOP" } + +command { service = "ChanServ"; name = "VOICE"; command = "chanserv/modes"; group = "chanserv/status"; set = "VOICE" } +command { service = "ChanServ"; name = "DEVOICE"; command = "chanserv/modes"; group = "chanserv/status"; unset = "VOICE" } + +module { name = "cs_register" } +command { service = "ChanServ"; name = "REGISTER"; command = "chanserv/register"; } + +module { + name = "cs_seen" + simple = false + purgetime = "30d" +} +command { service = "OperServ"; name = "SEEN"; command = "operserv/seen"; permission = "operserv/seen"; } + +module { + name = "cs_set" + defbantype = 2 + persist_lower_ts = true +} +command { service = "ChanServ"; name = "SET"; command = "chanserv/set"; group = "chanserv/management"; } +command { service = "ChanServ"; name = "SET AUTOOP"; command = "chanserv/set/autoop"; } +command { service = "ChanServ"; name = "SET BANTYPE"; command = "chanserv/set/bantype"; } +command { service = "ChanServ"; name = "SET DESCRIPTION"; command = "chanserv/set/description"; } +command { service = "ChanServ"; name = "SET DESC"; command = "chanserv/set/description"; hide = yes; } +command { service = "ChanServ"; name = "SET FOUNDER"; command = "chanserv/set/founder"; } +command { service = "ChanServ"; name = "SET KEEPMODES"; command = "chanserv/set/keepmodes"; } +command { service = "ChanServ"; name = "SET PEACE"; command = "chanserv/set/peace"; } +command { service = "ChanServ"; name = "SET PERSIST"; command = "chanserv/set/persist"; } +command { service = "ChanServ"; name = "SET RESTRICTED"; command = "chanserv/set/restricted"; } +command { service = "ChanServ"; name = "SET SECURE"; command = "chanserv/set/secure"; } +command { service = "ChanServ"; name = "SET SECUREFOUNDER"; command = "chanserv/set/securefounder"; } +command { service = "ChanServ"; name = "SET SECUREOPS"; command = "chanserv/set/secureops"; } +command { service = "ChanServ"; name = "SET SIGNKICK"; command = "chanserv/set/signkick"; } +command { service = "ChanServ"; name = "SET SUCCESSOR"; command = "chanserv/set/successor"; } +command { service = "ChanServ"; name = "SET NOEXPIRE"; command = "chanserv/saset/noexpire"; permission = "chanserv/saset/noexpire"; } + +module { name = "cs_set_misc" } +command { service = "ChanServ"; name = "SET URL"; command = "chanserv/set/misc"; misc_description = _("Associate a URL with the channel"); } +command { service = "ChanServ"; name = "SET EMAIL"; command = "chanserv/set/misc"; misc_description = _("Associate an E-mail address with the channel"); } + +module { name = "cs_status" } +command { service = "ChanServ"; name = "STATUS"; command = "chanserv/status"; } + +module { + name = "cs_suspend" + #expire = 90d + #show = "suspended, by, reason, on, expires" +} +command { service = "ChanServ"; name = "SUSPEND"; command = "chanserv/suspend"; permission = "chanserv/suspend"; group = "chanserv/admin"; } +command { service = "ChanServ"; name = "UNSUSPEND"; command = "chanserv/unsuspend"; permission = "chanserv/suspend"; group = "chanserv/admin"; } + +module { name = "cs_sync" } +command { service = "ChanServ"; name = "SYNC"; command = "chanserv/sync"; group = "chanserv/management"; } + +module { name = "cs_topic" } +command { service = "ChanServ"; name = "TOPIC"; command = "chanserv/topic"; group = "chanserv/management"; } +command { service = "ChanServ"; name = "SET KEEPTOPIC"; command = "chanserv/set/keeptopic"; } + +module { name = "cs_unban" } +command { service = "ChanServ"; name = "UNBAN"; command = "chanserv/unban"; } + +module { name = "cs_updown" } +command { service = "ChanServ"; name = "DOWN"; command = "chanserv/down"; group = "chanserv/status"; } +command { service = "ChanServ"; name = "UP"; command = "chanserv/up"; group = "chanserv/status"; } + +module { name = "cs_xop" } +command { service = "ChanServ"; name = "QOP"; command = "chanserv/xop"; group = "chanserv/access"; } +command { service = "ChanServ"; name = "SOP"; command = "chanserv/xop"; group = "chanserv/access"; } +command { service = "ChanServ"; name = "AOP"; command = "chanserv/xop"; group = "chanserv/access"; } +command { service = "ChanServ"; name = "HOP"; command = "chanserv/xop"; group = "chanserv/access"; } +command { service = "ChanServ"; name = "VOP"; command = "chanserv/xop"; group = "chanserv/access"; } + +module { name = "cs_statusupdate" } \ No newline at end of file diff --git a/data/global.conf b/data/global.conf new file mode 100644 index 0000000..092f331 --- /dev/null +++ b/data/global.conf @@ -0,0 +1,20 @@ +service { + nick = "Global" + user = "services" + host = "services.host" + gecos = "Global Noticer" + #channels = "@#services,#mychan" +} + +module { + name = "global" + client = "Global" + globaloncycledown = "Services are restarting and will be back shortly. Please cause as much chaos as possible in the mean time..." + globaloncycleup = "Services are now back online" + anonymousglobal = yes +} + +command { service = "Global"; name = "HELP"; command = "generic/help"; } + +module { name = "gl_global" } +command { service = "Global"; name = "GLOBAL"; command = "global/global"; permission = "global/global"; } diff --git a/data/hostserv.conf b/data/hostserv.conf new file mode 100644 index 0000000..f093c30 --- /dev/null +++ b/data/hostserv.conf @@ -0,0 +1,49 @@ +service { + nick = "HostServ" + user = "services" + host = "services.host" + gecos = "vHost Service" + #channels = "@#services,#mychan" +} + +module { + name = "hostserv" + client = "HostServ" + activate_on_set = false +} + +command { service = "HostServ"; name = "HELP"; command = "generic/help"; } + +module { name = "hs_del" } +command { service = "HostServ"; name = "DEL"; command = "hostserv/del"; permission = "hostserv/del"; } +command { service = "HostServ"; name = "DELALL"; command = "hostserv/delall"; permission = "hostserv/del"; } + +module { + name = "hs_group" + syncongroup = false + synconset = false +} +command { service = "HostServ"; name = "GROUP"; command = "hostserv/group"; } + +module { name = "hs_list" } +command { service = "HostServ"; name = "LIST"; command = "hostserv/list"; permission = "hostserv/list"; } + +module { name = "hs_off" } +command { service = "HostServ"; name = "OFF"; command = "hostserv/off"; } + +module { name = "hs_on" } +command { service = "HostServ"; name = "ON"; command = "hostserv/on"; } + +module { + name = "hs_request" + memouser = no + memooper = no +} +command { service = "HostServ"; name = "REQUEST"; command = "hostserv/request"; } +command { service = "HostServ"; name = "ACTIVATE"; command = "hostserv/activate"; permission = "hostserv/set"; } +command { service = "HostServ"; name = "REJECT"; command = "hostserv/reject"; permission = "hostserv/set"; } +command { service = "HostServ"; name = "WAITING"; command = "hostserv/waiting"; permission = "hostserv/set"; } + +module { name = "hs_set" } +command { service = "HostServ"; name = "SET"; command = "hostserv/set"; permission = "hostserv/set"; } +command { service = "HostServ"; name = "SETALL"; command = "hostserv/setall"; permission = "hostserv/set"; } diff --git a/data/nickserv.conf b/data/nickserv.conf new file mode 100644 index 0000000..1d3222c --- /dev/null +++ b/data/nickserv.conf @@ -0,0 +1,178 @@ +service { + nick = "NickServ" + user = "services" + host = "services.host" + gecos = "Nickname Registration Service" + #channels = "@#services,#mychan" +} + +module { + name = "nickserv" + client = "NickServ" + forceemail = no + confirmemailchanges = no + unregistered_notice = "Your nickname is not registered. To register it, use: /msg NickServ REGISTER password" + defaults = "kill_quick ns_secure ns_private hide_email hide_mask hide_status hide_quit autoop ns_keep_modes" + regdelay = 1h + expire = 7d + secureadmins = yes + modeonid = yes + #modesonid = "+R" + hidenetsplitquit = yes + killquick = 10s + kill = 30s + #restrictopernicks = yes + enforceruser = "enforcer" + enforcerhost = "services.host" + releasetimeout = 1m + guestnickprefix = "FAGGOT" + nonicknameownership = no + passlen = 100 +} + +command_group { + name = "nickserv/admin" + description = _("Services Operator commands") +} + +command { service = "NickServ"; name = "HELP"; command = "generic/help"; } + +module { + name = "ns_access" + accessmax = 10 + addaccessonreg = no +} +command { service = "NickServ"; name = "ACCESS"; command = "nickserv/access"; } + +module { + name = "ns_ajoin" + ajoinmax = 10 +} +command { service = "NickServ"; name = "AJOIN"; command = "nickserv/ajoin"; } + +module { name = "ns_alist" } +command { service = "NickServ"; name = "ALIST"; command = "nickserv/alist"; } + +module { + name = "ns_cert" + max = 3 +} +command { service = "NickServ"; name = "CERT"; command = "nickserv/cert"; } + +module { name = "ns_drop" } +command { service = "NickServ"; name = "DROP"; command = "nickserv/drop"; } + +#module { name = "ns_getemail" } +#command { service = "NickServ"; name = "GETEMAIL"; command = "nickserv/getemail"; permission = "nickserv/getemail"; group = "nickserv/admin"; } + +#module { name = "ns_getpass" } +#command { service = "NickServ"; name = "GETPASS"; command = "nickserv/getpass"; permission = "nickserv/getpass"; } + +module { + name = "ns_group" + maxaliases = 5 + nogroupchange = yes +} +command { service = "NickServ"; name = "GLIST"; command = "nickserv/glist"; } +command { service = "NickServ"; name = "GROUP"; command = "nickserv/group"; } +command { service = "NickServ"; name = "UNGROUP"; command = "nickserv/ungroup"; } + +module { + name = "ns_identify" + maxlogins = 3 +} +command { service = "NickServ"; name = "ID"; command = "nickserv/identify"; hide = true; } +command { service = "NickServ"; name = "IDENTIFY"; command = "nickserv/identify"; } + +module { name = "ns_info" } +command { service = "NickServ"; name = "INFO"; command = "nickserv/info"; } + +command { service = "NickServ"; name = "SET HIDE"; command = "nickserv/set/hide"; } +command { service = "NickServ"; name = "SASET HIDE"; command = "nickserv/saset/hide"; permission = "nickserv/saset/hide"; } + +module { + name = "ns_list" + listmax = 100 +} +command { service = "NickServ"; name = "LIST"; command = "nickserv/list"; } + +command { service = "NickServ"; name = "SET PRIVATE"; command = "nickserv/set/private"; } +command { service = "NickServ"; name = "SASET PRIVATE"; command = "nickserv/saset/private"; permission = "nickserv/saset/private"; } + +module { name = "ns_logout" } +command { service = "NickServ"; name = "LOGOUT"; command = "nickserv/logout"; } + +module { + name = "ns_recover" + restoreonrecover = yes +} +command { service = "NickServ"; name = "RECOVER"; command = "nickserv/recover"; } +command { service = "NickServ"; name = "GHOST"; command = "nickserv/recover"; } +command { service = "NickServ"; name = "RELEASE"; command = "nickserv/recover"; } + +module { + name = "ns_register" + registration = "none" + nickregdelay = 1h +} +command { service = "NickServ"; name = "CONFIRM"; command = "nickserv/confirm"; } +command { service = "NickServ"; name = "REGISTER"; command = "nickserv/register"; } +#command { service = "NickServ"; name = "RESEND"; command = "nickserv/resend"; } + +#module { name = "ns_resetpass" } +#command { service = "NickServ"; name = "RESETPASS"; command = "nickserv/resetpass"; } + +module { + name = "ns_set" + allowkillimmed = yes +} + +command { service = "NickServ"; name = "SET"; command = "nickserv/set"; } +command { service = "NickServ"; name = "SASET"; command = "nickserv/saset"; permission = "nickserv/saset/"; group = "nickserv/admin"; } + +command { service = "NickServ"; name = "SET AUTOOP"; command = "nickserv/set/autoop"; } +command { service = "NickServ"; name = "SASET AUTOOP"; command = "nickserv/saset/autoop"; permission = "nickserv/saset/autoop"; } + +command { service = "NickServ"; name = "SET DISPLAY"; command = "nickserv/set/display"; } +command { service = "NickServ"; name = "SASET DISPLAY"; command = "nickserv/saset/display"; permission = "nickserv/saset/display"; } + +command { service = "NickServ"; name = "SET EMAIL"; command = "nickserv/set/email"; } +command { service = "NickServ"; name = "SASET EMAIL"; command = "nickserv/saset/email"; permission = "nickserv/saset/email"; } + +command { service = "NickServ"; name = "SET KEEPMODES"; command = "nickserv/set/keepmodes"; } +command { service = "NickServ"; name = "SASET KEEPMODES"; command = "nickserv/saset/keepmodes"; permission = "nickserv/saset/keepmodes"; } + +command { service = "NickServ"; name = "SET KILL"; command = "nickserv/set/kill"; } +command { service = "NickServ"; name = "SASET KILL"; command = "nickserv/saset/kill"; permission = "nickserv/saset/kill"; } + +command { service = "NickServ"; name = "SET LANGUAGE"; command = "nickserv/set/language"; } +command { service = "NickServ"; name = "SASET LANGUAGE"; command = "nickserv/saset/language"; permission = "nickserv/saset/language"; } + +command { service = "NickServ"; name = "SET MESSAGE"; command = "nickserv/set/message"; } +command { service = "NickServ"; name = "SASET MESSAGE"; command = "nickserv/saset/message"; permission = "nickserv/saset/message"; } + +command { service = "NickServ"; name = "SET PASSWORD"; command = "nickserv/set/password"; } +command { service = "NickServ"; name = "SASET PASSWORD"; command = "nickserv/saset/password"; permission = "nickserv/saset/password"; } + +command { service = "NickServ"; name = "SET SECURE"; command = "nickserv/set/secure"; } +command { service = "NickServ"; name = "SASET SECURE"; command = "nickserv/saset/secure"; permission = "nickserv/saset/secure"; } + +command { service = "NickServ"; name = "SASET NOEXPIRE"; command = "nickserv/saset/noexpire"; permission = "nickserv/saset/noexpire"; } + +module { name = "ns_set_misc" } +command { service = "NickServ"; name = "SET URL"; command = "nickserv/set/misc"; misc_description = _("Associate a URL with your account"); } +command { service = "NickServ"; name = "SASET URL"; command = "nickserv/saset/misc"; misc_description = _("Associate a URL with this account"); permission = "nickserv/saset/url"; group = "nickserv/admin"; } + +module { name = "ns_status" } +command { service = "NickServ"; name = "STATUS"; command = "nickserv/status"; } + +module { + name = "ns_suspend" + #suspendexpire = 90d + #show = "suspended, by, reason, on, expires" +} +command { service = "NickServ"; name = "SUSPEND"; command = "nickserv/suspend"; permission = "nickserv/suspend"; group = "nickserv/admin"; } +command { service = "NickServ"; name = "UNSUSPEND"; command = "nickserv/unsuspend"; permission = "nickserv/suspend"; group = "nickserv/admin"; } + +module { name = "ns_update" } +command { service = "NickServ"; name = "UPDATE"; command = "nickserv/update"; } \ No newline at end of file diff --git a/data/operserv.conf b/data/operserv.conf new file mode 100644 index 0000000..55d8b2b --- /dev/null +++ b/data/operserv.conf @@ -0,0 +1,148 @@ +service { + nick = "OperServ" + user = "services" + host = "services.host" + gecos = "Operator Service" + #channels = "@#services,#mychan" +} + +module { + name = "operserv" + client = "OperServ" + autokillexpiry = 7d + chankillexpiry = 7d + snlineexpiry = 7d + sqlineexpiry = 7d + akillonadd = yes + killonsnline = yes + killonsqline = yes + addakiller = yes + akillids = yes + opersonly = yes +} + +command { service = "OperServ"; name = "HELP"; command = "generic/help"; } + +module { name = "os_akill" } +command { service = "OperServ"; name = "AKILL"; command = "operserv/akill"; permission = "operserv/akill"; } + +module { name = "os_chankill" } +command { service = "OperServ"; name = "CHANKILL"; command = "operserv/chankill"; permission = "operserv/chankill"; } + +module { + name = "os_defcon" + defaultlevel = 5 + level4 = "silentoperonly" # GET + level3 = "silentoperonly" # FUCKED + level2 = "silentoperonly" # GET + level1 = "silentoperonly" # FUCKED + timeout = 1h +} +command { service = "OperServ"; name = "DEFCON"; command = "operserv/defcon"; permission = "operserv/defcon"; } + +module { name = "os_config" } +command { service = "OperServ"; name = "CONFIG"; command = "operserv/config"; permission = "operserv/config"; } + +module { name = "os_forbid" } +command { service = "OperServ"; name = "FORBID"; command = "operserv/forbid"; permission = "operserv/forbid"; } + +module { name = "os_ignore" } +command { service = "OperServ"; name = "IGNORE"; command = "operserv/ignore"; permission = "operserv/ignore"; } + +module { name = "os_info" } +command { service = "OperServ"; name = "INFO"; command = "operserv/info"; permission = "operserv/info"; } + +module { name = "os_jupe" } +command { service = "OperServ"; name = "JUPE"; command = "operserv/jupe"; permission = "operserv/jupe"; } + +module { name = "os_kick" } +command { service = "OperServ"; name = "KICK"; command = "operserv/kick"; permission = "operserv/kick"; } + +module { name = "os_kill" } +command { service = "OperServ"; name = "KILL"; command = "operserv/kill"; permission = "operserv/kill"; } + +module { name = "os_list" } +command { service = "OperServ"; name = "CHANLIST"; command = "operserv/chanlist"; permission = "operserv/chanlist"; } +command { service = "OperServ"; name = "USERLIST"; command = "operserv/userlist"; permission = "operserv/userlist"; } + +module { name = "os_login" } +command { service = "OperServ"; name = "LOGIN"; command = "operserv/login"; } +command { service = "OperServ"; name = "LOGOUT"; command = "operserv/logout"; } + +module { + name = "os_logsearch" + logname = "services.log" +} +command { service = "OperServ"; name = "LOGSEARCH"; command = "operserv/logsearch"; permission = "operserv/logsearch"; } + +module { name = "os_mode" } +command { service = "OperServ"; name = "UMODE"; command = "operserv/umode"; permission = "operserv/umode"; } +command { service = "OperServ"; name = "MODE"; command = "operserv/mode"; permission = "operserv/mode"; } + +module { name = "os_modinfo" } +command { service = "OperServ"; name = "MODINFO"; command = "operserv/modinfo"; permission = "operserv/modinfo"; } +command { service = "OperServ"; name = "MODLIST"; command = "operserv/modlist"; permission = "operserv/modinfo"; } + +module { name = "os_module" } +command { service = "OperServ"; name = "MODLOAD"; command = "operserv/modload"; permission = "operserv/modload"; } +command { service = "OperServ"; name = "MODRELOAD"; command = "operserv/modreload"; permission = "operserv/modload"; } +command { service = "OperServ"; name = "MODUNLOAD"; command = "operserv/modunload"; permission = "operserv/modload"; } + +module { + name = "os_news" + announcer = "Global" + oper_announcer = "OperServ" + newscount = 5 +} +command { service = "OperServ"; name = "LOGONNEWS"; command = "operserv/logonnews"; permission = "operserv/news"; } +command { service = "OperServ"; name = "OPERNEWS"; command = "operserv/opernews"; permission = "operserv/news"; } +command { service = "OperServ"; name = "RANDOMNEWS"; command = "operserv/randomnews"; permission = "operserv/news"; } + +module { name = "os_noop" } +command { service = "OperServ"; name = "NOOP"; command = "operserv/noop"; permission = "operserv/noop"; } + +module { name = "os_oper" } +command { service = "OperServ"; name = "OPER"; command = "operserv/oper"; permission = "operserv/oper"; } + +module { name = "os_reload" } +command { service = "OperServ"; name = "RELOAD"; command = "operserv/reload"; permission = "operserv/reload"; } + +module { + name = "os_session" + defaultsessionlimit = 3 + maxsessionlimit = 100 + #exceptionexpiry = 1d + sessionlimitexceeded = "The session limit for your IP %IP% has been exceeded." + maxsessionkill = 10 + sessionautokillexpiry = 1h + session_ipv4_cidr = 32 + session_ipv6_cidr = 64 +} +command { service = "OperServ"; name = "EXCEPTION"; command = "operserv/exception"; permission = "operserv/exception"; } +command { service = "OperServ"; name = "SESSION"; command = "operserv/session"; permission = "operserv/session"; } + +module { + name = "os_set" + #superadmin = yes +} +command { service = "OperServ"; name = "SET"; command = "operserv/set"; permission = "operserv/set"; } + +module { name = "os_shutdown" } +command { service = "OperServ"; name = "QUIT"; command = "operserv/quit"; permission = "operserv/quit"; } +command { service = "OperServ"; name = "RESTART"; command = "operserv/restart"; permission = "operserv/restart"; } +command { service = "OperServ"; name = "SHUTDOWN"; command = "operserv/shutdown"; permission = "operserv/shutdown"; } + +module { name = "os_stats" } +command { service = "OperServ"; name = "STATS"; command = "operserv/stats"; permission = "operserv/stats"; } + +module { name = "os_svs" } +command { service = "OperServ"; name = "SVSNICK"; command = "operserv/svsnick"; permission = "operserv/svs"; } +command { service = "OperServ"; name = "SVSJOIN"; command = "operserv/svsjoin"; permission = "operserv/svs"; } +command { service = "OperServ"; name = "SVSPART"; command = "operserv/svspart"; permission = "operserv/svs"; } + +module { name = "os_sxline" } +command { service = "OperServ"; name = "SNLINE"; command = "operserv/snline"; permission = "operserv/snline"; } +command { service = "OperServ"; name = "SQLINE"; command = "operserv/sqline"; permission = "operserv/sqline"; } + +module { name = "os_update" } +command { service = "OperServ"; name = "UPDATE"; command = "operserv/update"; permission = "operserv/update"; } diff --git a/data/services.conf b/data/services.conf new file mode 100644 index 0000000..c4deb64 --- /dev/null +++ b/data/services.conf @@ -0,0 +1,132 @@ +define { + name = "services.host" + value = "services.supernets.org" +} + +uplink { + host = "REDACTED" + ipv6 = yes + ssl = yes + port = REDACTED + password = "REDACTED" +} + +serverinfo { + name = "services.supernets.org" + description = "Services for SuperNETs" + pid = "data/services.pid" + motd = "conf/services.motd" +} + +module { + name = "unreal4" + use_server_side_mlock = yes + use_server_side_topiclock = yes +} + +networkinfo { + networkname = "SuperNETs" + nicklen = 20 + userlen = 10 + hostlen = 64 + chanlen = 20 + modelistsize = 100 + vhost_chars = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789.-" + allow_undotted_vhosts = true + disallow_start_or_end = ".-" +} + +options { + casemap = "ascii" + seed = REDACTED + strictpasswords = yes + badpasslimit = 3 + badpasstimeout = 1h + updatetimeout = 5m + expiretimeout = 1h + readtimeout = 5s + warningtimeout = 4h + timeoutcheck = 3s + hidestatso = yes + retrywait = 60s + hideprivilegedcommands = yes + hideregisteredcommands = yes +} + +include { + type = "file" + name = "botserv.conf" +} + +include { + type = "file" + name = "chanserv.conf" +} + +include { + type = "file" + name = "global.conf" +} + +include { + type = "file" + name = "hostserv.conf" +} + +include{ + type = "file" + name = "nickserv.conf" +} + +include { + type = "file" + name = "operserv.conf" +} + +log { + target = "#services" + bot = "Global" + admin = "*" + override = "*" + commands = "*" + servers = "*" + channels = "*" + users = "*" + other = "*" + rawio = no + debug = no +} + +log { + bot = "Global" + target = "globops" + admin = "global/* operserv/chankill operserv/mode operserv/kick operserv/akill operserv/s*line operserv/noop operserv/jupe operserv/oline operserv/set operserv/svsnick operserv/svsjoin operserv/svspart nickserv/getpass */drop" + servers = "squit" + users = "oper" + other = "expire/* bados akill/*" +} + +opertype { + name = "Services Root" + commands = "*" + privs = "*" +} + +oper { + name = "acidvegas" + type = "Services Root" + require_oper = yes + certfp = "f42e0c30ff63484dde3284823829f9b08568259c0b0f2beb174595ee577a924a" + host = "*@big.dick.acid.vegas" +} + +module { + name = "db_flatfile" + database = "anope.db" + keepbackups = 7 + fork = no +} + +module { name = "enc_sha256" } +module { name = "help" } +module { name = "m_sasl" } diff --git a/docs/ASTYLE b/docs/ASTYLE new file mode 100644 index 0000000..be8cf23 --- /dev/null +++ b/docs/ASTYLE @@ -0,0 +1 @@ +astyle --style=java --indent=tab --brackets=break-closing --indent-switches --indent-cases --brackets=break diff --git a/docs/BUGS b/docs/BUGS new file mode 100644 index 0000000..d805dd7 --- /dev/null +++ b/docs/BUGS @@ -0,0 +1 @@ +For all bug reports / updates please see https://bugs.anope.org/ diff --git a/docs/C++CASTING b/docs/C++CASTING new file mode 100644 index 0000000..eed640b --- /dev/null +++ b/docs/C++CASTING @@ -0,0 +1,111 @@ +C++-style Casting +================= + +In C, you can cast in one of two ways: + +(type)var +type(var) + +The problem with C-style casting is that it allows a programmer to get away +with too much, and is also not designed to handle C++ classes. + +C++ has 4 types of casting in addition to allowing C-style casting. They are: + +static_cast +const_cast +dynamic_cast +reinterpret_cast + +The syntax is usually *_cast(var). + +static_cast +----------- + +From my experience, this cast is closest to C-style casting for non-pointer +types as well as between some (but not all) pointer types. This type of cast, +like C-style casting, is performed at compile-time. static_cast can also do +a downcast of a derived class to a base class, but only if the base class is +not a virtual base class. Sometimes the result of this cast can become +undefined. static_cast is a bit more strict that C-style casting, though. It +disallows certain class conversions that would've been allowed with a C-style +cast. static_cast also doesn't allow you to cast to an incomplete type. In +these cases, I would try either dynamic_cast or reinterpret_cast. + +const_cast +---------- + +This cast is mainly to add or remove const-ness or volatile-ness from a +variable. This is safer than using a C-style cast to change the const-ness +of a variable. In most cases if you try to use one of the other casts and it +complains about const-ness, you will want to either use this cast instead or +wrap the other cast around this cast. An example: + +const int *a; +static_cast(a); <-- This will fail. + +To remedy the above, you would might try this: + +const int *a; +const_cast(a); <-- But this will still fail. + +The real solution is this: + +const int *a; +static_cast(const_cast(a)); + +It is not recommended to use const_cast on the this variable within a member +function of a class that is declared const. Instead you should use the mutable +keyword on the variable in the class's definition. + +dynamic_cast +------------ + +This cast can only be used on pointers or references to classes. It can cast a +derived class to a base class, a derived class to another derived class +(provided that both are children of the same base class), or a base class to a +derived class. You can also use this to cast a class to void *. This cast is +done at run-time as opposed to the other casts, and relies on C++'s RTTI to be +enabled. It is meant to be used on polymorphic classes, so use static_cast on +non-polymorphic classes. + +derived-to-base conversions are actually done statically, so you use either +dynamic_cast or static_cast on them, regardless of if the classes are +polymorphic or not. + +derived-to-derived or base-to-derived conversions, however, rely on run-time +type information, and this cast is used on those classes that are polymorphic. +This is safer than C-style casting in that an invalid pointer conversion will +return a NULL pointer, and an invalid reference conversion will throw a +Bad_cast exception. + +Note that in Anope we prefer if Anope::debug_cast is used. +This uses dynamic_cast (and checks for a NULL pointer return) on debug builds +and static_cast on release builds, to speed up the program because of dynamic_cast's +reliance on RTTI. + +reinterpret_cast +---------------- + +This cast I would use only as a last resort if static_cast isn't allowed on a +conversion. It allows for conversions between two unrelated types, such as +going from char * to int *. It can also be used to convert a pointer to an +integral type and vica versa. The sites I've read mention how the result is +non-portable, which I assume means the resulting object code is non-portable, +so since the code is compiled on many systems anyways, I don't see this as +being a huge issue. It is recommended to only use this if necessary, though. + +Links +===== + +The following links are web sites I've used to get this information, and might +describe some of the above a bit better than I have. :P + +https://www.acm.org/crossroads/xrds3-1/ovp3-1.html +http://www.cplusplus.com/doc/tutorial/typecasting.html +http://www.codeguru.com/forum/showthread.php?t=312456 +https://web.archive.org/web/20170810222238/http://www.cs.umd.edu/class/sum2003/cmsc311/Notes/BitOp/cast.html +https://www.microsoft.com/en-us/download/details.aspx?id=55984 +https://en.wikibooks.org/wiki/C%2B%2B_Programming/Type_Casting +https://web.archive.org/web/20160510114447/http://www.informit.com/guides/content.aspx?g=cplusplus&seqNum=134 + +-- CyberBotX, Nov 23, 2008 diff --git a/docs/CMakeLists.txt b/docs/CMakeLists.txt new file mode 100644 index 0000000..082b1da --- /dev/null +++ b/docs/CMakeLists.txt @@ -0,0 +1,15 @@ +# We only need to install these docs on Windows as most Windows installations will be binary, not source +if(WIN32) + # Only install given files from this directory + # NOTE: I would've had this just find all files in the directory, but that would include files not needed (like this file) + execute_process(COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_CURRENT_SOURCE_DIR}/README ${CMAKE_CURRENT_BINARY_DIR}/README.txt) + if(IN_SOURCE) + # Add README.txt to list of files for CPack to ignore + add_to_cpack_ignored_files("README.txt$" TRUE) + endif(IN_SOURCE) + set(DOCS Changes Changes.conf DEFCON FAQ INSTALL LANGUAGE MODULES NEWS ${CMAKE_CURRENT_BINARY_DIR}/README.txt WIN32.txt) + install(FILES ${DOCS} + DESTINATION ${DOC_DIR} + ) + set_directory_properties(PROPERTIES ADDITIONAL_MAKE_CLEAN_FILES "${CMAKE_CURRENT_BINARY_DIR}/README.txt") +endif(WIN32) diff --git a/docs/CODING b/docs/CODING new file mode 100644 index 0000000..6c56d0d --- /dev/null +++ b/docs/CODING @@ -0,0 +1,239 @@ +Originally pulled from: https://wiki.inspircd.org/Coding_Guidelines + +--- + +InspIRCd Coding Guidelines + +The following are a set of guidelines for writing patches to InspIRCd, or for +creating modules for distribution with the official package. These guidelines +were written a time after InspIRCd development started, and so not all code +yet follows these. This will be rectified with time. + + +1. Comments + + * Multi Line + Multiple line comments should follow the C-style comment, for example: + /* + * This is a multiple line comment, huzzah.. + */ + + * Single Line + Single line comments should also be in the C style, for example: + /* This is a boring one-line comment */ + + * Doxygen commenting + If you wish your comment to show in doxygen, the comment should be directly + above the item you are documenting (a class, function, enum, etc) and the + first line should be "/**". For example: + /** This is a doxygen multiline comment. + * Description of thingymebob here. + */ + + The first line after the "**" is used as the short description of the item + (up to the full stop) and everything afterwards as the detailed description. + + +2. Indentation + + Tabs. Tabs. ONLY TABS. Use a single tab for each level of indentation, + for example: + int main() + { + if (condition) + { + code + } + } + + +3. Separation + + Always put a space in between a keyword like if/while and the condition, + for example: + if (foo == bar) + NOT + if(foo == bar) + + +4. Braces + + Always put braces opening and closing blocks on separate lines, see the + indentation example. For example, place braces like this: + if (apples == "green") + { + cout << "Apples are green" << endl; + } + + and not: + if (apples == "green") { + cout << "Apples are green" << endl; + } + + The one exception to this is if you are declaring a class method which is + only one line long, in that case the following is acceptable in most cases: + class foo : public bar + { + foo() { } + getrandomfoo() { return rand(); } + }; + + +5. Templates + + Where possible, use templates rather than #defines. Avoid use of RTTI. + + +6. Structs + + Structs should be declared in the following fashion: + struct BodyPartBasket + { + int arms; + int legs; + int scrotalsacs; + }; + and not like this: + typedef struct + { + int arms; + int legs; + int scrotalsacs; + } BodyPartBasket; + + The second way is not required in C++ to be able to do this: + BodyPartBasket mybasket; + + Plus, placing the name at the bottom of the declaration makes readability + more difficult (as you have to scroll down to the bottom of the struct to + find its name). (where possible, call them classes rather than structs.) + + +7. Variable naming + + Class and struct names should be in camel case with a leading capital letter, + for example "MyBagOfBones" and not "my_bag_of_bones" or "mybagofbones". + Variable names can be in either camel case with a leading capital letter or + alternatively all lower case, so long as the same naming convention is + adhered to throughout the class. No classes or variables should be named in + capitals unless this makes sense for the name (for example "class DNS"). + Constants and enum values should always be completely in CAPITALS and + underscores may be used, for example: + enum DecayState + { + DECAYED_MOULDY = 0, + DECAYED_SMELLY = 1, + DECAYED_MAGGOTS = 2 + }; + All value names in an enum should be started with the same text which should + be related in some way to the enum's use. For example "DNS_CNAME, DNS_A, + DNS_AAAA". + + +8. Use of references + + Wherever possible, when dealing with any complex class, pass a const reference + rather than a copy of the class. For example: + MyThingy::MyThingy(const std::string &thingyvalue) + { + } + Of course, if you intended to change the string you can just omit the 'const'. + + +9. Use of char pointers + + Whenever you use char pointers (char*, char**) try to use const equivalents. + This is much safer and avoids ugly and dangerous casts. For example: + MyThingy::Thingify(const char* const* wotsits) + { + } + If it is possible without performance loss, consider avoiding char pointers + altogether and using std::string instead. + + +10. Use of STL + + For more information on use of STL in InspIRCd, please see the separate + STL FAQ. + + +11. Making copies of data + + Never ever make a copy of a piece of data unless it is absolutely necessary. + For example, don't use strlcpy() to make a copy of the const char* string + returned by std::string::c_str(), if the change can be done to the std::string + itself. The same goes for unnecessary variable assignments, especially those + which assign large classes. + + +12. namespace std + + Avoid the following: + using namespace std; + It might take a bit more typing, but things work better if you don't set + (then later assume) the namespace -- specify it explicitly when you want to + use it. + + +13. Linefeeds + + Unix linefeeds only please. We do not like to see our screens covered in ^M. + + +14. Portability + + Always make sure your code is portable to all supported operating systems, + remember of course that as of 1.1.8 this includes windows. Don't write code + that only works on windows, or only works on Linux. Test your code on all + platforms or ask for help from other developers who have the platforms you + want to test on. + + * new() and delete(), malloc() and free() + Apart from the fact that using malloc() and free() is bad practice in C++ + code, you must never use malloc() or free() in InspIRCd, within its modules + or within the core. This is because if you use malloc() or free() in windows, + the memory is claimed from the program's local heap. + In windows, each shared object (module, dll) has its own heap, which is + protected from other dlls and executables. To get around this issue and + allow more posix-like memory access from other dlls in the program (other + modules), InspIRCd overrides the operators new and delete to ensure that + memory allocated by them comes from the windows global heap. If you use + malloc() and free() for this, the ircd will segfault when another module + tries to access the memory you have allocated! + + * strdup() + As with malloc(), above, strdup() should be avoided. Where strdup() is + absolutely necessary, use strnewdup() which is our strdup() implementation + that calls operator new instead of using malloc(). + char arrays allocated by strnewdup() should be deleted with operator delete[]. + + * CoreExport and DllImport + Prefix all types you want to import or export to other modules with CoreExport + and DllImport macros. These do nothing in POSIX operating systems, however + in windows these are expanded to the instructions __declspec(dllimport) and + __declspec(dllexport) respectively depending on where they are used and how. + + +15. External Dependencies + + If a module is compiled as standard, or the code is part of the core, you must + not use any dependencies that are not available as standard on all supported + operating systems beyond libstdc++, libc, and whatever else is currently + required to build the core. Modules which use nonstandard dependencies belong + in the modules/extra directory. + + +16. Profiling and Performance + + It is one thing to assume that code performs bad, it is another thing to prove + that it actually is. A lot of experienced programmers talk about 'premature + optimisation', and here is what it means: if you have a piece of code called + once on startup that takes 10 seconds instead of one second to run, and a + piece of code that takes 0.05 seconds to run when it should take 0.01, and + it is called once per second, the second piece of code is the priority. + + In other words, make sure that what you think is slow, and a performance + problem in Insp actually is. + To do this, use the callgrind tool from Valgrind (valgrind --tool=cachegrind + bin/inspircd -nofork -debug), and kcachegrind (or similar) to view the output + files. diff --git a/docs/COPYING b/docs/COPYING new file mode 100644 index 0000000..dd3f5ab --- /dev/null +++ b/docs/COPYING @@ -0,0 +1,347 @@ + GNU GENERAL PUBLIC LICENSE + Version 2, June 1991 + +Copyright (C) 1989, 1991 Free Software Foundation, Inc. + +51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA + +Everyone is permitted to copy and distribute verbatim copies +of this license document, but changing it is not allowed. + + Preamble + + The licenses for most software are designed to take away your +freedom to share and change it. By contrast, the GNU General Public +License is intended to guarantee your freedom to share and change free +software--to make sure the software is free for all its users. This +General Public License applies to most of the Free Software +Foundation's software and to any other program whose authors commit to +using it. (Some other Free Software Foundation software is covered by +the GNU Lesser General Public License instead.) You can apply it to +your programs, too. + + When we speak of free software, we are referring to freedom, not +price. Our General Public Licenses are designed to make sure that you +have the freedom to distribute copies of free software (and charge for +this service if you wish), that you receive source code or can get it +if you want it, that you can change the software or use pieces of it +in new free programs; and that you know you can do these things. + + To protect your rights, we need to make restrictions that forbid +anyone to deny you these rights or to ask you to surrender the rights. +These restrictions translate to certain responsibilities for you if you +distribute copies of the software, or if you modify it. + + For example, if you distribute copies of such a program, whether +gratis or for a fee, you must give the recipients all the rights that +you have. You must make sure that they, too, receive or can get the +source code. And you must show them these terms so they know their +rights. + + We protect your rights with two steps: (1) copyright the software, and +(2) offer you this license which gives you legal permission to copy, +distribute and/or modify the software. + + Also, for each author's protection and ours, we want to make certain +that everyone understands that there is no warranty for this free +software. If the software is modified by someone else and passed on, we +want its recipients to know that what they have is not the original, so +that any problems introduced by others will not reflect on the original +authors' reputations. + + Finally, any free program is threatened constantly by software +patents. We wish to avoid the danger that redistributors of a free +program will individually obtain patent licenses, in effect making the +program proprietary. To prevent this, we have made it clear that any +patent must be licensed for everyone's free use or not licensed at all. + + The precise terms and conditions for copying, distribution and +modification follow. + + GNU GENERAL PUBLIC LICENSE + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION + + + 0. This License applies to any program or other work which contains +a notice placed by the copyright holder saying it may be distributed +under the terms of this General Public License. The "Program", below, +refers to any such program or work, and a "work based on the Program" +means either the Program or any derivative work under copyright law: +that is to say, a work containing the Program or a portion of it, +either verbatim or with modifications and/or translated into another +language. (Hereinafter, translation is included without limitation in +the term "modification".) Each licensee is addressed as "you". + +Activities other than copying, distribution and modification are not +covered by this License; they are outside its scope. The act of +running the Program is not restricted, and the output from the Program +is covered only if its contents constitute a work based on the +Program (independent of having been made by running the Program). +Whether that is true depends on what the Program does. + + 1. You may copy and distribute verbatim copies of the Program's +source code as you receive it, in any medium, provided that you +conspicuously and appropriately publish on each copy an appropriate +copyright notice and disclaimer of warranty; keep intact all the +notices that refer to this License and to the absence of any warranty; +and give any other recipients of the Program a copy of this License +along with the Program. + +You may charge a fee for the physical act of transferring a copy, and +you may at your option offer warranty protection in exchange for a fee. + + 2. You may modify your copy or copies of the Program or any portion +of it, thus forming a work based on the Program, and copy and +distribute such modifications or work under the terms of Section 1 +above, provided that you also meet all of these conditions: + + a) You must cause the modified files to carry prominent notices + stating that you changed the files and the date of any change. + + b) You must cause any work that you distribute or publish, that in + whole or in part contains or is derived from the Program or any + part thereof, to be licensed as a whole at no charge to all third + parties under the terms of this License. + + c) If the modified program normally reads commands interactively + when run, you must cause it, when started running for such + interactive use in the most ordinary way, to print or display an + announcement including an appropriate copyright notice and a + notice that there is no warranty (or else, saying that you provide + a warranty) and that users may redistribute the program under + these conditions, and telling the user how to view a copy of this + License. (Exception: if the Program itself is interactive but + does not normally print such an announcement, your work based on + the Program is not required to print an announcement.) + +These requirements apply to the modified work as a whole. If +identifiable sections of that work are not derived from the Program, +and can be reasonably considered independent and separate works in +themselves, then this License, and its terms, do not apply to those +sections when you distribute them as separate works. But when you +distribute the same sections as part of a whole which is a work based +on the Program, the distribution of the whole must be on the terms of +this License, whose permissions for other licensees extend to the entire +whole, and thus to each and every part regardless of who wrote it. + +Thus, it is not the intent of this section to claim rights or contest +your rights to work written entirely by you; rather, the intent is to +exercise the right to control the distribution of derivative or +collective works based on the Program. + +In addition, mere aggregation of another work not based on the Program +with the Program (or with a work based on the Program) on a volume of +a storage or distribution medium does not bring the other work under +the scope of this License. + + 3. You may copy and distribute the Program (or a work based on it, +under Section 2) in object code or executable form under the terms of +Sections 1 and 2 above provided that you also do one of the following: + + a) Accompany it with the complete corresponding machine-readable + source code, which must be distributed under the terms of Sections + 1 and 2 above on a medium customarily used for software interchange; or, + + b) Accompany it with a written offer, valid for at least three years, + to give any third party, for a charge no more than your cost of + physically performing source distribution, a complete machine-readable + copy of the corresponding source code, to be distributed under the terms + of Sections 1 and 2 above on a medium customarily used for software + interchange; or, + + c) Accompany it with the information you received as to the offer + to distribute corresponding source code. (This alternative is allowed + only for noncommercial distribution and only if you received the program + in object code or executable form with such an offer, in accord with + Subsection b above.) + +The source code for a work means the preferred form of the work for +making modifications to it. For an executable work, complete source +code means all the source code for all modules it contains, plus any +associated interface definition files, plus the scripts used to +control compilation and installation of the executable. However, as a +special exception, the source code distributed need not include +anything that is normally distributed (in either source or binary +form) with the major components (compiler, kernel, and so on) of the +operating system on which the executable runs, unless that component +itself accompanies the executable. + +If distribution of executable or object code is made by offering +access to copy from a designated place, then offering equivalent +access to copy the source code from the same place counts as +distribution of the source code, even though third parties are not +compelled to copy the source along with the object code. + + 4. You may not copy, modify, sublicense, or distribute the Program +except as expressly provided under this License. Any attempt +otherwise to copy, modify, sublicense or distribute the Program is +void, and will automatically terminate your rights under this License. +However, parties who have received copies, or rights, from you under +this License will not have their licenses terminated so long as such +parties remain in full compliance. + + 5. You are not required to accept this License, since you have not +signed it. However, nothing else grants you permission to modify or +distribute the Program or its derivative works. These actions are +prohibited by law if you do not accept this License. Therefore, by +modifying or distributing the Program (or any work based on the +Program), you indicate your acceptance of this License to do so, and +all its terms and conditions for copying, distributing or modifying +the Program or works based on it. + + 6. Each time you redistribute the Program (or any work based on the +Program), the recipient automatically receives a license from the +original licensor to copy, distribute or modify the Program subject to +these terms and conditions. You may not impose any further +restrictions on the recipients' exercise of the rights granted herein. +You are not responsible for enforcing compliance by third parties to +this License. + + 7. If, as a consequence of a court judgment or allegation of patent +infringement or for any other reason (not limited to patent issues), +conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot +distribute so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you +may not distribute the Program at all. For example, if a patent license +would not permit royalty-free redistribution of the Program by all those +who receive copies directly or indirectly through you, then the only way +you could satisfy both it and this License would be to refrain entirely +from distribution of the Program. + +If any portion of this section is held invalid or unenforceable under +any particular circumstance, the balance of the section is intended to +apply and the section as a whole is intended to apply in other +circumstances. + +It is not the purpose of this section to induce you to infringe any +patents or other property right claims or to contest validity of any +such claims; this section has the sole purpose of protecting the +integrity of the free software distribution system, which is implemented +by public license practices. Many people have made generous contributions +to the wide range of software distributed through that system in reliance +on consistent application of that system; it is up to the author/donor to +decide if he or she is willing to distribute software through any other +system and a licensee cannot impose that choice. + +This section is intended to make thoroughly clear what is believed to be +a consequence of the rest of this License. + + + 8. If the distribution and/or use of the Program is restricted in +certain countries either by patents or by copyrighted interfaces, the +original copyright holder who places the Program under this License +may add an explicit geographical distribution limitation excluding +those countries, so that distribution is permitted only in or among +countries not thus excluded. In such case, this License incorporates +the limitation as if written in the body of this License. + + 9. The Free Software Foundation may publish revised and/or new versions +of the General Public License from time to time. Such new versions will +be similar in spirit to the present version, but may differ in detail to +address new problems or concerns. + +Each version is given a distinguishing version number. If the Program +specifies a version number of this License which applies to it and "any +later version", you have the option of following the terms and conditions +either of that version or of any later version published by the Free +Software Foundation. If the Program does not specify a version number of +this License, you may choose any version ever published by the Free Software +Foundation. + + 10. If you wish to incorporate parts of the Program into other free +programs whose distribution conditions are different, write to the author +to ask for permission. For software which is copyrighted by the Free +Software Foundation, write to the Free Software Foundation; we sometimes +make exceptions for this. Our decision will be guided by the two goals +of preserving the free status of all derivatives of our free software and +of promoting the sharing and reuse of software generally. + + NO WARRANTY + + 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY +FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN +OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES +PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED +OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS +TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE +PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, +REPAIR OR CORRECTION. + + 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING +WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR +REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, +INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING +OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED +TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY +YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER +PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE +POSSIBILITY OF SUCH DAMAGES. + + END OF TERMS AND CONDITIONS + +How to Apply These Terms to Your New Programs + + If you develop a new program, and you want it to be of the greatest +possible use to the public, the best way to achieve this is to make +it free software which everyone can redistribute and change under +these terms. + + To do so, attach the following notices to the program. It is safest +to attach them to the start of each source file to most effectively +convey the exclusion of warranty; and each file should have at least +the "copyright" line and a pointer to where the full notice is found. + + + Copyright (C) yyyy name of author + + This program is free software; you can redistribute it and/or + modify it under the terms of the GNU General Public License + as published by the Free Software Foundation; either version 2 + of the License, or (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA + 02110-1301, USA. + +Also add information on how to contact you by electronic and paper mail. + +If the program is interactive, make it output a short notice like this +when it starts in an interactive mode: + + Gnomovision version 69, Copyright (C) year name of author + Gnomovision comes with ABSOLUTELY NO WARRANTY; for details + type `show w'. This is free software, and you are welcome + to redistribute it under certain conditions; type `show c' + for details. + +The hypothetical commands `show w' and `show c' should show the appropriate +parts of the General Public License. Of course, the commands you use may +be called something other than `show w' and `show c'; they could even be +mouse-clicks or menu items--whatever suits your program. + +You should also get your employer (if you work as a programmer) or your +school, if any, to sign a "copyright disclaimer" for the program, if +necessary. Here is a sample; alter the names: + + Yoyodyne, Inc., hereby disclaims all copyright interest in the program + `Gnomovision' (which makes passes at compilers) written by James Hacker. + + , 1 April 1989 + Ty Coon, President of Vice + +This General Public License does not permit incorporating your program into +proprietary programs. If your program is a subroutine library, you may +consider it more useful to permit linking proprietary applications with the +library. If this is what you want to do, use the GNU Lesser General +Public License instead of this License. + + diff --git a/docs/Changes b/docs/Changes new file mode 100644 index 0000000..386c568 --- /dev/null +++ b/docs/Changes @@ -0,0 +1,412 @@ +Anope Version 2.0.12 +-------------------- +Added account confirmation to the web panel +Added the regex_pcre2 module which provides regex/pcre with PCRE2 +Documented the cs_no_expire channel default +Fixed config validation mistakenly allowing spaces in some fields +Fixed the bahamut protocol module not knowing about halfops +Fixed writing a flatfile database not being atomic +Updated the hybrid protocol module for recent protocol changes + +Anope Version 2.0.11 +-------------------- +Fixed ldap on OpenLDAP 2.5+ +Fixed not using utf-8 encoding for outgoing email +Fixed ns_resetpass not returning a response for XMLRPC +Fixed some message params being sent as instead of +Fixed unsetting vhosts on unreal4 +Fixed username validity checking on ircd-hybrid +Send the oper mode for services pseudoclients on InspIRCd +Updated the pl_PL translation +Updated unreal4 for various protocol changes + +Anope Version 2.0.10 +-------------------- +Add support for channel SQLines on InspIRCd +Change default protocol module from inspircd20 to inspircd3 +Change the character set used by chanstats and irc2sql to utf8mb4 +Fix a ton of typos in messages +Fix being able to override MAXLIST on InspIRCd +Fix blocking on boot when trying to upgrade SQL databases without account identifiers +Fix not flushing the ERROR message on squit +Fix using an invalidated iterator when deleting bots +Fix various harmless compiler warnings +Fix webcpanel not using the forwarded IP +Show the account name in nickserv/info + +Anope Version 2.0.9 +------------------- +Fix a regression from 2.0.8 that prevented serialising to MySQL +Send account identifiers to InspIRCd on SASL logins too +Fix a query bug in irc2sql + +Anope Version 2.0.8 +------------------- +Add +K channel mode for ircd-hybrid +Add immutable identifiers to user accounts +Fix build on systems that use musl libc +Fix help of global/global not showing the correct origin nick +Fix not removing vhosts when an nick is dropped +Fix parsing channel metadata on InspIRCd 3+ +Fix parsing kicks on InspIRCd 3+ +Fix parsing topic changes on InspIRCd 3+ +Fix topiclock on InspIRCd +Modernize the ircd-hybrid protocol module + + +Anope Version 2.0.7 +------------------- +Fix not sending login data on successful NickServ GROUP +Fix m_httpd to not consider headers to be case sensitive +Add InspIRCd 3 protocol support +Add 'n' email token for use in the email change template +Add logging for NickServ UNGROUP +Fix setting swhois on UnrealIRCd +Add nickserv/recover permission to allow opers to recover other users +Fix superadmin not being removed when deopering +Fix setting nickserv access list in webcpanel +Add support for post-handshake SASL in Unreal 4.2.2+ +Add logging for channel memo deletionso + +Anope Version 2.0.6 +------------------- +Log client IP for web clients running commands via webcpanel +Fix log file path for the config file could not be opened log message +Allow nickserv/group to be used via XMLRPC +Fix logsearch without wildcards +Support cidr exempts in m_dnsbl +Add support for IPv6 dnsbls +Add +u and +L channel modes for ircd-hybrid +Set +x after hostserv/off on InspIRCd and UnrealIRCd +Fix chanserv/mode not being able to set extbans +Send CHGIDENT/CHGHOST on SVSLOGIN on InspIRCd +Fix escaping replies from commands in webcpanel +Enable require_oper for all opers added via operserv/oper +Advertise SASL mechanisms to UnrealIRCd servers + +Anope Version 2.0.5 +------------------- +Fix negative levels to not match users with negative access +Fix memo sender to always be the account name of the sender +Allow unregistered users to use the ChanServ seen command +Fix secureops to not be enforced on operators with the chanserv/administration privilege +Fix command name in HELP syntax messages to always be upper case +Show unconfirmed nickname messages on registration in webcpanel +Fix NickServ SET EMAIL to be executable via XMLRPC +Fix OperServ USERLIST/CHANLIST to accept regexes +Allow OperServ USERLIST to also match realname syntax (n!u@h#r) +Fix db_old importing languages to use the UTF-8 version +Fix m_dns to return REFUSED if no answers could be found +Fix ns_maxemail to be case insensitive +Add MemoServ READ ALL command +Add support for NickServ GROUP to be executed via XMLRPC +Add support for logging hostname/ip of SASL authentication attempts, if supported by IRCd + +Anope Version 2.0.4 +------------------- +Add notice rpc method to XMLRPC +Fix access check in cs_updown to not allow actions on users with equal access +Fix randomnews to work when there are more than 'newscount' random news +Fix crash from handling nick introduction collisions on unreal4 +Add support for GCC6 +Fix handling /join 0 on ratbox +Fix saset display to update the account of the proper user +Fix nickserv/confirm to send account and +r when appropriate +Fix chankill to not add duplicate akills +Allow nickserv/maxemail to disregard gmail style aliases when comparing emails +Fix chanserv/mode when setting listmodes with CIDR ranges +Fix reported expiry time when the time is divisible by 1 year +Clarify botserv repeat kicker help and allow setting repeat times to 1 +Send vident/vhost with SASL login +Add support for SASL reauth +Fix log and database backup directories to be properly created by the installer + +Anope Version 2.0.3 +------------------- +Add support for UnrealIRCd 4 +Fix cs_access to respect chanserv/access/list privilege +Fix cs_access to match level -1 as every user, not any level <0 +Fix problems related to object destruction order when using db_sql_live +Show memo notify settings in ms_info +Fix some actions bumping channels last used time that shouldn't have +Add maxlogins configuration directive to limit the number of concurrent logins to one account +Fix race with auto svsnick on ghost sometimes causing nick collisions instead +Fix saset langauge reply +Show akill/sxlines ids in VIEW +Fix crash when an oper is configured in both the configuration and via os_oper +Fix m_ldap reconnect logic not properly setting protocol and network timeout settings +Fix crash from unloading regex modules when regex xlines exist +Fix irc2sql to store away messages +Add notice method to m_xmlrpc_main +Fix numerics on InspIRCd from being sent to user UID +Fix usermode +I on UnrealIRCd to be considered oper only +Fix crash in webcpanel when deleting your own access on a channel +Fix webcpanel allowing suspended users to login +Fix hs_off on InspIRCd to not desync active user host +Fix bs_bot to not allow colliding bots into users +Don't allow hostserv modules to load if there is no hostserv +Fix ns_register allowing bot nicks to be registered through webcpanel +Don't update chanserv keepmodes during inhabit +Fix build on cmake 2.4 +Allow searching emails by wildcard in ns_getemail + +Anope Version 2.0.2 +------------------- +Fix keepmodes preventing the first user of a channel from being deopped +Fix SQlines that don't begin with # from matching channels +Made cs_clone behave like the help describes, copying many settings and lists by default +Allow cs_clone to clone levels, too +Update Hybrid protocol module for 8.2 +Fix not unescaping all characters sent over XMLRPC +Fix crash when os_mode is used to destroy channels, like when unsetting permanent channel mode from an empty channel +Allow users with topic change privilege to change the topic instead of requiring them to use ChanServ's topic command +Fix negatively locking param modes in default mlock +Change entrymsg to check for the SET privilege, not real founder +Allow configuring characters allowed in nicknames +Fix crash when non users register channels externally (like XMLRPC) +Remove operserv/exception MOVE, it did not function correctly. Instead reorder the list by deleting/adding entries. +Allow flood ttb to be 0. +Enforce mlock when disabling defcon modes +Fix cs_mode not being able to apply mlock on register +Add log message when users send memos +Fix old collide timers from staying around after successful identify. Fixes being able to identify and logout and still being hit by the old timers. +Fix undefined behavior in cs_mode which usually crashes when clearing large list modes +Show all opertypes in operserv/info, even if no opers use them + +Anope Version 2.0.1 +------------------- +Fix access entries on accounts sometimes not updating when a user's display name changes +Fix ns_group to properly validate the account of the user against the target +Fix os_stats not saving max user count and time when using SQL +Fix nickalias's 'nc' field sometimes not being updated when using SQL +Fix several crashes on Windows related to being unable to load modules +Fix bs_bot change not properly reintroducing bots after changing their ident, host, or realname + +Add English language file to allow users to easily modify language strings +Add configuring which mode cs_ban sets, and added a MUTE command to BotServ's fantasy +Allow SVSPART to take an optional reason +Allow cs_list to search channel topics and descriptions + +Anope Version 2.0.0 +------------------- +Added irc2sql stats module + +Anope Version 1.9.9 +------------------- +A Added a better webpanel template, removed the old one +A Added SQL logging support +A Added Redis database support +A Added ability to configure what privileges XOP commands give +U Updated Dutch language file, from Robby +U Updated Spanish langauge file, from Isaac Fontal +F Fix build on Solaris and OSX +F Fixed setting BotServ's default settings in the config +F Fixed some names of config items, including NickServ's kill protect + +Anope Version 1.9.8 +------------------- +A Ability to configure fantasy commands in the config +A Add SVSJOIN and SVSPART commands +F Fix "leave" channel log level from not logging +F Fix users able to "resend" their registration mail with registration set to admin only +F Fix build on OpenBSD +F Fix not logging debug logs to the logfile when debug mode is enabled +F Fix defcon timeout timer +F Fix crash in os_forbid with expiring entries +F Fix several issues with db_sql_live + +Anope Version 1.9.7 +------------------- +A Added ability for using regex as patterns for various commands +A Extended ability of operserv/akill to also match against nick and realname +A Added chanserv:require configuration option +A Added nickserv:unregistered_notice and nickserv:registration configuration option +A Added options:casemap configuration option +A Added a web panel +A db_sql_live now allows all tables to be "live", not just a select few + +Anope Version 1.9.6 +------------------- +A Added ability to configure emails sent by services +A Added chanserv/up and chanserv/down +A Added m_proxyscan +A Added more configurability for what vhosts are valid +A Added chanserv/log +A Added ability to configure ChanServ privileges +A Added a new database format +A Added SQLite support +A Added more verbose messages on startup +A Added ability for chanserv/suspend and nickserv/suspend to take an expiry time +A Added no nickname ownership config option +A Added m_rewrite +A Added akill IDs +F Fixed crash in clearusers +F Fixed crash in /os oper info +F Fixed eventfd Config check to work properly on OpenVZ + +Anope Version 1.9.5 +------------------- +A Extended LDAP support +A Added os_oper, os_kill, os_forbid, m_statusupdate, cs_sync, and bs_autoassign +A Added a new configuration file format +A Added a new commands system +A Added a new access system, and cs_flags +F Fixed not logging debug logs to file +F Fixed the mail delay time +F Fixed sending account data for unconfirmed nicks +F Fixed poll() engine build on FreeBSD +F Fixed really large HELP replies being truncated +F Fixed sometimes appending !*@* to valid hosts on access lists +F Fixed m_ssl sometimes failing connecting for no reason +F Fixed crash in cs_entrymsg +F Fixed setting -P on channels with only a botserv bot in it +F Fixed modemanager complaining about prefixless modes on InspIRCd + +Anope Version 1.9.4 +------------------- +A Automatically set channel founder to the user with the highest access if there is no successor +A /chanserv clone command to copy settings from one channel to another. +A /chanserv mode command +A Ability for users to delete their own access in channels +A Added support for Plexus 3 +A Readded in support for /cs op/deop/etc to op/deop you in all channels +A Added LDAP support +A Added live SQL support +A Added support for learning tracking/storing/locking all modes at runtime +A Added m_alias +A Added support for XMLRPC queries +A Added /botserv set msg +A Added /operserv config +A Added /ns cert +A Added /operserv login +F Changed the GHOST command to not allow ghosting unidentified users if the RECOVER command exists +F Some failed logic in /operserv exception that prevents proper exceptions from being added +F Fixed the anope_os_sxlines MySQL table and code to work after restarting + +Anope Version 1.9.3 +------------------- +A Added italics BotServ kicks support +A Tell users when their nicks expire in /ns glist and /ns info +A Added SSL support +A Prevent negative mode changes, kicks, bans, and autokicks from affecting people with the 'god' user mode (On UnrealIRCd, usermode +q) +A Added nickserv/auxpex permission +A Added nickserv ungroup command +A Renamed the SGLINE to be SNLINE +A Added /chanserv saset command +A Added threads for mail sending +A Added m_dnsbl and an asynchronous DNS system +A Added a new language system that uses gettext +A Added m_mysql which uses threads to execute queries +A Added many subcommand modules for some commands, eg ns_set_autoop, ns_set_email, etc +A Added a new logging system that is a bit more flexible +A Added cs_set_misc and ns_set_misc to add miscellaneous set commands +A Added os_modreload, which allows reloading some modules not normally unloadable, like the protocol module +A Added FOUNDER access level +A Made OperServ, Global, MemoServ, and ChanServ optional +F Shutting down if a config reload fails +F Autoid to live through restarts on Unreal +F Storing vhosts in MySQL +F Not flushing the anope_extra table before rewriting database +F Anoperc start/stop to send the globaloncycle global, and fixed anoperc rehash to really rehash +F Fixed a potential crash if HostServ or BotServ was disabled + +Anope Version 1.9.2 +------------------- +A K alias to chanserv kick command +A KB alias to chanserv ban command +A The ability to register empty nonregistered channels +A Flatfile plaintext databases and removed old binary ones +A Added in live updating SQL and the ability to execute commands through SQL (see docs/MYSQL) +A Added support for many more modes into Anope and the ability to have generic support for modes unknown to Anope +A Added a mode stacker to combine many mode changes into fewer +A Added in the CS SET PERSIST command which can be used to keep service bots in channels even when the channel is empty +A Added AUTOOWNER OWNER and OWNERME into CS LEVELS +A Added ns_resetpass module to the core +A CS ACCESS VIEW which shows who added the access and last time used +A Last used time to CS AKICK VIEW +A Added a sha_256 encryption module +A Added the ability to load multiple encryption modules, and the ability to seamlessly convert your database between different encryptions +A Added configuration options to allow Anope to reconnect if it disconnects from the uplink instead of dying +A Added support for linking with IPv6 +F Unban command to accept an optional nick arg +F Some typos in services.conf +F Crash when users change their host that are identified to a group, but not a nick +F Host length checking in HS SET(ALL) and HS REQUEST +F Only show if a user is online in NS INFO if they are really identified for the group of the nick they are on +F Crash when using BSSmartJoin +F Converting access entries to access from xop when a users access is below voice +F A bad pointer passed to the OnDelEvent which could cause some 3rd party modules to crash +F CS FORBID allows to you forbid unregistered channels +F The -nothird command line option to work +F ms_rsend to really work +F SQUITing juped servers on InspIRCd1.2+ + +Anope Version 1.9.1 +------------------- +F Don't enforce akick/forbidden/etc.-restrictions on clients on ulined servers. +F Remove modules_unload_all fini + hack that goes with it. +F Signal handling cleanup. +A Seamless fantasy support on all ChanServ commands, instead of requiring bs_fantasy_*. +F Allow fantasy to be disabled on some commands (e.g. FORBID). +F Some commands (e.g. !help) need to strip the pre-provided channelname from them. +D HelpServ removed +F Command parser cleanup: mod_current_buffer removed and replaced with proper parser. Commands now indicate how they want the buffer split. +F Make NS ENFORCE/RELEASE stuff more sane, redo timers. +A Opertypes (similar to InspIRCd's opertypes) + +Provided by Ankit - 2009 +F Segfault on shutdown + +Provided by Adam - 2009 +F NickServ registration is sometimes denied. +F Applied patch from Adam to fix some potential screwups +F More fixes to bs_bot from Adam, plus an extra fix within DoAdd not covered in Adam's patch. +F Fix bs_bot to use the correct parameters, patch from Adam. +F Fix for bug #1004, based from second half of patch from Adam. +F Partial patch by Adam, commenting fix for #1006 for future reference. +F Forward-port r1946: Patch by Adam fixing #1006 (originally caused by #922): modes set by ChanServ are reversed. Thanks! + +Provided by DukePyrolator - 2009 +F Patch converting all match calls to new method, thanks! +F Add 'w' and 'y' support to dotime(), also prevent an overflow. +F Allow NS STATUS from unregistered users, thanks DP! +F Wild pointers do not a happy Anope make. Thanks DP :) +F Allow NS REGISTER to unregistered nicks, silly oversight. Thanks DP! :) +F Fix call order, thanks to DP +F Pass the right array to do_umode(), fixes mode tracking on Unreal. Thanks to DukePyrolator (yet again :P) +F Fix bs_set help, thanks to DukePyrolator! :) +F Fix two segfaults, noted by DukePyrolator. Thanks! +F Fix part one of #1010, reported by DukePyrolator. (Language settings are not respected in message sending.) Thanks! +F Memory leak on +beI modes. + +Provided by Liber - 2009 +F Support operoverride and such things (stop reversing changes from nonopped people where unnecessary) + +Anope Version 1.9.0 +------------------- +F Modified compile to use g++ +F Improve protocol modules support (classes, virtual methods, etc) +F Move core services to use BotInfo +F Move BotInfo and related methods into a class +F Move modules into a class +F Fixed ns resending of passcode issue +F Modules now delete themselves +F additional field where users' masked host can be stored so both masked IP and vhost are available instead of just one. +F No struct Uid, ugly, and, unnecessary that we store UID in BotInfo. +F Prevent deletion of core services via /bs bot +F Module subsystem cleanup ('modules' branch) +F Move modules to use classes somewhat (AnopeInit, AnopeFini) +F Change MODULE_INIT to return a pointer +F Remove duplicate module creation.. have loadModule return a pointer rather than creating one +F Remove buffered loading/unloading, this makes os_modunload perm, but who cares +F Remove 'delayed' loading, this is necessary because of before/after connected to ircd (ircd is before, rest after), I'm sure this can be done better. +A Remove old config, replace with insp-inspired (albeit bind format) config (CBX) +F Clean up protocol modules a bit +A InspIRCd 1.2 support +F Remove old (prior to 1.8.0) db compat +F Establish a proper base for services pseudoclients +F Add ss_main StatServ Hal9000 to play with :) +F Burn automake with fire (CBX) + +Provided by mooncup - 2009 +F Automatically reapply vhost on hs off for unreal. diff --git a/docs/Changes.conf b/docs/Changes.conf new file mode 100644 index 0000000..32b4977 --- /dev/null +++ b/docs/Changes.conf @@ -0,0 +1,220 @@ +Anope Version 2.0.12 +-------------------- +Added the regex_pcre2 module + +Anope Version 2.0.11 +-------------------- +No significant changes. + +Anope Version 2.0.10 +-------------------- +No significant changes. + +Anope Version 2.0.9 +------------------- +No significant changes. + +Anope Version 2.0.8 +------------------- +Fix ns_register:unconfirmedexpire not being used + +Anope Version 2.0.7 +------------------- +Add nickserv/recover permission +Add inspircd3 protocol module +Add default permission for chanstats saset chanstats command + +Anope Version 2.0.6 +------------------- +Mark enc_md5 and enc_sha1 as deprecated. Their use has been discouraged for years, and they will be removed in a future release. +Exempt all of 127.0.0.0/8 from m_dnsbl by default +Load m_sasl by default +Fix documentation for nickserv default option ns_keep_modes + +Anope Version 2.0.5 +------------------- +No significant changes. + +Anope Version 2.0.4 +------------------- +Removed m_sasl_dh-aes and m_sasl_dh-blowfish + +Anope Version 2.0.3 +------------------- +Add operserv/chankill to default globops log +Add ns_identify:maxlogins to limit the max number of concurrent logins per account +Document ns_no_expire nickserv default +Remove default session exception expiry time + +Anope Version 2.0.2 +------------------- +Add an operserv/oper/modify privilege, required to use oper add and oper del +Add a chanserv/access/list privilege, which allow readonly access to ChanServ access and akick lists +Changed m_dnsbl's result configuration to be more extensible +Add 'max' setting to cs_mode +Add 'nickchars' setting to networkinfo +Add 'botserv/fantasy', 'chanserv/access/list', and 'operserv/oper/modify' oper privileges +Fix 'emailchange_message' to include the proper email address +Set a default permission on operserv/defcon + +Anope Version 2.0.1 +------------------- +Add MUTE command to BotServ fantasy configuration +Document memo_mail option in nickserv.conf +Add 'show' setting to ns_info and cs_info to control which fields are shown to non opers + +Anope Version 2.0.0 +------------------- +options:passlen, enforceruser, enforcerhost, releasetimeout, and guestnickprefix moved to nickserv's module configuration +options:hideregisteredcommands added +m_ssl renamed to m_ssl_openssl +mail:restrict removed + +Anope Version 1.9.9 +------------------- +There is not many config changes between 1.9.8 and 1.9.9, however many of the +options have been moved around to make more sense, too many to list here, +so get a new config. + +Anope Version 1.9.8 +------------------- +networkinfo:chanlen added +options:user and options:group added +nickserv:modesonid added to set modes on everyone who identifies +nickserv:kill and nickserv:killquick added to configure NickServ's kill timeout +nickserv:restoreonrecover added to try to restore a user's session after a ghost +command:group added +fantasy block added +dns block has been moved to modules.conf as a part of m_dns + +Anope Version 1.9.7 +------------------- +operserv:notifications removed in favor of log{} blocks +options:regexengine added +options:casemap added +chanserv:require added +nickserv:registration added, emailregistration removed. +nickserv:unregistered_notice added + +Anope Version 1.9.6 +------------------- +service:channels added to join services to channels +mail block modified to allow configuring of email messages +oper:host and oper:vhost added +oper:require_oper added +options:nonicknameownership added +operserv:akillids added +nickserv/access oper privilege added + +Anope Version 1.9.5 +------------------- +Don't even try it, get a new config and start over. + +Anope Version 1.9.4 +------------------- +** ADDED CONFIGURATION DIRECTIVES ** +memoserv:modules added ms_ignore +chanserv:modules added cs_clone and cs_mode +nickserv:suspendexpire and nickserv:forbidexpire added +chanserv:suspendexpire and chanserv:forbidexpire added +module added cs_entrymsg +nickserv:modules added ns_ajoin, ns_cert +options:nomlock added +log:target added globops +nickserv:confirmemailchanges added +operserv:modules added os_config, os_login + +** MODIFIED CONFIGURATION DIRECTIVES ** +operserv:notifications removed osglobal, osmode, oskick, osakill, ossnline, ossqline, osszline, osnoop, osjupe, getpass, setpass, forbid, drop +renamed nickserv:preregexpire to nickserv:unconfirmedexpire + +** DELETED CONFIGURATION DIRECTIVES ** +opertype:commands removed operserv/umode +operserv:modules removed os_umode + +Anope Version 1.9.3 +------------------- +** ADDED CONFIGURATION DIRECTIVES ** +nickserv/auspex privilege added +SSL module added for SSL support +opertype:inherits added to allow opertypes to inherit commands and privs from other opertypes +Various nickserv/saset/* and chanserv/saset/* opertype command privileges added +nickserv:modules added many new ns_set_command modules +chanserv:modules added many new cs_set_command modules +opertype:commands added nickserv/saset/* and chanserv/saset/* +options:socketengine added to choose what socket engine to use +module:cs_set_misc and module:ns_set_misc added to replace the old set url/icq/email modules +options:hideprivilegedcommands added to hide privileged commands from normal users +log block added to customize logging +dns block added to configure dns settings +m_dnsbl added +mysql configuration block added + +** MODIFIED CONFIGURATION DIRECTIVES ** +opertype:commands changed operserv/sgline to opserv/snline +operserv:modules changed os_sgline to os_snline +operserv:modules added os_modreload +operserv:sglineexpiry changed to operserv:snlineexpiry +operserv:killonsgline changed to operserv:killonsnline +operserv:notifications ossgline changed ossnline +memoserv was made optional +moved operserv:global configuration into its own global block +chanserv was made optional + +** DELETED CONFIGURATION DIRECTIVES ** +serverinfo:helpchannel removed because it has been readded in m_helpchan +networkinfo:logchannel, logbot, logusers, logmaxusers, logchannel, and options:keeplogs removed because of the log block +dumpcore because it really didn't do anything + +Anope Version 1.9.2 +------------------- +** ADDED CONFIGURATION DIRECTIVES ** +options:enablelogchannel added to auto turn on the logchannel on startup +options:mlock added to configure the default mlock modes on new channels +options:database added for the database modules +options:botmodes added to configure modes BotServ bots should use +options:userlen added to configure maximum ident length +options:hostlen added to configure maximum hostname length +options:database added to configure what database modules to use +options:passlen added to specify the maximum length of passwords +uplink:ipv6 added to enable IPv6 connectivity +options:maxretries added to specify the number of reconnect attempts allowed +options:retrywait added to specify how long to wait between reconnect attempts +opertype command chanserv/aop/list removed as it was unnecessary, use chanserv/access/list instead + +** MODIFIED CONFIGURATION DIRECTIVES ** +options:encryption added enc_sha256 +chanserv:modules added cs_unban +nickserv:modules added ns_resetpass + +** DELETED CONFIGURATION DIRECTIVES ** +nickserv:database deleted because of new database system +nickserv:prenickdatabase deleted because of new database system +chanserv:database deleted because of the new database system +botserv:database deleted because of the new database system +hostserv:database deleted because of the new database system +operserv:database deleted because of the new database system +operserv:newsdatabase deleted because of the new database system +operserv:exceptiondatabase deleted because of the new database system +hs_request:database deleted because of the new database system +os_ignore:database deleted because of the new database system +serverinfo:localport deleted + +Anope Version 1.9.1 +------------------- +** ADDED CONFIGURATION DIRECTIVES ** +Opertypes have been added, through the opertype blocks. +Services Operators are now specified in the oper blocks. + +** MODIFIED CONFIGURATION DIRECTIVES ** +botserv:modules no longer contains bs_fantasy* modules, fantasy is now seamless. +operserv:modules has replaced os_logonnews, os_opernews, and os_randomnews with os_news. +operserv:modules no longer contains os_admin and os_oper modules, removed in favor of oper blocks. +operserv:notifications no longer contains osraw due to removal of OS RAW. + +** DELETED CONFIGURATION DIRECTIVES ** +Nick tracking has been removed as an option. +Restricting of NS GETPASS and CS GETPASS removed in favor of opertypes. +Host Setters were removed in favor of opertypes. +HelpServ has been removed entirely. +operserv:disableraw removed due to removal of OS RAW. diff --git a/docs/DEFCON b/docs/DEFCON new file mode 100644 index 0000000..dbc981d --- /dev/null +++ b/docs/DEFCON @@ -0,0 +1,93 @@ +Anope DefCon +------------ + +1) Introduction +2) Installation +3) Configuration +4) Usage +5) Usage Example +6) Support + +1) Introduction + + Anope 1.6 onwards supports a unique protection mechanism based on the + military "Defense Readiness Condition" (DefCon) system. It is based on + 5 levels of defense readiness defined as: + + DEFCON5 Normal peacetime readiness + DEFCON4 Increased intelligence and security readiness + DEFCON3 Increase in force readiness + DEFCON2 Further increase in force readiness + DEFCON1 Maximum force readiness. + + These are configurable levels that mandates what actions Anope should + take in case of emergency and change in readiness status. + + It is used to prevent abuse to both Services, and the ircd on which they + are running. Also to protect the users, primarily in the event of Clones + and/or FloodBOT attacks. + +2) Installation + + The DefCon system is part of Anope's core, + + The DefCon system has to be configured on your operserv.conf file to + be enabled. Defcon will be disabled if "defaultlevel" in the defcon + block is left commented, or set to 0. Look for the defcon block + on your operserv.conf file for more information on enabling and + configuring it. + + Make sure you restart Anope after changing the DefCon configuration + directives. + +3) Configuration + + Pre-defined DefCon actions: + + No new channel registrations + No New Nick Registrations + No Mode Lock changes + Force Chan Mode + Use Reduced Session Limit + KILL any new clients trying to connect + Services will ignore everyone but opers + Services will silently ignore everyone but opers + AKILL all new clients trying to connect + No new memos sent to block MemoServ attacks + + Information regarding how to enable this for specific defcon levels can + be found in operserv.conf + +4) Usage + + Anope starts up in DEFCON5 (normal readiness). To change the Defcon level + in action use: + + /msg OperServ DEFCON 1|2|3|4|5 + +5) Usage Example + + Place the network on DEFCON4: + + /msg OperServ DEFCON 4 + + -OperServ- Services are now at DEFCON 4 + -OperServ- * No new channel registrations + -OperServ- * No new nick registrations + -OperServ- * No mode lock changes + -OperServ- * Use the reduced session limit of 5 + + -Global- The Defcon Level is now at: 4 + + Restore normal readiness: + + /msg OperServ DEFCON 5 + + -OperServ- Services are now at DEFCON 5 + + -Global- Services are now back to normal, sorry for any inconvenience + +6) Support + + You might get DefCon support by posting on our online forum, or maybe on + our #anope channel at /server irc.anope.org. diff --git a/docs/EVENTS b/docs/EVENTS new file mode 100644 index 0000000..54e9c87 --- /dev/null +++ b/docs/EVENTS @@ -0,0 +1,34 @@ +Anope Internal Events +--------------------- + +1) Intro +2) Using Events + +1) Introduction to Internal Events + + Internal Events are setup to give module developers more information + about what the core is doing at different times. This information can + be as complex as data we are feeding to the uplink, to simple triggered + events such as the databases being saved. + + Additionally there is a module included with the core + which can provide some clue as to how to use the code in your modules. + The rest of this document assumes that you are used to writing modules. + +2) Using Events + + Each Event in Anope calls a function. + You must override these functions in your main modules class. + The full list of functions and parameters are in modules.h. In this + case, you would be overriding OnJoinChannel() and OnPartChannel() like so: + + void OnJoinChannel(User *u, Channel *c) anope_override { } + void OnPartChannel(User *u, Channel *c) anope_override { } + + Some of these event overrides can be used to prevent or allow things to + happen that would normally not be allowed or denied. You can also use + ModuleManager (not explained here) to set control which order the modules + are queried (when multiple modules hook to the same event). + + The "anope_override" identifier is for compatibility with C++11. + Its usage is highly recommended. diff --git a/docs/FAQ b/docs/FAQ new file mode 100644 index 0000000..c066158 --- /dev/null +++ b/docs/FAQ @@ -0,0 +1,10 @@ +Frequently Asked Questions (FAQ) concerning Anope +------------------------------------------------- + +The information in the 2.0 FAQ is subject to change at any +moment due to new developments. Please visit our website +for the most up to date information. + +An updated version of the FAQ can be found here: + +https://wiki.anope.org/index.php/2.0/FAQ diff --git a/docs/INSTALL b/docs/INSTALL new file mode 100644 index 0000000..1ad9533 --- /dev/null +++ b/docs/INSTALL @@ -0,0 +1,135 @@ +Anope Installation Instructions +------------------------------- + +1) Installing Anope +2) Upgrading Anope +3) Setting up the IRCd +4) Starting Anope +5) Setting up a crontab + +Note: You should also read the README and FAQ files! + +1) Installing Anope + + IMPORTANT NOTE: it is not recommended to use (and therefore install) + Anope as root. Use an unprivileged user instead -- the + one you're using for the ircd or a dedicated one will + be good enough. + + The very first thing you need to do is to get the Anope package (if not + already done). You can find it at: + + https://www.anope.org/ + + Anope requires cmake to build. You can check if CMake is already + installed on your system using the command: + + cmake --version + + If it's installed, you will get a line that says something similar to + "cmake version 2.8.12.2". If the version is less than 2.4 or you get + an error saying the command was not found, you will not be able to use + CMake unless you install it yourself into your home directory. CMake + can be downloaded from: + + https://cmake.org/download/ + + Next, unpack the package in your home directory, and go into the created + directory. + + If there are any extra modules you want to enable, such as m_mysql, run + the 'extras' script to enable them. If you do not know you can come back + later and enable them. + + Now type ./Config to start the configuration script. It will ask you a + few questions, and figure out how to compile Anope on your system. If + you are unsure about the answer to a question, use the default value. + + Now cd build and type make and make install. This will install + all the needed files in the paths you specified with the configure + script, and setup file permissions. You should ensure that the data + directory is not accessible by other users, as malicious users may + cause trouble on your network if passwords are not encrypted, or read + the memos of any user. + + Now go into the conf directory (by default, ~/services/conf). Copy the example + configuration file (example.conf) to services.conf, and open the latter + with your favorite text editor. It contains all the configuration + directives Anope will use at startup. Read the instructions contained in + the file carefully. Using the default values is NOT a good idea, and will + most likely not work! + + If you need help, you should visit https://forum.anope.org/ or #anope on + irc.anope.org. Provide *complete* error output, along with other relevant + information eg. OS, compiler and C++ library versions. + See the README file for more information. + +2) Upgrading Anope + + To upgrade Anope, just follow the installation instructions described in + section 1. There are however a few specific guidelines: + + * IMPORTANT: Back up your old databases! + * If you are upgrading to a new major release, ALWAYS restart a + fresh configuration file from example.conf. + +3) Setting up the IRCd + + Services acts as an IRC server with pseudo-clients on it. To link them to + your network, you'll need to configure your IRCd to allow services to link. + + The configuration varies depending on the IRCd, but you will probably need + a link block (also called connect block, or C line), a U line (also called + a shared block), and be sure that the IRCd is listening on the given port + in the link block. + + Example link configurations can be found in example.conf for some of the + popular IRCds. + + Don't forget to /rehash your IRCd to apply changes. + + You may also try our interactive link maker, which is located at: + + https://www.anope.org/ilm.php + +4) Starting Anope + + Go into the directory where binaries were installed (by default, this is + ~/services/bin). Type ./services to launch Anope. + + If there are syntax errors in the configuration file they will be + displayed on the screen. Correct them until there are no errors anymore. + A successful startup won't generate any message. + + Give Services at least one minute to link to your network, as certain + IRCds on some OSes may be really slow for the link process. If nothing + happens after about a minute, it is probably a configuration problem. Try + to launch Anope with ./services -debug -nofork to see any errors that it + encounters, and try to correct them. + + If you need help to solve errors, feel free to subscribe to the Anope + mailing list and ask there. See the README file for details. + +5) Setting up a crontab + + A crontab entry will allow you to check periodically whether Anope is + still running, and restart it if not. + + First rename the example.chk script that is in Anope path (by default, + this is ~/services/conf) to services.chk and edit it. You'll need to + modify the CONFIGURATION part of the file. Then ensure that the file is + marked as executable by typing chmod +x services.chk, and try to launch the + script to see if it works (Anope must not be running when you do this ;)) + + When this is done, you'll have to add the crontab entry. Type crontab -e. + This will open the default text editor with the crontab file. Enter the + following (with correct path): + + */5 * * * * /home/ircd/services/conf/services.chk >/dev/null 2>&1 + + The */5 at the beginning means "check every 5 minutes". You may replace + the 5 with other another number if you want (but less than 60). Consult + your system's manual pages for more details on the syntax of the crontab + file. Interesting manpages are crontab(5), crontab(1) and cron(8). + + Save and exit, and it's installed. diff --git a/docs/INSTALL.fr b/docs/INSTALL.fr new file mode 100644 index 0000000..245af3e --- /dev/null +++ b/docs/INSTALL.fr @@ -0,0 +1,149 @@ +Instructions d'installation d'Anope +----------------------------------- + +1) Installation d'Anope +2) Mettre à jour Anope +3) Configuration de l'IRCd +4) Mettre en route Anope +5) Mettre en place un crontab + +Note : Vous devrez également lire les fichiers README et FAQ ! + +1) Installation d'Anope + + NOTE IMPORTANTE : il est déconseillé d'utiliser (et même d'installer) + Anope en tant que root. Utilisez un utilisateur non + privilégié. Celui que vous utilisez pour l'IRCd ou + un utilisateur dédié suffira. + + La première chose que vous devez faire est d'obtenir le package Anope + (si ce n'est déjà fait). Vous pouvez le trouver ici : + + https://www.anope.org/ + + Anope nécessite cmake pour être compilé. Vous pouvez vérifier si CMake + est déjà installé sur votre système avec la commande : + + cmake --version + + Si CMake est installé, vous aurez une ligne qui dit quelque chose comme + "cmake version 2.8.12.2". Si la version est inférieure à 2.4 ou si vous + obtenez une erreur disant que la commande n'a pas été trouvée, vous ne + pourrez pas utiliser CMake à moins de l'installer vous-même dans votre + répertoire home. CMake peut être téléchargé ici : + + https://cmake.org/download/ + + Ensuite, décompressez le package dans votre répertoire home, et allez + dans le répértoire qui vient d'être créé. + + Si il y a des modules facultatifs que vous voulez activer comme m_mysql, + exécuter le script 'extras' pour les activer. Si vous ne savez pas, vous + pouvez les activer plus tard. + + Maintenant, tapez ./Config pour lancer le script de configuration. Il + va vous poser quelques questions, et déterminer comment compiler Anope + sur votre système. Si vous ne savez pas comment répondre à une question, + utilisez la valeur par défaut. + + Allez dans le dossier build (cd build) et tapez make et make install. + Ceci va installer tous les fichiers nécessaires dans les dossiers que + vous avez indiqués avec le script Config et régler les permissions des + fichiers. Vous devez vous assurer que le répertoire data n'est pas + accessible par les autres utilisateurs, car des utilisateurs + malveillants pourraient causer des problèmes sur votre réseau, si les + mots de passe ne sont pas chiffrés, ou lire les mémos de tous les + utilisateurs. + + Allez maintenant dans le répertoire conf (par défaut, ~/services/conf). + Copiez l'exemple de fichier de configuration (example.conf) en + services.conf et ouvrez ce dernier avec votre éditeur de texte favori. + Il contient toutes les directives de configuration qu'Anope va utiliser + en démarrant. Lisez attentivement les instructions contenues dans le + fichier. L'utilisation des valeurs par défaut n'est pas toujours + recommandée, et Anope ne fonctionnera probablement pas ! + + Si vous avez besoin d'aide, vous pouvez aller sur le site + https://forum.anope.org/ ou le canal #anope sur irc.anope.org. + Fournissez *l'essemble* des erreurs qui apparaîssent, en plus de + toutes informations utiles, comme les versions de votre OS, du + compilateur utilisé et de la librairie C++. Lisez le fichier README + pour plus d'informations. + +2) Mettre à jour Anope + + Pour mettre à jour Anope, suivez simplement les instructions + d'installation décrites dans la section 1. Prenez garde cependant : + + * IMPORTANT : Sauvegardez vos anciennes bases de données ! + * Si vous mettez à jour vers une nouvelle version majeure, + recommencez *toujours* toute votre configuration à partir du + fichier example.conf. + +3) Configuration de l'IRCd + + Les Services agissent comme un serveur IRC avec des pseudo-clients. + Pour les relier à votre réseau, vous aurez besoin de configurer votre + IRCd pour permettre aux services de se connecter. + + La configuration dépend de l'IRCd utilisé, mais vous aurez probablement + besoin d'un bloc link (aussi appelé connect block, ou C:line) et un + U:line (aussi appelé shared block). Assurez-vous que l'IRCd écoute + sur le port donné dans le bloc link. + + Des exemples de configurations de bloc link peuvent être trouvés dans + le fichier example.conf pour certains des IRCd les plus populaires. + + Souvenez-vous de /rehash votre IRCd pour appliquer les changements. + + Vous pouvez également essayer notre créateur de bloc link interactif + situé ici : + + https://www.anope.org/ilm.php + +4) Mettre en route Anope + + Allez dans le répertoire où les fichiers binaires ont été installés + (par défaut, ~/services/bin). Tapez ./services pour lancer Anope. + + S'il y a des erreurs de syntaxe dans le fichier de configuration, elles + seront affichées à l'écran. Corrigez-les jusqu'à ce qu'il n'y en ait + plus. Un démarrage réussi ne générera pas de message. + + Donnez aux services au moins une minute pour se connecter à votre + réseau, car certains IRCds sur certains systèmes peuvent être très + lents pour le processus de liaison. Si rien ne se passe après environ + une minute, il y a probablement un problème de configuration. Essayez + de lancer Anope en mode debug avec ./services -debug -nofork pour voir + toutes les erreurs rencontrées et essayez de les corriger. + + Si vous avez besoin d'aide pour résoudre des erreurs, n'hésitez pas à + vous abonner à la liste de diffusion Anope et d'y poser vos question. + Voir le fichier README pour plus de détails. + +5) Mettre en place un crontab + + Une entrée crontab vous permettra de vérifier périodiquement si Anope + est toujours en cours d'exécution et de le redémarrer s'il n'est pas. + + D'abord renommez le script example.chk qui est dans les dossiers + d'Anope (par défaut, ~/services/conf) en services.chk et modifiez-le. + Vous aurez besoin de modifier la partie CONFIGURATION du fichier. + Assurez-vous ensuite que le fichier est marqué comme exécutable en + tapant chmod +x services.chk et essayez de lancer le script pour voir + si cela fonctionne (Anope ne doit pas être en marche lorsque vous + testez cela ;)) + + Lorsque c'est fait, vous devrez ajouter l'entrée crontab. Entrez + crontab -e. Cela va ouvrir l'éditeur de texte par défaut avec le + fichier crontab. Entrez la ligne suivante (avec le chemin correct) : + + */5 * * * * /home/ircd/services/conf/services.chk > /dev/null 2>&1 + + Le */5 au début signifie "vérifier toutes les 5 minutes". Vous pouvez + remplacer le 5 par un autre numéro si vous voulez (mais moins de 60). + Consultez les pages de manuel de votre système pour plus de détails sur + la syntaxe du fichier crontab. Les pages de manuel intéressantes sont + crontab(5), crontab(1) et cron(8). + + Sauvegardez, quittez, et c'est installé ! diff --git a/docs/LANGUAGE b/docs/LANGUAGE new file mode 100644 index 0000000..b2e72cc --- /dev/null +++ b/docs/LANGUAGE @@ -0,0 +1,53 @@ +Anope Multi Language Support +---------------------------- + +1) Building Anope with gettext support +2) Adding a new language +3) Using languages with modules + +1) Building Anope with gettext support + + To build Anope with gettext support, gettext and its development libraries must be installed on the system. + + On Debian install the locales-all package. + + On Ubuntu run locale-gen for each language you want to enable. + For example: + locale-gen es_ES.UTF-8 + + Then execute: + dpkg-reconfigure locales + + Building Anope on Windows with gettext support is explained in docs/WIN32.txt + +2) Adding a new language + + Anope uses gettext (https://www.gnu.org/software/gettext/) to translate messages for users. To add a new language + install gettext and run `msginit -l language -o anope.language.po -i anope.pot`. For example if I was translating to + Spanish I could run `msginit -l es_ES -o anope.es_ES.po -i anope.pot`. Open the newly generating .po file and start + translating. Once you are done simply rerun ./Config; make && make install and add the language to your services.conf. + Note that on Windows it is not quite this simple, windows.cpp must be edited and Anope recompiled and restarted. + + Poedit (https://poedit.net/) is a popular po file editor, and we recommend using it or another editor designed to edit + po files (especially on Windows). + + If you have finished a language file translation and you want others to use it, please send it to team@anope.org + (don't forget to mention clearly your (nick)name, your e-mail and the language name). You'll of course get full credit for it. + + NOTE: There is no guarantee we will use your work so please do not be offended if we say no thanks. + +3) Using languages with modules + + Module authors can easily add the ability to have their modules translated by adding _() around the strings they + want translated (messages to the user, etc). + + If you want to translate a module someone has made, first generate a .pot file if there isn't one already using + `xgettext -s -d modulename -o modulename.pot --from-code=utf-8 --keyword --keyword=_ modulename.cpp`. + The .pot file is a template of all of the language strings extracted from the source file. + + Next, run msginit on the .pot file with + `msginit -l language -o modulename.language.po -i modulename.pot`. + Translate the new .po file and rerun ./Config; make && make install. + + All .po and .pot files should be placed in modules/third/language. Additionally an update script is provided there + that will create .pot files and merge any changes to it with existing .po files. diff --git a/docs/MODULES b/docs/MODULES new file mode 100644 index 0000000..52cb3b2 --- /dev/null +++ b/docs/MODULES @@ -0,0 +1,128 @@ +Anope Modules +------------- + +1) Introduction +2) Installation +3) Usage +4) Usage Example +5) More Modules +6) Support +7) Information for Developers +8) Modules Repository + +1) Introduction + + Anope 1.6 onwards supports external modules. External modules are pieces + of code that can be attached to a running Anope process dynamically. These + modules can serve several purposes, and perform all kind of operations to + enhance your network. + +2) Installation + + 1. If modules are supported by your system, they will be configured + automatically when you run ./Config. The modules will be installed + to the modules directory in your data path (by default this will + be ~/services/data/modules). + + 2. Compile Anope as usual using ./Config. The "make" process will now + compile module support into Anope, and compile the default sample + modules, and any other module located in the modules folder or any + of its sub-directories, eg. modules/extra. + + 3. Install Anope as usual. The "make install" process will place the + compiled modules in their runtime location, making them available + for loading. + + 4. Start or restart services to make use of the new Anope executable. + Note that you do not need to restart to load new or changed modules, + only to make use of a new Anope executable. + +3) Usage + + All module manipulation commands are done through OperServ. These are: + + MODLOAD Load a module + MODRELOAD Reload a module + MODUNLOAD Un-Load a module + MODLIST List loaded modules + MODINFO Info about a loaded module + + Access to the above commands require the operserv/modload and modlist + permissions. Refer to operserv.example.conf. + + You can also load (and pre-load) Modules automatically by loading them + on startup. To do so, edit any one of the configuration files (you may + want to use modules.conf for third-party/extra modules, or a config + file relevant to the *Serv your module operates on, eg. hostserv.conf), + and use the following method to load a module on startup or reload: + module { name="hs_modname" } + +4) Usage Example + + /msg OperServ modload ns_identify + -OperServ- Module ns_identify loaded + + /msg OperServ modinfo ns_identify + -OperServ- Module: ns_identify Version: 1.9.7 Author: Anope loaded: Jun 17 18:43:08 2012 BST (2 minutes ago) + -OperServ- Providing service: nickserv/identify + -OperServ- Command ID on NickServ is linked to nickserv/identify + -OperServ- Command IDENTIFY on NickServ is linked to nickserv/identify + + /msg OperServ modreload ns_identify + -OperServ- Module ns_identify reloaded + + /msg OperServ modunload ns_identify + -OperServ- Module ns_identify unloaded + + /msg NickServ IDENTIFY + -NickServ- Unknown command identify. "/msg NickServ HELP" for help. + NOTE: Doing the above, with the command still existing in a config file, + will result in a log message, similar to the following: + <@NickServ> Command IDENTIFY exists on me, but its service nickserv/identify was not found! + + * Note that the name of the module source file is "ns_identify.cpp", yet we + load and reference the module as "ns_identify" only. By naming convention + modules have an abbreviated service name they attach to (hs_ for + HostServ, cs_ for ChanServ, etc) followed by a descriptive keyword. + +5) More Modules + + You can download more useful modules from https://modules.anope.org/. Just + grab the module file (usually with a .cpp extension). Place the module + file in your modules (anope-1.9.x/modules/third) folder; although any of + the other folders within the modules directory will work. + + The new modules need to be compiled and installed before you can make + use of them: + + 1. Make sure you're in the main source directory. (usually anope-1.X.XX/) + 2. Run ./Config to find and configure modules, then `cd build`. + 3. Run `make` to compile Anope, and any modules. + 4. Run `make install` to copy the compiled binaries to the ~/services/ + directory. + + You can now use /msg OperServ MODLOAD to load the new modules. + +6) Support + + The Anope team is not responsible or liable for any unofficial module + (i.e. anything other than what was released with the Anope package). + + Use modules at your own risk, and make sure you get them from a + reputable source. You might get module support by contacting the module + author, posting on our online forum, or maybe on our #anope channel + at /server irc.anope.org. + +7) Information for Developers + + There are a number of useful documents on the Anope Wiki. The Anope Wiki + can be reached at: + + * https://wiki.anope.org/ + +8) Modules Repository + + You can find modules at https://modules.anope.org/ + + These modules are 3rd party and as such are not supported by the Anope Team. + Contact the Module Author directly with problems, not the Anope Team. diff --git a/docs/NEWS b/docs/NEWS new file mode 100644 index 0000000..07911e6 --- /dev/null +++ b/docs/NEWS @@ -0,0 +1,6 @@ +Highlighted News in Anope 1.9 +============================= + +* Added in live updating SQL and the ability to execute commands through SQL +* Re-designed configuration file +* Code refresh / rewrite into C++ diff --git a/docs/README b/docs/README new file mode 100644 index 0000000..2687f0e --- /dev/null +++ b/docs/README @@ -0,0 +1,258 @@ +Anope -- a set of IRC services for IRC networks +----------------------------------------------- + +Anope is 2003-2022 Anope Team . +Based on Epona 2000-2002 PegSoft . +Based on Services 1996-1999 Andrew Church . + +This program is free but copyrighted software; see the file COPYING for +details. + +Information about Anope may be found at https://www.anope.org/ + +Table of Contents +----------------- +1) Credits +2) Presentation +3) Installation +4) Command Line Options +5) Messages Translation +6) Contact + +1) Credits + + Anope is based on Lara's Epona version 1.4.14. + Epona is based on Andy Church's IRC Services version 4.3.3. + + The original credits: + + * Mauritz Antunes + Portuguese translation + * Jose R. Holzmann, Raul S. Villarreal + Spanish translation + * Andrew Kempe + News system + * + Italian translation + * + Turkish translation + * Andrew Kempe + Session limiting + + Epona credits: + + * lara + Main coding + * CafeiN + Turkish translation + * Sylvain Cresto aka tost + FreeBSD 5 patch + * Marcelo Conde Foscarini aka Bras + Portuguese translation + * Alvaro Toledo aka POLLITO + Spanish translation + * chemical + German translation + * shine + German translation + * Guven Guzelbey aka MeShGuL + Turkish translation + * Jordi Pujol + Catalan translation + * Eva Dachs + Catalan translation + * Toni Perez + Catalan translation + * Sergios Karalis + Greek translation + * Thomas J. Stensas aka ShadowMaster + Ultimate 3.x support + + Anope credits: + + * Adam Kramer + * Adam + * Alvaro Toledo + * Amanda Folson + * Andrew Berquist + * Björn Stiddien + * Charles Kingsley + * Chris Hogben + * Daniel Engel + * David + * David Narayan + * David Robson + * Daniele Nicolucci + * Florian Schulze + * Gabriel Acevedo H. + * Jan Milants + * Jens Voss + * JH + * Joris Vink + * Lee Holmes + * Lucas Nussbaum + * Mark Summers + * Matthew Beeching + * Naram Qashat + * Phil Lavin + * Pieter Bootsma + * Robin Burchell + * Sean Roe + * Sebastian V + * Thomas Juberg Stensås + * Trystan .S Lee + * openglx + + Anope Translations: + + * Robby (nl_NL) + * Kein (ru_RU) + * Maik Funke (de_DE) + * Isaac Fontal (es_ES) + * Janos Kapitany (hu_HU) + * Szymon S'wierkosz (pl_PL) + * Christopher N. (fr_FR) + * Yusuf Kurekci (tr_TR) + + Anope Web panel: + + * Denis M. (Phr33d0m) + +2) Presentation + + Anope is a set of Services for IRC networks that allows users to manage + their nicks and channels in a secure and efficient way, and administrators + to manage their network with powerful tools. + + Currently available services are: + + * NickServ, a powerful nickname manager that users can use to protect + themselves against nick stealing. Each user has its own nickname + group, that allows the user to register as many nicks as needed + while still being able to take profit of his privileges and to + modify the nick configuration. NickServ also has an optional + password retrieval feature. + + * ChanServ, a powerful channel manager that helps users to administer + their channels in a totally customizable way. ChanServ has an + internal list of privileged users and banned users that controls + accesses on a per-channel basis. It eliminates all takeover + problems, because of its powerful op/unban/invite and even mass + deop and mass kick functions. + + * MemoServ, an helpful companion that allows sending short messages + to offline users, that they can then read when they come online + later. + + * BotServ, an original service that allows users to get a permanent, + friendly bot on their channels in an easy way. Each bot can be + configured to monitor the channels against floods, repetitions, + caps writing, and swearing, and to take appropriate actions. It + also can handle user-friendly commands (like !op, !deop, !voice, + !devoice, !kick, and many others), say a short greet message when + an user joins a channel, and even "take over" ChanServ actions such + as auto-opping users, saying the entry notice, and so on. This + service can be disabled if you want to save some bandwidth. + + * OperServ, the IRCops' and IRC admins' black box, that allows them + to manage the list of network bans (also known as AKILL (DALnet) or + GLINE (Undernet)), to configure messages displayed to users when + they log on, to set modes and to kick users from any channel, to + send notices quickly to the entire network, and much more! + + * HostServ, a neat service that allows users to show custom vHosts + (virtual hosts) instead of their real IP address; this only works + on daemons supporting ip cloaking, such as UnrealIRCd. + + Anope currently works with: + + * Bahamut 1.4.27 or later (including 1.8) + * Charybdis 3.4 or later + * ircd-hybrid 8.2.23 or later + * InspIRCd 1.2 or later + * ngIRCd 19.2 or later + * Plexus 3 or later + * Ratbox 2.0.6 or later + * UnrealIRCd 3.2 or later + + Anope could also work with some of the daemons derived by the ones listed + above, but there's no support for them if they work or don't work. + + +3) Installation + + See the INSTALL file for instruction on installing Anope. + + +4) Command Line Options + + Normally, Anope can be run simply by invoking the "services" executable. + Any of the following command-line options can be specified to change + the behavior of Anope: + + --debug Enable debugging mode; more info sent to log (give + option more times for more info) + --readonly Enable read-only mode; no changes to databases + allowed + --nofork Do not fork after startup; log messages will be + written to terminal + --noexpire Expiration routines won't be run at all + --version Display the version of Anope + --nothird Do not load the non-core modules specified + --protocoldebug Debug each incoming message after protocol parsing + --support Used for support, same as --debug --nofork --nothird + + Upon starting, Anope will parse its command-line parameters then + (assuming the --nofork option is not given) detach itself and run in the + background. If Anope encounters a problem reading the database files or + cannot connect to its uplink server, it will terminate immediately; + otherwise, it will run until the connection is terminated (or a QUIT, + SHUTDOWN, or RESTART command is sent; see OperServ's help). + + In the case of an error, an appropriate error message will be written to + the log file. + + If Anope is run with the "--readonly" command-line option, it can serve as + a "backup" to the full version of services. A "full" version of services + (run without --readonly) will automatically reintroduce its pseudo-clients + (NickServ, ChanServ, etc.), while a "backup" services will not, thus + allowing full services to be brought up at any time without disrupting + the network (and without having to take backup services down beforehand). + + The "--debug" option is useful if you find or suspect a problem in Anope. + Giving it once on the command line will cause all traffic to and from + services as well as some other debugging information to be recorded in + the log file; if you send a bug report, PLEASE include an excerpt from + the log file WITH DEBUGGING ACTIVE; we cannot emphasize enough how + important this is to tracking down problems. (You can also enable + debugging while Services is running using OperServ's SET DEBUG command.) + If you repeat use --debug=, the debugging level will be increased, + which provides more detailed information but may also slow Anope down + considerably and make the log file grow dramatically faster. In general, + a debug level of 1 is sufficient for the coding team to be able to trace + a problem, because all network traffic is included and we can usually + reproduce the problem. + +5) Messages Translations + + Please see LANGUAGE for this information + +6) Contact + + For announcements and discussions about Anope, please visit our + Portal and Forums at https://www.anope.org/ -- make sure you register + yourself to get full benefits. + + If you read the documentation carefully, and didn't find the answer to + your question, feel free to post on the website forums or join our irc + channel (irc.anope.org #anope). Once you join our Support channel be as + precise as possible when asking a question, because we have no extraordinary + powers and can't guess things if they aren't provided. + + The more precise you are the sooner you'll be likely to get an answer. + + If you think you found a bug, add it to the bug tracking system + (https://bugs.anope.org/) and - again - be as precise as possible. Also say + whether the bug happens always or under what circumstances, and anything + that could be useful to track your bug down. If you wrote a patch, send + it over. :) diff --git a/docs/REDIS b/docs/REDIS new file mode 100644 index 0000000..8f7a076 --- /dev/null +++ b/docs/REDIS @@ -0,0 +1,160 @@ +Starting in Anope 1.9.9, Anope has Redis database support (https://redis.io/). +This document explains the data structure used by Anope, and explains how +keyspace notification works. + +This is not a tutorial on how to use Redis, see https://redis.io/documentation +for that. + +Table of Contents +----------------- +1) Data structure +2) Keyspace notifications +3) Examples of modifying, deleting, and creating objects + +1) Data structure + + There are 4 key namespaces in Anope, they are: + + id - The keys in id are used to atomically create object ids for new + objects. For example, if I were to create a new BotInfo I would first: + + redis 127.0.0.1:6379> INCR id:BotInfo + + To get the object ID of the new object. + + ids - The keys in ids contain a set of all object ids of the given type. + For example: + + redis 127.0.0.1:6379> SMEMBERS ids:BotInfo + + Returns "1", "2", "3", "4", "5", "6", "7", "8" because I have 8 bots that + have IDs 1, 2, 3, 4, 5, 6, 7, and 8, respectively. + + hash - The keys in hash are the actual objects, stored as hashes. For + example, if I had just looked up all BotInfo ids and wanted to iterate + over all of them, I would start by: + + redis 127.0.0.1:6379> HGETALL hash:BotInfo:1 + + Which gets all keys and values from the hash of type BotInfo with id 1. + This may return: + + "nick" -> "BotServ" + "user" -> "services" + "host" -> "services.anope.org" + "created" -> "1368704765" + + value - The keys in value only exist to aid looking up object IDs. They + are sets of object IDs and are used to map key+value pairs to objects. + For example: + + redis 127.0.0.1:6379> SMEMBERS value:NickAlias:nick:Adam + + Returns a set of object ids of NickAlias objects that have the key + 'nick' set to the value 'Adam' in its hash. Clearly this can only + ever contain at most one object, since it is not possible to have + more than one registered nick with the same name, but other keys + will contain more than one, such as: + + redis 127.0.0.1:6379> SMEMBERS value:NickCore:email:adam@anope.org + + Which would return all accounts with the email "adam@anope.org". + + redis 127.0.0.1:6379> SMEMBERS value:ChanAccess:mask:Adam + + Which would return all access entries set on the account "Adam". + + Behavior similar to SQL's AND, can be achieved using the + SINTER command, which does set intersection on one or more sets. + +2) Keyspace notifications + + Redis 2.7 (unstable) and 2.8 (stable) and newer support keyspace notifications + (https://redis.io/topics/notifications). This allows Redis to notify Anope of + any external changes to objects in the database. Once notified, Anope will + immediately update the object. Otherwise, Anope keeps all objects in memory + and will not regularly read from the database once started. + + You can use this to modify objects in Redis and have them immediately reflected + back into Anope. Additionally you can use this feature to run multiple Anope + instances simultaneously from the same database (see also, Redis database + replication). + + To use keyspace notifications you MUST execute + + redis 127.0.0.1:6379> CONFIG SET notify-keyspace-events KA + OK + + or set notify-keyspace-events in redis.conf properly. Anope always executes + CONFIG SET when it first connects. + + If you do not enable keyspace events properly Anope will be UNABLE to see any + object modifications you do. + + The key space ids and value are managed entirely by Anope, you do + not (and should not) modify them. Once you modify the object (hash), Anope will + update them for you to correctly reflect any changes made to the object. + + Finally, always use atomic operations. If you are inserting a new object with + multiple commands, or inserting multiple objects at once, specifically if the + objects depend on each other, you MUST use a transaction. + +3) Examples of modifying, deleting, and creating objects + + These examples will ONLY work if you meet the criteria in section 2. + + If I want to change the email account 'Adam' to 'Adam@anope.org', I would execute the following: + + redis 127.0.0.1:6379> SMEMBERS value:NickCore:display:Adam + + Which returns a value of "1", which is the object id I want to modify. + Now to change the email: + + redis 127.0.0.1:6379> HSET hash:NickCore:1 email Adam@anope.org + + You can now see this in NickServ's INFO command: + -NickServ- Email address: Adam@anope.org + + If I want to drop the account "Adam", I would execute the following: + + redis 127.0.0.1:6379> SMEMBERS value:NickCore:display:Adam + + Which returns a value of "1". I would then check: + + redis 127.0.0.1:6379> SMEMBERS value:NickAlias:nc:Adam + + To see what nicknames depend on this account to exist, as I will + have to remove those too. This returns the values "2", and "3". + + Finally, I can drop the nick using a transaction via: + + redis 127.0.0.1:6379> MULTI + OK + redis 127.0.0.1:6379> DEL hash:NickAlias:2 + QUEUED + redis 127.0.0.1:6379> DEL hash:NickAlias:3 + QUEUED + redis 127.0.0.1:6379> DEL hash:NickCore:1 + QUEUED + redis 127.0.0.1:6379> EXEC + + Or alternatively simply: + + redis 127.0.0.1:6379> DEL hash:NickAlias:2 hash:NickAlias:3 hash:NickCore:1 + + If I wanted to create a BotServ bot, I would execute the following: + + redis 127.0.0.1:6379> INCR id:BotInfo + + Which returns a new object ID for me, in this example it will be "8". + Now I can create the object: + + HMSET hash:BotInfo:8 nick redis user redis host services.anope.org realname "Services for IRC Networks" + + Note if you are using HSET instead of HMSET you will need to use a transaction, as shown in the above example. + If you are watching your services logs you will immediately see: + + USERS: redis!redis@services.anope.org (Services for IRC Networks) connected to the network (services.anope.org) + + And the bot redis will be in BotServ's bot list. + Notice how ids:BotInfo and the value keys are updated automatically. diff --git a/docs/TOOLS b/docs/TOOLS new file mode 100644 index 0000000..5e8f139 --- /dev/null +++ b/docs/TOOLS @@ -0,0 +1,25 @@ +Anope Bundled Tools +------------------- + +1) Anope SMTP Client + + Provided with Anope is a simple SMTP client which can be used instead of + programs like SendMail in some cases. + + The SMTP client can be used instead of sendmail for use with Anope's mail + options. To use the SMTP client instead of sendmail, find the line in your + services configuration file (services.conf) that defines sendmailpath. On + that line, change the path to your services installation directory, then + followed by "bin/anopesmtp" and the IP address of a valid SMTP server. It + should look like this: + + sendmailpath = "/home/anope/services/bin/anopesmtp 127.0.0.1" + + If the SMTP client doesn't send mail, or if there's an other problem with + it, you can enable debug mode by passing the --debug flag after the server + address. This should generate a log file of what happened when it tried + to connect to the SMTP server. + + Credits: + Originally written by Dominick Meglio + Ported to *nix by Trystan Scott Lee diff --git a/docs/WIN32.txt b/docs/WIN32.txt new file mode 100644 index 0000000..2880cb0 --- /dev/null +++ b/docs/WIN32.txt @@ -0,0 +1,161 @@ +Anope for Windows +----------------- + +1) Building the Source +2) Installation +3) Compiling Modules +4) Other compile options +5) Credits + +1) Building the Source + + NOTE: If you have downloaded one of the pre-compiled installers, you do + NOT need to complete this step, and you can proceed to step 2. + + If you want to build Anope from source on a Win32 system, you will need + to follow this instructions: + + 1) Download the required files: + + * Current Anope source: + https://github.com/anope/anope/releases + + * CMake: + https://cmake.org/download/ + + (NOTE: When installing, tell CMake to add itself to the PATH.) + + If you have Visual C++ 10 or 11 (2010/2012) skip ahead to step 2, else you + need to download and install the following free component from Microsoft. + + * Microsoft Visual C++ 2010 Express Edition: + http://www.microsoft.com/visualstudio/eng/downloads#d-2010-express + + 2) Unpack the Anope tarball with your favorite uncompression program + (WinZip or WinRAR, etc). + + 3) Bring up the Visual C++ Command Prompt; This will launch a + DOS Command Prompt like window, which will set the environment + properties needed to make Anope. + + Create a new directory, which will be used to hold the build files. You can make it + be a directory under the source directory unpacked in step 2, or somewhere else entirely. + + Change directories to this new folder, by typing: + + cd + + e.g. + + cd c:\anope-build + + 4) You now need to configure Anope to your requirements. At the prompt type: + + \Config.exe + + NOTE: If you run an Anti-Virus program such as McAfee or Norton, you may + be unable to run this command due to the protection in place. Some Anti- + Virus programs may detect the Anope Configuration Tool as a worm, however + this is not the case. If you are prompted to allow or deny execution of + the script, you should choose allow. If the script fails to run, and no + notice is displayed, please check your Anti-Virus settings before seeking + assistance. + + An interactive configuration program should guide you through the install + options. You will be given a choice to use NMake or not. NMake will compile + inside the command prompt window you are in. If you want to build within + the Visual C++ IDE, say no to that option, and it'll create a Solution for + you to open up. + + If you cannot find whats causing the error, please visit our forums or + our IRC Support channel for assistance. + + Some Anope modules require third party libraries, such as m_mysql and + the SSL modules. If these libraries are installed in nonstandard + locations, cmake will probably not find them and should be told where + they are by passing their location to Config. + + The libraries used to build the 'extra' modules are available at + https://github.com/Adam-/windows-scripts. + + 5) You are now ready to compile. If you said you wanted to use NMake in step 4, + at the prompt type: + + nmake + + Once you are back at the command prompt again, if there have been no + errors, you are ready to go. + + If instead you decided to use the Visual C++ IDE, open up the Anope.sln + file. After the IDE has fully loaded, hit F7 to build everything. + + Should you encounter errors with the installation process, check the + messages displayed for advice on resolving them. If you are unable to + resolve the issues yourself, seek assistance on our forums or in our + IRC Support channel. + + 6) Finally you will need to install Anope. If you said you wanted to use NMake + in step 4, at the prompt type: + + nmake install + + Otherwise, if you decided to use the Visual C++ IDE, find the project called + INSTALL within the Solution Explorer. Right-click on INSTALL and choose Build. + + When you have done this, all the files will be installed to where they belong. + The only thing you need to do is rename "data/example.conf" to be "data/services.conf", + and then follow the steps to set up Anope. + + You have now completed the building phase of Anope for Windows. You can + now move on to the next section, which is related to setting up Anope. + +2) Installation + + Since Anope for Windows does not use a visual interface, you must do the + configuration with a text editor before proceeding with running Anope + itself. + + NOTE: You may need to open the configuration file with Wordpad, or a text + editor which supports UNIX line endings. Opening the configuration file in + Notepad will cause strange characters to appear, and you may not be able to + edit the file correctly. + + Open services.conf, and read through it carefully and adjust the settings + you think you need to adjust. + + If you are unsure of the settings, you can go to the dos command prompt + and run "anope.exe --nofork --debug" and watch the information as it + attempts to connect. + + You can launch services in two ways. If you are sure that the entered + configuration information is correct, simply double clicking the Anope + executable will cause it to start; no window will pop up. If you'd rather + have a more textual output, you can start at the dos prompt and type in + "anope.exe". If services are successfully started up the dos prompt will + seem to hang; at this point you can safely close the dos window. + +3) Compiling Modules + + If you want to build other modules than the ones shipped by default, you + will need to rerun Config.exe + +4) Other compile options + + A) If you have trouble recompiling Anope, you should delete all files and folders + within the build folder you created in step 3 of section 1. Afterwards, follow + the directions from step 4 of section 1 down. + +5) Credits + + Anope is based on Epona and IRCServices. See CREDITS for more credits and + a complete list of all developers. + + Anope's Windows-specific code is provided by: + + * Dominick Meglio + * Trystan Scott Lee + * Chris Hogben + + Anope's Windows Installer was made using: + + * NSIS 2.20 diff --git a/docs/XMLRPC/XMLRPC b/docs/XMLRPC/XMLRPC new file mode 100644 index 0000000..52f2248 --- /dev/null +++ b/docs/XMLRPC/XMLRPC @@ -0,0 +1,29 @@ +Starting with Anope 1.9.4 XMLRPC using PHP's xmlrpc_encode_request and xmlrpc_decode functions is supported. +This allows external applications, such as websites, to execute remote procedure calls to Anope in real time. + +Currently there are 5 supported XMLRPC calls, provided by m_xmlrpc_main: + +checkAuthentication - Takes two parameters, an account name and a password. Checks if the account name is valid and the password + is correct for the account name, useful for making login pages on websites. + +command - Takes three parameters, a service name (BotServ, ChanServ, NickServ), a user name (whether online or not), and the command + to execute. This will execute the given command to Anope using the given service name. If the user given is online, the + command reply will go to them, if not it is returned by XMLRPC. + +stats - Takes no parameters, returns miscellaneous stats that can be found in the /operserv stats command. + +channel - Takes one parameter, a channel name, and returns real time information regarding that channel, such as users, modes + (ban lists and such), topic etc. + +user - Takes one parameter, a user name, and returns real time information regarding that user. + +opers - Takes no parameters, returns opertypes, their privileges and commands. + +notice - Takes three parameters, source user, target user, and message. Sends a message to the user. + +XMLRPC was designed to be used with db_sql, and will not return any information that can be pulled from the SQL +database, such as accounts and registered channel information. It is instead used for pulling realtime data such +as users and channels currently online. For examples on how to use these calls in PHP, see xmlrpc.php in docs/XMLRPC. + +Also note that the parameter named "id" is reserved for query ID. If you pass a query to Anope containing a value for id. it will +be stored by Anope and the same id will be passed back in the result. diff --git a/docs/XMLRPC/xmlrpc.php b/docs/XMLRPC/xmlrpc.php new file mode 100644 index 0000000..8ea884d --- /dev/null +++ b/docs/XMLRPC/xmlrpc.php @@ -0,0 +1,145 @@ +host = $host; + } + + /** + * Run an XMLRPC command. Name should be a query name and params an array of parameters, eg: + * $this->raw("checkAuthentication", ["adam", "qwerty"]); + * If successful returns back an array of useful information. + * + * Note that $params["id"] is reserved for query ID, you may set it to something if you wish. + * If you do, the same ID will be passed back with the reply from Anope. + * + * @param $name + * @param $params + * @return array|null + */ + public function run($name, $params) + { + $xmlquery = xmlrpc_encode_request($name, $params); + $context = stream_context_create(["http" => [ + "method" => "POST", + "header" => "Content-Type: text/xml", + "content" => $xmlquery]]); + + $inbuf = file_get_contents($this->host, false, $context); + $response = xmlrpc_decode($inbuf); + + if ($response) { + return $response; + } + + return null; + } + + /** + * Do Command on Service as User, eg: + * $anope->command("ChanServ", "Adam", "REGISTER #adam"); + * Returns an array of information regarding the command execution, if + * If 'online' is set to yes, then the reply to the command was sent to the user on IRC. + * If 'online' is set to no, then the reply to the command is in the array member 'return' + * + * @param $service + * @param $user + * @param $command + * @return array|null + */ + public function command($service, $user, $command) + { + return $this->run("command", [$service, $user, $command]); + } + + /** + * Check an account/nick name and password to see if they are valid + * Returns the account display name if valid + * + * @param $account + * @param $pass + * @return string|null + */ + public function auth($account, $pass) + { + $ret = $this->run("checkAuthentication", [$account, $pass]); + + if ($ret && $ret["result"] == "Success") { + return $ret["account"]; + } + + return null; + } + + /** + * Returns an array of misc stats regarding Anope + * + * @return array|null + */ + public function stats() + { + return $this->run("stats", null); + } + + /** + * Look up data for a channel + * Returns an array containing channel information, or an array of size one + * (just containing the name) if the channel does not exist + * + * @param $channel + * @return array|null + */ + public function channel($channel) + { + return $this->run("channel", [$channel]); + } + + /** + * Sent a notice to a user. + * Returns an array containing channel information, or an array of size one + * (just containing the name) if the channel does not exist + * + * @param $source + * @param $target + * @param $message + * @return array|null + */ + public function notice($source, $target, $message) + { + return $this->run("notice", [$source, $target, $message]); + } + + /** + * Like channel(), but different. + * + * @param $user + * @return array|null + */ + public function user($user) + { + return $this->run("user", [$user]); + } +} + +$anope = new AnopeXMLRPC("http://127.0.0.1:8080/xmlrpc"); diff --git a/extras b/extras new file mode 100755 index 0000000..b411a06 --- /dev/null +++ b/extras @@ -0,0 +1,168 @@ +#!/usr/bin/env perl + +# +# Script taken from InspIRCd, https://www.inspircd.org/ +# +# This program is distributed in the hope that it will be useful, but WITHOUT +# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS +# FOR A PARTICULAR PURPOSE. See the GNU General Public License for more +# details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see . +# + + +BEGIN { require 5.8.0; } + +use strict; +use warnings FATAL => qw(all); + +use File::Copy (); +use Cwd; + +sub list_extras (); +sub enable_extras (@); +sub disable_extras (@); + +# Routine to list out the extra/ modules that have been enabled. +# Note: when getting any filenames out and comparing, it's important to lc it if the +# file system is not case-sensitive (== Epoc, MacOS, OS/2 (incl DOS/DJGPP), VMS, Win32 +# (incl NetWare, Symbian)). Cygwin may or may not be case-sensitive, depending on +# configuration, however, File::Spec does not currently tell us (it assumes Unix behavior). +sub list_extras () { + use File::Spec; + # @_ not used + my $srcdir = File::Spec->catdir("modules"); + my $abs_srcdir = File::Spec->rel2abs($srcdir); + local $_; + my $dd; + opendir $dd, File::Spec->catdir($abs_srcdir, "extra") or die (File::Spec->catdir($abs_srcdir, "extra") . ": $!\n"); + my @extras = map { File::Spec->case_tolerant() ? lc($_) : $_ } (readdir($dd)); + closedir $dd; + undef $dd; + opendir $dd, $abs_srcdir or die "$abs_srcdir: $!\n"; + my @sources = map { File::Spec->case_tolerant() ? lc($_) : $_ } (readdir($dd)); + closedir $dd; + undef $dd; + my $maxlen = (sort { $b <=> $a } (map {length($_)} (@extras)))[0]; + my %extras = (); +EXTRA: for my $extra (@extras) { + next if (File::Spec->curdir() eq $extra || File::Spec->updir() eq $extra); + my $abs_extra = File::Spec->catfile($abs_srcdir, "extra", $extra); + my $abs_source = File::Spec->catfile($abs_srcdir, $extra); + next unless ($extra =~ m/\.(cpp|h)$/ || (-d $abs_extra)); # C++ Source/Header, or directory + if (-l $abs_source) { + # Symlink, is it in the right place? + my $targ = readlink($abs_source); + my $abs_targ = File::Spec->rel2abs($targ, $abs_srcdir); + if ($abs_targ eq $abs_extra) { + $extras{$extra} = "\e[32;1menabled\e[0m"; + } else { + $extras{$extra} = sprintf("\e[31;1mwrong symlink target (%s)\e[0m", $abs_targ); + } + } elsif (-e $abs_source) { + my ($devext, $inoext) = stat($abs_extra); + my ($devsrc, $inosrc, undef, $lnksrc) = stat($abs_source); + if ($lnksrc > 1) { + if ($devsrc == $devext && $inosrc == $inoext) { + $extras{$extra} = "\e[32;1menabled\e[0m"; + } else { + $extras{$extra} = sprintf("\e[31;1mwrong hardlink target (%d:%d)\e[0m", $devsrc, $inosrc); + } + } else { + open my $extfd, "<", $abs_extra; + open my $srcfd, "<", $abs_source; + local $/ = undef; + if (scalar(<$extfd>) eq scalar(<$srcfd>)) { + $extras{$extra} = "\e[32;1menabled\e[0m"; + } else { + $extras{$extra} = sprintf("\e[31;1mout of synch (re-copy)\e[0m"); + } + } + } else { + $extras{$extra} = "\e[33;1mdisabled\e[0m"; + } + } + + for my $extra (sort {$a cmp $b} keys(%extras)) { + my $text = $extras{$extra}; + if ($text =~ m/needed by/ && $text !~ m/enabled/) { + printf "\e[31;1;5m%-*s = %s%s\e[0m\n", $maxlen, $extra, $text, ($text =~ m/needed by/ ? ")" : ""); + } else { + printf "%-*s = %s%s\n", $maxlen, $extra, $text, ($text =~ m/needed by/ ? "\e[0m)" : ""); + } + } + return keys(%extras) if wantarray; # Can be used by manage_extras. +} + +sub enable_extras (@) { + my (@extras) = @_; + for my $extra (@extras) { + my $extrapath = "modules/extra/$extra"; + if (!-e $extrapath) { + print STDERR "Cannot enable \e[32;1m$extra\e[0m : No such file or directory in modules/extra\n"; + next; + } + my $source = "modules/$extra"; + if (-e $source) { + print STDERR "Cannot enable \e[32;1m$extra\e[0m : destination in modules exists (might already be enabled?)\n"; + next; + } + print "Enabling $extra ... \n"; + symlink "extra/$extra", $source or print STDERR "$source: Cannot link to 'extra/$extra': $!\n"; + } +} + +sub disable_extras (@) +{ + opendir my $dd, "modules/extra/"; + my @files = readdir($dd); + closedir $dd; + my (@extras) = @_; +EXTRA: for my $extra (@extras) { + my $extrapath = "modules/extra/$extra"; + my $source = "modules/$extra"; + if (!-e $extrapath) { + print STDERR "Cannot disable \e[32;1m$extra\e[0m : Is not an extra\n"; + next; + } + if ((! -l $source) || readlink($source) ne "extra/$extra") { + print STDERR "Cannot disable \e[32;1m$extra\e[0m : Source is not a link or doesn't refer to the right file. Remove manually if this is in error.\n"; + next; + } + # Now remove. + print "Disabling $extra ... \n"; + unlink "modules/$extra" or print STDERR "Cannot disable \e[32;1m$extra\e[0m : $!\n"; + } +} + +my $clearscreen = `clear`; +print $clearscreen; +while (1) +{ + list_extras; # print the module list + print "\nPlease enter the name of the module or type 'q' to quit.: "; + my $input = ; + chop($input); # remove the trailing \n from the user input + + if ($input eq "q") { + if (-e "build/CMakeFiles") { + system("cmake", "build/."); + print "\nNow cd build, then run make to build Anope.\n\n"; + } else { + print "\nBuild directory not found. You should run ./Config now.\n\n" + } + exit 0; + } + print $clearscreen; + if ($input eq "") { + next; + } + + if (-e "modules/$input") { + disable_extras($input) + } else { + enable_extras($input) + } +} diff --git a/include/CMakeLists.txt b/include/CMakeLists.txt new file mode 100644 index 0000000..73e57f5 --- /dev/null +++ b/include/CMakeLists.txt @@ -0,0 +1,64 @@ +# Set version.cpp to use C++ as well as set its compile flags +set_source_files_properties(version.cpp PROPERTIES LANGUAGE CXX COMPILE_FLAGS "${CXXFLAGS}") +# Generate version-bin executable to modify version.h, setting it's linker flags as well +add_executable(version-bin version.cpp) +set_target_properties(version-bin PROPERTIES LINKER_LANGUAGE CXX LINK_FLAGS "${LDFLAGS}") +get_target_property(version_BINARY version-bin LOCATION) +# Modify version.h from the above executable, with dependencies to version.cpp +# and all of the source files in the main build +add_custom_command(OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/version_build + COMMAND ${version_BINARY} ${Anope_SOURCE_DIR} ${CMAKE_CURRENT_BINARY_DIR}/version.h ${CMAKE_CURRENT_BINARY_DIR}/build.h + DEPENDS version-bin ${SRC_SRCS} +) +# Add version-bin to list of files for CPack to ignore +get_filename_component(version_BINARY ${version_BINARY} NAME) +add_to_cpack_ignored_files("${version_BINARY}$" TRUE) +if(NOT WIN32) + add_to_cpack_ignored_files("version.h$" TRUE) + add_to_cpack_ignored_files("build.h$" TRUE) +endif(NOT WIN32) + +set(PCH_SOURCES_GCH "") +if(USE_PCH AND CMAKE_COMPILER_IS_GNUCXX) + string(REPLACE " " ";" PCH_CXXFLAGS "${CXXFLAGS} ${CMAKE_CXX_FLAGS}") + + file(GLOB PCH_SOURCES RELATIVE ${CMAKE_CURRENT_SOURCE_DIR} "*.h") + sort_list(PCH_SOURCES) + + foreach(PCH_SOURCE ${PCH_SOURCES}) + find_includes(${PCH_SOURCE} INCLUDES) + set(INCLUDES_LIST) + append_to_list(INCLUDES_LIST ${PCH_SOURCE}) + foreach(INCLUDE ${INCLUDES}) + # Extract the filename from the #include line + extract_include_filename(${INCLUDE} FILENAME QUOTE_TYPE) + if(QUOTE_TYPE STREQUAL "quotes") + find_in_list(PCH_SOURCES "${FILENAME}" FOUND) + if(NOT FOUND EQUAL -1) + append_to_list(INCLUDES_LIST ${FILENAME}) + endif(NOT FOUND EQUAL -1) + endif(QUOTE_TYPE STREQUAL "quotes") + endforeach(INCLUDE) + + set(PCH_EXTRAFLAGS "") + if(DEBUG_BUILD) + set(PCH_EXTRAFLAGS "-g") + endif(DEBUG_BUILD) + if(PCH_SOURCE STREQUAL "module.h") + set(PCH_EXTRAFLAGS ${PCH_EXTRAFLAGS} -fPIC) + endif(PCH_SOURCE STREQUAL "module.h") + if(GETTEXT_INCLUDE) + set(PCH_GETTEXT_INCLUDE "-I${GETTEXT_INCLUDE}") + endif(GETTEXT_INCLUDE) + + set(PCH_SOURCES_GCH "${PCH_SOURCES_GCH};${CMAKE_CURRENT_BINARY_DIR}/${PCH_SOURCE}.gch") + add_custom_command(OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/${PCH_SOURCE}.gch + COMMAND ${CMAKE_CXX_COMPILER} ARGS ${PCH_CXXFLAGS} ${PCH_EXTRAFLAGS} + ${PCH_GETTEXT_INCLUDE} -I${CMAKE_CURRENT_BINARY_DIR} -I${Anope_SOURCE_DIR}/modules/pseudoclients ${CMAKE_CURRENT_SOURCE_DIR}/${PCH_SOURCE} -o ${CMAKE_CURRENT_BINARY_DIR}/${PCH_SOURCE}.gch + DEPENDS ${INCLUDES_LIST} VERBATIM + ) + endforeach(PCH_SOURCE ${PCH_SOURCES}) +endif(USE_PCH AND CMAKE_COMPILER_IS_GNUCXX) + +# Add a custom target to the above file +add_custom_target(headers DEPENDS version-bin ${CMAKE_CURRENT_BINARY_DIR}/version_build ${PCH_SOURCES_GCH}) diff --git a/include/access.h b/include/access.h new file mode 100644 index 0000000..23beac4 --- /dev/null +++ b/include/access.h @@ -0,0 +1,174 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef ACCESS_H +#define ACCESS_H + +#include "services.h" +#include "anope.h" +#include "serialize.h" +#include "service.h" + +enum +{ + ACCESS_INVALID = -10000, + ACCESS_FOUNDER = 10001 +}; + +/* A privilege, probably configured using a privilege{} block. Most + * commands require specific privileges to be executed. The AccessProvider + * backing each ChanAccess determines whether that ChanAccess has a given + * privilege. + */ +struct CoreExport Privilege +{ + Anope::string name; + Anope::string desc; + /* Rank relative to other privileges */ + int rank; + + Privilege(const Anope::string &name, const Anope::string &desc, int rank); + bool operator==(const Privilege &other) const; +}; + +class CoreExport PrivilegeManager +{ + static std::vector Privileges; + public: + static void AddPrivilege(Privilege p); + static void RemovePrivilege(Privilege &p); + static Privilege *FindPrivilege(const Anope::string &name); + static std::vector &GetPrivileges(); + static void ClearPrivileges(); +}; + +/* A provider of access. Only used for creating ChanAccesses, as + * they contain pure virtual functions. + */ +class CoreExport AccessProvider : public Service +{ + public: + AccessProvider(Module *owner, const Anope::string &name); + virtual ~AccessProvider(); + + /** Creates a new ChanAccess entry using this provider. + * @return The new entry + */ + virtual ChanAccess *Create() = 0; + + private: + static std::list Providers; + public: + static const std::list& GetProviders(); +}; + +/* Represents one entry of an access list on a channel. */ +class CoreExport ChanAccess : public Serializable +{ + Anope::string mask; + /* account this access entry is for, if any */ + Serialize::Reference nc; + + public: + typedef std::vector Path; + + /* The provider that created this access entry */ + AccessProvider *provider; + /* Channel this access entry is on */ + Serialize::Reference ci; + Anope::string creator; + time_t last_seen; + time_t created; + + ChanAccess(AccessProvider *p); + virtual ~ChanAccess(); + + void SetMask(const Anope::string &mask, ChannelInfo *ci); + const Anope::string &Mask() const; + NickCore *GetAccount() const; + + void Serialize(Serialize::Data &data) const anope_override; + static Serializable* Unserialize(Serializable *obj, Serialize::Data &); + + static const unsigned int MAX_DEPTH = 4; + + /** Check if this access entry matches the given user or account + * @param u The user + * @param nc The account + * @param next Next channel to check if any + */ + virtual bool Matches(const User *u, const NickCore *nc, ChannelInfo* &next) const; + + /** Check if this access entry has the given privilege. + * @param name The privilege name + */ + virtual bool HasPriv(const Anope::string &name) const = 0; + + /** Serialize the access given by this access entry into a human + * readable form. chanserv/access will return a number, chanserv/xop + * will be AOP, SOP, etc. + */ + virtual Anope::string AccessSerialize() const = 0; + + /** Unserialize this access entry from the given data. This data + * will be fetched from AccessSerialize. + */ + virtual void AccessUnserialize(const Anope::string &data) = 0; + + /* Comparison operators to other Access entries */ + virtual bool operator>(const ChanAccess &other) const; + virtual bool operator<(const ChanAccess &other) const; + bool operator>=(const ChanAccess &other) const; + bool operator<=(const ChanAccess &other) const; +}; + +/* A group of access entries. This is used commonly, for example with ChannelInfo::AccessFor, + * to show what access a user has on a channel because users can match multiple access entries. + */ +class CoreExport AccessGroup +{ + public: + /* access entries + paths */ + std::vector paths; + /* Channel these access entries are on */ + const ChannelInfo *ci; + /* Account these entries affect, if any */ + const NickCore *nc; + /* super_admin always gets all privs. founder is a special case where ci->founder == nc */ + bool super_admin, founder; + + AccessGroup(); + + /** Check if this access group has a certain privilege. Eg, it + * will check every ChanAccess entry of this group for any that + * has the given privilege. + * @param priv The privilege + * @return true if any entry has the given privilege + */ + bool HasPriv(const Anope::string &priv) const; + + /** Get the "highest" access entry from this group of entries. + * The highest entry is determined by the entry that has the privilege + * with the highest rank (see Privilege::rank). + * @return The "highest" entry + */ + const ChanAccess *Highest() const; + + /* Comparison operators to other AccessGroups */ + bool operator>(const AccessGroup &other) const; + bool operator<(const AccessGroup &other) const; + bool operator>=(const AccessGroup &other) const; + bool operator<=(const AccessGroup &other) const; + + inline bool empty() const { return paths.empty(); } +}; + +#endif diff --git a/include/account.h b/include/account.h new file mode 100644 index 0000000..cffd196 --- /dev/null +++ b/include/account.h @@ -0,0 +1,290 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef ACCOUNT_H +#define ACCOUNT_H + +#include "extensible.h" +#include "serialize.h" +#include "anope.h" +#include "memo.h" +#include "base.h" + +typedef Anope::hash_map nickalias_map; +typedef Anope::hash_map nickcore_map; +typedef TR1NS::unordered_map nickcoreid_map; + +extern CoreExport Serialize::Checker NickAliasList; +extern CoreExport Serialize::Checker NickCoreList; +extern CoreExport nickcoreid_map NickCoreIdList; + +/* A registered nickname. + * It matters that Base is here before Extensible (it is inherited by Serializable) + */ +class CoreExport NickAlias : public Serializable, public Extensible +{ + Anope::string vhost_ident, vhost_host, vhost_creator; + time_t vhost_created; + + public: + Anope::string nick; + Anope::string last_quit; + Anope::string last_realname; + /* Last usermask this nick was seen on, eg user@host */ + Anope::string last_usermask; + /* Last uncloaked usermask, requires nickserv/auspex to see */ + Anope::string last_realhost; + time_t time_registered; + time_t last_seen; + /* Account this nick is tied to. Multiple nicks can be tied to a single account. */ + Serialize::Reference nc; + + /** Constructor + * @param nickname The nick + * @param nickcore The nickcore for this nick + */ + NickAlias(const Anope::string &nickname, NickCore *nickcore); + ~NickAlias(); + + void Serialize(Serialize::Data &data) const anope_override; + static Serializable* Unserialize(Serializable *obj, Serialize::Data &); + + /** Set a vhost for the user + * @param ident The ident + * @param host The host + * @param creator Who created the vhost + * @param time When the vhost was created + */ + void SetVhost(const Anope::string &ident, const Anope::string &host, const Anope::string &creator, time_t created = Anope::CurTime); + + /** Remove a users vhost + **/ + void RemoveVhost(); + + /** Check if the user has a vhost + * @return true or false + */ + bool HasVhost() const; + + /** Retrieve the vhost ident + * @return the ident + */ + const Anope::string &GetVhostIdent() const; + + /** Retrieve the vhost host + * @return the host + */ + const Anope::string &GetVhostHost() const; + + /** Retrieve the vhost creator + * @return the creator + */ + const Anope::string &GetVhostCreator() const; + + /** Retrieve when the vhost was created + * @return the time it was created + */ + time_t GetVhostCreated() const; + + /** Finds a registered nick + * @param nick The nick to lookup + * @return the nick, if found + */ + static NickAlias *Find(const Anope::string &nick); +}; + +/* A registered account. Each account must have a NickAlias with the same nick as the + * account's display. + * It matters that Base is here before Extensible (it is inherited by Serializable) + */ +class CoreExport NickCore : public Serializable, public Extensible +{ + /* Channels which reference this core in some way (this is on their access list, akick list, is founder, successor, etc) */ + Serialize::Checker > chanaccess; + /* Unique identifier for the account. */ + uint64_t id; + public: + /* Name of the account. Find(display)->nc == this. */ + Anope::string display; + /* User password in form of hashm:data */ + Anope::string pass; + Anope::string email; + /* Locale name of the language of the user. Empty means default language */ + Anope::string language; + /* Access list, contains user@host masks of users who get certain privileges based + * on if NI_SECURE is set and what (if any) kill protection is enabled. */ + std::vector access; + MemoInfo memos; + std::map last_modes; + + /* Nicknames registered that are grouped to this account. + * for n in aliases, n->nc == this. + */ + Serialize::Checker > aliases; + + /* Set if this user is a services operator. o->ot must exist. */ + Oper *o; + + /* Unsaved data */ + + /* Number of channels registered by this account */ + uint16_t channelcount; + /* Last time an email was sent to this user */ + time_t lastmail; + /* Users online now logged into this account */ + std::list users; + + /** Constructor + * @param display The display nick + * @param id The account id + */ + NickCore(const Anope::string &nickdisplay, uint64_t nickid = 0); + ~NickCore(); + + void Serialize(Serialize::Data &data) const anope_override; + static Serializable* Unserialize(Serializable *obj, Serialize::Data &); + + /** Changes the display for this account + * @param na The new display, must be grouped to this account. + */ + void SetDisplay(const NickAlias *na); + + /** Checks whether this account is a services oper or not. + * @return True if this account is a services oper, false otherwise. + */ + virtual bool IsServicesOper() const; + + /** Add an entry to the nick's access list + * + * @param entry The nick!ident@host entry to add to the access list + * + * Adds a new entry into the access list. + */ + void AddAccess(const Anope::string &entry); + + /** Get an entry from the nick's access list by index + * + * @param entry Index in the access list vector to retrieve + * @return The access list entry of the given index if within bounds, an empty string if the vector is empty or the index is out of bounds + * + * Retrieves an entry from the access list corresponding to the given index. + */ + Anope::string GetAccess(unsigned entry) const; + + /** Get the number of entries on the access list for this account. + */ + unsigned GetAccessCount() const; + + /** Retrieves the account id for this user */ + uint64_t GetId(); + + /** Find an entry in the nick's access list + * + * @param entry The nick!ident@host entry to search for + * @return True if the entry is found in the access list, false otherwise + * + * Search for an entry within the access list. + */ + bool FindAccess(const Anope::string &entry); + + /** Erase an entry from the nick's access list + * + * @param entry The nick!ident@host entry to remove + * + * Removes the specified access list entry from the access list. + */ + void EraseAccess(const Anope::string &entry); + + /** Clears the entire nick's access list + * + * Deletes all the memory allocated in the access list vector and then clears the vector. + */ + void ClearAccess(); + + /** Is the given user on this accounts access list? + * + * @param u The user + * + * @return true if the user is on the access list + */ + bool IsOnAccess(const User *u) const; + + /** Finds an account + * @param nick The account name to find + * @return The account, if it exists + */ + static NickCore* Find(const Anope::string &nick); + + void AddChannelReference(ChannelInfo *ci); + void RemoveChannelReference(ChannelInfo *ci); + void GetChannelReferences(std::deque &queue); +}; + +/* A request to check if an account/password is valid. These can exist for + * extended periods due to the time some authentication modules take. + */ +class CoreExport IdentifyRequest +{ + /* Owner of this request, used to cleanup requests if a module is unloaded + * while a request us pending */ + Module *owner; + Anope::string account; + Anope::string password; + + std::set holds; + bool dispatched; + bool success; + + static std::set Requests; + + protected: + IdentifyRequest(Module *o, const Anope::string &acc, const Anope::string &pass); + virtual ~IdentifyRequest(); + + public: + /* One of these is called when the request goes through */ + virtual void OnSuccess() = 0; + virtual void OnFail() = 0; + + Module *GetOwner() const { return owner; } + const Anope::string &GetAccount() const { return account; } + const Anope::string &GetPassword() const { return password; } + + /* Holds this request. When a request is held it must be Released later + * for the request to complete. Multiple modules may hold a request at any time, + * but the request is not complete until every module has released it. If you do not + * require holding this (eg, your password check is done in this thread and immediately) + * then you don't need to hold the request before calling `Success()`. + * @param m The module holding this request + */ + void Hold(Module *m); + + /** Releases a held request + * @param m The module releasing the hold + */ + void Release(Module *m); + + /** Called by modules when this IdentifyRequest has succeeded. + * If this request is behind held it must still be Released after calling this. + * @param m The module confirming authentication + */ + void Success(Module *m); + + /** Used to either finalize this request or marks + * it as dispatched and begins waiting for the module(s) + * that have holds to finish. + */ + void Dispatch(); + + static void ModuleUnload(Module *m); +}; + +#endif // ACCOUNT_H diff --git a/include/anope.h b/include/anope.h new file mode 100644 index 0000000..40558f0 --- /dev/null +++ b/include/anope.h @@ -0,0 +1,791 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef ANOPE_H +#define ANOPE_H + +#include + +#include "hashcomp.h" + +namespace Anope +{ + /** + * A wrapper string class around all the other string classes, this class will + * allow us to only require one type of string everywhere that can be converted + * at any time to a specific type of string. + */ + class CoreExport string + { + private: + /** + * The actual string is stored in an std::string as it can be converted to + * ci::string, or a C-style string at any time. + */ + std::string _string; + public: + /** + * Extras. + */ + typedef std::string::iterator iterator; + typedef std::string::const_iterator const_iterator; + typedef std::string::reverse_iterator reverse_iterator; + typedef std::string::const_reverse_iterator const_reverse_iterator; + typedef std::string::size_type size_type; + static const size_type npos = static_cast(-1); + + /** + * Constructors that can take in any type of string. + */ + string() : _string("") { } + string(char chr) : _string() { _string = chr; } + string(size_type n, char chr) : _string(n, chr) { } + string(const char *_str) : _string(_str) { } + string(const char *_str, size_type n) : _string(_str, n) { } + string(const std::string &_str) : _string(_str) { } + string(const ci::string &_str) : _string(_str.c_str()) { } + string(const string &_str, size_type pos, size_type n = npos) : _string(_str._string, pos, n) { } + template string(InputIterator first, InputIterator last) : _string(first, last) { } +#if __cplusplus >= 201103L + string(const string &) = default; +#endif + + /** + * Assignment operators, so any type of string can be assigned to this class. + */ + inline string &operator=(char chr) { this->_string = chr; return *this; } + inline string &operator=(const char *_str) { this->_string = _str; return *this; } + inline string &operator=(const std::string &_str) { this->_string = _str; return *this; } + inline string &operator=(const string &_str) { if (this != &_str) this->_string = _str._string; return *this; } + + /** + * Equality operators, to compare to any type of string. + */ + inline bool operator==(const char *_str) const { return this->_string == _str; } + inline bool operator==(const std::string &_str) const { return this->_string == _str; } + inline bool operator==(const string &_str) const { return this->_string == _str._string; } + + inline bool equals_cs(const char *_str) const { return this->_string == _str; } + inline bool equals_cs(const std::string &_str) const { return this->_string == _str; } + inline bool equals_cs(const string &_str) const { return this->_string == _str._string; } + + inline bool equals_ci(const char *_str) const { return ci::string(this->_string.c_str()) == _str; } + inline bool equals_ci(const std::string &_str) const { return ci::string(this->_string.c_str()) == _str.c_str(); } + inline bool equals_ci(const string &_str) const { return ci::string(this->_string.c_str()) == _str._string.c_str(); } + + /** + * Inequality operators, exact opposites of the above. + */ + inline bool operator!=(const char *_str) const { return !operator==(_str); } + inline bool operator!=(const std::string &_str) const { return !operator==(_str); } + inline bool operator!=(const string &_str) const { return !operator==(_str); } + + /** + * Compound addition operators, overloaded to do concatenation. + */ + inline string &operator+=(char chr) { this->_string += chr; return *this; } + inline string &operator+=(const char *_str) { this->_string += _str; return *this; } + inline string &operator+=(const std::string &_str) { this->_string += _str; return *this; } + inline string &operator+=(const string &_str) { if (this != &_str) this->_string += _str._string; return *this; } + + /** + * Addition operators, overloaded to do concatenation. + */ + inline const string operator+(char chr) const { return string(*this) += chr; } + inline const string operator+(const char *_str) const { return string(*this) += _str; } + inline const string operator+(const std::string &_str) const { return string(*this) += _str; } + inline const string operator+(const string &_str) const { return string(*this) += _str; } + + friend const string operator+(char chr, const string &str); + friend const string operator+(const char *_str, const string &str); + friend const string operator+(const std::string &_str, const string &str); + + /** + * Less-than operator. + */ + inline bool operator<(const string &_str) const { return this->_string < _str._string; } + + /** + * The following functions return the various types of strings. + */ + inline const char *c_str() const { return this->_string.c_str(); } + inline const char *data() const { return this->_string.data(); } + inline std::string &str() { return this->_string; } + inline const std::string &str() const { return this->_string; } + inline ci::string ci_str() const { return ci::string(this->_string.c_str()); } + + /** + * Returns if the string is empty or not. + */ + inline bool empty() const { return this->_string.empty(); } + + /** + * Returns the string's length. + */ + inline size_type length() const { return this->_string.length(); } + + /** + * Returns the size of the currently allocated storage space in the string object. + * This can be equal or greater than the length of the string. + */ + inline size_type capacity() const { return this->_string.capacity(); } + + /** + * Add a char to the end of the string. + */ + inline void push_back(char c) { return this->_string.push_back(c); } + + inline string& append(const string &s) { this->_string.append(s.str()); return *this; } + inline string& append(const char *s, size_t n) { this->_string.append(s, n); return *this; } + + /** + * Resizes the string content to n characters. + */ + inline void resize(size_type n) { return this->_string.resize(n); } + + /** + * Erases characters from the string. + */ + inline iterator erase(const iterator &i) { return this->_string.erase(i); } + inline iterator erase(const iterator &first, const iterator &last) { return this->_string.erase(first, last); } + inline void erase(size_type pos = 0, size_type n = std::string::npos) { this->_string.erase(pos, n); } + + /** + * Trim leading and trailing white spaces from the string. + */ + + inline string& ltrim(const Anope::string &what = " \t\r\n") + { + while (!this->_string.empty() && what.find(this->_string[0]) != Anope::string::npos) + this->_string.erase(this->_string.begin()); + return *this; + } + + inline string& rtrim(const Anope::string &what = " \t\r\n") + { + while (!this->_string.empty() && what.find(this->_string[this->_string.length() - 1]) != Anope::string::npos) + this->_string.erase(this->_string.length() - 1); + return *this; + } + + inline string& trim(const Anope::string &what = " \t\r\n") + { + this->ltrim(what); + this->rtrim(what); + return *this; + } + + /** + * Clears the string. + */ + inline void clear() { this->_string.clear(); } + + /** + * Find substrings of the string. + */ + inline size_type find(const string &_str, size_type pos = 0) const { return this->_string.find(_str._string, pos); } + inline size_type find(char chr, size_type pos = 0) const { return this->_string.find(chr, pos); } + inline size_type find_ci(const string &_str, size_type pos = 0) const { return ci::string(this->_string.c_str()).find(ci::string(_str._string.c_str()), pos); } + inline size_type find_ci(char chr, size_type pos = 0) const { return ci::string(this->_string.c_str()).find(chr, pos); } + + inline size_type rfind(const string &_str, size_type pos = npos) const { return this->_string.rfind(_str._string, pos); } + inline size_type rfind(char chr, size_type pos = npos) const { return this->_string.rfind(chr, pos); } + inline size_type rfind_ci(const string &_str, size_type pos = npos) const { return ci::string(this->_string.c_str()).rfind(ci::string(_str._string.c_str()), pos); } + inline size_type rfind_ci(char chr, size_type pos = npos) const { return ci::string(this->_string.c_str()).rfind(chr, pos); } + + inline size_type find_first_of(const string &_str, size_type pos = 0) const { return this->_string.find_first_of(_str._string, pos); } + inline size_type find_first_of_ci(const string &_str, size_type pos = 0) const { return ci::string(this->_string.c_str()).find_first_of(ci::string(_str._string.c_str()), pos); } + + inline size_type find_first_not_of(const string &_str, size_type pos = 0) const { return this->_string.find_first_not_of(_str._string, pos); } + inline size_type find_first_not_of_ci(const string &_str, size_type pos = 0) const { return ci::string(this->_string.c_str()).find_first_not_of(ci::string(_str._string.c_str()), pos); } + + inline size_type find_last_of(const string &_str, size_type pos = npos) const { return this->_string.find_last_of(_str._string, pos); } + inline size_type find_last_of_ci(const string &_str, size_type pos = npos) const { return ci::string(this->_string.c_str()).find_last_of(ci::string(_str._string.c_str()), pos); } + + inline size_type find_last_not_of(const string &_str, size_type pos = npos) const { return this->_string.find_last_not_of(_str._string, pos); } + inline size_type find_last_not_of_ci(const string &_str, size_type pos = npos) const { return ci::string(this->_string.c_str()).find_last_not_of(ci::string(_str._string.c_str()), pos); } + + /** + * Determine if string consists of only numbers. + */ + inline bool is_number_only() const { return this->find_first_not_of("0123456789.-") == npos; } + inline bool is_pos_number_only() const { return this->find_first_not_of("0123456789.") == npos; } + + /** + * Replace parts of the string. + */ + inline string replace(size_type pos, size_type n, const string &_str) { return string(this->_string.replace(pos, n, _str._string)); } + inline string replace(size_type pos, size_type n, const string &_str, size_type pos1, size_type n1) { return string(this->_string.replace(pos, n, _str._string, pos1, n1)); } + inline string replace(size_type pos, size_type n, size_type n1, char chr) { return string(this->_string.replace(pos, n, n1, chr)); } + inline string replace(iterator first, iterator last, const string &_str) { return string(this->_string.replace(first, last, _str._string)); } + inline string replace(iterator first, iterator last, size_type n, char chr) { return string(this->_string.replace(first, last, n, chr)); } + template inline string replace(iterator first, iterator last, InputIterator f, InputIterator l) { return string(this->_string.replace(first, last, f, l)); } + inline string replace_all_cs(const string &_orig, const string &_repl) const + { + Anope::string new_string = *this; + size_type pos = new_string.find(_orig), orig_length = _orig.length(), repl_length = _repl.length(); + while (pos != npos) + { + new_string = new_string.substr(0, pos) + _repl + new_string.substr(pos + orig_length); + pos = new_string.find(_orig, pos + repl_length); + } + return new_string; + } + inline string replace_all_ci(const string &_orig, const string &_repl) const + { + Anope::string new_string = *this; + size_type pos = new_string.find_ci(_orig), orig_length = _orig.length(), repl_length = _repl.length(); + while (pos != npos) + { + new_string = new_string.substr(0, pos) + _repl + new_string.substr(pos + orig_length); + pos = new_string.find_ci(_orig, pos + repl_length); + } + return new_string; + } + + /** + * Get the string in lowercase. + */ + inline string lower() const + { + Anope::string new_string = *this; + for (size_type i = 0; i < new_string.length(); ++i) + new_string[i] = Anope::tolower(new_string[i]); + return new_string; + } + + /** + * Get the string in uppercase. + */ + inline string upper() const + { + Anope::string new_string = *this; + for (size_type i = 0; i < new_string.length(); ++i) + new_string[i] = Anope::toupper(new_string[i]); + return new_string; + } + + /** + * Get a substring of the string. + */ + inline string substr(size_type pos = 0, size_type n = npos) const { return string(this->_string.substr(pos, n)); } + + /** + * Iterators to the string. + */ + inline iterator begin() { return this->_string.begin(); } + inline const_iterator begin() const { return this->_string.begin(); } + inline iterator end() { return this->_string.end(); } + inline const_iterator end() const { return this->_string.end(); } + inline reverse_iterator rbegin() { return this->_string.rbegin(); } + inline const_reverse_iterator rbegin() const { return this->_string.rbegin(); } + inline reverse_iterator rend() { return this->_string.rend(); } + inline const_reverse_iterator rend() const { return this->_string.rend(); } + + /** + * Subscript operator, to access individual characters of the string. + */ + inline char &operator[](size_type n) { return this->_string[n]; } + inline const char &operator[](size_type n) const { return this->_string[n]; } + + /** + * Stream insertion operator, must be friend because they cannot be inside the class. + */ + friend std::ostream &operator<<(std::ostream &os, const string &_str); + friend std::istream &operator>>(std::istream &is, string &_str); + }; + + inline std::ostream &operator<<(std::ostream &os, const string &_str) { return os << _str._string; } + /* This is not standard to make operator>> behave like operator<< in that it will allow extracting a whole line, not just one word */ + inline std::istream &operator>>(std::istream &is, string &_str) { return std::getline(is, _str._string); } + + inline const string operator+(char chr, const string &str) { string tmp(chr); tmp += str; return tmp; } + inline const string operator+(const char *_str, const string &str) { string tmp(_str); tmp += str; return tmp; } + inline const string operator+(const std::string &_str, const string &str) { string tmp(_str); tmp += str; return tmp; } + + struct hash_ci + { + inline size_t operator()(const string &s) const + { + return TR1NS::hash()(s.lower().str()); + } + }; + + struct hash_cs + { + inline size_t operator()(const string &s) const + { + return TR1NS::hash()(s.str()); + } + }; + + struct compare + { + inline bool operator()(const string &s1, const string &s2) const + { + return s1.equals_ci(s2); + } + }; + + template class map : public std::map { }; + template class multimap : public std::multimap { }; + template class hash_map : public TR1NS::unordered_map { }; + +#ifndef REPRODUCIBLE_BUILD + static const char *const compiled = __TIME__ " " __DATE__; +#endif + + /** The time Anope started. + */ + extern CoreExport time_t StartTime; + + /** The value to return from main() + */ + extern int ReturnValue; + + extern sig_atomic_t Signal; + extern CoreExport bool Quitting; + extern CoreExport bool Restarting; + extern CoreExport Anope::string QuitReason; + + /** The current system time, which is pretty close to being accurate. + * Use this unless you need very specific time checks + */ + extern CoreExport time_t CurTime; + + /** The debug level we are running at. + */ + extern CoreExport int Debug; + + /** Other command line options. + */ + extern CoreExport bool ReadOnly, NoFork, NoThird, NoExpire, ProtocolDebug; + + /** The root of the services installation. Usually ~/services + */ + extern CoreExport Anope::string ServicesDir; + + /** Services binary name (eg services) + */ + extern CoreExport Anope::string ServicesBin; + + /** Various directory paths. These can be set at runtime by command line args + */ + extern CoreExport Anope::string ConfigDir; + extern CoreExport Anope::string DataDir; + extern CoreExport Anope::string ModuleDir; + extern CoreExport Anope::string LocaleDir; + extern CoreExport Anope::string LogDir; + + /** The uplink we are currently connected to + */ + extern CoreExport int CurrentUplink; + + /** Various methods to determine the Anope version running + */ + extern CoreExport string Version(); + extern CoreExport string VersionShort(); + extern CoreExport string VersionBuildString(); + extern CoreExport int VersionMajor(); + extern CoreExport int VersionMinor(); + extern CoreExport int VersionPatch(); + + /** Determines if we are still attached to the terminal, and can print + * messages to the user via stderr/stdout. + * @return true if still attached + */ + extern bool AtTerm(); + + /** Used to "fork" the process and go into the background during initial startup + * while we are AtTerm(). The actual fork is not done here, but earlier, and this + * simply notifies the parent via kill() to exit(). + */ + extern void Fork(); + + /** Does something with the signal in Anope::Signal + */ + extern void HandleSignal(); + + /** One of the first functions called, does general initialization such as reading + * command line args, loading the configuration, doing the initial fork() if necessary, + * initializing language support, loading modules, and loading databases. + * @throws CoreException if something bad went wrong + */ + extern void Init(int ac, char **av); + + /** Calls the save database event + */ + extern CoreExport void SaveDatabases(); + + /** Check whether two strings match. + * @param str The string to check against the pattern (e.g. foobar) + * @param mask The pattern to check (e.g. foo*bar) + * @param case_sensitive Whether or not the match is case sensitive, default false. + * @param use_regex Whether or not to try regex. case_sensitive is not used in regex. + */ + extern CoreExport bool Match(const string &str, const string &mask, bool case_sensitive = false, bool use_regex = false); + + /** Converts a string to hex + * @param the data to be converted + * @return a anope::string containing the hex value + */ + extern CoreExport string Hex(const string &data); + extern CoreExport string Hex(const char *data, unsigned len); + + /** Converts a string from hex + * @param src The data to be converted + * @param dest The destination string + */ + extern CoreExport void Unhex(const string &src, string &dest); + extern CoreExport void Unhex(const string &src, char *dest, size_t sz); + + /** Base 64 encode a string + * @param src The string to encode + * @param target Where the encoded string is placed + */ + extern CoreExport void B64Encode(const string &src, string &target); + + /** Base 64 decode a string + * @param src The base64 encoded string + * @param target The plain text result + */ + extern CoreExport void B64Decode(const string &src, string &target); + + /** Encrypts what is in 'src' to 'dest' + * @param src The source string to encrypt + * @param dest The destination where the encrypted string is placed + */ + extern CoreExport void Encrypt(const Anope::string &src, Anope::string &dest); + + /** Decrypts what is in 'src' to 'dest'. + * @param src The source string to decrypt + * @param dest The destination where the decrypted string is placed + * @return true if decryption was successful. This is usually not the case + * as most encryption methods we use are one way. + */ + extern CoreExport bool Decrypt(const Anope::string &src, Anope::string &dest); + + /** Hashes a buffer with SipHash-2-4 + * @param src The start of the buffer to hash + * @param src_sz The total number of bytes in the buffer + * @param key A 16 byte key to hash the buffer with. + */ + extern CoreExport uint64_t SipHash24(const void *src, unsigned long src_sz, const char key[16]); + + /** Returns a sequence of data formatted as the format argument specifies. + ** After the format parameter, the function expects at least as many + ** additional arguments as specified in format. + * @param fmt Format of the Message + * @param ... any number of parameters + * @return a Anope::string + */ + extern CoreExport string printf(const char *fmt, ...); + + /** Return the last error code + * @return The error code + */ + extern CoreExport int LastErrorCode(); + + /** Return the last error, uses errno/GetLastError() to determine this + * @return An error message + */ + extern CoreExport const string LastError(); + + /** Determines if a path is a file + */ + extern CoreExport bool IsFile(const Anope::string &file); + + /** Converts a string into seconds + * @param s The string, eg 3d + * @return The time represented by the string, eg 259,200 + */ + extern CoreExport time_t DoTime(const Anope::string &s); + + /** Retrieves a human readable string representing the time in seconds + * @param seconds The time on seconds, eg 60 + * @param nc The account to use language settings for to translate this string, if applicable + * @return A human readable string, eg "1 minute" + */ + extern CoreExport Anope::string Duration(time_t seconds, const NickCore *nc = NULL); + + /** Generates a human readable string of type "expires in ..." + * @param expires time in seconds + * @param nc The account to use language settings for to translate this string, if applicable + * @return A human readable string, eg "expires in 5 days" + */ + extern CoreExport Anope::string Expires(time_t seconds, const NickCore *nc = NULL); + + /** Converts a time in seconds (epoch) to a human readable format. + * @param t The time + * @param nc The account to use language settings for to translate this string, if applicable + * @param short_output If true, the output is just a date (eg, "Apr 12 20:18:22 2009 MSD"), else it includes the date and how long ago/from now that date is, (eg "Apr 12 20:18:22 2009 MSD (1313 days, 9 hours, 32 minutes ago)" + */ + extern CoreExport Anope::string strftime(time_t t, const NickCore *nc = NULL, bool short_output = false); + + /** Normalize buffer, stripping control characters and colors + * @param A string to be parsed for control and color codes + * @return A string stripped of control and color codes + */ + extern CoreExport Anope::string NormalizeBuffer(const Anope::string &); + + /** Main processing routine. Parses the message and takes the appropriate action. + * @param Raw message from the uplink + */ + extern void Process(const Anope::string &); + + /** Does a blocking dns query and returns the first IP. + * @param host host to look up + * @param type inet addr type + * @return the IP if it was found, else the host + */ + extern Anope::string Resolve(const Anope::string &host, int type); + + /** Generate a string of random letters and numbers + * @param len The length of the string returned + */ + extern CoreExport Anope::string Random(size_t len); +} + +/** sepstream allows for splitting token separated lists. + * Each successive call to sepstream::GetToken() returns + * the next token, until none remain, at which point the method returns + * an empty string. + */ +class CoreExport sepstream +{ + private: + /** Original string. + */ + Anope::string tokens; + /** Seperator value + */ + char sep; + /** Current string position + */ + size_t pos; + /** If set then GetToken() can return an empty string + */ + bool allow_empty; + public: + /** Create a sepstream and fill it with the provided data + */ + sepstream(const Anope::string &source, char separator, bool allowempty = false); + + /** Fetch the next token from the stream + * @param token The next token from the stream is placed here + * @return True if tokens still remain, false if there are none left + */ + bool GetToken(Anope::string &token); + + /** Gets token number 'num' from the stream + * @param token The token is placed here + * @param num The token number to fetch + * @return True if the token was able to be fetched + */ + bool GetToken(Anope::string &token, int num); + + /** Gets every token from this stream + * @param token Tokens are pushed back here + */ + template void GetTokens(T& token) + { + token.clear(); + Anope::string t; + while (this->GetToken(t)) + token.push_back(t); + } + + /** Gets token number 'num' from the stream and all remaining tokens. + * @param token The token is placed here + * @param num The token number to fetch + * @return True if the token was able to be fetched + */ + bool GetTokenRemainder(Anope::string &token, int num); + + /** Determines the number of tokens in this stream. + * @return The number of tokens in this stream + */ + int NumTokens(); + + /** Fetch the entire remaining stream, without tokenizing + * @return The remaining part of the stream + */ + const Anope::string GetRemaining(); + + /** Returns true if the end of the stream has been reached + * @return True if the end of the stream has been reached, otherwise false + */ + bool StreamEnd(); +}; + +/** A derived form of sepstream, which separates on commas + */ +class commasepstream : public sepstream +{ + public: + /** Initialize with comma separator + */ + commasepstream(const Anope::string &source, bool allowempty = false) : sepstream(source, ',', allowempty) { } +}; + +/** A derived form of sepstream, which separates on spaces + */ +class spacesepstream : public sepstream +{ + public: + /** Initialize with space separator + */ + spacesepstream(const Anope::string &source) : sepstream(source, ' ') { } +}; + +/** This class can be used on its own to represent an exception, or derived to represent a module-specific exception. + * When a module whishes to abort, e.g. within a constructor, it should throw an exception using ModuleException or + * a class derived from ModuleException. If a module throws an exception during its constructor, the module will not + * be loaded. If this happens, the error message returned by ModuleException::GetReason will be displayed to the user + * attempting to load the module, or dumped to the console if the ircd is currently loading for the first time. + */ +class CoreException : public std::exception +{ + protected: + /** Holds the error message to be displayed + */ + Anope::string err; + /** Source of the exception + */ + Anope::string source; + public: + /** Default constructor, just uses the error message 'Core threw an exception'. + */ + CoreException() : err("Core threw an exception"), source("The core") { } + /** This constructor can be used to specify an error message before throwing. + */ + CoreException(const Anope::string &message) : err(message), source("The core") { } + /** This constructor can be used to specify an error message before throwing, + * and to specify the source of the exception. + */ + CoreException(const Anope::string &message, const Anope::string &src) : err(message), source(src) { } + /** This destructor solves world hunger, cancels the world debt, and causes the world to end. + * Actually no, it does nothing. Never mind. + * @throws Nothing! + */ + virtual ~CoreException() throw() { } + /** Returns the reason for the exception. + * The module should probably put something informative here as the user will see this upon failure. + */ + virtual const Anope::string &GetReason() const + { + return err; + } + + virtual const Anope::string &GetSource() const + { + return source; + } +}; + +class ModuleException : public CoreException +{ + public: + /** Default constructor, just uses the error message 'Module threw an exception'. + */ + ModuleException() : CoreException("Module threw an exception", "A Module") { } + + /** This constructor can be used to specify an error message before throwing. + */ + ModuleException(const Anope::string &message) : CoreException(message, "A Module") { } + /** This destructor solves world hunger, cancels the world debt, and causes the world to end. + * Actually no, it does nothing. Never mind. + * @throws Nothing! + */ + virtual ~ModuleException() throw() { } +}; + +class ConvertException : public CoreException +{ + public: + ConvertException(const Anope::string &reason = "") : CoreException(reason) { } + + virtual ~ConvertException() throw() { } +}; + +/** Convert something to a string + */ +template inline Anope::string stringify(const T &x) +{ + std::ostringstream stream; + + if (!(stream << x)) + throw ConvertException("Stringify fail"); + + return stream.str(); +} + +template inline void convert(const Anope::string &s, T &x, Anope::string &leftover, bool failIfLeftoverChars = true) +{ + leftover.clear(); + std::istringstream i(s.str()); + char c; + if (!(i >> x)) + throw ConvertException("Convert fail"); + if (failIfLeftoverChars) + { + if (i.get(c)) + throw ConvertException("Convert fail"); + } + else + { + std::string left; + getline(i, left); + leftover = left; + } +} + +template inline void convert(const Anope::string &s, T &x, bool failIfLeftoverChars = true) +{ + Anope::string Unused; + convert(s, x, Unused, failIfLeftoverChars); +} + +template inline T convertTo(const Anope::string &s, Anope::string &leftover, bool failIfLeftoverChars = true) +{ + T x; + convert(s, x, leftover, failIfLeftoverChars); + return x; +} + +template inline T convertTo(const Anope::string &s, bool failIfLeftoverChars = true) +{ + T x; + convert(s, x, failIfLeftoverChars); + return x; +} + +/** Casts to be used instead of dynamic_cast, this uses dynamic_cast + * for debug builds and static_cast on release builds + * to speed up the program because dynamic_cast relies on RTTI. + */ +#ifdef DEBUG_BUILD +# include +template inline T anope_dynamic_static_cast(O ptr) +{ + T ret = dynamic_cast(ptr); + if (ptr != NULL && ret == NULL) + throw CoreException(Anope::string("anope_dynamic_static_cast<") + typeid(T).name() + ">(" + typeid(O).name() + ") fail"); + return ret; +} +#else +template inline T anope_dynamic_static_cast(O ptr) +{ + return static_cast(ptr); +} +#endif + +#endif // ANOPE_H diff --git a/include/base.h b/include/base.h new file mode 100644 index 0000000..e988f16 --- /dev/null +++ b/include/base.h @@ -0,0 +1,143 @@ +/* + * + * (C) 2008-2011 Adam + * (C) 2008-2022 Anope Team + * + * Please read COPYING and README for further details. + */ + +#ifndef BASE_H +#define BASE_H + +#include "services.h" + +/** The base class that most classes in Anope inherit from + */ +class CoreExport Base +{ + /* References to this base class */ + std::set *references; + public: + Base(); + virtual ~Base(); + + /** Adds a reference to this object. Eg, when a Reference + * is created referring to this object this is called. It is used to + * cleanup references when this object is destructed. + */ + void AddReference(ReferenceBase *r); + + void DelReference(ReferenceBase *r); +}; + +class ReferenceBase +{ + protected: + bool invalid; + public: + ReferenceBase() : invalid(false) { } + ReferenceBase(const ReferenceBase &other) : invalid(other.invalid) { } + virtual ~ReferenceBase() { } + inline void Invalidate() { this->invalid = true; } +}; + +/** Used to hold pointers to objects that may be deleted. A Reference will + * no longer be valid once the object it refers is destructed. + */ +template +class Reference : public ReferenceBase +{ + protected: + T *ref; + public: + Reference() : ref(NULL) + { + } + + Reference(T *obj) : ref(obj) + { + if (ref) + ref->AddReference(this); + } + + Reference(const Reference &other) : ReferenceBase(other), ref(other.ref) + { + if (operator bool()) + ref->AddReference(this); + } + + virtual ~Reference() + { + if (operator bool()) + ref->DelReference(this); + } + + inline Reference& operator=(const Reference &other) + { + if (this != &other) + { + if (*this) + this->ref->DelReference(this); + + this->ref = other.ref; + this->invalid = other.invalid; + + if (*this) + this->ref->AddReference(this); + } + return *this; + } + + /* We explicitly call operator bool here in several places to prevent other + * operators, such operator T*, from being called instead, which will mess + * with any class inheriting from this that overloads this operator. + */ + virtual operator bool() + { + if (!this->invalid) + return this->ref != NULL; + return false; + } + + inline operator T*() + { + if (operator bool()) + return this->ref; + return NULL; + } + + inline T* operator->() + { + if (operator bool()) + return this->ref; + return NULL; + } + + inline T* operator*() + { + if (operator bool()) + return this->ref; + return NULL; + } + + /** Note that we can't have an operator< that returns this->ref < other.ref + * because this function is used to sort objects in containers (such as set + * or map), and if the references themselves can change if the object they + * refer to is invalidated or changed, then this screws with the order that + * the objects would be in the container without properly adjusting the + * container, resulting in weird stuff. + * + * As such, we don't allow storing references in containers that require + * operator<, because they would not be able to compare what the references + * actually referred to. + */ + + inline bool operator==(const Reference &other) + { + if (!this->invalid) + return this->ref == other; + return false; + } +}; + +#endif // BASE_H diff --git a/include/bots.h b/include/bots.h new file mode 100644 index 0000000..a8b0624 --- /dev/null +++ b/include/bots.h @@ -0,0 +1,135 @@ +/* + * + * (C) 2008-2011 Robin Burchell + * (C) 2008-2022 Anope Team + * + * Please read COPYING and README for further details. + */ + +#ifndef BOTS_H +#define BOTS_H + +#include "users.h" +#include "anope.h" +#include "serialize.h" +#include "commands.h" + + +typedef Anope::map botinfo_map; + +extern CoreExport Serialize::Checker BotListByNick, BotListByUID; + +/* A service bot (NickServ, ChanServ, a BotServ bot, etc). */ +class CoreExport BotInfo : public User, public Serializable +{ + /* Channels this bot is assigned to */ + Serialize::Checker > channels; + public: + time_t created; + /* Last time this bot said something (via privmsg) */ + time_t lastmsg; + /* Map of actual command names -> service name/permission required */ + CommandInfo::map commands; + /* Modes the bot should have as configured in service:modes */ + Anope::string botmodes; + /* Channels the bot should be in as configured in service:channels */ + std::vector botchannels; + /* Whether or not this bot is introduced to the network */ + bool introduced; + /* Bot can only be assigned by irc ops */ + bool oper_only; + /* Bot is defined in the configuration file */ + bool conf; + + /** Create a new bot. + * @param nick The nickname to assign to the bot. + * @param user The ident to give the bot. + * @param host The hostname to give the bot. + * @param real The realname to give the bot. + * @param bmodes The modes to give the bot. + */ + BotInfo(const Anope::string &nick, const Anope::string &user = "", const Anope::string &host = "", const Anope::string &real = "", const Anope::string &bmodes = ""); + + /** Destroy a bot, clearing up appropriately. + */ + virtual ~BotInfo(); + + void Serialize(Serialize::Data &data) const; + static Serializable* Unserialize(Serializable *obj, Serialize::Data &); + + void GenerateUID(); + + void OnKill(); + + /** Change the nickname for the bot. + * @param newnick The nick to change to + */ + void SetNewNick(const Anope::string &newnick); + + /** Return the channels this bot is assigned to + */ + const std::set &GetChannels() const; + + /** Assign this bot to a given channel, removing the existing assigned bot if one exists. + * @param u The user assigning the bot, or NULL + * @param ci The channel registration to assign the bot to. + */ + void Assign(User *u, ChannelInfo *ci); + + /** Remove this bot from a given channel. + * @param u The user requesting the unassign, or NULL. + * @param ci The channel registration to remove the bot from. + */ + void UnAssign(User *u, ChannelInfo *ci); + + /** Get the number of channels this bot is assigned to + */ + unsigned GetChannelCount() const; + + /** Join this bot to a channel + * @param c The channel + * @param status The status the bot should have on the channel + */ + void Join(Channel *c, ChannelStatus *status = NULL); + + /** Join this bot to a channel + * @param chname The channel name + * @param status The status the bot should have on the channel + */ + void Join(const Anope::string &chname, ChannelStatus *status = NULL); + + /** Part this bot from a channel + * @param c The channel + * @param reason The reason we're parting + */ + void Part(Channel *c, const Anope::string &reason = ""); + + /** Called when a user messages this bot + * @param u The user + * @param message The users' message + */ + virtual void OnMessage(User *u, const Anope::string &message); + + /** Link a command name to a command in services + * @param cname The command name + * @param sname The service name + * @param permission Permission required to execute the command, if any + * @return The commandinfo for the newly created command + */ + CommandInfo& SetCommand(const Anope::string &cname, const Anope::string &sname, const Anope::string &permission = ""); + + /** Get command info for a command + * @param cname The command name + * @return A struct containing service name and permission + */ + CommandInfo *GetCommand(const Anope::string &cname); + + /** Find a bot by nick + * @param nick The nick + * @param nick_only True to only look by nick, and not by UID + * @return The bot, if it exists + */ + static BotInfo* Find(const Anope::string &nick, bool nick_only = false); +}; + +#endif // BOTS_H diff --git a/include/channels.h b/include/channels.h new file mode 100644 index 0000000..79ea738 --- /dev/null +++ b/include/channels.h @@ -0,0 +1,310 @@ +/* Channel support + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#ifndef CHANNELS_H +#define CHANNELS_H + +#include "anope.h" +#include "extensible.h" +#include "modes.h" +#include "serialize.h" + +typedef Anope::hash_map channel_map; + +extern CoreExport channel_map ChannelList; + +/* A user container, there is one of these per user per channel. */ +struct ChanUserContainer : public Extensible +{ + User *user; + Channel *chan; + /* Status the user has in the channel */ + ChannelStatus status; + + ChanUserContainer(User *u, Channel *c) : user(u), chan(c) { } +}; + +class CoreExport Channel : public Base, public Extensible +{ + static std::vector deleting; + + public: + typedef std::multimap ModeList; + private: + /** A map of channel modes with their parameters set on this channel + */ + ModeList modes; + + public: + /* Channel name */ + Anope::string name; + /* Set if this channel is registered. ci->c == this. Contains information relevant to the registered channel */ + Serialize::Reference ci; + /* When the channel was created */ + time_t creation_time; + /* If the channel has just been created in a netjoin */ + bool syncing; + /* Is configured in the conf as a channel bots should be in */ + bool botchannel; + + /* Users in the channel */ + typedef std::map ChanUserList; + ChanUserList users; + + /* Current topic of the channel */ + Anope::string topic; + /* Who set the topic */ + Anope::string topic_setter; + /* The timestamp associated with the topic. Not necessarily anywhere close to Anope::CurTime. + * This is the time the topic was *originally set*. When we restore the topic we want to change the TS back + * to this, but we can only do this on certain IRCds. + */ + time_t topic_ts; + /* The actual time the topic was set, probably close to Anope::CurTime */ + time_t topic_time; + + time_t server_modetime; /* Time of last server MODE */ + time_t chanserv_modetime; /* Time of last check_modes() */ + int16_t server_modecount; /* Number of server MODEs this second */ + int16_t chanserv_modecount; /* Number of check_mode()'s this sec */ + int16_t bouncy_modes; /* Did we fail to set modes here? */ + + private: + /** Constructor + * @param name The channel name + * @param ts The time the channel was created + */ + Channel(const Anope::string &nname, time_t ts = Anope::CurTime); + + public: + /** Destructor + */ + ~Channel(); + + /** Call if we need to unset all modes and clear all user status (internally). + * Only useful if we get a SJOIN with a TS older than what we have here + */ + void Reset(); + + /** Restore the channel topic, set mlock (key), set stickied bans, etc + */ + void Sync(); + + /** Check if a channels modes are correct. + */ + void CheckModes(); + + /** Check if this channel should be deleted + */ + bool CheckDelete(); + + /** Join a user internally to the channel + * @param u The user + * @param status The status to give the user, if any + * @return The UserContainer for the user + */ + ChanUserContainer* JoinUser(User *u, const ChannelStatus *status); + + /** Remove a user internally from the channel + * @param u The user + */ + void DeleteUser(User *u); + + /** Check if the user is on the channel + * @param u The user + * @return A user container if found, else NULL + */ + ChanUserContainer *FindUser(User *u) const; + + /** Check if a user has a status on a channel + * @param u The user + * @param cms The status mode, or NULL to represent no status + * @return true or false + */ + bool HasUserStatus(User *u, ChannelModeStatus *cms); + + /** Check if a user has a status on a channel + * Use the overloaded function for ChannelModeStatus* to check for no status + * @param u The user + * @param name The mode name, eg CMODE_OP, CMODE_VOICE + * @return true or false + */ + bool HasUserStatus(User *u, const Anope::string &name); + + /** See if a channel has a mode + * @param name The mode name + * @return The number of modes set + * @param param The optional mode param + */ + size_t HasMode(const Anope::string &name, const Anope::string ¶m = ""); + + /** Set a mode internally on a channel, this is not sent out to the IRCd + * @param setter The setter + * @param cm The mode + * @param param The param + * @param enforce_mlock true if mlocks should be enforced, false to override mlock + */ + void SetModeInternal(MessageSource &source, ChannelMode *cm, const Anope::string ¶m = "", bool enforce_mlock = true); + + /** Remove a mode internally on a channel, this is not sent out to the IRCd + * @param setter The Setter + * @param cm The mode + * @param param The param + * @param enforce_mlock true if mlocks should be enforced, false to override mlock + */ + void RemoveModeInternal(MessageSource &source, ChannelMode *cm, const Anope::string ¶m = "", bool enforce_mlock = true); + + /** Set a mode on a channel + * @param bi The client setting the modes + * @param cm The mode + * @param param Optional param arg for the mode + * @param enforce_mlock true if mlocks should be enforced, false to override mlock + */ + void SetMode(BotInfo *bi, ChannelMode *cm, const Anope::string ¶m = "", bool enforce_mlock = true); + + /** + * Set a mode on a channel + * @param bi The client setting the modes + * @param name The mode name + * @param param Optional param arg for the mode + * @param enforce_mlock true if mlocks should be enforced, false to override mlock + */ + void SetMode(BotInfo *bi, const Anope::string &name, const Anope::string ¶m = "", bool enforce_mlock = true); + + /** Remove a mode from a channel + * @param bi The client setting the modes + * @param cm The mode + * @param param Optional param arg for the mode + * @param enforce_mlock true if mlocks should be enforced, false to override mlock + */ + void RemoveMode(BotInfo *bi, ChannelMode *cm, const Anope::string ¶m = "", bool enforce_mlock = true); + + /** + * Remove a mode from a channel + * @param bi The client setting the modes + * @param name The mode name + * @param param Optional param arg for the mode + * @param enforce_mlock true if mlocks should be enforced, false to override mlock + */ + void RemoveMode(BotInfo *bi, const Anope::string &name, const Anope::string ¶m = "", bool enforce_mlock = true); + + /** Get a modes parameter for the channel + * @param name The mode + * @param target a string to put the param into + * @return true if the parameter was fetched, false if on error (mode not set) etc. + */ + bool GetParam(const Anope::string &name, Anope::string &target) const; + + /** Set a string of modes on the channel + * @param bi The client setting the modes + * @param enforce_mlock Should mlock be enforced on this mode change + * @param cmodes The modes to set + */ + void SetModes(BotInfo *bi, bool enforce_mlock, const char *cmodes, ...); + + /** Set a string of modes internally on a channel + * @param source The setter + * @param mode the modes + * @param enforce_mlock true to enforce mlock + */ + void SetModesInternal(MessageSource &source, const Anope::string &mode, time_t ts = 0, bool enforce_mlock = true); + + /** Does the given user match the given list? (CMODE_BAN, CMODE_EXCEPT, etc, a list mode) + * @param u The user + * @param list The mode of the list to check (eg CMODE_BAN) + * @return true if the user matches the list + */ + bool MatchesList(User *u, const Anope::string &list); + + /** Kick a user from a channel internally + * @param source The sender of the kick + * @param nick The nick being kicked + * @param reason The reason for the kick + */ + void KickInternal(const MessageSource &source, const Anope::string &nick, const Anope::string &reason); + + /** Kick a user from the channel + * @param bi The sender, can be NULL for the service bot for this channel + * @param u The user being kicked + * @param reason The reason for the kick + * @return true if the kick was successful, false if a module blocked the kick + */ + bool Kick(BotInfo *bi, User *u, const char *reason = NULL, ...); + + /** Get all modes set on this channel, excluding status modes. + * @return a map of modes and their optional parameters. + */ + const ModeList &GetModes() const; + + /** Get a list of modes on a channel + * @param name A mode name to get the list of + * @return a vector of the list mode entries + */ + std::vector GetModeList(const Anope::string &name); + + /** Get a string of the modes set on this channel + * @param complete Include mode parameters + * @param plus If set to false (with complete), mode parameters will not be given for modes requiring no parameters to be unset + * @return A mode string + */ + Anope::string GetModes(bool complete, bool plus); + + /** Update the topic of the channel internally, and reset it if topiclock etc says to + * @param user The user setting the new topic + * @param newtopic The new topic + * @param ts The time the new topic is being set + */ + void ChangeTopicInternal(User *u, const Anope::string &user, const Anope::string &newtopic, time_t ts = Anope::CurTime); + + /** Update the topic of the channel, and reset it if topiclock etc says to + * @param user The user setting the topic + * @param newtopic The new topic + * @param ts The time when the new topic is being set + */ + void ChangeTopic(const Anope::string &user, const Anope::string &newtopic, time_t ts = Anope::CurTime); + + /** Set the correct modes, or remove the ones granted without permission, + * for the specified user. + * @param user The user to give/remove modes to/from + * @param give_modes if true modes may be given to the user + */ + void SetCorrectModes(User *u, bool give_modes); + + /** Unbans a user from this channel. + * @param u The user to unban + * @param mode The mode to unban + * @param full Whether or not to match using the user's real host and IP + * @return whether or not a ban was removed + */ + bool Unban(User *u, const Anope::string &mode, bool full = false); + + /** Check whether a user is permitted to be on this channel + * @param u The user + * @return true if they are allowed, false if they aren't and were kicked + */ + bool CheckKick(User *user); + + /** Finds a channel + * @param name The channel to find + * @return The channel, if found + */ + static Channel* Find(const Anope::string &name); + + /** Finds or creates a channel + * @param name The channel name + * @param created Set to true if the channel was just created + * @param ts The time the channel was created + */ + static Channel *FindOrCreate(const Anope::string &name, bool &created, time_t ts = Anope::CurTime); + + void QueueForDeletion(); + + static void DeleteChannels(); +}; + +#endif // CHANNELS_H diff --git a/include/commands.h b/include/commands.h new file mode 100644 index 0000000..0a01e74 --- /dev/null +++ b/include/commands.h @@ -0,0 +1,187 @@ +/* Declarations for command data. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef COMMAND_H +#define COMMAND_H + +#include "service.h" +#include "anope.h" +#include "channels.h" + +struct CommandGroup +{ + Anope::string name, description; +}; + +/* Used in BotInfo::commands */ +struct CommandInfo +{ + typedef Anope::map map; + + CommandInfo() : hide(false), prepend_channel(false) { } + + /* Service name of the command */ + Anope::string name; + /* Permission required to execute the command */ + Anope::string permission; + /* Group this command is in */ + Anope::string group; + /* whether or not to hide this command in help output */ + bool hide; + /* Only used with fantasy */ + bool prepend_channel; +}; + +/* Where the replies from commands go to. User inherits from this and is the normal + * source of a CommandReply + */ +struct CoreExport CommandReply +{ + virtual ~CommandReply() { } + virtual void SendMessage(BotInfo *source, const Anope::string &msg) = 0; +}; + +/* The source for a command */ +class CoreExport CommandSource +{ + /* The nick executing the command */ + Anope::string nick; + /* User executing the command, may be NULL */ + Reference u; + public: + /* The account executing the command */ + Reference nc; + /* for web clients */ + Anope::string ip; + /* Where the reply should go */ + CommandReply *reply; + /* Channel the command was executed on (fantasy) */ + Reference c; + /* The service this command is on */ + Reference service; + /* The actual name of the command being executed */ + Anope::string command; + /* The permission of the command being executed */ + Anope::string permission; + + CommandSource(const Anope::string &n, User *user, NickCore *core, CommandReply *reply, BotInfo *bi); + + const Anope::string &GetNick() const; + User *GetUser(); + NickCore *GetAccount(); + AccessGroup AccessFor(ChannelInfo *ci); + bool IsFounder(ChannelInfo *ci); + + void Reply(const char *message, ...); + void Reply(const Anope::string &message); + + bool HasCommand(const Anope::string &cmd); + bool HasPriv(const Anope::string &cmd); + bool IsServicesOper(); + bool IsOper(); +}; + +/** Every services command is a class, inheriting from Command. + */ +class CoreExport Command : public Service +{ + Anope::string desc; + std::vector syntax; + /* Allow unregistered users to use this command */ + bool allow_unregistered; + /* Command requires that a user is executing it */ + bool require_user; + + public: + /* Maximum parameters accepted by this command */ + size_t max_params; + /* Minimum parameters required to use this command */ + size_t min_params; + + /* Module which owns us */ + Module *module; + + protected: + /** Create a new command. + * @param owner The owner of the command + * @param sname The command name + * @param min_params The minimum number of parameters the parser will require to execute this command + * @param max_params The maximum number of parameters the parser will create, after max_params, all will be combined into the last argument. + * NOTE: If max_params is not set (default), there is no limit to the max number of params. + */ + Command(Module *owner, const Anope::string &sname, size_t min_params, size_t max_params = 0); + + public: + virtual ~Command(); + + protected: + void SetDesc(const Anope::string &d); + + void ClearSyntax(); + void SetSyntax(const Anope::string &s); + void SendSyntax(CommandSource &); + + void AllowUnregistered(bool b); + void RequireUser(bool b); + + public: + bool AllowUnregistered() const; + bool RequireUser() const; + + /** Get the command description + * @param source The source wanting the command description + * @return The commands description + */ + virtual const Anope::string GetDesc(CommandSource &source) const; + + /** Execute this command. + * @param source The source + * @param params Command parameters + */ + virtual void Execute(CommandSource &source, const std::vector ¶ms) = 0; + + /** Called when HELP is requested for the client this command is on. + * @param source The source + */ + virtual void OnServHelp(CommandSource &source); + + /** Requested when the user is requesting help on this command. Help on this command should be sent to the user. + * @param source The source + * @param subcommand The subcommand the user is requesting help on, or an empty string. (e.g. /ns help set foo bar lol gives a subcommand of "FOO BAR LOL") + * @return true if help was provided to the user, false otherwise. + */ + virtual bool OnHelp(CommandSource &source, const Anope::string &subcommand); + + /** Requested when the user provides bad syntax to this command (not enough params, etc). + * @param source The source + * @param subcommand The subcommand the user tried to use + */ + virtual void OnSyntaxError(CommandSource &source, const Anope::string &subcommand); + + /** Runs a command + * @param source The source of the command + * @param message The full message to run, the command is at the beginning of the message + */ + static void Run(CommandSource &source, const Anope::string &message); + + void Run(CommandSource &source, const Anope::string &, const CommandInfo &, std::vector ¶ms); + + /** Looks up a command name from the service name. + * Note that if the same command exists multiple places this will return the first one encountered + * @param command_service The command service to lookup, eg, nickserv/register + * @param bot If found, is set to the bot the command is on, eg NickServ + * @param name If found, is set to the command name, eg REGISTER + * @return true if the given command service exists + */ + static bool FindCommandFromService(const Anope::string &command_service, BotInfo* &bi, Anope::string &name); +}; + +#endif // COMMANDS_H diff --git a/include/config.h b/include/config.h new file mode 100644 index 0000000..877cbab --- /dev/null +++ b/include/config.h @@ -0,0 +1,184 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef CONFIG_H +#define CONFIG_H + +#include "account.h" +#include "regchannel.h" +#include "users.h" +#include "opertype.h" +#include + +namespace Configuration +{ + class CoreExport Block + { + friend struct Conf; + + public: + typedef Anope::map item_map; + typedef Anope::multimap block_map; + + private: + Anope::string name; + item_map items; + block_map blocks; + int linenum; + + public: + Block(const Anope::string &); + const Anope::string &GetName() const; + int CountBlock(const Anope::string &name); + Block* GetBlock(const Anope::string &name, int num = 0); + + template inline T Get(const Anope::string &tag) + { + return this->Get(tag, ""); + } + /* VS 2008 has an issue with having a default argument here (def = ""), which is why the above + * function exists. + */ + template T Get(const Anope::string &tag, const Anope::string &def) const + { + const Anope::string &value = this->Get(tag, def); + if (!value.empty()) + try + { + return convertTo(value); + } + catch (const ConvertException &) { } + return T(); + } + + bool Set(const Anope::string &tag, const Anope::string &value); + const item_map* GetItems() const; + }; + + template<> CoreExport const Anope::string Block::Get(const Anope::string &tag, const Anope::string& def) const; + template<> CoreExport time_t Block::Get(const Anope::string &tag, const Anope::string &def) const; + template<> CoreExport bool Block::Get(const Anope::string &tag, const Anope::string &def) const; + + /** Represents a configuration file + */ + class File + { + Anope::string name; + bool executable; + FILE *fp; + public: + File(const Anope::string &, bool); + ~File(); + const Anope::string &GetName() const; + Anope::string GetPath() const; + + bool IsOpen() const; + bool Open(); + void Close(); + bool End() const; + Anope::string Read(); + }; + + struct Uplink; + + struct CoreExport Conf : Block + { + /* options:readtimeout */ + time_t ReadTimeout; + /* options:useprivmsg */ + bool UsePrivmsg; + /* If we should default to privmsging clients */ + bool DefPrivmsg; + /* Default language */ + Anope::string DefLanguage; + /* options:timeoutcheck */ + time_t TimeoutCheck; + /* options:usestrictprivmsg */ + bool UseStrictPrivmsg; + /* networkinfo:nickchars */ + Anope::string NickChars; + + /* either "/msg " or "/" */ + Anope::string StrictPrivmsg; + /* List of uplink servers to try and connect to */ + std::vector Uplinks; + /* A vector of our logfile options */ + std::vector LogInfos; + /* Array of ulined servers */ + std::vector Ulines; + /* List of available opertypes */ + std::vector MyOperTypes; + /* List of pairs of opers and their opertype from the config */ + std::vector Opers; + /* Map of fantasy commands */ + CommandInfo::map Fantasy; + /* Command groups */ + std::vector CommandGroups; + /* List of modules to autoload */ + std::vector ModulesAutoLoad; + + /* module configuration blocks */ + std::map modules; + Anope::map bots; + + Conf(); + ~Conf(); + + void LoadConf(File &file); + void Post(Conf *old); + + Block *GetModule(Module *); + Block *GetModule(const Anope::string &name); + + BotInfo *GetClient(const Anope::string &name); + + Block *GetCommand(CommandSource &); + }; + + struct Uplink + { + Anope::string host; + unsigned port; + Anope::string password; + bool ipv6; + + Uplink(const Anope::string &_host, int _port, const Anope::string &_password, bool _ipv6) : host(_host), port(_port), password(_password), ipv6(_ipv6) { } + inline bool operator==(const Uplink &other) const { return host == other.host && port == other.port && password == other.password && ipv6 == other.ipv6; } + inline bool operator!=(const Uplink &other) const { return !(*this == other); } + }; +} + +/** This class can be used on its own to represent an exception, or derived to represent a module-specific exception. + * When a module whishes to abort, e.g. within a constructor, it should throw an exception using ModuleException or + * a class derived from ModuleException. If a module throws an exception during its constructor, the module will not + * be loaded. If this happens, the error message returned by ModuleException::GetReason will be displayed to the user + * attempting to load the module, or dumped to the console if the ircd is currently loading for the first time. + */ +class ConfigException : public CoreException +{ + public: + /** Default constructor, just uses the error message 'Config threw an exception'. + */ + ConfigException() : CoreException("Config threw an exception", "Config Parser") { } + /** This constructor can be used to specify an error message before throwing. + */ + ConfigException(const Anope::string &message) : CoreException(message, "Config Parser") { } + /** This destructor solves world hunger, cancels the world debt, and causes the world to end. + * Actually no, it does nothing. Never mind. + * @throws Nothing! + */ + virtual ~ConfigException() throw() { } +}; + +extern Configuration::File ServicesConf; +extern CoreExport Configuration::Conf *Config; + +#endif // CONFIG_H diff --git a/include/defs.h b/include/defs.h new file mode 100644 index 0000000..3bc2165 --- /dev/null +++ b/include/defs.h @@ -0,0 +1,53 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +class AccessGroup; +class AutoKick; +class BotInfo; +class CallBack; +class ChanAccess; +class Channel; +class ChannelInfo; +class ChannelStatus; +struct ChanUserContainer; +class ClientSocket; +class Command; +class CommandSource; +namespace Configuration { struct Conf; } +class ConnectionSocket; +namespace DNS { struct Query; } +class Entry; +class IdentifyRequest; +class InfoFormatter; +class IRCDProto; +class ListenSocket; +class Log; +class Memo; +class MessageSource; +class Module; +class NickAlias; +class NickCore; +class OperType; +class ReferenceBase; +class Regex; +class Serializable; +class Server; +class Socket; +class Thread; +class User; +class XLine; +class XLineManager; +struct BadWord; +struct Exception; +struct MemoInfo; +struct ModeLock; +struct Oper; +namespace SASL { struct Message; } diff --git a/include/extensible.h b/include/extensible.h new file mode 100644 index 0000000..f911d68 --- /dev/null +++ b/include/extensible.h @@ -0,0 +1,263 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#ifndef EXTENSIBLE_H +#define EXTENSIBLE_H + +#include "anope.h" +#include "serialize.h" +#include "service.h" +#include "logger.h" + +class Extensible; + +class CoreExport ExtensibleBase : public Service +{ + protected: + std::map items; + + ExtensibleBase(Module *m, const Anope::string &n); + ~ExtensibleBase(); + + public: + virtual void Unset(Extensible *obj) = 0; + + /* called when an object we are keep track of is serializing */ + virtual void ExtensibleSerialize(const Extensible *, const Serializable *, Serialize::Data &) const { } + virtual void ExtensibleUnserialize(Extensible *, Serializable *, Serialize::Data &) { } +}; + +class CoreExport Extensible +{ + public: + std::set extension_items; + + virtual ~Extensible(); + + void UnsetExtensibles(); + + template T* GetExt(const Anope::string &name) const; + bool HasExt(const Anope::string &name) const; + + template T* Extend(const Anope::string &name, const T &what); + template T* Extend(const Anope::string &name); + template T* Require(const Anope::string &name); + template void Shrink(const Anope::string &name); + + static void ExtensibleSerialize(const Extensible *, const Serializable *, Serialize::Data &data); + static void ExtensibleUnserialize(Extensible *, Serializable *, Serialize::Data &data); +}; + +template +class BaseExtensibleItem : public ExtensibleBase +{ + protected: + virtual T *Create(Extensible *) = 0; + + public: + BaseExtensibleItem(Module *m, const Anope::string &n) : ExtensibleBase(m, n) { } + + ~BaseExtensibleItem() + { + while (!items.empty()) + { + std::map::iterator it = items.begin(); + Extensible *obj = it->first; + T *value = static_cast(it->second); + + obj->extension_items.erase(this); + items.erase(it); + delete value; + } + } + + T* Set(Extensible *obj, const T &value) + { + T* t = Set(obj); + if (t) + *t = value; + return t; + } + + T* Set(Extensible *obj) + { + T* t = Create(obj); + Unset(obj); + items[obj] = t; + obj->extension_items.insert(this); + return t; + } + + void Unset(Extensible *obj) anope_override + { + T *value = Get(obj); + items.erase(obj); + obj->extension_items.erase(this); + delete value; + } + + T* Get(const Extensible *obj) const + { + std::map::const_iterator it = items.find(const_cast(obj)); + if (it != items.end()) + return static_cast(it->second); + return NULL; + } + + bool HasExt(const Extensible *obj) const + { + return items.find(const_cast(obj)) != items.end(); + } + + T* Require(Extensible *obj) + { + T* t = Get(obj); + if (t) + return t; + + return Set(obj); + } +}; + +template +class ExtensibleItem : public BaseExtensibleItem +{ + protected: + T* Create(Extensible *obj) anope_override + { + return new T(obj); + } + public: + ExtensibleItem(Module *m, const Anope::string &n) : BaseExtensibleItem(m, n) { } +}; + +template +class PrimitiveExtensibleItem : public BaseExtensibleItem +{ + protected: + T* Create(Extensible *obj) anope_override + { + return new T(); + } + public: + PrimitiveExtensibleItem(Module *m, const Anope::string &n) : BaseExtensibleItem(m, n) { } +}; + +template<> +class PrimitiveExtensibleItem : public BaseExtensibleItem +{ + protected: + bool* Create(Extensible *) anope_override + { + return NULL; + } + public: + PrimitiveExtensibleItem(Module *m, const Anope::string &n) : BaseExtensibleItem(m, n) { } +}; + +template +class SerializableExtensibleItem : public PrimitiveExtensibleItem +{ + public: + SerializableExtensibleItem(Module *m, const Anope::string &n) : PrimitiveExtensibleItem(m, n) { } + + void ExtensibleSerialize(const Extensible *e, const Serializable *s, Serialize::Data &data) const anope_override + { + T* t = this->Get(e); + data[this->name] << *t; + } + + void ExtensibleUnserialize(Extensible *e, Serializable *s, Serialize::Data &data) anope_override + { + T t; + if (data[this->name] >> t) + this->Set(e, t); + else + this->Unset(e); + } +}; + +template<> +class SerializableExtensibleItem : public PrimitiveExtensibleItem +{ + public: + SerializableExtensibleItem(Module *m, const Anope::string &n) : PrimitiveExtensibleItem(m, n) { } + + void ExtensibleSerialize(const Extensible *e, const Serializable *s, Serialize::Data &data) const anope_override + { + data[this->name] << true; + } + + void ExtensibleUnserialize(Extensible *e, Serializable *s, Serialize::Data &data) anope_override + { + bool b = false; + data[this->name] >> b; + if (b) + this->Set(e); + else + this->Unset(e); + } +}; + +template +struct ExtensibleRef : ServiceReference > +{ + ExtensibleRef(const Anope::string &n) : ServiceReference >("Extensible", n) { } +}; + +template +T* Extensible::GetExt(const Anope::string &name) const +{ + ExtensibleRef ref(name); + if (ref) + return ref->Get(this); + + Log(LOG_DEBUG) << "GetExt for nonexistent type " << name << " on " << static_cast(this); + return NULL; +} + +template +T* Extensible::Extend(const Anope::string &name, const T &what) +{ + T* t = Extend(name); + if (t) + *t = what; + return t; +} + +template +T* Extensible::Extend(const Anope::string &name) +{ + ExtensibleRef ref(name); + if (ref) + return ref->Set(this); + + Log(LOG_DEBUG) << "Extend for nonexistent type " << name << " on " << static_cast(this); + return NULL; +} + +template +T* Extensible::Require(const Anope::string &name) +{ + if (HasExt(name)) + return GetExt(name); + else + return Extend(name); +} + +template +void Extensible::Shrink(const Anope::string &name) +{ + ExtensibleRef ref(name); + if (ref) + ref->Unset(this); + else + Log(LOG_DEBUG) << "Shrink for nonexistent type " << name << " on " << static_cast(this); +} + +#endif // EXTENSIBLE_H diff --git a/include/hashcomp.h b/include/hashcomp.h new file mode 100644 index 0000000..8d3d8d6 --- /dev/null +++ b/include/hashcomp.h @@ -0,0 +1,199 @@ +/* + * + * (C) 2002-2011 InspIRCd Development Team + * (C) 2009-2022 Anope Team + * + * Please read COPYING and README for further details. + */ + +#ifndef HASHCOMP_H +#define HASHCOMP_H + +#include +#include + +#if defined _LIBCPP_VERSION || defined _WIN32 +#include +#define TR1NS std +#else +#include +#define TR1NS std::tr1 +#endif + +#include "services.h" + +namespace Anope +{ + class string; + + /* Casemap in use by Anope. ci::string's comparison functions use this (and thus Anope::string) */ + extern std::locale casemap; + + extern void CaseMapRebuild(); + extern unsigned char tolower(unsigned char); + extern unsigned char toupper(unsigned char); + + /* ASCII case insensitive ctype. */ + template + class ascii_ctype : public std::ctype + { + public: + char_type do_toupper(char_type c) const anope_override + { + if (c >= 'a' && c <= 'z') + return c - 32; + else + return c; + } + + char_type do_tolower(char_type c) const anope_override + { + if (c >= 'A' && c <= 'Z') + return c + 32; + else + return c; + } + }; + + /* rfc1459 case insensitive ctype, { = [, } = ], and | = \ */ + template + class rfc1459_ctype : public ascii_ctype + { + public: + char_type do_toupper(char_type c) const anope_override + { + if (c == '{' || c == '}' || c == '|') + return c - 32; + else + return ascii_ctype::do_toupper(c); + } + + char_type do_tolower(char_type c) const anope_override + { + if (c == '[' || c == ']' || c == '\\') + return c + 32; + else + return ascii_ctype::do_tolower(c); + } + }; +} + +/** The ci namespace contains a number of helper classes relevant to case insensitive strings. + */ +namespace ci +{ + /** The ci_char_traits class is used for ASCII-style comparison of strings. + * This class is used to implement ci::string, a case-insensitive, ASCII- + * comparing string class. + */ + struct CoreExport ci_char_traits : std::char_traits + { + /** Check if two chars match. + * @param c1st First character + * @param c2nd Second character + * @return true if the characters are equal + */ + static bool eq(char c1st, char c2nd); + + /** Check if two chars do NOT match. + * @param c1st First character + * @param c2nd Second character + * @return true if the characters are unequal + */ + static bool ne(char c1st, char c2nd); + + /** Check if one char is less than another. + * @param c1st First character + * @param c2nd Second character + * @return true if c1st is less than c2nd + */ + static bool lt(char c1st, char c2nd); + + /** Compare two strings of size n. + * @param str1 First string + * @param str2 Second string + * @param n Length to compare to + * @return similar to strcmp, zero for equal, less than zero for str1 + * being less and greater than zero for str1 being greater than str2. + */ + static int compare(const char *str1, const char *str2, size_t n); + + /** Find a char within a string up to position n. + * @param s1 String to find in + * @param n Position to search up to + * @param c Character to search for + * @return Pointer to the first occurrence of c in s1 + */ + static const char *find(const char *s1, int n, char c); + }; + + /** This typedef declares ci::string based upon ci_char_traits. + */ + typedef std::basic_string > string; + + struct CoreExport less + { + /** Compare two Anope::strings as ci::strings and find which one is less + * @param s1 The first string + * @param s2 The second string + * @return true if s1 < s2, else false + */ + bool operator()(const Anope::string &s1, const Anope::string &s2) const; + }; +} + +/* Define operators for + and == with ci::string to std::string for easy assignment + * and comparison + * + * Operator + + */ +inline std::string operator+(std::string &leftval, ci::string &rightval) +{ + return leftval + std::string(rightval.c_str()); +} + +/* Define operators for + and == with ci::string to std::string for easy assignment + * and comparison + * + * Operator + + */ +inline ci::string operator+(ci::string &leftval, std::string &rightval) +{ + return leftval + ci::string(rightval.c_str()); +} + +/* Define operators for + and == with ci::string to std::string for easy assignment + * and comparison + * + * Operator == + */ +inline bool operator==(const std::string &leftval, const ci::string &rightval) +{ + return leftval.c_str() == rightval; +} + +/* Define operators for + and == with ci::string to std::string for easy assignment + * and comparison + * + * Operator == + */ +inline bool operator==(const ci::string &leftval, const std::string &rightval) +{ + return leftval == rightval.c_str(); +} + +/* Define operators != for ci::string to std::string for easy comparison + */ +inline bool operator!=(const ci::string &leftval, const std::string &rightval) +{ + return !(leftval == rightval.c_str()); +} + +/* Define operators != for std::string to ci::string for easy comparison + */ +inline bool operator!=(const std::string &leftval, const ci::string &rightval) +{ + return !(leftval.c_str() == rightval); +} + +#endif // HASHCOMP_H diff --git a/include/language.h b/include/language.h new file mode 100644 index 0000000..1bf1fc8 --- /dev/null +++ b/include/language.h @@ -0,0 +1,127 @@ +/* + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "anope.h" + +namespace Language +{ + + /* Languages we support as configured in services.conf. They are + * added to this list if we detect a language exists in the correct + * location for each language. + */ + extern CoreExport std::vector Languages; + + /* Domains to search when looking for translations other than the + * default "anope domain. This is used by modules who add their own + * language files (and thus domains) to Anope. If a module is loaded + * and we detect a language file exists for at least one of the supported + * languages for the module, then we add the module's domain (its name) + * here. + * + * When strings are translated they are checked against all domains. + */ + extern std::vector Domains; + + /** Initialize the language system. Finds valid language files and + * populates the Languages list. + */ + extern void InitLanguages(); + + /** Translates a string to the default language. + * @param string A string to translate + * @return The translated string if found, else the original string. + */ + extern CoreExport const char *Translate(const char *string); + + /** Translates a string to the language of the given user. + * @param u The user to translate the string for + * @param string A string to translate + * @return The translated string if found, else the original string. + */ + extern CoreExport const char *Translate(User *u, const char *string); + + /** Translates a string to the language of the given account. + * @param nc The account to translate the string for + * @param string A string to translate + * @return The translated string if count, else the original string + */ + extern CoreExport const char *Translate(const NickCore *nc, const char *string); + + /** Translatesa string to the given language. + * @param lang The language to translate to + * @param string The string to translate + * @return The translated string if found, else the original string. + */ + extern CoreExport const char *Translate(const char *lang, const char *string); + +} // namespace Language + +/* Commonly used language strings */ +#define MORE_INFO _("\002%s%s HELP %s\002 for more information.") +#define BAD_USERHOST_MASK _("Mask must be in the form \037user\037@\037host\037.") +#define BAD_EXPIRY_TIME _("Invalid expiry time.") +#define USERHOST_MASK_TOO_WIDE _("%s coverage is too wide; Please use a more specific mask.") +#define READ_ONLY_MODE _("Services are in read-only mode!") +#define PASSWORD_INCORRECT _("Password incorrect.") +#define ACCESS_DENIED _("Access denied.") +#define MORE_OBSCURE_PASSWORD _("Please try again with a more obscure password. Passwords should be at least\n" \ + "five characters long, should not be something easily guessed\n" \ + "(e.g. your real name or your nick), and cannot contain the space or tab characters.") +#define PASSWORD_TOO_LONG _("Your password is too long. It must not exceed %u characters.") +#define NICK_NOT_REGISTERED _("Your nick isn't registered.") +#define NICK_X_NOT_REGISTERED _("Nick \002%s\002 isn't registered.") +#define NICK_X_NOT_IN_USE _("Nick \002%s\002 isn't currently in use.") +#define NICK_X_NOT_ON_CHAN _("\002%s\002 is not currently on channel %s.") +#define NICK_X_SUSPENDED _("Nick %s is currently suspended.") +#define CHAN_X_SUSPENDED _("Channel %s is currently suspended.") +#define CHAN_X_NOT_REGISTERED _("Channel \002%s\002 isn't registered.") +#define CHAN_X_NOT_IN_USE _("Channel \002%s\002 doesn't exist.") +#define NICK_IDENTIFY_REQUIRED _("You must be logged into an account to use that command.") +#define MAIL_X_INVALID _("\002%s\002 is not a valid e-mail address.") +#define UNKNOWN _("") +#define NO_EXPIRE _("does not expire") +#define LIST_INCORRECT_RANGE _("Incorrect range specified. The correct syntax is \002#\037from\037-\037to\037\002.") +#define NICK_IS_REGISTERED _("This nick is owned by someone else. Please choose another.\n" \ + "(If this is your nick, type \002%s%s IDENTIFY \037password\037\002.)") +#define NICK_IS_SECURE _("This nickname is registered and protected. If it is your\n" \ + "nick, type \002%s%s IDENTIFY \037password\037\002. Otherwise,\n" \ + "please choose a different nick.") +#define FORCENICKCHANGE_NOW _("This nickname has been registered; you may not use it.") +#define NICK_CANNOT_BE_REGISTERED _("Nickname \002%s\002 may not be registered.") +#define NICK_ALREADY_REGISTERED _("Nickname \002%s\002 is already registered!") +#define NICK_SET_DISPLAY_CHANGED _("The new display is now \002%s\002.") +#define NICK_CONFIRM_INVALID _("Invalid passcode has been entered, please check the e-mail again, and retry.") +#define CHAN_NOT_ALLOWED_TO_JOIN _("You are not permitted to be on this channel.") +#define CHAN_X_INVALID _("Channel %s is not a valid channel.") +#define CHAN_REACHED_CHANNEL_LIMIT _("Sorry, you have already reached your limit of \002%d\002 channels.") +#define CHAN_EXCEEDED_CHANNEL_LIMIT _("Sorry, you have already exceeded your limit of \002%d\002 channels.") +#define CHAN_SYMBOL_REQUIRED _("Please use the symbol of \002#\002 when attempting to register.") +#define CHAN_SETTING_CHANGED _("%s for %s set to %s.") +#define CHAN_SETTING_UNSET _("%s for %s unset.") +#define CHAN_ACCESS_LEVEL_RANGE _("Access level must be between %d and %d inclusive.") +#define CHAN_INFO_HEADER _("Information for channel \002%s\002:") +#define CHAN_EXCEPTED _("\002%s\002 matches an except on %s and cannot be banned until the except has been removed.") +#define MEMO_NEW_X_MEMO_ARRIVED _("There is a new memo on channel %s.\n" \ + "Type \002%s%s READ %s %d\002 to read it.") +#define MEMO_NEW_MEMO_ARRIVED _("You have a new memo from %s.\n" \ + "Type \002%s%s READ %d\002 to read it.") +#define MEMO_HAVE_NO_MEMOS _("You have no memos.") +#define MEMO_X_HAS_NO_MEMOS _("%s has no memos.") +#define MEMO_SEND_DISABLED _("Sorry, memo sending is temporarily disabled.") +#define MEMO_HAVE_NO_NEW_MEMOS _("You have no new memos.") +#define MEMO_X_HAS_NO_NEW_MEMOS _("%s has no new memos.") +#define BOT_DOES_NOT_EXIST _("Bot \002%s\002 does not exist.") +#define BOT_NOT_ASSIGNED _("You must assign a bot to the channel before using this command.") +#define BOT_NOT_ON_CHANNEL _("Bot is not on channel \002%s\002.") +#define HOST_SET_ERROR _("A vHost must be in the format of a valid hostname.") +#define HOST_SET_IDENT_ERROR _("A vHost ident must be in the format of a valid ident.") +#define HOST_SET_TOOLONG _("Error! The vHost is too long, please use a hostname shorter than %d characters.") +#define HOST_SET_IDENTTOOLONG _("Error! The vHost ident is too long, please use an ident shorter than %d characters.") +#define HOST_NOT_ASSIGNED _("Please contact an Operator to get a vHost assigned to this nick.") +#define HOST_NO_VIDENT _("Your IRCd does not support vIdent's, if this is incorrect, please report this as a possible bug") diff --git a/include/lists.h b/include/lists.h new file mode 100644 index 0000000..2815ef8 --- /dev/null +++ b/include/lists.h @@ -0,0 +1,94 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef LISTS_H +#define LISTS_H + +#include "services.h" +#include "anope.h" + +/** A class to process numbered lists (passed to most DEL/LIST/VIEW commands). + * The function HandleNumber is called for every number in the list. Note that + * if descending is true it gets called in descending order. This is so deleting + * the index passed to the function from an array will not cause the other indexes + * passed to the function to be incorrect. This keeps us from having to have an + * 'in use' flag on everything. + */ +class CoreExport NumberList +{ + private: + bool is_valid; + + std::set numbers; + + bool desc; + public: + /** Processes a numbered list + * @param list The list + * @param descending True to make HandleNumber get called with numbers in descending order + */ + NumberList(const Anope::string &list, bool descending); + + /** Destructor, does nothing + */ + virtual ~NumberList(); + + /** Should be called after the constructors are done running. This calls the callbacks. + */ + void Process(); + + /** Called with a number from the list + * @param number The number + */ + virtual void HandleNumber(unsigned number); + + /** Called when there is an error with the numbered list + * Return false to immediately stop processing the list and return + * This is all done before we start calling HandleNumber, so no numbers will have been processed yet + * @param list The list + * @return false to stop processing + */ + virtual bool InvalidRange(const Anope::string &list); +}; + +/** This class handles formatting LIST/VIEW replies. + */ +class CoreExport ListFormatter +{ + public: + typedef std::map ListEntry; + private: + NickCore *nc; + std::vector columns; + std::vector entries; + public: + ListFormatter(NickCore *nc); + ListFormatter &AddColumn(const Anope::string &name); + void AddEntry(const ListEntry &entry); + bool IsEmpty() const; + void Process(std::vector &); +}; + +/** This class handles formatting INFO replies + */ +class CoreExport InfoFormatter +{ + NickCore *nc; + std::vector > replies; + unsigned longest; + public: + InfoFormatter(NickCore *nc); + void Process(std::vector &); + Anope::string &operator[](const Anope::string &key); + void AddOption(const Anope::string &opt); +}; + +#endif // LISTS_H diff --git a/include/logger.h b/include/logger.h new file mode 100644 index 0000000..5a5bfe9 --- /dev/null +++ b/include/logger.h @@ -0,0 +1,144 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef LOGGER_H +#define LOGGER_H + +#include "anope.h" +#include "defs.h" + +enum LogType +{ + /* Used whenever an administrator uses an administrative command */ + LOG_ADMIN, + /* Used whenever an administrator overrides something, such as adding + * access to a channel where they don't have permission to. + */ + LOG_OVERRIDE, + /* Any other command usage */ + LOG_COMMAND, + LOG_SERVER, + LOG_CHANNEL, + LOG_USER, + LOG_MODULE, + LOG_NORMAL, + LOG_TERMINAL, + LOG_RAWIO, + LOG_DEBUG, + LOG_DEBUG_2, + LOG_DEBUG_3, + LOG_DEBUG_4 +}; + +struct LogFile +{ + Anope::string filename; + std::ofstream stream; + + LogFile(const Anope::string &name); + ~LogFile(); + const Anope::string &GetName() const; +}; + +/* Represents a single log message */ +class CoreExport Log +{ + public: + /* Bot that should log this message */ + BotInfo *bi; + /* For commands, the user executing the command, but might not always exist */ + User *u; + /* For commands, the account executing the command, but will not always exist */ + NickCore *nc; + /* For commands, the command being executed */ + Command *c; + /* For commands, the command source */ + CommandSource *source; + /* Used for LOG_CHANNEL */ + Channel *chan; + /* For commands, the channel the command was executed on, will not always exist */ + const ChannelInfo *ci; + /* For LOG_SERVER */ + Server *s; + /* For LOG_MODULE */ + Module *m; + LogType type; + Anope::string category; + + std::stringstream buf; + + Log(LogType type = LOG_NORMAL, const Anope::string &category = "", BotInfo *bi = NULL); + + /* LOG_COMMAND/OVERRIDE/ADMIN */ + Log(LogType type, CommandSource &source, Command *c, ChannelInfo *ci = NULL); + + /* LOG_CHANNEL */ + Log(User *u, Channel *c, const Anope::string &category = ""); + + /* LOG_USER */ + Log(User *u, const Anope::string &category = "", BotInfo *bi = NULL); + + /* LOG_SERVER */ + Log(Server *s, const Anope::string &category = "", BotInfo *bi = NULL); + + Log(BotInfo *b, const Anope::string &category = ""); + + Log(Module *m, const Anope::string &category = "", BotInfo *bi = NULL); + + ~Log(); + + private: + Anope::string FormatSource() const; + Anope::string FormatCommand() const; + + public: + Anope::string BuildPrefix() const; + + template Log &operator<<(T val) + { + this->buf << val; + return *this; + } +}; + +/* Configured in the configuration file, actually does the message logging */ +class CoreExport LogInfo +{ + public: + BotInfo *bot; + std::vector targets; + std::vector logfiles; + int last_day; + std::vector sources; + int log_age; + std::vector admin; + std::vector override; + std::vector commands; + std::vector servers; + std::vector users; + std::vector channels; + std::vector normal; + bool raw_io; + bool debug; + + LogInfo(int logage, bool rawio, bool debug); + + ~LogInfo(); + + void OpenLogFiles(); + + bool HasType(LogType ltype, const Anope::string &type) const; + + /* Logs the message l if configured to */ + void ProcessMessage(const Log *l); +}; + +#endif // LOGGER_H diff --git a/include/mail.h b/include/mail.h new file mode 100644 index 0000000..7c3924c --- /dev/null +++ b/include/mail.h @@ -0,0 +1,56 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef MAIL_H +#define MAIL_H + +#include "anope.h" +#include "threadengine.h" +#include "serialize.h" + +namespace Mail +{ + extern CoreExport bool Send(User *from, NickCore *to, BotInfo *service, const Anope::string &subject, const Anope::string &message); + extern CoreExport bool Send(NickCore *to, const Anope::string &subject, const Anope::string &message); + extern CoreExport bool Validate(const Anope::string &email); + + /* A email message being sent */ + class Message : public Thread + { + private: + Anope::string sendmail_path; + Anope::string send_from; + Anope::string mail_to; + Anope::string addr; + Anope::string subject; + Anope::string message; + bool dont_quote_addresses; + + bool success; + public: + /** Construct this message. Once constructed call Thread::Start to launch the mail sending. + * @param sf Config->SendFrom + * @param mailto Name of person being mailed (u->nick, nc->display, etc) + * @param addr Destination address to mail + * @param subject Message subject + * @param message The actual message + */ + Message(const Anope::string &sf, const Anope::string &mailto, const Anope::string &addr, const Anope::string &subject, const Anope::string &message); + + ~Message(); + + /* Called from within the thread to actually send the mail */ + void Run() anope_override; + }; + +} // namespace Mail + +#endif // MAIL_H diff --git a/include/memo.h b/include/memo.h new file mode 100644 index 0000000..0a5d75b --- /dev/null +++ b/include/memo.h @@ -0,0 +1,55 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef MEMO_H +#define MEMO_H + +#include "anope.h" +#include "serialize.h" + +class CoreExport Memo : public Serializable +{ + public: + MemoInfo *mi; + bool unread; + bool receipt; + Memo(); + ~Memo(); + + void Serialize(Serialize::Data &data) const anope_override; + static Serializable* Unserialize(Serializable *obj, Serialize::Data &); + + Anope::string owner; + /* When it was sent */ + time_t time; + Anope::string sender; + Anope::string text; +}; + +/* Memo info structures. Since both nicknames and channels can have memos, + * we encapsulate memo data in a MemoInfo to make it easier to handle. + */ +struct CoreExport MemoInfo +{ + int16_t memomax; + Serialize::Checker > memos; + std::vector ignores; + + MemoInfo(); + Memo *GetMemo(unsigned index) const; + unsigned GetIndex(Memo *m) const; + void Del(unsigned index); + bool HasIgnore(User *u); + + static MemoInfo *GetMemoInfo(const Anope::string &targ, bool &is_chan); +}; + +#endif // MEMO_H diff --git a/include/messages.h b/include/messages.h new file mode 100644 index 0000000..dcef528 --- /dev/null +++ b/include/messages.h @@ -0,0 +1,173 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "protocol.h" + +/* Common IRCD messages. + * Protocol modules may chose to include some, none, or all of these handlers + * as they see fit. + */ + +namespace Message +{ + + struct CoreExport Away : IRCDMessage + { + Away(Module *creator, const Anope::string &mname = "AWAY") : IRCDMessage(creator, mname, 0) { SetFlag(IRCDMESSAGE_REQUIRE_USER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Capab : IRCDMessage + { + Capab(Module *creator, const Anope::string &mname = "CAPAB") : IRCDMessage(creator, mname, 1) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Error : IRCDMessage + { + Error(Module *creator, const Anope::string &mname = "ERROR") : IRCDMessage(creator, mname, 1) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Invite : IRCDMessage + { + Invite(Module *creator, const Anope::string &mname = "INVITE") : IRCDMessage(creator, mname, 2) { SetFlag(IRCDMESSAGE_REQUIRE_USER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Join : IRCDMessage + { + Join(Module *creator, const Anope::string &mname = "JOIN") : IRCDMessage(creator, mname, 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + + typedef std::pair SJoinUser; + + /** Handle a SJOIN. + * @param source The source of the SJOIN + * @param chan The channel the users are joining to + * @param ts The TS for the channel + * @param modes The modes sent with the SJOIN, if any + * @param users The users and their status, if any + */ + static void SJoin(MessageSource &source, const Anope::string &chan, time_t ts, const Anope::string &modes, const std::list &users); + }; + + struct CoreExport Kick : IRCDMessage + { + Kick(Module *creator, const Anope::string &mname = "KICK") : IRCDMessage(creator, mname, 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Kill : IRCDMessage + { + Kill(Module *creator, const Anope::string &mname = "KILL") : IRCDMessage(creator, mname, 2) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Mode : IRCDMessage + { + Mode(Module *creator, const Anope::string &mname = "MODE") : IRCDMessage(creator, mname, 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport MOTD : IRCDMessage + { + MOTD(Module *creator, const Anope::string &mname = "MOTD") : IRCDMessage(creator, mname, 1) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Notice : IRCDMessage + { + Notice(Module *creator, const Anope::string &mname = "NOTICE") : IRCDMessage(creator, mname, 2) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Part : IRCDMessage + { + Part(Module *creator, const Anope::string &mname = "PART") : IRCDMessage(creator, mname, 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Ping : IRCDMessage + { + Ping(Module *creator, const Anope::string &mname = "PING") : IRCDMessage(creator, mname, 1) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Privmsg : IRCDMessage + { + Privmsg(Module *creator, const Anope::string &mname = "PRIVMSG") : IRCDMessage(creator, mname, 2) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Quit : IRCDMessage + { + Quit(Module *creator, const Anope::string &mname = "QUIT") : IRCDMessage(creator, mname, 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport SQuit : IRCDMessage + { + SQuit(Module *creator, const Anope::string &mname = "SQUIT") : IRCDMessage(creator, mname, 2) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Stats : IRCDMessage + { + Stats(Module *creator, const Anope::string &mname = "STATS") : IRCDMessage(creator, mname, 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Time : IRCDMessage + { + Time(Module *creator, const Anope::string &mname = "TIME") : IRCDMessage(creator, mname, 0) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Topic : IRCDMessage + { + Topic(Module *creator, const Anope::string &mname = "TOPIC") : IRCDMessage(creator, mname, 2) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Version : IRCDMessage + { + Version(Module *creator, const Anope::string &mname = "VERSION") : IRCDMessage(creator, mname, 0) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + + struct CoreExport Whois : IRCDMessage + { + Whois(Module *creator, const Anope::string &mname = "WHOIS") : IRCDMessage(creator, mname, 1) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override; + }; + +} // namespace Message diff --git a/include/modes.h b/include/modes.h new file mode 100644 index 0000000..9488f81 --- /dev/null +++ b/include/modes.h @@ -0,0 +1,422 @@ +/* Mode support + * + * (C) 2008-2011 Adam + * (C) 2008-2022 Anope Team + * + * Please read COPYING and README for further details. + */ + +#ifndef MODES_H +#define MODES_H + +#include "anope.h" +#include "base.h" + +/** The different types of modes +*/ +enum ModeType +{ + /* Regular mode */ + MODE_REGULAR, + /* b/e/I */ + MODE_LIST, + /* k/l etc */ + MODE_PARAM, + /* v/h/o/a/q */ + MODE_STATUS +}; + +/* Classes of modes, Channel modes and User modes + */ +enum ModeClass +{ + MC_CHANNEL, + MC_USER +}; + +/** This class is the basis of all modes in Anope + */ +class CoreExport Mode : public Base +{ + public: + /* Mode name */ + Anope::string name; + /* Class of mode this is (user/channel) */ + ModeClass mclass; + /* Mode char for this, eg 'b' */ + char mchar; + /* Type of mode this is, eg MODE_LIST */ + ModeType type; + + /** constructor + * @param mname The mode name + * @param mclass The type of mode this is + * @param mc The mode char + * @param type The mode type + */ + Mode(const Anope::string &mname, ModeClass mclass, char mc, ModeType type); + virtual ~Mode(); + + /** Can a user set this mode, used for mlock + * @param u The user + */ + virtual bool CanSet(User *u) const; +}; + +/** This class is a user mode, all user modes use this/inherit from this + */ +class CoreExport UserMode : public Mode +{ + public: + /** constructor + * @param name The mode name + * @param mc The mode char + */ + UserMode(const Anope::string &name, char mc); +}; + +class CoreExport UserModeParam : public UserMode +{ + public: + /** constructor + * @param name The mode name + * @param mc The mode char + */ + UserModeParam(const Anope::string &name, char mc); + + /** Check if the param is valid + * @param value The param + * @return true or false + */ + virtual bool IsValid(Anope::string &value) const { return true; } +}; + +/** This class is a channel mode, all channel modes use this/inherit from this + */ +class CoreExport ChannelMode : public Mode +{ + public: + /* channel modes that can possibly unwrap this mode */ + std::vector listeners; + + /** constructor + * @param name The mode name + * @param mc The mode char + */ + ChannelMode(const Anope::string &name, char mc); + + bool CanSet(User *u) const anope_override; + + virtual void Check() { } + + /** 'wrap' this channel mode and param to the underlying mode and param + */ + virtual ChannelMode *Wrap(Anope::string ¶m); + + /** 'unwrap' this mode to our internal representation + */ + ChannelMode *Unwrap(Anope::string ¶m); + + /** called when a mode is being unwrapped, and is asking us if we can unwrap it + */ + virtual ChannelMode *Unwrap(ChannelMode *, Anope::string ¶m); +}; + +/** This is a mode for lists, eg b/e/I. These modes should inherit from this + */ +class CoreExport ChannelModeList : public ChannelMode +{ + public: + /** constructor + * @param name The mode name + * @param mc The mode char + */ + ChannelModeList(const Anope::string &name, char mc); + + /** Is the mask valid + * @param mask The mask + * @return true for yes, false for no + */ + virtual bool IsValid(Anope::string &mask) const; + + /** Checks if mask affects user + * Should only be used for extbans or other weird ircd-specific things. + * @param u The user + * @param e The entry to match against + * @return true on match + */ + virtual bool Matches(User *u, const Entry *e) { return false; } + + /** Called when a mask is added to a channel + * @param chan The channel + * @param mask The mask + */ + virtual void OnAdd(Channel *chan, const Anope::string &mask) { } + + /** Called when a mask is removed from a channel + * @param chan The channel + * @param mask The mask + */ + virtual void OnDel(Channel *chan, const Anope::string &mask) { } +}; + +/** This is a mode with a paramater, eg +k/l. These modes should use/inherit from this +*/ +class CoreExport ChannelModeParam : public ChannelMode +{ + public: + /** constructor + * @param name The mode name + * @param mc The mode char + * @param minus_no_arg true if this mode sends no arg when unsetting + */ + ChannelModeParam(const Anope::string &name, char mc, bool minus_no_arg = false); + + /* Should we send an arg when unsetting this mode? */ + bool minus_no_arg; + + /** Is the param valid + * @param value The param + * @return true for yes, false for no + */ + virtual bool IsValid(Anope::string &value) const { return true; } +}; + +/** This is a mode that is a channel status, eg +v/h/o/a/q. +*/ +class CoreExport ChannelModeStatus : public ChannelMode +{ + public: + /* The symbol, eg @ % + */ + char symbol; + /* The "level" of the mode, used to compare with other modes. + * Used so we know op > halfop > voice etc. + */ + unsigned level; + + /** constructor + * @param name The mode name + * @param mc The mode char + * @param msymbol The symbol for the mode, eg @ % + * @param mlevel A level for the mode, which is usually determined by the PREFIX capab + */ + ChannelModeStatus(const Anope::string &name, char mc, char msymbol, unsigned mlevel); +}; + +/** A virtual mode. This mode doesn't natively exist on the IRCd (like extbans), + * but we still have a representation for it. + */ +template +class CoreExport ChannelModeVirtual : public T +{ + Anope::string base; + ChannelMode *basech; + + public: + ChannelModeVirtual(const Anope::string &mname, const Anope::string &basename); + + ~ChannelModeVirtual(); + + void Check() anope_override; + + ChannelMode *Wrap(Anope::string ¶m) anope_override; + + ChannelMode *Unwrap(ChannelMode *cm, Anope::string ¶m) anope_override = 0; +}; + +/* The status a user has on a channel (+v, +h, +o) etc */ +class CoreExport ChannelStatus +{ + Anope::string modes; + public: + ChannelStatus(); + ChannelStatus(const Anope::string &modes); + void AddMode(char c); + void DelMode(char c); + bool HasMode(char c) const; + bool Empty() const; + void Clear(); + const Anope::string &Modes() const; + Anope::string BuildModePrefixList() const; +}; + +class CoreExport UserModeOperOnly : public UserMode +{ + public: + UserModeOperOnly(const Anope::string &mname, char um) : UserMode(mname, um) { } + + bool CanSet(User *u) const anope_override; +}; + +class CoreExport UserModeNoone : public UserMode +{ + public: + UserModeNoone(const Anope::string &mname, char um) : UserMode(mname, um) { } + + bool CanSet(User *u) const anope_override; +}; + +/** Channel mode +k (key) + */ +class CoreExport ChannelModeKey : public ChannelModeParam +{ + public: + ChannelModeKey(char mc) : ChannelModeParam("KEY", mc) { } + + bool IsValid(Anope::string &value) const anope_override; +}; + +/** This class is used for oper only channel modes + */ +class CoreExport ChannelModeOperOnly : public ChannelMode +{ + public: + ChannelModeOperOnly(const Anope::string &mname, char mc) : ChannelMode(mname, mc) { } + + /* Opers only */ + bool CanSet(User *u) const anope_override; +}; + +/** This class is used for channel modes only servers may set + */ +class CoreExport ChannelModeNoone : public ChannelMode +{ + public: + ChannelModeNoone(const Anope::string &mname, char mc) : ChannelMode(mname, mc) { } + + bool CanSet(User *u) const anope_override; +}; + +/** This is the mode manager + * It contains functions for adding modes to Anope so Anope can track them + * and do things such as MLOCK. + * This also contains a mode stacker that will combine multiple modes and set + * them on a channel or user at once + */ +class CoreExport ModeManager +{ + public: + + /* Number of generic channel and user modes we are tracking */ + static unsigned GenericChannelModes; + static unsigned GenericUserModes; + + /** Add a user mode to Anope + * @param um A UserMode or UserMode derived class + * @return true on success, false on error + */ + static bool AddUserMode(UserMode *um); + + /** Add a channel mode to Anope + * @param cm A ChannelMode or ChannelMode derived class + * @return true on success, false on error + */ + static bool AddChannelMode(ChannelMode *cm); + + /** Remove a user mode from Anope + * @param um A UserMode to remove + */ + static void RemoveUserMode(UserMode *um); + + /** Remove a channel mode from Anope + * @param um A ChanneMode to remove + */ + static void RemoveChannelMode(ChannelMode *cm); + + /** Find a channel mode + * @param mode The mode + * @return The mode class + */ + static ChannelMode *FindChannelModeByChar(char mode); + + /** Find a user mode + * @param mode The mode + * @return The mode class + */ + static UserMode *FindUserModeByChar(char mode); + + /** Find a channel mode + * @param name The modename + * @return The mode class + */ + static ChannelMode *FindChannelModeByName(const Anope::string &name); + + /** Find a user mode + * @param name The modename + * @return The mode class + */ + static UserMode *FindUserModeByName(const Anope::string &name); + + /** Gets the channel mode char for a symbol (eg + returns v) + * @param symbol The symbol + * @return The char + */ + static char GetStatusChar(char symbol); + + static const std::vector &GetChannelModes(); + static const std::vector &GetUserModes(); + static const std::vector &GetStatusChannelModesByRank(); + static void RebuildStatusModes(); + + /** Add a mode to the stacker to be set on a channel + * @param bi The client to set the modes from + * @param c The channel + * @param cm The channel mode + * @param set true for setting, false for removing + * @param param The param, if there is one + */ + static void StackerAdd(BotInfo *bi, Channel *c, ChannelMode *cm, bool set, const Anope::string ¶m = ""); + + /** Add a mode to the stacker to be set on a user + * @param bi The client to set the modes from + * @param u The user + * @param um The user mode + * @param set true for setting, false for removing + * @param param The param, if there is one + */ + static void StackerAdd(BotInfo *bi, User *u, UserMode *um, bool set, const Anope::string ¶m = ""); + + /** Process all of the modes in the stacker and send them to the IRCd to be set on channels/users + */ + static void ProcessModes(); + + /** Delete a user, channel, or mode from the stacker + */ + static void StackerDel(User *u); + static void StackerDel(Channel *c); + static void StackerDel(Mode *m); +}; + +/** Represents a mask set on a channel (b/e/I) + */ +class CoreExport Entry +{ + Anope::string name; + Anope::string mask; + public: + unsigned short cidr_len; + int family; + Anope::string nick, user, host, real; + + /** Constructor + * @param mode What mode this host is for, can be empty for unknown/no mode + * @param host A full or partial nick!ident@host/cidr#real name mask + */ + Entry(const Anope::string &mode, const Anope::string &host); + + /** Get the banned mask for this entry + * @return The mask + */ + const Anope::string GetMask() const; + + const Anope::string GetNUHMask() const; + + /** Check if this entry matches a user + * @param u The user + * @param full True to match against a users real host and IP + * @return true on match + */ + bool Matches(User *u, bool full = false) const; +}; + +#endif // MODES_H diff --git a/include/module.h b/include/module.h new file mode 100644 index 0000000..2ee4a43 --- /dev/null +++ b/include/module.h @@ -0,0 +1,54 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef MODULE_H +#define MODULE_H + +#include "access.h" +#include "account.h" +#include "anope.h" +#include "base.h" +#include "bots.h" +#include "channels.h" +#include "commands.h" +#include "config.h" +#include "extensible.h" +#include "hashcomp.h" +#include "language.h" +#include "lists.h" +#include "logger.h" +#include "mail.h" +#include "memo.h" +#include "messages.h" +#include "modes.h" +#include "modules.h" +#include "opertype.h" +#include "protocol.h" +#include "regexpr.h" +#include "regchannel.h" +#include "serialize.h" +#include "servers.h" +#include "service.h" +#include "services.h" +#include "socketengine.h" +#include "sockets.h" +#include "threadengine.h" +#include "timers.h" +#include "uplink.h" +#include "users.h" +#include "xline.h" + +#include "modules/pseudoclients/chanserv.h" +#include "modules/pseudoclients/global.h" +#include "modules/pseudoclients/memoserv.h" +#include "modules/pseudoclients/nickserv.h" + +#endif // MODULE_H diff --git a/include/modules.h b/include/modules.h new file mode 100644 index 0000000..3da6219 --- /dev/null +++ b/include/modules.h @@ -0,0 +1,1239 @@ +/* Modular support + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "serialize.h" + +#ifndef MODULES_H +#define MODULES_H + +#include "base.h" +#include "modes.h" +#include "timers.h" +#include "logger.h" +#include "extensible.h" +#include "version.h" + +/** This definition is used as shorthand for the various classes + * and functions needed to make a module loadable by the OS. + * It defines the class factory and external AnopeInit and AnopeFini functions. + */ +#ifdef _WIN32 +# define MODULE_INIT(x) \ + extern "C" DllExport Module *AnopeInit(const Anope::string &, const Anope::string &); \ + extern "C" Module *AnopeInit(const Anope::string &modname, const Anope::string &creator) \ + { \ + return new x(modname, creator); \ + } \ + BOOLEAN WINAPI DllMain(HINSTANCE, DWORD, LPVOID) \ + { \ + return TRUE; \ + } \ + extern "C" DllExport void AnopeFini(x *); \ + extern "C" void AnopeFini(x *m) \ + { \ + delete m; \ + } \ + extern "C" DllExport ModuleVersionC AnopeVersion() \ + { \ + ModuleVersionC ver; \ + ver.version_major = VERSION_MAJOR; \ + ver.version_minor = VERSION_MINOR; \ + ver.version_patch = VERSION_PATCH; \ + return ver; \ + } +#else +# define MODULE_INIT(x) \ + extern "C" DllExport Module *AnopeInit(const Anope::string &modname, const Anope::string &creator) \ + { \ + return new x(modname, creator); \ + } \ + extern "C" DllExport void AnopeFini(x *m) \ + { \ + delete m; \ + } \ + extern "C" DllExport ModuleVersionC AnopeVersion() \ + { \ + ModuleVersionC ver; \ + ver.version_major = VERSION_MAJOR; \ + ver.version_minor = VERSION_MINOR; \ + ver.version_patch = VERSION_PATCH; \ + return ver; \ + } +#endif + +/** + * This #define allows us to call a method in all + * loaded modules in a readable simple way, e.g.: + * + * FOREACH_MOD(OnUserConnect, (user, exempt)); + */ +#define FOREACH_MOD(ename, args) \ +if (true) \ +{ \ + std::vector &_modules = ModuleManager::EventHandlers[I_ ## ename]; \ + for (std::vector::iterator _i = _modules.begin(); _i != _modules.end();) \ + { \ + try \ + { \ + (*_i)->ename args; \ + } \ + catch (const ModuleException &modexcept) \ + { \ + Log() << "Exception caught: " << modexcept.GetReason(); \ + } \ + catch (const NotImplementedException &) \ + { \ + _i = _modules.erase(_i); \ + continue; \ + } \ + ++_i; \ + } \ +} \ +else \ + static_cast(0) + +/** + * This define is similar to the one above but returns a result. + * The first module to return a result other than EVENT_CONTINUE is the value to be accepted, + * and any modules after are ignored. This is used like: + * + * EventReturn MOD_RESULT; + * FOREACH_RESULT(OnUserConnect, MOD_RESULT, (user, exempt)); + */ +#define FOREACH_RESULT(ename, ret, args) \ +if (true) \ +{ \ + ret = EVENT_CONTINUE; \ + std::vector &_modules = ModuleManager::EventHandlers[I_ ## ename]; \ + for (std::vector::iterator _i = _modules.begin(); _i != _modules.end();) \ + { \ + try \ + { \ + EventReturn res = (*_i)->ename args; \ + if (res != EVENT_CONTINUE) \ + { \ + ret = res; \ + break; \ + } \ + } \ + catch (const ModuleException &modexcept) \ + { \ + Log() << "Exception caught: " << modexcept.GetReason(); \ + } \ + catch (const NotImplementedException &) \ + { \ + _i = _modules.erase(_i); \ + continue; \ + } \ + ++_i; \ + } \ +} \ +else \ + static_cast(0) + + +/** Possible return types from events. + */ +enum EventReturn +{ + EVENT_STOP, + EVENT_CONTINUE, + EVENT_ALLOW +}; + +enum ModuleReturn +{ + MOD_ERR_OK, + MOD_ERR_PARAMS, + MOD_ERR_EXISTS, + MOD_ERR_NOEXIST, + MOD_ERR_NOLOAD, + MOD_ERR_UNKNOWN, + MOD_ERR_FILE_IO, + MOD_ERR_EXCEPTION, + MOD_ERR_VERSION +}; + +/** Priority types which can be returned from Module::Prioritize() + */ +enum Priority { PRIORITY_FIRST, PRIORITY_DONTCARE, PRIORITY_LAST, PRIORITY_BEFORE, PRIORITY_AFTER }; +/* Module types, in the order in which they are unloaded. The order these are in is IMPORTANT */ +enum +{ + MT_BEGIN, + /* Module is 3rd party. All 3rd party modules should set this. Mutually exclusive to VENDOR. */ + THIRD = 1 << 0, + /* A vendor module, which is made and shipped by Anope. Mutually exclusive to THIRD. */ + VENDOR = 1 << 1, + /* Extra module not required for standard use. Probably requires external dependencies. + * This module does something extreme enough that we want it to show in the default /os modlist command + */ + EXTRA = 1 << 2, + /* Module provides access to a database */ + DATABASE = 1 << 3, + /* Module provides encryption */ + ENCRYPTION = 1 << 4, + /* Module provides a pseudoclient */ + PSEUDOCLIENT = 1 << 5, + /* Module provides IRCd protocol support */ + PROTOCOL = 1 << 6, + MT_END = 1 << 7 +}; +typedef unsigned short ModType; + +struct ModuleVersionC +{ + int version_major, version_minor, version_patch; +}; + +/** Returned by Module::GetVersion, used to see what version of Anope + * a module is compiled against. + */ +class ModuleVersion +{ + private: + int version_major; + int version_minor; + int version_patch; + + public: + ModuleVersion(const ModuleVersionC &); + + /** Get the major version of Anope this was built against + * @return The major version + */ + int GetMajor() const; + + /** Get the minor version of Anope this was built against + * @return The minor version + */ + int GetMinor() const; + + /** Get the patch version this was built against + * @return The patch version + */ + int GetPatch() const; +}; + +class NotImplementedException : public CoreException { }; + +/** Every module in Anope is actually a class. + */ +class CoreExport Module : public Extensible +{ + private: + bool permanent; + public: + /** The module name (e.g. os_modload) + */ + Anope::string name; + + /** What type this module is + */ + ModType type; + + /** The temporary path/filename + */ + Anope::string filename; + + /** Handle for this module, obtained from dlopen() + */ + void *handle; + + /** Time this module was created + */ + time_t created; + + /** Version of this module + */ + Anope::string version; + + /** Author of the module + */ + Anope::string author; + + /** Creates and initialises a new module. + * @param modname The module name + * @param loadernick The nickname of the user loading the module. + * @param type The module type + */ + Module(const Anope::string &modname, const Anope::string &loadernick, ModType type = THIRD); + + /** Destroys a module, freeing resources it has allocated. + */ + virtual ~Module(); + + /** Toggles the permanent flag on a module. If a module is permanent, + * then it may not be unloaded. + * + * Naturally, this setting should be used sparingly! + * + * @param state True if this module should be permanent, false else. + */ + void SetPermanent(bool state); + + /** Retrieves whether or not a given module is permanent. + * @return true if the module is permanent, false else. + */ + bool GetPermanent() const; + + /** Set the modules version info. + * @param version the version of the module + */ + void SetVersion(const Anope::string &version); + + /** Set the modules author info + * @param author the author of the module + */ + void SetAuthor(const Anope::string &author); + + virtual void Prioritize(); + + /* Everything below here are events. Modules must ModuleManager::Attach to these events + * before they will be called. + */ + + /** Called on startup after database load, but before + * connecting to the uplink. + */ + virtual void OnPostInit() { throw NotImplementedException(); } + + /** Called before a user has been kicked from a channel. + * @param source The kicker + * @param cu The user, channel, and status of the user being kicked + * @param kickmsg The reason for the kick. + */ + virtual void OnPreUserKicked(const MessageSource &source, ChanUserContainer *cu, const Anope::string &kickmsg) { throw NotImplementedException(); } + + /** Called when a user has been kicked from a channel. + * @param source The kicker + * @param target The user being kicked + * @param channel The channel the user was kicked from, which may no longer exist + * @param status The status the kicked user had on the channel before they were kicked + * @param kickmsg The reason for the kick. + */ + virtual void OnUserKicked(const MessageSource &source, User *target, const Anope::string &channel, ChannelStatus &status, const Anope::string &kickmsg) { throw NotImplementedException(); } + + /** Called when Services' configuration is being (re)loaded. + * @param conf The config that is being built now and will replace the global Config object + * @throws A ConfigException to abort the config (re)loading process. + */ + virtual void OnReload(Configuration::Conf *conf) { throw NotImplementedException(); } + + /** Called before a bot is assigned to a channel. + * @param sender The user assigning the bot + * @param ci The channel the bot is to be assigned to. + * @param bi The bot being assigned. + * @return EVENT_CONTINUE to let other modules decide, EVENT_STOP to deny the assign. + */ + virtual EventReturn OnPreBotAssign(User *sender, ChannelInfo *ci, BotInfo *bi) { throw NotImplementedException(); } + + /** Called when a bot is assigned ot a channel + */ + virtual void OnBotAssign(User *sender, ChannelInfo *ci, BotInfo *bi) { throw NotImplementedException(); } + + /** Called before a bot is unassigned from a channel. + * @param sender The user unassigning the bot + * @param ci The channel the bot is being removed from + * @return EVENT_CONTINUE to let other modules decide, EVENT_STOP to deny the unassign. + */ + virtual EventReturn OnBotUnAssign(User *sender, ChannelInfo *ci) { throw NotImplementedException(); } + + /** Called when a new user connects to the network. + * @param u The connecting user. + * @param exempt set to true/is true if the user should be excepted from bans etc + */ + virtual void OnUserConnect(User *u, bool &exempt) { throw NotImplementedException(); } + + /** Called when a new server connects to the network. + * @param s The server that has connected to the network + */ + virtual void OnNewServer(Server *s) { throw NotImplementedException(); } + + /** Called after a user changed the nick + * @param u The user. + * @param oldnick The old nick of the user + */ + virtual void OnUserNickChange(User *u, const Anope::string &oldnick) { throw NotImplementedException(); } + + /** Called when someone uses the generic/help command + * @param source Command source + * @param params Params + * @return EVENT_STOP to stop processing + */ + virtual EventReturn OnPreHelp(CommandSource &source, const std::vector ¶ms) { throw NotImplementedException(); } + + /** Called when someone uses the generic/help command + * @param source Command source + * @param params Params + */ + virtual void OnPostHelp(CommandSource &source, const std::vector ¶ms) { throw NotImplementedException(); } + + /** Called before a command is due to be executed. + * @param source The source of the command + * @param command The command the user is executing + * @param params The parameters the user is sending + * @return EVENT_CONTINUE to let other modules decide, EVENT_STOP to halt the command and not process it + */ + virtual EventReturn OnPreCommand(CommandSource &source, Command *command, std::vector ¶ms) { throw NotImplementedException(); } + + /** Called after a command has been executed. + * @param source The source of the command + * @param command The command the user executed + * @param params The parameters the user sent + */ + virtual void OnPostCommand(CommandSource &source, Command *command, const std::vector ¶ms) { throw NotImplementedException(); } + + /** Called when the databases are saved + */ + virtual void OnSaveDatabase() { throw NotImplementedException(); } + + /** Called when the databases are loaded + * @return EVENT_CONTINUE to let other modules continue loading, EVENT_STOP to stop + */ + virtual EventReturn OnLoadDatabase() { throw NotImplementedException(); } + + /** Called when anope needs to check passwords against encryption + * see src/encrypt.c for detailed informations + */ + virtual EventReturn OnEncrypt(const Anope::string &src, Anope::string &dest) { throw NotImplementedException(); } + virtual EventReturn OnDecrypt(const Anope::string &hashm, const Anope::string &src, Anope::string &dest) { throw NotImplementedException(); } + + /** Called on fantasy command + * @param source The source of the command + * @param c The command + * @param ci The channel it's being used in + * @param params The params + * @return EVENT_STOP to halt processing and not run the command, EVENT_ALLOW to allow the command to be executed + */ + virtual EventReturn OnBotFantasy(CommandSource &source, Command *c, ChannelInfo *ci, const std::vector ¶ms) { throw NotImplementedException(); } + + /** Called on fantasy command without access + * @param source The source of the command + * @param c The command + * @param ci The channel it's being used in + * @param params The params + * @return EVENT_STOP to halt processing and not run the command, EVENT_ALLOW to allow the command to be executed + */ + virtual EventReturn OnBotNoFantasyAccess(CommandSource &source, Command *c, ChannelInfo *ci, const std::vector ¶ms) { throw NotImplementedException(); } + + /** Called when a bot places a ban + * @param u User being banned + * @param ci Channel the ban is placed on + * @param mask The mask being banned + */ + virtual void OnBotBan(User *u, ChannelInfo *ci, const Anope::string &mask) { throw NotImplementedException(); } + + /** Called before a badword is added to the badword list + * @param ci The channel + * @param bw The badword + */ + virtual void OnBadWordAdd(ChannelInfo *ci, const BadWord *bw) { throw NotImplementedException(); } + + /** Called before a badword is deleted from a channel + * @param ci The channel + * @param bw The badword + */ + virtual void OnBadWordDel(ChannelInfo *ci, const BadWord *bw) { throw NotImplementedException(); } + + /** Called when a bot is created or destroyed + */ + virtual void OnCreateBot(BotInfo *bi) { throw NotImplementedException(); } + virtual void OnDelBot(BotInfo *bi) { throw NotImplementedException(); } + + /** Called before a bot kicks a user + * @param bi The bot sending the kick + * @param c The channel the user is being kicked on + * @param u The user being kicked + * @param reason The reason + * @return EVENT_CONTINUE to let other modules decide, EVENT_STOP to halt the command and not process it + */ + virtual EventReturn OnBotKick(BotInfo *bi, Channel *c, User *u, const Anope::string &reason) { throw NotImplementedException(); } + + /** Called before a user parts a channel + * @param u The user + * @param c The channel + */ + virtual void OnPrePartChannel(User *u, Channel *c) {} + + /** Called when a user parts a channel + * @param u The user + * @param c The channel, may be NULL if the channel no longer exists + * @param channel The channel name + * @param msg The part reason + */ + virtual void OnPartChannel(User *u, Channel *c, const Anope::string &channel, const Anope::string &msg) { throw NotImplementedException(); } + + /** Called when a user leaves a channel. + * From either parting, being kicked, or quitting/killed! + * @param u The user + * @param c The channel + */ + virtual void OnLeaveChannel(User *u, Channel *c) { throw NotImplementedException(); } + + /** Called after a user joins a channel + * If this event triggers the user is allowed to be in the channel, and will + * not be kicked for restricted/akick/forbidden, etc. If you want to kick the user, + * use the CheckKick event instead. + * @param u The user + * @param channel The channel + */ + virtual void OnJoinChannel(User *u, Channel *c) { throw NotImplementedException(); } + + /** Called when a new topic is set + * @param source The user changing the topic, if any + * @param c The channel + * @param setter The user who set the new topic, if there is no source + * @param topic The new topic + */ + virtual void OnTopicUpdated(User *source, Channel *c, const Anope::string &user, const Anope::string &topic) { throw NotImplementedException(); } + + /** Called before a channel expires + * @param ci The channel + * @param expire Set to true to allow the chan to expire + */ + virtual void OnPreChanExpire(ChannelInfo *ci, bool &expire) { throw NotImplementedException(); } + + /** Called before a channel expires + * @param ci The channel + */ + virtual void OnChanExpire(ChannelInfo *ci) { throw NotImplementedException(); } + + /** Called before Anope connects to its uplink + */ + virtual void OnPreServerConnect() { throw NotImplementedException(); } + + /** Called when Anope connects to its uplink + */ + virtual void OnServerConnect() { throw NotImplementedException(); } + + /** Called when we are almost done synching with the uplink, just before we send the EOB + */ + virtual void OnPreUplinkSync(Server *serv) { throw NotImplementedException(); } + + /** Called when Anope disconnects from its uplink, before it tries to reconnect + */ + virtual void OnServerDisconnect() { throw NotImplementedException(); } + + /** Called when services restart + */ + virtual void OnRestart() { throw NotImplementedException(); } + + /** Called when services shutdown + */ + virtual void OnShutdown() { throw NotImplementedException(); } + + /** Called before a nick expires + * @param na The nick + * @param expire Set to true to allow the nick to expire + */ + virtual void OnPreNickExpire(NickAlias *na, bool &expire) { throw NotImplementedException(); } + + /** Called when a nick drops + * @param na The nick + */ + virtual void OnNickExpire(NickAlias *na) { throw NotImplementedException(); } + + /** Called when defcon level changes + * @param level The level + */ + virtual void OnDefconLevel(int level) { throw NotImplementedException(); } + + /** Called after an exception has been added + * @param ex The exception + * @return EVENT_CONTINUE to let other modules decide, EVENT_STOP to halt the command and not process it + */ + virtual EventReturn OnExceptionAdd(Exception *ex) { throw NotImplementedException(); } + + /** Called before an exception is deleted + * @param source The source deleting it + * @param ex The exception + */ + virtual void OnExceptionDel(CommandSource &source, Exception *ex) { throw NotImplementedException(); } + + /** Called before a XLine is added + * @param source The source of the XLine + * @param x The XLine + * @param xlm The xline manager it was added to + * @return EVENT_CONTINUE to let other modules decide, EVENT_STOP to halt the command and not process it + */ + virtual EventReturn OnAddXLine(CommandSource &source, const XLine *x, XLineManager *xlm) { throw NotImplementedException(); } + + /** Called before a XLine is deleted + * @param source The source of the XLine + * @param x The XLine + * @param xlm The xline manager it was deleted from + */ + virtual void OnDelXLine(CommandSource &source, const XLine *x, XLineManager *xlm) { throw NotImplementedException(); } + + /** Called when a user is checked for whether they are a services oper + * @param u The user + * @return EVENT_ALLOW to allow, anything else to deny + */ + virtual EventReturn IsServicesOper(User *u) { throw NotImplementedException(); } + + /** Called when a server quits + * @param server The server + */ + virtual void OnServerQuit(Server *server) { throw NotImplementedException(); } + + /** Called when a user quits, or is killed + * @param u The user + * @param msg The quit message + */ + virtual void OnUserQuit(User *u, const Anope::string &msg) { throw NotImplementedException(); } + + /** Called when a user is quit, before and after being internally removed from + * This is different from OnUserQuit, which takes place at the time of the quit. + * This happens shortly after when all message processing is finished. + * all lists (channels, user list, etc) + * @param u The user + */ + virtual void OnPreUserLogoff(User *u) { throw NotImplementedException(); } + virtual void OnPostUserLogoff(User *u) { throw NotImplementedException(); } + + /** Called when a new bot is made + * @param bi The bot + */ + virtual void OnBotCreate(BotInfo *bi) { throw NotImplementedException(); } + + /** Called when a bot is changed + * @param bi The bot + */ + virtual void OnBotChange(BotInfo *bi) { throw NotImplementedException(); } + + /** Called when a bot is deleted + * @param bi The bot + */ + virtual void OnBotDelete(BotInfo *bi) { throw NotImplementedException(); } + + /** Called after an access entry is deleted from a channel + * @param ci The channel + * @param source The source of the command + * @param access The access entry that was removed + */ + virtual void OnAccessDel(ChannelInfo *ci, CommandSource &source, ChanAccess *access) { throw NotImplementedException(); } + + /** Called when access is added + * @param ci The channel + * @param source The source of the command + * @param access The access changed + */ + virtual void OnAccessAdd(ChannelInfo *ci, CommandSource &source, ChanAccess *access) { throw NotImplementedException(); } + + /** Called when the access list is cleared + * @param ci The channel + * @param u The user who cleared the access + */ + virtual void OnAccessClear(ChannelInfo *ci, CommandSource &source) { throw NotImplementedException(); } + + /** Called when a level for a channel is changed + * @param source The source of the command + * @param ci The channel the level was changed on + * @param priv The privilege changed + * @param what The new level + */ + virtual void OnLevelChange(CommandSource &source, ChannelInfo *ci, const Anope::string &priv, int16_t what) { throw NotImplementedException(); } + + /** Called right before a channel is dropped + * @param source The user dropping the channel + * @param ci The channel + */ + virtual EventReturn OnChanDrop(CommandSource &source, ChannelInfo *ci) { throw NotImplementedException(); } + + /** Called when a channel is registered + * @param ci The channel + */ + virtual void OnChanRegistered(ChannelInfo *ci) { throw NotImplementedException(); } + + /** Called when a channel is suspended + * @param ci The channel + */ + virtual void OnChanSuspend(ChannelInfo *ci) { throw NotImplementedException(); } + + /** Called when a channel is unsuspended + * @param ci The channel + */ + virtual void OnChanUnsuspend(ChannelInfo *ci) { throw NotImplementedException(); } + + /** Called when a channel is being created, for any reason + * @param ci The channel + */ + virtual void OnCreateChan(ChannelInfo *ci) { throw NotImplementedException(); } + + /** Called when a channel is being deleted, for any reason + * @param ci The channel + */ + virtual void OnDelChan(ChannelInfo *ci) { throw NotImplementedException(); } + + /** Called when a new channel is created + * Note that this channel may not be introduced to the uplink at this point. + * @param c The channel + */ + virtual void OnChannelCreate(Channel *c) { throw NotImplementedException(); } + + /** Called when a channel is deleted + * @param c The channel + */ + virtual void OnChannelDelete(Channel *c) { throw NotImplementedException(); } + + /** Called after adding an akick to a channel + * @param source The source of the command + * @param ci The channel + * @param ak The akick + */ + virtual void OnAkickAdd(CommandSource &source, ChannelInfo *ci, const AutoKick *ak) { throw NotImplementedException(); } + + /** Called before removing an akick from a channel + * @param source The source of the command + * @param ci The channel + * @param ak The akick + */ + virtual void OnAkickDel(CommandSource &source, ChannelInfo *ci, const AutoKick *ak) { throw NotImplementedException(); } + + /** Called after a user join a channel when we decide whether to kick them or not + * @param u The user + * @param c The channel + * @param kick Set to true to kick + * @param mask The mask to ban, if any + * @param reason The reason for the kick + * @return EVENT_STOP to prevent the user from joining by kicking/banning the user + */ + virtual EventReturn OnCheckKick(User *u, Channel *c, Anope::string &mask, Anope::string &reason) { throw NotImplementedException(); } + + /** Called when a user requests info for a channel + * @param source The user requesting info + * @param ci The channel the user is requesting info for + * @param info Data to show the user requesting information + * @param show_hidden true if we should show the user everything + */ + virtual void OnChanInfo(CommandSource &source, ChannelInfo *ci, InfoFormatter &info, bool show_hidden) { throw NotImplementedException(); } + + /** Checks if access has the channel privilege 'priv'. + * @param access THe access struct + * @param priv The privilege being checked for + * @return EVENT_ALLOW for yes, EVENT_STOP to stop all processing + */ + virtual EventReturn OnCheckPriv(const ChanAccess *access, const Anope::string &priv) { throw NotImplementedException(); } + + /** Check whether an access group has a privilege + * @param group The group + * @param priv The privilege + * @return MOD_ALLOW to allow, MOD_STOP to stop + */ + virtual EventReturn OnGroupCheckPriv(const AccessGroup *group, const Anope::string &priv) { throw NotImplementedException(); } + + /** Called when a nick is dropped + * @param source The source of the command + * @param na The nick + */ + virtual void OnNickDrop(CommandSource &source, NickAlias *na) { throw NotImplementedException(); } + + /** Called when a user groups their nick + * @param u The user grouping + * @param target The target they're grouping to + */ + virtual void OnNickGroup(User *u, NickAlias *target) { throw NotImplementedException(); } + + /** Called when a user identifies to a nick + * @param u The user + */ + virtual void OnNickIdentify(User *u) { throw NotImplementedException(); } + + /** Called when a user is logged into an account + * @param u The user + */ + virtual void OnUserLogin(User *u) { throw NotImplementedException(); } + + /** Called when a nick logs out + * @param u The nick + */ + virtual void OnNickLogout(User *u) { throw NotImplementedException(); } + + /** Called when a nick is registered + * @param user The user registering the nick, of any + * @param The nick + * @param pass The password of the newly registered nick + */ + virtual void OnNickRegister(User *user, NickAlias *na, const Anope::string &pass) { throw NotImplementedException(); } + + /** Called when a nick is confirmed. This will never be called if registration confirmation is not enabled. + * @param user The user confirming the nick + * @param The account being confirmed + */ + virtual void OnNickConfirm(User *user, NickCore *) { throw NotImplementedException(); } + + /** Called when a nick is suspended + * @param na The nick alias + */ + virtual void OnNickSuspend(NickAlias *na) { throw NotImplementedException(); } + + /** Called when a nick is unsuspended + * @param na The nick alias + */ + virtual void OnNickUnsuspended(NickAlias *na) { throw NotImplementedException(); } + + /** Called on delnick() + * @ param na pointer to the nickalias + */ + virtual void OnDelNick(NickAlias *na) { throw NotImplementedException(); } + + /** Called when a nickcore is created + * @param nc The nickcore + */ + virtual void OnNickCoreCreate(NickCore *nc) { throw NotImplementedException(); } + + /** Called on delcore() + * @param nc pointer to the NickCore + */ + virtual void OnDelCore(NickCore *nc) { throw NotImplementedException(); } + + /** Called on change_core_display() + * @param nc pointer to the NickCore + * @param newdisplay the new display + */ + virtual void OnChangeCoreDisplay(NickCore *nc, const Anope::string &newdisplay) { throw NotImplementedException(); } + + /** called from NickCore::ClearAccess() + * @param nc pointer to the NickCore + */ + virtual void OnNickClearAccess(NickCore *nc) { throw NotImplementedException(); } + + /** Called when a user adds an entry to their access list + * @param nc The nick + * @param entry The entry + */ + virtual void OnNickAddAccess(NickCore *nc, const Anope::string &entry) { throw NotImplementedException(); } + + /** Called from NickCore::EraseAccess() + * @param nc pointer to the NickCore + * @param entry The access mask + */ + virtual void OnNickEraseAccess(NickCore *nc, const Anope::string &entry) { throw NotImplementedException(); } + + /** called from NickCore::ClearCert() + * @param nc pointer to the NickCore + */ + virtual void OnNickClearCert(NickCore *nc) { throw NotImplementedException(); } + + /** Called when a user adds an entry to their cert list + * @param nc The nick + * @param entry The entry + */ + virtual void OnNickAddCert(NickCore *nc, const Anope::string &entry) { throw NotImplementedException(); } + + /** Called from NickCore::EraseCert() + * @param nc pointer to the NickCore + * @param entry The fingerprint + */ + virtual void OnNickEraseCert(NickCore *nc, const Anope::string &entry) { throw NotImplementedException(); } + + /** Called when a user requests info for a nick + * @param source The user requesting info + * @param na The nick the user is requesting info from + * @param info Data to show the user requesting information + * @param show_hidden true if we should show the user everything + */ + virtual void OnNickInfo(CommandSource &source, NickAlias *na, InfoFormatter &info, bool show_hidden) { throw NotImplementedException(); } + + /** Called when a user uses botserv/info on a bot or channel. + */ + virtual void OnBotInfo(CommandSource &source, BotInfo *bi, ChannelInfo *ci, InfoFormatter &info) { throw NotImplementedException(); } + + /** Check whether a username and password is correct + * @param u The user trying to identify, if applicable. + * @param req The login request + */ + virtual void OnCheckAuthentication(User *u, IdentifyRequest *req) { throw NotImplementedException(); } + + /** Called when a user does /ns update + * @param u The user + */ + virtual void OnNickUpdate(User *u) { throw NotImplementedException(); } + + /** Called when we get informed about a users SSL fingerprint + * when we call this, the fingerprint should already be stored in the user struct + * @param u pointer to the user + */ + virtual void OnFingerprint(User *u) { throw NotImplementedException(); } + + /** Called when a user becomes (un)away + * @param message The message, is .empty() if unaway + */ + virtual void OnUserAway(User *u, const Anope::string &message) { throw NotImplementedException(); } + + /** Called when a user invites one of our users to a channel + * @param source The user doing the inviting + * @param c The channel the user is inviting to + * @param targ The user being invited + */ + virtual void OnInvite(User *source, Channel *c, User *targ) { throw NotImplementedException(); } + + /** Called when a vhost is deleted + * @param na The nickalias of the vhost + */ + virtual void OnDeleteVhost(NickAlias *na) { throw NotImplementedException(); } + + /** Called when a vhost is set + * @param na The nickalias of the vhost + */ + virtual void OnSetVhost(NickAlias *na) { throw NotImplementedException(); } + + /** Called when a users host changes + * @param u The user + */ + virtual void OnSetDisplayedHost(User *) { throw NotImplementedException(); } + + /** Called when a memo is sent + * @param source The source of the memo + * @param target The target of the memo + * @param mi Memo info for target + * @param m The memo + */ + virtual void OnMemoSend(const Anope::string &source, const Anope::string &target, MemoInfo *mi, Memo *m) { throw NotImplementedException(); } + + /** Called when a memo is deleted + * @param target The target the memo is being deleted from (nick or channel) + * @param mi The memo info + * @param m The memo + */ + virtual void OnMemoDel(const Anope::string &target, MemoInfo *mi, const Memo *m) { throw NotImplementedException(); } + + /** Called when a mode is set on a channel + * @param c The channel + * @param setter The user or server that is setting the mode + * @param mode The mode + * @param param The mode param, if there is one + * @return EVENT_STOP to make mlock/secureops etc checks not happen + */ + virtual EventReturn OnChannelModeSet(Channel *c, MessageSource &setter, ChannelMode *mode, const Anope::string ¶m) { throw NotImplementedException(); } + + /** Called when a mode is unset on a channel + * @param c The channel + * @param setter The user or server that is unsetting the mode + * @param mode The mode + * @param param The mode param, if there is one + * @return EVENT_STOP to make mlock/secureops etc checks not happen + */ + virtual EventReturn OnChannelModeUnset(Channel *c, MessageSource &setter, ChannelMode *mode, const Anope::string ¶m) { throw NotImplementedException(); } + + /** Called when a mode is set on a user + * @param setter who/what is setting the mode + * @param u The user + * @param mname The mode name + */ + virtual void OnUserModeSet(const MessageSource &setter, User *u, const Anope::string &mname) { throw NotImplementedException(); } + + /** Called when a mode is unset from a user + * @param setter who/what is setting the mode + * @param u The user + * @param mname The mode name + */ + virtual void OnUserModeUnset(const MessageSource &setter, User *u, const Anope::string &mname) { throw NotImplementedException(); } + + /** Called when a channel mode is introduced into Anope + * @param cm The mode + */ + virtual void OnChannelModeAdd(ChannelMode *cm) { throw NotImplementedException(); } + + /** Called when a user mode is introduced into Anope + * @param um The mode + */ + virtual void OnUserModeAdd(UserMode *um) { throw NotImplementedException(); } + + /** Called when a mode is about to be mlocked + * @param ci The channel the mode is being locked on + * @param lock The mode lock + * @return EVENT_CONTINUE to let other modules decide, EVENT_STOP to deny the mlock. + */ + virtual EventReturn OnMLock(ChannelInfo *ci, ModeLock *lock) { throw NotImplementedException(); } + + /** Called when a mode is about to be unlocked + * @param ci The channel the mode is being unlocked from + * @param lock The mode lock + * @return EVENT_CONTINUE to let other modules decide, EVENT_STOP to deny the mlock. + */ + virtual EventReturn OnUnMLock(ChannelInfo *ci, ModeLock *lock) { throw NotImplementedException(); } + + /** Called after a module is loaded + * @param u The user loading the module, can be NULL + * @param m The module + */ + virtual void OnModuleLoad(User *u, Module *m) { throw NotImplementedException(); } + + /** Called before a module is unloaded + * @param u The user, can be NULL + * @param m The module + */ + virtual void OnModuleUnload(User *u, Module *m) { throw NotImplementedException(); } + + /** Called when a server is synced + * @param s The server, can be our uplink server + */ + virtual void OnServerSync(Server *s) { throw NotImplementedException(); } + + /** Called when we sync with our uplink + * @param s Our uplink + */ + virtual void OnUplinkSync(Server *s) { throw NotImplementedException(); } + + /** Called when we receive a PRIVMSG for one of our clients + * @param u The user sending the PRIVMSG + * @param bi The target of the PRIVMSG + * @param message The message + * @return EVENT_STOP to halt processing + */ + virtual EventReturn OnBotPrivmsg(User *u, BotInfo *bi, Anope::string &message) { throw NotImplementedException(); } + + /** Called when we receive a NOTICE for one of our clients + * @param u The user sending the NOTICE + * @param bi The target of the NOTICE + * @param message The message + */ + virtual void OnBotNotice(User *u, BotInfo *bi, Anope::string &message) { throw NotImplementedException(); } + + /** Called when we receive a PRIVMSG for a registered channel we are in + * @param u The source of the message + * @param c The channel + * @param msg The message + */ + virtual void OnPrivmsg(User *u, Channel *c, Anope::string &msg) { throw NotImplementedException(); } + + /** Called when a message is logged + * @param l The log message + */ + virtual void OnLog(Log *l) { throw NotImplementedException(); } + + /** Called when a log message is actually logged to a given log info + * The message has already passed validation checks by the LogInfo + * @param li The loginfo whee the message is being logged + * @param l The log message + * @param msg The final formatted message, derived from 'l' + */ + virtual void OnLogMessage(LogInfo *li, const Log *l, const Anope::string &msg) { throw NotImplementedException(); } + + /** Called when a DNS request (question) is received. + * @param req The dns request + * @param reply The reply that will be sent + */ + virtual void OnDnsRequest(DNS::Query &req, DNS::Query *reply) { throw NotImplementedException(); } + + /** Called when a channels modes are being checked to see if they are allowed, + * mostly to ensure mlock/+r are set. + * @param c The channel + */ + virtual void OnCheckModes(Reference &c) { throw NotImplementedException(); } + + /** Called when a channel is synced. + * Channels are synced after a sjoin is finished processing + * for a newly created channel to set the correct modes, topic, + * set. + */ + virtual void OnChannelSync(Channel *c) { throw NotImplementedException(); } + + /** Called to set the correct modes on the user on the given channel + * @param user The user + * @param chan The channel + * @param access The user's access on the channel + * @param give_modes If giving modes is desired + * @param take_modes If taking modes is desired + */ + virtual void OnSetCorrectModes(User *user, Channel *chan, AccessGroup &access, bool &give_modes, bool &take_modes) { throw NotImplementedException(); } + + virtual void OnSerializeCheck(Serialize::Type *) { throw NotImplementedException(); } + virtual void OnSerializableConstruct(Serializable *) { throw NotImplementedException(); } + virtual void OnSerializableDestruct(Serializable *) { throw NotImplementedException(); } + virtual void OnSerializableUpdate(Serializable *) { throw NotImplementedException(); } + virtual void OnSerializeTypeCreate(Serialize::Type *) { throw NotImplementedException(); } + + /** Called when a chanserv/set command is used + * @param source The source of the command + * @param cmd The command + * @param ci The channel the command was used on + * @param setting The setting passed to the command. Probably ON/OFF. + * @return EVENT_ALLOW to bypass access checks, EVENT_STOP to halt immediately. + */ + virtual EventReturn OnSetChannelOption(CommandSource &source, Command *cmd, ChannelInfo *ci, const Anope::string &setting) { throw NotImplementedException(); } + + /** Called when a nickserv/set command is used. + * @param source The source of the command + * @param cmd The command + * @param nc The nickcore being modifed + * @param setting The setting passed to the command. Probably ON/OFF. + * @return EVENT_STOP to halt immediately + */ + virtual EventReturn OnSetNickOption(CommandSource &source, Command *cmd, NickCore *nc, const Anope::string &setting) { throw NotImplementedException(); } + + /** Called whenever a message is received from the uplink + * @param source The source of the message + * @param command The command being executed + * @param params Parameters + * @return EVENT_STOP to prevent the protocol module from processing this message + */ + virtual EventReturn OnMessage(MessageSource &source, Anope::string &command, std::vector ¶m) { throw NotImplementedException(); } + + /** Called to determine if a channel mode can be set by a user + * @param u The user + * @param cm The mode + */ + virtual EventReturn OnCanSet(User *u, const ChannelMode *cm) { throw NotImplementedException(); } + + virtual EventReturn OnCheckDelete(Channel *) { throw NotImplementedException(); } + + /** Called every options:expiretimeout seconds. Should be used to expire nicks, + * channels, etc. + */ + virtual void OnExpireTick() { throw NotImplementedException(); } + + /** Called when a nick is validated. That is, to determine if a user is permitted + * to be on the given nick. + * @param u The user + * @param na The nick they are on + * @return EVENT_STOP to force the user off of the nick + */ + virtual EventReturn OnNickValidate(User *u, NickAlias *na) { throw NotImplementedException(); } + + /** Called when a certain user has to be unbanned on a certain channel. + * May be used to send protocol-specific messages. + * @param u The user to be unbanned + * @param c The channel that user has to be unbanned on + */ + virtual void OnChannelUnban(User *u, ChannelInfo *ci) { throw NotImplementedException(); } +}; + +enum Implementation +{ + I_OnPostInit, + I_OnPreUserKicked, I_OnUserKicked, I_OnReload, I_OnPreBotAssign, I_OnBotAssign, I_OnBotUnAssign, I_OnUserConnect, + I_OnNewServer, I_OnUserNickChange, I_OnPreHelp, I_OnPostHelp, I_OnPreCommand, I_OnPostCommand, I_OnSaveDatabase, + I_OnLoadDatabase, I_OnEncrypt, I_OnDecrypt, I_OnBotFantasy, I_OnBotNoFantasyAccess, I_OnBotBan, I_OnBadWordAdd, + I_OnBadWordDel, I_OnCreateBot, I_OnDelBot, I_OnBotKick, I_OnPrePartChannel, I_OnPartChannel, I_OnLeaveChannel, + I_OnJoinChannel, I_OnTopicUpdated, I_OnPreChanExpire, I_OnChanExpire, I_OnPreServerConnect, I_OnServerConnect, + I_OnPreUplinkSync, I_OnServerDisconnect, I_OnRestart, I_OnShutdown, I_OnPreNickExpire, I_OnNickExpire, I_OnDefconLevel, + I_OnExceptionAdd, I_OnExceptionDel, I_OnAddXLine, I_OnDelXLine, I_IsServicesOper, I_OnServerQuit, I_OnUserQuit, + I_OnPreUserLogoff, I_OnPostUserLogoff, I_OnBotCreate, I_OnBotChange, I_OnBotDelete, I_OnAccessDel, I_OnAccessAdd, + I_OnAccessClear, I_OnLevelChange, I_OnChanDrop, I_OnChanRegistered, I_OnChanSuspend, I_OnChanUnsuspend, + I_OnCreateChan, I_OnDelChan, I_OnChannelCreate, I_OnChannelDelete, I_OnAkickAdd, I_OnAkickDel, I_OnCheckKick, + I_OnChanInfo, I_OnCheckPriv, I_OnGroupCheckPriv, I_OnNickDrop, I_OnNickGroup, I_OnNickIdentify, + I_OnUserLogin, I_OnNickLogout, I_OnNickRegister, I_OnNickConfirm, I_OnNickSuspend, I_OnNickUnsuspended, I_OnDelNick, I_OnNickCoreCreate, + I_OnDelCore, I_OnChangeCoreDisplay, I_OnNickClearAccess, I_OnNickAddAccess, I_OnNickEraseAccess, I_OnNickClearCert, + I_OnNickAddCert, I_OnNickEraseCert, I_OnNickInfo, I_OnBotInfo, I_OnCheckAuthentication, I_OnNickUpdate, + I_OnFingerprint, I_OnUserAway, I_OnInvite, I_OnDeleteVhost, I_OnSetVhost, I_OnSetDisplayedHost, I_OnMemoSend, I_OnMemoDel, + I_OnChannelModeSet, I_OnChannelModeUnset, I_OnUserModeSet, I_OnUserModeUnset, I_OnChannelModeAdd, I_OnUserModeAdd, + I_OnMLock, I_OnUnMLock, I_OnModuleLoad, I_OnModuleUnload, I_OnServerSync, I_OnUplinkSync, I_OnBotPrivmsg, I_OnBotNotice, + I_OnPrivmsg, I_OnLog, I_OnLogMessage, I_OnDnsRequest, I_OnCheckModes, I_OnChannelSync, I_OnSetCorrectModes, + I_OnSerializeCheck, I_OnSerializableConstruct, I_OnSerializableDestruct, I_OnSerializableUpdate, + I_OnSerializeTypeCreate, I_OnSetChannelOption, I_OnSetNickOption, I_OnMessage, I_OnCanSet, I_OnCheckDelete, + I_OnExpireTick, I_OnNickValidate, I_OnChannelUnban, + I_SIZE +}; + +/** Used to manage modules. + */ +class CoreExport ModuleManager +{ + public: + /** Event handler hooks. + */ + static std::vector EventHandlers[I_SIZE]; + + /** List of all modules loaded in Anope + */ + static std::list Modules; + +#ifdef _WIN32 + /** Clean up the module runtime directory + */ + static void CleanupRuntimeDirectory(); +#endif + + /** Loads a given module. + * @param m the module to load + * @param u the user who loaded it, NULL for auto-load + * @return MOD_ERR_OK on success, anything else on fail + */ + static ModuleReturn LoadModule(const Anope::string &modname, User *u); + + /** Unload the given module. + * @param m the module to unload + * @param u the user who unloaded it + * @return MOD_ERR_OK on success, anything else on fail + */ + static ModuleReturn UnloadModule(Module *m, User * u); + + /** Find a module + * @param name The module name + * @return The module + */ + static Module *FindModule(const Anope::string &name); + + /** Find the first module of a certain type + * @param type The module type + * @return The module + */ + static Module *FindFirstOf(ModType type); + + /** Checks whether this version of Anope is at least major.minor.patch.build + * Throws a ModuleException if not + * @param major The major version + * @param minor The minor version + * @param patch The patch version + */ + static void RequireVersion(int major, int minor, int patch); + + /** Change the priority of one event in a module. + * Each module event has a list of modules which are attached to that event type. If you wish to be called before or after other specific modules, you may use this + * method (usually within void Module::Prioritize()) to set your events priority. You may use this call in other methods too, however, this is not supported behaviour + * for a module. + * @param mod The module to change the priority of + * @param i The event to change the priority of + * @param s The state you wish to use for this event. Use one of + * PRIO_FIRST to set the event to be first called, PRIO_LAST to set it to be the last called, or PRIO_BEFORE and PRIO_AFTER + * to set it to be before or after one or more other modules. + * @param modules If PRIO_BEFORE or PRIO_AFTER is set in parameter 's', then this contains a list of one or more modules your module must be + * placed before or after. Your module will be placed before the highest priority module in this list for PRIO_BEFORE, or after the lowest + * priority module in this list for PRIO_AFTER. + * @param sz The number of modules being passed for PRIO_BEFORE and PRIO_AFTER. Defaults to 1, as most of the time you will only want to prioritize your module + * to be before or after one other module. + */ + static bool SetPriority(Module *mod, Implementation i, Priority s, Module **modules = NULL, size_t sz = 1); + + /** Change the priority of all events in a module. + * @param mod The module to set the priority of + * @param s The priority of all events in the module. + * Note that with this method, it is not possible to effectively use PRIO_BEFORE or PRIO_AFTER, you should use the more fine tuned + * SetPriority method for this, where you may specify other modules to be prioritized against. + */ + static bool SetPriority(Module *mod, Priority s); + + /** Detach all events from a module (used on unload) + * @param mod Module to detach from + */ + static void DetachAll(Module *mod); + + /** Unloading all modules except the protocol module. + */ + static void UnloadAll(); + + private: + /** Call the module_delete function to safely delete the module + * @param m the module to delete + * @return MOD_ERR_OK on success, anything else on fail + */ + static ModuleReturn DeleteModule(Module *m); + + /** Get the version of Anope the module was compiled against + * @return The version + */ + static ModuleVersion GetVersion(void *handle); +}; + +#endif // MODULES_H diff --git a/include/modules/bs_badwords.h b/include/modules/bs_badwords.h new file mode 100644 index 0000000..17be4be --- /dev/null +++ b/include/modules/bs_badwords.h @@ -0,0 +1,70 @@ +/* BotServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +/** Flags for badwords + */ +enum BadWordType +{ + /* Always kicks if the word is said */ + BW_ANY, + /* User must way the entire word */ + BW_SINGLE, + /* The word has to start with the badword */ + BW_START, + /* The word has to end with the badword */ + BW_END +}; + +/* Structure used to contain bad words. */ +struct BadWord +{ + Anope::string chan; + Anope::string word; + BadWordType type; + + virtual ~BadWord() { } + protected: + BadWord() { } +}; + +struct BadWords +{ + virtual ~BadWords() { } + + /** Add a badword to the badword list + * @param word The badword + * @param type The type (SINGLE START END) + * @return The badword + */ + virtual BadWord* AddBadWord(const Anope::string &word, BadWordType type) = 0; + + /** Get a badword structure by index + * @param index The index + * @return The badword + */ + virtual BadWord* GetBadWord(unsigned index) const = 0; + + /** Get how many badwords are on this channel + * @return The number of badwords in the vector + */ + virtual unsigned GetBadWordCount() const = 0; + + /** Remove a badword + * @param index The index of the badword + */ + virtual void EraseBadWord(unsigned index) = 0; + + /** Clear all badwords from the channel + */ + virtual void ClearBadWords() = 0; + + virtual void Check() = 0; +}; diff --git a/include/modules/bs_kick.h b/include/modules/bs_kick.h new file mode 100644 index 0000000..88ae4d4 --- /dev/null +++ b/include/modules/bs_kick.h @@ -0,0 +1,44 @@ +/* BotServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +/* Indices for TTB (Times To Ban) */ +enum +{ + TTB_BOLDS, + TTB_COLORS, + TTB_REVERSES, + TTB_UNDERLINES, + TTB_BADWORDS, + TTB_CAPS, + TTB_FLOOD, + TTB_REPEAT, + TTB_ITALICS, + TTB_AMSGS, + TTB_SIZE +}; + +struct KickerData +{ + bool amsgs, badwords, bolds, caps, colors, flood, italics, repeat, reverses, underlines; + int16_t ttb[TTB_SIZE]; /* Times to ban for each kicker */ + int16_t capsmin, capspercent; /* For CAPS kicker */ + int16_t floodlines, floodsecs; /* For FLOOD kicker */ + int16_t repeattimes; /* For REPEAT kicker */ + + bool dontkickops, dontkickvoices; + + protected: + KickerData() { } + + public: + virtual ~KickerData() { } + virtual void Check(ChannelInfo *ci) = 0; +}; diff --git a/include/modules/cs_entrymsg.h b/include/modules/cs_entrymsg.h new file mode 100644 index 0000000..e90563c --- /dev/null +++ b/include/modules/cs_entrymsg.h @@ -0,0 +1,34 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +struct EntryMsg +{ + Anope::string chan; + Anope::string creator; + Anope::string message; + time_t when; + + virtual ~EntryMsg() { } + protected: + EntryMsg() { } +}; + +struct EntryMessageList : Serialize::Checker > +{ + protected: + EntryMessageList() : Serialize::Checker >("EntryMsg") { } + + public: + virtual ~EntryMessageList() + { + for (unsigned i = (*this)->size(); i > 0; --i) + delete (*this)->at(i - 1); + } + + virtual EntryMsg* Create() = 0; +}; diff --git a/include/modules/cs_log.h b/include/modules/cs_log.h new file mode 100644 index 0000000..0c3376c --- /dev/null +++ b/include/modules/cs_log.h @@ -0,0 +1,42 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +struct LogSetting +{ + Anope::string chan; + /* Our service name of the command */ + Anope::string service_name; + /* The name of the client the command is on */ + Anope::string command_service; + /* Name of the command to the user, can have spaces */ + Anope::string command_name; + Anope::string method, extra; + Anope::string creator; + time_t created; + + virtual ~LogSetting() { } + protected: + LogSetting() { } +}; + +struct LogSettings : Serialize::Checker > +{ + typedef std::vector::iterator iterator; + + protected: + LogSettings() : Serialize::Checker >("LogSetting") + { + } + + public: + virtual ~LogSettings() { } + virtual LogSetting *Create() = 0; +}; diff --git a/include/modules/cs_mode.h b/include/modules/cs_mode.h new file mode 100644 index 0000000..9a917ba --- /dev/null +++ b/include/modules/cs_mode.h @@ -0,0 +1,89 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +struct ModeLock +{ + Anope::string ci; + bool set; + Anope::string name; + Anope::string param; + Anope::string setter; + time_t created; + + virtual ~ModeLock() { } + protected: + ModeLock() { } +}; + +struct ModeLocks +{ + typedef std::vector ModeList; + + virtual ~ModeLocks() { } + + /** Check if a mode is mlocked + * @param mode The mode + * @param An optional param + * @param status True to check mlock on, false for mlock off + * @return true on success, false on fail + */ + virtual bool HasMLock(ChannelMode *mode, const Anope::string ¶m, bool status) const = 0; + + /** Set a mlock + * @param mode The mode + * @param status True for mlock on, false for mlock off + * @param param An optional param arg for + mlocked modes + * @param setter Who is setting the mlock + * @param created When the mlock was created + * @return true on success, false on failure (module blocking) + */ + virtual bool SetMLock(ChannelMode *mode, bool status, const Anope::string ¶m = "", Anope::string setter = "", time_t created = Anope::CurTime) = 0; + + /** Remove a mlock + * @param mode The mode + * @param status True for mlock on, false for mlock off + * @param param The param of the mode, required if it is a list or status mode + * @return true on success, false on failure + */ + virtual bool RemoveMLock(ChannelMode *mode, bool status, const Anope::string ¶m = "") = 0; + + virtual void RemoveMLock(ModeLock *mlock) = 0; + + /** Clear all mlocks on the channel + */ + virtual void ClearMLock() = 0; + + /** Get all of the mlocks for this channel + * @return The mlocks + */ + virtual const ModeList &GetMLock() const = 0; + + /** Get a list of mode locks on a channel + * @param name The mode name to get a list of + * @return a list of mlocks for the given mode + */ + virtual std::list GetModeLockList(const Anope::string &name) = 0; + + /** Get details for a specific mlock + * @param mname The mode name + * @param An optional param to match with + * @return The MLock, if any + */ + virtual const ModeLock *GetMLock(const Anope::string &mname, const Anope::string ¶m = "") = 0; + + /** Get the current mode locks as a string + * @param complete True to show mlock parameters as well + * @return A string of mode locks, eg: +nrt + */ + virtual Anope::string GetMLockAsString(bool complete) const = 0; + + virtual void Check() = 0; +}; diff --git a/include/modules/dns.h b/include/modules/dns.h new file mode 100644 index 0000000..491695d --- /dev/null +++ b/include/modules/dns.h @@ -0,0 +1,178 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef DNS_H +#define DNS_H + +namespace DNS +{ + /** Valid query types + */ + enum QueryType + { + /* Nothing */ + QUERY_NONE, + /* A simple A lookup */ + QUERY_A = 1, + /* An authoritative name server */ + QUERY_NS = 2, + /* A CNAME lookup */ + QUERY_CNAME = 5, + /* Start of a zone of authority */ + QUERY_SOA = 6, + /* Reverse DNS lookup */ + QUERY_PTR = 12, + /* IPv6 AAAA lookup */ + QUERY_AAAA = 28, + /* Zone transfer */ + QUERY_AXFR = 252, + /* A lookup for any record */ + QUERY_ANY = 255 + }; + + /** Flags that can be AND'd into DNSPacket::flags to receive certain values + */ + enum + { + QUERYFLAGS_QR = 0x8000, + QUERYFLAGS_OPCODE = 0x7800, + QUERYFLAGS_OPCODE_NOTIFY = 0x2000, + QUERYFLAGS_AA = 0x400, + QUERYFLAGS_TC = 0x200, + QUERYFLAGS_RD = 0x100, + QUERYFLAGS_RA = 0x80, + QUERYFLAGS_Z = 0x70, + QUERYFLAGS_RCODE = 0xF + }; + + enum Error + { + ERROR_NONE, + ERROR_UNKNOWN, + ERROR_UNLOADED, + ERROR_TIMEDOUT, + ERROR_NOT_AN_ANSWER, + ERROR_NONSTANDARD_QUERY, + ERROR_FORMAT_ERROR, + ERROR_SERVER_FAILURE, + ERROR_DOMAIN_NOT_FOUND, + ERROR_NOT_IMPLEMENTED, + ERROR_REFUSED, + ERROR_NO_RECORDS, + ERROR_INVALIDTYPE + }; + + struct Question + { + Anope::string name; + QueryType type; + unsigned short qclass; + + Question() : type(QUERY_NONE), qclass(0) { } + Question(const Anope::string &n, QueryType t, unsigned short c = 1) : name(n), type(t), qclass(c) { } + inline bool operator==(const Question & other) const { return name == other.name && type == other.type && qclass == other.qclass; } + + struct hash + { + size_t operator()(const Question &q) const + { + return Anope::hash_ci()(q.name); + } + }; + }; + + struct ResourceRecord : Question + { + unsigned int ttl; + Anope::string rdata; + time_t created; + + ResourceRecord(const Anope::string &n, QueryType t, unsigned short c = 1) : Question(n, t, c), ttl(0), created(Anope::CurTime) { } + ResourceRecord(const Question &q) : Question(q), ttl(0), created(Anope::CurTime) { } + }; + + struct Query + { + std::vector questions; + std::vector answers, authorities, additional; + Error error; + + Query() : error(ERROR_NONE) { } + Query(const Question &q) : error(ERROR_NONE) { questions.push_back(q); } + }; + + class ReplySocket; + class Request; + + /** DNS manager + */ + class Manager : public Service + { + public: + Manager(Module *creator) : Service(creator, "DNS::Manager", "dns/manager") { } + virtual ~Manager() { } + + virtual void Process(Request *req) = 0; + virtual void RemoveRequest(Request *req) = 0; + + virtual bool HandlePacket(ReplySocket *s, const unsigned char *const data, int len, sockaddrs *from) = 0; + + virtual void UpdateSerial() = 0; + virtual void Notify(const Anope::string &zone) = 0; + virtual uint32_t GetSerial() const = 0; + }; + + /** A DNS query. + */ + class Request : public Timer, public Question + { + Manager *manager; + public: + /* Use result cache if available */ + bool use_cache; + /* Request id */ + unsigned short id; + /* Creator of this request */ + Module *creator; + + Request(Manager *mgr, Module *c, const Anope::string &addr, QueryType qt, bool cache = false) : Timer(0), Question(addr, qt), manager(mgr), + use_cache(cache), id(0), creator(c) { } + + virtual ~Request() + { + manager->RemoveRequest(this); + } + + /** Called when this request succeeds + * @param r The query sent back from the nameserver + */ + virtual void OnLookupComplete(const Query *r) = 0; + + /** Called when this request fails or times out. + * @param r The query sent back from the nameserver, check the error code. + */ + virtual void OnError(const Query *r) { } + + /** Used to time out the query, xalls OnError and lets the TimerManager + * delete this request. + */ + void Tick(time_t) anope_override + { + Log(LOG_DEBUG_2) << "Resolver: timeout for query " << this->name; + Query rr(*this); + rr.error = ERROR_TIMEDOUT; + this->OnError(&rr); + } + }; + +} // namespace DNS + +#endif // DNS_H diff --git a/include/modules/encryption.h b/include/modules/encryption.h new file mode 100644 index 0000000..6311ab7 --- /dev/null +++ b/include/modules/encryption.h @@ -0,0 +1,35 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +namespace Encryption +{ + typedef std::pair Hash; + typedef std::pair IV; + + class Context + { + public: + virtual ~Context() { } + virtual void Update(const unsigned char *data, size_t len) = 0; + virtual void Finalize() = 0; + virtual Hash GetFinalizedHash() = 0; + }; + + class Provider : public Service + { + public: + Provider(Module *creator, const Anope::string &sname) : Service(creator, "Encryption::Provider", sname) { } + virtual ~Provider() { } + + virtual Context *CreateContext(IV * = NULL) = 0; + virtual IV GetDefaultIV() = 0; + }; +} diff --git a/include/modules/httpd.h b/include/modules/httpd.h new file mode 100644 index 0000000..4922754 --- /dev/null +++ b/include/modules/httpd.h @@ -0,0 +1,243 @@ +/* + * + * (C) 2012-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#ifndef ANOPE_HTTPD_H +#define ANOPE_HTTPD_H + +enum HTTPError +{ + HTTP_ERROR_OK = 200, + HTTP_FOUND = 302, + HTTP_BAD_REQUEST = 400, + HTTP_PAGE_NOT_FOUND = 404, + HTTP_NOT_SUPPORTED = 505 +}; + +/* A message to someone */ +struct HTTPReply +{ + HTTPError error; + Anope::string content_type; + std::map headers; + typedef std::list > cookie; + std::vector cookies; + + HTTPReply() : error(HTTP_ERROR_OK), length(0) { } + + HTTPReply(const HTTPReply& other) : error(other.error), length(other.length) + { + content_type = other.content_type; + headers = other.headers; + cookies = other.cookies; + + for (unsigned i = 0; i < other.out.size(); ++i) + out.push_back(new Data(other.out[i]->buf, other.out[i]->len)); + } + + ~HTTPReply() + { + for (unsigned i = 0; i < out.size(); ++i) + delete out[i]; + out.clear(); + } + + struct Data + { + char *buf; + size_t len; + + Data(const char *b, size_t l) + { + this->buf = new char[l]; + memcpy(this->buf, b, l); + this->len = l; + } + + ~Data() + { + delete [] buf; + } + }; + + std::deque out; + size_t length; + + void Write(const Anope::string &message) + { + this->out.push_back(new Data(message.c_str(), message.length())); + this->length += message.length(); + } + + void Write(const char *b, size_t l) + { + this->out.push_back(new Data(b, l)); + this->length += l; + } +}; + +/* A message from someone */ +struct HTTPMessage +{ + std::map headers; + std::map cookies; + std::map get_data; + std::map post_data; + Anope::string content; +}; + +class HTTPClient; +class HTTPProvider; + +class HTTPPage : public Base +{ + Anope::string url; + Anope::string content_type; + + public: + HTTPPage(const Anope::string &u, const Anope::string &ct = "text/html") : url(u), content_type(ct) { } + + const Anope::string &GetURL() const { return this->url; } + + const Anope::string &GetContentType() const { return this->content_type; } + + /** Called when this page is requested + * @param The server this page is on + * @param The page name + * @param The client requesting the page + * @param The HTTP header sent from the client to request the page + * @param The HTTP header that will be sent back to the client + */ + virtual bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &) = 0; +}; + +class HTTPClient : public ClientSocket, public BinarySocket, public Base +{ + protected: + void WriteClient(const Anope::string &message) + { + BinarySocket::Write(message + "\r\n"); + } + + public: + HTTPClient(ListenSocket *l, int f, const sockaddrs &a) : ClientSocket(l, a), BinarySocket() { } + + virtual const Anope::string GetIP() + { + return this->clientaddr.addr(); + } + + virtual void SendError(HTTPError err, const Anope::string &msg) = 0; + virtual void SendReply(HTTPReply *) = 0; +}; + +class HTTPProvider : public ListenSocket, public Service +{ + Anope::string ip; + unsigned short port; + bool ssl; + public: + std::vector ext_ips; + std::vector ext_headers; + + HTTPProvider(Module *c, const Anope::string &n, const Anope::string &i, const unsigned short p, bool s) : ListenSocket(i, p, i.find(':') != Anope::string::npos), Service(c, "HTTPProvider", n), ip(i), port(p), ssl(s) { } + + const Anope::string &GetIP() const + { + return this->ip; + } + + unsigned short GetPort() const + { + return this->port; + } + + bool IsSSL() const + { + return this->ssl; + } + + virtual bool RegisterPage(HTTPPage *page) = 0; + virtual void UnregisterPage(HTTPPage *page) = 0; + virtual HTTPPage* FindPage(const Anope::string &name) = 0; +}; + +namespace HTTPUtils +{ + inline Anope::string URLDecode(const Anope::string &url) + { + Anope::string decoded; + + for (unsigned i = 0; i < url.length(); ++i) + { + const char& c = url[i]; + + if (c == '%' && i + 2 < url.length()) + { + Anope::string dest; + Anope::Unhex(url.substr(i + 1, 2), dest); + decoded += dest; + i += 2; + } + else if (c == '+') + decoded += ' '; + else + decoded += c; + } + + return decoded; + } + + inline Anope::string URLEncode(const Anope::string &url) + { + Anope::string encoded; + + for (unsigned i = 0; i < url.length(); ++i) + { + const char& c = url[i]; + + if (isalnum(c) || c == '.' || c == '-' || c == '*' || c == '_') + encoded += c; + else if (c == ' ') + encoded += '+'; + else + encoded += "%" + Anope::Hex(c); + } + + return encoded; + } + + inline Anope::string Escape(const Anope::string &src) + { + Anope::string dst; + + for (unsigned i = 0; i < src.length(); ++i) + { + switch (src[i]) + { + case '<': + dst += "<"; + break; + case '>': + dst += ">"; + break; + case '"': + dst += """; + break; + case '&': + dst += "&"; + break; + default: + dst += src[i]; + } + } + + return dst; + } +} + +#endif // ANOPE_HTTPD_H diff --git a/include/modules/ldap.h b/include/modules/ldap.h new file mode 100644 index 0000000..58ecb6a --- /dev/null +++ b/include/modules/ldap.h @@ -0,0 +1,171 @@ +/* + * + * (C) 2011-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#ifndef ANOPE_LDAP_H +#define ANOPE_LDAP_H + +class LDAPException : public ModuleException +{ + public: + LDAPException(const Anope::string &reason) : ModuleException(reason) { } + + virtual ~LDAPException() throw() { } +}; + +struct LDAPModification +{ + enum LDAPOperation + { + LDAP_ADD, + LDAP_DEL, + LDAP_REPLACE + }; + + LDAPOperation op; + Anope::string name; + std::vector values; +}; +typedef std::vector LDAPMods; + +struct LDAPAttributes : public std::map > +{ + size_t size(const Anope::string &attr) const + { + const std::vector& array = this->getArray(attr); + return array.size(); + } + + const std::vector keys() const + { + std::vector k; + for (const_iterator it = this->begin(), it_end = this->end(); it != it_end; ++it) + k.push_back(it->first); + return k; + } + + const Anope::string &get(const Anope::string &attr) const + { + const std::vector& array = this->getArray(attr); + if (array.empty()) + throw LDAPException("Empty attribute " + attr + " in LDAPResult::get"); + return array[0]; + } + + const std::vector& getArray(const Anope::string &attr) const + { + const_iterator it = this->find(attr); + if (it == this->end()) + throw LDAPException("Unknown attribute " + attr + " in LDAPResult::getArray"); + return it->second; + } +}; + +enum QueryType +{ + QUERY_UNKNOWN, + QUERY_BIND, + QUERY_SEARCH, + QUERY_ADD, + QUERY_DELETE, + QUERY_MODIFY +}; + +struct LDAPResult +{ + std::vector messages; + Anope::string error; + + QueryType type; + + LDAPResult() + { + this->type = QUERY_UNKNOWN; + } + + size_t size() const + { + return this->messages.size(); + } + + bool empty() const + { + return this->messages.empty(); + } + + const LDAPAttributes &get(size_t sz) const + { + if (sz >= this->messages.size()) + throw LDAPException("Index out of range"); + return this->messages[sz]; + } + + const Anope::string &getError() const + { + return this->error; + } +}; + +class LDAPInterface +{ + public: + Module *owner; + + LDAPInterface(Module *m) : owner(m) { } + virtual ~LDAPInterface() { } + + virtual void OnResult(const LDAPResult &r) = 0; + virtual void OnError(const LDAPResult &err) = 0; + virtual void OnDelete() { } +}; + +class LDAPProvider : public Service +{ + public: + LDAPProvider(Module *c, const Anope::string &n) : Service(c, "LDAPProvider", n) { } + + /** Attempt to bind to the LDAP server as an admin + * @param i The LDAPInterface the result is sent to + */ + virtual void BindAsAdmin(LDAPInterface *i) = 0; + + /** Bind to LDAP + * @param i The LDAPInterface the result is sent to + * @param who The binddn + * @param pass The password + */ + virtual void Bind(LDAPInterface *i, const Anope::string &who, const Anope::string &pass) = 0; + + /** Search ldap for the specified filter + * @param i The LDAPInterface the result is sent to + * @param base The base DN to search + * @param filter The filter to apply + */ + virtual void Search(LDAPInterface *i, const Anope::string &base, const Anope::string &filter) = 0; + + /** Add an entry to LDAP + * @param i The LDAPInterface the result is sent to + * @param dn The dn of the entry to add + * @param attributes The attributes + */ + virtual void Add(LDAPInterface *i, const Anope::string &dn, LDAPMods &attributes) = 0; + + /** Delete an entry from LDAP + * @param i The LDAPInterface the result is sent to + * @param dn The dn of the entry to delete + */ + virtual void Del(LDAPInterface *i, const Anope::string &dn) = 0; + + /** Modify an existing entry in LDAP + * @param i The LDAPInterface the result is sent to + * @param base The base DN to modify + * @param attributes The attributes to modify + */ + virtual void Modify(LDAPInterface *i, const Anope::string &base, LDAPMods &attributes) = 0; +}; + +#endif // ANOPE_LDAP_H diff --git a/include/modules/ns_cert.h b/include/modules/ns_cert.h new file mode 100644 index 0000000..7164da6 --- /dev/null +++ b/include/modules/ns_cert.h @@ -0,0 +1,70 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +struct NSCertList +{ + protected: + NSCertList() { } + public: + virtual ~NSCertList() { } + + /** Add an entry to the nick's certificate list + * + * @param entry The fingerprint to add to the cert list + * + * Adds a new entry into the cert list. + */ + virtual void AddCert(const Anope::string &entry) = 0; + + /** Get an entry from the nick's cert list by index + * + * @param entry Index in the certificate list vector to retrieve + * @return The fingerprint entry of the given index if within bounds, an empty string if the vector is empty or the index is out of bounds + * + * Retrieves an entry from the certificate list corresponding to the given index. + */ + virtual Anope::string GetCert(unsigned entry) const = 0; + + virtual unsigned GetCertCount() const = 0; + + /** Find an entry in the nick's cert list + * + * @param entry The fingerprint to search for + * @return True if the fingerprint is found in the cert list, false otherwise + * + * Search for an fingerprint within the cert list. + */ + virtual bool FindCert(const Anope::string &entry) const = 0; + + /** Erase a fingerprint from the nick's certificate list + * + * @param entry The fingerprint to remove + * + * Removes the specified fingerprint from the cert list. + */ + virtual void EraseCert(const Anope::string &entry) = 0; + + /** Clears the entire nick's cert list + * + * Deletes all the memory allocated in the certificate list vector and then clears the vector. + */ + virtual void ClearCert() = 0; + + virtual void Check() = 0; +}; + +class CertService : public Service +{ + public: + CertService(Module *c) : Service(c, "CertService", "certs") { } + + virtual NickCore* FindAccountFromCert(const Anope::string &cert) = 0; +}; diff --git a/include/modules/os_forbid.h b/include/modules/os_forbid.h new file mode 100644 index 0000000..f505929 --- /dev/null +++ b/include/modules/os_forbid.h @@ -0,0 +1,55 @@ +/* + * + * (C) 2011-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#ifndef OS_FORBID_H +#define OS_FORBID_H + +enum ForbidType +{ + FT_NICK = 1, + FT_CHAN, + FT_EMAIL, + FT_REGISTER, + FT_SIZE +}; + +struct ForbidData +{ + Anope::string mask; + Anope::string creator; + Anope::string reason; + time_t created; + time_t expires; + ForbidType type; + + virtual ~ForbidData() { } + protected: + ForbidData() : created(0), expires(0) { } +}; + +class ForbidService : public Service +{ + public: + ForbidService(Module *m) : Service(m, "ForbidService", "forbid") { } + + virtual void AddForbid(ForbidData *d) = 0; + + virtual void RemoveForbid(ForbidData *d) = 0; + + virtual ForbidData* CreateForbid() = 0; + + virtual ForbidData *FindForbid(const Anope::string &mask, ForbidType type) = 0; + + virtual ForbidData *FindForbidExact(const Anope::string &mask, ForbidType type) = 0; + + virtual std::vector GetForbids() = 0; +}; + +static ServiceReference forbid_service("ForbidService", "forbid"); + +#endif diff --git a/include/modules/os_ignore.h b/include/modules/os_ignore.h new file mode 100644 index 0000000..afe5474 --- /dev/null +++ b/include/modules/os_ignore.h @@ -0,0 +1,43 @@ +/* OperServ ignore interface + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +struct IgnoreData +{ + Anope::string mask; + Anope::string creator; + Anope::string reason; + time_t time; /* When do we stop ignoring them? */ + + virtual ~IgnoreData() { } + protected: + IgnoreData() : time(0) { } +}; + +class IgnoreService : public Service +{ + protected: + IgnoreService(Module *c) : Service(c, "IgnoreService", "ignore") { } + + public: + virtual void AddIgnore(IgnoreData *) = 0; + + virtual void DelIgnore(IgnoreData *) = 0; + + virtual void ClearIgnores() = 0; + + virtual IgnoreData *Create() = 0; + + virtual IgnoreData *Find(const Anope::string &mask) = 0; + + virtual std::vector &GetIgnores() = 0; +}; + +static ServiceReference ignore_service("IgnoreService", "ignore"); diff --git a/include/modules/os_news.h b/include/modules/os_news.h new file mode 100644 index 0000000..5db8929 --- /dev/null +++ b/include/modules/os_news.h @@ -0,0 +1,52 @@ +/* + * + * (C) 2011-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#ifndef OS_NEWS +#define OS_NEWS + +enum NewsType +{ + NEWS_LOGON, + NEWS_RANDOM, + NEWS_OPER +}; + +struct NewsMessages +{ + NewsType type; + Anope::string name; + const char *msgs[10]; +}; + +struct NewsItem : Serializable +{ + NewsType type; + Anope::string text; + Anope::string who; + time_t time; + + NewsItem() : Serializable("NewsItem") { } +}; + +class NewsService : public Service +{ + public: + NewsService(Module *m) : Service(m, "NewsService", "news") { } + + virtual NewsItem *CreateNewsItem() = 0; + + virtual void AddNewsItem(NewsItem *n) = 0; + + virtual void DelNewsItem(NewsItem *n) = 0; + + virtual std::vector &GetNewsList(NewsType t) = 0; +}; + +static ServiceReference news_service("NewsService", "news"); + +#endif // OS_NEWS diff --git a/include/modules/os_session.h b/include/modules/os_session.h new file mode 100644 index 0000000..5be5104 --- /dev/null +++ b/include/modules/os_session.h @@ -0,0 +1,94 @@ +/* + * + * (C) 2011-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#ifndef OS_SESSION_H +#define OS_SESSION_H + +struct Session +{ + cidr addr; /* A cidr (sockaddrs + len) representing this session */ + unsigned count; /* Number of clients with this host */ + unsigned hits; /* Number of subsequent kills for a host */ + + Session(const sockaddrs &ip, int len) : addr(ip, len), count(1), hits(0) { } +}; + +struct Exception : Serializable +{ + Anope::string mask; /* Hosts to which this exception applies */ + unsigned limit; /* Session limit for exception */ + Anope::string who; /* Nick of person who added the exception */ + Anope::string reason; /* Reason for exception's addition */ + time_t time; /* When this exception was added */ + time_t expires; /* Time when it expires. 0 == no expiry */ + + Exception() : Serializable("Exception") { } + void Serialize(Serialize::Data &data) const anope_override; + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data); +}; + +class SessionService : public Service +{ + public: + typedef TR1NS::unordered_map SessionMap; + typedef std::vector ExceptionVector; + + SessionService(Module *m) : Service(m, "SessionService", "session") { } + + virtual Exception *CreateException() = 0; + + virtual void AddException(Exception *e) = 0; + + virtual void DelException(Exception *e) = 0; + + virtual Exception *FindException(User *u) = 0; + + virtual Exception *FindException(const Anope::string &host) = 0; + + virtual ExceptionVector &GetExceptions() = 0; + + virtual Session *FindSession(const Anope::string &ip) = 0; + + virtual SessionMap &GetSessions() = 0; +}; + +static ServiceReference session_service("SessionService", "session"); + +void Exception::Serialize(Serialize::Data &data) const +{ + data["mask"] << this->mask; + data["limit"] << this->limit; + data["who"] << this->who; + data["reason"] << this->reason; + data["time"] << this->time; + data["expires"] << this->expires; +} + +Serializable* Exception::Unserialize(Serializable *obj, Serialize::Data &data) +{ + if (!session_service) + return NULL; + + Exception *ex; + if (obj) + ex = anope_dynamic_static_cast(obj); + else + ex = new Exception; + data["mask"] >> ex->mask; + data["limit"] >> ex->limit; + data["who"] >> ex->who; + data["reason"] >> ex->reason; + data["time"] >> ex->time; + data["expires"] >> ex->expires; + + if (!obj) + session_service->AddException(ex); + return ex; +} + +#endif diff --git a/include/modules/pseudoclients/chanserv.h b/include/modules/pseudoclients/chanserv.h new file mode 100644 index 0000000..f05590b --- /dev/null +++ b/include/modules/pseudoclients/chanserv.h @@ -0,0 +1,25 @@ +/* + * + * (C) 2011-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#ifndef CHANSERV_H +#define CHANSERV_H + +class ChanServService : public Service +{ + public: + ChanServService(Module *m) : Service(m, "ChanServService", "ChanServ") + { + } + + /* Have ChanServ hold the channel, that is, join and set +nsti and wait + * for a few minutes so no one can join or rejoin. + */ + virtual void Hold(Channel *c) = 0; +}; + +#endif // CHANSERV_H diff --git a/include/modules/pseudoclients/global.h b/include/modules/pseudoclients/global.h new file mode 100644 index 0000000..cb548f7 --- /dev/null +++ b/include/modules/pseudoclients/global.h @@ -0,0 +1,30 @@ +/* + * + * (C) 2011-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#ifndef GLOBAL_H +#define GLOBAL_H + +class GlobalService : public Service +{ + public: + GlobalService(Module *m) : Service(m, "GlobalService", "Global") + { + } + + /** Retrieves the bot which sends global messages unless otherwise specified. */ + virtual Reference GetDefaultSender() = 0; + + /** Send out a global message to all users + * @param sender Our client which should send the global + * @param source The sender of the global + * @param message The message + */ + virtual void SendGlobal(BotInfo *sender, const Anope::string &source, const Anope::string &message) = 0; +}; + +#endif // GLOBAL_H diff --git a/include/modules/pseudoclients/memoserv.h b/include/modules/pseudoclients/memoserv.h new file mode 100644 index 0000000..583422c --- /dev/null +++ b/include/modules/pseudoclients/memoserv.h @@ -0,0 +1,41 @@ +/* + * + * (C) 2011-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#ifndef MEMOSERV_H +#define MEMOSERV_H + +class MemoServService : public Service +{ + public: + enum MemoResult + { + MEMO_SUCCESS, + MEMO_INVALID_TARGET, + MEMO_TOO_FAST, + MEMO_TARGET_FULL + }; + + MemoServService(Module *m) : Service(m, "MemoServService", "MemoServ") + { + } + + /** Sends a memo. + * @param source The source of the memo, can be anything. + * @param target The target of the memo, nick or channel. + * @param message Memo text + * @param force true to force the memo, restrictions/delays etc are not checked + */ + virtual MemoResult Send(const Anope::string &source, const Anope::string &target, const Anope::string &message, bool force = false) = 0; + + /** Check for new memos and notify the user if there are any + * @param u The user + */ + virtual void Check(User *u) = 0; +}; + +#endif // MEMOSERV_H diff --git a/include/modules/pseudoclients/nickserv.h b/include/modules/pseudoclients/nickserv.h new file mode 100644 index 0000000..c2d1381 --- /dev/null +++ b/include/modules/pseudoclients/nickserv.h @@ -0,0 +1,24 @@ +/* + * + * (C) 2011-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#ifndef NICKSERV_H +#define NICKSERV_H + +class NickServService : public Service +{ + public: + NickServService(Module *m) : Service(m, "NickServService", "NickServ") + { + } + + virtual void Validate(User *u) = 0; + virtual void Collide(User *u, NickAlias *na) = 0; + virtual void Release(NickAlias *na) = 0; +}; + +#endif // NICKSERV_H diff --git a/include/modules/redis.h b/include/modules/redis.h new file mode 100644 index 0000000..a5e878e --- /dev/null +++ b/include/modules/redis.h @@ -0,0 +1,74 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace Redis +{ + struct Reply + { + enum Type + { + NOT_PARSED, + NOT_OK, + OK, + INT, + BULK, + MULTI_BULK + } + type; + + Reply() { Clear(); } + ~Reply() { Clear(); } + + void Clear() + { + type = NOT_PARSED; + i = 0; + bulk.clear(); + multi_bulk_size = 0; + for (unsigned j = 0; j < multi_bulk.size(); ++j) + delete multi_bulk[j]; + multi_bulk.clear(); + } + + int64_t i; + Anope::string bulk; + int multi_bulk_size; + std::deque multi_bulk; + }; + + class Interface + { + public: + Module *owner; + + Interface(Module *m) : owner(m) { } + virtual ~Interface() { } + + virtual void OnResult(const Reply &r) = 0; + virtual void OnError(const Anope::string &error) { Log(owner) << error; } + }; + + class Provider : public Service + { + public: + Provider(Module *c, const Anope::string &n) : Service(c, "Redis::Provider", n) { } + + virtual bool IsSocketDead() = 0; + + virtual void SendCommand(Interface *i, const std::vector &cmds) = 0; + virtual void SendCommand(Interface *i, const Anope::string &str) = 0; + + virtual bool BlockAndProcess() = 0; + + virtual void Subscribe(Interface *i, const Anope::string &pattern) = 0; + virtual void Unsubscribe(const Anope::string &pattern) = 0; + + virtual void StartTransaction() = 0; + virtual void CommitTransaction() = 0; + }; +} diff --git a/include/modules/sasl.h b/include/modules/sasl.h new file mode 100644 index 0000000..405fa6e --- /dev/null +++ b/include/modules/sasl.h @@ -0,0 +1,139 @@ +/* + * + * (C) 2014-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace SASL +{ + struct Message + { + Anope::string source; + Anope::string target; + Anope::string type; + Anope::string data; + Anope::string ext; + }; + + class Mechanism; + struct Session; + + class Service : public ::Service + { + public: + Service(Module *o) : ::Service(o, "SASL::Service", "sasl") { } + + virtual void ProcessMessage(const Message &) = 0; + + virtual Anope::string GetAgent() = 0; + + virtual Session* GetSession(const Anope::string &uid) = 0; + + virtual void SendMessage(SASL::Session *session, const Anope::string &type, const Anope::string &data) = 0; + + virtual void Succeed(Session *, NickCore *) = 0; + virtual void Fail(Session *) = 0; + virtual void SendMechs(Session *) = 0; + virtual void DeleteSessions(Mechanism *, bool = false) = 0; + virtual void RemoveSession(Session *) = 0; + }; + + static ServiceReference sasl("SASL::Service", "sasl"); + + struct Session + { + time_t created; + Anope::string uid; + Anope::string hostname, ip; + Reference mech; + + Session(Mechanism *m, const Anope::string &u) : created(Anope::CurTime), uid(u), mech(m) { } + virtual ~Session() + { + if (sasl) + sasl->RemoveSession(this); + } + }; + + /* PLAIN, EXTERNAL, etc */ + class Mechanism : public ::Service + { + public: + Mechanism(Module *o, const Anope::string &sname) : Service(o, "SASL::Mechanism", sname) { } + + virtual Session* CreateSession(const Anope::string &uid) { return new Session(this, uid); } + + virtual void ProcessMessage(Session *session, const Message &) = 0; + + virtual ~Mechanism() + { + if (sasl) + sasl->DeleteSessions(this, true); + } + }; + + class IdentifyRequest : public ::IdentifyRequest + { + Anope::string uid; + Anope::string hostname, ip; + + public: + IdentifyRequest(Module *m, const Anope::string &id, const Anope::string &acc, const Anope::string &pass, const Anope::string &h, const Anope::string &i) : ::IdentifyRequest(m, acc, pass), uid(id), hostname(h), ip(i) { } + + void OnSuccess() anope_override + { + if (!sasl) + return; + + NickAlias *na = NickAlias::Find(GetAccount()); + if (!na || na->nc->HasExt("NS_SUSPENDED") || na->nc->HasExt("UNCONFIRMED")) + return OnFail(); + + unsigned int maxlogins = Config->GetModule("ns_identify")->Get("maxlogins"); + if (maxlogins && na->nc->users.size() >= maxlogins) + return OnFail(); + + Session *s = sasl->GetSession(uid); + if (s) + { + Anope::string user = "A user"; + if (!hostname.empty() && !ip.empty()) + user = hostname + " (" + ip + ")"; + + Log(this->GetOwner(), "sasl", Config->GetClient("NickServ")) << user << " identified to account " << this->GetAccount() << " using SASL"; + sasl->Succeed(s, na->nc); + delete s; + } + } + + void OnFail() anope_override + { + if (!sasl) + return; + + Session *s = sasl->GetSession(uid); + if (s) + { + sasl->Fail(s); + delete s; + } + + Anope::string accountstatus; + NickAlias *na = NickAlias::Find(GetAccount()); + if (!na) + accountstatus = "nonexistent "; + else if (na->nc->HasExt("NS_SUSPENDED")) + accountstatus = "suspended "; + else if (na->nc->HasExt("UNCONFIRMED")) + accountstatus = "unconfirmed "; + + Anope::string user = "A user"; + if (!hostname.empty() && !ip.empty()) + user = hostname + " (" + ip + ")"; + + Log(this->GetOwner(), "sasl", Config->GetClient("NickServ")) << user << " failed to identify for " << accountstatus << "account " << this->GetAccount() << " using SASL"; + } + }; +} diff --git a/include/modules/set_misc.h b/include/modules/set_misc.h new file mode 100644 index 0000000..b989555 --- /dev/null +++ b/include/modules/set_misc.h @@ -0,0 +1,17 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +struct MiscData +{ + Anope::string object; + Anope::string name; + Anope::string data; + + MiscData() { } + virtual ~MiscData() { } +}; diff --git a/include/modules/sql.h b/include/modules/sql.h new file mode 100644 index 0000000..50f9168 --- /dev/null +++ b/include/modules/sql.h @@ -0,0 +1,216 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace SQL +{ + + class Data : public Serialize::Data + { + public: + typedef std::map Map; + Map data; + std::map types; + + ~Data() + { + Clear(); + } + + std::iostream& operator[](const Anope::string &key) anope_override + { + std::stringstream *&ss = data[key]; + if (!ss) + ss = new std::stringstream(); + return *ss; + } + + std::set KeySet() const anope_override + { + std::set keys; + for (Map::const_iterator it = this->data.begin(), it_end = this->data.end(); it != it_end; ++it) + keys.insert(it->first); + return keys; + } + + size_t Hash() const anope_override + { + size_t hash = 0; + for (Map::const_iterator it = this->data.begin(), it_end = this->data.end(); it != it_end; ++it) + if (!it->second->str().empty()) + hash ^= Anope::hash_cs()(it->second->str()); + return hash; + } + + std::map GetData() const + { + std::map d; + for (Map::const_iterator it = this->data.begin(), it_end = this->data.end(); it != it_end; ++it) + d[it->first] = it->second; + return d; + } + + void Clear() + { + for (Map::const_iterator it = this->data.begin(), it_end = this->data.end(); it != it_end; ++it) + delete it->second; + this->data.clear(); + } + + void SetType(const Anope::string &key, Type t) anope_override + { + this->types[key] = t; + } + + Type GetType(const Anope::string &key) const anope_override + { + std::map::const_iterator it = this->types.find(key); + if (it != this->types.end()) + return it->second; + return DT_TEXT; + } + }; + + /** A SQL exception, can be thrown at various points + */ + class Exception : public ModuleException + { + public: + Exception(const Anope::string &reason) : ModuleException(reason) { } + + virtual ~Exception() throw() { } + }; + + /** A SQL query + */ + + struct QueryData + { + Anope::string data; + bool escape; + }; + + struct Query + { + Anope::string query; + std::map parameters; + + Query() { } + Query(const Anope::string &q) : query(q) { } + + Query& operator=(const Anope::string &q) + { + this->query = q; + this->parameters.clear(); + return *this; + } + + bool operator==(const Query &other) const + { + return this->query == other.query; + } + + inline bool operator!=(const Query &other) const + { + return !(*this == other); + } + + template void SetValue(const Anope::string &key, const T& value, bool escape = true) + { + try + { + Anope::string string_value = stringify(value); + this->parameters[key].data = string_value; + this->parameters[key].escape = escape; + } + catch (const ConvertException &ex) { } + } + }; + + /** A result from a SQL query + */ + class Result + { + protected: + /* Rows, column, item */ + std::vector > entries; + Query query; + Anope::string error; + public: + unsigned int id; + Anope::string finished_query; + + Result() : id(0) { } + Result(unsigned int i, const Query &q, const Anope::string &fq, const Anope::string &err = "") : query(q), error(err), id(i), finished_query(fq) { } + + inline operator bool() const { return this->error.empty(); } + + inline unsigned int GetID() const { return this->id; } + inline const Query &GetQuery() const { return this->query; } + inline const Anope::string &GetError() const { return this->error; } + + int Rows() const { return this->entries.size(); } + + const std::map &Row(size_t index) const + { + try + { + return this->entries.at(index); + } + catch (const std::out_of_range &) + { + throw Exception("Out of bounds access to SQLResult"); + } + } + + const Anope::string Get(size_t index, const Anope::string &col) const + { + const std::map rows = this->Row(index); + + std::map::const_iterator it = rows.find(col); + if (it == rows.end()) + throw Exception("Unknown column name in SQLResult: " + col); + + return it->second; + } + }; + + /* An interface used by modules to retrieve the results + */ + class Interface + { + public: + Module *owner; + + Interface(Module *m) : owner(m) { } + virtual ~Interface() { } + + virtual void OnResult(const Result &r) = 0; + virtual void OnError(const Result &r) = 0; + }; + + /** Class providing the SQL service, modules call this to execute queries + */ + class Provider : public Service + { + public: + Provider(Module *c, const Anope::string &n) : Service(c, "SQL::Provider", n) { } + + virtual void Run(Interface *i, const Query &query) = 0; + + virtual Result RunQuery(const Query &query) = 0; + + virtual std::vector CreateTable(const Anope::string &table, const Data &data) = 0; + + virtual Query BuildInsert(const Anope::string &table, unsigned int id, Data &data) = 0; + + virtual Query GetTables(const Anope::string &prefix) = 0; + + virtual Anope::string FromUnixtime(time_t) = 0; + }; + +} diff --git a/include/modules/ssl.h b/include/modules/ssl.h new file mode 100644 index 0000000..314edd4 --- /dev/null +++ b/include/modules/ssl.h @@ -0,0 +1,15 @@ +/* + * + * (C) 2010-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +class SSLService : public Service +{ + public: + SSLService(Module *o, const Anope::string &n) : Service(o, "SSLService", n) { } + + virtual void Init(Socket *s) = 0; +}; diff --git a/include/modules/suspend.h b/include/modules/suspend.h new file mode 100644 index 0000000..2214093 --- /dev/null +++ b/include/modules/suspend.h @@ -0,0 +1,19 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +struct SuspendInfo +{ + Anope::string what, by, reason; + time_t when, expires; + + SuspendInfo() { } + virtual ~SuspendInfo() { } +}; diff --git a/include/modules/xmlrpc.h b/include/modules/xmlrpc.h new file mode 100644 index 0000000..81c61c0 --- /dev/null +++ b/include/modules/xmlrpc.h @@ -0,0 +1,47 @@ +/* + * + * (C) 2010-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "httpd.h" + +class XMLRPCRequest +{ + std::map replies; + + public: + Anope::string name; + Anope::string id; + std::deque data; + HTTPReply& r; + + XMLRPCRequest(HTTPReply &_r) : r(_r) { } + inline void reply(const Anope::string &dname, const Anope::string &ddata) { this->replies.insert(std::make_pair(dname, ddata)); } + inline const std::map &get_replies() { return this->replies; } +}; + +class XMLRPCServiceInterface; + +class XMLRPCEvent +{ + public: + virtual ~XMLRPCEvent() { } + virtual bool Run(XMLRPCServiceInterface *iface, HTTPClient *client, XMLRPCRequest &request) = 0; +}; + +class XMLRPCServiceInterface : public Service +{ + public: + XMLRPCServiceInterface(Module *creator, const Anope::string &sname) : Service(creator, "XMLRPCServiceInterface", sname) { } + + virtual void Register(XMLRPCEvent *event) = 0; + + virtual void Unregister(XMLRPCEvent *event) = 0; + + virtual Anope::string Sanitize(const Anope::string &string) = 0; + + virtual void Reply(XMLRPCRequest &request) = 0; +}; diff --git a/include/opertype.h b/include/opertype.h new file mode 100644 index 0000000..bda67cb --- /dev/null +++ b/include/opertype.h @@ -0,0 +1,127 @@ +/* + * + * (C) 2008-2011 Robin Burchell + * (C) 2008-2022 Anope Team + * + * Please read COPYING and README for further details. + */ + +#ifndef OPERTYPE_H +#define OPERTYPE_H + +#include "services.h" +#include "account.h" + +/* A services operator. Usually made by the configuration file, but not always. + * NickAlias::Find(name)->nc->o == this + */ +struct CoreExport Oper +{ + /* The oper's nick */ + Anope::string name; + /* The type of operator this operator is */ + OperType *ot; + /* Whether the user must be an IRC operator (umode +o) to be considered a services operator */ + bool require_oper; + Anope::string password; + Anope::string certfp; + /* Hosts allowed to use this operator block */ + std::vector hosts; + Anope::string vhost; + + Oper(const Anope::string &n, OperType *o); + virtual ~Oper(); + + static std::vector opers; + + /** Find an oper block by name + * @param name The name + * @return the oper block + */ + static Oper *Find(const Anope::string &name); +}; + +class CoreExport OperType +{ + private: + /** The name of this opertype, e.g. "sra". + */ + Anope::string name; + + /** Privs that this opertype may use, e.g. 'users/auspex'. + * This *must* be std::list, see commands comment for details. + */ + std::list privs; + + /** Commands this user may execute, e.g: + * botserv/set/ *, botserv/set/private, botserv/ * + * et cetera. + * + * This *must* be std::list, not std::map, because + * we support full globbing here. This shouldn't be a problem + * as we don't invoke it often. + */ + std::list commands; + + /** Set of opertypes we inherit from + */ + std::set inheritances; + public: + /** Modes to set when someone identifies using this opertype + */ + Anope::string modes; + + /** Find an oper type by name + * @param name The name + * @return The oper type + */ + static OperType *Find(const Anope::string &name); + + /** Create a new opertype of the given name. + * @param nname The opertype name, e.g. "sra". + */ + OperType(const Anope::string &nname); + + /** Check whether this opertype has access to run the given command string. + * @param cmdstr The string to check, e.g. botserv/set/private. + * @return True if this opertype may run the specified command, false otherwise. + */ + bool HasCommand(const Anope::string &cmdstr) const; + + /** Check whether this opertype has access to the given special permission. + * @param privstr The priv to check for, e.g. users/auspex. + * @return True if this opertype has the specified priv, false otherwise. + */ + bool HasPriv(const Anope::string &privstr) const; + + /** Add the specified command to this opertype. + * @param cmdstr The command mask to grant this opertype access to, e.g: nickserv/ *, chanserv/set/ *, botserv/set/private. + */ + void AddCommand(const Anope::string &cmdstr); + + /** Add the specified priv mask to this opertype. + * @param privstr The specified mask of privs to grant this opertype access to, e.g. users/auspex, users/ *, etc. + */ + void AddPriv(const Anope::string &privstr); + + /** Returns the name of this opertype. + */ + const Anope::string &GetName() const; + + /** Make this opertype inherit commands and privs from another opertype + * @param ot The opertype to inherit from + */ + void Inherits(OperType *ot); + + /** Gets the icommands for this opertype + * @return A list of commands + */ + const std::list GetCommands() const; + + /** Gets the privileges for this opertype + * @return A list of privileges + */ + const std::list GetPrivs() const; +}; + +#endif // OPERTYPE_H diff --git a/include/protocol.h b/include/protocol.h new file mode 100644 index 0000000..b61cbfa --- /dev/null +++ b/include/protocol.h @@ -0,0 +1,318 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef PROTOCOL_H +#define PROTOCOL_H + +#include "services.h" +#include "anope.h" +#include "service.h" +#include "modes.h" + +/* Encapsulates the IRCd protocol we are speaking. */ +class CoreExport IRCDProto : public Service +{ + Anope::string proto_name; + + protected: + IRCDProto(Module *creator, const Anope::string &proto_name); + public: + virtual ~IRCDProto(); + + virtual void SendSVSKillInternal(const MessageSource &, User *, const Anope::string &); + virtual void SendModeInternal(const MessageSource &, const Channel *, const Anope::string &); + virtual void SendModeInternal(const MessageSource &, User *, const Anope::string &); + virtual void SendKickInternal(const MessageSource &, const Channel *, User *, const Anope::string &); + virtual void SendNoticeInternal(const MessageSource &, const Anope::string &dest, const Anope::string &msg); + virtual void SendPrivmsgInternal(const MessageSource &, const Anope::string &dest, const Anope::string &buf); + virtual void SendQuitInternal(User *, const Anope::string &buf); + virtual void SendPartInternal(User *, const Channel *chan, const Anope::string &buf); + virtual void SendGlobopsInternal(const MessageSource &, const Anope::string &buf); + virtual void SendCTCPInternal(const MessageSource &, const Anope::string &dest, const Anope::string &buf); + virtual void SendNumericInternal(int numeric, const Anope::string &dest, const Anope::string &buf); + + const Anope::string &GetProtocolName(); + virtual bool Parse(const Anope::string &, Anope::map &, Anope::string &, Anope::string &, std::vector &); + virtual Anope::string Format(const Anope::string &source, const Anope::string &message); + + /* Modes used by default by our clients */ + Anope::string DefaultPseudoclientModes; + /* Can we force change a users's nick? */ + bool CanSVSNick; + /* Can we force join or part users? */ + bool CanSVSJoin; + /* Can we set vhosts/vidents on users? */ + bool CanSetVHost, CanSetVIdent; + /* Can we ban specific gecos from being used? */ + bool CanSNLine; + /* Can we ban specific nicknames from being used? */ + bool CanSQLine; + /* Can we ban specific channel names from being used? */ + bool CanSQLineChannel; + /* Can we ban by IP? */ + bool CanSZLine; + /* Can we place temporary holds on specific nicknames? */ + bool CanSVSHold; + /* See os_oline */ + bool CanSVSO; + /* See ns_cert */ + bool CanCertFP; + /* Whether this IRCd requires unique IDs for each user or server. See TS6/P10. */ + bool RequiresID; + /* If this IRCd has unique ids, whether the IDs and nicknames are ambiguous */ + bool AmbiguousID; + /* The maximum number of modes we are allowed to set with one MODE command */ + unsigned MaxModes; + /* The maximum number of bytes a line may have */ + unsigned MaxLine; + + /* Retrieves the next free UID or SID */ + virtual Anope::string UID_Retrieve(); + virtual Anope::string SID_Retrieve(); + + /** Sets the server in NOOP mode. If NOOP mode is enabled, no users + * will be able to oper on the server. + * @param s The server + * @param mode Whether to turn NOOP on or off + */ + virtual void SendSVSNOOP(const Server *s, bool mode) { } + + /** Sets the topic on a channel + * @param bi The bot to set the topic from + * @param c The channel to set the topic on. The topic being set is Channel::topic + */ + virtual void SendTopic(const MessageSource &, Channel *); + + /** Sets a vhost on a user. + * @param u The user + * @param vident The ident to set + * @param vhost The vhost to set + */ + virtual void SendVhost(User *u, const Anope::string &vident, const Anope::string &vhost) { } + virtual void SendVhostDel(User *) { } + + /** Sets an akill. This is a recursive function that can be called multiple times + * for the same xline, but for different users, if the xline is not one that can be + * enforced by the IRCd, such as a nick/user/host/realname combination ban. + * @param u The user affected by the akill, if known + * @param x The akill + */ + virtual void SendAkill(User *, XLine *) = 0; + virtual void SendAkillDel(const XLine *) = 0; + + /* Realname ban */ + virtual void SendSGLine(User *, const XLine *) { } + virtual void SendSGLineDel(const XLine *) { } + + /* IP ban */ + virtual void SendSZLine(User *u, const XLine *) { } + virtual void SendSZLineDel(const XLine *) { } + + /* Nick ban (and sometimes channel) */ + virtual void SendSQLine(User *, const XLine *x) { } + virtual void SendSQLineDel(const XLine *x) { } + + virtual void SendKill(const MessageSource &source, const Anope::string &target, const Anope::string &reason); + + /** Kills a user + * @param source Who is doing the kill + * @param user The user to be killed + * @param fmt Kill reason + */ + virtual void SendSVSKill(const MessageSource &source, User *user, const char *fmt, ...); + + virtual void SendMode(const MessageSource &source, const Channel *dest, const char *fmt, ...); + virtual void SendMode(const MessageSource &source, User *u, const char *fmt, ...); + + /** Introduces a client to the rest of the network + * @param u The client to introduce + */ + virtual void SendClientIntroduction(User *u) = 0; + + virtual void SendKick(const MessageSource &source, const Channel *chan, User *user, const char *fmt, ...); + + virtual void SendNotice(const MessageSource &source, const Anope::string &dest, const char *fmt, ...); + virtual void SendPrivmsg(const MessageSource &source, const Anope::string &dest, const char *fmt, ...); + virtual void SendAction(const MessageSource &source, const Anope::string &dest, const char *fmt, ...); + virtual void SendCTCP(const MessageSource &source, const Anope::string &dest, const char *fmt, ...); + + virtual void SendGlobalNotice(BotInfo *bi, const Server *dest, const Anope::string &msg) = 0; + virtual void SendGlobalPrivmsg(BotInfo *bi, const Server *desc, const Anope::string &msg) = 0; + + virtual void SendQuit(User *u, const char *fmt, ...); + virtual void SendPing(const Anope::string &servname, const Anope::string &who); + virtual void SendPong(const Anope::string &servname, const Anope::string &who); + + /** Joins one of our users to a channel. + * @param u The user to join + * @param c The channel to join the user to + * @param status The status to set on the user after joining. This may or may not already internally + * be set on the user. This may include the modes in the join, but will usually place them on the mode + * stacker to be set "soon". + */ + virtual void SendJoin(User *u, Channel *c, const ChannelStatus *status) = 0; + virtual void SendPart(User *u, const Channel *chan, const char *fmt, ...); + + /** Force joins a user that isn't ours to a channel. + * @param bi The source of the message + * @param u The user to join + * @param chan The channel to join the user to + * @param param Channel key? + */ + virtual void SendSVSJoin(const MessageSource &source, User *u, const Anope::string &chan, const Anope::string ¶m) { } + + /** Force parts a user that isn't ours from a channel. + * @param source The source of the message + * @param u The user to part + * @param chan The channel to part the user from + * @param param part reason, some IRCds don't support this + */ + virtual void SendSVSPart(const MessageSource &source, User *u, const Anope::string &chan, const Anope::string ¶m) { } + + virtual void SendInvite(const MessageSource &source, const Channel *c, User *u); + virtual void SendGlobops(const MessageSource &source, const char *fmt, ...); + + /** Sets oper flags on a user, currently only supported by Unreal + */ + virtual void SendSVSO(BotInfo *, const Anope::string &, const Anope::string &) { } + + /** Sends a nick change of one of our clients. + */ + virtual void SendNickChange(User *u, const Anope::string &newnick); + + /** Forces a nick change of a user that isn't ours (SVSNICK) + */ + virtual void SendForceNickChange(User *u, const Anope::string &newnick, time_t when); + + /** Used to introduce ourselves to our uplink. Usually will SendServer(Me) and any other + * initial handshake requirements. + */ + virtual void SendConnect() = 0; + + /** Called right before we begin our burst, after we have handshaked successfully with the uplink. + * At this point none of our servers, users, or channels exist on the uplink + */ + virtual void SendBOB() { } + virtual void SendEOB() { } + + virtual void SendSVSHold(const Anope::string &, time_t) { } + virtual void SendSVSHoldDel(const Anope::string &) { } + + virtual void SendSWhois(const MessageSource &, const Anope::string &, const Anope::string &) { } + + /** Introduces a server to the uplink + */ + virtual void SendServer(const Server *) = 0; + virtual void SendSquit(Server *, const Anope::string &message); + + virtual void SendNumeric(int numeric, const Anope::string &dest, const char *fmt, ...); + + virtual void SendLogin(User *u, NickAlias *na) = 0; + virtual void SendLogout(User *u) = 0; + + /** Send a channel creation message to the uplink. + * On most TS6 IRCds this is a SJOIN with no nick + */ + virtual void SendChannel(Channel *c) { } + + /** Make the user an IRC operator + * Normally this is a simple +o, though some IRCds require us to send the oper type + */ + virtual void SendOper(User *u); + + virtual void SendSASLMechanisms(std::vector &) { } + virtual void SendSASLMessage(const SASL::Message &) { } + virtual void SendSVSLogin(const Anope::string &uid, const Anope::string &acc, const Anope::string &vident, const Anope::string &vhost) { } + + virtual bool IsNickValid(const Anope::string &); + virtual bool IsChannelValid(const Anope::string &); + virtual bool IsIdentValid(const Anope::string &); + virtual bool IsHostValid(const Anope::string &); + virtual bool IsExtbanValid(const Anope::string &) { return false; } + + /** Retrieve the maximum number of list modes settable on this channel + * Defaults to Config->ListSize + */ + virtual unsigned GetMaxListFor(Channel *c); + virtual unsigned GetMaxListFor(Channel *c, ChannelMode *cm); + + virtual Anope::string NormalizeMask(const Anope::string &mask); +}; + +class CoreExport MessageSource +{ + Anope::string source; + User *u; + Server *s; + + public: + MessageSource(const Anope::string &); + MessageSource(User *u); + MessageSource(Server *s); + const Anope::string &GetName() const; + const Anope::string &GetSource() const; + User *GetUser() const; + BotInfo *GetBot() const; + Server *GetServer() const; +}; + +enum IRCDMessageFlag +{ + IRCDMESSAGE_SOFT_LIMIT, + IRCDMESSAGE_REQUIRE_SERVER, + IRCDMESSAGE_REQUIRE_USER +}; + +class CoreExport IRCDMessage : public Service +{ + Anope::string name; + unsigned param_count; + std::set flags; + public: + IRCDMessage(Module *owner, const Anope::string &n, unsigned p = 0); + unsigned GetParamCount() const; + virtual void Run(MessageSource &, const std::vector ¶ms) = 0; + virtual void Run(MessageSource &, const std::vector ¶ms, const Anope::map &tags); + + void SetFlag(IRCDMessageFlag f) { flags.insert(f); } + bool HasFlag(IRCDMessageFlag f) const { return flags.count(f); } +}; + +/** MessageTokenizer allows tokens in the IRC wire format to be read from a string */ +class CoreExport MessageTokenizer +{ +private: + /** The message we are parsing tokens from. */ + Anope::string message; + + /** The current position within the message. */ + Anope::string::size_type position; + + public: + /** Create a tokenstream and fill it with the provided data. */ + MessageTokenizer(const Anope::string &msg); + + /** Retrieve the next \ token in the message. + * @param token The next token available, or an empty string if none remain. + * @return True if a token was retrieved; otherwise, false. + */ + bool GetMiddle(Anope::string &token); + + /** Retrieve the next \ token in the message. + * @param token The next token available, or an empty string if none remain. + * @return True if a token was retrieved; otherwise, false. + */ + bool GetTrailing(Anope::string &token); +}; + +extern CoreExport IRCDProto *IRCD; + +#endif // PROTOCOL_H diff --git a/include/pstdint.h b/include/pstdint.h new file mode 100644 index 0000000..b034ae0 --- /dev/null +++ b/include/pstdint.h @@ -0,0 +1,800 @@ +/* A portable stdint.h + **************************************************************************** + * BSD License: + **************************************************************************** + * + * Copyright (c) 2005-2011 Paul Hsieh + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + **************************************************************************** + * + * Version 0.1.12 + * + * The ANSI C standard committee, for the C99 standard, specified the + * inclusion of a new standard include file called stdint.h. This is + * a very useful and long desired include file which contains several + * very precise definitions for integer scalar types that is + * critically important for making portable several classes of + * applications including cryptography, hashing, variable length + * integer libraries and so on. But for most developers its likely + * useful just for programming sanity. + * + * The problem is that most compiler vendors have decided not to + * implement the C99 standard, and the next C++ language standard + * (which has a lot more mindshare these days) will be a long time in + * coming and its unknown whether or not it will include stdint.h or + * how much adoption it will have. Either way, it will be a long time + * before all compilers come with a stdint.h and it also does nothing + * for the extremely large number of compilers available today which + * do not include this file, or anything comparable to it. + * + * So that's what this file is all about. Its an attempt to build a + * single universal include file that works on as many platforms as + * possible to deliver what stdint.h is supposed to. A few things + * that should be noted about this file: + * + * 1) It is not guaranteed to be portable and/or present an identical + * interface on all platforms. The extreme variability of the + * ANSI C standard makes this an impossibility right from the + * very get go. Its really only meant to be useful for the vast + * majority of platforms that possess the capability of + * implementing usefully and precisely defined, standard sized + * integer scalars. Systems which are not intrinsically 2s + * complement may produce invalid constants. + * + * 2) There is an unavoidable use of non-reserved symbols. + * + * 3) Other standard include files are invoked. + * + * 4) This file may come in conflict with future platforms that do + * include stdint.h. The hope is that one or the other can be + * used with no real difference. + * + * 5) In the current version, if your platform can't represent + * int32_t, int16_t and int8_t, it just dumps out with a compiler + * error. + * + * 6) 64 bit integers may or may not be defined. Test for their + * presence with the test: #ifdef INT64_MAX or #ifdef UINT64_MAX. + * Note that this is different from the C99 specification which + * requires the existence of 64 bit support in the compiler. If + * this is not defined for your platform, yet it is capable of + * dealing with 64 bits then it is because this file has not yet + * been extended to cover all of your system's capabilities. + * + * 7) (u)intptr_t may or may not be defined. Test for its presence + * with the test: #ifdef PTRDIFF_MAX. If this is not defined + * for your platform, then it is because this file has not yet + * been extended to cover all of your system's capabilities, not + * because its optional. + * + * 8) The following might not been defined even if your platform is + * capable of defining it: + * + * WCHAR_MIN + * WCHAR_MAX + * (u)int64_t + * PTRDIFF_MIN + * PTRDIFF_MAX + * (u)intptr_t + * + * 9) The following have not been defined: + * + * WINT_MIN + * WINT_MAX + * + * 10) The criteria for defining (u)int_least(*)_t isn't clear, + * except for systems which don't have a type that precisely + * defined 8, 16, or 32 bit types (which this include file does + * not support anyways). Default definitions have been given. + * + * 11) The criteria for defining (u)int_fast(*)_t isn't something I + * would trust to any particular compiler vendor or the ANSI C + * committee. It is well known that "compatible systems" are + * commonly created that have very different performance + * characteristics from the systems they are compatible with, + * especially those whose vendors make both the compiler and the + * system. Default definitions have been given, but its strongly + * recommended that users never use these definitions for any + * reason (they do *NOT* deliver any serious guarantee of + * improved performance -- not in this file, nor any vendor's + * stdint.h). + * + * 12) The following macros: + * + * PRINTF_INTMAX_MODIFIER + * PRINTF_INT64_MODIFIER + * PRINTF_INT32_MODIFIER + * PRINTF_INT16_MODIFIER + * PRINTF_LEAST64_MODIFIER + * PRINTF_LEAST32_MODIFIER + * PRINTF_LEAST16_MODIFIER + * PRINTF_INTPTR_MODIFIER + * + * are strings which have been defined as the modifiers required + * for the "d", "u" and "x" printf formats to correctly output + * (u)intmax_t, (u)int64_t, (u)int32_t, (u)int16_t, (u)least64_t, + * (u)least32_t, (u)least16_t and (u)intptr_t types respectively. + * PRINTF_INTPTR_MODIFIER is not defined for some systems which + * provide their own stdint.h. PRINTF_INT64_MODIFIER is not + * defined if INT64_MAX is not defined. These are an extension + * beyond what C99 specifies must be in stdint.h. + * + * In addition, the following macros are defined: + * + * PRINTF_INTMAX_HEX_WIDTH + * PRINTF_INT64_HEX_WIDTH + * PRINTF_INT32_HEX_WIDTH + * PRINTF_INT16_HEX_WIDTH + * PRINTF_INT8_HEX_WIDTH + * PRINTF_INTMAX_DEC_WIDTH + * PRINTF_INT64_DEC_WIDTH + * PRINTF_INT32_DEC_WIDTH + * PRINTF_INT16_DEC_WIDTH + * PRINTF_INT8_DEC_WIDTH + * + * Which specifies the maximum number of characters required to + * print the number of that type in either hexadecimal or decimal. + * These are an extension beyond what C99 specifies must be in + * stdint.h. + * + * Compilers tested (all with 0 warnings at their highest respective + * settings): Borland Turbo C 2.0, WATCOM C/C++ 11.0 (16 bits and 32 + * bits), Microsoft Visual C++ 6.0 (32 bit), Microsoft Visual Studio + * .net (VC7), Intel C++ 4.0, GNU gcc v3.3.3 + * + * This file should be considered a work in progress. Suggestions for + * improvements, especially those which increase coverage are strongly + * encouraged. + * + * Acknowledgements + * + * The following people have made significant contributions to the + * development and testing of this file: + * + * Chris Howie + * John Steele Scott + * Dave Thorup + * John Dill + * + */ + +#include +#include +#include + +/* + * For gcc with _STDINT_H, fill in the PRINTF_INT*_MODIFIER macros, and + * do nothing else. On the Mac OS X version of gcc this is _STDINT_H_. + */ + +#if ((defined(__STDC__) && __STDC__ && __STDC_VERSION__ >= 199901L) || (defined (__WATCOMC__) && (defined (_STDINT_H_INCLUDED) || __WATCOMC__ >= 1250)) || (defined(__GNUC__) && (defined(_STDINT_H) || defined(_STDINT_H_) || defined (__UINT_FAST64_TYPE__)) )) && !defined (_PSTDINT_H_INCLUDED) +#include +#define _PSTDINT_H_INCLUDED +# ifndef PRINTF_INT64_MODIFIER +# define PRINTF_INT64_MODIFIER "ll" +# endif +# ifndef PRINTF_INT32_MODIFIER +# define PRINTF_INT32_MODIFIER "l" +# endif +# ifndef PRINTF_INT16_MODIFIER +# define PRINTF_INT16_MODIFIER "h" +# endif +# ifndef PRINTF_INTMAX_MODIFIER +# define PRINTF_INTMAX_MODIFIER PRINTF_INT64_MODIFIER +# endif +# ifndef PRINTF_INT64_HEX_WIDTH +# define PRINTF_INT64_HEX_WIDTH "16" +# endif +# ifndef PRINTF_INT32_HEX_WIDTH +# define PRINTF_INT32_HEX_WIDTH "8" +# endif +# ifndef PRINTF_INT16_HEX_WIDTH +# define PRINTF_INT16_HEX_WIDTH "4" +# endif +# ifndef PRINTF_INT8_HEX_WIDTH +# define PRINTF_INT8_HEX_WIDTH "2" +# endif +# ifndef PRINTF_INT64_DEC_WIDTH +# define PRINTF_INT64_DEC_WIDTH "20" +# endif +# ifndef PRINTF_INT32_DEC_WIDTH +# define PRINTF_INT32_DEC_WIDTH "10" +# endif +# ifndef PRINTF_INT16_DEC_WIDTH +# define PRINTF_INT16_DEC_WIDTH "5" +# endif +# ifndef PRINTF_INT8_DEC_WIDTH +# define PRINTF_INT8_DEC_WIDTH "3" +# endif +# ifndef PRINTF_INTMAX_HEX_WIDTH +# define PRINTF_INTMAX_HEX_WIDTH PRINTF_INT64_HEX_WIDTH +# endif +# ifndef PRINTF_INTMAX_DEC_WIDTH +# define PRINTF_INTMAX_DEC_WIDTH PRINTF_INT64_DEC_WIDTH +# endif + +/* + * Something really weird is going on with Open Watcom. Just pull some of + * these duplicated definitions from Open Watcom's stdint.h file for now. + */ + +# if defined (__WATCOMC__) && __WATCOMC__ >= 1250 +# if !defined (INT64_C) +# define INT64_C(x) (x + (INT64_MAX - INT64_MAX)) +# endif +# if !defined (UINT64_C) +# define UINT64_C(x) (x + (UINT64_MAX - UINT64_MAX)) +# endif +# if !defined (INT32_C) +# define INT32_C(x) (x + (INT32_MAX - INT32_MAX)) +# endif +# if !defined (UINT32_C) +# define UINT32_C(x) (x + (UINT32_MAX - UINT32_MAX)) +# endif +# if !defined (INT16_C) +# define INT16_C(x) (x) +# endif +# if !defined (UINT16_C) +# define UINT16_C(x) (x) +# endif +# if !defined (INT8_C) +# define INT8_C(x) (x) +# endif +# if !defined (UINT8_C) +# define UINT8_C(x) (x) +# endif +# if !defined (UINT64_MAX) +# define UINT64_MAX 18446744073709551615ULL +# endif +# if !defined (INT64_MAX) +# define INT64_MAX 9223372036854775807LL +# endif +# if !defined (UINT32_MAX) +# define UINT32_MAX 4294967295UL +# endif +# if !defined (INT32_MAX) +# define INT32_MAX 2147483647L +# endif +# if !defined (INTMAX_MAX) +# define INTMAX_MAX INT64_MAX +# endif +# if !defined (INTMAX_MIN) +# define INTMAX_MIN INT64_MIN +# endif +# endif +#endif + +#ifndef _PSTDINT_H_INCLUDED +#define _PSTDINT_H_INCLUDED + +#ifndef SIZE_MAX +# define SIZE_MAX (~(size_t)0) +#endif + +/* + * Deduce the type assignments from limits.h under the assumption that + * integer sizes in bits are powers of 2, and follow the ANSI + * definitions. + */ + +#ifndef UINT8_MAX +# define UINT8_MAX 0xff +#endif +#ifndef uint8_t +# if (UCHAR_MAX == UINT8_MAX) || defined (S_SPLINT_S) + typedef unsigned char uint8_t; +# define UINT8_C(v) ((uint8_t) v) +# else +# error "Platform not supported" +# endif +#endif + +#ifndef INT8_MAX +# define INT8_MAX 0x7f +#endif +#ifndef INT8_MIN +# define INT8_MIN INT8_C(0x80) +#endif +#ifndef int8_t +# if (SCHAR_MAX == INT8_MAX) || defined (S_SPLINT_S) + typedef signed char int8_t; +# define INT8_C(v) ((int8_t) v) +# else +# error "Platform not supported" +# endif +#endif + +#ifndef UINT16_MAX +# define UINT16_MAX 0xffff +#endif +#ifndef uint16_t +#if (UINT_MAX == UINT16_MAX) || defined (S_SPLINT_S) + typedef unsigned int uint16_t; +# ifndef PRINTF_INT16_MODIFIER +# define PRINTF_INT16_MODIFIER "" +# endif +# define UINT16_C(v) ((uint16_t) (v)) +#elif (USHRT_MAX == UINT16_MAX) + typedef unsigned short uint16_t; +# define UINT16_C(v) ((uint16_t) (v)) +# ifndef PRINTF_INT16_MODIFIER +# define PRINTF_INT16_MODIFIER "h" +# endif +#else +#error "Platform not supported" +#endif +#endif + +#ifndef INT16_MAX +# define INT16_MAX 0x7fff +#endif +#ifndef INT16_MIN +# define INT16_MIN INT16_C(0x8000) +#endif +#ifndef int16_t +#if (INT_MAX == INT16_MAX) || defined (S_SPLINT_S) + typedef signed int int16_t; +# define INT16_C(v) ((int16_t) (v)) +# ifndef PRINTF_INT16_MODIFIER +# define PRINTF_INT16_MODIFIER "" +# endif +#elif (SHRT_MAX == INT16_MAX) + typedef signed short int16_t; +# define INT16_C(v) ((int16_t) (v)) +# ifndef PRINTF_INT16_MODIFIER +# define PRINTF_INT16_MODIFIER "h" +# endif +#else +#error "Platform not supported" +#endif +#endif + +#ifndef UINT32_MAX +# define UINT32_MAX (0xffffffffUL) +#endif +#ifndef uint32_t +#if (ULONG_MAX == UINT32_MAX) || defined (S_SPLINT_S) + typedef unsigned long uint32_t; +# define UINT32_C(v) v ## UL +# ifndef PRINTF_INT32_MODIFIER +# define PRINTF_INT32_MODIFIER "l" +# endif +#elif (UINT_MAX == UINT32_MAX) + typedef unsigned int uint32_t; +# ifndef PRINTF_INT32_MODIFIER +# define PRINTF_INT32_MODIFIER "" +# endif +# define UINT32_C(v) v ## U +#elif (USHRT_MAX == UINT32_MAX) + typedef unsigned short uint32_t; +# define UINT32_C(v) ((unsigned short) (v)) +# ifndef PRINTF_INT32_MODIFIER +# define PRINTF_INT32_MODIFIER "" +# endif +#else +#error "Platform not supported" +#endif +#endif + +#ifndef INT32_MAX +# define INT32_MAX (0x7fffffffL) +#endif +#ifndef INT32_MIN +# define INT32_MIN INT32_C(0x80000000) +#endif +#ifndef int32_t +#if (LONG_MAX == INT32_MAX) || defined (S_SPLINT_S) + typedef signed long int32_t; +# define INT32_C(v) v ## L +# ifndef PRINTF_INT32_MODIFIER +# define PRINTF_INT32_MODIFIER "l" +# endif +#elif (INT_MAX == INT32_MAX) + typedef signed int int32_t; +# define INT32_C(v) v +# ifndef PRINTF_INT32_MODIFIER +# define PRINTF_INT32_MODIFIER "" +# endif +#elif (SHRT_MAX == INT32_MAX) + typedef signed short int32_t; +# define INT32_C(v) ((short) (v)) +# ifndef PRINTF_INT32_MODIFIER +# define PRINTF_INT32_MODIFIER "" +# endif +#else +#error "Platform not supported" +#endif +#endif + +/* + * The macro stdint_int64_defined is temporarily used to record + * whether or not 64 integer support is available. It must be + * defined for any 64 integer extensions for new platforms that are + * added. + */ + +#undef stdint_int64_defined +#if (defined(__STDC__) && defined(__STDC_VERSION__)) || defined (S_SPLINT_S) +# if (__STDC__ && __STDC_VERSION__ >= 199901L) || defined (S_SPLINT_S) +# define stdint_int64_defined + typedef long long int64_t; + typedef unsigned long long uint64_t; +# define UINT64_C(v) v ## ULL +# define INT64_C(v) v ## LL +# ifndef PRINTF_INT64_MODIFIER +# define PRINTF_INT64_MODIFIER "ll" +# endif +# endif +#endif + +#if !defined (stdint_int64_defined) +# if defined(__GNUC__) +# define stdint_int64_defined + __extension__ typedef long long int64_t; + __extension__ typedef unsigned long long uint64_t; +# define UINT64_C(v) v ## ULL +# define INT64_C(v) v ## LL +# ifndef PRINTF_INT64_MODIFIER +# define PRINTF_INT64_MODIFIER "ll" +# endif +# elif defined(__MWERKS__) || defined (__SUNPRO_C) || defined (__SUNPRO_CC) || defined (__APPLE_CC__) || defined (_LONG_LONG) || defined (_CRAYC) || defined (S_SPLINT_S) +# define stdint_int64_defined + typedef long long int64_t; + typedef unsigned long long uint64_t; +# define UINT64_C(v) v ## ULL +# define INT64_C(v) v ## LL +# ifndef PRINTF_INT64_MODIFIER +# define PRINTF_INT64_MODIFIER "ll" +# endif +# elif (defined(__WATCOMC__) && defined(__WATCOM_INT64__)) || (defined(_MSC_VER) && _INTEGRAL_MAX_BITS >= 64) || (defined (__BORLANDC__) && __BORLANDC__ > 0x460) || defined (__alpha) || defined (__DECC) +# define stdint_int64_defined + typedef __int64 int64_t; + typedef unsigned __int64 uint64_t; +# define UINT64_C(v) v ## UI64 +# define INT64_C(v) v ## I64 +# ifndef PRINTF_INT64_MODIFIER +# define PRINTF_INT64_MODIFIER "I64" +# endif +# endif +#endif + +#if !defined (LONG_LONG_MAX) && defined (INT64_C) +# define LONG_LONG_MAX INT64_C (9223372036854775807) +#endif +#ifndef ULONG_LONG_MAX +# define ULONG_LONG_MAX UINT64_C (18446744073709551615) +#endif + +#if !defined (INT64_MAX) && defined (INT64_C) +# define INT64_MAX INT64_C (9223372036854775807) +#endif +#if !defined (INT64_MIN) && defined (INT64_C) +# define INT64_MIN INT64_C (-9223372036854775808) +#endif +#if !defined (UINT64_MAX) && defined (INT64_C) +# define UINT64_MAX UINT64_C (18446744073709551615) +#endif + +/* + * Width of hexadecimal for number field. + */ + +#ifndef PRINTF_INT64_HEX_WIDTH +# define PRINTF_INT64_HEX_WIDTH "16" +#endif +#ifndef PRINTF_INT32_HEX_WIDTH +# define PRINTF_INT32_HEX_WIDTH "8" +#endif +#ifndef PRINTF_INT16_HEX_WIDTH +# define PRINTF_INT16_HEX_WIDTH "4" +#endif +#ifndef PRINTF_INT8_HEX_WIDTH +# define PRINTF_INT8_HEX_WIDTH "2" +#endif + +#ifndef PRINTF_INT64_DEC_WIDTH +# define PRINTF_INT64_DEC_WIDTH "20" +#endif +#ifndef PRINTF_INT32_DEC_WIDTH +# define PRINTF_INT32_DEC_WIDTH "10" +#endif +#ifndef PRINTF_INT16_DEC_WIDTH +# define PRINTF_INT16_DEC_WIDTH "5" +#endif +#ifndef PRINTF_INT8_DEC_WIDTH +# define PRINTF_INT8_DEC_WIDTH "3" +#endif + +/* + * Ok, lets not worry about 128 bit integers for now. Moore's law says + * we don't need to worry about that until about 2040 at which point + * we'll have bigger things to worry about. + */ + +#ifdef stdint_int64_defined + typedef int64_t intmax_t; + typedef uint64_t uintmax_t; +# define INTMAX_MAX INT64_MAX +# define INTMAX_MIN INT64_MIN +# define UINTMAX_MAX UINT64_MAX +# define UINTMAX_C(v) UINT64_C(v) +# define INTMAX_C(v) INT64_C(v) +# ifndef PRINTF_INTMAX_MODIFIER +# define PRINTF_INTMAX_MODIFIER PRINTF_INT64_MODIFIER +# endif +# ifndef PRINTF_INTMAX_HEX_WIDTH +# define PRINTF_INTMAX_HEX_WIDTH PRINTF_INT64_HEX_WIDTH +# endif +# ifndef PRINTF_INTMAX_DEC_WIDTH +# define PRINTF_INTMAX_DEC_WIDTH PRINTF_INT64_DEC_WIDTH +# endif +#else + typedef int32_t intmax_t; + typedef uint32_t uintmax_t; +# define INTMAX_MAX INT32_MAX +# define UINTMAX_MAX UINT32_MAX +# define UINTMAX_C(v) UINT32_C(v) +# define INTMAX_C(v) INT32_C(v) +# ifndef PRINTF_INTMAX_MODIFIER +# define PRINTF_INTMAX_MODIFIER PRINTF_INT32_MODIFIER +# endif +# ifndef PRINTF_INTMAX_HEX_WIDTH +# define PRINTF_INTMAX_HEX_WIDTH PRINTF_INT32_HEX_WIDTH +# endif +# ifndef PRINTF_INTMAX_DEC_WIDTH +# define PRINTF_INTMAX_DEC_WIDTH PRINTF_INT32_DEC_WIDTH +# endif +#endif + +/* + * Because this file currently only supports platforms which have + * precise powers of 2 as bit sizes for the default integers, the + * least definitions are all trivial. Its possible that a future + * version of this file could have different definitions. + */ + +#ifndef stdint_least_defined + typedef int8_t int_least8_t; + typedef uint8_t uint_least8_t; + typedef int16_t int_least16_t; + typedef uint16_t uint_least16_t; + typedef int32_t int_least32_t; + typedef uint32_t uint_least32_t; +# define PRINTF_LEAST32_MODIFIER PRINTF_INT32_MODIFIER +# define PRINTF_LEAST16_MODIFIER PRINTF_INT16_MODIFIER +# define UINT_LEAST8_MAX UINT8_MAX +# define INT_LEAST8_MAX INT8_MAX +# define UINT_LEAST16_MAX UINT16_MAX +# define INT_LEAST16_MAX INT16_MAX +# define UINT_LEAST32_MAX UINT32_MAX +# define INT_LEAST32_MAX INT32_MAX +# define INT_LEAST8_MIN INT8_MIN +# define INT_LEAST16_MIN INT16_MIN +# define INT_LEAST32_MIN INT32_MIN +# ifdef stdint_int64_defined + typedef int64_t int_least64_t; + typedef uint64_t uint_least64_t; +# define PRINTF_LEAST64_MODIFIER PRINTF_INT64_MODIFIER +# define UINT_LEAST64_MAX UINT64_MAX +# define INT_LEAST64_MAX INT64_MAX +# define INT_LEAST64_MIN INT64_MIN +# endif +#endif +#undef stdint_least_defined + +/* + * The ANSI C committee pretending to know or specify anything about + * performance is the epitome of misguided arrogance. The mandate of + * this file is to *ONLY* ever support that absolute minimum + * definition of the fast integer types, for compatibility purposes. + * No extensions, and no attempt to suggest what may or may not be a + * faster integer type will ever be made in this file. Developers are + * warned to stay away from these types when using this or any other + * stdint.h. + */ + +typedef int_least8_t int_fast8_t; +typedef uint_least8_t uint_fast8_t; +typedef int_least16_t int_fast16_t; +typedef uint_least16_t uint_fast16_t; +typedef int_least32_t int_fast32_t; +typedef uint_least32_t uint_fast32_t; +#define UINT_FAST8_MAX UINT_LEAST8_MAX +#define INT_FAST8_MAX INT_LEAST8_MAX +#define UINT_FAST16_MAX UINT_LEAST16_MAX +#define INT_FAST16_MAX INT_LEAST16_MAX +#define UINT_FAST32_MAX UINT_LEAST32_MAX +#define INT_FAST32_MAX INT_LEAST32_MAX +#define INT_FAST8_MIN INT_LEAST8_MIN +#define INT_FAST16_MIN INT_LEAST16_MIN +#define INT_FAST32_MIN INT_LEAST32_MIN +#ifdef stdint_int64_defined + typedef int_least64_t int_fast64_t; + typedef uint_least64_t uint_fast64_t; +# define UINT_FAST64_MAX UINT_LEAST64_MAX +# define INT_FAST64_MAX INT_LEAST64_MAX +# define INT_FAST64_MIN INT_LEAST64_MIN +#endif + +#undef stdint_int64_defined + +/* + * Whatever piecemeal, per compiler thing we can do about the wchar_t + * type limits. + */ + +#if defined(__WATCOMC__) || defined(_MSC_VER) || defined (__GNUC__) +# include +# ifndef WCHAR_MIN +# define WCHAR_MIN 0 +# endif +# ifndef WCHAR_MAX +# define WCHAR_MAX ((wchar_t)-1) +# endif +#endif + +/* + * Whatever piecemeal, per compiler/platform thing we can do about the + * (u)intptr_t types and limits. + */ + +#if defined (_MSC_VER) && defined (_UINTPTR_T_DEFINED) +# define STDINT_H_UINTPTR_T_DEFINED +#endif + +#ifndef STDINT_H_UINTPTR_T_DEFINED +# if defined (__alpha__) || defined (__ia64__) || defined (__x86_64__) || defined (_WIN64) +# define stdint_intptr_bits 64 +# elif defined (__WATCOMC__) || defined (__TURBOC__) +# if defined(__TINY__) || defined(__SMALL__) || defined(__MEDIUM__) +# define stdint_intptr_bits 16 +# else +# define stdint_intptr_bits 32 +# endif +# elif defined (__i386__) || defined (_WIN32) || defined (WIN32) +# define stdint_intptr_bits 32 +# elif defined (__INTEL_COMPILER) +/* TODO -- what did Intel do about x86-64? */ +# endif + +# ifdef stdint_intptr_bits +# define stdint_intptr_glue3_i(a,b,c) a##b##c +# define stdint_intptr_glue3(a,b,c) stdint_intptr_glue3_i(a,b,c) +# ifndef PRINTF_INTPTR_MODIFIER +# define PRINTF_INTPTR_MODIFIER stdint_intptr_glue3(PRINTF_INT,stdint_intptr_bits,_MODIFIER) +# endif +# ifndef PTRDIFF_MAX +# define PTRDIFF_MAX stdint_intptr_glue3(INT,stdint_intptr_bits,_MAX) +# endif +# ifndef PTRDIFF_MIN +# define PTRDIFF_MIN stdint_intptr_glue3(INT,stdint_intptr_bits,_MIN) +# endif +# ifndef UINTPTR_MAX +# define UINTPTR_MAX stdint_intptr_glue3(UINT,stdint_intptr_bits,_MAX) +# endif +# ifndef INTPTR_MAX +# define INTPTR_MAX stdint_intptr_glue3(INT,stdint_intptr_bits,_MAX) +# endif +# ifndef INTPTR_MIN +# define INTPTR_MIN stdint_intptr_glue3(INT,stdint_intptr_bits,_MIN) +# endif +# ifndef INTPTR_C +# define INTPTR_C(x) stdint_intptr_glue3(INT,stdint_intptr_bits,_C)(x) +# endif +# ifndef UINTPTR_C +# define UINTPTR_C(x) stdint_intptr_glue3(UINT,stdint_intptr_bits,_C)(x) +# endif + typedef stdint_intptr_glue3(uint,stdint_intptr_bits,_t) uintptr_t; + typedef stdint_intptr_glue3( int,stdint_intptr_bits,_t) intptr_t; +# else +/* TODO -- This following is likely wrong for some platforms, and does + nothing for the definition of uintptr_t. */ + typedef ptrdiff_t intptr_t; +# endif +# define STDINT_H_UINTPTR_T_DEFINED +#endif + +/* + * Assumes sig_atomic_t is signed and we have a 2s complement machine. + */ + +#ifndef SIG_ATOMIC_MAX +# define SIG_ATOMIC_MAX ((((sig_atomic_t) 1) << (sizeof (sig_atomic_t)*CHAR_BIT-1)) - 1) +#endif + +#endif + +#if defined (__TEST_PSTDINT_FOR_CORRECTNESS) + +/* + * Please compile with the maximum warning settings to make sure macros are not + * defined more than once. + */ + +#include +#include +#include + +#define glue3_aux(x,y,z) x ## y ## z +#define glue3(x,y,z) glue3_aux(x,y,z) + +#define DECLU(bits) glue3(uint,bits,_t) glue3(u,bits,=) glue3(UINT,bits,_C) (0); +#define DECLI(bits) glue3(int,bits,_t) glue3(i,bits,=) glue3(INT,bits,_C) (0); + +#define DECL(us,bits) glue3(DECL,us,) (bits) + +#define TESTUMAX(bits) glue3(u,bits,=) glue3(~,u,bits); if (glue3(UINT,bits,_MAX) glue3(!=,u,bits)) printf ("Something wrong with UINT%d_MAX\n", bits) + +int main () { + DECL(I,8) + DECL(U,8) + DECL(I,16) + DECL(U,16) + DECL(I,32) + DECL(U,32) +#ifdef INT64_MAX + DECL(I,64) + DECL(U,64) +#endif + intmax_t imax = INTMAX_C(0); + uintmax_t umax = UINTMAX_C(0); + char str0[256], str1[256]; + + sprintf (str0, "%d %x\n", 0, ~0); + + sprintf (str1, "%d %x\n", i8, ~0); + if (0 != strcmp (str0, str1)) printf ("Something wrong with i8 : %s\n", str1); + sprintf (str1, "%u %x\n", u8, ~0); + if (0 != strcmp (str0, str1)) printf ("Something wrong with u8 : %s\n", str1); + sprintf (str1, "%d %x\n", i16, ~0); + if (0 != strcmp (str0, str1)) printf ("Something wrong with i16 : %s\n", str1); + sprintf (str1, "%u %x\n", u16, ~0); + if (0 != strcmp (str0, str1)) printf ("Something wrong with u16 : %s\n", str1); + sprintf (str1, "%" PRINTF_INT32_MODIFIER "d %x\n", i32, ~0); + if (0 != strcmp (str0, str1)) printf ("Something wrong with i32 : %s\n", str1); + sprintf (str1, "%" PRINTF_INT32_MODIFIER "u %x\n", u32, ~0); + if (0 != strcmp (str0, str1)) printf ("Something wrong with u32 : %s\n", str1); +#ifdef INT64_MAX + sprintf (str1, "%" PRINTF_INT64_MODIFIER "d %x\n", i64, ~0); + if (0 != strcmp (str0, str1)) printf ("Something wrong with i64 : %s\n", str1); +#endif + sprintf (str1, "%" PRINTF_INTMAX_MODIFIER "d %x\n", imax, ~0); + if (0 != strcmp (str0, str1)) printf ("Something wrong with imax : %s\n", str1); + sprintf (str1, "%" PRINTF_INTMAX_MODIFIER "u %x\n", umax, ~0); + if (0 != strcmp (str0, str1)) printf ("Something wrong with umax : %s\n", str1); + + TESTUMAX(8); + TESTUMAX(16); + TESTUMAX(32); +#ifdef INT64_MAX + TESTUMAX(64); +#endif + + return EXIT_SUCCESS; +} + +#endif diff --git a/include/regchannel.h b/include/regchannel.h new file mode 100644 index 0000000..c92cdf2 --- /dev/null +++ b/include/regchannel.h @@ -0,0 +1,252 @@ +/* + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#ifndef REGCHANNEL_H +#define REGCHANNEL_H + +#include "memo.h" +#include "modes.h" +#include "extensible.h" +#include "logger.h" +#include "modules.h" +#include "serialize.h" +#include "bots.h" + +typedef Anope::hash_map registered_channel_map; + +extern CoreExport Serialize::Checker RegisteredChannelList; + +/* AutoKick data. */ +class CoreExport AutoKick : public Serializable +{ + public: + /* Channel this autokick is on */ + Serialize::Reference ci; + + Anope::string mask; + Serialize::Reference nc; + + Anope::string reason; + Anope::string creator; + time_t addtime; + time_t last_used; + + AutoKick(); + ~AutoKick(); + void Serialize(Serialize::Data &data) const anope_override; + static Serializable* Unserialize(Serializable *obj, Serialize::Data &); +}; + +/* It matters that Base is here before Extensible (it is inherited by Serializable) + */ +class CoreExport ChannelInfo : public Serializable, public Extensible +{ + /* channels who reference this one */ + Anope::map references; + private: + Serialize::Reference founder; /* Channel founder */ + Serialize::Reference successor; /* Who gets the channel if the founder nick is dropped or expires */ + Serialize::Checker > access; /* List of authorized users */ + Serialize::Checker > akick; /* List of users to kickban */ + Anope::map levels; + + public: + friend class ChanAccess; + friend class AutoKick; + + Anope::string name; /* Channel name */ + Anope::string desc; + + time_t time_registered; + time_t last_used; + + Anope::string last_topic; /* The last topic that was set on this channel */ + Anope::string last_topic_setter; /* Setter */ + time_t last_topic_time; /* Time */ + + Channel::ModeList last_modes; /* The last modes set on this channel */ + + int16_t bantype; + + MemoInfo memos; + + Channel *c; /* Pointer to channel, if the channel exists */ + + /* For BotServ */ + Serialize::Reference bi; /* Bot used on this channel */ + + time_t banexpire; /* Time bans expire in */ + + /** Constructor + * @param chname The channel name + */ + ChannelInfo(const Anope::string &chname); + + /** Copy constructor + * @param ci The ChannelInfo to copy settings from + */ + ChannelInfo(const ChannelInfo &ci); + + ~ChannelInfo(); + + void Serialize(Serialize::Data &data) const anope_override; + static Serializable* Unserialize(Serializable *obj, Serialize::Data &); + + /** Change the founder of the channel + * @params nc The new founder + */ + void SetFounder(NickCore *nc); + + /** Get the founder of the channel + * @return The founder + */ + NickCore *GetFounder() const; + + void SetSuccessor(NickCore *nc); + NickCore *GetSuccessor() const; + + /** Find which bot should send mode/topic/etc changes for this channel + * @return The bot + */ + BotInfo *WhoSends() const; + + /** Add an entry to the channel access list + * @param access The entry + */ + void AddAccess(ChanAccess *access); + + /** Get an entry from the channel access list by index + * + * @param index The index in the access list vector + * @return A ChanAccess struct corresponding to the index given, or NULL if outside the bounds + * + * Retrieves an entry from the access list that matches the given index. + */ + ChanAccess *GetAccess(unsigned index) const; + + /** Retrieve the access for a user or group in the form of a vector of access entries + * (as multiple entries can affect a single user). + */ + AccessGroup AccessFor(const User *u, bool updateLastUsed = true); + AccessGroup AccessFor(const NickCore *nc, bool updateLastUsed = true); + + /** Get the size of the access vector for this channel + * @return The access vector size + */ + unsigned GetAccessCount() const; + + /** Get the number of access entries for this channel, + * including those that are on other channels. + */ + unsigned GetDeepAccessCount() const; + + /** Erase an entry from the channel access list + * + * @param index The index in the access list vector + * + * @return The erased entry + */ + ChanAccess *EraseAccess(unsigned index); + + /** Clear the entire channel access list + * + * Clears the entire access list by deleting every item and then clearing the vector. + */ + void ClearAccess(); + + /** Add an akick entry to the channel by NickCore + * @param user The user who added the akick + * @param akicknc The nickcore being akicked + * @param reason The reason for the akick + * @param t The time the akick was added, defaults to now + * @param lu The time the akick was last used, defaults to never + */ + AutoKick* AddAkick(const Anope::string &user, NickCore *akicknc, const Anope::string &reason, time_t t = Anope::CurTime, time_t lu = 0); + + /** Add an akick entry to the channel by reason + * @param user The user who added the akick + * @param mask The mask of the akick + * @param reason The reason for the akick + * @param t The time the akick was added, defaults to now + * @param lu The time the akick was last used, defaults to never + */ + AutoKick* AddAkick(const Anope::string &user, const Anope::string &mask, const Anope::string &reason, time_t t = Anope::CurTime, time_t lu = 0); + + /** Get an entry from the channel akick list + * @param index The index in the akick vector + * @return The akick structure, or NULL if not found + */ + AutoKick* GetAkick(unsigned index) const; + + /** Get the size of the akick vector for this channel + * @return The akick vector size + */ + unsigned GetAkickCount() const; + + /** Erase an entry from the channel akick list + * @param index The index of the akick + */ + void EraseAkick(unsigned index); + + /** Clear the whole akick list + */ + void ClearAkick(); + + /** Get the level entries for the channel. + * @return The levels for the channel. + */ + const Anope::map &GetLevelEntries(); + + /** Get the level for a privilege + * @param priv The privilege name + * @return the level + * @throws CoreException if priv is not a valid privilege + */ + int16_t GetLevel(const Anope::string &priv) const; + + /** Set the level for a privilege + * @param priv The privilege priv + * @param level The new level + */ + void SetLevel(const Anope::string &priv, int16_t level); + + /** Remove a privilege from the channel + * @param priv The privilege + */ + void RemoveLevel(const Anope::string &priv); + + /** Clear all privileges from the channel + */ + void ClearLevels(); + + /** Gets a ban mask for the given user based on the bantype + * of the channel. + * @param u The user + * @return A ban mask that affects the user + */ + Anope::string GetIdealBan(User *u) const; + + /** Finds a ChannelInfo + * @param name channel name to lookup + * @return the ChannelInfo associated with the channel + */ + static ChannelInfo* Find(const Anope::string &name); + + void AddChannelReference(const Anope::string &what); + void RemoveChannelReference(const Anope::string &what); + void GetChannelReferences(std::deque &chans); +}; + +/** Is the user the real founder? + * @param user The user + * @param ci The channel + * @return true or false + */ +extern CoreExport bool IsFounder(const User *user, const ChannelInfo *ci); + +#endif // REGCHANNEL_H diff --git a/include/regexpr.h b/include/regexpr.h new file mode 100644 index 0000000..a53df4f --- /dev/null +++ b/include/regexpr.h @@ -0,0 +1,45 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef REGEXPR_H +#define REGEXPR_H + +#include "services.h" +#include "anope.h" +#include "service.h" + +class RegexException : public CoreException +{ + public: + RegexException(const Anope::string &reason = "") : CoreException(reason) { } + + virtual ~RegexException() throw() { } +}; + +class CoreExport Regex +{ + Anope::string expression; + protected: + Regex(const Anope::string &expr) : expression(expr) { } + public: + virtual ~Regex() { } + const Anope::string &GetExpression() { return expression; } + virtual bool Matches(const Anope::string &str) = 0; +}; + +class CoreExport RegexProvider : public Service +{ + public: + RegexProvider(Module *o, const Anope::string &n) : Service(o, "Regex", n) { } + virtual Regex *Compile(const Anope::string &) = 0; +}; + +#endif // REGEXPR_H diff --git a/include/serialize.h b/include/serialize.h new file mode 100644 index 0000000..458dd51 --- /dev/null +++ b/include/serialize.h @@ -0,0 +1,335 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef SERIALIZE_H +#define SERIALIZE_H + +#include + +#include "anope.h" +#include "base.h" + +namespace Serialize +{ + class Data + { + public: + enum Type + { + DT_TEXT, + DT_INT + }; + + virtual ~Data() { } + + virtual std::iostream& operator[](const Anope::string &key) = 0; + virtual std::set KeySet() const { throw CoreException("Not supported"); } + virtual size_t Hash() const { throw CoreException("Not supported"); } + + virtual void SetType(const Anope::string &key, Type t) { } + virtual Type GetType(const Anope::string &key) const { return DT_TEXT; } + }; + + extern void RegisterTypes(); + extern void CheckTypes(); + + class Type; + template class Checker; + template class Reference; +} + +/** A serializable object. Serializable objects can be serialized into + * abstract data types (Serialize::Data), and then reconstructed or + * updated later at any time. + */ +class CoreExport Serializable : public virtual Base +{ + private: + /* A list of every serializable item in Anope. + * Some of these are static and constructed at runtime, + * so this list must be on the heap, as it is not always + * constructed before other objects are if it isn't. + */ + static std::list *SerializableItems; + friend class Serialize::Type; + /* The type of item this object is */ + Serialize::Type *s_type; + /* Iterator into serializable_items */ + std::list::iterator s_iter; + /* The hash of the last serialized form of this object committed to the database */ + size_t last_commit; + /* The last time this object was committed to the database */ + time_t last_commit_time; + + protected: + Serializable(const Anope::string &serialize_type); + Serializable(const Serializable &); + + Serializable &operator=(const Serializable &); + + public: + virtual ~Serializable(); + + /* Unique ID (per type, not globally) for this object */ + uint64_t id; + + /* Only used by redis, to ignore updates */ + unsigned short redis_ignore; + + /** Marks the object as potentially being updated "soon". + */ + void QueueUpdate(); + + bool IsCached(Serialize::Data &); + void UpdateCache(Serialize::Data &); + + bool IsTSCached(); + void UpdateTS(); + + /** Get the type of serializable object this is + * @return The serializable object type + */ + Serialize::Type* GetSerializableType() const { return this->s_type; } + + virtual void Serialize(Serialize::Data &data) const = 0; + + static const std::list &GetItems(); +}; + +/* A serializable type. There should be one of these classes for each type + * of class that inherits from Serializable. Used for unserializing objects + * of this type, as it requires a function pointer to a static member function. + */ +class CoreExport Serialize::Type : public Base +{ + typedef Serializable* (*unserialize_func)(Serializable *obj, Serialize::Data &); + + static std::vector TypeOrder; + static std::map Types; + + /* The name of this type, should be a class name */ + Anope::string name; + unserialize_func unserialize; + /* Owner of this type. Used for placing objects of this type in separate databases + * based on what module, if any, owns it. + */ + Module *owner; + + /* The timestamp for this type. All objects of this type are as up to date as + * this timestamp. if curtime == timestamp then we have the most up to date + * version of every object of this type. + */ + time_t timestamp; + + public: + /* Map of Serializable::id to Serializable objects */ + std::map objects; + + /** Creates a new serializable type + * @param n Type name + * @param f Func to unserialize objects + * @param owner Owner of this type. Leave NULL for the core. + */ + Type(const Anope::string &n, unserialize_func f, Module *owner = NULL); + ~Type(); + + /** Gets the name for this type + * @return The name, eg "NickAlias" + */ + const Anope::string &GetName() { return this->name; } + + /** Unserialized an object. + * @param obj NULL if this object doesn't yet exist. If this isn't NULL, instead + * update the contents of this object. + * @param data The data to unserialize + * @return The unserialized object. If obj != NULL this should be obj. + */ + Serializable *Unserialize(Serializable *obj, Serialize::Data &data); + + /** Check if this object type has any pending changes and update them. + */ + void Check(); + + /** Gets the timestamp for the object type. That is, the time we know + * all objects of this type are updated at least to. + */ + time_t GetTimestamp() const; + + /** Bumps object type timestamp to current time + */ + void UpdateTimestamp(); + + Module* GetOwner() const { return this->owner; } + + static Serialize::Type *Find(const Anope::string &name); + + static const std::vector &GetTypeOrder(); + + static const std::map& GetTypes(); +}; + +/** Should be used to hold lists and other objects of a specific type, + * but not a specific object. Used for ensuring that any access to + * this object type is always up to date. These are usually constructed + * at run time, before main is called, so no types are registered. This + * is why there are static Serialize::Type* variables in every function. + */ +template +class Serialize::Checker +{ + Anope::string name; + T obj; + mutable ::Reference type; + + inline void Check() const + { + if (!type) + type = Serialize::Type::Find(this->name); + if (type) + type->Check(); + } + + public: + Checker(const Anope::string &n) : name(n), type(NULL) { } + + inline const T* operator->() const + { + this->Check(); + return &this->obj; + } + inline T* operator->() + { + this->Check(); + return &this->obj; + } + + inline const T& operator*() const + { + this->Check(); + return this->obj; + } + inline T& operator*() + { + this->Check(); + return this->obj; + } + + inline operator const T&() const + { + this->Check(); + return this->obj; + } + inline operator T&() + { + this->Check(); + return this->obj; + } +}; + +/** Used to hold references to serializable objects. Reference should always be + * used when holding references to serializable objects for extended periods of time + * to ensure that the object it refers to it always up to date. This also behaves like + * Reference in that it will invalidate itself if the object it refers to is + * destructed. + */ +template +class Serialize::Reference : public ReferenceBase +{ + protected: + T *ref; + + public: + Reference() : ref(NULL) + { + } + + Reference(T *obj) : ref(obj) + { + if (obj) + obj->AddReference(this); + } + + Reference(const Reference &other) : ReferenceBase(other), ref(other.ref) + { + if (ref && !invalid) + this->ref->AddReference(this); + } + + ~Reference() + { + if (ref && !invalid) + this->ref->DelReference(this); + } + + inline Reference& operator=(const Reference &other) + { + if (this != &other) + { + if (ref && !invalid) + this->ref->DelReference(this); + + this->ref = other.ref; + this->invalid = other.invalid; + + if (ref && !invalid) + this->ref->AddReference(this); + } + return *this; + } + + inline operator bool() const + { + if (!this->invalid) + return this->ref != NULL; + return false; + } + + inline operator T*() const + { + if (!this->invalid) + { + if (this->ref) + // This can invalidate me + this->ref->QueueUpdate(); + if (!this->invalid) + return this->ref; + } + return NULL; + } + + inline T* operator*() const + { + if (!this->invalid) + { + if (this->ref) + // This can invalidate me + this->ref->QueueUpdate(); + if (!this->invalid) + return this->ref; + } + return NULL; + } + + inline T* operator->() const + { + if (!this->invalid) + { + if (this->ref) + // This can invalidate me + this->ref->QueueUpdate(); + if (!this->invalid) + return this->ref; + } + return NULL; + } +}; + +#endif // SERIALIZE_H diff --git a/include/servers.h b/include/servers.h new file mode 100644 index 0000000..76d0128 --- /dev/null +++ b/include/servers.h @@ -0,0 +1,187 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef SERVERS_H +#define SERVERS_H + +#include "services.h" +#include "anope.h" +#include "extensible.h" + +/* Anope. We are at the top of the server tree, our uplink is + * almost always me->GetLinks()[0]. We never have an uplink. */ +extern CoreExport Server *Me; + +namespace Servers +{ + /* Gets our uplink. Note we don't actually have an "uplink", this is just + * the only server whose uplink *is* Me that is not a juped server. + * @return Our uplink, or NULL if not uplinked to anything + */ + extern CoreExport Server* GetUplink(); + + /* Server maps by name and id */ + extern CoreExport Anope::map ByName; + extern CoreExport Anope::map ByID; + + /* CAPAB/PROTOCTL given by the uplink */ + extern CoreExport std::set Capab; +} + +/** Class representing a server + */ +class CoreExport Server : public Extensible +{ + private: + /* Server name */ + Anope::string name; + /* Hops between services and server */ + unsigned int hops; + /* Server description */ + Anope::string description; + /* Server ID */ + Anope::string sid; + /* Links for this server */ + std::vector links; + /* Uplink for this server */ + Server *uplink; + /* Server is syncing */ + bool syncing; + /* The server is juped */ + bool juped; + /* The server is about to quit */ + bool quitting; + /* Reason this server was quit */ + Anope::string quit_reason; + + public: + /** Constructor + * @param uplink The uplink this server is from, is only NULL when creating Me + * @param name The server name + * @param hops Hops from services server + * @param description Server rdescription + * @param sid Server sid/numeric + * @param jupe If the server is juped + */ + Server(Server *uplink, const Anope::string &name, unsigned hops, const Anope::string &description, const Anope::string &sid = "", bool jupe = false); + + private: + /** Destructor + */ + ~Server(); + + public: + /* Number of users on the server */ + unsigned users; + + /** Delete this server with a reason + * @param reason The reason + */ + void Delete(const Anope::string &reason); + + /** Get the name for this server + * @return The name + */ + const Anope::string &GetName() const; + + /** Get the number of hops this server is from services + * @return Number of hops + */ + unsigned GetHops() const; + + /** Set the server description + * @param desc The new description + */ + void SetDescription(const Anope::string &desc); + + /** Get the server description + * @return The server description + */ + const Anope::string &GetDescription() const; + + /** Change this servers SID + * @param sid The new SID + */ + void SetSID(const Anope::string &sid); + + /** Get the server numeric/SID, else the server name + * @return The numeric/SID + */ + const Anope::string &GetSID() const; + + /** Retrieves the reason this server is quitting + */ + const Anope::string &GetQuitReason() const; + + /** Get the list of links this server has, or NULL if it has none + * @return A list of servers + */ + const std::vector &GetLinks() const; + + /** Get the uplink server for this server, if this is our uplink will be Me + * @return The servers uplink + */ + Server *GetUplink(); + + /** Adds a link to this server + * @param s The linking server + */ + void AddLink(Server *s); + + /** Delinks a server from this server + * @param s The server + */ + void DelLink(Server *s); + + /** Finish syncing this server and optionally all links to it + * @param sync_links True to sync the links for this server too (if any) + */ + void Sync(bool sync_links); + + /** Check if this server is synced + * @return true or false + */ + bool IsSynced() const; + + /** Unsync the server. Only used for Me->Unsync() + */ + void Unsync(); + + /** Check if this server is ULined + * @return true or false + */ + bool IsULined() const; + + /** Check if this server is juped (a pseudoserver other than us) + * @return true if this server is a juped server + */ + bool IsJuped() const; + + /** Check if the server is quitting + * @return true if this server is quitting. + */ + bool IsQuitting() const; + + /** Send a message to all users on this server + * @param source The source of the message + * @param message The message + */ + void Notice(BotInfo *source, const Anope::string &message); + + /** Find a server + * @param name The name or SID/numeric + * @param name_only set to true to only look up by name, not SID + * @return The server + */ + static Server *Find(const Anope::string &name, bool name_only = false); +}; + +#endif // SERVERS_H diff --git a/include/service.h b/include/service.h new file mode 100644 index 0000000..a231923 --- /dev/null +++ b/include/service.h @@ -0,0 +1,173 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef SERVICE_H +#define SERVICE_H + +#include "services.h" +#include "anope.h" +#include "base.h" + +/** Anything that inherits from this class can be referred to + * using ServiceReference. Any interfaces provided by modules, + * such as commands, use this. This is also used for modules + * that publish a service (m_ssl_openssl, etc). + */ +class CoreExport Service : public virtual Base +{ + static std::map > Services; + static std::map > Aliases; + + static Service *FindService(const std::map &services, const std::map *aliases, const Anope::string &n) + { + std::map::const_iterator it = services.find(n); + if (it != services.end()) + return it->second; + + if (aliases != NULL) + { + std::map::const_iterator it2 = aliases->find(n); + if (it2 != aliases->end()) + return FindService(services, aliases, it2->second); + } + + return NULL; + } + + public: + static Service *FindService(const Anope::string &t, const Anope::string &n) + { + std::map >::const_iterator it = Services.find(t); + if (it == Services.end()) + return NULL; + + std::map >::const_iterator it2 = Aliases.find(t); + if (it2 != Aliases.end()) + return FindService(it->second, &it2->second, n); + + return FindService(it->second, NULL, n); + } + + static std::vector GetServiceKeys(const Anope::string &t) + { + std::vector keys; + std::map >::iterator it = Services.find(t); + if (it != Services.end()) + for (std::map::iterator it2 = it->second.begin(); it2 != it->second.end(); ++it2) + keys.push_back(it2->first); + return keys; + } + + static void AddAlias(const Anope::string &t, const Anope::string &n, const Anope::string &v) + { + std::map &smap = Aliases[t]; + smap[n] = v; + } + + static void DelAlias(const Anope::string &t, const Anope::string &n) + { + std::map &smap = Aliases[t]; + smap.erase(n); + if (smap.empty()) + Aliases.erase(t); + } + + Module *owner; + /* Service type, which should be the class name (eg "Command") */ + Anope::string type; + /* Service name, commands are usually named service/command */ + Anope::string name; + + Service(Module *o, const Anope::string &t, const Anope::string &n) : owner(o), type(t), name(n) + { + this->Register(); + } + + virtual ~Service() + { + this->Unregister(); + } + + void Register() + { + std::map &smap = Services[this->type]; + if (smap.find(this->name) != smap.end()) + throw ModuleException("Service " + this->type + " with name " + this->name + " already exists"); + smap[this->name] = this; + } + + void Unregister() + { + std::map &smap = Services[this->type]; + smap.erase(this->name); + if (smap.empty()) + Services.erase(this->type); + } +}; + +/** Like Reference, but used to refer to Services. + */ +template +class ServiceReference : public Reference +{ + Anope::string type; + Anope::string name; + + public: + ServiceReference() { } + + ServiceReference(const Anope::string &t, const Anope::string &n) : type(t), name(n) + { + } + + inline void operator=(const Anope::string &n) + { + this->name = n; + this->invalid = true; + } + + operator bool() anope_override + { + if (this->invalid) + { + this->invalid = false; + this->ref = NULL; + } + if (!this->ref) + { + /* This really could be dynamic_cast in every case, except for when a module + * creates its own service type (that other modules must include the header file + * for), as the core is not compiled with it so there is no RTTI for it. + */ + this->ref = static_cast(::Service::FindService(this->type, this->name)); + if (this->ref) + this->ref->AddReference(this); + } + return this->ref; + } +}; + +class ServiceAlias +{ + Anope::string t, f; + public: + ServiceAlias(const Anope::string &type, const Anope::string &from, const Anope::string &to) : t(type), f(from) + { + Service::AddAlias(type, from, to); + } + + ~ServiceAlias() + { + Service::DelAlias(t, f); + } +}; + +#endif // SERVICE_H diff --git a/include/services.h b/include/services.h new file mode 100644 index 0000000..e012d21 --- /dev/null +++ b/include/services.h @@ -0,0 +1,68 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef SERVICES_H +#define SERVICES_H + +#include "sysconf.h" + +#define BUFSIZE 1024 + +#include +#include +#include +#include + +#include +#if HAVE_STRINGS_H +# include +#endif + +#ifndef _WIN32 +#include +#endif + +/* Pull in the various bits of STL */ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "defs.h" + +#define _(x) x + +#if defined __GXX_EXPERIMENTAL_CXX0X__ || __cplusplus >= 201103L +# define anope_override override +# define anope_final final +#else +# define anope_override +# define anope_final +#endif + +#ifndef _WIN32 +# define DllExport +# define CoreExport +# define MARK_DEPRECATED __attribute((deprecated)) +# define anope_close close +#else +# include "anope_windows.h" +#endif + +#endif // SERVICES_H diff --git a/include/socketengine.h b/include/socketengine.h new file mode 100644 index 0000000..f958eba --- /dev/null +++ b/include/socketengine.h @@ -0,0 +1,50 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef SOCKETENGINE_H +#define SOCKETENGINE_H + +#include "services.h" +#include "sockets.h" + +class CoreExport SocketEngine +{ + static const int DefaultSize = 2; // Uplink, mode stacker + public: + /* Map of sockets */ + static std::map Sockets; + + /** Called to initialize the socket engine + */ + static void Init(); + + /** Called to shutdown the socket engine + */ + static void Shutdown(); + + /** Set a flag on a socket + * @param s The socket + * @param set Whether setting or unsetting + * @param flag The flag to set or unset + */ + static void Change(Socket *s, bool set, SocketFlag flag); + + /** Read from sockets and do things + */ + static void Process(); + + static int GetLastError(); + static void SetLastError(int); + + static bool IgnoreErrno(); +}; + +#endif // SOCKETENGINE_H diff --git a/include/sockets.h b/include/sockets.h new file mode 100644 index 0000000..b8b4200 --- /dev/null +++ b/include/sockets.h @@ -0,0 +1,511 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef SOCKETS_H +#define SOCKETS_H + +#ifndef _WIN32 +#include +#include +#include +#endif + +#include "anope.h" + +#define NET_BUFSIZE 65535 + +/** A sockaddr union used to combine IPv4 and IPv6 sockaddrs + */ +union CoreExport sockaddrs +{ + sockaddr sa; + sockaddr_in sa4; + sockaddr_in6 sa6; + + /** Construct the object, sets everything to 0 + */ + sockaddrs(const Anope::string &address = ""); + + /** Memset the object to 0 + */ + void clear(); + + /** Get address family. + */ + int family() const; + + /** Get the size of the sockaddr we represent + * @return The size + */ + size_t size() const; + + /** Get the port represented by this addr + * @return The port, or -1 on fail + */ + int port() const; + + /** Get the address represented by this addr + * @return The address + */ + Anope::string addr() const; + + /** Get the reverse address represented by this addr + * @return The reverse address + */ + Anope::string reverse() const; + + /* Is this address ipv6? */ + bool ipv6() const; + + /** Check if this sockaddr has data in it + */ + bool valid() const; + + /** Compares with sockaddr with another. Compares address type, port, and address + * @return true if they are the same + */ + bool operator==(const sockaddrs &other) const; + /* The same as above but not */ + inline bool operator!=(const sockaddrs &other) const { return !(*this == other); } + + /** The equivalent of inet_pton + * @param type AF_INET or AF_INET6 + * @param address The address to place in the sockaddr structures + * @param pport An option port to include in the sockaddr structures + * @throws A socket exception if given invalid IPs + */ + void pton(int type, const Anope::string &address, int pport = 0); + + /** The equivalent of inet_ntop + * @param type AF_INET or AF_INET6 + * @param address The in_addr or in_addr6 structure + * @throws A socket exception if given an invalid structure + */ + void ntop(int type, const void *src); +}; + +class CoreExport cidr +{ + sockaddrs addr; + Anope::string cidr_ip; + unsigned short cidr_len; + public: + cidr(const Anope::string &ip); + cidr(const Anope::string &ip, unsigned char len); + cidr(const sockaddrs &ip, unsigned char len); + Anope::string mask() const; + bool match(const sockaddrs &other); + bool valid() const; + + bool operator<(const cidr &other) const; + bool operator==(const cidr &other) const; + bool operator!=(const cidr &other) const; + + struct CoreExport hash + { + size_t operator()(const cidr &s) const; + }; +}; + +class SocketException : public CoreException +{ + public: + /** Constructor for socket exceptions + * @param message Error message + */ + SocketException(const Anope::string &message) : CoreException(message) { } + + /** Destructor + * @throws Nothing + */ + virtual ~SocketException() throw() { } +}; + +enum SocketFlag +{ + SF_DEAD = 1, + SF_READABLE, + SF_WRITABLE, + SF_CONNECTING, + SF_CONNECTED, + SF_ACCEPTING, + SF_ACCEPTED, + SF_SIZE +}; + +class CoreExport SocketIO +{ + public: + virtual ~SocketIO() { } + + /** Receive something from the buffer + * @param s The socket + * @param buf The buf to read to + * @param sz How much to read + * @return Number of bytes received + */ + virtual int Recv(Socket *s, char *buf, size_t sz); + + /** Write something to the socket + * @param s The socket + * @param buf The data to write + * @param size The length of the data + */ + virtual int Send(Socket *s, const char *buf, size_t sz); + int Send(Socket *s, const Anope::string &buf); + + /** Accept a connection from a socket + * @param s The socket + * @return The new socket + */ + virtual ClientSocket *Accept(ListenSocket *s); + + /** Finished accepting a connection from a socket + * @param s The socket + * @return SF_ACCEPTED if accepted, SF_ACCEPTING if still in process, SF_DEAD on error + */ + virtual SocketFlag FinishAccept(ClientSocket *cs); + + /** Bind a socket + * @param s The socket + * @param ip The IP to bind to + * @param port The optional port to bind to + */ + virtual void Bind(Socket *s, const Anope::string &ip, int port = 0); + + /** Connect the socket + * @param s The socket + * @param target IP to connect to + * @param port to connect to + */ + virtual void Connect(ConnectionSocket *s, const Anope::string &target, int port); + + /** Called to potentially finish a pending connection + * @param s The socket + * @return SF_CONNECTED on success, SF_CONNECTING if still pending, and SF_DEAD on error. + */ + virtual SocketFlag FinishConnect(ConnectionSocket *s); + + /** Called when the socket is destructing + */ + virtual void Destroy() { } +}; + +class CoreExport Socket +{ + protected: + /* Socket FD */ + int sock; + /* Is this an IPv6 socket? */ + bool ipv6; + + public: + std::bitset flags; + + /* Sockaddrs for bind() (if it's bound) */ + sockaddrs bindaddr; + + /* I/O functions used for this socket */ + SocketIO *io; + + /** Empty constructor, should not be called. + */ + Socket(); + + /** Constructor, possibly creates the socket and adds it to the engine + * @param sock The socket to use, -1 if we need to create our own + * @param ipv6 true if using ipv6 + * @param type The socket type, defaults to SOCK_STREAM + */ + Socket(int sock, bool ipv6 = false, int type = SOCK_STREAM); + + /** Destructor, closes the socket and removes it from the engine + */ + virtual ~Socket(); + + /** Get the socket FD for this socket + * @return the fd + */ + int GetFD() const; + + /** Check if this socket is IPv6 + * @return true or false + */ + bool IsIPv6() const; + + /** Mark a socket as (non)blocking + * @param state true to enable blocking, false to disable blocking + * @return true if the socket is now blocking + */ + bool SetBlocking(bool state); + + /** Bind the socket to an ip and port + * @param ip The ip + * @param port The port + */ + void Bind(const Anope::string &ip, int port = 0); + + /** Called when there either is a read or write event. + * @return true to continue to call ProcessRead/ProcessWrite, false to not continue + */ + virtual bool Process(); + + /** Called when there is something to be received for this socket + * @return true on success, false to drop this socket + */ + virtual bool ProcessRead(); + + /** Called when the socket is ready to be written to + * @return true on success, false to drop this socket + */ + virtual bool ProcessWrite(); + + /** Called when there is an error for this socket + * @return true on success, false to drop this socket + */ + virtual void ProcessError(); +}; + +class CoreExport BufferedSocket : public virtual Socket +{ + protected: + /* Things read from the socket */ + Anope::string read_buffer; + /* Things to be written to the socket */ + Anope::string write_buffer; + /* How much data was received from this socket on this recv() */ + int recv_len; + + public: + BufferedSocket(); + virtual ~BufferedSocket(); + + /** Called when there is something to be received for this socket + * @return true on success, false to drop this socket + */ + bool ProcessRead() anope_override; + + /** Called when the socket is ready to be written to + * @return true on success, false to drop this socket + */ + bool ProcessWrite() anope_override; + + /** Gets the new line from the input buffer, if any + */ + const Anope::string GetLine(); + + /** Write to the socket + * @param message The message + */ + protected: + virtual void Write(const char *buffer, size_t l); + public: + void Write(const char *message, ...); + void Write(const Anope::string &message); + + /** Get the length of the read buffer + * @return The length of the read buffer + */ + int ReadBufferLen() const; + + /** Get the length of the write buffer + * @return The length of the write buffer + */ + int WriteBufferLen() const; +}; + +class CoreExport BinarySocket : public virtual Socket +{ + protected: + struct DataBlock + { + char *orig; + char *buf; + size_t len; + + DataBlock(const char *b, size_t l); + ~DataBlock(); + }; + + /* Data to be written out */ + std::deque write_buffer; + + public: + BinarySocket(); + virtual ~BinarySocket(); + + /** Called when there is something to be received for this socket + * @return true on success, false to drop this socket + */ + bool ProcessRead() anope_override; + + /** Called when the socket is ready to be written to + * @return true on success, false to drop this socket + */ + bool ProcessWrite() anope_override; + + /** Write data to the socket + * @param buffer The data to write + * @param l The length of the data; if 0 then this function returns without doing anything + */ + virtual void Write(const char *buffer, size_t l); + void Write(const char *message, ...); + void Write(const Anope::string &message); + + /** Called with data from the socket + * @param buffer The data + * @param l The length of buffer + * @return true to continue reading, false to drop the socket + */ + virtual bool Read(const char *buffer, size_t l); +}; + +class CoreExport ListenSocket : public virtual Socket +{ + public: + /** Constructor + * @param bindip The IP to bind to + * @param port The port to listen on + * @param ipv6 true for ipv6 + */ + ListenSocket(const Anope::string &bindip, int port, bool ipv6); + virtual ~ListenSocket(); + + /** Process what has come in from the connection + * @return false to destroy this socket + */ + bool ProcessRead(); + + /** Called when a connection is accepted + * @param fd The FD for the new connection + * @param addr The sockaddr for where the connection came from + * @return The new socket + */ + virtual ClientSocket *OnAccept(int fd, const sockaddrs &addr) = 0; +}; + +class CoreExport ConnectionSocket : public virtual Socket +{ + public: + /* Sockaddrs for connection ip/port */ + sockaddrs conaddr; + + /** Connect the socket + * @param TargetHost The target host to connect to + * @param Port The target port to connect to + */ + void Connect(const Anope::string &TargetHost, int Port); + + /** Called when there either is a read or write event. + * Used to determine whether or not this socket is connected yet. + * @return true to continue to call ProcessRead/ProcessWrite, false to not continue + */ + bool Process() anope_override; + + /** Called when there is an error for this socket + * @return true on success, false to drop this socket + */ + void ProcessError() anope_override; + + /** Called on a successful connect + */ + virtual void OnConnect(); + + /** Called when a connection is not successful + * @param error The error + */ + virtual void OnError(const Anope::string &error); +}; + +class CoreExport ClientSocket : public virtual Socket +{ + public: + /* Listen socket this connection came from */ + ListenSocket *ls; + /* Clients address */ + sockaddrs clientaddr; + + /** Constructor + * @param ls Listen socket this connection is from + * @param addr Address the connection came from + */ + ClientSocket(ListenSocket *ls, const sockaddrs &addr); + + /** Called when there either is a read or write event. + * Used to determine whether or not this socket is connected yet. + * @return true to continue to call ProcessRead/ProcessWrite, false to not continue + */ + bool Process() anope_override; + + /** Called when there is an error for this socket + * @return true on success, false to drop this socket + */ + void ProcessError() anope_override; + + /** Called when a client has been accepted() successfully. + */ + virtual void OnAccept(); + + /** Called when there was an error accepting the client + */ + virtual void OnError(const Anope::string &error); +}; + +class CoreExport Pipe : public Socket +{ + public: + /** The FD of the write pipe + * this->sock is the readfd + */ + int write_pipe; + + Pipe(); + ~Pipe(); + + /** Called when data is to be read, reads the data then calls OnNotify + */ + bool ProcessRead() anope_override; + + /** Write data to this pipe + * @param data The data to write + * @param sz The amount of data to wirite + */ + void Write(const char *data, size_t sz); + inline void Write(const Anope::string &data) { this->Write(data.c_str(), data.length() + 1); } + + /** Read data from this pipe + * @param data A buffer to read data into + * @param sz The size of the buffer + * @return The amount of data read + */ + int Read(char *data, size_t sz); + + /** Mark the write end of this pipe (non)blocking + * @param state true to enable blocking, false to disable blocking + * @return true if the socket is now blocking + */ + bool SetWriteBlocking(bool state); + + /** Called when this pipe needs to be woken up + * Is the same as Write("\0", 1) + */ + void Notify(); + + /** Called after ProcessRead comes back from Notify(), overload to do something useful + */ + virtual void OnNotify() = 0; +}; + +extern CoreExport uint32_t TotalRead; +extern CoreExport uint32_t TotalWritten; +extern CoreExport SocketIO NormalSocketIO; + +#endif // SOCKET_H diff --git a/include/sysconf.h.cmake b/include/sysconf.h.cmake new file mode 100644 index 0000000..5f0e275 --- /dev/null +++ b/include/sysconf.h.cmake @@ -0,0 +1,47 @@ +#ifndef _SYSCONF_H_ +#define _SYSCONF_H_ + +#cmakedefine DEBUG_BUILD + +#cmakedefine DEFUMASK @DEFUMASK@ +#cmakedefine HAVE_CSTDINT 1 +#cmakedefine HAVE_STDINT_H 1 +#cmakedefine HAVE_STDDEF_H 1 +#cmakedefine HAVE_STRCASECMP 1 +#cmakedefine HAVE_STRICMP 1 +#cmakedefine HAVE_STRINGS_H 1 +#cmakedefine HAVE_UMASK 1 +#cmakedefine HAVE_EVENTFD 1 +#cmakedefine HAVE_EPOLL 1 +#cmakedefine HAVE_POLL 1 +#cmakedefine GETTEXT_FOUND 1 + +#ifdef HAVE_CSTDINT +# include +#else +# ifdef HAVE_STDINT_H +# include +# else +# include "pstdint.h" +# endif +#endif +#ifdef HAVE_STDDEF_H +# include +#endif + +#ifdef _WIN32 +# define popen _popen +# define pclose _pclose +# define ftruncate _chsize +# ifdef MSVCPP +# define PATH_MAX MAX_PATH +# endif +# define MAXPATHLEN MAX_PATH +# define bzero(buf, size) memset(buf, 0, size) +# ifdef MSVCPP +# define strcasecmp stricmp +# endif +# define sleep(x) Sleep(x * 1000) +#endif + +#endif diff --git a/include/threadengine.h b/include/threadengine.h new file mode 100644 index 0000000..864bd8a --- /dev/null +++ b/include/threadengine.h @@ -0,0 +1,120 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef THREADENGINE_H +#define THREADENGINE_H + +#include "sockets.h" +#include "extensible.h" + +class CoreExport Thread : public Pipe, public Extensible +{ + private: + /* Set to true to tell the thread to finish and we are waiting for it */ + bool exit; + + public: + /* Handle for this thread */ + pthread_t handle; + + /** Threads constructor + */ + Thread(); + + /** Threads destructor + */ + virtual ~Thread(); + + /** Join to the thread, sets the exit state to true + */ + void Join(); + + /** Sets the exit state as true informing the thread we want it to shut down + */ + void SetExitState(); + + /** Exit the thread. Note that the thread still must be joined to free resources! + */ + void Exit(); + + /** Launch the thread + */ + void Start(); + + /** Returns the exit state of the thread + * @return true if we want to exit + */ + bool GetExitState() const; + + /** Called when this thread should be joined to + */ + void OnNotify(); + + /** Called when the thread is run. + */ + virtual void Run() = 0; +}; + +class CoreExport Mutex +{ + protected: + /* A mutex, used to keep threads in sync */ + pthread_mutex_t mutex; + + public: + /** Constructor + */ + Mutex(); + + /** Destructor + */ + ~Mutex(); + + /** Attempt to lock the mutex, will hang until a lock can be achieved + */ + void Lock(); + + /** Unlock the mutex, it must be locked first + */ + void Unlock(); + + /** Attempt to lock the mutex, will return true on success and false on fail + * Does not block + * @return true or false + */ + bool TryLock(); +}; + +class CoreExport Condition : public Mutex +{ + private: + /* A condition */ + pthread_cond_t cond; + + public: + /** Constructor + */ + Condition(); + + /** Destructor + */ + ~Condition(); + + /** Called to wakeup the waiter + */ + void Wakeup(); + + /** Called to wait for a Wakeup() call + */ + void Wait(); +}; + +#endif // THREADENGINE_H diff --git a/include/timers.h b/include/timers.h new file mode 100644 index 0000000..a8e913f --- /dev/null +++ b/include/timers.h @@ -0,0 +1,131 @@ +/* Timer include stuff. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef TIMERS_H +#define TIMERS_H + +#include "anope.h" + +class CoreExport Timer +{ + private: + /** The owner of the timer, if any + */ + Module *owner; + + /** The time this was created + */ + time_t settime; + + /** The triggering time + */ + time_t trigger; + + /** Numer of seconds between triggers + */ + long secs; + + /** True if this is a repeating timer + */ + bool repeat; + + public: + /** Constructor, initializes the triggering time + * @param time_from_now The number of seconds from now to trigger the timer + * @param now The time now + * @param repeating Repeat this timer every time_from_now if this is true + */ + Timer(long time_from_now, time_t now = Anope::CurTime, bool repeating = false); + + /** Constructor, initializes the triggering time + * @param creator The creator of the timer + * @param time_from_now The number of seconds from now to trigger the timer + * @param now The time now + * @param repeating Repeat this timer every time_from_now if this is true + */ + Timer(Module *creator, long time_from_now, time_t now = Anope::CurTime, bool repeating = false); + + /** Destructor, removes the timer from the list + */ + virtual ~Timer(); + + /** Set the trigger time to a new value + * @param t The new time + */ + void SetTimer(time_t t); + + /** Retrieve the triggering time + * @return The trigger time + */ + time_t GetTimer() const; + + /** Returns true if the timer is set to repeat + * @return Returns true if the timer is set to repeat + */ + bool GetRepeat() const; + + /** Set the interval between ticks + * @paramt t The new interval + */ + void SetSecs(time_t t); + + /** Returns the interval between ticks + * @return The interval + */ + long GetSecs() const; + + /** Returns the time this timer was created + * @return The time this timer was created + */ + time_t GetSetTime() const; + + /** Returns the owner of this timer, if any + * @return The owner of the timer + */ + Module *GetOwner() const; + + /** Called when the timer ticks + * This should be overridden with something useful + */ + virtual void Tick(time_t ctime) = 0; +}; + +/** This class manages sets of Timers, and triggers them at their defined times. + * This will ensure timers are not missed, as well as removing timers that have + * expired and allowing the addition of new ones. + */ +class CoreExport TimerManager +{ + /** A list of timers + */ + static std::multimap Timers; + public: + /** Add a timer to the list + * @param t A Timer derived class to add + */ + static void AddTimer(Timer *t); + + /** Deletes a timer + * @param t A Timer derived class to delete + */ + static void DelTimer(Timer *t); + + /** Tick all pending timers + * @param ctime The current time + */ + static void TickTimers(time_t ctime = Anope::CurTime); + + /** Deletes all timers owned by the given module + */ + static void DeleteTimersFor(Module *m); +}; + +#endif // TIMERS_H diff --git a/include/uplink.h b/include/uplink.h new file mode 100644 index 0000000..58ce20b --- /dev/null +++ b/include/uplink.h @@ -0,0 +1,53 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef UPLINK_H +#define UPLINK_H + +#include "sockets.h" +#include "protocol.h" + +namespace Uplink +{ + extern void Connect(); +} + +/* This is the socket to our uplink */ +class UplinkSocket : public ConnectionSocket, public BufferedSocket +{ + public: + bool error; + UplinkSocket(); + ~UplinkSocket(); + bool ProcessRead() anope_override; + void OnConnect() anope_override; + void OnError(const Anope::string &) anope_override; + + /* A message sent over the uplink socket */ + class CoreExport Message + { + MessageSource source; + std::stringstream buffer; + + public: + Message(); + Message(const MessageSource &); + ~Message(); + template Message &operator<<(const T &val) + { + this->buffer << val; + return *this; + } + }; +}; +extern CoreExport UplinkSocket *UplinkSock; + +#endif // UPLINK_H diff --git a/include/users.h b/include/users.h new file mode 100644 index 0000000..150b47e --- /dev/null +++ b/include/users.h @@ -0,0 +1,374 @@ +/* + * + * (C) 2008-2011 Robin Burchell + * (C) 2003-2022 Anope Team + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef USERS_H +#define USERS_H + +#include "anope.h" +#include "modes.h" +#include "extensible.h" +#include "serialize.h" +#include "commands.h" +#include "account.h" +#include "sockets.h" + +typedef Anope::hash_map user_map; + +extern CoreExport user_map UserListByNick, UserListByUID; + +extern CoreExport int OperCount; +extern CoreExport unsigned MaxUserCount; +extern CoreExport time_t MaxUserTime; + +/* Online user and channel data. */ +class CoreExport User : public virtual Base, public Extensible, public CommandReply +{ + /* true if the user was quit or killed */ + bool quit; + /* Users that are in the process of quitting */ + static std::list quitting_users; + + public: + typedef std::map ModeList; + protected: + Anope::string vident; + Anope::string ident; + Anope::string uid; + /* If the user is on the access list of the nick they're on */ + bool on_access; + /* Map of user modes and the params this user has (if any) */ + ModeList modes; + /* NickCore account the user is currently logged in as, if they are logged in */ + Serialize::Reference nc; + + /* # of invalid password attempts */ + unsigned short invalid_pw_count; + /* Time of last invalid password */ + time_t invalid_pw_time; + + + public: // XXX: exposing a tiny bit too much + /* User's current nick */ + Anope::string nick; + + /* User's real hostname */ + Anope::string host; + /* User's virtual hostname */ + Anope::string vhost; + /* User's cloaked hostname */ + Anope::string chost; + /* Realname */ + Anope::string realname; + /* SSL Fingerprint */ + Anope::string fingerprint; + /* User's IP */ + sockaddrs ip; + /* Server user is connected to */ + Server *server; + /* When the user signed on. Set on connect and never modified. */ + time_t signon; + /* Timestamp of the nick. Updated when the nick changes. */ + time_t timestamp; + /* Is the user as super admin? */ + bool super_admin; + + /* Channels the user is in */ + typedef std::map ChanUserList; + ChanUserList chans; + + /* Last time this user sent a memo command used */ + time_t lastmemosend; + /* Last time this user registered */ + time_t lastnickreg; + /* Last time this user sent an email */ + time_t lastmail; + + protected: + /** Create a new user object, initialising necessary fields and + * adds it to the hash + * + * @param snick The nickname of the user. + * @param sident The username of the user + * @param shost The hostname of the user + * @param svhost The vhost of the user + * @param sip The ip of the user + * @param sserver The server of the user + * @param srealname The realname/gecos of the user + * @param ts User's timestamp + * @param smodes User's modes + * @param suid The unique identifier of the user. + * @param nc The account the user is identified as, if any + */ + User(const Anope::string &snick, const Anope::string &sident, const Anope::string &shost, const Anope::string &svhost, const Anope::string &sip, Server *sserver, const Anope::string &srealname, time_t ts, const Anope::string &smodes, const Anope::string &suid, NickCore *nc); + + /** Destroy a user. + */ + virtual ~User(); + + public: + static User* OnIntroduce(const Anope::string &snick, const Anope::string &sident, const Anope::string &shost, const Anope::string &svhost, const Anope::string &sip, Server *sserver, const Anope::string &srealname, time_t ts, const Anope::string &smodes, const Anope::string &suid, NickCore *nc); + + /** Update the nickname of a user record accordingly, should be + * called from ircd protocol. + * @param newnick The new username + * @param ts The time the nick was changed, User::timestamp will be updated to this. + */ + void ChangeNick(const Anope::string &newnick, time_t ts = Anope::CurTime); + + /** Update the displayed (vhost) of a user record. + * This is used (if set) instead of real host. + * @param host The new displayed host to give the user. + */ + void SetDisplayedHost(const Anope::string &host); + + /** Get the displayed vhost of a user record. + * @return The displayed vhost of the user, where ircd-supported, or the user's real host. + */ + const Anope::string &GetDisplayedHost() const; + + /** Update the cloaked host of a user + * @param host The cloaked host + */ + void SetCloakedHost(const Anope::string &newhost); + + /** Get the cloaked host of a user + * @return The cloaked host + */ + const Anope::string &GetCloakedHost() const; + + /** Retrieves the UID of the user, if set, else the nick. + * @return The UID of the user. + */ + const Anope::string &GetUID() const; + + /** Update the displayed ident (username) of a user record. + * @param ident The new ident to give this user. + */ + void SetVIdent(const Anope::string &ident); + + /** Get the displayed ident (username) of this user. + * @return The displayed ident of this user. + */ + const Anope::string &GetVIdent() const; + + /** Update the real ident (username) of a user record. + * @param ident The new ident to give this user. + * NOTE: Where possible, you should use the Get/SetVIdent() equivalents. + */ + void SetIdent(const Anope::string &ident); + + /** Get the real ident (username) of this user. + * @return The displayed ident of this user. + * NOTE: Where possible, you should use the Get/SetVIdent() equivalents. + */ + const Anope::string &GetIdent() const; + + /** Get the full mask (nick!ident@realhost) of a user + */ + Anope::string GetMask() const; + + /** Get the full display mask (nick!vident@vhost/chost) + */ + Anope::string GetDisplayedMask() const; + + /** Updates the realname of the user record. + */ + void SetRealname(const Anope::string &realname); + + /** + * Send a message (notice or privmsg, depending on settings) to a user + * @param source Sender + * @param fmt Format of the Message + * @param ... any number of parameters + */ + void SendMessage(BotInfo *source, const char *fmt, ...); + void SendMessage(BotInfo *source, const Anope::string &msg) anope_override; + + /** Identify the user to a nick. + * updates last_seen, logs the user in, + * send messages, checks for mails, set vhost and more + * @param na the nick to identify to, should be the same as + * the user's current nick + */ + void Identify(NickAlias *na); + + /** Login the user to an account + * @param core The account + */ + void Login(NickCore *core); + + /** Logout the user + */ + void Logout(); + + /** Get the account the user is logged in using + * @return The account or NULL + */ + NickCore *Account() const; + + /** Check if the user is identified for their nick + * @param check_nick True to check if the user is identified to the nickname they are on too + * @return true or false + */ + bool IsIdentified(bool check_nick = false) const; + + /** Check if the user is recognized for their nick (on the nicks access list) + * @param check_secure Only returns true if the user has secure off + * @return true or false + */ + bool IsRecognized(bool check_secure = true) const; + + /** Check if the user is a services oper + * @return true if they are an oper + */ + bool IsServicesOper(); + + /** Check whether this user has access to run the given command string. + * @param cmdstr The string to check, e.g. botserv/set/private. + * @return True if this user may run the specified command, false otherwise. + */ + bool HasCommand(const Anope::string &cmdstr); + + /** Check whether this user has access to the given special permission. + * @param privstr The priv to check for, e.g. users/auspex. + * @return True if this user has the specified priv, false otherwise. + */ + bool HasPriv(const Anope::string &privstr); + + /** Update the last usermask stored for a user, and check to see if they are recognized + */ + void UpdateHost(); + + /** Check if the user has a mode + * @param name Mode name + * @return true or false + */ + bool HasMode(const Anope::string &name) const; + + /** Set a mode internally on the user, the IRCd is not informed + * @param setter who/what is setting the mode + * @param um The user mode + * @param Param The param, if there is one + */ + void SetModeInternal(const MessageSource &setter, UserMode *um, const Anope::string ¶m = ""); + + /** Remove a mode internally on the user, the IRCd is not informed + * @param setter who/what is setting the mode + * @param um The user mode + */ + void RemoveModeInternal(const MessageSource &setter, UserMode *um); + + /** Set a mode on the user + * @param bi The client setting the mode + * @param um The user mode + * @param Param Optional param for the mode + */ + void SetMode(BotInfo *bi, UserMode *um, const Anope::string ¶m = ""); + + /** Set a mode on the user + * @param bi The client setting the mode + * @param name The mode name + * @param Param Optional param for the mode + */ + void SetMode(BotInfo *bi, const Anope::string &name, const Anope::string ¶m = ""); + + /** Remove a mode on the user + * @param bi The client setting the mode + * @param um The user mode + * @param param Optional param for the mode + */ + void RemoveMode(BotInfo *bi, UserMode *um, const Anope::string ¶m = ""); + + /** Remove a mode from the user + * @param bi The client setting the mode + * @param name The mode name + * @param param Optional param for the mode + */ + void RemoveMode(BotInfo *bi, const Anope::string &name, const Anope::string ¶m = ""); + + /** Set a string of modes on a user + * @param bi The client setting the modes + * @param umodes The modes + */ + void SetModes(BotInfo *bi, const char *umodes, ...); + + /** Set a string of modes on a user internally + * @param setter who/what is setting the mode + * @param umodes The modes + */ + void SetModesInternal(const MessageSource &source, const char *umodes, ...); + + /** Get modes set for this user. + * @return A string of modes set on the user + */ + Anope::string GetModes() const; + + const ModeList &GetModeList() const; + + /** Find the channel container for Channel c that the user is on + * This is preferred over using FindUser in Channel, as there are usually more users in a channel + * than channels a user is in + * @param c The channel + * @return The channel container, or NULL + */ + ChanUserContainer *FindChannel(Channel *c) const; + + /** Check if the user is protected from kicks and negative mode changes + * @return true or false + */ + bool IsProtected(); + + /** Kill a user + * @param source The user/server doing the kill + * @param reason The reason for the kill + */ + void Kill(const MessageSource &source, const Anope::string &reason); + + /** Process a kill for a user + * @param source The user/server doing the kill + * @param reason The reason for the kill + */ + void KillInternal(const MessageSource &source, const Anope::string &reason); + + /** Processes a quit for the user, and marks them as quit + * @param reason The reason for the quit + */ + void Quit(const Anope::string &reason = ""); + + bool Quitting() const; + + /* Returns a mask that will most likely match any address the + * user will have from that location. For IP addresses, wildcards the + * last octet (e.g. 35.1.1.1 -> 35.1.1.*). for named addresses, wildcards + * the leftmost part of the name unless the name only contains two parts. + * If the username begins with a ~, replace with *. + */ + Anope::string Mask() const; + + /** Notes the usage of an incorrect password. If too many + * incorrect passwords are used the user might be killed. + * @return true if the user was killed + */ + bool BadPassword(); + + /** Finds a user by nick, or possibly UID + * @param name The nick, or possibly UID, to lookup + * @param nick_only set to true to only look up by nick, not UID + * @return the user, if they exist + */ + static User* Find(const Anope::string &name, bool nick_only = false); + + /** Quits all users who are pending to be quit + */ + static void QuitUsers(); +}; + +#endif // USERS_H diff --git a/include/version.cpp b/include/version.cpp new file mode 100644 index 0000000..8329d7b --- /dev/null +++ b/include/version.cpp @@ -0,0 +1,188 @@ +/* Build bumper + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include +#include +#include +#include +#include + +static std::string get_git_hash(const std::string &git_dir) +{ + std::fstream fd; + std::string filebuf; + + fd.open((git_dir + "/HEAD").c_str(), std::ios::in); + if (!fd.is_open()) + return ""; + if (!getline(fd, filebuf) || filebuf.find("ref: ") != 0) + { + fd.close(); + return ""; + } + + fd.close(); + + filebuf = filebuf.substr(5); + fd.open((git_dir + "/" + filebuf).c_str(), std::ios::in); + if (!fd.is_open()) + return ""; + if (!getline(fd, filebuf)) + { + fd.close(); + return ""; + } + fd.close(); + + return "g" + filebuf.substr(0, 7); +} + +static bool read_version_sh(const std::string &version_sh, std::map &versions) +{ + std::fstream fd(version_sh.c_str(), std::ios::in); + if (!fd.is_open()) + { + std::cerr << "Error: Unable to open src/version.sh for reading: " << version_sh << std::endl; + return false; + } + + std::string filebuf; + while (getline(fd, filebuf)) + { + if (!filebuf.find("VERSION_")) + { + size_t eq = filebuf.find('='); + + std::string type = filebuf.substr(0, eq); + std::string value = filebuf.substr(eq + 1); + + versions[type] = value; + } + } + + fd.close(); + + return true; +} + +static bool write_build_h(const std::string &buildh, const std::string &git_version) +{ + std::fstream fd(buildh.c_str(), std::ios::in); + + std::string build = "#define BUILD 1"; + if (fd.is_open()) + { + for (std::string filebuf; getline(fd, filebuf);) + { + if (!filebuf.find("#define BUILD")) + { + size_t tab = filebuf.find(' '); + + int ibuild = atoi(filebuf.substr(tab + 1).c_str()) + 1; + + std::stringstream ss; + ss << "#define BUILD " << ibuild; + build = ss.str(); + } + } + + fd.close(); + } + + fd.clear(); + fd.open(buildh.c_str(), std::ios::out); + if (!fd.is_open()) + { + std::cerr << "Error: Unable to open build.h for writing: " << buildh << std::endl; + return false; + } + + fd << "/* This file is automatically generated by version.cpp - do not edit it! */" << std::endl; + fd << build << std::endl; + if (!git_version.empty()) + fd << "#define VERSION_GIT \"" << git_version << "\"" << std::endl; + fd.close(); + + return true; +} + +static void read_version_h(const std::string &versionh, std::map &versions) +{ + std::fstream fd(versionh.c_str(), std::ios::in); + + if (!fd.is_open()) + return; + + for (std::string filebuf; getline(fd, filebuf);) + { + if (!filebuf.find("#define VERSION_")) + { + size_t space = filebuf.substr(8).find(' '); + + std::string name = filebuf.substr(8).substr(0, space), + version = filebuf.substr(8).substr(space + 1); + + versions[name] = version; + } + } + + fd.close(); +} + +static bool write_version_h(const std::string &versionh, const std::map &versions) +{ + std::fstream fd(versionh.c_str(), std::ios::out); + + if (!fd.is_open()) + return false; + + for (std::map::const_iterator it = versions.begin(); it != versions.end(); ++it) + { + fd << "#define " << it->first << " " << it->second << std::endl; + } + + fd.close(); + + return true; +} + +int main(int argc, char *argv[]) +{ + if (argc < 4) + { + std::cerr << "Syntax: " << argv[0] << " " << std::endl; + return 1; + } + + std::string version_sh = std::string(argv[1]) + "/src/version.sh"; + std::string git_dir = std::string(argv[1]) + "/.git"; + std::string versionh = argv[2]; + std::string buildh = argv[3]; + + std::map versions, old_versions; + + if (!read_version_sh(version_sh, versions)) + return -1; + + std::string git_version = get_git_hash(git_dir); + if (!write_build_h(buildh, git_version)) + return -1; + + read_version_h(versionh, old_versions); + + if (versions == old_versions) + return 0; + + if (!write_version_h(versionh, versions)) + return -1; + + return 0; +} diff --git a/include/xline.h b/include/xline.h new file mode 100644 index 0000000..5eed177 --- /dev/null +++ b/include/xline.h @@ -0,0 +1,184 @@ +/* + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#ifndef XLINE_H +#define XLINE_H + +#include "serialize.h" +#include "service.h" +#include "sockets.h" + +/* An Xline, eg, anything added with operserv/akill, or any of the operserv/sxline commands */ +class CoreExport XLine : public Serializable +{ + void Init(); + Anope::string nick, user, host, real; + public: + cidr *c; + Anope::string mask; + Regex *regex; + Anope::string by; + time_t created; + time_t expires; + Anope::string reason; + XLineManager *manager; + Anope::string id; + + XLine(const Anope::string &mask, const Anope::string &reason = "", const Anope::string &uid = ""); + + XLine(const Anope::string &mask, const Anope::string &by, const time_t expires, const Anope::string &reason, const Anope::string &uid = ""); + ~XLine(); + + const Anope::string &GetNick() const; + const Anope::string &GetUser() const; + const Anope::string &GetHost() const; + const Anope::string &GetReal() const; + + Anope::string GetReason() const; + + bool HasNickOrReal() const; + bool IsRegex() const; + + void Serialize(Serialize::Data &data) const anope_override; + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data); +}; + +/* Managers XLines. There is one XLineManager per type of XLine. */ +class CoreExport XLineManager : public Service +{ + char type; + /* List of XLines in this XLineManager */ + Serialize::Checker > xlines; + /* Akills can have the same IDs, sometimes */ + static Serialize::Checker > XLinesByUID; + public: + /* List of XLine managers we check users against in XLineManager::CheckAll */ + static std::list XLineManagers; + + /** Register a XLineManager, places it in XLineManagers for use in XLineManager::CheckAll + * It is important XLineManagers are registered in the proper order. Eg, if you had one akilling + * clients and one handing them free olines, you would want the akilling one first. This way if a client + * matches an entry on both of the XLineManagers, they would be akilled. + * @param xlm THe XLineManager + */ + static void RegisterXLineManager(XLineManager *xlm); + + /** Unregister a XLineManager + * @param xlm The XLineManager + */ + static void UnregisterXLineManager(XLineManager *xlm); + + /** Check a user against all known XLineManagers + * Wparam u The user + * @return A pair of the XLineManager the user was found in and the XLine they matched, both may be NULL for no match + */ + static void CheckAll(User *u); + + /** Generate a unique ID for this XLine + * @return A unique ID + */ + static Anope::string GenerateUID(); + + /** Constructor + */ + XLineManager(Module *creator, const Anope::string &name, char t); + + /** Destructor + */ + virtual ~XLineManager(); + + /** The type of xline provided by this service + * @return The type + */ + const char &Type(); + + /** Get the number of XLines in this XLineManager + * @return The number of XLines + */ + size_t GetCount() const; + + /** Get the XLine vector + * @return The vector + */ + const std::vector &GetList() const; + + /** Add an entry to this XLineManager + * @param x The entry + */ + void AddXLine(XLine *x); + + void RemoveXLine(XLine *); + + /** Delete an entry from this XLineManager + * @param x The entry + * @return true if the entry was found and deleted, else false + */ + bool DelXLine(XLine *x); + + /** Gets an entry by index + * @param index The index + * @return The XLine, or NULL if the index is out of bounds + */ + XLine* GetEntry(unsigned index); + + /** Clear the XLine vector + * Note: This does not remove the XLines from the IRCd + */ + void Clear(); + + /** Checks if a mask can/should be added to the XLineManager + * @param source The source adding the mask. + * @param mask The mask + * @param expires When the mask would expire + * @param reason the reason + * @return true if the mask can be added + */ + bool CanAdd(CommandSource &source, const Anope::string &mask, time_t expires, const Anope::string &reason); + + /** Checks if this list has an entry + * @param mask The mask + * @return The XLine the user matches, or NULL + */ + XLine* HasEntry(const Anope::string &mask); + + /** Check a user against all of the xlines in this XLineManager + * @param u The user + * @return The xline the user marches, if any. + */ + XLine *CheckAllXLines(User *u); + + /** Check a user against an xline + * @param u The user + * @param x The xline + */ + virtual bool Check(User *u, const XLine *x) = 0; + + /** Called when a user matches a xline in this XLineManager + * @param u The user + * @param x The XLine they match + */ + virtual void OnMatch(User *u, XLine *x) = 0; + + /** Called when an XLine expires + * @param x The xline + */ + virtual void OnExpire(const XLine *x); + + /** Called to send an XLine to the IRCd + * @param u The user, if we know it + * @param x The xline + */ + virtual void Send(User *u, XLine *x) = 0; + + /** Called to remove an XLine from the IRCd + * @param x The XLine + */ + virtual void SendDel(XLine *x) = 0; +}; + +#endif // XLINE_H diff --git a/language/CMakeLists.txt b/language/CMakeLists.txt new file mode 100644 index 0000000..577e132 --- /dev/null +++ b/language/CMakeLists.txt @@ -0,0 +1,37 @@ +# Only do this if gettext is installed +if(GETTEXT_FOUND) + # Get all of the .po files + file(GLOB LANG_SRCS_PO RELATIVE ${CMAKE_CURRENT_SOURCE_DIR} "*.*.po") + sort_list(LANG_SRCS_PO) + + foreach(LANG_PO ${LANG_SRCS_PO}) + # Get the domain for this language file + string(LENGTH ${LANG_PO} LANG_PO_LENGTH) + math(EXPR DOMAIN_LENGTH "${LANG_PO_LENGTH} - 9") + string(SUBSTRING ${LANG_PO} 0 ${DOMAIN_LENGTH} LANG_DOMAIN) + + # Get the language for this language file + math(EXPR DOMAIN_LENGTH "${LANG_PO_LENGTH} - 8") + string(SUBSTRING ${LANG_PO} ${DOMAIN_LENGTH} 5 LANG_LANG) + + # Get the .mo file name + string(REGEX REPLACE "\\.po$" ".mo" LANG_MO ${LANG_PO}) + # Add the .mo file to a list for use later with add_custom_target + set(LANG_SRCS_MO ${LANG_SRCS_MO} ${CMAKE_CURRENT_BINARY_DIR}/${LANG_MO}) + # Run msgfmt on the language file, depends on the .po file + add_custom_command(OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/${LANG_MO} + COMMAND ${GETTEXT_MSGFMT_EXECUTABLE} -c ${CMAKE_CURRENT_SOURCE_DIR}/${LANG_PO} -o ${CMAKE_CURRENT_BINARY_DIR}/${LANG_MO} + MAIN_DEPENDENCY ${LANG_PO} + ) + # Add to cpack ignored files if not on Windows. + if(NOT WIN32) + add_to_cpack_ignored_files("${LANG_MO}") + endif(NOT WIN32) + + # Install the new language file + install(FILES ${CMAKE_CURRENT_BINARY_DIR}/${LANG_MO} DESTINATION ${LOCALE_DIR}/${LANG_LANG}/LC_MESSAGES RENAME ${LANG_DOMAIN}.mo PERMISSIONS ${PERMS}) + endforeach(LANG_PO) + + # Generate languages, depends on the mo files + add_custom_target(language DEPENDS ${LANG_SRCS_MO}) +endif(GETTEXT_FOUND) diff --git a/language/anope.ca_ES.po b/language/anope.ca_ES.po new file mode 100644 index 0000000..d713785 --- /dev/null +++ b/language/anope.ca_ES.po @@ -0,0 +1,11920 @@ +# Anope IRC Services language file +# Copyright (C) 2011 +# This file is distributed under the same license as the Anope IRC Services package. +# Adam , 2011. +# +msgid "" +msgstr "" +"Project-Id-Version: Anope\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2020-01-06 18:19+0100\n" +"PO-Revision-Date: 2010-09-19 20:12-0400\n" +"Last-Translator: Adam \n" +"Language-Team: Catalan\n" +"Language: ca_ES\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" + +#: modules/commands/os_forbid.cpp:324 +#, c-format +msgid "%d channel(s) cleared, and %d channel(s) dropped." +msgstr "" + +#: modules/commands/os_forbid.cpp:265 +#, fuzzy, c-format +msgid "%d nickname(s) dropped." +msgstr "El teu nickname ha estat expulsat." + +#: modules/commands/cs_xop.cpp:219 +#, fuzzy, c-format +msgid "%s added to %s %s list." +msgstr "%s afegit a la llista de AKILLs." + +#: modules/commands/cs_access.cpp:225 +#, c-format +msgid "%s added to %s access list at level %d." +msgstr "%s afegit a la llista d'accés de %s amb nivel %d." + +#: modules/commands/cs_access.cpp:223 +#, fuzzy, c-format +msgid "%s added to %s access list at privilege %s (level %d)" +msgstr "%s afegit a la llista d'accés de %s amb nivel %d." + +#: modules/commands/cs_akick.cpp:190 +#, c-format +msgid "%s added to %s autokick list." +msgstr "%s afegit a la llista de kicks automàtics en el canal %s." + +#: modules/commands/bs_badwords.cpp:307 +#, c-format +msgid "%s added to %s bad words list." +msgstr "%s afegida a la llista de paraules malsonants de %s." + +#: modules/commands/ns_access.cpp:45 +#, fuzzy, c-format +msgid "%s added to %s's access list." +msgstr "%s afegit a la teva lllista d'accés." + +#: modules/commands/ns_cert.cpp:204 +#, fuzzy, c-format +msgid "%s added to %s's certificate list." +msgstr "%s afegit a la teva lllista d'accés." + +#: modules/commands/ms_ignore.cpp:62 +#, fuzzy, c-format +msgid "%s added to ignore list." +msgstr "%s afegit a la teva lllista d'accés." + +#: modules/commands/os_sxline.cpp:415 modules/commands/os_sxline.cpp:649 +#, fuzzy, c-format +msgid "%s added to the %s list." +msgstr "%s afegit a la llista de AKILLs." + +#: modules/commands/os_akill.cpp:203 +#, c-format +msgid "%s added to the AKILL list." +msgstr "%s afegit a la llista de AKILLs." + +#: modules/pseudoclients/botserv.cpp:134 +#, c-format +msgid "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands " +"that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" +msgstr "" + +#: modules/pseudoclients/botserv.cpp:148 +#, fuzzy, c-format +msgid "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s et permet crear un bot en el teu propi canal.\n" +"Això ha estat creat per a usuaris que no poden\n" +"tenir un bot en un host o configurar un bot, o per a us en xarxes\n" +"que no permeten bots d'usuaris. Comandes\n" +"disponibles estan llistades més endavant; per a\n" +"utilitzar-los, escriu /msg %s comanda. per a més\n" +"informació sobre un comanda especifica, escriu \n" +"/msg %s HELP comanda." + +#: modules/pseudoclients/nickserv.cpp:466 +#, fuzzy, c-format +msgid "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s Et permet \"registrar\" un nickname i\n" +"prevenir a d'altres utilitzar-lo. Les següents comandes\n" +"permeten el registre i manteniment de nicknames;\n" +"per a utilitzar-los, escriu /msg %s comanda.\n" +"per més informació sobre una comanda especifica\n" +"escriu /msg %s HELP comanda." + +#: modules/pseudoclients/nickserv.cpp:473 +#, fuzzy, c-format +msgid "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s Et permet \"registrar\" un nickname i\n" +"prevenir a d'altres utilitzar-lo. Les següents comandes\n" +"permeten el registre i manteniment de nicknames;\n" +"per a utilitzar-los, escriu /msg %s comanda.\n" +"per més informació sobre una comanda especifica\n" +"escriu /msg %s HELP comanda." + +#: modules/pseudoclients/chanserv.cpp:255 +#, fuzzy, c-format +msgid "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" +msgstr "" +"%s et permet registrar i controlar varis\n" +"aspectes dels canals. Sovint, %s pot prevenir\n" +"a usuaris maliciosos \"pendre\" canals limitant\n" +"qui esta permés a tenir privilegis d'operador.\n" +"Les comandes disponibles estan llistades a continuació;\n" +"Per a utilitzar-los, escriu /msg %s comanda.\n" +"Per més informació sobre una comanda especifica,\n" +"escriu /msg %s HELP comanda.\n" +" " + +#: modules/commands/bs_badwords.cpp:298 +#, c-format +msgid "%s already exists in %s bad words list." +msgstr "%s ja existeix a la llista de paraules malsonants de %s." + +#: modules/commands/cs_akick.cpp:170 +#, c-format +msgid "%s already exists on %s autokick list." +msgstr "%s ja esta present a la llista de kick automàtic en el canal %s." + +#: modules/commands/os_session.cpp:361 +#, c-format +msgid "%s already exists on the EXCEPTION list." +msgstr "%s already exists on the EXCEPTION list." + +#: modules/commands/bs_kick.cpp:214 modules/commands/bs_kick.cpp:389 +#: modules/commands/bs_kick.cpp:520 modules/commands/bs_kick.cpp:651 +#, c-format +msgid "%s cannot be taken as times to ban." +msgstr "%s no pot ser pres com vegades a banegar" + +#: modules/commands/os_mode.cpp:163 +#, fuzzy, c-format +msgid "%s changed your usermodes to %s." +msgstr "%s changed your usermodes." + +#: modules/commands/os_list.cpp:47 +#, fuzzy, c-format +msgid "%s channel list:" +msgstr "Fi de la llista de canals." + +#: modules/commands/cs_xop.cpp:343 +#, fuzzy, c-format +msgid "%s deleted from %s %s list." +msgstr "%s esborrat de la llista AOP de %s." + +#: modules/commands/cs_access.cpp:326 +#, c-format +msgid "%s deleted from %s access list." +msgstr "%s esborrat de la llista d'accés de %s." + +#: modules/commands/cs_akick.cpp:276 +#, c-format +msgid "%s deleted from %s autokick list." +msgstr "%s esborrat de la llista de kicks automàtics del canal %s." + +#: modules/commands/bs_badwords.cpp:348 +#, c-format +msgid "%s deleted from %s bad words list." +msgstr "%s esborrada de la llista de paraules malsonants de %s." + +#: modules/commands/ns_access.cpp:72 +#, fuzzy, c-format +msgid "%s deleted from %s's access list." +msgstr "%s esborrat de la llista d'accés de %s." + +#: modules/commands/ns_cert.cpp:233 +#, fuzzy, c-format +msgid "%s deleted from %s's certificate list." +msgstr "%s esborrat de la teva lllista d'accés." + +#: modules/commands/os_session.cpp:414 +#, c-format +msgid "%s deleted from session-limit exception list." +msgstr "" +"%s instàncies esborrades de la llista d'excepcions al límit de sessions." + +#: modules/commands/os_sxline.cpp:99 +#, fuzzy, c-format +msgid "%s deleted from the %s list." +msgstr "%s esborrat de la llista AOP de %s." + +#: modules/commands/os_akill.cpp:246 +#, c-format +msgid "%s deleted from the AKILL list." +msgstr "%s esborrat de la llista de AKILLs." + +#: modules/commands/cs_access.cpp:685 +#, c-format +msgid "%s disabled on channel %s." +msgstr "%s inhabilitat(s) en el canal %s." + +#: modules/commands/cs_invite.cpp:75 +#, c-format +msgid "%s has been invited to %s." +msgstr "%s has been invited to %s." + +#: modules/commands/os_svs.cpp:104 +#, fuzzy, c-format +msgid "%s has been joined to %s." +msgstr "%s has been invited to %s." + +#: modules/commands/os_svs.cpp:152 +#, fuzzy, c-format +msgid "%s has been parted from %s." +msgstr "%s has been unbanned from %s." + +#: modules/commands/cs_unban.cpp:96 +#, c-format +msgid "%s has been unbanned from %s." +msgstr "%s has been unbanned from %s." + +#: modules/commands/ns_alist.cpp:110 +#, fuzzy, c-format +msgid "%s has no access in any channels." +msgstr "%s inhabilitat(s) en el canal %s." + +#: modules/commands/cs_status.cpp:55 +#, fuzzy, c-format +msgid "%s has no access on %s." +msgstr "%s has been invited to %s." + +#: modules/commands/cs_set.cpp:307 +#, c-format +msgid "%s has too many channels registered." +msgstr "%s te masses canals registrats." + +#: modules/commands/cs_status.cpp:51 +#, fuzzy, c-format +msgid "%s is a super administrator." +msgstr "%s is a services operator of type %s." + +#: modules/pseudoclients/memoserv.cpp:214 +#, fuzzy, c-format +msgid "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" +msgstr "" +"%s és una utilitat que permet a usuaris de IRC\n" +"enviar missatges curts a altres usuaris de IRC, estiguin\n" +"en linea o no, o a canals(*). Ambdós el nickname que\n" +"envia i el nickname o canal destinataris han d'estar\n" +"registrats per a enviar un memo.\n" +"\n" +"Les comandes de %s incloen:" + +#: modules/commands/cs_invite.cpp:66 +#, fuzzy, c-format +msgid "%s is already in %s!" +msgstr "You are already in %s! " + +#: modules/commands/os_svs.cpp:99 +#, fuzzy, c-format +msgid "%s is already in %s." +msgstr "You are already in %s! " + +#: modules/commands/ms_ignore.cpp:65 +#, fuzzy, c-format +msgid "%s is already on the ignore list." +msgstr "%s afegit a la teva lllista d'accés." + +#: modules/commands/cs_suspend.cpp:97 modules/commands/ns_suspend.cpp:106 +#, fuzzy, c-format +msgid "%s is already suspended." +msgstr "You are already in %s! " + +#: modules/commands/ms_rsend.cpp:56 modules/commands/ms_send.cpp:55 +#, fuzzy, c-format +msgid "%s is not a registered unforbidden nick or channel." +msgstr "%s no és un bot valid o un canal registrat." + +#: modules/commands/cs_set.cpp:178 +#, c-format +msgid "%s is not a valid ban type." +msgstr "%s no es un tipus de ban valid." + +#: modules/commands/bs_info.cpp:101 +#, c-format +msgid "%s is not a valid bot or registered channel." +msgstr "%s no és un bot valid o un canal registrat." + +#: include/language.h:86 +#, fuzzy, c-format +msgid "%s is not a valid e-mail address." +msgstr "%s no es un tipus de ban valid." + +#: include/language.h:80 +#, fuzzy, c-format +msgid "%s is not currently on channel %s." +msgstr "%s inhabilitat(s) en el canal %s." + +#: modules/commands/os_svs.cpp:144 +#, fuzzy, c-format +msgid "%s is not in %s." +msgstr "You are already in %s! " + +#: modules/commands/ms_ignore.cpp:77 +#, fuzzy, c-format +msgid "%s is not on the ignore list." +msgstr "%s not found on ignore list." + +#: modules/commands/cs_status.cpp:90 +#, fuzzy, c-format +msgid "%s is on the auto kick list of %s (%s)." +msgstr "%s afegit a la llista de kicks automàtics en el canal %s." + +#: modules/commands/cs_status.cpp:53 +#, fuzzy, c-format +msgid "%s is the founder of %s." +msgstr "%s inhabilitat(s) en el canal %s." + +#: modules/commands/cs_status.cpp:78 +#, c-format +msgid "%s matches access entry %s (from entry %s), which has privilege %s." +msgstr "" + +#: modules/commands/cs_status.cpp:71 +#, c-format +msgid "%s matches access entry %s, which has privilege %s." +msgstr "" + +#: include/language.h:109 +#, c-format +msgid "" +"%s matches an except on %s and cannot be banned until the except has been " +"removed." +msgstr "" + +#: modules/commands/cs_status.cpp:96 +#, fuzzy, c-format +msgid "%s matches auto kick entry %s on %s (%s)." +msgstr "%s afegit a la llista de kicks automàtics en el canal %s." + +#: modules/commands/cs_xop.cpp:353 +#, fuzzy, c-format +msgid "%s not found on %s %s list." +msgstr "%s no trobat a la llista AOP de %s." + +#: modules/commands/cs_access.cpp:338 modules/commands/cs_flags.cpp:255 +#, c-format +msgid "%s not found on %s access list." +msgstr "%s no trobat a la llista d'accés de %s." + +#: modules/commands/cs_akick.cpp:265 +#, c-format +msgid "%s not found on %s autokick list." +msgstr "%s no trobat a la llista de kicks automàtics en el canal %s." + +#: modules/commands/bs_badwords.cpp:341 +#, c-format +msgid "%s not found on %s bad words list." +msgstr "%s no trobada a la llista de paraules malsonants de %s." + +#: modules/commands/ns_access.cpp:66 +#, fuzzy, c-format +msgid "%s not found on %s's access list." +msgstr "%s no trobat a la llista d'accés de %s." + +#: modules/commands/ns_cert.cpp:226 +#, fuzzy, c-format +msgid "%s not found on %s's certificate list." +msgstr "%s no trobat a la teva lllista d'accés." + +#: modules/commands/os_ignore.cpp:320 +#, fuzzy, c-format +msgid "%s not found on ignore list." +msgstr "%s not found on ignore list." + +#: modules/commands/os_session.cpp:238 +#, c-format +msgid "" +"%s not found on session list, but has a limit of %d because it matches entry:" +" %s." +msgstr "" + +#: modules/commands/os_session.cpp:418 +#, c-format +msgid "%s not found on session-limit exception list." +msgstr "%s no trobat a a la llista d'excepcions al límit de sessions." + +#: modules/commands/os_sxline.cpp:92 +#, fuzzy, c-format +msgid "%s not found on the %s list." +msgstr "%s no trobat a la llista AOP de %s." + +#: modules/commands/os_akill.cpp:237 +#, c-format +msgid "%s not found on the AKILL list." +msgstr "%s no trobat a la llista de AKILLs." + +#: modules/commands/cs_flags.cpp:251 +#, fuzzy, c-format +msgid "%s removed from the %s access list." +msgstr "%s esborrat de la llista d'accés de %s." + +#: modules/commands/ms_ignore.cpp:74 +#, fuzzy, c-format +msgid "%s removed from the ignore list." +msgstr "%s esborrat de la teva lllista d'accés." + +#: modules/commands/os_list.cpp:157 +#, fuzzy, c-format +msgid "%s users list:" +msgstr "Fi de la llista d'usuaris." + +#: modules/commands/os_ignore.cpp:316 +#, c-format +msgid "%s will no longer be ignored." +msgstr "%s will no longer be ignored." + +#: modules/commands/os_ignore.cpp:238 +#, c-format +msgid "%s will now be ignored for %s." +msgstr "%s will now be ignored for %s." + +#: modules/commands/os_ignore.cpp:233 +#, c-format +msgid "%s will now permanently be ignored." +msgstr "%s will now permanently be ignored." + +#: include/language.h:66 +#, fuzzy, c-format +msgid "%s%s HELP %s for more information." +msgstr "" +"Escriu /msg %s HELP opció per més informació\n" +"sobre una opció en particular." + +#: modules/commands/bs_bot.cpp:270 +msgid "ADD nick user host real" +msgstr "" + +#: modules/commands/bs_bot.cpp:271 +#, fuzzy +msgid "CHANGE oldnick newnick [user [host [real]]]" +msgstr "" +"BOT ADD nick usuari host nom-real\n" +"BOT CHANGE nick-antic nick-nou [usuari [host [nom-real]]]\n" +"BOT DEL nick" + +#: modules/commands/bs_bot.cpp:272 +#, fuzzy +msgid "DEL nick" +msgstr "DEL ." + +#: modules/commands/os_session.cpp:560 +#, fuzzy +msgid "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." +msgstr "" +"Sintaxis: EXCEPTION ADD [+expiració] mascara límit raó\n" +" EXCEPTION DEL {mascara | llista}\n" +" EXCEPTION MOVE numero posició\n" +" EXCEPTION LIST [mascara | llista]\n" +" EXCEPTION VIEW [mascara | llista]\n" +"\n" +"Permet als administradors de serveis manipular la llista\n" +"de hosts que tenen un límit de sessió específic - permetent \n" +"a certes màquines, com servidors de shells, mantenir un nombre més alt \n" +"de clients al mateix temps. En quant un host arribi al seu límit\n" +"de sessions, tots els clients intentant conectarse desde aquest \n" +"host seran expulsats. Abans de expulsar usuaris, aquests son\n" +"notificats a traves de un /NOTICE del %s amb ajuda sobre\n" +"el límit de sessió. El contingut d'aquest notice es un establiment\n" +"de configuració.\n" +"\n" +"EXCEPTION ADD afegeix la mascara de host donada a la llista de\n" +"excepcion. Teniu en compte que les mascares nick!usuari@host\n" +"i usuari@host son invalides. Nomès mascares reals com\n" +"irc.aujac.org i *.aujac.org, son permessas ja que el\n" +"límit de sessions no compta nicks o noms d'usuari.\n" +"Límit ha de ser un numero mes gran o igual a zero. Això determina\n" +"quantes sessions el host pot tenir en un cert temps. El valor\n" +"zero significa que el host no te límits de sessió. Veure la ajuda\n" +"sobre AKILL per a més detalls sobre el parametre opcional\n" +"expiració.\n" +"EXCEPTION DEL remou la mascara donada de la llista d'excepcions.\n" +"EXCEPTION MOVE mou l'excepció numero a posició. Les\n" +"excepcions entremig seran mogudes amunt o avall per a omplir l'espai.\n" +"\n" +"EXCEPTION LIST i EXCEPTION VIEW mostra totes les\n" +"excepcions actuals; si la mascara opcional es donada, la llista es\n" +"limitada a les excepcions similars a la mascara. La diferencia\n" +"es que EXCEPTION VIEW es mes verbal, mostrant el nom de la\n" +"persona que va afegir l'excepció, el límit d'excepció, raó,\n" +"mascara de hosts i la data i hora d'expiració. \n" +"\n" +"Pren nota de que un client conectant-se \"utilitzara\" la primera\n" +"excepció a la que el host s'assembli. Llargues llistes d'excepcions\n" +"i mascares que s'assemblin a moltes mascares possiblement contribueixin\n" +"al mal rendiment dels serveis.\n" +"\n" +"Limitat a administradors de serveis." + +#: modules/commands/os_noop.cpp:68 +msgid "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." +msgstr "" + +#: modules/commands/cs_access.cpp:611 +#, c-format +msgid "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." +msgstr "" + +#: modules/commands/ms_read.cpp:35 +#, c-format +msgid "[auto-memo] The memo you sent to %s has been viewed." +msgstr "[auto-memo] The memo you sent to %s has been viewed." + +#: modules/commands/ns_group.cpp:92 +#, fuzzy +msgid "[target] [password]" +msgstr "GROUP grup clau" + +#: modules/commands/ns_set.cpp:453 +msgid "address" +msgstr "" + +#: modules/commands/bs_set.cpp:162 +#, fuzzy +msgid "botname {ON|OFF}" +msgstr "SASET nickname AUTOOP {ON | OFF}" + +#: modules/extra/stats/cs_fantasy_top.cpp:39 +#: modules/extra/stats/cs_fantasy_top.cpp:51 +#: modules/commands/cs_suspend.cpp:152 modules/commands/cs_sync.cpp:20 +#: modules/commands/cs_log.cpp:106 modules/commands/bs_assign.cpp:91 +#: modules/commands/cs_info.cpp:20 modules/commands/cs_getkey.cpp:20 +#, fuzzy +msgid "channel" +msgstr "DROP canal" + +#: modules/commands/cs_set.cpp:138 +#, fuzzy +msgid "channel bantype" +msgstr "ACT canal text" + +#: modules/commands/cs_drop.cpp:20 +#, fuzzy +msgid "channel channel" +msgstr "TOPIC canal [tòpic]" + +#: modules/commands/cs_log.cpp:107 +#, fuzzy +msgid "channel command method [status]" +msgstr "KICK canal opció {ON|OFF} [establiments]" + +#: modules/commands/cs_kick.cpp:21 +#, fuzzy +msgid "channel mask [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_mode.cpp:20 +#, fuzzy +msgid "channel modes" +msgstr "MODE canal Modes" + +#: modules/commands/cs_set.cpp:267 modules/commands/bs_assign.cpp:20 +#, fuzzy +msgid "channel nick" +msgstr "UNBAN canal [nick]" + +#: modules/commands/cs_kick.cpp:20 +#, fuzzy +msgid "channel nick [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_clone.cpp:115 +#, fuzzy +msgid "channel target [what]" +msgstr "CLEAR canal Modes-a-netegar" + +#: modules/commands/bs_control.cpp:20 modules/commands/bs_control.cpp:80 +#, fuzzy +msgid "channel text" +msgstr "ACT canal text" + +#: modules/commands/bs_set.cpp:91 +#, fuzzy +msgid "channel time" +msgstr "ACT canal text" + +#: modules/commands/os_kick.cpp:20 +#, fuzzy +msgid "channel user reason" +msgstr "KICK canal usuari raó" + +#: modules/commands/cs_enforce.cpp:228 +#, fuzzy +msgid "channel what" +msgstr "TOPIC canal [tòpic]" + +#: modules/commands/cs_xop.cpp:481 +#, fuzzy +msgid "channel ADD mask" +msgstr "MODE canal Modes" + +#: modules/commands/cs_access.cpp:499 +msgid "channel ADD mask level" +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:194 +#, fuzzy +msgid "channel ADD message" +msgstr "MODE canal Modes" + +#: modules/commands/bs_badwords.cpp:371 +msgid "channel ADD word [SINGLE | START | END]" +msgstr "" + +#: modules/commands/cs_akick.cpp:435 +#, fuzzy +msgid "channel ADD {nick | mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_topic.cpp:151 +#, fuzzy +msgid "channel APPEND topic" +msgstr "TOPIC canal [tòpic]" + +#: modules/commands/cs_access.cpp:503 modules/commands/cs_flags.cpp:376 +#: modules/commands/cs_xop.cpp:484 modules/commands/cs_entrymsg.cpp:197 +#: modules/commands/bs_badwords.cpp:374 modules/commands/cs_akick.cpp:440 +#, fuzzy +msgid "channel CLEAR" +msgstr "DROP canal" + +#: modules/commands/cs_mode.cpp:736 +#, fuzzy +msgid "channel CLEAR [what]" +msgstr "TOPIC canal [tòpic]" + +#: modules/commands/os_mode.cpp:21 +#, fuzzy +msgid "channel CLEAR [ALL]" +msgstr "DROP canal" + +#: modules/commands/cs_entrymsg.cpp:195 +#, fuzzy +msgid "channel DEL num" +msgstr "MODE canal Modes" + +#: modules/commands/cs_access.cpp:500 modules/commands/cs_xop.cpp:482 +#, fuzzy +msgid "channel DEL {mask | entry-num | list}" +msgstr "DEL [canal] {numero | llista | ALL}" + +#: modules/commands/cs_akick.cpp:436 +#, fuzzy +msgid "channel DEL {nick | mask | entry-num | list}" +msgstr "AOP canal {ADD|DEL|LIST|CLEAR} [nick | instància]" + +#: modules/commands/bs_badwords.cpp:372 +#, fuzzy +msgid "channel DEL {word | entry-num | list}" +msgstr "DEL [canal] {numero | llista | ALL}" + +#: modules/commands/cs_akick.cpp:439 +msgid "channel ENFORCE" +msgstr "" + +#: modules/commands/cs_access.cpp:744 modules/commands/cs_entrymsg.cpp:196 +#, fuzzy +msgid "channel LIST" +msgstr "DROP canal" + +#: modules/commands/cs_akick.cpp:437 +#, fuzzy +msgid "channel LIST [mask | entry-num | list]" +msgstr "AOP canal {ADD|DEL|LIST|CLEAR} [nick | instància]" + +#: modules/commands/cs_access.cpp:501 modules/commands/cs_xop.cpp:483 +#: modules/commands/bs_badwords.cpp:373 +#, fuzzy +msgid "channel LIST [mask | list]" +msgstr "AOP canal {ADD|DEL|LIST|CLEAR} [nick | instància]" + +#: modules/commands/cs_flags.cpp:375 +msgid "channel LIST [mask | +flags]" +msgstr "" + +#: modules/commands/cs_mode.cpp:734 +#, fuzzy +msgid "channel LOCK {ADD|DEL|SET|LIST} [what]" +msgstr "AOP canal {ADD|DEL|LIST|CLEAR} [nick | instància]" + +#: modules/commands/cs_access.cpp:745 +#, fuzzy +msgid "channel RESET" +msgstr "SET canal GREET {ON|OFF}" + +#: modules/commands/cs_mode.cpp:735 +#, fuzzy +msgid "channel SET modes" +msgstr "MODE canal Modes" + +#: modules/commands/cs_access.cpp:742 +msgid "channel SET type level" +msgstr "" + +#: modules/commands/cs_akick.cpp:438 +#, fuzzy +msgid "channel VIEW [mask | entry-num | list]" +msgstr "AOP canal {ADD|DEL|LIST|CLEAR} [nick | instància]" + +#: modules/commands/cs_access.cpp:502 +#, fuzzy +msgid "channel VIEW [mask | list]" +msgstr "DEL [canal] {numero | llista | ALL}" + +#: modules/commands/cs_register.cpp:20 modules/commands/cs_set.cpp:205 +#, fuzzy +msgid "channel [description]" +msgstr "REGISTER canal descripció" + +#: modules/commands/cs_set.cpp:950 modules/commands/cs_invite.cpp:20 +#: modules/commands/cs_unban.cpp:20 +#, fuzzy +msgid "channel [nick]" +msgstr "UNBAN canal [nick]" + +#: modules/commands/cs_set_misc.cpp:96 +#, fuzzy +msgid "channel [parameters]" +msgstr "CLEAR canal Modes-a-netegar" + +#: modules/commands/cs_mode.cpp:807 modules/commands/cs_status.cpp:20 +#, fuzzy +msgid "channel [user]" +msgstr "UNBAN canal [nick]" + +#: modules/commands/cs_suspend.cpp:59 +#, fuzzy +msgid "channel [+expiry] [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_ban.cpp:40 +#, fuzzy +msgid "channel [+expiry] {nick | mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_flags.cpp:374 +#, fuzzy +msgid "channel [MODIFY] mask changes" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_topic.cpp:150 +#, fuzzy +msgid "channel [SET] [topic]" +msgstr "TOPIC canal [tòpic]" + +#: modules/commands/cs_topic.cpp:152 +#, fuzzy +msgid "channel [UNLOCK|LOCK]" +msgstr "DROP canal" + +#: modules/fantasy.cpp:20 modules/commands/greet.cpp:20 +#: modules/commands/bs_assign.cpp:154 +#, fuzzy +msgid "channel {ON|OFF}" +msgstr "SET canal XOP {ON | OFF}" + +#: modules/commands/bs_kick.cpp:491 +#, fuzzy +msgid "channel {ON|OFF} [ttb [ln [secs]]]" +msgstr "KICK canal opció {ON|OFF} [establiments]" + +#: modules/commands/bs_kick.cpp:361 +#, fuzzy +msgid "channel {ON|OFF} [ttb [min [percent]]]" +msgstr "KICK canal opció {ON|OFF} [establiments]" + +#: modules/commands/bs_kick.cpp:623 +#, fuzzy +msgid "channel {ON|OFF} [ttb [num]]" +msgstr "KICK canal opció {ON|OFF} [establiments]" + +#: modules/commands/bs_kick.cpp:252 modules/commands/bs_kick.cpp:288 +#: modules/commands/bs_kick.cpp:327 modules/commands/bs_kick.cpp:457 +#: modules/commands/bs_kick.cpp:589 modules/commands/bs_kick.cpp:724 +#: modules/commands/bs_kick.cpp:758 +#, fuzzy +msgid "channel {ON|OFF} [ttb]" +msgstr "SET canal XOP {ON | OFF}" + +#: modules/commands/cs_access.cpp:743 +msgid "channel {DIS | DISABLE} type" +msgstr "" + +#: modules/commands/cs_set.cpp:873 +#, fuzzy +msgid "channel {ON | LEVEL | OFF}" +msgstr "SET canal SIGNKICK {ON | LEVEL | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:18 modules/commands/cs_set.cpp:75 +#: modules/commands/cs_set.cpp:336 modules/commands/cs_set.cpp:401 +#: modules/commands/cs_set.cpp:473 modules/commands/cs_set.cpp:622 +#: modules/commands/cs_set.cpp:684 modules/commands/cs_set.cpp:747 +#: modules/commands/cs_set.cpp:811 modules/commands/cs_set.cpp:1044 +#: modules/commands/bs_kick.cpp:792 modules/commands/bs_kick.cpp:857 +#: modules/commands/cs_topic.cpp:21 modules/commands/cs_list.cpp:181 +#, fuzzy +msgid "channel {ON | OFF}" +msgstr "SET canal XOP {ON | OFF}" + +#: modules/commands/ns_getemail.cpp:24 +msgid "email" +msgstr "" + +#: modules/commands/ns_set.cpp:794 +#, fuzzy +msgid "language" +msgstr "SET LANGUAGE numero" + +#: modules/commands/ms_sendall.cpp:25 modules/commands/ms_staff.cpp:25 +#, fuzzy +msgid "memo-text" +msgstr "STAFF memo-text" + +#: modules/commands/gl_global.cpp:22 modules/commands/greet.cpp:84 +#, fuzzy +msgid "message" +msgstr "GLOBAL missatge" + +#: modules/commands/os_modinfo.cpp:20 modules/commands/os_module.cpp:20 +#: modules/commands/os_module.cpp:57 modules/commands/os_module.cpp:129 +msgid "modname" +msgstr "" + +#: modules/commands/ns_set.cpp:330 +msgid "new-display" +msgstr "" + +#: modules/commands/ns_set.cpp:120 +#, fuzzy +msgid "new-password" +msgstr "GROUP grup clau" + +#: modules/extra/stats/cs_fantasy_stats.cpp:52 modules/commands/hs_del.cpp:20 +#: modules/commands/hs_del.cpp:60 modules/commands/ms_check.cpp:20 +#: modules/commands/hs_request.cpp:192 modules/commands/cs_seen.cpp:262 +#, fuzzy +msgid "nick" +msgstr "INFO nick" + +#: modules/commands/os_svs.cpp:79 +#, fuzzy +msgid "nick channel" +msgstr "CANCEL {nick | canal}" + +#: modules/commands/os_svs.cpp:123 +#, fuzzy +msgid "nick channel [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_oline.cpp:20 +#, fuzzy +msgid "nick flags" +msgstr "OLINE nick flags" + +#: modules/commands/hs_set.cpp:20 modules/commands/hs_set.cpp:126 +#, fuzzy +msgid "nick hostmask" +msgstr "SET  ." + +#: modules/commands/os_svs.cpp:20 +#, fuzzy +msgid "nick newnick" +msgstr "SVSNICK nick newnick " + +#: modules/commands/hs_request.cpp:241 +#, fuzzy +msgid "nick [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/ns_getpass.cpp:20 modules/commands/ns_drop.cpp:19 +#: modules/commands/ns_suspend.cpp:161 +#, fuzzy +msgid "nickname" +msgstr "CHECK nickname" + +#: modules/commands/ns_set.cpp:546 +#, fuzzy +msgid "nickname address" +msgstr "FORBID nickname rao" + +#: modules/commands/ns_resetpass.cpp:22 +#, fuzzy +msgid "nickname email" +msgstr "FORBID nickname rao" + +#: modules/commands/ns_set.cpp:872 +#, fuzzy +msgid "nickname language" +msgstr "FORBID nickname rao" + +#: modules/commands/greet.cpp:145 +#, fuzzy +msgid "nickname message" +msgstr "FORBID nickname rao" + +#: modules/commands/ns_set.cpp:399 +#, fuzzy +msgid "nickname new-display" +msgstr "FORBID nickname rao" + +#: modules/commands/ns_set.cpp:173 +#, fuzzy +msgid "nickname new-password" +msgstr "GHOST nickname [clau]" + +#: modules/commands/ns_set_misc.cpp:170 +#, fuzzy +msgid "nickname [parameter]" +msgstr "GHOST nickname [clau]" + +#: modules/commands/ns_recover.cpp:150 +#, fuzzy +msgid "nickname [password]" +msgstr "GHOST nickname [clau]" + +#: modules/commands/ns_suspend.cpp:61 +#, fuzzy +msgid "nickname [+expiry] [reason]" +msgstr "FORBID nickname rao" + +#: modules/commands/ns_info.cpp:239 +#, fuzzy +msgid "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +msgstr "SET HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:130 modules/commands/ns_set.cpp:302 +#: modules/commands/ns_set.cpp:631 modules/commands/ns_set.cpp:985 +#: modules/commands/ns_set.cpp:1076 modules/commands/ns_set.cpp:1105 +#: modules/commands/ns_list.cpp:252 +#, fuzzy +msgid "nickname {ON | OFF}" +msgstr "SASET nickname AUTOOP {ON | OFF}" + +#: modules/commands/ns_set.cpp:760 +#, fuzzy +msgid "nickname {ON | QUICK | IMMED | OFF}" +msgstr "SASET nickname KILL {ON | QUICK | IMMED | OFF}" + +#: modules/commands/bs_set.cpp:20 +#, fuzzy +msgid "option (channel | bot) settings" +msgstr "SET canal Opció establiments" + +#: modules/commands/cs_set.cpp:21 +#, fuzzy +msgid "option channel parameters" +msgstr "SEND {nick | canal} text" + +#: modules/commands/bs_kick.cpp:120 +#, fuzzy +msgid "option channel {ON|OFF} [settings]" +msgstr "KICK canal opció {ON|OFF} [establiments]" + +#: modules/commands/ns_set.cpp:75 +msgid "option nickname parameters" +msgstr "" + +#: modules/commands/ms_set.cpp:207 modules/commands/ns_set.cpp:20 +#, fuzzy +msgid "option parameters" +msgstr "SET Opció estabilment" + +#: modules/commands/os_set.cpp:170 +#, fuzzy +msgid "option setting" +msgstr "SET Opció estabilment" + +#: modules/commands/ns_register.cpp:22 +#, fuzzy +msgid "passcode" +msgstr "REGISTER clau email" + +#: modules/commands/os_login.cpp:19 +#, fuzzy +msgid "password" +msgstr "GROUP grup clau" + +#: modules/commands/ns_register.cpp:124 +#, fuzzy +msgid "password [email]" +msgstr "REGISTER clau email" + +#: modules/commands/ns_register.cpp:122 +#, fuzzy +msgid "password email" +msgstr "REGISTER clau email" + +#: modules/commands/cs_list.cpp:21 +#, fuzzy +msgid "pattern [SUSPENDED] [NOEXPIRE]" +msgstr "LIST patro [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/ns_list.cpp:20 +#, fuzzy +msgid "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" +msgstr "LIST patro [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/os_jupe.cpp:20 +#, fuzzy +msgid "server [reason]" +msgstr "JUPE nom-del-servidor [raó]" + +#: modules/commands/os_mode.cpp:147 +#, fuzzy +msgid "user modes" +msgstr "MODE canal Modes" + +#: modules/commands/os_kill.cpp:20 +#, fuzzy +msgid "user [reason]" +msgstr "JUPE nom-del-servidor [raó]" + +#: modules/commands/os_sxline.cpp:440 +#, fuzzy +msgid "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." +msgstr "" +"Sintàxi: AKILL ADD [+expiració] mascara raó\n" +" AKILL DEL {mascara | nom | llista}\n" +" AKILL LIST [mascara | llista]\n" +" AKILL VIEW [mascara | llista]\n" +" AKILL CLEAR\n" +"\n" +"Permet als operadors de serveis manipular la llista de\n" +"AKILLS. Si un usuari coincideix amb una mascara en la\n" +"llista de AKILLS i s'esta intentant connectar, els serveis enviaran\n" +"un KILL a aquest usuari i, en tipus de servidors soportats,\n" +"notificara a tots els servidors que afegeixin un ban (linea K)\n" +"per la mascara de l'usuari.\n" +"\n" +"AKILL ADD afegeix la mascara usuari@host especificada a la llista\n" +"de AKILLS per la raó especificada (que HA DE SER especificada).\n" +"expiració es especificada com un sencer seguit de\n" +" d (dies), h (hores), o m (minuts). Combinacions (com\n" +"1h30m) no estan permesses. Si un especificador d'unitats no\n" +"es inclòs, per defecte seran dies (o sigui +30 nomès\n" +"significa 30 dies). Per afegir un AKILL que no caduqui, utilitza +0.\n" +"Si la mascara a afegir comença amb un +, s'ha d'especificar\n" +"un temps d'expiració. El temps d'expiració per defecte actual de AKILLS\n" +"pot ser consultat amb la comanda STATS AKILL.\n" +"\n" +"La comanda AKILL DEL esborra la mascara especificada de la llista\n" +"d'AKILLS si esta present. Si s'especifica una llista de noms,\n" +"aquestes instàncies son esborrades. (Veure l'exemple per LIST \n" +"especificat més endavant.)\n" +"\n" +"La comanda AKILL LIST mostra la llista d'AKILLS. \n" +"Si s'especifica una mascara, nomès les instàncies coincidents\n" +"amb la mascara són mostrades. Si s'especifica una llista de noms,\n" +"nomès aquestes instàncies son mostrades; per exemple:\n" +"\n" +" AKILL LIST 2-5,7-9\n" +" Llista les instàncies de AKILL enumerades de 2 a 5 i de 7 \n" +" a 9.\n" +" \n" +"AKILL VIEW es una versió més verbal d'AKILL LIST, i \n" +"mostrara qui va afegir un AKILL, la data en que va ser afegit,\n" +"i quan caducara, així com tambe la mascara usuari@host\n" +"i la raó.\n" +"\n" +"AKILL CLEAR neteja totes les instàncies de la llista d'AKILLS.\n" +"\n" +"Limitat a operadors de serveis." + +#: modules/commands/os_sxline.cpp:678 +#, fuzzy +msgid "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Sintàxi: AKILL ADD [+expiració] mascara raó\n" +" AKILL DEL {mascara | nom | llista}\n" +" AKILL LIST [mascara | llista]\n" +" AKILL VIEW [mascara | llista]\n" +" AKILL CLEAR\n" +"\n" +"Permet als operadors de serveis manipular la llista de\n" +"AKILLS. Si un usuari coincideix amb una mascara en la\n" +"llista de AKILLS i s'esta intentant connectar, els serveis enviaran\n" +"un KILL a aquest usuari i, en tipus de servidors soportats,\n" +"notificara a tots els servidors que afegeixin un ban (linea K)\n" +"per la mascara de l'usuari.\n" +"\n" +"AKILL ADD afegeix la mascara usuari@host especificada a la llista\n" +"de AKILLS per la raó especificada (que HA DE SER especificada).\n" +"expiració es especificada com un sencer seguit de\n" +" d (dies), h (hores), o m (minuts). Combinacions (com\n" +"1h30m) no estan permesses. Si un especificador d'unitats no\n" +"es inclòs, per defecte seran dies (o sigui +30 nomès\n" +"significa 30 dies). Per afegir un AKILL que no caduqui, utilitza +0.\n" +"Si la mascara a afegir comença amb un +, s'ha d'especificar\n" +"un temps d'expiració. El temps d'expiració per defecte actual de AKILLS\n" +"pot ser consultat amb la comanda STATS AKILL.\n" +"\n" +"La comanda AKILL DEL esborra la mascara especificada de la llista\n" +"d'AKILLS si esta present. Si s'especifica una llista de noms,\n" +"aquestes instàncies son esborrades. (Veure l'exemple per LIST \n" +"especificat més endavant.)\n" +"\n" +"La comanda AKILL LIST mostra la llista d'AKILLS. \n" +"Si s'especifica una mascara, nomès les instàncies coincidents\n" +"amb la mascara són mostrades. Si s'especifica una llista de noms,\n" +"nomès aquestes instàncies son mostrades; per exemple:\n" +"\n" +" AKILL LIST 2-5,7-9\n" +" Llista les instàncies de AKILL enumerades de 2 a 5 i de 7 \n" +" a 9.\n" +" \n" +"AKILL VIEW es una versió més verbal d'AKILL LIST, i \n" +"mostrara qui va afegir un AKILL, la data en que va ser afegit,\n" +"i quan caducara, així com tambe la mascara usuari@host\n" +"i la raó.\n" +"\n" +"AKILL CLEAR neteja totes les instàncies de la llista d'AKILLS.\n" +"\n" +"Limitat a operadors de serveis." + +#: modules/pseudoclients/nickserv.cpp:492 +#, fuzzy, c-format +msgid "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." +msgstr "" +"Nicknames en desus estan subjectes a l'expiració\n" +"automatica, en altres paraules, seran esborrats després\n" +"de %d dies." + +#: modules/pseudoclients/botserv.cpp:143 +#, fuzzy +msgid "" +" \n" +"Available commands are:" +msgstr "No existeix ajuda per %s." + +#: modules/pseudoclients/botserv.cpp:167 +#, c-format +msgid "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." +msgstr "" + +#: modules/fantasy.cpp:69 +#, fuzzy, c-format +msgid "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." +msgstr "" +"Sintàxi: SET canal FANTASY {ON|OFF}\n" +"\n" +"Habilita o deshabilita el mode de fantasia\n" +"en un canal. En habilitar-lo, els usuaris podran\n" +"utilitzar les comandes !op, !deop, !voice, !devoice,\n" +"!kick, !kb, !unban, !seen en un canal (investiga\n" +"com utilitzar-los; intenta amb o sense nick per cadascú\n" +"i amb raó per a alguns?).\n" +"\n" +"Cal dir que els usuaris que desitgin utilitzar comandes\n" +"de fantasia HAN DE DISPOSSAR del nivell necessari\n" +"pel nivell FANTASIA i altres depenent\n" +"de la comanda si es requereix (per exemple, per a\n" +"utilitzar !op, l'usuari ha de tenir suficient\n" +"accés pel nivell OPDEOP)." + +#: modules/commands/greet.cpp:69 +#, fuzzy +msgid "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." +msgstr "" +"Sintàxi: SET canal GREET {ON|OFF}\n" +"\n" +"Habilita o deshabilita el mode de asludo en\n" +"un canal. En habilitar-lo, el bot mostrara els\n" +"missatges dels usuaris que entrin al canal,\n" +"sempre i quan tinguin el suficient accés\n" +"al canal." + +#: modules/commands/bs_kick.cpp:843 +#, fuzzy +msgid "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +"Sintàxi: SET canal DONTKICKOPS {ON|OFF}\n" +"\n" +"Habilita o deshabilita el mode de protecció d'ops\n" +"en un canal. En habilitar-lo, ops no seran\n" +"kickejats pel bot, encara que no concideixen amb\n" +"el nivell NOKICK." + +#: modules/commands/bs_kick.cpp:908 +#, fuzzy +msgid "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +"Sintàxi: SET canal DONTKICKVOICES {ON|OFF}\n" +"\n" +"Habilita o deshabilita el mode de protecció de voices\n" +"en un canal. En hbilitarlo, voices no seran\n" +"kickejatos pel bot, encara que no coincideixin amb\n" +"el nivell NOKICK." + +#: modules/pseudoclients/botserv.cpp:141 +#, c-format +msgid "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" +msgstr "" + +#: modules/commands/cs_register.cpp:105 +msgid "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." +msgstr "" + +#: modules/pseudoclients/chanserv.cpp:272 +#, fuzzy, c-format +msgid "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." +msgstr "" +"Tingues en compte que qualsevol canal que no sigui utilitzat durant\n" +"%d dies (al qual cap usuari a la llista d'accés\n" +"del canal entri en aquest periode de temps) sera\n" +"automaticament eliminat." + +#: modules/commands/cs_register.cpp:101 +#, c-format +msgid "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +msgstr "" + +#: modules/pseudoclients/nickserv.cpp:486 +#, fuzzy +msgid "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." +msgstr "" +"Administradors de serveis poden també eliminar qualsevol\n" +"nickname sense tenir que identificar-se pel nick i poden\n" +"veure la llista d'accés per qualsevol nickname\n" +"(/msg %s ACCESS LIST nick)." + +#: modules/pseudoclients/chanserv.cpp:277 +#, fuzzy +msgid "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." +msgstr "" +" \n" +"Les següents comandes estan disponibles per a administradors\n" +"de serveis:\n" +"\n" +" STATUS Retorna el nivell d'accés actual d'un\n" +" usuari en un canal\n" +" CLIST llista tots els canals en els que l'usuari\n" +" sigui fundador\n" +"\n" +"Administradors de serveis també poden eliminar un canal\n" +"sense haver d'identificar-se per mitjà d'una clau, i poden\n" +"Veure l'accés, AKICK, i paràmetres de les llistes de nivells per a\n" +"qualsevol canal." + +#: modules/commands/bs_set.cpp:147 +msgid "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." +msgstr "" + +#: modules/commands/cs_xop.cpp:542 +#, fuzzy, c-format +msgid "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." +msgstr "" +"Sintàxi: HOP canal ADD nick\n" +" HOP canal DEL {nick | instancia | llista}\n" +" HOP canal LIST [mascara | llista]\n" +" HOP canal CLEAR\n" +"\n" +"Manté la llista HOP (HalfOP) per a un canal. La llista\n" +"HOP li dóna a l'usuari el dret de ser automàticament\n" +"halfopejat en el teu canal.\n" +"\n" +"La comanda HOP ADD agrega al nickname donat a la llista\n" +"HOP.\n" +"\n" +"La comanda HOP DEL esborra el nickname donat de la\n" +"llista HOP. Si una llista d'instàncies és donada, aquestes\n" +"instàncies són esborrades. (Veure l'exemple per a LIST més\n" +"endevant.)\n" +"\n" +"La comanda HOP LIST mostra la llista HOP. Si una\n" +"mascara amb comodí és donada, només les instàncies\n" +"que concordin amb la mascara són mostrades. Si una llista de\n" +"instàncies és donada, només aquestes instàncies són mostrades;\n" +"per exemple:\n" +"\n" +" HOP #canal LIST 2-5,7-9\n" +" Mostra instàncies de HOP enumerades 2 a 5 y\n" +" 7 a 9.\n" +"\n" +"La comanda HOP CLEAR neteja totes les instàncies de la\n" +"llista HOP.\n" +"\n" +"Les comandes HOP ADD i HOP DEL estan limitades a\n" +"AOPs o superior, mentre que la comanda HOP CLEAR\n" +"sols pot ser utilitzada per el fundador del canal.\n" +"\n" +"Aquesta comanda pot haber estat deshabilitada per al teu canal.\n" +"Si aquest és el cas, has de fer servir la llista d'accés. Veure\n" +"/msg %s HELP ACCESS per a informació sobre la llista\n" +"d'accés i /msg %s HELP SET XOP per a saber com canviar\n" +"entre la llista d'accés i el sistema de llistes xOP." + +#: modules/commands/cs_akick.cpp:508 +#, c-format +msgid "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." +msgstr "" + +#: modules/commands/os_akill.cpp:448 +#, fuzzy +msgid "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." +msgstr "" +"Sintàxi: HOP canal ADD nick\n" +" HOP canal DEL {nick | instancia | llista}\n" +" HOP canal LIST [mascara | llista]\n" +" HOP canal CLEAR\n" +"\n" +"Manté la llista HOP (HalfOP) per a un canal. La llista\n" +"HOP li dóna a l'usuari el dret de ser automàticament\n" +"halfopejat en el teu canal.\n" +"\n" +"La comanda HOP ADD agrega al nickname donat a la llista\n" +"HOP.\n" +"\n" +"La comanda HOP DEL esborra el nickname donat de la\n" +"llista HOP. Si una llista d'instàncies és donada, aquestes\n" +"instàncies són esborrades. (Veure l'exemple per a LIST més\n" +"endevant.)\n" +"\n" +"La comanda HOP LIST mostra la llista HOP. Si una\n" +"mascara amb comodí és donada, només les instàncies\n" +"que concordin amb la mascara són mostrades. Si una llista de\n" +"instàncies és donada, només aquestes instàncies són mostrades;\n" +"per exemple:\n" +"\n" +" HOP #canal LIST 2-5,7-9\n" +" Mostra instàncies de HOP enumerades 2 a 5 y\n" +" 7 a 9.\n" +"\n" +"La comanda HOP CLEAR neteja totes les instàncies de la\n" +"llista HOP.\n" +"\n" +"Les comandes HOP ADD i HOP DEL estan limitades a\n" +"AOPs o superior, mentre que la comanda HOP CLEAR\n" +"sols pot ser utilitzada per el fundador del canal.\n" +"\n" +"Aquesta comanda pot haber estat deshabilitada per al teu canal.\n" +"Si aquest és el cas, has de fer servir la llista d'accés. Veure\n" +"/msg %s HELP ACCESS per a informació sobre la llista\n" +"d'accés i /msg %s HELP SET XOP per a saber com canviar\n" +"entre la llista d'accés i el sistema de llistes xOP." + +#: modules/commands/os_sxline.cpp:462 +#, fuzzy +msgid "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." +msgstr "" +"Sintàxi: HOP canal ADD nick\n" +" HOP canal DEL {nick | instancia | llista}\n" +" HOP canal LIST [mascara | llista]\n" +" HOP canal CLEAR\n" +"\n" +"Manté la llista HOP (HalfOP) per a un canal. La llista\n" +"HOP li dóna a l'usuari el dret de ser automàticament\n" +"halfopejat en el teu canal.\n" +"\n" +"La comanda HOP ADD agrega al nickname donat a la llista\n" +"HOP.\n" +"\n" +"La comanda HOP DEL esborra el nickname donat de la\n" +"llista HOP. Si una llista d'instàncies és donada, aquestes\n" +"instàncies són esborrades. (Veure l'exemple per a LIST més\n" +"endevant.)\n" +"\n" +"La comanda HOP LIST mostra la llista HOP. Si una\n" +"mascara amb comodí és donada, només les instàncies\n" +"que concordin amb la mascara són mostrades. Si una llista de\n" +"instàncies és donada, només aquestes instàncies són mostrades;\n" +"per exemple:\n" +"\n" +" HOP #canal LIST 2-5,7-9\n" +" Mostra instàncies de HOP enumerades 2 a 5 y\n" +" 7 a 9.\n" +"\n" +"La comanda HOP CLEAR neteja totes les instàncies de la\n" +"llista HOP.\n" +"\n" +"Les comandes HOP ADD i HOP DEL estan limitades a\n" +"AOPs o superior, mentre que la comanda HOP CLEAR\n" +"sols pot ser utilitzada per el fundador del canal.\n" +"\n" +"Aquesta comanda pot haber estat deshabilitada per al teu canal.\n" +"Si aquest és el cas, has de fer servir la llista d'accés. Veure\n" +"/msg %s HELP ACCESS per a informació sobre la llista\n" +"d'accés i /msg %s HELP SET XOP per a saber com canviar\n" +"entre la llista d'accés i el sistema de llistes xOP." + +#: modules/commands/os_sxline.cpp:697 +#, fuzzy +msgid "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." +msgstr "" +"Sintàxi: HOP canal ADD nick\n" +" HOP canal DEL {nick | instancia | llista}\n" +" HOP canal LIST [mascara | llista]\n" +" HOP canal CLEAR\n" +"\n" +"Manté la llista HOP (HalfOP) per a un canal. La llista\n" +"HOP li dóna a l'usuari el dret de ser automàticament\n" +"halfopejat en el teu canal.\n" +"\n" +"La comanda HOP ADD agrega al nickname donat a la llista\n" +"HOP.\n" +"\n" +"La comanda HOP DEL esborra el nickname donat de la\n" +"llista HOP. Si una llista d'instàncies és donada, aquestes\n" +"instàncies són esborrades. (Veure l'exemple per a LIST més\n" +"endevant.)\n" +"\n" +"La comanda HOP LIST mostra la llista HOP. Si una\n" +"mascara amb comodí és donada, només les instàncies\n" +"que concordin amb la mascara són mostrades. Si una llista de\n" +"instàncies és donada, només aquestes instàncies són mostrades;\n" +"per exemple:\n" +"\n" +" HOP #canal LIST 2-5,7-9\n" +" Mostra instàncies de HOP enumerades 2 a 5 y\n" +" 7 a 9.\n" +"\n" +"La comanda HOP CLEAR neteja totes les instàncies de la\n" +"llista HOP.\n" +"\n" +"Les comandes HOP ADD i HOP DEL estan limitades a\n" +"AOPs o superior, mentre que la comanda HOP CLEAR\n" +"sols pot ser utilitzada per el fundador del canal.\n" +"\n" +"Aquesta comanda pot haber estat deshabilitada per al teu canal.\n" +"Si aquest és el cas, has de fer servir la llista d'accés. Veure\n" +"/msg %s HELP ACCESS per a informació sobre la llista\n" +"d'accés i /msg %s HELP SET XOP per a saber com canviar\n" +"entre la llista d'accés i el sistema de llistes xOP." + +#: modules/commands/bs_assign.cpp:197 +#, fuzzy +msgid "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." +msgstr "" +"Sintaxi: SET canal NOBOT {ON|OFF}\n" +"\n" +"Aquesta opció fa al canal no sigui assignable. Si un\n" +"bot ja està assignat al canal, es desassignara\n" +"automàticament quan habiliteu aquesta opció.\n" +"\n" +"Limitat a administradors de serveis." + +#: modules/commands/bs_set.cpp:199 +#, fuzzy +msgid "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." +msgstr "" +"Sintaxi: SET nick-del-bot PRIVATE {ON|OFF}\n" +"\n" +"Aquesta opció evita un bot de ser assignat\n" +"a un canal per usuaris que no son operadors\n" +"d'IRC.\n" +"\n" +"Limitat a administradors de serveis." + +#: modules/pseudoclients/memoserv.cpp:227 +#, c-format +msgid "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." +msgstr "" + +#: modules/commands/os_oper.cpp:167 +#, c-format +msgid " %s is online using this oper block." +msgstr "" + +#: modules/commands/os_modinfo.cpp:55 +#, c-format +msgid " Command %s on %s is linked to %s" +msgstr "" + +#: modules/commands/os_modinfo.cpp:43 +#, fuzzy, c-format +msgid " Providing service: %s" +msgstr "Providing command: /msg %s %s" + +#: modules/commands/os_oper.cpp:163 +msgid " This oper is configured in the configuration file." +msgstr "" + +#: modules/commands/os_modinfo.cpp:34 +#, c-format +msgid " Loaded at: %p" +msgstr "" + +#: modules/commands/cs_seen.cpp:303 +#, c-format +msgid " but %s mysteriously dematerialized." +msgstr "" + +#: src/messages.cpp:339 +#, c-format +msgid "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." +msgstr "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." + +#: modules/commands/os_jupe.cpp:19 +#, fuzzy +msgid "\"Jupiter\" a server" +msgstr " JUPE \"Jupiter\" (Mart,Saturn....) un servidor" + +#: modules/commands/os_oper.cpp:161 +#, fuzzy, c-format +msgid "%-8s %s" +msgstr "%-20s %s@%s" + +#: modules/extra/stats/cs_fantasy_top.cpp:152 +#, c-format +msgid "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:359 +msgid "%b %d %H:%M:%S %Y %Z" +msgstr "" + +#: modules/commands/cs_log.cpp:205 +#, c-format +msgid "%c is an unknown status mode." +msgstr "" + +#: modules/commands/cs_mode.cpp:431 +#, fuzzy, c-format +msgid "%c%c is not locked on %s." +msgstr "%s no es notificat per memos nous." + +#: modules/commands/cs_mode.cpp:427 +#, fuzzy, c-format +msgid "%c%c%s has been unlocked from %s." +msgstr "Nick %s has been ungrouped from %s." + +#: modules/commands/cs_clone.cpp:56 +#, fuzzy, c-format +msgid "%d access entries from %s have been cloned to %s." +msgstr "All vhost's in the group %s have been set to %s" + +#: modules/commands/bs_botlist.cpp:56 +#, c-format +msgid "%d bots available." +msgstr "%d bots disponibles." + +#: modules/commands/os_modinfo.cpp:189 +#, fuzzy, c-format +msgid "%d modules loaded." +msgstr "%d Modules loaded." + +#: modules/commands/ns_group.cpp:357 +#, fuzzy, c-format +msgid "%d nickname(s) in the group." +msgstr "%d nicknames en el grup." + +#: modules/commands/cs_seen.cpp:137 +#, c-format +msgid "%lu nicks are stored in the database, using %.2Lf kB of memory." +msgstr "" + +#: modules/commands/cs_xop.cpp:241 modules/commands/cs_xop.cpp:372 +#: modules/commands/cs_xop.cpp:450 +#, fuzzy, c-format +msgid "%s %s list is empty." +msgstr "La llista AOP de %s esta buida." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1181 +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1201 +#: modules/commands/bs_kick.cpp:1211 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban)" +msgstr " Kicker per negretes : %s (%d kick(s) per a ban)" + +#: modules/commands/bs_kick.cpp:1161 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; %d lines in %ds)" +msgstr " Kicker per flood : %s (%d kick(s) per a ban; %d linees en %ds)" + +#: modules/commands/bs_kick.cpp:1171 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; %d times)" +msgstr " Kicker per repetició : %s (%d kick(s) per a ban; %d vegades)" + +#: modules/commands/bs_kick.cpp:1141 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; minimum %d/%d%%)" +msgstr " Kicker per majuscules : %s (%d kick(s) per a ban; mínim %d/%d%%)" + +#: modules/commands/bs_kick.cpp:1163 +#, fuzzy, c-format +msgid "%s (%d lines in %ds)" +msgstr " %s (expires in %s)" + +#: modules/commands/bs_kick.cpp:1173 +#, c-format +msgid "%s (%d times)" +msgstr "" + +#: modules/commands/cs_seen.cpp:358 +#, c-format +msgid "%s (%s) was kicked from %s (\"%s\") %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:355 +#, c-format +msgid "%s (%s) was kicked from a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:326 +#, c-format +msgid "%s (%s) was last seen changing nick from %s to %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:321 +#, c-format +msgid "%s (%s) was last seen changing nick to %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:310 +#, c-format +msgid "%s (%s) was last seen connecting %s ago (%s)%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:335 +#, c-format +msgid "%s (%s) was last seen joining %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:332 +#, c-format +msgid "%s (%s) was last seen joining a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:344 +#, c-format +msgid "%s (%s) was last seen parting %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:341 +#, c-format +msgid "%s (%s) was last seen parting a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:349 +#, c-format +msgid "%s (%s) was last seen quitting (%s) %s ago (%s)." +msgstr "" + +#: modules/commands/bs_kick.cpp:1143 +#, fuzzy, c-format +msgid "%s (minimum %d/%d%%)" +msgstr " Caps kicker : %s (mínim %d/%d%%)" + +#: modules/commands/cs_access.cpp:245 modules/commands/cs_access.cpp:349 +#: modules/commands/cs_access.cpp:454 modules/commands/cs_access.cpp:467 +#: modules/commands/cs_flags.cpp:295 +#, c-format +msgid "%s access list is empty." +msgstr "La llista d'accés de %s esta buida." + +#: modules/commands/ns_ajoin.cpp:184 +#, fuzzy, c-format +msgid "%s added to %s's auto join list." +msgstr "%s afegit a la llista de kicks automàtics en el canal %s." + +#: src/xline.cpp:389 +#, fuzzy, c-format +msgid "%s already exists." +msgstr "El bot %s ja existeix." + +#: modules/commands/cs_akick.cpp:202 modules/commands/cs_akick.cpp:387 +#: modules/commands/cs_akick.cpp:400 +#, c-format +msgid "%s autokick list is empty." +msgstr "La llista de kicks automàtics del canal %s esta buida." + +#: modules/commands/bs_badwords.cpp:198 modules/commands/bs_badwords.cpp:316 +#, c-format +msgid "%s bad words list is empty." +msgstr "La llista de paraules malsonants de %s esta buida." + +#: modules/commands/cs_set.cpp:993 +#, fuzzy, c-format +msgid "%s cannot be the successor on channel %s as they are the founder." +msgstr "%s no pot ser el sucessor en el canal %s ja que n'es el fundador." + +#: modules/pseudoclients/global.cpp:90 modules/pseudoclients/hostserv.cpp:78 +#: modules/pseudoclients/operserv.cpp:287 +#, c-format +msgid "%s commands:" +msgstr "%s commands:" + +#: include/language.h:69 +#, c-format +msgid "%s coverage is too wide; Please use a more specific mask." +msgstr "" + +#: modules/commands/ms_info.cpp:94 +#, c-format +msgid "%s currently has %d memos, of which %d are unread." +msgstr "%s actualment te %d memos, dels quals %d encara no han estat llegits." + +#: modules/commands/ms_info.cpp:92 +#, c-format +msgid "%s currently has %d memos, of which 1 is unread." +msgstr "%s actualment te %d memos, dels quals 1 encara no ha estat llegit." + +#: modules/commands/ms_info.cpp:90 +#, c-format +msgid "%s currently has %d memos." +msgstr "%s actualment te %d memos." + +#: modules/commands/ms_info.cpp:88 +#, c-format +msgid "%s currently has %d memos; all of them are unread." +msgstr "%s actualment te %d memos, dels quals cap ha estat llegit." + +#: modules/commands/ms_info.cpp:77 +#, c-format +msgid "%s currently has 1 memo, and it has not yet been read." +msgstr "%s actualment te 1 memo i encara no ha estat llegit." + +#: modules/commands/ms_info.cpp:79 +#, c-format +msgid "%s currently has 1 memo." +msgstr "%s te 1 memo." + +#: modules/commands/ms_info.cpp:73 +#, c-format +msgid "%s currently has no memos." +msgstr "%s no te memos." + +#: modules/commands/os_forbid.cpp:344 +#, fuzzy, c-format +msgid "%s deleted from the %s forbid list." +msgstr "%s esborrada de la llista de paraules malsonants de %s." + +#: include/language.h:105 +#, fuzzy, c-format +msgid "%s for %s set to %s." +msgstr "vhost for %s set to %s." + +#: include/language.h:106 +#, fuzzy, c-format +msgid "%s for %s unset." +msgstr "Sucessor de %s desabilitat." + +#: modules/commands/ns_ajoin.cpp:176 +#, c-format +msgid "%s had an invalid key specified, and was thus ignored." +msgstr "" + +#: modules/commands/ms_info.cpp:111 +#, c-format +msgid "%s has no memo limit." +msgstr "%s no te límit per a memos." + +#: include/language.h:115 +#, fuzzy, c-format +msgid "%s has no memos." +msgstr "%s no te límit per a memos." + +#: include/language.h:118 +#, fuzzy, c-format +msgid "%s has no new memos." +msgstr "%s no te límit per a memos." + +#: modules/commands/ns_info.cpp:53 +#, c-format +msgid "%s is %s" +msgstr "%s es %s" + +#: modules/commands/ns_info.cpp:59 +#, fuzzy, c-format +msgid "%s is a Services Operator of type %s." +msgstr "%s is a services operator of type %s." + +#: modules/commands/cs_seen.cpp:281 +#, fuzzy, c-format +msgid "%s is a client on services." +msgstr "%s Esta actualment online." + +#: modules/commands/cs_seen.cpp:200 +#, fuzzy, c-format +msgid "%s is a network service." +msgstr "%s Esta actualment online." + +#: src/xline.cpp:407 +#, fuzzy, c-format +msgid "%s is already covered by %s." +msgstr "%s ja esta cobert per %s." + +#: modules/commands/ns_ajoin.cpp:170 +#, fuzzy, c-format +msgid "%s is already on %s's auto join list." +msgstr "%s afegit a la teva lllista d'accés." + +#: modules/commands/ns_info.cpp:56 +#, fuzzy, c-format +msgid "%s is an unconfirmed nickname." +msgstr "Aquest nickname no caducara." + +#: modules/commands/cs_flags.cpp:432 +#, c-format +msgid "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." +msgstr "" + +#: modules/commands/ns_info.cpp:74 +#, c-format +msgid "%s is currently online." +msgstr "%s Esta actualment online." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is disabled" +msgstr "%s is disabled" + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is enabled" +msgstr "%s is enable" + +#: modules/commands/os_dns.cpp:507 +#, fuzzy, c-format +msgid "%s is not a valid IP address." +msgstr "%s no es un tipus de ban valid." + +#: modules/commands/cs_log.cpp:167 modules/commands/cs_log.cpp:192 +#, fuzzy, c-format +msgid "%s is not a valid command." +msgstr "%s no es un tipus de ban valid." + +#: modules/commands/cs_log.cpp:198 +#, fuzzy, c-format +msgid "%s is not a valid logging method." +msgstr "%s no es un tipus de ban valid." + +#: modules/commands/ms_info.cpp:124 +#, c-format +msgid "%s is not notified of new memos." +msgstr "%s no es notificat per memos nous." + +#: modules/commands/ms_info.cpp:118 +#, c-format +msgid "%s is notified of new memos at logon and when they arrive." +msgstr "" +"%s es notificat per memos nous quant es connecta i quant li són enviats." + +#: modules/commands/ms_info.cpp:122 +#, c-format +msgid "%s is notified of new memos at logon." +msgstr "%s es notificat de nous memos quant es connecta." + +#: modules/commands/ms_info.cpp:120 +#, c-format +msgid "%s is notified when new memos arrive." +msgstr "%s es notificat quant nous memos li són enviats." + +#: modules/commands/cs_seen.cpp:232 +#, c-format +msgid "%s is on the channel right now (as %s)!" +msgstr "" + +#: modules/commands/cs_seen.cpp:221 +#, fuzzy, c-format +msgid "%s is on the channel right now!" +msgstr "%s inhabilitat(s) en el canal %s." + +#: modules/commands/cs_xop.cpp:434 +#, fuzzy, c-format +msgid "%s list for %s" +msgstr "Lllista d'accés per %s:" + +#: modules/commands/os_sxline.cpp:69 modules/commands/os_sxline.cpp:113 +#, fuzzy, c-format +msgid "%s list is empty." +msgstr "La llista AOP de %s esta buida." + +#: modules/commands/cs_mode.cpp:376 +#, fuzzy, c-format +msgid "%s locked on %s." +msgstr "%s no es notificat per memos nous." + +#: modules/extra/stats/cs_fantasy_stats.cpp:120 +#, fuzzy, c-format +msgid "%s not found." +msgstr "%s no trobat a la llista AOP de %s." + +#: modules/commands/os_config.cpp:79 +#, c-format +msgid "%s settings:" +msgstr "" + +#: modules/commands/cs_seen.cpp:255 +#, c-format +msgid "%s was last seen here %s ago." +msgstr "" + +#: modules/commands/ns_ajoin.cpp:213 +#, fuzzy, c-format +msgid "%s was not found on %s's auto join list." +msgstr "%s no trobat a la llista de kicks automàtics en el canal %s." + +#: modules/commands/ns_ajoin.cpp:221 +#, fuzzy, c-format +msgid "%s was removed from %s's auto join list." +msgstr "%s esborrat de la llista de kicks automàtics del canal %s." + +#: modules/commands/ms_set.cpp:64 +#, c-format +msgid "%s will not send you any notification of memos." +msgstr "%s no t'enviara cap notificació dels teus memos." + +#: modules/commands/ms_set.cpp:42 +#, c-format +msgid "%s will now notify you of memos when they are sent to you." +msgstr "%s ara te notificara dels teus memos quant se t'enviin." + +#: modules/commands/ms_set.cpp:30 +#, c-format +msgid "" +"%s will now notify you of memos when you log on and when they are sent to " +"you." +msgstr "" +"%s ara et notificara dels teus memos quant et conectis i quant et siguin " +"enviats." + +#: modules/commands/ms_set.cpp:36 +#, c-format +msgid "%s will now notify you of memos when you log on or unset /AWAY." +msgstr "" +"%s ara et notificara dels teus memos quant et conectis o treguis el teu /" +"AWAY." + +#: modules/commands/bs_bot.cpp:89 +#, c-format +msgid "%s!%s@%s (%s) added to the bot list." +msgstr "%s!%s@%s (%s) afegit a la llista de bots." + +#: modules/commands/ns_access.cpp:83 +#, fuzzy, c-format +msgid "%s's access list is empty." +msgstr "La llista d'accés de %s esta buida." + +#: modules/commands/ns_ajoin.cpp:96 +#, fuzzy, c-format +msgid "%s's auto join list is empty." +msgstr "La llista de kicks automàtics del canal %s esta buida." + +#: modules/commands/ns_ajoin.cpp:111 +#, fuzzy, c-format +msgid "%s's auto join list:" +msgstr " AKICK Manté la llista d'AutoKick" + +#: modules/commands/ns_cert.cpp:242 +#, fuzzy, c-format +msgid "%s's certificate list is empty." +msgstr "Your access list is empty." + +#: modules/commands/ms_info.cpp:99 modules/commands/ms_info.cpp:106 +#, c-format +msgid "%s's memo limit is %d, and may not be changed." +msgstr "El límit de memos per a %s es %d, i no pot ser canviat." + +#: modules/commands/ms_info.cpp:101 modules/commands/ms_info.cpp:108 +#, c-format +msgid "%s's memo limit is %d." +msgstr "El límit de memos per a %s es %d." + +#: src/misc.cpp:363 +#, c-format +msgid "(%s ago)" +msgstr "" + +#: src/misc.cpp:365 +#, c-format +msgid "(%s from now)" +msgstr "" + +#: modules/commands/os_dns.cpp:244 +msgid "(Split)" +msgstr "" + +#: modules/commands/os_info.cpp:268 +#, c-format +msgid "(by %s on %s) %s" +msgstr "" + +#: modules/commands/cs_access.cpp:710 +#, fuzzy +msgid "(disabled)" +msgstr "%s is enable" + +#: modules/commands/cs_access.cpp:712 +msgid "(founder only)" +msgstr "" + +#: src/misc.cpp:367 +msgid "(now)" +msgstr "" + +#: modules/commands/os_defcon.cpp:168 +msgid "* AKILL any new clients connecting" +msgstr "* AKILL any new clients connecting" + +#: modules/commands/os_defcon.cpp:158 +#, fuzzy, c-format +msgid "* Force channel modes (%s) to be set on all channels" +msgstr "* Force Chan Modes (%s) to be set on all channels" + +#: modules/commands/os_defcon.cpp:164 +#, fuzzy +msgid "* Ignore non-opers with a message" +msgstr "* Ignore any non-opers with message" + +#: modules/commands/os_defcon.cpp:162 +#, fuzzy +msgid "* Kill any new clients connecting" +msgstr "* Kill any NEW clients connecting" + +#: modules/commands/os_defcon.cpp:156 +#, fuzzy +msgid "* No mode lock changes" +msgstr "* No MLOCK changes" + +#: modules/commands/os_defcon.cpp:152 +msgid "* No new channel registrations" +msgstr "* No new channel registrations" + +#: modules/commands/os_defcon.cpp:170 +msgid "* No new memos sent" +msgstr "* No new memos sent" + +#: modules/commands/os_defcon.cpp:154 +msgid "* No new nick registrations" +msgstr "* No new nick registrations" + +#: modules/commands/os_defcon.cpp:166 +msgid "* Silently ignore non-opers" +msgstr "* Silently ignore non-opers" + +#: modules/commands/os_defcon.cpp:160 +#, c-format +msgid "* Use the reduced session limit of %d" +msgstr "* Use the reduced session limit of %d" + +#: modules/commands/cs_seen.cpp:319 +#, c-format +msgid ", but %s mysteriously dematerialized." +msgstr "" + +#: modules/commands/cs_seen.cpp:317 +#, fuzzy, c-format +msgid ". %s is still online." +msgstr "%s Esta actualment online." + +#: include/language.h:87 +msgid "" +msgstr "" + +#: modules/commands/ns_set.cpp:504 +#, fuzzy, c-format +msgid "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." +msgstr "" +"A passcode has been sent to %s, please type /msg %s confirm to " +"complete registration" + +#: modules/commands/ms_sendall.cpp:45 +msgid "A massmemo has been sent to all registered users." +msgstr "A massmemo has been sent to all registered users." + +#: modules/commands/hs_request.cpp:285 +msgid "" +"A memo informing the user will also be sent, which includes the reason for " +"the rejection if supplied." +msgstr "" + +#: modules/commands/hs_request.cpp:229 +msgid "A memo informing the user will also be sent." +msgstr "" + +#: modules/commands/ms_read.cpp:42 +#, c-format +msgid "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." +msgstr "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." + +#: include/language.h:123 +msgid "A vHost ident must be in the format of a valid ident." +msgstr "" + +#: include/language.h:122 +msgid "A vHost must be in the format of a valid hostname." +msgstr "" + +#: modules/commands/os_ignore.cpp:342 +#, fuzzy +msgid "ADD expiry {nick|mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_oper.cpp:70 +msgid "ADD oper type" +msgstr "" + +#: modules/commands/os_info.cpp:102 +#, fuzzy +msgid "ADD target info" +msgstr "GROUP grup clau" + +#: modules/commands/os_news.cpp:278 +msgid "ADD text" +msgstr "" + +#: modules/commands/os_session.cpp:523 +#, fuzzy +msgid "ADD [+expiry] mask limit reason" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/ns_ajoin.cpp:231 +#, fuzzy +msgid "ADD [nickname] channel [key]" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/ns_access.cpp:102 +#, fuzzy +msgid "ADD [nickname] mask" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/ns_cert.cpp:258 +#, fuzzy +msgid "ADD [nickname] [fingerprint]" +msgstr "FORBID nickname rao" + +#: modules/commands/os_sxline.cpp:659 modules/commands/os_akill.cpp:386 +#, fuzzy +msgid "ADD [+expiry] mask reason" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/os_sxline.cpp:425 +#, fuzzy +msgid "ADD [+expiry] mask:reason" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/os_forbid.cpp:157 +#, fuzzy +msgid "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/os_dns.cpp:665 +msgid "ADDIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:663 +msgid "ADDSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:661 +msgid "ADDZONE zone.name" +msgstr "" + +#: modules/commands/cs_akick.cpp:38 +#, c-format +msgid "AKICK ENFORCE for %s complete; %d users were affected." +msgstr "AKICK ENFORCE en %s completa; %d usuaris afectats." + +#: modules/commands/os_chankill.cpp:21 +#, fuzzy +msgid "AKILL all users on a specific channel" +msgstr " CHANKILL AKILL all users on a specific channel" + +#: modules/commands/os_akill.cpp:222 modules/commands/os_akill.cpp:339 +#: modules/commands/os_akill.cpp:353 +msgid "AKILL list is empty." +msgstr "La llista de AKILLS esta buida." + +#: modules/commands/bs_kick.cpp:1211 modules/commands/bs_kick.cpp:1213 +#: modules/commands/bs_kick.cpp:1216 +#, fuzzy +msgid "AMSG kicker" +msgstr " Kicker per majuscules : %s" + +#: modules/commands/ns_alist.cpp:48 +#, fuzzy +msgid "Access" +msgstr "Lllista d'accés:" + +#: include/language.h:72 +#, fuzzy +msgid "Access denied." +msgstr "Lllista d'accés:" + +#: modules/commands/cs_status.cpp:58 +#, fuzzy, c-format +msgid "Access for %s on %s:" +msgstr "Nivell d'accés per a %s en %s cambiada a %d." + +#: include/language.h:107 +#, fuzzy, c-format +msgid "Access level must be between %d and %d inclusive." +msgstr "El nivell ha d'estar entre %d i %d inclosos." + +#: modules/commands/cs_access.cpp:108 +msgid "Access level must be non-zero." +msgstr "El nivell de accés no pot ser zero." + +#: modules/commands/cs_access.cpp:694 +#, c-format +msgid "Access level settings for channel %s:" +msgstr "Opcions del nivell d'accés pel canal %s:" + +#: modules/commands/cs_access.cpp:734 +#, c-format +msgid "Access levels for %s reset to defaults." +msgstr "Nivells d'accés per a %s canviats als valors originals." + +#: modules/commands/cs_access.cpp:439 modules/commands/ns_access.cpp:87 +#, fuzzy, c-format +msgid "Access list for %s:" +msgstr "Lllista d'accés per %s:" + +#: modules/commands/help.cpp:166 +#, c-format +msgid "" +"Access to this command requires the permission %s to be present in your " +"opertype." +msgstr "" +"Access to this command requires the permission %s to be present in your " +"opertype." + +#: modules/commands/ns_cert.cpp:368 modules/commands/ns_cert.cpp:392 +#: modules/commands/ns_identify.cpp:94 +#, c-format +msgid "" +"Account %s has already reached the maximum number of simultaneous logins " +"(%u)." +msgstr "" + +#: modules/commands/cs_set.cpp:683 +#, fuzzy +msgid "Activate security features" +msgstr " SECURE Activa les opcions de seguretat de %s" + +#: modules/commands/hs_request.cpp:227 +msgid "Activate the requested vHost for the given nick." +msgstr "" + +#: modules/commands/hs_on.cpp:55 +#, fuzzy +msgid "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." +msgstr "" +"Syntax: ON\n" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real IP address." + +#: modules/commands/hs_on.cpp:19 +#, fuzzy +msgid "Activates your assigned vhost" +msgstr " ON Activates your assigned vhost" + +#: modules/commands/os_info.cpp:243 +msgid "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." +msgstr "" + +#: modules/commands/os_dns.cpp:515 +#, c-format +msgid "Added IP %s to %s." +msgstr "" + +#: modules/commands/os_forbid.cpp:239 +#, c-format +msgid "Added a forbid on %s of type %s to expire on %s." +msgstr "" + +#: modules/commands/os_info.cpp:164 +#, fuzzy, c-format +msgid "Added info to %s." +msgstr "Memo enviat a %s." + +#: modules/commands/os_news.cpp:34 +#, fuzzy +msgid "Added new logon news item." +msgstr "Noves notícies d'entrada afegida (#%d)." + +#: modules/commands/os_news.cpp:44 +#, fuzzy +msgid "Added new oper news item." +msgstr "Nueva noticia de oper anadida (#%d)." + +#: modules/commands/os_news.cpp:54 +#, fuzzy +msgid "Added new random news item." +msgstr "Nova noticia a l'atzar afegida (#%d)." + +#: modules/commands/os_dns.cpp:395 +#, fuzzy, c-format +msgid "Added server %s." +msgstr "Uplink server: %s" + +#: modules/commands/os_dns.cpp:300 +#, c-format +msgid "Added zone %s." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:257 +msgid "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." +msgstr "" + +#: modules/commands/ns_register.cpp:104 +msgid "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." +msgstr "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." + +#: modules/pseudoclients/botserv.cpp:172 +#, c-format +msgid "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" +msgstr "" + +#: modules/commands/os_noop.cpp:58 +#, c-format +msgid "All O:lines of %s have been reset." +msgstr "Totes les linees O de %s han estat esborrades." + +#: modules/commands/cs_clone.cpp:71 +#, fuzzy, c-format +msgid "All akick entries from %s have been cloned to %s." +msgstr "All vhost's in the group %s have been set to %s" + +#: modules/commands/help.cpp:57 +#, fuzzy, c-format +msgid "All available commands for %s:" +msgstr "No existeix ajuda per %s." + +#: modules/commands/cs_clone.cpp:96 +#, fuzzy, c-format +msgid "All badword entries from %s have been cloned to %s." +msgstr "All vhost's in the group %s have been set to %s" + +#: modules/commands/cs_clone.cpp:108 +#, fuzzy, c-format +msgid "All level entries from %s have been cloned into %s." +msgstr "All vhost's in the group %s have been set to %s" + +#: modules/commands/os_news.cpp:38 +msgid "All logon news items deleted." +msgstr "Totes les notícies d'entrada esborrades." + +#: modules/commands/ms_del.cpp:115 +#, c-format +msgid "All memos for channel %s have been deleted." +msgstr "All memos for channel %s have been deleted." + +#: modules/commands/os_mode.cpp:61 +#, c-format +msgid "All modes cleared on %s." +msgstr "" + +#: modules/commands/ns_register.cpp:258 modules/commands/ns_register.cpp:389 +msgid "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." +msgstr "" + +#: modules/commands/ms_del.cpp:119 +msgid "All of your memos have been deleted." +msgstr "Tots els teus memos han estat esborrats." + +#: modules/commands/os_news.cpp:48 +msgid "All oper news items deleted." +msgstr "Totes les notícies de oper esborrades." + +#: modules/commands/os_noop.cpp:41 +#, fuzzy, c-format +msgid "All operators from %s have been removed." +msgstr "Totes les linees O de %s han estat esborrades." + +#: modules/commands/os_news.cpp:58 +msgid "All random news items deleted." +msgstr "Totes les notícies al azar esborrades." + +#: modules/commands/cs_clone.cpp:211 +#, fuzzy, c-format +msgid "All settings from %s have been cloned to %s." +msgstr "All vhost's in the group %s have been set to %s" + +#: modules/commands/cs_sync.cpp:41 +#, fuzzy, c-format +msgid "All user modes on %s have been synced." +msgstr "Totes les linees O de %s han estat esborrades." + +#: modules/commands/hs_group.cpp:60 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s." +msgstr "All vhost's in the group %s have been set to %s" + +#: modules/commands/hs_group.cpp:58 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s@%s." +msgstr "All vhost's in the group %s have been set to %s@%s" + +#: src/access.cpp:40 +msgid "Allowed to (de)halfop him/herself" +msgstr "" + +#: src/access.cpp:39 +msgid "Allowed to (de)halfop users" +msgstr "" + +#: src/access.cpp:48 +msgid "Allowed to (de)op him/herself" +msgstr "" + +#: src/access.cpp:47 +msgid "Allowed to (de)op users" +msgstr "" + +#: src/access.cpp:50 +msgid "Allowed to (de)owner him/herself" +msgstr "" + +#: src/access.cpp:49 +msgid "Allowed to (de)owner users" +msgstr "" + +#: src/access.cpp:52 +msgid "Allowed to (de)protect him/herself" +msgstr "" + +#: src/access.cpp:51 +msgid "Allowed to (de)protect users" +msgstr "" + +#: src/access.cpp:59 +msgid "Allowed to (de)voice him/herself" +msgstr "" + +#: src/access.cpp:58 +msgid "Allowed to (de)voice users" +msgstr "" + +#: src/access.cpp:27 +msgid "Allowed to assign/unassign a bot" +msgstr "" + +#: src/access.cpp:34 +msgid "Allowed to ban users" +msgstr "" + +#: src/access.cpp:56 +#, fuzzy +msgid "Allowed to change channel topics" +msgstr "%s changed your usermodes." + +#: src/access.cpp:41 +msgid "Allowed to get full INFO output" +msgstr "" + +#: src/access.cpp:36 +msgid "Allowed to issue commands restricted to channel founders" +msgstr "" + +#: src/access.cpp:33 +msgid "Allowed to modify channel badwords list" +msgstr "" + +#: src/access.cpp:24 +#, fuzzy +msgid "Allowed to modify the access list" +msgstr "%s esborrat de la llista d'accés de %s." + +#: src/access.cpp:44 +msgid "Allowed to read channel memos" +msgstr "" + +#: src/access.cpp:54 +#, fuzzy +msgid "Allowed to set channel settings" +msgstr "* No new channel registrations" + +#: src/access.cpp:57 +msgid "Allowed to unban users" +msgstr "" + +#: src/access.cpp:37 +msgid "Allowed to use GETKEY command" +msgstr "" + +#: src/access.cpp:53 +msgid "Allowed to use SAY and ACT commands" +msgstr "" + +#: src/access.cpp:35 +#, fuzzy +msgid "Allowed to use fantasy commands" +msgstr " PEACE Regula l'ús de comandes critiques" + +#: src/access.cpp:26 +#, fuzzy +msgid "Allowed to use the AKICK command" +msgstr "You cannot use this command." + +#: src/access.cpp:42 +msgid "Allowed to use the INVITE command" +msgstr "" + +#: src/access.cpp:43 +#, fuzzy +msgid "Allowed to use the KICK command" +msgstr "You cannot use this command." + +#: src/access.cpp:45 +#, fuzzy +msgid "Allowed to use the MODE command" +msgstr "You cannot use this command." + +#: src/access.cpp:25 +#, fuzzy +msgid "Allowed to view the access list" +msgstr "%s esborrat de la llista d'accés de %s." + +#: modules/commands/gl_global.cpp:42 +#, fuzzy, c-format +msgid "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." +msgstr "" +"Sintàxi: GLOBAL missatge\n" +"\n" +"Permet als Administrators a enviar missatges als usuaris de\n" +"la xarxa. El missatge sera enviat desde el nick %s." + +#: modules/commands/os_mode.cpp:133 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." +msgstr "" +"Sintàxi: MODE canal Modes\n" +"\n" +"Permet als operadors de serveis establir modes de canal\n" +"per a qualsevol canal. Els parametres son els mateixos que per la\n" +"comando estandart /MODE.\n" +"\n" +"Limitat a operadors de serveis." + +#: modules/commands/os_mode.cpp:173 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." +msgstr "" +"Sintàxi: MODE canal Modes\n" +"\n" +"Permet als operadors de serveis establir modes de canal\n" +"per a qualsevol canal. Els parametres son els mateixos que per la\n" +"comando estandart /MODE.\n" +"\n" +"Limitat a operadors de serveis." + +#: modules/commands/bs_bot.cpp:352 +#, fuzzy +msgid "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." +msgstr "" +"Sintaxi: BOT ADD nick usuari host real\n" +" BOT CHANGE nick-ant nick-nue [usuari [host [real]]]\n" +" BOT DEL nick\n" +"\n" +"Permet als administradors de serveis crear, modificar\n" +"i esborrar bots que usuaris podran usar en els seus propis\n" +"canals.\n" +"\n" +"BOT ADD afegeix un bot con el nickname, usuari, host\n" +"i nombre reial donats. Ja que no es fan comprovacions \n" +"d'integritat per aquests parametres, tingues molta cura.\n" +"BOT CHANGE permet cambiar el nickname, usuari, host\n" +"o nom real d'un bot sense tenir que esborrar-lo (i la\n" +"informació associada a ell).\n" +"BOT DEL esborra el bot donat de la llista de bots.\n" +"\n" +"Nota: Si fas un bot amb un nick ja enregistrat,\n" +"sera eliminat. A més, si un usuari està actualment\n" +"usant el nick, serà killejat." + +#: modules/commands/os_oline.cpp:56 +#, fuzzy +msgid "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." +msgstr "" +"Syntax: OLINE user flags\n" +"\n" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." + +#: modules/commands/os_ignore.cpp:370 +#, fuzzy +msgid "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." +msgstr "" +"Syntax: IGNORE {ADD|DEL|LIST|CLEAR} [time] [nick | mask]\n" +"\n" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes, \n" +"h for hours and d for days. \n" +"Combinations of these units are not permitted. To make\n" +"Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format user@host\n" +"or nick!user@host, everything else will be considered a nick.\n" +"Wildcards are permitted.\n" +"\n" +"Ignores will not be enforced on IRC Operators." + +#: modules/commands/os_akill.cpp:420 +#, fuzzy +msgid "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Sintàxi: AKILL ADD [+expiració] mascara raó\n" +" AKILL DEL {mascara | nom | llista}\n" +" AKILL LIST [mascara | llista]\n" +" AKILL VIEW [mascara | llista]\n" +" AKILL CLEAR\n" +"\n" +"Permet als operadors de serveis manipular la llista de\n" +"AKILLS. Si un usuari coincideix amb una mascara en la\n" +"llista de AKILLS i s'esta intentant connectar, els serveis enviaran\n" +"un KILL a aquest usuari i, en tipus de servidors soportats,\n" +"notificara a tots els servidors que afegeixin un ban (linea K)\n" +"per la mascara de l'usuari.\n" +"\n" +"AKILL ADD afegeix la mascara usuari@host especificada a la llista\n" +"de AKILLS per la raó especificada (que HA DE SER especificada).\n" +"expiració es especificada com un sencer seguit de\n" +" d (dies), h (hores), o m (minuts). Combinacions (com\n" +"1h30m) no estan permesses. Si un especificador d'unitats no\n" +"es inclòs, per defecte seran dies (o sigui +30 nomès\n" +"significa 30 dies). Per afegir un AKILL que no caduqui, utilitza +0.\n" +"Si la mascara a afegir comença amb un +, s'ha d'especificar\n" +"un temps d'expiració. El temps d'expiració per defecte actual de AKILLS\n" +"pot ser consultat amb la comanda STATS AKILL.\n" +"\n" +"La comanda AKILL DEL esborra la mascara especificada de la llista\n" +"d'AKILLS si esta present. Si s'especifica una llista de noms,\n" +"aquestes instàncies son esborrades. (Veure l'exemple per LIST \n" +"especificat més endavant.)\n" +"\n" +"La comanda AKILL LIST mostra la llista d'AKILLS. \n" +"Si s'especifica una mascara, nomès les instàncies coincidents\n" +"amb la mascara són mostrades. Si s'especifica una llista de noms,\n" +"nomès aquestes instàncies son mostrades; per exemple:\n" +"\n" +" AKILL LIST 2-5,7-9\n" +" Llista les instàncies de AKILL enumerades de 2 a 5 i de 7 \n" +" a 9.\n" +" \n" +"AKILL VIEW es una versió més verbal d'AKILL LIST, i \n" +"mostrara qui va afegir un AKILL, la data en que va ser afegit,\n" +"i quan caducara, així com tambe la mascara usuari@host\n" +"i la raó.\n" +"\n" +"AKILL CLEAR neteja totes les instàncies de la llista d'AKILLS.\n" +"\n" +"Limitat a operadors de serveis." + +#: modules/commands/os_sxline.cpp:436 +msgid "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." +msgstr "" + +#: modules/commands/os_sxline.cpp:670 +msgid "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." +msgstr "" + +#: modules/commands/os_session.cpp:551 +msgid "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." +msgstr "" + +#: modules/commands/os_session.cpp:270 +#, fuzzy +msgid "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." +msgstr "" +"Sintaxis: SESSION LIST umbral\n" +" SESSION VIEW host\n" +"\n" +"Permet als administradors de serveis veure la llista de sessions.\n" +"\n" +"SESSION LIST llista hosts amb un mínim de umbral sessions.\n" +"L'umbral ha de ser un numero superior a 1. Això es per a prevenir\n" +"llistats accidentals del gran nombre de hosts de sessió.\n" +"SESSION VIEW mostra informació detallada sobre un host \n" +"específic - incloent el compte de sessió i el límit de sessió\n" +"actual.\n" +"El valor host no pot incluir comodins.\n" +"\n" +"Mireu l'ajuda sobre EXCEPTION per a més informació sobre\n" +"límits de sessió i como establir-los per a hosts i grups específics\n" +"d'ara endavant. \n" +"\n" +"Limitat a administradors de serveis." + +#: modules/commands/cs_topic.cpp:193 +msgid "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do " +"not have\n" +"the TOPIC privilege." +msgstr "" + +#: modules/commands/os_kick.cpp:62 +#, fuzzy, c-format +msgid "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" +msgstr "" +"Sintàxi: KICK canal usuari raó\n" +"\n" +"Permet als IRCops kickejar un usuari de qualsevol\n" +"canal. Els parametres son els mateixos que per la comanda\n" +"/KICK. El missatge de kick tindra el nickname del IRCop\n" +"que envia la comanda KICK; per exemple:\n" +"\n" +"*** SpamMan ha estat kickejat del canal #aujac per %s (cistus (Flood))\n" +"\n" +"Limitat a operadors de serveis." + +#: modules/commands/cs_set.cpp:33 +#, fuzzy +msgid "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" +msgstr "" +"Sintaxis: SET canal opció parametres\n" +"\n" +"Li permet al fundador del canal establir varies opcions\n" +"del canal i altres informacions.\n" +"\n" +"Opcions disponibles:" + +#: modules/commands/os_oper.cpp:250 +msgid "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." +msgstr "" + +#: modules/commands/os_config.cpp:127 +msgid "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" +msgstr "" + +#: modules/commands/ns_set.cpp:992 +#, fuzzy +msgid "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." +msgstr "" +"Syntax: SASET nickname MSG {ON | OFF}\n" +"\n" +"Allows you to choose the way Services are communicating with \n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." + +#: modules/commands/ns_set.cpp:966 +#, fuzzy, c-format +msgid "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." +msgstr "" +"Sintaxis: SET MSG {ON | OFF}\n" +"\n" +"Et permet escollir la forma en la que els serveis es\n" +"comunicaran amb tu. Amb MSG establert, els serveis\n" +"utilitzaran msgs, de l'altra forma utilitzaran notícies. " + +#: modules/commands/ms_ignore.cpp:113 +msgid "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." +msgstr "" + +#: modules/commands/os_kill.cpp:48 +msgid "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." +msgstr "" + +#: modules/commands/ns_info.cpp:252 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Syntax: SASET nickname HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}\n" +"\n" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." + +#: modules/commands/ns_info.cpp:223 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Sintaxis: SET HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}\n" +"\n" +"Permet prevenir que certa informació sobre el teu nick sigui donada\n" +"quant es sol.licitada mitjançant la comanda %s INFO.\n" +"Pots ocultar la teva adreça e-mail (EMAIL), l'ultima\n" +"mascara usuari@host (USERMASK), i el teu últim missatge\n" +"quit (QUIT).\n" +"El segon parametre especifica si la informació ha de ser\n" +"ocultada (OFF) o mostrada (ON)." + +#: modules/commands/bs_info.cpp:118 +#, fuzzy, c-format +msgid "Allows you to see %s information about a channel or a bot" +msgstr "" +"INFO Allows you to see BotServ information about a channel or " +"a bot" + +#: modules/commands/bs_info.cpp:108 +#, fuzzy, c-format +msgid "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." +msgstr "" +"Sintàxi: INFO {canal | nick}\n" +"\n" +"Permet veure la informació de %s sobre un canal o\n" +"bot. Si el parametre es un canal, rebràs informació\n" +"així como kickers activats. Si el parametre es un nick,\n" +"rebràs informació sobre el bot, així com temps\n" +"de creació o nom de canals en els que aquest estigui." + +#: modules/commands/cs_xop.cpp:567 +msgid "" +"Alternative methods of modifying channel access lists are\n" +"available. " +msgstr "" + +#: modules/commands/hs_request.cpp:191 +#, fuzzy +msgid "Approve the requested vHost of a user" +msgstr " DEL Delete the vhost of another user" + +#: modules/commands/ns_drop.cpp:68 +#, fuzzy +msgid "As a Services Operator, you may drop any nick." +msgstr "%s is a services operator of type %s." + +#: modules/commands/bs_assign.cpp:19 +#, fuzzy +msgid "Assigns a bot to a channel" +msgstr "ASSIGN Assigna un bot a un canal" + +#: modules/commands/bs_assign.cpp:78 +#, fuzzy +msgid "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." +msgstr "" +"Sintàxi: ASSIGN canal nick\n" +"\n" +"Assigna un bot especificat per nick al canal.\n" +"Desprès d'això pots configurar el bot segons\n" +"les teves necessitats." + +#: data/chanserv.example.conf:1197 +#, fuzzy +msgid "Associate a URL with the channel" +msgstr "ASSIGN Assigna un bot a un canal" + +#: data/nickserv.example.conf:594 +msgid "Associate a URL with this account" +msgstr "" + +#: data/nickserv.example.conf:593 +#, fuzzy +msgid "Associate a URL with your account" +msgstr " GREET Associa un salutació amb el teu nickname" + +#: modules/commands/greet.cpp:83 +#, fuzzy +msgid "Associate a greet message with your nickname" +msgstr " GREET Associa un salutació amb el teu nickname" + +#: data/chanserv.example.conf:1198 +#, fuzzy +msgid "Associate an E-mail address with the channel" +msgstr " EMAIL Associa un E-mail amb el teu nickname" + +#: modules/commands/ns_set.cpp:452 +#, fuzzy +msgid "Associate an E-mail address with your nickname" +msgstr " EMAIL Associa un E-mail amb el teu nickname" + +#: modules/commands/os_info.cpp:101 +#, fuzzy +msgid "Associate oper info with a nick or channel" +msgstr "ASSIGN Assigna un bot a un canal" + +#: modules/commands/ns_set.cpp:558 +#, fuzzy +msgid "Associates the given E-mail address with the nickname." +msgstr " EMAIL Associa un E-mail amb el teu nickname" + +#: modules/commands/ns_set.cpp:533 +#, fuzzy +msgid "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." +msgstr "" +"Sintaxis: SET EMAIL direccion\n" +"\n" +"Associa el E-mail donat amb el teu nickname. L'e-mail\n" +"sera mostrat quant algu demani informació\n" +"sobre el teu nick amb la comanda INFO." + +#: modules/commands/ns_set.cpp:1315 +msgid "Auto-op" +msgstr "Auto-op" + +#: modules/commands/cs_akick.cpp:374 +#, c-format +msgid "Autokick list for %s:" +msgstr "Llista de kicks automàtics pel canal %s:" + +#: src/access.cpp:29 +msgid "Automatic channel operator status upon join" +msgstr "" + +#: src/access.cpp:28 +msgid "Automatic halfop upon join" +msgstr "" + +#: src/access.cpp:30 +msgid "Automatic owner upon join" +msgstr "" + +#: src/access.cpp:31 +msgid "Automatic protect upon join" +msgstr "" + +#: src/access.cpp:32 +msgid "Automatic voice on join" +msgstr "" + +#: modules/commands/os_oper.cpp:196 +#, fuzzy, c-format +msgid "Available commands for %s:" +msgstr "No existeix ajuda per %s." + +#: modules/commands/os_oper.cpp:175 +#, fuzzy +msgid "Available opertypes:" +msgstr "No existeix ajuda per %s." + +#: modules/commands/os_oper.cpp:218 +#, c-format +msgid "Available privileges for %s:" +msgstr "" + +#: modules/commands/cs_enforce.cpp:162 +msgid "BANS enforced by " +msgstr "" + +#: modules/commands/bs_kick.cpp:1121 modules/commands/bs_kick.cpp:1123 +#: modules/commands/bs_kick.cpp:1126 +#, fuzzy +msgid "Bad words kicker" +msgstr " Kicker per paraules malsonants : %s" + +#: modules/commands/bs_badwords.cpp:252 +#, fuzzy, c-format +msgid "Bad words list for %s:" +msgstr "Lllista d'accés per %s:" + +#: modules/commands/bs_badwords.cpp:364 +msgid "Bad words list is now empty." +msgstr "La llista de paraules malsonants esta ara buida." + +#: modules/commands/bs_set.cpp:129 +msgid "Ban expiry may not be longer than 1 day." +msgstr "" + +#: modules/commands/cs_ban.cpp:140 modules/commands/cs_ban.cpp:175 +#, fuzzy, c-format +msgid "Ban on %s expires in %s." +msgstr "El bot %s ja existeix." + +#: modules/commands/cs_info.cpp:60 +msgid "Ban type" +msgstr "" + +#: modules/commands/cs_set.cpp:174 +#, c-format +msgid "Ban type for channel %s is now #%d." +msgstr "Tipus de ban pel canal %s es ara #%d." + +#: modules/commands/cs_ban.cpp:39 +#, fuzzy +msgid "Bans a given nick or mask on a channel" +msgstr " BAN Bans a selected nick on a channel" + +#: modules/commands/cs_ban.cpp:227 +#, fuzzy +msgid "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." +msgstr "" +"Sintàxi: BAN #canal nick [raó]\n" +"\n" +"Baneja un nick seleccionat en un canal.\n" +"\n" +"Per defecte, limitat a AOPs o aquells amb nivell d'\n" +"accés 5 i major en el canal." + +#: modules/commands/cs_enforce.cpp:166 +#, fuzzy, c-format +msgid "Bans enforced on %s." +msgstr "%s no es notificat per memos nous." + +#: modules/commands/bs_kick.cpp:1131 modules/commands/bs_kick.cpp:1133 +#: modules/commands/bs_kick.cpp:1136 +#, fuzzy +msgid "Bolds kicker" +msgstr " Kicker per negretes : %s" + +#: modules/commands/bs_bot.cpp:26 modules/commands/bs_bot.cpp:175 +#, c-format +msgid "Bot %s already exists." +msgstr "El bot %s ja existeix." + +#: include/language.h:119 +#, fuzzy, c-format +msgid "Bot %s does not exist." +msgstr "El bot %s ja existeix." + +#: modules/commands/bs_assign.cpp:71 modules/commands/bs_assign.cpp:246 +#, c-format +msgid "Bot %s has been assigned to %s." +msgstr "El bot %s ha estat assignat al canal %s." + +#: modules/commands/bs_bot.cpp:228 +#, fuzzy, c-format +msgid "Bot %s has been changed to %s!%s@%s (%s)." +msgstr "El bot %s ha estat canviat a %s!%s@%s (%s)" + +#: modules/commands/bs_bot.cpp:262 +#, c-format +msgid "Bot %s has been deleted." +msgstr "El bot %s ha estat esborrat." + +#: modules/commands/bs_assign.cpp:63 modules/commands/bs_assign.cpp:241 +#, c-format +msgid "Bot %s is already assigned to channel %s." +msgstr "Bot %s is already assigned to channel %s." + +#: modules/commands/bs_kick.cpp:832 +#, c-format +msgid "Bot will kick ops on channel %s." +msgstr "Bot kickejara ops en el canal %s." + +#: modules/commands/bs_kick.cpp:897 +#, c-format +msgid "Bot will kick voices on channel %s." +msgstr "Bot kickejara voices en el canal %s." + +#: modules/commands/bs_kick.cpp:824 +#, c-format +msgid "Bot won't kick ops on channel %s." +msgstr "Bot no kickejara ops en el canal %s." + +#: modules/commands/bs_kick.cpp:889 +#, c-format +msgid "Bot won't kick voices on channel %s." +msgstr "Bot no kickejara voices en el canal %s." + +#: modules/commands/bs_bot.cpp:118 +#, fuzzy, c-format +msgid "Bot %s is not changeable." +msgstr "Mode no bot ara activat en el canal %s." + +#: modules/commands/bs_bot.cpp:254 +#, fuzzy, c-format +msgid "Bot %s is not deletable." +msgstr "El bot %s ha estat esborrat." + +#: modules/commands/bs_set.cpp:141 +#, c-format +msgid "Bot bans will automatically expire after %s." +msgstr "" + +#: modules/commands/bs_set.cpp:139 +#, fuzzy +msgid "Bot bans will no longer automatically expire." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/bs_bot.cpp:46 modules/commands/bs_bot.cpp:138 +#, fuzzy, c-format +msgid "Bot hosts may only be %d characters long." +msgstr "Bot Hosts may only contain %d characters." + +#: modules/commands/bs_bot.cpp:64 modules/commands/bs_bot.cpp:167 +#, fuzzy +msgid "Bot hosts may only contain valid host characters." +msgstr "Bot Hosts may only contain valid host characters." + +#: modules/commands/bs_bot.cpp:40 modules/commands/bs_bot.cpp:132 +#, fuzzy, c-format +msgid "Bot idents may only be %d characters long." +msgstr "Bot Idents may only contain %d characters." + +#: modules/commands/bs_bot.cpp:58 modules/commands/bs_bot.cpp:161 +#, fuzzy +msgid "Bot idents may only contain valid ident characters." +msgstr "Bot Idents may only contain valid characters." + +#: include/language.h:121 +#, fuzzy, c-format +msgid "Bot is not on channel %s." +msgstr "Bot kickejara ops en el canal %s." + +#: modules/commands/bs_botlist.cpp:51 +msgid "Bot list:" +msgstr "Llista de bots:" + +#: modules/commands/bs_info.cpp:87 +msgid "Bot nick" +msgstr "" + +#: modules/commands/bs_bot.cpp:34 modules/commands/bs_bot.cpp:126 +#, fuzzy, c-format +msgid "Bot nicks may only be %d characters long." +msgstr "Bot Idents may only contain %d characters." + +#: modules/commands/bs_bot.cpp:52 modules/commands/bs_bot.cpp:155 +#, fuzzy +msgid "Bot nicks may only contain valid nick characters." +msgstr "Bot Nicks may only contain valid nick characters." + +#: modules/commands/bs_kick.cpp:225 +#, fuzzy, c-format +msgid "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." +msgstr "" +"Bot will now kick italics, and will place a ban after\n" +"%d kicks for the same user." + +#: modules/commands/bs_kick.cpp:228 +#, fuzzy, c-format +msgid "Bot will now kick for %s." +msgstr "El bot ara kickjeara negretes." + +#: modules/commands/bs_kick.cpp:416 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." +msgstr "" +"El bot ara kickejara majusculas (han de ser al menys\n" +"%d caràcters i %d%% del missatge senser), i banegara\n" +"després de %d kicks al mateix usuari." + +#: modules/commands/bs_kick.cpp:420 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." +msgstr "" +"El bot ara kickejara majuscules (han de ser al menys\n" +"%d caràcters i %d%% del missatge senser)." + +#: modules/commands/bs_kick.cpp:551 +#, fuzzy, c-format +msgid "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." +msgstr "" +"El bot ara kickejara flood (%d linees in %d segons), i \n" +"banejara després de %d kicks al mateix usuari." + +#: modules/commands/bs_kick.cpp:554 +#, fuzzy, c-format +msgid "Bot will now kick for flood (%d lines in %d seconds)." +msgstr "El bot ara kickejara flood (%d linees en %d segons)." + +#: modules/commands/bs_kick.cpp:677 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"El bot ara kickejara repeticions (usuaris que repeteixin %d vegades\n" +"el mateix), i banejara després de %d \n" +"kicks al mateix usuari." + +#: modules/commands/bs_kick.cpp:687 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." +msgstr "" +"El bot ara kickejara repeticions (usuaris que repeteixin %d vegades\n" +"el mateix)." + +#: modules/commands/bs_kick.cpp:673 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"El bot ara kickejara repeticions (usuaris que repeteixin %d vegades\n" +"el mateix), i banejara després de %d \n" +"kicks al mateix usuari." + +#: modules/commands/bs_kick.cpp:684 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." +msgstr "" +"El bot ara kickejara repeticions (usuaris que repeteixin %d vegades\n" +"el mateix)." + +#: modules/commands/bs_kick.cpp:239 +#, fuzzy, c-format +msgid "Bot won't kick for %s anymore." +msgstr "El bot ja no kickejara majuscules." + +#: modules/commands/bs_kick.cpp:426 +#, fuzzy +msgid "Bot won't kick for caps anymore." +msgstr "El bot ja no kickejara majuscules." + +#: modules/commands/bs_kick.cpp:559 +#, fuzzy +msgid "Bot won't kick for flood anymore." +msgstr "El bot ja no kickejara flood." + +#: modules/commands/bs_kick.cpp:694 +#, fuzzy +msgid "Bot won't kick for repeats anymore." +msgstr "El bot ja no kickejara repeticions." + +#: modules/commands/cs_access.cpp:472 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_session.cpp:514 +msgid "By" +msgstr "" + +#: modules/commands/os_info.cpp:104 +msgid "CLEAR target" +msgstr "" + +#: modules/commands/cs_seen.cpp:119 +msgid "CLEAR time" +msgstr "" + +#: modules/commands/ms_cancel.cpp:19 +#, fuzzy +msgid "Cancel the last memo you sent" +msgstr " CANCEL Cancela l'últim memo enviat" + +#: modules/commands/cs_drop.cpp:19 +#, fuzzy +msgid "Cancel the registration of a channel" +msgstr " DROP Cancel.la l'enregistrament d'un canal" + +#: modules/commands/ns_drop.cpp:20 +#, fuzzy +msgid "Cancel the registration of a nickname" +msgstr " DROP Cancela el registre d'un nickname" + +#: modules/commands/ms_cancel.cpp:84 +#, fuzzy +msgid "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." +msgstr "" +"Sintàxi: CANCEL {nick | canal}\n" +"\n" +"Cancela l'ultim memo enviat al nick o canal donat,\n" +"sempre i quan no hagi sigut llegit al moment en el que\n" +"vas fer servir la comanda." + +#: modules/commands/cs_clone.cpp:149 +#, fuzzy, c-format +msgid "Cannot clone channel %s to itself!" +msgstr "Bot kickejara ops en el canal %s." + +#: modules/commands/ns_register.cpp:332 +msgid "Cannot send mail now; please retry a little later." +msgstr "Imposible enviar email ara; per favor intenta en uns instants." + +#: modules/commands/bs_kick.cpp:1141 modules/commands/bs_kick.cpp:1143 +#: modules/commands/bs_kick.cpp:1146 +#, fuzzy +msgid "Caps kicker" +msgstr " Kicker per majuscules : %s" + +#: modules/commands/os_shutdown.cpp:34 +#, fuzzy +msgid "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." +msgstr "" +"Sintàxi: QUIT\n" +"\n" +"Força als serveis a parar inmediatament; les bases de\n" +"dades no son guardades. Aquesta comanda no ha de ser utilitzada\n" +"excepte que les còpies en la memòria semblin espatllades i no\n" +"hagin de ser guardades. Per parar normalment, utilitza la comanda\n" +"SHUTDOWN.\n" +"\n" +"Limitat a administradors de serveis." + +#: modules/commands/os_reload.cpp:47 +#, fuzzy +msgid "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." +msgstr "" +"Sintàxi: RELOAD\n" +"\n" +"Força als serveis a recarregar l'arxiu de\n" +"configuració. Tenir en compe que algunes directives\n" +"necessiten que els serveis es reinicin de nou per tenir\n" +"efecte (tal com nicknames dels serveis, activació\n" +"de la limitació de sessions, etc.)\n" +"\n" +"Limitat a administradors de serveis." + +#: modules/commands/os_shutdown.cpp:62 +#, fuzzy +msgid "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." +msgstr "" +"Sintàxi: RESTART\n" +"\n" +"Força als serveis a guardar totes les bases de\n" +"dades i després parar i arrancar de nou.\n" +"(es a dir, finalitzar el programa e inmediatament reiniciar\n" +"el programa de nou).\n" +"\n" +"Limitat a administradors de serveis." + +#: modules/commands/os_shutdown.cpp:89 +#, fuzzy +msgid "Causes Services to save all databases and then shut down." +msgstr "" +"Sintàxi: SHUTDOWN\n" +"\n" +"Força als serveis a guardar totes les bases de\n" +"datos i parar.\n" +"\n" +"Limitat a administradors de serveis." + +#: modules/commands/os_update.cpp:34 +#, fuzzy +msgid "" +"Causes Services to update all database files as soon as you\n" +"send the command." +msgstr "" +"Sintàxi: UPDATE\n" +"\n" +"Força als serveis a actualitzar tots els arxius de\n" +"la base de dades tan aviat como enviis la comanda.\n" +"\n" +"Limitat a administradors de serveis." + +#: modules/commands/ns_cert.cpp:246 +#, fuzzy, c-format +msgid "Certificate list for %s:" +msgstr "Lllista d'accés per %s:" + +#: modules/commands/cs_set.cpp:528 modules/commands/cs_set.cpp:570 +msgid "ChanServ is required to enable persist on this network." +msgstr "" + +#: modules/commands/os_mode.cpp:19 +#, fuzzy +msgid "Change channel modes" +msgstr "%s changed your usermodes." + +#: modules/commands/ns_set.cpp:905 +#, fuzzy +msgid "Change the communication method of Services" +msgstr "" +" MSG canvia el metode de comunicació amb els\n" +" serveis" + +#: modules/commands/os_mode.cpp:146 +#, fuzzy +msgid "Change user modes" +msgstr "%s changed your usermodes." + +#: modules/commands/os_mode.cpp:161 +#, fuzzy, c-format +msgid "Changed usermodes of %s to %s." +msgstr "Changed usermodes of %s." + +#: modules/commands/ns_set.cpp:411 +#, fuzzy +msgid "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." +msgstr "" +"Sintaxis: SET DISPLAY nou-display\n" +"\n" +"canvia el display utilitzat per referir-te al teu grup de\n" +"nicks en serveis. El nou display HA DE SER un nick\n" +"del teu grup." + +#: modules/commands/ns_set.cpp:387 +#, fuzzy +msgid "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." +msgstr "" +"Sintaxis: SET DISPLAY nou-display\n" +"\n" +"canvia el display utilitzat per referir-te al teu grup de\n" +"nicks en serveis. El nou display HA DE SER un nick\n" +"del teu grup." + +#: modules/commands/cs_set.cpp:324 +#, fuzzy +msgid "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." +msgstr "" +"Sintaxis: %s canal FOUNDER nick\n" +"\n" +"Canvia el fundador d'un canal. El nou nickname ha de\n" +"ser un d'enregistrat." + +#: modules/commands/ns_set.cpp:884 +#, fuzzy +msgid "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Sintaxis: SET LANGUAGE numero\n" +"\n" +"Canvia el llenguatge que serveis utilitza per enviar-te missatges\n" +"(per exemple, al respondre a una comanda que enviis).\n" +"numero ha de ser escollit de la llista de llenguatges\n" +"soportats:" + +#: modules/commands/ns_set.cpp:848 +#, fuzzy +msgid "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Sintaxis: SET LANGUAGE numero\n" +"\n" +"Canvia el llenguatge que serveis utilitza per enviar-te missatges\n" +"(per exemple, al respondre a una comanda que enviis).\n" +"numero ha de ser escollit de la llista de llenguatges\n" +"soportats:" + +#: modules/commands/ns_set.cpp:227 +#, fuzzy +msgid "Changes the password used to identify as the nick's owner." +msgstr "" +"Sintaxis: SET PASSWORD nueva-clau\n" +"\n" +"Canvia la clau utilitzada per identificar-te com el\n" +"propietari del nick." + +#: modules/commands/ns_set.cpp:161 +#, fuzzy +msgid "" +"Changes the password used to identify you as the nick's\n" +"owner." +msgstr "" +"Sintaxis: SET PASSWORD nueva-clau\n" +"\n" +"Canvia la clau utilitzada per identificar-te com el\n" +"propietari del nick." + +#: modules/commands/cs_set.cpp:1017 +#, fuzzy +msgid "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." +msgstr "" +"Sintaxis: %s canal SUCCESSOR nick\n" +"\n" +"Canvia el successor d'un canal. Si el nickname fundador\n" +"caduca o es eliminat mentres el canal esta encara registrat,\n" +"el successor es convertira en el nou fundador del canal.\n" +"Però, si el successor ja te molts canals\n" +"registrats (%d), el canal sera eliminat, tal i com\n" +"si no hi haguès un successor. El nou nickname ha de ser un\n" +"d'enregistrat." + +#: modules/commands/ns_alist.cpp:48 modules/commands/ns_ajoin.cpp:100 +#, fuzzy +msgid "Channel" +msgstr "DROP canal" + +#: include/language.h:84 +#, fuzzy, c-format +msgid "Channel %s doesn't exist." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_drop.cpp:63 +#, c-format +msgid "Channel %s has been dropped." +msgstr "El canal %s ha estat eliminat." + +#: modules/commands/cs_getkey.cpp:43 +#, fuzzy, c-format +msgid "Channel %s has no key." +msgstr "The channel %s has no key." + +#: modules/commands/cs_register.cpp:47 +#, c-format +msgid "Channel %s is already registered!" +msgstr "El canal %s ja esta enregistrat!" + +#: modules/commands/os_forbid.cpp:524 +#, fuzzy, c-format +msgid "Channel %s is forbidden by %s: %s" +msgstr "Aquest canal ha estat registrat amb %s." + +#: modules/commands/os_forbid.cpp:526 +#, fuzzy, c-format +msgid "Channel %s is forbidden." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_set.cpp:580 +#, fuzzy, c-format +msgid "Channel %s is no longer persistent." +msgstr "Channel %s is no longer persistant." + +#: modules/commands/cs_set.cpp:542 +#, fuzzy, c-format +msgid "Channel %s is now persistent." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_suspend.cpp:180 +#, c-format +msgid "Channel %s is now released." +msgstr "Channel %s is now released." + +#: modules/commands/cs_suspend.cpp:125 +#, c-format +msgid "Channel %s is now suspended." +msgstr "Channel %s is now suspended." + +#: include/language.h:83 +#, fuzzy, c-format +msgid "Channel %s isn't registered." +msgstr "El canal %s no pot ser enregistrat." + +#: modules/commands/cs_suspend.cpp:172 +#, fuzzy, c-format +msgid "Channel %s isn't suspended." +msgstr "Channel %s is now suspended." + +#: modules/commands/cs_register.cpp:68 +#, fuzzy, c-format +msgid "Channel %s registered under your account: %s" +msgstr "El nickname %s ja esta registrat sota el teu compte: %s" + +#: modules/commands/cs_set.cpp:1078 +#, c-format +msgid "Channel %s will expire." +msgstr "El canal %s caducara." + +#: modules/commands/cs_set.cpp:1072 +#, c-format +msgid "Channel %s will not expire." +msgstr "El canal %s no caducara." + +#: modules/commands/cs_xop.cpp:475 +#, fuzzy, c-format +msgid "Channel %s %s list has been cleared." +msgstr "La llista AOP de canals %s ha estat netegada." + +#: modules/commands/cs_access.cpp:486 modules/commands/cs_flags.cpp:361 +#, c-format +msgid "Channel %s access list has been cleared." +msgstr "La llista d'accés pel canal %s ha estat netegada." + +#: modules/commands/cs_akick.cpp:428 +#, c-format +msgid "Channel %s akick list has been cleared." +msgstr "La llista de kicks automàtics en canal %s ha estat netegada." + +#: modules/commands/cs_mode.cpp:444 +#, fuzzy, c-format +msgid "Channel %s has no mode locks." +msgstr "Channel %s is now released." + +#: include/language.h:82 +#, fuzzy, c-format +msgid "Channel %s is currently suspended." +msgstr "Channel %s is now suspended." + +#: include/language.h:101 +#, fuzzy, c-format +msgid "Channel %s is not a valid channel." +msgstr "%s no es un tipus de ban valid." + +#: modules/commands/os_list.cpp:70 +#, fuzzy +msgid "Channel list:" +msgstr "Llista de bots:" + +#: modules/extra/stats/cs_fantasy_stats.cpp:148 +#, fuzzy, c-format +msgid "Channel stats for %s on %s:" +msgstr "" +"Channels that %s has access on:\n" +" Num Channel Level Description " + +#: modules/commands/cs_access.cpp:142 modules/commands/cs_flags.cpp:97 +#: modules/commands/cs_xop.cpp:139 +#, fuzzy +msgid "Channels may not be on access lists." +msgstr "%s no trobat a la llista d'accés de %s." + +#: modules/commands/ns_alist.cpp:114 +#, fuzzy, c-format +msgid "Channels that %s has access on:" +msgstr "" +"Channels that %s has access on:\n" +" Num Channel Level Description " + +#: modules/commands/os_stats.cpp:181 +#, c-format +msgid "Channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:517 +#: modules/extra/stats/m_chanstats.cpp:525 +msgid "Chanstats" +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:102 +#, fuzzy, c-format +msgid "Chanstats statistics are now disabled for %s" +msgstr " SECURE Activa o desactiva la seguretat de nickname" + +#: modules/extra/stats/m_chanstats.cpp:51 +msgid "Chanstats statistics are now disabled for this channel." +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:104 +#, fuzzy +msgid "Chanstats statistics are now disabled for your nick." +msgstr " SECURE Activa o desactiva la seguretat de nickname" + +#: modules/extra/stats/m_chanstats.cpp:93 +#, fuzzy, c-format +msgid "Chanstats statistics are now enabled for %s" +msgstr " SECURE Activa o desactiva la seguretat de nickname" + +#: modules/extra/stats/m_chanstats.cpp:44 +msgid "Chanstats statistics are now enabled for this channel." +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:95 +#, fuzzy +msgid "Chanstats statistics are now enabled for your nick." +msgstr " SECURE Activa o desactiva la seguretat de nickname" + +#: modules/commands/cs_seen.cpp:367 +msgid "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." +msgstr "" + +#: modules/commands/ms_check.cpp:19 +#, fuzzy +msgid "Checks if last memo to a nick was read" +msgstr " CHECK Checks if last memo to a nick was read" + +#: modules/commands/ms_check.cpp:69 +#, fuzzy +msgid "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." +msgstr "" +"Syntax: CHECK nick\n" +"\n" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this does only work with nicks, not with chans." + +#: modules/commands/os_info.cpp:227 +#, c-format +msgid "Cleared info from %s." +msgstr "" + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1153 +#: modules/commands/bs_kick.cpp:1156 +#, fuzzy +msgid "Colors kicker" +msgstr "KICK Configura kickers" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Command" +msgstr "%s commands:" + +#: modules/commands/bs_kick.cpp:251 +#, fuzzy +msgid "Configures AMSG kicker" +msgstr "KICK Configura kickers" + +#: modules/commands/bs_kick.cpp:287 +#, fuzzy +msgid "Configures badwords kicker" +msgstr "KICK Configura kickers" + +#: modules/commands/bs_kick.cpp:326 +#, fuzzy +msgid "Configures bolds kicker" +msgstr "KICK Configura kickers" + +#: modules/commands/bs_kick.cpp:132 +#, fuzzy +msgid "Configures bot kickers. option can be one of:" +msgstr "" +"Sintaxis: SET Opció parametres\n" +"\n" +"Estableix varies opcions per a nicknames. Opció pot ser\n" +"una de:" + +#: modules/commands/bs_set.cpp:19 +#, fuzzy +msgid "Configures bot options" +msgstr "SET Configura opcions de bots" + +#: modules/commands/bs_set.cpp:32 +#, fuzzy +msgid "" +"Configures bot options.\n" +" \n" +"Available options:" +msgstr "SET Configura opcions de bots" + +#: modules/commands/bs_kick.cpp:360 +#, fuzzy +msgid "Configures caps kicker" +msgstr "KICK Configura kickers" + +#: modules/commands/cs_log.cpp:105 +#, fuzzy +msgid "Configures channel logging settings" +msgstr "* No new channel registrations" + +#: modules/commands/bs_kick.cpp:456 +#, fuzzy +msgid "Configures color kicker" +msgstr "KICK Configura kickers" + +#: modules/commands/bs_kick.cpp:490 +#, fuzzy +msgid "Configures flood kicker" +msgstr "KICK Configura kickers" + +#: modules/commands/bs_kick.cpp:588 +#, fuzzy +msgid "Configures italics kicker" +msgstr "KICK Configura kickers" + +#: modules/commands/bs_kick.cpp:119 +#, fuzzy +msgid "Configures kickers" +msgstr "KICK Configura kickers" + +#: modules/commands/bs_kick.cpp:622 +#, fuzzy +msgid "Configures repeat kicker" +msgstr "KICK Configura kickers" + +#: modules/commands/bs_kick.cpp:723 +#, fuzzy +msgid "Configures reverses kicker" +msgstr "KICK Configura kickers" + +#: modules/commands/bs_set.cpp:90 +#, fuzzy +msgid "Configures the time bot bans expire in" +msgstr "SET Configura opcions de bots" + +#: modules/commands/bs_kick.cpp:757 +#, fuzzy +msgid "Configures underlines kicker" +msgstr "KICK Configura kickers" + +#: modules/commands/ns_register.cpp:21 +#, fuzzy +msgid "Confirm a passcode" +msgstr " CONFIRM Confirm a nickserv auth code" + +#: modules/commands/cs_mode.cpp:733 +#, fuzzy +msgid "Control modes and mode locks on a channel" +msgstr " CLEARMODES neteja els Modes d'un canal" + +#: modules/commands/cs_entrymsg.cpp:239 +msgid "" +"Controls what messages will be sent to users when they join the channel." +msgstr "" + +#: modules/commands/cs_clone.cpp:242 +msgid "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." +msgstr "" + +#: modules/commands/cs_clone.cpp:114 +#, fuzzy +msgid "Copy all settings from one channel to another" +msgstr "" +" UNBAN Remove all bans preventing a user from entering a channel" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/bs_info.cpp:57 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Created" +msgstr " Creat : %s" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_ignore.cpp:266 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_news.cpp:156 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Creator" +msgstr " Creat : %s" + +#: modules/commands/os_sxline.cpp:180 +#, fuzzy, c-format +msgid "Current %s list:" +msgstr "Llista actual de AKILLs:" + +#: modules/commands/os_akill.cpp:323 +#, fuzzy +msgid "Current AKILL list:" +msgstr "Llista actual de AKILLs:" + +#: modules/commands/os_session.cpp:493 +msgid "Current Session Limit Exception list:" +msgstr "llista d'excepcions al límit de sessions actual:" + +#: modules/commands/os_modinfo.cpp:116 +#, fuzzy +msgid "Current module list:" +msgstr "Current Module list:" + +#: modules/commands/os_stats.cpp:69 +#, c-format +msgid "Current number of AKILLs: %d" +msgstr "Numero actual de AKILLs: %d" + +#: modules/commands/os_stats.cpp:89 +#, c-format +msgid "Current number of SNLINEs: %d" +msgstr "Numero actual de SNLINEs: %d" + +#: modules/commands/os_stats.cpp:109 +#, c-format +msgid "Current number of SQLINEs: %d" +msgstr "Numero actual de SQLINEs: %d" + +#: modules/commands/os_stats.cpp:138 +#, c-format +msgid "Current users: %d (%d ops)" +msgstr "Actuals usuaris: %d (%d ops)" + +#: modules/commands/os_oper.cpp:71 +#, fuzzy +msgid "DEL oper" +msgstr "DEL ." + +#: modules/commands/os_info.cpp:103 +#, fuzzy +msgid "DEL target info" +msgstr "GROUP grup clau" + +#: modules/commands/ns_ajoin.cpp:232 +#, fuzzy +msgid "DEL [nickname] channel" +msgstr "MODE canal Modes" + +#: modules/commands/ns_cert.cpp:259 +#, fuzzy +msgid "DEL [nickname] fingerprint" +msgstr "FORBID nickname rao" + +#: modules/commands/ns_access.cpp:103 +#, fuzzy +msgid "DEL [nickname] mask" +msgstr "MODE canal Modes" + +#: modules/commands/os_sxline.cpp:426 modules/commands/os_sxline.cpp:660 +#: modules/commands/os_akill.cpp:387 +#, fuzzy +msgid "DEL {mask | entry-num | list | id}" +msgstr "DEL [canal] {numero | llista | ALL}" + +#: modules/commands/os_session.cpp:524 +#, fuzzy +msgid "DEL {mask | entry-num | list}" +msgstr "DEL [canal] {numero | llista | ALL}" + +#: modules/commands/os_ignore.cpp:343 +#, fuzzy +msgid "DEL {nick|mask}" +msgstr "DEL ." + +#: modules/commands/os_news.cpp:279 +#, fuzzy +msgid "DEL {num | ALL}" +msgstr "Sintaxis: OPERNEWS DEL {numero | ALL}" + +#: modules/commands/os_forbid.cpp:158 +msgid "DEL {NICK|CHAN|EMAIL|REGISTER} entry" +msgstr "" + +#: modules/commands/os_dns.cpp:666 +msgid "DELIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:664 +msgid "DELSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:662 +msgid "DELZONE zone.name" +msgstr "" + +#: modules/commands/os_dns.cpp:669 +#, fuzzy +msgid "DEPOOL server.name" +msgstr "NOOP {SET|REVOKE} servidor" + +#: modules/commands/cs_seen.cpp:162 +#, c-format +msgid "Database cleared, removed %lu nicks that were added after %s." +msgstr "" + +#: modules/commands/ms_list.cpp:64 +msgid "Date/Time" +msgstr "" + +#: modules/commands/hs_off.cpp:49 +#, fuzzy +msgid "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." +msgstr "" +"Syntax: OFF\n" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real IP address." + +#: modules/commands/hs_off.cpp:19 +#, fuzzy +msgid "Deactivates your assigned vhost" +msgstr " OFF Deactivates your assigned vhost" + +#: modules/commands/os_stats.cpp:72 +#, c-format +msgid "Default AKILL expiry time: %d days" +msgstr "Temps d'expiració per defecte de AKILL: %d dies" + +#: modules/commands/os_stats.cpp:76 +#, c-format +msgid "Default AKILL expiry time: %d hours" +msgstr "Temps d'expiració per defecte de AKILL: %d hores" + +#: modules/commands/os_stats.cpp:80 +#, c-format +msgid "Default AKILL expiry time: %d minutes" +msgstr "Temps d'expiració per defecte de AKILL: %d minuts" + +#: modules/commands/os_stats.cpp:74 +msgid "Default AKILL expiry time: 1 day" +msgstr "Temps d'expiració per defecte de AKILL: 1 dia" + +#: modules/commands/os_stats.cpp:78 +msgid "Default AKILL expiry time: 1 hour" +msgstr "Temps d'expiració per defecte de AKILL: 1 hora" + +#: modules/commands/os_stats.cpp:82 +msgid "Default AKILL expiry time: 1 minute" +msgstr "Temps d'expiració per defecte de AKILL: 1 minut" + +#: modules/commands/os_stats.cpp:84 +msgid "Default AKILL expiry time: No expiration" +msgstr "Temps d'expiració per defecte de AKILL: Sense expiració" + +#: modules/commands/os_stats.cpp:92 +#, c-format +msgid "Default SNLINE expiry time: %d days" +msgstr "Temps d'expiració per defecte de SNLINE: %d dies" + +#: modules/commands/os_stats.cpp:96 +#, c-format +msgid "Default SNLINE expiry time: %d hours" +msgstr "Temps d'expiració per defecte de SNLINE: %d hores" + +#: modules/commands/os_stats.cpp:100 +#, c-format +msgid "Default SNLINE expiry time: %d minutes" +msgstr "Temps d'expiració per defecte de SNLINE: %d minuts" + +#: modules/commands/os_stats.cpp:94 +msgid "Default SNLINE expiry time: 1 day" +msgstr "Temps d'expiració per defecte de SNLINE: 1 dia" + +#: modules/commands/os_stats.cpp:98 +msgid "Default SNLINE expiry time: 1 hour" +msgstr "Temps d'expiració per defecte de SNLINE: 1 hora" + +#: modules/commands/os_stats.cpp:102 +msgid "Default SNLINE expiry time: 1 minute" +msgstr "Temps d'expiració per defecte de SNLINE: 1 minut" + +#: modules/commands/os_stats.cpp:104 +msgid "Default SNLINE expiry time: No expiration" +msgstr "Temps d'expiració per defecte de SNLINE: Sense expiració" + +#: modules/commands/os_stats.cpp:112 +#, c-format +msgid "Default SQLINE expiry time: %d days" +msgstr "Temps d'expiració per defecte de SQLINE: %d dies" + +#: modules/commands/os_stats.cpp:116 +#, c-format +msgid "Default SQLINE expiry time: %d hours" +msgstr "Temps d'expiració per defecte de SQLINE: %d hores" + +#: modules/commands/os_stats.cpp:120 +#, c-format +msgid "Default SQLINE expiry time: %d minutes" +msgstr "Temps d'expiració per defecte de SQLINE: %d minuts" + +#: modules/commands/os_stats.cpp:114 +msgid "Default SQLINE expiry time: 1 day" +msgstr "Temps d'expiració per defecte de SQLINE: 1 dia" + +#: modules/commands/os_stats.cpp:118 +msgid "Default SQLINE expiry time: 1 hour" +msgstr "Temps d'expiració per defecte de SQLINE: 1 hora" + +#: modules/commands/os_stats.cpp:122 +msgid "Default SQLINE expiry time: 1 minute" +msgstr "Temps d'expiració per defecte de SQLINE: 1 minut" + +#: modules/commands/os_stats.cpp:124 +msgid "Default SQLINE expiry time: No expiration" +msgstr "Temps d'expiració per defecte de SQLINE: Sense expiració" + +#: modules/commands/os_news.cpp:351 +#, fuzzy +msgid "Define messages to be randomly shown to users at logon" +msgstr "" +" LOGONNEWS Defineix missatges per a ser mostrats a usuaris\n" +" al conectarse" + +#: modules/commands/os_news.cpp:297 +#, fuzzy +msgid "Define messages to be shown to users at logon" +msgstr "" +" LOGONNEWS Defineix missatges per a ser mostrats a usuaris\n" +" al conectarse" + +#: modules/commands/os_news.cpp:324 +#, fuzzy +msgid "Define messages to be shown to users who oper" +msgstr "" +" OPERNEWS Defineix missatges per a ser mostrats a usuaris\n" +" al transformar-se en operadors" + +#: modules/commands/ms_del.cpp:44 +#, fuzzy +msgid "Delete a memo or memos" +msgstr " DEL Esborra un o més memos" + +#: modules/commands/hs_del.cpp:19 +#, fuzzy +msgid "Delete the vhost of another user" +msgstr " DEL Delete the vhost of another user" + +#: modules/commands/cs_xop.cpp:302 +#, fuzzy, c-format +msgid "Deleted %d entries from %s %s list." +msgstr "%d instàncies esborrades de la llista AOP de %s." + +#: modules/commands/cs_access.cpp:277 +#, c-format +msgid "Deleted %d entries from %s access list." +msgstr "%d instàncies esborrades de la llista d'accés de %s." + +#: modules/commands/cs_akick.cpp:228 +#, c-format +msgid "Deleted %d entries from %s autokick list." +msgstr "" +"%d instàncies esborrades de la llista de kicks automàtics del canal %s." + +#: modules/commands/bs_badwords.cpp:170 +#, c-format +msgid "Deleted %d entries from %s bad words list." +msgstr "%d paraules esborrades de la llista de paraules malsonants de %s." + +#: modules/commands/os_session.cpp:149 +#, c-format +msgid "Deleted %d entries from session-limit exception list." +msgstr "" +"%d instàncies esborrades de la llista d'excepcions al límit de sessions." + +#: modules/commands/os_sxline.cpp:32 +#, fuzzy, c-format +msgid "Deleted %d entries from the %s list." +msgstr "%d instàncies esborrades de la llista AOP de %s." + +#: modules/commands/os_akill.cpp:33 +#, c-format +msgid "Deleted %d entries from the AKILL list." +msgstr "%d instàncies esborrades de la llista de AKILLs." + +#: modules/commands/cs_access.cpp:275 +#, c-format +msgid "Deleted 1 entry from %s access list." +msgstr "1 instància esborrada de la llista d'accés de %s." + +#: modules/commands/cs_akick.cpp:226 +#, c-format +msgid "Deleted 1 entry from %s autokick list." +msgstr "1 instància esborrada de la llista de kicks automàtics del canal %s." + +#: modules/commands/bs_badwords.cpp:168 +#, c-format +msgid "Deleted 1 entry from %s bad words list." +msgstr "1 paraula esborrada de la llista de paraules malsonants de %s." + +#: modules/commands/os_session.cpp:147 +msgid "Deleted 1 entry from session-limit exception list." +msgstr "1 instància esborrada de la llista d'excepcions al límit de sessions." + +#: modules/commands/os_sxline.cpp:30 +#, fuzzy, c-format +msgid "Deleted 1 entry from the %s list." +msgstr "1 instància esborrada de la llista de AKILLs." + +#: modules/commands/os_akill.cpp:31 +msgid "Deleted 1 entry from the AKILL list." +msgstr "1 instància esborrada de la llista de AKILLs." + +#: modules/commands/os_info.cpp:208 +#, fuzzy, c-format +msgid "Deleted info from %s." +msgstr "1 instància esborrada de la llista de AKILLs." + +#: modules/commands/cs_xop.cpp:300 +#, fuzzy, c-format +msgid "Deleted one entry from %s %s list." +msgstr "1 instància esborrada de la llista AOP de %s." + +#: modules/commands/ms_del.cpp:129 +#, fuzzy +msgid "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Sintàxi: DEL [canal] {nombre | llista | LAST | ALL}\n" +"\n" +"Esorra el o els memos especificats. pots donar multiples\n" +"nombres o rangs de nombres en lloc d'un solo, com en el\n" +"exemple.\n" +"\n" +"If LAST is given, the last memo will be deleted.\n" +"Si ALL és donat, esborra tots els teus memos.\n" +"\n" +"exemples:\n" +"\n" +" DEL 1\n" +" Esorra el teu primer memo.\n" +"\n" +" DEL 2-5,7-9\n" +" Esborra els memos enumerats 2 a 5 i 7 a 9." + +#: modules/commands/hs_del.cpp:48 +#, fuzzy +msgid "" +"Deletes the vhost assigned to the given nick from the\n" +"database." +msgstr "" +"Syntax: DEL \n" +"Deletes the vhost assigned to the given nick from the\n" +"database.\n" +"Limited to Services operators." + +#: modules/commands/hs_del.cpp:59 +#, fuzzy +msgid "Deletes the vhost for all nicks in a group" +msgstr " DELALL Delete the vhost for all nicks in a group" + +#: modules/commands/hs_del.cpp:93 +#, fuzzy +msgid "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." +msgstr "" +"Syntax: DELALL .\n" +"Deletes the vhost for all nick's in the same group as\n" +"that of the given nick.\n" +"Limited to Host Removers." + +#: modules/commands/os_dns.cpp:653 +#, c-format +msgid "Depooled %s." +msgstr "" + +#: modules/commands/cs_access.cpp:799 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_list.cpp:75 modules/commands/cs_info.cpp:53 +#, fuzzy +msgid "Description" +msgstr "La descripció de %s canviada a%s." + +#: modules/commands/cs_set.cpp:239 +#, c-format +msgid "Description of %s changed to %s." +msgstr "La descripció de %s canviada a%s." + +#: modules/commands/cs_set.cpp:245 +#, fuzzy, c-format +msgid "Description of %s unset." +msgstr "La descripció de %s canviada a%s." + +#: modules/commands/bs_kick.cpp:1115 modules/commands/bs_info.cpp:90 +#, fuzzy +msgid "Disabled" +msgstr "%s is enable" + +#: modules/commands/cs_suspend.cpp:134 +#, fuzzy +msgid "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." +msgstr "" +"Syntax: SUSPEND channel [reason]\n" +"\n" +"Disallows anyone from registering or using the given\n" +"channel. May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"\n" +"Reason may be required on certain networks." + +#: modules/commands/hs_request.cpp:337 +#, fuzzy, c-format +msgid "Displayed %d records (%d total)." +msgstr "Displayed all records (Count: %d)" + +#: modules/commands/hs_list.cpp:122 +#, fuzzy, c-format +msgid "Displayed all records (count: %d)." +msgstr "Displayed all records (Count: %d)" + +#: modules/commands/hs_list.cpp:120 +#, fuzzy, c-format +msgid "Displayed records from %d to %d." +msgstr "Displayed records from %d to %d" + +#: modules/commands/hs_list.cpp:116 +#, fuzzy, c-format +msgid "Displayed records matching key %s (count: %d)." +msgstr "Displayed records matching key %s (Count: %d)" + +#: modules/commands/ns_info.cpp:19 +#, fuzzy +msgid "Displays information about a given nickname" +msgstr " INFO Displays information about a given nickname" + +#: modules/commands/ns_info.cpp:125 +#, fuzzy +msgid "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." +msgstr "" +"Sintaxis: INFO nickname\n" +"\n" +"Mostra informació relativa al nick que s'especifiqui,\n" +"tal com el propietari del nick, l'ultima adreça utilitzada\n" +"i temps, i opcions del nick." + +#: modules/commands/ms_info.cpp:19 +#, fuzzy +msgid "Displays information about your memos" +msgstr " INFO Displays information about your memos" + +#: modules/commands/hs_list.cpp:19 +#, fuzzy +msgid "Displays one or more vhost entries" +msgstr " LIST Displays one or more vhost entries." + +#: modules/extra/stats/cs_fantasy_top.cpp:50 +#, fuzzy +msgid "Displays the top 10 users of a channel" +msgstr " FOUNDER Estableix el fundador d'un canal" + +#: modules/extra/stats/cs_fantasy_top.cpp:73 +msgid "Displays the top 10 users of the network" +msgstr "" + +#: modules/extra/stats/cs_fantasy_top.cpp:38 +#, fuzzy +msgid "Displays the top 3 users of a channel" +msgstr " FOUNDER Estableix el fundador d'un canal" + +#: modules/extra/stats/cs_fantasy_top.cpp:62 +msgid "Displays the top 3 users of the network" +msgstr "" + +#: modules/commands/help.cpp:33 +#, fuzzy +msgid "Displays this list and give information about commands" +msgstr " INFO Displays information about your memos" + +#: modules/extra/stats/cs_fantasy_stats.cpp:39 +msgid "Displays your Channel Stats" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:51 +msgid "Displays your Global Stats" +msgstr "" + +#: modules/commands/bs_kick.cpp:1463 +msgid "Don't use AMSGs!" +msgstr "" + +#: modules/commands/bs_kick.cpp:1266 +msgid "Don't use bolds on this channel!" +msgstr "No utilitzis negreta en aquest canal!" + +#: modules/commands/bs_kick.cpp:1274 +msgid "Don't use colors on this channel!" +msgstr "No utilitzis colors en aquest canal!" + +#: modules/commands/bs_kick.cpp:1290 +msgid "Don't use italics on this channel!" +msgstr "Don't use italics on this channel!" + +#: modules/commands/bs_kick.cpp:1282 +msgid "Don't use reverses on this channel!" +msgstr "No utilitzis reversos en aquest canal!" + +#: modules/commands/bs_kick.cpp:1408 +#, c-format +msgid "Don't use the word \"%s\" on this channel!" +msgstr "No utilitzis la paraula %s en aquest canal!" + +#: modules/commands/bs_kick.cpp:1298 +msgid "Don't use underlines on this channel!" +msgstr "No utilitzis subratllats en aquest canal!" + +#: modules/commands/ns_drop.cpp:61 +msgid "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." +msgstr "" + +#: modules/commands/ns_set.cpp:513 +#, c-format +msgid "E-mail address for %s changed to %s." +msgstr "E-mail address for %s changed to %s." + +#: modules/commands/ns_set.cpp:519 +#, c-format +msgid "E-mail address for %s unset." +msgstr "E-mail address for %s unset." + +#: src/mail.cpp:80 +#, c-format +msgid "E-mail for %s is invalid." +msgstr "E-mail per %s es invalid." + +#: modules/commands/os_news.cpp:309 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Syntax: LOGONNEWS ADD text\n" +" LOGONNEWS DEL {num | ALL}\n" +" LOGONNEWS LIST\n" +"\n" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. (However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent.)\n" +"NewsCount can be configured in services.conf.\n" +"\n" +"LOGONNEWS may only be used by Services Operators." + +#: modules/commands/os_news.cpp:336 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Syntax: OPERNEWS ADD text\n" +" OPERNEWS DEL {num | ALL}\n" +" OPERNEWS LIST\n" +"\n" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. (However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent.)\n" +"NewsCount can be configured in services.conf.\n" +"\n" +"OPERNEWS may only be used by Services Operators." + +#: modules/commands/os_news.cpp:363 +#, fuzzy +msgid "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." +msgstr "" +"Sintaxis: RANDOMNEWS ADD text\n" +" RANDOMNEWS DEL {numero | ALL}\n" +" RANDOMNEWS LIST\n" +"\n" +"Edita o mostra la llista de missatges de noticia a l'atzar.\n" +"Quant un usuari es connecta a la xarxa, un (i nomès un) dels\n" +"missatges a l'atzar sera escollit i enviat a ells.\n" +"\n" +"RANDOMNEWS may only be used by Services Operators." + +#: modules/commands/ns_info.cpp:98 +#, fuzzy +msgid "Email address" +msgstr " \t\tAdreça E-mail: %s" + +#: modules/commands/ns_getemail.cpp:41 +#, fuzzy, c-format +msgid "Email matched: %s (%s) to %s." +msgstr "Emails Match %s to %s." + +#: modules/fantasy.cpp:19 +msgid "Enable fantaisist commands" +msgstr "" + +#: modules/commands/greet.cpp:19 +msgid "Enable greet messages" +msgstr "" + +#: modules/commands/ns_set.cpp:568 +msgid "Enable or disable keep modes" +msgstr "" + +#: modules/commands/bs_kick.cpp:1114 modules/commands/bs_info.cpp:89 +#, fuzzy +msgid "Enabled" +msgstr "%s is enable" + +#: modules/commands/cs_set.cpp:124 +#, fuzzy, c-format +msgid "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." +msgstr "" +"Sintàxi: %s canal SECUREOPS {ON | OFF}\n" +"\n" +"Habilita o deshabilita l'opció seguretat de ops per a un\n" +"canal. Quan seguretat de ops està establerta, usuaris\n" +"que no estaven a la llista d'usuaris no els serà permès \n" +"obtenir l' estatus d'operador de canal." + +#: modules/commands/cs_set.cpp:388 +#, fuzzy +msgid "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." +msgstr "" +"Sintaxis: %s canal KEEPTOPIC {ON | OFF}\n" +"\n" +"Habilita o deshabilita l'opció de retenció de topic \n" +"per un canal. Quant la retenció de topic esta\n" +"establerta, el topic pel canal sera recordat \n" +"%s fins i tot després de que l'últim usuari\n" +"sorti del canal, i sigui restaurat la pròxima vegada que\n" +"el canal sigui creat." + +#: modules/commands/ns_set.cpp:643 +msgid "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." +msgstr "" + +#: modules/commands/ns_set.cpp:618 +msgid "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." +msgstr "" + +#: modules/commands/cs_set.cpp:733 +#, fuzzy +msgid "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." +msgstr "" +"Sintàxi: %s canal SECURE {ON | OFF}\n" +"\n" +"Habilita o deshabilita les característiques de seguretat\n" +"de %s per a un canal. Quan SECURE està\n" +"establert, només usuaris que haguin registrat els seus nicknames\n" +"amb %s i haguin utilitzat IDENTIFY amb la seva clau els serà\n" +"atorgat accés al canal controlat per la llista de\n" +"accés." + +#: modules/commands/cs_set.cpp:932 +#, fuzzy +msgid "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." +msgstr "" +"Sintàxi: %s canal SIGNKICK {ON | LEVEL | OFF}\n" +"\n" +"Habilita o deshabilita els kicks firmats per a un\n" +"canal. Quan SIGNKICK està establert, kicks\n" +"fets amb la comanda %s KICK tindran el\n" +"nick que ha fet servir la comanda en la raó.\n" +"\n" +"Si uses LEVEL, aquells que tenen nivelll superior o\n" +"igual al nivelll SIGNKICK en el canal no tindran els seus kicks \n" +"firmats. Veure /msg %s HELP LEVELS per a més informació." + +#: modules/commands/cs_set.cpp:452 +#, fuzzy, c-format +msgid "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." +msgstr "" +"Sintàxi: %s canal PEACE {ON | OFF}\n" +"\n" +"Habilita o deshabilita l'opció de pau per a un\n" +"canal. Quan pau està establerta, un usuari no\n" +"podra expulsar, banejar o esborrar un estatus de canal\n" +"d'un usuari amb nivelll igual o superior a ell via\n" +"comandes de %s." + +#: modules/commands/cs_list.cpp:232 +msgid "Enables or disables the private option for a channel." +msgstr "" + +#: modules/commands/cs_set.cpp:671 +#, fuzzy +msgid "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." +msgstr "" +"Sintàxi: %s canal RESTRICTED {ON | OFF}\n" +"\n" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." + +#: modules/commands/cs_set.cpp:796 +#, fuzzy +msgid "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." +msgstr "" +"Sintàxi: %s canal SECUREFOUNDER {ON | OFF}\n" +"\n" +"Habilita o deshabilita l'opció seguretat de fundador per a\n" +"un canal. Quan seguretat de fundador està establerta, només\n" +"el fundador real podrà eliminar el canal, canviar la seva clau,\n" +"el seu fundador i el seu sucesor, i no aquells que estiguin identificats\n" +"amb %s." + +#: modules/commands/cs_set.cpp:860 +#, fuzzy +msgid "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." +msgstr "" +"Sintàxi: %s canal SECUREOPS {ON | OFF}\n" +"\n" +"Habilita o deshabilita l'opció seguretat de ops per a un\n" +"canal. Quan seguretat de ops està establerta, usuaris\n" +"que no estaven a la llista d'usuaris no els serà permès \n" +"obtenir l' estatus d'operador de canal." + +#: modules/commands/cs_topic.cpp:70 +#, fuzzy, c-format +msgid "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." +msgstr "" +"Sintaxis: %s canal KEEPTOPIC {ON | OFF}\n" +"\n" +"Habilita o deshabilita l'opció de retenció de topic \n" +"per un canal. Quant la retenció de topic esta\n" +"establerta, el topic pel canal sera recordat \n" +"%s fins i tot després de que l'últim usuari\n" +"sorti del canal, i sigui restaurat la pròxima vegada que\n" +"el canal sigui creat." + +#: modules/commands/cs_set.cpp:592 +#, fuzzy, c-format +msgid "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." +msgstr "" +"Syntax: %s channel PERSIST {ON | OFF}\n" +"Enables or disables the persistant channel setting.\n" +"When persistant is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +"\n" +"If your IRCd does not a permanent (persistant) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +"\n" +"If this network does not have BotServ enabled and does\n" +"not have a permanent channel mode, ChanServ will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +"\n" +"If your IRCd has a permanent (persistant) channel mode\n" +"and is is set or unset (for any reason, including MLOCK),\n" +"persist is automatically set and unset for the channel aswell.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." + +#: modules/commands/os_akill.cpp:331 +#, fuzzy +msgid "End of AKILL list." +msgstr "Fi de la llista d'usuaris." + +#: modules/commands/cs_access.cpp:444 +#, fuzzy +msgid "End of access list" +msgstr "fi de llista d'accés." + +#: modules/commands/cs_flags.cpp:347 +#, fuzzy, c-format +msgid "End of access list - %d/%d entries shown." +msgstr "Fi de la lllista - %d/%d resultat(s) mostrat(s)." + +#: modules/commands/cs_flags.cpp:345 +msgid "End of access list." +msgstr "fi de llista d'accés." + +#: modules/commands/cs_akick.cpp:379 +#, fuzzy +msgid "End of autokick list" +msgstr "fi de llista d'accés." + +#: modules/commands/bs_badwords.cpp:257 +#, fuzzy +msgid "End of bad words list." +msgstr "Fi de la llista d'usuaris." + +#: modules/commands/os_list.cpp:100 +#, fuzzy, c-format +msgid "End of channel list. %u channels shown." +msgstr "Fi de la lllista - %d/%d resultat(s) mostrat(s)." + +#: modules/commands/os_config.cpp:117 +msgid "End of configuration." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:134 +#, fuzzy +msgid "End of entry message list." +msgstr "Fi de la llista d'usuaris." + +#: modules/commands/os_forbid.cpp:407 +#, fuzzy, c-format +msgid "End of forbid list - %d/%d entries shown." +msgstr "Fi de la lllista - %d/%d resultat(s) mostrat(s)." + +#: modules/commands/os_forbid.cpp:405 +#, fuzzy +msgid "End of forbid list." +msgstr "Fi de la llista d'usuaris." + +#: modules/commands/ns_alist.cpp:119 +#, fuzzy, c-format +msgid "End of list - %d channels shown." +msgstr "Fi de la lllista - %d/%d resultat(s) mostrat(s)." + +#: modules/commands/ns_list.cpp:131 modules/commands/cs_list.cpp:130 +#, c-format +msgid "End of list - %d/%d matches shown." +msgstr "Fi de la lllista - %d/%d resultat(s) mostrat(s)." + +#: modules/commands/os_news.cpp:176 +#, fuzzy +msgid "End of news list." +msgstr "Fi de la llista d'usuaris." + +#: modules/commands/os_list.cpp:235 +#, fuzzy, c-format +msgid "End of users list. %u users shown." +msgstr "Fi de la lllista - %d/%d resultat(s) mostrat(s)." + +#: modules/commands/cs_enforce.cpp:227 +msgid "Enforce various channel modes and set options" +msgstr "" + +#: modules/commands/cs_enforce.cpp:263 +msgid "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." +msgstr "" + +#: src/language.cpp:43 modules/commands/ns_set.cpp:836 +#: modules/commands/ns_set.cpp:856 modules/commands/ns_set.cpp:891 +msgid "English" +msgstr "Catala" + +#: modules/commands/cs_entrymsg.cpp:170 +#, fuzzy, c-format +msgid "Entry message %i for %s deleted." +msgstr "Greet message for %s unset." + +#: modules/commands/cs_entrymsg.cpp:177 +#, fuzzy, c-format +msgid "Entry message %s not found on channel %s." +msgstr "Mode fantasia ara activada en el canal %s." + +#: modules/commands/cs_entrymsg.cpp:147 +#, fuzzy, c-format +msgid "Entry message added to %s" +msgstr "Greet message for %s changed to %s." + +#: modules/commands/cs_entrymsg.cpp:109 modules/commands/cs_entrymsg.cpp:158 +#, fuzzy, c-format +msgid "Entry message list for %s is empty." +msgstr "Access list for %s is empty." + +#: modules/commands/cs_entrymsg.cpp:113 +#, fuzzy, c-format +msgid "Entry message list for %s:" +msgstr "Lllista d'accés per %s:" + +#: modules/commands/cs_entrymsg.cpp:187 +#, fuzzy, c-format +msgid "Entry messages for %s have been cleared." +msgstr "All memos for channel %s have been deleted." + +#: modules/commands/os_reload.cpp:39 +#, fuzzy, c-format +msgid "Error reloading configuration file: %s" +msgstr " RELOAD Recarrega la configuració dels serveis" + +#: include/language.h:125 +#, c-format +msgid "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." +msgstr "" + +#: include/language.h:124 +#, c-format +msgid "" +"Error! The vHost is too long, please use a hostname shorter than %d " +"characters." +msgstr "" + +#: modules/commands/ns_cert.cpp:325 +msgid "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." +msgstr "" + +#: modules/commands/os_session.cpp:358 +#, c-format +msgid "Exception for %s has been updated to %d." +msgstr "Exception for %s has been updated to %d." + +#: modules/pseudoclients/chanserv.cpp:465 +#: modules/pseudoclients/nickserv.cpp:557 +#: modules/pseudoclients/nickserv.cpp:562 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_session.cpp:514 modules/commands/ns_group.cpp:327 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Expires" +msgstr "Expires in: %s" + +#: src/xline.cpp:397 +#, fuzzy, c-format +msgid "Expiry and reason updated for %s." +msgstr "Exception for %s has been updated to %d." + +#: src/xline.cpp:400 +#, fuzzy, c-format +msgid "Expiry for %s updated." +msgstr "Temps d'expiració per a %s canviat." + +#: modules/fantasy.cpp:214 +msgid "Fantasy" +msgstr "Fantasia" + +#: modules/fantasy.cpp:60 +#, fuzzy, c-format +msgid "Fantasy mode is now off on channel %s." +msgstr "Mode fantasia ara activada en el canal %s." + +#: modules/fantasy.cpp:52 +#, fuzzy, c-format +msgid "Fantasy mode is now on on channel %s." +msgstr "Mode fantasia ara activada en el canal %s." + +#: modules/commands/cs_status.cpp:19 +#, fuzzy +msgid "Find a user's status on a channel" +msgstr " DEOWNER Removes your owner status on a channel" + +#: modules/commands/ns_cert.cpp:192 +#, fuzzy, c-format +msgid "Fingerprint %s already present on %s's certificate list." +msgstr "La mascara %s ja esta present a la teva lllista d'accés." + +#: modules/commands/ns_cert.cpp:198 +#, fuzzy, c-format +msgid "Fingerprint %s is already in use." +msgstr "You are already in %s! " + +#: modules/commands/cs_flags.cpp:301 +msgid "Flags" +msgstr "" + +#: modules/commands/cs_flags.cpp:286 +#, fuzzy, c-format +msgid "Flags for %s on %s set to +%s" +msgstr "Nivell d'accés per a %s en %s cambiada a %d." + +#: modules/commands/cs_flags.cpp:341 +#, fuzzy, c-format +msgid "Flags list for %s" +msgstr "Lllista d'accés per %s:" + +#: modules/commands/bs_kick.cpp:1161 modules/commands/bs_kick.cpp:1163 +#: modules/commands/bs_kick.cpp:1166 +#, fuzzy +msgid "Flood kicker" +msgstr " Kicker per flood : %s" + +#: modules/commands/os_forbid.cpp:421 +msgid "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." +msgstr "" + +#: modules/commands/os_forbid.cpp:354 +#, fuzzy +msgid "Forbid list is empty." +msgstr "La llista ignore esta buida." + +#: modules/commands/os_forbid.cpp:396 +#, fuzzy +msgid "Forbid list:" +msgstr "Llista de bots:" + +#: modules/commands/os_forbid.cpp:348 +#, c-format +msgid "Forbid on %s was not found." +msgstr "" + +#: modules/commands/os_forbid.cpp:156 +msgid "Forbid usage of nicknames, channels, and emails" +msgstr "" + +#: modules/commands/os_update.cpp:19 +#, fuzzy +msgid "Force the Services databases to be updated immediately" +msgstr "" +" UPDATE Força a la base de dades dels serveis a\n" +" ser actualitzada a disc inmediatament" + +#: modules/commands/os_svs.cpp:19 +#, fuzzy +msgid "Forcefully change a user's nickname" +msgstr " SVSNICK Forcefully change a user's nickname" + +#: modules/commands/os_svs.cpp:68 +#, fuzzy +msgid "Forcefully changes a user's nickname from nick to newnick." +msgstr "" +"Syntax: SVSNICK nick newnick\n" +"\n" +"Forcefully changes a user's nickname from nick to newnick." + +#: modules/commands/os_svs.cpp:78 +#, fuzzy +msgid "Forcefully join a user to a channel" +msgstr " SVSNICK Forcefully change a user's nickname" + +#: modules/commands/os_svs.cpp:112 +#, fuzzy +msgid "Forcefully join a user to a channel." +msgstr " SVSNICK Forcefully change a user's nickname" + +#: modules/commands/os_svs.cpp:122 +#, fuzzy +msgid "Forcefully part a user from a channel" +msgstr " KICK Kickeja un usuari d'un canal" + +#: modules/commands/os_svs.cpp:160 +#, fuzzy +msgid "Forcefully part a user from a channel." +msgstr " KICK Kickeja un usuari d'un canal" + +#: modules/commands/ns_alist.cpp:64 modules/commands/cs_info.cpp:47 +#, fuzzy +msgid "Founder" +msgstr "Fundador Segur" + +#: modules/commands/cs_set.cpp:315 +#, fuzzy, c-format +msgid "Founder of %s changed to %s." +msgstr "El Fundador de %s cambiat a %s." + +#: modules/commands/ns_getpass.cpp:41 +msgid "GETPASS command unavailable because encryption is in use." +msgstr "La comanda GETPASS no esta disponible per l'us d'encriptació." + +#: modules/commands/ns_recover.cpp:84 +msgid "Ghost with your nick has been killed." +msgstr "El ghost amb el teu nick ha estat expulsat." + +#: modules/commands/os_oline.cpp:19 +#, fuzzy +msgid "Give Operflags to a certain user" +msgstr " OLINE Give Operflags to a certain user" + +#: modules/commands/cs_mode.cpp:905 +#, c-format +msgid "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." +msgstr "" + +#: modules/commands/cs_mode.cpp:888 +#, fuzzy, c-format +msgid "Gives you or the specified nick %s status on a channel" +msgstr " OWNER Gives you owner status on channel" + +#: modules/commands/greet.cpp:206 modules/commands/greet.cpp:212 +msgid "Greet" +msgstr "Salutació" + +#: src/access.cpp:38 +#, fuzzy +msgid "Greet message displayed on join" +msgstr "Greet message for %s changed to %s." + +#: modules/commands/greet.cpp:112 +#, c-format +msgid "Greet message for %s changed to %s." +msgstr "Greet message for %s changed to %s." + +#: modules/commands/greet.cpp:118 +#, c-format +msgid "Greet message for %s unset." +msgstr "Greet message for %s unset." + +#: modules/commands/greet.cpp:60 +#, fuzzy, c-format +msgid "Greet mode is now off on channel %s." +msgstr "Mode salutació ara activat en el canal %s." + +#: modules/commands/greet.cpp:52 +#, fuzzy, c-format +msgid "Greet mode is now on on channel %s." +msgstr "Mode salutació ara activat en el canal %s." + +#: modules/commands/ns_resetpass.cpp:21 +#, fuzzy +msgid "Helps you reset lost passwords" +msgstr " RESETPASS Helps you reset lost passwords." + +#: modules/commands/ns_info.cpp:141 +#, fuzzy +msgid "Hide certain pieces of nickname information" +msgstr " HIDE Oculta algunes parts de la teva informació" + +#: modules/commands/cs_list.cpp:180 +#, fuzzy +msgid "Hide channel from the LIST command" +msgstr " PRIVATE Oculta el canal de la comanda LIST" + +#: modules/commands/os_session.cpp:192 +msgid "Host" +msgstr "" + +#: modules/commands/os_session.cpp:207 +#, c-format +msgid "Hosts with at least %d sessions:" +msgstr "Hosts amb un mínim de %d sessions:" + +#: modules/commands/cs_seen.cpp:207 +#, c-format +msgid "I don't know who %s is." +msgstr "" + +#: modules/commands/cs_seen.cpp:253 +#, fuzzy, c-format +msgid "I've never seen %s on this channel." +msgstr "No utilitzis reversos en aquest canal!" + +#: modules/commands/os_sxline.cpp:203 modules/commands/os_akill.cpp:360 +msgid "ID" +msgstr "" + +#: modules/commands/os_oper.cpp:72 +msgid "INFO [type]" +msgstr "" + +#: modules/commands/os_dns.cpp:218 +msgid "IP" +msgstr "" + +#: modules/commands/os_dns.cpp:500 +#, fuzzy, c-format +msgid "IP %s already exists for %s." +msgstr "El bot %s ja existeix." + +#: modules/commands/os_dns.cpp:562 +#, fuzzy, c-format +msgid "IP %s does not exist for %s." +msgstr "El bot %s ja existeix." + +#: modules/commands/ns_identify.cpp:65 +#, fuzzy +msgid "Identify yourself with your password" +msgstr " IDENTIFY Per identificar-te amb la teva clau" + +#: modules/pseudoclients/nickserv.cpp:205 +#: modules/pseudoclients/nickserv.cpp:211 +#, fuzzy, c-format +msgid "If you do not change within %s, I will change your nick." +msgstr "Si no canvies el teu nick en 20 segons, el canviare jo." + +#: modules/commands/os_ignore.cpp:333 +msgid "Ignore list has been cleared." +msgstr "Ignore list has been cleared." + +#: modules/commands/os_ignore.cpp:262 +msgid "Ignore list is empty." +msgstr "La llista ignore esta buida." + +#: modules/commands/ms_ignore.cpp:94 +#, fuzzy +msgid "Ignore list:" +msgstr "Llista de bots:" + +#: modules/commands/ns_set.cpp:1305 +#, fuzzy +msgid "Immediate protection" +msgstr "Protecció de Voices" + +#: modules/commands/ns_resetpass.cpp:33 +#, fuzzy +msgid "Incorrect email address." +msgstr " \t\tAdreça E-mail: %s" + +#: include/language.h:89 +msgid "Incorrect range specified. The correct syntax is #from-to." +msgstr "" + +#: modules/commands/os_modinfo.cpp:19 +#, fuzzy +msgid "Info about a loaded module" +msgstr " MODINFO Info about a loaded module" + +#: modules/commands/bs_info.cpp:54 +#, c-format +msgid "Information for bot %s:" +msgstr "Informació pel bot %s:" + +#: include/language.h:108 +#, fuzzy, c-format +msgid "Information for channel %s:" +msgstr "Informació pel bot %s:" + +#: modules/commands/os_logsearch.cpp:57 +#, c-format +msgid "Invalid duration %s, using %d days." +msgstr "" + +#: include/language.h:68 +msgid "Invalid expiry time." +msgstr "" + +#: modules/commands/os_session.cpp:346 +#, fuzzy +msgid "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not " +"matched against nicks or usernames." +msgstr "" +"Mascara invalida. Nomès mascares reals son valides ja que excepcions no son " +"comparades a nicks o usernames." + +#: modules/commands/os_logsearch.cpp:73 +#, c-format +msgid "Invalid limit %s, using %d." +msgstr "" + +#: include/language.h:99 +msgid "" +"Invalid passcode has been entered, please check the e-mail again, and retry." +msgstr "" + +#: modules/commands/ns_register.cpp:83 modules/commands/ns_register.cpp:86 +msgid "Invalid passcode." +msgstr "" + +#: modules/commands/os_session.cpp:339 +#, c-format +msgid "" +"Invalid session limit. It must be a valid integer greater than or equal to " +"zero and less than %d." +msgstr "" +"Límit de sessió invàlid. Ha de ser un sencer vàlido més gran o igual a zero " +"i mes petit que %d." + +#: modules/commands/os_session.cpp:188 +msgid "Invalid threshold value. It must be a valid integer greater than 1." +msgstr "Valor de umbral invàlid. Ha de ser un sencer vàlid més gran a 1." + +#: modules/commands/os_dns.cpp:591 +msgid "Invalid value for LIMIT. Must be numerical." +msgstr "" + +#: modules/commands/cs_invite.cpp:19 +#, fuzzy +msgid "Invites you or an optionally specified nick into a channel" +msgstr " OP Gives Op status to a selected nick on a channel" + +#: modules/commands/bs_kick.cpp:1201 modules/commands/bs_kick.cpp:1203 +#: modules/commands/bs_kick.cpp:1206 +#, fuzzy +msgid "Italics kicker" +msgstr " Italics kicker : %s" + +#: modules/commands/ns_group.cpp:91 +#, fuzzy +msgid "Join a group" +msgstr " GROUP Ingresa en un grup" + +#: modules/commands/cs_set.cpp:1305 modules/commands/ns_set.cpp:1319 +#, fuzzy +msgid "Keep modes" +msgstr "Mode de missatge" + +#: modules/commands/cs_set.cpp:377 modules/commands/ns_set.cpp:603 +#, fuzzy, c-format +msgid "Keep modes for %s is now off." +msgstr "Peace option for %s is now ON." + +#: modules/commands/cs_set.cpp:369 modules/commands/ns_set.cpp:597 +#, fuzzy, c-format +msgid "Keep modes for %s is now on." +msgstr "Peace option for %s is now ON." + +#: modules/commands/ns_ajoin.cpp:100 +msgid "Key" +msgstr "" + +#: modules/commands/cs_getkey.cpp:50 +#, c-format +msgid "Key for channel %s is %s." +msgstr "Key for channel %s is %s." + +#: modules/commands/os_kick.cpp:19 +#, fuzzy +msgid "Kick a user from a channel" +msgstr " KICK Kickeja un usuari d'un canal" + +#: modules/commands/cs_ban.cpp:217 modules/commands/cs_kick.cpp:116 +#, c-format +msgid "Kicked %d/%d users matching %s from %s." +msgstr "" + +#: modules/commands/cs_kick.cpp:19 +#, fuzzy +msgid "Kicks a specified nick from a channel" +msgstr " KICK Kicks a selected nick from a channel" + +#: modules/commands/cs_kick.cpp:128 +#, fuzzy +msgid "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." +msgstr "" +"Sintàxi: KICK #canal nick [raó]\n" +"\n" +"Kickeja al nick seleccionat en el canal.\n" +"\n" +"Per defecte, limitat a AOPs o aquells amb nivell d'\n" +"accés 5 i major en el canal." + +#: modules/commands/os_kill.cpp:19 +msgid "Kill a user" +msgstr "" + +#: modules/commands/cs_enforce.cpp:217 +msgid "LIMIT enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:221 +#, c-format +msgid "LIMIT enforced on %s, %d users removed." +msgstr "" + +#: modules/commands/os_session.cpp:246 +msgid "LIST threshold" +msgstr "" + +#: modules/commands/os_sxline.cpp:427 modules/commands/os_sxline.cpp:661 +#: modules/commands/os_akill.cpp:388 +#, fuzzy +msgid "LIST [mask | list | id]" +msgstr "LIST [canal] [llista | NEW]" + +#: modules/commands/os_session.cpp:525 +#, fuzzy +msgid "LIST [mask | list]" +msgstr "LIST [canal] [llista | NEW]" + +#: modules/commands/ns_access.cpp:104 modules/commands/ns_cert.cpp:260 +#: modules/commands/ns_ajoin.cpp:233 +#, fuzzy +msgid "LIST [nickname]" +msgstr "CHECK nickname" + +#: modules/commands/os_news.cpp:31 +msgid "LOGONNEWS {ADD|DEL|LIST} [text|num]" +msgstr "LOGONNEWS {ADD|DEL|LIST} [text|numero]" + +#: modules/commands/ns_set.cpp:834 +msgid "Language changed to English." +msgstr "Llenguatge canviat a Català." + +#: modules/commands/ns_set.cpp:836 +#, fuzzy, c-format +msgid "Language for %s changed to %s." +msgstr "Sucessor de %s cambiat a %s." + +#: modules/commands/ms_cancel.cpp:72 +#, c-format +msgid "Last memo to %s has been cancelled." +msgstr "Ultim memo enviat a %s va ser cancel.lat." + +#: modules/commands/ns_info.cpp:95 +#, fuzzy +msgid "Last quit message" +msgstr " Ùltim missatge quit: %s" + +#: modules/commands/cs_access.cpp:472 modules/commands/ns_info.cpp:92 +#, fuzzy +msgid "Last seen" +msgstr " Ultima vegada vist: %s" + +#: modules/commands/ns_info.cpp:81 modules/commands/ns_info.cpp:86 +#, fuzzy +msgid "Last seen address" +msgstr "Ultima adreça vista: %s" + +#: modules/commands/cs_topic.cpp:264 +msgid "Last topic" +msgstr "" + +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_info.cpp:56 +#, fuzzy +msgid "Last used" +msgstr " Ultima vegada vist: %s" + +#: modules/commands/ns_list.cpp:75 +#, fuzzy +msgid "Last usermask" +msgstr " Ultima vegada vist: %s" + +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +#: modules/commands/cs_access.cpp:697 +msgid "Level" +msgstr "" + +#: modules/commands/cs_access.cpp:660 +#, c-format +msgid "Level for %s on channel %s changed to %d." +msgstr "Nivell per a %s en el canal %s cambiat a %d." + +#: modules/commands/cs_access.cpp:658 +#, c-format +msgid "Level for %s on channel %s changed to founder only." +msgstr "Level for %s on channel %s changed to founder only." + +#: modules/commands/cs_access.cpp:643 +#, c-format +msgid "Level must be between %d and %d inclusive." +msgstr "El nivell ha d'estar entre %d i %d inclosos." + +#: modules/commands/os_dns.cpp:218 modules/commands/os_session.cpp:506 +#: modules/commands/os_session.cpp:514 +msgid "Limit" +msgstr "" + +#: modules/commands/ns_list.cpp:19 +#, fuzzy +msgid "List all registered nicknames that match a given pattern" +msgstr "" +" LIST List all registered nicknames that match a given pattern" + +#: modules/commands/ns_alist.cpp:24 +#, fuzzy +msgid "List channels you have access on" +msgstr " ALIST List channels you have access on" + +#: modules/commands/cs_mode.cpp:341 +#, c-format +msgid "List for mode %c is full." +msgstr "" + +#: modules/commands/os_modinfo.cpp:80 +#, fuzzy +msgid "List loaded modules" +msgstr " MODLIST List loaded modules" + +#: modules/commands/ns_list.cpp:123 modules/commands/cs_list.cpp:72 +#, fuzzy, c-format +msgid "List of entries matching %s:" +msgstr "Lllista de nicknames en el grup de %s:" + +#: modules/commands/ns_group.cpp:350 +#, c-format +msgid "List of nicknames in the group of %s:" +msgstr "Lllista de nicknames en el grup de %s:" + +#: modules/commands/ns_group.cpp:350 +msgid "List of nicknames in your group:" +msgstr "Lllista de nicknames en el teu grup:" + +#: modules/commands/ms_list.cpp:19 +#, fuzzy +msgid "List your memos" +msgstr " LIST llista els teus memos" + +#: modules/commands/bs_botlist.cpp:64 +#, fuzzy +msgid "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." +msgstr "" +"Sintàxi: BOTLIST\n" +"\n" +"Llista tots els bots disponibles en aquesta xarxa." + +#: modules/commands/os_list.cpp:19 +#, fuzzy +msgid "Lists all channel records" +msgstr " CHANLIST Llista tots els records de canal" + +#: modules/commands/os_list.cpp:107 +#, fuzzy +msgid "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." +msgstr "" +"Sintàxi: CHANLIST [{patró | nick} [SECRET]]\n" +"\n" +"Llista tots els canals actualment en ús en la xarxa IRC,\n" +"estiguin registrats o no.\n" +"\n" +"Si s'especifica patró, llista nomès els canals que concordin amb ell. \n" +"Si s'especifica un nickname, llista nomès els canals en els que l'usuari\n" +"hi sigui. Si s'especifica SECRET, llista nomès els canals que\n" +"concordin amb patró i que tinguin modes +s o +p.\n" +"\n" +"Limitat a administradors de serveis." + +#: modules/commands/ns_alist.cpp:127 +msgid "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" +msgstr "" + +#: modules/commands/ns_group.cpp:299 +#, fuzzy +msgid "Lists all nicknames in your group" +msgstr "Lllista de nicknames en el teu grup:" + +#: modules/commands/cs_list.cpp:20 +#, fuzzy +msgid "Lists all registered channels matching the given pattern" +msgstr "" +" LIST Lists all registered channels matching the given pattern" + +#: modules/commands/cs_list.cpp:137 +#, fuzzy +msgid "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." +msgstr "" +"Sintaxis: LIST patró [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]\n" +"\n" +"Llista tots els nicknames registrats que concordin amb el\n" +"patró donat, en el format nick!usuari@host. Nicks amb\n" +"L'opció PRIVATE tan sols sera mostrada a administradors\n" +"de serveis. Nicks amb l'opció NOEXPIRE establerta tindran\n" +"un ! avantposat al nickname per a administradors de\n" +"serveis.\n" +"\n" +"If the FORBIDDEN, SUSPENDED, NOEXPIRE or UNCONFIRMED options are given, " +"only\n" +"nicks which, respectively, are FORBIDDEN, SUSPENDED, UNCONFIRMED or have " +"the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"These options are limited to Services Operators. \n" +"\n" +"Exemples:\n" +"\n" +" LIST *!cistus@aujac.org\n" +" Llista tots els nicks registrats per cistus@aujac.org.\n" +"\n" +" LIST *Bot*!*@*\n" +" Llista tots els nicks registrats amb Bot en\n" +" els seus noms. (no sensible a majuscules i minuscules).\n" +"\n" +" LIST * NOEXPIRE\n" +" Llista tots els nicks registrats que hagin estat establerts\n" +" a no caducitat." + +#: modules/commands/ns_list.cpp:139 +#, fuzzy +msgid "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." +msgstr "" +"Sintaxis: LIST patró [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]\n" +"\n" +"Llista tots els nicknames registrats que concordin amb el\n" +"patró donat, en el format nick!usuari@host. Nicks amb\n" +"L'opció PRIVATE tan sols sera mostrada a administradors\n" +"de serveis. Nicks amb l'opció NOEXPIRE establerta tindran\n" +"un ! avantposat al nickname per a administradors de\n" +"serveis.\n" +"\n" +"If the FORBIDDEN, SUSPENDED, NOEXPIRE or UNCONFIRMED options are given, " +"only\n" +"nicks which, respectively, are FORBIDDEN, SUSPENDED, UNCONFIRMED or have " +"the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"These options are limited to Services Operators. \n" +"\n" +"Exemples:\n" +"\n" +" LIST *!cistus@aujac.org\n" +" Llista tots els nicks registrats per cistus@aujac.org.\n" +"\n" +" LIST *Bot*!*@*\n" +" Llista tots els nicks registrats amb Bot en\n" +" els seus noms. (no sensible a majuscules i minuscules).\n" +"\n" +" LIST * NOEXPIRE\n" +" Llista tots els nicks registrats que hagin estat establerts\n" +" a no caducitat." + +#: modules/commands/os_list.cpp:132 +#, fuzzy +msgid "Lists all user records" +msgstr " USERLIST Llista tots els records d'usuaris" + +#: modules/commands/os_list.cpp:243 +#, fuzzy +msgid "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only " +"users\n" +"with the +i flag will be listed." +msgstr "" +"Sintàxi: USERLIST [{patró | canal} [INVISIBLE]]\n" +"\n" +"Llista tots els usuaris actualment en linea en la xarxa IRC,\n" +"estiguin registrats o no.\n" +"\n" +"Si s'especifica patró, llista nomès els usuaris que concordin\n" +"amb ell (ha de ser amb el format nick!usuari@host). Si s'especifica canal,\n" +"llista nomès els usuaris que estiguin en el canal donat. Si s'especifica\n" +"INVISIBLE, nomès els usuaris amb la bandera +i seran\n" +"llistats.\n" +"\n" +"Limitat a administradors de serveis." + +#: modules/commands/ms_list.cpp:142 +#, fuzzy +msgid "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Sintàxi: LIST [canal] [llista | NEW]\n" +"\n" +"llista els memos que tens actualment. Amb NEW, llista\n" +"només els memos nous (no llegits). Memos nous estan\n" +"marcats amb un \"*\" a l'esquerra del nobre del memo.\n" +"També pots especificar una llista de nombres, com en el\n" +"exemple més endevant:\n" +"\n" +" LIST 2-5,7-9\n" +" llista memos enumerats 2 a 5 i 7 a 9." + +#: modules/commands/bs_botlist.cpp:19 +#, fuzzy +msgid "Lists available bots" +msgstr "BOTLIST Llista bots disponibles" + +#: modules/commands/os_modinfo.cpp:196 +#, fuzzy +msgid "Lists currently loaded modules." +msgstr " MODLIST List loaded modules" + +#: modules/commands/cs_info.cpp:19 +#, fuzzy +msgid "Lists information about the specified registered channel" +msgstr " INFO Lists information about the named registered channel" + +#: modules/commands/cs_info.cpp:76 +#, fuzzy +msgid "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." +msgstr "" +"Sintàxi: INFO canal\n" +"\n" +"llista informació sobre el canal registrat donat,\n" +"incloent el seu fundador, temps de registració, últim\n" +"cop utilitzat, descripció i fixació de Modes, si existeixen.\n" +"Si ALL és especificat, el misatge d'entrada i\n" +"sucsesor també seran mostrats." + +#: modules/commands/os_module.cpp:19 +#, fuzzy +msgid "Load a module" +msgstr " MODLOAD Load a module" + +#: modules/commands/cs_register.cpp:39 +msgid "Local channels cannot be registered." +msgstr "Canals locals no poden ser enregistrats." + +#: modules/commands/cs_log.cpp:142 +#, fuzzy, c-format +msgid "Log list for %s:" +msgstr "Lllista d'accés per %s:" + +#: modules/commands/cs_log.cpp:227 +#, c-format +msgid "Logging changed for command %s on %s, now using log method %s%s%s." +msgstr "" + +#: modules/commands/cs_log.cpp:220 +#, c-format +msgid "Logging for command %s on %s with log method %s%s%s has been removed." +msgstr "" + +#: modules/commands/cs_log.cpp:248 +#, c-format +msgid "Logging is now active for command %s on %s, using log method %s%s%s." +msgstr "" + +#: modules/commands/os_login.cpp:60 +#, c-format +msgid "Login to %s" +msgstr "" + +#: modules/commands/os_news.cpp:36 +#, c-format +msgid "Logon news item #%d deleted." +msgstr "Notícia d'entrada #%d esborrada." + +#: modules/commands/os_news.cpp:35 +#, fuzzy, c-format +msgid "Logon news item #%s not found!" +msgstr "Notícia d'entrada #%d no trobada!" + +#: modules/commands/os_news.cpp:32 +msgid "Logon news items:" +msgstr "Notícies d'entrada:" + +#: modules/commands/os_login.cpp:102 +#, fuzzy, c-format +msgid "Logout from %s" +msgstr "Lllista d'accés per %s:" + +#: modules/commands/os_login.cpp:52 +#, c-format +msgid "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." +msgstr "" + +#: modules/commands/os_login.cpp:94 +#, c-format +msgid "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." +msgstr "" + +#: modules/commands/cs_seen.cpp:213 +#, c-format +msgid "Looking for yourself, eh %s?" +msgstr "" + +#: modules/commands/cs_mode.cpp:773 +#, c-format +msgid "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a " +"channel.\n" +"If a mode is locked on or off, services will not allow that mode to be " +"changed. The SET\n" +"command will clear all existing mode locks and set the new one given, while " +"ADD and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * " +"and ? may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may " +"be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, " +"halfops, and voices. If what\n" +"is not given then all basic modes are removed." +msgstr "" + +#: modules/commands/cs_akick.cpp:434 +#, fuzzy +msgid "Maintain the AutoKick list" +msgstr " AKICK Manté la llista d'AutoKick" + +#: modules/commands/bs_bot.cpp:269 +#, fuzzy +msgid "Maintains network bot list" +msgstr "BOT Manté la llista de bots de la xarxa" + +#: modules/commands/cs_xop.cpp:522 +#, c-format +msgid "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " +msgstr "" + +#: modules/commands/cs_akick.cpp:493 +#, c-format +msgid "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" +msgstr "" + +#: modules/commands/cs_access.cpp:568 +#, c-format +msgid "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." +msgstr "" + +#: modules/commands/bs_badwords.cpp:424 +#, fuzzy, c-format +msgid "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" +msgstr "" +"Sintàxi: BADWORDS canal ADD paraula [SINGLE | START | END]\n" +" BADWORDS canal DEL {paraula | nom | llista}\n" +" BADWORDS canal LIST [mascara | llista]\n" +" BADWORDS canal CLEAR\n" +"\n" +"Mante la llista de paraules malsonants per un canal. La llista\n" +"de paraules malsonants determina quines paraules han de donar peu a ser " +"kickejats\n" +"Quan el kick per paraules malsonants esta habilitat. Per més\n" +"informació, escriu /msg %s HELP KICK BADWORDS.\n" +"\n" +"La comanda BADWORDS ADD afegeix una paraula a la llista\n" +"de paraules malsonants. Si s'especifica SINGLE, el kick es\n" +"fara nomès si l'usuari du la paraula completa. Si s'especifica\n" +"START, el kick es fara nomès si l'usuari\n" +"escriu una paraula que comenci amb paraula.\n" +"Si no s'especifica END, el kick es fara nomès si\n" +"l'usuari escriu una paraula que finalitzi amb paraula. Si\n" +"no s'especifica res, un kick es farà cada vegada que\n" +"paraula sigui escrita per un usuari.\n" +"\n" +"La comanda BADWORDS DEL esborra la paraula esmantada de la\n" +"llista de paraules malsonants. Si s'especifica una llista de noms, aquestes\n" +"instàncies son esborrades. (Veure l'exemple per LIST especificat més\n" +"endavant).\n" +"\n" +"La comanda BADWORDS LIST mostra la llista de bad\n" +"words. Si s'especifica una mascara, nomès les instàncies\n" +"concordant amb la mascara són mostrades. Si s'especifica una llista\n" +"de noms, nomès aquestes instàncies son mostrades;\n" +"per exemple:\n" +"\n" +" BADWORDS #canal LIST 2-5,7-9\n" +" Llista paraules malsonants enumerades de 2 a 5 i de 7 a 9.\n" +" \n" +"La comanda BADWORDS CLEAR neteja totes les instàncies\n" +"de la llista de paraules malsonants." + +#: modules/commands/bs_badwords.cpp:370 +#, fuzzy +msgid "Maintains the bad words list" +msgstr "BADWORDS Manté una llista de paraules malsonants" + +#: modules/commands/bs_control.cpp:79 +#, fuzzy +msgid "Makes the bot do the equivalent of a \"/me\" command" +msgstr "" +"ACT Makes the bot do the equivalent of a \"/me\" command" + +#: modules/commands/bs_control.cpp:127 +#, fuzzy +msgid "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." +msgstr "" +"Sintàxi: ACT canal text\n" +"\n" +"Fa que el bot fagi l'equivalent a la comanda \"/me\"\n" +"en el canal especificat utilitzant el text especificat." + +#: modules/commands/bs_control.cpp:19 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel" +msgstr "" +"SAY Makes the bot say the given text on the given channel" + +#: modules/commands/bs_control.cpp:69 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel." +msgstr "" +"SAY Makes the bot say the given text on the given channel" + +#: modules/commands/greet.cpp:157 +#, fuzzy +msgid "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." +msgstr "" +"Syntax: SASET nickname GREET message\n" +"\n" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary \n" +"access on it." + +#: modules/commands/greet.cpp:131 +#, fuzzy +msgid "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." +msgstr "" +"Sintaxis: SET GREET missatge\n" +"\n" +"Fa que el missatge introduit sigui la salutació pel teu nickname, \n" +"el que sera mostrat quant entris a un canal amb la\n" +"opció GREET habilitada, sempre i quant tinguis \n" +"l'accés necessari." + +#: modules/commands/os_dns.cpp:660 +#, fuzzy +msgid "Manage DNS zones for this network" +msgstr "No pots establir la teva adreça e-mail en aquesta xarxa." + +#: modules/commands/cs_entrymsg.cpp:193 +#, fuzzy +msgid "Manage the channel's entry messages" +msgstr " PERSIST Set the channel as permanent" + +#: modules/commands/ms_ignore.cpp:19 +#, fuzzy +msgid "Manage the memo ignore list" +msgstr " IGNORE Modify the Services ignore list" + +#: modules/commands/ns_ajoin.cpp:230 +#, fuzzy +msgid "Manage your auto join list" +msgstr " AKICK Manté la llista d'AutoKick" + +#: modules/commands/os_sxline.cpp:233 +#, fuzzy, c-format +msgid "Manipulate the %s list" +msgstr " AKILL Manipula la llista AKILL" + +#: modules/commands/os_akill.cpp:385 +#, fuzzy +msgid "Manipulate the AKILL list" +msgstr " AKILL Manipula la llista AKILL" + +#: modules/commands/os_defcon.cpp:176 +#, fuzzy +msgid "Manipulate the DefCon system" +msgstr " DEFCON Manipulate the DefCon system" + +#: modules/commands/cs_topic.cpp:149 +#, fuzzy +msgid "Manipulate the topic of the specified channel" +msgstr " TOPIC Manipulate the topic of the specified channel" + +#: modules/commands/bs_botlist.cpp:27 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_forbid.cpp:358 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/ms_ignore.cpp:86 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_list.cpp:153 modules/commands/bs_info.cpp:55 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +msgid "Mask" +msgstr "" + +#: modules/commands/ns_access.cpp:39 +#, fuzzy, c-format +msgid "Mask %s already present on %s's access list." +msgstr "La mascara %s ja esta present a la teva lllista d'accés." + +#: include/language.h:67 +msgid "Mask must be in the form user@host." +msgstr "" + +#: modules/commands/cs_access.cpp:166 modules/commands/cs_flags.cpp:120 +#: modules/commands/cs_xop.cpp:162 +#, fuzzy +msgid "Masks and unregistered users may not be on access lists." +msgstr "La mascara %s ja esta present a la teva lllista d'accés." + +#: modules/commands/ns_getemail.cpp:23 +#, fuzzy +msgid "Matches and returns all users that registered using given email" +msgstr "" +" GETEMAIL Matches and returns all users that registered using given " +"email" + +#: modules/commands/os_logsearch.cpp:148 +#, fuzzy, c-format +msgid "Matches for %s:" +msgstr " Mode de lock: %s" + +#: modules/commands/os_stats.cpp:139 +#, c-format +msgid "Maximum users: %d (%s)" +msgstr "Màxim numero d'usuaris: %d (%s)" + +#: modules/commands/ms_read.cpp:84 modules/commands/ms_read.cpp:86 +#, fuzzy, c-format +msgid "Memo %d from %s (%s)." +msgstr " Mode de lock: %s" + +#: modules/commands/ms_del.cpp:33 modules/commands/ms_del.cpp:101 +#, c-format +msgid "Memo %d has been deleted." +msgstr "Memo %d ha estat esborrat." + +#: modules/commands/ms_ignore.cpp:82 +#, fuzzy +msgid "Memo ignore list is empty." +msgstr "La llista ignore esta buida." + +#: modules/commands/ms_set.cpp:199 +#, c-format +msgid "Memo limit disabled for %s." +msgstr "Límit de memos per a %s deshabilitat." + +#: modules/commands/ms_set.cpp:185 +#, c-format +msgid "Memo limit for %s set to %d." +msgstr "Límite de memos per a %s establert a %d." + +#: modules/commands/ms_set.cpp:192 +#, c-format +msgid "Memo limit for %s set to 0." +msgstr "Límit de memos per a %s establert a 0." + +#: modules/commands/ms_rsend.cpp:63 modules/commands/ms_send.cpp:51 +#, c-format +msgid "Memo sent to %s." +msgstr "Memo enviat a %s." + +#: modules/commands/ms_list.cpp:131 +#, fuzzy, c-format +msgid "Memos for %s:" +msgstr " Mode de lock: %s" + +#: modules/commands/cs_entrymsg.cpp:116 +#, fuzzy +msgid "Message" +msgstr "GLOBAL missatge" + +#: modules/commands/ns_set.cpp:1313 +msgid "Message mode" +msgstr "Mode de missatge" + +#: modules/commands/cs_log.cpp:127 +msgid "Method" +msgstr "" + +#: modules/commands/cs_mode.cpp:329 modules/commands/cs_mode.cpp:420 +#, c-format +msgid "Missing parameter for mode %c." +msgstr "" + +#: modules/commands/cs_mode.cpp:449 +msgid "Mode" +msgstr "" + +#: modules/commands/cs_mode.cpp:718 +#, fuzzy, c-format +msgid "Mode %s is a virtual mode and can't be cleared." +msgstr "Nick %s is an illegal nickname and cannot be used." + +#: modules/commands/cs_mode.cpp:712 +#, fuzzy, c-format +msgid "Mode %s is not a status or list mode." +msgstr "%s not found on ignore list." + +#: modules/commands/cs_mode.cpp:1065 +#, fuzzy +msgid "Mode lock" +msgstr " Mode de lock: %s" + +#: modules/commands/cs_mode.cpp:466 +#, fuzzy, c-format +msgid "Mode locks for %s:" +msgstr " Mode de lock: %s" + +#: modules/commands/os_list.cpp:43 +msgid "Modes" +msgstr "" + +#: modules/commands/os_mode.cpp:44 +#, c-format +msgid "Modes cleared on %s and the channel destroyed." +msgstr "" + +#: modules/commands/ns_access.cpp:166 +#, fuzzy, c-format +msgid "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." +msgstr "" +"Sintaxis: ACCESS ADD mascara\n" +" ACCESS DEL mascara\n" +" ACCESS LIST\n" +"\n" +"Modifica o mostra la llista d'accés pel teu nick. Aquesta\n" +"és la llista d'adreces que seran automaticament\n" +"reconegudes per %s com autoritzades a utilitzar el nick. Si\n" +"vols utilitzar el nick des d'una adreça diferent,\n" +"has d'enviar una comanda IDENTIFY per fer que %s et\n" +"reconegui.\n" +"\n" +"Exemples:\n" +"\n" +" ACCESS ADD anyone@*.aujac.org\n" +" Permet accés a l'usuari anyone des de\n" +" qualsevol maquina en el domini aujac.org.\n" +"\n" +" ACCESS DEL anyone@*.aujac.org\n" +" Anul.la la comanda anterior.\n" +"\n" +" ACCESS LIST\n" +" Mostra la llista d'accés actual." + +#: modules/commands/ns_cert.cpp:319 +msgid "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" +msgstr "" + +#: modules/commands/os_ignore.cpp:341 +#, fuzzy +msgid "Modify the Services ignore list" +msgstr " IGNORE Modify the Services ignore list" + +#: modules/commands/cs_xop.cpp:489 +#, fuzzy, c-format +msgid "Modify the list of %s users" +msgstr " AOP Modifica la llista d'usuaris AOP" + +#: modules/commands/ns_access.cpp:101 +#, fuzzy +msgid "Modify the list of authorized addresses" +msgstr " ACCESS Modifica la llista d'adreçes autoritzades" + +#: modules/commands/cs_access.cpp:498 modules/commands/cs_flags.cpp:373 +#, fuzzy +msgid "Modify the list of privileged users" +msgstr " ACCESS Modifica la llista d'usuaris privilegiats" + +#: modules/commands/ns_cert.cpp:257 +#, fuzzy +msgid "Modify the nickname client certificate list" +msgstr " IGNORE Modify the Services ignore list" + +#: modules/commands/os_session.cpp:522 +#, fuzzy +msgid "Modify the session-limit exception list" +msgstr " EXCEPTION Modifica la llista de límit de sessió" + +#: modules/commands/os_module.cpp:34 +#, c-format +msgid "Module %s is already loaded." +msgstr "Module %s is already loaded." + +#: modules/commands/os_module.cpp:67 modules/commands/os_module.cpp:139 +#, c-format +msgid "Module %s isn't loaded." +msgstr "Module %s isn't loaded." + +#: modules/commands/os_module.cpp:31 +#, fuzzy, c-format +msgid "Module %s loaded." +msgstr "Module %s loaded" + +#: modules/commands/os_module.cpp:98 +#, fuzzy, c-format +msgid "Module %s reloaded." +msgstr "Module %s loaded" + +#: modules/commands/os_module.cpp:156 +#, fuzzy, c-format +msgid "Module %s unloaded." +msgstr "Module %s unloaded" + +#: modules/commands/os_config.cpp:88 +#, fuzzy +msgid "Module Name" +msgstr "Module %s loaded" + +#: modules/commands/os_config.cpp:112 +msgid "Module settings:" +msgstr "" + +#: modules/commands/os_modinfo.cpp:32 +#, fuzzy, c-format +msgid "Module: %s Version: %s Author: %s Loaded: %s" +msgstr "Module: %s Version: %s Author: %s loaded: %s" + +#: modules/commands/os_modinfo.cpp:183 +#, c-format +msgid "Module: %s [%s] [%s]" +msgstr "Module: %s [%s] [%s]" + +#: modules/commands/cs_access.cpp:697 modules/commands/cs_access.cpp:799 +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +#: modules/commands/cs_list.cpp:75 modules/commands/os_list.cpp:43 +#: modules/commands/os_list.cpp:153 +msgid "Name" +msgstr "" + +#: modules/commands/os_oper.cpp:153 +msgid "Name Type" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:146 +#, fuzzy, c-format +msgid "Network stats for %s:" +msgstr "Lllista d'accés per %s:" + +#: modules/commands/os_forbid.cpp:384 +msgid "Never" +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/bs_botlist.cpp:27 +#: modules/commands/hs_request.cpp:305 modules/commands/ns_list.cpp:75 +#: modules/commands/ns_group.cpp:327 +#, fuzzy +msgid "Nick" +msgstr "INFO nick" + +#: modules/commands/ns_register.cpp:42 +#, fuzzy, c-format +msgid "Nick %s has been confirmed." +msgstr "Nickname %s ha estat expulsat." + +#: modules/commands/os_oper.cpp:95 +#, fuzzy, c-format +msgid "Nick %s is already an operator." +msgstr "El nickname %s ja esta registrat!" + +#: modules/commands/ns_register.cpp:36 +#, fuzzy, c-format +msgid "Nick %s is already confirmed." +msgstr "El nickname %s ja esta registrat!" + +#: modules/commands/os_svs.cpp:46 +#, c-format +msgid "Nick %s is an illegal nickname and cannot be used." +msgstr "Nick %s is an illegal nickname and cannot be used." + +#: modules/commands/bs_bot.cpp:81 modules/commands/bs_bot.cpp:181 +#: modules/commands/os_svs.cpp:54 +#, c-format +msgid "Nick %s is currently in use." +msgstr "Nick %s is currently in use." + +#: modules/commands/os_forbid.cpp:512 +#, fuzzy, c-format +msgid "Nick %s is forbidden by %s: %s" +msgstr "Nick %s is currently in use." + +#: modules/commands/os_forbid.cpp:514 +#, fuzzy, c-format +msgid "Nick %s is forbidden." +msgstr "El nick %s no esta sent utilitzat." + +#: modules/commands/os_oper.cpp:134 +#, fuzzy, c-format +msgid "Nick %s is not a Services Operator." +msgstr "%s is a services operator of type %s." + +#: modules/commands/ns_info.cpp:34 +#, c-format +msgid "Nick %s is part of this Network's Services." +msgstr "Nick %s is part of this Network's Services." + +#: include/language.h:79 +#, fuzzy, c-format +msgid "Nick %s isn't currently in use." +msgstr "Nick %s is currently in use." + +#: include/language.h:78 +#, fuzzy, c-format +msgid "Nick %s isn't registered." +msgstr "Nickname %s registered." + +#: modules/commands/os_svs.cpp:39 +#, c-format +msgid "Nick %s was truncated to %d characters." +msgstr "Nick %s was truncated to %d characters." + +#: modules/commands/ns_set.cpp:1135 +#, c-format +msgid "Nick %s will expire." +msgstr "Nick %s will expire." + +#: modules/commands/ns_set.cpp:1129 +#, c-format +msgid "Nick %s will not expire." +msgstr "Nick %s will not expire." + +#: modules/commands/ms_check.cpp:60 +#, c-format +msgid "Nick %s doesn't have a memo from you." +msgstr "Nick %s doesn't have a memo from you." + +#: modules/commands/ns_logout.cpp:48 +#, c-format +msgid "Nick %s has been logged out." +msgstr "Nick %s ha estat desconnectat." + +#: modules/commands/ns_group.cpp:272 +#, c-format +msgid "Nick %s has been ungrouped from %s." +msgstr "Nick %s has been ungrouped from %s." + +#: include/language.h:81 +#, fuzzy, c-format +msgid "Nick %s is currently suspended." +msgstr "Nick %s is now suspended." + +#: modules/commands/ns_group.cpp:250 +#, fuzzy, c-format +msgid "Nick %s is not in your group." +msgstr "The nick %s is not in your group." + +#: modules/commands/ns_suspend.cpp:180 +#, fuzzy, c-format +msgid "Nick %s is not suspended." +msgstr "Nick %s is now suspended." + +#: modules/commands/ns_suspend.cpp:190 +#, c-format +msgid "Nick %s is now released." +msgstr "Nick %s is now released." + +#: modules/commands/ns_suspend.cpp:138 +#, c-format +msgid "Nick %s is now suspended." +msgstr "Nick %s is now suspended." + +#: modules/commands/cs_seen.cpp:275 +#, c-format +msgid "Nick too long, max length is %u characters." +msgstr "" + +#: modules/commands/ns_drop.cpp:53 +#, c-format +msgid "Nickname %s has been dropped." +msgstr "Nickname %s ha estat expulsat." + +#: include/language.h:97 +#, fuzzy, c-format +msgid "Nickname %s is already registered!" +msgstr "El canal %s ja esta enregistrat!" + +#: include/language.h:96 +#, fuzzy, c-format +msgid "Nickname %s may not be registered." +msgstr "El canal %s no pot ser enregistrat." + +#: modules/commands/ns_register.cpp:226 +#, fuzzy, c-format +msgid "Nickname %s registered under your user@host-mask: %s" +msgstr "El nickname %s ja esta registrat sota el teu compte: %s" + +#: modules/commands/ns_register.cpp:228 +#, fuzzy, c-format +msgid "Nickname %s registered." +msgstr "Nickname %s registered." + +#: modules/commands/cs_set.cpp:1307 +#, fuzzy +msgid "No auto-op" +msgstr "Auto-op" + +#: modules/commands/bs_assign.cpp:252 +msgid "No bot" +msgstr "Sense bot" + +#: modules/commands/cs_set.cpp:1303 modules/commands/ns_set.cpp:1317 +#, fuzzy +msgid "No expire" +msgstr "no expira" + +#: modules/commands/help.cpp:184 +#, c-format +msgid "No help available for %s." +msgstr "No existeix ajuda per %s." + +#: modules/commands/os_modinfo.cpp:61 +#, fuzzy, c-format +msgid "No information about module %s is available." +msgstr "No information about module %s is available" + +#: modules/commands/cs_enforce.cpp:177 +#, fuzzy, c-format +msgid "No limit is set on %s." +msgstr "Límite de memos per a %s establert a %d." + +#: modules/commands/os_news.cpp:37 +msgid "No logon news items to delete!" +msgstr "No hi ha notícies d'entrada per a esborrar!" + +#: modules/commands/os_logsearch.cpp:133 +#, fuzzy, c-format +msgid "No matches for %s found." +msgstr "No Emails listed for %s." + +#: modules/commands/cs_xop.cpp:294 +#, fuzzy, c-format +msgid "No matching entries on %s %s list." +msgstr "No existeixen instàncies coincidents a la llista AOP de %s." + +#: modules/commands/cs_access.cpp:269 modules/commands/cs_access.cpp:433 +#: modules/commands/cs_flags.cpp:335 modules/commands/cs_xop.cpp:428 +#, c-format +msgid "No matching entries on %s access list." +msgstr "No hi ha instàncies que concordin a la llista d'accés de %s ." + +#: modules/commands/cs_akick.cpp:224 modules/commands/cs_akick.cpp:368 +#, c-format +msgid "No matching entries on %s autokick list." +msgstr "" +"No existeixen instàncies que concordin a la llista de kicks automàtics en el " +"canal %s." + +#: modules/commands/bs_badwords.cpp:166 modules/commands/bs_badwords.cpp:246 +#, c-format +msgid "No matching entries on %s bad words list." +msgstr "" +"No existeixen paraules que concordin a la llista de paraules malsonants de " +"%s." + +#: modules/commands/os_session.cpp:145 modules/commands/os_session.cpp:490 +msgid "No matching entries on session-limit exception list." +msgstr "" +"No existeixen instàncies similars a la llista d'excepcions al límit de " +"sessions." + +#: modules/commands/os_sxline.cpp:28 modules/commands/os_sxline.cpp:177 +#, fuzzy, c-format +msgid "No matching entries on the %s list." +msgstr "No existeixen instàncies coincidents a la llista AOP de %s." + +#: modules/commands/os_akill.cpp:29 modules/commands/os_akill.cpp:320 +msgid "No matching entries on the AKILL list." +msgstr "No existeixen instàncies similars a la llista de AKILLs." + +#: modules/commands/ms_cancel.cpp:77 +msgid "No memo was cancelable." +msgstr "Cap memo pot ser cancelat." + +#: modules/commands/ms_read.cpp:65 +msgid "No memos to display." +msgstr "" + +#: modules/commands/os_modinfo.cpp:187 +#, fuzzy +msgid "No modules currently loaded matching that criteria." +msgstr "No modules currently loaded" + +#: modules/commands/ns_recover.cpp:55 +msgid "No one is using your nick, and services are not holding it." +msgstr "" + +#: modules/commands/os_login.cpp:30 modules/commands/os_login.cpp:77 +msgid "No oper block for your nick." +msgstr "" + +#: modules/commands/os_news.cpp:47 +msgid "No oper news items to delete!" +msgstr "No hi ha notícies de oper per esborrar!" + +#: modules/commands/os_news.cpp:57 +msgid "No random news items to delete!" +msgstr "No hi ha notícies a l'atzar per esborrar!" + +#: modules/commands/hs_list.cpp:111 +msgid "No records to display." +msgstr "" + +#: modules/commands/ns_getemail.cpp:47 +#, fuzzy, c-format +msgid "No registrations matching %s were found." +msgstr "* No new nick registrations" + +#: modules/commands/hs_request.cpp:220 modules/commands/hs_request.cpp:276 +#, c-format +msgid "No request for nick %s found." +msgstr "" + +#: src/access.cpp:55 +msgid "No signed kick when SIGNKICK LEVEL is used" +msgstr "" + +#: modules/extra/stats/cs_fantasy_top.cpp:159 +#: modules/extra/stats/cs_fantasy_stats.cpp:156 +#, fuzzy, c-format +msgid "No stats for %s." +msgstr "Lllista d'accés per %s:" + +#: modules/commands/os_info.cpp:201 +#, fuzzy, c-format +msgid "No such info \"%s\" on %s." +msgstr "%s has been invited to %s." + +#: modules/commands/cs_ban.cpp:219 modules/commands/cs_kick.cpp:118 +#, fuzzy, c-format +msgid "No users on %s match %s." +msgstr "Changed usermodes of %s." + +#: modules/commands/bs_assign.cpp:188 +#, fuzzy, c-format +msgid "No-bot mode is now off on channel %s." +msgstr "Mode no bot ara activat en el canal %s." + +#: modules/commands/bs_assign.cpp:181 +#, fuzzy, c-format +msgid "No-bot mode is now on on channel %s." +msgstr "Mode no bot ara activat en el canal %s." + +#: modules/commands/os_mode.cpp:64 +#, c-format +msgid "Non-status modes cleared on %s." +msgstr "" + +#: modules/commands/os_dns.cpp:226 modules/commands/bs_info.cpp:58 +msgid "None" +msgstr "Cap" + +#: modules/commands/cs_set.cpp:1029 +#, c-format +msgid "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." +msgstr "" + +#: modules/commands/cs_mode.cpp:380 modules/commands/cs_mode.cpp:437 +msgid "Nothing to do." +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:201 modules/commands/ms_list.cpp:64 +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_log.cpp:127 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +#: modules/commands/ns_ajoin.cpp:100 +msgid "Number" +msgstr "" + +#: modules/commands/os_news.cpp:41 +msgid "OPERNEWS {ADD|DEL|LIST} [text|num]" +msgstr "OPERNEWS {ADD|DEL|LIST} [texto|numero]" + +#: modules/commands/ns_info.cpp:68 modules/commands/ns_info.cpp:72 +#, fuzzy +msgid "Online from" +msgstr " Esta en linea desde: %s" + +#: modules/commands/os_oper.cpp:138 +#, c-format +msgid "" +"Oper %s is configured in the configuration file(s) and can not be removed by " +"this command." +msgstr "" + +#: modules/commands/os_info.cpp:268 +msgid "Oper Info" +msgstr "" + +#: modules/commands/os_info.cpp:182 modules/commands/os_info.cpp:221 +#, fuzzy, c-format +msgid "Oper info list for %s is empty." +msgstr "Access list for %s is empty." + +#: modules/commands/os_news.cpp:46 +#, c-format +msgid "Oper news item #%d deleted." +msgstr "Noticia de oper #%d esborrada." + +#: modules/commands/os_news.cpp:45 +#, fuzzy, c-format +msgid "Oper news item #%s not found!" +msgstr "Noticia de oper #%d no trobada!" + +#: modules/commands/os_news.cpp:42 +msgid "Oper news items:" +msgstr "notícies de oper:" + +#: modules/commands/os_oper.cpp:148 +#, c-format +msgid "Oper privileges removed from %s (%s)." +msgstr "" + +#: modules/commands/os_oper.cpp:101 modules/commands/os_oper.cpp:189 +#, fuzzy, c-format +msgid "Oper type %s has not been configured." +msgstr "Nickname %s ha estat expulsat." + +#: modules/commands/os_oline.cpp:37 +#, c-format +msgid "Operflags %s have been added for %s." +msgstr "An O:Line with the flags %s has been added for %s." + +#: modules/commands/os_oline.cpp:43 +#, fuzzy, c-format +msgid "Operflags %s have been removed from %s." +msgstr "An O:Line with the flags %s has been added for %s." + +#: modules/commands/os_oper.cpp:193 +#, c-format +msgid "Opertype %s has no allowed commands." +msgstr "" + +#: modules/commands/os_oper.cpp:215 +#, c-format +msgid "Opertype %s has no allowed privileges." +msgstr "" + +#: modules/commands/os_oper.cpp:237 +#, c-format +msgid "Opertype %s receives modes %s once identified." +msgstr "" + +#: modules/commands/bs_kick.cpp:1219 +msgid "Ops protection" +msgstr "Protecció de Ops" + +#: src/misc.cpp:258 modules/commands/bs_info.cpp:58 +#, fuzzy +msgid "Options" +msgstr " Opcions : %s" + +#: modules/commands/os_dns.cpp:668 +#, fuzzy +msgid "POOL server.name" +msgstr "NOOP {SET|REVOKE} servidor" + +#: modules/commands/cs_mode.cpp:449 +msgid "Param" +msgstr "" + +#: modules/commands/ns_identify.cpp:38 +msgid "Password accepted - you are now recognized." +msgstr "Clau aceptada - Has estat reconegut." + +#: modules/commands/os_login.cpp:44 +#, fuzzy +msgid "Password accepted." +msgstr "Clau incorrecta." + +#: include/language.h:85 +msgid "Password authentication required for that command." +msgstr "" + +#: modules/commands/ns_set.cpp:152 modules/commands/ns_set.cpp:218 +#, fuzzy, c-format +msgid "Password for %s changed to %s." +msgstr "Sucessor de %s cambiat a %s." + +#: modules/commands/ns_set.cpp:154 modules/commands/ns_set.cpp:220 +#, fuzzy, c-format +msgid "Password for %s changed." +msgstr "La clau de %s ha estat enviada." + +#: modules/commands/ns_getpass.cpp:38 +#, c-format +msgid "Password for %s is %s." +msgstr "La clau per %s es %s." + +#: include/language.h:71 +#, fuzzy +msgid "Password incorrect." +msgstr "Clau incorrecta." + +#: modules/commands/ns_resetpass.cpp:39 +#, c-format +msgid "Password reset email for %s has been sent." +msgstr "Password reset email for %s has been sent." + +#: modules/commands/cs_set.cpp:1289 +msgid "Peace" +msgstr "Pau" + +#: modules/commands/cs_set.cpp:440 +#, fuzzy, c-format +msgid "Peace option for %s is now off." +msgstr "Peace option for %s is now ON." + +#: modules/commands/cs_set.cpp:434 +#, fuzzy, c-format +msgid "Peace option for %s is now on." +msgstr "Peace option for %s is now ON." + +#: modules/commands/cs_set.cpp:1301 +#, fuzzy +msgid "Persistent" +msgstr "Persistant" + +#: include/language.h:126 +msgid "Please contact an Operator to get a vHost assigned to this nick." +msgstr "" + +#: include/language.h:73 +msgid "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." +msgstr "" + +#: modules/commands/os_jupe.cpp:30 +#, fuzzy +msgid "Please use a valid server name when juping." +msgstr "Please use a valid server name when juping" + +#: include/language.h:104 +msgid "Please use the symbol of # when attempting to register." +msgstr "" + +#: src/mail.cpp:78 +#, c-format +msgid "Please wait %d seconds and retry." +msgstr "Per favor espera %d segons i intenta un altre cop." + +#: modules/commands/hs_request.cpp:158 +#, fuzzy, c-format +msgid "Please wait %d seconds before requesting a new vHost." +msgstr "" +"Per favor espera %d segons abans d'utilizar la comanda SEND un altre cop." + +#: modules/commands/ms_rsend.cpp:58 modules/commands/ms_send.cpp:57 +#, fuzzy, c-format +msgid "Please wait %d seconds before using the %s command again." +msgstr "" +"Per favor espera %d segons abans d'utilizar la comanda SEND un altre cop." + +#: modules/commands/ns_group.cpp:149 +#, c-format +msgid "Please wait %d seconds before using the GROUP command again." +msgstr "" +"Per favor espera %d segons abans d'utilitzar la comanda GROUP novament." + +#: modules/commands/ns_register.cpp:198 +#, c-format +msgid "Please wait %d seconds before using the REGISTER command again." +msgstr "" +"Per favor espera %d segons abans d'utilitzar la comanda REGISTER novament." + +#: modules/commands/os_dns.cpp:628 +#, c-format +msgid "Pooled %s." +msgstr "" + +#: modules/commands/os_dns.cpp:237 +msgid "Pooled/Active" +msgstr "" + +#: modules/commands/os_dns.cpp:239 +msgid "Pooled/Not Active" +msgstr "" + +#: modules/commands/bs_set.cpp:161 +msgid "Prevent a bot from being assigned by non IRC operators" +msgstr "" + +#: modules/commands/bs_assign.cpp:153 +#, fuzzy +msgid "Prevent a bot from being assigned to a channel" +msgstr "" +" SUSPEND Prevent a channel from being used preserving\n" +" channel data and settings" + +#: modules/commands/cs_suspend.cpp:58 +#, fuzzy +msgid "Prevent a channel from being used preserving channel data and settings" +msgstr "" +" SUSPEND Prevent a channel from being used preserving\n" +" channel data and settings" + +#: modules/commands/cs_set.cpp:1043 +#, fuzzy +msgid "Prevent the channel from expiring" +msgstr " NOEXPIRE Prevent the channel from expiring" + +#: modules/commands/ns_list.cpp:186 +#, fuzzy +msgid "Prevent the nickname from appearing in the LIST command" +msgstr "" +" PRIVATE Prevent the nickname from appearing in a\n" +" /msg %s LIST" + +#: modules/commands/ns_set.cpp:1104 +#, fuzzy +msgid "Prevent the nickname from expiring" +msgstr " NOEXPIRE Prevent the nickname from expiring" + +#: src/access.cpp:46 +msgid "Prevents users being kicked by Services" +msgstr "" + +#: modules/commands/ns_list.cpp:297 modules/commands/cs_list.cpp:262 +#: modules/commands/bs_info.cpp:58 +msgid "Private" +msgstr "Privat" + +#: modules/commands/bs_set.cpp:190 +#, fuzzy, c-format +msgid "Private mode of bot %s is now off." +msgstr "Mode privado del bot %s esta ara activat." + +#: modules/commands/bs_set.cpp:185 +#, fuzzy, c-format +msgid "Private mode of bot %s is now on." +msgstr "Mode privado del bot %s esta ara activat." + +#: modules/commands/cs_list.cpp:220 +#, fuzzy, c-format +msgid "Private option for %s is now off." +msgstr "Private option for %s is now ON." + +#: modules/commands/cs_list.cpp:214 +#, fuzzy, c-format +msgid "Private option for %s is now on." +msgstr "Private option for %s is now ON." + +#: modules/commands/ns_list.cpp:221 +#, fuzzy, c-format +msgid "Private option is now off for %s." +msgstr "Private option is now ON for %s." + +#: modules/commands/ns_list.cpp:215 +#, fuzzy, c-format +msgid "Private option is now on for %s." +msgstr "Private option is now ON for %s." + +#: modules/commands/cs_flags.cpp:281 +#, c-format +msgid "Privilege %s added to %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/cs_flags.cpp:283 +#, c-format +msgid "Privilege %s removed from %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/ns_set.cpp:1309 +msgid "Protection" +msgstr "Protecció" + +#: modules/commands/ns_set.cpp:721 +#, fuzzy, c-format +msgid "Protection is now off for %s." +msgstr "Protection is now ON for %s." + +#: modules/commands/ns_set.cpp:700 +#, fuzzy, c-format +msgid "Protection is now on for %s, with a reduced delay." +msgstr "Protection is now ON for %s, with a reduced delay." + +#: modules/commands/ns_set.cpp:710 +#, fuzzy, c-format +msgid "Protection is now on for %s, with no delay." +msgstr "Protection is now ON for %s, with no delay." + +#: modules/commands/ns_set.cpp:692 +#, fuzzy, c-format +msgid "Protection is now on for %s." +msgstr "Protection is now ON for %s." + +#: modules/commands/os_chankill.cpp:100 +#, fuzzy +msgid "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." +msgstr "" +"Syntax: CHANKILL [+expiry] channel reason\n" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire and complete real ident@host for every nick,\n" +"then enforces the AKILL. " + +#: modules/commands/ns_set.cpp:1307 +#, fuzzy +msgid "Quick protection" +msgstr "Protecció de Voices" + +#: modules/commands/os_news.cpp:51 +msgid "RANDOMNEWS {ADD|DEL|LIST} [text|num]" +msgstr "RANDOMNEWS {ADD|DEL|LIST} [text|numero]" + +#: modules/commands/cs_enforce.cpp:99 +msgid "REGONLY enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:68 +msgid "RESTRICTED enforced by " +msgstr "" + +#: modules/commands/os_noop.cpp:21 +#, fuzzy +msgid "REVOKE server" +msgstr "NOOP {SET|REVOKE} servidor" + +#: modules/commands/os_news.cpp:56 +#, c-format +msgid "Random news item #%d deleted." +msgstr "Notícia a l'atzar #%d esborrada." + +#: modules/commands/os_news.cpp:55 +#, fuzzy, c-format +msgid "Random news item #%s not found!" +msgstr "Noticia a l'atzar #%d no trobada!" + +#: modules/commands/os_news.cpp:52 +msgid "Random news items:" +msgstr "Notícies al Azar:" + +#: modules/commands/ms_read.cpp:112 +#, fuzzy +msgid "Read a memo or memos" +msgstr " READ Llegeix un o més memos" + +#: modules/commands/bs_info.cpp:56 +#, fuzzy +msgid "Real name" +msgstr " Nom real : %s" + +#: modules/commands/os_list.cpp:153 +#, fuzzy +msgid "Realname" +msgstr " Nom real : %s" + +#: modules/commands/os_ignore.cpp:266 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:204 modules/commands/os_forbid.cpp:358 +#: modules/commands/cs_akick.cpp:392 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:361 +msgid "Reason" +msgstr "" + +#: src/xline.cpp:386 +#, fuzzy, c-format +msgid "Reason for %s updated." +msgstr "Sucessor de %s desabilitat." + +#: modules/commands/ns_recover.cpp:214 +msgid "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." +msgstr "" + +#: modules/commands/cs_access.cpp:741 +#, fuzzy +msgid "Redefine the meanings of access levels" +msgstr " LEVELS Redefine el significat de nivells d'accés" + +#: modules/commands/ns_recover.cpp:149 +#, fuzzy +msgid "Regains control of your nick" +msgstr " RELEASE Repren possesió del teu nick després de RECOVER" + +#: modules/commands/os_sxline.cpp:330 modules/commands/os_sxline.cpp:545 +#: modules/commands/os_akill.cpp:129 +#, fuzzy +msgid "Regex is disabled." +msgstr "%s is enable" + +#: modules/commands/os_sxline.cpp:459 modules/commands/os_sxline.cpp:694 +#: modules/commands/os_akill.cpp:444 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." +msgstr "" + +#: modules/commands/os_ignore.cpp:386 modules/commands/os_forbid.cpp:428 +#: modules/commands/ns_list.cpp:172 modules/commands/cs_list.cpp:167 +#: modules/commands/os_list.cpp:119 modules/commands/os_list.cpp:255 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." +msgstr "" + +#: modules/commands/cs_register.cpp:19 +#, fuzzy +msgid "Register a channel" +msgstr " REGISTER Registra un nickname" + +#: modules/commands/ns_register.cpp:120 +#, fuzzy +msgid "Register a nickname" +msgstr " REGISTER Registra un nickname" + +#: modules/commands/ns_info.cpp:89 modules/commands/cs_info.cpp:55 +#, fuzzy +msgid "Registered" +msgstr " Temps registrat: %s" + +#: modules/commands/os_stats.cpp:184 +#, c-format +msgid "Registered channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:190 +#, c-format +msgid "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:187 +#, c-format +msgid "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/cs_enforce.cpp:105 +#, c-format +msgid "Registered only enforced on %s." +msgstr "" + +#: modules/commands/cs_register.cpp:86 +#, fuzzy, c-format +msgid "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." +msgstr "" +"Sintaxis: REGISTER canal descripció\n" +"\n" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which must be included, is a\n" +"general description of the channel's purpose.\n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel.\n" +"See the ACCESS command (/msg %s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname. If you haven't,\n" +"/msg %s HELP for information on how to do so." + +#: modules/commands/ns_register.cpp:269 +#, fuzzy, c-format +msgid "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." +msgstr "" +"Sintaxis: REGISTER clau [email]\n" +"\n" +"Registra el teu nickname a la base de dades de %s. Un\n" +"cop registrat, pots utilitzar les comandes SET i ACCESS\n" +"per configurar els parametres del teu nick al teu gust.\n" +"Assegura't de recordar la clau que vas fer servir per\n" +"registrar-te - la necessitaras per fer canvis en el teu nick\n" +"(Tingues en compte que les majuscules importen! AUJAC,\n" +"Aujac, i aujac són totes claus diferents!)\n" +"\n" +"Guies per escollir claus:\n" +"\n" +"Las claus no han de ser fàcils d'endevinar. Per exemple,\n" +"utilitzar el teu nom real com clau es una mala idea. Utilitzar\n" +"el teu nickname com a clau es una idea pitjor :( i,\n" +"de fet, %s no ho permetria. A mes, claus curtes\n" +"son vulnerables a ser encertades, aixi que hauries d'escollir una\n" +"clau de com a mínim 5 caràcters.\n" +"Per últim, el caràcter d'espai no pot ser utilitzat.\n" +"\n" +"El parametre email es opcional i establira l'email pel\n" +"teu nick inmediatament. Com sigui, pot ser que sigui demanat\n" +"en certes xarxes.\n" +"La teva privacitat es respectada; aquest e-mail no sera donat a\n" +"terceres persones.\n" +"\n" +"Aquesta comanda crea un nou grup pel teu nickname\n" +"que et permetra registrar altres nicks després compartint\n" +"la mateixa configuració, memos i privilegis. Per més\n" +"informació sobre aquesta característica, escriu /msg %s\n" +"HELP GROUP." + +#: modules/commands/ns_register.cpp:145 +#, fuzzy +msgid "Registration is currently disabled." +msgstr "Ho sento, el registre de canals esta temporalment inhabilitat." + +#: modules/commands/cs_set.cpp:400 +#, fuzzy +msgid "Regulate the use of critical commands" +msgstr " PEACE Regula l'ús de comandes critiques" + +#: modules/commands/hs_request.cpp:283 +#, fuzzy +msgid "Reject the requested vHost for the given nick." +msgstr " STATUS Returns the owner status of the given nickname" + +#: modules/commands/hs_request.cpp:240 +#, fuzzy +msgid "Reject the requested vHost of a user" +msgstr " DEL Delete the vhost of another user" + +#: modules/commands/cs_suspend.cpp:151 +#, fuzzy +msgid "Releases a suspended channel" +msgstr " UNSUSPEND Releases a suspended channel" + +#: modules/commands/cs_suspend.cpp:191 +#, fuzzy +msgid "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." +msgstr "" +"Syntax: UNSUSPEND channel\n" +"\n" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." + +#: modules/commands/os_module.cpp:56 +#, fuzzy +msgid "Reload a module" +msgstr " MODLOAD Load a module" + +#: modules/commands/os_reload.cpp:19 +#, fuzzy +msgid "Reload services' configuration file" +msgstr " RELOAD Recarrega la configuració dels serveis" + +#: modules/commands/ns_group.cpp:236 +#, fuzzy +msgid "Remove a nick from a group" +msgstr " UNGROUP Remove a nick from a group" + +#: modules/commands/cs_unban.cpp:19 +#, fuzzy +msgid "Remove all bans preventing a user from entering a channel" +msgstr "" +" UNBAN Remove all bans preventing a user from entering a channel" + +#: modules/commands/os_noop.cpp:19 +#, fuzzy +msgid "Remove all operators from a server remotely" +msgstr "" +" NOOP Temporalment elimina totes les linees O:\n" +" d'un servidor remotamente" + +#: modules/commands/os_dns.cpp:543 +#, fuzzy, c-format +msgid "Removed IP %s from %s." +msgstr " Mode de lock: %s" + +#: modules/commands/os_dns.cpp:460 +#, c-format +msgid "Removed server %s from zone %s." +msgstr "" + +#: modules/commands/os_dns.cpp:483 +#, c-format +msgid "Removed server %s." +msgstr "" + +#: modules/commands/cs_mode.cpp:909 +#, c-format +msgid "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." +msgstr "" + +#: modules/commands/cs_mode.cpp:890 +#, fuzzy, c-format +msgid "Removes %s status from you or the specified nick on a channel" +msgstr " OP Gives Op status to a selected nick on a channel" + +#: modules/commands/cs_updown.cpp:146 +#, fuzzy +msgid "Removes a selected nicks status from a channel" +msgstr " KICK Kicks a selected nick from a channel" + +#: modules/commands/cs_updown.cpp:223 +msgid "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." +msgstr "" + +#: src/xline.cpp:412 +#, c-format +msgid "Removing %s because %s covers it." +msgstr "" + +#: modules/commands/bs_kick.cpp:1171 modules/commands/bs_kick.cpp:1173 +#: modules/commands/bs_kick.cpp:1176 +#, fuzzy +msgid "Repeat kicker" +msgstr " Kicker per repetició : %s" + +#: modules/commands/hs_request.cpp:78 +#, fuzzy +msgid "Request a vHost for your nick" +msgstr "There's no email address set for your nick." + +#: modules/commands/hs_request.cpp:179 +msgid "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." +msgstr "" + +#: modules/commands/ns_register.cpp:312 +#, fuzzy +msgid "Resend registration confirmation email" +msgstr " RELOAD Recarrega la configuració dels serveis" + +#: modules/commands/cs_set.cpp:621 +#, fuzzy +msgid "Restrict access to the channel" +msgstr " RESTRICTED Restringeix l'accés al canal" + +#: modules/commands/cs_set.cpp:1291 +#, fuzzy +msgid "Restricted access" +msgstr "accés restringit" + +#: modules/commands/cs_set.cpp:661 +#, fuzzy, c-format +msgid "Restricted access option for %s is now off." +msgstr "Restricted access option for %s is now ON." + +#: modules/commands/cs_set.cpp:655 +#, fuzzy, c-format +msgid "Restricted access option for %s is now on." +msgstr "Restricted access option for %s is now ON." + +#: modules/commands/cs_enforce.cpp:73 +#, fuzzy, c-format +msgid "Restricted enforced on %s." +msgstr "accés restringit" + +#: modules/commands/cs_set.cpp:335 +#, fuzzy +msgid "Retain modes when channel is not in use" +msgstr "" +" KEEPTOPIC Rete el topic quant el canal no\n" +" esta en uso" + +#: modules/commands/cs_topic.cpp:20 +#, fuzzy +msgid "Retain topic when channel is not in use" +msgstr "" +" KEEPTOPIC Rete el topic quant el canal no\n" +" esta en uso" + +#: modules/commands/ns_getpass.cpp:19 +#, fuzzy +msgid "Retrieve the password for a nickname" +msgstr "" +" GETPASS Recupera la clau per un nickname\n" +" (sols si encriptació esta deshabilitada)" + +#: modules/commands/hs_request.cpp:296 +msgid "Retrieves the vhost requests" +msgstr "" + +#: modules/commands/cs_getkey.cpp:19 +#, fuzzy +msgid "Returns the key of the given channel" +msgstr " GETKEY Returns the key of the given channel" + +#: modules/commands/cs_getkey.cpp:57 +#, fuzzy +msgid "Returns the key of the given channel." +msgstr " GETKEY Returns the key of the given channel" + +#: modules/commands/ns_getemail.cpp:58 +#, fuzzy +msgid "Returns the matching accounts that used given email." +msgstr " GETKEY Returns the key of the given channel" + +#: modules/commands/ns_status.cpp:19 +#, fuzzy +msgid "Returns the owner status of the given nickname" +msgstr " STATUS Returns the owner status of the given nickname" + +#: modules/commands/ns_getpass.cpp:50 +#, fuzzy +msgid "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." +msgstr "" +"Sintaxis: GETPASS nickname\n" +"\n" +"Retorna la clau pel nickname donat. Tingues en compte\n" +"que quant aquesta comanda es utilitzada, un missatge inclouent\n" +"la persona que va executar la comanda i el nickname en el qual\n" +"va ser utilitzat sera establert i enviat com WALLOPS/GLOBOPS.\n" +"\n" +"Limitat a administradors de serveis.\n" +"\n" +"Aquesta comanda no esta disponible si encriptació esta habilitada." + +#: modules/commands/ns_status.cpp:55 +#, fuzzy +msgid "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." +msgstr "" +"Sintaxis: STATUS nickname...\n" +"\n" +"Retorna informació sobre si l'usuari que utilitza el nick especificat\n" +"ha estat reconegut com el propietari del nickname.\n" +"La resposta te el següent format:\n" +"\n" +" nickname codi-del-status account\n" +"\n" +"where nickname is the nickname sent with the command,\n" +"codi-del-status is one of the following, and account\n" +"is the account they are logged in as.\n" +"\n" +" 0 - Usuari no esta en linea o el nick no esta registrat.\n" +" 1 - Usuari no reconegut com el propietari del nick.\n" +" 2 - Usuari reconegut sols mitjançant la llista d'accés.\n" +" 3 - Usuari reconegut mitjançant autentificació per clau.\n" +"\n" +"Fins 16 nicknames poden ser enviats amb cada comanda. El\n" +"reste seran ignorats. If no nickname is given, your status\n" +"will be returned." + +#: modules/commands/bs_kick.cpp:1181 modules/commands/bs_kick.cpp:1183 +#: modules/commands/bs_kick.cpp:1186 +#, fuzzy +msgid "Reverses kicker" +msgstr " Kicker per inversos : %s" + +#: modules/commands/ns_logout.cpp:21 +#, fuzzy +msgid "Reverses the effect of the IDENTIFY command" +msgstr " LOGOUT Reverses the effect of the IDENTIFY command" + +#: modules/commands/os_noop.cpp:20 +#, fuzzy +msgid "SET server" +msgstr "NOOP {SET|REVOKE} servidor" + +#: modules/commands/os_dns.cpp:667 +msgid "SET server.name option value" +msgstr "" + +#: modules/commands/ns_cert.cpp:378 +#, fuzzy, c-format +msgid "SSL certificate fingerprint accepted, you are now identified to %s." +msgstr "Clau aceptada - Has estat reconegut." + +#: modules/commands/ns_cert.cpp:398 +#, fuzzy +msgid "SSL certificate fingerprint accepted, you are now identified." +msgstr "Clau aceptada - Has estat reconegut." + +#: modules/commands/cs_enforce.cpp:137 +#, c-format +msgid "SSL only enforced on %s." +msgstr "" + +#: modules/commands/cs_enforce.cpp:131 +msgid "SSLONLY enforced by " +msgstr "" + +#: modules/commands/os_shutdown.cpp:47 +#, fuzzy +msgid "Save databases and restart Services" +msgstr "" +" RESTART Guarda la base de dades dels serveis i\n" +" reinicia els serveis" + +#: modules/commands/os_logsearch.cpp:32 +msgid "Searches logs for a matching pattern" +msgstr "" + +#: modules/commands/cs_set.cpp:1295 +#, fuzzy +msgid "Secure founder" +msgstr "Fundador Segur" + +#: modules/commands/cs_set.cpp:786 +#, fuzzy, c-format +msgid "Secure founder option for %s is now off." +msgstr "Secure founder option for %s is now ON." + +#: modules/commands/cs_set.cpp:780 +#, fuzzy, c-format +msgid "Secure founder option for %s is now on." +msgstr "Secure founder option for %s is now ON." + +#: modules/commands/cs_set.cpp:1297 +#, fuzzy +msgid "Secure ops" +msgstr "Ops Segurs" + +#: modules/commands/cs_set.cpp:850 +#, fuzzy, c-format +msgid "Secure ops option for %s is now off." +msgstr "Secure ops option for %s is now ON." + +#: modules/commands/cs_set.cpp:844 +#, fuzzy, c-format +msgid "Secure ops option for %s is now on." +msgstr "Secure ops option for %s is now ON." + +#: modules/commands/cs_set.cpp:723 +#, fuzzy, c-format +msgid "Secure option for %s is now off." +msgstr "Secure option for %s is now ON." + +#: modules/commands/cs_set.cpp:717 +#, fuzzy, c-format +msgid "Secure option for %s is now on." +msgstr "Secure option for %s is now ON." + +#: modules/commands/ns_set.cpp:1044 +#, fuzzy, c-format +msgid "Secure option is now off for %s." +msgstr "Secure option is now ON for %s." + +#: modules/commands/ns_set.cpp:1038 +#, fuzzy, c-format +msgid "Secure option is now on for %s." +msgstr "Secure option is now ON for %s." + +#: modules/commands/cs_enforce.cpp:42 +#, fuzzy, c-format +msgid "Secureops enforced on %s." +msgstr "Secure option is now ON for %s." + +#: modules/commands/cs_set.cpp:1293 modules/commands/ns_set.cpp:1311 +msgid "Security" +msgstr "Segur" + +#: modules/commands/cs_xop.cpp:570 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the access list." +msgstr "" +"Escriu /msg %s HELP opció per més informació\n" +"sobre una opció en particular." + +#: modules/commands/cs_xop.cpp:573 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the flags system." +msgstr "" +"Escriu /msg %s HELP opció per més informació\n" +"sobre una opció en particular." + +#: modules/commands/ms_send.cpp:24 +#, fuzzy +msgid "Send a memo to a nick or channel" +msgstr " SEND Envia un memo a un nick o canal" + +#: modules/commands/ms_staff.cpp:24 +#, fuzzy +msgid "Send a memo to all opers/admins" +msgstr " STAFF Send a memo to all opers/admins" + +#: modules/commands/ms_sendall.cpp:24 +#, fuzzy +msgid "Send a memo to all registered users" +msgstr " SENDALL Send a memo to all registered users" + +#: modules/commands/gl_global.cpp:21 +#, fuzzy +msgid "Send a message to all users" +msgstr " GLOBAL Envia un missatge a totss els usuaris" + +#: modules/commands/ms_list.cpp:64 +#, fuzzy +msgid "Sender" +msgstr "Fundador Segur" + +#: modules/commands/ms_rsend.cpp:24 +#, fuzzy +msgid "Sends a memo and requests a read receipt" +msgstr " RSEND Sends a memo and requests a read receipt" + +#: modules/commands/ns_resetpass.cpp:50 +#, fuzzy +msgid "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." +msgstr "" +"Syntax: RESETPASS nickname\n" +"\n" +"Sends a code key to the nickname with instructions on how to\n" +"reset their password." + +#: modules/commands/ms_sendall.cpp:52 +#, fuzzy +msgid "Sends all registered users a memo containing memo-text." +msgstr "" +"Syntax: SENDALL memo-text\n" +"Sends all registered users a memo containing memo-text." + +#: modules/commands/ms_staff.cpp:48 +#, fuzzy +msgid "Sends all services staff a memo containing memo-text." +msgstr "" +"Syntax: STAFF memo-text\n" +"Sends all services staff a memo containing memo-text." + +#: modules/commands/ms_send.cpp:66 +#, fuzzy +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." +msgstr "" +"Sintàxi: SEND {nick | canal} text-del-memo\n" +"\n" +"Envia un memo al nick o canal donat, que conté\n" +"text-del-memo. A l'enviar a un nickname, aquest\n" +"rebrà noticia de que ell/ella té un nou memo. El nick\n" +"o canal receptors han d'estar registrats." + +#: modules/commands/ms_rsend.cpp:80 +#, fuzzy +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." +msgstr "" +"Syntax: RSEND {nick | channel} memo-text\n" +"\n" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recepient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." + +#: modules/commands/ms_read.cpp:199 +#, fuzzy +msgid "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Sintàxi: READ [canal] {nombre | llista | LAST | NEW}\n" +"\n" +"T'envia el text dels memos especificats. Si LAST és\n" +"donat, t'envia l'ultim memo rebut. si NEW és donat, t'\n" +"envia tots els teus memos nous. D'altra forma, t'envia el\n" +"memo nombre nombre. També pots donar una llista de\n" +"nombres, com en el exemple:\n" +"\n" +" READ 2-5,7-9\n" +" mostra els memos enumerats 2 a 5 i 7 a 9." + +#: modules/commands/os_dns.cpp:218 +#, fuzzy +msgid "Server" +msgstr "NOOP {SET|REVOKE} servidor" + +#: modules/commands/os_dns.cpp:375 +#, fuzzy, c-format +msgid "Server %s added to zone %s." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:345 +#, fuzzy, c-format +msgid "Server %s already exists." +msgstr "El bot %s ja existeix." + +#: modules/commands/os_noop.cpp:31 modules/commands/os_dns.cpp:430 +#: modules/commands/os_dns.cpp:493 modules/commands/os_dns.cpp:532 +#: modules/commands/os_dns.cpp:571 modules/commands/os_dns.cpp:604 +#: modules/commands/os_dns.cpp:639 +#, fuzzy, c-format +msgid "Server %s does not exist." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:619 +#, fuzzy, c-format +msgid "Server %s has no configured IPs." +msgstr "Nickname %s ha estat expulsat." + +#: modules/commands/os_dns.cpp:357 +#, fuzzy, c-format +msgid "Server %s is already in zone %s." +msgstr "You are already in %s! " + +#: modules/commands/os_dns.cpp:614 +#, fuzzy, c-format +msgid "Server %s is already pooled." +msgstr "Module %s is already loaded." + +#: modules/commands/os_dns.cpp:609 +#, fuzzy, c-format +msgid "Server %s is not currently linked." +msgstr "%s Esta actualment online." + +#: modules/commands/os_dns.cpp:443 +#, fuzzy, c-format +msgid "Server %s is not in zone %s." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:384 +#, fuzzy, c-format +msgid "Server %s is not linked to the network." +msgstr "Ja no hi ha un bot assignat a %s." + +#: modules/commands/os_dns.cpp:644 +#, fuzzy, c-format +msgid "Server %s is not pooled." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:465 +#, c-format +msgid "Server %s must be quit before it can be deleted." +msgstr "" + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Servers" +msgstr "NOOP {SET|REVOKE} servidor" + +#: modules/commands/os_stats.cpp:155 +#, c-format +msgid "Servers found: %d" +msgstr "Servers found: %d" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Service" +msgstr "Servers found: %d" + +#: modules/commands/ns_recover.cpp:51 +#, fuzzy, c-format +msgid "Service's hold on %s has been released." +msgstr "El teu nick ha estat alliberat pels serveis." + +#: data/nickserv.example.conf:236 data/chanserv.example.conf:827 +#, fuzzy +msgid "Services Operator commands" +msgstr "%s is a services operator of type %s." + +#: modules/commands/os_defcon.cpp:443 modules/commands/os_defcon.cpp:454 +#: modules/commands/os_defcon.cpp:462 modules/commands/os_defcon.cpp:470 +#: modules/commands/os_defcon.cpp:478 +#, fuzzy +msgid "Services are in DefCon mode, please try again later." +msgstr "This service is temporarly disabled, please try again later" + +#: include/language.h:70 +#, fuzzy +msgid "Services are in read-only mode!" +msgstr "Serveis ara en Mode nomès lectura." + +#: modules/commands/os_defcon.cpp:186 modules/commands/os_defcon.cpp:213 +#, fuzzy, c-format +msgid "Services are now at DEFCON %d." +msgstr "Services are now at DEFCON %d" + +#: modules/commands/os_set.cpp:128 +#, fuzzy, c-format +msgid "Services are now in debug mode (level %d)." +msgstr "Serveis ara en Mode debug (nivell %d)." + +#: modules/commands/os_set.cpp:114 +#, fuzzy +msgid "Services are now in debug mode." +msgstr "Serveis ara en Mode debug." + +#: modules/commands/os_set.cpp:159 +msgid "Services are now in expire mode." +msgstr "Serveis ara en Mode expire." + +#: modules/commands/os_set.cpp:153 +msgid "Services are now in no expire mode." +msgstr "Serveis ara en Mode no expire." + +#: modules/commands/os_set.cpp:120 +#, fuzzy +msgid "Services are now in non-debug mode." +msgstr "Serveis ara en Mode no-debug." + +#: modules/commands/os_set.cpp:47 +msgid "Services are now in read-only mode." +msgstr "Serveis ara en Mode nomès lectura." + +#: modules/commands/os_set.cpp:53 +msgid "Services are now in read-write mode." +msgstr "Serveis ara en Mode de lectura-escriptura." + +#: src/mail.cpp:76 +msgid "Services have been configured to not send mail." +msgstr "Els serveis han estat configurats per no enviar email" + +#: modules/commands/os_ignore.cpp:280 +#, fuzzy +msgid "Services ignore list:" +msgstr " IGNORE Modify the Services ignore list" + +#: modules/commands/os_mode.cpp:33 modules/commands/os_kick.cpp:39 +#, fuzzy +msgid "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" +msgstr "" +"Els serveis no han pogut canviar Modes. Estan les linees U: dels teus " +"servidors configurades correctament?" + +#: modules/commands/os_stats.cpp:140 +#, fuzzy, c-format +msgid "Services up %s." +msgstr "Servers found: %d" + +#: modules/commands/ns_set.cpp:266 +#, fuzzy, c-format +msgid "Services will from now on set status modes on %s in channels." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/cs_set.cpp:114 +#, fuzzy, c-format +msgid "Services will no longer automatically give modes to users in %s." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/ns_set.cpp:272 +#, fuzzy, c-format +msgid "Services will no longer set status modes on %s in channels." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/cs_set.cpp:108 +#, fuzzy, c-format +msgid "Services will now automatically give modes to users in %s." +msgstr "Services will now autoop %s in channels." + +#: modules/commands/ns_set.cpp:940 +#, c-format +msgid "Services will now reply to %s with messages." +msgstr "Services will now reply to %s with messages." + +#: modules/commands/ns_set.cpp:946 +#, c-format +msgid "Services will now reply to %s with notices." +msgstr "Services will now reply to %s with notices." + +#: modules/commands/os_reload.cpp:34 +#, fuzzy +msgid "Services' configuration has been reloaded." +msgstr "L'arxiu de configuració de serveis ha estat carregat novament." + +#: modules/commands/os_session.cpp:192 +msgid "Session" +msgstr "" + +#: modules/commands/os_session.cpp:382 +#, c-format +msgid "Session limit for %s set to %d." +msgstr "Límit de sessió per a %s establert a %d." + +#: modules/commands/os_session.cpp:257 modules/commands/os_session.cpp:534 +msgid "Session limiting is disabled." +msgstr "Límits de sessions no disponibles." + +#: modules/commands/os_stats.cpp:195 +#, c-format +msgid "Sessions: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/ns_set.cpp:74 +#, fuzzy +msgid "Set SET-options on another nickname" +msgstr " SASET Set SET-options on another nickname" + +#: modules/commands/cs_set.cpp:20 +#, fuzzy +msgid "Set channel options and information" +msgstr " SET Establir opcions i informació d'un canal" + +#: modules/commands/cs_set.cpp:137 +#, fuzzy +msgid "Set how Services make bans on the channel" +msgstr "" +" BANTYPE Estableix com els serveis posen bans\n" +" en el canal" + +#: modules/commands/ms_set.cpp:206 +#, fuzzy +msgid "Set options related to memos" +msgstr " SET Estableix opcions relacionades a memos" + +#: modules/commands/ns_set.cpp:19 +#, fuzzy +msgid "Set options, including kill protection" +msgstr " SET Estableix proteccions, inclouent kills" + +#: modules/commands/cs_set.cpp:472 +#, fuzzy +msgid "Set the channel as permanent" +msgstr " PERSIST Set the channel as permanent" + +#: modules/commands/cs_set.cpp:204 +#, fuzzy +msgid "Set the channel description" +msgstr " DESC Estableix la descripció del canal" + +#: modules/commands/ns_set.cpp:329 +#, fuzzy +msgid "Set the display of your group in Services" +msgstr " DISPLAY Estableix el display del teu grup amb serveis" + +#: modules/commands/cs_set.cpp:266 +#, fuzzy +msgid "Set the founder of a channel" +msgstr " FOUNDER Estableix el fundador d'un canal" + +#: modules/commands/ns_set.cpp:793 +#, fuzzy +msgid "Set the language Services will use when messaging you" +msgstr "" +" LANGUAGE Estableix el llenguatge amb el que els serveis\n" +" t'enviaran missatges" + +#: modules/commands/ns_set.cpp:172 +#, fuzzy +msgid "Set the nickname password" +msgstr " PASSWORD Set the nickname password" + +#: modules/commands/cs_set.cpp:949 +#, fuzzy +msgid "Set the successor for a channel" +msgstr " SUCCESSOR Estableix el successor d'un canal" + +#: modules/commands/hs_set.cpp:125 +#, fuzzy +msgid "Set the vhost for all nicks in a group" +msgstr " SETALL Set the vhost for all nicks in a group" + +#: modules/commands/hs_set.cpp:19 +#, fuzzy +msgid "Set the vhost of another user" +msgstr " SET Set the vhost of another user" + +#: modules/commands/os_set.cpp:169 +#, fuzzy +msgid "Set various global Services options" +msgstr " SET Estableix varies opcions globals dels serveis" + +#: modules/commands/ns_set.cpp:119 +#, fuzzy +msgid "Set your nickname password" +msgstr " PASSWORD Estableix la clau del teu nickname" + +#: modules/commands/bs_kick.cpp:271 +#, fuzzy, c-format +msgid "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK channel ITALICS {ON|OFF} [ttb]\n" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +"ttb is the number of times a user can be kicked\n" +"before it get banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:307 +#, fuzzy, c-format +msgid "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintàxi: KICK #canal BADWORDS {ON|OFF} [ttb]\n" +"\n" +"Estableix el kick per paraules malsonants a activat o desactivat.\n" +"En habilitar-lo, aquesta opció li diu al bot que kickegi\n" +"usuaris que utilitzin certes paraules al canal.\n" +"\n" +"Pots definir paraules malsonants pel teu canal utilitzant la comanda\n" +"BADWORDS. Escriu /msg %s HELP BADWORDS per més informació.\n" +"\n" +"ttb es el numero de cops que un usuari sera kickejat\n" +"abans de ser banejat. No cal especificar ttb per a deshabilitar\n" +"el sistema de ban un cop activat." + +#: modules/commands/cs_set.cpp:186 +#, fuzzy +msgid "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" +msgstr "" +"Sintaxis: %s canal BANTYPE tipus_de_ban\n" +"\n" +"Especifica el tipus de ban que sera utilitzat pels\n" +"serveis quant necessitin banear algu\n" +"del teu canal.\n" +"\n" +"Tipus de ban es un numero entre 0 i 3 que significa:\n" +"\n" +"0: ban de la forma *!usuari@host\n" +"1: ban de la forma *!*usuari@host\n" +"2: ban de la forma *!*@host\n" +"3: ban de la forma *!*usuari@*.domini" + +#: modules/commands/bs_kick.cpp:345 +#, fuzzy +msgid "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintàxi: KICK canal BOLDS {ON|OFF} [ttb]\n" +"Estableix el kick per negretes a actvitat o desactivat.\n" +"En habilitar-lo, aquesta opció li diu al bot que kickegi\n" +"usuaris que utilitzin negretes.\n" +"\n" +"ttb es el numero de cops que un usuari sera kickejat\n" +"abans de ser banejat. No cal especificar ttb per a deshabilitar\n" +"el sistema de ban un cop activat." + +#: modules/commands/bs_kick.cpp:436 +#, fuzzy, c-format +msgid "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintàxi: KICK canal CAPS {ON|OFF} [ttb [min [porcentaje]]]\n" +"Estableix el kick per mayusculas a activat o desactivat.\n" +"En habilitar-lo, aquesta opció le diu al bot que kickegi\n" +"usuaris que estiguin escrivint en majuscules.\n" +"\n" +"El bot kickeja nomès si hi ha com a mínim min majuscules\n" +"i que constitueixin com a mínim porcentatge%% del total\n" +"del text (si no s'especifica, per defecte s'estableix a 10\n" +"caràcters i 25%%).\n" +"\n" +"ttb es el numero de cops que un usuari sera kickejat\n" +"abans de ser banejat. No cal especificar ttb per a deshabilitar\n" +"el sistema de ban un cop activat." + +#: modules/commands/bs_kick.cpp:475 +#, fuzzy +msgid "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintàxi: KICK canal COLORS {ON|OFF} [ttb]\n" +"\n" +"Estableix el kick per colors a activat o desactivat.\n" +"En habilitar-lo, aquesta opció li diu al bot que kickegi\n" +"usuaris que utilitzin colors.\n" +"\n" +"ttb es el numero de cops que un usuari sera kickejat\n" +"abans de ser banejat. No cal especificar ttb per a deshabilitar\n" +"el sistema de ban un cop activat." + +#: modules/commands/cs_set.cpp:255 +#, fuzzy +msgid "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." +msgstr "" +"Sintaxis: %s canal DESC descripció\n" +"\n" +"Estableix la descripció pel canal, la que es mostrada\n" +"amb les comandes LIST i INFO." + +#: modules/commands/bs_kick.cpp:571 +#, fuzzy +msgid "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintàxi: KICK canal FLOOD {ON|OFF} [ttb [ln [segs]]]\n" +"Estableix el kick per flood a activat o desactivat.\n" +"En habilitar-lo, aquesta opció li diu al bot que kickegi\n" +"usuaris que estiguin floodejant el canal utilitzant com a mínim\n" +"ln linees en segs segons (si no s'especifica, per\n" +"defecte es establert a 6 linees en 10 segons).\n" +"\n" +"ttb es el numero de cops que un usuari sera kickejat\n" +"abans de ser banejat. No cal especificar ttb per a deshabilitar\n" +"el sistema de ban un cop activat." + +#: modules/commands/bs_kick.cpp:607 +#, fuzzy +msgid "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK channel ITALICS {ON|OFF} [ttb]\n" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +"ttb is the number of times a user can be kicked\n" +"before it get banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:706 +#, fuzzy +msgid "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintàxi: KICK #canal REPEAT {ON|OFF} [ttb [num]]\n" +"\n" +"Estableix el kick per repetició a activat o desactivat.\n" +"En habilitar-lo, aquesta opció li diu al bot que kickegi\n" +"usuaris que estiguin repetint num cops (si num no s'especifica,\n" +"per defecte es establert a 3).\n" +"\n" +"ttb es el numero de cops que un usuari sera kickejat\n" +"abans de ser banejat. No cal especificar ttb per a deshabilitar\n" +"el sistema de ban un cop activat." + +#: modules/commands/bs_kick.cpp:742 +#, fuzzy +msgid "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintàxi: KICK canal REVERSES {ON|OFF} [ttb]\n" +"\n" +"Estableix el kick per reversos a activat o desactivat.\n" +"En habilitar-lo, aquesta opció li diu al bot que kickegi\n" +"usuaris que utilitzin reversos.\n" +"\n" +"ttb es el numero de cops que un usuari sera kickejat\n" +"abans de ser banejat. No cal especificar ttb per a deshabilitar\n" +"el sistema de ban un cop activat." + +#: modules/commands/bs_kick.cpp:776 +#, fuzzy +msgid "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintàxi: KICK canal UNDERLINES {ON|OFF} [ttb]\n" +"\n" +"Estableix el kick per subratllats a activat o apagat.\n" +"En habilitar-lo, aquesta opció li diu al bot que kickegi\n" +"usuaris que utilitzin subratllats.\n" +"\n" +"ttb es el numero de cops que un usuari sera kickejat\n" +"abans de ser banejat. No cal especificar ttb per a deshabilitar\n" +"el sistema de ban un cop activat." + +#: modules/commands/hs_set.cpp:206 +#, fuzzy +msgid "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." +msgstr "" +"Syntax: SETALL  .\n" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nick's\n" +"added to the group after this command was used.\n" +"Limited to Services operators." + +#: modules/commands/hs_set.cpp:99 +#, fuzzy +msgid "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." +msgstr "" +"Syntax: SET  .\n" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as \n" +"well as vhosts.\n" +"Limited to Services operators." + +#: modules/commands/os_set.cpp:199 +#, fuzzy +msgid "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" +msgstr "" +"Sintàxi: SET opció parametres\n" +"\n" +"Estableix varies opcions globals de serveis.\n" +"Noms de opcions actualment definides són:\n" +" READONLY Estableix Mode nomès lectura o nomès escritura\n" +" LOGCHAN Report log messages to a channel\n" +" DEBUG Activa o desactiva el Mode debug\n" +" NOEXPIRE Activa o desactiva el Mode no expire\n" +" SUPERADMIN Activate or deactivate super-admin mode\n" +" IGNORE Activate or deactivate ignore mode\n" +" LIST List the options\n" +"\n" +"Limitat a administradors de serveis." + +#: modules/commands/ms_set.cpp:235 +#, fuzzy, c-format +msgid "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Sintàxi: SET Opció paràmetros\n" +"\n" +"Estableix varies opcions de memos. Opció pot ser una de:\n" +"\n" +" NOTIFY Canvia quan seràs notificat sobre de\n" +" nous memos (sols per a nicknames)\n" +" LIMIT Estableix el màxim nombre de memos que\n" +" pots rebre\n" +"\n" +"escriu /msg %s HELP SET Opció per a més informació\n" +"sobre una opció específica." + +#: modules/commands/ns_set.cpp:33 modules/commands/ns_set.cpp:88 +#, fuzzy +msgid "Sets various nickname options. option can be one of:" +msgstr "" +"Sintaxis: SET Opció parametres\n" +"\n" +"Estableix varies opcions per a nicknames. Opció pot ser\n" +"una de:" + +#: modules/commands/ns_set.cpp:237 +msgid "" +"Sets whether services should set channel status modes on you automatically." +msgstr "" + +#: modules/commands/cs_set.cpp:1090 +#, fuzzy +msgid "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." +msgstr "" +"Sintàxi: SET canal NOEXPIRE {ON | OFF}\n" +"\n" +"Estableix si el canal expirarà. Establint-lo \n" +"a ON evita que el canal expiri.\n" +"\n" +"limitat a administradors de serveis." + +#: modules/commands/ns_set.cpp:315 +#, fuzzy, c-format +msgid "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." +msgstr "" +"Syntax: SASET nickname AUTOOP {ON | OFF}\n" +"\n" +"Sets whether the given nickname will be opped automatically.\n" +"Set to ON to allow ChanServ to op the given nickname \n" +"automatically when joining channels." + +#: modules/commands/ns_set.cpp:1145 +#, fuzzy +msgid "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." +msgstr "" +"Syntax: SASET nickname NOEXPIRE {ON | OFF}\n" +"\n" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." + +#: modules/commands/ns_set.cpp:288 +#, fuzzy, c-format +msgid "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." +msgstr "" +"Syntax: SET AUTOOP {ON | OFF}\n" +"\n" +"Sets whether you will be opped automatically. Set to ON to \n" +"allow ChanServ to op you automatically when entering channels." + +#: modules/commands/cs_access.cpp:648 modules/commands/cs_access.cpp:689 +#, fuzzy, c-format +msgid "" +"Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." +msgstr "" +"Opció %s no coneguda. Escriu /msg %s HELP LEVELS DESC per a una llista de " +"opcións valides." + +#: modules/commands/os_set.cpp:133 +#, fuzzy +msgid "Setting for DEBUG must be ON, OFF, or a positive number." +msgstr "L'establiment per a DEBUG ha de ser ON, OFF, o un numero positiu." + +#: modules/commands/os_set.cpp:162 +#, fuzzy +msgid "Setting for NOEXPIRE must be ON or OFF." +msgstr "Establiment per a NOEXPIRE ha de ser ON o OFF." + +#: modules/commands/os_set.cpp:56 +#, fuzzy +msgid "Setting for READONLY must be ON or OFF." +msgstr "L'establiment per a READONLY ha de ser ON o OFF." + +#: modules/commands/os_set.cpp:95 +#, fuzzy +msgid "Setting for super admin must be ON or OFF." +msgstr "L'establiment per a READONLY ha de ser ON o OFF." + +#: modules/commands/cs_set.cpp:74 +#, fuzzy +msgid "Should services automatically give status to users" +msgstr " AUTOOP Should services op you automatically. " + +#: modules/commands/os_stats.cpp:203 +#, fuzzy +msgid "Show status of Services and network" +msgstr " STATS mostra estatus dels serveis i la xarxa" + +#: modules/commands/os_logsearch.cpp:152 +#, c-format +msgid "Showed %d/%d matches for %s." +msgstr "" + +#: modules/commands/cs_set.cpp:872 +#, fuzzy +msgid "Sign kicks that are done with the KICK command" +msgstr " SIGNKICK Firma kicks fets amb la comanda KICK" + +#: modules/commands/cs_set.cpp:921 +#, fuzzy, c-format +msgid "Signed kick option for %s is now off." +msgstr "Signed kick option for %s is now ON." + +#: modules/commands/cs_set.cpp:913 +#, fuzzy, c-format +msgid "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." +msgstr "" +"Signed kick option for %s is now ON, but depends of the\n" +"level of the user that is using the command." + +#: modules/commands/cs_set.cpp:906 +#, fuzzy, c-format +msgid "Signed kick option for %s is now on." +msgstr "Signed kick option for %s is now ON." + +#: modules/commands/cs_set.cpp:1299 +msgid "Signed kicks" +msgstr "Kicks Signats" + +#: modules/commands/ms_rsend.cpp:60 modules/commands/ms_send.cpp:59 +#, fuzzy, c-format +msgid "Sorry, %s currently has too many memos and cannot receive more." +msgstr "%s actualment te molts memos i no pot rebre'n mes." + +#: modules/commands/cs_seen.cpp:294 +#, c-format +msgid "Sorry, I have not seen %s." +msgstr "" + +#: modules/commands/bs_badwords.cpp:404 +#, fuzzy +msgid "Sorry, bad words list modification is temporarily disabled." +msgstr "" +"Ho sento, la llista de paraules malsonants per a canals esta temporalment " +"inabilitada." + +#: modules/commands/bs_assign.cpp:30 modules/commands/bs_assign.cpp:98 +#, fuzzy +msgid "Sorry, bot assignment is temporarily disabled." +msgstr "" +"Ho sento, l'establiment d'opcions per a bot esta temporalment inhabilitat" + +#: modules/commands/bs_bot.cpp:281 modules/commands/bs_assign.cpp:164 +msgid "Sorry, bot modification is temporarily disabled." +msgstr "Ho sento, la modificació de bots esta temporalment inabilitada." + +#: modules/fantasy.cpp:42 modules/commands/bs_kick.cpp:813 +#: modules/commands/bs_kick.cpp:878 +msgid "Sorry, bot option setting is temporarily disabled." +msgstr "" +"Ho sento, l'establiment d'opcions per a bot esta temporalment inhabilitat" + +#: modules/commands/bs_set.cpp:115 +#, fuzzy +msgid "Sorry, changing bot options is temporarily disabled." +msgstr "" +"Ho sento, l'establiment d'opcions per a bot esta temporalment inhabilitat" + +#: modules/commands/cs_xop.cpp:112 modules/commands/cs_xop.cpp:235 +#: modules/commands/cs_xop.cpp:444 +#, fuzzy, c-format +msgid "Sorry, channel %s list modification is temporarily disabled." +msgstr "" +"Ho sento, la modificació de la llista AOP de canals esta\n" +"temporalment deshabilitada." + +#: modules/commands/cs_access.cpp:547 modules/commands/cs_flags.cpp:405 +msgid "Sorry, channel access list modification is temporarily disabled." +msgstr "" +"Ho sento, la modificació d'accés a canals esta temporalment inabilitada." + +#: modules/commands/cs_akick.cpp:469 +msgid "Sorry, channel autokick list modification is temporarily disabled." +msgstr "" +"Ho sento, la modificació de kicks automàtics a canals esta temporalment " +"inabilitada." + +#: modules/commands/cs_drop.cpp:29 +msgid "Sorry, channel de-registration is temporarily disabled." +msgstr "" +"Ho sento, el desenregistrament de canals esta temporalment desabilitat." + +#: modules/commands/cs_register.cpp:35 +msgid "Sorry, channel registration is temporarily disabled." +msgstr "Ho sento, el registre de canals esta temporalment inhabilitat." + +#: modules/commands/bs_kick.cpp:181 +msgid "Sorry, kicker configuration is temporarily disabled." +msgstr "Ho sento, la configuració de kicker esta temporalment inabilitada." + +#: modules/commands/ms_set.cpp:216 +msgid "Sorry, memo option setting is temporarily disabled." +msgstr "" +"Ho sento, l'establiment d'opcions per a memos esta temporalment inhabilitat." + +#: include/language.h:116 +#, fuzzy +msgid "Sorry, memo sending is temporarily disabled." +msgstr "" +"Ho sento, l'establiment d'opcions per a memos esta temporalment inhabilitat." + +#: modules/commands/ns_drop.cpp:29 +msgid "Sorry, nickname de-registration is temporarily disabled." +msgstr "Ho sento, desenregistrament de nickname esta temporalment inhabilitat." + +#: modules/commands/ns_group.cpp:120 +msgid "Sorry, nickname grouping is temporarily disabled." +msgstr "Ho sento, La agrupació de nicks esta temporalment inabilitada." + +#: modules/commands/ns_register.cpp:139 +msgid "Sorry, nickname registration is temporarily disabled." +msgstr "Ho sento, el registre de nicknames esta temporalment deshabilitat." + +#: modules/commands/ns_access.cpp:33 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d access entries has been reached." +msgstr "" +"Ho sento, sols pots tenir %d instàncies d'accés en un determinat canal." + +#: modules/commands/ns_ajoin.cpp:141 +#, c-format +msgid "Sorry, the maximum of %d auto join entries has been reached." +msgstr "" + +#: modules/commands/ns_cert.cpp:173 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d certificate entries has been reached." +msgstr "" +"Ho sento, sols pots tenir %d instàncies a la teva lllista d'accés per " +"nickname." + +#: modules/commands/ms_ignore.cpp:55 +#, fuzzy, c-format +msgid "Sorry, the memo ignore list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/cs_access.cpp:204 modules/commands/cs_flags.cpp:174 +#: modules/commands/cs_xop.cpp:201 +#, fuzzy, c-format +msgid "" +"Sorry, you can only have %d access entries on a channel, including access " +"entries from other channels." +msgstr "" +"Ho sento, sols pots tenir %d instàncies d'accés en un determinat canal." + +#: modules/commands/cs_akick.cpp:177 +#, c-format +msgid "Sorry, you can only have %d autokick masks on a channel." +msgstr "" +"Ho sento, sols pots tenir %d mascaras per a kicks automàtics a un canal." + +#: modules/commands/bs_badwords.cpp:286 +#, c-format +msgid "Sorry, you can only have %d bad words entries on a channel." +msgstr "Ho sento, sols pots tenir %d paraules malsonants en un canal." + +#: include/language.h:103 +#, fuzzy, c-format +msgid "Sorry, you have already exceeded your limit of %d channels." +msgstr "Ho sento, sols pots tenir %d paraules malsonants en un canal." + +#: include/language.h:102 +#, fuzzy, c-format +msgid "Sorry, you have already reached your limit of %d channels." +msgstr "Ho sento, sols pots tenir %d paraules malsonants en un canal." + +#: modules/commands/os_dns.cpp:218 +msgid "State" +msgstr "" + +#: modules/commands/cs_seen.cpp:117 +msgid "Statistics and maintenance for seen data" +msgstr "" + +#: modules/commands/os_stats.cpp:131 +msgid "Statistics reset." +msgstr "Estadistiques restablertes." + +#: modules/commands/ns_update.cpp:36 +msgid "Status updated (memos, vhost, chmodes, flags)." +msgstr "Status updated (memos, vhost, chmodes, flags)." + +#: modules/commands/bs_kick.cpp:1432 +msgid "Stop flooding!" +msgstr "Para de floodejar!" + +#: modules/commands/bs_kick.cpp:1448 +msgid "Stop repeating yourself!" +msgstr "No repeteixis com l'allioli!" + +#: modules/commands/cs_set.cpp:746 +#, fuzzy +msgid "Stricter control of channel founder status" +msgstr "" +" SECUREFOUNDER Estricto control de l'estatus de fundador\n" +" del canal" + +#: modules/commands/cs_set.cpp:810 +#, fuzzy +msgid "Stricter control of chanop status" +msgstr " SECUREOPS Estricte control de l'estatus de chanop" + +#: modules/commands/ns_alist.cpp:75 modules/commands/cs_info.cpp:50 +msgid "Successor" +msgstr "" + +#: modules/commands/cs_set.cpp:1006 +#, fuzzy, c-format +msgid "Successor for %s changed to %s." +msgstr "Sucessor de %s cambiat a %s." + +#: modules/commands/cs_set.cpp:1008 +#, c-format +msgid "Successor for %s unset." +msgstr "Sucessor de %s desabilitat." + +#: modules/commands/os_set.cpp:81 +#, fuzzy +msgid "" +"Super admin can not be set because it is not enabled in the configuration." +msgstr "SuperAdmin setting not enabled in services.conf" + +#: modules/commands/ns_suspend.cpp:60 +#, fuzzy +msgid "Suspend a given nick" +msgstr " SUSPEND Suspend a given nick" + +#: modules/commands/cs_suspend.cpp:236 modules/commands/ns_suspend.cpp:250 +#, fuzzy +msgid "Suspend reason" +msgstr "JUPE nom-del-servidor [raó]" + +#: modules/commands/cs_suspend.cpp:232 modules/commands/ns_suspend.cpp:246 +msgid "Suspended" +msgstr "" + +#: modules/commands/cs_suspend.cpp:234 modules/commands/ns_suspend.cpp:248 +msgid "Suspended by" +msgstr "" + +#: modules/commands/cs_suspend.cpp:238 modules/commands/ns_suspend.cpp:252 +#, fuzzy +msgid "Suspended on" +msgstr " SUSPEND Suspend a given nick" + +#: modules/commands/ns_suspend.cpp:147 +#, fuzzy +msgid "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." +msgstr "" +"Syntax: SUSPEND channel [reason]\n" +"\n" +"Disallows anyone from registering or using the given\n" +"channel. May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"\n" +"Reason may be required on certain networks." + +#: modules/commands/cs_suspend.cpp:240 modules/commands/ns_suspend.cpp:254 +#, fuzzy +msgid "Suspension expires" +msgstr " %s (does not expire)" + +#: modules/commands/cs_sync.cpp:19 +#, fuzzy +msgid "Sync users channel modes" +msgstr "%s changed your usermodes." + +#: modules/commands/cs_sync.cpp:49 +msgid "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." +msgstr "" + +#: modules/commands/hs_group.cpp:42 +#, fuzzy +msgid "Syncs the vhost for all nicks in a group" +msgstr " GROUP Syncs the vhost for all nicks in a group" + +#: src/command.cpp:146 +msgid "Syntax" +msgstr "" + +#: modules/commands/ns_group.cpp:373 +#, fuzzy, c-format +msgid "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." +msgstr "" +"Sintaxis: GLIST\n" +"\n" +"Llista tots els nicks en el teu grup." + +#: modules/commands/ns_group.cpp:363 +#, fuzzy, c-format +msgid "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." +msgstr "" +"Sintaxis: GLIST [nickname]\n" +"\n" +"Sense un parametre, llista tots els nicknames en el teu\n" +"grup.\n" +"\n" +"Amb un parametre, llista tots els nicknames que hi ha\n" +"en el grup del nick esmentat.\n" +"El seu ús esta limitat a administradors de serveis." + +#: modules/commands/os_set.cpp:227 +#, fuzzy +msgid "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." +msgstr "" +"Sintàxi: SET NOEXPIRE {ON | OFF}\n" +"\n" +"Estableix el mode no expire a activat o desactivat. En\n" +"mode no expire, nicks, canals, akills i excepcions\n" +"no caducaran fins que l'opció sigui desactivada.\n" +"\n" +"Aquaquesta opció es equivalent a l'opció -noexpire\n" +"en la linea de comandes." + +#: modules/commands/ms_set.cpp:287 +#, fuzzy, c-format +msgid "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." +msgstr "" +"Sintàxi: SET LIMIT [canal] límit\n" +"\n" +"Estableix el màxim nombre de memos que tu (o el canal donat)\n" +"pots tenir. Si queda a 0, ningú podrà\n" +"enviar-te memos. A més, no pots establir el límit més\n" +"alt que %d." + +#: modules/commands/ms_set.cpp:267 +#, fuzzy, c-format +msgid "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." +msgstr "" +"Sintàxi: SET LIMIT [usuari | canal] {límit | NONE} [HARD]\n" +"\n" +"Estableix el màxim nombre de memos un usuari o canal està\n" +"permès. Establir el límit a 0 evita a l'usuari\n" +"de rebre memos; posar-lo a NONE permet a l'usuari\n" +"de rebre i guardar els memos que vulgui. Si no dones un\n" +"nickname o canal, el teu propi límit està establert.\n" +"\n" +"Afegir HARD evita al usuari de canviar el límit. No\n" +"afegir HARD té l'efect contrari, permetent a l'\n" +"usuari canviar el límit (encara que un límit previ hagui sigut establert\n" +"amb HARD).\n" +"\n" +"L'us de la comanda SET LIMIT està limitat a\n" +"administradors de serveis. altres usuaris poden\n" +"només establir límits per a ells mateixos o per a un canal en\n" +"el que tinguin certos privilegos, no podenn esborrar el seu\n" +"límit, no poden establir el límit més enllà de %d, i no\n" +"poden establir un límit hard." + +#: modules/commands/os_set.cpp:208 +#, fuzzy, c-format +msgid "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." +msgstr "" +"Syntax: SET LIST\n" +"Display the various %s settings" + +#: modules/commands/os_set.cpp:234 +#, fuzzy +msgid "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." +msgstr "" +"Sintàxi: SET NOEXPIRE {ON | OFF}\n" +"\n" +"Estableix el mode no expire a activat o desactivat. En\n" +"mode no expire, nicks, canals, akills i excepcions\n" +"no caducaran fins que l'opció sigui desactivada.\n" +"\n" +"Aquaquesta opció es equivalent a l'opció -noexpire\n" +"en la linea de comandes." + +#: modules/commands/ms_set.cpp:246 +#, fuzzy +msgid "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." +msgstr "" +"Sintàxi: SET NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +"\n" +"Canvia quan se't notificarà de nous memos:\n" +"\n" +" ON Notificació de memos quan et conectis,\n" +" quan treguis /AWAY, i quan \n" +" s'enviin\n" +" LOGON Sols seras notificat de memos quan et conectis\n" +" o quan treguis /AWAY.\n" +" NEW Sols seras notificat de memos quan se't \n" +" enviin.\n" +" MAIL You will be notified of memos by email aswell as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF No rebràs cap notificació per memos.\n" +"\n" +"ON és escencialment LOGON i NEW combinats." + +#: modules/commands/os_set.cpp:212 +#, fuzzy +msgid "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." +msgstr "" +"Sintàxi: SET READONLY {ON | OFF}\n" +"\n" +"Estableix el mode nomès lectura a activat o desactivat. En mode\n" +"nomès lectura, els usuaris normals no podran modificar dades\n" +"de serveis, incloent accés a llistes de canals i\n" +"nicknames, etc. IRCops amb suficients privilegis amb\n" +"els serveis podren modificar la llista AKILL de\n" +"serveis i eliminar o prohibir nicknames i canals, però\n" +"cap d'aquests canvios sera guardat excepte que el\n" +"mode nomès lectura es desactivi abans de que els serveis\n" +"siguin desactivats o reiniciats.\n" +"\n" +"Aquesta opció es equivalent a l'opció -readonly en\n" +"la linea de comandes." + +#: modules/commands/os_set.cpp:243 +#, fuzzy +msgid "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." +msgstr "" +"Syntax: SET SUPERADMIN {ON | OFF}\n" +"Setting this will grant you extra privlages such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +"This opion is _NOT_ persistant, and should only be used when\n" +"needed, and set back to OFF when no longer needed." + +#: modules/commands/ns_identify.cpp:107 +#, fuzzy, c-format +msgid "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." +msgstr "" +"Sintaxis: IDENTIFY [account] clau\n" +"\n" +"Informa a %s que tu ets realment el propietari del teu nick.\n" +"Moltes comandes requereixen que t'identifiquis amb aquesta\n" +"comanda abans d'utilitzar-les. La clau hauria de ser la mateixa\n" +"que va ser enviada amb la comanda REGISTER." + +#: modules/commands/cs_invite.cpp:91 +#, fuzzy, c-format +msgid "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Sintàxi: INVITE canal\n" +"\n" +"Li diu a %s que et convidi al canal donat.\n" +"\n" +"Per defecte, limitat a AOPs o aquells amb nivell 5\n" +"i major en el canal." + +#: modules/commands/cs_unban.cpp:103 +#, fuzzy, c-format +msgid "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Sintàxi: UNBAN canal [nick]\n" +"\n" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel.\n" +"\n" +"Per defecte, limitat a AOPs o aquells amb nivell 5\n" +"i major en el canal." + +#: modules/commands/os_jupe.cpp:56 +#, fuzzy +msgid "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." +msgstr "" +"Sintàxi: JUPE servidor [raó]\n" +"\n" +"Li diu als serveis que fagin jupiter (saturn, mart,...) a un servidor\n" +"-- és a dir, crear un \"servidor\" fals conectant als\n" +"serveis el qual preveu al servidor real de\n" +"connectar-se. El jupe pot ser eliminat utilitzant la comanda\n" +"estandart SQUIT. Si una raó es especificada, es afegida\n" +"en el camp d'informació sobre el servidor; d'altra\n" +"banda, el camp de informació sobre el servidor tindra\n" +"el text \"Juped per \", mostrant el nickname\n" +"de la persona que va jupitejar el servidor.\n" +"\n" +"Limitat a administradors de serveis." + +#: modules/commands/cs_seen.cpp:261 +msgid "Tells you about the last time a user was seen" +msgstr "" + +#: modules/commands/os_shutdown.cpp:19 +#, fuzzy +msgid "Terminate Services WITHOUT saving" +msgstr "" +" SHUTDOWN Termina el programa de serveis guardant els\n" +" canvios" + +#: modules/commands/os_shutdown.cpp:73 +#, fuzzy +msgid "Terminate services with save" +msgstr "" +" SHUTDOWN Termina el programa de serveis guardant els\n" +" canvios" + +#: modules/commands/os_news.cpp:156 +msgid "Text" +msgstr "" + +#: modules/commands/cs_access.cpp:576 +msgid "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." +msgstr "" + +#: modules/commands/cs_access.cpp:587 +msgid "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." +msgstr "" + +#: modules/commands/cs_access.cpp:593 +msgid "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." +msgstr "" + +#: modules/commands/cs_flags.cpp:447 +msgid "" +"The CLEAR command clears the channel access list. This requires channel " +"founder access." +msgstr "" + +#: modules/commands/cs_seen.cpp:173 +#, c-format +msgid "" +"The CLEAR command lets you clean the database by removing all entries from " +"the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." +msgstr "" + +#: modules/commands/bs_badwords.cpp:438 +#, fuzzy +msgid "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." +msgstr "" +"Sintàxi: HOP canal ADD nick\n" +" HOP canal DEL {nick | instancia | llista}\n" +" HOP canal LIST [mascara | llista]\n" +" HOP canal CLEAR\n" +"\n" +"Manté la llista HOP (HalfOP) per a un canal. La llista\n" +"HOP li dóna a l'usuari el dret de ser automàticament\n" +"halfopejat en el teu canal.\n" +"\n" +"La comanda HOP ADD agrega al nickname donat a la llista\n" +"HOP.\n" +"\n" +"La comanda HOP DEL esborra el nickname donat de la\n" +"llista HOP. Si una llista d'instàncies és donada, aquestes\n" +"instàncies són esborrades. (Veure l'exemple per a LIST més\n" +"endevant.)\n" +"\n" +"La comanda HOP LIST mostra la llista HOP. Si una\n" +"mascara amb comodí és donada, només les instàncies\n" +"que concordin amb la mascara són mostrades. Si una llista de\n" +"instàncies és donada, només aquestes instàncies són mostrades;\n" +"per exemple:\n" +"\n" +" HOP #canal LIST 2-5,7-9\n" +" Mostra instàncies de HOP enumerades 2 a 5 y\n" +" 7 a 9.\n" +"\n" +"La comanda HOP CLEAR neteja totes les instàncies de la\n" +"llista HOP.\n" +"\n" +"Les comandes HOP ADD i HOP DEL estan limitades a\n" +"AOPs o superior, mentre que la comanda HOP CLEAR\n" +"sols pot ser utilitzada per el fundador del canal.\n" +"\n" +"Aquesta comanda pot haber estat deshabilitada per al teu canal.\n" +"Si aquest és el cas, has de fer servir la llista d'accés. Veure\n" +"/msg %s HELP ACCESS per a informació sobre la llista\n" +"d'accés i /msg %s HELP SET XOP per a saber com canviar\n" +"entre la llista d'accés i el sistema de llistes xOP." + +#: modules/commands/cs_entrymsg.cpp:241 +msgid "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:253 +msgid "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:245 +msgid "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:250 +msgid "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." +msgstr "" + +#: modules/commands/ns_set.cpp:713 +msgid "The IMMED option is not available on this network." +msgstr "The IMMED option is not available on this network." + +#: modules/commands/cs_access.cpp:821 +#, fuzzy, c-format +msgid "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." +msgstr "" +"Sintàxi: LEVELS canal SET tipo [nivell|FOUNDER]\n" +" LEVELS canal {DIS | DISABLE} tipo\n" +" LEVELS canal LIST\n" +" LEVELS canal RESET\n" +"\n" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +"\n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it).\n" +"\n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel (see\n" +"HELP ACCESS LEVELS).\n" +"\n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." + +#: modules/commands/cs_flags.cpp:442 +msgid "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." +msgstr "" + +#: modules/commands/cs_flags.cpp:435 +msgid "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access " +"list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. " +"You are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of " +"what your access is." +msgstr "" + +#: modules/commands/cs_seen.cpp:172 +msgid "" +"The STATS command prints out statistics about stored nicks and memory usage." +msgstr "" + +#: modules/commands/ns_register.cpp:291 +#, fuzzy +msgid "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." +msgstr "" +"Escriu /msg %s SET EMAIL e-mail per provar el teu e-mail.\n" +"Respectems la teva privacitat; Aquest e-mail no sera entregat\n" +"a cap persona." + +#: modules/commands/cs_log.cpp:258 +#, c-format +msgid "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." +msgstr "" + +#: modules/commands/cs_ban.cpp:64 +#, fuzzy, c-format +msgid "The %s list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/os_sxline.cpp:220 +#, fuzzy, c-format +msgid "The %s list has been cleared." +msgstr "La llista de AKILLs ha estat netegada." + +#: modules/commands/os_akill.cpp:377 +msgid "The AKILL list has been cleared." +msgstr "La llista de AKILLs ha estat netegada." + +#: modules/commands/os_defcon.cpp:136 modules/commands/os_defcon.cpp:225 +#, fuzzy, c-format +msgid "The Defcon level is now at: %d" +msgstr "The Defcon Level is now at Level: %d" + +#: modules/commands/ns_info.cpp:171 +#, c-format +msgid "The E-mail address of %s will now be hidden from %s INFO displays." +msgstr "The E-mail address of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:172 +#, c-format +msgid "The E-mail address of %s will now be shown in %s INFO displays." +msgstr "The E-mail address of %s will now be shown in %s INFO displays." + +#: modules/commands/cs_flags.cpp:449 +msgid "The available flags are:" +msgstr "" + +#: modules/commands/os_defcon.cpp:240 +#, fuzzy +msgid "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." +msgstr "" +"Syntax: DEFCON [1|2|3|4|5]\n" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." + +#: modules/ns_maxemail.cpp:51 +#, c-format +msgid "The email address %s has reached its usage limit of %d users." +msgstr "" + +#: modules/ns_maxemail.cpp:49 +#, c-format +msgid "The email address %s has reached its usage limit of 1 user." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:142 +#, fuzzy, c-format +msgid "The entry message list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/cs_access.cpp:796 +msgid "The following feature/function names are available:" +msgstr "" + +#: modules/commands/cs_access.cpp:584 +msgid "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." +msgstr "" + +#: modules/commands/os_session.cpp:240 +#, fuzzy, c-format +msgid "" +"The host %s currently has %d sessions with a limit of %d because it matches " +"entry: %s." +msgstr "El host %s actualment te %d sessions amb un límit de %d." + +#: modules/commands/ms_check.cpp:54 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has been read." +msgstr "The last memo you sent to %s (sent on %s) has been read." + +#: modules/commands/ms_check.cpp:52 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has not yet been read." +msgstr "The last memo you sent to %s (sent on %s) has not yet been read." + +#: modules/commands/ns_info.cpp:189 +#, c-format +msgid "The last quit message of %s will now be hidden from %s INFO displays." +msgstr "The last quit message of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:190 +#, c-format +msgid "The last quit message of %s will now be shown in %s INFO displays." +msgstr "The last quit message of %s will now be shown in %s INFO displays." + +#: modules/commands/ns_info.cpp:177 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." +msgstr "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:178 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." +msgstr "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." + +#: modules/commands/cs_enforce.cpp:190 +#, fuzzy, c-format +msgid "The limit on %s is not valid." +msgstr "El límit de memos per a %s no pot ser canviat." + +#: modules/commands/os_forbid.cpp:193 +msgid "The mask must contain at least one non wildcard character." +msgstr "" + +#: modules/commands/ms_set.cpp:153 +#, c-format +msgid "The memo limit for %s may not be changed." +msgstr "El límit de memos per a %s no pot ser canviat." + +#: modules/commands/cs_mode.cpp:347 +#, fuzzy, c-format +msgid "The mode lock list of %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/ns_set.cpp:355 +#, c-format +msgid "The new display MUST be a nickname of the nickname group %s." +msgstr "" + +#: include/language.h:98 +#, fuzzy, c-format +msgid "The new display is now %s." +msgstr "The Defcon Level is now at Level: %d" + +#: modules/commands/os_svs.cpp:57 +#, c-format +msgid "The nick %s is now being changed to %s." +msgstr "The nick %s is now being changed to %s." + +#: modules/commands/bs_bot.cpp:149 +msgid "The old information is the same as the new information specified." +msgstr "" + +#: modules/commands/os_info.cpp:157 +#, fuzzy, c-format +msgid "The oper info already exists on %s." +msgstr "El bot %s ja existeix." + +#: modules/commands/os_info.cpp:147 +#, fuzzy, c-format +msgid "The oper info list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/ns_info.cpp:183 +#, c-format +msgid "" +"The services access status of %s will now be hidden from %s INFO displays." +msgstr "" +"The services access status of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:184 +#, c-format +msgid "The services access status of %s will now be shown in %s INFO displays." +msgstr "" +"The services access status of %s will now be shown in %s INFO displays." + +#: modules/commands/os_session.cpp:433 +#, fuzzy +msgid "The session exception list is empty." +msgstr " EXCEPTION Modifica la llista de límit de sessió" + +#: modules/commands/ns_recover.cpp:121 +msgid "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:195 +#, c-format +msgid "There are %d memos on channel %s." +msgstr "There are %d memos on channel %s." + +#: modules/commands/bs_botlist.cpp:47 +msgid "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" +msgstr "" +"No hi ha bots disponibles en aquest moment.\n" +"Demana-li a un administrador de serveis que en fagi un!" + +#: modules/commands/os_dns.cpp:213 +msgid "There are no configured servers." +msgstr "" + +#: modules/commands/os_forbid.cpp:392 +#, fuzzy, c-format +msgid "There are no forbids of type %s." +msgstr "There are %d memos on channel %s." + +#: modules/commands/ns_group.cpp:162 +#, fuzzy +msgid "There are too many nicks in your group." +msgstr " DELALL Delete the vhost for all nicks in a group" + +#: modules/commands/cs_log.cpp:123 +#, fuzzy, c-format +msgid "There currently are no logging configurations for %s." +msgstr " RELOAD Recarrega la configuració dels serveis" + +#: modules/pseudoclients/memoserv.cpp:193 +#, c-format +msgid "There is %d memo on channel %s." +msgstr "There is %d memo on channel %s." + +#: include/language.h:110 +#, fuzzy, c-format +msgid "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." +msgstr "Escriu /msg %s READ %d per a llegir-lo." + +#: modules/commands/bs_assign.cpp:132 +#, c-format +msgid "There is no bot assigned to %s anymore." +msgstr "Ja no hi ha un bot assignat a %s." + +#: modules/commands/os_news.cpp:33 +msgid "There is no logon news." +msgstr "No hi ha notícies de entrada." + +#: modules/commands/os_news.cpp:43 +msgid "There is no oper news." +msgstr "No hay notícies de oper." + +#: modules/commands/os_news.cpp:53 +msgid "There is no random news." +msgstr "No hi ha notícies al azar." + +#: modules/commands/os_config.cpp:41 +#, fuzzy, c-format +msgid "There is no such configuration block %s." +msgstr " RELOAD Recarrega la configuració dels serveis" + +#: modules/commands/cs_mode.cpp:706 +#, fuzzy, c-format +msgid "There is no such mode %s." +msgstr "No hay notícies de oper." + +#: modules/commands/ms_set.cpp:52 +msgid "There's no email address set for your nick." +msgstr "There's no email address set for your nick." + +#: modules/commands/os_forbid.cpp:304 modules/commands/os_forbid.cpp:496 +#, fuzzy, c-format +msgid "This channel has been forbidden: %s" +msgstr "Aquest canal ha estat registrat amb %s." + +#: modules/commands/cs_suspend.cpp:121 +#, fuzzy +msgid "This channel has been suspended." +msgstr "Aquest canal esta prohibit." + +#: modules/commands/cs_suspend.cpp:232 +#, fuzzy +msgid "This channel is suspended." +msgstr "Aquest canal esta prohibit." + +#: modules/commands/cs_suspend.cpp:268 +msgid "This channel may not be used." +msgstr "Aquest canal esta prohibit." + +#: modules/commands/os_dns.cpp:702 +msgid "" +"This command allows managing DNS zones used for controlling what servers " +"users\n" +"are directed to when connecting. Omitting all parameters prints out the " +"status of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to " +"this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, " +"the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given " +"zones." +msgstr "" + +#: modules/commands/hs_group.cpp:72 +#, fuzzy +msgid "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." +msgstr "" +"Syntax: GROUP\n" +"\n" +"This command allows users to set the vhost of thier\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." + +#: modules/commands/ns_register.cpp:299 +msgid "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." +msgstr "" + +#: modules/m_rewrite.cpp:145 +#, c-format +msgid "This command is an alias to the command %s." +msgstr "" + +#: modules/commands/ns_register.cpp:95 +#, fuzzy +msgid "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." +msgstr "" +"Syntax: CONFIRM passcode\n" +"\n" +"This is the second step of nickname registration process.\n" +"You must perform this command in order to get your nickname\n" +"registered with %s. The passcode (or called auth code also)\n" +"is sent to your e-mail address in the first step of the\n" +"registration process. For more information about the first\n" +"stage of the registration process, type: /msg %s HELP REGISTER\n" +"\n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." + +#: modules/commands/os_modinfo.cpp:70 +#, fuzzy +msgid "This command lists information about the specified loaded module." +msgstr "" +"Syntax: MODINFO FileName\n" +"This command lists information about the specified loaded module" + +#: modules/commands/hs_list.cpp:136 +#, fuzzy +msgid "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." +msgstr "" +"Syntax: LIST [|<#X-Y>]\n" +"This command lists registered vhosts to the operator\n" +"if a Key is specified, only entries whos nick or vhost match\n" +"the pattern given in are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries.\n" +"The list uses the value of NSListMax as a hard limit for the\n" +"number of items to display to a operator at any 1 time.\n" +"Limited to Services operators." + +#: modules/commands/os_module.cpp:45 +#, fuzzy +msgid "" +"This command loads the module named modname from the modules\n" +"directory." +msgstr "" +"Syntax: MODLOAD FileName\n" +"This command loads the module named FileName from the modules\n" +"directory." + +#: modules/commands/ns_group.cpp:201 +#, fuzzy +msgid "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." +msgstr "" +"Sintaxis: GROUP grupo clau\n" +"\n" +"Aquesta comanda fa que el teu nickname s'adhereixi al grup de nicknames\n" +"grup. clau es la de teu nickname.\n" +"\n" +"L'unió a un grup et permetra compartir configuracions,\n" +"memos, i privilegis en canals amb tots els nicknames en un\n" +"grup, i molt més!\n" +" \n" +"Un grup existeix sempre i quant sigui servible. Això\n" +"significa que si un nick del grup es eliminat, no perdràs\n" +"les caracteristiques compartides descrites anteriorment, sempre i\n" +"quant al menys un nick quedi al grup.\n" +"\n" +"Pots utilitzar aquesta comanda encara que no estigui registrar el teu\n" +"nick. Si el teu nick ja esta registrat hauras d'identificar-te\n" +"abans d'utilitzar aquesta comanda. Escriu /msg %s HELP\n" +"IDENTIFY per més informació. Potser que no sigui possible\n" +"a la teva xarxa.\n" +"\n" +"Es recomenable utilitzar aquesta comanda amb un nick no registrat ja\n" +"que sera registrat automaticament quant l'utilitzis.\n" +"Pots utilitzar-la amb un nick ja registrat (per canviar de grup) \n" +"sols si els administradors de la teva xarxa ho permeten.\n" +"\n" +"Pots estar en un sol grup a la vegada. L'unió de\n" +"grups no es possible.\n" +"\n" +"Tingues en compte: tots els nicks en un grup comparteixen la\n" +"mateixa clau." + +#: modules/commands/ns_ajoin.cpp:292 +msgid "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." +msgstr "" + +#: modules/commands/ns_set.cpp:345 modules/commands/ns_set.cpp:669 +msgid "" +"This command may not be used on this network because nickname ownership is " +"disabled." +msgstr "" + +#: modules/commands/os_module.cpp:118 +#, fuzzy +msgid "This command reloads the module named modname." +msgstr "" +"Syntax: MODLOAD FileName\n" +"This command loads the module named FileName from the modules\n" +"directory." + +#: modules/commands/hs_request.cpp:344 +msgid "This command retrieves the vhost requests." +msgstr "" + +#: modules/commands/os_logsearch.cpp:159 +msgid "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." +msgstr "" + +#: modules/commands/cs_status.cpp:106 +msgid "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." +msgstr "" + +#: modules/commands/ns_group.cpp:285 +#, fuzzy +msgid "" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." +msgstr "" +"Syntax: UNGROUP [nick]\n" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, url, and icq. Everything\n" +"else is reset. You may not ungroup yourself if there is only one\n" +"nick in your group." + +#: modules/commands/os_module.cpp:168 +#, fuzzy +msgid "This command unloads the module named modname." +msgstr "" +"Syntax: MODLOAD FileName\n" +"This command loads the module named FileName from the modules\n" +"directory." + +#: modules/commands/ns_register.cpp:353 +msgid "This command will resend you the registration confirmation email." +msgstr "" + +#: include/language.h:90 +#, c-format +msgid "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" +msgstr "" + +#: modules/commands/os_forbid.cpp:469 +#, fuzzy, c-format +msgid "This nickname has been forbidden: %s" +msgstr "This nickname is currently suspended, reason: %s" + +#: modules/commands/ns_recover.cpp:99 +#, fuzzy, c-format +msgid "This nickname has been recovered by %s." +msgstr "This nickname is currently suspended, reason: %s" + +#: modules/commands/ns_recover.cpp:77 +#, c-format +msgid "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." +msgstr "" + +#: include/language.h:95 +#, fuzzy +msgid "This nickname has been registered; you may not use it." +msgstr "Aquest canal ha estat registrat amb %s." + +#: modules/commands/ns_suspend.cpp:246 +#, fuzzy +msgid "This nickname is suspended." +msgstr "Aquest canal esta prohibit." + +#: include/language.h:92 +#, c-format +msgid "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." +msgstr "" + +#: modules/commands/ms_read.cpp:95 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %d" +msgstr "Memo %d de %s (%s). per a esborrar-lo escriu: /msg %s DEL %s %d" + +#: modules/commands/ms_read.cpp:93 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %s %d" +msgstr "Memo %d de %s (%s). per a esborrar-lo escriu: /msg %s DEL %s %d" + +#: modules/commands/bs_kick.cpp:791 +msgid "To protect ops against bot kicks" +msgstr "" + +#: modules/commands/bs_kick.cpp:856 +msgid "To protect voices against bot kicks" +msgstr "" + +#: modules/commands/cs_list.cpp:46 +msgid "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." +msgstr "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." + +#: modules/commands/os_logsearch.cpp:139 +#, fuzzy, c-format +msgid "Too many results for %s." +msgstr "Lllista d'accés per %s:" + +#: modules/extra/stats/cs_fantasy_top.cpp:149 +#, c-format +msgid "Top %i of %s" +msgstr "" + +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Topic" +msgstr "Lock de tòpic" + +#: modules/commands/cs_topic.cpp:258 +#, fuzzy +msgid "Topic lock" +msgstr "Lock de tòpic" + +#: modules/commands/cs_topic.cpp:114 +#, fuzzy, c-format +msgid "Topic lock option for %s is now off." +msgstr "Topic lock option for %s is now ON." + +#: modules/commands/cs_topic.cpp:97 +#, fuzzy, c-format +msgid "Topic lock option for %s is now on." +msgstr "Topic lock option for %s is now ON." + +#: modules/commands/cs_topic.cpp:256 +#, fuzzy +msgid "Topic retention" +msgstr "Retenció de tòpic" + +#: modules/commands/cs_topic.cpp:60 +#, fuzzy, c-format +msgid "Topic retention option for %s is now off." +msgstr "Topic retention option for %s is now ON." + +#: modules/commands/cs_topic.cpp:54 +#, fuzzy, c-format +msgid "Topic retention option for %s is now on." +msgstr "Topic retention option for %s is now ON." + +#: modules/commands/cs_topic.cpp:265 +msgid "Topic set by" +msgstr "" + +#: modules/commands/bs_kick.cpp:1323 +msgid "Turn caps lock OFF!" +msgstr "Desactiva les majuscules!" + +#: modules/extra/stats/m_chanstats.cpp:17 +#: modules/extra/stats/m_chanstats.cpp:71 +#, fuzzy +msgid "Turn chanstats statistics on or off" +msgstr " SECURE Activa o desactiva la seguretat de nickname" + +#: modules/commands/ns_set.cpp:1009 +#, fuzzy +msgid "Turn nickname security on or off" +msgstr " SECURE Activa o desactiva la seguretat de nickname" + +#: modules/commands/ns_set.cpp:655 +#, fuzzy +msgid "Turn protection on or off" +msgstr " KILL Activa o desactiva la protecció" + +#: modules/commands/ns_list.cpp:264 +#, fuzzy, c-format +msgid "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Syntax: SASET nickname PRIVATE {ON | OFF}\n" +"\n" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" + +#: modules/commands/ns_list.cpp:236 +#, fuzzy, c-format +msgid "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Sintaxis: SET PRIVATE {ON | OFF}\n" +"\n" +"Fa que %s activi o desactivi l'opció de privacitat del teu\n" +"nick. Amb PRIVATE establert,el teu nickname no apareixera en les\n" +"llistes de nicknames generades amb la comanda LIST de %s.\n" +"(D'altra banda, qualsevol persona que sapigue el teu nick podra comprobar\n" +"la teva informació utilitzant la comanda INFO.)" + +#: modules/commands/ns_set.cpp:1059 modules/commands/ns_set.cpp:1088 +#, fuzzy, c-format +msgid "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." +msgstr "" +"Sintaxis: SET SECURE {ON | OFF}\n" +"\n" +"Canvia les caracteristiques de seguretat de %s pel teu nick a on\n" +"u off. Amb SECURE establert, has d'especificar la teva clau \n" +"per ser reconegut com propietari del nick, a pesar de que la teva adreça\n" +"estigui a la llista d'accéss. D'altra banda, si estas a la llista \n" +"d'accés, %s no te auto-kickejara no important l'establiment de l'opció\n" +"KILL." + +#: modules/extra/stats/m_chanstats.cpp:142 +#, fuzzy +msgid "Turns chanstats channel statistics ON or OFF for this user." +msgstr " SECURE Activa o desactiva la seguretat de nickname" + +#: modules/extra/stats/m_chanstats.cpp:61 +#: modules/extra/stats/m_chanstats.cpp:119 +#, fuzzy +msgid "Turns chanstats statistics ON or OFF." +msgstr " SECURE Activa o desactiva la seguretat de nickname" + +#: modules/commands/ns_set.cpp:772 +#, fuzzy, c-format +msgid "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Syntax: SASET nickname KILL {ON | QUICK | IMMED | OFF}\n" +"\n" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +"\n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." + +#: modules/commands/ns_set.cpp:738 +#, fuzzy, c-format +msgid "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Sintaxis: SET KILL {ON | QUICK | IMMED | OFF}\n" +"\n" +"Canvia la protecció automàtica del teu nick a on o off.\n" +"Amb protecció on, si un altre usuari intenta utilitzar el teu nick,\n" +"tindra un minut per canviar de nick, desprès del qual\n" +"%s canviara el seu nick automaticament.\n" +"\n" +"Si estableixes QUICK, l'usuari tibdrà nomès 20 segons\n" +"per canviar el nick en comptes dels 60 habituals. Si selecciones\n" +"IMMED, el nick del usuari sera canviat automaticament\n" +"sense ser avisat ni donar-li oportunitat de canviar-lo abans;\n" +"per favor no utilitzis aquesta opció excepte que ho consideris\n" +"necessari. A mes, els administradors de la xarxa poden haber\n" +"deshabilitat aquesta opció." + +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_forbid.cpp:358 +msgid "Type" +msgstr "" + +#: modules/commands/ns_set.cpp:62 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Escriu /msg %s HELP opció per més informació\n" +"sobre una opció en particular." + +#: modules/commands/bs_kick.cpp:151 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." +msgstr "" +"Type /msg %s HELP SASET option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname. " + +#: modules/commands/ns_set.cpp:107 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." +msgstr "" +"Type /msg %s HELP SASET option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname. " + +#: modules/commands/bs_set.cpp:62 modules/commands/cs_set.cpp:63 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." +msgstr "" +"Escriu /msg %s HELP opció per més informació\n" +"sobre una opció en particular." + +#: modules/pseudoclients/nickserv.cpp:361 +#, fuzzy, c-format +msgid "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." +msgstr "" +"Escriu /msg %s SET EMAIL e-mail per provar el teu e-mail.\n" +"Respectems la teva privacitat; Aquest e-mail no sera entregat\n" +"a cap persona." + +#: modules/commands/os_module.cpp:128 +#, fuzzy +msgid "Un-Load a module" +msgstr " MODUNLOAD Un-Load a module" + +#: modules/commands/os_sxline.cpp:337 modules/commands/os_sxline.cpp:552 +#: modules/commands/os_akill.cpp:136 +#, fuzzy, c-format +msgid "Unable to find regex engine %s." +msgstr "Unable to remove module %s" + +#: modules/commands/os_module.cpp:36 modules/commands/os_module.cpp:108 +#, fuzzy, c-format +msgid "Unable to load module %s." +msgstr "Unable to load module %s" + +#: modules/commands/os_module.cpp:73 modules/commands/os_module.cpp:90 +#: modules/commands/os_module.cpp:145 modules/commands/os_module.cpp:159 +#, fuzzy, c-format +msgid "Unable to remove module %s." +msgstr "Unable to remove module %s" + +#: modules/commands/bs_assign.cpp:90 +#, fuzzy +msgid "Unassigns a bot from a channel" +msgstr "UNASSIGN Unassigns a bot from a channel" + +#: modules/commands/bs_assign.cpp:139 +#, fuzzy +msgid "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." +msgstr "" +"Sintàxi: UNASSIGN canal\n" +"\n" +"Desassigna un bot d'un canal. A l'utilitzar aquesta comanda\n" +"el bot ja no entrara al canal. De totes maneres, la configuració\n" +"del bot pel canal es enmagatzemada, així et sera possible\n" +"reassignar un bot sense haver de configurar-lo de nou." + +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1193 +#: modules/commands/bs_kick.cpp:1196 +#, fuzzy +msgid "Underlines kicker" +msgstr " Kicker per subrallats : %s" + +#: modules/commands/os_dns.cpp:595 +#, fuzzy +msgid "Unknown SET option." +msgstr "Unknown SASET option %s." + +#: modules/commands/os_stats.cpp:229 +#, fuzzy, c-format +msgid "Unknown STATS option: %s" +msgstr "Opció STATS %s desconeguda." + +#: src/command.cpp:222 src/command.cpp:233 +#, fuzzy, c-format +msgid "Unknown command %s." +msgstr "Opció %s desconeguda." + +#: src/command.cpp:220 src/command.cpp:231 +#, fuzzy, c-format +msgid "Unknown command %s. \"%s%s HELP\" for help." +msgstr "Comanda no coneguda %s. \"%s%s HELP\" per ajuda." + +#: modules/commands/cs_mode.cpp:317 modules/commands/cs_mode.cpp:409 +#, fuzzy, c-format +msgid "Unknown mode character %c ignored." +msgstr "Caràcter de Mode %c desconegut i ignorat." + +#: modules/commands/os_logsearch.cpp:78 +#, fuzzy, c-format +msgid "Unknown parameter: %s" +msgstr "SET Opció estabilment" + +#: modules/commands/os_dns.cpp:241 +msgid "Unpooled" +msgstr "" + +#: modules/commands/cs_drop.cpp:77 +#, fuzzy +msgid "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." +msgstr "" +"Sintaxis: DROP canal\n" +"\n" +"Desenregistra el canal especificat. Nomès pot ser utilitzat pel\n" +"fundador del canal." + +#: modules/commands/cs_drop.cpp:74 +#, fuzzy +msgid "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." +msgstr "" +"Sintàxi: DROP canal\n" +"\n" +"Desregistra el canal donat. Només\n" +"administradors de serveis poden eliminar un\n" +"canal per el qual no s'haguin identificado." + +#: modules/commands/ns_suspend.cpp:160 +#, fuzzy +msgid "Unsuspend a given nick" +msgstr " UNSUSPEND Unsuspend a given nick" + +#: modules/commands/ns_suspend.cpp:199 +msgid "Unsuspends a nickname which allows it to be used again." +msgstr "" + +#: modules/commands/cs_updown.cpp:126 +msgid "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." +msgstr "" + +#: modules/commands/cs_updown.cpp:48 +#, fuzzy +msgid "Updates a selected nicks status on a channel" +msgstr " BAN Bans a selected nick on a channel" + +#: modules/commands/ns_update.cpp:19 +#, fuzzy +msgid "Updates your current status, i.e. it checks for new memos" +msgstr "" +" UPDATE Updates your current status, i.e. it checks for new memos" + +#: modules/commands/ns_update.cpp:43 +#, fuzzy +msgid "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." +msgstr "" +"Syntax: UPDATE\n" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed chanmodes (ModeonID) and updates your vhost and\n" +"your userflags (lastseentime, etc)." + +#: modules/commands/os_update.cpp:25 +msgid "Updating databases." +msgstr "Actualitzant les bases de dades." + +#: modules/commands/os_stats.cpp:154 +#, c-format +msgid "Uplink capab: %s" +msgstr "Uplink capab: %s" + +#: modules/commands/os_stats.cpp:153 +#, c-format +msgid "Uplink server: %s" +msgstr "Uplink server: %s" + +#: modules/commands/help.cpp:127 +#, c-format +msgid "Use the %s ALL command to list all commands and their descriptions." +msgstr "" + +#: modules/commands/bs_info.cpp:59 +msgid "Used on" +msgstr "" + +#: data/chanserv.example.conf:821 +#, fuzzy +msgid "Used to manage channels" +msgstr "%s changed your usermodes." + +#: data/chanserv.example.conf:809 +#, fuzzy +msgid "Used to manage the list of privileged users" +msgstr " ACCESS Modifica la llista d'usuaris privilegiats" + +#: data/chanserv.example.conf:815 +msgid "Used to modify the channel status of you or other users" +msgstr "" + +#: modules/commands/cs_akick.cpp:575 +#, fuzzy +msgid "User has been banned from the channel" +msgstr "Has estat desbanegat de %s." + +#: modules/commands/os_dns.cpp:587 +#, fuzzy, c-format +msgid "User limit for %s removed." +msgstr "vhost for %s removed." + +#: modules/commands/os_dns.cpp:585 +#, fuzzy, c-format +msgid "User limit for %s set to %d." +msgstr "Límite de memos per a %s establert a %d." + +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Users" +msgstr "Llista de bots:" + +#: modules/commands/os_stats.cpp:172 +#, c-format +msgid "Users (nick): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:177 +#, c-format +msgid "Users (uid): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_list.cpp:184 +#, fuzzy +msgid "Users list:" +msgstr "Llista de bots:" + +#: modules/commands/ns_info.cpp:105 modules/commands/ns_info.cpp:107 +msgid "VHost" +msgstr "" + +#: modules/commands/hs_set.cpp:92 +#, fuzzy, c-format +msgid "VHost for %s set to %s." +msgstr "vhost for %s set to %s." + +#: modules/commands/hs_set.cpp:90 +#, fuzzy, c-format +msgid "VHost for %s set to %s@%s." +msgstr "vhost for %s set to %s@%s." + +#: modules/commands/hs_set.cpp:199 +#, fuzzy, c-format +msgid "VHost for group %s set to %s." +msgstr "vhost for group %s set to %s." + +#: modules/commands/hs_set.cpp:197 +#, fuzzy, c-format +msgid "VHost for group %s set to %s@%s." +msgstr "vhost for group %s set to %s@%s." + +#: modules/commands/os_session.cpp:247 +msgid "VIEW host" +msgstr "" + +#: modules/commands/os_sxline.cpp:428 modules/commands/os_sxline.cpp:662 +#: modules/commands/os_akill.cpp:389 +#, fuzzy +msgid "VIEW [mask | list | id]" +msgstr "LIST [canal] [llista | NEW]" + +#: modules/commands/os_session.cpp:526 +msgid "VIEW [mask | list]" +msgstr "" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +msgid "Value" +msgstr "" + +#: modules/commands/os_config.cpp:48 +#, fuzzy, c-format +msgid "Value of %s:%s changed to %s" +msgstr "El Fundador de %s cambiat a %s." + +#: modules/commands/hs_list.cpp:58 modules/commands/hs_request.cpp:305 +msgid "Vhost" +msgstr "" + +#: modules/commands/hs_del.cpp:38 +#, fuzzy, c-format +msgid "Vhost for %s removed." +msgstr "vhost for %s removed." + +#: modules/commands/os_oper.cpp:69 +#, fuzzy +msgid "View and change Services Operators" +msgstr "%s is a services operator of type %s." + +#: modules/commands/os_config.cpp:19 +msgid "View and change configuration file settings" +msgstr "" + +#: modules/commands/os_session.cpp:245 +#, fuzzy +msgid "View the list of host sessions" +msgstr " SESSION Mostra la llista de sessions de host" + +#: modules/commands/bs_kick.cpp:1221 +msgid "Voices protection" +msgstr "Protecció de Voices" + +#: modules/commands/bs_kick.cpp:1406 +msgid "Watch your language!" +msgstr "Cuida el teu llenguatge!" + +#: modules/commands/cs_list.cpp:237 +#, c-format +msgid "" +"When private is set, the channel will not appear in\n" +"%s's %s command." +msgstr "" + +#: modules/commands/ms_info.cpp:204 +#, fuzzy +msgid "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." +msgstr "" +"Sintàxi: INFO [nick | canal]\n" +"\n" +"Sense un paràmetro, mostra informació del nombre\n" +"de memos que tens, quants d' ells encara no s'han\n" +"llegit, i el nombre total de memos que pots rebre.\n" +"\n" +"amb un canal de paràmetre, mostra la mateixa informació\n" +"pel canal donat.\n" +"\n" +"amb un nickname de paràmetr, mostra la misma\n" +"informació pel nickname donat. Aquest us està\n" +"limitat a administradors de serveis." + +#: modules/commands/ns_logout.cpp:66 +#, fuzzy +msgid "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." +msgstr "" +"Sintaxis: LOGOUT [nickname [REVALIDATE]]\n" +"\n" +"Sense un parametre, desfà l'efecte de la comanda IDENTIFY, \n" +"és a dir, fa que no siguis reconegut com l'autentic propietari del nick\n" +"Tingues en compte, que no seras necessari tornar-te a identificar.\n" +"\n" +"Amb un parametre, fa lo mateix pel nick donat. Si\n" +"a més a més especifiques REVALIDATE, els serveis requeriran\n" +"a l'esmentat nick a reidentificar-se. Aquest ús esta limitat a\n" +"administradors de serveis." + +#: modules/commands/os_stats.cpp:236 +#, fuzzy +msgid "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." +msgstr "" +"Sintàxi: STATS [AKILL | ALL | RESET]\n" +"\n" +"Sense una opció, mostra el nom actual d'usuaris i\n" +"IRCops en linea (excluient els serveis), el màxim\n" +"nombre d'usuaris desde que els serveis s'han iniciat, i\n" +"el temps que els serveis han estat funcionant.\n" +"\n" +"Amb L'opció AKILL, mostra la mida actual de la\n" +"llista AKILL i l'actual temps d'expiració per defecte.\n" +"\n" +"L'opció ALL esta sols disponible per administradors de\n" +"serveis, i mostra informació en el us de memòria dels\n" +"serveis. Utilitzar aquesta opció pot congelar els\n" +"serveis per un curt periode de temps en xarxes grans,\n" +"aixi que no es recomana utilitzar sovint.\n" +"\n" +"L'opció RESET estableix el nombre màxim d'usuaris\n" +"al nombre d'usuaris actualment presents en la xarxa." + +#: modules/commands/bs_badwords.cpp:194 +msgid "Word" +msgstr "" + +#: modules/commands/ns_group.cpp:158 +#, c-format +msgid "You are already a member of the group of %s." +msgstr "Ja ets membre del grup de %s." + +#: modules/commands/os_login.cpp:34 modules/commands/ns_identify.cpp:87 +msgid "You are already identified." +msgstr "You are already identified." + +#: modules/commands/cs_invite.cpp:64 +#, fuzzy, c-format +msgid "You are already in %s!" +msgstr "You are already in %s! " + +#: modules/commands/os_set.cpp:91 +#, fuzzy +msgid "You are no longer a super admin." +msgstr "You are no longer a SuperAdmin" + +#: modules/commands/os_login.cpp:81 +#, fuzzy +msgid "You are not identified." +msgstr "You are already identified." + +#: include/language.h:100 +#, fuzzy +msgid "You are not permitted to be on this channel." +msgstr "No estas autoritzat a canviar el teu límit de memos." + +#: modules/commands/ms_set.cpp:158 +msgid "You are not permitted to change your memo limit." +msgstr "No estas autoritzat a canviar el teu límit de memos." + +#: modules/commands/ns_cert.cpp:183 +#, fuzzy +msgid "You are not using a client certificate." +msgstr "You are already identified." + +#: modules/commands/os_set.cpp:85 +#, fuzzy +msgid "You are now a super admin." +msgstr "You are now a SuperAdmin" + +#: modules/commands/os_oline.cpp:36 +msgid "You are now an IRC Operator." +msgstr "You are now an IRC Operator." + +#: modules/commands/ns_resetpass.cpp:108 +#, fuzzy +msgid "You are now identified for your nick. Change your password now." +msgstr "You are now identified for your nick. Change your password now." + +#: modules/commands/ns_group.cpp:64 +#, c-format +msgid "You are now in the group of %s." +msgstr "Ara ets membre en el grup de %s." + +#: modules/pseudoclients/memoserv.cpp:147 +#, fuzzy, c-format +msgid "" +"You are over your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Advertència: Has sobrepassat el màximo numero de memos (%d). Et resultara " +"impossible rebre més memos fins que esborris alguns dels existents." + +#: modules/commands/os_noop.cpp:33 +msgid "You can not NOOP Services." +msgstr "" + +#: modules/commands/cs_access.cpp:672 +msgid "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." +msgstr "" + +#: modules/commands/os_jupe.cpp:34 +#, fuzzy +msgid "You can not jupe an already juped server." +msgstr "You can not jupe your services server or your uplink server." + +#: modules/commands/os_jupe.cpp:32 +#, fuzzy +msgid "You can not jupe your Services' pseudoserver or your uplink server." +msgstr "You can not jupe your services server or your uplink server." + +#: modules/commands/os_module.cpp:80 +#, c-format +msgid "You can not reload this module directly, instead reload %s." +msgstr "" + +#: modules/commands/ms_rsend.cpp:46 +msgid "You can not request a receipt when sending a memo to yourself." +msgstr "You can not request a receipt when sending a memo to yourself." + +#: modules/commands/ns_recover.cpp:163 +#, fuzzy, c-format +msgid "You can't %s yourself!" +msgstr "No pots fer GHOST a tu mateix!" + +#: modules/commands/cs_access.cpp:154 modules/commands/cs_flags.cpp:109 +#: modules/commands/cs_xop.cpp:151 +#, fuzzy +msgid "You can't add a channel to its own access list." +msgstr "No hi ha instàncies que concordin a la llista d'accés de %s ." + +#: modules/commands/ns_logout.cpp:37 +#, fuzzy, c-format +msgid "You can't logout %s, they are a Services Operator." +msgstr "Can't logout %s because he's a services operator." + +#: modules/commands/ns_set.cpp:927 +#, fuzzy, c-format +msgid "You cannot %s on this network." +msgstr "No pots establir la teva adreça e-mail en aquesta xarxa." + +#: modules/commands/cs_flags.cpp:231 +#, fuzzy, c-format +msgid "You cannot set the %c flag." +msgstr "You cannot use this command." + +#: modules/commands/ms_set.cpp:173 +#, c-format +msgid "You cannot set the memo limit for %s higher than %d." +msgstr "No pots establir el límite de memos per %s mes de %d." + +#: modules/commands/ms_set.cpp:175 +#, c-format +msgid "You cannot set your memo limit higher than %d." +msgstr "No pots establir el teu límit de memos a mes de %d." + +#: modules/commands/bs_assign.cpp:124 +#, fuzzy +msgid "You cannot unassign bots while persist is set on the channel." +msgstr "You can not unassign bots while persist is set on the channel." + +#: modules/commands/ns_set.cpp:480 +msgid "You cannot unset the e-mail on this network." +msgstr "No pots establir la teva adreça e-mail en aquesta xarxa." + +#: modules/commands/help.cpp:177 +msgid "You cannot use this command." +msgstr "You cannot use this command." + +#: modules/commands/ms_info.cpp:151 +#, c-format +msgid "You currently have %d memos, of which %d are unread." +msgstr "Tens %d memos, dels quals %d encara no han estat llegits." + +#: modules/commands/ms_info.cpp:149 +#, c-format +msgid "You currently have %d memos, of which 1 is unread." +msgstr "Tens %d memos, dels quals 1 encara no ha estat llegit." + +#: modules/commands/ms_info.cpp:147 +#, c-format +msgid "You currently have %d memos." +msgstr "Tens %d memos." + +#: modules/commands/ms_info.cpp:145 +#, c-format +msgid "You currently have %d memos; all of them are unread." +msgstr "Tens %d memos, cap d'ells llegit." + +#: modules/commands/ms_info.cpp:134 +msgid "You currently have 1 memo, and it has not yet been read." +msgstr "Tens 1 memo i encara no ha estat llegit." + +#: modules/commands/ms_info.cpp:136 +msgid "You currently have 1 memo." +msgstr "Tens 1 memo." + +#: modules/commands/ms_info.cpp:130 +msgid "You currently have no memos." +msgstr "No tens memos." + +#: modules/commands/cs_mode.cpp:564 modules/commands/cs_mode.cpp:621 +#, c-format +msgid "You do not have access to set mode %c." +msgstr "" + +#: modules/commands/cs_mode.cpp:578 modules/commands/cs_mode.cpp:590 +#: modules/commands/cs_mode.cpp:631 +#, c-format +msgid "You do not have the access to change %s's modes." +msgstr "" + +#: modules/commands/cs_seen.cpp:198 +#, c-format +msgid "You found me, %s!" +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:143 +#, c-format +msgid "You have %d new memos." +msgstr "Tens %d memos nous." + +#: modules/pseudoclients/memoserv.cpp:143 +msgid "You have 1 new memo." +msgstr "Tens 1 memo nou." + +#: include/language.h:112 +#, fuzzy, c-format +msgid "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." +msgstr "Escriu /msg %s READ %d per a llegir-lo." + +#: modules/commands/cs_invite.cpp:76 +#, fuzzy, c-format +msgid "You have been invited to %s by %s." +msgstr "You have been invited to %s." + +#: modules/commands/cs_invite.cpp:81 +#, c-format +msgid "You have been invited to %s." +msgstr "You have been invited to %s." + +#: modules/protocol/ratbox.cpp:166 modules/commands/ns_recover.cpp:96 +#, fuzzy, c-format +msgid "You have been logged in as %s." +msgstr "El teu nick ha estat desconnectat." + +#: modules/commands/os_login.cpp:86 +#, fuzzy +msgid "You have been logged out." +msgstr "El teu nick ha estat desconnectat." + +#: modules/commands/cs_unban.cpp:94 +#, c-format +msgid "You have been unbanned from %s." +msgstr "Has estat desbanegat de %s." + +#: modules/commands/cs_unban.cpp:54 +#, fuzzy, c-format +msgid "You have been unbanned from %d channels." +msgstr "Has estat desbanegat de %s." + +#: modules/commands/ms_info.cpp:169 +msgid "You have no limit on the number of memos you may keep." +msgstr "No tens límit en el numero de memos que pots mantenir." + +#: include/language.h:114 +#, fuzzy +msgid "You have no memos." +msgstr "Tens %d memos nous." + +#: include/language.h:117 +#, fuzzy +msgid "You have no new memos." +msgstr "Tens %d memos nous." + +#: modules/pseudoclients/memoserv.cpp:149 +#, fuzzy, c-format +msgid "" +"You have reached your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Advertència: Has assolit el màxim numero de memos (%d). No podras rebre mes " +"memos fins que esborris alguns dels existents." + +#: modules/commands/ns_recover.cpp:117 +#, fuzzy, c-format +msgid "You have regained control of %s." +msgstr "You have been invited to %s." + +#: modules/commands/ns_drop.cpp:66 +#, fuzzy +msgid "You may drop any nick within your group." +msgstr " DELALL Delete the vhost for all nicks in a group" + +#: modules/commands/cs_mode.cpp:322 modules/commands/cs_mode.cpp:414 +#, c-format +msgid "You may not (un)lock mode %c." +msgstr "" + +#: modules/commands/ns_set.cpp:485 +#, fuzzy +msgid "You may not change the e-mail of other Services Operators." +msgstr "No pots establir la teva adreça e-mail en aquesta xarxa." + +#: modules/commands/ns_set.cpp:474 +#, fuzzy +msgid "You may not change the email of an unconfirmed account." +msgstr "No pots establir la teva adreça e-mail en aquesta xarxa." + +#: modules/commands/ns_set.cpp:196 +#, fuzzy +msgid "You may not change the password of other Services Operators." +msgstr "Can't logout %s because he's a services operator." + +#: modules/commands/ns_drop.cpp:45 +#, fuzzy +msgid "You may not drop other Services Operators' nicknames." +msgstr "%s is a services operator of type %s." + +#: modules/commands/ns_getpass.cpp:32 +#, fuzzy +msgid "You may not get the password of other Services Operators." +msgstr "Can't logout %s because he's a services operator." + +#: modules/commands/ns_suspend.cpp:100 +#, fuzzy +msgid "You may not suspend other Services Operators' nicknames." +msgstr "Can't logout %s because he's a services operator." + +#: modules/commands/ns_access.cpp:136 +#, fuzzy +msgid "" +"You may view but not modify the access list of other Services Operators." +msgstr "Can't logout %s because he's a services operator." + +#: modules/commands/ns_cert.cpp:292 +#, fuzzy +msgid "" +"You may view but not modify the certificate list of other Services Operators." +msgstr "Can't logout %s because he's a services operator." + +#: modules/commands/cs_seen.cpp:287 +#, c-format +msgid "You might see yourself in the mirror, %s." +msgstr "" + +#: include/language.h:120 +msgid "You must assign a bot to the channel before using this command." +msgstr "" + +#: modules/commands/cs_register.cpp:49 +msgid "You must be a channel operator to register the channel." +msgstr "Has de ser un operador de canal per registrar el canal." + +#: modules/commands/cs_updown.cpp:94 modules/commands/cs_updown.cpp:192 +#, fuzzy, c-format +msgid "You must be in %s to use this command." +msgstr "You need to be identified to use this command." + +#: modules/commands/cs_register.cpp:37 +#, fuzzy +msgid "You must confirm your account before you can register a channel." +msgstr "Has de ser un operador de canal per registrar el canal." + +#: modules/commands/hs_request.cpp:100 +#, fuzzy +msgid "You must confirm your account before you may request a vhost." +msgstr "Has de ser un operador de canal per registrar el canal." + +#: modules/commands/ms_send.cpp:44 +#, fuzzy +msgid "You must confirm your account before you may send a memo." +msgstr "Has de ser un operador de canal per registrar el canal." + +#: modules/commands/cs_drop.cpp:42 +#, c-format +msgid "" +"You must enter the channel name twice as a confirmation that you wish to drop" +" %s." +msgstr "" + +#: modules/commands/ns_register.cpp:153 +#, c-format +msgid "You must have been using this nick for at least %d seconds to register." +msgstr "You have to be connected longer than %d seconds to register your nick." + +#: modules/commands/cs_mode.cpp:913 +#, fuzzy, c-format +msgid "You must have the %s(ME) privilege on the channel to use this command." +msgstr "You need to be identified to use this command." + +#: modules/pseudoclients/nickserv.cpp:358 +msgid "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." +msgstr "" +"Ara has de proveir un e-mail pel teu nick.\n" +"Aquest e-mail et permetra recuperar la teva clau en\n" +"cas de que la olvidis." + +#: modules/commands/help.cpp:172 +msgid "You need to be identified to use this command." +msgstr "You need to be identified to use this command." + +#: modules/commands/ms_info.cpp:182 +#, fuzzy +msgid "You will be notified by message and by mail when new memos arrive." +msgstr "Seràs notificat quan els memos nous se t'enviin." + +#: modules/commands/ms_info.cpp:175 +#, fuzzy +msgid "" +"You will be notified of new memos at logon and when they arrive, and by mail " +"when they arrive." +msgstr "Seràs notificat per nous memos quant et conectis i quant se t'enviin." + +#: modules/commands/ms_info.cpp:177 +msgid "You will be notified of new memos at logon and when they arrive." +msgstr "Seràs notificat per nous memos quant et conectis i quant se t'enviin." + +#: modules/commands/ms_info.cpp:189 +#, fuzzy +msgid "" +"You will be notified of new memos at logon, and by mail when they arrive." +msgstr "Seràs notificat per nous memos quant et conectis i quant se t'enviin." + +#: modules/commands/ms_info.cpp:191 +msgid "You will be notified of new memos at logon." +msgstr "Seràs notificat per memos nous quant et conectis." + +#: modules/commands/ms_info.cpp:184 +msgid "You will be notified when new memos arrive." +msgstr "Seràs notificat quan els memos nous se t'enviin." + +#: modules/commands/ms_set.cpp:190 +msgid "You will no longer be able to receive memos." +msgstr "No et sera possible rebre més memos." + +#: modules/commands/ms_set.cpp:57 +msgid "You will no longer be informed via email." +msgstr "You will no longer be informed via email." + +#: modules/commands/ms_info.cpp:195 +msgid "You will not be notified of new memos." +msgstr "No seràs notificat per memos nous." + +#: modules/commands/ms_set.cpp:49 +msgid "You will now be informed about new memos via email." +msgstr "You will now be informed about new memos via email." + +#: modules/commands/os_svs.cpp:86 +msgid "Your IRCd does not support SVSJOIN." +msgstr "" + +#: modules/commands/os_svs.cpp:31 +msgid "Your IRCd does not support SVSNICK." +msgstr "" + +#: modules/commands/os_svs.cpp:130 +msgid "Your IRCd does not support SVSPART." +msgstr "" + +#: include/language.h:127 +msgid "" +"Your IRCd does not support vIdent's, if this is incorrect, please report " +"this as a possible bug" +msgstr "" + +#: modules/extra/m_ldap_authentication.cpp:110 +#: modules/extra/m_sql_authentication.cpp:55 +#, fuzzy, c-format +msgid "Your account %s has been successfully created." +msgstr "El bot %s ha estat esborrat." + +#: modules/commands/ns_register.cpp:328 +#, fuzzy +msgid "Your account is already confirmed." +msgstr "You are already identified." + +#: modules/commands/ns_register.cpp:396 +#, fuzzy, c-format +msgid "Your account will expire, if not confirmed, in %s." +msgstr "You are already identified." + +#: modules/commands/ns_set.cpp:1274 +#, fuzzy, c-format +msgid "Your email address has been changed to %s." +msgstr "E-mail address for %s changed to %s." + +#: modules/commands/os_forbid.cpp:544 modules/commands/os_forbid.cpp:553 +#, fuzzy +msgid "Your email address is not allowed, choose a different one." +msgstr "Totes les linees O de %s han estat esborrades." + +#: modules/commands/ns_register.cpp:260 modules/commands/ns_register.cpp:391 +msgid "" +"Your email address is not confirmed. To confirm it, follow the instructions " +"that were emailed to you." +msgstr "" + +#: modules/commands/ns_register.cpp:67 +#, fuzzy, c-format +msgid "Your email address of %s has been confirmed." +msgstr "Totes les linees O de %s han estat esborrades." + +#: modules/extra/m_ldap_authentication.cpp:159 +#, fuzzy, c-format +msgid "Your email has been updated to %s" +msgstr "E-mail address for %s changed to %s." + +#: modules/extra/m_sql_authentication.cpp:62 +#, fuzzy, c-format +msgid "Your email has been updated to %s." +msgstr "E-mail address for %s changed to %s." + +#: modules/commands/ms_set.cpp:197 +msgid "Your memo limit has been disabled." +msgstr "El teu límit de memos ha estat deshabilitat." + +#: modules/commands/ms_set.cpp:183 +#, c-format +msgid "Your memo limit has been set to %d." +msgstr "El teu límite de memos ha estat establert a %d." + +#: modules/commands/ms_info.cpp:164 +#, c-format +msgid "Your memo limit is %d, and may not be changed." +msgstr "El teu límit de memos es %d i no pot ser canviat." + +#: modules/commands/ms_info.cpp:166 +#, c-format +msgid "Your memo limit is %d." +msgstr "El teu límit de memos es %d." + +#: modules/commands/ms_info.cpp:159 +msgid "Your memo limit is 0; you will not receive any new memos." +msgstr "El teu límit de memos es 0; no rebràs nous memos." + +#: modules/commands/ms_info.cpp:157 +#, fuzzy +msgid "" +"Your memo limit is 0; you will not receive any new memos. You cannot change " +"this limit." +msgstr "" +"El teu límit de memos es 0; no rebràs nous memos. No pots cambiar aquest " +"límit." + +#: modules/commands/ns_logout.cpp:50 +msgid "Your nick has been logged out." +msgstr "El teu nick ha estat desconnectat." + +#: modules/commands/ns_group.cpp:156 +#, fuzzy +msgid "Your nick is already registered." +msgstr "El teu nick ja esta registrat; escriu /msg %s DROP primer." + +#: modules/commands/ns_group.cpp:246 +msgid "Your nick is not grouped to anything, you can't ungroup it." +msgstr "Your nick is not grouped to anything, you can't ungroup it." + +#: include/language.h:77 +#, fuzzy +msgid "Your nick isn't registered." +msgstr "Nickname %s registered." + +#: modules/pseudoclients/nickserv.cpp:254 +#, c-format +msgid "Your nickname is now being changed to %s" +msgstr "El teu nickname s'esta canviant a %s" + +#: modules/commands/os_login.cpp:32 modules/commands/os_login.cpp:79 +msgid "Your oper block doesn't require logging in." +msgstr "" + +#: modules/commands/ns_register.cpp:336 +#, c-format +msgid "Your passcode has been re-sent to %s." +msgstr "Your passcode has been re-sent to %s." + +#: modules/commands/ns_register.cpp:232 +#, c-format +msgid "Your password is %s - remember this for later use." +msgstr "La teva clau es %s - Recordala per un us futur." + +#: include/language.h:76 +#, c-format +msgid "Your password is too long. It must not exceed %u characters." +msgstr "" + +#: modules/commands/ns_resetpass.cpp:96 +msgid "Your password reset request has expired." +msgstr "Your password reset request has expired." + +#: modules/commands/hs_request.cpp:170 +#, fuzzy +msgid "Your vHost has been requested." +msgstr "El bot %s ha estat esborrat." + +#: modules/pseudoclients/hostserv.cpp:64 +#: modules/pseudoclients/hostserv.cpp:103 modules/commands/hs_on.cpp:37 +#, c-format +msgid "Your vhost of %s is now activated." +msgstr "Your vhost of %s is now activated." + +#: modules/pseudoclients/hostserv.cpp:62 +#: modules/pseudoclients/hostserv.cpp:101 modules/commands/hs_on.cpp:35 +#, c-format +msgid "Your vhost of %s@%s is now activated." +msgstr "Your vhost of %s@%s is now activated." + +#: modules/commands/hs_off.cpp:39 +msgid "Your vhost was removed and the normal cloaking restored." +msgstr "Your vhost was removed and the normal cloaking restored." + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Zone" +msgstr "Cap" + +#: modules/commands/os_dns.cpp:290 +#, fuzzy, c-format +msgid "Zone %s already exists." +msgstr "El bot %s ja existeix." + +#: modules/commands/os_dns.cpp:310 modules/commands/os_dns.cpp:352 +#: modules/commands/os_dns.cpp:402 modules/commands/os_dns.cpp:438 +#, fuzzy, c-format +msgid "Zone %s does not exist." +msgstr "El bot %s ja existeix." + +#: modules/commands/os_dns.cpp:332 +#, fuzzy, c-format +msgid "Zone %s removed." +msgstr "vhost for %s removed." + +#: modules/commands/os_defcon.cpp:177 +#, fuzzy +msgid "[1|2|3|4|5]" +msgstr "DEFCON [1|2|3|4|5]" + +#: modules/commands/os_news.cpp:400 +#, c-format +msgid "[Logon News - %s] %s" +msgstr "[Notícies de Logon - %s] %s" + +#: modules/commands/os_news.cpp:402 +#, c-format +msgid "[Oper News - %s] %s" +msgstr "[Notícies de Oper - %s] %s" + +#: modules/commands/os_news.cpp:404 +#, c-format +msgid "[Random News - %s] %s" +msgstr "[Notícies al Atzar - %s] %s" + +#: modules/commands/ns_identify.cpp:66 +#, fuzzy +msgid "[account] password" +msgstr "IDENTIFY clau" + +#: modules/commands/cs_updown.cpp:49 modules/commands/cs_updown.cpp:147 +#, fuzzy +msgid "[channel [nick]]" +msgstr "OP #channel [nick]" + +#: modules/commands/ms_ignore.cpp:20 +#, fuzzy +msgid "[channel] ADD entry" +msgstr "AOP canal {ADD|DEL|LIST|CLEAR} [nick | instància]" + +#: modules/commands/ms_ignore.cpp:21 +#, fuzzy +msgid "[channel] DEL entry" +msgstr "MODE canal Modes" + +#: modules/commands/ms_ignore.cpp:22 +#, fuzzy +msgid "[channel] LIST" +msgstr "DROP canal" + +#: modules/commands/ms_list.cpp:20 +#, fuzzy +msgid "[channel] [list | NEW]" +msgstr "LIST [canal] [llista | NEW]" + +#: modules/extra/stats/cs_fantasy_stats.cpp:40 +#, fuzzy +msgid "[channel] [nick]" +msgstr "OP #channel [nick]" + +#: modules/commands/ms_del.cpp:45 +#, fuzzy +msgid "[channel] {num | list | LAST | ALL}" +msgstr "DEL [canal] {numero | llista | ALL}" + +#: modules/commands/ms_read.cpp:113 +#, fuzzy +msgid "[channel] {num | list | LAST | NEW | ALL}" +msgstr "DEL [canal] {numero | llista | ALL}" + +#: modules/commands/hs_list.cpp:20 +msgid "[key|#X-Y]" +msgstr "" + +#: modules/commands/ms_info.cpp:20 +#, fuzzy +msgid "[nick | channel]" +msgstr "CANCEL {nick | canal}" + +#: modules/commands/ns_group.cpp:237 +#, fuzzy +msgid "[nick]" +msgstr "INFO nick" + +#: modules/commands/ns_logout.cpp:22 +msgid "[nickname [REVALIDATE]]" +msgstr "" + +#: modules/commands/ns_alist.cpp:25 modules/commands/ns_status.cpp:20 +#: modules/commands/ns_info.cpp:20 +#, fuzzy +msgid "[nickname]" +msgstr "CHECK nickname" + +#: modules/commands/ns_set_misc.cpp:96 +msgid "[parameter]" +msgstr "" + +#: modules/commands/os_logsearch.cpp:33 +msgid "[+daysd] [+limitl] pattern" +msgstr "" + +#: modules/commands/os_chankill.cpp:22 +#, fuzzy +msgid "[+expiry] channel reason" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/ns_list.cpp:110 +msgid "[Hostname hidden]" +msgstr "" + +#: modules/commands/ns_list.cpp:112 modules/commands/cs_list.cpp:115 +msgid "[Suspended]" +msgstr "" + +#: modules/commands/ns_list.cpp:114 +msgid "[Unconfirmed]" +msgstr "" + +#: modules/commands/hs_request.cpp:213 +#, fuzzy +msgid "[auto memo] Your requested vHost has been approved." +msgstr "[auto-memo] The memo you sent to %s has been viewed." + +#: modules/commands/hs_request.cpp:267 +#, fuzzy +msgid "[auto memo] Your requested vHost has been rejected." +msgstr "[auto-memo] The memo you sent to %s has been viewed." + +#: modules/commands/hs_request.cpp:265 +#, c-format +msgid "[auto memo] Your requested vHost has been rejected. Reason: %s" +msgstr "" + +#: modules/commands/hs_request.cpp:388 +#, fuzzy, c-format +msgid "[auto memo] vHost %s has been requested by %s." +msgstr "Ultim memo enviat a %s va ser cancel.lat." + +#: modules/commands/os_list.cpp:133 +msgid "[{pattern | channel} [INVISIBLE]]" +msgstr "" + +#: modules/commands/os_list.cpp:20 +msgid "[{pattern | nick} [SECRET]]" +msgstr "" + +#: src/misc.cpp:337 +msgid "day" +msgstr "" + +#: src/misc.cpp:337 +msgid "days" +msgstr "" + +#: include/language.h:88 +#, fuzzy +msgid "does not expire" +msgstr " %s (does not expire)" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d day" +msgstr "expira en %d dia" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d days" +msgstr "expira en %d dies" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minute" +msgstr "expira en %d hora, %d minut" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minutes" +msgstr "expira en %d hora, %d minuts" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minute" +msgstr "expira en %d hores, %d minut" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minutes" +msgstr "expira en %d hores, %d minuts" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minute" +msgstr "expira en %d minuts" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minutes" +msgstr "expira en %d minuts" + +#: src/misc.cpp:375 +#, fuzzy +msgid "expires momentarily" +msgstr "expira en %d dia" + +#: src/misc.cpp:343 +msgid "hour" +msgstr "" + +#: src/misc.cpp:343 +msgid "hours" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:150 +#, c-format +msgid "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:349 +msgid "minute" +msgstr "" + +#: src/misc.cpp:349 +msgid "minutes" +msgstr "" + +#: modules/commands/bs_info.cpp:87 +msgid "not assigned yet" +msgstr "" + +#: src/misc.cpp:324 +msgid "second" +msgstr "" + +#: src/misc.cpp:324 +#, fuzzy +msgid "seconds" +msgstr "%s commands:" + +#: modules/commands/hs_request.cpp:215 +#, fuzzy, c-format +msgid "vHost for %s has been activated." +msgstr "Your vhost of %s is now activated." + +#: modules/commands/hs_request.cpp:272 +#, fuzzy, c-format +msgid "vHost for %s has been rejected." +msgstr "El bot %s ha estat esborrat." + +#: modules/commands/hs_request.cpp:79 +msgid "vhost" +msgstr "" + +#: modules/commands/hs_del.cpp:83 +#, c-format +msgid "vhosts for group %s have been removed." +msgstr "vhosts for group %s have been removed." + +#: src/misc.cpp:331 +msgid "year" +msgstr "" + +#: src/misc.cpp:331 +msgid "years" +msgstr "" + +#: modules/commands/os_config.cpp:20 +msgid "{MODIFY|VIEW} [block name item name item value]" +msgstr "" + +#: modules/commands/bs_info.cpp:41 +#, fuzzy +msgid "{channel | nickname}" +msgstr "UNBAN canal [nick]" + +#: modules/commands/ms_cancel.cpp:20 +#, fuzzy +msgid "{nick | channel}" +msgstr "CANCEL {nick | canal}" + +#: modules/commands/ms_rsend.cpp:25 modules/commands/ms_send.cpp:25 +#, fuzzy +msgid "{nick | channel} memo-text" +msgstr "SEND {nick | canal} text" diff --git a/language/anope.de_DE.po b/language/anope.de_DE.po new file mode 100644 index 0000000..4b85b15 --- /dev/null +++ b/language/anope.de_DE.po @@ -0,0 +1,11638 @@ +# Anope IRC Services language file +# Copyright (C) 2011 +# This file is distributed under the same license as the Anope IRC Services package. +# Adam , 2011. +# +msgid "" +msgstr "" +"Project-Id-Version: Anope\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2020-01-06 18:19+0100\n" +"PO-Revision-Date: 2013-06-30 13:05+0100\n" +"Last-Translator: DukePyrolator \n" +"Language-Team: German\n" +"Language: de_DE\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" +"X-Generator: Poedit 1.5.5\n" + +#: modules/commands/os_forbid.cpp:324 +#, c-format +msgid "%d channel(s) cleared, and %d channel(s) dropped." +msgstr "" + +#: modules/commands/os_forbid.cpp:265 +#, fuzzy, c-format +msgid "%d nickname(s) dropped." +msgstr "Die Registrierung Deines Nicknamens wurde gelöscht." + +#: modules/commands/cs_xop.cpp:219 +#, c-format +msgid "%s added to %s %s list." +msgstr "%s wurde zur %s %s-Liste hinzugefügt." + +#: modules/commands/cs_access.cpp:225 +#, c-format +msgid "%s added to %s access list at level %d." +msgstr "%s wurde zur Access-Liste von %s hinzugefügt mit Level %d." + +#: modules/commands/cs_access.cpp:223 +#, fuzzy, c-format +msgid "%s added to %s access list at privilege %s (level %d)" +msgstr "%s wurde zur Access-Liste von %s hinzugefügt mit Level %d." + +#: modules/commands/cs_akick.cpp:190 +#, c-format +msgid "%s added to %s autokick list." +msgstr "%s wurde der AutoKick-Liste von %s hinzugefügt." + +#: modules/commands/bs_badwords.cpp:307 +#, c-format +msgid "%s added to %s bad words list." +msgstr "%s zur Bad Words-Liste von %s hinzugefügt." + +#: modules/commands/ns_access.cpp:45 +#, c-format +msgid "%s added to %s's access list." +msgstr "%s wurde zu %s' Access-Liste hinzugefügt." + +#: modules/commands/ns_cert.cpp:204 +#, fuzzy, c-format +msgid "%s added to %s's certificate list." +msgstr "%s wurde zu Deiner Zertifikat-Liste hinzugefügt." + +#: modules/commands/ms_ignore.cpp:62 +#, fuzzy, c-format +msgid "%s added to ignore list." +msgstr "%s wurde zu Deiner Ignore-Liste hinzugefügt." + +#: modules/commands/os_sxline.cpp:415 modules/commands/os_sxline.cpp:649 +#, c-format +msgid "%s added to the %s list." +msgstr "%s wurde zur %s-Liste hinzugefügt." + +#: modules/commands/os_akill.cpp:203 +#, c-format +msgid "%s added to the AKILL list." +msgstr "%s wurde zur AKILL-Liste hinzugefügt." + +#: modules/pseudoclients/botserv.cpp:134 +#, fuzzy, c-format +msgid "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands " +"that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" +msgstr "" +"%s erlaubt es \"fantasy\" Befehle im Channel auszuführen.\n" +"Fantasy Befehle sind an bestehende Befehle gebunden, normalerweise an %s,\n" +"und bieten eine bequemere Möglichkeit Befehle auszuführen. Befehle welche\n" +"einen Channel als Parameter benötigen erhalten diesen Parameter " +"automatisch.\n" + +#: modules/pseudoclients/botserv.cpp:148 +#, fuzzy, c-format +msgid "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s erlaubt Dir, Bots in Räume einzubringen.\n" +"Geschaffen wurde er für User, die selbst keinen Bot\n" +"hosten können, oder auch Netzwerke, die Bots verbieten.\n" +"Mögliche Befehle sind unten aufgelistet. Die Syntax ist\n" +"%s%s Befehl. Für weitergehende Informationen zu\n" +"einem bestimmten Befehl tippe %s%s %s Befehl" + +#: modules/pseudoclients/nickserv.cpp:466 +#, fuzzy, c-format +msgid "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"Mit %s kannst Du einen Nicknamen \"registrieren\" und somit\n" +"verhindern, dass andere ihn nutzen. Die folgenden Befehle\n" +"erlauben die Registrierung und das Ändern der Einstellungen\n" +"registrierter Nicknamen. Um sie zu benutzen, tippe\n" +"%s%s Befehl. Für weitergehende Informationen zu\n" +"einem bestimmten Befehl, tippe %s%s %s Befehl." + +#: modules/pseudoclients/nickserv.cpp:473 +#, fuzzy, c-format +msgid "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"Mit %s kannst Du einen Nicknamen \"registrieren\" und somit\n" +"verhindern, dass andere ihn nutzen. Die folgenden Befehle\n" +"erlauben die Registrierung und das Ändern der Einstellungen\n" +"registrierter Nicknamen. Um sie zu benutzen, tippe\n" +"%s%s Befehl. Für weitergehende Informationen zu\n" +"einem bestimmten Befehl, tippe %s%s %s Befehl." + +#: modules/pseudoclients/chanserv.cpp:255 +#, fuzzy, c-format +msgid "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" +msgstr "" +"Mit Hilfe von %s kann man Räume registrieren und\n" +"eine Vielzahl von Kontrolloptionen einstellen. %s kann\n" +"zum Beispiel das \"Takeover\" von Räumen verhindern,\n" +"indem man die Channel-Op Privilegien auf bestimmte registrierte \n" +"Nicknamen begrenzt. Verfügbare Befehle sind unten aufgelistet.\n" +"Um sie zu benutzen tippe %s%s Befehl. Für weitere \n" +"Informationen zu einem bestimmten Befehl, tippe:\n" +"%s%s HELP Befehl." + +#: modules/commands/bs_badwords.cpp:298 +#, c-format +msgid "%s already exists in %s bad words list." +msgstr "%s existiert bereits in der BadWord-Liste von %s." + +#: modules/commands/cs_akick.cpp:170 +#, c-format +msgid "%s already exists on %s autokick list." +msgstr "%s existiert bereits auf der AutoKick-Liste von %s." + +#: modules/commands/os_session.cpp:361 +#, c-format +msgid "%s already exists on the EXCEPTION list." +msgstr "%s ist bereits in der EXCEPTION-Liste." + +#: modules/commands/bs_kick.cpp:214 modules/commands/bs_kick.cpp:389 +#: modules/commands/bs_kick.cpp:520 modules/commands/bs_kick.cpp:651 +#, c-format +msgid "%s cannot be taken as times to ban." +msgstr "%s ist eine ungültige Ban-Zeit." + +#: modules/commands/os_mode.cpp:163 +#, c-format +msgid "%s changed your usermodes to %s." +msgstr "%s hat Deine Usermodi zu %s geändert." + +#: modules/commands/os_list.cpp:47 +#, c-format +msgid "%s channel list:" +msgstr "%s Raum-Liste:" + +#: modules/commands/cs_xop.cpp:343 +#, c-format +msgid "%s deleted from %s %s list." +msgstr "%s wurde von der %s %s-Liste entfernt." + +#: modules/commands/cs_access.cpp:326 +#, c-format +msgid "%s deleted from %s access list." +msgstr "%s wurde von der Access-Liste von %s entfernt." + +#: modules/commands/cs_akick.cpp:276 +#, c-format +msgid "%s deleted from %s autokick list." +msgstr "%s wurde von der Autokick-Liste von %s entfernt." + +#: modules/commands/bs_badwords.cpp:348 +#, c-format +msgid "%s deleted from %s bad words list." +msgstr "%s wurde aus der Bad Words-Liste von %s entfernt." + +#: modules/commands/ns_access.cpp:72 +#, c-format +msgid "%s deleted from %s's access list." +msgstr "%s wurde von der Access-Liste von %s entfernt." + +#: modules/commands/ns_cert.cpp:233 +#, fuzzy, c-format +msgid "%s deleted from %s's certificate list." +msgstr "%s wurde von Deiner Zertifikat-Liste entfernt." + +#: modules/commands/os_session.cpp:414 +#, c-format +msgid "%s deleted from session-limit exception list." +msgstr "" +"%s wurde von der Liste der Verbindungseinschränkungen \n" +"entfernt." + +#: modules/commands/os_sxline.cpp:99 +#, c-format +msgid "%s deleted from the %s list." +msgstr "%s wurde von der %s Liste entfernt." + +#: modules/commands/os_akill.cpp:246 +#, c-format +msgid "%s deleted from the AKILL list." +msgstr "%s wurde von der AKILL-Liste entfernt." + +#: modules/commands/cs_access.cpp:685 +#, c-format +msgid "%s disabled on channel %s." +msgstr "%s wurde deaktiviert im Raum %s." + +#: modules/commands/cs_invite.cpp:75 +#, c-format +msgid "%s has been invited to %s." +msgstr "%s wurde nach %s eingeladen." + +#: modules/commands/os_svs.cpp:104 +#, fuzzy, c-format +msgid "%s has been joined to %s." +msgstr "%s wurde nach %s eingeladen." + +#: modules/commands/os_svs.cpp:152 +#, fuzzy, c-format +msgid "%s has been parted from %s." +msgstr "Der Ban von %s wurde aus %s entfernt." + +#: modules/commands/cs_unban.cpp:96 +#, c-format +msgid "%s has been unbanned from %s." +msgstr "Der Bann von %s wurde aus %s entfernt." + +#: modules/commands/ns_alist.cpp:110 +#, fuzzy, c-format +msgid "%s has no access in any channels." +msgstr "%s befindet sich nicht im Raum %s." + +#: modules/commands/cs_status.cpp:55 +#, fuzzy, c-format +msgid "%s has no access on %s." +msgstr "%s wurde nach %s eingeladen." + +#: modules/commands/cs_set.cpp:307 +#, c-format +msgid "%s has too many channels registered." +msgstr "%s hat zu viele Räume auf seinen Nicknamen registriert." + +#: modules/commands/cs_status.cpp:51 +#, fuzzy, c-format +msgid "%s is a super administrator." +msgstr "%s ist ein services operator vom Typ %s." + +#: modules/pseudoclients/memoserv.cpp:214 +#, c-format +msgid "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" +msgstr "" +"%s ist eine Einrichtung, die es erlaubt, \n" +"dass sich IRC User untereinander kurze Textnachrichten \n" +"senden, egal ob die Empfänger zu dem Zeitpunkt online \n" +"sind oder nicht.\n" +"Als Empfänger können auch Chaträume angegeben werden (*).\n" +"\n" +"Sowohl der Nickname des Senders als auch Empfängers müssen\n" +"registriert sein, um eine Memo versenden zu können.\n" +"%s's Befehle beinhalten:" + +#: modules/commands/cs_invite.cpp:66 +#, c-format +msgid "%s is already in %s!" +msgstr "%s ist bereits in %s! " + +#: modules/commands/os_svs.cpp:99 +#, fuzzy, c-format +msgid "%s is already in %s." +msgstr "%s ist bereits in %s! " + +#: modules/commands/ms_ignore.cpp:65 +#, fuzzy, c-format +msgid "%s is already on the ignore list." +msgstr "%s befindet sich bereits in Deiner Ignore-Liste." + +#: modules/commands/cs_suspend.cpp:97 modules/commands/ns_suspend.cpp:106 +#, fuzzy, c-format +msgid "%s is already suspended." +msgstr "%s ist bereits in %s! " + +#: modules/commands/ms_rsend.cpp:56 modules/commands/ms_send.cpp:55 +#, c-format +msgid "%s is not a registered unforbidden nick or channel." +msgstr "%s ist kein registrierter Nick bzw. Chatraum." + +#: modules/commands/cs_set.cpp:178 +#, c-format +msgid "%s is not a valid ban type." +msgstr "%s ist kein gültiger Bann-Typ." + +#: modules/commands/bs_info.cpp:101 +#, c-format +msgid "%s is not a valid bot or registered channel." +msgstr "%s ist kein gültiger Bot bzw. registrierter Chatraum." + +#: include/language.h:86 +#, fuzzy, c-format +msgid "%s is not a valid e-mail address." +msgstr "%s ist keine gültige E-Mail Adresse." + +#: include/language.h:80 +#, fuzzy, c-format +msgid "%s is not currently on channel %s." +msgstr "%s wurde deaktiviert im Raum %s." + +#: modules/commands/os_svs.cpp:144 +#, fuzzy, c-format +msgid "%s is not in %s." +msgstr "%s ist bereits in %s! " + +#: modules/commands/ms_ignore.cpp:77 +#, fuzzy, c-format +msgid "%s is not on the ignore list." +msgstr "Der Nickname %s wurde nicht in Deiner Ignore-Liste gefunden." + +#: modules/commands/cs_status.cpp:90 +#, fuzzy, c-format +msgid "%s is on the auto kick list of %s (%s)." +msgstr "%s wurde der AutoKick-Liste von %s hinzugefügt." + +#: modules/commands/cs_status.cpp:53 +#, fuzzy, c-format +msgid "%s is the founder of %s." +msgstr "%s wurde deaktiviert im Raum %s." + +#: modules/commands/cs_status.cpp:78 +#, c-format +msgid "%s matches access entry %s (from entry %s), which has privilege %s." +msgstr "" + +#: modules/commands/cs_status.cpp:71 +#, c-format +msgid "%s matches access entry %s, which has privilege %s." +msgstr "" + +#: include/language.h:109 +#, fuzzy, c-format +msgid "" +"%s matches an except on %s and cannot be banned until the except has been " +"removed." +msgstr "" +"%s ist auf der Exception-Liste von %s und kann nicht gebannt werden bis die " +"Exception entfernt wurde." + +#: modules/commands/cs_status.cpp:96 +#, fuzzy, c-format +msgid "%s matches auto kick entry %s on %s (%s)." +msgstr "%s wurde der AutoKick-Liste von %s hinzugefügt." + +#: modules/commands/cs_xop.cpp:353 +#, c-format +msgid "%s not found on %s %s list." +msgstr "%s wurde nicht auf der %s %s-Liste gefunden." + +#: modules/commands/cs_access.cpp:338 modules/commands/cs_flags.cpp:255 +#, c-format +msgid "%s not found on %s access list." +msgstr "%s wurde nicht auf der Access-Liste von %s gefunden." + +#: modules/commands/cs_akick.cpp:265 +#, c-format +msgid "%s not found on %s autokick list." +msgstr "%s wurde nicht auf der AutoKick-Liste von %s gefunden." + +#: modules/commands/bs_badwords.cpp:341 +#, c-format +msgid "%s not found on %s bad words list." +msgstr "%s nicht in der Bad Words-Liste von %s gefunden." + +#: modules/commands/ns_access.cpp:66 +#, c-format +msgid "%s not found on %s's access list." +msgstr "%s wurde auf der Access-Liste von %s nicht gefunden." + +#: modules/commands/ns_cert.cpp:226 +#, fuzzy, c-format +msgid "%s not found on %s's certificate list." +msgstr "%s wurde nicht auf Deiner Zertifikat-Liste gefunden." + +#: modules/commands/os_ignore.cpp:320 +#, fuzzy, c-format +msgid "%s not found on ignore list." +msgstr "Der Nickname %s wurde nicht in der Ignore-Liste gefunden." + +#: modules/commands/os_session.cpp:238 +#, c-format +msgid "" +"%s not found on session list, but has a limit of %d because it matches entry:" +" %s." +msgstr "" + +#: modules/commands/os_session.cpp:418 +#, c-format +msgid "%s not found on session-limit exception list." +msgstr "" +"%s konnte auf der Liste der Verbindungseinschränkungen\n" +"nicht gefunden werden." + +#: modules/commands/os_sxline.cpp:92 +#, c-format +msgid "%s not found on the %s list." +msgstr "%s wurde nicht auf der %s-Liste gefunden." + +#: modules/commands/os_akill.cpp:237 +#, c-format +msgid "%s not found on the AKILL list." +msgstr "%s wurde nicht auf der AKILL-Liste gefunden." + +#: modules/commands/cs_flags.cpp:251 +#, c-format +msgid "%s removed from the %s access list." +msgstr "%s wurde von der Zugriffsliste von %s entfernt." + +#: modules/commands/ms_ignore.cpp:74 +#, fuzzy, c-format +msgid "%s removed from the ignore list." +msgstr "%s wurde von Deiner Ignore-Liste entfernt." + +#: modules/commands/os_list.cpp:157 +#, c-format +msgid "%s users list:" +msgstr "%s Benutzer-Liste:" + +#: modules/commands/os_ignore.cpp:316 +#, c-format +msgid "%s will no longer be ignored." +msgstr "%s wird nicht länger ignoriert." + +#: modules/commands/os_ignore.cpp:238 +#, c-format +msgid "%s will now be ignored for %s." +msgstr "%s wird jetzt für %s ignoriert." + +#: modules/commands/os_ignore.cpp:233 +#, c-format +msgid "%s will now permanently be ignored." +msgstr "%s wird jetzt permanent ignoriert." + +#: include/language.h:66 +#, c-format +msgid "%s%s HELP %s for more information." +msgstr "" +"Tippe %s%s HELP %s für weitere Informationen\n" +"zu einem bestimmten Befehl." + +#: modules/commands/bs_bot.cpp:270 +msgid "ADD nick user host real" +msgstr "ADD Nick User Host Realname" + +#: modules/commands/bs_bot.cpp:271 +msgid "CHANGE oldnick newnick [user [host [real]]]" +msgstr " CHANGE Botnick Neuer-Botnick [User [Hostmaske [Realname]]]" + +#: modules/commands/bs_bot.cpp:272 +msgid "DEL nick" +msgstr "DEL Nickname." + +#: modules/commands/os_session.cpp:560 +#, fuzzy +msgid "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." +msgstr "" +"EXCEPTION ADD fügt die angegebene Hostmaske zu der\n" +"Liste der Verbindungseinschränkungen hinzu.\n" +"Beachte, dass nick!user@host und user@host keine richtigen\n" +"Hostmasken sind!\n" +"Nur echte Hosts, wie z.B. box.host.dom und *.host.dom sind \n" +"zulässig, weil für eingeschränkte Verbindungen die Nicknamen\n" +"oder Idents nicht von Interesse sind.\n" +"Limit muss eine Nummer grösser oder gleich 0 sein, und legt\n" +"fest, wieviele Verbindungen von diesem Host gemacht werden dürfen.\n" +"Ein Limit von Null bedeutet, dass dieser Host keine ein-\n" +"geschränkte Verbindung hat. Siehe die AKILL Hilfe fuer\n" +"weitere Informationen über das Format des optionalen Zeit \n" +"Parameter.\n" +"EXCEPTION DEL entfernt den Host von der Liste.\n" +"EXCEPTION MOVE verschiebt den Eintrag mit der Nummer \n" +"auf die Position. Die Einträge dazwischen werden\n" +"hoch bzw runtergeschoben um die Lücken zu füllen.\n" +"EXCEPTION LIST und EXCEPTION VIEW zeigen alle aktuellen \n" +"Verbindungseinschränkungen. Wird die optionale Hostmaske \n" +"angegeben, werden nur die entsprechenden Einträge aus\n" +"der Liste angezeigt. Der Unterschied zwischen den beiden \n" +"Befehlen liegt darin, dass EXCEPTION VIEW ausführlicher ist.\n" +"Es zeigt unter anderem den Namen der Person, die den Eintrag\n" +"erstellt hat, dessen Grund, das Limit, die Hostmaske und\n" +"die Auslaufzeit.\n" +"Beachte das ein verbundender Client die erste Beschränkung\n" +"die auf seinen Host zutrifft, \"benutzen\" wird. Grosse und\n" +"weit treffende Einträge in der Liste der Verbindungs-\n" +"einschränkungen senken die Performance der Services." + +#: modules/commands/os_noop.cpp:68 +msgid "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." +msgstr "" + +#: modules/commands/cs_access.cpp:611 +#, c-format +msgid "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." +msgstr "" + +#: modules/commands/ms_read.cpp:35 +#, c-format +msgid "[auto-memo] The memo you sent to %s has been viewed." +msgstr "[auto-memo] Das Memo das Du an %s gesendet hast wurde angesehen." + +#: modules/commands/ns_group.cpp:92 +#, fuzzy +msgid "[target] [password]" +msgstr "Ziel Passwort" + +#: modules/commands/ns_set.cpp:453 +msgid "address" +msgstr "Adresse" + +#: modules/commands/bs_set.cpp:162 +msgid "botname {ON|OFF}" +msgstr "Botname {ON|OFF}" + +#: modules/extra/stats/cs_fantasy_top.cpp:39 +#: modules/extra/stats/cs_fantasy_top.cpp:51 +#: modules/commands/cs_suspend.cpp:152 modules/commands/cs_sync.cpp:20 +#: modules/commands/cs_log.cpp:106 modules/commands/bs_assign.cpp:91 +#: modules/commands/cs_info.cpp:20 modules/commands/cs_getkey.cpp:20 +msgid "channel" +msgstr "Channel" + +#: modules/commands/cs_set.cpp:138 +msgid "channel bantype" +msgstr "Channel Bantyp" + +#: modules/commands/cs_drop.cpp:20 +#, fuzzy +msgid "channel channel" +msgstr "Channel [was]" + +#: modules/commands/cs_log.cpp:107 +msgid "channel command method [status]" +msgstr "Channel Befehl Methode} [Status]" + +#: modules/commands/cs_kick.cpp:21 +msgid "channel mask [reason]" +msgstr "Channel Maske [reason]" + +#: modules/commands/os_mode.cpp:20 +msgid "channel modes" +msgstr "Channel Modi" + +#: modules/commands/cs_set.cpp:267 modules/commands/bs_assign.cpp:20 +msgid "channel nick" +msgstr "Channel Nick" + +#: modules/commands/cs_kick.cpp:20 +msgid "channel nick [reason]" +msgstr "Channel Nick [Grund]" + +#: modules/commands/cs_clone.cpp:115 +msgid "channel target [what]" +msgstr "Channel Ziel [was]" + +#: modules/commands/bs_control.cpp:20 modules/commands/bs_control.cpp:80 +msgid "channel text" +msgstr "Channel Text" + +#: modules/commands/bs_set.cpp:91 +#, fuzzy +msgid "channel time" +msgstr "Channel Text" + +#: modules/commands/os_kick.cpp:20 +msgid "channel user reason" +msgstr "Channel User Grund" + +#: modules/commands/cs_enforce.cpp:228 +#, fuzzy +msgid "channel what" +msgstr "Channel [was]" + +#: modules/commands/cs_xop.cpp:481 +#, fuzzy +msgid "channel ADD mask" +msgstr "Channel ADD Nachricht" + +#: modules/commands/cs_access.cpp:499 +msgid "channel ADD mask level" +msgstr "Channel ADD Maske Level" + +#: modules/commands/cs_entrymsg.cpp:194 +msgid "channel ADD message" +msgstr "Channel ADD Nachricht" + +#: modules/commands/bs_badwords.cpp:371 +msgid "channel ADD word [SINGLE | START | END]" +msgstr "channel ADD Wort [SINGLE | START | END]" + +#: modules/commands/cs_akick.cpp:435 +msgid "channel ADD {nick | mask} [reason]" +msgstr "Channel ADD {Nick | Maske} [Grund]" + +#: modules/commands/cs_topic.cpp:151 +#, fuzzy +msgid "channel APPEND topic" +msgstr "Channel [Topic]" + +#: modules/commands/cs_access.cpp:503 modules/commands/cs_flags.cpp:376 +#: modules/commands/cs_xop.cpp:484 modules/commands/cs_entrymsg.cpp:197 +#: modules/commands/bs_badwords.cpp:374 modules/commands/cs_akick.cpp:440 +msgid "channel CLEAR" +msgstr "Channel CLEAR" + +#: modules/commands/cs_mode.cpp:736 +#, fuzzy +msgid "channel CLEAR [what]" +msgstr "Channel [was]" + +#: modules/commands/os_mode.cpp:21 +#, fuzzy +msgid "channel CLEAR [ALL]" +msgstr "Channel CLEAR" + +#: modules/commands/cs_entrymsg.cpp:195 +msgid "channel DEL num" +msgstr "Channel DEL Nummer" + +#: modules/commands/cs_access.cpp:500 modules/commands/cs_xop.cpp:482 +msgid "channel DEL {mask | entry-num | list}" +msgstr "Channel DEL {Maske | Nummer | Liste }" + +#: modules/commands/cs_akick.cpp:436 +msgid "channel DEL {nick | mask | entry-num | list}" +msgstr "Channel DEL {Nickname | Maske | Nummer | Liste}" + +#: modules/commands/bs_badwords.cpp:372 +msgid "channel DEL {word | entry-num | list}" +msgstr "Channel DEL {Wort | Nummer | Liste}" + +#: modules/commands/cs_akick.cpp:439 +msgid "channel ENFORCE" +msgstr "" + +#: modules/commands/cs_access.cpp:744 modules/commands/cs_entrymsg.cpp:196 +msgid "channel LIST" +msgstr "Channel LIST" + +#: modules/commands/cs_akick.cpp:437 +msgid "channel LIST [mask | entry-num | list]" +msgstr "Channel LIST [Maske | Nummer | Liste]" + +#: modules/commands/cs_access.cpp:501 modules/commands/cs_xop.cpp:483 +#: modules/commands/bs_badwords.cpp:373 +msgid "channel LIST [mask | list]" +msgstr "Channel LIST [Maske | Liste]" + +#: modules/commands/cs_flags.cpp:375 +msgid "channel LIST [mask | +flags]" +msgstr "" + +#: modules/commands/cs_mode.cpp:734 +#, fuzzy +msgid "channel LOCK {ADD|DEL|SET|LIST} [what]" +msgstr "Channel LOCK {ADD|DEL|LIST} [Was]" + +#: modules/commands/cs_access.cpp:745 +msgid "channel RESET" +msgstr "Channel RESET" + +#: modules/commands/cs_mode.cpp:735 +msgid "channel SET modes" +msgstr "Channel SET Modi" + +#: modules/commands/cs_access.cpp:742 +msgid "channel SET type level" +msgstr "" + +#: modules/commands/cs_akick.cpp:438 +msgid "channel VIEW [mask | entry-num | list]" +msgstr "Channel VIEW [Maske | Nummer | Liste]" + +#: modules/commands/cs_access.cpp:502 +msgid "channel VIEW [mask | list]" +msgstr "Channel VIEW [Maske | Liste}" + +#: modules/commands/cs_register.cpp:20 modules/commands/cs_set.cpp:205 +msgid "channel [description]" +msgstr "Channel [Beschreibung]" + +#: modules/commands/cs_set.cpp:950 modules/commands/cs_invite.cpp:20 +#: modules/commands/cs_unban.cpp:20 +msgid "channel [nick]" +msgstr "Channel [Nick]" + +#: modules/commands/cs_set_misc.cpp:96 +msgid "channel [parameters]" +msgstr "Channel [Parameter]" + +#: modules/commands/cs_mode.cpp:807 modules/commands/cs_status.cpp:20 +#, fuzzy +msgid "channel [user]" +msgstr "Channel [Nick]" + +#: modules/commands/cs_suspend.cpp:59 +msgid "channel [+expiry] [reason]" +msgstr "Channel [+Bandauer [Grund]" + +#: modules/commands/cs_ban.cpp:40 +#, fuzzy +msgid "channel [+expiry] {nick | mask} [reason]" +msgstr "Channel [+Bandauer [Grund]" + +#: modules/commands/cs_flags.cpp:374 +#, fuzzy +msgid "channel [MODIFY] mask changes" +msgstr "Channel ADD Maske Level" + +#: modules/commands/cs_topic.cpp:150 +#, fuzzy +msgid "channel [SET] [topic]" +msgstr "Channel [Topic]" + +#: modules/commands/cs_topic.cpp:152 +#, fuzzy +msgid "channel [UNLOCK|LOCK]" +msgstr "Channel CLEAR" + +#: modules/fantasy.cpp:20 modules/commands/greet.cpp:20 +#: modules/commands/bs_assign.cpp:154 +msgid "channel {ON|OFF}" +msgstr "Channel {ON | OFF}" + +#: modules/commands/bs_kick.cpp:491 +#, fuzzy +msgid "channel {ON|OFF} [ttb [ln [secs]]]" +msgstr "Channel Option {ON|OFF} [Einstellungen]" + +#: modules/commands/bs_kick.cpp:361 +#, fuzzy +msgid "channel {ON|OFF} [ttb [min [percent]]]" +msgstr "Channel Option {ON|OFF} [Einstellungen]" + +#: modules/commands/bs_kick.cpp:623 +#, fuzzy +msgid "channel {ON|OFF} [ttb [num]]" +msgstr "Channel Option {ON|OFF} [Einstellungen]" + +#: modules/commands/bs_kick.cpp:252 modules/commands/bs_kick.cpp:288 +#: modules/commands/bs_kick.cpp:327 modules/commands/bs_kick.cpp:457 +#: modules/commands/bs_kick.cpp:589 modules/commands/bs_kick.cpp:724 +#: modules/commands/bs_kick.cpp:758 +#, fuzzy +msgid "channel {ON|OFF} [ttb]" +msgstr "Channel {ON | OFF}" + +#: modules/commands/cs_access.cpp:743 +msgid "channel {DIS | DISABLE} type" +msgstr "" + +#: modules/commands/cs_set.cpp:873 +#, fuzzy +msgid "channel {ON | LEVEL | OFF}" +msgstr "Channel SIGNKICK {ON | LEVEL | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:18 modules/commands/cs_set.cpp:75 +#: modules/commands/cs_set.cpp:336 modules/commands/cs_set.cpp:401 +#: modules/commands/cs_set.cpp:473 modules/commands/cs_set.cpp:622 +#: modules/commands/cs_set.cpp:684 modules/commands/cs_set.cpp:747 +#: modules/commands/cs_set.cpp:811 modules/commands/cs_set.cpp:1044 +#: modules/commands/bs_kick.cpp:792 modules/commands/bs_kick.cpp:857 +#: modules/commands/cs_topic.cpp:21 modules/commands/cs_list.cpp:181 +msgid "channel {ON | OFF}" +msgstr "Channel {ON | OFF}" + +#: modules/commands/ns_getemail.cpp:24 +msgid "email" +msgstr "" + +#: modules/commands/ns_set.cpp:794 +msgid "language" +msgstr "Sprache" + +#: modules/commands/ms_sendall.cpp:25 modules/commands/ms_staff.cpp:25 +msgid "memo-text" +msgstr "Memo-Text" + +#: modules/commands/gl_global.cpp:22 modules/commands/greet.cpp:84 +msgid "message" +msgstr "Nachricht" + +#: modules/commands/os_modinfo.cpp:20 modules/commands/os_module.cpp:20 +#: modules/commands/os_module.cpp:57 modules/commands/os_module.cpp:129 +msgid "modname" +msgstr "Modulname" + +#: modules/commands/ns_set.cpp:330 +msgid "new-display" +msgstr "Neues Display" + +#: modules/commands/ns_set.cpp:120 +msgid "new-password" +msgstr "Neues Passwort" + +#: modules/extra/stats/cs_fantasy_stats.cpp:52 modules/commands/hs_del.cpp:20 +#: modules/commands/hs_del.cpp:60 modules/commands/ms_check.cpp:20 +#: modules/commands/hs_request.cpp:192 modules/commands/cs_seen.cpp:262 +msgid "nick" +msgstr "Nickname" + +#: modules/commands/os_svs.cpp:79 +#, fuzzy +msgid "nick channel" +msgstr "[Nickname | Channel]" + +#: modules/commands/os_svs.cpp:123 +#, fuzzy +msgid "nick channel [reason]" +msgstr "Channel Nick [Grund]" + +#: modules/commands/os_oline.cpp:20 +msgid "nick flags" +msgstr "Nickname Flags" + +#: modules/commands/hs_set.cpp:20 modules/commands/hs_set.cpp:126 +msgid "nick hostmask" +msgstr "Nickname Hostmaske" + +#: modules/commands/os_svs.cpp:20 +msgid "nick newnick" +msgstr "Nickname Neuer-Nickname" + +#: modules/commands/hs_request.cpp:241 +#, fuzzy +msgid "nick [reason]" +msgstr "Channel Nick [Grund]" + +#: modules/commands/ns_getpass.cpp:20 modules/commands/ns_drop.cpp:19 +#: modules/commands/ns_suspend.cpp:161 +msgid "nickname" +msgstr "Nickname" + +#: modules/commands/ns_set.cpp:546 +msgid "nickname address" +msgstr "Nickname Mail-Adresse" + +#: modules/commands/ns_resetpass.cpp:22 +#, fuzzy +msgid "nickname email" +msgstr "Nickname Nachricht" + +#: modules/commands/ns_set.cpp:872 +msgid "nickname language" +msgstr "Nickname Sprache" + +#: modules/commands/greet.cpp:145 +msgid "nickname message" +msgstr "Nickname Nachricht" + +#: modules/commands/ns_set.cpp:399 +msgid "nickname new-display" +msgstr "Nickname Display" + +#: modules/commands/ns_set.cpp:173 +msgid "nickname new-password" +msgstr "Nickname Neues-Passwort" + +#: modules/commands/ns_set_misc.cpp:170 +msgid "nickname [parameter]" +msgstr "Nickname [Parameter]" + +#: modules/commands/ns_recover.cpp:150 +#, fuzzy +msgid "nickname [password]" +msgstr "Nickname Neues-Passwort" + +#: modules/commands/ns_suspend.cpp:61 +#, fuzzy +msgid "nickname [+expiry] [reason]" +msgstr "Nickname [+Zeit] Grund" + +#: modules/commands/ns_info.cpp:239 +#, fuzzy +msgid "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +msgstr "{EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:130 modules/commands/ns_set.cpp:302 +#: modules/commands/ns_set.cpp:631 modules/commands/ns_set.cpp:985 +#: modules/commands/ns_set.cpp:1076 modules/commands/ns_set.cpp:1105 +#: modules/commands/ns_list.cpp:252 +msgid "nickname {ON | OFF}" +msgstr "Nickname {ON | OFF}" + +#: modules/commands/ns_set.cpp:760 +msgid "nickname {ON | QUICK | IMMED | OFF}" +msgstr "Nickname {ON | QUICK | IMMED | OFF}" + +#: modules/commands/bs_set.cpp:20 +msgid "option (channel | bot) settings" +msgstr "option (Channel | Bot) Einstellungen" + +#: modules/commands/cs_set.cpp:21 +msgid "option channel parameters" +msgstr "Option Channel Parameter" + +#: modules/commands/bs_kick.cpp:120 +#, fuzzy +msgid "option channel {ON|OFF} [settings]" +msgstr "Channel Option {ON|OFF} [Einstellungen]" + +#: modules/commands/ns_set.cpp:75 +msgid "option nickname parameters" +msgstr "Option Nickname Parameter" + +#: modules/commands/ms_set.cpp:207 modules/commands/ns_set.cpp:20 +msgid "option parameters" +msgstr "Option Parameter" + +#: modules/commands/os_set.cpp:170 +msgid "option setting" +msgstr "Option Einstellungen" + +#: modules/commands/ns_register.cpp:22 +msgid "passcode" +msgstr "Passcode" + +#: modules/commands/os_login.cpp:19 +msgid "password" +msgstr "Passwort" + +#: modules/commands/ns_register.cpp:124 +msgid "password [email]" +msgstr "Passwort [eMail]" + +#: modules/commands/ns_register.cpp:122 +msgid "password email" +msgstr "Passwort eMail" + +#: modules/commands/cs_list.cpp:21 +msgid "pattern [SUSPENDED] [NOEXPIRE]" +msgstr "Muster [SUSPENDED] [NOEXPIRE]" + +#: modules/commands/ns_list.cpp:20 +msgid "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" +msgstr "Muster [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/os_jupe.cpp:20 +msgid "server [reason]" +msgstr "Servername [Grund]" + +#: modules/commands/os_mode.cpp:147 +msgid "user modes" +msgstr "Channel Modi" + +#: modules/commands/os_kill.cpp:20 +msgid "user [reason]" +msgstr "Nickname [Grund]" + +#: modules/commands/os_sxline.cpp:440 +#, fuzzy +msgid "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." +msgstr "" +"Erlaubt Services Operatoren die AutoKill-Liste zu\n" +"bearbeiten. Versucht ein Benutzer, der einen entsprechenden\n" +"Eintrag auf der AKILL-Liste hat, zu verbinden, werden\n" +"die Services ihn killen und falls der Server dies\n" +"unterstützt wird ein Ban (G-line) für den User gesetzt.\n" +"\n" +"AKILL ADD fügt die angegebene Hostmaske mit\n" +"dem Grund (dieser muss angegeben werden) zur AKILL-\n" +"Liste hinzu. Die Hostmaske darf im Format nick!user@host#real\n" +"sein, wobei ein einfaches user@host ausreichend ist.\n" +"Wenn ein Real Namen angegeben wird muss der nachfolgende Grund\n" +"mit einem ':' anfangen.\n" +"Über den Parameter Zeit lässt sich eine bestimmte\n" +"Auslaufzeit dieses Eintrags definieren. Zeit wird durch\n" +"eine Ganzzahl angegeben, gefolgt von einem Buchstaben:\n" +"d (Tage), h (Stunden), oder m (Minuten). Kombinationen\n" +"(wie zum Beispiel 1h30m) sind nicht zulässig. Wird kein\n" +"Buchstabe angegeben, wird von Tagen ausgegangen (also +30 \n" +"bedeutet dann z.B. 30 Tage). Um einen AKILL-Eintrag zu\n" +"erstellen, der nicht ausläuft, benutze +0. Fängt die Usermaske\n" +"mit einem + an, muss eine Auslaufzeit (Zeit) definiert\n" +"werden, auch wenn es die Standard-Zeit ist. Die Standard-\n" +"Auslaufzeit für einen AKILL kann man unter STATS AKILL finden.\n" + +#: modules/commands/os_sxline.cpp:678 +#, fuzzy +msgid "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Erlaubt Services Operatoren die AutoKill-Liste zu\n" +"bearbeiten. Versucht ein Benutzer, der einen entsprechenden\n" +"Eintrag auf der AKILL-Liste hat, zu verbinden, werden\n" +"die Services ihn killen und falls der Server dies\n" +"unterstützt wird ein Ban (G-line) für den User gesetzt.\n" +"\n" +"AKILL ADD fügt die angegebene Hostmaske mit\n" +"dem Grund (dieser muss angegeben werden) zur AKILL-\n" +"Liste hinzu. Die Hostmaske darf im Format nick!user@host#real\n" +"sein, wobei ein einfaches user@host ausreichend ist.\n" +"Wenn ein Real Namen angegeben wird muss der nachfolgende Grund\n" +"mit einem ':' anfangen.\n" +"Über den Parameter Zeit lässt sich eine bestimmte\n" +"Auslaufzeit dieses Eintrags definieren. Zeit wird durch\n" +"eine Ganzzahl angegeben, gefolgt von einem Buchstaben:\n" +"d (Tage), h (Stunden), oder m (Minuten). Kombinationen\n" +"(wie zum Beispiel 1h30m) sind nicht zulässig. Wird kein\n" +"Buchstabe angegeben, wird von Tagen ausgegangen (also +30 \n" +"bedeutet dann z.B. 30 Tage). Um einen AKILL-Eintrag zu\n" +"erstellen, der nicht ausläuft, benutze +0. Fängt die Usermaske\n" +"mit einem + an, muss eine Auslaufzeit (Zeit) definiert\n" +"werden, auch wenn es die Standard-Zeit ist. Die Standard-\n" +"Auslaufzeit für einen AKILL kann man unter STATS AKILL finden.\n" + +#: modules/pseudoclients/nickserv.cpp:492 +#, fuzzy, c-format +msgid "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." +msgstr "" +"Nicknamen die seit einer längeren Zeit nicht mehr\n" +"genutzt wurden, werden durch den automatischen Auslauf\n" +"nach %d Tagen aus der Datenbank entfernt." + +#: modules/pseudoclients/botserv.cpp:143 +#, fuzzy +msgid "" +" \n" +"Available commands are:" +msgstr "Verfügbare Befehle für %s:" + +#: modules/pseudoclients/botserv.cpp:167 +#, c-format +msgid "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." +msgstr "" +" \n" +"Der Bot wird den Raum betreten wenn mindestens\n" +"%d Benutzer anwesend sind." + +#: modules/fantasy.cpp:69 +#, fuzzy, c-format +msgid "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." +msgstr "" +" \n" +"Aktiviert oder deaktiviert den Fantasy Modus in einem\n" +"Raum. Wenn dieser aktiviert ist, ist es Benutzern\n" +"möglich, %s Befehle im Raum zu benutzen, wenn der Befehl\n" +"mit einem der folgenden Zeichen anfängt: %s.\n" +"\n" +"Hinweis: Auch hier benötigt der ausführende Benutzer\n" +"die Rechte um die Befehle zu benutzen, und zwar\n" +"sowohl das Level um Fantasy zu nutzen, als auch\n" +"ein Level bzw Mode, mit dem er das gegebene \n" +"Kommando ausführen könnte. (Beispiel: Jemand, \n" +"der kein Op ist, kann auch niemanden mit !op oppen.)" + +#: modules/commands/greet.cpp:69 +msgid "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." +msgstr "" +" \n" +"Aktiviert oder deaktiviert den Greet Mode\n" +"in einem Raum. Wenn dieser Mode aktiviert ist, zeigt der Bot\n" +"eine Begrüssungsnachricht bei joinenden Benutzern, die eine\n" +"Nachricht definiert haben und weiterhin auch die \n" +"Berechtigung haben, dass diese angezeigt wird." + +#: modules/commands/bs_kick.cpp:843 +msgid "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Aktiviert oder deaktiviert den Op Protection Modus in\n" +"einem Raum. Wenn dieser aktiviert ist, werden Ops nicht\n" +"vom Bot gekickt, auch wenn sie nicht das NOKICK-Level\n" +"haben." + +#: modules/commands/bs_kick.cpp:908 +msgid "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Aktiviert oder deaktiviert den Voice Protection\n" +"Modus in einem Raum. Wenn dieser aktiviert ist, werden\n" +"Benutzer mit Voice (+v) vom Bot nicht gekickt, auch wenn\n" +"sie nicht das NOKICK-Level haben." + +#: modules/pseudoclients/botserv.cpp:141 +#, c-format +msgid "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" +msgstr "" + +#: modules/commands/cs_register.cpp:105 +msgid "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." +msgstr "" + +#: modules/pseudoclients/chanserv.cpp:272 +#, c-format +msgid "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." +msgstr "" +" \n" +"Beachte das jeder Channel der für %d Tage nicht\n" +"genutzt wird, automatisch auslaufen wird." + +#: modules/commands/cs_register.cpp:101 +#, c-format +msgid "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +msgstr "" + +#: modules/pseudoclients/nickserv.cpp:486 +msgid "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." +msgstr "" +" \n" +"Services Administratoren können auch registrierte Nicknamen\n" +"löschen, ohne sich für den jeweiligen Nicknamen identifizieren\n" +"zu müssen. Zusätzlich können sie die Zugriffsliste eines\n" +"jeden Nicknamen ansehen und bearbeiten." + +#: modules/pseudoclients/chanserv.cpp:277 +msgid "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." +msgstr "" +" \n" +"Services Administratoren können weiterhin beliebige Channels\n" +"DROPPEN (löschen), Zugriffslisten oder Channel-Einstellungen\n" +"ansehen oder verändern." + +#: modules/commands/bs_set.cpp:147 +msgid "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." +msgstr "" + +#: modules/commands/cs_xop.cpp:542 +#, fuzzy, c-format +msgid "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." +msgstr "" +"Syntax: HOP Channel ADD Nickname\n" +" HOP Channel DEL {Nickname | entry-num | Liste}\n" +" HOP Channel LIST [Maske | Liste]\n" +" HOP Channel CLEAR\n" +"\n" +"Verwaltet die HOP (HalfOP) Liste eines Channels. User auf\n" +"dieser Liste werden automatisch gehalfopt, wenn sie joinen.\n" +"\n" +"Der HOP ADD Befehl fügt den jeweiligen Nicknamen zur HOP-Liste\n" +"hinzu.\n" +"Der HOP DEL Befehl löscht den jeweiligen Nicknamen aus der\n" +"HOP-Liste. Wenn mehrere Eintragsnummern angegeben werden,\n" +"werden diese Einträge gelöscht. (Siehe Beispiel bei LIST.)\n" +" \n" +"\n" +"Der HOP LIST Befehl zeigt die aktuelle HOP-Liste an. Wenn\n" +"Wildcard Masks angegeben werden, werden nur die betroffenen\n" +"Einträge angezeigt. Werden mehrere Eintragsnummern angegeben,\n" +"werden nur diese Einträge angezeigt, zB:\n" +"\n" +" HOP #channel LIST 2-5,7-9\n" +" Listet die HOP Einträge 2 bis 5 und 7 bis 9.\n" +"Der HOP CLEAR Befehl löscht alle Einträge der HOP-Liste.\n" +"HOP ADD, HOP DEL und HOP LIST sind auf AOPs oder\n" +"höher beschränkt, während HOP CLEAR nur vom Founder genutzt\n" +"werden kann.\n" +"\n" +"Dieser Befehl kann für Deinen Channel ausgeschaltet sein, in \n" +"diesem Fall nutze bitte die Access Liste. Für weitere Infos zur\n" +"Access Liste, tippe bitte /msg %s HELP ACCESS und\n" +"/msg %s HELP SET XOP für Infos über den Wechsel vom xOP und\n" +"vom Access System." + +#: modules/commands/cs_akick.cpp:508 +#, c-format +msgid "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." +msgstr "" + +#: modules/commands/os_akill.cpp:448 +#, fuzzy +msgid "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." +msgstr "" +"Syntax: HOP Channel ADD Nickname\n" +" HOP Channel DEL {Nickname | entry-num | Liste}\n" +" HOP Channel LIST [Maske | Liste]\n" +" HOP Channel CLEAR\n" +"\n" +"Verwaltet die HOP (HalfOP) Liste eines Channels. User auf\n" +"dieser Liste werden automatisch gehalfopt, wenn sie joinen.\n" +"\n" +"Der HOP ADD Befehl fügt den jeweiligen Nicknamen zur HOP-Liste\n" +"hinzu.\n" +"Der HOP DEL Befehl löscht den jeweiligen Nicknamen aus der\n" +"HOP-Liste. Wenn mehrere Eintragsnummern angegeben werden,\n" +"werden diese Einträge gelöscht. (Siehe Beispiel bei LIST.)\n" +" \n" +"\n" +"Der HOP LIST Befehl zeigt die aktuelle HOP-Liste an. Wenn\n" +"Wildcard Masks angegeben werden, werden nur die betroffenen\n" +"Einträge angezeigt. Werden mehrere Eintragsnummern angegeben,\n" +"werden nur diese Einträge angezeigt, zB:\n" +"\n" +" HOP #channel LIST 2-5,7-9\n" +" Listet die HOP Einträge 2 bis 5 und 7 bis 9.\n" +"Der HOP CLEAR Befehl löscht alle Einträge der HOP-Liste.\n" +"HOP ADD, HOP DEL und HOP LIST sind auf AOPs oder\n" +"höher beschränkt, während HOP CLEAR nur vom Founder genutzt\n" +"werden kann.\n" +"\n" +"Dieser Befehl kann für Deinen Channel ausgeschaltet sein, in \n" +"diesem Fall nutze bitte die Access Liste. Für weitere Infos zur\n" +"Access Liste, tippe bitte /msg %s HELP ACCESS und\n" +"/msg %s HELP SET XOP für Infos über den Wechsel vom xOP und\n" +"vom Access System." + +#: modules/commands/os_sxline.cpp:462 +#, fuzzy +msgid "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." +msgstr "" +"Syntax: HOP Channel ADD Nickname\n" +" HOP Channel DEL {Nickname | entry-num | Liste}\n" +" HOP Channel LIST [Maske | Liste]\n" +" HOP Channel CLEAR\n" +"\n" +"Verwaltet die HOP (HalfOP) Liste eines Channels. User auf\n" +"dieser Liste werden automatisch gehalfopt, wenn sie joinen.\n" +"\n" +"Der HOP ADD Befehl fügt den jeweiligen Nicknamen zur HOP-Liste\n" +"hinzu.\n" +"Der HOP DEL Befehl löscht den jeweiligen Nicknamen aus der\n" +"HOP-Liste. Wenn mehrere Eintragsnummern angegeben werden,\n" +"werden diese Einträge gelöscht. (Siehe Beispiel bei LIST.)\n" +" \n" +"\n" +"Der HOP LIST Befehl zeigt die aktuelle HOP-Liste an. Wenn\n" +"Wildcard Masks angegeben werden, werden nur die betroffenen\n" +"Einträge angezeigt. Werden mehrere Eintragsnummern angegeben,\n" +"werden nur diese Einträge angezeigt, zB:\n" +"\n" +" HOP #channel LIST 2-5,7-9\n" +" Listet die HOP Einträge 2 bis 5 und 7 bis 9.\n" +"Der HOP CLEAR Befehl löscht alle Einträge der HOP-Liste.\n" +"HOP ADD, HOP DEL und HOP LIST sind auf AOPs oder\n" +"höher beschränkt, während HOP CLEAR nur vom Founder genutzt\n" +"werden kann.\n" +"\n" +"Dieser Befehl kann für Deinen Channel ausgeschaltet sein, in \n" +"diesem Fall nutze bitte die Access Liste. Für weitere Infos zur\n" +"Access Liste, tippe bitte /msg %s HELP ACCESS und\n" +"/msg %s HELP SET XOP für Infos über den Wechsel vom xOP und\n" +"vom Access System." + +#: modules/commands/os_sxline.cpp:697 +#, fuzzy +msgid "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." +msgstr "" +"Syntax: HOP Channel ADD Nickname\n" +" HOP Channel DEL {Nickname | entry-num | Liste}\n" +" HOP Channel LIST [Maske | Liste]\n" +" HOP Channel CLEAR\n" +"\n" +"Verwaltet die HOP (HalfOP) Liste eines Channels. User auf\n" +"dieser Liste werden automatisch gehalfopt, wenn sie joinen.\n" +"\n" +"Der HOP ADD Befehl fügt den jeweiligen Nicknamen zur HOP-Liste\n" +"hinzu.\n" +"Der HOP DEL Befehl löscht den jeweiligen Nicknamen aus der\n" +"HOP-Liste. Wenn mehrere Eintragsnummern angegeben werden,\n" +"werden diese Einträge gelöscht. (Siehe Beispiel bei LIST.)\n" +" \n" +"\n" +"Der HOP LIST Befehl zeigt die aktuelle HOP-Liste an. Wenn\n" +"Wildcard Masks angegeben werden, werden nur die betroffenen\n" +"Einträge angezeigt. Werden mehrere Eintragsnummern angegeben,\n" +"werden nur diese Einträge angezeigt, zB:\n" +"\n" +" HOP #channel LIST 2-5,7-9\n" +" Listet die HOP Einträge 2 bis 5 und 7 bis 9.\n" +"Der HOP CLEAR Befehl löscht alle Einträge der HOP-Liste.\n" +"HOP ADD, HOP DEL und HOP LIST sind auf AOPs oder\n" +"höher beschränkt, während HOP CLEAR nur vom Founder genutzt\n" +"werden kann.\n" +"\n" +"Dieser Befehl kann für Deinen Channel ausgeschaltet sein, in \n" +"diesem Fall nutze bitte die Access Liste. Für weitere Infos zur\n" +"Access Liste, tippe bitte /msg %s HELP ACCESS und\n" +"/msg %s HELP SET XOP für Infos über den Wechsel vom xOP und\n" +"vom Access System." + +#: modules/commands/bs_assign.cpp:197 +#, fuzzy +msgid "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." +msgstr "" +" \n" +"Durch diese Option kann einem Channel explizit kein Bot \n" +"zugewiesen werden. Sollte dem Channel, für den diese \n" +"Option gewählt wird, bereits ein Bot zugewiesen \n" +"sein, so verfällt die Zuweisung." + +#: modules/commands/bs_set.cpp:199 +#, fuzzy +msgid "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." +msgstr "" +" \n" +"Verhindert, dass der Bot durch Nicht-IRC Operatoren\n" +"zugeordnet werden kann." + +#: modules/pseudoclients/memoserv.cpp:227 +#, c-format +msgid "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." +msgstr "" + +#: modules/commands/os_oper.cpp:167 +#, c-format +msgid " %s is online using this oper block." +msgstr " %s ist mit diesem Oper-Block online." + +#: modules/commands/os_modinfo.cpp:55 +#, c-format +msgid " Command %s on %s is linked to %s" +msgstr " Befehl %s auf %s ist mit %s verknüpft." + +#: modules/commands/os_modinfo.cpp:43 +#, c-format +msgid " Providing service: %s" +msgstr " Unterstützter Dienst: %s" + +#: modules/commands/os_oper.cpp:163 +msgid " This oper is configured in the configuration file." +msgstr " Dieser Operator wurde in der Konfigurationsdatei eingestellt." + +#: modules/commands/os_modinfo.cpp:34 +#, c-format +msgid " Loaded at: %p" +msgstr "" + +#: modules/commands/cs_seen.cpp:303 +#, c-format +msgid " but %s mysteriously dematerialized." +msgstr " aber %s ist auf mysteriöse Weise verschwunden." + +#: src/messages.cpp:339 +#, c-format +msgid "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." +msgstr "" +"\"/msg %s\" wird nicht mehr unterstützt. Benutze \"/msg %s@%s\" oder \"/" +"%sstattdessen." + +#: modules/commands/os_jupe.cpp:19 +msgid "\"Jupiter\" a server" +msgstr "Einen Server \"jupitern\"" + +#: modules/commands/os_oper.cpp:161 +#, c-format +msgid "%-8s %s" +msgstr "%-8s %s" + +#: modules/extra/stats/cs_fantasy_top.cpp:152 +#, c-format +msgid "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:359 +msgid "%b %d %H:%M:%S %Y %Z" +msgstr "%A, %d.%m.%Y, %H:%M:%S %Z" + +#: modules/commands/cs_log.cpp:205 +#, c-format +msgid "%c is an unknown status mode." +msgstr "%c ist ein unbekannter Status Modus." + +#: modules/commands/cs_mode.cpp:431 +#, c-format +msgid "%c%c is not locked on %s." +msgstr "%c%c ist im %s nicht gelockt." + +#: modules/commands/cs_mode.cpp:427 +#, c-format +msgid "%c%c%s has been unlocked from %s." +msgstr "%c%c%s wurde von %s entsperrt." + +#: modules/commands/cs_clone.cpp:56 +#, fuzzy, c-format +msgid "%d access entries from %s have been cloned to %s." +msgstr "Alle Zugriffsrechte von %s wurden nach %s kopiert." + +#: modules/commands/bs_botlist.cpp:56 +#, c-format +msgid "%d bots available." +msgstr "%d Bots verfügbar." + +#: modules/commands/os_modinfo.cpp:189 +#, fuzzy, c-format +msgid "%d modules loaded." +msgstr "%d Module geladen." + +#: modules/commands/ns_group.cpp:357 +#, fuzzy, c-format +msgid "%d nickname(s) in the group." +msgstr "%d Nicknamen in der Gruppe." + +#: modules/commands/cs_seen.cpp:137 +#, fuzzy, c-format +msgid "%lu nicks are stored in the database, using %.2Lf kB of memory." +msgstr "%lu Nicks sind in der Datenbank und belegen %.2Lf kB des Speichers." + +#: modules/commands/cs_xop.cpp:241 modules/commands/cs_xop.cpp:372 +#: modules/commands/cs_xop.cpp:450 +#, c-format +msgid "%s %s list is empty." +msgstr "Die %s %s-Liste ist leer." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1181 +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1201 +#: modules/commands/bs_kick.cpp:1211 +#, c-format +msgid "%s (%d kick(s) to ban)" +msgstr "%s (%d Kick(s) bis zum Ban)" + +#: modules/commands/bs_kick.cpp:1161 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; %d lines in %ds)" +msgstr "%s (%d Kick(s) bis zum Ban, %d Zeilen in %ds)" + +#: modules/commands/bs_kick.cpp:1171 +#, c-format +msgid "%s (%d kick(s) to ban; %d times)" +msgstr "%s (%d Kick(s) bis zum Ban, %d Mal)" + +#: modules/commands/bs_kick.cpp:1141 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; minimum %d/%d%%)" +msgstr "%s (%d Kick(s) bis zum Ban, Minimum %d/%d%%)" + +#: modules/commands/bs_kick.cpp:1163 +#, c-format +msgid "%s (%d lines in %ds)" +msgstr "%s (%d Zeilen in %d Sekunden)" + +#: modules/commands/bs_kick.cpp:1173 +#, c-format +msgid "%s (%d times)" +msgstr "%s (%d Mal)" + +#: modules/commands/cs_seen.cpp:358 +#, c-format +msgid "%s (%s) was kicked from %s (\"%s\") %s ago%s" +msgstr "%1$s (%2$s) wurde vor %5$s aus %3$s gekickt (\"%4$s\")%6$s" + +#: modules/commands/cs_seen.cpp:355 +#, c-format +msgid "%s (%s) was kicked from a secret channel %s ago%s" +msgstr "%s (%s) wurde vor %s aus einem geheimen Channel gekickt%s" + +#: modules/commands/cs_seen.cpp:326 +#, c-format +msgid "%s (%s) was last seen changing nick from %s to %s %s ago%s" +msgstr "%1$s (%2$s) hat vor %5$s den Nick von %3$s zu %4$s gewechselt%6$s" + +#: modules/commands/cs_seen.cpp:321 +#, c-format +msgid "%s (%s) was last seen changing nick to %s %s ago%s" +msgstr "%1$s (%2$s) hat seinen Nick vor %4$s zu %3$s gewechselt%5$s" + +#: modules/commands/cs_seen.cpp:310 +#, c-format +msgid "%s (%s) was last seen connecting %s ago (%s)%s" +msgstr "%s (%s) ist vor %s in den IRC gekommen (%s)%s" + +#: modules/commands/cs_seen.cpp:335 +#, c-format +msgid "%s (%s) was last seen joining %s %s ago%s" +msgstr "%1$s (%2$s) hat vor %4$s den Raum %3$s betreten%5$s" + +#: modules/commands/cs_seen.cpp:332 +#, c-format +msgid "%s (%s) was last seen joining a secret channel %s ago%s" +msgstr "%s (%s) hat vor %s einen geheimen Raum betreten%s" + +#: modules/commands/cs_seen.cpp:344 +#, c-format +msgid "%s (%s) was last seen parting %s %s ago%s" +msgstr "%1$s (%2$s) hat vor %4$s den Raum %3$s verlassen%5$s" + +#: modules/commands/cs_seen.cpp:341 +#, c-format +msgid "%s (%s) was last seen parting a secret channel %s ago%s" +msgstr "%s (%s) hat vor %s einen geheimen Raum verlassen%s" + +#: modules/commands/cs_seen.cpp:349 +#, c-format +msgid "%s (%s) was last seen quitting (%s) %s ago (%s)." +msgstr "%1$s (%2$s) hat vor %4$s (%5$s) den IRC verlassen (%3$s)." + +#: modules/commands/bs_kick.cpp:1143 +#, c-format +msgid "%s (minimum %d/%d%%)" +msgstr "%s (Minimum %d/%d%%)" + +#: modules/commands/cs_access.cpp:245 modules/commands/cs_access.cpp:349 +#: modules/commands/cs_access.cpp:454 modules/commands/cs_access.cpp:467 +#: modules/commands/cs_flags.cpp:295 +#, c-format +msgid "%s access list is empty." +msgstr "Die Zugriffsliste von %s ist leer." + +#: modules/commands/ns_ajoin.cpp:184 +#, fuzzy, c-format +msgid "%s added to %s's auto join list." +msgstr "%s wurde Deiner Auto-Join-Liste hinzugefügt." + +#: src/xline.cpp:389 +#, c-format +msgid "%s already exists." +msgstr "%s existiert bereits." + +#: modules/commands/cs_akick.cpp:202 modules/commands/cs_akick.cpp:387 +#: modules/commands/cs_akick.cpp:400 +#, c-format +msgid "%s autokick list is empty." +msgstr "Die Autokick-Liste von %s ist leer." + +#: modules/commands/bs_badwords.cpp:198 modules/commands/bs_badwords.cpp:316 +#, c-format +msgid "%s bad words list is empty." +msgstr "Die Bad Words-Liste von %s ist leer." + +#: modules/commands/cs_set.cpp:993 +#, c-format +msgid "%s cannot be the successor on channel %s as they are the founder." +msgstr "%s kann nicht gleichzeitig Gründer und Nachfolger im Raum %s sein." + +#: modules/pseudoclients/global.cpp:90 modules/pseudoclients/hostserv.cpp:78 +#: modules/pseudoclients/operserv.cpp:287 +#, c-format +msgid "%s commands:" +msgstr "Befehle von %s:" + +#: include/language.h:69 +#, c-format +msgid "%s coverage is too wide; Please use a more specific mask." +msgstr "" + +#: modules/commands/ms_info.cpp:94 +#, c-format +msgid "%s currently has %d memos, of which %d are unread." +msgstr "%s hat derzeit %d Memos, von denen %d ungelesen sind." + +#: modules/commands/ms_info.cpp:92 +#, c-format +msgid "%s currently has %d memos, of which 1 is unread." +msgstr "%s hat derzeit %d Memos, von denen eine ungelesen ist." + +#: modules/commands/ms_info.cpp:90 +#, c-format +msgid "%s currently has %d memos." +msgstr "%s hat derzeit %d Memos." + +#: modules/commands/ms_info.cpp:88 +#, c-format +msgid "%s currently has %d memos; all of them are unread." +msgstr "%s hat derzeit %d Memos, von denen alle ungelesen sind." + +#: modules/commands/ms_info.cpp:77 +#, c-format +msgid "%s currently has 1 memo, and it has not yet been read." +msgstr "%s hat derzeit eine ungelesene Memo." + +#: modules/commands/ms_info.cpp:79 +#, c-format +msgid "%s currently has 1 memo." +msgstr "%s hat derzeit eine Memo." + +#: modules/commands/ms_info.cpp:73 +#, c-format +msgid "%s currently has no memos." +msgstr "%s hat derzeit keine Memos." + +#: modules/commands/os_forbid.cpp:344 +#, c-format +msgid "%s deleted from the %s forbid list." +msgstr "%s wurde aus der %s-Liste entfernt." + +#: include/language.h:105 +#, c-format +msgid "%s for %s set to %s." +msgstr "%s für %s wurde auf %s geändert." + +#: include/language.h:106 +#, c-format +msgid "%s for %s unset." +msgstr "%s wurde für %s entfernt." + +#: modules/commands/ns_ajoin.cpp:176 +#, c-format +msgid "%s had an invalid key specified, and was thus ignored." +msgstr "" + +#: modules/commands/ms_info.cpp:111 +#, c-format +msgid "%s has no memo limit." +msgstr "%s hat kein Memo-Limit." + +#: include/language.h:115 +#, c-format +msgid "%s has no memos." +msgstr "%s hat keine Memos." + +#: include/language.h:118 +#, c-format +msgid "%s has no new memos." +msgstr "%s hat keine neuen Memos." + +#: modules/commands/ns_info.cpp:53 +#, c-format +msgid "%s is %s" +msgstr "%s ist %s" + +#: modules/commands/ns_info.cpp:59 +#, fuzzy, c-format +msgid "%s is a Services Operator of type %s." +msgstr "%s ist ein services operator vom Typ %s." + +#: modules/commands/cs_seen.cpp:281 +#, c-format +msgid "%s is a client on services." +msgstr "%s ist ein Services Dienst." + +#: modules/commands/cs_seen.cpp:200 +#, fuzzy, c-format +msgid "%s is a network service." +msgstr "%s ist ein Services Dienst." + +#: src/xline.cpp:407 +#, c-format +msgid "%s is already covered by %s." +msgstr "%s wird bereits von %s getroffen." + +#: modules/commands/ns_ajoin.cpp:170 +#, fuzzy, c-format +msgid "%s is already on %s's auto join list." +msgstr "%s befindet sich bereits in Deiner AutoJoin-Liste." + +#: modules/commands/ns_info.cpp:56 +#, fuzzy, c-format +msgid "%s is an unconfirmed nickname." +msgstr "Der Nickname %s ist noch nicht bestätigt." + +#: modules/commands/cs_flags.cpp:432 +#, c-format +msgid "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." +msgstr "" +"%s ist eine weitere Möglichkeit, die Zugriffslisten eines\n" +"Raumes zu verwalten, ähnlich wie bei XOP und ACCESS." + +#: modules/commands/ns_info.cpp:74 +#, c-format +msgid "%s is currently online." +msgstr "%s ist derzeit online." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is disabled" +msgstr "%s ist ausgeschaltet" + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is enabled" +msgstr "%s ist eingeschaltet" + +#: modules/commands/os_dns.cpp:507 +#, fuzzy, c-format +msgid "%s is not a valid IP address." +msgstr "%s ist keine gültige E-Mail Adresse." + +#: modules/commands/cs_log.cpp:167 modules/commands/cs_log.cpp:192 +#, c-format +msgid "%s is not a valid command." +msgstr "%s ist kein gültiger Befehl." + +#: modules/commands/cs_log.cpp:198 +#, c-format +msgid "%s is not a valid logging method." +msgstr "%s ist keine gültige Log-Methode." + +#: modules/commands/ms_info.cpp:124 +#, c-format +msgid "%s is not notified of new memos." +msgstr "%s wird bei neuen Memos nicht benachrichtigt." + +#: modules/commands/ms_info.cpp:118 +#, c-format +msgid "%s is notified of new memos at logon and when they arrive." +msgstr "%s wird beim Logon und bei Ankunft neuer Memos benachrichtigt." + +#: modules/commands/ms_info.cpp:122 +#, c-format +msgid "%s is notified of new memos at logon." +msgstr "%s wird beim Logon über neuer Memos benachrichtigt." + +#: modules/commands/ms_info.cpp:120 +#, c-format +msgid "%s is notified when new memos arrive." +msgstr "%s wird bei Ankunft neuer Memos benachrichtigt." + +#: modules/commands/cs_seen.cpp:232 +#, c-format +msgid "%s is on the channel right now (as %s)!" +msgstr "" + +#: modules/commands/cs_seen.cpp:221 +#, fuzzy, c-format +msgid "%s is on the channel right now!" +msgstr "%s wurde deaktiviert im Raum %s." + +#: modules/commands/cs_xop.cpp:434 +#, c-format +msgid "%s list for %s" +msgstr "%s Liste von %s:" + +#: modules/commands/os_sxline.cpp:69 modules/commands/os_sxline.cpp:113 +#, c-format +msgid "%s list is empty." +msgstr "Die %s-Liste ist leer." + +#: modules/commands/cs_mode.cpp:376 +#, fuzzy, c-format +msgid "%s locked on %s." +msgstr "%c%c%s wurde in %s gelockt." + +#: modules/extra/stats/cs_fantasy_stats.cpp:120 +#, c-format +msgid "%s not found." +msgstr "%s nicht gefunden." + +#: modules/commands/os_config.cpp:79 +#, c-format +msgid "%s settings:" +msgstr "%s Einstellungen:" + +#: modules/commands/cs_seen.cpp:255 +#, fuzzy, c-format +msgid "%s was last seen here %s ago." +msgstr "%1$s (%2$s) hat vor %4$s den Raum %3$s verlassen%5$s" + +#: modules/commands/ns_ajoin.cpp:213 +#, fuzzy, c-format +msgid "%s was not found on %s's auto join list." +msgstr "%s wurde nicht in Deiner Auto-Join-Liste gefunden." + +#: modules/commands/ns_ajoin.cpp:221 +#, fuzzy, c-format +msgid "%s was removed from %s's auto join list." +msgstr "%s wurde von Deiner Auto-Join-Liste entfernt." + +#: modules/commands/ms_set.cpp:64 +#, c-format +msgid "%s will not send you any notification of memos." +msgstr "%s wird Dich nicht länger beim Eintreffen neuer Memos benachrichtigen." + +#: modules/commands/ms_set.cpp:42 +#, c-format +msgid "%s will now notify you of memos when they are sent to you." +msgstr "%s wird Dich benachrichtigen, sobald neue Memos für Dich eintreffen." + +#: modules/commands/ms_set.cpp:30 +#, c-format +msgid "" +"%s will now notify you of memos when you log on and when they are sent to " +"you." +msgstr "%s wird dich beim Einloggen über eingegangene Memos informieren." + +#: modules/commands/ms_set.cpp:36 +#, c-format +msgid "%s will now notify you of memos when you log on or unset /AWAY." +msgstr "" +"%s wird dich beim Einloggen oder bei der Rückkehr aus /AWAY über " +"eingegangene Memos informieren." + +#: modules/commands/bs_bot.cpp:89 +#, c-format +msgid "%s!%s@%s (%s) added to the bot list." +msgstr "%s!%s@%s (%s) wurde zur der Bot-Liste hinzugefügt." + +#: modules/commands/ns_access.cpp:83 +#, c-format +msgid "%s's access list is empty." +msgstr "Die Access-Liste von %s ist leer." + +#: modules/commands/ns_ajoin.cpp:96 +#, fuzzy, c-format +msgid "%s's auto join list is empty." +msgstr "Deine Autojoin-Liste ist leer." + +#: modules/commands/ns_ajoin.cpp:111 +#, fuzzy, c-format +msgid "%s's auto join list:" +msgstr "Deine Autojoin Liste:" + +#: modules/commands/ns_cert.cpp:242 +#, fuzzy, c-format +msgid "%s's certificate list is empty." +msgstr "Deine Zertifikat-Liste ist leer." + +#: modules/commands/ms_info.cpp:99 modules/commands/ms_info.cpp:106 +#, c-format +msgid "%s's memo limit is %d, and may not be changed." +msgstr "%s's Memo-Limit liegt bei %d und kann nicht geändert werden." + +#: modules/commands/ms_info.cpp:101 modules/commands/ms_info.cpp:108 +#, c-format +msgid "%s's memo limit is %d." +msgstr "%s's Memo-Limit liegt bei %d." + +#: src/misc.cpp:363 +#, c-format +msgid "(%s ago)" +msgstr "(vor %s)" + +#: src/misc.cpp:365 +#, c-format +msgid "(%s from now)" +msgstr "(in %s)" + +#: modules/commands/os_dns.cpp:244 +msgid "(Split)" +msgstr "" + +#: modules/commands/os_info.cpp:268 +#, c-format +msgid "(by %s on %s) %s" +msgstr "" + +#: modules/commands/cs_access.cpp:710 +#, fuzzy +msgid "(disabled)" +msgstr "Deaktiviert" + +#: modules/commands/cs_access.cpp:712 +msgid "(founder only)" +msgstr "" + +#: src/misc.cpp:367 +msgid "(now)" +msgstr "" + +#: modules/commands/os_defcon.cpp:168 +msgid "* AKILL any new clients connecting" +msgstr "* Setzt einen AKILL auf jeden NEU verbindenden Clienten" + +#: modules/commands/os_defcon.cpp:158 +#, fuzzy, c-format +msgid "* Force channel modes (%s) to be set on all channels" +msgstr "* Zwingt alle Channels die Modes (%s) zu setzen" + +#: modules/commands/os_defcon.cpp:164 +#, fuzzy +msgid "* Ignore non-opers with a message" +msgstr "* Ignoriert jeden non-opers mit Nachrichten" + +#: modules/commands/os_defcon.cpp:162 +#, fuzzy +msgid "* Kill any new clients connecting" +msgstr "* Trennt die Verbindung jedes NEU verbindenden Clienten" + +#: modules/commands/os_defcon.cpp:156 +msgid "* No mode lock changes" +msgstr "* Keine Mode Lock Änderungen" + +#: modules/commands/os_defcon.cpp:152 +msgid "* No new channel registrations" +msgstr "* Keine neuen Channel-Registrierungen" + +#: modules/commands/os_defcon.cpp:170 +msgid "* No new memos sent" +msgstr "* Es werden keine neuen Memos gesendet" + +#: modules/commands/os_defcon.cpp:154 +msgid "* No new nick registrations" +msgstr "* Keine neuen Nicknamen-Registrierungen" + +#: modules/commands/os_defcon.cpp:166 +msgid "* Silently ignore non-opers" +msgstr "* Stilles ignorieren von Nicht-Operatoren." + +#: modules/commands/os_defcon.cpp:160 +#, c-format +msgid "* Use the reduced session limit of %d" +msgstr "* Benutzt das reduzierte Session-Limit von %d" + +#: modules/commands/cs_seen.cpp:319 +#, fuzzy, c-format +msgid ", but %s mysteriously dematerialized." +msgstr " aber %s ist auf mysteriöse Weise verschwunden." + +#: modules/commands/cs_seen.cpp:317 +#, c-format +msgid ". %s is still online." +msgstr ". %s ist noch online." + +#: include/language.h:87 +msgid "" +msgstr "" + +#: modules/commands/ns_set.cpp:504 +#, fuzzy, c-format +msgid "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." +msgstr "" +"Eine Bestätigungsmail wurde an %s gesendet. Folge den Anweisungen\n" +"um Deine E-Mail Adresse zu ändern." + +#: modules/commands/ms_sendall.cpp:45 +msgid "A massmemo has been sent to all registered users." +msgstr "Ein Massen-Memo wurde an alle regsitrierten Benutzer gesendet." + +#: modules/commands/hs_request.cpp:285 +msgid "" +"A memo informing the user will also be sent, which includes the reason for " +"the rejection if supplied." +msgstr "" + +#: modules/commands/hs_request.cpp:229 +msgid "A memo informing the user will also be sent." +msgstr "" + +#: modules/commands/ms_read.cpp:42 +#, c-format +msgid "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." +msgstr "" +"Eine Benachrichtigungs-Memo wurde an %s gesendet um ihn/sie zu\n" +"informieren, dass Du seine/ihre Memo gelesen hast." + +#: include/language.h:123 +#, fuzzy +msgid "A vHost ident must be in the format of a valid ident." +msgstr "Der Ident eines vHost muss ein gültiger Ident sein." + +#: include/language.h:122 +#, fuzzy +msgid "A vHost must be in the format of a valid hostname." +msgstr "Ein vHost muss eine gültige HostMaske besitzen." + +#: modules/commands/os_ignore.cpp:342 +#, fuzzy +msgid "ADD expiry {nick|mask} [reason]" +msgstr "ADD Zeit nick Grund" + +#: modules/commands/os_oper.cpp:70 +msgid "ADD oper type" +msgstr "" + +#: modules/commands/os_info.cpp:102 +#, fuzzy +msgid "ADD target info" +msgstr "Ziel Passwort" + +#: modules/commands/os_news.cpp:278 +msgid "ADD text" +msgstr "" + +#: modules/commands/os_session.cpp:523 +msgid "ADD [+expiry] mask limit reason" +msgstr "ADDL [+Zeit] Maske Limit Grund" + +#: modules/commands/ns_ajoin.cpp:231 +#, fuzzy +msgid "ADD [nickname] channel [key]" +msgstr "ADD [Benutzer] Maske" + +#: modules/commands/ns_access.cpp:102 +#, fuzzy +msgid "ADD [nickname] mask" +msgstr "ADD [Benutzer] Maske" + +#: modules/commands/ns_cert.cpp:258 +#, fuzzy +msgid "ADD [nickname] [fingerprint]" +msgstr "Nickname Sprache" + +#: modules/commands/os_sxline.cpp:659 modules/commands/os_akill.cpp:386 +msgid "ADD [+expiry] mask reason" +msgstr "ADD [+Zeit] Maske Grund" + +#: modules/commands/os_sxline.cpp:425 +msgid "ADD [+expiry] mask:reason" +msgstr "ADD [+Zeit] Maske:Grund" + +#: modules/commands/os_forbid.cpp:157 +#, fuzzy +msgid "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" +msgstr "ADD {NICK|CHAN|EMAIL} [+Zeit] Was [Grund]" + +#: modules/commands/os_dns.cpp:665 +msgid "ADDIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:663 +msgid "ADDSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:661 +msgid "ADDZONE zone.name" +msgstr "" + +#: modules/commands/cs_akick.cpp:38 +#, c-format +msgid "AKICK ENFORCE for %s complete; %d users were affected." +msgstr "AKICK ENFORCE für %s erledigt. %d User betroffen." + +#: modules/commands/os_chankill.cpp:21 +msgid "AKILL all users on a specific channel" +msgstr "AKILL alle User des angegebenen Channels" + +#: modules/commands/os_akill.cpp:222 modules/commands/os_akill.cpp:339 +#: modules/commands/os_akill.cpp:353 +msgid "AKILL list is empty." +msgstr "Die AKILL-Liste ist leer." + +#: modules/commands/bs_kick.cpp:1211 modules/commands/bs_kick.cpp:1213 +#: modules/commands/bs_kick.cpp:1216 +msgid "AMSG kicker" +msgstr "AMSG kicker" + +#: modules/commands/ns_alist.cpp:48 +#, fuzzy +msgid "Access" +msgstr "Zugriff verweigert." + +#: include/language.h:72 +msgid "Access denied." +msgstr "Zugriff verweigert." + +#: modules/commands/cs_status.cpp:58 +#, fuzzy, c-format +msgid "Access for %s on %s:" +msgstr "Access-Level für %s in %s wurde auf +%s geändert." + +#: include/language.h:107 +#, c-format +msgid "Access level must be between %d and %d inclusive." +msgstr "Das Level darf nur zwischen %d und %d liegen." + +#: modules/commands/cs_access.cpp:108 +msgid "Access level must be non-zero." +msgstr "Zugriffs-Level muss grösser als 0 sein." + +#: modules/commands/cs_access.cpp:694 +#, c-format +msgid "Access level settings for channel %s:" +msgstr "Zugriffslevel für Channel %s:" + +#: modules/commands/cs_access.cpp:734 +#, c-format +msgid "Access levels for %s reset to defaults." +msgstr "Zugriffslevel für %s wurden auf Standardwerte zurückgesetzt." + +#: modules/commands/cs_access.cpp:439 modules/commands/ns_access.cpp:87 +#, c-format +msgid "Access list for %s:" +msgstr "Zugriffs-Liste von %s:" + +#: modules/commands/help.cpp:166 +#, c-format +msgid "" +"Access to this command requires the permission %s to be present in your " +"opertype." +msgstr "" +"Um Zugriff auf diesen Befehl zu haben benötigst Du die Berechtigung %s in " +"Deinem Oper Type." + +#: modules/commands/ns_cert.cpp:368 modules/commands/ns_cert.cpp:392 +#: modules/commands/ns_identify.cpp:94 +#, c-format +msgid "" +"Account %s has already reached the maximum number of simultaneous logins " +"(%u)." +msgstr "" + +#: modules/commands/cs_set.cpp:683 +msgid "Activate security features" +msgstr "Aktiviert Sicherheits-funktionen" + +#: modules/commands/hs_request.cpp:227 +msgid "Activate the requested vHost for the given nick." +msgstr "Schaltet den beantragten vHost für einen Nick frei." + +#: modules/commands/hs_on.cpp:55 +#, fuzzy +msgid "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." +msgstr "" +"Aktiviert den vHost der Deinem Nicknamen zugewiesen wurde. \n" +"Wenn Du diesen Befehl benutzt, wird jeder User, der ein /whois\n" +"auf dich anwendet, diesen vHost anstatt Deiner Host sehen." + +#: modules/commands/hs_on.cpp:19 +msgid "Activates your assigned vhost" +msgstr "Aktiviert Deinen vHost" + +#: modules/commands/os_info.cpp:243 +msgid "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." +msgstr "" + +#: modules/commands/os_dns.cpp:515 +#, c-format +msgid "Added IP %s to %s." +msgstr "" + +#: modules/commands/os_forbid.cpp:239 +#, fuzzy, c-format +msgid "Added a forbid on %s of type %s to expire on %s." +msgstr "%s wurde aus %s gebannt. Der Ban wird in %s automatisch entfernt." + +#: modules/commands/os_info.cpp:164 +#, fuzzy, c-format +msgid "Added info to %s." +msgstr "Memo wurde an %s versandt." + +#: modules/commands/os_news.cpp:34 +msgid "Added new logon news item." +msgstr "Neuer Logon News-Eintrag hinzugefügt." + +#: modules/commands/os_news.cpp:44 +msgid "Added new oper news item." +msgstr "Neuer Oper-News-Eintrag hinzugefügt." + +#: modules/commands/os_news.cpp:54 +msgid "Added new random news item." +msgstr "Neuer randomnews Eintrag hinzugefügt." + +#: modules/commands/os_dns.cpp:395 +#, fuzzy, c-format +msgid "Added server %s." +msgstr "Uplink Server: %s" + +#: modules/commands/os_dns.cpp:300 +#, c-format +msgid "Added zone %s." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:257 +msgid "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." +msgstr "" + +#: modules/commands/ns_register.cpp:104 +msgid "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." +msgstr "" +"Services Operatoren mit dem nickserv/confirm Recht können\n" +"den passcode durch den Nick eines Benutzers ersetzen um ihn zu validieren." + +#: modules/pseudoclients/botserv.cpp:172 +#, c-format +msgid "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" +msgstr "" + +#: modules/commands/os_noop.cpp:58 +#, c-format +msgid "All O:lines of %s have been reset." +msgstr "Alle O:lines von %s wurden wiederhergestellt." + +#: modules/commands/cs_clone.cpp:71 +#, fuzzy, c-format +msgid "All akick entries from %s have been cloned to %s." +msgstr "Alle Autokick Einträge von %s wurden nach %s kopiert." + +#: modules/commands/help.cpp:57 +#, fuzzy, c-format +msgid "All available commands for %s:" +msgstr "Verfügbare Befehle für %s:" + +#: modules/commands/cs_clone.cpp:96 +#, fuzzy, c-format +msgid "All badword entries from %s have been cloned to %s." +msgstr "Alle badword Einträge von %s wurden nach %s kopiert." + +#: modules/commands/cs_clone.cpp:108 +#, fuzzy, c-format +msgid "All level entries from %s have been cloned into %s." +msgstr "Alle Autokick Einträge von %s wurden nach %s kopiert." + +#: modules/commands/os_news.cpp:38 +msgid "All logon news items deleted." +msgstr "Alle Logon-News wurden entfernt." + +#: modules/commands/ms_del.cpp:115 +#, c-format +msgid "All memos for channel %s have been deleted." +msgstr "Alle Memos für den Channel %s wurden gelöscht." + +#: modules/commands/os_mode.cpp:61 +#, c-format +msgid "All modes cleared on %s." +msgstr "" + +#: modules/commands/ns_register.cpp:258 modules/commands/ns_register.cpp:389 +msgid "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." +msgstr "" + +#: modules/commands/ms_del.cpp:119 +msgid "All of your memos have been deleted." +msgstr "Alle Deine Memos wurden gelöscht." + +#: modules/commands/os_news.cpp:48 +msgid "All oper news items deleted." +msgstr "Alle Oper-News-Einträge wurden entfernt." + +#: modules/commands/os_noop.cpp:41 +#, fuzzy, c-format +msgid "All operators from %s have been removed." +msgstr "Alle O:Lines von %s wurden temporär entfernt." + +#: modules/commands/os_news.cpp:58 +msgid "All random news items deleted." +msgstr "Alle randomnews Einträge wurden gelöscht." + +#: modules/commands/cs_clone.cpp:211 +#, fuzzy, c-format +msgid "All settings from %s have been cloned to %s." +msgstr "Alle Einstellungen von %s wurden nach %s kopiert." + +#: modules/commands/cs_sync.cpp:41 +#, c-format +msgid "All user modes on %s have been synced." +msgstr "Alle Benutzermodi von %s wurden synchronisiert." + +#: modules/commands/hs_group.cpp:60 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s." +msgstr "Alle vHosts in der Gruppe %s wurden auf %s gesetzt." + +#: modules/commands/hs_group.cpp:58 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s@%s." +msgstr "Alle vHosts in der Gruppe %s wurden auf %s@%s gesetzt." + +#: src/access.cpp:40 +msgid "Allowed to (de)halfop him/herself" +msgstr "" + +#: src/access.cpp:39 +msgid "Allowed to (de)halfop users" +msgstr "" + +#: src/access.cpp:48 +msgid "Allowed to (de)op him/herself" +msgstr "" + +#: src/access.cpp:47 +msgid "Allowed to (de)op users" +msgstr "" + +#: src/access.cpp:50 +msgid "Allowed to (de)owner him/herself" +msgstr "" + +#: src/access.cpp:49 +msgid "Allowed to (de)owner users" +msgstr "" + +#: src/access.cpp:52 +msgid "Allowed to (de)protect him/herself" +msgstr "" + +#: src/access.cpp:51 +msgid "Allowed to (de)protect users" +msgstr "" + +#: src/access.cpp:59 +msgid "Allowed to (de)voice him/herself" +msgstr "" + +#: src/access.cpp:58 +msgid "Allowed to (de)voice users" +msgstr "" + +#: src/access.cpp:27 +msgid "Allowed to assign/unassign a bot" +msgstr "" + +#: src/access.cpp:34 +msgid "Allowed to ban users" +msgstr "" + +#: src/access.cpp:56 +#, fuzzy +msgid "Allowed to change channel topics" +msgstr "Ändert die Raum Modi" + +#: src/access.cpp:41 +msgid "Allowed to get full INFO output" +msgstr "" + +#: src/access.cpp:36 +msgid "Allowed to issue commands restricted to channel founders" +msgstr "" + +#: src/access.cpp:33 +msgid "Allowed to modify channel badwords list" +msgstr "" + +#: src/access.cpp:24 +#, fuzzy +msgid "Allowed to modify the access list" +msgstr "%s wurde von der Zugriffsliste von %s entfernt." + +#: src/access.cpp:44 +msgid "Allowed to read channel memos" +msgstr "" + +#: src/access.cpp:54 +#, fuzzy +msgid "Allowed to set channel settings" +msgstr "* Keine neuen Channel-Registrierungen" + +#: src/access.cpp:57 +msgid "Allowed to unban users" +msgstr "" + +#: src/access.cpp:37 +msgid "Allowed to use GETKEY command" +msgstr "" + +#: src/access.cpp:53 +msgid "Allowed to use SAY and ACT commands" +msgstr "" + +#: src/access.cpp:35 +#, fuzzy +msgid "Allowed to use fantasy commands" +msgstr " PEACE Regulate the use of critical commands" + +#: src/access.cpp:26 +#, fuzzy +msgid "Allowed to use the AKICK command" +msgstr "Du kannst diesen befehl nicht benutzen." + +#: src/access.cpp:42 +msgid "Allowed to use the INVITE command" +msgstr "" + +#: src/access.cpp:43 +#, fuzzy +msgid "Allowed to use the KICK command" +msgstr "Du kannst diesen befehl nicht benutzen." + +#: src/access.cpp:45 +#, fuzzy +msgid "Allowed to use the MODE command" +msgstr "Du kannst diesen befehl nicht benutzen." + +#: src/access.cpp:25 +#, fuzzy +msgid "Allowed to view the access list" +msgstr "%s wurde von der Zugriffsliste von %s entfernt." + +#: modules/commands/gl_global.cpp:42 +#, fuzzy, c-format +msgid "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." +msgstr "" +"Ermöglicht Administratoren eine Nachricht an alle User auf\n" +"dem Netzwerk zu senden. Die Nachricht wird von %s gesendet." + +#: modules/commands/os_mode.cpp:133 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." +msgstr "" +"Erlaubt es Services Operatoren die Modes eines beliebigen\n" +"Raumes zu verändern. Der Paramater hat das gleiche Format\n" +"wie der normale /MODE Befehl." + +#: modules/commands/os_mode.cpp:173 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." +msgstr "" +"Erlaubt es Services Operatoren die Modes eines beliebigen\n" +"Benutzers zu verändern. Der Paramater hat das gleiche Format\n" +"wie der normale /MODE Befehl." + +#: modules/commands/bs_bot.cpp:352 +#, fuzzy +msgid "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." +msgstr "" +"Erlaubt Services Administratoren Bots, die die Benutzer in\n" +"Ihren Räumen nutzen können, zu erstellen, zu verändern,\n" +"und zu löschen.\n" +"\n" +"Der BOT ADD Befehl fügt einen Bot mit dem angegebenen \n" +"Botnick, User, Host und Realnamen hinzu.\n" +"Der BOT CHANGE Befehl ändert Attribute eines Bots.\n" +"Der BOT DEL Befehl löscht den angegebenen Bot aus der Botliste.\n" +"\n" +"Achtung: Wenn ein Bot erstellt wird, dessen Nickname\n" +"registriert ist, wird dieser Nickname gelöscht. Falls\n" +"der User mit diesem Nicknamen online ist, wird dieser\n" +"entfernt (gekillt)." + +#: modules/commands/os_oline.cpp:56 +#, fuzzy +msgid "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." +msgstr "" +"Erlaubt es Services Operatoren einem User Operflags \n" +"zu setzen. Den Flags muss ein \"+\" oder ein \"-\" vorangestellt \n" +"werden. Um alle Operflags zu entfernen, tippe einfach ein \n" +"\"-\" ohne Operflags." + +#: modules/commands/os_ignore.cpp:370 +#, fuzzy +msgid "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." +msgstr "" +"Erlaubt Services Admins den Services einen Nick oder eine\n" +"Hostmaske für eine bestimmte Zeit oder bis zum nächsten\n" +"Neustart zu ignorieren. Mit Hilfe von Zeit lässt sich eine\n" +"bestimmte Auslaufzeit dieses Eintrags definieren.\n" +"Zeit wird durch eine Ganzzahl angegeben, gefolgt von einem\n" +"Buchstaben: s (Sekunden), m (Minuten), h (Stunden)\n" +"oder d (Tage).\n" +"Kombinationen (wie zum Beispiel 1h30m) sind nicht zulässig.\n" +"Wird kein Buchstabe angegeben, wird von Sekunden ausgegangen\n" +"(also 30 bedeutet dann z.B. 30 Sekunden). Um einen \n" +"IGNORE-Eintrag zu erstellen, der nicht ausläuft, benutze 0.\n" +"Wenn eine Hostmaske hinzugefügt wird sollte es in dem Format\n" +"user@host oder nick!user@host erfolgen, ansonsten wird es als\n" +"Nick angesehen. Wildcards sind erlaubt.\n" +"\n" +"Ignores werden nicht bei IRC Operatoren erzwungen." + +#: modules/commands/os_akill.cpp:420 +#, fuzzy +msgid "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Erlaubt Services Operatoren die AutoKill-Liste zu\n" +"bearbeiten. Versucht ein Benutzer, der einen entsprechenden\n" +"Eintrag auf der AKILL-Liste hat, zu verbinden, werden\n" +"die Services ihn killen und falls der Server dies\n" +"unterstützt wird ein Ban (G-line) für den User gesetzt.\n" +"\n" +"AKILL ADD fügt die angegebene Hostmaske mit\n" +"dem Grund (dieser muss angegeben werden) zur AKILL-\n" +"Liste hinzu. Die Hostmaske darf im Format nick!user@host#real\n" +"sein, wobei ein einfaches user@host ausreichend ist.\n" +"Wenn ein Real Namen angegeben wird muss der nachfolgende Grund\n" +"mit einem ':' anfangen.\n" +"Über den Parameter Zeit lässt sich eine bestimmte\n" +"Auslaufzeit dieses Eintrags definieren. Zeit wird durch\n" +"eine Ganzzahl angegeben, gefolgt von einem Buchstaben:\n" +"d (Tage), h (Stunden), oder m (Minuten). Kombinationen\n" +"(wie zum Beispiel 1h30m) sind nicht zulässig. Wird kein\n" +"Buchstabe angegeben, wird von Tagen ausgegangen (also +30 \n" +"bedeutet dann z.B. 30 Tage). Um einen AKILL-Eintrag zu\n" +"erstellen, der nicht ausläuft, benutze +0. Fängt die Usermaske\n" +"mit einem + an, muss eine Auslaufzeit (Zeit) definiert\n" +"werden, auch wenn es die Standard-Zeit ist. Die Standard-\n" +"Auslaufzeit für einen AKILL kann man unter STATS AKILL finden.\n" + +#: modules/commands/os_sxline.cpp:436 +#, fuzzy +msgid "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." +msgstr "" +"Erlaubt Services Operatoren die SNLINE Liste zu bearbeiten.\n" +"Wenn der Realname eines Benutzers mit einer SNLINE Maske\n" +"übereinstimmt, werden die Services seine IRC Sitzung beenden.\n" + +#: modules/commands/os_sxline.cpp:670 +#, fuzzy +msgid "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." +msgstr "" +"Erlaubt Services Operatoren die SNLINE Liste zu bearbeiten.\n" +"Wenn der Realname eines Benutzers mit einer SNLINE Maske\n" +"übereinstimmt, werden die Services seine IRC Sitzung beenden.\n" + +#: modules/commands/os_session.cpp:551 +msgid "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." +msgstr "" + +#: modules/commands/os_session.cpp:270 +#, fuzzy +msgid "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." +msgstr "" +"Zeigt Services Administratoren eine Liste mit Hosts, die \n" +"eine bestimmte Anzahl Verbindungen zum Chat-Netz haben.\n" +"\n" +"SESSION LIST zeigt die Hosts mit mindestens threshold \n" +"gleichzeitigen Verbindungen.\n" +"Der threshold muss eine Nummer grösser als 1 sein. Dies\n" +"soll verhindern, dass aus Versehen eine riesige Liste\n" +"von Einzelsitzungen ausgegeben wird.\n" +"\n" +"SESSION VIEW ist etwas ausführlicher und zeigt mehr\n" +"Informationen über den bestimmten Host - mit\n" +"Anzahl Verbindungen und dessen Limit. Der Wert bei\n" +"host kann keine Platzhalter (Wildcards) enthalten.\n" +"\n" +"Siehe die Hilfe zu EXCEPTION um weitere Informationen\n" +"über das Einschränken von Verbindungen zu erhalten." + +#: modules/commands/cs_topic.cpp:193 +msgid "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do " +"not have\n" +"the TOPIC privilege." +msgstr "" + +#: modules/commands/os_kick.cpp:62 +#, c-format +msgid "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" +msgstr "" +"Erlaubt es einen User aus einem beliebigen\n" +"Channel zu kicken. Die Parameter sind dieselben\n" +"wie für den normalen /KICK Befehl.\n" +"Die Kick-Nachricht wird den Nicknamen des IRCops\n" +"vor dem Grund haben. Zum Beispiel:\n" +"\n" +"*** SpamMan has been kicked off channel #my_channel by %s (chemical (Flood))" + +#: modules/commands/cs_set.cpp:33 +msgid "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" +msgstr "" +"Erlaubt es dem Raum-Gründer bestimmte Optionen\n" +"und Informationen des Channels zu ändern.\n" +"\n" +"Verfügbare Optionen:" + +#: modules/commands/os_oper.cpp:250 +msgid "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." +msgstr "" + +#: modules/commands/os_config.cpp:127 +msgid "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" +msgstr "" + +#: modules/commands/ns_set.cpp:992 +#, fuzzy +msgid "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." +msgstr "" +"Bestimmt die Art, mit dem sich die Services mit dem \n" +"angebenen Nicknamen unterhalten. \n" +"Ist MSG eingeschaltet benutzen die Services Messages\n" +"(Queries), ansonsten werden die Antworten als Notices\n" +"geschickt (Standard)." + +#: modules/commands/ns_set.cpp:966 +#, fuzzy, c-format +msgid "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." +msgstr "" +"Bestimmt den Modus, mit dem sich die Services mit Dir\n" +"unterhalten. \n" +"Ist MSG eingeschaltet, benutzen die Services Messages\n" +"(Queries), ansonsten werden Dir die Antworten als Notices\n" +"geschickt (Standard)." + +#: modules/commands/ms_ignore.cpp:113 +msgid "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." +msgstr "" + +#: modules/commands/os_kill.cpp:48 +msgid "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." +msgstr "" + +#: modules/commands/ns_info.cpp:252 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Erlaubt es beim angegebenen Nicknamen, bestimmte Informationen\n" +"in der Ausgabe von %s INFO zu verstecken.\n" +"Es kann die eMail-Adresse versteckt (EMAIL) werden, die \n" +"zuletzt gesehene user@host-Maske (USERMASK), der\n" +"Services-Zugriffsstatus (STATUS) und die letzte Quit-Nachricht\n" +"(QUIT).\n" +"Der zweite Parameter bestimmt, ob die Information angezeigt\n" +"werden soll (OFF) oder nicht (ON)." + +#: modules/commands/ns_info.cpp:223 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Erlaubt es Dir, bestimmte Informationen in der Ausgabe\n" +"von %s INFO zu verstecken.\n" +"Du kannst Deine eMail-Adresse verstecken (EMAIL), die \n" +"zuletzt gesehene user@host-Maske (USERMASK), Dein\n" +"Services-Zugriffsstatus (STATUS) und die letzte Quit-Nachricht\n" +"(QUIT).\n" +"Der zweite Parameter bestimmt, ob die Information angezeigt\n" +"werden soll (OFF) oder nicht (ON)." + +#: modules/commands/bs_info.cpp:118 +#, fuzzy, c-format +msgid "Allows you to see %s information about a channel or a bot" +msgstr "Erlaubt Dir Informationen über ein BotServ ServicesBot zu sehen" + +#: modules/commands/bs_info.cpp:108 +#, c-format +msgid "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." +msgstr "" +"Zeigt %s Informationen über einen Bot oder einen Channel\n" +"an. Wenn der Parameter ein Channel ist, so werden \n" +"Informationen wie aktive Kicks etc. angezeigt, wenn der \n" +"Parameter ein Botnick ist, werden Informationen wie \n" +"Erstellungsdatum oder Anzahl der Channels angezeigt." + +#: modules/commands/cs_xop.cpp:567 +msgid "" +"Alternative methods of modifying channel access lists are\n" +"available. " +msgstr "" + +#: modules/commands/hs_request.cpp:191 +msgid "Approve the requested vHost of a user" +msgstr "Genehmigt den beantragten vHost eines Users" + +#: modules/commands/ns_drop.cpp:68 +#, fuzzy +msgid "As a Services Operator, you may drop any nick." +msgstr "%s ist ein services operator vom Typ %s." + +#: modules/commands/bs_assign.cpp:19 +msgid "Assigns a bot to a channel" +msgstr "Weist einem Channel einen Bot zu" + +#: modules/commands/bs_assign.cpp:78 +#, fuzzy +msgid "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." +msgstr "" +"Weist einem Channel einen Bot zu. Der Botnick muss \n" +"jedoch existieren. Nach dieser Zuweisung können die \n" +"Channel-spezifischen Einstellungen des Bots angepasst \n" +"werden." + +#: data/chanserv.example.conf:1197 +#, fuzzy +msgid "Associate a URL with the channel" +msgstr "Weist einem Channel einen Bot zu" + +#: data/nickserv.example.conf:594 +msgid "Associate a URL with this account" +msgstr "" + +#: data/nickserv.example.conf:593 +#, fuzzy +msgid "Associate a URL with your account" +msgstr "Stellt eine Begrüssungsmeldung für Deinen Nicknamen ein." + +#: modules/commands/greet.cpp:83 +msgid "Associate a greet message with your nickname" +msgstr "Stellt eine Begrüssungsmeldung für Deinen Nicknamen ein." + +#: data/chanserv.example.conf:1198 +#, fuzzy +msgid "Associate an E-mail address with the channel" +msgstr "Verbindet eine eMail-Adresse mit Deinem Nicknamen" + +#: modules/commands/ns_set.cpp:452 +msgid "Associate an E-mail address with your nickname" +msgstr "Verbindet eine eMail-Adresse mit Deinem Nicknamen" + +#: modules/commands/os_info.cpp:101 +#, fuzzy +msgid "Associate oper info with a nick or channel" +msgstr "Weist einem Channel einen Bot zu" + +#: modules/commands/ns_set.cpp:558 +msgid "Associates the given E-mail address with the nickname." +msgstr "Verbindet die angegebene eMail-Adresse mit Deinem Nicknamen." + +#: modules/commands/ns_set.cpp:533 +msgid "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." +msgstr "" +"Verbindet die angegebene eMail-Adresse mit Deinem\n" +"Nicknamen. Diese Adresse wird angezeigt, wenn jemand \n" +"Informationen über Deinen Nicknamen mit dem INFO \n" +"Befehl anfordert." + +#: modules/commands/ns_set.cpp:1315 +msgid "Auto-op" +msgstr "Auto-op" + +#: modules/commands/cs_akick.cpp:374 +#, c-format +msgid "Autokick list for %s:" +msgstr "Autokick-Liste von %s:" + +#: src/access.cpp:29 +msgid "Automatic channel operator status upon join" +msgstr "" + +#: src/access.cpp:28 +msgid "Automatic halfop upon join" +msgstr "" + +#: src/access.cpp:30 +msgid "Automatic owner upon join" +msgstr "" + +#: src/access.cpp:31 +msgid "Automatic protect upon join" +msgstr "" + +#: src/access.cpp:32 +msgid "Automatic voice on join" +msgstr "" + +#: modules/commands/os_oper.cpp:196 +#, c-format +msgid "Available commands for %s:" +msgstr "Verfügbare Befehle für %s:" + +#: modules/commands/os_oper.cpp:175 +#, fuzzy +msgid "Available opertypes:" +msgstr "Verfügbare Befehle für %s:" + +#: modules/commands/os_oper.cpp:218 +#, c-format +msgid "Available privileges for %s:" +msgstr "Verfügbare Rechte für %s:" + +#: modules/commands/cs_enforce.cpp:162 +msgid "BANS enforced by " +msgstr "" + +#: modules/commands/bs_kick.cpp:1121 modules/commands/bs_kick.cpp:1123 +#: modules/commands/bs_kick.cpp:1126 +msgid "Bad words kicker" +msgstr "Bad words kicker" + +#: modules/commands/bs_badwords.cpp:252 +#, fuzzy, c-format +msgid "Bad words list for %s:" +msgstr "Badword Liste von %s:" + +#: modules/commands/bs_badwords.cpp:364 +msgid "Bad words list is now empty." +msgstr "Die Bad Words-Liste ist jetzt leer." + +#: modules/commands/bs_set.cpp:129 +msgid "Ban expiry may not be longer than 1 day." +msgstr "" + +#: modules/commands/cs_ban.cpp:140 modules/commands/cs_ban.cpp:175 +#, fuzzy, c-format +msgid "Ban on %s expires in %s." +msgstr "%s wurde aus %s gebannt. Der Ban wird in %s automatisch entfernt." + +#: modules/commands/cs_info.cpp:60 +msgid "Ban type" +msgstr "" + +#: modules/commands/cs_set.cpp:174 +#, c-format +msgid "Ban type for channel %s is now #%d." +msgstr "Bann-Typ für den Channel %s ist jetzt #%d." + +#: modules/commands/cs_ban.cpp:39 +#, fuzzy +msgid "Bans a given nick or mask on a channel" +msgstr "Bannt den angegebenen Nicknamen aus einen Channel" + +#: modules/commands/cs_ban.cpp:227 +#, fuzzy +msgid "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." +msgstr "" +"Bannt einen Nicknamen im Channel.\n" +"\n" +"Standardmässig auf AOPs oder User mit Access Level 5 oder\n" +"höher beschränkt." + +#: modules/commands/cs_enforce.cpp:166 +#, fuzzy, c-format +msgid "Bans enforced on %s." +msgstr "%c%c ist im %s nicht gelockt." + +#: modules/commands/bs_kick.cpp:1131 modules/commands/bs_kick.cpp:1133 +#: modules/commands/bs_kick.cpp:1136 +msgid "Bolds kicker" +msgstr "Bolds kicker" + +#: modules/commands/bs_bot.cpp:26 modules/commands/bs_bot.cpp:175 +#, c-format +msgid "Bot %s already exists." +msgstr "Bot %s existiert bereits." + +#: include/language.h:119 +#, fuzzy, c-format +msgid "Bot %s does not exist." +msgstr "Bot %s existiert bereits." + +#: modules/commands/bs_assign.cpp:71 modules/commands/bs_assign.cpp:246 +#, c-format +msgid "Bot %s has been assigned to %s." +msgstr "Bot %s wurde dem Channel %s zugewiesen." + +#: modules/commands/bs_bot.cpp:228 +#, fuzzy, c-format +msgid "Bot %s has been changed to %s!%s@%s (%s)." +msgstr "Bot %s wurde geändert auf %s!%s@%s (%s)" + +#: modules/commands/bs_bot.cpp:262 +#, c-format +msgid "Bot %s has been deleted." +msgstr "Bot %s wurde gelöscht." + +#: modules/commands/bs_assign.cpp:63 modules/commands/bs_assign.cpp:241 +#, c-format +msgid "Bot %s is already assigned to channel %s." +msgstr "Bot %s ist bereits dem Channel %s zugewiesen." + +#: modules/commands/bs_kick.cpp:832 +#, c-format +msgid "Bot will kick ops on channel %s." +msgstr "Bot wird Ops kicken im %s." + +#: modules/commands/bs_kick.cpp:897 +#, c-format +msgid "Bot will kick voices on channel %s." +msgstr "Bot wird Voices kicken im %s." + +#: modules/commands/bs_kick.cpp:824 +#, c-format +msgid "Bot won't kick ops on channel %s." +msgstr "Bot wird keine Ops kicken im %s." + +#: modules/commands/bs_kick.cpp:889 +#, c-format +msgid "Bot won't kick voices on channel %s." +msgstr "Bot wird keine Voices kicken im %s." + +#: modules/commands/bs_bot.cpp:118 +#, fuzzy, c-format +msgid "Bot %s is not changeable." +msgstr "Bot ist nicht im Channel %s." + +#: modules/commands/bs_bot.cpp:254 +#, fuzzy, c-format +msgid "Bot %s is not deletable." +msgstr "Bot %s wurde gelöscht." + +#: modules/commands/bs_set.cpp:141 +#, c-format +msgid "Bot bans will automatically expire after %s." +msgstr "" + +#: modules/commands/bs_set.cpp:139 +#, fuzzy +msgid "Bot bans will no longer automatically expire." +msgstr "" +"Die Services werden %s jetzt nicht mehr automatisch Op-Status geben in den " +"Channels." + +#: modules/commands/bs_bot.cpp:46 modules/commands/bs_bot.cpp:138 +#, fuzzy, c-format +msgid "Bot hosts may only be %d characters long." +msgstr "Bot Hosts dürfen nur %d Zeichen lang sein." + +#: modules/commands/bs_bot.cpp:64 modules/commands/bs_bot.cpp:167 +#, fuzzy +msgid "Bot hosts may only contain valid host characters." +msgstr "Bot Hosts dürfen nur gültige Zeichen enthalten." + +#: modules/commands/bs_bot.cpp:40 modules/commands/bs_bot.cpp:132 +#, fuzzy, c-format +msgid "Bot idents may only be %d characters long." +msgstr "Bot Idents dürfen nur %d Zeichen enthalten." + +#: modules/commands/bs_bot.cpp:58 modules/commands/bs_bot.cpp:161 +#, fuzzy +msgid "Bot idents may only contain valid ident characters." +msgstr "Bot Idents dürfen nur gültige Zeichen enthalten." + +#: include/language.h:121 +#, fuzzy, c-format +msgid "Bot is not on channel %s." +msgstr "Bot wird Ops kicken im %s." + +#: modules/commands/bs_botlist.cpp:51 +msgid "Bot list:" +msgstr "Bot-Liste:" + +#: modules/commands/bs_info.cpp:87 +msgid "Bot nick" +msgstr "Bot Nick" + +#: modules/commands/bs_bot.cpp:34 modules/commands/bs_bot.cpp:126 +#, fuzzy, c-format +msgid "Bot nicks may only be %d characters long." +msgstr "Bot Idents dürfen nur %d Zeichen enthalten." + +#: modules/commands/bs_bot.cpp:52 modules/commands/bs_bot.cpp:155 +#, fuzzy +msgid "Bot nicks may only contain valid nick characters." +msgstr "Bot Nicknamen dürfen nur gültige Zeichen enthalten." + +#: modules/commands/bs_kick.cpp:225 +#, fuzzy, c-format +msgid "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." +msgstr "" +"Der Bot wird nun bei amsgs kicken, und seetzt einen Ban\n" +"nach %d Kicks." + +#: modules/commands/bs_kick.cpp:228 +#, fuzzy, c-format +msgid "Bot will now kick for %s." +msgstr "Der Bot kickt jetzt Leute, die fett schreiben." + +#: modules/commands/bs_kick.cpp:416 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." +msgstr "" +"Der Bot wird jetzt User mit GROSSSCHRIFT kicken (es müssen allerdings\n" +"%d Zeichen und %d%% der gesamten Nachricht sein), und wird nach %d Kicks\n" +"einen Ban setzen." + +#: modules/commands/bs_kick.cpp:420 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." +msgstr "" +"Der Bot wird jetzt User mit GROSSSCHRIFT kicken (es müssen allerdings\n" +"%d Zeichen und %d%% der gesamten Nachricht sein)." + +#: modules/commands/bs_kick.cpp:551 +#, fuzzy, c-format +msgid "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." +msgstr "" +"Der Bot wird jetzt Flooder kicken (%d Zeilen in %d Sekunden), und wird nach " +"%d Kicks\n" +"einen Ban setzen." + +#: modules/commands/bs_kick.cpp:554 +#, fuzzy, c-format +msgid "Bot will now kick for flood (%d lines in %d seconds)." +msgstr "Der Bot wird jetzt Flooder kicken (%d Zeilen in %d Sekunden)." + +#: modules/commands/bs_kick.cpp:677 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Der Bot kickt jetzt User die sich wiederholen ( %d Mal das Gleiche), und " +"setzt\n" +"einen Ban nach %d Kicks." + +#: modules/commands/bs_kick.cpp:687 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." +msgstr "Der Bot kickt jetzt User die sich wiederholen ( %d Mal das Gleiche)" + +#: modules/commands/bs_kick.cpp:673 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Der Bot kickt jetzt User die sich wiederholen ( %d Mal das Gleiche), und " +"setzt\n" +"einen Ban nach %d Kicks." + +#: modules/commands/bs_kick.cpp:684 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." +msgstr "Der Bot kickt jetzt User die sich wiederholen ( %d Mal das Gleiche)" + +#: modules/commands/bs_kick.cpp:239 +#, fuzzy, c-format +msgid "Bot won't kick for %s anymore." +msgstr "Der Bot wird GROSSSCHRIFT ignorieren und nicht kicken." + +#: modules/commands/bs_kick.cpp:426 +#, fuzzy +msgid "Bot won't kick for caps anymore." +msgstr "Der Bot wird GROSSSCHRIFT ignorieren und nicht kicken." + +#: modules/commands/bs_kick.cpp:559 +#, fuzzy +msgid "Bot won't kick for flood anymore." +msgstr "Der Bot wird jetzt Flooder ignorieren und nicht kicken." + +#: modules/commands/bs_kick.cpp:694 +#, fuzzy +msgid "Bot won't kick for repeats anymore." +msgstr "" +"Der Bot ignoriert jetzt User die sich wiederholen und wird nicht kicken." + +#: modules/commands/cs_access.cpp:472 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_session.cpp:514 +msgid "By" +msgstr "" + +#: modules/commands/os_info.cpp:104 +#, fuzzy +msgid "CLEAR target" +msgstr "CLEAR Zeit" + +#: modules/commands/cs_seen.cpp:119 +#, fuzzy +msgid "CLEAR time" +msgstr "CLEAR Zeit" + +#: modules/commands/ms_cancel.cpp:19 +msgid "Cancel the last memo you sent" +msgstr "Annulliert Deine letzte gesendete Memo" + +#: modules/commands/cs_drop.cpp:19 +msgid "Cancel the registration of a channel" +msgstr "Registrierung eines Channels aufheben" + +#: modules/commands/ns_drop.cpp:20 +msgid "Cancel the registration of a nickname" +msgstr "Die Registrierung einen Nicknamen löschen" + +#: modules/commands/ms_cancel.cpp:84 +msgid "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." +msgstr "" +"Widerruft die letzte Memo die Du an den angegebenen Nicknamen\n" +"oder Channel gesendet hast, vorrausgesetzt sie ist noch nicht\n" +"gelesen worden." + +#: modules/commands/cs_clone.cpp:149 +#, fuzzy, c-format +msgid "Cannot clone channel %s to itself!" +msgstr "Bot wird Ops kicken im %s." + +#: modules/commands/ns_register.cpp:332 +msgid "Cannot send mail now; please retry a little later." +msgstr "" +"Die Services können gerade keine Mail verschicken, bitte versuche es später " +"noch einmal." + +#: modules/commands/bs_kick.cpp:1141 modules/commands/bs_kick.cpp:1143 +#: modules/commands/bs_kick.cpp:1146 +msgid "Caps kicker" +msgstr "Grossbuchstaben Kicker" + +#: modules/commands/os_shutdown.cpp:34 +msgid "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." +msgstr "" +"Veranlasst die Services, sich sofort zu beenden. Die\n" +"Datenbanken werden dabei nicht gespeichert.\n" +"Dieser Befehl sollte nicht benutzt werden, ausser\n" +"die Datenbanken sollen wirklich nicht aktualisiert\n" +"werden. Für das normale Beenden der Services sollte\n" +"der SHUTDOWN Befehl benutzt werden." + +#: modules/commands/os_reload.cpp:47 +#, fuzzy +msgid "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." +msgstr "" +"Die Services werden bei diesem Befehl die Konfigurations-\n" +"datei neu einlesen. Beachte das für einige Direktiven\n" +"trotzdem ein Neustart der Services erforderlich ist, um\n" +"sie wirksam zu machen (so wie die Services Nicknamen,\n" +"Aktivierung der Verbindungseinschränkungen, etc.)" + +#: modules/commands/os_shutdown.cpp:62 +msgid "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." +msgstr "" +"Die Services werden bei diesem Befehl die Datenbanken speichern\n" +"und danach neustarten (die ausführbare Datei erneut aufrufen)." + +#: modules/commands/os_shutdown.cpp:89 +msgid "Causes Services to save all databases and then shut down." +msgstr "" +"Die Services werden durch dieses Befehl normal\n" +"beendet und die Datenbanken werden gespeichert." + +#: modules/commands/os_update.cpp:34 +msgid "" +"Causes Services to update all database files as soon as you\n" +"send the command." +msgstr "Lässt die Services sofort die Datenbanken speichern." + +#: modules/commands/ns_cert.cpp:246 +#, fuzzy, c-format +msgid "Certificate list for %s:" +msgstr "Zertifikat-Liste von %s:" + +#: modules/commands/cs_set.cpp:528 modules/commands/cs_set.cpp:570 +msgid "ChanServ is required to enable persist on this network." +msgstr "" + +#: modules/commands/os_mode.cpp:19 +msgid "Change channel modes" +msgstr "Ändert die Raum Modi" + +#: modules/commands/ns_set.cpp:905 +msgid "Change the communication method of Services" +msgstr "Ändert die Methode, wie die Services mit Dir kommunizieren" + +#: modules/commands/os_mode.cpp:146 +#, fuzzy +msgid "Change user modes" +msgstr "Ändert die Raum Modi" + +#: modules/commands/os_mode.cpp:161 +#, c-format +msgid "Changed usermodes of %s to %s." +msgstr "Benutzermodi von %s auf %s geändert." + +#: modules/commands/ns_set.cpp:411 +#, fuzzy +msgid "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." +msgstr "" +"Ändert den virtuellen \"Anführer\" der Gruppe in den\n" +"Services. Der Wert von Neues-Display MUSS ein Nickname\n" +"in Deiner Gruppe sein.\n" +"\n" +"Hinweis: Dieser Befehl ändert keine Zugriffsrechte\n" +"des einzelnen Nicks, er wird nur als \"Ursprung\" der \n" +"Gruppe in der Liste aufgeführt." + +#: modules/commands/ns_set.cpp:387 +#, fuzzy +msgid "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." +msgstr "" +"Ändert den virtuellen \"Anführer\" Deiner Gruppe in den\n" +"Services. Der Wert von Neues-Display MUSS ein Nickname\n" +"in Deiner Gruppe sein.\n" +"\n" +"Hinweis: Dieser Befehl ändert keine Zugriffsrechte\n" +"des einzelnen Nicks, er wird nur als \"Ursprung\" der \n" +"Gruppe in der Liste aufgeführt." + +#: modules/commands/cs_set.cpp:324 +msgid "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." +msgstr "" +"Ändert den Gründer (Founder) eines Channels. Der neue\n" +"Nickname muss registriert sein." + +#: modules/commands/ns_set.cpp:884 +msgid "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Stellt die Sprache ein, mit der die Services mit einem User\n" +"kommunizieren. (Zum Beispiel in einer Antwort auf einen\n" +"Befehl den Du gesendet hast.)\n" +"\n" +"Die Sprache muss von der folgenden Liste der unter-\n" +"stützten Sprachen ausgewählt werden: " + +#: modules/commands/ns_set.cpp:848 +msgid "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Stellt die Sprache ein, mit der die Services mit Dir\n" +"kommunizieren. (Zum Beispiel in einer Antwort auf einen\n" +"Befehl den Du gesendet hast.)\n" +"\n" +"Die Sprache muss von der folgenden Liste der unter-\n" +"stützten Sprachen ausgewählt werden: " + +#: modules/commands/ns_set.cpp:227 +msgid "Changes the password used to identify as the nick's owner." +msgstr "" +"Ändert das Passwort, mit dem sich der Besitzer des\n" +"Nicknamen identifiziert." + +#: modules/commands/ns_set.cpp:161 +msgid "" +"Changes the password used to identify you as the nick's\n" +"owner." +msgstr "" +"Ändert das Passwort, mit dem Du dich als Besitzer des\n" +"Nicknamen identifizierst." + +#: modules/commands/cs_set.cpp:1017 +#, fuzzy +msgid "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." +msgstr "" +"Ändert den Vertreter des Gründers in dem Channel. Wenn\n" +"der Nickname des Gründers ausläuft oder gedropped wird,\n" +"wenn der Channel registriert ist, wird der Vertreter\n" +"der neue Gründer des Channels. Wenn jedoch der \n" +"Vertreter bereits zu viele Channels registriert hat\n" +"(max %d), wird der Channel gelöscht.\n" +"Der Nickname des Vertreters muss registriert sein." + +#: modules/commands/ns_alist.cpp:48 modules/commands/ns_ajoin.cpp:100 +#, fuzzy +msgid "Channel" +msgstr "Channel" + +#: include/language.h:84 +#, c-format +msgid "Channel %s doesn't exist." +msgstr "Raum %s existiert nicht." + +#: modules/commands/cs_drop.cpp:63 +#, c-format +msgid "Channel %s has been dropped." +msgstr "Channel %s wurde aus der Datenbank entfernt." + +#: modules/commands/cs_getkey.cpp:43 +#, c-format +msgid "Channel %s has no key." +msgstr "Der Raum %s hat keinen Schlüssel." + +#: modules/commands/cs_register.cpp:47 +#, c-format +msgid "Channel %s is already registered!" +msgstr "Der Raum %s ist bereits registriert!" + +#: modules/commands/os_forbid.cpp:524 +#, fuzzy, c-format +msgid "Channel %s is forbidden by %s: %s" +msgstr "Dieser Channel wurde registriert von %s." + +#: modules/commands/os_forbid.cpp:526 +#, fuzzy, c-format +msgid "Channel %s is forbidden." +msgstr "Der Rauml %s ist jetzt persistant." + +#: modules/commands/cs_set.cpp:580 +#, c-format +msgid "Channel %s is no longer persistent." +msgstr "Der Raum %s is nicht länger persistent." + +#: modules/commands/cs_set.cpp:542 +#, c-format +msgid "Channel %s is now persistent." +msgstr "Der Rauml %s ist jetzt persistant." + +#: modules/commands/cs_suspend.cpp:180 +#, c-format +msgid "Channel %s is now released." +msgstr "Der Channel %s ist jetzt nicht mehr auf SUSPENDED gesetzt." + +#: modules/commands/cs_suspend.cpp:125 +#, c-format +msgid "Channel %s is now suspended." +msgstr "Der Channel %s ist jetzt auf SUSPENDED gesetzt." + +#: include/language.h:83 +#, c-format +msgid "Channel %s isn't registered." +msgstr "Der Raum %s ist nicht registriert." + +#: modules/commands/cs_suspend.cpp:172 +#, fuzzy, c-format +msgid "Channel %s isn't suspended." +msgstr "Der Channel %s ist jetzt auf SUSPENDED gesetzt." + +#: modules/commands/cs_register.cpp:68 +#, c-format +msgid "Channel %s registered under your account: %s" +msgstr "Der Raum %s wurde unter deinem Account %s registriert." + +#: modules/commands/cs_set.cpp:1078 +#, c-format +msgid "Channel %s will expire." +msgstr "Der Raum %s wird nach einer bestimmten Zeit ablaufen." + +#: modules/commands/cs_set.cpp:1072 +#, c-format +msgid "Channel %s will not expire." +msgstr "Der Raum %s wird nicht mehr ablaufen." + +#: modules/commands/cs_xop.cpp:475 +#, c-format +msgid "Channel %s %s list has been cleared." +msgstr "Die %2$s-Liste von %1$s wurde geleert." + +#: modules/commands/cs_access.cpp:486 modules/commands/cs_flags.cpp:361 +#, c-format +msgid "Channel %s access list has been cleared." +msgstr "Die Access-Liste von %s wurde geleert." + +#: modules/commands/cs_akick.cpp:428 +#, c-format +msgid "Channel %s akick list has been cleared." +msgstr "Die Autokick-Liste von %s wurde geleert." + +#: modules/commands/cs_mode.cpp:444 +#, c-format +msgid "Channel %s has no mode locks." +msgstr "Der Raum %s hat keine gesperrten Modi." + +#: include/language.h:82 +#, c-format +msgid "Channel %s is currently suspended." +msgstr "Der Raum %s ist momentan auf SUSPENDED gesetzt." + +#: include/language.h:101 +#, c-format +msgid "Channel %s is not a valid channel." +msgstr "%s ist kein gültiger Raum." + +#: modules/commands/os_list.cpp:70 +msgid "Channel list:" +msgstr "Raum-Liste:" + +#: modules/extra/stats/cs_fantasy_stats.cpp:148 +#, c-format +msgid "Channel stats for %s on %s:" +msgstr "Statistiken für %s im Raum %s:" + +#: modules/commands/cs_access.cpp:142 modules/commands/cs_flags.cpp:97 +#: modules/commands/cs_xop.cpp:139 +#, fuzzy +msgid "Channels may not be on access lists." +msgstr "%s wurde nicht auf der Access-Liste von %s gefunden." + +#: modules/commands/ns_alist.cpp:114 +#, c-format +msgid "Channels that %s has access on:" +msgstr "Die Räume auf die %s Zugriff hat:" + +#: modules/commands/os_stats.cpp:181 +#, c-format +msgid "Channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:517 +#: modules/extra/stats/m_chanstats.cpp:525 +msgid "Chanstats" +msgstr "Chanstats" + +#: modules/extra/stats/m_chanstats.cpp:102 +#, fuzzy, c-format +msgid "Chanstats statistics are now disabled for %s" +msgstr "Für Deinen Nicknamen werden keine Statistiken mehr geführt." + +#: modules/extra/stats/m_chanstats.cpp:51 +#, fuzzy +msgid "Chanstats statistics are now disabled for this channel." +msgstr "Für diesen Raum werden keine Statistiken mehr geführt." + +#: modules/extra/stats/m_chanstats.cpp:104 +#, fuzzy +msgid "Chanstats statistics are now disabled for your nick." +msgstr "Für Deinen Nicknamen werden keine Statistiken mehr geführt." + +#: modules/extra/stats/m_chanstats.cpp:93 +#, fuzzy, c-format +msgid "Chanstats statistics are now enabled for %s" +msgstr "Für Deinen Nicknamen werden ab sofort Statistiken geführt." + +#: modules/extra/stats/m_chanstats.cpp:44 +#, fuzzy +msgid "Chanstats statistics are now enabled for this channel." +msgstr "Für diesen Raum werden ab sofort Statistiken geführt." + +#: modules/extra/stats/m_chanstats.cpp:95 +#, fuzzy +msgid "Chanstats statistics are now enabled for your nick." +msgstr "Für Deinen Nicknamen werden ab sofort Statistiken geführt." + +#: modules/commands/cs_seen.cpp:367 +msgid "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." +msgstr "" + +#: modules/commands/ms_check.cpp:19 +msgid "Checks if last memo to a nick was read" +msgstr "Überprüft ob Deine letzte gesendete Memo vom Empänger gelesen wurde" + +#: modules/commands/ms_check.cpp:69 +#, fuzzy +msgid "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." +msgstr "" +"Überprüft ob Deine letzte gesendete Memo an einen Benutzer gelesen\n" +"wurde. Der CHECK Befehl funktioniert nicht mit Räumen." + +#: modules/commands/os_info.cpp:227 +#, c-format +msgid "Cleared info from %s." +msgstr "" + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1153 +#: modules/commands/bs_kick.cpp:1156 +msgid "Colors kicker" +msgstr "Farb-Kicker" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Command" +msgstr "Befehle von %s:" + +#: modules/commands/bs_kick.cpp:251 +#, fuzzy +msgid "Configures AMSG kicker" +msgstr "Konfiguriert den Kicker" + +#: modules/commands/bs_kick.cpp:287 +#, fuzzy +msgid "Configures badwords kicker" +msgstr "Konfiguriert den Kicker" + +#: modules/commands/bs_kick.cpp:326 +#, fuzzy +msgid "Configures bolds kicker" +msgstr "Konfiguriert den Kicker" + +#: modules/commands/bs_kick.cpp:132 +#, fuzzy +msgid "Configures bot kickers. option can be one of:" +msgstr "" +"Syntax: SET Option Parameter\n" +"\n" +"Stellt verschiedene Optionen zu Deinem Nicknamen ein.\n" +"Option kann eines der folgenden Werte sein:" + +#: modules/commands/bs_set.cpp:19 +msgid "Configures bot options" +msgstr "Konfiguriert die Bot-Optionen" + +#: modules/commands/bs_set.cpp:32 +msgid "" +"Configures bot options.\n" +" \n" +"Available options:" +msgstr "" +"Konfiguriert die Bot-Einstellungen\n" +" \n" +"Verfügbare Optionen:" + +#: modules/commands/bs_kick.cpp:360 +#, fuzzy +msgid "Configures caps kicker" +msgstr "Konfiguriert den Kicker" + +#: modules/commands/cs_log.cpp:105 +msgid "Configures channel logging settings" +msgstr "Konfiguriert Log Einstellungen für den Channel" + +#: modules/commands/bs_kick.cpp:456 +#, fuzzy +msgid "Configures color kicker" +msgstr "Konfiguriert den Kicker" + +#: modules/commands/bs_kick.cpp:490 +#, fuzzy +msgid "Configures flood kicker" +msgstr "Konfiguriert den Kicker" + +#: modules/commands/bs_kick.cpp:588 +#, fuzzy +msgid "Configures italics kicker" +msgstr "Konfiguriert den Kicker" + +#: modules/commands/bs_kick.cpp:119 +msgid "Configures kickers" +msgstr "Konfiguriert den Kicker" + +#: modules/commands/bs_kick.cpp:622 +#, fuzzy +msgid "Configures repeat kicker" +msgstr "Konfiguriert den Kicker" + +#: modules/commands/bs_kick.cpp:723 +#, fuzzy +msgid "Configures reverses kicker" +msgstr "Konfiguriert den Kicker" + +#: modules/commands/bs_set.cpp:90 +#, fuzzy +msgid "Configures the time bot bans expire in" +msgstr "Konfiguriert die Bot-Optionen" + +#: modules/commands/bs_kick.cpp:757 +#, fuzzy +msgid "Configures underlines kicker" +msgstr "Konfiguriert den Kicker" + +#: modules/commands/ns_register.cpp:21 +#, fuzzy +msgid "Confirm a passcode" +msgstr "Bestätigt einen Authentifizierungs Code" + +#: modules/commands/cs_mode.cpp:733 +msgid "Control modes and mode locks on a channel" +msgstr "Regelt Modi und gesperrte Modi eines Raumes" + +#: modules/commands/cs_entrymsg.cpp:239 +msgid "" +"Controls what messages will be sent to users when they join the channel." +msgstr "" + +#: modules/commands/cs_clone.cpp:242 +msgid "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." +msgstr "" + +#: modules/commands/cs_clone.cpp:114 +msgid "Copy all settings from one channel to another" +msgstr "Kopiert alle Einstellungen von einem Raum zu einem anderen." + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/bs_info.cpp:57 +#: modules/commands/os_akill.cpp:358 +msgid "Created" +msgstr "Erstellt" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_ignore.cpp:266 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_news.cpp:156 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Creator" +msgstr "Erstellt" + +#: modules/commands/os_sxline.cpp:180 +#, c-format +msgid "Current %s list:" +msgstr "Aktuelle %s-Liste:" + +#: modules/commands/os_akill.cpp:323 +#, fuzzy +msgid "Current AKILL list:" +msgstr "Aktuelle %s-Liste:" + +#: modules/commands/os_session.cpp:493 +msgid "Current Session Limit Exception list:" +msgstr "Aktuelle Liste für eingeschränkte Verbindungen:" + +#: modules/commands/os_modinfo.cpp:116 +#, fuzzy +msgid "Current module list:" +msgstr "Aktuelle Module - Liste:" + +#: modules/commands/os_stats.cpp:69 +#, c-format +msgid "Current number of AKILLs: %d" +msgstr "Aktuelle Anzahl von AKILLs: %d" + +#: modules/commands/os_stats.cpp:89 +#, c-format +msgid "Current number of SNLINEs: %d" +msgstr "Aktuelle Anzahl von SNLINEs: %d" + +#: modules/commands/os_stats.cpp:109 +#, c-format +msgid "Current number of SQLINEs: %d" +msgstr "Aktuelle Anzahl von SQLINEs: %d" + +#: modules/commands/os_stats.cpp:138 +#, c-format +msgid "Current users: %d (%d ops)" +msgstr "Derzeit eingeloggte User: %d (%d Oper)" + +#: modules/commands/os_oper.cpp:71 +#, fuzzy +msgid "DEL oper" +msgstr "DEL [oper]" + +#: modules/commands/os_info.cpp:103 +#, fuzzy +msgid "DEL target info" +msgstr "Ziel Passwort" + +#: modules/commands/ns_ajoin.cpp:232 +#, fuzzy +msgid "DEL [nickname] channel" +msgstr "DEL [Benutzer] Maske" + +#: modules/commands/ns_cert.cpp:259 +#, fuzzy +msgid "DEL [nickname] fingerprint" +msgstr "Nickname Sprache" + +#: modules/commands/ns_access.cpp:103 +#, fuzzy +msgid "DEL [nickname] mask" +msgstr "DEL [Benutzer] Maske" + +#: modules/commands/os_sxline.cpp:426 modules/commands/os_sxline.cpp:660 +#: modules/commands/os_akill.cpp:387 +msgid "DEL {mask | entry-num | list | id}" +msgstr "DEL [Maske] {Nummer | Liste | id}" + +#: modules/commands/os_session.cpp:524 +#, fuzzy +msgid "DEL {mask | entry-num | list}" +msgstr "DEL [Maske] {Nummer | Liste | id}" + +#: modules/commands/os_ignore.cpp:343 +#, fuzzy +msgid "DEL {nick|mask}" +msgstr "DEL Nickname." + +#: modules/commands/os_news.cpp:279 +msgid "DEL {num | ALL}" +msgstr "DEL {Nummer | ALL}" + +#: modules/commands/os_forbid.cpp:158 +#, fuzzy +msgid "DEL {NICK|CHAN|EMAIL|REGISTER} entry" +msgstr "DEL {NICK|CHAN|EMAIL} Eintrag" + +#: modules/commands/os_dns.cpp:666 +msgid "DELIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:664 +msgid "DELSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:662 +msgid "DELZONE zone.name" +msgstr "" + +#: modules/commands/os_dns.cpp:669 +#, fuzzy +msgid "DEPOOL server.name" +msgstr "NOOP {SET|REVOKE} Server" + +#: modules/commands/cs_seen.cpp:162 +#, fuzzy, c-format +msgid "Database cleared, removed %lu nicks that were added after %s." +msgstr "" +"Datenbank gesäubert, %lu nicks, die nach dem %s hinzugefügt wurden, wurden " +"entfernt." + +#: modules/commands/ms_list.cpp:64 +msgid "Date/Time" +msgstr "" + +#: modules/commands/hs_off.cpp:49 +#, fuzzy +msgid "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." +msgstr "" +"Deaktiviert den vHost des gerade genutzten Nicknamens.\n" +"Nach der Nutzung dieses Befehls wird jeder User, der\n" +"ein /whois auf dich anwendet, Deine echte IP Adresse\n" +"sehen." + +#: modules/commands/hs_off.cpp:19 +msgid "Deactivates your assigned vhost" +msgstr "Deaktiviert Deinen vHost" + +#: modules/commands/os_stats.cpp:72 +#, c-format +msgid "Default AKILL expiry time: %d days" +msgstr "Standard Auslaufzeit von AKILLs: %d Tage" + +#: modules/commands/os_stats.cpp:76 +#, c-format +msgid "Default AKILL expiry time: %d hours" +msgstr "Standard Auslaufzeit von AKILLs: %d Stunden" + +#: modules/commands/os_stats.cpp:80 +#, c-format +msgid "Default AKILL expiry time: %d minutes" +msgstr "Standard Auslaufzeit von AKILLs: %d Minuten" + +#: modules/commands/os_stats.cpp:74 +msgid "Default AKILL expiry time: 1 day" +msgstr "Standard Auslaufzeit von AKILLs: 1 Tag" + +#: modules/commands/os_stats.cpp:78 +msgid "Default AKILL expiry time: 1 hour" +msgstr "Standard Auslaufzeit von AKILLs: 1 Stunde" + +#: modules/commands/os_stats.cpp:82 +msgid "Default AKILL expiry time: 1 minute" +msgstr "Standard Auslaufzeit von AKILLs: 1 Minute" + +#: modules/commands/os_stats.cpp:84 +msgid "Default AKILL expiry time: No expiration" +msgstr "Standard Auslaufzeit von AKILLs: Kein Auslauf, permanent" + +#: modules/commands/os_stats.cpp:92 +#, c-format +msgid "Default SNLINE expiry time: %d days" +msgstr "Standard Auslaufzeit von SNLINEs: %d Tage" + +#: modules/commands/os_stats.cpp:96 +#, c-format +msgid "Default SNLINE expiry time: %d hours" +msgstr "Standard Auslaufzeit von SNLINEs: %d Stunden" + +#: modules/commands/os_stats.cpp:100 +#, c-format +msgid "Default SNLINE expiry time: %d minutes" +msgstr "Standard Auslaufzeit von SNLINEs: %d Minuten" + +#: modules/commands/os_stats.cpp:94 +msgid "Default SNLINE expiry time: 1 day" +msgstr "Standard Auslaufzeit von SNLINEs: 1 Tag" + +#: modules/commands/os_stats.cpp:98 +msgid "Default SNLINE expiry time: 1 hour" +msgstr "Standard Auslaufzeit von SNLINEs: 1 Stunde" + +#: modules/commands/os_stats.cpp:102 +msgid "Default SNLINE expiry time: 1 minute" +msgstr "Standard Auslaufzeit von SNLINEs: 1 Minute" + +#: modules/commands/os_stats.cpp:104 +msgid "Default SNLINE expiry time: No expiration" +msgstr "Standard Auslaufzeit von SNLINEs: Kein Auslauf, permanent" + +#: modules/commands/os_stats.cpp:112 +#, c-format +msgid "Default SQLINE expiry time: %d days" +msgstr "Standard Auslaufzeit von SQLINEs: %d Tage" + +#: modules/commands/os_stats.cpp:116 +#, c-format +msgid "Default SQLINE expiry time: %d hours" +msgstr "Standard Auslaufzeit von SQLINEs: %d Stunden" + +#: modules/commands/os_stats.cpp:120 +#, c-format +msgid "Default SQLINE expiry time: %d minutes" +msgstr "Standard Auslaufzeit von SQLINEs: %d Minuten" + +#: modules/commands/os_stats.cpp:114 +msgid "Default SQLINE expiry time: 1 day" +msgstr "Standard Auslaufzeit von SQLINEs: 1 Tag" + +#: modules/commands/os_stats.cpp:118 +msgid "Default SQLINE expiry time: 1 hour" +msgstr "Standard Auslaufzeit von SQLINEs: 1 Stunde" + +#: modules/commands/os_stats.cpp:122 +msgid "Default SQLINE expiry time: 1 minute" +msgstr "Standard Auslaufzeit von SQLINEs: 1 Minuten" + +#: modules/commands/os_stats.cpp:124 +msgid "Default SQLINE expiry time: No expiration" +msgstr "Standard Auslaufzeit von SQLINEs: Kein Auslauf, permanent" + +#: modules/commands/os_news.cpp:351 +msgid "Define messages to be randomly shown to users at logon" +msgstr "Zufalls-News bearbeiten, die beim Einloggen angezeigt werden." + +#: modules/commands/os_news.cpp:297 +msgid "Define messages to be shown to users at logon" +msgstr "Logon-News bearbeiten" + +#: modules/commands/os_news.cpp:324 +msgid "Define messages to be shown to users who oper" +msgstr "Oper News bearbeiten" + +#: modules/commands/ms_del.cpp:44 +msgid "Delete a memo or memos" +msgstr "Löschen einer oder mehrerer Memos" + +#: modules/commands/hs_del.cpp:19 +msgid "Delete the vhost of another user" +msgstr "Löscht den vHost eines anderen Benutzers" + +#: modules/commands/cs_xop.cpp:302 +#, c-format +msgid "Deleted %d entries from %s %s list." +msgstr "%d Einträge wurden aus der %s %s-Liste entfernt." + +#: modules/commands/cs_access.cpp:277 +#, c-format +msgid "Deleted %d entries from %s access list." +msgstr "%d Einträge wurden aus der Access-Liste von %s entfernt." + +#: modules/commands/cs_akick.cpp:228 +#, c-format +msgid "Deleted %d entries from %s autokick list." +msgstr "%d Einträge wurden aus der AutoKick-Liste von %s entfernt." + +#: modules/commands/bs_badwords.cpp:170 +#, c-format +msgid "Deleted %d entries from %s bad words list." +msgstr "%d Einträge wurden aus der Bad Words-Liste von %s entfernt." + +#: modules/commands/os_session.cpp:149 +#, c-format +msgid "Deleted %d entries from session-limit exception list." +msgstr "" +"Es wurden %d Einträge von der Liste der Verbindungs-\n" +"einschränkungen entfernt." + +#: modules/commands/os_sxline.cpp:32 +#, c-format +msgid "Deleted %d entries from the %s list." +msgstr "%d Einträge wurden aus der %s-Liste entfernt." + +#: modules/commands/os_akill.cpp:33 +#, c-format +msgid "Deleted %d entries from the AKILL list." +msgstr "Es wurden %d Einträge aus der AKILL-Liste entfernt." + +#: modules/commands/cs_access.cpp:275 +#, c-format +msgid "Deleted 1 entry from %s access list." +msgstr "1 Eintrag wurde aus der Access-Liste von %s entfernt." + +#: modules/commands/cs_akick.cpp:226 +#, c-format +msgid "Deleted 1 entry from %s autokick list." +msgstr "1 Eintrag der AutoKick-Liste von %s entfernt." + +#: modules/commands/bs_badwords.cpp:168 +#, c-format +msgid "Deleted 1 entry from %s bad words list." +msgstr "1 Eintrag wurde aus der Bad Words-Liste von %s entfernt." + +#: modules/commands/os_session.cpp:147 +msgid "Deleted 1 entry from session-limit exception list." +msgstr "" +"Es wurde 1 Eintrag von der Liste der Verbindungs-\n" +"einschränkungen entfernt." + +#: modules/commands/os_sxline.cpp:30 +#, c-format +msgid "Deleted 1 entry from the %s list." +msgstr "Es wurde 1 Eintrag aus der %s Liste entfernt." + +#: modules/commands/os_akill.cpp:31 +msgid "Deleted 1 entry from the AKILL list." +msgstr "Es wurde 1 Eintrag aus der AKILL-Liste entfernt." + +#: modules/commands/os_info.cpp:208 +#, fuzzy, c-format +msgid "Deleted info from %s." +msgstr "Es wurde 1 Eintrag aus der %s Liste entfernt." + +#: modules/commands/cs_xop.cpp:300 +#, c-format +msgid "Deleted one entry from %s %s list." +msgstr "Ein Eintrag wurde aus der %s %s-Liste entfernt." + +#: modules/commands/ms_del.cpp:129 +msgid "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Entfernt Memos aus Deinem Postfach. Du kannst mehrere\n" +"Nummern oder Bereiche angeben anstatt einer einzelnen\n" +"Nummer, wie das zweite Beispiel zeigt.\n" +"\n" +"Wird LAST angegeben, wird die letzte Memo gelöscht.\n" +"Wird ALL angegeben, werden alle Deine Memos\n" +"entfernt.\n" +"\n" +"Beispiele:\n" +"\n" +" DEL 1\n" +" Löscht Dein Memo mit der Nummer 1.\n" +"\n" +" DEL 2-5,7-9\n" +" Löscht Memos mit den Nummern 2 bis 5 und 7 bis 9." + +#: modules/commands/hs_del.cpp:48 +msgid "" +"Deletes the vhost assigned to the given nick from the\n" +"database." +msgstr "Löscht den vHost des angegebenen Nicknamens." + +#: modules/commands/hs_del.cpp:59 +#, fuzzy +msgid "Deletes the vhost for all nicks in a group" +msgstr "Löscht den vHost aller Nicknamen in einer Gruppe" + +#: modules/commands/hs_del.cpp:93 +msgid "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." +msgstr "" +"Löscht den vHost aller Nicknamen aus der gleichen Gruppe \n" +"des angegeben Nicknamens." + +#: modules/commands/os_dns.cpp:653 +#, c-format +msgid "Depooled %s." +msgstr "" + +#: modules/commands/cs_access.cpp:799 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_list.cpp:75 modules/commands/cs_info.cpp:53 +#, fuzzy +msgid "Description" +msgstr "Die Beschreibung von %s wurde entfernt." + +#: modules/commands/cs_set.cpp:239 +#, c-format +msgid "Description of %s changed to %s." +msgstr "Beschreibung von %s wurde geändert zu %s." + +#: modules/commands/cs_set.cpp:245 +#, c-format +msgid "Description of %s unset." +msgstr "Die Beschreibung von %s wurde entfernt." + +#: modules/commands/bs_kick.cpp:1115 modules/commands/bs_info.cpp:90 +msgid "Disabled" +msgstr "Deaktiviert" + +#: modules/commands/cs_suspend.cpp:134 +#, fuzzy +msgid "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." +msgstr "" +"Verbietet jegliche Nutzung des Channels. Kann durch\n" +"den UNSUSPEND Befehls wieder aufgehoben werden,\n" +"wobei alle vorherigen Einstellungen wieder übernommen\n" +"werden.\n" +"\n" +"Ein Grund kann auf manchen Netzwerke notwendig sein." + +#: modules/commands/hs_request.cpp:337 +#, fuzzy, c-format +msgid "Displayed %d records (%d total)." +msgstr "Liste alle Einträge. (Count: %d)" + +#: modules/commands/hs_list.cpp:122 +#, fuzzy, c-format +msgid "Displayed all records (count: %d)." +msgstr "Liste alle Einträge. (Count: %d)" + +#: modules/commands/hs_list.cpp:120 +#, fuzzy, c-format +msgid "Displayed records from %d to %d." +msgstr "Einträge von %d bis %d" + +#: modules/commands/hs_list.cpp:116 +#, fuzzy, c-format +msgid "Displayed records matching key %s (count: %d)." +msgstr "Auf das Muster %s passenden Einträge. (Count: %d)" + +#: modules/commands/ns_info.cpp:19 +msgid "Displays information about a given nickname" +msgstr "Zeigt Informationen über den angegebenen Nicknamen" + +#: modules/commands/ns_info.cpp:125 +msgid "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." +msgstr "" +"Zeigt Informationen über den angegebenen Nickname, zum\n" +"Beispiel den Besitzer des Nicknamens, die letzte gesehene\n" +"Adresse und dessen Uhrzeit und die Optionen des Nicknamens." + +#: modules/commands/ms_info.cpp:19 +msgid "Displays information about your memos" +msgstr "Zeigt Informationen bezüglich Deiner Memos an" + +#: modules/commands/hs_list.cpp:19 +#, fuzzy +msgid "Displays one or more vhost entries" +msgstr "Zeigt einen oder mehrere vHost Einträge an" + +#: modules/extra/stats/cs_fantasy_top.cpp:50 +msgid "Displays the top 10 users of a channel" +msgstr "Zeigt die Top 10 Benutzer des Raumes an" + +#: modules/extra/stats/cs_fantasy_top.cpp:73 +msgid "Displays the top 10 users of the network" +msgstr "Zeigt die Top 10 Benutzer im Netzwerk an" + +#: modules/extra/stats/cs_fantasy_top.cpp:38 +msgid "Displays the top 3 users of a channel" +msgstr "Zeigt die Top 3 Benutzer des Raumes an" + +#: modules/extra/stats/cs_fantasy_top.cpp:62 +msgid "Displays the top 3 users of the network" +msgstr "Zeigt die Top 3 Benutzer im Netzwerk an" + +#: modules/commands/help.cpp:33 +msgid "Displays this list and give information about commands" +msgstr "Zeigt Informationen bezüglich Deiner Memos an" + +#: modules/extra/stats/cs_fantasy_stats.cpp:39 +msgid "Displays your Channel Stats" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:51 +msgid "Displays your Global Stats" +msgstr "" + +#: modules/commands/bs_kick.cpp:1463 +msgid "Don't use AMSGs!" +msgstr "Benutze keine AMSGs!" + +#: modules/commands/bs_kick.cpp:1266 +msgid "Don't use bolds on this channel!" +msgstr "Im Channel ist keine fettgedruckte-Schrift erlaubt!" + +#: modules/commands/bs_kick.cpp:1274 +msgid "Don't use colors on this channel!" +msgstr "Keine Farben im Channel benutzen!" + +#: modules/commands/bs_kick.cpp:1290 +msgid "Don't use italics on this channel!" +msgstr "Don't use italics on this channel!" + +#: modules/commands/bs_kick.cpp:1282 +msgid "Don't use reverses on this channel!" +msgstr "Nicht invertiert schreiben!" + +#: modules/commands/bs_kick.cpp:1408 +#, c-format +msgid "Don't use the word \"%s\" on this channel!" +msgstr "Benutze nicht das Wort %s in diesem Channel!" + +#: modules/commands/bs_kick.cpp:1298 +msgid "Don't use underlines on this channel!" +msgstr "Keine Unterstreichungen in diesem Channel benutzen!" + +#: modules/commands/ns_drop.cpp:61 +msgid "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." +msgstr "" + +#: modules/commands/ns_set.cpp:513 +#, c-format +msgid "E-mail address for %s changed to %s." +msgstr "E-mail Adresse für %s wurde auf %s geändert." + +#: modules/commands/ns_set.cpp:519 +#, c-format +msgid "E-mail address for %s unset." +msgstr "E-mail Adresse %s wurde entfernt." + +#: src/mail.cpp:80 +#, c-format +msgid "E-mail for %s is invalid." +msgstr "E-mail-Adresse für %s ist ungültig." + +#: modules/commands/os_news.cpp:309 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Zeigt oder bearbeitet die Liste der LogonNews.\n" +"Nach der Verbindung des Users werden diese Nachrichten\n" +"angezeigt. (Es werden jedoch nur max. %d angezeigt, um ein\n" +"Flooding des Users zu verhindern. Wenn mehr News\n" +"existieren, werden nur die neuesten angezeigt.)\n" +"NewsCount kann in der services.conf eingestellt werden.\n" +"\n" +"Diese Funktion ist beschränkt auf Services Operatoren." + +#: modules/commands/os_news.cpp:336 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Zeigt oder bearbeitet die Liste der Oper-News.Nachdem \n" +"sich ein User die Oper-Flags gesetzt hat (mit dem\n" +"/OPER Befehl) werden ihm diese Nachrichten angezeigt.\n" +"(Es werden jedoch nur max. %d Nachrichten angezeigt, um ein\n" +"Flooding des Users zu verhindern. Wenn mehr News\n" +"existieren, werden nur die neüsten angezeigt.)\n" +"NewsCount can be configured in services.conf.\n" +"\n" +"Diese Funktion ist beschränkt auf Services Operatoren." + +#: modules/commands/os_news.cpp:363 +#, fuzzy +msgid "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." +msgstr "" +"Bearbeitet die Liste der RandomNews Nachrichten oder zeigt diese an.\n" +"Wenn ein User zum Netzwerk verbindet, wird eine (und nur eine!) dieser\n" +"RandomNews Nachrichten zufällig gewählt und an den User gesendet.\n" +"\n" +"Diese Funktion ist beschränkt auf Services Operatoren." + +#: modules/commands/ns_info.cpp:98 +msgid "Email address" +msgstr "E-mail-Adresse" + +#: modules/commands/ns_getemail.cpp:41 +#, fuzzy, c-format +msgid "Email matched: %s (%s) to %s." +msgstr "Passende Emails %s bis %s." + +#: modules/fantasy.cpp:19 +msgid "Enable fantaisist commands" +msgstr "" + +#: modules/commands/greet.cpp:19 +msgid "Enable greet messages" +msgstr "" + +#: modules/commands/ns_set.cpp:568 +msgid "Enable or disable keep modes" +msgstr "" + +#: modules/commands/bs_kick.cpp:1114 modules/commands/bs_info.cpp:89 +msgid "Enabled" +msgstr "Aktiviert" + +#: modules/commands/cs_set.cpp:124 +#, fuzzy, c-format +msgid "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." +msgstr "" +"Ändert die Secure-Ops Option für einen Channel.\n" +"Wird diese Option eingeschaltet, können Nicknamen, \n" +"die nicht auf der Zugriffsliste des Channels stehen, \n" +"keinen Op-Status erhalten." + +#: modules/commands/cs_set.cpp:388 +#, fuzzy +msgid "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." +msgstr "" +"Aktiviert oder deaktiviert die Topic Wiederherstellung für\n" +"den Raum. Wird %s eingeschaltet, wird das \n" +"Topic des Chatraumes durch %s gespeichert. Selbst wenn \n" +"der letzte Benutzer den Chatraum verlässt, wird es \n" +"wiederhergestellt sobald jemand wieder in den Raum \n" +"kommt." + +#: modules/commands/ns_set.cpp:643 +msgid "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." +msgstr "" + +#: modules/commands/ns_set.cpp:618 +msgid "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." +msgstr "" + +#: modules/commands/cs_set.cpp:733 +#, fuzzy +msgid "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." +msgstr "" +"Aktiviert oder deaktiviert die Sicherheitsfunktionen\n" +"für den angegebenen Channel. \n" +"Wird %s eingeschaltet, werden nur registrierte\n" +"und identifizierte Nicknamen in den Channel gelassen,\n" +"so wie es in der Zugriffsliste des Channels steht." + +#: modules/commands/cs_set.cpp:932 +msgid "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." +msgstr "" +"Aktiviert oder deaktiviert signierte Kicks für einen\n" +"Channel. Ist SIGNKICK aktiviert, wird der Grund\n" +"eines Kicks der durch %s KICK ausgeführt wurde, durch\n" +"den Nicknamen des Kickers signiert.\n" +"\n" +"Wird LEVEL benutzt, werden Kicks durch Nicknamen\n" +"deren Level grösser oder gleich dem SIGNKICK Level ist,\n" +"nicht durch den Nicknamen signiert.\n" +"Siehe /msg %s HELP LEVELS für weitere Informationen." + +#: modules/commands/cs_set.cpp:452 +#, c-format +msgid "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." +msgstr "" +"Aktiviert oder deaktiviert die peace Option. Wenn\n" +"peace aktiviert ist, kann ein User einen anderen User\n" +"mit gleichem oder höherem Zugriffslevel nicht mehr per \n" +"%s kicken, bannen oder dessen Channelstatus löschen." + +#: modules/commands/cs_list.cpp:232 +msgid "Enables or disables the private option for a channel." +msgstr "" + +#: modules/commands/cs_set.cpp:671 +msgid "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." +msgstr "" +"Aktiviert oder deaktiviert den Restricted Access Modus\n" +"in einem Raum. Wenn der Restricted Access Modus aktiviert\n" +"ist, werden alle Benutzer, die nicht in der ACCESS Liste stehen,\n" +"aus dem Raum geworfen und gebannt." + +#: modules/commands/cs_set.cpp:796 +msgid "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." +msgstr "" +"Aktiviert oder deaktiviert die Secure Founder-Option\n" +"für einen Channel.\n" +"Wird diese Option eingeschaltet, kann nur der \"echte\"\n" +"Gründer des Channels diesen löschen, den Gründer und den\n" +"Successor verändern und nicht derjenige, der Founder-Zugriff \n" +"durch den Zugriffslevel bzw. QOP hat." + +#: modules/commands/cs_set.cpp:860 +#, fuzzy +msgid "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." +msgstr "" +"Ändert die Secure-Ops Option für einen Channel.\n" +"Wird diese Option eingeschaltet, können Nicknamen, \n" +"die nicht auf der Zugriffsliste des Channels stehen, \n" +"keinen Op-Status erhalten." + +#: modules/commands/cs_topic.cpp:70 +#, c-format +msgid "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." +msgstr "" +"Aktiviert oder deaktiviert die Topic Wiederherstellung für\n" +"den Raum. Wird %s eingeschaltet, wird das \n" +"Topic des Chatraumes durch %s gespeichert. Selbst wenn \n" +"der letzte Benutzer den Chatraum verlässt, wird es \n" +"wiederhergestellt sobald jemand wieder in den Raum \n" +"kommt." + +#: modules/commands/cs_set.cpp:592 +#, fuzzy, c-format +msgid "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." +msgstr "" +"Syntax: %s channel PERSIST {ON | OFF}\n" +"Enables or disables the persistant channel setting.\n" +"When persistant is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +"\n" +"If your IRCd does not a permanent (persistant) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +"\n" +"If this network does not have BotServ enabled and does\n" +"not have a permanent channel mode, ChanServ will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +"\n" +"If your IRCd has a permanent (persistant) channel mode\n" +"and is is set or unset (for any reason, including MLOCK),\n" +"persist is automatically set and unset for the channel aswell.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." + +#: modules/commands/os_akill.cpp:331 +#, fuzzy +msgid "End of AKILL list." +msgstr "Ende der User-Liste." + +#: modules/commands/cs_access.cpp:444 +msgid "End of access list" +msgstr "Ende der Zugangsliste." + +#: modules/commands/cs_flags.cpp:347 +#, c-format +msgid "End of access list - %d/%d entries shown." +msgstr "Ende der Zugangsliste - %d/%d Treffer angezeigt." + +#: modules/commands/cs_flags.cpp:345 +msgid "End of access list." +msgstr "Ende der Zugangsliste." + +#: modules/commands/cs_akick.cpp:379 +msgid "End of autokick list" +msgstr "Ende der Autokick-liste." + +#: modules/commands/bs_badwords.cpp:257 +#, fuzzy +msgid "End of bad words list." +msgstr "Ende der Badword-Liste." + +#: modules/commands/os_list.cpp:100 +#, fuzzy, c-format +msgid "End of channel list. %u channels shown." +msgstr "Ende der Liste - %d/%d Treffer angezeigt." + +#: modules/commands/os_config.cpp:117 +msgid "End of configuration." +msgstr "Ende der Konfiguration." + +#: modules/commands/cs_entrymsg.cpp:134 +msgid "End of entry message list." +msgstr "Ende der Begrüssungsnachricht-Liste." + +#: modules/commands/os_forbid.cpp:407 +#, fuzzy, c-format +msgid "End of forbid list - %d/%d entries shown." +msgstr "Ende der Zugangsliste - %d/%d Treffer angezeigt." + +#: modules/commands/os_forbid.cpp:405 +msgid "End of forbid list." +msgstr "Ende der FORBID-Liste." + +#: modules/commands/ns_alist.cpp:119 +#, fuzzy, c-format +msgid "End of list - %d channels shown." +msgstr "Ende der Liste - %d/%d Treffer angezeigt." + +#: modules/commands/ns_list.cpp:131 modules/commands/cs_list.cpp:130 +#, c-format +msgid "End of list - %d/%d matches shown." +msgstr "Ende der Liste - %d/%d Treffer angezeigt." + +#: modules/commands/os_news.cpp:176 +#, fuzzy +msgid "End of news list." +msgstr "Ende der News-Liste." + +#: modules/commands/os_list.cpp:235 +#, fuzzy, c-format +msgid "End of users list. %u users shown." +msgstr "Ende der Zugangsliste - %d/%d Treffer angezeigt." + +#: modules/commands/cs_enforce.cpp:227 +msgid "Enforce various channel modes and set options" +msgstr "" + +#: modules/commands/cs_enforce.cpp:263 +msgid "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." +msgstr "" + +#: src/language.cpp:43 modules/commands/ns_set.cpp:836 +#: modules/commands/ns_set.cpp:856 modules/commands/ns_set.cpp:891 +msgid "English" +msgstr "Deutsch" + +#: modules/commands/cs_entrymsg.cpp:170 +#, c-format +msgid "Entry message %i for %s deleted." +msgstr "Begrüssungsnachricht %i für %s wurde entfernt." + +#: modules/commands/cs_entrymsg.cpp:177 +#, c-format +msgid "Entry message %s not found on channel %s." +msgstr "Begrüssungsnachricht %s wurde im Raum %s nicht gefunden.." + +#: modules/commands/cs_entrymsg.cpp:147 +#, c-format +msgid "Entry message added to %s" +msgstr "Begrüssungsnachricht wurde %s hinzugefügt." + +#: modules/commands/cs_entrymsg.cpp:109 modules/commands/cs_entrymsg.cpp:158 +#, c-format +msgid "Entry message list for %s is empty." +msgstr "Keine Begrüssungsnachrichten für %s gesetzt." + +#: modules/commands/cs_entrymsg.cpp:113 +#, c-format +msgid "Entry message list for %s:" +msgstr "Begrüssungsnachrichten für %s:" + +#: modules/commands/cs_entrymsg.cpp:187 +#, c-format +msgid "Entry messages for %s have been cleared." +msgstr "Alle Begrüssungsnachrichten für %s wurden gelöscht." + +#: modules/commands/os_reload.cpp:39 +#, fuzzy, c-format +msgid "Error reloading configuration file: %s" +msgstr "Fehler beim Einlesen der Konfigurationsdatei: " + +#: include/language.h:125 +#, fuzzy, c-format +msgid "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." +msgstr "Fehler! Der Ident ist zu lang, er darf maximal %d Zeichen lang sein." + +#: include/language.h:124 +#, fuzzy, c-format +msgid "" +"Error! The vHost is too long, please use a hostname shorter than %d " +"characters." +msgstr "Fehler! Der Vhost ist zu lang, er darf maximal %d Zeichen lang sein." + +#: modules/commands/ns_cert.cpp:325 +msgid "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." +msgstr "" + +#: modules/commands/os_session.cpp:358 +#, c-format +msgid "Exception for %s has been updated to %d." +msgstr "Ausnahme für %s ist zu %d aktualisiert worden." + +#: modules/pseudoclients/chanserv.cpp:465 +#: modules/pseudoclients/nickserv.cpp:557 +#: modules/pseudoclients/nickserv.cpp:562 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_session.cpp:514 modules/commands/ns_group.cpp:327 +#: modules/commands/os_akill.cpp:358 +msgid "Expires" +msgstr "Läuft ab" + +#: src/xline.cpp:397 +#, c-format +msgid "Expiry and reason updated for %s." +msgstr "Ablaufzeit und Grund wurden für %s aktualisiert." + +#: src/xline.cpp:400 +#, c-format +msgid "Expiry for %s updated." +msgstr "Ablaufzeit von %s geändert." + +#: modules/fantasy.cpp:214 +msgid "Fantasy" +msgstr "Fantasy-Modus" + +#: modules/fantasy.cpp:60 +#, c-format +msgid "Fantasy mode is now off on channel %s." +msgstr "Fantasy Modus ist jetzt AUS im %s." + +#: modules/fantasy.cpp:52 +#, c-format +msgid "Fantasy mode is now on on channel %s." +msgstr "Fantasy Modus ist jetzt ON im %s." + +#: modules/commands/cs_status.cpp:19 +#, fuzzy +msgid "Find a user's status on a channel" +msgstr " DEOWNER Entfernt Dein Gründer Status in einen Channel" + +#: modules/commands/ns_cert.cpp:192 +#, fuzzy, c-format +msgid "Fingerprint %s already present on %s's certificate list." +msgstr "%s ist bereits auf der Zertifikat-Liste." + +#: modules/commands/ns_cert.cpp:198 +#, fuzzy, c-format +msgid "Fingerprint %s is already in use." +msgstr "%s ist bereits in %s! " + +#: modules/commands/cs_flags.cpp:301 +msgid "Flags" +msgstr "" + +#: modules/commands/cs_flags.cpp:286 +#, fuzzy, c-format +msgid "Flags for %s on %s set to +%s" +msgstr "Zugriffs-Level für %s in %s wurde auf +%s geändert." + +#: modules/commands/cs_flags.cpp:341 +#, c-format +msgid "Flags list for %s" +msgstr "Flags-Liste von %s:" + +#: modules/commands/bs_kick.cpp:1161 modules/commands/bs_kick.cpp:1163 +#: modules/commands/bs_kick.cpp:1166 +msgid "Flood kicker" +msgstr "Flood kicker" + +#: modules/commands/os_forbid.cpp:421 +msgid "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." +msgstr "" +"FORBID erlaubt Dir die Benutzung von Nicknamen, Chaträumen und\n" +"Mail-Adressen zu verbieten. Platzhalter sind erlaubt." + +#: modules/commands/os_forbid.cpp:354 +msgid "Forbid list is empty." +msgstr "Verbotsliste ist leer." + +#: modules/commands/os_forbid.cpp:396 +msgid "Forbid list:" +msgstr "Verbotsliste:" + +#: modules/commands/os_forbid.cpp:348 +#, c-format +msgid "Forbid on %s was not found." +msgstr "Kein Verbot für %s gefunden." + +#: modules/commands/os_forbid.cpp:156 +msgid "Forbid usage of nicknames, channels, and emails" +msgstr "Verbietet die Benutzung von Nicknamen, Chaträumen und Mail-Adressen" + +#: modules/commands/os_update.cpp:19 +msgid "Force the Services databases to be updated immediately" +msgstr "Die Services Datenbanken sofort speichern" + +#: modules/commands/os_svs.cpp:19 +msgid "Forcefully change a user's nickname" +msgstr "Erzwingt die Änderung eines Nicknamen" + +#: modules/commands/os_svs.cpp:68 +#, fuzzy +msgid "Forcefully changes a user's nickname from nick to newnick." +msgstr "" +"Erzwingt die Änderung des Nicknamens eines User zu dem neuen Nicknamen." + +#: modules/commands/os_svs.cpp:78 +#, fuzzy +msgid "Forcefully join a user to a channel" +msgstr "Erzwingt einen Nicknamen wechsel" + +#: modules/commands/os_svs.cpp:112 +#, fuzzy +msgid "Forcefully join a user to a channel." +msgstr "Erzwingt einen Nicknamen wechsel" + +#: modules/commands/os_svs.cpp:122 +#, fuzzy +msgid "Forcefully part a user from a channel" +msgstr "Kickt einen Benutzer aus einem Raum." + +#: modules/commands/os_svs.cpp:160 +#, fuzzy +msgid "Forcefully part a user from a channel." +msgstr "Kickt einen Benutzer aus einem Raum." + +#: modules/commands/ns_alist.cpp:64 modules/commands/cs_info.cpp:47 +#, fuzzy +msgid "Founder" +msgstr "Sicher Founder" + +#: modules/commands/cs_set.cpp:315 +#, c-format +msgid "Founder of %s changed to %s." +msgstr "Neuer Gründer %s ist jetzt %s." + +#: modules/commands/ns_getpass.cpp:41 +msgid "GETPASS command unavailable because encryption is in use." +msgstr "GETPASS nicht verfügbar, da die Verschlüsselung aktiviert ist." + +#: modules/commands/ns_recover.cpp:84 +msgid "Ghost with your nick has been killed." +msgstr "Ghost mit Deinem Nicknamen wurde entfernt." + +#: modules/commands/os_oline.cpp:19 +msgid "Give Operflags to a certain user" +msgstr "Einem User \"Operflags\" setzen" + +#: modules/commands/cs_mode.cpp:905 +#, c-format +msgid "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." +msgstr "" + +#: modules/commands/cs_mode.cpp:888 +#, fuzzy, c-format +msgid "Gives you or the specified nick %s status on a channel" +msgstr "Gibt Dir Gründer Status in einem Chatraum" + +#: modules/commands/greet.cpp:206 modules/commands/greet.cpp:212 +msgid "Greet" +msgstr "Begrüssungsnachricht" + +#: src/access.cpp:38 +#, fuzzy +msgid "Greet message displayed on join" +msgstr "Begrüssungsnachricht %s wurde auf %s geändert." + +#: modules/commands/greet.cpp:112 +#, c-format +msgid "Greet message for %s changed to %s." +msgstr "Begrüssungsnachricht %s wurde auf %s geändert." + +#: modules/commands/greet.cpp:118 +#, c-format +msgid "Greet message for %s unset." +msgstr "Begrüssungsnachricht %s wurde entfernt." + +#: modules/commands/greet.cpp:60 +#, c-format +msgid "Greet mode is now off on channel %s." +msgstr "Begrüssungsnachrichten sind jetzt im %s DEAKTIVIERT." + +#: modules/commands/greet.cpp:52 +#, c-format +msgid "Greet mode is now on on channel %s." +msgstr "Begrüssungsnachrichten sind jetzt im %s AKTIVIERT." + +#: modules/commands/ns_resetpass.cpp:21 +msgid "Helps you reset lost passwords" +msgstr "Hift Dir, verlorene Passwörter zurückzusetzen" + +#: modules/commands/ns_info.cpp:141 +msgid "Hide certain pieces of nickname information" +msgstr "Verbirgt bestimmte Informationen Deines Nicknamens" + +#: modules/commands/cs_list.cpp:180 +#, fuzzy +msgid "Hide channel from the LIST command" +msgstr "Versteckt den Channel vom LIST-Befehl." + +#: modules/commands/os_session.cpp:192 +#, fuzzy +msgid "Host" +msgstr "vHost" + +#: modules/commands/os_session.cpp:207 +#, c-format +msgid "Hosts with at least %d sessions:" +msgstr "Hosts mit mindestens %d Verbindungen:" + +#: modules/commands/cs_seen.cpp:207 +#, c-format +msgid "I don't know who %s is." +msgstr "" + +#: modules/commands/cs_seen.cpp:253 +#, fuzzy, c-format +msgid "I've never seen %s on this channel." +msgstr "Nicht invertiert schreiben!" + +#: modules/commands/os_sxline.cpp:203 modules/commands/os_akill.cpp:360 +msgid "ID" +msgstr "" + +#: modules/commands/os_oper.cpp:72 +msgid "INFO [type]" +msgstr "" + +#: modules/commands/os_dns.cpp:218 +msgid "IP" +msgstr "" + +#: modules/commands/os_dns.cpp:500 +#, fuzzy, c-format +msgid "IP %s already exists for %s." +msgstr "%s existiert bereits." + +#: modules/commands/os_dns.cpp:562 +#, fuzzy, c-format +msgid "IP %s does not exist for %s." +msgstr "Bot %s existiert bereits." + +#: modules/commands/ns_identify.cpp:65 +msgid "Identify yourself with your password" +msgstr "Melde dich mit deinem Passwort an" + +#: modules/pseudoclients/nickserv.cpp:205 +#: modules/pseudoclients/nickserv.cpp:211 +#, fuzzy, c-format +msgid "If you do not change within %s, I will change your nick." +msgstr "" +"Wenn Du ihn nicht innerhalb von 20 Sekunden identifizierst, wird er " +"automatisch geändert." + +#: modules/commands/os_ignore.cpp:333 +msgid "Ignore list has been cleared." +msgstr "Die Ignore-Liste wurde geleert." + +#: modules/commands/os_ignore.cpp:262 +msgid "Ignore list is empty." +msgstr "Ignore-Liste ist leer." + +#: modules/commands/ms_ignore.cpp:94 +msgid "Ignore list:" +msgstr "Ignore Liste:" + +#: modules/commands/ns_set.cpp:1305 +#, fuzzy +msgid "Immediate protection" +msgstr "Voice-Schutz" + +#: modules/commands/ns_resetpass.cpp:33 +#, fuzzy +msgid "Incorrect email address." +msgstr "E-mail-Adresse" + +#: include/language.h:89 +msgid "Incorrect range specified. The correct syntax is #from-to." +msgstr "" + +#: modules/commands/os_modinfo.cpp:19 +msgid "Info about a loaded module" +msgstr "Info über ein geladenes Modul" + +#: modules/commands/bs_info.cpp:54 +#, c-format +msgid "Information for bot %s:" +msgstr "Information vom Bot %s:" + +#: include/language.h:108 +#, c-format +msgid "Information for channel %s:" +msgstr "Information für den Raum %s:" + +#: modules/commands/os_logsearch.cpp:57 +#, c-format +msgid "Invalid duration %s, using %d days." +msgstr "" + +#: include/language.h:68 +msgid "Invalid expiry time." +msgstr "Ungültige Ablaufzeit." + +#: modules/commands/os_session.cpp:346 +msgid "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not " +"matched against nicks or usernames." +msgstr "" +"Ungültige Hostmask. Nur echte Hostmasken sind gültig, da auf Nicknames oder " +"Idents nicht geprüft wird." + +#: modules/commands/os_logsearch.cpp:73 +#, c-format +msgid "Invalid limit %s, using %d." +msgstr "" + +#: include/language.h:99 +msgid "" +"Invalid passcode has been entered, please check the e-mail again, and retry." +msgstr "" + +#: modules/commands/ns_register.cpp:83 modules/commands/ns_register.cpp:86 +msgid "Invalid passcode." +msgstr "" + +#: modules/commands/os_session.cpp:339 +#, c-format +msgid "" +"Invalid session limit. It must be a valid integer greater than or equal to " +"zero and less than %d." +msgstr "" +"Ungültige Verbindungseinschränkung. Es muss eine gültige ganze Zahl sein, " +"grösser oder gleich\n" +"Null aber kleiner als %d." + +#: modules/commands/os_session.cpp:188 +msgid "Invalid threshold value. It must be a valid integer greater than 1." +msgstr "" +"Ungültiger Wert. Es muss eine gültige grade Zahl sein, die grösser als 1 ist." + +#: modules/commands/os_dns.cpp:591 +msgid "Invalid value for LIMIT. Must be numerical." +msgstr "" + +#: modules/commands/cs_invite.cpp:19 +msgid "Invites you or an optionally specified nick into a channel" +msgstr "Lädt Dich oder einen optional angegeben Benutzer in einen Raum ein." + +#: modules/commands/bs_kick.cpp:1201 modules/commands/bs_kick.cpp:1203 +#: modules/commands/bs_kick.cpp:1206 +msgid "Italics kicker" +msgstr "Italics kicker : %s" + +#: modules/commands/ns_group.cpp:91 +msgid "Join a group" +msgstr "Verknüpfe deinen Nicknamen" + +#: modules/commands/cs_set.cpp:1305 modules/commands/ns_set.cpp:1319 +#, fuzzy +msgid "Keep modes" +msgstr "Nachrichten-Modus" + +#: modules/commands/cs_set.cpp:377 modules/commands/ns_set.cpp:603 +#, fuzzy, c-format +msgid "Keep modes for %s is now off." +msgstr "Peace Option für %s ist jetzt ON." + +#: modules/commands/cs_set.cpp:369 modules/commands/ns_set.cpp:597 +#, fuzzy, c-format +msgid "Keep modes for %s is now on." +msgstr "Peace Option für %s ist jetzt ON." + +#: modules/commands/ns_ajoin.cpp:100 +msgid "Key" +msgstr "" + +#: modules/commands/cs_getkey.cpp:50 +#, c-format +msgid "Key for channel %s is %s." +msgstr "Key für Chatrauml %s ist %s." + +#: modules/commands/os_kick.cpp:19 +msgid "Kick a user from a channel" +msgstr "Kickt einen Benutzer aus einem Chatraum." + +#: modules/commands/cs_ban.cpp:217 modules/commands/cs_kick.cpp:116 +#, c-format +msgid "Kicked %d/%d users matching %s from %s." +msgstr "" + +#: modules/commands/cs_kick.cpp:19 +#, fuzzy +msgid "Kicks a specified nick from a channel" +msgstr "Kickt den angegebenen Nicknamen aus einen Channel" + +#: modules/commands/cs_kick.cpp:128 +#, fuzzy +msgid "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." +msgstr "" +"Syntax: KICK Channel Nickname [Grund]\n" +"\n" +"Kickt den ausgewählten Nicknamen aus dem Channel.\n" +"\n" +"Standardmässig ist für diese Funktion ein Level\n" +"von mindestens 5 erforderlich." + +#: modules/commands/os_kill.cpp:19 +msgid "Kill a user" +msgstr "Trennt die Verbindung eines Nutzers zum Netz" + +#: modules/commands/cs_enforce.cpp:217 +msgid "LIMIT enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:221 +#, c-format +msgid "LIMIT enforced on %s, %d users removed." +msgstr "" + +#: modules/commands/os_session.cpp:246 +msgid "LIST threshold" +msgstr "" + +#: modules/commands/os_sxline.cpp:427 modules/commands/os_sxline.cpp:661 +#: modules/commands/os_akill.cpp:388 +msgid "LIST [mask | list | id]" +msgstr "LIST [Channel | Liste | Nummer]" + +#: modules/commands/os_session.cpp:525 +msgid "LIST [mask | list]" +msgstr "LIST [Channel | [Liste]" + +#: modules/commands/ns_access.cpp:104 modules/commands/ns_cert.cpp:260 +#: modules/commands/ns_ajoin.cpp:233 +#, fuzzy +msgid "LIST [nickname]" +msgstr "[Nickname]" + +#: modules/commands/os_news.cpp:31 +msgid "LOGONNEWS {ADD|DEL|LIST} [text|num]" +msgstr "LOGONNEWS {ADD|DEL|LIST} [Text|Nummer]" + +#: modules/commands/ns_set.cpp:834 +msgid "Language changed to English." +msgstr "Sprache wurde geändert zu Deutsch." + +#: modules/commands/ns_set.cpp:836 +#, fuzzy, c-format +msgid "Language for %s changed to %s." +msgstr "Vertreter von %s wurde geändert zu %s." + +#: modules/commands/ms_cancel.cpp:72 +#, c-format +msgid "Last memo to %s has been cancelled." +msgstr "Die letzte Memo an %s wurde widerrufen." + +#: modules/commands/ns_info.cpp:95 +msgid "Last quit message" +msgstr "Letzte Quit-Nachricht:" + +#: modules/commands/cs_access.cpp:472 modules/commands/ns_info.cpp:92 +msgid "Last seen" +msgstr "Letztes Mal gesehen:" + +#: modules/commands/ns_info.cpp:81 modules/commands/ns_info.cpp:86 +msgid "Last seen address" +msgstr "Letzte gesehene Hostmaske: %s" + +#: modules/commands/cs_topic.cpp:264 +msgid "Last topic" +msgstr "" + +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_info.cpp:56 +#, fuzzy +msgid "Last used" +msgstr "Letztes Mal gesehen:" + +#: modules/commands/ns_list.cpp:75 +#, fuzzy +msgid "Last usermask" +msgstr "Letztes Mal gesehen:" + +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +#: modules/commands/cs_access.cpp:697 +msgid "Level" +msgstr "" + +#: modules/commands/cs_access.cpp:660 +#, c-format +msgid "Level for %s on channel %s changed to %d." +msgstr "Der Level für %s für den Channel %s wurde geändert auf %d." + +#: modules/commands/cs_access.cpp:658 +#, c-format +msgid "Level for %s on channel %s changed to founder only." +msgstr "Level für %s in Chatrauml %s zu \"founder only\" geändert." + +#: modules/commands/cs_access.cpp:643 +#, c-format +msgid "Level must be between %d and %d inclusive." +msgstr "Der Level kann nur zwischen %d und einschliesslich %d liegen." + +#: modules/commands/os_dns.cpp:218 modules/commands/os_session.cpp:506 +#: modules/commands/os_session.cpp:514 +msgid "Limit" +msgstr "" + +#: modules/commands/ns_list.cpp:19 +msgid "List all registered nicknames that match a given pattern" +msgstr "Listet alle registrieten Nicknamen des angegebenen Musters" + +#: modules/commands/ns_alist.cpp:24 +msgid "List channels you have access on" +msgstr "Listet Chaträume zu denen Du Zugang hast" + +#: modules/commands/cs_mode.cpp:341 +#, c-format +msgid "List for mode %c is full." +msgstr "" + +#: modules/commands/os_modinfo.cpp:80 +msgid "List loaded modules" +msgstr "Listet die geladenen Module auf" + +#: modules/commands/ns_list.cpp:123 modules/commands/cs_list.cpp:72 +#, c-format +msgid "List of entries matching %s:" +msgstr "Liste der Einträge die mit %s übereinstimmen:" + +#: modules/commands/ns_group.cpp:350 +#, c-format +msgid "List of nicknames in the group of %s:" +msgstr "Liste der Nicknamen in der Gruppe von %s:" + +#: modules/commands/ns_group.cpp:350 +msgid "List of nicknames in your group:" +msgstr "Liste der Nicknamen in Deiner Gruppe:" + +#: modules/commands/ms_list.cpp:19 +msgid "List your memos" +msgstr "Zeigt Deine Memos an" + +#: modules/commands/bs_botlist.cpp:64 +#, fuzzy +msgid "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." +msgstr "" +"Zeigt alle verfügbaren Bots des Netzwerkes an.\n" +"Bots die mit einem * anfangen können nur von\n" +"IRC Operatoren zugewiesen werden." + +#: modules/commands/os_list.cpp:19 +msgid "Lists all channel records" +msgstr "Alle registrierten Räume anzeigen" + +#: modules/commands/os_list.cpp:107 +#, fuzzy +msgid "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." +msgstr "" +"Zeigt alle Räume an, die augenblicklich benutzt werden, \n" +"egal ob sie registriert sind oder nicht.\n" +"\n" +"Wird ein Muster angegeben, werden nur die dem Muster \n" +"entsprechenden Channel angezeigt. Wird ein Nickname \n" +"angegeben, werden nur die Channels aufgelistet, in denen \n" +"sich der User mit dem Nick befindet. Wird zusätzlich der \n" +"Parameter SECRET angegeben, werden nur Channel aufgelistet, \n" +"die Mode +s oder Mode +p gesetzt haben." + +#: modules/commands/ns_alist.cpp:127 +msgid "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" +msgstr "" + +#: modules/commands/ns_group.cpp:299 +msgid "Lists all nicknames in your group" +msgstr "Liste der Nicknamen in Deiner Gruppe:" + +#: modules/commands/cs_list.cpp:20 +msgid "Lists all registered channels matching the given pattern" +msgstr "Listet alle registrieten Channels des angegebenen Musters" + +#: modules/commands/cs_list.cpp:137 +#, fuzzy +msgid "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." +msgstr "" +"Syntax: LIST Muster [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]\n" +"\n" +"Zeigt alle registrierten Nicknamen an, die einem bestimmten\n" +"Muster, nickname!user@host, entsprechen. Nicknamen mit \n" +"aktivierter PRIVATE und NOEXPIRE Option werden nur \n" +"Services Administratoren angezeigt. Nicknamen bei denen das \n" +"NOEXPIRE eingeschaltet ist, werden ein ! vor ihrem\n" +"Eintrag in der Liste haben.\n" +"\n" +"Wenn die Option FORBIDDEN, SUSPENDED, NOEXPIRE oder UNCONFIRMED\n" +"angegeben wird, werden nur Nicknamen angezeigt die das entsprechene\n" +"Muster haben (FORBIDDEN, SUSPENDED, UNCONFIRMED oder NOEXPIRE). \n" +"Wenn mehr Optionen angegeben werden, werden alle Nicknamen angezeigt\n" +"die den Muster entsprechen. \n" +"\n" +"Diese optionen ist beschränkt auf Services Administratoren.\n" +"\n" +"Beispiele:\n" +"\n" +" LIST *!joeuser@foo.com\n" +" Zeigt alle Nicknamen die von joeuser@foo.com\n" +" besessen werden.\n" +"\n" +" LIST *Bot*!*@*\n" +" Listet alle registrierten Nicknamen die Bot in\n" +" ihrem Ident haben (unabhängig von Gross/Klein-\n" +" schreibung).\n" +"\n" +" LIST * NOEXPIRE\n" +" Zeigt alle registrierten Nicknamen an, die das NOEXPIRE\n" +" Flag gesetzt haben." + +#: modules/commands/ns_list.cpp:139 +#, fuzzy +msgid "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." +msgstr "" +"Syntax: LIST Muster [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]\n" +"\n" +"Zeigt alle registrierten Nicknamen an, die einem bestimmten\n" +"Muster, nickname!user@host, entsprechen. Nicknamen mit \n" +"aktivierter PRIVATE und NOEXPIRE Option werden nur \n" +"Services Administratoren angezeigt. Nicknamen bei denen das \n" +"NOEXPIRE eingeschaltet ist, werden ein ! vor ihrem\n" +"Eintrag in der Liste haben.\n" +"\n" +"Wenn die Option FORBIDDEN, SUSPENDED, NOEXPIRE oder UNCONFIRMED\n" +"angegeben wird, werden nur Nicknamen angezeigt die das entsprechene\n" +"Muster haben (FORBIDDEN, SUSPENDED, UNCONFIRMED oder NOEXPIRE). \n" +"Wenn mehr Optionen angegeben werden, werden alle Nicknamen angezeigt\n" +"die den Muster entsprechen. \n" +"\n" +"Diese optionen ist beschränkt auf Services Administratoren.\n" +"\n" +"Beispiele:\n" +"\n" +" LIST *!joeuser@foo.com\n" +" Zeigt alle Nicknamen die von joeuser@foo.com\n" +" besessen werden.\n" +"\n" +" LIST *Bot*!*@*\n" +" Listet alle registrierten Nicknamen die Bot in\n" +" ihrem Ident haben (unabhängig von Gross/Klein-\n" +" schreibung).\n" +"\n" +" LIST * NOEXPIRE\n" +" Zeigt alle registrierten Nicknamen an, die das NOEXPIRE\n" +" Flag gesetzt haben." + +#: modules/commands/os_list.cpp:132 +msgid "Lists all user records" +msgstr "Zeigt alle registrierten Nicknamen an" + +#: modules/commands/os_list.cpp:243 +#, fuzzy +msgid "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only " +"users\n" +"with the +i flag will be listed." +msgstr "" +"Listet alle User auf, die gerade im IRC Netzwerk sind, egal ob\n" +"ihr Nicknamen registriert ist oder nicht.\n" +"\n" +"Wird ein Muster angegeben, werden nur die User\n" +"angezeigt, auf die das Muster passt (es muss im Format\n" +"nick!user@host sein). Wird ein Raum angegeben, werden\n" +"nur die User angezeigt, die in diesem Raum sind. Wird\n" +"zusätzlich INVISIBLE angegeben, werden nur User mit dem Flag\n" +"+i angezeigt." + +#: modules/commands/ms_list.cpp:142 +msgid "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Führt alle Memos auf, die Du im Moment gespeichert hast.\n" +"Mit dem Parameter NEW werden nur neue, ungelesene, Memos\n" +"aufgelistet. Ungelesene Memos sind durch ein \"*\" markiert,\n" +"links neben ihrer Nummer. Du kannst auch einen Bereich\n" +"von Nummern definieren. Siehe das Beispiel:\n" +"\n" +" LIST 2-5,7-9\n" +" Zeigt Memos mit den Nummern 2 bis 5 und 7 bis 9." + +#: modules/commands/bs_botlist.cpp:19 +msgid "Lists available bots" +msgstr "Zeigt alle vorhandenen Bots an" + +#: modules/commands/os_modinfo.cpp:196 +#, fuzzy +msgid "Lists currently loaded modules." +msgstr "Listet alle geladenen Module auf" + +#: modules/commands/cs_info.cpp:19 +#, fuzzy +msgid "Lists information about the specified registered channel" +msgstr "Zeigt Informationen über den angegebenen Channel" + +#: modules/commands/cs_info.cpp:76 +#, fuzzy +msgid "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." +msgstr "" +"Zeigt Informationen über einen registrierten Channel,\n" +"seinen Gründer, das Datum der Registrierung, die\n" +"letzte Nutzung, seine Beschreibung und Mode-Locks,\n" +"wenn welche eingestellt sind." + +#: modules/commands/os_module.cpp:19 +msgid "Load a module" +msgstr "Lädt ein Modul" + +#: modules/commands/cs_register.cpp:39 +msgid "Local channels cannot be registered." +msgstr "Lokale Channels können nicht registriert werden." + +#: modules/commands/cs_log.cpp:142 +#, c-format +msgid "Log list for %s:" +msgstr "Log-iste von %s:" + +#: modules/commands/cs_log.cpp:227 +#, c-format +msgid "Logging changed for command %s on %s, now using log method %s%s%s." +msgstr "" + +#: modules/commands/cs_log.cpp:220 +#, c-format +msgid "Logging for command %s on %s with log method %s%s%s has been removed." +msgstr "" + +#: modules/commands/cs_log.cpp:248 +#, c-format +msgid "Logging is now active for command %s on %s, using log method %s%s%s." +msgstr "" + +#: modules/commands/os_login.cpp:60 +#, c-format +msgid "Login to %s" +msgstr "" + +#: modules/commands/os_news.cpp:36 +#, c-format +msgid "Logon news item #%d deleted." +msgstr "Logon News-Eintrag #%d wurde gelöscht." + +#: modules/commands/os_news.cpp:35 +#, c-format +msgid "Logon news item #%s not found!" +msgstr "Logon News-Eintrag #%s konnte nicht gefunden werden!" + +#: modules/commands/os_news.cpp:32 +msgid "Logon news items:" +msgstr "Logon News Einträge:" + +#: modules/commands/os_login.cpp:102 +#, fuzzy, c-format +msgid "Logout from %s" +msgstr "Log-iste von %s:" + +#: modules/commands/os_login.cpp:52 +#, c-format +msgid "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." +msgstr "" + +#: modules/commands/os_login.cpp:94 +#, c-format +msgid "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." +msgstr "" + +#: modules/commands/cs_seen.cpp:213 +#, c-format +msgid "Looking for yourself, eh %s?" +msgstr "" + +#: modules/commands/cs_mode.cpp:773 +#, c-format +msgid "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a " +"channel.\n" +"If a mode is locked on or off, services will not allow that mode to be " +"changed. The SET\n" +"command will clear all existing mode locks and set the new one given, while " +"ADD and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * " +"and ? may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may " +"be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, " +"halfops, and voices. If what\n" +"is not given then all basic modes are removed." +msgstr "" + +#: modules/commands/cs_akick.cpp:434 +#, fuzzy +msgid "Maintain the AutoKick list" +msgstr " AKICK Die Autokick-Liste bearbeiten" + +#: modules/commands/bs_bot.cpp:269 +#, fuzzy +msgid "Maintains network bot list" +msgstr " BOT Verwaltung von Bots" + +#: modules/commands/cs_xop.cpp:522 +#, c-format +msgid "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " +msgstr "" + +#: modules/commands/cs_akick.cpp:493 +#, c-format +msgid "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" +msgstr "" + +#: modules/commands/cs_access.cpp:568 +#, c-format +msgid "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." +msgstr "" + +#: modules/commands/bs_badwords.cpp:424 +#, fuzzy, c-format +msgid "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" +msgstr "" +"Syntax: BADWORDS Channel ADD Wort [SINGLE | START | END]\n" +" BADWORDS Channel DEL {Wort | entry-num | Liste}\n" +" BADWORDS Channel LIST [Maske | Liste]\n" +" BADWORDS Channel CLEAR\n" +"\n" +"Verwaltet die Bad-Word-List eines Channels.\n" +"\n" +"In dieser Liste sind Wörter gespeichert, bei denen der\n" +"entsprechende User aus dem Channel gekickt wird, wenn er \n" +"eines dieser Wörter erwähnt.\n" +"\n" +"Für mehr Informationen: /msg %s HELP KICK BADWORDS.\n" +"\n" +"Der BADWORDS ADD Befehl fügt Wörter zur der\n" +"Bad-Word-Liste hinzu. Wenn das Wort mit dem Paramter\n" +"SINGLE angeben wird, so wird ein User nur dann gekickt,\n" +"wenn er das ganze Wort sagt. Mit dem Parametern\n" +"END / START wird der User gekickt, wenn er ein Wort sagt,\n" +"das mit dem angegebenen Wort anfängt / endet.\n" +"\n" +"Wenn keine Parameter angegeben werden, wird der User,\n" +"sobald er das angegebene Wort in irgendeiner Kombination\n" +"sagt, gekickt.\n" +"\n" +"Der BADWORDS DEL Befehl löscht Einträge von der Bad- \n" +"Word-Liste. Auch hier gibt es die Möglichkeit, mehrere\n" +"Einträge auf einmal zu löschen (siehe BADWORDS LIST).\n" +"\n" +"Der BADWORDS LIST Befehl zeigt Einträge der Bad-Word-Liste.\n" +"Wildcards wie auch Bereiche werden interpretiert, z.B:\n" +"\n" +"BADWORDS #Channel LIST 2-5,7-9\n" +"Zeigt die Einträge 2-5 und 7-9 der Bad-Word-Liste an.\n" +"\n" +"Der BADWORDS CLEAR Befehl löscht alle Einträge aus der\n" +"Bad-Word-Liste." + +#: modules/commands/bs_badwords.cpp:370 +#, fuzzy +msgid "Maintains the bad words list" +msgstr " BADWORDS Verwaltet die Bad-Word-Liste" + +#: modules/commands/bs_control.cpp:79 +#, fuzzy +msgid "Makes the bot do the equivalent of a \"/me\" command" +msgstr " ACT Veranlaßt den Bot ein \"/me\" Befehl ausführen" + +#: modules/commands/bs_control.cpp:127 +#, fuzzy +msgid "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." +msgstr "" +"Syntax: ACT Channel Text\n" +"\n" +"Bringt den Bot dazu, /me text auf dem angegebenen Channel auszugeben." + +#: modules/commands/bs_control.cpp:19 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel" +msgstr " SAY Veranlaßt ein Bot ein Text in einen Channel zu sagen" + +#: modules/commands/bs_control.cpp:69 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel." +msgstr " SAY Veranlaßt ein Bot ein Text in einen Channel zu sagen" + +#: modules/commands/greet.cpp:157 +#, fuzzy +msgid "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." +msgstr "" +"Syntax: SASET nickname GREET message\n" +"\n" +"Setzt die angegebene Nachricht als Begrüssungsnachricht\n" +"für den Nicknamen. Diese wird angezeigt, wenn der Nickname\n" +"den Channel betritt und die GREET Einstellung aktiviert\n" +"ist. Vorraussetzung ist, dass der Benutzer die entsprechenden\n" +"Rechte besitzt." + +#: modules/commands/greet.cpp:131 +#, fuzzy +msgid "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." +msgstr "" +"Syntax: SET GREET Nachricht\n" +"\n" +"Die angegebene Nachricht wird als Begrüssungsnachricht\n" +"gesendet, wenn Du in einen Channel eintrittst, der\n" +"die GREET Option eingeschaltet hat. Vorausgesetzt\n" +"Du hast den nötigen Zugriffslevel in der Access-Liste\n" +"des Channels. \t" + +#: modules/commands/os_dns.cpp:660 +#, fuzzy +msgid "Manage DNS zones for this network" +msgstr "Du kannst in diesem Netzwerk Deine eMail-Adresse nicht entfernen." + +#: modules/commands/cs_entrymsg.cpp:193 +#, fuzzy +msgid "Manage the channel's entry messages" +msgstr " PERSIST Set the channel as permanent" + +#: modules/commands/ms_ignore.cpp:19 +#, fuzzy +msgid "Manage the memo ignore list" +msgstr " IGNORE Die \"Services Ignore Liste\" bearbeiten" + +#: modules/commands/ns_ajoin.cpp:230 +#, fuzzy +msgid "Manage your auto join list" +msgstr " AKICK Die Autokick-Liste bearbeiten" + +#: modules/commands/os_sxline.cpp:233 +#, fuzzy, c-format +msgid "Manipulate the %s list" +msgstr " AKILL Die AutoKill-Liste bearbeiten" + +#: modules/commands/os_akill.cpp:385 +#, fuzzy +msgid "Manipulate the AKILL list" +msgstr " AKILL Die AutoKill-Liste bearbeiten" + +#: modules/commands/os_defcon.cpp:176 +#, fuzzy +msgid "Manipulate the DefCon system" +msgstr " DEFCON Ändert das DefCon System" + +#: modules/commands/cs_topic.cpp:149 +#, fuzzy +msgid "Manipulate the topic of the specified channel" +msgstr " TOPIC Ändert den Topic des angegebenen Channels" + +#: modules/commands/bs_botlist.cpp:27 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_forbid.cpp:358 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/ms_ignore.cpp:86 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_list.cpp:153 modules/commands/bs_info.cpp:55 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +msgid "Mask" +msgstr "" + +#: modules/commands/ns_access.cpp:39 +#, fuzzy, c-format +msgid "Mask %s already present on %s's access list." +msgstr "Diese Hostmaske %s ist bereits auf der Access-Liste." + +#: include/language.h:67 +#, fuzzy +msgid "Mask must be in the form user@host." +msgstr "Eine vHost muss eine gültige HostMaske besitzen." + +#: modules/commands/cs_access.cpp:166 modules/commands/cs_flags.cpp:120 +#: modules/commands/cs_xop.cpp:162 +#, fuzzy +msgid "Masks and unregistered users may not be on access lists." +msgstr "Diese Hostmaske %s ist bereits auf der Access-Liste." + +#: modules/commands/ns_getemail.cpp:23 +#, fuzzy +msgid "Matches and returns all users that registered using given email" +msgstr "" +" GETEMAIL Gibt die passenden Nicknamen wieder, \n" +" welche die angegebene eMail benutzen." + +#: modules/commands/os_logsearch.cpp:148 +#, fuzzy, c-format +msgid "Matches for %s:" +msgstr " Mode lock: %s" + +#: modules/commands/os_stats.cpp:139 +#, c-format +msgid "Maximum users: %d (%s)" +msgstr " Maximum: %d (%s)" + +#: modules/commands/ms_read.cpp:84 modules/commands/ms_read.cpp:86 +#, fuzzy, c-format +msgid "Memo %d from %s (%s)." +msgstr " Mode lock: %s" + +#: modules/commands/ms_del.cpp:33 modules/commands/ms_del.cpp:101 +#, c-format +msgid "Memo %d has been deleted." +msgstr "Memo %d wurde gelöscht." + +#: modules/commands/ms_ignore.cpp:82 +#, fuzzy +msgid "Memo ignore list is empty." +msgstr "Deine Ignore-Liste ist leer." + +#: modules/commands/ms_set.cpp:199 +#, c-format +msgid "Memo limit disabled for %s." +msgstr "Memo-Limit von %s wurde aufgehoben." + +#: modules/commands/ms_set.cpp:185 +#, c-format +msgid "Memo limit for %s set to %d." +msgstr "Memo-Limit von %s wurde auf %d gesetzt." + +#: modules/commands/ms_set.cpp:192 +#, c-format +msgid "Memo limit for %s set to 0." +msgstr "" +"Memo-Limit von %s wurde auf 0 gesetzt, kein Memo-Empfang für ihn mehr " +"möglich." + +#: modules/commands/ms_rsend.cpp:63 modules/commands/ms_send.cpp:51 +#, c-format +msgid "Memo sent to %s." +msgstr "Memo wurde an %s versandt." + +#: modules/commands/ms_list.cpp:131 +#, fuzzy, c-format +msgid "Memos for %s:" +msgstr " Mode lock: %s" + +#: modules/commands/cs_entrymsg.cpp:116 +#, fuzzy +msgid "Message" +msgstr "Nachricht" + +#: modules/commands/ns_set.cpp:1313 +msgid "Message mode" +msgstr "Nachrichten-Modus" + +#: modules/commands/cs_log.cpp:127 +msgid "Method" +msgstr "" + +#: modules/commands/cs_mode.cpp:329 modules/commands/cs_mode.cpp:420 +#, c-format +msgid "Missing parameter for mode %c." +msgstr "" + +#: modules/commands/cs_mode.cpp:449 +msgid "Mode" +msgstr "" + +#: modules/commands/cs_mode.cpp:718 +#, fuzzy, c-format +msgid "Mode %s is a virtual mode and can't be cleared." +msgstr "" +"Der Nickname %s ist ein illegaler Nickname und kann nicht benutzt werden." + +#: modules/commands/cs_mode.cpp:712 +#, fuzzy, c-format +msgid "Mode %s is not a status or list mode." +msgstr "Der Nickname %s wurde nicht in Deiner Ignore-Liste gefunden." + +#: modules/commands/cs_mode.cpp:1065 +#, fuzzy +msgid "Mode lock" +msgstr " Mode lock: %s" + +#: modules/commands/cs_mode.cpp:466 +#, fuzzy, c-format +msgid "Mode locks for %s:" +msgstr " Mode lock: %s" + +#: modules/commands/os_list.cpp:43 +msgid "Modes" +msgstr "" + +#: modules/commands/os_mode.cpp:44 +#, c-format +msgid "Modes cleared on %s and the channel destroyed." +msgstr "" + +#: modules/commands/ns_access.cpp:166 +#, fuzzy, c-format +msgid "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." +msgstr "" +"Syntax: ACCESS ADD Maske\n" +" ACCESS DEL Maske\n" +" ACCESS LIST\n" +"\n" +"Zeigt oder bearbeitet die Zugriffsliste für Deinen \n" +"Nicknamen. Durch diese Liste erkennt %s dich \n" +"automatisch als berechtigt, diesen Nicknamen zu \n" +"nutzen. Wenn Du den Nicknamen von anderen Adressen\n" +"verwenden willst, musst Du dich durch das \n" +"IDENTIFY Befehls einloggen, damit %s\n" +"dich erkennt.\n" +"\n" +"Beispiele:\n" +"\n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Erlaubt zugriff vom User anyone von\n" +" jedem Host aus der bepeg.com Domain.\n" +"\n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Hebt den oben genannten Befehl wieder auf.\n" +"\n" +" ACCESS LIST\n" +" Zeigt die aktuelle Zugriffsliste an." + +#: modules/commands/ns_cert.cpp:319 +msgid "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" +msgstr "" + +#: modules/commands/os_ignore.cpp:341 +#, fuzzy +msgid "Modify the Services ignore list" +msgstr " IGNORE Die \"Services Ignore Liste\" bearbeiten" + +#: modules/commands/cs_xop.cpp:489 +#, fuzzy, c-format +msgid "Modify the list of %s users" +msgstr " AOP Verwaltet die AOP-Liste von einen Channel" + +#: modules/commands/ns_access.cpp:101 +#, fuzzy +msgid "Modify the list of authorized addresses" +msgstr " ACCESS Liste der autorisierten Adressen" + +#: modules/commands/cs_access.cpp:498 modules/commands/cs_flags.cpp:373 +#, fuzzy +msgid "Modify the list of privileged users" +msgstr "" +" ACCESS Die Liste der priviligierten User\n" +" bearbeiten" + +#: modules/commands/ns_cert.cpp:257 +#, fuzzy +msgid "Modify the nickname client certificate list" +msgstr " IGNORE Die \"Services Ignore Liste\" bearbeiten" + +#: modules/commands/os_session.cpp:522 +#, fuzzy +msgid "Modify the session-limit exception list" +msgstr "" +" EXCEPTION Bearbeiten der Liste der eingeschränkten Verbindungen" + +#: modules/commands/os_module.cpp:34 +#, c-format +msgid "Module %s is already loaded." +msgstr "Module %s is already loaded." + +#: modules/commands/os_module.cpp:67 modules/commands/os_module.cpp:139 +#, c-format +msgid "Module %s isn't loaded." +msgstr "Module %s isn't loaded." + +#: modules/commands/os_module.cpp:31 +#, fuzzy, c-format +msgid "Module %s loaded." +msgstr "Modul %s geladen" + +#: modules/commands/os_module.cpp:98 +#, fuzzy, c-format +msgid "Module %s reloaded." +msgstr "Modul %s geladen" + +#: modules/commands/os_module.cpp:156 +#, fuzzy, c-format +msgid "Module %s unloaded." +msgstr "Modul %s entfernt" + +#: modules/commands/os_config.cpp:88 +#, fuzzy +msgid "Module Name" +msgstr "Modul %s geladen" + +#: modules/commands/os_config.cpp:112 +#, fuzzy +msgid "Module settings:" +msgstr "%s Einstellungen:" + +#: modules/commands/os_modinfo.cpp:32 +#, fuzzy, c-format +msgid "Module: %s Version: %s Author: %s Loaded: %s" +msgstr "Module: %s Version: %s Autor: %s geladen: %s" + +#: modules/commands/os_modinfo.cpp:183 +#, c-format +msgid "Module: %s [%s] [%s]" +msgstr "Module: %s [%s] [%s]" + +#: modules/commands/cs_access.cpp:697 modules/commands/cs_access.cpp:799 +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +#: modules/commands/cs_list.cpp:75 modules/commands/os_list.cpp:43 +#: modules/commands/os_list.cpp:153 +msgid "Name" +msgstr "" + +#: modules/commands/os_oper.cpp:153 +msgid "Name Type" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:146 +#, fuzzy, c-format +msgid "Network stats for %s:" +msgstr "Badword Liste von %s:" + +#: modules/commands/os_forbid.cpp:384 +msgid "Never" +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/bs_botlist.cpp:27 +#: modules/commands/hs_request.cpp:305 modules/commands/ns_list.cpp:75 +#: modules/commands/ns_group.cpp:327 +#, fuzzy +msgid "Nick" +msgstr "Nickname" + +#: modules/commands/ns_register.cpp:42 +#, fuzzy, c-format +msgid "Nick %s has been confirmed." +msgstr "Der Nickname %s wurde aus der Datenbank entfernt." + +#: modules/commands/os_oper.cpp:95 +#, fuzzy, c-format +msgid "Nick %s is already an operator." +msgstr "Dieser Nickname %s ist bereits registriert!" + +#: modules/commands/ns_register.cpp:36 +#, fuzzy, c-format +msgid "Nick %s is already confirmed." +msgstr "Dieser Nickname %s ist bereits registriert!" + +#: modules/commands/os_svs.cpp:46 +#, c-format +msgid "Nick %s is an illegal nickname and cannot be used." +msgstr "" +"Der Nickname %s ist ein illegaler Nickname und kann nicht benutzt werden." + +#: modules/commands/bs_bot.cpp:81 modules/commands/bs_bot.cpp:181 +#: modules/commands/os_svs.cpp:54 +#, c-format +msgid "Nick %s is currently in use." +msgstr "Der Nickname %s wird derzeit benutzt." + +#: modules/commands/os_forbid.cpp:512 +#, fuzzy, c-format +msgid "Nick %s is forbidden by %s: %s" +msgstr "Der Nickname %s wird derzeit benutzt." + +#: modules/commands/os_forbid.cpp:514 +#, fuzzy, c-format +msgid "Nick %s is forbidden." +msgstr "Der Nickname %s ist nicht gesperrt." + +#: modules/commands/os_oper.cpp:134 +#, fuzzy, c-format +msgid "Nick %s is not a Services Operator." +msgstr "%s ist ein services operator vom Typ %s." + +#: modules/commands/ns_info.cpp:34 +#, c-format +msgid "Nick %s is part of this Network's Services." +msgstr "Der Nickname %s ist ein Teil der Netzwerkdienste." + +#: include/language.h:79 +#, fuzzy, c-format +msgid "Nick %s isn't currently in use." +msgstr "Der Nickname %s wird derzeit benutzt." + +#: include/language.h:78 +#, fuzzy, c-format +msgid "Nick %s isn't registered." +msgstr "Der Nickname %s wurde erfolgreich registriert." + +#: modules/commands/os_svs.cpp:39 +#, c-format +msgid "Nick %s was truncated to %d characters." +msgstr "Dein Nickname %s wurde auf %d Zeichen gekürzt." + +#: modules/commands/ns_set.cpp:1135 +#, c-format +msgid "Nick %s will expire." +msgstr "Nickname %s wird wieder verfallen." + +#: modules/commands/ns_set.cpp:1129 +#, c-format +msgid "Nick %s will not expire." +msgstr "Nickname %s wird nicht mehr verfallen." + +#: modules/commands/ms_check.cpp:60 +#, c-format +msgid "Nick %s doesn't have a memo from you." +msgstr "Nickname %s hat keine Nachricht von Dir." + +#: modules/commands/ns_logout.cpp:48 +#, c-format +msgid "Nick %s has been logged out." +msgstr "Der Nickname %s wurde erfolgreich ausgeloggt." + +#: modules/commands/ns_group.cpp:272 +#, c-format +msgid "Nick %s has been ungrouped from %s." +msgstr "Die Gruppierung des Nicks %s mit %s wurde aufgehoben." + +#: include/language.h:81 +#, fuzzy, c-format +msgid "Nick %s is currently suspended." +msgstr "Der Nickname %s ist jetzt suspendiert." + +#: modules/commands/ns_group.cpp:250 +#, fuzzy, c-format +msgid "Nick %s is not in your group." +msgstr "The nick %s is not in your group." + +#: modules/commands/ns_suspend.cpp:180 +#, fuzzy, c-format +msgid "Nick %s is not suspended." +msgstr "Der Nickname %s ist jetzt suspendiert." + +#: modules/commands/ns_suspend.cpp:190 +#, c-format +msgid "Nick %s is now released." +msgstr "Der Nickname %s ist jetzt freigegeben." + +#: modules/commands/ns_suspend.cpp:138 +#, c-format +msgid "Nick %s is now suspended." +msgstr "Der Nickname %s ist jetzt suspendiert." + +#: modules/commands/cs_seen.cpp:275 +#, c-format +msgid "Nick too long, max length is %u characters." +msgstr "" + +#: modules/commands/ns_drop.cpp:53 +#, c-format +msgid "Nickname %s has been dropped." +msgstr "Der Nickname %s wurde aus der Datenbank entfernt." + +#: include/language.h:97 +#, fuzzy, c-format +msgid "Nickname %s is already registered!" +msgstr "Der Channel %s ist bereits registriert!" + +#: include/language.h:96 +#, fuzzy, c-format +msgid "Nickname %s may not be registered." +msgstr "Der Channel %s kann nicht registriert werden." + +#: modules/commands/ns_register.cpp:226 +#, fuzzy, c-format +msgid "Nickname %s registered under your user@host-mask: %s" +msgstr "Dein Nickname %s ist unter Deinem Host registriert worden: %s" + +#: modules/commands/ns_register.cpp:228 +#, fuzzy, c-format +msgid "Nickname %s registered." +msgstr "Der Nickname %s wurde erfolgreich registriert." + +#: modules/commands/cs_set.cpp:1307 +#, fuzzy +msgid "No auto-op" +msgstr "Auto-op" + +#: modules/commands/bs_assign.cpp:252 +msgid "No bot" +msgstr "Kein Bot" + +#: modules/commands/cs_set.cpp:1303 modules/commands/ns_set.cpp:1317 +#, fuzzy +msgid "No expire" +msgstr "läuft nicht aus" + +#: modules/commands/help.cpp:184 +#, c-format +msgid "No help available for %s." +msgstr "Keine Hilfe verfügbar für %s." + +#: modules/commands/os_modinfo.cpp:61 +#, fuzzy, c-format +msgid "No information about module %s is available." +msgstr "Es sind keine Informationen für das Modul %s verfügbar" + +#: modules/commands/cs_enforce.cpp:177 +#, fuzzy, c-format +msgid "No limit is set on %s." +msgstr "Memo-Limit von %s wurde auf %d gesetzt." + +#: modules/commands/os_news.cpp:37 +msgid "No logon news items to delete!" +msgstr "Keine zu löschenden Einträge in der Logon News-Liste gefunden." + +#: modules/commands/os_logsearch.cpp:133 +#, fuzzy, c-format +msgid "No matches for %s found." +msgstr "Keine eingetragenen Emails für %s." + +#: modules/commands/cs_xop.cpp:294 +#, fuzzy, c-format +msgid "No matching entries on %s %s list." +msgstr "Keine passenden Einträge in der %s AOP-Liste." + +#: modules/commands/cs_access.cpp:269 modules/commands/cs_access.cpp:433 +#: modules/commands/cs_flags.cpp:335 modules/commands/cs_xop.cpp:428 +#, c-format +msgid "No matching entries on %s access list." +msgstr "" +"Es existieren keine entsprechenden Einträge in der Zugangs-Liste von %s." + +#: modules/commands/cs_akick.cpp:224 modules/commands/cs_akick.cpp:368 +#, c-format +msgid "No matching entries on %s autokick list." +msgstr "Keine entsprechenden Einträge auf der AutoKick-Liste von %s gefunden." + +#: modules/commands/bs_badwords.cpp:166 modules/commands/bs_badwords.cpp:246 +#, c-format +msgid "No matching entries on %s bad words list." +msgstr "Keine entsprechenden Einträge zu %s in der Bad Words-Liste gefunden." + +#: modules/commands/os_session.cpp:145 modules/commands/os_session.cpp:490 +msgid "No matching entries on session-limit exception list." +msgstr "" +"Keine entsprechenden Einträge in der Liste der \n" +"Verbindungseinschränkungen." + +#: modules/commands/os_sxline.cpp:28 modules/commands/os_sxline.cpp:177 +#, fuzzy, c-format +msgid "No matching entries on the %s list." +msgstr "Keine passenden Einträge in der %s AOP-Liste." + +#: modules/commands/os_akill.cpp:29 modules/commands/os_akill.cpp:320 +msgid "No matching entries on the AKILL list." +msgstr "Keine entsprechenden Einträge auf der AKILL-Liste." + +#: modules/commands/ms_cancel.cpp:77 +msgid "No memo was cancelable." +msgstr "Kein Memo konnte widerrufen werden." + +#: modules/commands/ms_read.cpp:65 +msgid "No memos to display." +msgstr "" + +#: modules/commands/os_modinfo.cpp:187 +#, fuzzy +msgid "No modules currently loaded matching that criteria." +msgstr "Derzeit keine Module geladen" + +#: modules/commands/ns_recover.cpp:55 +msgid "No one is using your nick, and services are not holding it." +msgstr "" + +#: modules/commands/os_login.cpp:30 modules/commands/os_login.cpp:77 +msgid "No oper block for your nick." +msgstr "" + +#: modules/commands/os_news.cpp:47 +msgid "No oper news items to delete!" +msgstr "Keine Oper-News-Einträge zu löschen!" + +#: modules/commands/os_news.cpp:57 +msgid "No random news items to delete!" +msgstr "Keine randomnews Einträge zu löschen!" + +#: modules/commands/hs_list.cpp:111 +msgid "No records to display." +msgstr "" + +#: modules/commands/ns_getemail.cpp:47 +#, fuzzy, c-format +msgid "No registrations matching %s were found." +msgstr "* Keine neuen Nicknamen-Registrierungen" + +#: modules/commands/hs_request.cpp:220 modules/commands/hs_request.cpp:276 +#, c-format +msgid "No request for nick %s found." +msgstr "" + +#: src/access.cpp:55 +msgid "No signed kick when SIGNKICK LEVEL is used" +msgstr "" + +#: modules/extra/stats/cs_fantasy_top.cpp:159 +#: modules/extra/stats/cs_fantasy_stats.cpp:156 +#, fuzzy, c-format +msgid "No stats for %s." +msgstr "Access-Liste von %s:" + +#: modules/commands/os_info.cpp:201 +#, fuzzy, c-format +msgid "No such info \"%s\" on %s." +msgstr "%s wurde nach %s eingeladen." + +#: modules/commands/cs_ban.cpp:219 modules/commands/cs_kick.cpp:118 +#, fuzzy, c-format +msgid "No users on %s match %s." +msgstr "Usermodi von %s geändert." + +#: modules/commands/bs_assign.cpp:188 +#, fuzzy, c-format +msgid "No-bot mode is now off on channel %s." +msgstr "No-Bot-Mode ist jetzt ON im Channel %s." + +#: modules/commands/bs_assign.cpp:181 +#, fuzzy, c-format +msgid "No-bot mode is now on on channel %s." +msgstr "No-Bot-Mode ist jetzt ON im Channel %s." + +#: modules/commands/os_mode.cpp:64 +#, c-format +msgid "Non-status modes cleared on %s." +msgstr "" + +#: modules/commands/os_dns.cpp:226 modules/commands/bs_info.cpp:58 +msgid "None" +msgstr "Keine" + +#: modules/commands/cs_set.cpp:1029 +#, c-format +msgid "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." +msgstr "" + +#: modules/commands/cs_mode.cpp:380 modules/commands/cs_mode.cpp:437 +msgid "Nothing to do." +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:201 modules/commands/ms_list.cpp:64 +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_log.cpp:127 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +#: modules/commands/ns_ajoin.cpp:100 +msgid "Number" +msgstr "" + +#: modules/commands/os_news.cpp:41 +msgid "OPERNEWS {ADD|DEL|LIST} [text|num]" +msgstr "OPERNEWS {ADD|DEL|LIST} [Text|Nummer]" + +#: modules/commands/ns_info.cpp:68 modules/commands/ns_info.cpp:72 +#, fuzzy +msgid "Online from" +msgstr " Ist online von: %s" + +#: modules/commands/os_oper.cpp:138 +#, fuzzy, c-format +msgid "" +"Oper %s is configured in the configuration file(s) and can not be removed by " +"this command." +msgstr " Dieser Operator wurde in der Konfigurationsdatei eingestellt." + +#: modules/commands/os_info.cpp:268 +msgid "Oper Info" +msgstr "" + +#: modules/commands/os_info.cpp:182 modules/commands/os_info.cpp:221 +#, fuzzy, c-format +msgid "Oper info list for %s is empty." +msgstr "Zertifikat-Liste von %s ist leer." + +#: modules/commands/os_news.cpp:46 +#, c-format +msgid "Oper news item #%d deleted." +msgstr "Oper-News-Eintrag #%d wurde entfernt." + +#: modules/commands/os_news.cpp:45 +#, fuzzy, c-format +msgid "Oper news item #%s not found!" +msgstr "Oper-News-Eintrag #%d nicht gefunden!" + +#: modules/commands/os_news.cpp:42 +msgid "Oper news items:" +msgstr "Oper News Einträge:" + +#: modules/commands/os_oper.cpp:148 +#, c-format +msgid "Oper privileges removed from %s (%s)." +msgstr "" + +#: modules/commands/os_oper.cpp:101 modules/commands/os_oper.cpp:189 +#, fuzzy, c-format +msgid "Oper type %s has not been configured." +msgstr "Der Nickname %s wurde aus der Datenbank entfernt." + +#: modules/commands/os_oline.cpp:37 +#, c-format +msgid "Operflags %s have been added for %s." +msgstr "Operflags %s wurden für %s hinzugefügt. " + +#: modules/commands/os_oline.cpp:43 +#, fuzzy, c-format +msgid "Operflags %s have been removed from %s." +msgstr "Operflags %s wurden für %s hinzugefügt. " + +#: modules/commands/os_oper.cpp:193 +#, c-format +msgid "Opertype %s has no allowed commands." +msgstr "" + +#: modules/commands/os_oper.cpp:215 +#, c-format +msgid "Opertype %s has no allowed privileges." +msgstr "" + +#: modules/commands/os_oper.cpp:237 +#, c-format +msgid "Opertype %s receives modes %s once identified." +msgstr "" + +#: modules/commands/bs_kick.cpp:1219 +msgid "Ops protection" +msgstr "Op-Schutz" + +#: src/misc.cpp:258 modules/commands/bs_info.cpp:58 +#, fuzzy +msgid "Options" +msgstr " Options : %s" + +#: modules/commands/os_dns.cpp:668 +#, fuzzy +msgid "POOL server.name" +msgstr "NOOP {SET|REVOKE} Server" + +#: modules/commands/cs_mode.cpp:449 +msgid "Param" +msgstr "" + +#: modules/commands/ns_identify.cpp:38 +msgid "Password accepted - you are now recognized." +msgstr "Passwort akzeptiert - Du bist jetzt angemeldet." + +#: modules/commands/os_login.cpp:44 +#, fuzzy +msgid "Password accepted." +msgstr "Falsches Passwort." + +#: include/language.h:85 +msgid "Password authentication required for that command." +msgstr "" + +#: modules/commands/ns_set.cpp:152 modules/commands/ns_set.cpp:218 +#, fuzzy, c-format +msgid "Password for %s changed to %s." +msgstr "Vertreter von %s wurde geändert zu %s." + +#: modules/commands/ns_set.cpp:154 modules/commands/ns_set.cpp:220 +#, fuzzy, c-format +msgid "Password for %s changed." +msgstr "Das Passwort von %s wurde per eMail verschickt." + +#: modules/commands/ns_getpass.cpp:38 +#, c-format +msgid "Password for %s is %s." +msgstr "Passwort von %s ist %s." + +#: include/language.h:71 +#, fuzzy +msgid "Password incorrect." +msgstr "Falsches Passwort." + +#: modules/commands/ns_resetpass.cpp:39 +#, c-format +msgid "Password reset email for %s has been sent." +msgstr "Password reset email for %s has been sent." + +#: modules/commands/cs_set.cpp:1289 +msgid "Peace" +msgstr "Frieden" + +#: modules/commands/cs_set.cpp:440 +#, fuzzy, c-format +msgid "Peace option for %s is now off." +msgstr "Peace Option für %s ist jetzt ON." + +#: modules/commands/cs_set.cpp:434 +#, fuzzy, c-format +msgid "Peace option for %s is now on." +msgstr "Peace Option für %s ist jetzt ON." + +#: modules/commands/cs_set.cpp:1301 +#, fuzzy +msgid "Persistent" +msgstr "Persistant" + +#: include/language.h:126 +msgid "Please contact an Operator to get a vHost assigned to this nick." +msgstr "" + +#: include/language.h:73 +msgid "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." +msgstr "" + +#: modules/commands/os_jupe.cpp:30 +#, fuzzy +msgid "Please use a valid server name when juping." +msgstr "Benutze bitte einen gültigen hostnamen, wenn Du jupiterst" + +#: include/language.h:104 +msgid "Please use the symbol of # when attempting to register." +msgstr "" + +#: src/mail.cpp:78 +#, c-format +msgid "Please wait %d seconds and retry." +msgstr "Bitte warte noch %d Sekunden und versuche es dann erneut." + +#: modules/commands/hs_request.cpp:158 +#, fuzzy, c-format +msgid "Please wait %d seconds before requesting a new vHost." +msgstr "Bitte warte %d Sekunden bis Du den SEND Befehl wieder benutzen kannst." + +#: modules/commands/ms_rsend.cpp:58 modules/commands/ms_send.cpp:57 +#, fuzzy, c-format +msgid "Please wait %d seconds before using the %s command again." +msgstr "Bitte warte %d Sekunden bis du den SEND Befehl wieder benutzen kannst." + +#: modules/commands/ns_group.cpp:149 +#, c-format +msgid "Please wait %d seconds before using the GROUP command again." +msgstr "Bitte warte %d Sekunden, bevor der GROUP Befehl wieder funktioniert." + +#: modules/commands/ns_register.cpp:198 +#, c-format +msgid "Please wait %d seconds before using the REGISTER command again." +msgstr "" +"Bitte warte %d Sekunden, bevor der REGISTER Befehl wieder funktioniert." + +#: modules/commands/os_dns.cpp:628 +#, c-format +msgid "Pooled %s." +msgstr "" + +#: modules/commands/os_dns.cpp:237 +msgid "Pooled/Active" +msgstr "" + +#: modules/commands/os_dns.cpp:239 +msgid "Pooled/Not Active" +msgstr "" + +#: modules/commands/bs_set.cpp:161 +msgid "Prevent a bot from being assigned by non IRC operators" +msgstr "" + +#: modules/commands/bs_assign.cpp:153 +#, fuzzy +msgid "Prevent a bot from being assigned to a channel" +msgstr "" +" SUSPEND Verbietet jegliche Nutzung des Channels.\n" +" Die Channel Einstellungen bleiben jedoch\n" +" erhalten" + +#: modules/commands/cs_suspend.cpp:58 +#, fuzzy +msgid "Prevent a channel from being used preserving channel data and settings" +msgstr "" +" SUSPEND Verbietet jegliche Nutzung des Channels.\n" +" Die Channel Einstellungen bleiben jedoch\n" +" erhalten" + +#: modules/commands/cs_set.cpp:1043 +#, fuzzy +msgid "Prevent the channel from expiring" +msgstr " NOEXPIRE Prevent the channel from expiring" + +#: modules/commands/ns_list.cpp:186 +#, fuzzy +msgid "Prevent the nickname from appearing in the LIST command" +msgstr "" +" PRIVATE Verhindert, dass der Nickname im Befehl\n" +" /msg %s LIST auftaucht" + +#: modules/commands/ns_set.cpp:1104 +#, fuzzy +msgid "Prevent the nickname from expiring" +msgstr "" +" NOEXPIRE Verhindert, dass der Nickname nach einer bestimmten\n" +" Zeit verfällt" + +#: src/access.cpp:46 +msgid "Prevents users being kicked by Services" +msgstr "" + +#: modules/commands/ns_list.cpp:297 modules/commands/cs_list.cpp:262 +#: modules/commands/bs_info.cpp:58 +msgid "Private" +msgstr "Privat" + +#: modules/commands/bs_set.cpp:190 +#, fuzzy, c-format +msgid "Private mode of bot %s is now off." +msgstr "Private-Mode des Bots im %s ist jetzt ON." + +#: modules/commands/bs_set.cpp:185 +#, fuzzy, c-format +msgid "Private mode of bot %s is now on." +msgstr "Private-Mode des Bots im %s ist jetzt ON." + +#: modules/commands/cs_list.cpp:220 +#, fuzzy, c-format +msgid "Private option for %s is now off." +msgstr "Private Option für %s ist jetzt ON." + +#: modules/commands/cs_list.cpp:214 +#, fuzzy, c-format +msgid "Private option for %s is now on." +msgstr "Private Option für %s ist jetzt ON." + +#: modules/commands/ns_list.cpp:221 +#, fuzzy, c-format +msgid "Private option is now off for %s." +msgstr "Der Privat-Modus (PRIVATE) ist für %s jetzt aktiviert (ON)." + +#: modules/commands/ns_list.cpp:215 +#, fuzzy, c-format +msgid "Private option is now on for %s." +msgstr "Der Privat-Modus (PRIVATE) ist für %s jetzt aktiviert (ON)." + +#: modules/commands/cs_flags.cpp:281 +#, c-format +msgid "Privilege %s added to %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/cs_flags.cpp:283 +#, c-format +msgid "Privilege %s removed from %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/ns_set.cpp:1309 +msgid "Protection" +msgstr "Kill-Schutz" + +#: modules/commands/ns_set.cpp:721 +#, fuzzy, c-format +msgid "Protection is now off for %s." +msgstr "Schutz des Nicknamens %s ist jetzt aktiviert (ON)." + +#: modules/commands/ns_set.cpp:700 +#, fuzzy, c-format +msgid "Protection is now on for %s, with a reduced delay." +msgstr "Schutz des Nicknamens %s mit verkürzter Verzögerung aktiviert (ON)." + +#: modules/commands/ns_set.cpp:710 +#, fuzzy, c-format +msgid "Protection is now on for %s, with no delay." +msgstr "Schutz des Nicknamens %s ohne Verzögerung aktiviert (ON)." + +#: modules/commands/ns_set.cpp:692 +#, fuzzy, c-format +msgid "Protection is now on for %s." +msgstr "Schutz des Nicknamens %s ist jetzt aktiviert (ON)." + +#: modules/commands/os_chankill.cpp:100 +#, fuzzy +msgid "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." +msgstr "" +"Syntax: CHANKILL [+Zeit] Channel Grund\n" +"Setzt einen AKILL für jeden Nicknamen des angegebenen Channels. \n" +"Es werden die Einträge und komplette reale ident@host für jeden \n" +"Nickname benutzt, dann wird der AKILL durchgeführt. " + +#: modules/commands/ns_set.cpp:1307 +#, fuzzy +msgid "Quick protection" +msgstr "Voice-Schutz" + +#: modules/commands/os_news.cpp:51 +msgid "RANDOMNEWS {ADD|DEL|LIST} [text|num]" +msgstr "RANDOMNEWS {ADD|DEL|LIST} [Text|Nummer]" + +#: modules/commands/cs_enforce.cpp:99 +msgid "REGONLY enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:68 +msgid "RESTRICTED enforced by " +msgstr "" + +#: modules/commands/os_noop.cpp:21 +#, fuzzy +msgid "REVOKE server" +msgstr "NOOP {SET|REVOKE} Server" + +#: modules/commands/os_news.cpp:56 +#, c-format +msgid "Random news item #%d deleted." +msgstr "Random news Eintrag #%d gelöscht." + +#: modules/commands/os_news.cpp:55 +#, fuzzy, c-format +msgid "Random news item #%s not found!" +msgstr "Randomnews Eintrag #%d nicht gefunden!" + +#: modules/commands/os_news.cpp:52 +msgid "Random news items:" +msgstr "Random news Einträge:" + +#: modules/commands/ms_read.cpp:112 +#, fuzzy +msgid "Read a memo or memos" +msgstr " READ Lesen einer oder mehrerer Memos" + +#: modules/commands/bs_info.cpp:56 +#, fuzzy +msgid "Real name" +msgstr " Echter Name: %s" + +#: modules/commands/os_list.cpp:153 +#, fuzzy +msgid "Realname" +msgstr " Echter Name: %s" + +#: modules/commands/os_ignore.cpp:266 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:204 modules/commands/os_forbid.cpp:358 +#: modules/commands/cs_akick.cpp:392 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:361 +msgid "Reason" +msgstr "" + +#: src/xline.cpp:386 +#, fuzzy, c-format +msgid "Reason for %s updated." +msgstr "%s wurde für %s entfernt." + +#: modules/commands/ns_recover.cpp:214 +msgid "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." +msgstr "" + +#: modules/commands/cs_access.cpp:741 +#, fuzzy +msgid "Redefine the meanings of access levels" +msgstr "" +" LEVELS Die Einstellungen verschiedener\n" +" Zugriffslevel neu definieren" + +#: modules/commands/ns_recover.cpp:149 +#, fuzzy +msgid "Regains control of your nick" +msgstr "" +" RELEASE Hebt die Nickname-Sperre auf nach der \n" +" verwendung des RECOVER Befehls" + +#: modules/commands/os_sxline.cpp:330 modules/commands/os_sxline.cpp:545 +#: modules/commands/os_akill.cpp:129 +#, fuzzy +msgid "Regex is disabled." +msgstr "%s ist eingeschaltet" + +#: modules/commands/os_sxline.cpp:459 modules/commands/os_sxline.cpp:694 +#: modules/commands/os_akill.cpp:444 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." +msgstr "" + +#: modules/commands/os_ignore.cpp:386 modules/commands/os_forbid.cpp:428 +#: modules/commands/ns_list.cpp:172 modules/commands/cs_list.cpp:167 +#: modules/commands/os_list.cpp:119 modules/commands/os_list.cpp:255 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." +msgstr "" + +#: modules/commands/cs_register.cpp:19 +#, fuzzy +msgid "Register a channel" +msgstr " REGISTER Registriert einen Nicknamen" + +#: modules/commands/ns_register.cpp:120 +#, fuzzy +msgid "Register a nickname" +msgstr " REGISTER Registriert einen Nicknamen" + +#: modules/commands/ns_info.cpp:89 modules/commands/cs_info.cpp:55 +#, fuzzy +msgid "Registered" +msgstr " Registriert seit: %s" + +#: modules/commands/os_stats.cpp:184 +#, c-format +msgid "Registered channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:190 +#, c-format +msgid "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:187 +#, c-format +msgid "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/cs_enforce.cpp:105 +#, c-format +msgid "Registered only enforced on %s." +msgstr "" + +#: modules/commands/cs_register.cpp:86 +#, fuzzy, c-format +msgid "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." +msgstr "" +"Syntax: REGISTER Channel Beschreibung\n" +"\n" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which must be included, is a\n" +"general description of the channel's purpose.\n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel.\n" +"See the ACCESS command (/msg %s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname. If you haven't,\n" +"/msg %s HELP for information on how to do so." + +#: modules/commands/ns_register.cpp:269 +#, fuzzy, c-format +msgid "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." +msgstr "" +"Syntax: REGISTER Passwort [eMail]\n" +"\n" +"Registriert Deinen Nicknamen in der Datenbank von \n" +"%s. Nachdem Dein Nickname registriert ist, kannst Du mit \n" +"den SET und ACCESS Befehlen die Einstellungen Deines\n" +"Nicknames anpassen wie Du es möchtest. Stell bitte\n" +"sicher, dass Du Dir das Passwort bei der Registrierung\n" +"merkst - Du wirst es brauchen, wenn Du später\n" +"Änderungen an den Einstellungen vornehmen willst!\n" +"\n" +"Beachte auch, dass Gross/Kleinschreibung unterschieden\n" +"werden! ANOPE, Anope, und anope sind \n" +"verschiedene Passworte!\n" +"\n" +"Richtlinien bei der Auswahl eines Passwortes:\n" +"\n" +"Passworte sollten nicht einfach zu erraten sein.\n" +"Zum Beispiel Deinen echten Namen als Passwort zu \n" +"nehmen ist eine schlechte Idee. Deinen Nicknamen selbst\n" +"als Passwort zu nehmen, ist eine noch viel schlechtere\n" +"Idee :) und ausserdem würde %s es auch nicht erlauben.\n" +"Weiterhin sind kurze Passworte anfällig bei Trial-\n" +"and-Error-Versuchen, also sollte es zumindest 5 Zeichen\n" +"lang sein.\n" +"Zu guter letzt solltest Du auch keine Leerzeichen im \n" +"Passwort verwenden. \n" +"\n" +"Der Parameter eMail ist optional und ermöglicht\n" +"Nickserv Dir Dein Passwort per eMail zu senden, falls\n" +"Du es vergessen haben solltest. \n" +"Deine Privatsphäre wird respektiert und Deine \n" +"eMail-Adresse wird keinem Dritten verfügbar gemacht.\n" +"\n" +"Dieser Befehl (REGISTER) erstellt auch ausserdem\n" +"eine neue Gruppe für Deinen Nicknamen, die Dir erlaubt,\n" +"nachher weitere Nicknamen in diese Gruppe aufzunehmen,\n" +"die dann automatisch die gleiche Konfiguration und\n" +"Channel-Privilegien bekommen. Für weitere Informationen\n" +"über diese Funktion tippe /msg %s HELP GROUP." + +#: modules/commands/ns_register.cpp:145 +#, fuzzy +msgid "Registration is currently disabled." +msgstr "Die Registrierung von Channels ist derzeit deaktiviert." + +#: modules/commands/cs_set.cpp:400 +#, fuzzy +msgid "Regulate the use of critical commands" +msgstr " PEACE Regulate the use of critical commands" + +#: modules/commands/hs_request.cpp:283 +#, fuzzy +msgid "Reject the requested vHost for the given nick." +msgstr " STATUS Zeigt den Status des angegebenen Nicknamens an" + +#: modules/commands/hs_request.cpp:240 +#, fuzzy +msgid "Reject the requested vHost of a user" +msgstr " DEL Löscht den vHost eines Users" + +#: modules/commands/cs_suspend.cpp:151 +#, fuzzy +msgid "Releases a suspended channel" +msgstr " UNSUSPEND Hebt ein SUSPEND wieder auf" + +#: modules/commands/cs_suspend.cpp:191 +#, fuzzy +msgid "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." +msgstr "" +"Syntax: UNSUSPEND Channel\n" +"\n" +"Gibt einen Channel, der auf SUSPEND gesetzt ist,\n" +"wieder frei. Alle vorherigen Einstellungen werden\n" +"übernommen." + +#: modules/commands/os_module.cpp:56 +#, fuzzy +msgid "Reload a module" +msgstr " MODLOAD Lädt ein Modul" + +#: modules/commands/os_reload.cpp:19 +#, fuzzy +msgid "Reload services' configuration file" +msgstr " RELOAD Die Konfigurationsdatei neu einlesen" + +#: modules/commands/ns_group.cpp:236 +#, fuzzy +msgid "Remove a nick from a group" +msgstr " UNGROUP Remove a nick from a group" + +#: modules/commands/cs_unban.cpp:19 +#, fuzzy +msgid "Remove all bans preventing a user from entering a channel" +msgstr "" +" UNBAN Remove all bans preventing a user from entering a channel" + +#: modules/commands/os_noop.cpp:19 +#, fuzzy +msgid "Remove all operators from a server remotely" +msgstr " NOOP Alle O:Lines temporär deaktivieren" + +#: modules/commands/os_dns.cpp:543 +#, fuzzy, c-format +msgid "Removed IP %s from %s." +msgstr " Mode lock: %s" + +#: modules/commands/os_dns.cpp:460 +#, c-format +msgid "Removed server %s from zone %s." +msgstr "" + +#: modules/commands/os_dns.cpp:483 +#, c-format +msgid "Removed server %s." +msgstr "" + +#: modules/commands/cs_mode.cpp:909 +#, c-format +msgid "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." +msgstr "" + +#: modules/commands/cs_mode.cpp:890 +#, fuzzy, c-format +msgid "Removes %s status from you or the specified nick on a channel" +msgstr "Gibt dem angegebenen Nicknamen Op-Status in einem Raum" + +#: modules/commands/cs_updown.cpp:146 +#, fuzzy +msgid "Removes a selected nicks status from a channel" +msgstr "Kickt den angegebenen Nicknamen aus einen Channel" + +#: modules/commands/cs_updown.cpp:223 +msgid "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." +msgstr "" + +#: src/xline.cpp:412 +#, c-format +msgid "Removing %s because %s covers it." +msgstr "" + +#: modules/commands/bs_kick.cpp:1171 modules/commands/bs_kick.cpp:1173 +#: modules/commands/bs_kick.cpp:1176 +#, fuzzy +msgid "Repeat kicker" +msgstr " Repeat kicker : %s" + +#: modules/commands/hs_request.cpp:78 +#, fuzzy +msgid "Request a vHost for your nick" +msgstr "Du hast keine zulässige Email Adresse gesetzt." + +#: modules/commands/hs_request.cpp:179 +msgid "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." +msgstr "" + +#: modules/commands/ns_register.cpp:312 +#, fuzzy +msgid "Resend registration confirmation email" +msgstr " RELOAD Die Konfigurationsdatei neu einlesen" + +#: modules/commands/cs_set.cpp:621 +#, fuzzy +msgid "Restrict access to the channel" +msgstr " RESTRICTED Eingeschränkter Zugriff auf den Channel" + +#: modules/commands/cs_set.cpp:1291 +#, fuzzy +msgid "Restricted access" +msgstr "Eingeschränkter Zugang" + +#: modules/commands/cs_set.cpp:661 +#, fuzzy, c-format +msgid "Restricted access option for %s is now off." +msgstr "Eingeschränkter Access Option für %s ist jetzt ON." + +#: modules/commands/cs_set.cpp:655 +#, fuzzy, c-format +msgid "Restricted access option for %s is now on." +msgstr "Eingeschränkter Access Option für %s ist jetzt ON." + +#: modules/commands/cs_enforce.cpp:73 +#, fuzzy, c-format +msgid "Restricted enforced on %s." +msgstr "Eingeschränkter Access" + +#: modules/commands/cs_set.cpp:335 +#, fuzzy +msgid "Retain modes when channel is not in use" +msgstr "" +" KEEPTOPIC Topic behalten, wenn Channel nicht\n" +" benutzt wird" + +#: modules/commands/cs_topic.cpp:20 +#, fuzzy +msgid "Retain topic when channel is not in use" +msgstr "" +" KEEPTOPIC Topic behalten, wenn Channel nicht\n" +" benutzt wird" + +#: modules/commands/ns_getpass.cpp:19 +#, fuzzy +msgid "Retrieve the password for a nickname" +msgstr "" +" GETPASS Das Passwort eines Nicknamens aus der\n" +" Datenbank auslesen (nur wenn keine\n" +" Verschlüsselung aktiv ist)" + +#: modules/commands/hs_request.cpp:296 +msgid "Retrieves the vhost requests" +msgstr "" + +#: modules/commands/cs_getkey.cpp:19 +#, fuzzy +msgid "Returns the key of the given channel" +msgstr " GETKEY Gibt den Channel-Schlüßel wieder" + +#: modules/commands/cs_getkey.cpp:57 +#, fuzzy +msgid "Returns the key of the given channel." +msgstr " GETKEY Gibt den Channel-Schlüßel wieder" + +#: modules/commands/ns_getemail.cpp:58 +#, fuzzy +msgid "Returns the matching accounts that used given email." +msgstr " GETKEY Gibt den Channel-Schlüßel wieder" + +#: modules/commands/ns_status.cpp:19 +#, fuzzy +msgid "Returns the owner status of the given nickname" +msgstr " STATUS Zeigt den Status des angegebenen Nicknamens an" + +#: modules/commands/ns_getpass.cpp:50 +#, fuzzy +msgid "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." +msgstr "" +"Syntax: GETPASS Nickname\n" +"\n" +"Liest das Passwort von Nickname aus der Datenbank aus.\n" +"Beachte dass wenn jemand dieses Befehl benutzt,\n" +"diese Aktion im Logbuch der Services vermerkt wird.\n" +"Zusätzlich wird eine Nachricht an alle IRC Operatoren\n" +"per WALLOPS/GLOBOPS ausgesandt.\n" +"\n" +"Dieser Befehl ist nicht verfügbar bei aktivierter\n" +"Verschlüsselung." + +#: modules/commands/ns_status.cpp:55 +#, fuzzy +msgid "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." +msgstr "" +"Syntax: STATUS Nickname\n" +"\n" +"Liefert einen Wert zurück, der besagt, ob der augenblickliche\n" +"Nutzer des Nicknamens der identifizierte Eigentümer ist, oder \n" +"nicht.Die Antwort hat das Format:\n" +"\n" +" Nickname Status-Code Account\n" +"\n" +"where Nickname is the nickname sent with the command,\n" +"Status-Code is one of the following, and Account\n" +"is the account they are logged in as.\n" +"\n" +" 0 - User ist nicht online oder Nickname ist nicht registriert\n" +" 1 - User wird nicht als Eigentümer erkannt\n" +" 2 - User wird als Eigentümer erkannt durch die\n" +" Zugriffsliste\n" +" 3 - User wird als Eigentümer erkannt durch die\n" +" Identifizierung mit Passwort\n" +"\n" +"Bis zu 16 Nicknamen können mit dem Befehl übergeben werden,\n" +"der Rest wird ignoriert. Wenn kein Nickname angegeben wird,\n" +"wird Dein STATUS angezeigt." + +#: modules/commands/bs_kick.cpp:1181 modules/commands/bs_kick.cpp:1183 +#: modules/commands/bs_kick.cpp:1186 +#, fuzzy +msgid "Reverses kicker" +msgstr " Reverses kicker : %s" + +#: modules/commands/ns_logout.cpp:21 +#, fuzzy +msgid "Reverses the effect of the IDENTIFY command" +msgstr " LOGOUT Macht das IDENTIFY Befehl rückgängig" + +#: modules/commands/os_noop.cpp:20 +#, fuzzy +msgid "SET server" +msgstr "NOOP {SET|REVOKE} Server" + +#: modules/commands/os_dns.cpp:667 +msgid "SET server.name option value" +msgstr "" + +#: modules/commands/ns_cert.cpp:378 +#, fuzzy, c-format +msgid "SSL certificate fingerprint accepted, you are now identified to %s." +msgstr "Passwort akzeptiert - Du bist jetzt angemeldet." + +#: modules/commands/ns_cert.cpp:398 +#, fuzzy +msgid "SSL certificate fingerprint accepted, you are now identified." +msgstr "Passwort akzeptiert - Du bist jetzt angemeldet." + +#: modules/commands/cs_enforce.cpp:137 +#, c-format +msgid "SSL only enforced on %s." +msgstr "" + +#: modules/commands/cs_enforce.cpp:131 +msgid "SSLONLY enforced by " +msgstr "" + +#: modules/commands/os_shutdown.cpp:47 +#, fuzzy +msgid "Save databases and restart Services" +msgstr " RESTART Datenbanken speichern und Services neustarten" + +#: modules/commands/os_logsearch.cpp:32 +msgid "Searches logs for a matching pattern" +msgstr "" + +#: modules/commands/cs_set.cpp:1295 +#, fuzzy +msgid "Secure founder" +msgstr "Sicher Founder" + +#: modules/commands/cs_set.cpp:786 +#, fuzzy, c-format +msgid "Secure founder option for %s is now off." +msgstr "Secure Founder Option für %s ist jetzt ON." + +#: modules/commands/cs_set.cpp:780 +#, fuzzy, c-format +msgid "Secure founder option for %s is now on." +msgstr "Secure Founder Option für %s ist jetzt ON." + +#: modules/commands/cs_set.cpp:1297 +#, fuzzy +msgid "Secure ops" +msgstr "Sicher Ops" + +#: modules/commands/cs_set.cpp:850 +#, fuzzy, c-format +msgid "Secure ops option for %s is now off." +msgstr "Secure-Ops Option für %s ist jetzt ON." + +#: modules/commands/cs_set.cpp:844 +#, fuzzy, c-format +msgid "Secure ops option for %s is now on." +msgstr "Secure-Ops Option für %s ist jetzt ON." + +#: modules/commands/cs_set.cpp:723 +#, fuzzy, c-format +msgid "Secure option for %s is now off." +msgstr "Secure Option für %s ist jetzt ON." + +#: modules/commands/cs_set.cpp:717 +#, fuzzy, c-format +msgid "Secure option for %s is now on." +msgstr "Secure Option für %s ist jetzt ON." + +#: modules/commands/ns_set.cpp:1044 +#, fuzzy, c-format +msgid "Secure option is now off for %s." +msgstr "Sicherheitsfunktion (SECURE) ist für %s jetzt aktiviert (ON)." + +#: modules/commands/ns_set.cpp:1038 +#, fuzzy, c-format +msgid "Secure option is now on for %s." +msgstr "Sicherheitsfunktion (SECURE) ist für %s jetzt aktiviert (ON)." + +#: modules/commands/cs_enforce.cpp:42 +#, fuzzy, c-format +msgid "Secureops enforced on %s." +msgstr "Sicherheitsfunktion (SECURE) ist für %s jetzt aktiviert (ON)." + +#: modules/commands/cs_set.cpp:1293 modules/commands/ns_set.cpp:1311 +msgid "Security" +msgstr "Sicherheits Modus" + +#: modules/commands/cs_xop.cpp:570 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the access list." +msgstr "" +"Tippe %s%s HELP %s für weitere Informationen\n" +"zu einem bestimmten Befehl." + +#: modules/commands/cs_xop.cpp:573 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the flags system." +msgstr "" +"Tippe %s%s HELP %s für weitere Informationen\n" +"zu einem bestimmten Befehl." + +#: modules/commands/ms_send.cpp:24 +#, fuzzy +msgid "Send a memo to a nick or channel" +msgstr " SEND Sendet eine Memo an einen Nickname oder Channel" + +#: modules/commands/ms_staff.cpp:24 +#, fuzzy +msgid "Send a memo to all opers/admins" +msgstr " STAFF Sendet allen Opers/Admins eine Nachricht." + +#: modules/commands/ms_sendall.cpp:24 +#, fuzzy +msgid "Send a memo to all registered users" +msgstr " SENDALL Sendet eine Nachricht an alle registrierten User." + +#: modules/commands/gl_global.cpp:21 +#, fuzzy +msgid "Send a message to all users" +msgstr " GLOBAL Eine Notice an alle User schicken" + +#: modules/commands/ms_list.cpp:64 +#, fuzzy +msgid "Sender" +msgstr "Sicher Founder" + +#: modules/commands/ms_rsend.cpp:24 +#, fuzzy +msgid "Sends a memo and requests a read receipt" +msgstr "" +" RSEND Sendet eine Memo an einen Nickname oder Channel\n" +" und sendet Dir eine Empfangsbestätigung zurück" + +#: modules/commands/ns_resetpass.cpp:50 +#, fuzzy +msgid "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." +msgstr "" +"Syntax: RESETPASS nickname\n" +"\n" +"Sends a code key to the nickname with instructions on how to\n" +"reset their password." + +#: modules/commands/ms_sendall.cpp:52 +#, fuzzy +msgid "Sends all registered users a memo containing memo-text." +msgstr "" +"Syntax: SENDALL Memo-Text\n" +"Sendet allen registrieten Usern eine Nachricht mit dem \n" +"Memo-Text." + +#: modules/commands/ms_staff.cpp:48 +#, fuzzy +msgid "Sends all services staff a memo containing memo-text." +msgstr "" +"Syntax: STAFF Memo-Text\n" +"Sendet allen Usern mit Zugriff auf die Services eine Nachricht mit\n" +"dem Memo-Text." + +#: modules/commands/ms_send.cpp:66 +#, fuzzy +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." +msgstr "" +"Syntax: SEND {Nickname | Channel} Memo-Text\n" +"\n" +"Sendet an einen Nicknamen oder Channel die Memo \n" +"mit dem Inhalt Memo-Text. Wird an einen Nicknamen \n" +"gesendet, erhält der Empfänger eine Notice, dass\n" +"er/sie eine neue Memo hat.\n" +"Der Empfänger (Nickname/Channel) muss registriert sein." + +#: modules/commands/ms_rsend.cpp:80 +#, fuzzy +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." +msgstr "" +"Syntax: RSEND {Nickname | Channel} Memo-Text\n" +"\n" +"Sendet an einen Nicknamen oder Channel die Memo \n" +"mit dem Inhalt Memo-Text. Wird an einen Nicknamen \n" +"gesendet, erhält der Empfänger eine Notice, dass er/sie \n" +"eine neue Memo hat. Der Empfänger (Nickname/Channel) muss \n" +"registriert sein. Wenn Deine Memo gelesen worden ist, \n" +"bekommst Du eine Auto-Memo die dich Informirmiert\n" +"das der / die jenige Dein Memo-Text gelesen hat." + +#: modules/commands/ms_read.cpp:199 +#, fuzzy +msgid "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Syntax: READ [Channel] {Nummer | List | LAST | NEW}\n" +"\n" +"Schickt Dir den Inhalt der Memo, die Du lesen möchtest.\n" +"Wird LAST angegeben, bekommst Du die Memo die Du als \n" +"letztes erhalten hast. Mit NEW werden Dir alle neuen,\n" +"ungelesenen, Memos geschickt. \n" +"\n" +"Andernfalls kannst Du auch mit Hilfe der Memo-Nummer\n" +"Nummer oder einer Bereichsliste Dir Memos anzeigen\n" +"lassen, zum Beispiel so:\n" +"\n" +" READ 2-5,7-9\n" +" Zeigt den Inhalt der Memos 2 bis 5 und 7 bis 9." + +#: modules/commands/os_dns.cpp:218 +#, fuzzy +msgid "Server" +msgstr "NOOP {SET|REVOKE} Server" + +#: modules/commands/os_dns.cpp:375 +#, fuzzy, c-format +msgid "Server %s added to zone %s." +msgstr " %s (wird nicht auslaufen)" + +#: modules/commands/os_dns.cpp:345 +#, fuzzy, c-format +msgid "Server %s already exists." +msgstr "%s existiert bereits." + +#: modules/commands/os_noop.cpp:31 modules/commands/os_dns.cpp:430 +#: modules/commands/os_dns.cpp:493 modules/commands/os_dns.cpp:532 +#: modules/commands/os_dns.cpp:571 modules/commands/os_dns.cpp:604 +#: modules/commands/os_dns.cpp:639 +#, fuzzy, c-format +msgid "Server %s does not exist." +msgstr " %s (wird nicht auslaufen)" + +#: modules/commands/os_dns.cpp:619 +#, fuzzy, c-format +msgid "Server %s has no configured IPs." +msgstr "Der Nickname %s wurde aus der Datenbank entfernt." + +#: modules/commands/os_dns.cpp:357 +#, fuzzy, c-format +msgid "Server %s is already in zone %s." +msgstr "%s ist bereits in %s! " + +#: modules/commands/os_dns.cpp:614 +#, fuzzy, c-format +msgid "Server %s is already pooled." +msgstr "Module %s is already loaded." + +#: modules/commands/os_dns.cpp:609 +#, fuzzy, c-format +msgid "Server %s is not currently linked." +msgstr "%s ist derzeit online." + +#: modules/commands/os_dns.cpp:443 +#, fuzzy, c-format +msgid "Server %s is not in zone %s." +msgstr " %s (wird nicht auslaufen)" + +#: modules/commands/os_dns.cpp:384 +#, fuzzy, c-format +msgid "Server %s is not linked to the network." +msgstr "Der Bot von %s wurde entfernt." + +#: modules/commands/os_dns.cpp:644 +#, fuzzy, c-format +msgid "Server %s is not pooled." +msgstr " %s (wird nicht auslaufen)" + +#: modules/commands/os_dns.cpp:465 +#, c-format +msgid "Server %s must be quit before it can be deleted." +msgstr "" + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Servers" +msgstr "NOOP {SET|REVOKE} Server" + +#: modules/commands/os_stats.cpp:155 +#, c-format +msgid "Servers found: %d" +msgstr "Server gefunden: %d" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Service" +msgstr "Server gefunden: %d" + +#: modules/commands/ns_recover.cpp:51 +#, fuzzy, c-format +msgid "Service's hold on %s has been released." +msgstr "Die Services haben den Nicknamen wieder verfügbar gemacht." + +#: data/nickserv.example.conf:236 data/chanserv.example.conf:827 +#, fuzzy +msgid "Services Operator commands" +msgstr "%s ist ein services operator vom Typ %s." + +#: modules/commands/os_defcon.cpp:443 modules/commands/os_defcon.cpp:454 +#: modules/commands/os_defcon.cpp:462 modules/commands/os_defcon.cpp:470 +#: modules/commands/os_defcon.cpp:478 +#, fuzzy +msgid "Services are in DefCon mode, please try again later." +msgstr "" +"Dieser Service ist derzeit deaktiviert, bitte versuche es später nochmal" + +#: include/language.h:70 +#, fuzzy +msgid "Services are in read-only mode!" +msgstr "Services sind jetzt im read-only Modus." + +#: modules/commands/os_defcon.cpp:186 modules/commands/os_defcon.cpp:213 +#, fuzzy, c-format +msgid "Services are now at DEFCON %d." +msgstr "Services sind jetzt beim DEFCON %d" + +#: modules/commands/os_set.cpp:128 +#, fuzzy, c-format +msgid "Services are now in debug mode (level %d)." +msgstr "Die Services sind jetzt im Debug-Modus (Level %d)." + +#: modules/commands/os_set.cpp:114 +#, fuzzy +msgid "Services are now in debug mode." +msgstr "Die Services sind jetzt im Debug-Modus." + +#: modules/commands/os_set.cpp:159 +msgid "Services are now in expire mode." +msgstr "Services sind jetzt im Expire Modus." + +#: modules/commands/os_set.cpp:153 +msgid "Services are now in no expire mode." +msgstr "Services sind jetzt im No Expire Modus." + +#: modules/commands/os_set.cpp:120 +#, fuzzy +msgid "Services are now in non-debug mode." +msgstr "Die Services sind nicht mehr im Debug-Modus." + +#: modules/commands/os_set.cpp:47 +msgid "Services are now in read-only mode." +msgstr "Services sind jetzt im read-only Modus." + +#: modules/commands/os_set.cpp:53 +msgid "Services are now in read-write mode." +msgstr "Services sind jetzt im read-write Modus." + +#: src/mail.cpp:76 +msgid "Services have been configured to not send mail." +msgstr "Der Service emails zu versenden wurde deaktiviert." + +#: modules/commands/os_ignore.cpp:280 +#, fuzzy +msgid "Services ignore list:" +msgstr " IGNORE Die \"Services Ignore Liste\" bearbeiten" + +#: modules/commands/os_mode.cpp:33 modules/commands/os_kick.cpp:39 +#, fuzzy +msgid "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" +msgstr "" +"Services können die Modi nicht ändern. Sind die U:lines des\n" +"Servers richtig konfiguriert?" + +#: modules/commands/os_stats.cpp:140 +#, fuzzy, c-format +msgid "Services up %s." +msgstr "Server gefunden: %d" + +#: modules/commands/ns_set.cpp:266 +#, fuzzy, c-format +msgid "Services will from now on set status modes on %s in channels." +msgstr "" +"Die Services werden %s jetzt nicht mehr automatisch Op-Status geben in den " +"Channels." + +#: modules/commands/cs_set.cpp:114 +#, fuzzy, c-format +msgid "Services will no longer automatically give modes to users in %s." +msgstr "" +"Die Services werden %s jetzt nicht mehr automatisch Op-Status geben in den " +"Channels." + +#: modules/commands/ns_set.cpp:272 +#, fuzzy, c-format +msgid "Services will no longer set status modes on %s in channels." +msgstr "" +"Die Services werden %s jetzt nicht mehr automatisch Op-Status geben in den " +"Channels." + +#: modules/commands/cs_set.cpp:108 +#, fuzzy, c-format +msgid "Services will now automatically give modes to users in %s." +msgstr "" +"Die Services werden %s jetzt automatisch Op-Status geben in den Channels." + +#: modules/commands/ns_set.cpp:940 +#, c-format +msgid "Services will now reply to %s with messages." +msgstr "Die Services werden jetzt %s mit messages antworten." + +#: modules/commands/ns_set.cpp:946 +#, c-format +msgid "Services will now reply to %s with notices." +msgstr "Die Services werden jetzt %s mit notices antworten." + +#: modules/commands/os_reload.cpp:34 +#, fuzzy +msgid "Services' configuration has been reloaded." +msgstr "Die Konfigurationsdatei wurde neu eingelesen." + +#: modules/commands/os_session.cpp:192 +msgid "Session" +msgstr "" + +#: modules/commands/os_session.cpp:382 +#, c-format +msgid "Session limit for %s set to %d." +msgstr "Verbindungslimit für %s geändert auf %d." + +#: modules/commands/os_session.cpp:257 modules/commands/os_session.cpp:534 +msgid "Session limiting is disabled." +msgstr "Eingeschränkte Verbindungen sind deaktiviert." + +#: modules/commands/os_stats.cpp:195 +#, c-format +msgid "Sessions: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/ns_set.cpp:74 +#, fuzzy +msgid "Set SET-options on another nickname" +msgstr " SASET Setzt SET Einstellungen auf einen anderen Nicknamen" + +#: modules/commands/cs_set.cpp:20 +#, fuzzy +msgid "Set channel options and information" +msgstr "" +" SET Bestimmte Channel-Optionen und\n" +" Informationen einstellen" + +#: modules/commands/cs_set.cpp:137 +#, fuzzy +msgid "Set how Services make bans on the channel" +msgstr "" +" BANTYPE Ändert den Ban-Typ, den die Services\n" +" in dem Channel anwenden" + +#: modules/commands/ms_set.cpp:206 +#, fuzzy +msgid "Set options related to memos" +msgstr "" +" SET Stellt bestimmte Optionen ein in Hinsicht\n" +" auf Memos" + +#: modules/commands/ns_set.cpp:19 +#, fuzzy +msgid "Set options, including kill protection" +msgstr " SET Optionen einstellen, auch Kill-Schutz" + +#: modules/commands/cs_set.cpp:472 +#, fuzzy +msgid "Set the channel as permanent" +msgstr " PERSIST Set the channel as permanent" + +#: modules/commands/cs_set.cpp:204 +#, fuzzy +msgid "Set the channel description" +msgstr " DESC Ändert die Channel-Beschreibung" + +#: modules/commands/ns_set.cpp:329 +#, fuzzy +msgid "Set the display of your group in Services" +msgstr " DISPLAY Ändert den \"Ursprung\" Deiner Gruppe" + +#: modules/commands/cs_set.cpp:266 +#, fuzzy +msgid "Set the founder of a channel" +msgstr " FOUNDER Stellt den Gründer des Channels ein" + +#: modules/commands/ns_set.cpp:793 +#, fuzzy +msgid "Set the language Services will use when messaging you" +msgstr "" +" LANGUAGE Stellt die Sprache ein, in der Dir die \n" +" Services antworten sollen." + +#: modules/commands/ns_set.cpp:172 +#, fuzzy +msgid "Set the nickname password" +msgstr " PASSWORD Setzt das Passwort eines Nicknamens" + +#: modules/commands/cs_set.cpp:949 +#, fuzzy +msgid "Set the successor for a channel" +msgstr " SUCCESSOR Stellt den Vertreter des Founders ein" + +#: modules/commands/hs_set.cpp:125 +#, fuzzy +msgid "Set the vhost for all nicks in a group" +msgstr " SETALL Setzt einer Gruppe einen vHost" + +#: modules/commands/hs_set.cpp:19 +#, fuzzy +msgid "Set the vhost of another user" +msgstr " SET Setzt einem User einen vHost" + +#: modules/commands/os_set.cpp:169 +#, fuzzy +msgid "Set various global Services options" +msgstr " SET Verschiedene Services Optionen einstellen" + +#: modules/commands/ns_set.cpp:119 +#, fuzzy +msgid "Set your nickname password" +msgstr " PASSWORD Setzt das Passwort Deines Nicknamens neu" + +#: modules/commands/bs_kick.cpp:271 +#, fuzzy, c-format +msgid "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK channel ITALICS {ON|OFF} [ttb]\n" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +"ttb is the number of times a user can be kicked\n" +"before it get banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:307 +#, fuzzy, c-format +msgid "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK Channel BADWORDS {ON|OFF} [ttb]\n" +"\n" +"Schaltet den Bad-Word-Kicker an oder aus. Wenn er \n" +"aktiviert ist, kickt der er den Bösewicht, der ein Wort\n" +"aus der Bad-Word-Liste sagt.\n" +"\n" +"Die Bad-Words werden mit dem BADWORDS Befehl festgelegt.\n" +"/msg %s HELP BADWORDS um weitere Informationen zu erhalten.\n" +"\n" +"ttb beschreibt wie oft der User gekickt wird, bevor\n" +"er einen Ban bekommt. Wenn keine ttb angegeben \n" +"wird, wird er nie gebannt." + +#: modules/commands/cs_set.cpp:186 +#, fuzzy +msgid "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" +msgstr "" +"Syntax: %s Channel BANTYPE Ban-Typ\n" +"\n" +"Stellt den Ban-Typ für den Channel ein, den die\n" +"Services anwenden, wenn sie einen Ban eintragen\n" +"(z.B. bei einem Auto-Kick).\n" +"\n" +"bantype muss einer der folgenden Werte sein:\n" +"\n" +"0: Ban in der Form *!user@host\n" +"1: Ban in der Form *!*user@host\n" +"2: Ban in der Form *!*@host\n" +"3: Ban in der Form *!*user@*.domain" + +#: modules/commands/bs_kick.cpp:345 +#, fuzzy +msgid "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK Channel BOLDS {ON|OFF} [ttb]\n" +"\n" +"Kicken bei fettem Schriftstil an oder aus. Wenn \n" +"der Parameter ON gegeben ist, werden User, die fetten \n" +"Schriftstil verwenden, durch den Bot gekickt.\n" +"\n" +"ttb beschreibt wie oft der User gekickt wird, \n" +"bevor er einen Ban bekommt. Wenn keine ttb \n" +"angegeben wird, wird er nie gebannt." + +#: modules/commands/bs_kick.cpp:436 +#, fuzzy, c-format +msgid "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK Channel CAPS {ON|OFF} [ttb [min [prozente]]]\n" +"\n" +"Kicken bei CAPS an oder aus. Wenn der Parameter\n" +"ON gegeben ist, werden User, die CAPS verwenden,\n" +"durch den Bot gekickt.\n" +"\n" +"Der Bot kickt nur, wenn mindestens min Grossbuchstaben\n" +"verwendet wurden und der Text mindestens prozente%% \n" +"Grossbuchstaben enthält. (Standard ist hier zehn Zeichen und\n" +"25 %% - dieser wird angewendet, wenn die Paramter nicht\n" +"angegeben werden.\n" +"\n" +"ttb beschreibt wie oft der User gekickt wird, bevor\n" +"er einen Ban bekommt. Wenn keine ttb angegeben \n" +"wird, wird er nie gebannt." + +#: modules/commands/bs_kick.cpp:475 +#, fuzzy +msgid "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK Channel COLORS {ON|OFF} [ttb]\n" +"\n" +"Kicken bei Farben an oder aus. Wenn der Parameter\n" +"ON gegeben ist, werden User, die Farben verwenden,\n" +"durch den Bot gekickt.\n" +"\n" +"ttb beschreibt wie oft der User gekickt wird, bevor\n" +"er einen Ban bekommt. Wenn keine ttb angegeben \n" +"wird, wird er nie gebannt." + +#: modules/commands/cs_set.cpp:255 +#, fuzzy +msgid "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." +msgstr "" +"Syntax: %s Channel DESC Beschreibung\n" +"\n" +"Ändert die Beschreibung für einen Channel, die bei\n" +"dem LIST und INFO Befehl angezeigt wird." + +#: modules/commands/bs_kick.cpp:571 +#, fuzzy +msgid "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK Channel FLOOD {ON|OFF} [ttb [ln [secs]]]\n" +"\n" +"Schaltet den Flood-Kicker an oder aus. Wenn er \n" +"aktiviert ist, kickt er User, die den Channel \n" +"mit mindestens ln Zeilen in secs flooden.\n" +"Sollte weder ln noch secs angegeben sein,\n" +"so werden defaultmässig 6 Zeilen / 10 Sekunden \n" +"gesetzt.\n" +"\n" +"ttb beschreibt wie oft der User gekickt wird, bevor\n" +"er einen Ban bekommt. Wenn keine ttb angegeben \n" +"wird, wird er nie gebannt." + +#: modules/commands/bs_kick.cpp:607 +#, fuzzy +msgid "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK channel ITALICS {ON|OFF} [ttb]\n" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +"ttb is the number of times a user can be kicked\n" +"before it get banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:706 +#, fuzzy +msgid "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK Channel REPEAT {ON|OFF} [ttb [nummer]]\n" +"\n" +"Schaltet den Wiederholungs-Kicker an oder aus.Wenn \n" +"dieser aktiviert ist, wird ein User, der sich nummer \n" +"mal wiederholt, gekickt. Sollte kein nummer angegeben \n" +"sein, so wird 3 als Standardwert gesetzt.\n" +"\n" +"ttb beschreibt wie oft der User gekickt wird, bevor\n" +"er einen Ban bekommt. Wenn keine ttb angegeben \n" +"wird, wird er nie gebannt." + +#: modules/commands/bs_kick.cpp:742 +#, fuzzy +msgid "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK Channel REVERSES {ON|OFF} [ttb]\n" +"\n" +"Kicken bei invertiertem Schriftstil an oder aus. \n" +"Wenn der Parameter ON gegeben ist, werden User, die \n" +"invertierten Schriftstil verwenden, durch den Bot \n" +"gekickt.\n" +"\n" +"ttb beschreibt wie oft der User gekickt wird, bevor\n" +"er einen Ban bekommt. Wenn keine ttb angegeben \n" +"wird, wird er nie gebannt." + +#: modules/commands/bs_kick.cpp:776 +#, fuzzy +msgid "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK Channel UNDERLINES {ON|OFF} [ttb]\n" +"\n" +"Kicken bei Unterstreichungen an oder aus. Wenn der \n" +"Parameter ON gegeben ist, werden User, die \n" +"Unterstreichungen verwenden, durch den Bot gekickt.\n" +"\n" +"ttb beschreibt wie oft der User gekickt wird, bevor\n" +"er einen Ban bekommt. Wenn keine ttb angegeben \n" +"wird, wird er nie gebannt." + +#: modules/commands/hs_set.cpp:206 +#, fuzzy +msgid "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." +msgstr "" +"Syntax: SETALL Nickname Hostmaske.\n" +"Setzt allen Usern einer Gruppe einen vHost. Falls Dein\n" +"IRCd vIdents unterstützt, kannst Du mit \n" +"SETALL @ eine Ident sowie \n" +"einen vHosts setzen.\n" +"* Anmerkung: Dieser Befehl betrifft keine Nicknamen,\n" +"die nachträglich zu der Gruppe hinzugefügt wurden." + +#: modules/commands/hs_set.cpp:99 +#, fuzzy +msgid "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." +msgstr "" +"Syntax: SET Nickname Hostmaske.\n" +"Setzt einem User einen vHost anstelle des normalen\n" +"Hosts. Falls Dein IRCd vIdents unterstützt, kannst\n" +"Du mit SET @ auch eine Ident\n" +"wie einen vHost setzen." + +#: modules/commands/os_set.cpp:199 +#, fuzzy +msgid "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" +msgstr "" +"Syntax: SET Option Einstellungen\n" +"\n" +"Ändert globale Einstellungen der Services Optionen.\n" +"Diese Optionen lassen sich ändern:\n" +"\n" +" READONLY Nur-Lese Modus der Datenbank an\n" +" oder aus\n" +" LOGCHAN Zeigt Logmessages in einem Chan\n" +" DEBUG Debug-Modus der Services an oder aus\n" +" NOEXPIRE Auslauf-Modus der Services\n" +" an oder aus\n" +" SUPERADMIN Den Super-Admin Modus an oder aus\n" +" IGNORE Ignore-Modus an oder aus\n" +" LIST Optionen-Liste" + +#: modules/commands/ms_set.cpp:235 +#, fuzzy, c-format +msgid "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Syntax: SET Option Parameter\n" +"\n" +"Stellt verschiedene Optionen bezüglich der Memos ein.\n" +"Option kann einer der Parameter sein:\n" +"\n" +" NOTIFY Stellt ein, wann Du benachrichtigt wirst,\n" +" wenn Du eine neue Memo bekommst.\n" +"\n" +" LIMIT Ändert die maximale Anzahl Memos, die\n" +" Du empfangen kannst.\n" +"\n" +"Tippe: /msg %s HELP SET Option für weitere Informationen\n" +"über eine bestimmte Option." + +#: modules/commands/ns_set.cpp:33 modules/commands/ns_set.cpp:88 +#, fuzzy +msgid "Sets various nickname options. option can be one of:" +msgstr "" +"Syntax: SET Option Parameter\n" +"\n" +"Stellt verschiedene Optionen zu Deinem Nicknamen ein.\n" +"Option kann eines der folgenden Werte sein:" + +#: modules/commands/ns_set.cpp:237 +msgid "" +"Sets whether services should set channel status modes on you automatically." +msgstr "" + +#: modules/commands/cs_set.cpp:1090 +#, fuzzy +msgid "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." +msgstr "" +"Syntax: SET Channel NOEXPIRE {ON | OFF}\n" +"\n" +"Ändert das NOEXPIRE-Flag an einem Channel. Wird es\n" +"auf ON gestellt, wird der Channel bei Nichtnutzung\n" +"nicht auslaufen." + +#: modules/commands/ns_set.cpp:315 +#, fuzzy, c-format +msgid "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." +msgstr "" +"Syntax: SASET nickname AUTOOP {ON | OFF}\n" +"\n" +"Bestimmt ob der angegebene Nickname automatisch Op-Status erhält.\n" +"Wird AUTOOP auf ON gestellt erlaubt es ChanServ den\n" +"angegebenen Nicknamen automatisch Op-Status zu geben,\n" +"wenn der Nick die Channels betritt." + +#: modules/commands/ns_set.cpp:1145 +#, fuzzy +msgid "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." +msgstr "" +"Syntax: SASET nickname NOEXPIRE {ON | OFF}\n" +"\n" +"Bestimmt ob ein Nickname nach einer gewissen Zeit \n" +"verfällt. Wird NOEXPIRE auf ON gesetzt verfällt\n" +"der Nickname nie." + +#: modules/commands/ns_set.cpp:288 +#, fuzzy, c-format +msgid "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." +msgstr "" +"Syntax: SET AUTOOP {ON | OFF}\n" +"\n" +"Bestimmt ob Du automatisch Op-Status erhälst. Auf ON gestellt\n" +"erlaubt es ChanServ Dir automatisch Op-Status zu geben,\n" +"wenn Du die Channels betrittst." + +#: modules/commands/cs_access.cpp:648 modules/commands/cs_access.cpp:689 +#, fuzzy, c-format +msgid "" +"Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." +msgstr "" +"Einstellung %s ist unbekannt. Tippe /msg %s HELP LEVELS DESC für eine " +"ausführliche Einstellungsliste." + +#: modules/commands/os_set.cpp:133 +#, fuzzy +msgid "Setting for DEBUG must be ON, OFF, or a positive number." +msgstr "" +"Die Einstellung von DEBUG kann nur ON, OFF, oder eine positive Zahl sein." + +#: modules/commands/os_set.cpp:162 +#, fuzzy +msgid "Setting for NOEXPIRE must be ON or OFF." +msgstr "Die Einstellung von NOEXPIRE kann nur ON oder OFF sein." + +#: modules/commands/os_set.cpp:56 +#, fuzzy +msgid "Setting for READONLY must be ON or OFF." +msgstr "Der Wert für READONLY muss entweder ON oder OFF sein." + +#: modules/commands/os_set.cpp:95 +#, fuzzy +msgid "Setting for super admin must be ON or OFF." +msgstr "Der Wert für READONLY muss entweder ON oder OFF sein." + +#: modules/commands/cs_set.cpp:74 +#, fuzzy +msgid "Should services automatically give status to users" +msgstr "" +" AUTOOP Sollten Dir die Services automatisch\n" +" Op-Status geben. " + +#: modules/commands/os_stats.cpp:203 +#, fuzzy +msgid "Show status of Services and network" +msgstr " STATS Status des Netzes und der Services anzeigen" + +#: modules/commands/os_logsearch.cpp:152 +#, c-format +msgid "Showed %d/%d matches for %s." +msgstr "" + +#: modules/commands/cs_set.cpp:872 +#, fuzzy +msgid "Sign kicks that are done with the KICK command" +msgstr "" +" SIGNKICK Kicks durch ChanServ in dem Channel\n" +" werden durch den Kicker signiert" + +#: modules/commands/cs_set.cpp:921 +#, fuzzy, c-format +msgid "Signed kick option for %s is now off." +msgstr "Signierte kicks Option für %s ist jetzt ON." + +#: modules/commands/cs_set.cpp:913 +#, fuzzy, c-format +msgid "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." +msgstr "" +"Signierte kicks Option für %s ist jetzt ON, hängt aber von den\n" +"Level des Benutzers der den Befehl verwendet ab." + +#: modules/commands/cs_set.cpp:906 +#, fuzzy, c-format +msgid "Signed kick option for %s is now on." +msgstr "Signierte kicks Option für %s ist jetzt ON." + +#: modules/commands/cs_set.cpp:1299 +msgid "Signed kicks" +msgstr "Signierte kicks" + +#: modules/commands/ms_rsend.cpp:60 modules/commands/ms_send.cpp:59 +#, fuzzy, c-format +msgid "Sorry, %s currently has too many memos and cannot receive more." +msgstr "%s hat zu viele Memos gespeichert und kann keine weiteren empfangen." + +#: modules/commands/cs_seen.cpp:294 +#, c-format +msgid "Sorry, I have not seen %s." +msgstr "" + +#: modules/commands/bs_badwords.cpp:404 +#, fuzzy +msgid "Sorry, bad words list modification is temporarily disabled." +msgstr "Das Ändern der Bad Words-Liste ist derzeit deaktiviert." + +#: modules/commands/bs_assign.cpp:30 modules/commands/bs_assign.cpp:98 +#, fuzzy +msgid "Sorry, bot assignment is temporarily disabled." +msgstr "Die SET-Optionen sind derzeit deaktiviert." + +#: modules/commands/bs_bot.cpp:281 modules/commands/bs_assign.cpp:164 +msgid "Sorry, bot modification is temporarily disabled." +msgstr "Das Verändern von Bot-Einstellungen ist derzeit deaktiviert." + +#: modules/fantasy.cpp:42 modules/commands/bs_kick.cpp:813 +#: modules/commands/bs_kick.cpp:878 +msgid "Sorry, bot option setting is temporarily disabled." +msgstr "Die SET-Optionen sind derzeit deaktiviert." + +#: modules/commands/bs_set.cpp:115 +#, fuzzy +msgid "Sorry, changing bot options is temporarily disabled." +msgstr "Die SET-Optionen sind derzeit deaktiviert." + +#: modules/commands/cs_xop.cpp:112 modules/commands/cs_xop.cpp:235 +#: modules/commands/cs_xop.cpp:444 +#, fuzzy, c-format +msgid "Sorry, channel %s list modification is temporarily disabled." +msgstr "Die Channel AOP-Liste kann derzeit nicht geändert werden." + +#: modules/commands/cs_access.cpp:547 modules/commands/cs_flags.cpp:405 +msgid "Sorry, channel access list modification is temporarily disabled." +msgstr "Das Ändern der Channel-Access-Liste wurde zwischenzeitig deaktiviert." + +#: modules/commands/cs_akick.cpp:469 +msgid "Sorry, channel autokick list modification is temporarily disabled." +msgstr "Das Bearbeiten der AutoKick-Liste wurde zwischenzeitlich deaktiviert." + +#: modules/commands/cs_drop.cpp:29 +msgid "Sorry, channel de-registration is temporarily disabled." +msgstr "Das Entfernen von Channel-Registrierungen ist derzeit deaktiviert." + +#: modules/commands/cs_register.cpp:35 +msgid "Sorry, channel registration is temporarily disabled." +msgstr "Die Registrierung von Channels ist derzeit deaktiviert." + +#: modules/commands/bs_kick.cpp:181 +msgid "Sorry, kicker configuration is temporarily disabled." +msgstr "Die Konfiguration des Kickers ist derzeit deaktiviert." + +#: modules/commands/ms_set.cpp:216 +msgid "Sorry, memo option setting is temporarily disabled." +msgstr "MEMO SET Befehl wurde kurzzeitig deaktiviert." + +#: include/language.h:116 +#, fuzzy +msgid "Sorry, memo sending is temporarily disabled." +msgstr "MEMO SET Befehl wurde kurzzeitig deaktiviert." + +#: modules/commands/ns_drop.cpp:29 +msgid "Sorry, nickname de-registration is temporarily disabled." +msgstr "Das Entfernen von Nicknamen ist derzeit deaktiviert." + +#: modules/commands/ns_group.cpp:120 +msgid "Sorry, nickname grouping is temporarily disabled." +msgstr "Das Gruppieren von Nicknamen ist derzeit deaktiviert." + +#: modules/commands/ns_register.cpp:139 +msgid "Sorry, nickname registration is temporarily disabled." +msgstr "Das Registrieren von Nicknamen ist derzeit deaktiviert." + +#: modules/commands/ns_access.cpp:33 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d access entries has been reached." +msgstr "Die Access-Liste ist auf %d Einträge beschränkt." + +#: modules/commands/ns_ajoin.cpp:141 +#, c-format +msgid "Sorry, the maximum of %d auto join entries has been reached." +msgstr "" + +#: modules/commands/ns_cert.cpp:173 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d certificate entries has been reached." +msgstr "Du kannst nur %d Einträge auf der Access-Liste speichern." + +#: modules/commands/ms_ignore.cpp:55 +#, fuzzy, c-format +msgid "Sorry, the memo ignore list for %s is full." +msgstr "Die Liste der Begrüßungsnachrichten für %s ist voll." + +#: modules/commands/cs_access.cpp:204 modules/commands/cs_flags.cpp:174 +#: modules/commands/cs_xop.cpp:201 +#, fuzzy, c-format +msgid "" +"Sorry, you can only have %d access entries on a channel, including access " +"entries from other channels." +msgstr "Die Access-Liste ist auf %d Einträge beschränkt." + +#: modules/commands/cs_akick.cpp:177 +#, c-format +msgid "Sorry, you can only have %d autokick masks on a channel." +msgstr "Du kannst nur max. %d Einträge auf der AutoKick-Liste haben." + +#: modules/commands/bs_badwords.cpp:286 +#, c-format +msgid "Sorry, you can only have %d bad words entries on a channel." +msgstr "Du kannst nur %d Einträge in der Bad Words-Liste eines Channels haben." + +#: include/language.h:103 +#, fuzzy, c-format +msgid "Sorry, you have already exceeded your limit of %d channels." +msgstr "Du kannst nur %d Einträge in der Bad Words-Liste eines Channels haben." + +#: include/language.h:102 +#, fuzzy, c-format +msgid "Sorry, you have already reached your limit of %d channels." +msgstr "Du kannst nur %d Einträge in der Bad Words-Liste eines Channels haben." + +#: modules/commands/os_dns.cpp:218 +msgid "State" +msgstr "" + +#: modules/commands/cs_seen.cpp:117 +msgid "Statistics and maintenance for seen data" +msgstr "" + +#: modules/commands/os_stats.cpp:131 +msgid "Statistics reset." +msgstr "Statistiken zurückgesetzt." + +#: modules/commands/ns_update.cpp:36 +msgid "Status updated (memos, vhost, chmodes, flags)." +msgstr "Status aktualisiert (memos, vhost, chmodes, flags)." + +#: modules/commands/bs_kick.cpp:1432 +msgid "Stop flooding!" +msgstr "Hör auf zu flooden!" + +#: modules/commands/bs_kick.cpp:1448 +msgid "Stop repeating yourself!" +msgstr "Hör auf dich dauernd zu wiederholen!" + +#: modules/commands/cs_set.cpp:746 +#, fuzzy +msgid "Stricter control of channel founder status" +msgstr " SECUREFOUNDER Strengere Kontrolle des Founder-Status" + +#: modules/commands/cs_set.cpp:810 +#, fuzzy +msgid "Stricter control of chanop status" +msgstr " SECUREOPS Strengere Kontrolle des Op-Status im Channel" + +#: modules/commands/ns_alist.cpp:75 modules/commands/cs_info.cpp:50 +msgid "Successor" +msgstr "" + +#: modules/commands/cs_set.cpp:1006 +#, fuzzy, c-format +msgid "Successor for %s changed to %s." +msgstr "Vertreter von %s wurde geändert zu %s." + +#: modules/commands/cs_set.cpp:1008 +#, c-format +msgid "Successor for %s unset." +msgstr "Der Eintrag des Vertreters für %s wurde entfernt." + +#: modules/commands/os_set.cpp:81 +#, fuzzy +msgid "" +"Super admin can not be set because it is not enabled in the configuration." +msgstr "SuperAdmin muss in der services.conf eingeschaltet werden." + +#: modules/commands/ns_suspend.cpp:60 +#, fuzzy +msgid "Suspend a given nick" +msgstr " SUSPEND Suspendet den angegebenen Nicknamen" + +#: modules/commands/cs_suspend.cpp:236 modules/commands/ns_suspend.cpp:250 +#, fuzzy +msgid "Suspend reason" +msgstr "Nickname [Grund]" + +#: modules/commands/cs_suspend.cpp:232 modules/commands/ns_suspend.cpp:246 +msgid "Suspended" +msgstr "" + +#: modules/commands/cs_suspend.cpp:234 modules/commands/ns_suspend.cpp:248 +msgid "Suspended by" +msgstr "" + +#: modules/commands/cs_suspend.cpp:238 modules/commands/ns_suspend.cpp:252 +#, fuzzy +msgid "Suspended on" +msgstr " SUSPEND Suspendet den angegebenen Nicknamen" + +#: modules/commands/ns_suspend.cpp:147 +#, fuzzy +msgid "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." +msgstr "" +"Verbietet jegliche Nutzung des Channels. Kann durch\n" +"den UNSUSPEND Befehls wieder aufgehoben werden,\n" +"wobei alle vorherigen Einstellungen wieder übernommen\n" +"werden.\n" +"\n" +"Ein Grund kann auf manchen Netzwerke notwendig sein." + +#: modules/commands/cs_suspend.cpp:240 modules/commands/ns_suspend.cpp:254 +#, fuzzy +msgid "Suspension expires" +msgstr "wird nicht auslaufen" + +#: modules/commands/cs_sync.cpp:19 +#, fuzzy +msgid "Sync users channel modes" +msgstr "%s hat Deine Usermodi geändert." + +#: modules/commands/cs_sync.cpp:49 +msgid "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." +msgstr "" + +#: modules/commands/hs_group.cpp:42 +#, fuzzy +msgid "Syncs the vhost for all nicks in a group" +msgstr "" +" GROUP Gleicht den vHost aller Nicknamen \n" +" in einer Gruppe an" + +#: src/command.cpp:146 +msgid "Syntax" +msgstr "" + +#: modules/commands/ns_group.cpp:373 +#, fuzzy, c-format +msgid "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." +msgstr "" +"Syntax: GLIST\n" +"\n" +"Zeigt alle Nicknamen die in Deiner Gruppe enthalten sind.\t" + +#: modules/commands/ns_group.cpp:363 +#, fuzzy, c-format +msgid "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." +msgstr "" +"Syntax: GLIST [Nickname]\n" +"\n" +"Wird kein Parameter angegeben, werden alle Nicknamen\n" +"in Deiner Gruppe angezeigt.\n" +"\n" +"Ansonsten werden alle Nicknamen, die in der Gruppe des\n" +"angegebenen Nicknamens sind, aufgelistet." + +#: modules/commands/os_set.cpp:227 +#, fuzzy +msgid "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." +msgstr "" +"Syntax: SET NOEXPIRE {ON | OFF}\n" +"\n" +"Setzt den No-Expire-Mode an oder aus. Wird er\n" +"aktiviert, werden Nicknamen, Channels und AKILLs nicht\n" +"auslaufen bis dieser Modus wieder ausgeschaltet\n" +"wird.\n" +"Diese Option ist äquivalent mit der Befehlszeilen-\n" +"Option -noexpire." + +#: modules/commands/ms_set.cpp:287 +#, fuzzy, c-format +msgid "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." +msgstr "" +"Syntax: SET LIMIT [Channel] Limit\n" +"\n" +"Ändert das Limit der Anzahl der Memos, die Du\n" +"(oder der angegebene Channel) haben darf. Wird dies auf\n" +"0 gesetzt, kann Dir niemand mehr Memos senden.\n" +"Du kannst es jedoch auch nicht höher als %d setzen." + +#: modules/commands/ms_set.cpp:267 +#, fuzzy, c-format +msgid "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." +msgstr "" +"Syntax: SET LIMIT [User | Channel] {Limit | NONE} [HARD]\n" +"\n" +"Ändert die max. Anzahl von Memos die ein User oder\n" +"Channel haben kann. Das setzen dieser Grenze auf 0\n" +"verhindert das Empfangen jeglicher Memos. Wird \n" +"hingegen NONE eingestellt, kann der User so\n" +"viele Memos empfangen und behalten wie er will.\n" +"Wird kein User oder Channel angegeben, veränderst\n" +"Du Dein eigenes Limit.\n" +"\n" +"Durch den Zusatzparameter HARD wird eine Änderung\n" +"des Limits durch den entsprechenden User verhindert.\n" +"Wird dieser Parameter nicht angegeben, hat das den\n" +"gegenteiligen Effekt - der User kann sein Limit \n" +"ändern (sogar wenn das vorherige Limit auf \n" +"HARD eingestellt war).\n" +"\n" +"Die Nutzung des SET LIMIT Befehls ist beschränkt auf \n" +"Services Administratoren. Jeder andere User kann nur \n" +"das Limit von sich selbst oder dem Channel ändern, in \n" +"dem er einen entsprechenden Zugriffslevel besitzt, er \n" +"kann auch nicht die Grenze von %d Memos überschreiten.\n" +"Der HARD Befehl kann er auch nicht nutzen." + +#: modules/commands/os_set.cpp:208 +#, fuzzy, c-format +msgid "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." +msgstr "" +"Syntax: SET LIST\n" +"Zeigt Dir eine Liste der verfügbaren Einstellungen von %s" + +#: modules/commands/os_set.cpp:234 +#, fuzzy +msgid "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." +msgstr "" +"Syntax: SET NOEXPIRE {ON | OFF}\n" +"\n" +"Setzt den No-Expire-Mode an oder aus. Wird er\n" +"aktiviert, werden Nicknamen, Channels und AKILLs nicht\n" +"auslaufen bis dieser Modus wieder ausgeschaltet\n" +"wird.\n" +"Diese Option ist äquivalent mit der Befehlszeilen-\n" +"Option -noexpire." + +#: modules/commands/ms_set.cpp:246 +#, fuzzy +msgid "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." +msgstr "" +"Syntax: SET NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +"\n" +"Ändert den Zeitpunkt, wann MemoServ dich über neue\n" +"eingegangene Memos informiert:\n" +"\n" +" ON Du wirst über neue Nachrichten informiert,\n" +" wenn Du dich identifizierst, /AWAY aufhebst,\n" +" und wenn sie an dich gesandt werden.\n" +" LOGON Du wirst nur benachrichtigt, wenn Du dich\n" +" identifizierst oder das /AWAY rückgängig\n" +" machst.\n" +" NEW Du wirst nur informiert, wenn sie an dich\n" +" gesendet werden.\n" +" MAIL You will be notified of memos by email aswell as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF Es wird keine Benachrichtigung über neue\n" +" Memos stattfinden.\n" +"\n" +"ON ist eine Kombination aus LOGON und NEW." + +#: modules/commands/os_set.cpp:212 +#, fuzzy +msgid "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." +msgstr "" +"Syntax: SET READONLY {ON | OFF}\n" +"\n" +"Schaltet den Read-Only-Mode an oder aus. Im\n" +"Read-Only-Modus können normale User nichts mehr\n" +"an den Datenbanken der Services ändern, dies beinhaltet\n" +"Channel und Nicknamen-Zugriffslisten, etc. IRCops mit\n" +"genügend Rechten werden weiterhin Änderungen an der\n" +"AKILL-Liste, Nicknamen sperren oder DROPEN (löschen) dürfen,\n" +"aber diese Änderungen werden nicht gespeichert, bis\n" +"der Read-Only-Mode deaktiviert wurde bevor die\n" +"Services beendet oder neu gestartet werden.\n" +"\n" +"Diese Option ist äquivalent mit der Befehlszeilen-\n" +"Option -readonly." + +#: modules/commands/os_set.cpp:243 +#, fuzzy +msgid "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." +msgstr "" +"Syntax: SET SUPERADMIN {ON | OFF}\n" +"Der Super-Admin Modus verleiht Dir zusätzliche Rechte, wie\n" +"zB. Founder in jedem Channel, etc.\n" +"Dieser Modus ist nicht dauerhaft und sollte nur genutzt\n" +"werden, wenn er wirklich gebraucht wird. Danach sollte er\n" +"sofort wieder ausgeschaltet werden." + +#: modules/commands/ns_identify.cpp:107 +#, fuzzy, c-format +msgid "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." +msgstr "" +"Syntax: IDENTIFY [account] Passwort\n" +"\n" +"Beweist %s, dass Du wirklich der Besitzer dieses \n" +"Nicknamens bist. Viele Befehle erzwingen, dass \n" +"Du dich vorher hiermit autorisierst, bevor Du sie \n" +"benutzen kannst. Das Passwort ist das von Deiner \n" +"Registrierung, die Du mit dem REGISTER Befehl \n" +"gesetzt hast." + +#: modules/commands/cs_invite.cpp:91 +#, fuzzy, c-format +msgid "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Syntax: INVITE Channel\n" +"\n" +"Diese Funktion erlaubt es Dir, dich durch %s in den\n" +"angegebenen Channel einladen zu lassen. Standardmässig\n" +"wird dies nur ausgeführt, wenn den Nickname auf der \n" +"Zugriffsliste des Channels einen Level grösser 5 \n" +"(oder INVITE) hat." + +#: modules/commands/cs_unban.cpp:103 +#, fuzzy, c-format +msgid "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Syntax: UNBAN Channel [nick]\n" +"\n" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel.\n" +"\n" +"By default, limited to AOPs or those with level 5 and above\n" +"on the channel." + +#: modules/commands/os_jupe.cpp:56 +#, fuzzy +msgid "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." +msgstr "" +"Syntax: JUPE Server [Grund]\n" +"Durch die Services wird ein Server \"gejupitert\". Dies\n" +"bedeutet, dass ein Server vorgetäuscht und so der\n" +"echte Server daran gehindert wird, zu connecten. Der\n" +"\"Server\" kann durch das normale SQUIT Befehls\n" +"entfernt werden. Wird ein Grund angegeben,\n" +"wird dieser im Server Informationsfeld angezeigt,\n" +"ansonsten nur \"Jupitered by \"." + +#: modules/commands/cs_seen.cpp:261 +msgid "Tells you about the last time a user was seen" +msgstr "" + +#: modules/commands/os_shutdown.cpp:19 +msgid "Terminate Services WITHOUT saving" +msgstr " Datenbanken NICHT speichern und Services beenden" + +#: modules/commands/os_shutdown.cpp:73 +msgid "Terminate services with save" +msgstr " Datenbanken speichern und Services beenden" + +#: modules/commands/os_news.cpp:156 +msgid "Text" +msgstr "" + +#: modules/commands/cs_access.cpp:576 +msgid "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." +msgstr "" + +#: modules/commands/cs_access.cpp:587 +msgid "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." +msgstr "" + +#: modules/commands/cs_access.cpp:593 +msgid "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." +msgstr "" + +#: modules/commands/cs_flags.cpp:447 +msgid "" +"The CLEAR command clears the channel access list. This requires channel " +"founder access." +msgstr "" + +#: modules/commands/cs_seen.cpp:173 +#, c-format +msgid "" +"The CLEAR command lets you clean the database by removing all entries from " +"the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." +msgstr "" + +#: modules/commands/bs_badwords.cpp:438 +#, fuzzy +msgid "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." +msgstr "" +"Syntax: HOP Channel ADD Nickname\n" +" HOP Channel DEL {Nickname | entry-num | Liste}\n" +" HOP Channel LIST [Maske | Liste]\n" +" HOP Channel CLEAR\n" +"\n" +"Verwaltet die HOP (HalfOP) Liste eines Channels. User auf\n" +"dieser Liste werden automatisch gehalfopt, wenn sie joinen.\n" +"\n" +"Der HOP ADD Befehl fügt den jeweiligen Nicknamen zur HOP-Liste\n" +"hinzu.\n" +"Der HOP DEL Befehl löscht den jeweiligen Nicknamen aus der\n" +"HOP-Liste. Wenn mehrere Eintragsnummern angegeben werden,\n" +"werden diese Einträge gelöscht. (Siehe Beispiel bei LIST.)\n" +" \n" +"\n" +"Der HOP LIST Befehl zeigt die aktuelle HOP-Liste an. Wenn\n" +"Wildcard Masks angegeben werden, werden nur die betroffenen\n" +"Einträge angezeigt. Werden mehrere Eintragsnummern angegeben,\n" +"werden nur diese Einträge angezeigt, zB:\n" +"\n" +" HOP #channel LIST 2-5,7-9\n" +" Listet die HOP Einträge 2 bis 5 und 7 bis 9.\n" +"Der HOP CLEAR Befehl löscht alle Einträge der HOP-Liste.\n" +"HOP ADD, HOP DEL und HOP LIST sind auf AOPs oder\n" +"höher beschränkt, während HOP CLEAR nur vom Founder genutzt\n" +"werden kann.\n" +"\n" +"Dieser Befehl kann für Deinen Channel ausgeschaltet sein, in \n" +"diesem Fall nutze bitte die Access Liste. Für weitere Infos zur\n" +"Access Liste, tippe bitte /msg %s HELP ACCESS und\n" +"/msg %s HELP SET XOP für Infos über den Wechsel vom xOP und\n" +"vom Access System." + +#: modules/commands/cs_entrymsg.cpp:241 +msgid "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:253 +msgid "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:245 +msgid "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:250 +msgid "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." +msgstr "" + +#: modules/commands/ns_set.cpp:713 +msgid "The IMMED option is not available on this network." +msgstr "Die IMMED Option ist in diesem Netzwerk nicht verfügbar." + +#: modules/commands/cs_access.cpp:821 +#, fuzzy, c-format +msgid "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." +msgstr "" +"Syntax: LEVELS channel SET Typ [Level|FOUNDER]\n" +" LEVELS channel {DIS | DISABLE} Typ\n" +" LEVELS channel LIST\n" +" LEVELS channel RESET\n" +"\n" +"The LEVELS Befehl erlaubt eine gute Kontrolle über die\n" +"Bedeutung der numerischen Zugangslevel die für Chaträume benutzt werden. \n" +"Mit diesem Befehl kannst du das Zugriffslevel für die meisten Funktionen von " +"%s festlegen\n" +" ( SET FOUNDER und dieser Befehl sind immer dem Founder vorbehalten)\n" +"\n" +"LEVELS SET ändert das Zugriffslevel für eine Funktion oder Gruppe. LEVELS " +"DISABLE (oder kurz DIS for )\n" +"deaktiviert eine automatische Funktion oder erlaubt jedem den Zugriff a\n" +" INCLUSIVE Founder (Wenn auch der Founder\n" +"diese Funkrion jederzeit wieder einachalten kann).\n" +"\n" +"LEVELS LIST zeigt das aktuelle Level für jede Funktion oder Gruppe von " +"Funktionen\n" +" LEVELS RESET setzt die Levels auf Grundeinstellungen eines neuen Chatraums " +"zurück\n" +" (siehe\n" +"HELP ACCESS LEVELS).\n" +"Für eine vollständige Liste der Funktionen für die Levels gesetzt werden " +"können: HELP LEVELS DESC." + +#: modules/commands/cs_flags.cpp:442 +msgid "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." +msgstr "" + +#: modules/commands/cs_flags.cpp:435 +msgid "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access " +"list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. " +"You are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of " +"what your access is." +msgstr "" + +#: modules/commands/cs_seen.cpp:172 +msgid "" +"The STATS command prints out statistics about stored nicks and memory usage." +msgstr "" + +#: modules/commands/ns_register.cpp:291 +#, fuzzy +msgid "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." +msgstr "" +" \n" +"Der Paramater eMail ist optional und setzt die eMail für Deinen\n" +"Nick.\n" +"Deine Privatsphäre wird respektiert und Deine eMail-Adresse ist Dritten\n" +"nicht zugänglich.\n" +" \n" + +#: modules/commands/cs_log.cpp:258 +#, c-format +msgid "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." +msgstr "" + +#: modules/commands/cs_ban.cpp:64 +#, fuzzy, c-format +msgid "The %s list for %s is full." +msgstr "Die Liste der Begrüßungsnachrichten für %s ist voll." + +#: modules/commands/os_sxline.cpp:220 +#, fuzzy, c-format +msgid "The %s list has been cleared." +msgstr "Die AKILL-Liste wurde geleert." + +#: modules/commands/os_akill.cpp:377 +msgid "The AKILL list has been cleared." +msgstr "Die AKILL-Liste wurde geleert." + +#: modules/commands/os_defcon.cpp:136 modules/commands/os_defcon.cpp:225 +#, fuzzy, c-format +msgid "The Defcon level is now at: %d" +msgstr "Das Defcon-Level ist jetzt auf Level: %d" + +#: modules/commands/ns_info.cpp:171 +#, c-format +msgid "The E-mail address of %s will now be hidden from %s INFO displays." +msgstr "Die Emailadresse %s wird jetzt bei %s INFO Abrufen versteckt." + +#: modules/commands/ns_info.cpp:172 +#, c-format +msgid "The E-mail address of %s will now be shown in %s INFO displays." +msgstr "Die Emailadresse %s wird jetzt bei %s INFO Abrufen angezeigt." + +#: modules/commands/cs_flags.cpp:449 +msgid "The available flags are:" +msgstr "" + +#: modules/commands/os_defcon.cpp:240 +#, fuzzy +msgid "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." +msgstr "" +"Syntax: DEFCON [1|2|3|4|5]\n" +"Das Defcon-System kann benutzt werden, um vordefinierte\tEinstellung \n" +"von einschränkungen der Services einzubinden - nützlich während \n" +"versuchter Angriffe auf das Netzwerk." + +#: modules/ns_maxemail.cpp:51 +#, c-format +msgid "The email address %s has reached its usage limit of %d users." +msgstr "" + +#: modules/ns_maxemail.cpp:49 +#, c-format +msgid "The email address %s has reached its usage limit of 1 user." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:142 +#, c-format +msgid "The entry message list for %s is full." +msgstr "Die Liste der Begrüßungsnachrichten für %s ist voll." + +#: modules/commands/cs_access.cpp:796 +msgid "The following feature/function names are available:" +msgstr "" + +#: modules/commands/cs_access.cpp:584 +msgid "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." +msgstr "" + +#: modules/commands/os_session.cpp:240 +#, fuzzy, c-format +msgid "" +"The host %s currently has %d sessions with a limit of %d because it matches " +"entry: %s." +msgstr "Der Host %s hat momentan %d Verbindungen und ein Limit von %d." + +#: modules/commands/ms_check.cpp:54 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has been read." +msgstr "" +"Die letzte Memo die Du zu %s gesendet hast (gesendet am %s) wurde gelesen." + +#: modules/commands/ms_check.cpp:52 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has not yet been read." +msgstr "" +"Die letzte Memo die Du zu %s gesendet hast (gesendet am %s) wurde nicht " +"gelesen." + +#: modules/commands/ns_info.cpp:189 +#, c-format +msgid "The last quit message of %s will now be hidden from %s INFO displays." +msgstr "" +"Die letzte Quit-Nachricht von %s wird jetzt bei %s INFO Abrufen versteckt." + +#: modules/commands/ns_info.cpp:190 +#, c-format +msgid "The last quit message of %s will now be shown in %s INFO displays." +msgstr "" +"Die letzte Quit-Nachricht von %s wird jetzt bei %s INFO Abrufen angezeigt." + +#: modules/commands/ns_info.cpp:177 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." +msgstr "" +"Die letzte bekannte user@host Maske von %s wird jetzt bei %s INFO Abrufen " +"versteckt." + +#: modules/commands/ns_info.cpp:178 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." +msgstr "" +"Die letzte bekannte user@host Maske von %s wird jetzt bei %s INFO Abrufen " +"angezeigt." + +#: modules/commands/cs_enforce.cpp:190 +#, c-format +msgid "The limit on %s is not valid." +msgstr "Das Limit von %s ist ungültig." + +#: modules/commands/os_forbid.cpp:193 +msgid "The mask must contain at least one non wildcard character." +msgstr "" + +#: modules/commands/ms_set.cpp:153 +#, c-format +msgid "The memo limit for %s may not be changed." +msgstr "Du hast keine Berechtigung das Memo-Limit für %s zu ändern." + +#: modules/commands/cs_mode.cpp:347 +#, fuzzy, c-format +msgid "The mode lock list of %s is full." +msgstr "Die Liste der Begrüßungsnachrichten für %s ist voll." + +#: modules/commands/ns_set.cpp:355 +#, c-format +msgid "The new display MUST be a nickname of the nickname group %s." +msgstr "" + +#: include/language.h:98 +#, c-format +msgid "The new display is now %s." +msgstr "Die neue Anzeige ist jetzt %s" + +#: modules/commands/os_svs.cpp:57 +#, c-format +msgid "The nick %s is now being changed to %s." +msgstr "Der Nickname %s wird jetzt zu %s geändert." + +#: modules/commands/bs_bot.cpp:149 +msgid "The old information is the same as the new information specified." +msgstr "" + +#: modules/commands/os_info.cpp:157 +#, fuzzy, c-format +msgid "The oper info already exists on %s." +msgstr "%s existiert bereits." + +#: modules/commands/os_info.cpp:147 +#, fuzzy, c-format +msgid "The oper info list for %s is full." +msgstr "Die Liste der Begrüßungsnachrichten für %s ist voll." + +#: modules/commands/ns_info.cpp:183 +#, c-format +msgid "" +"The services access status of %s will now be hidden from %s INFO displays." +msgstr "" +"Die Services-Zugriffsberechtigungen von %s werden jetzt bei %s INFO Abrufen " +"versteckt." + +#: modules/commands/ns_info.cpp:184 +#, c-format +msgid "The services access status of %s will now be shown in %s INFO displays." +msgstr "" +"Die Services-Zugriffsberechtigungen von %s werden jetzt bei %s INFO Abrufen " +"angezeigt." + +#: modules/commands/os_session.cpp:433 +msgid "The session exception list is empty." +msgstr "Die Liste der Verbindungsausnahmen ist leer." + +#: modules/commands/ns_recover.cpp:121 +msgid "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:195 +#, c-format +msgid "There are %d memos on channel %s." +msgstr "Es gibt %d Benachrichtigungen für den Channel %s." + +#: modules/commands/bs_botlist.cpp:47 +msgid "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" +msgstr "" +"Es sind derzeit keine Bots verfügbar. Frag einen \n" +"Services Administrator, ob er einen erstellt." + +#: modules/commands/os_dns.cpp:213 +msgid "There are no configured servers." +msgstr "" + +#: modules/commands/os_forbid.cpp:392 +#, fuzzy, c-format +msgid "There are no forbids of type %s." +msgstr "Es gibt %d Benachrichtigungen für den Channel %s." + +#: modules/commands/ns_group.cpp:162 +#, fuzzy +msgid "There are too many nicks in your group." +msgstr "Es befinden sich zu viele Nicks in der Gruppe von %s." + +#: modules/commands/cs_log.cpp:123 +#, c-format +msgid "There currently are no logging configurations for %s." +msgstr "Zur Zeit gibt es keine Log Informationen für %s." + +#: modules/pseudoclients/memoserv.cpp:193 +#, c-format +msgid "There is %d memo on channel %s." +msgstr "Es gibt %d Benachrichtigung für Channel %s." + +#: include/language.h:110 +#, c-format +msgid "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." +msgstr "" +"Im Chatraum %s gibt es eine neue Nachricht.Tippe %s%s READ %s %d um sie zu " +"lesen." + +#: modules/commands/bs_assign.cpp:132 +#, c-format +msgid "There is no bot assigned to %s anymore." +msgstr "Der Bot von %s wurde entfernt." + +#: modules/commands/os_news.cpp:33 +msgid "There is no logon news." +msgstr "Es gibt keine Logon News." + +#: modules/commands/os_news.cpp:43 +msgid "There is no oper news." +msgstr "Es gibt keine Oper-News." + +#: modules/commands/os_news.cpp:53 +msgid "There is no random news." +msgstr "Keine randomnews vorhanden." + +#: modules/commands/os_config.cpp:41 +#, fuzzy, c-format +msgid "There is no such configuration block %s." +msgstr "Zur Zeit gibt es keine Log Informationen für %s." + +#: modules/commands/cs_mode.cpp:706 +#, fuzzy, c-format +msgid "There is no such mode %s." +msgstr "Es gibt keine Oper-News." + +#: modules/commands/ms_set.cpp:52 +msgid "There's no email address set for your nick." +msgstr "Du hast keine zulässige Email Adresse gesetzt." + +#: modules/commands/os_forbid.cpp:304 modules/commands/os_forbid.cpp:496 +#, c-format +msgid "This channel has been forbidden: %s" +msgstr "Dieser Channel wurde verboten: %s." + +#: modules/commands/cs_suspend.cpp:121 +#, fuzzy +msgid "This channel has been suspended." +msgstr "Dieser Channel kann nicht benutzt werden." + +#: modules/commands/cs_suspend.cpp:232 +#, fuzzy +msgid "This channel is suspended." +msgstr "Dieser Channel kann nicht benutzt werden." + +#: modules/commands/cs_suspend.cpp:268 +msgid "This channel may not be used." +msgstr "Dieser Channel kann nicht benutzt werden." + +#: modules/commands/os_dns.cpp:702 +msgid "" +"This command allows managing DNS zones used for controlling what servers " +"users\n" +"are directed to when connecting. Omitting all parameters prints out the " +"status of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to " +"this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, " +"the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given " +"zones." +msgstr "" + +#: modules/commands/hs_group.cpp:72 +#, fuzzy +msgid "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." +msgstr "" +"Syntax:GROUP\n" +"\n" +"Dieser Befehl erlaubt es Usern, den vHost ihres aktuellen\n" +"Nicknamens, zum vHost der gesamten Gruppe zu setzen." + +#: modules/commands/ns_register.cpp:299 +msgid "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." +msgstr "" + +#: modules/m_rewrite.cpp:145 +#, c-format +msgid "This command is an alias to the command %s." +msgstr "" + +#: modules/commands/ns_register.cpp:95 +#, fuzzy +msgid "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." +msgstr "" +"Syntax: CONFIRM passcode\n" +"\n" +"Dies ist der zweite Schritt beim Registrieren des Nicknamens.\n" +"Du mußt diesen Befehl ausführen, um ihn mit %s zu registrieren.\n" +"Der Passcode (oder auch Authentifizierungscode genannt) wird\n" +"an Deine email-adresse gesendet beim ersten Schritt des\n" +"Registrationsprozesses. Für mehr Informationen über die erste\n" +"Stufe des Registrationsprozesses tippe: /msg %s HELP REGISTER\n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." + +#: modules/commands/os_modinfo.cpp:70 +#, fuzzy +msgid "This command lists information about the specified loaded module." +msgstr "" +"Syntax: MODINFO Modul-Name\n" +"Dieser Befehl listet Informationen über das benannte, geladene \n" +"Module auf." + +#: modules/commands/hs_list.cpp:136 +#, fuzzy +msgid "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." +msgstr "" +"Syntax: LIST [Muster|#X-Y]\n" +"Dieser Befehl listet dem Operator die registrierten vHost's.\n" +"Wenn ein Muster angegeben ist, werden nur die Einträge des \n" +"Nicknamens oder die vHost's, die dem gegeben Muster entsprechen, \n" +"z.B. Rob* für alle Einträge, die mit \"Rob\" beginnen.\n" +"Wenn ein #X-Y Style benutzt wird, werden nur die Einträge \n" +"zwischen den angegeben Faktoren angezeigt, z.B. #1-3 wird \n" +"die ersten drei Nicknamen/vHost-Einträge anzeigen.\n" +"Die Liste benutzt jedes mal den Wert von NSListMax als ein \n" +"festes Limit für die Anzahl der dem Operator anzuzeigenden \n" +"Einträge." + +#: modules/commands/os_module.cpp:45 +#, fuzzy +msgid "" +"This command loads the module named modname from the modules\n" +"directory." +msgstr "" +"Syntax: MODLOAD Modul-Name\n" +"Dieser Befehl lädt das benannte Module aus dem \n" +"modules - Verzeichnis." + +#: modules/commands/ns_group.cpp:201 +#, fuzzy +msgid "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." +msgstr "" +"Syntax: GROUP Ziel Passwort\n" +"\n" +"Dieser Befehl verbindet Deinen Nicknamen mit der\n" +"Gruppe von Ziel. Passwort ist das Passwort\n" +"des Ziel-Nicknamens.\n" +"\n" +"Das Teilnehmen in der Gruppe teilt Deine Konfiguration,\n" +"Memos und Channel-Privilegien mit allen Nicknamen der \n" +"Gruppe, und vieles mehr!\n" +"\n" +"Eine Gruppe existiert so lange es sinnvoll ist. Dies\n" +"bedeutet, dass selbst wenn ein Nicknamen der Gruppe \n" +"GEDROPED (gelöscht) wird, die geteilten Konfigurationen,\n" +"Rechte erhalten bleiben, so lange mindestens ein Nickname \n" +"in der Gruppe verbleibt.\n" +" \n" +"Dieser Befehl lässt sich sogar verwenden, wenn Dein Nickname\n" +"(noch) nicht registriert ist. Wenn er jedoch registriert ist, \n" +"musst Du dich vorher identifizieren. \n" +"Tippe /msg %s HELP IDENTIFY für weitere Informationen.\n" +"\n" +"Es wird allerdings empfohlen diesen Befehl mit einem\n" +"nicht-registrierten Nicknamen zu verwenden, da der \n" +"Nickname automatisch registriert wird, wenn er der Gruppe \n" +"beitritt. Das Beitreten einer Gruppe mit einem bereits \n" +"registrierten Nicknamen kann durch die Netzwerk-Administratoren \n" +"gesperrt sein.\n" +" \n" +"Du kannst nur in einer Gruppe zur gleichen Zeit sein.\n" +"Das Zusammenführen verschiedener Gruppen ist nicht\n" +"möglich.\n" +"\n" +"Achtung: Alle Mitglieder einer Gruppe haben dasselbe\n" +"Passwort." + +#: modules/commands/ns_ajoin.cpp:292 +msgid "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." +msgstr "" + +#: modules/commands/ns_set.cpp:345 modules/commands/ns_set.cpp:669 +msgid "" +"This command may not be used on this network because nickname ownership is " +"disabled." +msgstr "" + +#: modules/commands/os_module.cpp:118 +#, fuzzy +msgid "This command reloads the module named modname." +msgstr "" +"Syntax: MODLOAD Modul-Name\n" +"Dieser Befehl lädt das benannte Module aus dem \n" +"modules - Verzeichnis." + +#: modules/commands/hs_request.cpp:344 +msgid "This command retrieves the vhost requests." +msgstr "" + +#: modules/commands/os_logsearch.cpp:159 +msgid "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." +msgstr "" + +#: modules/commands/cs_status.cpp:106 +msgid "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." +msgstr "" + +#: modules/commands/ns_group.cpp:285 +msgid "" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." +msgstr "" +"Syntax: UNGROUP [nick]\n" +"Dieser befehl hebt die Gruppierung deines Nicks oder eines ausgewählten " +"Nicks auf,\n" +"Der Nick ohne Gruppierung behält Registrierung\n" +"Zeit,PAsswort, Email, Begrüßungsnachricht, Sprache, url, and icq. \n" +"Alles andere wird zurückgesetzt.Du kannst die Gruppierung nicht aufheben " +"wenn sich nur ein nick\n" +"in der gruppe befindet." + +#: modules/commands/os_module.cpp:168 +#, fuzzy +msgid "This command unloads the module named modname." +msgstr "" +"Syntax: MODLOAD Modul-Name\n" +"Dieser Befehl lädt das benannte Module aus dem \n" +"modules - Verzeichnis." + +#: modules/commands/ns_register.cpp:353 +msgid "This command will resend you the registration confirmation email." +msgstr "" + +#: include/language.h:90 +#, c-format +msgid "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" +msgstr "" + +#: modules/commands/os_forbid.cpp:469 +#, fuzzy, c-format +msgid "This nickname has been forbidden: %s" +msgstr "Dieser Nickname ist zur Zeit gesperrt, Grund: %s" + +#: modules/commands/ns_recover.cpp:99 +#, c-format +msgid "This nickname has been recovered by %s." +msgstr "Dieser Nickname wurde von %s wiederhergestellt." + +#: modules/commands/ns_recover.cpp:77 +#, c-format +msgid "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." +msgstr "" + +#: include/language.h:95 +msgid "This nickname has been registered; you may not use it." +msgstr "" +"Dieser Nickname wurde bereits registriert, du kannst ihn nicht benutzen." + +#: modules/commands/ns_suspend.cpp:246 +#, fuzzy +msgid "This nickname is suspended." +msgstr "Dieser Channel kann nicht benutzt werden." + +#: include/language.h:92 +#, c-format +msgid "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." +msgstr "" + +#: modules/commands/ms_read.cpp:95 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %d" +msgstr "Memo %d von %s (%s). Um sie zu löschen, tippe /msg %s DEL %s %d" + +#: modules/commands/ms_read.cpp:93 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %s %d" +msgstr "Memo %d von %s (%s). Um sie zu löschen, tippe /msg %s DEL %s %d" + +#: modules/commands/bs_kick.cpp:791 +msgid "To protect ops against bot kicks" +msgstr "" + +#: modules/commands/bs_kick.cpp:856 +msgid "To protect voices against bot kicks" +msgstr "" + +#: modules/commands/cs_list.cpp:46 +msgid "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." +msgstr "" +"Um nach Chaträumen beginnend mit # zu suchen, suche nach dem\n" +"Namen des Chatraums ohne das # Zeichen (anope anstelle von#anope)." + +#: modules/commands/os_logsearch.cpp:139 +#, fuzzy, c-format +msgid "Too many results for %s." +msgstr "Access-Liste von %s:" + +#: modules/extra/stats/cs_fantasy_top.cpp:149 +#, c-format +msgid "Top %i of %s" +msgstr "" + +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Topic" +msgstr "Topic-Sperre" + +#: modules/commands/cs_topic.cpp:258 +#, fuzzy +msgid "Topic lock" +msgstr "Topic-Sperre" + +#: modules/commands/cs_topic.cpp:114 +#, c-format +msgid "Topic lock option for %s is now off." +msgstr "Topic-Sperre Option für %s ist jetzt deaktiviert (OFF)." + +#: modules/commands/cs_topic.cpp:97 +#, fuzzy, c-format +msgid "Topic lock option for %s is now on." +msgstr "Topic-Sperre Option für %s ist jetzt ON." + +#: modules/commands/cs_topic.cpp:256 +#, fuzzy +msgid "Topic retention" +msgstr "Topic-Wiederherstellung" + +#: modules/commands/cs_topic.cpp:60 +#, c-format +msgid "Topic retention option for %s is now off." +msgstr "Die Topic-Beibehaltung für %s ist jetzt deaktiviert (OFF)." + +#: modules/commands/cs_topic.cpp:54 +#, fuzzy, c-format +msgid "Topic retention option for %s is now on." +msgstr "Die Topic-Beibehaltung für %s ist jetzt aktiviert (ON)." + +#: modules/commands/cs_topic.cpp:265 +msgid "Topic set by" +msgstr "" + +#: modules/commands/bs_kick.cpp:1323 +msgid "Turn caps lock OFF!" +msgstr "Schalte Caps-Lock aus!" + +#: modules/extra/stats/m_chanstats.cpp:17 +#: modules/extra/stats/m_chanstats.cpp:71 +#, fuzzy +msgid "Turn chanstats statistics on or off" +msgstr "" +" SECURE Aktiviert/Deaktiviert den Sicherheitsmodus\n" +" für Deinen Nicknamen" + +#: modules/commands/ns_set.cpp:1009 +#, fuzzy +msgid "Turn nickname security on or off" +msgstr "" +" SECURE Aktiviert/Deaktiviert den Sicherheitsmodus\n" +" für Deinen Nicknamen" + +#: modules/commands/ns_set.cpp:655 +#, fuzzy +msgid "Turn protection on or off" +msgstr " KILL Stellt Kill-Schutz an oder aus." + +#: modules/commands/ns_list.cpp:264 +#, fuzzy, c-format +msgid "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Syntax: SASET nickname PRIVATE {ON | OFF}\n" +"\n" +"Ändert %s's Privat-Modus für den Nicknamen.\n" +"Mit eingeschaltetem PRIVATE wird der Nickname\n" +"nicht auf Listen erscheinen, die durch %s's LIST \n" +"Befehl erstellt wurden.\n" +"\n" +"(Jeder der den Nicknamen kennt, kann gezielt mit \n" +"dem INFO Befehl Informationen über den Nicknamen \n" +"abrufen, unabhängig vom Privat-Modus.)" + +#: modules/commands/ns_list.cpp:236 +#, fuzzy, c-format +msgid "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Syntax: SET PRIVATE {ON | OFF}\n" +"\n" +"Ändert %s's Privat-Modus für Deinen Nicknamen.\n" +"Mit eingeschaltetem PRIVATE wird Dein Nickname\n" +"nicht auf Listen erscheinen, die durch %s's LIST \n" +"Befehls erstellt wurden.\n" +"\n" +"(Jeder der Deinen Nicknamen kennt, kann gezielt mit \n" +"dem INFO Befehl Informationen über Deinen Nicknamen \n" +"abrufen, unabhängig vom Privat-Modus.)" + +#: modules/commands/ns_set.cpp:1059 modules/commands/ns_set.cpp:1088 +#, fuzzy, c-format +msgid "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." +msgstr "" +"Syntax: SET SECURE {ON | OFF}\n" +"\n" +"Stellt die Sicherheitsfunktionen von %s für Deinen\n" +"Nicknamen an oder aus. Mit eingeschaltetem SECURE\n" +"musst Du dich immer identifizieren, egal ob Deine\n" +"Hostmaske auf der Zugriffsliste für den Nicknamen\n" +"steht oder nicht. Wenn Du allerdings auf \n" +"der Zugriffsliste stehst, wird %s bei \n" +"fehlender Identifizierung den Nicknamen nicht killen\n" +"(ist von der KILL Option unabhängig)." + +#: modules/extra/stats/m_chanstats.cpp:142 +#, fuzzy +msgid "Turns chanstats channel statistics ON or OFF for this user." +msgstr "" +" SECURE Aktiviert/Deaktiviert den Sicherheitsmodus\n" +" für Deinen Nicknamen" + +#: modules/extra/stats/m_chanstats.cpp:61 +#: modules/extra/stats/m_chanstats.cpp:119 +#, fuzzy +msgid "Turns chanstats statistics ON or OFF." +msgstr "" +" SECURE Aktiviert/Deaktiviert den Sicherheitsmodus\n" +" für Deinen Nicknamen" + +#: modules/commands/ns_set.cpp:772 +#, fuzzy, c-format +msgid "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Syntax: SASET nickname KILL {ON | QUICK | IMMED | OFF}\n" +"\n" +"Stellt den automatischen Schutz des Nicknames durch\n" +"einen Kill an oder aus. Nimmt ein User diesen Nickname, \n" +"hat er eine Minute Zeit sich zu identifizieren,\n" +"danach wird er, bei eingeschaltetem Schutz, durch\n" +"%s umbenannt in einen Zufallsnamen.\n" +"\n" +"Bei der Einstellung QUICK wird Wartezeit zum\n" +"Identifizieren auf 20 Sekunden herabgesenkt. Bei\n" +"IMMED wird der User sofort ohne Warnung\n" +"umbenannt, wenn er nicht auf der Zugriffsliste des\n" +"Nicknamens steht. Bitte benutze diese Option nicht\n" +"unnötigerweise.\n" +"Ausserdem ist es möglich, dass die Netz-Admins\n" +"diese Option deaktiviert haben." + +#: modules/commands/ns_set.cpp:738 +#, fuzzy, c-format +msgid "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Syntax: SET KILL {ON | QUICK | IMMED | OFF}\n" +"\n" +"Stellt den automatischen Schutz des Nicknames durch\n" +"einen Kill an oder aus. Nimmt ein User Deinen Nickname, \n" +"hat er eine Minute Zeit sich zu identifizieren,\n" +"danach wird er, bei eingeschaltetem Schutz, durch\n" +"%s umbenannt in einen Zufallsnamen.\n" +"\n" +"Bei der Einstellung QUICK wird Wartezeit zum\n" +"Identifizieren auf 20 Sekunden herabgesenkt. Bei\n" +"IMMED wird der User sofort ohne Warnung\n" +"umbenannt, wenn er nicht auf der Zugriffsliste des\n" +"Nicknamens steht. Bitte benutze diese Option nicht\n" +"unnötigerweise.\n" +"Ausserdem ist es möglich, dass die Netz-Admins\n" +"diese Option deaktiviert haben." + +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_forbid.cpp:358 +msgid "Type" +msgstr "" + +#: modules/commands/ns_set.cpp:62 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Tippe /msg %s HELP Option für weitere Informationen\n" +"zu einem bestimmten Befehl." + +#: modules/commands/bs_kick.cpp:151 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." +msgstr "" +"Mit /msg %s HELP SASET option können mehr Informationen zu \n" +"den Einstellungen angefordert werden. Die Einstellungen betreffen den\n" +"angegebenen Nicknamen. \n" +"\n" +"Die Befehle sind nur für Services Admins verfügbar." + +#: modules/commands/ns_set.cpp:107 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." +msgstr "" +"Mit /msg %s HELP SASET option können mehr Informationen zu \n" +"den Einstellungen angefordert werden. Die Einstellungen betreffen den\n" +"angegebenen Nicknamen. \n" +"\n" +"Die Befehle sind nur für Services Admins verfügbar." + +#: modules/commands/bs_set.cpp:62 modules/commands/cs_set.cpp:63 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." +msgstr "" +"Tippe /msg %s HELP Option für weitere Informationen\n" +"zu einem bestimmten Befehl." + +#: modules/pseudoclients/nickserv.cpp:361 +#, fuzzy, c-format +msgid "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." +msgstr "" +"Tippe /msg %s SET EMAIL eMail wenn Du Deine eMail-Adresse einstellen " +"willst.\n" +"Deine Privatsphäre wird respektiert und Deine eMail-Adresse ist Dritten " +"nicht \n" +"zugänglich." + +#: modules/commands/os_module.cpp:128 +#, fuzzy +msgid "Un-Load a module" +msgstr " MODUNLOAD Entfernt ein Modul" + +#: modules/commands/os_sxline.cpp:337 modules/commands/os_sxline.cpp:552 +#: modules/commands/os_akill.cpp:136 +#, fuzzy, c-format +msgid "Unable to find regex engine %s." +msgstr "Kann Modul %s nicht entfernen" + +#: modules/commands/os_module.cpp:36 modules/commands/os_module.cpp:108 +#, fuzzy, c-format +msgid "Unable to load module %s." +msgstr "Kann Modul %s nicht laden" + +#: modules/commands/os_module.cpp:73 modules/commands/os_module.cpp:90 +#: modules/commands/os_module.cpp:145 modules/commands/os_module.cpp:159 +#, fuzzy, c-format +msgid "Unable to remove module %s." +msgstr "Kann Modul %s nicht entfernen" + +#: modules/commands/bs_assign.cpp:90 +#, fuzzy +msgid "Unassigns a bot from a channel" +msgstr " UNASSIGN Entfernt ein ServicesBot von einen Channel" + +#: modules/commands/bs_assign.cpp:139 +#, fuzzy +msgid "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." +msgstr "" +"Syntax: UNASSIGN Channel\n" +"\n" +"Löscht die Zuweisung eines Bots zu einem Channel.\n" +"Dieser Befehl bewirkt, dass der Bot den Channel\n" +"nicht mehr betritt. Die Konfiguration des Bots für den \n" +"Channel bleibt jedoch erhalten, sodass der Bot dem\n" +"Channel wieder zugewiesen werden kann, ohne das \n" +"alle Einstellungen verloren gehen." + +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1193 +#: modules/commands/bs_kick.cpp:1196 +#, fuzzy +msgid "Underlines kicker" +msgstr " Underlines kicker : %s" + +#: modules/commands/os_dns.cpp:595 +#, fuzzy +msgid "Unknown SET option." +msgstr "Ubekannte SASET option %s." + +#: modules/commands/os_stats.cpp:229 +#, fuzzy, c-format +msgid "Unknown STATS option: %s" +msgstr "Unbekannte STATS Option %s." + +#: src/command.cpp:222 src/command.cpp:233 +#, fuzzy, c-format +msgid "Unknown command %s." +msgstr "Unbekannte Option %s." + +#: src/command.cpp:220 src/command.cpp:231 +#, fuzzy, c-format +msgid "Unknown command %s. \"%s%s HELP\" for help." +msgstr "Unbekannter Befehl %s. \"%s%s HELP\" für Hilfe." + +#: modules/commands/cs_mode.cpp:317 modules/commands/cs_mode.cpp:409 +#, fuzzy, c-format +msgid "Unknown mode character %c ignored." +msgstr "Unbekanntes Mode-Zeichen: %c wurde ignoriert." + +#: modules/commands/os_logsearch.cpp:78 +#, fuzzy, c-format +msgid "Unknown parameter: %s" +msgstr "Option Parameter" + +#: modules/commands/os_dns.cpp:241 +msgid "Unpooled" +msgstr "" + +#: modules/commands/cs_drop.cpp:77 +#, fuzzy +msgid "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." +msgstr "" +"Syntax: DROP Channel\n" +"\n" +"Entfernt die Registrierung des angegebenen Channels.\n" +"Kann nur vom Channel-Founder benutzt werden." + +#: modules/commands/cs_drop.cpp:74 +#, fuzzy +msgid "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." +msgstr "" +"Syntax: DROP Channel\n" +"\n" +"Entfernt die Registrierung des angegebenen Channels aus\n" +"der Datenbank. Zusätzlich werden Zugriffslisten, \n" +"Einstellungen usw mit aus der Datenbank entfernt.\t\n" +"\n" +"Nur Services Operators können Channel DROPEN, \n" +"(löschen) ohne sich vorher gegenüber dem Channel als \n" +"Founder zu identifizieren." + +#: modules/commands/ns_suspend.cpp:160 +#, fuzzy +msgid "Unsuspend a given nick" +msgstr " UNSUSPEND Unsuspend den angegebenen Nicknamen" + +#: modules/commands/ns_suspend.cpp:199 +msgid "Unsuspends a nickname which allows it to be used again." +msgstr "" + +#: modules/commands/cs_updown.cpp:126 +msgid "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." +msgstr "" + +#: modules/commands/cs_updown.cpp:48 +#, fuzzy +msgid "Updates a selected nicks status on a channel" +msgstr "Bannt den angegebenen Nicknamen aus einen Channel" + +#: modules/commands/ns_update.cpp:19 +#, fuzzy +msgid "Updates your current status, i.e. it checks for new memos" +msgstr "" +" UPDATE Erneuert Dein gegenwärtigen Status ( Memos , Flags , vHost )" + +#: modules/commands/ns_update.cpp:43 +#, fuzzy +msgid "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." +msgstr "" +"Syntax: UPDATE\n" +"Updatet Deinen derzeiten Status, z.B. prüft es auf neue Nachrichten,\n" +"setzt benötigte Channel-Modes (ModeonID), aktualisiert Deinen vHost und\n" +"Deine userflags (lastseentime, etc)." + +#: modules/commands/os_update.cpp:25 +msgid "Updating databases." +msgstr "Datenbanken wurden aktualisiert." + +#: modules/commands/os_stats.cpp:154 +#, c-format +msgid "Uplink capab: %s" +msgstr "Uplink-Fähigkeiten: %s" + +#: modules/commands/os_stats.cpp:153 +#, c-format +msgid "Uplink server: %s" +msgstr "Uplink Server: %s" + +#: modules/commands/help.cpp:127 +#, c-format +msgid "Use the %s ALL command to list all commands and their descriptions." +msgstr "" + +#: modules/commands/bs_info.cpp:59 +msgid "Used on" +msgstr "" + +#: data/chanserv.example.conf:821 +#, fuzzy +msgid "Used to manage channels" +msgstr "Ändert die Raum Modi" + +#: data/chanserv.example.conf:809 +#, fuzzy +msgid "Used to manage the list of privileged users" +msgstr "" +" ACCESS Die Liste der priviligierten User\n" +" bearbeiten" + +#: data/chanserv.example.conf:815 +msgid "Used to modify the channel status of you or other users" +msgstr "" + +#: modules/commands/cs_akick.cpp:575 +#, fuzzy +msgid "User has been banned from the channel" +msgstr "Dein Ban in %s wurde entfernt." + +#: modules/commands/os_dns.cpp:587 +#, fuzzy, c-format +msgid "User limit for %s removed." +msgstr "vHost für %s wurde entfernt." + +#: modules/commands/os_dns.cpp:585 +#, fuzzy, c-format +msgid "User limit for %s set to %d." +msgstr "Memo-Limit von %s wurde auf %d gesetzt." + +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Users" +msgstr "Benutzer-Liste:" + +#: modules/commands/os_stats.cpp:172 +#, c-format +msgid "Users (nick): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:177 +#, c-format +msgid "Users (uid): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_list.cpp:184 +msgid "Users list:" +msgstr "Benutzer-Liste:" + +#: modules/commands/ns_info.cpp:105 modules/commands/ns_info.cpp:107 +msgid "VHost" +msgstr "" + +#: modules/commands/hs_set.cpp:92 +#, fuzzy, c-format +msgid "VHost for %s set to %s." +msgstr "vHost für %s wurde gesetzt: %s." + +#: modules/commands/hs_set.cpp:90 +#, fuzzy, c-format +msgid "VHost for %s set to %s@%s." +msgstr "vHost für %s wurde gesetzt: %s@%s." + +#: modules/commands/hs_set.cpp:199 +#, fuzzy, c-format +msgid "VHost for group %s set to %s." +msgstr "vHost für die Gruppe %s wurde gesetzt: %s." + +#: modules/commands/hs_set.cpp:197 +#, c-format +msgid "VHost for group %s set to %s@%s." +msgstr "Der vHost für die Gruppe %s wurde gesetzt auf %s@%s." + +#: modules/commands/os_session.cpp:247 +msgid "VIEW host" +msgstr "" + +#: modules/commands/os_sxline.cpp:428 modules/commands/os_sxline.cpp:662 +#: modules/commands/os_akill.cpp:389 +#, fuzzy +msgid "VIEW [mask | list | id]" +msgstr "LIST [Channel] [Liste | NEW]" + +#: modules/commands/os_session.cpp:526 +msgid "VIEW [mask | list]" +msgstr "" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +msgid "Value" +msgstr "" + +#: modules/commands/os_config.cpp:48 +#, fuzzy, c-format +msgid "Value of %s:%s changed to %s" +msgstr "Founder von %s wurde geändert zu %s." + +#: modules/commands/hs_list.cpp:58 modules/commands/hs_request.cpp:305 +#, fuzzy +msgid "Vhost" +msgstr "vHost" + +#: modules/commands/hs_del.cpp:38 +#, c-format +msgid "Vhost for %s removed." +msgstr "vHost für %s wurde entfernt." + +#: modules/commands/os_oper.cpp:69 +msgid "View and change Services Operators" +msgstr "\"Service Operators\" ansehen und ändern." + +#: modules/commands/os_config.cpp:19 +msgid "View and change configuration file settings" +msgstr "" + +#: modules/commands/os_session.cpp:245 +#, fuzzy +msgid "View the list of host sessions" +msgstr "Die Liste der \"Host Sessions\" anzeigen" + +#: modules/commands/bs_kick.cpp:1221 +msgid "Voices protection" +msgstr "Voice-Schutz" + +#: modules/commands/bs_kick.cpp:1406 +msgid "Watch your language!" +msgstr "Pass bitte auf was Du sagst!" + +#: modules/commands/cs_list.cpp:237 +#, c-format +msgid "" +"When private is set, the channel will not appear in\n" +"%s's %s command." +msgstr "" + +#: modules/commands/ms_info.cpp:204 +#, fuzzy +msgid "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." +msgstr "" +"Syntax: INFO [Nickname | Channel]\n" +"\n" +"Ohne Parameter werden Informationen über Dein Postfach\n" +"angezeigt, die Anzahl Memos die Du hast, die davon neu\n" +"bzw ungelesen sind, und wie viele Memos Du max.\n" +"empfangen kannst.\n" +"\n" +"Mit einem Channel als Parameter werden die entsprechenden\n" +"Informationen über den Channel angezeigt.\n" +"\n" +"Wird eine Nickname übergeben, werden die entsprechenden\n" +"Informationen über den Nicknamen angezeigt. Diese\n" +"Funktion ist beschränkt auf Services Administratoren." + +#: modules/commands/ns_logout.cpp:66 +#, fuzzy +msgid "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." +msgstr "" +"Syntax: LOGOUT [Nickname [REVALIDATE]]\n" +"\n" +"Ohne angegebenen Parameter, macht dieser Befehl die\n" +"Wirkung von IDENTIFY rückgängig, zum Beispiel\n" +"wirst Du nicht mehr als Eigentümer des Nicknamens erkannt.\n" +"Beachte jedoch, dass Du nicht erneut zur Identifizierung\n" +"aufgefordert wirst.\n" +"\n" +"Mit angegebenem Parameter passiert das gleiche für den\n" +"Nicknamen. Wenn Du zusätzlich REVALIDATE angibst, wird\n" +"Services dich auffordern, dich erneut für den Nickname\n" +"zu identifizieren. \n" +"\n" +"Diese Funktion ist beschränkt auf die Services Administartoren." + +#: modules/commands/os_stats.cpp:236 +#, fuzzy +msgid "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." +msgstr "" +"Syntax: STATS [AKILL | ALL | RESET]\n" +"\n" +"Wird keine Option angegeben, wird eine kurze Statistik\n" +"ausgegeben. Sie enthält die aktuelle Anzahl verbundener\n" +"User, IRCops (inklusive den Services). Die max. Anzahl\n" +"gleichzeitig verbundener User seitdem die Services\n" +"gestartet wurden und die Uptime.\n" +"\n" +"Mit der AKILL Option, wird die aktuelle Grösse der\n" +"AutoKill-Liste ausgegeben und dessen standardmässige\n" +"Auslaufzeit.\n" +"\n" +"Die ALL Option ist nur für Services Administratoren verfügbar.\n" +"Sie zeigt unter anderem den aktuellen Speicherverbrauch der \n" +"Services. Dieser Befehl kann auf einem grossen Netzwerk dazu \n" +"führen, dass die Services für kurze Zeit nicht mehr ansprechbar \n" +"sind, also übertreib es nicht.\n" +"\n" +"Durch RESET werden einige Werte der Statistik zurück-\n" +"gesetzt, unter anderem die max. Anzahl gleichzeitig\n" +"verbundenen User." + +#: modules/commands/bs_badwords.cpp:194 +msgid "Word" +msgstr "" + +#: modules/commands/ns_group.cpp:158 +#, c-format +msgid "You are already a member of the group of %s." +msgstr "Du bist bereits Mitglied der Gruppe %s." + +#: modules/commands/os_login.cpp:34 modules/commands/ns_identify.cpp:87 +msgid "You are already identified." +msgstr "Du bist bereits angemeldet." + +#: modules/commands/cs_invite.cpp:64 +#, c-format +msgid "You are already in %s!" +msgstr "Du bist schon in %s! " + +#: modules/commands/os_set.cpp:91 +#, fuzzy +msgid "You are no longer a super admin." +msgstr "Du bist jetzt kein Super-Admin mehr." + +#: modules/commands/os_login.cpp:81 +msgid "You are not identified." +msgstr "Du bist nicht angmeldet." + +#: include/language.h:100 +msgid "You are not permitted to be on this channel." +msgstr "Du hast keine Berechtigung in diesem Chatraum zu sein." + +#: modules/commands/ms_set.cpp:158 +msgid "You are not permitted to change your memo limit." +msgstr "Du hast keine Berechtigung Dein Memo-Limit zu ändern." + +#: modules/commands/ns_cert.cpp:183 +#, fuzzy +msgid "You are not using a client certificate." +msgstr "Du bist nicht angmeldet." + +#: modules/commands/os_set.cpp:85 +#, fuzzy +msgid "You are now a super admin." +msgstr "Du bist jetzt ein Super-Admin." + +#: modules/commands/os_oline.cpp:36 +msgid "You are now an IRC Operator." +msgstr "Du bist jetzt ein IRC Operator." + +#: modules/commands/ns_resetpass.cpp:108 +msgid "You are now identified for your nick. Change your password now." +msgstr "" +"Du bist jetzt für Deinen Nick angemeldet. Bitte ändere jetzt das Passwort." + +#: modules/commands/ns_group.cpp:64 +#, c-format +msgid "You are now in the group of %s." +msgstr "Du bist jetzt in der Gruppe %s vertreten." + +#: modules/pseudoclients/memoserv.cpp:147 +#, fuzzy, c-format +msgid "" +"You are over your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Warnung: Du hast die maximale Anzahl gespeicherter Memos überschritten (%d). " +"Du kannst keine weiteren Memos empfangen, bis Du einige Deiner jetzigen " +"Memos gelöscht hast." + +#: modules/commands/os_noop.cpp:33 +msgid "You can not NOOP Services." +msgstr "" + +#: modules/commands/cs_access.cpp:672 +msgid "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." +msgstr "" + +#: modules/commands/os_jupe.cpp:34 +#, fuzzy +msgid "You can not jupe an already juped server." +msgstr "You can not jupe your services server or your uplink server." + +#: modules/commands/os_jupe.cpp:32 +#, fuzzy +msgid "You can not jupe your Services' pseudoserver or your uplink server." +msgstr "You can not jupe your services server or your uplink server." + +#: modules/commands/os_module.cpp:80 +#, c-format +msgid "You can not reload this module directly, instead reload %s." +msgstr "" + +#: modules/commands/ms_rsend.cpp:46 +msgid "You can not request a receipt when sending a memo to yourself." +msgstr "" +"Das Erhalten von Empfangsbestätigungen ist nur beim Senden\n" +"einer Memo an andere User möglich." + +#: modules/commands/ns_recover.cpp:163 +#, c-format +msgid "You can't %s yourself!" +msgstr "Du kannst %s nicht auf Dich selbst anwenden!" + +#: modules/commands/cs_access.cpp:154 modules/commands/cs_flags.cpp:109 +#: modules/commands/cs_xop.cpp:151 +#, fuzzy +msgid "You can't add a channel to its own access list." +msgstr "" +"Es existieren keine entsprechenden Einträge in der Zugangs-Liste von %s." + +#: modules/commands/ns_logout.cpp:37 +#, fuzzy, c-format +msgid "You can't logout %s, they are a Services Operator." +msgstr "" +"Ausloggen von %s nicht möglich, da es sich um einen Services Administrator " +"handelt." + +#: modules/commands/ns_set.cpp:927 +#, c-format +msgid "You cannot %s on this network." +msgstr "Du kannst in diesem Netzwerk nicht %s ." + +#: modules/commands/cs_flags.cpp:231 +#, fuzzy, c-format +msgid "You cannot set the %c flag." +msgstr "Du kannst das %c flag nicht setzen." + +#: modules/commands/ms_set.cpp:173 +#, c-format +msgid "You cannot set the memo limit for %s higher than %d." +msgstr "Du kannst das Memo-Limit für %s nicht höher als %d setzen." + +#: modules/commands/ms_set.cpp:175 +#, c-format +msgid "You cannot set your memo limit higher than %d." +msgstr "Du kannst Dein Memo-Limit nicht höher als %d setzen." + +#: modules/commands/bs_assign.cpp:124 +#, fuzzy +msgid "You cannot unassign bots while persist is set on the channel." +msgstr "" +"Du kannst die Zuweisung eines Bots nicht entfernen während im channel " +"\"persist\" gesetzt ist." + +#: modules/commands/ns_set.cpp:480 +msgid "You cannot unset the e-mail on this network." +msgstr "Du kannst in diesem Netzwerk Deine eMail-Adresse nicht entfernen." + +#: modules/commands/help.cpp:177 +msgid "You cannot use this command." +msgstr "Du kannst diesen befehl nicht benutzen." + +#: modules/commands/ms_info.cpp:151 +#, c-format +msgid "You currently have %d memos, of which %d are unread." +msgstr "Du hast derzeit %d Memos, davon sind %d ungelesen." + +#: modules/commands/ms_info.cpp:149 +#, c-format +msgid "You currently have %d memos, of which 1 is unread." +msgstr "Du hast derzeit %d Memos, davon ist eine ungelesen." + +#: modules/commands/ms_info.cpp:147 +#, c-format +msgid "You currently have %d memos." +msgstr "Du hast derzeit %d Memos." + +#: modules/commands/ms_info.cpp:145 +#, c-format +msgid "You currently have %d memos; all of them are unread." +msgstr "Du hast derezeit %d Memos, alle davon sind ungelesen." + +#: modules/commands/ms_info.cpp:134 +msgid "You currently have 1 memo, and it has not yet been read." +msgstr "Du hast derzeit eine ungelesene Nachricht." + +#: modules/commands/ms_info.cpp:136 +msgid "You currently have 1 memo." +msgstr "Du hast derzeit eine Nachricht." + +#: modules/commands/ms_info.cpp:130 +msgid "You currently have no memos." +msgstr "Du hast keine Memos." + +#: modules/commands/cs_mode.cpp:564 modules/commands/cs_mode.cpp:621 +#, c-format +msgid "You do not have access to set mode %c." +msgstr "" + +#: modules/commands/cs_mode.cpp:578 modules/commands/cs_mode.cpp:590 +#: modules/commands/cs_mode.cpp:631 +#, c-format +msgid "You do not have the access to change %s's modes." +msgstr "" + +#: modules/commands/cs_seen.cpp:198 +#, c-format +msgid "You found me, %s!" +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:143 +#, c-format +msgid "You have %d new memos." +msgstr "Du hast %d neue Nachrichten." + +#: modules/pseudoclients/memoserv.cpp:143 +msgid "You have 1 new memo." +msgstr "Du hast eine neue Nachricht." + +#: include/language.h:112 +#, c-format +msgid "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." +msgstr "" +"Du hast eine neue Nachricht von %s.\n" +"Tippe %s%s READ %d um sie zu lesen." + +#: modules/commands/cs_invite.cpp:76 +#, fuzzy, c-format +msgid "You have been invited to %s by %s." +msgstr "Du wurdest zu %s eingeladen." + +#: modules/commands/cs_invite.cpp:81 +#, c-format +msgid "You have been invited to %s." +msgstr "Du wurdest zu %s eingeladen." + +#: modules/protocol/ratbox.cpp:166 modules/commands/ns_recover.cpp:96 +#, c-format +msgid "You have been logged in as %s." +msgstr "Du bist als %seingeloggt." + +#: modules/commands/os_login.cpp:86 +msgid "You have been logged out." +msgstr "Du wurdest ausgeloggt." + +#: modules/commands/cs_unban.cpp:94 +#, c-format +msgid "You have been unbanned from %s." +msgstr "Dein Bann in %s wurde entfernt." + +#: modules/commands/cs_unban.cpp:54 +#, fuzzy, c-format +msgid "You have been unbanned from %d channels." +msgstr "Dein Ban in %s wurde entfernt." + +#: modules/commands/ms_info.cpp:169 +msgid "You have no limit on the number of memos you may keep." +msgstr "Du kannst eine unbegrenzte Anzahl Memos behalten." + +#: include/language.h:114 +msgid "You have no memos." +msgstr "Du hast keine Nachrichten." + +#: include/language.h:117 +msgid "You have no new memos." +msgstr "Du hast keine neuen Nachrichten." + +#: modules/pseudoclients/memoserv.cpp:149 +#, c-format +msgid "" +"You have reached your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Du hast die maximale Anzahl gespeicherter Memos erreicht (%d). Du kannst " +"keine weiteren Nachrichten empfangen, bis Du einige Deiner jetzigen Memos " +"gelöscht hast." + +#: modules/commands/ns_recover.cpp:117 +#, fuzzy, c-format +msgid "You have regained control of %s." +msgstr "Du wurdest zu %seingeladen." + +#: modules/commands/ns_drop.cpp:66 +#, fuzzy +msgid "You may drop any nick within your group." +msgstr "Es befinden sich zu viele Nicks in der Gruppe von %s." + +#: modules/commands/cs_mode.cpp:322 modules/commands/cs_mode.cpp:414 +#, c-format +msgid "You may not (un)lock mode %c." +msgstr "" + +#: modules/commands/ns_set.cpp:485 +msgid "You may not change the e-mail of other Services Operators." +msgstr "" +"Du kannst in diesem Netzwerk die eMail-Adresse anderer \"Servive Operaotors" +"\" nicht ändern." + +#: modules/commands/ns_set.cpp:474 +#, fuzzy +msgid "You may not change the email of an unconfirmed account." +msgstr "" +"Du kannst in diesem Netzwerk die eMail-Adresse anderer \"Servive Operaotors" +"\" nicht ändern." + +#: modules/commands/ns_set.cpp:196 +#, fuzzy +msgid "You may not change the password of other Services Operators." +msgstr "" +"Ausloggen von %s nicht möglich, da es sich um einen Services Administrator " +"handelt." + +#: modules/commands/ns_drop.cpp:45 +#, fuzzy +msgid "You may not drop other Services Operators' nicknames." +msgstr "%s ist ein services operator vom Typ %s." + +#: modules/commands/ns_getpass.cpp:32 +#, fuzzy +msgid "You may not get the password of other Services Operators." +msgstr "" +"Ausloggen von %s nicht möglich, da es sich um einen Services Administrator " +"handelt." + +#: modules/commands/ns_suspend.cpp:100 +#, fuzzy +msgid "You may not suspend other Services Operators' nicknames." +msgstr "" +"Ausloggen von %s nicht möglich, da es sich um einen Services Administrator " +"handelt." + +#: modules/commands/ns_access.cpp:136 +#, fuzzy +msgid "" +"You may view but not modify the access list of other Services Operators." +msgstr "" +"Ausloggen von %s nicht möglich, da es sich um einen Services Administrator " +"handelt." + +#: modules/commands/ns_cert.cpp:292 +#, fuzzy +msgid "" +"You may view but not modify the certificate list of other Services Operators." +msgstr "" +"Ausloggen von %s nicht möglich, da es sich um einen Services Administrator " +"handelt." + +#: modules/commands/cs_seen.cpp:287 +#, c-format +msgid "You might see yourself in the mirror, %s." +msgstr "Schau doch mal in den Spiegel, %s." + +#: include/language.h:120 +msgid "You must assign a bot to the channel before using this command." +msgstr "" +"Bevor Du diesen Befehl benutzen kannst musst Du dem Chatraum erst einen Bot " +"zuordnen." + +#: modules/commands/cs_register.cpp:49 +msgid "You must be a channel operator to register the channel." +msgstr "Du musst Channel-Operator sein um diesen Channel zu registrieren." + +#: modules/commands/cs_updown.cpp:94 modules/commands/cs_updown.cpp:192 +#, fuzzy, c-format +msgid "You must be in %s to use this command." +msgstr "Du musst dich anmelden um diesen Befehl zu nutzen." + +#: modules/commands/cs_register.cpp:37 +msgid "You must confirm your account before you can register a channel." +msgstr "" +"Du musst Deinen Account bestätigen bevor Du einen Chatraum registrieren " +"kannst." + +#: modules/commands/hs_request.cpp:100 +#, fuzzy +msgid "You must confirm your account before you may request a vhost." +msgstr "" +"Du musst Deinen Account bestätigen bevor Du einen Chatraum registrieren " +"kannst." + +#: modules/commands/ms_send.cpp:44 +#, fuzzy +msgid "You must confirm your account before you may send a memo." +msgstr "" +"Du musst Deinen Account bestätigen bevor Du einen Chatraum registrieren " +"kannst." + +#: modules/commands/cs_drop.cpp:42 +#, c-format +msgid "" +"You must enter the channel name twice as a confirmation that you wish to drop" +" %s." +msgstr "" + +#: modules/commands/ns_register.cpp:153 +#, c-format +msgid "You must have been using this nick for at least %d seconds to register." +msgstr "" +"Du musst länger als %d Sekunden verbunden sein, um einen Nicknamen zu " +"registrieren." + +#: modules/commands/cs_mode.cpp:913 +#, fuzzy, c-format +msgid "You must have the %s(ME) privilege on the channel to use this command." +msgstr "" +"Bevor Du diesen Befehl benutzen kannst musst Du dem Chatraum erst einen Bot " +"zuordnen." + +#: modules/pseudoclients/nickserv.cpp:358 +msgid "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." +msgstr "" +"Du musst eine eMail-Adresse für Deinen Nicknamen angeben.\n" +"NickServ kann Dir dann Dein Passwort per Mail senden, falls Du es\n" +"vergessen solltest." + +#: modules/commands/help.cpp:172 +msgid "You need to be identified to use this command." +msgstr "Du musst dich anmelden um diesen Befehl zu nutzen." + +#: modules/commands/ms_info.cpp:182 +#, fuzzy +msgid "You will be notified by message and by mail when new memos arrive." +msgstr "Du wirst bei neuen Memos benachrichtigt, wenn sie eintreffen." + +#: modules/commands/ms_info.cpp:175 +#, fuzzy +msgid "" +"You will be notified of new memos at logon and when they arrive, and by mail " +"when they arrive." +msgstr "" +"Du wirst bei neuen Memos benachrichtigt, wenn Du dich identifizierst bzw " +"wenn sie eintreffen." + +#: modules/commands/ms_info.cpp:177 +msgid "You will be notified of new memos at logon and when they arrive." +msgstr "" +"Du wirst bei neuen Memos benachrichtigt, wenn Du dich identifizierst bzw " +"wenn sie eintreffen." + +#: modules/commands/ms_info.cpp:189 +#, fuzzy +msgid "" +"You will be notified of new memos at logon, and by mail when they arrive." +msgstr "" +"Du wirst bei neuen Memos benachrichtigt, wenn Du dich identifizierst bzw " +"wenn sie eintreffen." + +#: modules/commands/ms_info.cpp:191 +msgid "You will be notified of new memos at logon." +msgstr "Du wirst bei neuen Memos benachrichtigt, wenn Du dich identifizierst." + +#: modules/commands/ms_info.cpp:184 +msgid "You will be notified when new memos arrive." +msgstr "Du wirst bei neuen Memos benachrichtigt, wenn sie eintreffen." + +#: modules/commands/ms_set.cpp:190 +msgid "You will no longer be able to receive memos." +msgstr "Du wirst ab sofort keine Memos mehr empfangen können." + +#: modules/commands/ms_set.cpp:57 +msgid "You will no longer be informed via email." +msgstr "Du wirst nicht länger per Email über neue Memos benachrichtigt." + +#: modules/commands/ms_info.cpp:195 +msgid "You will not be notified of new memos." +msgstr "Du wirst bei neuen Memos nicht benachrichtigt." + +#: modules/commands/ms_set.cpp:49 +msgid "You will now be informed about new memos via email." +msgstr "Du wirst jetzt per Email über neue Memos informiert." + +#: modules/commands/os_svs.cpp:86 +#, fuzzy +msgid "Your IRCd does not support SVSJOIN." +msgstr "Dein IRCd unterstützt SNLINE nicht." + +#: modules/commands/os_svs.cpp:31 +#, fuzzy +msgid "Your IRCd does not support SVSNICK." +msgstr "Dein IRCd unterstützt SNLINE nicht." + +#: modules/commands/os_svs.cpp:130 +#, fuzzy +msgid "Your IRCd does not support SVSPART." +msgstr "Dein IRCd unterstützt SNLINE nicht." + +#: include/language.h:127 +#, fuzzy +msgid "" +"Your IRCd does not support vIdent's, if this is incorrect, please report " +"this as a possible bug" +msgstr "" +"Dein IRCd unterstützt keine vIdent's.\n" +"Sollte dies falsch sein bitte melde einen Bug." + +#: modules/extra/m_ldap_authentication.cpp:110 +#: modules/extra/m_sql_authentication.cpp:55 +#, c-format +msgid "Your account %s has been successfully created." +msgstr "Dein Account %s wurde erfolgreich angelegt." + +#: modules/commands/ns_register.cpp:328 +msgid "Your account is already confirmed." +msgstr "Dein Account ist bereits bestätigt." + +#: modules/commands/ns_register.cpp:396 +#, fuzzy, c-format +msgid "Your account will expire, if not confirmed, in %s." +msgstr "Wenn Dein Account nicht bestätigt wird, wird er in %s auslaufen." + +#: modules/commands/ns_set.cpp:1274 +#, c-format +msgid "Your email address has been changed to %s." +msgstr "Deine eMail-Adresse wurde auf %s geändert." + +#: modules/commands/os_forbid.cpp:544 modules/commands/os_forbid.cpp:553 +#, fuzzy +msgid "Your email address is not allowed, choose a different one." +msgstr "Deine eMail-Adresse %s wurde bestätigt.#" + +#: modules/commands/ns_register.cpp:260 modules/commands/ns_register.cpp:391 +msgid "" +"Your email address is not confirmed. To confirm it, follow the instructions " +"that were emailed to you." +msgstr "" + +#: modules/commands/ns_register.cpp:67 +#, c-format +msgid "Your email address of %s has been confirmed." +msgstr "Deine eMail-Adresse %s wurde bestätigt.#" + +#: modules/extra/m_ldap_authentication.cpp:159 +#, c-format +msgid "Your email has been updated to %s" +msgstr "Deine eMail Adresse wurde auf %s geändert." + +#: modules/extra/m_sql_authentication.cpp:62 +#, fuzzy, c-format +msgid "Your email has been updated to %s." +msgstr "Deine eMail Adresse wurde auf %s geändert." + +#: modules/commands/ms_set.cpp:197 +msgid "Your memo limit has been disabled." +msgstr "Dein Memo-Limit wurde aufgehoben." + +#: modules/commands/ms_set.cpp:183 +#, c-format +msgid "Your memo limit has been set to %d." +msgstr "Dein Memo-Limit wurde auf %d gesetzt." + +#: modules/commands/ms_info.cpp:164 +#, c-format +msgid "Your memo limit is %d, and may not be changed." +msgstr "Dein Memo-Limit liegt bei %d, und kann nicht geändert werden." + +#: modules/commands/ms_info.cpp:166 +#, c-format +msgid "Your memo limit is %d." +msgstr "Dein Memo-Limit liegt bei %d." + +#: modules/commands/ms_info.cpp:159 +msgid "Your memo limit is 0; you will not receive any new memos." +msgstr "Dein Memo-Limit liegt bei 0, Du kannst keine neuen Memos empfangen." + +#: modules/commands/ms_info.cpp:157 +msgid "" +"Your memo limit is 0; you will not receive any new memos. You cannot change " +"this limit." +msgstr "" +"Dein Memo-Limit liegt bei 0, Du kannst keine neuen Memos empfangen. Das " +"Limit kann von Dir nicht verändert werden." + +#: modules/commands/ns_logout.cpp:50 +msgid "Your nick has been logged out." +msgstr "Du wurdest ausgeloggt." + +#: modules/commands/ns_group.cpp:156 +msgid "Your nick is already registered." +msgstr "Dein Nickname ist bereits registriert." + +#: modules/commands/ns_group.cpp:246 +#, fuzzy +msgid "Your nick is not grouped to anything, you can't ungroup it." +msgstr "" +"Dein Nick ist nicht gruppiert, daher kann die Gruppierung nicht aufgehoben " +"werden." + +#: include/language.h:77 +msgid "Your nick isn't registered." +msgstr "Dein Nick ist nicht registriert." + +#: modules/pseudoclients/nickserv.cpp:254 +#, c-format +msgid "Your nickname is now being changed to %s" +msgstr "Dein Nickname wurde geändert in %s" + +#: modules/commands/os_login.cpp:32 modules/commands/os_login.cpp:79 +msgid "Your oper block doesn't require logging in." +msgstr "" + +#: modules/commands/ns_register.cpp:336 +#, c-format +msgid "Your passcode has been re-sent to %s." +msgstr "Dein Passcode wurde noch einmal an %s geschickt." + +#: modules/commands/ns_register.cpp:232 +#, c-format +msgid "Your password is %s - remember this for later use." +msgstr "Dein Passwort ist %s - behalte es für spätere Benutzung." + +#: include/language.h:76 +#, fuzzy, c-format +msgid "Your password is too long. It must not exceed %u characters." +msgstr "" +"Dein Passwort ist zu lang, bitte versuche es mit einem kürzeren Passwort." + +#: modules/commands/ns_resetpass.cpp:96 +msgid "Your password reset request has expired." +msgstr "Deine Anfrage für die Zurücksetzung des Passworts ist abgelaufen." + +#: modules/commands/hs_request.cpp:170 +msgid "Your vHost has been requested." +msgstr "Dein vHost wurde beantragt" + +#: modules/pseudoclients/hostserv.cpp:64 +#: modules/pseudoclients/hostserv.cpp:103 modules/commands/hs_on.cpp:37 +#, c-format +msgid "Your vhost of %s is now activated." +msgstr "Dein vHost (%s) ist jetzt aktiviert." + +#: modules/pseudoclients/hostserv.cpp:62 +#: modules/pseudoclients/hostserv.cpp:101 modules/commands/hs_on.cpp:35 +#, c-format +msgid "Your vhost of %s@%s is now activated." +msgstr "Dein vHost (%s@%s) ist jetzt aktiviert." + +#: modules/commands/hs_off.cpp:39 +#, fuzzy +msgid "Your vhost was removed and the normal cloaking restored." +msgstr "Dein vHost wurde entfernt und das normale cloaking wiederhergestellt." + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Zone" +msgstr "Keine" + +#: modules/commands/os_dns.cpp:290 +#, fuzzy, c-format +msgid "Zone %s already exists." +msgstr "%s existiert bereits." + +#: modules/commands/os_dns.cpp:310 modules/commands/os_dns.cpp:352 +#: modules/commands/os_dns.cpp:402 modules/commands/os_dns.cpp:438 +#, fuzzy, c-format +msgid "Zone %s does not exist." +msgstr "Bot %s existiert bereits." + +#: modules/commands/os_dns.cpp:332 +#, fuzzy, c-format +msgid "Zone %s removed." +msgstr "vHost für %s wurde entfernt." + +#: modules/commands/os_defcon.cpp:177 +msgid "[1|2|3|4|5]" +msgstr "[1|2|3|4|5]" + +#: modules/commands/os_news.cpp:400 +#, c-format +msgid "[Logon News - %s] %s" +msgstr "[Logon News - %s] %s" + +#: modules/commands/os_news.cpp:402 +#, c-format +msgid "[Oper News - %s] %s" +msgstr "[Oper News - %s] %s" + +#: modules/commands/os_news.cpp:404 +#, c-format +msgid "[Random News - %s] %s" +msgstr "[Random News - %s] %s" + +#: modules/commands/ns_identify.cpp:66 +msgid "[account] password" +msgstr "[Account] Passwort" + +#: modules/commands/cs_updown.cpp:49 modules/commands/cs_updown.cpp:147 +msgid "[channel [nick]]" +msgstr "Chatraum [nick]" + +#: modules/commands/ms_ignore.cpp:20 +#, fuzzy +msgid "[channel] ADD entry" +msgstr "[Channel] {ADD|DEL|LIST} [Nummer]" + +#: modules/commands/ms_ignore.cpp:21 +#, fuzzy +msgid "[channel] DEL entry" +msgstr "Channel DEL Nummer" + +#: modules/commands/ms_ignore.cpp:22 +#, fuzzy +msgid "[channel] LIST" +msgstr "Channel LIST" + +#: modules/commands/ms_list.cpp:20 +msgid "[channel] [list | NEW]" +msgstr "[Raum] [Liste | NEW]" + +#: modules/extra/stats/cs_fantasy_stats.cpp:40 +#, fuzzy +msgid "[channel] [nick]" +msgstr "Chatraum [nick]" + +#: modules/commands/ms_del.cpp:45 +msgid "[channel] {num | list | LAST | ALL}" +msgstr "[Channel] {Nummer | Liste | ALL}" + +#: modules/commands/ms_read.cpp:113 +#, fuzzy +msgid "[channel] {num | list | LAST | NEW | ALL}" +msgstr "[Channel] {Nummer | Liste | ALL}" + +#: modules/commands/hs_list.cpp:20 +#, fuzzy +msgid "[key|#X-Y]" +msgstr "[|<#X-Y>" + +#: modules/commands/ms_info.cpp:20 +msgid "[nick | channel]" +msgstr "[Nickname | Channel]" + +#: modules/commands/ns_group.cpp:237 +#, fuzzy +msgid "[nick]" +msgstr "Nickname" + +#: modules/commands/ns_logout.cpp:22 +msgid "[nickname [REVALIDATE]]" +msgstr "" + +#: modules/commands/ns_alist.cpp:25 modules/commands/ns_status.cpp:20 +#: modules/commands/ns_info.cpp:20 +msgid "[nickname]" +msgstr "[Nickname]" + +#: modules/commands/ns_set_misc.cpp:96 +msgid "[parameter]" +msgstr "" + +#: modules/commands/os_logsearch.cpp:33 +msgid "[+daysd] [+limitl] pattern" +msgstr "" + +#: modules/commands/os_chankill.cpp:22 +msgid "[+expiry] channel reason" +msgstr "[+Zeit] {Channel} [Grund]" + +#: modules/commands/ns_list.cpp:110 +msgid "[Hostname hidden]" +msgstr "" + +#: modules/commands/ns_list.cpp:112 modules/commands/cs_list.cpp:115 +msgid "[Suspended]" +msgstr "" + +#: modules/commands/ns_list.cpp:114 +msgid "[Unconfirmed]" +msgstr "" + +#: modules/commands/hs_request.cpp:213 +msgid "[auto memo] Your requested vHost has been approved." +msgstr "[Auto Memo] Dein beantragter vHost wurde akzeptiert." + +#: modules/commands/hs_request.cpp:267 +msgid "[auto memo] Your requested vHost has been rejected." +msgstr "[Auto Memo] Dein beantragert vHost wurde abgelehnt." + +#: modules/commands/hs_request.cpp:265 +#, c-format +msgid "[auto memo] Your requested vHost has been rejected. Reason: %s" +msgstr "[Auto Memo] Dein beantragter vHost wurde abgelehnt. Grund: %s" + +#: modules/commands/hs_request.cpp:388 +#, c-format +msgid "[auto memo] vHost %s has been requested by %s." +msgstr "[Auto Memo] %2$s hat den vHost %1$s beantragt." + +#: modules/commands/os_list.cpp:133 +msgid "[{pattern | channel} [INVISIBLE]]" +msgstr "" + +#: modules/commands/os_list.cpp:20 +msgid "[{pattern | nick} [SECRET]]" +msgstr "" + +#: src/misc.cpp:337 +msgid "day" +msgstr "Tag" + +#: src/misc.cpp:337 +msgid "days" +msgstr "Tagen" + +#: include/language.h:88 +msgid "does not expire" +msgstr "wird nicht auslaufen" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d day" +msgstr "verfällt in %d Tag" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d days" +msgstr "verfällt in %d Tagen" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minute" +msgstr "verfällt in %d Stunde, %d Minute" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minutes" +msgstr "verfällt in %d Stunde, %d Minuten" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minute" +msgstr "verfällt in %d Stunden, %d Minute" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minutes" +msgstr "verfällt in %d Stunden, %d Minuten" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minute" +msgstr "verfällt in %d Minute" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minutes" +msgstr "verfällt in %d Minuten" + +#: src/misc.cpp:375 +msgid "expires momentarily" +msgstr "verfällt jeden Moment" + +#: src/misc.cpp:343 +msgid "hour" +msgstr "Stunde" + +#: src/misc.cpp:343 +msgid "hours" +msgstr "Stunden" + +#: modules/extra/stats/cs_fantasy_stats.cpp:150 +#, c-format +msgid "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:349 +msgid "minute" +msgstr "Minute" + +#: src/misc.cpp:349 +msgid "minutes" +msgstr "Minuten" + +#: modules/commands/bs_info.cpp:87 +msgid "not assigned yet" +msgstr "" + +#: src/misc.cpp:324 +msgid "second" +msgstr "Sekunde" + +#: src/misc.cpp:324 +msgid "seconds" +msgstr "Sekunden" + +#: modules/commands/hs_request.cpp:215 +#, fuzzy, c-format +msgid "vHost for %s has been activated." +msgstr "vHost für %s ist jetzt aktiviert." + +#: modules/commands/hs_request.cpp:272 +#, fuzzy, c-format +msgid "vHost for %s has been rejected." +msgstr "vHost für %s wurde abgelehnt." + +#: modules/commands/hs_request.cpp:79 +msgid "vhost" +msgstr "vHost" + +#: modules/commands/hs_del.cpp:83 +#, c-format +msgid "vhosts for group %s have been removed." +msgstr "vHost für die Gruppe %s wurden gelöscht." + +#: src/misc.cpp:331 +msgid "year" +msgstr "" + +#: src/misc.cpp:331 +msgid "years" +msgstr "" + +#: modules/commands/os_config.cpp:20 +msgid "{MODIFY|VIEW} [block name item name item value]" +msgstr "" + +#: modules/commands/bs_info.cpp:41 +#, fuzzy +msgid "{channel | nickname}" +msgstr "Channel Nick" + +#: modules/commands/ms_cancel.cpp:20 +msgid "{nick | channel}" +msgstr "{Nickname | Channel}" + +#: modules/commands/ms_rsend.cpp:25 modules/commands/ms_send.cpp:25 +msgid "{nick | channel} memo-text" +msgstr "{Nickname | Channel} Memo-text" diff --git a/language/anope.el_GR.po b/language/anope.el_GR.po new file mode 100644 index 0000000..28217bb --- /dev/null +++ b/language/anope.el_GR.po @@ -0,0 +1,11858 @@ +# Anope IRC Services language file +# Copyright (C) 2011 +# This file is distributed under the same license as the Anope IRC Services package. +# VisioN , 2011. +# +msgid "" +msgstr "" +"Project-Id-Version: Anope\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2020-01-06 18:19+0100\n" +"PO-Revision-Date: 2010-09-19 20:34-0400\n" +"Last-Translator: VisioN \n" +"Language-Team: Greek\n" +"Language: el_GR\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" + +#: modules/commands/os_forbid.cpp:324 +#, c-format +msgid "%d channel(s) cleared, and %d channel(s) dropped." +msgstr "" + +#: modules/commands/os_forbid.cpp:265 +#, fuzzy, c-format +msgid "%d nickname(s) dropped." +msgstr "Το ψευδώνυμό σου σβήστηκε επιτυχώς από την υπηρεσία." + +#: modules/commands/cs_xop.cpp:219 +#, fuzzy, c-format +msgid "%s added to %s %s list." +msgstr "#%s# προσθέθηκε στην λίστα AKILL." + +#: modules/commands/cs_access.cpp:225 +#, c-format +msgid "%s added to %s access list at level %d." +msgstr "Ο/η #%s# προσθέθηκε στο access list του %s με επίπεδο πρόσβασης #%d#." + +#: modules/commands/cs_access.cpp:223 +#, fuzzy, c-format +msgid "%s added to %s access list at privilege %s (level %d)" +msgstr "Ο/η #%s# προσθέθηκε στο access list του %s με επίπεδο πρόσβασης #%d#." + +#: modules/commands/cs_akick.cpp:190 +#, c-format +msgid "%s added to %s autokick list." +msgstr "Ο/η #%s# προσθέθηκε επιτυχώς στην autokick λίστα του %s." + +#: modules/commands/bs_badwords.cpp:307 +#, c-format +msgid "%s added to %s bad words list." +msgstr "#%s# προσθέθηκε στην λίστα των κακών λέξεων του %s." + +#: modules/commands/ns_access.cpp:45 +#, fuzzy, c-format +msgid "%s added to %s's access list." +msgstr "#%s# έγινε προσθήκη στην λίστα πρόσβασής σου." + +#: modules/commands/ns_cert.cpp:204 +#, fuzzy, c-format +msgid "%s added to %s's certificate list." +msgstr "#%s# έγινε προσθήκη στην λίστα πρόσβασής σου." + +#: modules/commands/ms_ignore.cpp:62 +#, fuzzy, c-format +msgid "%s added to ignore list." +msgstr "#%s# έγινε προσθήκη στην λίστα αγνόησης σου." + +#: modules/commands/os_sxline.cpp:415 modules/commands/os_sxline.cpp:649 +#, fuzzy, c-format +msgid "%s added to the %s list." +msgstr "#%s# προσθέθηκε στην λίστα AKILL." + +#: modules/commands/os_akill.cpp:203 +#, c-format +msgid "%s added to the AKILL list." +msgstr "#%s# προσθέθηκε στην λίστα AKILL." + +#: modules/pseudoclients/botserv.cpp:134 +#, c-format +msgid "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands " +"that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" +msgstr "" + +#: modules/pseudoclients/botserv.cpp:148 +#, fuzzy, c-format +msgid "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"Ο #%s# σου επιτρέπει να έχεις bot στο δικό σου κανάλι.\n" +"Αυτή η υπηρεσια έχει δημιουργηθεί για τους χρήστες που δεν μπορούν\n" +"να ρυθμίσουν bots ή για δίκτυα που δεν επιτρέπουν οι χρήστες να έχουν\n" +"δικά τους bots για ασφάλεια. \n" +"Διαθέσημες εντολές είναι οι επόμενες, για να τις δείτε γράψτε\n" +"#/msg %s #command##.Για περισσότερες πληροφορίες σε συγκεκριμένες\n" +"εντολές γράψτε #/msg %s HELP #command##. \n" +" " + +#: modules/pseudoclients/nickserv.cpp:466 +#, fuzzy, c-format +msgid "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"O #%s# σας επιτρέπει να κατοχυρώσετε ένα ψευδώνυμο,\n" +"εμποδίζοντας έτσι άλλους χρήστες να το χρησιμοποιούν.\n" +"Οι παρακάτω εντολές, επιτρέπουν την κατοχύρωση και τη διαχείρηση των\n" +"ψευδωνύμων; για να χρησιμοποιήσετε αυτά, γράψτε #/msg %s ^_command^_#.\n" +"Για περισσότερες πληροφορίες σε μια συγκεκριμένη εντολή,γράψτε\n" +"#/msg %s HELP ^_command^_#." + +#: modules/pseudoclients/nickserv.cpp:473 +#, fuzzy, c-format +msgid "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"O #%s# σας επιτρέπει να κατοχυρώσετε ένα ψευδώνυμο,\n" +"εμποδίζοντας έτσι άλλους χρήστες να το χρησιμοποιούν.\n" +"Οι παρακάτω εντολές, επιτρέπουν την κατοχύρωση και τη διαχείρηση των\n" +"ψευδωνύμων; για να χρησιμοποιήσετε αυτά, γράψτε #/msg %s ^_command^_#.\n" +"Για περισσότερες πληροφορίες σε μια συγκεκριμένη εντολή,γράψτε\n" +"#/msg %s HELP ^_command^_#." + +#: modules/pseudoclients/chanserv.cpp:255 +#, fuzzy, c-format +msgid "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" +msgstr "" +"Ο #%s# σας επιτρέπει να κατοχυρώσετε και να χειριστείτε\n" +"διάφορες λειτουργίες των καναλιών. Ο %s μπορεί συνήθως\n" +"να αποτρέψει κακόβουλους χρήστες να κάνουν \"κατάληψη\" σε\n" +"κανάλια, με το να περιορίζει τις αρμοδιότητες των\n" +"διαχειριστών καναλιών. Οι διαθέσιμες εντολές, βρίσκονται\n" +"παρακάτω. Για να τις χρησιμοποιήσετε, πληκτρολογήστε\n" +"#/msg %s #εντολή##. Για περισσότερες πληροφορίες σε μία\n" +"συγκεκριμένη εντολή, πληκτρολογήστε #/msg %s HELP #εντολή##.\n" +" " + +#: modules/commands/bs_badwords.cpp:298 +#, c-format +msgid "%s already exists in %s bad words list." +msgstr "Το #%s# υπάρχει ήδη στη λίστα κακών λέξεων του %s" + +#: modules/commands/cs_akick.cpp:170 +#, c-format +msgid "%s already exists on %s autokick list." +msgstr "Ο/η #%s# υπάρχει ήδη στην autokick λίστα του %s." + +#: modules/commands/os_session.cpp:361 +#, c-format +msgid "%s already exists on the EXCEPTION list." +msgstr "#%s# already exists on the EXCEPTION list." + +#: modules/commands/bs_kick.cpp:214 modules/commands/bs_kick.cpp:389 +#: modules/commands/bs_kick.cpp:520 modules/commands/bs_kick.cpp:651 +#, c-format +msgid "%s cannot be taken as times to ban." +msgstr "#%s# δεν μπορεί να πάρει τόσο χρόνο τo ban." + +#: modules/commands/os_mode.cpp:163 +#, fuzzy, c-format +msgid "%s changed your usermodes to %s." +msgstr "Ο/η #%s# άλλαξε τα usermodes σας." + +#: modules/commands/os_list.cpp:47 +#, fuzzy, c-format +msgid "%s channel list:" +msgstr "Τέλος λίστας καναλιού." + +#: modules/commands/cs_xop.cpp:343 +#, fuzzy, c-format +msgid "%s deleted from %s %s list." +msgstr "Ο/η #%s# διαγράφηκε επιτυχώς από την AOP λίστα του %s." + +#: modules/commands/cs_access.cpp:326 +#, c-format +msgid "%s deleted from %s access list." +msgstr "#%s# διαγράφηκε από το access list του %s." + +#: modules/commands/cs_akick.cpp:276 +#, c-format +msgid "%s deleted from %s autokick list." +msgstr "Ο/η #%s# διαγράφτηκε από την autokick list του %s." + +#: modules/commands/bs_badwords.cpp:348 +#, c-format +msgid "%s deleted from %s bad words list." +msgstr "#%s# διαγράφτηκε από την λίστα των κακών λέξεων απο το %s." + +#: modules/commands/ns_access.cpp:72 +#, fuzzy, c-format +msgid "%s deleted from %s's access list." +msgstr "#%s# διαγράφηκε από το access list του %s." + +#: modules/commands/ns_cert.cpp:233 +#, fuzzy, c-format +msgid "%s deleted from %s's certificate list." +msgstr "#%s# διαγράφτηκε από την λίστα πρόσβασής σου." + +#: modules/commands/os_session.cpp:414 +#, c-format +msgid "%s deleted from session-limit exception list." +msgstr "#%s# διαγράφηκε από την λίστα session-limit exception." + +#: modules/commands/os_sxline.cpp:99 +#, c-format +msgid "%s deleted from the %s list." +msgstr "Ο/η #%s# διαγράφηκε επιτυχώς από την AOP λίστα του %s." + +#: modules/commands/os_akill.cpp:246 +#, c-format +msgid "%s deleted from the AKILL list." +msgstr "#%s# διαγράφηκε από την λίστα AKILL." + +#: modules/commands/cs_access.cpp:685 +#, c-format +msgid "%s disabled on channel %s." +msgstr "Τα #%s# απενεργοποιήθηκαν στο κανάλι %s." + +#: modules/commands/cs_invite.cpp:75 +#, c-format +msgid "%s has been invited to %s." +msgstr "Ο/η #%s# προσκαλέσθηκε στο κανλάλι #%s#." + +#: modules/commands/os_svs.cpp:104 +#, fuzzy, c-format +msgid "%s has been joined to %s." +msgstr "Ο/η #%s# προσκαλέσθηκε στο κανλάλι #%s#." + +#: modules/commands/os_svs.cpp:152 +#, fuzzy, c-format +msgid "%s has been parted from %s." +msgstr "Ο/η #%s# έγινε unban από το κανάλι #%s#." + +#: modules/commands/cs_unban.cpp:96 +#, c-format +msgid "%s has been unbanned from %s." +msgstr "Ο/η #%s# έγινε unban από το κανάλι #%s#." + +#: modules/commands/ns_alist.cpp:110 +#, fuzzy, c-format +msgid "%s has no access in any channels." +msgstr "%s είναι ήση μέσα στο δίκτυο." + +#: modules/commands/cs_status.cpp:55 +#, fuzzy, c-format +msgid "%s has no access on %s." +msgstr "Ο/η #%s# προσκαλέσθηκε στο κανλάλι #%s#." + +#: modules/commands/cs_set.cpp:307 +#, c-format +msgid "%s has too many channels registered." +msgstr "#%s# έχει πολλά κατοχυρωμένα κανάλια." + +#: modules/commands/cs_status.cpp:51 +#, fuzzy, c-format +msgid "%s is a super administrator." +msgstr "%s είναι services operator τού τύπου %s." + +#: modules/pseudoclients/memoserv.cpp:214 +#, c-format +msgid "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" +msgstr "" +"Ο #%s# είναι μια υπηρεσία που επιτρέπει στους χρήστες\n" +"του IRC να στέλνουν μικρά γραπτά μηνύματα σε άλλους χρήστες\n" +"του δικτύου (είτε βρίσκονται συνδεδεμένοι εκείνη τη στιγμή,\n" +"είτε όχι) ή σε κανάλια(*).\n" +"Τα ψευδώνυμα του αποστολέα και του παραλήπτη πρέπει να είναι\n" +"κατοχυρωμένα για να χρησιμοποιηθεί η υπηρεσία.\n" +"\n" +"Οι εντολές του %s είναι:" + +#: modules/commands/cs_invite.cpp:66 +#, fuzzy, c-format +msgid "%s is already in %s!" +msgstr "Είστε ήδη στο κανάλι #%s#! " + +#: modules/commands/os_svs.cpp:99 +#, fuzzy, c-format +msgid "%s is already in %s." +msgstr "Είστε ήδη στο κανάλι #%s#! " + +#: modules/commands/ms_ignore.cpp:65 +#, fuzzy, c-format +msgid "%s is already on the ignore list." +msgstr "#%s# είναι ήδη στη λίστα αγνόησης σου" + +#: modules/commands/cs_suspend.cpp:97 modules/commands/ns_suspend.cpp:106 +#, fuzzy, c-format +msgid "%s is already suspended." +msgstr "Είστε ήδη στο κανάλι #%s#! " + +#: modules/commands/ms_rsend.cpp:56 modules/commands/ms_send.cpp:55 +#, c-format +msgid "%s is not a registered unforbidden nick or channel." +msgstr "#%s# δεν είναι σωστό bot ή κατοχυρωμένο κανάλι." + +#: modules/commands/cs_set.cpp:178 +#, c-format +msgid "%s is not a valid ban type." +msgstr "#%s# δεν είναι σωστός τύπος ban" + +#: modules/commands/bs_info.cpp:101 +#, c-format +msgid "%s is not a valid bot or registered channel." +msgstr "#%s# δεν είναι σωστό bot ή κατοχυρωμένο κανάλι." + +#: include/language.h:86 +#, fuzzy, c-format +msgid "%s is not a valid e-mail address." +msgstr "#%s# δεν είναι σωστός τύπος ban" + +#: include/language.h:80 +#, fuzzy, c-format +msgid "%s is not currently on channel %s." +msgstr "Τα #%s# απενεργοποιήθηκαν στο κανάλι %s." + +#: modules/commands/os_svs.cpp:144 +#, fuzzy, c-format +msgid "%s is not in %s." +msgstr "Είστε ήδη στο κανάλι #%s#! " + +#: modules/commands/ms_ignore.cpp:77 +#, fuzzy, c-format +msgid "%s is not on the ignore list." +msgstr "Ο/η #%s# δεν βρέθηκε στη λίστα αγνόησης σου." + +#: modules/commands/cs_status.cpp:90 +#, fuzzy, c-format +msgid "%s is on the auto kick list of %s (%s)." +msgstr "Ο/η #%s# προσθέθηκε επιτυχώς στην autokick λίστα του %s." + +#: modules/commands/cs_status.cpp:53 +#, fuzzy, c-format +msgid "%s is the founder of %s." +msgstr "Τα #%s# απενεργοποιήθηκαν στο κανάλι %s." + +#: modules/commands/cs_status.cpp:78 +#, c-format +msgid "%s matches access entry %s (from entry %s), which has privilege %s." +msgstr "" + +#: modules/commands/cs_status.cpp:71 +#, c-format +msgid "%s matches access entry %s, which has privilege %s." +msgstr "" + +#: include/language.h:109 +#, c-format +msgid "" +"%s matches an except on %s and cannot be banned until the except has been " +"removed." +msgstr "" + +#: modules/commands/cs_status.cpp:96 +#, fuzzy, c-format +msgid "%s matches auto kick entry %s on %s (%s)." +msgstr "Ο/η #%s# προσθέθηκε επιτυχώς στην autokick λίστα του %s." + +#: modules/commands/cs_xop.cpp:353 +#, fuzzy, c-format +msgid "%s not found on %s %s list." +msgstr "Ο/η #%s# δεν βρέθηκε η θέση στην AOP λίστα του %s." + +#: modules/commands/cs_access.cpp:338 modules/commands/cs_flags.cpp:255 +#, c-format +msgid "%s not found on %s access list." +msgstr "Ο/η #%s# δεν βρέθηκε στην access list του %s" + +#: modules/commands/cs_akick.cpp:265 +#, c-format +msgid "%s not found on %s autokick list." +msgstr "O #%s# δεν βρέθηκε στην autokick list του %s." + +#: modules/commands/bs_badwords.cpp:341 +#, c-format +msgid "%s not found on %s bad words list." +msgstr "#%s# δεν βρέθηκε στη λίστα των κακών λέξεων του %s." + +#: modules/commands/ns_access.cpp:66 +#, fuzzy, c-format +msgid "%s not found on %s's access list." +msgstr "Ο/η #%s# δεν βρέθηκε στην access list του %s" + +#: modules/commands/ns_cert.cpp:226 +#, fuzzy, c-format +msgid "%s not found on %s's certificate list." +msgstr "#%s# δεν βρέθηκε στη λίστα πρόσβασής σου." + +#: modules/commands/os_ignore.cpp:320 +#, fuzzy, c-format +msgid "%s not found on ignore list." +msgstr "#%s# δεν βρέθηκε στη λίστα Ignore." + +#: modules/commands/os_session.cpp:238 +#, c-format +msgid "" +"%s not found on session list, but has a limit of %d because it matches entry:" +" %s." +msgstr "" + +#: modules/commands/os_session.cpp:418 +#, c-format +msgid "%s not found on session-limit exception list." +msgstr "#%s# δεν βρέθηκε στην λίστα session-limit exception." + +#: modules/commands/os_sxline.cpp:92 +#, c-format +msgid "%s not found on the %s list." +msgstr "Ο/η #%s# δεν βρέθηκε η θέση στην AOP λίστα του %s." + +#: modules/commands/os_akill.cpp:237 +#, c-format +msgid "%s not found on the AKILL list." +msgstr "#%s# δεν βρέθηκε στην λίστα AKILL." + +#: modules/commands/cs_flags.cpp:251 +#, c-format +msgid "%s removed from the %s access list." +msgstr "#%s# διαγράφηκε από το access list του %s." + +#: modules/commands/ms_ignore.cpp:74 +#, fuzzy, c-format +msgid "%s removed from the ignore list." +msgstr "#%s# διαγράφτηκε από την λίστα πρόσβασής σου." + +#: modules/commands/os_list.cpp:157 +#, fuzzy, c-format +msgid "%s users list:" +msgstr "Τελος της λίστας προσβασης." + +#: modules/commands/os_ignore.cpp:316 +#, c-format +msgid "%s will no longer be ignored." +msgstr "Ο/η #%s# δεν θα αγνοείται πια." + +#: modules/commands/os_ignore.cpp:238 +#, c-format +msgid "%s will now be ignored for %s." +msgstr "#%s# θα αγνοείται για #%s#." + +#: modules/commands/os_ignore.cpp:233 +#, c-format +msgid "%s will now permanently be ignored." +msgstr "#%s# θα αγνοείται για πάντα." + +#: include/language.h:66 +#, fuzzy, c-format +msgid "%s%s HELP %s for more information." +msgstr "’γνωστη εντολή #%s#. \"/msg %s HELP\" για βοήθεια." + +#: modules/commands/bs_bot.cpp:270 +msgid "ADD nick user host real" +msgstr "" + +#: modules/commands/bs_bot.cpp:271 +msgid "CHANGE oldnick newnick [user [host [real]]]" +msgstr "" + +#: modules/commands/bs_bot.cpp:272 +msgid "DEL nick" +msgstr "DEL ##." + +#: modules/commands/os_session.cpp:560 +#, fuzzy +msgid "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." +msgstr "" +"Σύνταξη: #EXCEPTION ADD [#+expiry#] #mask# #limit# #reason##\n" +" #EXCEPTION DEL {#mask# | #list#}#\n" +" #EXCEPTION MOVE #num# #position##\n" +" #EXCEPTION LIST [#mask# | #list#]#\n" +" #EXCEPTION VIEW [#mask# | #list#]#\n" +"\n" +"Επιτρέπουν στους Services Operators να ορίσουν την λίστα των hosts τα\n" +"οποία έχουν ένα συγκεκριμένο όριο - αφήνοντας ασφαλής μηχανήματα, \n" +"όπως είναι τα shell servers, to carry more than the default number\n" +"of clients at a time. Αν κάποιο host περάσει από το session limit,\n" +"όλοι οι clients που θα προσπαθήσουν να συνδεθούν με αυτό το host θα \n" +"απορριφθούν-σκοτωθούν.Πριν ο χρήστης σκοτωθεί-απορριφθεί, θαn " +"προηδοποιηθεί,\n" +"με /NOTICE από τον %s. Το σημείωμα αυτό είναι επιλογή από το configuration.\n" +" \n" +"#EXCEPTION ADD# προσθέτει το hostname στην Exception list.\n" +"Σημείωση,αν γράψετε #nick!user@host# και #user@host# σαν μάσκες είναι " +"λάθος! \n" +"Μόνο πραγματικά host masks, όπως #box.host.dom# και #*.host.dom#, \n" +"είναι επιτρεπόμενα γιατί το όριο των sessions δεν περιέχει ψευδώνυμα ή \n" +"user names μέσα στο account. #όριο# πρέπει να είναι ένα νούμερο μεγαλύτερο " +"από\n" +"ή κοντά στο μηδέν. Αυτό εξαρτάται από τα πόσα sessions αυτό το host\n" +"μπορεί να πάρει μέσα στο χρόνο. Ο βαθμός μηδέν σημαίνει οτι το host δεν θα " +"έχει\n" +"όριο στην session limit. Κοίτα το βοήθημα #AKILL# για περισσότερες " +"πληροφορίες\n" +"με την σύνταξη της εντολής και την παράμετρο #expiry#.\n" +"#EXCEPTION DEL# σβήνει την δωσμένη μάσκα από την λίστα exception.\n" +"#EXCEPTION MOVE# απομακρύνει το exception #νούμερο# σε #θέση#.\n" +"#EXCEPTION LIST# and #EXCEPTION VIEW# δείχνει όλα τα έως τώρα \n" +"exceptions; αν η καθορισμένη μάσκα δψθεί, τότε θα εμφανίζεται στη λίστα.\n" +"#EXCEPTION VIEW# είναι πιο αναλυτική, εμφανίζει το ψευδώνυμο του χρήστη\n" +"που πρόσθεσε αυτό το exception, με λόγο,μάσκα και το χρόνο λήξης σε μέρα και " +"ώρα.\n" +" \n" +"Σημείωση το συνδεδεμένο client θα \"χρησιμοποιεί\" την πρώτη exception\n" +"και όπου ταιριάξει το host.\n" +" \n" +"Μόνο για τους #Επικεφαλείς Υπηρεσιών#." + +#: modules/commands/os_noop.cpp:68 +msgid "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." +msgstr "" + +#: modules/commands/cs_access.cpp:611 +#, c-format +msgid "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." +msgstr "" + +#: modules/commands/ms_read.cpp:35 +#, c-format +msgid "[auto-memo] The memo you sent to %s has been viewed." +msgstr "#[auto-memo]# Το memo που στείλατε στο %s έχει διαβαστεί." + +# +#: modules/commands/ns_group.cpp:92 +#, fuzzy +msgid "[target] [password]" +msgstr "^_στόχος^_ ^_κωδικό^_" + +#: modules/commands/ns_set.cpp:453 +msgid "address" +msgstr "" + +#: modules/commands/bs_set.cpp:162 +#, fuzzy +msgid "botname {ON|OFF}" +msgstr "SASET #nickname# AUTOOP {ON | OFF}" + +#: modules/extra/stats/cs_fantasy_top.cpp:39 +#: modules/extra/stats/cs_fantasy_top.cpp:51 +#: modules/commands/cs_suspend.cpp:152 modules/commands/cs_sync.cpp:20 +#: modules/commands/cs_log.cpp:106 modules/commands/bs_assign.cpp:91 +#: modules/commands/cs_info.cpp:20 modules/commands/cs_getkey.cpp:20 +msgid "channel" +msgstr "DROP #channel#" + +#: modules/commands/cs_set.cpp:138 +msgid "channel bantype" +msgstr "" + +#: modules/commands/cs_drop.cpp:20 +#, fuzzy +msgid "channel channel" +msgstr "ACT #κανάλι# #κείμενο#" + +# +#: modules/commands/cs_log.cpp:107 +#, fuzzy +msgid "channel command method [status]" +msgstr "KICK #channel# #option# {#ON|OFF#} [#settings#]" + +#: modules/commands/cs_kick.cpp:21 +#, fuzzy +msgid "channel mask [reason]" +msgstr "BAN ##channel# #nick# [#reason#]" + +#: modules/commands/os_mode.cpp:20 +msgid "channel modes" +msgstr "" + +#: modules/commands/cs_set.cpp:267 modules/commands/bs_assign.cpp:20 +msgid "channel nick" +msgstr "UNBAN #κανάλι# [#nick#]" + +#: modules/commands/cs_kick.cpp:20 +msgid "channel nick [reason]" +msgstr "BAN ##channel# #nick# [#reason#]" + +#: modules/commands/cs_clone.cpp:115 +msgid "channel target [what]" +msgstr "" + +#: modules/commands/bs_control.cpp:20 modules/commands/bs_control.cpp:80 +msgid "channel text" +msgstr "ACT #κανάλι# #κείμενο#" + +#: modules/commands/bs_set.cpp:91 +#, fuzzy +msgid "channel time" +msgstr "ACT #κανάλι# #κείμενο#" + +#: modules/commands/os_kick.cpp:20 +msgid "channel user reason" +msgstr "KICK #channel# #user# #reason#" + +#: modules/commands/cs_enforce.cpp:228 +#, fuzzy +msgid "channel what" +msgstr "ACT #κανάλι# #κείμενο#" + +#: modules/commands/cs_xop.cpp:481 +#, fuzzy +msgid "channel ADD mask" +msgstr "ACT #κανάλι# #κείμενο#" + +#: modules/commands/cs_access.cpp:499 +msgid "channel ADD mask level" +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:194 +#, fuzzy +msgid "channel ADD message" +msgstr "ACT #κανάλι# #κείμενο#" + +#: modules/commands/bs_badwords.cpp:371 +msgid "channel ADD word [SINGLE | START | END]" +msgstr "" + +#: modules/commands/cs_akick.cpp:435 +msgid "channel ADD {nick | mask} [reason]" +msgstr "" + +#: modules/commands/cs_topic.cpp:151 +#, fuzzy +msgid "channel APPEND topic" +msgstr "TOPIC #κανάλι# [#topic#]" + +#: modules/commands/cs_access.cpp:503 modules/commands/cs_flags.cpp:376 +#: modules/commands/cs_xop.cpp:484 modules/commands/cs_entrymsg.cpp:197 +#: modules/commands/bs_badwords.cpp:374 modules/commands/cs_akick.cpp:440 +msgid "channel CLEAR" +msgstr "" + +#: modules/commands/cs_mode.cpp:736 +#, fuzzy +msgid "channel CLEAR [what]" +msgstr "TOPIC #κανάλι# [#topic#]" + +#: modules/commands/os_mode.cpp:21 +#, fuzzy +msgid "channel CLEAR [ALL]" +msgstr "DROP #channel#" + +#: modules/commands/cs_entrymsg.cpp:195 +#, fuzzy +msgid "channel DEL num" +msgstr "UNBAN #κανάλι# [#nick#]" + +#: modules/commands/cs_access.cpp:500 modules/commands/cs_xop.cpp:482 +msgid "channel DEL {mask | entry-num | list}" +msgstr "" + +#: modules/commands/cs_akick.cpp:436 +msgid "channel DEL {nick | mask | entry-num | list}" +msgstr "" + +#: modules/commands/bs_badwords.cpp:372 +msgid "channel DEL {word | entry-num | list}" +msgstr "" + +#: modules/commands/cs_akick.cpp:439 +msgid "channel ENFORCE" +msgstr "" + +#: modules/commands/cs_access.cpp:744 modules/commands/cs_entrymsg.cpp:196 +msgid "channel LIST" +msgstr "" + +#: modules/commands/cs_akick.cpp:437 +msgid "channel LIST [mask | entry-num | list]" +msgstr "" + +#: modules/commands/cs_access.cpp:501 modules/commands/cs_xop.cpp:483 +#: modules/commands/bs_badwords.cpp:373 +msgid "channel LIST [mask | list]" +msgstr "" + +#: modules/commands/cs_flags.cpp:375 +msgid "channel LIST [mask | +flags]" +msgstr "" + +# +#: modules/commands/cs_mode.cpp:734 +#, fuzzy +msgid "channel LOCK {ADD|DEL|SET|LIST} [what]" +msgstr "AOP #channel# {ADD|DEL|LIST|CLEAR} [#nick# | #entry-list#]" + +#: modules/commands/cs_access.cpp:745 +msgid "channel RESET" +msgstr "" + +#: modules/commands/cs_mode.cpp:735 +msgid "channel SET modes" +msgstr "" + +#: modules/commands/cs_access.cpp:742 +msgid "channel SET type level" +msgstr "" + +#: modules/commands/cs_akick.cpp:438 +msgid "channel VIEW [mask | entry-num | list]" +msgstr "" + +#: modules/commands/cs_access.cpp:502 +msgid "channel VIEW [mask | list]" +msgstr "" + +# +#: modules/commands/cs_register.cpp:20 modules/commands/cs_set.cpp:205 +msgid "channel [description]" +msgstr "Αλλάζει την περιγραφή του καναλιού" + +#: modules/commands/cs_set.cpp:950 modules/commands/cs_invite.cpp:20 +#: modules/commands/cs_unban.cpp:20 +msgid "channel [nick]" +msgstr "UNBAN #κανάλι# [#nick#]" + +#: modules/commands/cs_set_misc.cpp:96 +msgid "channel [parameters]" +msgstr "" + +#: modules/commands/cs_mode.cpp:807 modules/commands/cs_status.cpp:20 +#, fuzzy +msgid "channel [user]" +msgstr "UNBAN #κανάλι# [#nick#]" + +#: modules/commands/cs_suspend.cpp:59 +#, fuzzy +msgid "channel [+expiry] [reason]" +msgstr "BAN ##channel# #nick# [#reason#]" + +#: modules/commands/cs_ban.cpp:40 +#, fuzzy +msgid "channel [+expiry] {nick | mask} [reason]" +msgstr "BAN ##channel# #nick# [#reason#]" + +#: modules/commands/cs_flags.cpp:374 +#, fuzzy +msgid "channel [MODIFY] mask changes" +msgstr "BAN ##channel# #nick# [#reason#]" + +#: modules/commands/cs_topic.cpp:150 +#, fuzzy +msgid "channel [SET] [topic]" +msgstr "TOPIC #κανάλι# [#topic#]" + +#: modules/commands/cs_topic.cpp:152 +#, fuzzy +msgid "channel [UNLOCK|LOCK]" +msgstr "SET #channel# XOP {ON | OFF}" + +#: modules/fantasy.cpp:20 modules/commands/greet.cpp:20 +#: modules/commands/bs_assign.cpp:154 +#, fuzzy +msgid "channel {ON|OFF}" +msgstr "SET #channel# XOP {ON | OFF}" + +# +#: modules/commands/bs_kick.cpp:491 +#, fuzzy +msgid "channel {ON|OFF} [ttb [ln [secs]]]" +msgstr "KICK #channel# #option# {#ON|OFF#} [#settings#]" + +# +#: modules/commands/bs_kick.cpp:361 +#, fuzzy +msgid "channel {ON|OFF} [ttb [min [percent]]]" +msgstr "KICK #channel# #option# {#ON|OFF#} [#settings#]" + +# +#: modules/commands/bs_kick.cpp:623 +#, fuzzy +msgid "channel {ON|OFF} [ttb [num]]" +msgstr "KICK #channel# #option# {#ON|OFF#} [#settings#]" + +#: modules/commands/bs_kick.cpp:252 modules/commands/bs_kick.cpp:288 +#: modules/commands/bs_kick.cpp:327 modules/commands/bs_kick.cpp:457 +#: modules/commands/bs_kick.cpp:589 modules/commands/bs_kick.cpp:724 +#: modules/commands/bs_kick.cpp:758 +#, fuzzy +msgid "channel {ON|OFF} [ttb]" +msgstr "SET #channel# XOP {ON | OFF}" + +#: modules/commands/cs_access.cpp:743 +msgid "channel {DIS | DISABLE} type" +msgstr "" + +#: modules/commands/cs_set.cpp:873 +#, fuzzy +msgid "channel {ON | LEVEL | OFF}" +msgstr "SET #channel# SIGNKICK {ON | LEVEL | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:18 modules/commands/cs_set.cpp:75 +#: modules/commands/cs_set.cpp:336 modules/commands/cs_set.cpp:401 +#: modules/commands/cs_set.cpp:473 modules/commands/cs_set.cpp:622 +#: modules/commands/cs_set.cpp:684 modules/commands/cs_set.cpp:747 +#: modules/commands/cs_set.cpp:811 modules/commands/cs_set.cpp:1044 +#: modules/commands/bs_kick.cpp:792 modules/commands/bs_kick.cpp:857 +#: modules/commands/cs_topic.cpp:21 modules/commands/cs_list.cpp:181 +msgid "channel {ON | OFF}" +msgstr "SET #channel# XOP {ON | OFF}" + +#: modules/commands/ns_getemail.cpp:24 +msgid "email" +msgstr "" + +#: modules/commands/ns_set.cpp:794 +msgid "language" +msgstr "" + +#: modules/commands/ms_sendall.cpp:25 modules/commands/ms_staff.cpp:25 +msgid "memo-text" +msgstr "STAFF #memo-text#" + +#: modules/commands/gl_global.cpp:22 modules/commands/greet.cpp:84 +msgid "message" +msgstr "" + +#: modules/commands/os_modinfo.cpp:20 modules/commands/os_module.cpp:20 +#: modules/commands/os_module.cpp:57 modules/commands/os_module.cpp:129 +msgid "modname" +msgstr "" + +#: modules/commands/ns_set.cpp:330 +msgid "new-display" +msgstr "" + +#: modules/commands/ns_set.cpp:120 +msgid "new-password" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:52 modules/commands/hs_del.cpp:20 +#: modules/commands/hs_del.cpp:60 modules/commands/ms_check.cpp:20 +#: modules/commands/hs_request.cpp:192 modules/commands/cs_seen.cpp:262 +msgid "nick" +msgstr "" + +#: modules/commands/os_svs.cpp:79 +#, fuzzy +msgid "nick channel" +msgstr "RSEND {#nick# | #channel#} #memo-text#" + +#: modules/commands/os_svs.cpp:123 +#, fuzzy +msgid "nick channel [reason]" +msgstr "BAN ##channel# #nick# [#reason#]" + +#: modules/commands/os_oline.cpp:20 +msgid "nick flags" +msgstr "" + +#: modules/commands/hs_set.cpp:20 modules/commands/hs_set.cpp:126 +msgid "nick hostmask" +msgstr "SET ## ##." + +#: modules/commands/os_svs.cpp:20 +msgid "nick newnick" +msgstr "" + +#: modules/commands/hs_request.cpp:241 +#, fuzzy +msgid "nick [reason]" +msgstr "BAN ##channel# #nick# [#reason#]" + +#: modules/commands/ns_getpass.cpp:20 modules/commands/ns_drop.cpp:19 +#: modules/commands/ns_suspend.cpp:161 +msgid "nickname" +msgstr "CHECK #nickname#" + +#: modules/commands/ns_set.cpp:546 +msgid "nickname address" +msgstr "" + +#: modules/commands/ns_resetpass.cpp:22 +#, fuzzy +msgid "nickname email" +msgstr "DEL ##." + +#: modules/commands/ns_set.cpp:872 +msgid "nickname language" +msgstr "" + +#: modules/commands/greet.cpp:145 +msgid "nickname message" +msgstr "" + +#: modules/commands/ns_set.cpp:399 +msgid "nickname new-display" +msgstr "" + +# +#: modules/commands/ns_set.cpp:173 +msgid "nickname new-password" +msgstr "Ρυθμίζει τον κωδικό του ψευδονύμου." + +#: modules/commands/ns_set_misc.cpp:170 +msgid "nickname [parameter]" +msgstr "" + +# +#: modules/commands/ns_recover.cpp:150 +#, fuzzy +msgid "nickname [password]" +msgstr "Ρυθμίζει τον κωδικό του ψευδονύμου." + +#: modules/commands/ns_suspend.cpp:61 +#, fuzzy +msgid "nickname [+expiry] [reason]" +msgstr "SUSPEND nickname reason" + +#: modules/commands/ns_info.cpp:239 +#, fuzzy +msgid "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +msgstr "SET HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:130 modules/commands/ns_set.cpp:302 +#: modules/commands/ns_set.cpp:631 modules/commands/ns_set.cpp:985 +#: modules/commands/ns_set.cpp:1076 modules/commands/ns_set.cpp:1105 +#: modules/commands/ns_list.cpp:252 +msgid "nickname {ON | OFF}" +msgstr "SASET #nickname# AUTOOP {ON | OFF}" + +#: modules/commands/ns_set.cpp:760 +msgid "nickname {ON | QUICK | IMMED | OFF}" +msgstr "SASET #nickname# KILL {ON | QUICK | IMMED | OFF}" + +#: modules/commands/bs_set.cpp:20 +#, fuzzy +msgid "option (channel | bot) settings" +msgstr "SET #channel# #option# #settings#" + +#: modules/commands/cs_set.cpp:21 +msgid "option channel parameters" +msgstr "" + +# +#: modules/commands/bs_kick.cpp:120 +#, fuzzy +msgid "option channel {ON|OFF} [settings]" +msgstr "KICK #channel# #option# {#ON|OFF#} [#settings#]" + +#: modules/commands/ns_set.cpp:75 +msgid "option nickname parameters" +msgstr "" + +#: modules/commands/ms_set.cpp:207 modules/commands/ns_set.cpp:20 +msgid "option parameters" +msgstr "" + +#: modules/commands/os_set.cpp:170 +msgid "option setting" +msgstr "SET #option# #setting#" + +#: modules/commands/ns_register.cpp:22 +msgid "passcode" +msgstr "" + +# +#: modules/commands/os_login.cpp:19 +msgid "password" +msgstr "LOGIN #password#" + +# +#: modules/commands/ns_register.cpp:124 +msgid "password [email]" +msgstr "^_κωδικό^_ ^_email^_" + +# +#: modules/commands/ns_register.cpp:122 +msgid "password email" +msgstr "^_κωδικό^_ ^_email^_" + +#: modules/commands/cs_list.cpp:21 +#, fuzzy +msgid "pattern [SUSPENDED] [NOEXPIRE]" +msgstr "LIST #pattern# [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/ns_list.cpp:20 +msgid "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" +msgstr "LIST #pattern# [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/os_jupe.cpp:20 +msgid "server [reason]" +msgstr "JUPE #servername# [#reason#]" + +#: modules/commands/os_mode.cpp:147 +msgid "user modes" +msgstr "" + +#: modules/commands/os_kill.cpp:20 +msgid "user [reason]" +msgstr "" + +# +#: modules/commands/os_sxline.cpp:440 +#, fuzzy +msgid "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." +msgstr "" +"Σύνταξη: #AKILL ADD [+#expiry#] #μάσκα# #λόγος##\n" +" #AKILL DEL {#μάσκα# | #θέσεις-νούμερα# | #λίστα#}#\n" +" #AKILL LIST [#μάσκα# | #λίστα#]#\n" +" #AKILL VIEW [#μάσκα# | #λίστα#]#\n" +" #AKILL CLEAR#\n" +"\n" +"Μπορούν οι Services operators να αλλάξουν την λίστα AKILL. Αν\n" +"η μάσκα του χρήστη ταιριάξει με μια από αυτές που περιέχονται στην λίστα " +"AKILL,\n" +"τα Services δεν θα επιτρέψουν στο χρήστη να συνδεθεί με το δίκτυο (server) " +"και \n" +"θα έχει KILL, σε όλους τους servers που είναι μαζί.Δηλ γίνεται προσθήκη\n" +"ban (K-line) για την μάσκα που ταιριάζει στο χρήστη.\n" +" \n" +"Η εντολή #AKILL ADD# προσθέτει το ανάλογο user@host μάσκα στην λίστα AKILL\n" +"με έναν λόγο που πρέπει να δώσετε ωστε ο χρήστης να καταλάβει γιατί είναι " +"AKILL.\n" +"Το #expiry# είναι συγκεκριμένο και επιλέγεται από τα επόμενα, #d# \n" +"(μέρες), #h# (ώρες), ή #m# (λεπτά). Συνδιασμοί (όπως \n" +"#1h30m#) δεν επιτρέπονται . Αν δεν δώσετε το χρόνο \n" +"από default θα είναι σε μέρες (θα είναι #+30# που σημαίνει 30 \n" +"μέρες). Για να προσθέσετε ένα AKILL που να μην λήγει, χρησιμοποιείστε #" +"+0#.\n" +"Αν η usermask ξεκινάει με #+#, ο χρόνος λήξης θα πρέπει να δίνετε\n" +"ακόμα και αν είναι ίδιος με τον default. Ο\n" +"συγκεκριμένος χρόνος λήξης της εντολής AKILL μπορεί να βρεθεί με την εντολή\n" +"#STATS AKILL#.\n" +"\n" +"Η εντολή #AKILL DEL# διαγράφει τη συγκεκριμένη μάσκα από την λίστα. \n" +"AKILL αν υπάρχει. Αν σας δωθεί λίστα με τις θέσεις-νούμερα\n" +"αυτές οι θέσεις θα διαγραφούν. (Κοίτα το παράδειγμα με την εντολή LIST.)\n" +"\n" +"Η εντολή #AKILL LIST# εμφανίζει την λίστα με τα AKILL.\n" +"Αν δίνεται μια συγκεκριμένη μάσκα, θα εμφανιστούν οι θέσεις που αντιστοιχούν " +"σε\n" +"αυτή τη μάσκα. Αν δίνετε η λίστα με τις θέσεις-νούμερα μπορείτε να τις " +"δείτε και \n" +"αλλιώς,\n" +"παράδειγμα:\n" +" #AKILL LIST 2-5,7-9#\n" +" Εμφανίζει τις θέσεις με τα νούμερα 2 εως 5 και 7 \n" +" εως 9 της λίστας AKILL.\n" +" \n" +"Η εντολή #AKILL VIEW# είναι πιο καλύτερη από την #AKILL LIST#, και\n" +"εμφανίζει ποιος συγκεκριμένα έβαλε κάποιον AKILL, την ημερομηνία που έγινε, " +"και\n" +"πότε θα λήξει, όπως και το user@host και τον λόγο.\n" +"Η εντολή _AKILL CLEAR_ καθαρίζει όλες τις θέσεις της λίστας AKILL.\n" +"Μόνο για τους #Services operators#.\t\n" +" " + +# +#: modules/commands/os_sxline.cpp:678 +#, fuzzy +msgid "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Σύνταξη: #AKILL ADD [+#expiry#] #μάσκα# #λόγος##\n" +" #AKILL DEL {#μάσκα# | #θέσεις-νούμερα# | #λίστα#}#\n" +" #AKILL LIST [#μάσκα# | #λίστα#]#\n" +" #AKILL VIEW [#μάσκα# | #λίστα#]#\n" +" #AKILL CLEAR#\n" +"\n" +"Μπορούν οι Services operators να αλλάξουν την λίστα AKILL. Αν\n" +"η μάσκα του χρήστη ταιριάξει με μια από αυτές που περιέχονται στην λίστα " +"AKILL,\n" +"τα Services δεν θα επιτρέψουν στο χρήστη να συνδεθεί με το δίκτυο (server) " +"και \n" +"θα έχει KILL, σε όλους τους servers που είναι μαζί.Δηλ γίνεται προσθήκη\n" +"ban (K-line) για την μάσκα που ταιριάζει στο χρήστη.\n" +" \n" +"Η εντολή #AKILL ADD# προσθέτει το ανάλογο user@host μάσκα στην λίστα AKILL\n" +"με έναν λόγο που πρέπει να δώσετε ωστε ο χρήστης να καταλάβει γιατί είναι " +"AKILL.\n" +"Το #expiry# είναι συγκεκριμένο και επιλέγεται από τα επόμενα, #d# \n" +"(μέρες), #h# (ώρες), ή #m# (λεπτά). Συνδιασμοί (όπως \n" +"#1h30m#) δεν επιτρέπονται . Αν δεν δώσετε το χρόνο \n" +"από default θα είναι σε μέρες (θα είναι #+30# που σημαίνει 30 \n" +"μέρες). Για να προσθέσετε ένα AKILL που να μην λήγει, χρησιμοποιείστε #" +"+0#.\n" +"Αν η usermask ξεκινάει με #+#, ο χρόνος λήξης θα πρέπει να δίνετε\n" +"ακόμα και αν είναι ίδιος με τον default. Ο\n" +"συγκεκριμένος χρόνος λήξης της εντολής AKILL μπορεί να βρεθεί με την εντολή\n" +"#STATS AKILL#.\n" +"\n" +"Η εντολή #AKILL DEL# διαγράφει τη συγκεκριμένη μάσκα από την λίστα. \n" +"AKILL αν υπάρχει. Αν σας δωθεί λίστα με τις θέσεις-νούμερα\n" +"αυτές οι θέσεις θα διαγραφούν. (Κοίτα το παράδειγμα με την εντολή LIST.)\n" +"\n" +"Η εντολή #AKILL LIST# εμφανίζει την λίστα με τα AKILL.\n" +"Αν δίνεται μια συγκεκριμένη μάσκα, θα εμφανιστούν οι θέσεις που αντιστοιχούν " +"σε\n" +"αυτή τη μάσκα. Αν δίνετε η λίστα με τις θέσεις-νούμερα μπορείτε να τις " +"δείτε και \n" +"αλλιώς,\n" +"παράδειγμα:\n" +" #AKILL LIST 2-5,7-9#\n" +" Εμφανίζει τις θέσεις με τα νούμερα 2 εως 5 και 7 \n" +" εως 9 της λίστας AKILL.\n" +" \n" +"Η εντολή #AKILL VIEW# είναι πιο καλύτερη από την #AKILL LIST#, και\n" +"εμφανίζει ποιος συγκεκριμένα έβαλε κάποιον AKILL, την ημερομηνία που έγινε, " +"και\n" +"πότε θα λήξει, όπως και το user@host και τον λόγο.\n" +"Η εντολή _AKILL CLEAR_ καθαρίζει όλες τις θέσεις της λίστας AKILL.\n" +"Μόνο για τους #Services operators#.\t\n" +" " + +#: modules/pseudoclients/nickserv.cpp:492 +#, fuzzy, c-format +msgid "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." +msgstr "" +"Ψευδώνυμα τα οποία δεν χρησιμοποιούνται πλέον θα είναι στην διαδικασία \n" +"της αυτόματης λήξης, π.ς. θα διαγράφονται αυτόματα\n" +"μετά από %d μέρες αν δεν χρησιμοποιούνται." + +#: modules/pseudoclients/botserv.cpp:143 +msgid "" +" \n" +"Available commands are:" +msgstr "" + +#: modules/pseudoclients/botserv.cpp:167 +#, c-format +msgid "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." +msgstr "" + +#: modules/fantasy.cpp:69 +#, fuzzy, c-format +msgid "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." +msgstr "" +"Σύνταξη: #SET #κανάλι# FANTASY {#ON|OFF#}\n" +"\n" +"Ενεργοποιεί ή απενεργοποιεί την επιλογή #fantasy# στο κανάλι.\n" +"Όταν είναι ενεργοποιημένη, οι χρήστες μπορούν να χρησιμοποιήσουν εντολές\n" +"!op, !deop, !voice, !devoice,!kick, !kb, !unban, !seen\n" +"στο κανάλι (ψάχνετε να δείτε πως δουλεύουν \n" +"προσπαθήστε με ή χωρίς ψευδώνυμο για κάθε μια,και με λόγο για κάποιες) \n" +" \n" +"Σημειώνεται οτι όσοι χρήστες θέλουν να χρησιμοποιήσουν τις fantaisist\n" +"εντολές θα ΠΡΕΠΕΙ να έχουν αρκετό level και για την\n" +"FANTASIA και άλλο level για τις εντολές\n" +"(για παράδειγμα, για να χρησιμοποιήσεις !op, θα πρέπει να έχεις αρκετή \n" +"access για την OPDEOP level)." + +#: modules/commands/greet.cpp:69 +#, fuzzy +msgid "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." +msgstr "" +"Σύνταξη: #SET #κανάλι# GREET {#ON|OFF#}\n" +"\n" +"Ενεργοποιεί ή απενεργοποιεί την επιλογή #greet# στο κανάλι.\n" +"Όταν είναι ενεργοποιημένη, το bot θα εμφανίζει το μήνυμα χαιρετισμού\n" +"στους χρήστες που θα μπένουν στο κανάλι, με την προυπόθεση οτι\n" +"έχουν αρκετή access στο κανάλι." + +#: modules/commands/bs_kick.cpp:843 +#, fuzzy +msgid "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +"Σύνταξη: #SET #κανάλι# DONTKICKOPS {#ON|OFF#}\n" +"\n" +"Ενεργοποιεί ή απενεργοποιεί την επιλογή #op προστασία# στο κανάλι.\n" +"Όταν είναι ενεργοποιημένη, οι ops δεν θα τρώνε kick από το bot\n" +"ακόμα και αν δεν ταιριάζοτν με την NOKICK level." + +#: modules/commands/bs_kick.cpp:908 +#, fuzzy +msgid "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +"Σύνταξη: #SET #κανάλι# DONTKICKVOICES {#ON|OFF#}\n" +"\n" +"Ενεργοποιεί ή απενεργοποιεί την επιλογή #voices προστασία# στο κανάλι.\n" +"Όταν είναι ενεργοποιημένη, οι voices δεν θα τρώνε kick από το bot\n" +"ακόμα και αν δεν ταιριάζοτν με την NOKICK level." + +#: modules/pseudoclients/botserv.cpp:141 +#, fuzzy, c-format +msgid "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" +msgstr "" +"To Bot θα μπεί στο κανάλι όταν είναι τουλάχιστον \n" +"#%d# χρήστες σε αυτό. Επιπλέον όλες οι %s εντολές\n" +"μπορούν να χρησιμοποιηθούν αν το fantasy έχει ενεργοποιηθεί\n" +"με τη χρήση του ονόματος της εντολής και μπροστά το σύμβολο %c." + +#: modules/commands/cs_register.cpp:105 +msgid "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." +msgstr "" + +#: modules/pseudoclients/chanserv.cpp:272 +#, c-format +msgid "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." +msgstr "" +"Σημείωση: οποιοδήποτε κανάλι δεν χρησιμοποιείται για %d μέρες\n" +"(δηλ κανένας χρήστης που έχει access δεν μπένει στο κανάλι\n" +"για εκείνη την περίοδο των ημερών) θα διαγραφεί αυτόματα." + +#: modules/commands/cs_register.cpp:101 +#, c-format +msgid "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +msgstr "" + +#: modules/pseudoclients/nickserv.cpp:486 +msgid "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." +msgstr "" +"Οι Services operators (επικεφαλείς) μπορούν να διαγράψουν ένα ψευδώνυμο " +"χωρίς να\n" +"χρειαστεί να κάνουν εντολή αναγνώρισης και καν αλλαγή ψευδώνυμου, και " +"μπορούν να\n" +"δουν την λίστα access για κάθε ψευδώνυμο (#/msg %s ACCESS LIST #nick##)." + +#: modules/pseudoclients/chanserv.cpp:277 +#, fuzzy +msgid "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." +msgstr "" +" \n" +"Οι Services Operators μπορούν να διαγράψουν οποιοδήποτε κανάλι, χωρίς να " +"κάνουν\n" +"εντολή αναγνώρισης μέσω κωδικού, μπορούν να δούν την access, AKICK,\n" +"και τα level οποιουδήποτε καναλιού." + +#: modules/commands/bs_set.cpp:147 +msgid "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." +msgstr "" + +#: modules/commands/cs_xop.cpp:542 +#, fuzzy, c-format +msgid "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." +msgstr "" +"Η εντολή #BADWORDS DEL# αφαιρεί τη δοσμένη λέξη από τη λίστα των\n" +"απαγορευμένων λέξεων. Σε περίπτωση που δοθεί μια λίστα με αριθμούς " +"καταχωρήσεων,\n" +"αυτές οι καταχωρήσεις διαγράφονται. (Βλέπε παράδειγμα για λίστα παρακάτω.)\n" +" \n" +"Η εντολή #BADWORDS LIST# προβάλλει τη λίστα των απαγορευμένων λέξεων. Αν " +"δοθεί\n" +"μια wildcard mask, τοτε μόνο οι καταχωρήσεις που αντιστοιχούν στη\n" +"mask προβάλλονται. Αν δοθεί μια λίστα με αριθμούς καταχωρήσεων,\n" +"τότε μόνο οι συγκεκριμένες καταχωρήσεις προβάλλονται. Για παράδειγμα:\n" +" #BADWORDS #channel LIST 2-5,7-9#\n" +" Προβάλλει τις καταχωρημένες απαγορευμένες λέξεις από το 2 εως το 5 " +"και\n" +" απο το 7 μέχρι το 9.\n" +" \n" +"Η εντολή #BADWORDS CLEAR# διαγράφει όλες τις καταχωρήσεις της λίστας\n" +"των απαγορευμένων λέξεων." + +#: modules/commands/cs_akick.cpp:508 +#, c-format +msgid "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." +msgstr "" + +#: modules/commands/os_akill.cpp:448 +#, fuzzy +msgid "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." +msgstr "" +"Η εντολή #BADWORDS DEL# αφαιρεί τη δοσμένη λέξη από τη λίστα των\n" +"απαγορευμένων λέξεων. Σε περίπτωση που δοθεί μια λίστα με αριθμούς " +"καταχωρήσεων,\n" +"αυτές οι καταχωρήσεις διαγράφονται. (Βλέπε παράδειγμα για λίστα παρακάτω.)\n" +" \n" +"Η εντολή #BADWORDS LIST# προβάλλει τη λίστα των απαγορευμένων λέξεων. Αν " +"δοθεί\n" +"μια wildcard mask, τοτε μόνο οι καταχωρήσεις που αντιστοιχούν στη\n" +"mask προβάλλονται. Αν δοθεί μια λίστα με αριθμούς καταχωρήσεων,\n" +"τότε μόνο οι συγκεκριμένες καταχωρήσεις προβάλλονται. Για παράδειγμα:\n" +" #BADWORDS #channel LIST 2-5,7-9#\n" +" Προβάλλει τις καταχωρημένες απαγορευμένες λέξεις από το 2 εως το 5 " +"και\n" +" απο το 7 μέχρι το 9.\n" +" \n" +"Η εντολή #BADWORDS CLEAR# διαγράφει όλες τις καταχωρήσεις της λίστας\n" +"των απαγορευμένων λέξεων." + +#: modules/commands/os_sxline.cpp:462 +#, fuzzy +msgid "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." +msgstr "" +"Η εντολή #BADWORDS DEL# αφαιρεί τη δοσμένη λέξη από τη λίστα των\n" +"απαγορευμένων λέξεων. Σε περίπτωση που δοθεί μια λίστα με αριθμούς " +"καταχωρήσεων,\n" +"αυτές οι καταχωρήσεις διαγράφονται. (Βλέπε παράδειγμα για λίστα παρακάτω.)\n" +" \n" +"Η εντολή #BADWORDS LIST# προβάλλει τη λίστα των απαγορευμένων λέξεων. Αν " +"δοθεί\n" +"μια wildcard mask, τοτε μόνο οι καταχωρήσεις που αντιστοιχούν στη\n" +"mask προβάλλονται. Αν δοθεί μια λίστα με αριθμούς καταχωρήσεων,\n" +"τότε μόνο οι συγκεκριμένες καταχωρήσεις προβάλλονται. Για παράδειγμα:\n" +" #BADWORDS #channel LIST 2-5,7-9#\n" +" Προβάλλει τις καταχωρημένες απαγορευμένες λέξεις από το 2 εως το 5 " +"και\n" +" απο το 7 μέχρι το 9.\n" +" \n" +"Η εντολή #BADWORDS CLEAR# διαγράφει όλες τις καταχωρήσεις της λίστας\n" +"των απαγορευμένων λέξεων." + +#: modules/commands/os_sxline.cpp:697 +#, fuzzy +msgid "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." +msgstr "" +"Η εντολή #BADWORDS DEL# αφαιρεί τη δοσμένη λέξη από τη λίστα των\n" +"απαγορευμένων λέξεων. Σε περίπτωση που δοθεί μια λίστα με αριθμούς " +"καταχωρήσεων,\n" +"αυτές οι καταχωρήσεις διαγράφονται. (Βλέπε παράδειγμα για λίστα παρακάτω.)\n" +" \n" +"Η εντολή #BADWORDS LIST# προβάλλει τη λίστα των απαγορευμένων λέξεων. Αν " +"δοθεί\n" +"μια wildcard mask, τοτε μόνο οι καταχωρήσεις που αντιστοιχούν στη\n" +"mask προβάλλονται. Αν δοθεί μια λίστα με αριθμούς καταχωρήσεων,\n" +"τότε μόνο οι συγκεκριμένες καταχωρήσεις προβάλλονται. Για παράδειγμα:\n" +" #BADWORDS #channel LIST 2-5,7-9#\n" +" Προβάλλει τις καταχωρημένες απαγορευμένες λέξεις από το 2 εως το 5 " +"και\n" +" απο το 7 μέχρι το 9.\n" +" \n" +"Η εντολή #BADWORDS CLEAR# διαγράφει όλες τις καταχωρήσεις της λίστας\n" +"των απαγορευμένων λέξεων." + +#: modules/commands/bs_assign.cpp:197 +#, fuzzy +msgid "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." +msgstr "" +"Σύνταξη: #SET #κανάλι# NOBOT {#ON|OFF#}#\n" +"\n" +"Αυτή η επιλογή κάνει το κανάλι να είναι unassignable (να μη μπει bot). Αν \n" +"το bot είναι ήδη assigned στο κανάλι, θα γίνει unassigned\n" +"αυτόματα, όταν θα ενεργοποιήσεις αυτή την επιλογή.\n" +"\n" +"Μόνο για τους #Services Operators#." + +#: modules/commands/bs_set.cpp:199 +#, fuzzy +msgid "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." +msgstr "" +"Σύνταξη: #SET #ψευδώνυμο-bot# PRIVATE {#ON|OFF#}#\n" +"\n" +"Αυτή η επιλογή κάνει το bot από assigned σε κανάλια\n" +"των χρηστων που δεν είναι IRC operators.\n" +"\n" +"Μόνο για τους #Services Operators#." + +#: modules/pseudoclients/memoserv.cpp:227 +#, c-format +msgid "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." +msgstr "" + +#: modules/commands/os_oper.cpp:167 +#, c-format +msgid " %s is online using this oper block." +msgstr "" + +#: modules/commands/os_modinfo.cpp:55 +#, c-format +msgid " Command %s on %s is linked to %s" +msgstr "" + +#: modules/commands/os_modinfo.cpp:43 +#, c-format +msgid " Providing service: %s" +msgstr "" + +#: modules/commands/os_oper.cpp:163 +msgid " This oper is configured in the configuration file." +msgstr "" + +#: modules/commands/os_modinfo.cpp:34 +#, c-format +msgid " Loaded at: %p" +msgstr "" + +#: modules/commands/cs_seen.cpp:303 +#, c-format +msgid " but %s mysteriously dematerialized." +msgstr "" + +#: src/messages.cpp:339 +#, c-format +msgid "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." +msgstr "" +"\"/msg %s\" δεν υποστηρίζεται πιά. Χρησιμοποιείστε \"/msg %s@%s\" or \"/%s" +"\" ." + +# +#: modules/commands/os_jupe.cpp:19 +msgid "\"Jupiter\" a server" +msgstr "\"Jupiter\" έναν server" + +#: modules/commands/os_oper.cpp:161 +#, fuzzy, c-format +msgid "%-8s %s" +msgstr "%-20s %s@%s" + +#: modules/extra/stats/cs_fantasy_top.cpp:152 +#, c-format +msgid "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:359 +msgid "%b %d %H:%M:%S %Y %Z" +msgstr "" + +#: modules/commands/cs_log.cpp:205 +#, c-format +msgid "%c is an unknown status mode." +msgstr "" + +#: modules/commands/cs_mode.cpp:431 +#, fuzzy, c-format +msgid "%c%c is not locked on %s." +msgstr "%c δεν έχει κλειδωθεί στο %s." + +#: modules/commands/cs_mode.cpp:427 +#, c-format +msgid "%c%c%s has been unlocked from %s." +msgstr "Τα modes %c%c%s ξεκλειδώθηκαν από το %s" + +#: modules/commands/cs_clone.cpp:56 +#, fuzzy, c-format +msgid "%d access entries from %s have been cloned to %s." +msgstr "Όλες οι καταχωρίσεις πρόσβασης από το #%s# έχουν μεταφερθεί στο #%s#" + +#: modules/commands/bs_botlist.cpp:56 +#, c-format +msgid "%d bots available." +msgstr "%d bots διαθέσιμα." + +#: modules/commands/os_modinfo.cpp:189 +#, fuzzy, c-format +msgid "%d modules loaded." +msgstr "%d Modules έχουν φορτωθεί." + +#: modules/commands/ns_group.cpp:357 +#, fuzzy, c-format +msgid "%d nickname(s) in the group." +msgstr "%d ψευδώνυμα μέσα στο group." + +#: modules/commands/cs_seen.cpp:137 +#, c-format +msgid "%lu nicks are stored in the database, using %.2Lf kB of memory." +msgstr "" + +#: modules/commands/cs_xop.cpp:241 modules/commands/cs_xop.cpp:372 +#: modules/commands/cs_xop.cpp:450 +#, c-format +msgid "%s %s list is empty." +msgstr "Η %s %s λίστα είναι άδεια." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1181 +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1201 +#: modules/commands/bs_kick.cpp:1211 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban)" +msgstr " Έντονοι χαρακτήρες με kick : %s (%d kick(s) to ban)" + +#: modules/commands/bs_kick.cpp:1161 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; %d lines in %ds)" +msgstr " Επανάληψη με kick : %s (%d kick(s) to ban; %d γραμμές σε %ds)" + +#: modules/commands/bs_kick.cpp:1171 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; %d times)" +msgstr " Επανάληψη με kick : %s (%d kick(s) to ban; %d times)" + +#: modules/commands/bs_kick.cpp:1141 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; minimum %d/%d%%)" +msgstr "" +" Κεφαλαία γράμματα με kick : %s (%d kick(s) για ban; ελάχιστο %d/%d%%)" + +#: modules/commands/bs_kick.cpp:1163 +#, fuzzy, c-format +msgid "%s (%d lines in %ds)" +msgstr " %s (λήγει σε %s)" + +#: modules/commands/bs_kick.cpp:1173 +#, c-format +msgid "%s (%d times)" +msgstr "" + +#: modules/commands/cs_seen.cpp:358 +#, c-format +msgid "%s (%s) was kicked from %s (\"%s\") %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:355 +#, c-format +msgid "%s (%s) was kicked from a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:326 +#, c-format +msgid "%s (%s) was last seen changing nick from %s to %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:321 +#, c-format +msgid "%s (%s) was last seen changing nick to %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:310 +#, c-format +msgid "%s (%s) was last seen connecting %s ago (%s)%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:335 +#, c-format +msgid "%s (%s) was last seen joining %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:332 +#, c-format +msgid "%s (%s) was last seen joining a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:344 +#, c-format +msgid "%s (%s) was last seen parting %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:341 +#, c-format +msgid "%s (%s) was last seen parting a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:349 +#, c-format +msgid "%s (%s) was last seen quitting (%s) %s ago (%s)." +msgstr "" + +#: modules/commands/bs_kick.cpp:1143 +#, fuzzy, c-format +msgid "%s (minimum %d/%d%%)" +msgstr " Κεφαλαία γράμματα με kick : %s (ελάχιστο %d/%d%%)" + +#: modules/commands/cs_access.cpp:245 modules/commands/cs_access.cpp:349 +#: modules/commands/cs_access.cpp:454 modules/commands/cs_access.cpp:467 +#: modules/commands/cs_flags.cpp:295 +#, c-format +msgid "%s access list is empty." +msgstr "Η λίστα του %s access list είναι άδεια." + +#: modules/commands/ns_ajoin.cpp:184 +#, fuzzy, c-format +msgid "%s added to %s's auto join list." +msgstr "Το #%s# προσθέθηκε επιτυχώς στην autojoin λίστα σας." + +#: src/xline.cpp:389 +#, fuzzy, c-format +msgid "%s already exists." +msgstr "Το Bot #%s# υπάρχει ήδη." + +#: modules/commands/cs_akick.cpp:202 modules/commands/cs_akick.cpp:387 +#: modules/commands/cs_akick.cpp:400 +#, c-format +msgid "%s autokick list is empty." +msgstr "H autokick list του %s είναι άδεια." + +#: modules/commands/bs_badwords.cpp:198 modules/commands/bs_badwords.cpp:316 +#, c-format +msgid "%s bad words list is empty." +msgstr "Η λίοστα των κακών λέξεων του %s είναι άδεια." + +#: modules/commands/cs_set.cpp:993 +#, fuzzy, c-format +msgid "%s cannot be the successor on channel %s as they are the founder." +msgstr "" +"%s δεν μπορεί να είναι successor στο κανάλι %s γιατί είναι founder σε αυτό." + +#: modules/pseudoclients/global.cpp:90 modules/pseudoclients/hostserv.cpp:78 +#: modules/pseudoclients/operserv.cpp:287 +#, c-format +msgid "%s commands:" +msgstr "Οι εντολές του %s είναι::" + +#: include/language.h:69 +#, c-format +msgid "%s coverage is too wide; Please use a more specific mask." +msgstr "" + +#: modules/commands/ms_info.cpp:94 +#, c-format +msgid "%s currently has %d memos, of which %d are unread." +msgstr "%s έχεις #%d# μηνύματα, εκ των οποίων #%d# δεν έχουν διαβαστεί." + +#: modules/commands/ms_info.cpp:92 +#, c-format +msgid "%s currently has %d memos, of which 1 is unread." +msgstr "%s έχεις #%d# μηνύματα, εκ των οποίων #1# δεν έχει διαβαστεί." + +#: modules/commands/ms_info.cpp:90 +#, c-format +msgid "%s currently has %d memos." +msgstr "%s έχεις #%d# μηνύματα." + +#: modules/commands/ms_info.cpp:88 +#, c-format +msgid "%s currently has %d memos; all of them are unread." +msgstr "%s έχεις #%d# μηνύματα; εκ των οποίων όλα δεν έχουν διαβαστεί." + +#: modules/commands/ms_info.cpp:77 +#, c-format +msgid "%s currently has 1 memo, and it has not yet been read." +msgstr "%s έχεις #1# μήνυμα, και δεν το έχεις διαβάσει ακόμα." + +#: modules/commands/ms_info.cpp:79 +#, c-format +msgid "%s currently has 1 memo." +msgstr "%s έχεις #1# μήνυμα.." + +#: modules/commands/ms_info.cpp:73 +#, c-format +msgid "%s currently has no memos." +msgstr "%s δεν έχεις κανένα μήνυμα." + +#: modules/commands/os_forbid.cpp:344 +#, c-format +msgid "%s deleted from the %s forbid list." +msgstr "#%s# διαγράφτηκε από την λίστα των κακών λέξεων απο το %s." + +#: include/language.h:105 +#, fuzzy, c-format +msgid "%s for %s set to %s." +msgstr "Η vhost για τον #%s# έγινε #%s#." + +#: include/language.h:106 +#, fuzzy, c-format +msgid "%s for %s unset." +msgstr "Ο Successor του #%s# δεν έχει οριστεί." + +#: modules/commands/ns_ajoin.cpp:176 +#, c-format +msgid "%s had an invalid key specified, and was thus ignored." +msgstr "" + +#: modules/commands/ms_info.cpp:111 +#, c-format +msgid "%s has no memo limit." +msgstr "%s δεν έχεις όριο μηνυμάτων." + +#: include/language.h:115 +#, c-format +msgid "%s has no memos." +msgstr "%s δεν έχεις όριο μηνυμάτων." + +#: include/language.h:118 +#, c-format +msgid "%s has no new memos." +msgstr "%s δεν έχεις όριο μηνυμάτων." + +#: modules/commands/ns_info.cpp:53 +#, c-format +msgid "%s is %s" +msgstr "%s είναι %s" + +#: modules/commands/ns_info.cpp:59 +#, fuzzy, c-format +msgid "%s is a Services Operator of type %s." +msgstr "%s είναι services operator τού τύπου %s." + +#: modules/commands/cs_seen.cpp:281 +#, c-format +msgid "%s is a client on services." +msgstr "%s είναι ήση μέσα στο δίκτυο." + +#: modules/commands/cs_seen.cpp:200 +#, fuzzy, c-format +msgid "%s is a network service." +msgstr "%s είναι ήση μέσα στο δίκτυο." + +#: src/xline.cpp:407 +#, fuzzy, c-format +msgid "%s is already covered by %s." +msgstr "#%s# έχει ήδη καλυφθεί από τον %s." + +#: modules/commands/ns_ajoin.cpp:170 +#, fuzzy, c-format +msgid "%s is already on %s's auto join list." +msgstr "#%s# είναι ήδη στη λίστα αγνόησης σου" + +# +#: modules/commands/ns_info.cpp:56 +#, fuzzy, c-format +msgid "%s is an unconfirmed nickname." +msgstr "Αυτό το ψευδώνυμο δεν είναι επιβεβαιωμένο." + +#: modules/commands/cs_flags.cpp:432 +#, c-format +msgid "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." +msgstr "" + +#: modules/commands/ns_info.cpp:74 +#, c-format +msgid "%s is currently online." +msgstr "Ο %s είναι για την ώρα off." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is disabled" +msgstr "%s έχει απενεργοποιηθεί." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is enabled" +msgstr "%s έχει απενεργοποιηθεί." + +#: modules/commands/os_dns.cpp:507 +#, fuzzy, c-format +msgid "%s is not a valid IP address." +msgstr "#%s# δεν είναι σωστός τύπος ban" + +#: modules/commands/cs_log.cpp:167 modules/commands/cs_log.cpp:192 +#, fuzzy, c-format +msgid "%s is not a valid command." +msgstr "#%s# δεν είναι σωστός τύπος ban" + +#: modules/commands/cs_log.cpp:198 +#, fuzzy, c-format +msgid "%s is not a valid logging method." +msgstr "#%s# δεν είναι σωστός τύπος ban" + +#: modules/commands/ms_info.cpp:124 +#, c-format +msgid "%s is not notified of new memos." +msgstr "%s δεν θα ειδοποιηθεί για νέα μηνύματα." + +#: modules/commands/ms_info.cpp:118 +#, c-format +msgid "%s is notified of new memos at logon and when they arrive." +msgstr "%s θα παρατηρηθεί για νέα μηνύματα στο logon και όταν θα φτάσουν." + +#: modules/commands/ms_info.cpp:122 +#, c-format +msgid "%s is notified of new memos at logon." +msgstr "%s θα παρατηρηθεί για νέα μηνύματα στο logon." + +#: modules/commands/ms_info.cpp:120 +#, c-format +msgid "%s is notified when new memos arrive." +msgstr "%s θα παρατηρηθεί όταν τα νέα μηνύματα θα φτάσουν." + +#: modules/commands/cs_seen.cpp:232 +#, c-format +msgid "%s is on the channel right now (as %s)!" +msgstr "" + +#: modules/commands/cs_seen.cpp:221 +#, fuzzy, c-format +msgid "%s is on the channel right now!" +msgstr "Τα #%s# απενεργοποιήθηκαν στο κανάλι %s." + +#: modules/commands/cs_xop.cpp:434 +#, fuzzy, c-format +msgid "%s list for %s" +msgstr "Λίστα πρόσβασης για #%s#:" + +#: modules/commands/os_sxline.cpp:69 modules/commands/os_sxline.cpp:113 +#, fuzzy, c-format +msgid "%s list is empty." +msgstr "Η %s %s λίστα είναι άδεια." + +#: modules/commands/cs_mode.cpp:376 +#, fuzzy, c-format +msgid "%s locked on %s." +msgstr "%c%c%s κλειδώθηκε στο %s" + +#: modules/extra/stats/cs_fantasy_stats.cpp:120 +#, fuzzy, c-format +msgid "%s not found." +msgstr "Ο/η #%s# δεν βρέθηκε η θέση στην AOP λίστα του %s." + +#: modules/commands/os_config.cpp:79 +#, c-format +msgid "%s settings:" +msgstr "" + +#: modules/commands/cs_seen.cpp:255 +#, c-format +msgid "%s was last seen here %s ago." +msgstr "" + +#: modules/commands/ns_ajoin.cpp:213 +#, fuzzy, c-format +msgid "%s was not found on %s's auto join list." +msgstr "O #%s# δεν βρέθηκε στην autojoin list" + +#: modules/commands/ns_ajoin.cpp:221 +#, fuzzy, c-format +msgid "%s was removed from %s's auto join list." +msgstr "Ο/η #%s# διαγράφτηκε από την autojoin list" + +#: modules/commands/ms_set.cpp:64 +#, c-format +msgid "%s will not send you any notification of memos." +msgstr "%s δεν θα σου έρχεται καμία παρατήρηση από την υπηρεσία." + +#: modules/commands/ms_set.cpp:42 +#, c-format +msgid "%s will now notify you of memos when they are sent to you." +msgstr "%s θα σου γίνεται ειδοποίηση οτι έρχονται μηνύματα από την υπηρεσία." + +#: modules/commands/ms_set.cpp:30 +#, c-format +msgid "" +"%s will now notify you of memos when you log on and when they are sent to " +"you." +msgstr "" +"%s από τώρα όταν θα κάνεις εντολή logon θα βλέπεις τα μηνύματα που θα σου " +"στέλνουν καθώς θασαι στο δίκτυο." + +#: modules/commands/ms_set.cpp:36 +#, c-format +msgid "%s will now notify you of memos when you log on or unset /AWAY." +msgstr "" +"%s όταν θα κάνεις log on ή θα επανέρχεσαι από away θα λαμβάνεις τα μηνύματα." + +#: modules/commands/bs_bot.cpp:89 +#, c-format +msgid "%s!%s@%s (%s) added to the bot list." +msgstr "%s!%s@%s (%s) προσθέθηκε στη λίστα του bot." + +#: modules/commands/ns_access.cpp:83 +#, fuzzy, c-format +msgid "%s's access list is empty." +msgstr "Η λίστα του %s access list είναι άδεια." + +# +#: modules/commands/ns_ajoin.cpp:96 +#, fuzzy, c-format +msgid "%s's auto join list is empty." +msgstr "H autojoin list του %s είναι άδεια." + +#: modules/commands/ns_ajoin.cpp:111 +#, fuzzy, c-format +msgid "%s's auto join list:" +msgstr "Η λίστα αυτόματης εισόδου σας είναι γεμάτη." + +# +#: modules/commands/ns_cert.cpp:242 +#, fuzzy, c-format +msgid "%s's certificate list is empty." +msgstr "Η access λίστα σας είναι άδεια." + +#: modules/commands/ms_info.cpp:99 modules/commands/ms_info.cpp:106 +#, c-format +msgid "%s's memo limit is %d, and may not be changed." +msgstr "%s's όριο μηνυμάτων είναι #%d#, και δεν μπορεί να αλλαχτεί." + +#: modules/commands/ms_info.cpp:101 modules/commands/ms_info.cpp:108 +#, c-format +msgid "%s's memo limit is %d." +msgstr "Του/της %s's το όριο μηνυμάτων είναι #%d#." + +#: src/misc.cpp:363 +#, c-format +msgid "(%s ago)" +msgstr "" + +#: src/misc.cpp:365 +#, c-format +msgid "(%s from now)" +msgstr "" + +#: modules/commands/os_dns.cpp:244 +msgid "(Split)" +msgstr "" + +#: modules/commands/os_info.cpp:268 +#, c-format +msgid "(by %s on %s) %s" +msgstr "" + +#: modules/commands/cs_access.cpp:710 +#, fuzzy +msgid "(disabled)" +msgstr "%s ενεργοποιήθηκε." + +#: modules/commands/cs_access.cpp:712 +msgid "(founder only)" +msgstr "" + +#: src/misc.cpp:367 +msgid "(now)" +msgstr "" + +#: modules/commands/os_defcon.cpp:168 +msgid "* AKILL any new clients connecting" +msgstr "* AKILL όλους τους χρήστες που συνδέονται." + +#: modules/commands/os_defcon.cpp:158 +#, fuzzy, c-format +msgid "* Force channel modes (%s) to be set on all channels" +msgstr "* Αναγκάζει τα Chan Modes (%s) να ενεργοποιηθούν σε όλα τα κανάλια." + +#: modules/commands/os_defcon.cpp:164 +#, fuzzy +msgid "* Ignore non-opers with a message" +msgstr "* Αγνοεί όλους τους non opers με το μήνυμα" + +#: modules/commands/os_defcon.cpp:162 +#, fuzzy +msgid "* Kill any new clients connecting" +msgstr "* Κάνει Kill όλους τους καινούριους χρήστες που συνδέονται." + +#: modules/commands/os_defcon.cpp:156 +#, fuzzy +msgid "* No mode lock changes" +msgstr "* Καμία αλλαγή στο MLOCK" + +#: modules/commands/os_defcon.cpp:152 +msgid "* No new channel registrations" +msgstr "* Δεν επιτρέπονται καινούριες κατοχυρώσεις καναλιών." + +#: modules/commands/os_defcon.cpp:170 +msgid "* No new memos sent" +msgstr "* Δεν στάλνονται καινούρια memos" + +#: modules/commands/os_defcon.cpp:154 +msgid "* No new nick registrations" +msgstr "* Δεν επιτρέπονται οι κατοχυρώσεις ψευδονύμου." + +#: modules/commands/os_defcon.cpp:166 +msgid "* Silently ignore non-opers" +msgstr "* Αγνοεί όλους τους non-opers" + +#: modules/commands/os_defcon.cpp:160 +#, c-format +msgid "* Use the reduced session limit of %d" +msgstr "* Χρησιμοποιεί το μειωμένο session limit του %d" + +#: modules/commands/cs_seen.cpp:319 +#, c-format +msgid ", but %s mysteriously dematerialized." +msgstr "" + +#: modules/commands/cs_seen.cpp:317 +#, c-format +msgid ". %s is still online." +msgstr "Ο %s είναι για την ώρα off." + +#: include/language.h:87 +msgid "" +msgstr "" + +#: modules/commands/ns_set.cpp:504 +#, fuzzy, c-format +msgid "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." +msgstr "" +" Ένα email ενεργοποίησης στάλθηκε στο #%s#. Ακολουθήστε τις οδηγίες του " +"email για να αλλάξετε την διευθυνση email σας. " + +#: modules/commands/ms_sendall.cpp:45 +msgid "A massmemo has been sent to all registered users." +msgstr "Ένα massmemo στάλθηκε σε όλους τους εγγεγραμμένους χρήστες" + +#: modules/commands/hs_request.cpp:285 +msgid "" +"A memo informing the user will also be sent, which includes the reason for " +"the rejection if supplied." +msgstr "" + +#: modules/commands/hs_request.cpp:229 +msgid "A memo informing the user will also be sent." +msgstr "" + +#: modules/commands/ms_read.cpp:42 +#, c-format +msgid "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." +msgstr "" +"Μια ειδοποίηση στάλθηκε στον/στην %s που τον ενημερώνει οτι έχετε διαβάσει\n" +"το memo του/της." + +#: include/language.h:123 +msgid "A vHost ident must be in the format of a valid ident." +msgstr "" + +#: include/language.h:122 +msgid "A vHost must be in the format of a valid hostname." +msgstr "" + +#: modules/commands/os_ignore.cpp:342 +#, fuzzy +msgid "ADD expiry {nick|mask} [reason]" +msgstr "BAN ##channel# #nick# [#reason#]" + +#: modules/commands/os_oper.cpp:70 +msgid "ADD oper type" +msgstr "" + +# +#: modules/commands/os_info.cpp:102 +#, fuzzy +msgid "ADD target info" +msgstr "^_στόχος^_ ^_κωδικό^_" + +#: modules/commands/os_news.cpp:278 +msgid "ADD text" +msgstr "" + +#: modules/commands/os_session.cpp:523 +msgid "ADD [+expiry] mask limit reason" +msgstr "" + +#: modules/commands/ns_ajoin.cpp:231 +#, fuzzy +msgid "ADD [nickname] channel [key]" +msgstr "CHANKILL [+#expiry#] {##channel#} [#reason#]" + +#: modules/commands/ns_access.cpp:102 +#, fuzzy +msgid "ADD [nickname] mask" +msgstr "DEL ##." + +# +#: modules/commands/ns_cert.cpp:258 +#, fuzzy +msgid "ADD [nickname] [fingerprint]" +msgstr "Ρυθμίζει τον κωδικό του ψευδονύμου." + +#: modules/commands/os_sxline.cpp:659 modules/commands/os_akill.cpp:386 +msgid "ADD [+expiry] mask reason" +msgstr "" + +#: modules/commands/os_sxline.cpp:425 +msgid "ADD [+expiry] mask:reason" +msgstr "" + +#: modules/commands/os_forbid.cpp:157 +msgid "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" +msgstr "" + +#: modules/commands/os_dns.cpp:665 +msgid "ADDIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:663 +msgid "ADDSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:661 +msgid "ADDZONE zone.name" +msgstr "" + +#: modules/commands/cs_akick.cpp:38 +#, c-format +msgid "AKICK ENFORCE for %s complete; %d users were affected." +msgstr "" +"Η AKICK ENFORCE για τον #%s# ολοκληρώθηκε; #%d# χρήστες θα επιρρεαστούν." + +# +#: modules/commands/os_chankill.cpp:21 +msgid "AKILL all users on a specific channel" +msgstr "Κάνει AKILL σε όλους τους χρήστες σε ενα συγκεκριμένο κανάλι" + +#: modules/commands/os_akill.cpp:222 modules/commands/os_akill.cpp:339 +#: modules/commands/os_akill.cpp:353 +msgid "AKILL list is empty." +msgstr "Η λίστα AKILL είναι άδεια." + +#: modules/commands/bs_kick.cpp:1211 modules/commands/bs_kick.cpp:1213 +#: modules/commands/bs_kick.cpp:1216 +#, fuzzy +msgid "AMSG kicker" +msgstr " Kick για AMSG: %s" + +#: modules/commands/ns_alist.cpp:48 +#, fuzzy +msgid "Access" +msgstr "Λίστα πρόσβασης:" + +#: include/language.h:72 +msgid "Access denied." +msgstr "Λίστα πρόσβασης:" + +#: modules/commands/cs_status.cpp:58 +#, fuzzy, c-format +msgid "Access for %s on %s:" +msgstr "Η vhost για τον #%s# έγινε #%s#." + +#: include/language.h:107 +#, c-format +msgid "Access level must be between %d and %d inclusive." +msgstr "Ο βαθμός πρέπει να είναι μεταξύ %d και %d." + +#: modules/commands/cs_access.cpp:108 +msgid "Access level must be non-zero." +msgstr "Η Access level δεν πρέπει να είναι ποτέ στο μηδέν." + +#: modules/commands/cs_access.cpp:694 +#, c-format +msgid "Access level settings for channel %s:" +msgstr "Ο βαθμός access για το κανάλι %s:" + +#: modules/commands/cs_access.cpp:734 +#, c-format +msgid "Access levels for %s reset to defaults." +msgstr "Ο βαθμός Access για το #%s# σβήστηκε στο αρχικό." + +#: modules/commands/cs_access.cpp:439 modules/commands/ns_access.cpp:87 +#, fuzzy, c-format +msgid "Access list for %s:" +msgstr "Λίστα πρόσβασης για #%s#:" + +#: modules/commands/help.cpp:166 +#, c-format +msgid "" +"Access to this command requires the permission %s to be present in your " +"opertype." +msgstr "" +"Η πρόσβαση σε αυτή την εντολή χρειάζεται την άδεια #%s# να υπάρχει στο " +"opertype σας." + +#: modules/commands/ns_cert.cpp:368 modules/commands/ns_cert.cpp:392 +#: modules/commands/ns_identify.cpp:94 +#, c-format +msgid "" +"Account %s has already reached the maximum number of simultaneous logins " +"(%u)." +msgstr "" + +#: modules/commands/cs_set.cpp:683 +msgid "Activate security features" +msgstr "Ενεργοποίηση των στοιχείων ασφάλειας του %s." + +#: modules/commands/hs_request.cpp:227 +msgid "Activate the requested vHost for the given nick." +msgstr "" + +#: modules/commands/hs_on.cpp:55 +#, fuzzy +msgid "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." +msgstr "" +"Syntax: #ON#\n" +"Ενεργοποιεί τη vhost ενός nickname.\n" +"Αν χρησιμοποιήσετε αυτή την εντολή και κάποιος χρήστης σας κάνει /whois\n" +"θα δεί τη vhost αντί για τη πραγματική IP σας." + +# +#: modules/commands/hs_on.cpp:19 +msgid "Activates your assigned vhost" +msgstr "Ενεργοποιεί το vhost σας." + +#: modules/commands/os_info.cpp:243 +msgid "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." +msgstr "" + +#: modules/commands/os_dns.cpp:515 +#, c-format +msgid "Added IP %s to %s." +msgstr "" + +#: modules/commands/os_forbid.cpp:239 +#, c-format +msgid "Added a forbid on %s of type %s to expire on %s." +msgstr "" + +#: modules/commands/os_info.cpp:164 +#, fuzzy, c-format +msgid "Added info to %s." +msgstr "Το μήνυμα στάλθηκε στον #%s#." + +#: modules/commands/os_news.cpp:34 +msgid "Added new logon news item." +msgstr "Προστέθηκε ένας κανονισμός ή πληροφορία στη θέση (#%d)." + +#: modules/commands/os_news.cpp:44 +msgid "Added new oper news item." +msgstr "Προσθέθηκε ένα νέο μήνυμα για τους opers θέση (#%d)." + +#: modules/commands/os_news.cpp:54 +msgid "Added new random news item." +msgstr "Προσθέθηκε ένα νέο μήνυμα στην θέση (#%d)." + +#: modules/commands/os_dns.cpp:395 +#, fuzzy, c-format +msgid "Added server %s." +msgstr "Uplink server: %s" + +#: modules/commands/os_dns.cpp:300 +#, c-format +msgid "Added zone %s." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:257 +msgid "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." +msgstr "" + +#: modules/commands/ns_register.cpp:104 +msgid "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." +msgstr "" +"Επιπλέον οι Services Operators με την άδεια #nickserv/confirm# μπορούν\n" +"αντικαταστήσουν το #passcode# με το όνομα του χρήστη για να γίνει η " +"επιβεβαίωση." + +#: modules/pseudoclients/botserv.cpp:172 +#, fuzzy, c-format +msgid "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" +msgstr "" +"To Bot θα μπεί στο κανάλι όταν είναι τουλάχιστον \n" +"#%d# χρήστες σε αυτό. Επιπλέον όλες οι %s εντολές\n" +"μπορούν να χρησιμοποιηθούν αν το fantasy έχει ενεργοποιηθεί\n" +"με τη χρήση του ονόματος της εντολής και μπροστά το σύμβολο %c." + +#: modules/commands/os_noop.cpp:58 +#, c-format +msgid "All O:lines of %s have been reset." +msgstr "Όλες οι O:lines του #%s# έχουν σβηστεί." + +#: modules/commands/cs_clone.cpp:71 +#, fuzzy, c-format +msgid "All akick entries from %s have been cloned to %s." +msgstr "Όλες οι καταχωρίσεις akick από το #%s# έχουν μεταφερθεί στο #%s#" + +#: modules/commands/help.cpp:57 +#, fuzzy, c-format +msgid "All available commands for %s:" +msgstr "Δεν υπάρχει διαθέσιμη βοήθεια για #%s#." + +#: modules/commands/cs_clone.cpp:96 +#, fuzzy, c-format +msgid "All badword entries from %s have been cloned to %s." +msgstr "Όλες οι καταχωρίσεις badword από το #%s# έχουν μεταφερθεί στο #%s#" + +#: modules/commands/cs_clone.cpp:108 +#, fuzzy, c-format +msgid "All level entries from %s have been cloned into %s." +msgstr "Όλες οι καταχωρίσεις akick από το #%s# έχουν μεταφερθεί στο #%s#" + +#: modules/commands/os_news.cpp:38 +msgid "All logon news items deleted." +msgstr "Όλοι οι κανονισμοί ή οι πληροφορίες διαγράφηκαν." + +#: modules/commands/ms_del.cpp:115 +#, c-format +msgid "All memos for channel %s have been deleted." +msgstr "Όλα τα memos από το κανάλι %s έχουν διαγραφεί." + +#: modules/commands/os_mode.cpp:61 +#, c-format +msgid "All modes cleared on %s." +msgstr "" + +#: modules/commands/ns_register.cpp:258 modules/commands/ns_register.cpp:389 +msgid "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." +msgstr "" + +#: modules/commands/ms_del.cpp:119 +msgid "All of your memos have been deleted." +msgstr "Όλα τα μηνύματα διαγράφηκαν." + +#: modules/commands/os_news.cpp:48 +msgid "All oper news items deleted." +msgstr "Όλα τα νέα για τους opers διαγράφηκαν." + +#: modules/commands/os_noop.cpp:41 +#, fuzzy, c-format +msgid "All operators from %s have been removed." +msgstr "Όλες οι O:lines του #%s# έχουν απομακρυνθεί." + +#: modules/commands/os_news.cpp:58 +msgid "All random news items deleted." +msgstr "Όλα τα μηνύματα διαγράφηκαν." + +#: modules/commands/cs_clone.cpp:211 +#, fuzzy, c-format +msgid "All settings from %s have been cloned to %s." +msgstr "Όλες οι ρυθμίσεις από το #%s# έχουν μεταφερθεί στο #%s#" + +#: modules/commands/cs_sync.cpp:41 +#, c-format +msgid "All user modes on %s have been synced." +msgstr "Όλα τα memos από το κανάλι %s έχουν διαγραφεί." + +#: modules/commands/hs_group.cpp:60 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s." +msgstr "Όλες οι vhosts στο #%s# μεταφέρθηκαν στο #%s#" + +#: modules/commands/hs_group.cpp:58 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s@%s." +msgstr "Όλες οι vhosts στο group #%s# έγιναν #%s#@#%s#" + +#: src/access.cpp:40 +msgid "Allowed to (de)halfop him/herself" +msgstr "" + +#: src/access.cpp:39 +msgid "Allowed to (de)halfop users" +msgstr "" + +#: src/access.cpp:48 +msgid "Allowed to (de)op him/herself" +msgstr "" + +#: src/access.cpp:47 +msgid "Allowed to (de)op users" +msgstr "" + +#: src/access.cpp:50 +msgid "Allowed to (de)owner him/herself" +msgstr "" + +#: src/access.cpp:49 +msgid "Allowed to (de)owner users" +msgstr "" + +#: src/access.cpp:52 +msgid "Allowed to (de)protect him/herself" +msgstr "" + +#: src/access.cpp:51 +msgid "Allowed to (de)protect users" +msgstr "" + +#: src/access.cpp:59 +msgid "Allowed to (de)voice him/herself" +msgstr "" + +#: src/access.cpp:58 +msgid "Allowed to (de)voice users" +msgstr "" + +#: src/access.cpp:27 +msgid "Allowed to assign/unassign a bot" +msgstr "" + +#: src/access.cpp:34 +msgid "Allowed to ban users" +msgstr "" + +# +#: src/access.cpp:56 +#, fuzzy +msgid "Allowed to change channel topics" +msgstr "Ο/η #%s# άλλαξε τα usermodes σας." + +#: src/access.cpp:41 +msgid "Allowed to get full INFO output" +msgstr "" + +#: src/access.cpp:36 +msgid "Allowed to issue commands restricted to channel founders" +msgstr "" + +#: src/access.cpp:33 +msgid "Allowed to modify channel badwords list" +msgstr "" + +#: src/access.cpp:24 +#, fuzzy +msgid "Allowed to modify the access list" +msgstr "#%s# διαγράφηκε από το access list του %s." + +#: src/access.cpp:44 +msgid "Allowed to read channel memos" +msgstr "" + +#: src/access.cpp:54 +#, fuzzy +msgid "Allowed to set channel settings" +msgstr "* Δεν επιτρέπονται καινούριες κατοχυρώσεις καναλιών." + +#: src/access.cpp:57 +msgid "Allowed to unban users" +msgstr "" + +#: src/access.cpp:37 +msgid "Allowed to use GETKEY command" +msgstr "" + +#: src/access.cpp:53 +msgid "Allowed to use SAY and ACT commands" +msgstr "" + +# +#: src/access.cpp:35 +#, fuzzy +msgid "Allowed to use fantasy commands" +msgstr "Να ελλατώνει την χρήση \"βίαιων\" εντολών" + +#: src/access.cpp:26 +#, fuzzy +msgid "Allowed to use the AKICK command" +msgstr "Δεν μπορείτε να χρησιμοποιήσετε αυτή την εντολή." + +#: src/access.cpp:42 +msgid "Allowed to use the INVITE command" +msgstr "" + +#: src/access.cpp:43 +#, fuzzy +msgid "Allowed to use the KICK command" +msgstr "Δεν μπορείτε να χρησιμοποιήσετε αυτή την εντολή." + +#: src/access.cpp:45 +#, fuzzy +msgid "Allowed to use the MODE command" +msgstr "Δεν μπορείτε να χρησιμοποιήσετε αυτή την εντολή." + +#: src/access.cpp:25 +#, fuzzy +msgid "Allowed to view the access list" +msgstr "#%s# διαγράφηκε από το access list του %s." + +#: modules/commands/gl_global.cpp:42 +#, fuzzy, c-format +msgid "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." +msgstr "" +"Σύνταξη: #GLOBAL #μήνυμα##\n" +"\n" +"Επιτρέπει στους IRCops να στέλνουν μυνήματα σε όλους τους χρήστες του \n" +"δικτύου. Το μήνυμα θα στέλνεται από το ψευδώνυμο υπηρεσίας #%s#." + +# +#: modules/commands/os_mode.cpp:133 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." +msgstr "" +"Σύνταξη: #MODE #κανάλι# #modes##\n" +"\n" +"Επιτρέπει στους Services operators να αλλάζουν τα modes κάθε καναλιού.\n" +"Οι παράμετροι είναι ίδιοι σαν της εντολής /MODE.\n" +" \n" +"Μόνο για τους #Services operators#." + +# +#: modules/commands/os_mode.cpp:173 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." +msgstr "" +"Σύνταξη: #MODE #κανάλι# #modes##\n" +"\n" +"Επιτρέπει στους Services operators να αλλάζουν τα modes κάθε καναλιού.\n" +"Οι παράμετροι είναι ίδιοι σαν της εντολής /MODE.\n" +" \n" +"Μόνο για τους #Services operators#." + +#: modules/commands/bs_bot.cpp:352 +#, fuzzy +msgid "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." +msgstr "" +"Σύνταξη: #BOT ADD #ψευδώνυμο# #ID# #host# #πραγματικό όνομα##\n" +" #BOT CHANGE #παλιό-ψευδώνυμοick# #νέο-ψευδώνυμο# [#ID# [#host# " +"[#πραγματικό όνομα#]]]#\n" +" #BOT DEL #ψευδώνυμο##\t \n" +"\n" +"Επιτρέπει μόνο στους Services Operators να δημιουργήσουν, αλλάξουν, και \n" +"να σβήσουν τα bots στα οποία οι χρήστες θα μπορούν να χρησιμοποιήσουν \n" +"στα δικά τους τα κανάλια.\n" +" \n" +"Η εντολή #BOT ADD# προσθέτει ένα botμε το ψευδώνυμο, ID,\n" +"hostname και πραγματικό όνομα. Αν δεν γίνουν οι κατάλληλοι έλεγχοι \n" +"με τις επιλογές, να είστε προσεκτικοί.\n" +"Η εντολή #BOT CHANGE# σας επιτρέπει να αλλάξετε το ψευδώνυμο, ID, hostname\n" +"ή πραγματικό όνομα του bot χωρίς να χρειάζεται να το σβήσετε (και όλες\n" +"οι ρυθμίσεις θα μείνουν).\n" +"Η εντολή #BOT DEL# αφαιρεί το bot από την λίστα bot. \n" +"\n" +"#Σημείωση#: αν φτιάξεις ένα bot που έχει ψευδώνυμο κατοχυρωμένο \n" +"θα διαγραφεί. Επίσης, αν ένας χρήστης χρησιμοποιεί ήδη το ψευδώνυμο\n" +"την ώρα που φτιάχνεις το bot, θα γίνει kill." + +#: modules/commands/os_oline.cpp:56 +#, fuzzy +msgid "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." +msgstr "" +"Syntax: #OLINE #user# #flags##\n" +"\n" +"Επιτρέπει στους #Services Operators# να δώσουν Operflags σε κάποιο χρήστη.\n" +"Τα flags πρέπει να αρχίζουν με \"+\" ή \"-\". Για να\n" +"αφαιρέσετε όλα τα flags πληκτρολογήστε \"-\" αντί για κάποιο flag." + +# +#: modules/commands/os_ignore.cpp:370 +#, fuzzy +msgid "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." +msgstr "" +"Syntax: #IGNORE {ADD|DEL|LIST|CLEAR} [#time#] [#nick#] [#reason#]#\n" +" \n" +"Επιτρέπει στους IRC Opers να κάνουν τα services να αγνοούν ένα nick/host\n" +"για κάποιο χρόνο, μέχρι το επόμενο restart. Η προεπιλογή είναι\n" +"δευτερόλεπτα. Μπορείτε να το ορίσετε με Units.\n" +"Τα units που ισχύουν είναι: #s# για δευτερόλεπτα, #m# για λεπτά \n" +"#h# για ώρες #d# για μέρες. \n" +"Οι συνδιασμοί αυτών των units δεν επιτρέπονται.\n" +"Για μόνιμο ignore πατήστε 0 στο χρόνο.\n" +"Τα #mask# πρέπει να είναι της μορφής user@host\n" +"ή nick!user@host, όλα τα άλλα θεωρούνται ψευδόνυμα.\n" +"Επιτρέπονται τα wildcards.\n" +" \n" +"Οι IRC Operators δεν γίνονται ignore." + +# +#: modules/commands/os_akill.cpp:420 +#, fuzzy +msgid "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Σύνταξη: #AKILL ADD [+#expiry#] #μάσκα# #λόγος##\n" +" #AKILL DEL {#μάσκα# | #θέσεις-νούμερα# | #λίστα#}#\n" +" #AKILL LIST [#μάσκα# | #λίστα#]#\n" +" #AKILL VIEW [#μάσκα# | #λίστα#]#\n" +" #AKILL CLEAR#\n" +"\n" +"Μπορούν οι Services operators να αλλάξουν την λίστα AKILL. Αν\n" +"η μάσκα του χρήστη ταιριάξει με μια από αυτές που περιέχονται στην λίστα " +"AKILL,\n" +"τα Services δεν θα επιτρέψουν στο χρήστη να συνδεθεί με το δίκτυο (server) " +"και \n" +"θα έχει KILL, σε όλους τους servers που είναι μαζί.Δηλ γίνεται προσθήκη\n" +"ban (K-line) για την μάσκα που ταιριάζει στο χρήστη.\n" +" \n" +"Η εντολή #AKILL ADD# προσθέτει το ανάλογο user@host μάσκα στην λίστα AKILL\n" +"με έναν λόγο που πρέπει να δώσετε ωστε ο χρήστης να καταλάβει γιατί είναι " +"AKILL.\n" +"Το #expiry# είναι συγκεκριμένο και επιλέγεται από τα επόμενα, #d# \n" +"(μέρες), #h# (ώρες), ή #m# (λεπτά). Συνδιασμοί (όπως \n" +"#1h30m#) δεν επιτρέπονται . Αν δεν δώσετε το χρόνο \n" +"από default θα είναι σε μέρες (θα είναι #+30# που σημαίνει 30 \n" +"μέρες). Για να προσθέσετε ένα AKILL που να μην λήγει, χρησιμοποιείστε #" +"+0#.\n" +"Αν η usermask ξεκινάει με #+#, ο χρόνος λήξης θα πρέπει να δίνετε\n" +"ακόμα και αν είναι ίδιος με τον default. Ο\n" +"συγκεκριμένος χρόνος λήξης της εντολής AKILL μπορεί να βρεθεί με την εντολή\n" +"#STATS AKILL#.\n" +"\n" +"Η εντολή #AKILL DEL# διαγράφει τη συγκεκριμένη μάσκα από την λίστα. \n" +"AKILL αν υπάρχει. Αν σας δωθεί λίστα με τις θέσεις-νούμερα\n" +"αυτές οι θέσεις θα διαγραφούν. (Κοίτα το παράδειγμα με την εντολή LIST.)\n" +"\n" +"Η εντολή #AKILL LIST# εμφανίζει την λίστα με τα AKILL.\n" +"Αν δίνεται μια συγκεκριμένη μάσκα, θα εμφανιστούν οι θέσεις που αντιστοιχούν " +"σε\n" +"αυτή τη μάσκα. Αν δίνετε η λίστα με τις θέσεις-νούμερα μπορείτε να τις " +"δείτε και \n" +"αλλιώς,\n" +"παράδειγμα:\n" +" #AKILL LIST 2-5,7-9#\n" +" Εμφανίζει τις θέσεις με τα νούμερα 2 εως 5 και 7 \n" +" εως 9 της λίστας AKILL.\n" +" \n" +"Η εντολή #AKILL VIEW# είναι πιο καλύτερη από την #AKILL LIST#, και\n" +"εμφανίζει ποιος συγκεκριμένα έβαλε κάποιον AKILL, την ημερομηνία που έγινε, " +"και\n" +"πότε θα λήξει, όπως και το user@host και τον λόγο.\n" +"Η εντολή _AKILL CLEAR_ καθαρίζει όλες τις θέσεις της λίστας AKILL.\n" +"Μόνο για τους #Services operators#.\t\n" +" " + +#: modules/commands/os_sxline.cpp:436 +msgid "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." +msgstr "" + +#: modules/commands/os_sxline.cpp:670 +msgid "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." +msgstr "" + +#: modules/commands/os_session.cpp:551 +msgid "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." +msgstr "" + +#: modules/commands/os_session.cpp:270 +#, fuzzy +msgid "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." +msgstr "" +"Σύνταξη: #SESSION LIST #threshold##\n" +" #SESSION VIEW #host##\n" +"\n" +"Αφήνει τους επικεφαλείς υπηρεσιών να δουν την λίστα session.\n" +"\n" +"#SESSION LIST# Λίστα με hosts με τουλάχιστον #threshold# sessions.\n" +"Το threshold πρέπει να είναι ένα νούμερο μεγαλύτερο από 1. Αυτό γίνεται \n" +"για να αποφευχθούν ατυχήματα στη λίστα μεγάλων νούμερων μονών session " +"hosts. \n" +"#SESSION VIEW# εμφανίζει αναλυτικές πληροφορίες σχετικά με τα specific\n" +"host - συμεριλαμβανομένου πρόσφατου session μετρητή και session limit.\n" +"Η #μάσκα# πρέπει να μην περιλαμβάνεται σε wildcards.\n" +" \n" +"Κοίτα στο #EXCEPTION# help για περισσότερες πληροφορίες σχετικά με το " +"session\n" +"limiting και για το πως θα κάνεις session limits σε specific hosts και " +"groups.\n" +" \n" +"Μόνο για τους #Επικεφαλείς Υπηρεσιών#." + +#: modules/commands/cs_topic.cpp:193 +msgid "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do " +"not have\n" +"the TOPIC privilege." +msgstr "" + +#: modules/commands/os_kick.cpp:62 +#, c-format +msgid "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" +msgstr "" +"Σύνταξη: #KICK #κανάλι# #χρήστη# #λόγο##\n" +"\n" +"Επιτρέπει στους IRCops να κάνουν kick ε΄να χρήστη από το κανάλι.\n" +"Οι παράμετροι είναι ίδιοι με την εντολή /KICK.\n" +"Το μήνυμα του kick θα έχει το ψευδώνυμο του\n" +"IRCop σαν μια προειδοποίηση; Για παράδειγμα:\n" +"\n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))\n" +"\n" +"Μόνο για τους #Services operators#." + +#: modules/commands/cs_set.cpp:33 +msgid "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" +msgstr "" +"Σύνταξη: #SET #κανάλι# #επιλογή# #παράμετροι##\n" +"\n" +"Επιτρέπουν στον founder του καναλιού να επιλέξει και να ρυθμίσει το κανάλι\n" +"του και άλλες πληροφορίες.\n" +"\n" +"Διαθέσιμες επιλογές:" + +#: modules/commands/os_oper.cpp:250 +msgid "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." +msgstr "" + +#: modules/commands/os_config.cpp:127 +#, fuzzy +msgid "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" +msgstr "" +"Syntax: #CONFIG {#MODIFY#|#VIEW#} [#block name# #item name# #item value#]#\n" +"\n" +"To #CONFIG# επιτρέπει να δείτε και να αλλάξετε τις ρυθμίσεις " +"configuration. \n" +"Οι αλλαγές αυτές δεν αποθηκεύονται μέσα στο configuration αρχείο, και " +"χάνονται αν η Anope γίνει RESTART/SHUT DOWN/RELOADExample:\n" +" #CONFIG MODIFY nickserv forcemail no# \n" + +#: modules/commands/ns_set.cpp:992 +#, fuzzy +msgid "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." +msgstr "" +"Syntax: #SASET #nickname# MSG {ON | OFF}#\n" +"\n" +"Επιτρέπει να διαλέξετε ένα τρόπο με τον οποίο τα services θα επικοινωνούν \n" +"με το χρήστη. Με τη παράμετρο #MSG#, τα Services θα χρησιμοποιούν μηνύματα,\n" +"αλλιώς θα χρησιμοποιούν notices." + +#: modules/commands/ns_set.cpp:966 +#, fuzzy, c-format +msgid "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." +msgstr "" +"Σύνταξη: #SET MSG {ON | OFF}#\n" +"\n" +"Σας επιτρέπει να διαλέξετε το τρόπο με τον οποίο τα Services θα \n" +"επικοινωνούν μαζί σου. Με την εντολή #MSG#, τα Services θα \n" +"χρησιμοποιούν μηνύματα, διαφορετικά θα χρησιμοποιούν παρατηρήσεις \n" +"(notices). " + +#: modules/commands/ms_ignore.cpp:113 +#, fuzzy +msgid "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." +msgstr "" +"Syntax: #IGNORE [#channel#] {#ADD|DEL|LIST#} [#entry#]\n" +" \n" +"Επιτρέπει να αγνοείτε χρήστες με βάση το nick ή τη host τους και δεν θα " +"μπορούν να σας στέλνουν memo.\n" +"Οι χρήστες που σας στέλνουν το memo δεν θα ειδοποιούνται οτι τους έχετε " +"κάνει ignore" + +#: modules/commands/os_kill.cpp:48 +msgid "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." +msgstr "" + +#: modules/commands/ns_info.cpp:252 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Syntax: #SASET #nickname# HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +"#\n" +"\n" +"Επιτρέπει να κάνετε κάποιες πληροφορίες να μη φαίνονται\n" +"όταν κάποιος κάνει ένα %s #INFO# \n" +"σε ένα nick. Μπορείτε να κρύψετε το email (#EMAIL#), τελευταίο\n" +"user@host mask (#USERMASK#), τη πρόσβαση στα services\n" +"(#STATUS#) και το quit message (#QUIT#).\n" +"Η δεύτερη παράμετρος ορίζει αν οι πληροφορίες πρέπει να\n" +"φαίνονται (#OFF#) ή να κρύβονται (#ON#)." + +#: modules/commands/ns_info.cpp:223 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Σύνταξη: #SET HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}#\n" +"\n" +"Σας επιτρέπει να εμποδίσετε την εμφάνιση συγκεκριμένων\n" +"πληροφοριών όταν κάποιος εκτελεί την εντολή του %s #INFO#, στο\n" +"ψευδώνυμό σας. Μπορείτε να αποκρύψετε τη διεύθυνση e-mail\n" +"user@host mask (#USERMASK#), and last quit message (#QUIT#).\n" +"σας (#EMAIL#), την τελευταία διεύθυνση με την οποία συνδεθήκατε\n" +"(#USERMASK#), και το τελευταίο μήνυμα (#QUIT#).\n" +"Η δεύτερη παράμετρος καθορίζει το αν η πληροφορία θα πρέπει\n" +"να εμφανίζεται (#OFF#) ή να αποκρύπτεται (#ON#)." + +# +#: modules/commands/bs_info.cpp:118 +#, fuzzy, c-format +msgid "Allows you to see %s information about a channel or a bot" +msgstr "Επιτρέπει να δείτε πληροφορίες για ένα κανάλι ή ένα bot." + +#: modules/commands/bs_info.cpp:108 +#, c-format +msgid "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." +msgstr "" +"Σύνταξη: #INFO {#κανάλι# | #ψευδώνυμο#}#\n" +"\n" +"Σου επιτρέπει να δεις από το %s πληροφορίες σχετικά με το κανάλι ή το bot.\n" +"Αν η παράμετρος είναι το κανάλι, θα δείς πληροφορίες μόνο αν έχεις\n" +"ενεργοποιη΄σει την επιλογή kickers. Αν η παράμετρος είναι το ψευδώνυμο,\n" +"θα δεις πληροφορίες σχετικά με το bot.\n" +" " + +#: modules/commands/cs_xop.cpp:567 +msgid "" +"Alternative methods of modifying channel access lists are\n" +"available. " +msgstr "" + +# +#: modules/commands/hs_request.cpp:191 +msgid "Approve the requested vHost of a user" +msgstr "Διαγράφει τη vhost ενός χρήστη." + +#: modules/commands/ns_drop.cpp:68 +#, fuzzy +msgid "As a Services Operator, you may drop any nick." +msgstr "%s είναι services operator τού τύπου %s." + +# +#: modules/commands/bs_assign.cpp:19 +msgid "Assigns a bot to a channel" +msgstr "Ζητάτε από το bot να έρθει στο κανάλι σας" + +#: modules/commands/bs_assign.cpp:78 +#, fuzzy +msgid "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." +msgstr "" +"Σύνταξη: #ASSIGN #κανάλι# #ψευδώνυμο##\n" +"\n" +"Με την εντολή αυτή ζητάς από το bot να μπεί στο κανάλι σου. Μπορείς\n" +"μετά να το ρυθμίσεις για τις ανάγκες του καναλιού σου.\n" +" " + +# +#: data/chanserv.example.conf:1197 +#, fuzzy +msgid "Associate a URL with the channel" +msgstr "Ζητάτε από το bot να έρθει στο κανάλι σας" + +#: data/nickserv.example.conf:594 +msgid "Associate a URL with this account" +msgstr "" + +# +#: data/nickserv.example.conf:593 +#, fuzzy +msgid "Associate a URL with your account" +msgstr "Συσχετίζει ένα μήνυμα χαιρετισμού με το ψευδώνυμό σας" + +# +#: modules/commands/greet.cpp:83 +msgid "Associate a greet message with your nickname" +msgstr "Συσχετίζει ένα μήνυμα χαιρετισμού με το ψευδώνυμό σας" + +# +#: data/chanserv.example.conf:1198 +#, fuzzy +msgid "Associate an E-mail address with the channel" +msgstr "Συσχετίζει μία διεύθυνση e-mail με το ψευδώνυμό σας" + +# +#: modules/commands/ns_set.cpp:452 +msgid "Associate an E-mail address with your nickname" +msgstr "Συσχετίζει μία διεύθυνση e-mail με το ψευδώνυμό σας" + +# +#: modules/commands/os_info.cpp:101 +#, fuzzy +msgid "Associate oper info with a nick or channel" +msgstr "Ζητάτε από το bot να έρθει στο κανάλι σας" + +# +#: modules/commands/ns_set.cpp:558 +msgid "Associates the given E-mail address with the nickname." +msgstr "Συσχετίζει μία διεύθυνση e-mail με το ψευδώνυμό σας" + +#: modules/commands/ns_set.cpp:533 +msgid "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." +msgstr "" +"Σύνταξη: #SET EMAIL #διεύθυνση##\n" +"\n" +"Δείχνει την δεύθυνση E-mail που του έχεις δώσει για το ψευδώνυμο σου.\n" +"Αυτή η διεύθυνση θα εμφανίζεται κάθε φορά που κάποιος θα κοιτάζει " +"πληροφορίες\n" +"στο κανάλι με την εντολή #INFO#." + +#: modules/commands/ns_set.cpp:1315 +msgid "Auto-op" +msgstr "Auto-op" + +#: modules/commands/cs_akick.cpp:374 +#, c-format +msgid "Autokick list for %s:" +msgstr "Η Autokick list του %s είναι:" + +#: src/access.cpp:29 +msgid "Automatic channel operator status upon join" +msgstr "" + +#: src/access.cpp:28 +msgid "Automatic halfop upon join" +msgstr "" + +#: src/access.cpp:30 +msgid "Automatic owner upon join" +msgstr "" + +#: src/access.cpp:31 +msgid "Automatic protect upon join" +msgstr "" + +#: src/access.cpp:32 +msgid "Automatic voice on join" +msgstr "" + +#: modules/commands/os_oper.cpp:196 +#, c-format +msgid "Available commands for %s:" +msgstr "" + +# +#: modules/commands/os_oper.cpp:175 +#, fuzzy +msgid "Available opertypes:" +msgstr "Λίστα με διαθέσιμα bots" + +#: modules/commands/os_oper.cpp:218 +#, c-format +msgid "Available privileges for %s:" +msgstr "" + +#: modules/commands/cs_enforce.cpp:162 +msgid "BANS enforced by " +msgstr "" + +#: modules/commands/bs_kick.cpp:1121 modules/commands/bs_kick.cpp:1123 +#: modules/commands/bs_kick.cpp:1126 +#, fuzzy +msgid "Bad words kicker" +msgstr " Κακές λέξεις ώστε να κάνει kick : %s" + +#: modules/commands/bs_badwords.cpp:252 +#, fuzzy, c-format +msgid "Bad words list for %s:" +msgstr "Λίστα πρόσβασης για #%s#:" + +#: modules/commands/bs_badwords.cpp:364 +msgid "Bad words list is now empty." +msgstr "Η λίστα των κακών λέξεων είναι άδεια." + +#: modules/commands/bs_set.cpp:129 +msgid "Ban expiry may not be longer than 1 day." +msgstr "" + +#: modules/commands/cs_ban.cpp:140 modules/commands/cs_ban.cpp:175 +#, fuzzy, c-format +msgid "Ban on %s expires in %s." +msgstr " %s (δεν λήγει ποτέ)" + +#: modules/commands/cs_info.cpp:60 +msgid "Ban type" +msgstr "" + +#: modules/commands/cs_set.cpp:174 +#, c-format +msgid "Ban type for channel %s is now #%d." +msgstr "Ban τύπος του καναλιού %s είναι τώρα #%d." + +# +#: modules/commands/cs_ban.cpp:39 +#, fuzzy +msgid "Bans a given nick or mask on a channel" +msgstr "Κάνει ban ένα συγκεκριμένο ψευδόνυμο σε ένα κανάλι" + +#: modules/commands/cs_ban.cpp:227 +#, fuzzy +msgid "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." +msgstr "" +"Σύνταξη: #BAN ##κανάλι# #ψευδώνυμο# [#λόγος#]#\n" +"\n" +"Κάνει ban το ψευδώνυμο που του δίνεις στο κανάλι.\n" +" \n" +"Από default, χρησιμοποιείται από τους AOPs ή αυτούς που έχουν level 5 " +"access \n" +"και παραπάνω στο κανάλι." + +#: modules/commands/cs_enforce.cpp:166 +#, fuzzy, c-format +msgid "Bans enforced on %s." +msgstr "%c δεν έχει κλειδωθεί στο %s." + +#: modules/commands/bs_kick.cpp:1131 modules/commands/bs_kick.cpp:1133 +#: modules/commands/bs_kick.cpp:1136 +#, fuzzy +msgid "Bolds kicker" +msgstr " Έντονη χαρακτήρες με kick : %s" + +#: modules/commands/bs_bot.cpp:26 modules/commands/bs_bot.cpp:175 +#, c-format +msgid "Bot %s already exists." +msgstr "Το Bot #%s# υπάρχει ήδη." + +#: include/language.h:119 +#, fuzzy, c-format +msgid "Bot %s does not exist." +msgstr " %s (δεν λήγει ποτέ)" + +#: modules/commands/bs_assign.cpp:71 modules/commands/bs_assign.cpp:246 +#, c-format +msgid "Bot %s has been assigned to %s." +msgstr "Το Bot #%s# θα μπει στο %s." + +#: modules/commands/bs_bot.cpp:228 +#, fuzzy, c-format +msgid "Bot %s has been changed to %s!%s@%s (%s)." +msgstr "Bot #%s# άλλαξε σε %s!%s@%s (%s)" + +#: modules/commands/bs_bot.cpp:262 +#, c-format +msgid "Bot %s has been deleted." +msgstr "Bot #%s# διαγράφηκε." + +#: modules/commands/bs_assign.cpp:63 modules/commands/bs_assign.cpp:241 +#, c-format +msgid "Bot %s is already assigned to channel %s." +msgstr "Το Bot #%s# υπάρχει ήδη στο κανάλι #%s#." + +#: modules/commands/bs_kick.cpp:832 +#, c-format +msgid "Bot will kick ops on channel %s." +msgstr "Το Bot #θα κάνει kick τους ops# του καναλιού %s." + +#: modules/commands/bs_kick.cpp:897 +#, c-format +msgid "Bot will kick voices on channel %s." +msgstr "Το Bot #θα κάνει kick τους voices# του καναλιού %s." + +#: modules/commands/bs_kick.cpp:824 +#, c-format +msgid "Bot won't kick ops on channel %s." +msgstr "Το Bot #δεν θα κάνει kick τουε ops# του καναλιού %s." + +#: modules/commands/bs_kick.cpp:889 +#, c-format +msgid "Bot won't kick voices on channel %s." +msgstr "Το Bot #δεν θα κάνει kick τους voices# του καναλιού %s." + +#: modules/commands/bs_bot.cpp:118 +#, fuzzy, c-format +msgid "Bot %s is not changeable." +msgstr "Κανένα Bot έχει επιλογή #ON# στο κανάλι %s." + +#: modules/commands/bs_bot.cpp:254 +#, fuzzy, c-format +msgid "Bot %s is not deletable." +msgstr "Bot #%s# διαγράφηκε." + +#: modules/commands/bs_set.cpp:141 +#, c-format +msgid "Bot bans will automatically expire after %s." +msgstr "" + +#: modules/commands/bs_set.cpp:139 +#, fuzzy +msgid "Bot bans will no longer automatically expire." +msgstr "Τα services δεν θα δίνουν πια autoop στον %s στα κανάλια." + +#: modules/commands/bs_bot.cpp:46 modules/commands/bs_bot.cpp:138 +#, fuzzy, c-format +msgid "Bot hosts may only be %d characters long." +msgstr "Οι Hosts των Bots μπορούν να περιέχουν μόνο %d χαρακτήρες." + +#: modules/commands/bs_bot.cpp:64 modules/commands/bs_bot.cpp:167 +#, fuzzy +msgid "Bot hosts may only contain valid host characters." +msgstr "Οι hosts των bots μπορούν να περιέχουν μόνο έγκυρους χαρακτήρες." + +#: modules/commands/bs_bot.cpp:40 modules/commands/bs_bot.cpp:132 +#, fuzzy, c-format +msgid "Bot idents may only be %d characters long." +msgstr "Οι idents των bots μπορούν να περιέχουν μόνο %d χαρακτήρες." + +#: modules/commands/bs_bot.cpp:58 modules/commands/bs_bot.cpp:161 +#, fuzzy +msgid "Bot idents may only contain valid ident characters." +msgstr "Οι Idents των bots μπορούν να περιέχουν μόνο έγκυρους χαρακτήρες." + +#: include/language.h:121 +#, fuzzy, c-format +msgid "Bot is not on channel %s." +msgstr "Το Bot #θα κάνει kick τους ops# του καναλιού %s." + +#: modules/commands/bs_botlist.cpp:51 +msgid "Bot list:" +msgstr "Bot λίστα:" + +#: modules/commands/bs_info.cpp:87 +msgid "Bot nick" +msgstr "" + +#: modules/commands/bs_bot.cpp:34 modules/commands/bs_bot.cpp:126 +#, fuzzy, c-format +msgid "Bot nicks may only be %d characters long." +msgstr "Οι idents των bots μπορούν να περιέχουν μόνο %d χαρακτήρες." + +#: modules/commands/bs_bot.cpp:52 modules/commands/bs_bot.cpp:155 +#, fuzzy +msgid "Bot nicks may only contain valid nick characters." +msgstr "Τα ψευδόνυμα των bots μπορούν να περιέχουν μόνο έγκυρους χαρακτήρες." + +#: modules/commands/bs_kick.cpp:225 +#, fuzzy, c-format +msgid "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." +msgstr "" +"Bot will now kick #italics#, and will place a ban after %d\n" +"kicks for the same user." + +#: modules/commands/bs_kick.cpp:228 +#, fuzzy, c-format +msgid "Bot will now kick for %s." +msgstr "Το Bot θα κάνει τώρα kick #έντονους χαρακτήρες#." + +#: modules/commands/bs_kick.cpp:416 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." +msgstr "" +"Το Bot θα κάνει kick #κεφαλαία# (πρέπει να είναι τουλάχιστον\n" +"%d χαρακτήρες και %d%% από το μήνυμα), και θα \n" +"γίνει ban μετά από %d kicks για τον ίδιο χρήστη." + +#: modules/commands/bs_kick.cpp:420 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." +msgstr "" +"Το Bot θα κάνει kick #κεφαλαία# (πρέπει να είναι τουλάχιστον\n" +"%d χαρακτήρες και %d%% από το μήνυμα)." + +#: modules/commands/bs_kick.cpp:551 +#, fuzzy, c-format +msgid "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." +msgstr "" +"Το Bot θα κάνει kick #για επαναλήψεις# (%d γραμμές σε %d δευτερόλεπτα), " +"και \n" +"θα κάνει ban μετά από %d kicks για τον ίδιο χρήστη." + +#: modules/commands/bs_kick.cpp:554 +#, fuzzy, c-format +msgid "Bot will now kick for flood (%d lines in %d seconds)." +msgstr "" +"Το Bot θα κάνει kick #για επαναλήψεις# (%d γραμμές σε %d δευτερόλεπτα)." + +#: modules/commands/bs_kick.cpp:677 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Το Bot θα κάνει kick #για επαναλήψεις# (χρήστες που λένε %d φορές\n" +"το ίδιο πράγμα), και θα γίνεται ban μετά από %d \n" +"kicks για τον ίδιο χρήστη." + +#: modules/commands/bs_kick.cpp:687 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." +msgstr "" +"Το Bot θα κάνει kick #για επαναλήψεις# (χρήστες που λένε %d φορές\n" +"το ίδιο πράγμα)." + +#: modules/commands/bs_kick.cpp:673 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Το Bot θα κάνει kick #για επαναλήψεις# (χρήστες που λένε %d φορές\n" +"το ίδιο πράγμα), και θα γίνεται ban μετά από %d \n" +"kicks για τον ίδιο χρήστη." + +#: modules/commands/bs_kick.cpp:684 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." +msgstr "" +"Το Bot θα κάνει kick #για επαναλήψεις# (χρήστες που λένε %d φορές\n" +"το ίδιο πράγμα)." + +#: modules/commands/bs_kick.cpp:239 +#, fuzzy, c-format +msgid "Bot won't kick for %s anymore." +msgstr "Το Bot δεν θα κάνει kick #κεφαλαία# πλέον." + +#: modules/commands/bs_kick.cpp:426 +#, fuzzy +msgid "Bot won't kick for caps anymore." +msgstr "Το Bot δεν θα κάνει kick #κεφαλαία# πλέον." + +#: modules/commands/bs_kick.cpp:559 +#, fuzzy +msgid "Bot won't kick for flood anymore." +msgstr "Το Bot δεν θα κάνει kick #για επαναλήψεις# πλέον." + +#: modules/commands/bs_kick.cpp:694 +#, fuzzy +msgid "Bot won't kick for repeats anymore." +msgstr "Το Bot δεν θα κάνει kick #για επαναλήψεις# πλέον." + +#: modules/commands/cs_access.cpp:472 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_session.cpp:514 +msgid "By" +msgstr "" + +#: modules/commands/os_info.cpp:104 +msgid "CLEAR target" +msgstr "" + +#: modules/commands/cs_seen.cpp:119 +msgid "CLEAR time" +msgstr "" + +# +#: modules/commands/ms_cancel.cpp:19 +msgid "Cancel the last memo you sent" +msgstr "Ακυρώνει το τελευταίο μήνυμα που στέλνετε" + +# +#: modules/commands/cs_drop.cpp:19 +msgid "Cancel the registration of a channel" +msgstr "Ακυρώνει την κατοχύρωση ενός καναλιού" + +# +#: modules/commands/ns_drop.cpp:20 +msgid "Cancel the registration of a nickname" +msgstr "Διαγράφει ένα ψευδώνυμο" + +#: modules/commands/ms_cancel.cpp:84 +msgid "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." +msgstr "" +"Σύνταξη: #CANCEL {#ψευδώνυμο# | #κανάλι#}#\n" +"\n" +"Ακυρώνει το τελευταίο μήνυμα που στείλατε στον παραλείπτη ή το κανάλι,\n" +"με την προυπόθεση οτι δεν έχει διαβαστεί,γιατί η εντολή τότε θα είναι σαν " +"να\n" +"μην έγινε." + +#: modules/commands/cs_clone.cpp:149 +#, fuzzy, c-format +msgid "Cannot clone channel %s to itself!" +msgstr "Το Bot #θα κάνει kick τους ops# του καναλιού %s." + +#: modules/commands/ns_register.cpp:332 +msgid "Cannot send mail now; please retry a little later." +msgstr "" +"Δεν μπορεί να σταλεί στη διεύθυνση το μήνυμα για την ώρα; παρακαλώ " +"προσπάθησε λίγο αργότερα." + +#: modules/commands/bs_kick.cpp:1141 modules/commands/bs_kick.cpp:1143 +#: modules/commands/bs_kick.cpp:1146 +#, fuzzy +msgid "Caps kicker" +msgstr " Κεφαλαία γράμματα με kick : %s" + +#: modules/commands/os_shutdown.cpp:34 +msgid "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." +msgstr "" +"Σύνταξη: #QUIT#\n" +"\n" +"Έχει ως αποτέλεσμα τα Services να κλείσουν αμέσως(να τερματιστούν); οι " +"βάσεις\n" +"δεδομένων #δεν# γράφονται(δεν σώζονται). Αυτή η εντολή δεν πρέπει να\n" +"χρησιμοποιείται εκτός και αν υπάρχει βλάβη στην μνήμη των databases\n" +"και δεν γίνεται να γραφτούν(δεν γίνεται να γίνουν save).\n" +"Για κανονικό τερματισμό, κάντε την εντολή #SHUTDOWN#.\n" +" \n" +"Μόνο για τους #Services Operators#." + +#: modules/commands/os_reload.cpp:47 +#, fuzzy +msgid "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." +msgstr "" +"Σύνταξη: #RELOAD#\n" +"\n" +"Έχει ως αποτέλεσμα τα Services να επαναφορτώνουν το configuration αρχείο.\n" +"Σημείωση οτι μερικές επιλογές για να έχουν αποτέλεσμα χρειάζονται " +"επανεκκίνηση\n" +"των Services (όπως Services' ψευδώνυμα, ενεργοποίηση της session \n" +"limitation, κλπ.)\n" +" \n" +"Μόνο για τους #Services Operators#." + +#: modules/commands/os_shutdown.cpp:62 +msgid "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." +msgstr "" +"Σύνταξη: #RESTART#\n" +"\n" +"Έχει ως αποτέλεσμα τα Services να γράψουν όλη την βάση δεδομένων και να\n" +"επανεκκινηθούν (δηλ να κλείσουν και αμέσως να \n" +"ξανατρεχτεί το εκτελέσιμο αρχείο).\n" +"\n" +"Μόνο για τους #Services Operators#.\t" + +#: modules/commands/os_shutdown.cpp:89 +msgid "Causes Services to save all databases and then shut down." +msgstr "" +"Σύνταξη: #SHUTDOWN#\n" +"\n" +"Έχει ως αποτέλεσμα τα Services να γράψουν όλη την βάση δεδομένων και να \n" +"τερματιστούν.\n" +"\n" +"Μόνο για τους #Services Operators#." + +#: modules/commands/os_update.cpp:34 +msgid "" +"Causes Services to update all database files as soon as you\n" +"send the command." +msgstr "" +"Σύνταξη: #UPDATE#\n" +"\n" +"Έxei ως αποτέλεσμα τα Services να κάνουν update σε όλες τις βάσεις " +"δεδομένων\n" +"το συντομότερο που κάνετε αυτή την εντολή.\n" +" \n" +"Μόνο για τους #Services Operators#." + +#: modules/commands/ns_cert.cpp:246 +#, fuzzy, c-format +msgid "Certificate list for %s:" +msgstr "Λίστα πρόσβασης για #%s#:" + +#: modules/commands/cs_set.cpp:528 modules/commands/cs_set.cpp:570 +msgid "ChanServ is required to enable persist on this network." +msgstr "" + +# +#: modules/commands/os_mode.cpp:19 +msgid "Change channel modes" +msgstr "Ο/η #%s# άλλαξε τα usermodes σας." + +# +#: modules/commands/ns_set.cpp:905 +msgid "Change the communication method of Services" +msgstr "Αλλάζει την μέθοδο επικοινωνίας με τις υπηρεσίες" + +# +#: modules/commands/os_mode.cpp:146 +#, fuzzy +msgid "Change user modes" +msgstr "Ο/η #%s# άλλαξε τα usermodes σας." + +#: modules/commands/os_mode.cpp:161 +#, fuzzy, c-format +msgid "Changed usermodes of %s to %s." +msgstr "Τα usermodes του #%s# άλλαξαν." + +#: modules/commands/ns_set.cpp:411 +#, fuzzy +msgid "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." +msgstr "" +"Σύνταξη: #SET DISPLAY #νέο-display##\n" +"\n" +"Βλέπεις στη λίστα το ψευδώνυμο σου σε ποια ομάδα είναι των \n" +"υπηρεσιών. Στη λίστα πρέπει να είναι το ψευδώνυμο που είναι στην ομάδα." + +#: modules/commands/ns_set.cpp:387 +#, fuzzy +msgid "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." +msgstr "" +"Σύνταξη: #SET DISPLAY #νέο-display##\n" +"\n" +"Βλέπεις στη λίστα το ψευδώνυμο σου σε ποια ομάδα είναι των \n" +"υπηρεσιών. Στη λίστα πρέπει να είναι το ψευδώνυμο που είναι στην ομάδα." + +#: modules/commands/cs_set.cpp:324 +msgid "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." +msgstr "" +"Σύνταξη: #%s #κανάλι# FOUNDER #ψευδώνυμο##\n" +"\n" +"Αλλάζει τον founder του καναλιού. Το νέο ψευδώνυμο πρέπει να είναι\n" +"κατοχυρωμένο." + +# +#: modules/commands/ns_set.cpp:884 +msgid "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Σύνταξη: #SET LANGUAGE #νούμερο##\n" +"\n" +"Αλλάζει την γλώσσα των υπηρεσιών που στέλνει με μηνύματα σε σένα\n" +"(για παράδειγμα, όταν ανταποκρίνεσαι σε μια εντολή θα σου στείλει σε άλλη " +"γλώσσα).\n" +"Το #νούμερο# πρέπει να είναι ένα από τα επόμενα που υπάρχουν στην λίστα\n" +"υποστηριζόμενων γλωσσών:" + +# +#: modules/commands/ns_set.cpp:848 +msgid "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Σύνταξη: #SET LANGUAGE #νούμερο##\n" +"\n" +"Αλλάζει την γλώσσα των υπηρεσιών που στέλνει με μηνύματα σε σένα\n" +"(για παράδειγμα, όταν ανταποκρίνεσαι σε μια εντολή θα σου στείλει σε άλλη " +"γλώσσα).\n" +"Το #νούμερο# πρέπει να είναι ένα από τα επόμενα που υπάρχουν στην λίστα\n" +"υποστηριζόμενων γλωσσών:" + +#: modules/commands/ns_set.cpp:227 +msgid "Changes the password used to identify as the nick's owner." +msgstr "" +"Σύνταξη: #SET PASSWORD #νέος-κωδικός##\n" +"\n" +"Αλλάζει τον κωδικό που χρησιμοποιείς για την εντολή αναγνώρισης του κάτοχου\n" +"ψευδώνυμου." + +#: modules/commands/ns_set.cpp:161 +msgid "" +"Changes the password used to identify you as the nick's\n" +"owner." +msgstr "" +"Σύνταξη: #SET PASSWORD #νέος-κωδικός##\n" +"\n" +"Αλλάζει τον κωδικό που χρησιμοποιείς για την εντολή αναγνώρισης του κάτοχου\n" +"ψευδώνυμου." + +#: modules/commands/cs_set.cpp:1017 +#, fuzzy +msgid "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." +msgstr "" +"Σύνταξη: #%s #κανάλι# SUCCESSOR #ψευδώνυμο##\n" +"\n" +"Αλλάζει τον successor του καναλιού. Αν το ψευδώνυμο του founder\n" +"λήξει ή σβηστεί (drop) τότε το κανάλι θα είναι ακόμα κατοχυρωμένο.\n" +"Ο successor θα γίνει ο νέος founder του καναλιού.\n" +"Αν όμως, ο successor έχει κατοχυρώσει πολλά κανάλια,\n" +"αν δηλ έχει (%d), το κανάλι θα σβηστεί,σαν να μην είχε οριστεί\n" +"successor. Το νέο ψευδώνυμο θα πρέπει να είναι κατοχυρωμένο." + +#: modules/commands/ns_alist.cpp:48 modules/commands/ns_ajoin.cpp:100 +#, fuzzy +msgid "Channel" +msgstr "DROP #channel#" + +#: include/language.h:84 +#, c-format +msgid "Channel %s doesn't exist." +msgstr "Το κανάλι #%s# είναι πλέον μόνιμο." + +#: modules/commands/cs_drop.cpp:63 +#, c-format +msgid "Channel %s has been dropped." +msgstr "Το κανάλι #%s# διαγράφτηκε από τις υπηρεσίες." + +#: modules/commands/cs_getkey.cpp:43 +#, fuzzy, c-format +msgid "Channel %s has no key." +msgstr "Το κανάλι #%s# δεν έχει key." + +#: modules/commands/cs_register.cpp:47 +#, c-format +msgid "Channel %s is already registered!" +msgstr "Το κανάλι #%s# είναι ήδη κατοχυρωμένο!" + +#: modules/commands/os_forbid.cpp:524 +#, fuzzy, c-format +msgid "Channel %s is forbidden by %s: %s" +msgstr "Αυτό το κανάλι δεν μπορεί να χρησιμοποιηθεί." + +#: modules/commands/os_forbid.cpp:526 +#, fuzzy, c-format +msgid "Channel %s is forbidden." +msgstr "Το κανάλι #%s# δεν είναι πλέον μόνιμο." + +#: modules/commands/cs_set.cpp:580 +#, c-format +msgid "Channel %s is no longer persistent." +msgstr "Το κανάλι #%s# δεν είναι πλέον μόνιμο." + +#: modules/commands/cs_set.cpp:542 +#, c-format +msgid "Channel %s is now persistent." +msgstr "Το κανάλι #%s# δεν είναι πλέον μόνιμο." + +#: modules/commands/cs_suspend.cpp:180 +#, c-format +msgid "Channel %s is now released." +msgstr "Το κανάλι #%s# έγινε release" + +#: modules/commands/cs_suspend.cpp:125 +#, c-format +msgid "Channel %s is now suspended." +msgstr "Το κανάλι #%s# έγινε suspend." + +#: include/language.h:83 +#, c-format +msgid "Channel %s isn't registered." +msgstr "Το κανάλι #%s# δεν μπορεί να κατοχυρωθεί." + +#: modules/commands/cs_suspend.cpp:172 +#, fuzzy, c-format +msgid "Channel %s isn't suspended." +msgstr "Το κανάλι #%s# έγινε suspend." + +#: modules/commands/cs_register.cpp:68 +#, fuzzy, c-format +msgid "Channel %s registered under your account: %s" +msgstr "Αυτό το ψευδώνυμο #%s# κατοχυρώθηκε υπό την διεύθυνσή σου: %s" + +#: modules/commands/cs_set.cpp:1078 +#, c-format +msgid "Channel %s will expire." +msgstr "Το κανάλι %s #θα# λήξει." + +#: modules/commands/cs_set.cpp:1072 +#, c-format +msgid "Channel %s will not expire." +msgstr "Το κανάλι %s #δεν θα# λήξει." + +#: modules/commands/cs_xop.cpp:475 +#, c-format +msgid "Channel %s %s list has been cleared." +msgstr "Η λίστα του %s %s καναλιού έχει σβηστεί." + +#: modules/commands/cs_access.cpp:486 modules/commands/cs_flags.cpp:361 +#, c-format +msgid "Channel %s access list has been cleared." +msgstr "Η λίστα access του %s καναλιού έχει σβηστεί." + +#: modules/commands/cs_akick.cpp:428 +#, c-format +msgid "Channel %s akick list has been cleared." +msgstr "Η λίστα akick του %s καναλιού έχει σβηστεί." + +#: modules/commands/cs_mode.cpp:444 +#, c-format +msgid "Channel %s has no mode locks." +msgstr "Το κανάλι %s δεν έχει πια mode locks." + +#: include/language.h:82 +#, c-format +msgid "Channel %s is currently suspended." +msgstr "Το κανάλι #%s# έγινε suspend." + +#: include/language.h:101 +#, c-format +msgid "Channel %s is not a valid channel." +msgstr "#%s# δεν είναι σωστός τύπος ban" + +# +#: modules/commands/os_list.cpp:70 +#, fuzzy +msgid "Channel list:" +msgstr "Bot λίστα:" + +#: modules/extra/stats/cs_fantasy_stats.cpp:148 +#, fuzzy, c-format +msgid "Channel stats for %s on %s:" +msgstr "" +"Κανάλια στα οποία ο/η #%s# έχει access:\n" +" Num Channel Level Description " + +#: modules/commands/cs_access.cpp:142 modules/commands/cs_flags.cpp:97 +#: modules/commands/cs_xop.cpp:139 +#, fuzzy +msgid "Channels may not be on access lists." +msgstr "Ο/η #%s# δεν βρέθηκε στην access list του %s" + +#: modules/commands/ns_alist.cpp:114 +#, fuzzy, c-format +msgid "Channels that %s has access on:" +msgstr "" +"Κανάλια στα οποία ο/η #%s# έχει access:\n" +" Num Channel Level Description " + +#: modules/commands/os_stats.cpp:181 +#, c-format +msgid "Channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:517 +#: modules/extra/stats/m_chanstats.cpp:525 +msgid "Chanstats" +msgstr "" + +# +#: modules/extra/stats/m_chanstats.cpp:102 +#, fuzzy, c-format +msgid "Chanstats statistics are now disabled for %s" +msgstr "Ενεργοποιεί/απενεργοποιεί τη λειτουργία ασφάλειας ψευδώνυμου" + +#: modules/extra/stats/m_chanstats.cpp:51 +msgid "Chanstats statistics are now disabled for this channel." +msgstr "" + +# +#: modules/extra/stats/m_chanstats.cpp:104 +#, fuzzy +msgid "Chanstats statistics are now disabled for your nick." +msgstr "Ενεργοποιεί/απενεργοποιεί τη λειτουργία ασφάλειας ψευδώνυμου" + +# +#: modules/extra/stats/m_chanstats.cpp:93 +#, fuzzy, c-format +msgid "Chanstats statistics are now enabled for %s" +msgstr "Ενεργοποιεί/απενεργοποιεί τη λειτουργία ασφάλειας ψευδώνυμου" + +#: modules/extra/stats/m_chanstats.cpp:44 +msgid "Chanstats statistics are now enabled for this channel." +msgstr "" + +# +#: modules/extra/stats/m_chanstats.cpp:95 +#, fuzzy +msgid "Chanstats statistics are now enabled for your nick." +msgstr "Ενεργοποιεί/απενεργοποιεί τη λειτουργία ασφάλειας ψευδώνυμου" + +#: modules/commands/cs_seen.cpp:367 +msgid "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." +msgstr "" + +# +#: modules/commands/ms_check.cpp:19 +msgid "Checks if last memo to a nick was read" +msgstr "Ελένχει αν το τελευταίο memo σε ένα ψευδόνυμο λεχει διαβαστεί." + +#: modules/commands/ms_check.cpp:69 +#, fuzzy +msgid "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." +msgstr "" +"Syntax: #CHECK #nick##\n" +"\n" +"Checks whether the _last_ memo you sent to #nick# has been read\n" +"or not. Note that this does only work with nicks, not with chans." + +#: modules/commands/os_info.cpp:227 +#, c-format +msgid "Cleared info from %s." +msgstr "" + +# +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1153 +#: modules/commands/bs_kick.cpp:1156 +#, fuzzy +msgid "Colors kicker" +msgstr "Ρυθμίζει τα kickers" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Command" +msgstr "Οι εντολές του %s είναι::" + +# +#: modules/commands/bs_kick.cpp:251 +#, fuzzy +msgid "Configures AMSG kicker" +msgstr "Ρυθμίζει τα kickers" + +# +#: modules/commands/bs_kick.cpp:287 +#, fuzzy +msgid "Configures badwords kicker" +msgstr "Ρυθμίζει τα kickers" + +# +#: modules/commands/bs_kick.cpp:326 +#, fuzzy +msgid "Configures bolds kicker" +msgstr "Ρυθμίζει τα kickers" + +#: modules/commands/bs_kick.cpp:132 +#, fuzzy +msgid "Configures bot kickers. option can be one of:" +msgstr "" +"Σύνταξη: #SET #option# #parameters##\n" +"\n" +"Αλλάζει διάφορες επιλογές του ψευδωνύμου. Η #επιλογή# μπορεί να είναι:" + +# +#: modules/commands/bs_set.cpp:19 +msgid "Configures bot options" +msgstr "Αλλάζετε τις επιλογές του bot" + +# +#: modules/commands/bs_set.cpp:32 +#, fuzzy +msgid "" +"Configures bot options.\n" +" \n" +"Available options:" +msgstr "Αλλάζετε τις επιλογές του bot" + +# +#: modules/commands/bs_kick.cpp:360 +#, fuzzy +msgid "Configures caps kicker" +msgstr "Ρυθμίζει τα kickers" + +#: modules/commands/cs_log.cpp:105 +#, fuzzy +msgid "Configures channel logging settings" +msgstr "* Δεν επιτρέπονται καινούριες κατοχυρώσεις καναλιών." + +# +#: modules/commands/bs_kick.cpp:456 +#, fuzzy +msgid "Configures color kicker" +msgstr "Ρυθμίζει τα kickers" + +# +#: modules/commands/bs_kick.cpp:490 +#, fuzzy +msgid "Configures flood kicker" +msgstr "Ρυθμίζει τα kickers" + +# +#: modules/commands/bs_kick.cpp:588 +#, fuzzy +msgid "Configures italics kicker" +msgstr "Ρυθμίζει τα kickers" + +# +#: modules/commands/bs_kick.cpp:119 +msgid "Configures kickers" +msgstr "Ρυθμίζει τα kickers" + +# +#: modules/commands/bs_kick.cpp:622 +#, fuzzy +msgid "Configures repeat kicker" +msgstr "Ρυθμίζει τα kickers" + +# +#: modules/commands/bs_kick.cpp:723 +#, fuzzy +msgid "Configures reverses kicker" +msgstr "Ρυθμίζει τα kickers" + +# +#: modules/commands/bs_set.cpp:90 +#, fuzzy +msgid "Configures the time bot bans expire in" +msgstr "Αλλάζετε τις επιλογές του bot" + +# +#: modules/commands/bs_kick.cpp:757 +#, fuzzy +msgid "Configures underlines kicker" +msgstr "Ρυθμίζει τα kickers" + +# +#: modules/commands/ns_register.cpp:21 +#, fuzzy +msgid "Confirm a passcode" +msgstr "Κάνει confirm με ένα κωδικό" + +# +#: modules/commands/cs_mode.cpp:733 +msgid "Control modes and mode locks on a channel" +msgstr "Καθαρίζει τα modes από το κανάλι" + +#: modules/commands/cs_entrymsg.cpp:239 +msgid "" +"Controls what messages will be sent to users when they join the channel." +msgstr "" + +#: modules/commands/cs_clone.cpp:242 +#, fuzzy +msgid "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." +msgstr "" +"Syntax: #CLONE #channel# #target# [all | access | akick | badwords]#\n" +" \n" +"Αντιγράφει τις ρυθμίσεις από ένα κανάλι σε ένα άλλο. Αν βάλετε κάποια " +"παράμετρο, τότε μόνο εκείνη η ρύθμιση θα μεταφερθεί. Πρέπει να έχετε " +"πρόσβαση επιπέδου ιδρητή και στα δύο κανάλια." + +# +#: modules/commands/cs_clone.cpp:114 +msgid "Copy all settings from one channel to another" +msgstr "Αντιγράφει όλες τις ρυθμίσεις από ένα κανάλι σε ένα άλλο." + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/bs_info.cpp:57 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Created" +msgstr " Δημιουργήθηκε : %s" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_ignore.cpp:266 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_news.cpp:156 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Creator" +msgstr " Δημιουργήθηκε : %s" + +#: modules/commands/os_sxline.cpp:180 +#, fuzzy, c-format +msgid "Current %s list:" +msgstr "Η έως τώρα AKILL λίστα είναι:" + +#: modules/commands/os_akill.cpp:323 +#, fuzzy +msgid "Current AKILL list:" +msgstr "Η έως τώρα AKILL λίστα είναι:" + +#: modules/commands/os_session.cpp:493 +msgid "Current Session Limit Exception list:" +msgstr "Η έως τώρα λίστα Session Limit Exception είναι οι εξής:" + +#: modules/commands/os_modinfo.cpp:116 +#, fuzzy +msgid "Current module list:" +msgstr "Η λίστα Module είναι:" + +#: modules/commands/os_stats.cpp:69 +#, c-format +msgid "Current number of AKILLs: %d" +msgstr "Ως τώρα υπάρχουν AKILLs: #%d#" + +#: modules/commands/os_stats.cpp:89 +#, c-format +msgid "Current number of SNLINEs: %d" +msgstr "Ως τώρα υπάρχουν SNLINEs: #%d#" + +#: modules/commands/os_stats.cpp:109 +#, c-format +msgid "Current number of SQLINEs: %d" +msgstr "Ως τώρα υπάρχουν SQLINEs: #%d#" + +#: modules/commands/os_stats.cpp:138 +#, c-format +msgid "Current users: %d (%d ops)" +msgstr "Οι ως τώρα χρήστες: #%d# (#%d# ops)" + +#: modules/commands/os_oper.cpp:71 +#, fuzzy +msgid "DEL oper" +msgstr "DEL ##." + +# +#: modules/commands/os_info.cpp:103 +#, fuzzy +msgid "DEL target info" +msgstr "^_στόχος^_ ^_κωδικό^_" + +#: modules/commands/ns_ajoin.cpp:232 +#, fuzzy +msgid "DEL [nickname] channel" +msgstr "RSEND {#nick# | #channel#} #memo-text#" + +# +#: modules/commands/ns_cert.cpp:259 +#, fuzzy +msgid "DEL [nickname] fingerprint" +msgstr "Ρυθμίζει τον κωδικό του ψευδονύμου." + +#: modules/commands/ns_access.cpp:103 +#, fuzzy +msgid "DEL [nickname] mask" +msgstr "DEL ##." + +#: modules/commands/os_sxline.cpp:426 modules/commands/os_sxline.cpp:660 +#: modules/commands/os_akill.cpp:387 +msgid "DEL {mask | entry-num | list | id}" +msgstr "" + +#: modules/commands/os_session.cpp:524 +msgid "DEL {mask | entry-num | list}" +msgstr "" + +#: modules/commands/os_ignore.cpp:343 +#, fuzzy +msgid "DEL {nick|mask}" +msgstr "DEL ##." + +#: modules/commands/os_news.cpp:279 +msgid "DEL {num | ALL}" +msgstr "" + +#: modules/commands/os_forbid.cpp:158 +msgid "DEL {NICK|CHAN|EMAIL|REGISTER} entry" +msgstr "" + +#: modules/commands/os_dns.cpp:666 +msgid "DELIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:664 +msgid "DELSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:662 +msgid "DELZONE zone.name" +msgstr "" + +#: modules/commands/os_dns.cpp:669 +#, fuzzy +msgid "DEPOOL server.name" +msgstr "NOOP {SET|REVOKE} #server#" + +#: modules/commands/cs_seen.cpp:162 +#, c-format +msgid "Database cleared, removed %lu nicks that were added after %s." +msgstr "" + +#: modules/commands/ms_list.cpp:64 +msgid "Date/Time" +msgstr "" + +#: modules/commands/hs_off.cpp:49 +#, fuzzy +msgid "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." +msgstr "" +"Syntax: #OFF#\n" +"Απενεργοποιεί τη vhost ενός nickname.\n" +"Αν χρησιμοποιήσετε αυτή την εντολή και κάποιος χρήστης σας κάνει /whois\n" +"θα δεί τη πραγματική IP σας." + +# +#: modules/commands/hs_off.cpp:19 +msgid "Deactivates your assigned vhost" +msgstr "Απενεργοποιεί τη vhost σας." + +#: modules/commands/os_stats.cpp:72 +#, c-format +msgid "Default AKILL expiry time: %d days" +msgstr "Προκαθορισμένος χρόνος λήξης AKILL: #%d μέρες#" + +#: modules/commands/os_stats.cpp:76 +#, c-format +msgid "Default AKILL expiry time: %d hours" +msgstr "Προκαθορισμένος χρόνος λήξης AKILL: #%d ώρες#" + +#: modules/commands/os_stats.cpp:80 +#, c-format +msgid "Default AKILL expiry time: %d minutes" +msgstr "Προκαθορισμένος χρόνος λήξης AKILL: #%d λεπτά#" + +#: modules/commands/os_stats.cpp:74 +msgid "Default AKILL expiry time: 1 day" +msgstr "Προκαθορισμένος χρόνος λήξης AKILL: #1 μέρα#" + +#: modules/commands/os_stats.cpp:78 +msgid "Default AKILL expiry time: 1 hour" +msgstr "Προκαθορισμένος χρόνος λήξης AKILL: #1 ώρα#" + +#: modules/commands/os_stats.cpp:82 +msgid "Default AKILL expiry time: 1 minute" +msgstr "Προκαθορισμένος χρόνος λήξης AKILL: #1 λεπτό#" + +#: modules/commands/os_stats.cpp:84 +msgid "Default AKILL expiry time: No expiration" +msgstr "Προκαθορισμένος χρόνος λήξης AKILL: #Δεν λήγει ποτέ#" + +#: modules/commands/os_stats.cpp:92 +#, c-format +msgid "Default SNLINE expiry time: %d days" +msgstr "Προκαθορισμένος χρόνος λήξης SNLINE: #%d μέρες#" + +#: modules/commands/os_stats.cpp:96 +#, c-format +msgid "Default SNLINE expiry time: %d hours" +msgstr "Προκαθορισμένος χρόνος λήξης SNLINE: #%d ώρες#" + +#: modules/commands/os_stats.cpp:100 +#, c-format +msgid "Default SNLINE expiry time: %d minutes" +msgstr "Προκαθορισμένος χρόνος λήξης SNLINE: #%d λεπτά#" + +#: modules/commands/os_stats.cpp:94 +msgid "Default SNLINE expiry time: 1 day" +msgstr "Προκαθορισμένος χρόνος λήξης SNLINE: #1 μέρα#" + +#: modules/commands/os_stats.cpp:98 +msgid "Default SNLINE expiry time: 1 hour" +msgstr "Προκαθορισμένος χρόνος λήξης SNLINE: #1 ώρα#" + +#: modules/commands/os_stats.cpp:102 +msgid "Default SNLINE expiry time: 1 minute" +msgstr "Προκαθορισμένος χρόνος λήξης SNLINE: #1 λεπτό#" + +#: modules/commands/os_stats.cpp:104 +msgid "Default SNLINE expiry time: No expiration" +msgstr "Προκαθορισμένος χρόνος λήξης SNLINE: #Δεν λήγει ποτέ#" + +#: modules/commands/os_stats.cpp:112 +#, c-format +msgid "Default SQLINE expiry time: %d days" +msgstr "Προκαθορισμένος χρόνος λήξης SQLINE: #%d μέρες#" + +#: modules/commands/os_stats.cpp:116 +#, c-format +msgid "Default SQLINE expiry time: %d hours" +msgstr "Προκαθορισμένος χρόνος λήξης SQLINE: #%d ώρες#" + +#: modules/commands/os_stats.cpp:120 +#, c-format +msgid "Default SQLINE expiry time: %d minutes" +msgstr "Προκαθορισμένος χρόνος λήξης SQLINE: #%d λεπτά#" + +#: modules/commands/os_stats.cpp:114 +msgid "Default SQLINE expiry time: 1 day" +msgstr "Προκαθορισμένος χρόνος λήξης SQLINE: #1 μέρα#" + +#: modules/commands/os_stats.cpp:118 +msgid "Default SQLINE expiry time: 1 hour" +msgstr "Προκαθορισμένος χρόνος λήξης SQLINE: #1 ώρα#" + +#: modules/commands/os_stats.cpp:122 +msgid "Default SQLINE expiry time: 1 minute" +msgstr "Προκαθορισμένος χρόνος λήξης SQLINE: #1 λεπτό#" + +#: modules/commands/os_stats.cpp:124 +msgid "Default SQLINE expiry time: No expiration" +msgstr "Προκαθορισμένος χρόνος λήξης SQLINE: #Δεν λήγει ποτέ#" + +# +#: modules/commands/os_news.cpp:351 +msgid "Define messages to be randomly shown to users at logon" +msgstr "" +"Αλλάζεις τα μηνύματα που θα εμφανίζονται στους χρήστες όταν αυτοί θα μπένουν " +"στο δίκτυο" + +# +#: modules/commands/os_news.cpp:297 +msgid "Define messages to be shown to users at logon" +msgstr "" +"Αλλάζεις τα μηνύματα που θα εμφανίζονται στους χρήστες όταν αυτοί θα μπένουν " +"στο δίκτυο" + +# +#: modules/commands/os_news.cpp:324 +msgid "Define messages to be shown to users who oper" +msgstr "" +"Αλλάζεις τα μηνύματα που θα εμφανίζονται στους χρήστες που\n" +"γίνονται oper" + +# +#: modules/commands/ms_del.cpp:44 +msgid "Delete a memo or memos" +msgstr "Διαγράφει ένα ή πολλά μηνύματα" + +# +#: modules/commands/hs_del.cpp:19 +msgid "Delete the vhost of another user" +msgstr "Διαγράφει τη vhost ενός χρήστη." + +#: modules/commands/cs_xop.cpp:302 +#, c-format +msgid "Deleted %d entries from %s %s list." +msgstr "Διαγράφηκαν %d θέσεις από την AOP λίστα του %s %s." + +#: modules/commands/cs_access.cpp:277 +#, c-format +msgid "Deleted %d entries from %s access list." +msgstr "Διαγράφηκαν %d θέσεις από %s access list." + +#: modules/commands/cs_akick.cpp:228 +#, c-format +msgid "Deleted %d entries from %s autokick list." +msgstr "Διαγράφηκαν %d θέσεις από την autokick list %s." + +#: modules/commands/bs_badwords.cpp:170 +#, c-format +msgid "Deleted %d entries from %s bad words list." +msgstr "Διαγράφηκαν %d θέσεις από το %s ,τη λίστα των κακών λέξεων." + +#: modules/commands/os_session.cpp:149 +#, c-format +msgid "Deleted %d entries from session-limit exception list." +msgstr "Διαγράφηκαν %d θέσεις από την λίστα session-limit exception." + +#: modules/commands/os_sxline.cpp:32 +#, fuzzy, c-format +msgid "Deleted %d entries from the %s list." +msgstr "Διαγράφηκαν %d θέσεις από την AOP λίστα του %s %s." + +#: modules/commands/os_akill.cpp:33 +#, c-format +msgid "Deleted %d entries from the AKILL list." +msgstr "Διαγράφηκαν %d θέσεις από την λίστα AKILL." + +#: modules/commands/cs_access.cpp:275 +#, c-format +msgid "Deleted 1 entry from %s access list." +msgstr "Διαγράφει 1 θέση από %s access list." + +#: modules/commands/cs_akick.cpp:226 +#, c-format +msgid "Deleted 1 entry from %s autokick list." +msgstr "Διαγράφτηκε 1 θέση από την autokick list %s." + +#: modules/commands/bs_badwords.cpp:168 +#, c-format +msgid "Deleted 1 entry from %s bad words list." +msgstr "Διαγράφηκε 1 θέση από του %s λίστα κακών λέξεων." + +#: modules/commands/os_session.cpp:147 +msgid "Deleted 1 entry from session-limit exception list." +msgstr "Διαγράφηκε 1 θέση από την λίστα session-limit exception." + +#: modules/commands/os_sxline.cpp:30 +#, fuzzy, c-format +msgid "Deleted 1 entry from the %s list." +msgstr "Διαγράφηκε 1 θέση από την λίστα AKILL." + +#: modules/commands/os_akill.cpp:31 +msgid "Deleted 1 entry from the AKILL list." +msgstr "Διαγράφηκε 1 θέση από την λίστα AKILL." + +#: modules/commands/os_info.cpp:208 +#, fuzzy, c-format +msgid "Deleted info from %s." +msgstr "Διαγράφηκε 1 θέση από την λίστα AKILL." + +#: modules/commands/cs_xop.cpp:300 +#, c-format +msgid "Deleted one entry from %s %s list." +msgstr "Διαγράφηκε 1 θέση από την AOP λίστα του %s %s." + +# +#: modules/commands/ms_del.cpp:129 +msgid "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Σύνταξη: #DEL [#κανάλι#] {#νου# | #list# | LAST | ALL}#\n" +"\n" +"Σβήνει το μήνυμα ή τα μηνύματα. Σβήνονται μέσω της λίστας\n" +"ανάλογα με τα νούμερα.Για παράδειγμα:\n" +" \n" +"If #LAST# is given, the last memo will be deleted.\n" +"Αν επιλέξετε #ALL#, θα σβήσετε όλα τα μηνύματά σας.\n" +"\n" +"Παράδειγμα:\n" +"\n" +" #DEL 1#\n" +" Διαγράφεται το πρώτο μήνυμα.(νούμερο 1).\n" +"\n" +" #DEL 2-5,7-9#\n" +" Διαγράφονται τα μηνύματα με νούμερα 2 έως 5 και 7 έως 9." + +#: modules/commands/hs_del.cpp:48 +msgid "" +"Deletes the vhost assigned to the given nick from the\n" +"database." +msgstr "" +"Syntax: #DEL# ##\n" +"Διαγράφει από την βάση δεδωμένων μια vhost από ένα Nick" + +# +#: modules/commands/hs_del.cpp:59 +#, fuzzy +msgid "Deletes the vhost for all nicks in a group" +msgstr "Διαγράφει τη vhost από όλα τα nicks σε ένα group" + +# +#: modules/commands/hs_del.cpp:93 +msgid "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." +msgstr "" +"Syntax: #DELALL# ##.\n" +"Διαγράφει όλες τις vhosts από το group του ονόματος που δώσατε." + +#: modules/commands/os_dns.cpp:653 +#, c-format +msgid "Depooled %s." +msgstr "" + +#: modules/commands/cs_access.cpp:799 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_list.cpp:75 modules/commands/cs_info.cpp:53 +#, fuzzy +msgid "Description" +msgstr "Περιγραφή του %s άλλαξε σε #%s#." + +#: modules/commands/cs_set.cpp:239 +#, c-format +msgid "Description of %s changed to %s." +msgstr "Περιγραφή του %s άλλαξε σε #%s#." + +#: modules/commands/cs_set.cpp:245 +#, fuzzy, c-format +msgid "Description of %s unset." +msgstr "Περιγραφή του %s άλλαξε σε #%s#." + +#: modules/commands/bs_kick.cpp:1115 modules/commands/bs_info.cpp:90 +msgid "Disabled" +msgstr "%s ενεργοποιήθηκε." + +#: modules/commands/cs_suspend.cpp:134 +#, fuzzy +msgid "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." +msgstr "" +"Syntax: #SUSPEND #channel# [#reason#]#\n" +"\n" +"Εμποδίζει τον οποιονδήποτε από το να κατοχυρώσει ή να χρησιμοποιήσει το\n" +"συγκεκριμένο κανάλι. Μπορεί να αναιρεθεί με τη χρήση της εντολής UNSUSPEND\n" +"η οποία επαναφέρει όλα τα προηγούμενα δεδομένα και ρυθμίσεις του καναλιού.\n" +"\n" +"Σε ορισμένα δίκτυα μπορεί να απαιτείται λόγος (reason) κατά τη χρήση της " +"εντολής." + +#: modules/commands/hs_request.cpp:337 +#, fuzzy, c-format +msgid "Displayed %d records (%d total)." +msgstr "Εμφανίστηκαν όλα τα records (Αριθμός: #%d#)" + +#: modules/commands/hs_list.cpp:122 +#, fuzzy, c-format +msgid "Displayed all records (count: %d)." +msgstr "Εμφανίστηκαν όλα τα records (Αριθμός: #%d#)" + +#: modules/commands/hs_list.cpp:120 +#, fuzzy, c-format +msgid "Displayed records from %d to %d." +msgstr "Εμφανίστηκαν όλα τα records από #%d# εώς #%d#" + +#: modules/commands/hs_list.cpp:116 +#, fuzzy, c-format +msgid "Displayed records matching key %s (count: %d)." +msgstr "" +"Εμφανίστηκαν όλα τα records που ταιριάζουν το κρητήριο #%s# (Αριθμός: #%d#)" + +# +#: modules/commands/ns_info.cpp:19 +msgid "Displays information about a given nickname" +msgstr "Εμφανίζει πληροφορίες για ένα ψευδόνυμο" + +#: modules/commands/ns_info.cpp:125 +msgid "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." +msgstr "" +"Σύνταξη: #INFO #ψευδώνυμο##\n" +"\n" +"Εμφανίζει πληροφορίες για το ψευδώνυμο που θα δώσετε, όπως\n" +"τον κάτοχο του ψευδωνύμου, την τελευταία διεύθυνση και ώρα\n" +"σύνδεσης και τις επιλογές του ψευδωνύμου. Αν έχετε \n" +"αναγνωριστεί για το ψευδώνυμο που ζητάτε πληροφορίες και\n" +"χρησιμοποιήσετε την παράμετρο #ALL# στην εντολή, θα δείτε\n" +"όλες τις πληροφορίες, άσχετα αν αυτές αποκρύπτονται ή όχι." + +# +#: modules/commands/ms_info.cpp:19 +msgid "Displays information about your memos" +msgstr "Εμφανίζει πληροφορίες για τα memos σας." + +# +#: modules/commands/hs_list.cpp:19 +#, fuzzy +msgid "Displays one or more vhost entries" +msgstr "Εμφανίζει μία η περισσότερες vhost entries." + +# +#: modules/extra/stats/cs_fantasy_top.cpp:50 +#, fuzzy +msgid "Displays the top 10 users of a channel" +msgstr "Αλλάζει τον founder του καναλιού" + +#: modules/extra/stats/cs_fantasy_top.cpp:73 +msgid "Displays the top 10 users of the network" +msgstr "" + +# +#: modules/extra/stats/cs_fantasy_top.cpp:38 +#, fuzzy +msgid "Displays the top 3 users of a channel" +msgstr "Αλλάζει τον founder του καναλιού" + +#: modules/extra/stats/cs_fantasy_top.cpp:62 +msgid "Displays the top 3 users of the network" +msgstr "" + +# +#: modules/commands/help.cpp:33 +msgid "Displays this list and give information about commands" +msgstr "Εμφανίζει τη λίστα και δίνει πληροφορίες για εντολές" + +#: modules/extra/stats/cs_fantasy_stats.cpp:39 +msgid "Displays your Channel Stats" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:51 +msgid "Displays your Global Stats" +msgstr "" + +#: modules/commands/bs_kick.cpp:1463 +msgid "Don't use AMSGs!" +msgstr "Μή χρησιμοποιείτε AMSGs!" + +#: modules/commands/bs_kick.cpp:1266 +msgid "Don't use bolds on this channel!" +msgstr "Μην χρησιμοποιείς έντονους χαρακτήρες μέσα στο κανάλι!" + +#: modules/commands/bs_kick.cpp:1274 +msgid "Don't use colors on this channel!" +msgstr "Μην χρησιμοποιείς χρώματα μέσα στο κανάλι!" + +#: modules/commands/bs_kick.cpp:1290 +msgid "Don't use italics on this channel!" +msgstr "Μη χρησιμοποιείς πλάγια γράμματα σε αυτό το κανάλι!" + +#: modules/commands/bs_kick.cpp:1282 +msgid "Don't use reverses on this channel!" +msgstr "Μην χρησιμοποιείς reverses μέσα στο κανάλι!" + +#: modules/commands/bs_kick.cpp:1408 +#, c-format +msgid "Don't use the word \"%s\" on this channel!" +msgstr "Μην χρησιμοποιείς αυτή τη λέξη %s στο κανάλι!" + +#: modules/commands/bs_kick.cpp:1298 +msgid "Don't use underlines on this channel!" +msgstr "Μην χρησιμοποιείς χαρακτήρες υπογράμμισης στο κανάλι!" + +#: modules/commands/ns_drop.cpp:61 +msgid "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." +msgstr "" + +#: modules/commands/ns_set.cpp:513 +#, c-format +msgid "E-mail address for %s changed to %s." +msgstr "Η διεύθυνση email για το #%s# άλλαξε σε #%s#." + +#: modules/commands/ns_set.cpp:519 +#, c-format +msgid "E-mail address for %s unset." +msgstr "Η διεύθυνση email για το #%s# διαγράφηκε." + +#: src/mail.cpp:80 +#, c-format +msgid "E-mail for %s is invalid." +msgstr "Η διεύθυνση για #%s# είναι λανθασμένη." + +#: modules/commands/os_news.cpp:309 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Syntax: #LOGONNEWS ADD #text##\n" +" #LOGONNEWS DEL {#num# | ALL}#\n" +" #LOGONNEWS LIST#\n" +"\n" +"Τροποποιεί ή εμφανίζει τη λίστα με τα logon news μηνύματα. Όταν\n" +"ένας χρήστης συνδέεται στο δίκτυο, αυτά τα μηνύματα θα του στέλνονται.\n" +"(Παρόλα αυτά, δεν θα του στέλνονται παραπάνω από #%d# μηνύματα\n" +"για να αποφευχθεί το flood του χρήστη. Αν υπάρχουν\n" +"περισσότερα μηνύματα, θα φαίνονται τα πιο πρόσφατα.)\n" +"Το NewsCount μπορεί να ρυθμιστεί στο services.conf.\n" +"\n" +"Η εντολή LOGONNEWS μπορεί να χρησιμοποιηθεί μόνο από IRC Operators." + +#: modules/commands/os_news.cpp:336 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Syntax: #OPERNEWS ADD #text##\n" +" #OPERNEWS DEL {#num# | ALL}#\n" +" #OPERNEWS LIST#\n" +" \n" +"Τροποποιεί ή παρουσιάζει τη λίστα των opers news μηνυμάτων. Όταν ένας user\n" +"σηκώνει oline (με την εντολή /OPER), αυτά τα μηνύματα θα\n" +"του στέλνονται. (Παρ όλα αυτά δεν θα φαίνονται περισσότερα από #%d# " +"μηνύματα\n" +"για να αποφευχθεί flood στον χρήστη. Αν υπάρχουν \n" +"περισσότερα μηνύματα, θα φαίνονται τα πιο πρόσφατα.)\n" +"Το NewsCount μπορεί να ρυθμιστεί στο services.conf.\n" +" \n" +"Το OPERNEWS μπορεί να χρησιμοποιηθεί μόνο από Services Operators." + +#: modules/commands/os_news.cpp:363 +#, fuzzy +msgid "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." +msgstr "" +"Σύνταξη: #RANDOMNEWS ADD #περιεχόμενα##\n" +" #RANDOMNEWS DEL {#νούμερο# | ALL}#\n" +" #RANDOMNEWS LIST#\n" +"\n" +"Μπορείς να προσθέσεις, να αφαιρέσεις ή να δεις την λίστα των μηνυμάτων.\n" +"Όταν ένας χρήστης συνδεθεί στο δίκτυο, ένα (και μόνο ένα) από τα\n" +"μηνύματα θα επιλεχθεί τυχαία και θα σταλεί.\n" +"\n" +"RANDOMNEWS may only be used by Services Operators." + +#: modules/commands/ns_info.cpp:98 +#, fuzzy +msgid "Email address" +msgstr " Διεύθυνση E-mail: %s" + +#: modules/commands/ns_getemail.cpp:41 +#, fuzzy, c-format +msgid "Email matched: %s (%s) to %s." +msgstr "Τα emails ταιριάζουν το #%s# στο #%s#." + +#: modules/fantasy.cpp:19 +msgid "Enable fantaisist commands" +msgstr "" + +#: modules/commands/greet.cpp:19 +msgid "Enable greet messages" +msgstr "" + +#: modules/commands/ns_set.cpp:568 +msgid "Enable or disable keep modes" +msgstr "" + +#: modules/commands/bs_kick.cpp:1114 modules/commands/bs_info.cpp:89 +msgid "Enabled" +msgstr "%s ενεργοποιήθηκε." + +#: modules/commands/cs_set.cpp:124 +#, fuzzy, c-format +msgid "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." +msgstr "" +"Σύνταξη: #%s #κανάλι# SECUREOPS {ON | OFF}#\n" +"\n" +"Ενεργοποιεί ή απενεργοποιεί την επιλογή #προστατευμένης# διαχείρησης\n" +"για ένα κανάλι. Όταν ενεργοποιείται η προστατευμένη διαχείρηση, οι\n" +"χρήστες που δεν είναι στη λίστα πρόσβασης, δε μπορούν να πάρουν op." + +#: modules/commands/cs_set.cpp:388 +#, fuzzy +msgid "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." +msgstr "" +"Σύνταξη: #%s #κανάλι# KEEPTOPIC {ON | OFF}#\n" +"\n" +"Ενεργοποιεί ή απενεργοποιεί την επιλογή #topic retention# του καναλιού.\n" +"Όταν το #topic retention# είναι on, το topic του καναλιού\n" +"θα υπενθυμίζεται από τον %s μετά τον τελευταίο χρήστη που θα φύγει από\n" +"το κανάλι, και θα αποθηκεύεται για την επόμενη φορά." + +#: modules/commands/ns_set.cpp:643 +msgid "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." +msgstr "" + +#: modules/commands/ns_set.cpp:618 +msgid "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." +msgstr "" + +#: modules/commands/cs_set.cpp:733 +#, fuzzy +msgid "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." +msgstr "" +"Σύνταξη: #%s #κανάλι# SECURE {ON | OFF}#\n" +"\n" +"Ενεργοποιεί ή απενεργοποιεί τις δυνατότητες ασφάλειας του %s για\n" +"ένα κανάλι. Όταν ενεργοποιείται το #SECURE#, μόνο οι χρήστες που\n" +"έχουν κατοχυρωμένα τα ψευδώνυμά τους με το %s και έχουν αναγνωριστεί\n" +"με τον κωδικό τους, θα έχουν πρόσβαση στο κανάλι όπως ορίζεται και\n" +"από τη λίστα πρόσβασης." + +#: modules/commands/cs_set.cpp:932 +#, fuzzy +msgid "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." +msgstr "" +"Σύνταξη: #%s #κανάλι# SIGNKICK {ON | LEVEL | OFF}#\n" +"\n" +"Ενεργοποιεί ή απενεργοποιεί την επιλογή signed kicks του\n" +"καναλιού. Όταν ενεργοποιείται η επιλογή #SIGNKICK#, τα kicks θα \n" +"εκτελούνται %s KICK command will have the nick that used the\n" +"με εντολή περιέχοντας τον λόγο.\n" +"\n" +"Αν χρησιμοποιείς #LEVEL#, αυτοί που έχουν μεγαλύτερη level ή ίση \n" +"με την SIGNKICK level του καναλιού δεν θα έχουν \n" +"kicks signed. Δες #/msg %s HELP LEVELS# για περισσότερες πληροφορίες. " + +#: modules/commands/cs_set.cpp:452 +#, fuzzy, c-format +msgid "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." +msgstr "" +"Σύνταξη: #%s #κανάλι# PEACE {ON | OFF}#\n" +"\n" +"Ενεργοποιεί ή απεεργοποιεί την εντολή #peace# στο κανάλι.\n" +"Όταν η εντολή #peace# είναι on, ο χρήστης δεν μπορεί να κάνει kick,\n" +"ban ή να αφαιρέσει op από κάποιον χρήστη ο οποίος έχει μεγαλύτερο\n" +"level από αυτόν ή ίσο με αυτόν μέσω εντολών %s." + +#: modules/commands/cs_list.cpp:232 +msgid "Enables or disables the private option for a channel." +msgstr "" + +#: modules/commands/cs_set.cpp:671 +#, fuzzy +msgid "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." +msgstr "" +"Σύνταξη: #%s #κανάλι# RESTRICTED {ON | OFF}#\n" +"\n" +"Ενεργοποιεί ή απενεργοποιεί την ρύθμιση #restricted access# για ένα κανάλι. " +"Όταν η #restricted access# έχει ενεργοποιηθεί, οι χρήστες που δεν είναι " +"στην access list θα απομακρυνθούν από το κανάλι.\n" + +#: modules/commands/cs_set.cpp:796 +#, fuzzy +msgid "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." +msgstr "" +"Σύνταξη: #%s #κανάλι# SECUREFOUNDER {ON | OFF}#\n" +"\n" +"Ενεργοποιεί ή απενεργοποιεί την επιλογή #ασφαλής founder# για ένα κανάλι.\n" +"Όταν ενεργοποιείται η επιλογή #ασφαλής founder#, μόνο ο πραγματικός " +"founder \n" +"μπορεί να κάνει drop (σβήσει) το κανάλι, να αλλάξει τον κωδικό του, \n" +"μόνο ο founder και ο successor, και όχι αυτοί που κάνουν εντολή \n" +"αναγνώρισης με τον %s.\n" +" " + +#: modules/commands/cs_set.cpp:860 +#, fuzzy +msgid "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." +msgstr "" +"Σύνταξη: #%s #κανάλι# SECUREOPS {ON | OFF}#\n" +"\n" +"Ενεργοποιεί ή απενεργοποιεί την επιλογή #προστατευμένης# διαχείρησης\n" +"για ένα κανάλι. Όταν ενεργοποιείται η προστατευμένη διαχείρηση, οι\n" +"χρήστες που δεν είναι στη λίστα πρόσβασης, δε μπορούν να πάρουν op." + +#: modules/commands/cs_topic.cpp:70 +#, fuzzy, c-format +msgid "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." +msgstr "" +"Σύνταξη: #%s #κανάλι# KEEPTOPIC {ON | OFF}#\n" +"\n" +"Ενεργοποιεί ή απενεργοποιεί την επιλογή #topic retention# του καναλιού.\n" +"Όταν το #topic retention# είναι on, το topic του καναλιού\n" +"θα υπενθυμίζεται από τον %s μετά τον τελευταίο χρήστη που θα φύγει από\n" +"το κανάλι, και θα αποθηκεύεται για την επόμενη φορά." + +#: modules/commands/cs_set.cpp:592 +#, fuzzy, c-format +msgid "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." +msgstr "" +"Syntax: #%s #channel# PERSIST {ON | OFF}#\n" +"Ενεργοποιεί ή απενεργοποιεί τη ρύθμιση persist.\n" +"Όταν το persist είναι ενεργοποιημένο, το bot θα μένει\n" +"στο κανάλι ακόμη και οταν δεν έχει χρήστες.\n" +"\n" +"Αν το ircd σας δεν υποστηρίζει ένα μόνιμο κανάλι,\n" +"πρέπει να έχετε στο κανάλι ένα services bot με\n" +"persist on, ωστε να κρατά το κανάλι ανοιχτό.\n" +"\n" +"Αν το δίκτυο δεν έχει ενεργοποιήσει τον Botserv και\n" +"δεν υποστηρίζει μόνιμα κανάλια, ο Chanserv θα\n" +"μπεί στο κανάλι σας όταν ενεργοποιήσετε το Persist. (και θα\n" +"βγεί όταν το απενεργοποιήσετε) \n" +"Αν το ircd σας υποστηρίζει μόνιμα κανάλια\n" +"και το (απ)ενεργοποιήσετε για οποιδήποτε λόγο (ακόμη και με MLOCK\n" +"η ρύθμιση persist θα επιρρεαστεί αντίστοιχα.\n" + +#: modules/commands/os_akill.cpp:331 +#, fuzzy +msgid "End of AKILL list." +msgstr "Τελος της λίστας προσβασης." + +#: modules/commands/cs_access.cpp:444 +#, fuzzy +msgid "End of access list" +msgstr "Τελος της λίστας προσβασης." + +#: modules/commands/cs_flags.cpp:347 +#, c-format +msgid "End of access list - %d/%d entries shown." +msgstr "Τέλος της λίστας - %d/%d βρέθηκαν και εμφανίστηκαν." + +#: modules/commands/cs_flags.cpp:345 +msgid "End of access list." +msgstr "Τελος της λίστας προσβασης." + +#: modules/commands/cs_akick.cpp:379 +#, fuzzy +msgid "End of autokick list" +msgstr "Τελος της λίστας προσβασης." + +#: modules/commands/bs_badwords.cpp:257 +#, fuzzy +msgid "End of bad words list." +msgstr "Τέλος λίστας χρηστών." + +#: modules/commands/os_list.cpp:100 +#, fuzzy, c-format +msgid "End of channel list. %u channels shown." +msgstr "Τέλος της λίστας - %d/%d βρέθηκαν και εμφανίστηκαν." + +#: modules/commands/os_config.cpp:117 +msgid "End of configuration." +msgstr "Τέλος ρυθμίσεων" + +#: modules/commands/cs_entrymsg.cpp:134 +msgid "End of entry message list." +msgstr "Τελος της λίστας προσβασης." + +#: modules/commands/os_forbid.cpp:407 +#, fuzzy, c-format +msgid "End of forbid list - %d/%d entries shown." +msgstr "Τέλος της λίστας - %d/%d βρέθηκαν και εμφανίστηκαν." + +#: modules/commands/os_forbid.cpp:405 +msgid "End of forbid list." +msgstr "Τέλος λίστας χρηστών." + +#: modules/commands/ns_alist.cpp:119 +#, fuzzy, c-format +msgid "End of list - %d channels shown." +msgstr "Τέλος της λίστας - %d/%d βρέθηκαν και εμφανίστηκαν." + +#: modules/commands/ns_list.cpp:131 modules/commands/cs_list.cpp:130 +#, c-format +msgid "End of list - %d/%d matches shown." +msgstr "Τέλος της λίστας - %d/%d βρέθηκαν και εμφανίστηκαν." + +#: modules/commands/os_news.cpp:176 +#, fuzzy +msgid "End of news list." +msgstr "Τέλος λίστας χρηστών." + +#: modules/commands/os_list.cpp:235 +#, fuzzy, c-format +msgid "End of users list. %u users shown." +msgstr "Τέλος της λίστας - %d/%d βρέθηκαν και εμφανίστηκαν." + +#: modules/commands/cs_enforce.cpp:227 +msgid "Enforce various channel modes and set options" +msgstr "" + +#: modules/commands/cs_enforce.cpp:263 +msgid "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." +msgstr "" + +#: src/language.cpp:43 modules/commands/ns_set.cpp:836 +#: modules/commands/ns_set.cpp:856 modules/commands/ns_set.cpp:891 +msgid "English" +msgstr "Ελληνικά" + +#: modules/commands/cs_entrymsg.cpp:170 +#, fuzzy, c-format +msgid "Entry message %i for %s deleted." +msgstr "Το μήνυμα χαιρετισμού για τον #%s# αφερέθηκε." + +#: modules/commands/cs_entrymsg.cpp:177 +#, fuzzy, c-format +msgid "Entry message %s not found on channel %s." +msgstr "Η Fantasy επιλογή είναι τώρα #ON# στο κανάλι %s." + +#: modules/commands/cs_entrymsg.cpp:147 +#, c-format +msgid "Entry message added to %s" +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:109 modules/commands/cs_entrymsg.cpp:158 +#, c-format +msgid "Entry message list for %s is empty." +msgstr "Access list for #%s# is empty." + +#: modules/commands/cs_entrymsg.cpp:113 +#, c-format +msgid "Entry message list for %s:" +msgstr "Λίστα πρόσβασης για #%s#:" + +#: modules/commands/cs_entrymsg.cpp:187 +#, c-format +msgid "Entry messages for %s have been cleared." +msgstr "Όλα τα memos από το κανάλι %s έχουν διαγραφεί." + +# +#: modules/commands/os_reload.cpp:39 +#, fuzzy, c-format +msgid "Error reloading configuration file: %s" +msgstr "Λάθος στην επαναφόρτηση του αρχείου configuration" + +#: include/language.h:125 +#, c-format +msgid "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." +msgstr "" + +#: include/language.h:124 +#, c-format +msgid "" +"Error! The vHost is too long, please use a hostname shorter than %d " +"characters." +msgstr "" + +#: modules/commands/ns_cert.cpp:325 +#, fuzzy +msgid "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." +msgstr "" +"Παραδείγματα:\n" +" \n" +" #CERT ADD #\n" +" Προσθέτει ένα fingerprint στην certificate list και\n" +" σας κάνει αυτόματα identify μόλις συνδέεστε στο IRC\n" +" χρησιμοποιώντας αυτό το certificate.\n" +" \n" +" #CERT DEL #\n" +" Αντιστρέφει τη προηγούμενη εντολή.\n" +" \n" +" #CERT LIST#\n" +" Εμφανίζει την λίστα certificate." + +#: modules/commands/os_session.cpp:358 +#, c-format +msgid "Exception for %s has been updated to %d." +msgstr "Exception για #%s# άλλαξε σε %d." + +#: modules/pseudoclients/chanserv.cpp:465 +#: modules/pseudoclients/nickserv.cpp:557 +#: modules/pseudoclients/nickserv.cpp:562 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_session.cpp:514 modules/commands/ns_group.cpp:327 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Expires" +msgstr "Λίγει στις: %s" + +#: src/xline.cpp:397 +#, fuzzy, c-format +msgid "Expiry and reason updated for %s." +msgstr "Exception για #%s# άλλαξε σε %d." + +#: src/xline.cpp:400 +#, fuzzy, c-format +msgid "Expiry for %s updated." +msgstr "Το χρονικό όριο του/ης #%s# άλλαξε" + +#: modules/fantasy.cpp:214 +msgid "Fantasy" +msgstr "Φαντασία" + +#: modules/fantasy.cpp:60 +#, c-format +msgid "Fantasy mode is now off on channel %s." +msgstr "Η Fantasy επιλογή είναι τώρα #ON# στο κανάλι %s." + +#: modules/fantasy.cpp:52 +#, c-format +msgid "Fantasy mode is now on on channel %s." +msgstr "Η Fantasy επιλογή είναι τώρα #ON# στο κανάλι %s." + +# +#: modules/commands/cs_status.cpp:19 +#, fuzzy +msgid "Find a user's status on a channel" +msgstr "Αφαιρεί το owner status σε ένα κανάλι." + +#: modules/commands/ns_cert.cpp:192 +#, fuzzy, c-format +msgid "Fingerprint %s already present on %s's certificate list." +msgstr "Η μάσκα #%s# είναι ήδη μέσα στην λίστα πρόσβασης." + +#: modules/commands/ns_cert.cpp:198 +#, fuzzy, c-format +msgid "Fingerprint %s is already in use." +msgstr "Είστε ήδη στο κανάλι #%s#! " + +#: modules/commands/cs_flags.cpp:301 +msgid "Flags" +msgstr "" + +#: modules/commands/cs_flags.cpp:286 +#, fuzzy, c-format +msgid "Flags for %s on %s set to +%s" +msgstr "Η vhost για τον #%s# έγινε #%s#." + +#: modules/commands/cs_flags.cpp:341 +#, c-format +msgid "Flags list for %s" +msgstr "Λίστα πρόσβασης για #%s#:" + +#: modules/commands/bs_kick.cpp:1161 modules/commands/bs_kick.cpp:1163 +#: modules/commands/bs_kick.cpp:1166 +#, fuzzy +msgid "Flood kicker" +msgstr " Επανάληψη με kick : %s" + +#: modules/commands/os_forbid.cpp:421 +msgid "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." +msgstr "" + +#: modules/commands/os_forbid.cpp:354 +msgid "Forbid list is empty." +msgstr "Η λίστα ignore των υπηρεσιών είναι άδεια." + +#: modules/commands/os_forbid.cpp:396 +msgid "Forbid list:" +msgstr "Bot λίστα:" + +#: modules/commands/os_forbid.cpp:348 +#, c-format +msgid "Forbid on %s was not found." +msgstr "" + +#: modules/commands/os_forbid.cpp:156 +msgid "Forbid usage of nicknames, channels, and emails" +msgstr "" + +# +#: modules/commands/os_update.cpp:19 +msgid "Force the Services databases to be updated immediately" +msgstr "" +"Ενεργούν τα Services (βάσεις δεδομένων) για\n" +"να γίνουν update στο δίσκο αμέσως" + +# +#: modules/commands/os_svs.cpp:19 +msgid "Forcefully change a user's nickname" +msgstr "Αλλάζει το όνομα ενός χρήστη" + +#: modules/commands/os_svs.cpp:68 +#, fuzzy +msgid "Forcefully changes a user's nickname from nick to newnick." +msgstr "" +"Syntax: #SVSNICK #nick# #newnick##\n" +"\n" +"Αλλάζει αναγκαστικά το ψευδώνυμο ενός χρήστη από nick σε newnick." + +# +#: modules/commands/os_svs.cpp:78 +#, fuzzy +msgid "Forcefully join a user to a channel" +msgstr "Αλλάζει το όνομα ενός χρήστη" + +# +#: modules/commands/os_svs.cpp:112 +#, fuzzy +msgid "Forcefully join a user to a channel." +msgstr "Αλλάζει το όνομα ενός χρήστη" + +# +#: modules/commands/os_svs.cpp:122 +#, fuzzy +msgid "Forcefully part a user from a channel" +msgstr "Απομακρύνει το χρήστη από το κανάλι" + +# +#: modules/commands/os_svs.cpp:160 +#, fuzzy +msgid "Forcefully part a user from a channel." +msgstr "Απομακρύνει το χρήστη από το κανάλι" + +#: modules/commands/ns_alist.cpp:64 modules/commands/cs_info.cpp:47 +#, fuzzy +msgid "Founder" +msgstr "Ασφάλεια στον Καναλάρχη" + +#: modules/commands/cs_set.cpp:315 +#, fuzzy, c-format +msgid "Founder of %s changed to %s." +msgstr "Ο Founder του %s άλλαξε και πήγε στον #%s#." + +#: modules/commands/ns_getpass.cpp:41 +msgid "GETPASS command unavailable because encryption is in use." +msgstr "" +"Η GETPASS εντολή δεν είναι διαθέσιμη γιατί χρησιμοποιείται η κωδικοποίηση." + +#: modules/commands/ns_recover.cpp:84 +msgid "Ghost with your nick has been killed." +msgstr "Το ψευδώνυμο σου έγινε kill μέσω ghost εντολής." + +# +#: modules/commands/os_oline.cpp:19 +msgid "Give Operflags to a certain user" +msgstr "Δίνει πρόσβαση IRC Operator σε κάποιο χρήστη" + +#: modules/commands/cs_mode.cpp:905 +#, c-format +msgid "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." +msgstr "" + +# +#: modules/commands/cs_mode.cpp:888 +#, fuzzy, c-format +msgid "Gives you or the specified nick %s status on a channel" +msgstr "Σας δίνει πρόσβαση διαχειριστή στο κανάλι" + +#: modules/commands/greet.cpp:206 modules/commands/greet.cpp:212 +msgid "Greet" +msgstr "Χαιρετισμός" + +#: src/access.cpp:38 +#, fuzzy +msgid "Greet message displayed on join" +msgstr "Το μήνυμα χαιρετισμού για τον #%s# άλλαξε σε #%s#." + +#: modules/commands/greet.cpp:112 +#, c-format +msgid "Greet message for %s changed to %s." +msgstr "Το μήνυμα χαιρετισμού για τον #%s# άλλαξε σε #%s#." + +#: modules/commands/greet.cpp:118 +#, c-format +msgid "Greet message for %s unset." +msgstr "Το μήνυμα χαιρετισμού για τον #%s# αφερέθηκε." + +#: modules/commands/greet.cpp:60 +#, c-format +msgid "Greet mode is now off on channel %s." +msgstr "Η επιλογή χαιρετισμού είναι #ON# στο κανάλι %s." + +#: modules/commands/greet.cpp:52 +#, c-format +msgid "Greet mode is now on on channel %s." +msgstr "Η επιλογή χαιρετισμού είναι #ON# στο κανάλι %s." + +# +#: modules/commands/ns_resetpass.cpp:21 +msgid "Helps you reset lost passwords" +msgstr "Σας βοηθά να ανακτήσετε έναν χαμένο κωδικό." + +# +#: modules/commands/ns_info.cpp:141 +msgid "Hide certain pieces of nickname information" +msgstr "Αποκρύπτει συγκεκριμένα τμήματα πληροφοριών του ψευδωνύμου" + +# +#: modules/commands/cs_list.cpp:180 +#, fuzzy +msgid "Hide channel from the LIST command" +msgstr "Να μην εμφανίζεται το κανάλι όταν γίνεται εντολή LIST" + +#: modules/commands/os_session.cpp:192 +msgid "Host" +msgstr "" + +#: modules/commands/os_session.cpp:207 +#, c-format +msgid "Hosts with at least %d sessions:" +msgstr "Hosts με το λιγότερο #%d# sessions:" + +#: modules/commands/cs_seen.cpp:207 +#, c-format +msgid "I don't know who %s is." +msgstr "" + +#: modules/commands/cs_seen.cpp:253 +#, fuzzy, c-format +msgid "I've never seen %s on this channel." +msgstr "Μην χρησιμοποιείς reverses μέσα στο κανάλι!" + +#: modules/commands/os_sxline.cpp:203 modules/commands/os_akill.cpp:360 +msgid "ID" +msgstr "" + +#: modules/commands/os_oper.cpp:72 +msgid "INFO [type]" +msgstr "" + +#: modules/commands/os_dns.cpp:218 +msgid "IP" +msgstr "" + +#: modules/commands/os_dns.cpp:500 +#, fuzzy, c-format +msgid "IP %s already exists for %s." +msgstr "Το Bot #%s# υπάρχει ήδη." + +#: modules/commands/os_dns.cpp:562 +#, fuzzy, c-format +msgid "IP %s does not exist for %s." +msgstr " %s (δεν λήγει ποτέ)" + +# +#: modules/commands/ns_identify.cpp:65 +msgid "Identify yourself with your password" +msgstr "Σας αναγνωρίζει με τη χρήση κωδικού" + +#: modules/pseudoclients/nickserv.cpp:205 +#: modules/pseudoclients/nickserv.cpp:211 +#, fuzzy, c-format +msgid "If you do not change within %s, I will change your nick." +msgstr "" +"Αν δεν αλλάξεις το ψευδώνυμο αυτό μέσα σε 20 δευτερόλεπτα, θα αλλάξει " +"αυτόματα." + +#: modules/commands/os_ignore.cpp:333 +msgid "Ignore list has been cleared." +msgstr "Η λίστα ignore έχει διαγραφεί." + +#: modules/commands/os_ignore.cpp:262 +msgid "Ignore list is empty." +msgstr "Η λίστα ignore των υπηρεσιών είναι άδεια." + +# +#: modules/commands/ms_ignore.cpp:94 +msgid "Ignore list:" +msgstr "Bot λίστα:" + +#: modules/commands/ns_set.cpp:1305 +#, fuzzy +msgid "Immediate protection" +msgstr "Προστασία στους Voices" + +#: modules/commands/ns_resetpass.cpp:33 +#, fuzzy +msgid "Incorrect email address." +msgstr " Διεύθυνση E-mail: %s" + +#: include/language.h:89 +msgid "Incorrect range specified. The correct syntax is #from-to." +msgstr "" + +# +#: modules/commands/os_modinfo.cpp:19 +msgid "Info about a loaded module" +msgstr "Πληροφορίες για ένα φορτομένο Module" + +#: modules/commands/bs_info.cpp:54 +#, c-format +msgid "Information for bot %s:" +msgstr "Πληροφορίες για το bot #%s#:" + +#: include/language.h:108 +#, c-format +msgid "Information for channel %s:" +msgstr "Πληροφορίες για το bot #%s#:" + +#: modules/commands/os_logsearch.cpp:57 +#, c-format +msgid "Invalid duration %s, using %d days." +msgstr "" + +#: include/language.h:68 +msgid "Invalid expiry time." +msgstr "" + +#: modules/commands/os_session.cpp:346 +msgid "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not " +"matched against nicks or usernames." +msgstr "" +"Λάθος hostmask. Μόνο πραγματικά hostmasks χρησιμοποιούνται και όχι ψευδώνυμα " +"ή usernames." + +#: modules/commands/os_logsearch.cpp:73 +#, c-format +msgid "Invalid limit %s, using %d." +msgstr "" + +#: include/language.h:99 +msgid "" +"Invalid passcode has been entered, please check the e-mail again, and retry." +msgstr "" + +#: modules/commands/ns_register.cpp:83 modules/commands/ns_register.cpp:86 +msgid "Invalid passcode." +msgstr "Μη έγγυρο passcode" + +#: modules/commands/os_session.cpp:339 +#, c-format +msgid "" +"Invalid session limit. It must be a valid integer greater than or equal to " +"zero and less than %d." +msgstr "" +"Λάθος session limit. Πρέπει να είναι λάθος ο integer greater ή πρέπει να " +"είναι μεταξύ μηδέν και #%d#." + +#: modules/commands/os_session.cpp:188 +msgid "Invalid threshold value. It must be a valid integer greater than 1." +msgstr "Λάθος threshold value. Πρέπει να είναι μεγαλύτερο από το 1." + +#: modules/commands/os_dns.cpp:591 +msgid "Invalid value for LIMIT. Must be numerical." +msgstr "" + +# +#: modules/commands/cs_invite.cpp:19 +#, fuzzy +msgid "Invites you or an optionally specified nick into a channel" +msgstr "Κάνει έναν χρήστη διαχειριστή καναλιού " + +#: modules/commands/bs_kick.cpp:1201 modules/commands/bs_kick.cpp:1203 +#: modules/commands/bs_kick.cpp:1206 +#, fuzzy +msgid "Italics kicker" +msgstr " Πλάγια γράμματα kicker : %s" + +# +#: modules/commands/ns_group.cpp:91 +msgid "Join a group" +msgstr " GROUP Μπένετε σε ομάδα ψευδώνυμου" + +#: modules/commands/cs_set.cpp:1305 modules/commands/ns_set.cpp:1319 +#, fuzzy +msgid "Keep modes" +msgstr "Επιλογή μηνύματος" + +#: modules/commands/cs_set.cpp:377 modules/commands/ns_set.cpp:603 +#, fuzzy, c-format +msgid "Keep modes for %s is now off." +msgstr "Η Peace επιλογή για το %s #ΑΠΕΝΕΡΓΟΠΟΙΉΘΗΚΕ#." + +#: modules/commands/cs_set.cpp:369 modules/commands/ns_set.cpp:597 +#, fuzzy, c-format +msgid "Keep modes for %s is now on." +msgstr "Η Peace επιλογή για το %s #ΕΝΕΡΓΟΠΟΙΉΘΗΚΕ#." + +#: modules/commands/ns_ajoin.cpp:100 +msgid "Key" +msgstr "" + +#: modules/commands/cs_getkey.cpp:50 +#, c-format +msgid "Key for channel %s is %s." +msgstr "Key for channel #%s# is #%s#." + +# +#: modules/commands/os_kick.cpp:19 +msgid "Kick a user from a channel" +msgstr "Απομακρύνει το χρήστη από το κανάλι" + +#: modules/commands/cs_ban.cpp:217 modules/commands/cs_kick.cpp:116 +#, c-format +msgid "Kicked %d/%d users matching %s from %s." +msgstr "" + +# +#: modules/commands/cs_kick.cpp:19 +#, fuzzy +msgid "Kicks a specified nick from a channel" +msgstr "Κάνει kick ένα ψευδόνυμο από ένα κανάλι." + +#: modules/commands/cs_kick.cpp:128 +#, fuzzy +msgid "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." +msgstr "" +"Σύνταξη: #KICK ##κανάλι# #ψευδώνυμο# [#λόγος#]#\n" +"\n" +"Κάνει kick το ψευδώνυμο που του δίνεις στο κανάλι.\n" +"\n" +"Από default, χρησιμοποιείται από τους AOPs ή αυτούς που έχουν level 5 " +"access \n" +"και παραπάνω στο κανάλι." + +#: modules/commands/os_kill.cpp:19 +msgid "Kill a user" +msgstr "" + +#: modules/commands/cs_enforce.cpp:217 +msgid "LIMIT enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:221 +#, c-format +msgid "LIMIT enforced on %s, %d users removed." +msgstr "" + +#: modules/commands/os_session.cpp:246 +msgid "LIST threshold" +msgstr "" + +#: modules/commands/os_sxline.cpp:427 modules/commands/os_sxline.cpp:661 +#: modules/commands/os_akill.cpp:388 +msgid "LIST [mask | list | id]" +msgstr "" + +#: modules/commands/os_session.cpp:525 +msgid "LIST [mask | list]" +msgstr "" + +#: modules/commands/ns_access.cpp:104 modules/commands/ns_cert.cpp:260 +#: modules/commands/ns_ajoin.cpp:233 +#, fuzzy +msgid "LIST [nickname]" +msgstr "CHECK #nickname#" + +#: modules/commands/os_news.cpp:31 +msgid "LOGONNEWS {ADD|DEL|LIST} [text|num]" +msgstr "LOGONNEWS {ADD|DEL|LIST} [#περιεχόμενο#|#νούμερο#]#" + +#: modules/commands/ns_set.cpp:834 +msgid "Language changed to English." +msgstr "Η γλώσσα άλλαξε σε #Ελληνικά#." + +#: modules/commands/ns_set.cpp:836 +#, fuzzy, c-format +msgid "Language for %s changed to %s." +msgstr "Ο Successor του %s άλλαξε και πήγε στον #%s#." + +#: modules/commands/ms_cancel.cpp:72 +#, c-format +msgid "Last memo to %s has been cancelled." +msgstr "Το τελευταίο μήνυμα που πήγαινε για τον #%s# ακυρώθηκε." + +#: modules/commands/ns_info.cpp:95 +#, fuzzy +msgid "Last quit message" +msgstr "Τελευταίο αποχαιρετιστήριο μήνυμα: %s" + +#: modules/commands/cs_access.cpp:472 modules/commands/ns_info.cpp:92 +#, fuzzy +msgid "Last seen" +msgstr " Τελευταία φορά που ήταν στο δίκτυο: %s" + +#: modules/commands/ns_info.cpp:81 modules/commands/ns_info.cpp:86 +#, fuzzy +msgid "Last seen address" +msgstr "Τελευταία διεύθυνση: %s" + +#: modules/commands/cs_topic.cpp:264 +msgid "Last topic" +msgstr "" + +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_info.cpp:56 +#, fuzzy +msgid "Last used" +msgstr " Τελευταία φορά που ήταν στο δίκτυο: %s" + +#: modules/commands/ns_list.cpp:75 +#, fuzzy +msgid "Last usermask" +msgstr " Τελευταία φορά που ήταν στο δίκτυο: %s" + +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +#: modules/commands/cs_access.cpp:697 +msgid "Level" +msgstr "" + +#: modules/commands/cs_access.cpp:660 +#, c-format +msgid "Level for %s on channel %s changed to %d." +msgstr "Ο βαθμός για τον #%s# στο κανάλι %s άλλξε σε #%d#." + +#: modules/commands/cs_access.cpp:658 +#, c-format +msgid "Level for %s on channel %s changed to founder only." +msgstr "Το Level για %s στο κανάλι %s άλλαξε σε founder only." + +#: modules/commands/cs_access.cpp:643 +#, c-format +msgid "Level must be between %d and %d inclusive." +msgstr "Ο βαθμός πρέπει να είναι μεταξύ %d και %d." + +#: modules/commands/os_dns.cpp:218 modules/commands/os_session.cpp:506 +#: modules/commands/os_session.cpp:514 +msgid "Limit" +msgstr "" + +# +#: modules/commands/ns_list.cpp:19 +msgid "List all registered nicknames that match a given pattern" +msgstr "Εμφανίζει όλα τα κατωχηρωμένα ψευδόνυμα που ταιριάζουν ένα pattern" + +# +#: modules/commands/ns_alist.cpp:24 +msgid "List channels you have access on" +msgstr "Εμφανίζει όλα τα κανάλια στα οποία έχετε πρόσβαση." + +#: modules/commands/cs_mode.cpp:341 +#, c-format +msgid "List for mode %c is full." +msgstr "" + +# +#: modules/commands/os_modinfo.cpp:80 +msgid "List loaded modules" +msgstr "Εμφανίζει όλα τα φορτωμένα Modules." + +#: modules/commands/ns_list.cpp:123 modules/commands/cs_list.cpp:72 +#, c-format +msgid "List of entries matching %s:" +msgstr "" + +#: modules/commands/ns_group.cpp:350 +#, c-format +msgid "List of nicknames in the group of %s:" +msgstr "Η λίστα με τα ψευδώνυμα στην ομάδα του #%s#:" + +#: modules/commands/ns_group.cpp:350 +msgid "List of nicknames in your group:" +msgstr "Η λίστα με τα ψευδώνυμα στην ομάδα:" + +# +#: modules/commands/ms_list.cpp:19 +msgid "List your memos" +msgstr "Εμφανίζει λίστα με τα μηνύματα σας" + +#: modules/commands/bs_botlist.cpp:64 +#, fuzzy +msgid "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." +msgstr "" +"Σύνταξη: #BOTLIST#\n" +"\n" +"Εμφανίζει την λίστα με τα διαθέσιμα bots αυτού του δικτύου." + +# +#: modules/commands/os_list.cpp:19 +msgid "Lists all channel records" +msgstr "Εμφανίζει όλα τα κανάλια" + +#: modules/commands/os_list.cpp:107 +#, fuzzy +msgid "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." +msgstr "" +"Σύνταξη: #CHANLIST [{#επιλογή# | #ψευδώνυμο#} [#SECRET#]]#\t\n" +"\n" +"Εμφανίζει τις λίστες όλων των καναλιών που υπάρχουν συγκεκριμένα εκείνη τη\n" +"στιγμή στο IRC δίκτυο, είτε είναι κατοχυρωμένα είτε όχι.\n" +" \n" +"Αν δίνετε #επιλογή#, εμφανίζει την λίστα μόνο με τα κανάλια που ταιριάζουν.\n" +"Αν δίνετε ψευδώνυμο εμφανίζει μόνο τα κανάλια που τα χρησιμοποιεί ο " +"ζητούμενος \n" +"χρήστης. Αν δίνετε SECRET εμφανίζει μόνο τα κανάλια που ταιριάζουν με την\n" +"#επιλογή# που έχουν +s ή +p mode.\n" +" \n" +"Μόνο για τους #Services Operators#." + +#: modules/commands/ns_alist.cpp:127 +msgid "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" +msgstr "" + +# +#: modules/commands/ns_group.cpp:299 +msgid "Lists all nicknames in your group" +msgstr "Η λίστα με τα ψευδώνυμα στην ομάδα:" + +# +#: modules/commands/cs_list.cpp:20 +msgid "Lists all registered channels matching the given pattern" +msgstr "Εμφανίζει όλα τα κατωχηρωμένα κανάλια που ταιριάζουν ένα pattern" + +# +#: modules/commands/cs_list.cpp:137 +#, fuzzy +msgid "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." +msgstr "" +"Σύνταξη: #LIST #pattern# [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]#\n" +"\n" +"Δίνει την λίστα όλων των κατοχυρωμένων ψευδώνυμων που ταιριάζουν με το " +"ανάλογο\n" +"pattern, σε σύνταξη #nick!user@host#. Ψευδώνυμα με επιλογή #PRIVATE#\n" +"θα φαίνονται μόνο στους (επικεφαλείς) Services Operators. Ψευδώνυμα με\n" +"επιλογή #NOEXPIRE# θα έχουν ένα #!# μπροστά από το ψευδώνυμο το οποίο θα το\n" +"λέπουν οι (επικεφαλείς) Services Operators.\n" +" \n" +"Παραδείγματα:\n" +"\n" +" #LIST *!joeuser@foo.com#\n" +" Εμφανίζει όλα τα κατοχυρωμένα ψευδώνυμα που ανήκουν στο joeuser@foo." +"com.\n" +"\n" +" #LIST *Bot*!*@*#\n" +" Εμφανίζει όλα τα κατοχυρωμένα ψευδώνυμα #Bot#.\n" +" \n" +" #LIST * NOEXPIRE#\n" +" Εμφανίζει όλα τα κατοχυρωμένα ψευδώνυμα που είναι σε no-expire.\n" +" " + +# +#: modules/commands/ns_list.cpp:139 +#, fuzzy +msgid "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." +msgstr "" +"Σύνταξη: #LIST #pattern# [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]#\n" +"\n" +"Δίνει την λίστα όλων των κατοχυρωμένων ψευδώνυμων που ταιριάζουν με το " +"ανάλογο\n" +"pattern, σε σύνταξη #nick!user@host#. Ψευδώνυμα με επιλογή #PRIVATE#\n" +"θα φαίνονται μόνο στους (επικεφαλείς) Services Operators. Ψευδώνυμα με\n" +"επιλογή #NOEXPIRE# θα έχουν ένα #!# μπροστά από το ψευδώνυμο το οποίο θα το\n" +"λέπουν οι (επικεφαλείς) Services Operators.\n" +" \n" +"Παραδείγματα:\n" +"\n" +" #LIST *!joeuser@foo.com#\n" +" Εμφανίζει όλα τα κατοχυρωμένα ψευδώνυμα που ανήκουν στο joeuser@foo." +"com.\n" +"\n" +" #LIST *Bot*!*@*#\n" +" Εμφανίζει όλα τα κατοχυρωμένα ψευδώνυμα #Bot#.\n" +" \n" +" #LIST * NOEXPIRE#\n" +" Εμφανίζει όλα τα κατοχυρωμένα ψευδώνυμα που είναι σε no-expire.\n" +" " + +# +#: modules/commands/os_list.cpp:132 +msgid "Lists all user records" +msgstr "Εμφανίζει όλους τους χρήστες" + +#: modules/commands/os_list.cpp:243 +#, fuzzy +msgid "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only " +"users\n" +"with the +i flag will be listed." +msgstr "" +"Σύνταξη: #USERLIST [{#επιλογή | κανάλι#} [#INVISIBLE#]]#\n" +"\n" +"Εμφανίζει τις λίστες όλων των χρηστών που είναι την συγκεκριμένη στιγμή\n" +"online στο IRC δίκτυο, είτε το ψευδώνυμο είναι κατοχυρωμένο είτε όχι.\n" +" \n" +"Αν η #επιλογή# δίνετε, εμφανίζονται οι λίστες με τους χρήστες που\n" +"ταιριάζουν με την επιλογή σας (πρέπει να είναι της μορφής ψευδώνυμο!" +"user@host).\n" +"Αν δίνετε το #κανάλι#, εμφανίζονται λίστες των χρηστών που είναι στο " +"κανάλι \n" +"αυτό. Αν δίνετε INVISIBLE, μόνο χρήστες με +i flag θα εμφανίζονται.\n" +" \n" +"Μόνο για τους #Services Operators#." + +# +#: modules/commands/ms_list.cpp:142 +msgid "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Σύνταξη: #LIST [#κανάλι#] [#list# | NEW]#\n" +"\n" +"Παρουσιάζει την λίστα των μηνυμάτων. Με την #NEW#, δείχνει\n" +"μόνο τα νέα μηνύματα (τα μη-διαβασμένα). Τα μη διαβασμένα μηνύματα\n" +"σημειώνονται με ένα \"*\"\tστα αριστερά που αναγράφεται ο αριθμός του\n" +"μηνύματος. Μπορείς να δεις μια λίστα με νούμερα,\n" +"σαν το παρακάτω παράδειγμα:\n" +"\n" +" #LIST 2-5,7-9#\n" +" Λίστα μηνυμάτων νούμερο 2 περνά 5 και 7 περνά 9." + +# +#: modules/commands/bs_botlist.cpp:19 +msgid "Lists available bots" +msgstr "Λίστα με διαθέσιμα bots" + +# +#: modules/commands/os_modinfo.cpp:196 +#, fuzzy +msgid "Lists currently loaded modules." +msgstr "Εμφανίζει όλα τα φορτωμένα Modules." + +# +#: modules/commands/cs_info.cpp:19 +#, fuzzy +msgid "Lists information about the specified registered channel" +msgstr "Εμφανίζει πληροφορίες για ένα κατωχυρωμένο κανάλι" + +#: modules/commands/cs_info.cpp:76 +#, fuzzy +msgid "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." +msgstr "" +"Σύνταξη: #INFO #κανάλι##\n" +"\n" +"Εμφανίζει πληροφορίες σχετικά με το όνομα του κατοχυρωμένου καναλιού,\n" +"περιλαμβανομένου τον founder, την ώρα της κατοχύρωσης, πότε " +"χρησιμοποιήθηκε \n" +"τελευταία φορά, και τα κλειδωμένα mode, αν υπάρχουν.\n" +"Αν χρησιμοποιήσετε την παράμετρο #ALL# \n" +"θα εμφανιστεί το μήνυμα εισαγωγής του καναλιού και ο successor. \n" +" \n" +"Από default, η επιλογή #ALL# είναι ορισμένη μόνο σε αυτούς που έχουν\n" +"founder access στο συγκεκριμένο κανάλι." + +# +#: modules/commands/os_module.cpp:19 +msgid "Load a module" +msgstr "Φορτώνει ένα module" + +#: modules/commands/cs_register.cpp:39 +msgid "Local channels cannot be registered." +msgstr "Κανάλια τοπικά δεν μπορούν να κατοχυρωθούν." + +#: modules/commands/cs_log.cpp:142 +#, fuzzy, c-format +msgid "Log list for %s:" +msgstr "Λίστα πρόσβασης για #%s#:" + +#: modules/commands/cs_log.cpp:227 +#, c-format +msgid "Logging changed for command %s on %s, now using log method %s%s%s." +msgstr "" + +#: modules/commands/cs_log.cpp:220 +#, c-format +msgid "Logging for command %s on %s with log method %s%s%s has been removed." +msgstr "" + +#: modules/commands/cs_log.cpp:248 +#, c-format +msgid "Logging is now active for command %s on %s, using log method %s%s%s." +msgstr "" + +#: modules/commands/os_login.cpp:60 +#, c-format +msgid "Login to %s" +msgstr "Κάντε login στο %s" + +#: modules/commands/os_news.cpp:36 +#, c-format +msgid "Logon news item #%d deleted." +msgstr "Κανονισμός ή πληροφορία στη θέση #%d διαγράφηκε." + +#: modules/commands/os_news.cpp:35 +#, c-format +msgid "Logon news item #%s not found!" +msgstr "Κανονισμός στη θέση #%s δεν βρέθηκε!" + +#: modules/commands/os_news.cpp:32 +msgid "Logon news items:" +msgstr "Κανονισμοί:" + +#: modules/commands/os_login.cpp:102 +#, fuzzy, c-format +msgid "Logout from %s" +msgstr "Κάντε login στο %s" + +#: modules/commands/os_login.cpp:52 +#, c-format +msgid "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." +msgstr "" +"Syntax: #LOGIN# #password#\n" +" \n" +"Σας κάνει login στο %s ώστε να αναγνωριστείτε ως Services Operator. \n" +"Αυτή η εντολή μπορεί να είναι άχρηστη αν στο oper block \n" +"σας δεν ζητείται password." + +#: modules/commands/os_login.cpp:94 +#, fuzzy, c-format +msgid "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." +msgstr "" +"Syntax: #LOGIN# #password#\n" +" \n" +"Σας κάνει login στο %s ώστε να αναγνωριστείτε ως Services Operator. \n" +"Αυτή η εντολή μπορεί να είναι άχρηστη αν στο oper block \n" +"σας δεν ζητείται password." + +#: modules/commands/cs_seen.cpp:213 +#, c-format +msgid "Looking for yourself, eh %s?" +msgstr "" + +#: modules/commands/cs_mode.cpp:773 +#, fuzzy, c-format +msgid "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a " +"channel.\n" +"If a mode is locked on or off, services will not allow that mode to be " +"changed. The SET\n" +"command will clear all existing mode locks and set the new one given, while " +"ADD and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * " +"and ? may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may " +"be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, " +"halfops, and voices. If what\n" +"is not given then all basic modes are removed." +msgstr "" +"Syntax: #MODE #channel# LOCK {ADD|DEL|LIST} [#what#]#\n" +" #MODE #channel# SET #modes##\n" +" \n" +"Κυρίως ελέγχει τα mode locks και mode access (διαφορετικό του channel " +"access)σε ένα κανάλι.\n" +"Η εντολή #MODE LOCK# επιτρέπει να προσθέσετε, αφαιρέσετε και να δελιτε τα " +"mode locksσε ένα κανάλι\n" +"Αν ένα mode είναι locked on ή off, τα services δε θα επιτρέψουν να αλλάξει.\n" +"Παράδειγμα:\n" +" #MODE #channel SET +v *#\n" +" Δίνει voice σε όλους τους χρήστες σε ένα κανάλι.\n" +" \n" +" #MODE #channel SET -b ~c:*\n" +" Διαγράφει όλα τα extended bans που ξεκινούν με ~c:" + +# +#: modules/commands/cs_akick.cpp:434 +msgid "Maintain the AutoKick list" +msgstr "Συντηρεί τη λίστα αυτόματης απόρριψης" + +# +#: modules/commands/bs_bot.cpp:269 +msgid "Maintains network bot list" +msgstr "Αλλάζει την λίστα των bot του δικτύου" + +#: modules/commands/cs_xop.cpp:522 +#, c-format +msgid "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " +msgstr "" + +#: modules/commands/cs_akick.cpp:493 +#, c-format +msgid "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" +msgstr "" + +#: modules/commands/cs_access.cpp:568 +#, c-format +msgid "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." +msgstr "" + +#: modules/commands/bs_badwords.cpp:424 +#, fuzzy, c-format +msgid "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" +msgstr "" +"Σύνταξη: #BADWORDS #κανάλι# ADD #λέξη# [#SINGLE# | #START# | #END#]#\n" +" #BADWORDS #κανάλι# DEL {#λέξη# | #θέση-νου# | #list#}#\n" +" #BADWORDS #κανάλι# LIST [#μάσκα# | #list#]#\n" +" #BADWORDS #κανάλι# CLEAR#\n" +"\n" +"Αλλάζει την #bad words λίστα# του καναλιού. Η λίστα bad\n" +"words δείχνει ποιές λέξεις είναι να γίνεται το kick,\n" +"όταν το bad words kick είναι ενεργοποιημένο. Για περισσότερες πληροφορίες,\n" +"γράφτε #/msg %s HELP KICK BADWORDS#.\n" +"\n" +"Η εντολή #BADWORDS ADD# προσθέτει μια κακιά λέξη στην λίστα\n" +"badword. Αν πεί αυτη τη λέξη (SINGLE), τότε θα γίνεται\n" +"kick. Αν ξεκινάει με αυτή τη λέξη (START) τότε θα γίνεται \n" +"kick ο χρήστης επειδή ξεκίνησε με αυτη τη #λέξη#. Αν στο τέλος της λέξης \n" +"προσθέσει την κακιά λέξη (END) θα γίνεται kick επειδή την είπε στο τέλος \n" +"της φράσης/#λέξης#. Αν δεν είστε συγκεκριμένος τότε θα γίνεται kick\n" +"όποτε θα λέει συγκεκριμένα αυτή τη #λέξη#.\n" +" \n" +"Η εντολή #BADWORDS DEL# αφαιρεί την λέξη αυτή από την λίστα\tbadwords.\n" +"Αν σας δίνετε η λίστα με τις θέσεις-νούμερα, αυτές οι θέσεις θα διαγραφούν\n" +"(Δες το παράδειγμα με την εντολή LIST.)\n" +"\n" +"Η εντολή #BADWORDS LIST# εμφανίζει την λίστα με τις κακές λέξεις. Αν " +"δώσετε\n" +"συγκεκριμένη λέξη, θα εμφανιστούν οι θέσεις που ταιριάζουν με αυτήν.\n" +"Παράδειγμα:\n" +"\n" +" #BADWORDS #κανάλι LIST 2-5,7-9#\n" +" Εμφανίζει από την λίστα τις θέσεις με τα νούμερα 2 έως 5 και\n" +" 7 έως 9.\n" +" \n" +"Η εντολή #BADWORDS CLEAR# καθαρίζει όλες τις θέσεις από την λίστα\n" +"badword." + +# +#: modules/commands/bs_badwords.cpp:370 +#, fuzzy +msgid "Maintains the bad words list" +msgstr "Αλλάζετε την λίστα κακών λέξεων" + +# +#: modules/commands/bs_control.cpp:79 +msgid "Makes the bot do the equivalent of a \"/me\" command" +msgstr "Κάνει το bot να εκτελέσει μια εντολή \"/me\" " + +#: modules/commands/bs_control.cpp:127 +#, fuzzy +msgid "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." +msgstr "" +"Σύνταξη: #ACT #κανάλι# #μήνυμα##\n" +"\n" +"Κάνει το bot να ενεργεί,δηλ να εκτελεί εντολή \"/me\"\n" +"εμφανίζοντας το μήνυμα στο ανάλογο κανάλι." + +# +#: modules/commands/bs_control.cpp:19 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel" +msgstr "Κάνει το bot να πεί ένα κείμενο σε ένα κανάλι" + +# +#: modules/commands/bs_control.cpp:69 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel." +msgstr "Κάνει το bot να πεί ένα κείμενο σε ένα κανάλι" + +#: modules/commands/greet.cpp:157 +#, fuzzy +msgid "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." +msgstr "" +"Syntax: #SASET #nickname# GREET #message##\n" +"\n" +"Ορίζει ένα μήνυμα greet με ένα ψευδόνυμο, που παρουσιάζεται\n" +"όταν ο χρήστης μπαίνει σε κανάλια που εχουν ενεργή την επιλογή GREET,\n" +"όταν ο χρήστης έχει αρκετή access στο κανάλι." + +#: modules/commands/greet.cpp:131 +#, fuzzy +msgid "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." +msgstr "" +"Σύνταξη: #SET GREET #message##\n" +"\n" +"Προσθέτει στο ψευδώνυμού σου ένα μήνυμα χαιρετισμού, το\n" +"οποίο θα εμφανίζεται κάθε φορα που θα μπένεις σε κανάλι με την προυπόθεση " +"οτι\n" +"η επιλογή GREET θα είναι ενεργοποιημένη, και με την προυπόθεση οτι θα έχεις\n" +"και την κατάλληλη access σε αυτό. " + +#: modules/commands/os_dns.cpp:660 +#, fuzzy +msgid "Manage DNS zones for this network" +msgstr "" +"Δεν μπορείς να απενεργοποιήσεις την διεύθυνση του e-mail σε αυτό το δίκτυο." + +# +#: modules/commands/cs_entrymsg.cpp:193 +msgid "Manage the channel's entry messages" +msgstr "Κάνει το κανάλι permanent." + +# +#: modules/commands/ms_ignore.cpp:19 +#, fuzzy +msgid "Manage the memo ignore list" +msgstr "Συντηρεί την Services ignore list" + +# +#: modules/commands/ns_ajoin.cpp:230 +msgid "Manage your auto join list" +msgstr "Συντηρεί τη λίστα αυτόματης εισόδου" + +# +#: modules/commands/os_sxline.cpp:233 +#, fuzzy, c-format +msgid "Manipulate the %s list" +msgstr "Προσθέτει ip κλπ στην λίστα AKILL" + +# +#: modules/commands/os_akill.cpp:385 +msgid "Manipulate the AKILL list" +msgstr "Προσθέτει ip κλπ στην λίστα AKILL" + +# +#: modules/commands/os_defcon.cpp:176 +msgid "Manipulate the DefCon system" +msgstr "Διαχειρίζεται το σύστημα DefCon" + +# +#: modules/commands/cs_topic.cpp:149 +msgid "Manipulate the topic of the specified channel" +msgstr "Αλλάζει το topic σε ένα κανάλι." + +#: modules/commands/bs_botlist.cpp:27 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_forbid.cpp:358 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/ms_ignore.cpp:86 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_list.cpp:153 modules/commands/bs_info.cpp:55 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +msgid "Mask" +msgstr "" + +#: modules/commands/ns_access.cpp:39 +#, fuzzy, c-format +msgid "Mask %s already present on %s's access list." +msgstr "Η μάσκα #%s# είναι ήδη μέσα στην λίστα πρόσβασης." + +#: include/language.h:67 +msgid "Mask must be in the form user@host." +msgstr "" + +#: modules/commands/cs_access.cpp:166 modules/commands/cs_flags.cpp:120 +#: modules/commands/cs_xop.cpp:162 +#, fuzzy +msgid "Masks and unregistered users may not be on access lists." +msgstr "Η μάσκα #%s# είναι ήδη μέσα στην λίστα πρόσβασης." + +# +#: modules/commands/ns_getemail.cpp:23 +msgid "Matches and returns all users that registered using given email" +msgstr "Εμφανίζει τους χρήστες που έκαναν register με ένα συγκεκριμένο email" + +#: modules/commands/os_logsearch.cpp:148 +#, fuzzy, c-format +msgid "Matches for %s:" +msgstr " Επιλογές κλειδώματος: %s" + +#: modules/commands/os_stats.cpp:139 +#, c-format +msgid "Maximum users: %d (%s)" +msgstr "Μέγιστοι χρήστες: #%d# (%s)" + +#: modules/commands/ms_read.cpp:84 modules/commands/ms_read.cpp:86 +#, fuzzy, c-format +msgid "Memo %d from %s (%s)." +msgstr " Επιλογές κλειδώματος: %s" + +#: modules/commands/ms_del.cpp:33 modules/commands/ms_del.cpp:101 +#, c-format +msgid "Memo %d has been deleted." +msgstr "Μήνυμα %d διαγράφηκε." + +# +#: modules/commands/ms_ignore.cpp:82 +#, fuzzy +msgid "Memo ignore list is empty." +msgstr "Η λίστα σας ανεπιθύμητων memo είναι άδεια." + +#: modules/commands/ms_set.cpp:199 +#, c-format +msgid "Memo limit disabled for %s." +msgstr "Το όριο μηνυμάτων #απενεργοποιήθηκε# για τον %s." + +#: modules/commands/ms_set.cpp:185 +#, c-format +msgid "Memo limit for %s set to %d." +msgstr "Το όριο μηνυμάτων για τον %s άλλαξε σε #%d#." + +#: modules/commands/ms_set.cpp:192 +#, c-format +msgid "Memo limit for %s set to 0." +msgstr "Το όριο μηνυμάτων για τον %s άλλαξε σε #0#." + +#: modules/commands/ms_rsend.cpp:63 modules/commands/ms_send.cpp:51 +#, c-format +msgid "Memo sent to %s." +msgstr "Το μήνυμα στάλθηκε στον #%s#." + +#: modules/commands/ms_list.cpp:131 +#, fuzzy, c-format +msgid "Memos for %s:" +msgstr " Επιλογές κλειδώματος: %s" + +#: modules/commands/cs_entrymsg.cpp:116 +#, fuzzy +msgid "Message" +msgstr "Επιλογή μηνύματος" + +#: modules/commands/ns_set.cpp:1313 +msgid "Message mode" +msgstr "Επιλογή μηνύματος" + +#: modules/commands/cs_log.cpp:127 +msgid "Method" +msgstr "" + +#: modules/commands/cs_mode.cpp:329 modules/commands/cs_mode.cpp:420 +#, c-format +msgid "Missing parameter for mode %c." +msgstr "" + +#: modules/commands/cs_mode.cpp:449 +msgid "Mode" +msgstr "" + +#: modules/commands/cs_mode.cpp:718 +#, fuzzy, c-format +msgid "Mode %s is a virtual mode and can't be cleared." +msgstr "Το Nick #%s# είναι παράνομο και δεν μπορεί να χρησιμοποιηθεί." + +#: modules/commands/cs_mode.cpp:712 +#, fuzzy, c-format +msgid "Mode %s is not a status or list mode." +msgstr "Ο/η #%s# δεν βρέθηκε στη λίστα αγνόησης σου." + +#: modules/commands/cs_mode.cpp:1065 +#, fuzzy +msgid "Mode lock" +msgstr " Επιλογές κλειδώματος: %s" + +#: modules/commands/cs_mode.cpp:466 +#, c-format +msgid "Mode locks for %s:" +msgstr " Επιλογές κλειδώματος: %s" + +#: modules/commands/os_list.cpp:43 +msgid "Modes" +msgstr "" + +#: modules/commands/os_mode.cpp:44 +#, c-format +msgid "Modes cleared on %s and the channel destroyed." +msgstr "" + +#: modules/commands/ns_access.cpp:166 +#, fuzzy, c-format +msgid "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." +msgstr "" +"Σύνταξη: #ACCESS ADD ^_μάσκα^_#\n" +" #ACCESS DEL ^_μάσκα^_#\n" +" #ACCESS LIST#\n" +"\n" +"Αλλάζει ή εμφανίζει τη λίστα πρόσβασης του ψευδωνύμου σας.\n" +"Αυτή είναι η λίστα των διευθύνσεων που θα αναγνωρίζονται\n" +"αυτόματα από τον %s σαν επιτρεπτοί για τη χρήση\n" +"του ψευδωνύμου. Αν θέλετε να χρησιμοποιήσετε το ψευδώνυμο\n" +"από μία διαφορετική διεύθυνση, πρέπει να αναγνωριστείτε\n" +"από τον %s με τη χρήση της εντολής #IDENTIFY#.\n" +"\n" +"Παραδείγματα:\n" +"\n" +" #ACCESS ADD anyone@*.bepeg.com#\n" +" Επιτρέπει πρόσβαση στο χρήστη με ID #anyone#\n" +" από οποιοδήποτε υπολογιστή της διεύθυνσης #bepeg.com#.\n" +"\n" +" #ACCESS DEL anyone@*.bepeg.com#\n" +" Αναιρεί την προηγούμενη εντολή.\n" +" \n" +" #ACCESS LIST#\n" +" Εμφανίζει την τρέχουσα λίστα πρόσβασης.\n" +" " + +#: modules/commands/ns_cert.cpp:319 +msgid "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" +msgstr "" + +# +#: modules/commands/os_ignore.cpp:341 +msgid "Modify the Services ignore list" +msgstr "Τροποποιεί την Services Ignore List" + +# +#: modules/commands/cs_xop.cpp:489 +#, fuzzy, c-format +msgid "Modify the list of %s users" +msgstr "Αλλάζει την λίστα των AOP χρηστών" + +# +#: modules/commands/ns_access.cpp:101 +msgid "Modify the list of authorized addresses" +msgstr "Αλλάζει τη λίστα των εξουσιοδοτημένων διευθύνσεων" + +# +#: modules/commands/cs_access.cpp:498 modules/commands/cs_flags.cpp:373 +msgid "Modify the list of privileged users" +msgstr "Αλλάζει τη λίστα των εξουσιοδοτημένων χρηστών" + +# +#: modules/commands/ns_cert.cpp:257 +#, fuzzy +msgid "Modify the nickname client certificate list" +msgstr "Τροποποιεί την Services Ignore List" + +# +#: modules/commands/os_session.cpp:522 +msgid "Modify the session-limit exception list" +msgstr "Αλλάζεις την λίστα του session-limit exception" + +#: modules/commands/os_module.cpp:34 +#, c-format +msgid "Module %s is already loaded." +msgstr "Το Module #%s# είναι ήδη φορτωμένο." + +#: modules/commands/os_module.cpp:67 modules/commands/os_module.cpp:139 +#, c-format +msgid "Module %s isn't loaded." +msgstr "Το Module #%s# δεν είναι φορτωμένο." + +#: modules/commands/os_module.cpp:31 +#, fuzzy, c-format +msgid "Module %s loaded." +msgstr "Το Module #%s# φορτώθηκε." + +#: modules/commands/os_module.cpp:98 +#, fuzzy, c-format +msgid "Module %s reloaded." +msgstr "Το Module #%s# ξαναφορτώθηκε" + +#: modules/commands/os_module.cpp:156 +#, fuzzy, c-format +msgid "Module %s unloaded." +msgstr "Το Module #%s# ξεφορτώθηκε" + +#: modules/commands/os_config.cpp:88 +#, fuzzy +msgid "Module Name" +msgstr "Το Module #%s# φορτώθηκε." + +#: modules/commands/os_config.cpp:112 +msgid "Module settings:" +msgstr "" + +#: modules/commands/os_modinfo.cpp:32 +#, fuzzy, c-format +msgid "Module: %s Version: %s Author: %s Loaded: %s" +msgstr "Module: #%s# Έκδωση: #%s# Συγγραφέας: #%s# φορτώθηκε: #%s#" + +#: modules/commands/os_modinfo.cpp:183 +#, c-format +msgid "Module: %s [%s] [%s]" +msgstr "Module: #%s# [%s] [%s]" + +#: modules/commands/cs_access.cpp:697 modules/commands/cs_access.cpp:799 +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +#: modules/commands/cs_list.cpp:75 modules/commands/os_list.cpp:43 +#: modules/commands/os_list.cpp:153 +msgid "Name" +msgstr "" + +#: modules/commands/os_oper.cpp:153 +msgid "Name Type" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:146 +#, fuzzy, c-format +msgid "Network stats for %s:" +msgstr "Λίστα πρόσβασης για #%s#:" + +#: modules/commands/os_forbid.cpp:384 +msgid "Never" +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/bs_botlist.cpp:27 +#: modules/commands/hs_request.cpp:305 modules/commands/ns_list.cpp:75 +#: modules/commands/ns_group.cpp:327 +msgid "Nick" +msgstr "" + +#: modules/commands/ns_register.cpp:42 +#, c-format +msgid "Nick %s has been confirmed." +msgstr "Το ψευδώνυμο #%s# σβήστηκε επιτυχώς από την υπηρεσία." + +#: modules/commands/os_oper.cpp:95 +#, c-format +msgid "Nick %s is already an operator." +msgstr "Το κανάλι #%s# είναι ήδη κατοχυρωμένο!" + +#: modules/commands/ns_register.cpp:36 +#, c-format +msgid "Nick %s is already confirmed." +msgstr "Αυτό το ψευδώνυμο #%s# είναι ήδη κατοχυρωμένο!" + +#: modules/commands/os_svs.cpp:46 +#, c-format +msgid "Nick %s is an illegal nickname and cannot be used." +msgstr "Το Nick #%s# είναι παράνομο και δεν μπορεί να χρησιμοποιηθεί." + +#: modules/commands/bs_bot.cpp:81 modules/commands/bs_bot.cpp:181 +#: modules/commands/os_svs.cpp:54 +#, c-format +msgid "Nick %s is currently in use." +msgstr "Το Nick #%s# δεν χρησιμοποιείται αυτή τη στιγμή." + +#: modules/commands/os_forbid.cpp:512 +#, fuzzy, c-format +msgid "Nick %s is forbidden by %s: %s" +msgstr "Το Nick #%s# δεν χρησιμοποιείται αυτή τη στιγμή." + +#: modules/commands/os_forbid.cpp:514 +#, fuzzy, c-format +msgid "Nick %s is forbidden." +msgstr "Το ψευδώνυμο #%s# δεν κρατείται.." + +#: modules/commands/os_oper.cpp:134 +#, fuzzy, c-format +msgid "Nick %s is not a Services Operator." +msgstr "%s είναι services operator τού τύπου %s." + +#: modules/commands/ns_info.cpp:34 +#, c-format +msgid "Nick %s is part of this Network's Services." +msgstr "Το Nick #%s# είναι μέρος των Network Services." + +#: include/language.h:79 +#, c-format +msgid "Nick %s isn't currently in use." +msgstr "Το Nick #%s# δεν χρησιμοποιείται αυτή τη στιγμή." + +#: include/language.h:78 +#, c-format +msgid "Nick %s isn't registered." +msgstr "Το Nickname %s κατωχυρώθηκε." + +#: modules/commands/os_svs.cpp:39 +#, c-format +msgid "Nick %s was truncated to %d characters." +msgstr "Το Nick #%s# περικόπηκε σε %d χαρακτήρες." + +#: modules/commands/ns_set.cpp:1135 +#, c-format +msgid "Nick %s will expire." +msgstr "Το Nick %s #θα# λήξει." + +#: modules/commands/ns_set.cpp:1129 +#, c-format +msgid "Nick %s will not expire." +msgstr "Το Nick %s #δεν θα# λήξει." + +#: modules/commands/ms_check.cpp:60 +#, c-format +msgid "Nick %s doesn't have a memo from you." +msgstr "Το Nick %s δεν έχει memo από εσάς." + +#: modules/commands/ns_logout.cpp:48 +#, c-format +msgid "Nick %s has been logged out." +msgstr "Το ψευδώνυμό σου %s δεν κατέχεται για την ώρα." + +#: modules/commands/ns_group.cpp:272 +#, c-format +msgid "Nick %s has been ungrouped from %s." +msgstr "Το Nick %s έγινε ungroup από το %s." + +#: include/language.h:81 +#, c-format +msgid "Nick %s is currently suspended." +msgstr "Το Nick %s έγινε suspended." + +#: modules/commands/ns_group.cpp:250 +#, fuzzy, c-format +msgid "Nick %s is not in your group." +msgstr "Tο nick %s δεν είναι στο group σας." + +#: modules/commands/ns_suspend.cpp:180 +#, fuzzy, c-format +msgid "Nick %s is not suspended." +msgstr "Το Nick %s έγινε suspended." + +#: modules/commands/ns_suspend.cpp:190 +#, c-format +msgid "Nick %s is now released." +msgstr "Το Nick %s απελευθερώθηκε." + +#: modules/commands/ns_suspend.cpp:138 +#, c-format +msgid "Nick %s is now suspended." +msgstr "Το Nick %s έγινε suspended." + +#: modules/commands/cs_seen.cpp:275 +#, c-format +msgid "Nick too long, max length is %u characters." +msgstr "" + +#: modules/commands/ns_drop.cpp:53 +#, c-format +msgid "Nickname %s has been dropped." +msgstr "Το ψευδώνυμο #%s# σβήστηκε επιτυχώς από την υπηρεσία." + +#: include/language.h:97 +#, c-format +msgid "Nickname %s is already registered!" +msgstr "Το κανάλι #%s# είναι ήδη κατοχυρωμένο!" + +#: include/language.h:96 +#, c-format +msgid "Nickname %s may not be registered." +msgstr "Το κανάλι #%s# δεν μπορεί να κατοχυρωθεί." + +#: modules/commands/ns_register.cpp:226 +#, fuzzy, c-format +msgid "Nickname %s registered under your user@host-mask: %s" +msgstr "Αυτό το ψευδώνυμο #%s# κατοχυρώθηκε υπό την διεύθυνσή σου: %s" + +#: modules/commands/ns_register.cpp:228 +#, c-format +msgid "Nickname %s registered." +msgstr "Το κανάλι #%s# δεν μπορεί να κατοχυρωθεί." + +#: modules/commands/cs_set.cpp:1307 +#, fuzzy +msgid "No auto-op" +msgstr "Auto-op" + +#: modules/commands/bs_assign.cpp:252 +msgid "No bot" +msgstr "Κανένα bot" + +# +#: modules/commands/cs_set.cpp:1303 modules/commands/ns_set.cpp:1317 +msgid "No expire" +msgstr "δεν λήγει ποτέ" + +#: modules/commands/help.cpp:184 +#, c-format +msgid "No help available for %s." +msgstr "Δεν υπάρχει διαθέσιμη βοήθεια για #%s#." + +#: modules/commands/os_modinfo.cpp:61 +#, fuzzy, c-format +msgid "No information about module %s is available." +msgstr "Καμια πληροφορία για το module #%s# δεν είναι διαθέσιμη" + +#: modules/commands/cs_enforce.cpp:177 +#, fuzzy, c-format +msgid "No limit is set on %s." +msgstr "Το όριο μηνυμάτων για τον %s άλλαξε σε #%d#." + +#: modules/commands/os_news.cpp:37 +msgid "No logon news items to delete!" +msgstr "Κανένας Κανονισμός ή πληροφορία για να διαγραφεί!" + +#: modules/commands/os_logsearch.cpp:133 +#, fuzzy, c-format +msgid "No matches for %s found." +msgstr "Δεν υπάρχει κανένα email για το #%s#." + +#: modules/commands/cs_xop.cpp:294 +#, c-format +msgid "No matching entries on %s %s list." +msgstr "Δεν βρέθηκαν θέσεις στην AOP λίστα του %s %s." + +#: modules/commands/cs_access.cpp:269 modules/commands/cs_access.cpp:433 +#: modules/commands/cs_flags.cpp:335 modules/commands/cs_xop.cpp:428 +#, c-format +msgid "No matching entries on %s access list." +msgstr "Δεν βρέθηκαν θέσεις στου %s στην access list." + +#: modules/commands/cs_akick.cpp:224 modules/commands/cs_akick.cpp:368 +#, c-format +msgid "No matching entries on %s autokick list." +msgstr "Δεν βρέθηκαν θέσεις στην autokick list του %s." + +#: modules/commands/bs_badwords.cpp:166 modules/commands/bs_badwords.cpp:246 +#, c-format +msgid "No matching entries on %s bad words list." +msgstr "Δεν βρέθηκαν οι θέσεις στην λίστα των κακών λέξεων του %s." + +#: modules/commands/os_session.cpp:145 modules/commands/os_session.cpp:490 +msgid "No matching entries on session-limit exception list." +msgstr "Δεν βρέθηκαν θέσεις στην λίστα session-limit exception." + +#: modules/commands/os_sxline.cpp:28 modules/commands/os_sxline.cpp:177 +#, fuzzy, c-format +msgid "No matching entries on the %s list." +msgstr "Δεν βρέθηκαν θέσεις στην AOP λίστα του %s %s." + +#: modules/commands/os_akill.cpp:29 modules/commands/os_akill.cpp:320 +msgid "No matching entries on the AKILL list." +msgstr "Δεν βρέθηκαν θέσεις στην λίστα AKILL." + +#: modules/commands/ms_cancel.cpp:77 +msgid "No memo was cancelable." +msgstr "Κανένα μήνυμα δεν ακυρώθηκε." + +#: modules/commands/ms_read.cpp:65 +msgid "No memos to display." +msgstr "" + +#: modules/commands/os_modinfo.cpp:187 +#, fuzzy +msgid "No modules currently loaded matching that criteria." +msgstr "Κανένα module δεν είναι φορτωμένο" + +#: modules/commands/ns_recover.cpp:55 +msgid "No one is using your nick, and services are not holding it." +msgstr "" + +#: modules/commands/os_login.cpp:30 modules/commands/os_login.cpp:77 +msgid "No oper block for your nick." +msgstr "Κανένα oper block για το ψευδόνυμό σας." + +#: modules/commands/os_news.cpp:47 +msgid "No oper news items to delete!" +msgstr "Δεν υπάρχουν θέσεις στην λίστα για να διαγράψεις!" + +#: modules/commands/os_news.cpp:57 +msgid "No random news items to delete!" +msgstr "Δεν βρέθηκαν μηνύματα για να διαγραφούν!" + +#: modules/commands/hs_list.cpp:111 +msgid "No records to display." +msgstr "" + +#: modules/commands/ns_getemail.cpp:47 +#, fuzzy, c-format +msgid "No registrations matching %s were found." +msgstr "* Δεν επιτρέπονται οι κατοχυρώσεις ψευδονύμου." + +#: modules/commands/hs_request.cpp:220 modules/commands/hs_request.cpp:276 +#, c-format +msgid "No request for nick %s found." +msgstr "" + +#: src/access.cpp:55 +msgid "No signed kick when SIGNKICK LEVEL is used" +msgstr "" + +#: modules/extra/stats/cs_fantasy_top.cpp:159 +#: modules/extra/stats/cs_fantasy_stats.cpp:156 +#, fuzzy, c-format +msgid "No stats for %s." +msgstr "Λίστα πρόσβασης για #%s#:" + +#: modules/commands/os_info.cpp:201 +#, fuzzy, c-format +msgid "No such info \"%s\" on %s." +msgstr "Ο/η #%s# προσκαλέσθηκε στο κανλάλι #%s#." + +#: modules/commands/cs_ban.cpp:219 modules/commands/cs_kick.cpp:118 +#, fuzzy, c-format +msgid "No users on %s match %s." +msgstr "Τα usermodes του #%s# άλλαξαν." + +#: modules/commands/bs_assign.cpp:188 +#, fuzzy, c-format +msgid "No-bot mode is now off on channel %s." +msgstr "Κανένα Bot έχει επιλογή #ON# στο κανάλι %s." + +#: modules/commands/bs_assign.cpp:181 +#, fuzzy, c-format +msgid "No-bot mode is now on on channel %s." +msgstr "Κανένα Bot έχει επιλογή #ON# στο κανάλι %s." + +#: modules/commands/os_mode.cpp:64 +#, c-format +msgid "Non-status modes cleared on %s." +msgstr "" + +#: modules/commands/os_dns.cpp:226 modules/commands/bs_info.cpp:58 +msgid "None" +msgstr "Κανένα" + +#: modules/commands/cs_set.cpp:1029 +#, c-format +msgid "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." +msgstr "" + +#: modules/commands/cs_mode.cpp:380 modules/commands/cs_mode.cpp:437 +msgid "Nothing to do." +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:201 modules/commands/ms_list.cpp:64 +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_log.cpp:127 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +#: modules/commands/ns_ajoin.cpp:100 +msgid "Number" +msgstr "" + +#: modules/commands/os_news.cpp:41 +msgid "OPERNEWS {ADD|DEL|LIST} [text|num]" +msgstr "OPERNEWS {ADD|DEL|LIST} [#περιεχόμενο#|#νούμερο#]#\t" + +#: modules/commands/ns_info.cpp:68 modules/commands/ns_info.cpp:72 +#, fuzzy +msgid "Online from" +msgstr " Είναι συνδεδεμένος από: %s" + +#: modules/commands/os_oper.cpp:138 +#, c-format +msgid "" +"Oper %s is configured in the configuration file(s) and can not be removed by " +"this command." +msgstr "" + +#: modules/commands/os_info.cpp:268 +msgid "Oper Info" +msgstr "" + +#: modules/commands/os_info.cpp:182 modules/commands/os_info.cpp:221 +#, fuzzy, c-format +msgid "Oper info list for %s is empty." +msgstr "Η λίστα access του #%s# είναι άδεια." + +#: modules/commands/os_news.cpp:46 +#, c-format +msgid "Oper news item #%d deleted." +msgstr "Η θέση #%d διαγράφηκε." + +#: modules/commands/os_news.cpp:45 +#, c-format +msgid "Oper news item #%s not found!" +msgstr "Η θέση #%s στην λίστα δεν βρέθηκε!" + +#: modules/commands/os_news.cpp:42 +msgid "Oper news items:" +msgstr "Νέα των Opers:" + +#: modules/commands/os_oper.cpp:148 +#, c-format +msgid "Oper privileges removed from %s (%s)." +msgstr "" + +#: modules/commands/os_oper.cpp:101 modules/commands/os_oper.cpp:189 +#, c-format +msgid "Oper type %s has not been configured." +msgstr "Το ψευδώνυμο #%s# σβήστηκε επιτυχώς από την υπηρεσία." + +#: modules/commands/os_oline.cpp:37 +#, c-format +msgid "Operflags %s have been added for %s." +msgstr "μια O:Line με τα flags #%s# προστέθηκε για τον #%s#." + +#: modules/commands/os_oline.cpp:43 +#, fuzzy, c-format +msgid "Operflags %s have been removed from %s." +msgstr "μια O:Line με τα flags #%s# προστέθηκε για τον #%s#." + +#: modules/commands/os_oper.cpp:193 +#, c-format +msgid "Opertype %s has no allowed commands." +msgstr "" + +#: modules/commands/os_oper.cpp:215 +#, c-format +msgid "Opertype %s has no allowed privileges." +msgstr "" + +#: modules/commands/os_oper.cpp:237 +#, c-format +msgid "Opertype %s receives modes %s once identified." +msgstr "" + +#: modules/commands/bs_kick.cpp:1219 +msgid "Ops protection" +msgstr "Προστασία στους Ops" + +#: src/misc.cpp:258 modules/commands/bs_info.cpp:58 +#, fuzzy +msgid "Options" +msgstr " Επιλογές : %s" + +#: modules/commands/os_dns.cpp:668 +#, fuzzy +msgid "POOL server.name" +msgstr "NOOP {SET|REVOKE} #server#" + +#: modules/commands/cs_mode.cpp:449 +msgid "Param" +msgstr "" + +#: modules/commands/ns_identify.cpp:38 +msgid "Password accepted - you are now recognized." +msgstr "Ο κωδικός έγινε δεκτός - τώρα είσαι αναγνωρισμένος." + +# +#: modules/commands/os_login.cpp:44 +msgid "Password accepted." +msgstr "Λάθος κωδικός." + +#: include/language.h:85 +msgid "Password authentication required for that command." +msgstr "" + +#: modules/commands/ns_set.cpp:152 modules/commands/ns_set.cpp:218 +#, c-format +msgid "Password for %s changed to %s." +msgstr "Ο Successor του %s άλλαξε και πήγε στον #%s#." + +#: modules/commands/ns_set.cpp:154 modules/commands/ns_set.cpp:220 +#, fuzzy, c-format +msgid "Password for %s changed." +msgstr "Ο κωδικός για τον %s είναι #%s#." + +#: modules/commands/ns_getpass.cpp:38 +#, c-format +msgid "Password for %s is %s." +msgstr "Ο κωδικός για τον %s είναι #%s#." + +# +#: include/language.h:71 +msgid "Password incorrect." +msgstr "Λάθος κωδικός." + +#: modules/commands/ns_resetpass.cpp:39 +#, c-format +msgid "Password reset email for %s has been sent." +msgstr "Αλλαγή κωδικού για το ψευδόνυμο #%s# στάλθηκε." + +#: modules/commands/cs_set.cpp:1289 +msgid "Peace" +msgstr "Ειρηνικό" + +#: modules/commands/cs_set.cpp:440 +#, c-format +msgid "Peace option for %s is now off." +msgstr "Η Peace επιλογή για το %s #ΑΠΕΝΕΡΓΟΠΟΙΉΘΗΚΕ#." + +#: modules/commands/cs_set.cpp:434 +#, c-format +msgid "Peace option for %s is now on." +msgstr "Η Peace επιλογή για το %s #ΕΝΕΡΓΟΠΟΙΉΘΗΚΕ#." + +#: modules/commands/cs_set.cpp:1301 +#, fuzzy +msgid "Persistent" +msgstr "Persistant" + +#: include/language.h:126 +msgid "Please contact an Operator to get a vHost assigned to this nick." +msgstr "" + +#: include/language.h:73 +msgid "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." +msgstr "" + +#: modules/commands/os_jupe.cpp:30 +#, fuzzy +msgid "Please use a valid server name when juping." +msgstr "Παρακαλώ διαλέξτε ένα έγκυρο όνομα server όταν κάνετε jupe" + +#: include/language.h:104 +msgid "Please use the symbol of # when attempting to register." +msgstr "" + +#: src/mail.cpp:78 +#, c-format +msgid "Please wait %d seconds and retry." +msgstr "Παρακαλώ περίμενε #%d# δευτερόλεπτα και ξαναπροσπάθησε." + +#: modules/commands/hs_request.cpp:158 +#, fuzzy, c-format +msgid "Please wait %d seconds before requesting a new vHost." +msgstr "" +"Παρακαλώ περίμενε %d δευτερόλεπτα πριν χρησιμοποιήσεις την εντολή SEND ξανά." + +#: modules/commands/ms_rsend.cpp:58 modules/commands/ms_send.cpp:57 +#, fuzzy, c-format +msgid "Please wait %d seconds before using the %s command again." +msgstr "" +"Παρακαλώ περίμενε %d δευτερόλεπτα πριν χρησιμοποιήσεις την εντολή SEND ξανά." + +#: modules/commands/ns_group.cpp:149 +#, c-format +msgid "Please wait %d seconds before using the GROUP command again." +msgstr "" +"Παρακαλώ περίμενε %d δευτερόλεπτα και μετά ξαναχρησιμοποίησε την εντολή " +"ομαδοποίησης." + +#: modules/commands/ns_register.cpp:198 +#, c-format +msgid "Please wait %d seconds before using the REGISTER command again." +msgstr "" +"Παρακαλώ περίμενε %d δευτερόλεπτα και μετά ξαναχρησιμοποίησε την εντολή " +"κατοχύρωσης ξανά." + +#: modules/commands/os_dns.cpp:628 +#, c-format +msgid "Pooled %s." +msgstr "" + +#: modules/commands/os_dns.cpp:237 +msgid "Pooled/Active" +msgstr "" + +#: modules/commands/os_dns.cpp:239 +msgid "Pooled/Not Active" +msgstr "" + +#: modules/commands/bs_set.cpp:161 +msgid "Prevent a bot from being assigned by non IRC operators" +msgstr "" + +# +#: modules/commands/bs_assign.cpp:153 +#, fuzzy +msgid "Prevent a bot from being assigned to a channel" +msgstr "" +"Απαγορεύστε τη χρήση ενός καναλιού, διατηρώντας τις ρυθμίσεις και τις " +"πληροφορίες του" + +# +#: modules/commands/cs_suspend.cpp:58 +msgid "Prevent a channel from being used preserving channel data and settings" +msgstr "" +"Απαγορεύστε τη χρήση ενός καναλιού, διατηρώντας τις ρυθμίσεις και τις " +"πληροφορίες του" + +# +#: modules/commands/cs_set.cpp:1043 +msgid "Prevent the channel from expiring" +msgstr "Κάντε ένα κανάλι να μη λήγει ποτέ." + +#: modules/commands/ns_list.cpp:186 +#, fuzzy +msgid "Prevent the nickname from appearing in the LIST command" +msgstr "Κάντε ένα nick να μή φαίνεται στην εντολή #/msg %s LIST#" + +# +#: modules/commands/ns_set.cpp:1104 +msgid "Prevent the nickname from expiring" +msgstr "Κάντε ένα nickname να μη λήγει ποτέ." + +#: src/access.cpp:46 +msgid "Prevents users being kicked by Services" +msgstr "" + +#: modules/commands/ns_list.cpp:297 modules/commands/cs_list.cpp:262 +#: modules/commands/bs_info.cpp:58 +msgid "Private" +msgstr "Μυστικότητα" + +#: modules/commands/bs_set.cpp:190 +#, c-format +msgid "Private mode of bot %s is now off." +msgstr "Μυστικότητα επιλογής του bot %s είναι τώρα #ON#." + +#: modules/commands/bs_set.cpp:185 +#, c-format +msgid "Private mode of bot %s is now on." +msgstr "Μυστικότητα επιλογής του bot %s είναι τώρα #ON#." + +#: modules/commands/cs_list.cpp:220 +#, c-format +msgid "Private option for %s is now off." +msgstr "Η Private επιλογή για το %s #ΑΠΕΝΕΡΓΟΠΟΙΗΘΗΚΕ#." + +#: modules/commands/cs_list.cpp:214 +#, c-format +msgid "Private option for %s is now on." +msgstr "Η Private επιλογή για το %s #ΕΝΕΡΓΟΠΟΙΗΘΗΚΕ#." + +#: modules/commands/ns_list.cpp:221 +#, c-format +msgid "Private option is now off for %s." +msgstr "Η Private επιλογή #απενεργοποιηθηκε# για τον #%s#." + +#: modules/commands/ns_list.cpp:215 +#, c-format +msgid "Private option is now on for %s." +msgstr "Η Private επιλογή #ενεργοποιηθηκε# για τον #%s#." + +#: modules/commands/cs_flags.cpp:281 +#, c-format +msgid "Privilege %s added to %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/cs_flags.cpp:283 +#, c-format +msgid "Privilege %s removed from %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/ns_set.cpp:1309 +msgid "Protection" +msgstr "Προστασία" + +#: modules/commands/ns_set.cpp:721 +#, c-format +msgid "Protection is now off for %s." +msgstr "Η προστασία #απενεργοποιήθηκε# για το #%s#." + +#: modules/commands/ns_set.cpp:700 +#, c-format +msgid "Protection is now on for %s, with a reduced delay." +msgstr "" +"Η προστασία #ενεργοποιήθηκε# για το #%s#. , με μια μειωμένη καθυστέρηση" + +#: modules/commands/ns_set.cpp:710 +#, c-format +msgid "Protection is now on for %s, with no delay." +msgstr "Η προστασία #ενεργοποιήθηκε# για το #%s#. ,με καθόλου καθυστέρηση" + +#: modules/commands/ns_set.cpp:692 +#, c-format +msgid "Protection is now on for %s." +msgstr "Η προστασία #ενεργοποιήθηκε# για το #%s#." + +#: modules/commands/os_chankill.cpp:100 +#, fuzzy +msgid "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." +msgstr "" +"Syntax: #CHANKILL [+#expiry#] #channel# #reason##\n" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire and complete real ident@host for every nick,\n" +"then enforces the AKILL. " + +#: modules/commands/ns_set.cpp:1307 +#, fuzzy +msgid "Quick protection" +msgstr "Προστασία στους Voices" + +#: modules/commands/os_news.cpp:51 +msgid "RANDOMNEWS {ADD|DEL|LIST} [text|num]" +msgstr "RANDOMNEWS {ADD|DEL|LIST} [#περιεχόμενο#|#νούμερο#]#" + +#: modules/commands/cs_enforce.cpp:99 +msgid "REGONLY enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:68 +msgid "RESTRICTED enforced by " +msgstr "" + +#: modules/commands/os_noop.cpp:21 +msgid "REVOKE server" +msgstr "NOOP {SET|REVOKE} #server#" + +#: modules/commands/os_news.cpp:56 +#, c-format +msgid "Random news item #%d deleted." +msgstr "Το μήνυμα στην θέση #%d διαγράφηκε." + +#: modules/commands/os_news.cpp:55 +#, c-format +msgid "Random news item #%s not found!" +msgstr "Το μήνυμα στην θέση #%s δεν βρέθηκε!" + +#: modules/commands/os_news.cpp:52 +msgid "Random news items:" +msgstr "Νέα για το δίκτυο:" + +# +#: modules/commands/ms_read.cpp:112 +msgid "Read a memo or memos" +msgstr "Διαβάζει ένα ή πολλά μηνύματα" + +#: modules/commands/bs_info.cpp:56 +#, fuzzy +msgid "Real name" +msgstr " Πραγματικό όνομα : %s" + +#: modules/commands/os_list.cpp:153 +#, fuzzy +msgid "Realname" +msgstr " Πραγματικό όνομα : %s" + +#: modules/commands/os_ignore.cpp:266 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:204 modules/commands/os_forbid.cpp:358 +#: modules/commands/cs_akick.cpp:392 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:361 +msgid "Reason" +msgstr "" + +#: src/xline.cpp:386 +#, fuzzy, c-format +msgid "Reason for %s updated." +msgstr "Ο Successor του #%s# δεν έχει οριστεί." + +#: modules/commands/ns_recover.cpp:214 +msgid "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." +msgstr "" + +# +#: modules/commands/cs_access.cpp:741 +msgid "Redefine the meanings of access levels" +msgstr "Επανακαθορίζει το νόημα των επιπέδων πρόσβασης" + +# +#: modules/commands/ns_recover.cpp:149 +#, fuzzy +msgid "Regains control of your nick" +msgstr "Ανάκτηση της κατακράτησης του ψευδωνύμου,μετά από RECOVER" + +#: modules/commands/os_sxline.cpp:330 modules/commands/os_sxline.cpp:545 +#: modules/commands/os_akill.cpp:129 +#, fuzzy +msgid "Regex is disabled." +msgstr "%s έχει απενεργοποιηθεί." + +#: modules/commands/os_sxline.cpp:459 modules/commands/os_sxline.cpp:694 +#: modules/commands/os_akill.cpp:444 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." +msgstr "" + +#: modules/commands/os_ignore.cpp:386 modules/commands/os_forbid.cpp:428 +#: modules/commands/ns_list.cpp:172 modules/commands/cs_list.cpp:167 +#: modules/commands/os_list.cpp:119 modules/commands/os_list.cpp:255 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." +msgstr "" + +# +#: modules/commands/cs_register.cpp:19 +msgid "Register a channel" +msgstr "Κατοχυρώνει ένα ψευδώνυμο" + +# +#: modules/commands/ns_register.cpp:120 +msgid "Register a nickname" +msgstr "Κατοχυρώνει ένα ψευδώνυμο" + +#: modules/commands/ns_info.cpp:89 modules/commands/cs_info.cpp:55 +#, fuzzy +msgid "Registered" +msgstr " Κατάσταση κατοχύρωσης με την ημερομηνία: %s" + +#: modules/commands/os_stats.cpp:184 +#, c-format +msgid "Registered channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:190 +#, c-format +msgid "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:187 +#, c-format +msgid "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/cs_enforce.cpp:105 +#, c-format +msgid "Registered only enforced on %s." +msgstr "" + +#: modules/commands/cs_register.cpp:86 +#, fuzzy, c-format +msgid "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." +msgstr "" +"Σύνταξη: #REGISTER #κανάλι# #περιγραφή##\n" +"\n" +"Κατωχυρώνει ένα κανάλι στη βάση δεδωμένων του %s. Για να\n" +"χρησιμοποιήσετε αυτή την εντολή πρέπει πρώτα να είστε Channel Operator\n" +"Η περιγραφή που πρέπει να περιλαμβάνεται, είναι μια\n" +"γενική περιγραφή του σκοπού του καναλιού.\n" +"Όταν κατωχυρώνετε ένα κανάλι, γίνεστε ο\n" +"\"Ιδριτής\" του καναλιού. Ο ιδριτής μπορεί\n" +"να αλλάξει όλες τις ρυθμίσεις για το κανάλι;\n" +"Επίσης ο %s θα του δίνει αυτόματα \n" +"channel-operator δικαιώματα όταν μπαίνει στο κανάλι.\n" +"Δείτε την εντολή #ACCESS# (#/msg %s HELP ACCESS#) για\n" +"να μάθετε πώς να κάνετε κάποιους χρήστες channel operators.\n" +"ΠΡΟΣΟΧΗ: Για να κατωχυρώσετε ένα κανάλι θα πρέπει\n" +"να έχετε πρώτα κατωχυρωμένο ψευδόνυμο. Αν δεν έχετε,\n" +"#/msg %s HELP# για πληροφορίες." + +#: modules/commands/ns_register.cpp:269 +#, fuzzy, c-format +msgid "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." +msgstr "" +"Κατοχυρώνοντας το ψευδώνυμο σου καταγράφεται στο %s, την βάση δεδομένων.\n" +"Αφού το κατοχύρωσες, μπορείς να χρησιμοποιήσεις τις εντολές\n" +"#SET# και #ACCESS# για να σετάρεις το ψευδώνυμο όπως θες εσύ.\n" +"Να είσαι σίγουρος οτι θυμάσαι πάντα το κωδικό που έκανες την κατοχύρωση\n" +"του ψευδώνυμού σου - θα σου χρειαστεί στο να κάνεις αλλαγές\n" +"αργότερα. (Σημείωση οτι #case matters!# #ANOPE#, #Anope#, και \n" +"#anope# έχουν όλα διαφορετικούς κωδικούς!)\n" +"\n" +"Χρήσιμες οδηγίες για το διάλεγμα κωδικών:\n" +"\n" +"Οι κωδικοί δεν θα πρέπει να είναι εύκολη ώστε να μαντεύονται. Για " +"παράδειγμα,\n" +"χρησιμοποιώντας το πραγματικό όνομα σαν κωδικός είναι άσχημη ιδέα.\n" +"Χρησιμοποιώντας το ψευδώνυμο ωε κωδικό είναι η πιο χειρότερη\n" +"ιδέα ;) και, στο κάτω κάτω, ο %s δεν θα σε αφήσει να το κάνεις.\n" +"Επίσης, μικροί κωδικοί δεν είναι αξιόπιστοι, γι'αυτό\n" +"θα πρέπει να διαλέξεις ένα κωδικό με τουλάχιστον το λιγότερο 5 χαρακτήρες.\n" +"Τελικά, ο χαρακτήρας το κενό δεν χρησιμοποιείται σε κωδικούς.\n" +" \n" +"Η παράμετρος #email# είναι προεπιλεγμένη και θα πρέπει να έχετε \n" +"σετάρει το email του ψευδώνυμού σας άμεσα. Όπως και να'χει, σε \n" +"ορισμένα δίκτυα απαιτείται αμέσως στην εντολή κατοχύρωσης.\n" +"Η μυστικότητα είναι σεβαστή; αυτό το e-mail δεν θα το πάρει\n" +"κανένα τρίτο άτομο.\n" +" \n" +"Αυτή η εντολή δημιουργεί νέες ομάδες για το ψευδώνυμό σας,\n" +"και μπορούν να επιτρέπουν την κατοχύρωση άλλων ψευδονύμων αργότερα \n" +"με μοίρασμα ίδιων σεταρισμάτων, ίδιων μηνυμάτων και ίδιων\n" +"δικαιωμάτων στα κανάλια. Για περισσότερες πληροφορίες για αυτή \n" +"τη μελλοντική εντολή, γράψε #/msg %s HELP GROUP#.\n" + +#: modules/commands/ns_register.cpp:145 +#, fuzzy +msgid "Registration is currently disabled." +msgstr "Συγνώμη, η υπηρεσία κατοχύρωσεις καναλιών δεν λειτουργεί για την ώρα." + +# +#: modules/commands/cs_set.cpp:400 +msgid "Regulate the use of critical commands" +msgstr "Να ελλατώνει την χρήση \"βίαιων\" εντολών" + +# +#: modules/commands/hs_request.cpp:283 +msgid "Reject the requested vHost for the given nick." +msgstr "Επιστρέφει τον ιδιοκτήτη του εν λόγω καναλιού." + +# +#: modules/commands/hs_request.cpp:240 +msgid "Reject the requested vHost of a user" +msgstr "Διαγράφει τη vhost ενός χρήστη." + +# +#: modules/commands/cs_suspend.cpp:151 +msgid "Releases a suspended channel" +msgstr "Απελευθερώνει ένα suspended κανάλι." + +#: modules/commands/cs_suspend.cpp:191 +msgid "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." +msgstr "" +"Syntax: #UNSUSPEND #channel##\n" +"\n" +"Απελευθερώνει ένα παρακρατημένο(suspended) κανάλι. Ολα τα δεδομένα και οι " +"ρυθμίσεις\n" +"επαναφέρονται σε αυτά που υπήρχαν πριν το κλείσιμο." + +# +#: modules/commands/os_module.cpp:56 +msgid "Reload a module" +msgstr "Ξαναφορτώνει ένα module" + +# +#: modules/commands/os_reload.cpp:19 +msgid "Reload services' configuration file" +msgstr "Ξαναφορτώνει το services' configuration αρχείο" + +# +#: modules/commands/ns_group.cpp:236 +msgid "Remove a nick from a group" +msgstr "Αφαιρεί ένα nick από ένα group." + +# +#: modules/commands/cs_unban.cpp:19 +msgid "Remove all bans preventing a user from entering a channel" +msgstr "Αφαιρεί όλα τα bans που εμποδίζουν έναν χρήστη να μπεί σε ένα κανάλι." + +# +#: modules/commands/os_noop.cpp:19 +#, fuzzy +msgid "Remove all operators from a server remotely" +msgstr "Αφαιρεί προσωρινά και εξ αποστάσεως όλες τις O:lines από τον server" + +#: modules/commands/os_dns.cpp:543 +#, fuzzy, c-format +msgid "Removed IP %s from %s." +msgstr " Επιλογές κλειδώματος: %s" + +#: modules/commands/os_dns.cpp:460 +#, c-format +msgid "Removed server %s from zone %s." +msgstr "" + +#: modules/commands/os_dns.cpp:483 +#, c-format +msgid "Removed server %s." +msgstr "" + +#: modules/commands/cs_mode.cpp:909 +#, c-format +msgid "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." +msgstr "" + +# +#: modules/commands/cs_mode.cpp:890 +#, fuzzy, c-format +msgid "Removes %s status from you or the specified nick on a channel" +msgstr "Κάνει έναν χρήστη διαχειριστή καναλιού " + +# +#: modules/commands/cs_updown.cpp:146 +#, fuzzy +msgid "Removes a selected nicks status from a channel" +msgstr "Κάνει kick ένα ψευδόνυμο από ένα κανάλι." + +#: modules/commands/cs_updown.cpp:223 +msgid "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." +msgstr "" + +#: src/xline.cpp:412 +#, c-format +msgid "Removing %s because %s covers it." +msgstr "" + +#: modules/commands/bs_kick.cpp:1171 modules/commands/bs_kick.cpp:1173 +#: modules/commands/bs_kick.cpp:1176 +#, fuzzy +msgid "Repeat kicker" +msgstr " Επανάληψη με kick : %s" + +#: modules/commands/hs_request.cpp:78 +msgid "Request a vHost for your nick" +msgstr "Δεν υπάρχει email που να συνδέεται με το nick σας." + +#: modules/commands/hs_request.cpp:179 +msgid "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." +msgstr "" + +# +#: modules/commands/ns_register.cpp:312 +#, fuzzy +msgid "Resend registration confirmation email" +msgstr "Ξαναφορτώνει το services' configuration αρχείο" + +# +#: modules/commands/cs_set.cpp:621 +msgid "Restrict access to the channel" +msgstr "Απαγόρευση εισόδου στο κανάλι αν δεν έχεις access εκεί" + +#: modules/commands/cs_set.cpp:1291 +#, fuzzy +msgid "Restricted access" +msgstr "Μόνο όσοι έχουν Access" + +#: modules/commands/cs_set.cpp:661 +#, c-format +msgid "Restricted access option for %s is now off." +msgstr "Η Restricted access επιλογή για το %s #ΑΠΕΝΕΡΓΟΠΟΙΗΘΗΚΕ#." + +#: modules/commands/cs_set.cpp:655 +#, c-format +msgid "Restricted access option for %s is now on." +msgstr "Η Restricted access επιλογή για το %s #ΕΝΕΡΓΟΠΟΙΗΘΗΚΕ#." + +#: modules/commands/cs_enforce.cpp:73 +#, fuzzy, c-format +msgid "Restricted enforced on %s." +msgstr "Μόνο όσοι έχουν Access" + +# +#: modules/commands/cs_set.cpp:335 +#, fuzzy +msgid "Retain modes when channel is not in use" +msgstr "Να αλλάζει το topic όταν δεν χρησιμοποιείται το κανάλι" + +# +#: modules/commands/cs_topic.cpp:20 +msgid "Retain topic when channel is not in use" +msgstr "Να αλλάζει το topic όταν δεν χρησιμοποιείται το κανάλι" + +# +#: modules/commands/ns_getpass.cpp:19 +msgid "Retrieve the password for a nickname" +msgstr "" +"Εμφανίζει τον κωδικό για το συγκεκριμένο ψευδώνυμο\n" +"(μόνο αν η κωδικοποίηση είναι ανενεργή)" + +#: modules/commands/hs_request.cpp:296 +msgid "Retrieves the vhost requests" +msgstr "" + +# +#: modules/commands/cs_getkey.cpp:19 +msgid "Returns the key of the given channel" +msgstr "Επιστρέφει το κλειδί για το εν λόγω κανάλι." + +# +#: modules/commands/cs_getkey.cpp:57 +msgid "Returns the key of the given channel." +msgstr "Επιστρέφει το κλειδί για το εν λόγω κανάλι." + +# +#: modules/commands/ns_getemail.cpp:58 +#, fuzzy +msgid "Returns the matching accounts that used given email." +msgstr "Επιστρέφει το κλειδί για το εν λόγω κανάλι." + +# +#: modules/commands/ns_status.cpp:19 +msgid "Returns the owner status of the given nickname" +msgstr "Επιστρέφει τον ιδιοκτήτη του εν λόγω καναλιού." + +# +#: modules/commands/ns_getpass.cpp:50 +msgid "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." +msgstr "" +"Σύνταξη: #GETPASS #ψευδώνυμο##\n" +"\n" +"Δίνει τον χαμένο κωδικό στο συγκεκριμένο ψευδώνυμο. #Σημείωση# όταν\n" +"η εντολή αυτή χρησιμοποιείται, το μήνυμα που θα πάει για τον\n" +"συγκεκριμένο θα καταγραφεί και η εντολή που εκτελέστηκε και το ψευδώνυμο\n" +"και θα σταλεί μέσω WALLOPS/GLOBOPS.\n" +"\n" +"Μόνο για τους #Services Operators#.\n" +"\n" +"Αυτή η εντολή δεν είναι διαθέσιμη αν είναι ενεργή η κωδικοποίηση." + +# +#: modules/commands/ns_status.cpp:55 +#, fuzzy +msgid "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." +msgstr "" +"Σύνταξη: #STATUS #ψευδώνυμο(α)#...#\n" +"\n" +"Σας ενημερώνει για το αν ο χρήστης που χρησιμοποιεί το\n" +"ψευδώνυμο που δώσατε, έχει αναγνωριστεί σαν κάτοχός του.\n" +"Το αποτέλεσμα της εντολής έχει τη μορφή:\n" +"\n" +" #ψευδώνυμο# #κωδικός-κατάστασης# #account#\n" +"\n" +"where #ψευδώνυμο# is the nickname sent with the command,\n" +"#κωδικός-κατάστασης# is one of the following, and #account#\n" +"is the account they are logged in as.\n" +"\n" +" 0 - δεν υπάρχει τέτοιος χρήστης συνδεδεμένος #ή# το ψευδώνυμο είναι μη " +"κατοχυρωμένο\n" +" 1 - ο χρήστης δεν αναγνωρίστηκε σαν κάτοχος του ψευδωνύμου\n" +" 2 - ο χρήστης αναγνωρίστηκε σαν κάτοχος μέσω της λίστας πρόσβασης " +"(access list) μόνο\n" +" 3 - ο χρήστης αναγνωρίστηκε σαν κάτοχος του ψευδωνύμου μέσω της " +"αναγνώρισης με κωδικό\n" +"\n" +"Μέχρι δεκαέξι ψευδώνυμα μπορούν να χρησιμοποιηθούν με κάθε εντολή; Τα\n" +"υπόλοιπα θα αγνοούνται. If no nickname is given, your status\n" +"will be returned." + +#: modules/commands/bs_kick.cpp:1181 modules/commands/bs_kick.cpp:1183 +#: modules/commands/bs_kick.cpp:1186 +#, fuzzy +msgid "Reverses kicker" +msgstr " Αντιθετος με kick : %s" + +# +#: modules/commands/ns_logout.cpp:21 +msgid "Reverses the effect of the IDENTIFY command" +msgstr "Αντιστρέφει την εντολή IDENTIFY." + +#: modules/commands/os_noop.cpp:20 +msgid "SET server" +msgstr "" + +#: modules/commands/os_dns.cpp:667 +msgid "SET server.name option value" +msgstr "" + +# +#: modules/commands/ns_cert.cpp:378 +#, fuzzy, c-format +msgid "SSL certificate fingerprint accepted, you are now identified to %s." +msgstr "Ο κωδικός έγινε δεκτός - τώρα είσαι αναγνωρισμένος." + +# +#: modules/commands/ns_cert.cpp:398 +#, fuzzy +msgid "SSL certificate fingerprint accepted, you are now identified." +msgstr "Ο κωδικός έγινε δεκτός - τώρα είσαι αναγνωρισμένος." + +#: modules/commands/cs_enforce.cpp:137 +#, c-format +msgid "SSL only enforced on %s." +msgstr "" + +#: modules/commands/cs_enforce.cpp:131 +msgid "SSLONLY enforced by " +msgstr "" + +# +#: modules/commands/os_shutdown.cpp:47 +msgid "Save databases and restart Services" +msgstr "Σώζει τις βάσεις δεδομένων και επανεκκινεί τα Services" + +#: modules/commands/os_logsearch.cpp:32 +msgid "Searches logs for a matching pattern" +msgstr "" + +#: modules/commands/cs_set.cpp:1295 +#, fuzzy +msgid "Secure founder" +msgstr "Ασφάλεια στον Καναλάρχη" + +#: modules/commands/cs_set.cpp:786 +#, c-format +msgid "Secure founder option for %s is now off." +msgstr "H Secure founder επιλογή για το %s #ΑΠΕΝΕΡΓΟΠΟΙΗΘΗΚΕ#." + +#: modules/commands/cs_set.cpp:780 +#, c-format +msgid "Secure founder option for %s is now on." +msgstr "H Secure founder επιλογή για το %s #ΕΝΕΡΓΟΠΟΙΗΘΗΚΕ#." + +#: modules/commands/cs_set.cpp:1297 +#, fuzzy +msgid "Secure ops" +msgstr "Μόνο αυτοί που έχουν access θα παίρνουν op από opers" + +#: modules/commands/cs_set.cpp:850 +#, c-format +msgid "Secure ops option for %s is now off." +msgstr "H Secure ops επιλογή για το %s #ΑΠΕΝΕΡΓΟΠΟΙΗΘΗΚΕ#." + +#: modules/commands/cs_set.cpp:844 +#, c-format +msgid "Secure ops option for %s is now on." +msgstr "H Secure ops επιλογή για το %s #ΕΝΕΡΓΟΠΟΙΗΘΗΚΕ#." + +#: modules/commands/cs_set.cpp:723 +#, c-format +msgid "Secure option for %s is now off." +msgstr "H Secure option επιλογή για το %s #ΑΠΕΝΕΡΓΟΠΟΙΗΘΗΚΕ#." + +#: modules/commands/cs_set.cpp:717 +#, c-format +msgid "Secure option for %s is now on." +msgstr "H Secure option επιλογή για το %s #ΕΝΕΡΓΟΠΟΙΗΘΗΚΕ#." + +#: modules/commands/ns_set.cpp:1044 +#, c-format +msgid "Secure option is now off for %s." +msgstr "Η επιλογή Secure option #ΑΠΕΝΕΡΓΟΠΟΙΗΘΗΚΕ# για τον #%s#." + +#: modules/commands/ns_set.cpp:1038 +#, c-format +msgid "Secure option is now on for %s." +msgstr "Η επιλογή Secure option #ΕΝΕΡΓΟΠΟΙΗΘΗΚΕ# για τον #%s#." + +#: modules/commands/cs_enforce.cpp:42 +#, fuzzy, c-format +msgid "Secureops enforced on %s." +msgstr "Η επιλογή Secure option #ΕΝΕΡΓΟΠΟΙΗΘΗΚΕ# για τον #%s#." + +#: modules/commands/cs_set.cpp:1293 modules/commands/ns_set.cpp:1311 +msgid "Security" +msgstr "Ασφάλεια" + +#: modules/commands/cs_xop.cpp:570 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the access list." +msgstr "’γνωστη εντολή #%s#. \"/msg %s HELP\" για βοήθεια." + +#: modules/commands/cs_xop.cpp:573 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the flags system." +msgstr "’γνωστη εντολή #%s#. \"/msg %s HELP\" για βοήθεια." + +# +#: modules/commands/ms_send.cpp:24 +msgid "Send a memo to a nick or channel" +msgstr "Στέλνει ένα μήνυμα σε ένα ψευδώνυμο ή ένα κανάλι" + +# +#: modules/commands/ms_staff.cpp:24 +msgid "Send a memo to all opers/admins" +msgstr "Στέλνει ένα memo σε όλους τους opers/admins" + +# +#: modules/commands/ms_sendall.cpp:24 +msgid "Send a memo to all registered users" +msgstr "Στέλνει ένα memo σε όλους τους registered χρήστες." + +# +#: modules/commands/gl_global.cpp:21 +msgid "Send a message to all users" +msgstr "Στέλνει μήνυμα σε όλους τους χρήστες" + +#: modules/commands/ms_list.cpp:64 +#, fuzzy +msgid "Sender" +msgstr "Ασφάλεια στον Καναλάρχη" + +# +#: modules/commands/ms_rsend.cpp:24 +msgid "Sends a memo and requests a read receipt" +msgstr "Στέλνει ένα memo και ζητά απόδειξη ανάγνωσης." + +#: modules/commands/ns_resetpass.cpp:50 +#, fuzzy +msgid "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." +msgstr "" +"Syntax: #RESETPASS #nickname##\n" +"\n" +"Στέλνει έναν κωδικό στο ψευδόνυμο, με οδηγίες πώς\n" +"να επανακτήσουν το κωδικό τους." + +# +#: modules/commands/ms_sendall.cpp:52 +msgid "Sends all registered users a memo containing memo-text." +msgstr "" +"Syntax: #SENDALL# #memo-text#\n" +"Στέλνει σε όλους τους χρήστες ένα memo που περιέχει #memo-text#." + +# +#: modules/commands/ms_staff.cpp:48 +msgid "Sends all services staff a memo containing memo-text." +msgstr "" +"Syntax: #STAFF# #memo-text#\n" +"Στέλνει σε όλο το services staff ένα memo που περιέχει #memo-text#." + +# +#: modules/commands/ms_send.cpp:66 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." +msgstr "" +"Στέλνει στο #ψευδώνυμο# ή στο #κανάλι# που δίνεται, ένα μήνυμα που \n" +"περιέχει το κείμενο-μηνύματος. Όταν το μήνυμα στέλνεται σε ένα ψευδώνυμο,\n" +"#memo-text#. When sending to a nickname, the recipient will\n" +"ο παραλείπτης θα λάβει μια ειδοποίηση οτι έχει ένα νέο #μήνυμα#.\n" +"Το ψευδώνυμο ή το κανάλι που δίνεται, πρέπει να είναι κατοχυρωμένο." + +# +#: modules/commands/ms_rsend.cpp:80 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." +msgstr "" +"Syntax: #RSEND {#nick# | #channel#} #memo-text##\n" +"\n" +"Στέλνει στο #nick# ή #κανάλι# ένα memo που περιέχει\n" +"#memo-text#. Όταν το στείλετε σε ένα nick, ο παραλήπτης θα λάβει\n" +"ένα notice ότι έχει νέο memo. Το nick του παραλήπτη\n" +"πρέπει να είναι κατωχυρωμένο.\n" +"Όταν το memo διαβάζεται από τον παραλήπτη, μια αυτόματη ειδοποίηση\n" +"θα στέλνεται σε αυτόν που το έστειλε, που τον ενημερώνει οτι το \n" +"memo του έχει διαβαστεί." + +# +#: modules/commands/ms_read.cpp:199 +#, fuzzy +msgid "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Σύνταξη: #READ [#κανάλι#] {#νου# | #list# | LAST | NEW}#\n" +"\n" +"Με την εντολή αυτή διαβάζεται τα μηνύματα που σας έρχονται. Αν δώσετε LAST\n" +"θα διαβάσετε το τελευταίο μήνυμα που δεχθήκατε. Αν γράψετε\n" +"NEW θα διαβάσετε όλα τα νέα μηνύματα που σας ήρθαν. Αλλιώς,\n" +"θα δείτε τα νούμερα των μηνυμάτων. Μπορείτα να δείτε την λίστα με τα\n" +"νούμερα, για παράδειγμα:\n" +"\n" +" #Διάβασε 2-5,7-9#\n" +" Εμφανίζει τα μηνύματα με τα νούμερα 2 έως και 5 και 7 έως και 9." + +#: modules/commands/os_dns.cpp:218 +#, fuzzy +msgid "Server" +msgstr "Ασφαλές" + +#: modules/commands/os_dns.cpp:375 +#, fuzzy, c-format +msgid "Server %s added to zone %s." +msgstr " %s (δεν λήγει ποτέ)" + +#: modules/commands/os_dns.cpp:345 +#, fuzzy, c-format +msgid "Server %s already exists." +msgstr "Το Bot #%s# υπάρχει ήδη." + +#: modules/commands/os_noop.cpp:31 modules/commands/os_dns.cpp:430 +#: modules/commands/os_dns.cpp:493 modules/commands/os_dns.cpp:532 +#: modules/commands/os_dns.cpp:571 modules/commands/os_dns.cpp:604 +#: modules/commands/os_dns.cpp:639 +#, c-format +msgid "Server %s does not exist." +msgstr " %s (δεν λήγει ποτέ)" + +#: modules/commands/os_dns.cpp:619 +#, fuzzy, c-format +msgid "Server %s has no configured IPs." +msgstr "Το ψευδώνυμο #%s# σβήστηκε επιτυχώς από την υπηρεσία." + +#: modules/commands/os_dns.cpp:357 +#, fuzzy, c-format +msgid "Server %s is already in zone %s." +msgstr "Είστε ήδη στο κανάλι #%s#! " + +#: modules/commands/os_dns.cpp:614 +#, fuzzy, c-format +msgid "Server %s is already pooled." +msgstr "Το Module #%s# είναι ήδη φορτωμένο." + +#: modules/commands/os_dns.cpp:609 +#, fuzzy, c-format +msgid "Server %s is not currently linked." +msgstr "Ο %s είναι για την ώρα off." + +#: modules/commands/os_dns.cpp:443 +#, fuzzy, c-format +msgid "Server %s is not in zone %s." +msgstr " %s (δεν λήγει ποτέ)" + +#: modules/commands/os_dns.cpp:384 +#, fuzzy, c-format +msgid "Server %s is not linked to the network." +msgstr "Δεν υπάρχει bot που να είναι στο %s τώρα πια." + +#: modules/commands/os_dns.cpp:644 +#, fuzzy, c-format +msgid "Server %s is not pooled." +msgstr " %s (δεν λήγει ποτέ)" + +#: modules/commands/os_dns.cpp:465 +#, c-format +msgid "Server %s must be quit before it can be deleted." +msgstr "" + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Servers" +msgstr "Ασφαλές" + +#: modules/commands/os_stats.cpp:155 +#, c-format +msgid "Servers found: %d" +msgstr "Βρέθηκαν οι servers: %d" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Service" +msgstr "Τα services είναι ενεργά για %s" + +#: modules/commands/ns_recover.cpp:51 +#, fuzzy, c-format +msgid "Service's hold on %s has been released." +msgstr "Οι υπηρεσίες απελευθέρωααν το ψευδώνυμό σου." + +#: data/nickserv.example.conf:236 data/chanserv.example.conf:827 +#, fuzzy +msgid "Services Operator commands" +msgstr "%s είναι services operator τού τύπου %s." + +#: modules/commands/os_defcon.cpp:443 modules/commands/os_defcon.cpp:454 +#: modules/commands/os_defcon.cpp:462 modules/commands/os_defcon.cpp:470 +#: modules/commands/os_defcon.cpp:478 +#, fuzzy +msgid "Services are in DefCon mode, please try again later." +msgstr "Τα services είναι σε Defcon mode, Παρακαλώ δοκιμάστε αργότερα" + +#: include/language.h:70 +msgid "Services are in read-only mode!" +msgstr "Τα Services είναι τώρα #μόνο ανάγνωσης#." + +#: modules/commands/os_defcon.cpp:186 modules/commands/os_defcon.cpp:213 +#, fuzzy, c-format +msgid "Services are now at DEFCON %d." +msgstr "Τα services είναι τώρα σε DEFCON #%d#" + +#: modules/commands/os_set.cpp:128 +#, fuzzy, c-format +msgid "Services are now in debug mode (level %d)." +msgstr "Τα Services είναι τώρα σε debug επιλογή (βαθμός %d)." + +#: modules/commands/os_set.cpp:114 +#, fuzzy +msgid "Services are now in debug mode." +msgstr "Τα Services είναι τώρα σε debug επιλογή." + +#: modules/commands/os_set.cpp:159 +msgid "Services are now in expire mode." +msgstr "Τα Services είναι τώρα σε επιλογή να #λήγει#." + +#: modules/commands/os_set.cpp:153 +msgid "Services are now in no expire mode." +msgstr "Τα Services είναι τώρα σε επιλογή να #μην λήγει#." + +#: modules/commands/os_set.cpp:120 +#, fuzzy +msgid "Services are now in non-debug mode." +msgstr "Τα Services είναι τώρα σε μη-debug επιλογή." + +#: modules/commands/os_set.cpp:47 +msgid "Services are now in read-only mode." +msgstr "Τα Services είναι τώρα #μόνο ανάγνωσης#." + +#: modules/commands/os_set.cpp:53 +msgid "Services are now in read-write mode." +msgstr "Τα Services είναι σε επιλογή #ανάγνωσης-εγγραφής#." + +#: src/mail.cpp:76 +msgid "Services have been configured to not send mail." +msgstr "Οι υπηρεσίες έχουν ρυθμιστεί να μην στέλνουν μήνυμα στη διεύθυνση." + +# +#: modules/commands/os_ignore.cpp:280 +#, fuzzy +msgid "Services ignore list:" +msgstr "Τροποποιεί την Services Ignore List" + +# +#: modules/commands/os_mode.cpp:33 modules/commands/os_kick.cpp:39 +msgid "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" +msgstr "" +"Οι υπηρεσίες αδυνατούν να αλλάξουν τις επιλογές. Οι servers' U: γραμμές " +"είναι οι σωστές?" + +#: modules/commands/os_stats.cpp:140 +#, fuzzy, c-format +msgid "Services up %s." +msgstr "Τα services είναι ενεργά για %s" + +#: modules/commands/ns_set.cpp:266 +#, fuzzy, c-format +msgid "Services will from now on set status modes on %s in channels." +msgstr "Τα services δεν θα δίνουν πια autoop στον %s στα κανάλια." + +#: modules/commands/cs_set.cpp:114 +#, fuzzy, c-format +msgid "Services will no longer automatically give modes to users in %s." +msgstr "Τα services δεν θα δίνουν πια autoop στον %s στα κανάλια." + +#: modules/commands/ns_set.cpp:272 +#, fuzzy, c-format +msgid "Services will no longer set status modes on %s in channels." +msgstr "Τα services δεν θα δίνουν πια autoop στον %s στα κανάλια." + +#: modules/commands/cs_set.cpp:108 +#, fuzzy, c-format +msgid "Services will now automatically give modes to users in %s." +msgstr "Τα services θα δίνουν autoop στον %s στα κανάλια." + +#: modules/commands/ns_set.cpp:940 +#, c-format +msgid "Services will now reply to %s with messages." +msgstr "Τα services δεν θα απαντούν πια στον #%s# με #μυνήματα#." + +#: modules/commands/ns_set.cpp:946 +#, c-format +msgid "Services will now reply to %s with notices." +msgstr "Τα services θα απαντούν πια στον #%s# με #notices#." + +#: modules/commands/os_reload.cpp:34 +#, fuzzy +msgid "Services' configuration has been reloaded." +msgstr "Το αρχείο των υπηρεσιών,conf file έγινε reloaded,επαναφορτώθηκε." + +#: modules/commands/os_session.cpp:192 +msgid "Session" +msgstr "" + +#: modules/commands/os_session.cpp:382 +#, c-format +msgid "Session limit for %s set to %d." +msgstr "Session limit για τον #%s# ρυθμίστηκε σε #%d#." + +#: modules/commands/os_session.cpp:257 modules/commands/os_session.cpp:534 +msgid "Session limiting is disabled." +msgstr "Η Session limiting εντολή είναι απενεργοποιημένη." + +#: modules/commands/os_stats.cpp:195 +#, c-format +msgid "Sessions: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +# +#: modules/commands/ns_set.cpp:74 +msgid "Set SET-options on another nickname" +msgstr "Αλλάζει τις ρυθμίσεις ενός άλλου ψευδονύμου." + +# +#: modules/commands/cs_set.cpp:20 +msgid "Set channel options and information" +msgstr "Ρυθμίζει τις επιλογές και τις πληροφορίες του καναλιού" + +# +#: modules/commands/cs_set.cpp:137 +msgid "Set how Services make bans on the channel" +msgstr "Αλλάζει τον τύπο του ban που θα κάνουν τα Services" + +# +#: modules/commands/ms_set.cpp:206 +msgid "Set options related to memos" +msgstr "Αλλάζει τις επιλογές των μηνυμάτων" + +# +#: modules/commands/ns_set.cpp:19 +msgid "Set options, including kill protection" +msgstr "Αλλαγή επιλογών, συμπεριλαμβάνεται η προστασία με αποσύνδεση" + +# +#: modules/commands/cs_set.cpp:472 +msgid "Set the channel as permanent" +msgstr "Κάνει το κανάλι permanent." + +# +#: modules/commands/cs_set.cpp:204 +msgid "Set the channel description" +msgstr "Αλλάζει την περιγραφή του καναλιού" + +# +#: modules/commands/ns_set.cpp:329 +msgid "Set the display of your group in Services" +msgstr "Αλλάζει την λίστα των ομάδων" + +# +#: modules/commands/cs_set.cpp:266 +msgid "Set the founder of a channel" +msgstr "Αλλάζει τον founder του καναλιού" + +# +#: modules/commands/ns_set.cpp:793 +msgid "Set the language Services will use when messaging you" +msgstr "" +"Αλλάζει τη γλώσσα που χρησιμοποιούν οι\n" +" υπηρεσίες όταν τις χρησιμοποιείτε" + +# +#: modules/commands/ns_set.cpp:172 +msgid "Set the nickname password" +msgstr "Ρυθμίζει τον κωδικό του ψευδονύμου." + +# +#: modules/commands/cs_set.cpp:949 +msgid "Set the successor for a channel" +msgstr "Αλλάζει τον successor του καναλιού" + +# +#: modules/commands/hs_set.cpp:125 +msgid "Set the vhost for all nicks in a group" +msgstr "ρυθμίζει τη vhost για όλα τα nicks σε ένα group." + +# +#: modules/commands/hs_set.cpp:19 +msgid "Set the vhost of another user" +msgstr "Ρυθμίζει το vhost κάποιου άλλου χρήστη." + +# +#: modules/commands/os_set.cpp:169 +msgid "Set various global Services options" +msgstr "Ρυθμίζεις διάφορες επιλογές των Services" + +# +#: modules/commands/ns_set.cpp:119 +msgid "Set your nickname password" +msgstr "Αλλάζει τον κωδικό του ψευδωνύμου σας" + +# +#: modules/commands/bs_kick.cpp:271 +#, fuzzy, c-format +msgid "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: #KICK #channel# ITALICS {#ON|OFF#} [#ttb#]#\n" +"Ενεργοποιεί/απενεργοποιεί το kick για πλάγια γράμματα. Όταν ενεργοποιείται " +"αυτή\n" +"η επιλογή λέει στο bot να κάνει kick όσους χρησιμοποιούν πλάγια γράμματα.\n" +"ttb είναι ο αριθμός των φορών που ο χρήστης γίνεται kick\n" +"πρίν να γίνει ban. Μη δώσετε ttb για να απενεργοποιείσετε\n" +"το ban system." + +#: modules/commands/bs_kick.cpp:307 +#, fuzzy, c-format +msgid "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Σύνταξη: #KICK ##κανάλι# BADWORDS {#ON|OFF#} [#ttb#]#\n" +"Ενεργοποιεί την εντολή kick για κακές λέξεις. Όταν ενεργοποιηθεί,\n" +"το bot θα κάνει kick τους χρήστες που λένε αυτές τις κακές λέξεις στα " +"κανάλια.\n" +"\n" +"Μπορείς να βάλεις μια λίστα με τις κακές λέξεις κάνοντας την εντολή\n" +"#BADWORDS#. Γράψε #/msg %s HELP BADWORDS# για\n" +"περισσότερες πληροφορίες.\n" +"Το ttb είναι το νούμερο με το οποίο θα γίνεται ο χρήστης αρχικά kick\n" +"και μετά ban. Μην προσπαθήσετε να απενεργοποιήσετε το ttb\n" +"γιατί το σύστημα θα το ενεργοποιήσει ξανά." + +#: modules/commands/cs_set.cpp:186 +#, fuzzy +msgid "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" +msgstr "" +"Σύνταξη: #%s #κανάλι# BANTYPE #τύπος-ban##\n" +"\n" +"Αλλάζει τον τύπο του ban, ο οποίος θα χρησιμοποιείται από τις υπηρεσίες " +"όταν\n" +"θα χρειάζεται να κάνει κάποιον ban από το κανάλι (πχ akick).\n" +"\n" +"Οι τύποι ban είναι από 0 έως 3 και σημαίνει:\n" +"\n" +"0: το ban θα είναι της μορφής *!user@host\n" +"1: το ban θα είναι της μορφής *!*user@host\n" +"2: το ban θα είναι της μορφής *!*@host\n" +"3: το ban θα είναι της μορφής *!*user@*.domain" + +#: modules/commands/bs_kick.cpp:345 +#, fuzzy +msgid "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Σύνταξη: #KICK #κανάλι# BOLDS {#ON|OFF#} [#ttb#]#\n" +"Ενεργοποιεί την εντολή kick έντονων χαρακτήρων. Αν την\n" +"ενεργοποιήσετε, θα κάνει kick όσους χρησιμοποιούν bolds (έντονους\n" +"χαρακτήρες).\n" +"Το ttb είναι το νούμερο με το οποίο θα γίνεται ο χρήστης αρχικά kick\n" +"και μετά ban. Μην προσπαθήσετε να απενεργοποιήσετε το ttb\n" +"γιατί το σύστημα θα το ενεργοποιήσει ξανά." + +#: modules/commands/bs_kick.cpp:436 +#, fuzzy, c-format +msgid "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Σύνταξη: #KICK #κανάλι# CAPS {#ON|OFF#} [#ttb# [#min# [#ποσοστό#]]]#\n" +"Ενεργοποιεί την εντολή kick για κεφαλαίους χαρακτήρες.Αν την\n" +"ενεργοποιήσετε, αυτή η επιλογή θα κάνει kick όσους χρησιμοποιούν\n" +"κεφαλαίους χαρακτήρες.\n" +"Το bot θα κάνει kick μόνο αν είναι το λιγότερο #min# κεφαλαία\n" +"και είναι συνολικά στο #ποσοστό#%% του συνολικού μηνύματος \n" +"της γραμμής (αν δεν δωθεί, από default είναι στους 10 χαρακτήρες\n" +"και 25%%).\n" +"Το ttb είναι το νούμερο με το οποίο θα γίνεται ο χρήστης αρχικά kick\n" +"και μετά ban. Μην προσπαθήσετε να απενεργοποιήσετε το ttb\n" +"γιατί το σύστημα θα το ενεργοποιήσει ξανά." + +#: modules/commands/bs_kick.cpp:475 +#, fuzzy +msgid "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Σύνταξη: #KICK #κανάλι# COLORS {#ON|OFF#} [#ttb#]#\n" +"Ενεργοποιεί την εντολή kick για έγχρωμους χαρακτήρες.Αν την ενεργοποιήσετε,\n" +"αυτή η επιλογή θα κάνει kick όσους χρησιμοποιούν έγχρωμους χαρακτήρες.\n" +"Το ttb είναι το νούμερο με το οποίο θα γίνεται ο χρήστης αρχικά kick\n" +"και μετά ban. Μην προσπαθήσετε να απενεργοποιήσετε το ttb\n" +"γιατί το σύστημα θα το ενεργοποιήσει ξανά." + +#: modules/commands/cs_set.cpp:255 +msgid "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." +msgstr "" +"Σύνταξη: #%s #κανάλι# DESC #περιγραφή##\n" +"\n" +"Αλλάζετε την περιγραφή του καναλιού, η οποία φένεται με την εντολή\n" +"#LIST# και #INFO#." + +#: modules/commands/bs_kick.cpp:571 +#, fuzzy +msgid "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Σύνταξη: #KICK #κανάλι# FLOOD {#ON|OFF#} [#ttb# [#ln# [#secs#]]]#\n" +"Ενεργοποιεί την εντολή kick για συνεχόμενα μηνύματα.Αν την\n" +"ενεργοποιήσετε, αυτή η επιλογή θα κάνει kick όσους γράφουν\n" +"αρκετά από όσο πρέπει.Οι επιλογές για ένα κανάλι είναι\n" +"το λιγότερο να έχει #ln# γραμμές σε #secs# δευτερόλεπτα\n" +"(αν δεν δίνετε, από default είναι 6 γραμμές σε 10 δευτερόλεπτα).\n" +"\n" +"Το ttb είναι το νούμερο με το οποίο θα γίνεται ο χρήστης αρχικά kick\n" +"και μετά ban. Μην προσπαθήσετε να απενεργοποιήσετε το ttb\n" +"γιατί το σύστημα θα το ενεργοποιήσει ξανά." + +#: modules/commands/bs_kick.cpp:607 +#, fuzzy +msgid "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Σύνταξη: #KICK #κανάλι# FLOOD {#ON|OFF#} [#ttb# [#ln# [#secs#]]]#\n" +"Ενεργοποιεί την εντολή kick για συνεχόμενα μηνύματα.Αν την\n" +"ενεργοποιήσετε, αυτή η επιλογή θα κάνει kick όσους γράφουν\n" +"αρκετά από όσο πρέπει.Οι επιλογές για ένα κανάλι είναι\n" +"το λιγότερο να έχει #ln# γραμμές σε #secs# δευτερόλεπτα\n" +"(αν δεν δίνετε, από default είναι 6 γραμμές σε 10 δευτερόλεπτα).\n" +"\n" +"Το ttb είναι το νούμερο με το οποίο θα γίνεται ο χρήστης αρχικά kick\n" +"και μετά ban. Μην προσπαθήσετε να απενεργοποιήσετε το ttb\n" +"γιατί το σύστημα θα το ενεργοποιήσει ξανά." + +#: modules/commands/bs_kick.cpp:706 +#, fuzzy +msgid "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Σύνταξη: #KICK ##κανάλι# REPEAT {#ON|OFF#} [#ttb# [#num#]]#\n" +"Ενεργοποιεί την εντολή kick για επαναλαμβανόμενα μηνύματα.Αν την\n" +"ενεργοποιήσετε, αυτή η επιλογή θα κάνει kick όσους γράφουν\n" +"τα ίδια πράγματα,επιλέγεται εσείς το #num#,τις φορές που δεν θέλετε\n" +"να γίνεται (αν δεν δώσετε num, από defaults θα είναι 3).\n" +"Το ttb είναι το νούμερο με το οποίο θα γίνεται ο χρήστης αρχικά kick\n" +"και μετά ban. Μην προσπαθήσετε να απενεργοποιήσετε το ttb\n" +"γιατί το σύστημα θα το ενεργοποιήσει ξανά." + +#: modules/commands/bs_kick.cpp:742 +#, fuzzy +msgid "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Σύνταξη: #KICK #κανάλι# REVERSES {#ON|OFF#} [#ttb#]#\n" +"Ενεργοποιεί την εντολή kick για τους αντίθετους με τις επιλογές που\n" +"έχει ένα κανάλι.\n" +"\n" +"Το ttb είναι το νούμερο με το οποίο θα γίνεται ο χρήστης αρχικά kick\n" +"και μετά ban. Μην προσπαθήσετε να απενεργοποιήσετε το ttb\n" +"γιατί το σύστημα θα το ενεργοποιήσει ξανά." + +#: modules/commands/bs_kick.cpp:776 +#, fuzzy +msgid "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Σύνταξη: #KICK #κανάλι# UNDERLINES {#ON|OFF#} [#ttb#]#\n" +"Ενεργοποιεί την εντολή kick για υπογραμμισμένους χαρακτήρες.Αν την\n" +"ενεργοποιήσετε, αυτή η επιλογή θα κάνει kick όσους χρησιμοποιούν\n" +"υπογραμμισμένους χαρακτήρες.\n" +"Το ttb είναι το νούμερο με το οποίο θα γίνεται ο χρήστης αρχικά kick\n" +"και μετά ban. Μην προσπαθήσετε να απενεργοποιήσετε το ttb\n" +"γιατί το σύστημα θα το ενεργοποιήσει ξανά." + +# +#: modules/commands/hs_set.cpp:206 +msgid "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." +msgstr "" +"Syntax: #SETALL# ## ##.\n" +"Ρυθμίζει τη vhost για όλα τα ψευδώνυμα που ανήκουν στο ίδιο γκρουπ με\n" +"αυτό του δοσμένου ψευδώνυμου. Αν το IRCD σας υποστηρίζει vIdents, τότε\n" +"χρησιμοποιώντας την εντολή SETALL @ θα ρυθμιστούν οι " +"idents\n" +"τόσο για τους χρήστες όσο και για τις vhosts.\n" +"* ΣΗΜΕΙΩΣΗ, αυτό δεν θα αλλάξει τη vhost για ψευδώνυμο\n" +"που προστέθηκε στο γκρουπ μετά τη χρήση της εντολής." + +#: modules/commands/hs_set.cpp:99 +#, fuzzy +msgid "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." +msgstr "" +"Syntax: #SET# ## ##.\n" +"Ρυθμίζει τη vhost για το nick που διαλέξατε.\n" +"Αν το ircd σας υποστηρίζει vidents τότε με την εντολή\n" +"SET @ ρυθμίζει idents στους χρήστες \n" +"εκτός από vhosts." + +# +#: modules/commands/os_set.cpp:199 +#, fuzzy +msgid "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" +msgstr "" +"Σύνταξη: #SET #option# #setting##\n" +"\n" +"Ρυθμίσεις σχετικά με τις επιλογές των Services. Ονομαστικά\n" +"οι επιλογές είναι:\n" +" #READONLY# Αλλάζετε σε διαδικασία read-only ή read-write mode\n" +" #LOGCHAN# Report log messages to a channel\n" +" #DEBUG# Ενεργοποιείτε ή απενεργοποιείτε σε debug mode\n" +" #NOEXPIRE# Ενεργοποιείτε ή απενεργοποιείτε σε no expire mode\n" +" #SUPERADMIN# Activate or deactivate super-admin mode\n" +" #IGNORE# Activate or deactivate ignore mode\n" +" #LIST# List the options\n" +"\n" +"Μόνο για τους #Services Operators#." + +#: modules/commands/ms_set.cpp:235 +#, fuzzy, c-format +msgid "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Σύνταξη: #SET #επιλογή# #παράμετροι##\n" +"\n" +"Αλλάζει διάφορες επιλογές για τα μηνύματα.\n" +"Η #επιλογή# μπορεί να είναι μια από:\n" +" \n" +" NOTIFY Αλλάζει το πότε θα ενημερώνεστε για τα\n" +" νέα σας μηνύματα (μόνο για ψευδώνυμα)\n" +" LIMIT Αλλάζει το μέγιστο αριθμό μηνυμάτων που\n" +" μπορείτε να δεχτείτε\n" +"\n" +"Γράψτε #/msg %s HELP SET #επιλογή## για περισσότερες πληροφορίες\n" +"σε μια συγκεκριμένη επιλογή." + +#: modules/commands/ns_set.cpp:33 modules/commands/ns_set.cpp:88 +msgid "Sets various nickname options. option can be one of:" +msgstr "" +"Σύνταξη: #SET #option# #parameters##\n" +"\n" +"Αλλάζει διάφορες επιλογές του ψευδωνύμου. Η #επιλογή# μπορεί να είναι:" + +#: modules/commands/ns_set.cpp:237 +msgid "" +"Sets whether services should set channel status modes on you automatically." +msgstr "" + +#: modules/commands/cs_set.cpp:1090 +msgid "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." +msgstr "" +"Σύνταξη: #SET #κανάλι# NOEXPIRE {ON | OFF}#\n" +"\n" +"Με αυτή την εντολή μπορείς να κάνεις ένα κανάλι να μην λήγει ποτέ, χωρις να\n" +"είσαι υποχρεωμένος να κάνεις εντολή αναγνώρισης στο χρονικό\n" +"περιθώριο που σου δίνεται.\n" +"\n" +"Μόνο οι #Services Operators# μπορούν να το κάνουν." + +# +#: modules/commands/ns_set.cpp:315 +#, fuzzy, c-format +msgid "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." +msgstr "" +"Syntax: #SASET #nickname# AUTOOP {ON | OFF}#\n" +"\n" +"Ορίζει αν ένα άλλο nick θα πέρνει αυτόματο op.\n" +"Με επιλογή #ON# ο ChanServ θα δίνει Op στον χρήστη \n" +"αυτόματα όταν μπαίνει στα κανάλια." + +#: modules/commands/ns_set.cpp:1145 +msgid "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." +msgstr "" +"Syntax: #SASET #nickname# NOEXPIRE {ON | OFF}#\n" +"\n" +"Ρυθμίζει αν ένα ψευδόνυμο θα λήγει. Με τη παράμετρο\n" +"#ON# το nickname δεν θα λήγει." + +#: modules/commands/ns_set.cpp:288 +#, fuzzy, c-format +msgid "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." +msgstr "" +"Syntax: #SET AUTOOP {ON | OFF}#\n" +"\n" +"Ελένχει αν θα γίνεστε OP αυτόματα. Πατήστε ON για να \n" +"επιτρέψετε στον ChanServ να σας δίνει αυτόματο op στα κανάλια." + +#: modules/commands/cs_access.cpp:648 modules/commands/cs_access.cpp:689 +#, fuzzy, c-format +msgid "" +"Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." +msgstr "" +"Η επιλογή #%s# δεν είναι γνωστή. Γράψε #/msg %s HELP LEVELS DESC# για τη " +"λίστα με τισ αναλυτικές επιλογές." + +# +#: modules/commands/os_set.cpp:133 +msgid "Setting for DEBUG must be ON, OFF, or a positive number." +msgstr "" +"Η επιλογή για DEBUG πρέπει να είναι #ON#, #OFF#, ή ένα κατηγοριματικό " +"νούμερο." + +# +#: modules/commands/os_set.cpp:162 +#, fuzzy +msgid "Setting for NOEXPIRE must be ON or OFF." +msgstr "Η επιλογή για NOEXPIRE πρέπει να είναι #ON# ή #OFF#." + +# +#: modules/commands/os_set.cpp:56 +#, fuzzy +msgid "Setting for READONLY must be ON or OFF." +msgstr "Η επιλογή για READONLY πρέπει να είναι #ON# ή #OFF#." + +# +#: modules/commands/os_set.cpp:95 +#, fuzzy +msgid "Setting for super admin must be ON or OFF." +msgstr "Η επιλογή για READONLY πρέπει να είναι #ON# ή #OFF#." + +# +#: modules/commands/cs_set.cpp:74 +#, fuzzy +msgid "Should services automatically give status to users" +msgstr "Αν τα services πρέπει να σας δίνουν αυτόματα op" + +# +#: modules/commands/os_stats.cpp:203 +msgid "Show status of Services and network" +msgstr "Δείχνει στατιστικά σχετικά με τα Services και το δίκτυο" + +#: modules/commands/os_logsearch.cpp:152 +#, c-format +msgid "Showed %d/%d matches for %s." +msgstr "" + +# +#: modules/commands/cs_set.cpp:872 +#, fuzzy +msgid "Sign kicks that are done with the KICK command" +msgstr "Εμφαν. kicks τα οποία γίνονται με την εντολή KICK" + +#: modules/commands/cs_set.cpp:921 +#, c-format +msgid "Signed kick option for %s is now off." +msgstr "Η επιλογή Signed kick για το %s #ΑΠΕΝΕΡΓΟΠΟΙΗΘΗΚΕ#." + +#: modules/commands/cs_set.cpp:913 +#, fuzzy, c-format +msgid "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." +msgstr "" +"Η επιλογή Signed kick για το %s #ΕΝΕΡΓΟΠΟΙΗΘΗΚΕ#, αλλά εξαρτάται από το\n" +"level του χρήστη που χρησιμοποιεί την εντολή." + +#: modules/commands/cs_set.cpp:906 +#, c-format +msgid "Signed kick option for %s is now on." +msgstr "Η επιλογή Signed kick για το %s #ΕΝΕΡΓΟΠΟΙΗΘΗΚΕ#." + +#: modules/commands/cs_set.cpp:1299 +msgid "Signed kicks" +msgstr "Δηλωμένα kicks" + +#: modules/commands/ms_rsend.cpp:60 modules/commands/ms_send.cpp:59 +#, fuzzy, c-format +msgid "Sorry, %s currently has too many memos and cannot receive more." +msgstr "%s έχεις πολλά μηνύματα και δεν μπορείς να λάβεις άλλα." + +#: modules/commands/cs_seen.cpp:294 +#, c-format +msgid "Sorry, I have not seen %s." +msgstr "" + +#: modules/commands/bs_badwords.cpp:404 +#, fuzzy +msgid "Sorry, bad words list modification is temporarily disabled." +msgstr "Συγνώμη, η υπηρεσία bad words είναι απενεργοποιημένη." + +#: modules/commands/bs_assign.cpp:30 modules/commands/bs_assign.cpp:98 +msgid "Sorry, bot assignment is temporarily disabled." +msgstr "Συγνώμη, η υπηρεσία bot είναι απενεργοποιημένη." + +#: modules/commands/bs_bot.cpp:281 modules/commands/bs_assign.cpp:164 +msgid "Sorry, bot modification is temporarily disabled." +msgstr "Συγνώμη, η υπηρεσία για το bot είναι απενεργοποιημένη." + +#: modules/fantasy.cpp:42 modules/commands/bs_kick.cpp:813 +#: modules/commands/bs_kick.cpp:878 +msgid "Sorry, bot option setting is temporarily disabled." +msgstr "Συγνώμη, η εντολή setting είναι απενεργοποιημένη." + +#: modules/commands/bs_set.cpp:115 +#, fuzzy +msgid "Sorry, changing bot options is temporarily disabled." +msgstr "Συγνώμη, η εντολή setting είναι απενεργοποιημένη." + +#: modules/commands/cs_xop.cpp:112 modules/commands/cs_xop.cpp:235 +#: modules/commands/cs_xop.cpp:444 +#, c-format +msgid "Sorry, channel %s list modification is temporarily disabled." +msgstr "" +"Συγνώμη, η υπηρεσία για την εντολή AOP του καναλιού %s είναι εκτός " +"λειτουργίας." + +#: modules/commands/cs_access.cpp:547 modules/commands/cs_flags.cpp:405 +msgid "Sorry, channel access list modification is temporarily disabled." +msgstr "Συγνώμη, η υπηρεσία για την εντολή access είναι εκτός λειτουργίας." + +#: modules/commands/cs_akick.cpp:469 +msgid "Sorry, channel autokick list modification is temporarily disabled." +msgstr "Συγνώμη, η υπηρεσία για την εντολή akick είναι εκτός λειτουργίας." + +#: modules/commands/cs_drop.cpp:29 +msgid "Sorry, channel de-registration is temporarily disabled." +msgstr "Συγνώμη, η υπηρεσία διαγραφής καναλιών είναι απενεργοποιημένη." + +#: modules/commands/cs_register.cpp:35 +msgid "Sorry, channel registration is temporarily disabled." +msgstr "Συγνώμη, η υπηρεσία κατοχύρωσεις καναλιών δεν λειτουργεί για την ώρα." + +#: modules/commands/bs_kick.cpp:181 +msgid "Sorry, kicker configuration is temporarily disabled." +msgstr "Συγνώμη, η υπηρεσία kicker είναι απενεργοποιημένη." + +#: modules/commands/ms_set.cpp:216 +msgid "Sorry, memo option setting is temporarily disabled." +msgstr "Συγνώμη, η εντολή setting είναι απενεργοποιημένη." + +#: include/language.h:116 +msgid "Sorry, memo sending is temporarily disabled." +msgstr "Συγνώμη, η εντολή setting είναι απενεργοποιημένη." + +#: modules/commands/ns_drop.cpp:29 +msgid "Sorry, nickname de-registration is temporarily disabled." +msgstr "" +"Συγνώμη, η υπηρεσία για να σβήνει τα ψευδώνυμα είναι απενεργοποιημένη." + +#: modules/commands/ns_group.cpp:120 +msgid "Sorry, nickname grouping is temporarily disabled." +msgstr "" +"Συγνώμη, η ομαδοποίηση του ψευδώνυμού σου είναι για την ώρα απενεργοποιημένη." + +#: modules/commands/ns_register.cpp:139 +msgid "Sorry, nickname registration is temporarily disabled." +msgstr "Συγνώμη, η κατοχύρωση ψευδώνυμου είναι για την ώρα απενεργοποιημένη." + +#: modules/commands/ns_access.cpp:33 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d access entries has been reached." +msgstr "Συγνώμη, μπορείς μόνο να έχεις %d access στο κανάλι." + +#: modules/commands/ns_ajoin.cpp:141 +#, c-format +msgid "Sorry, the maximum of %d auto join entries has been reached." +msgstr "" + +#: modules/commands/ns_cert.cpp:173 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d certificate entries has been reached." +msgstr "Συγνώμη, μπορείς μόνο να έχεις %d πρόσβαση σε κατάταξη του ψευδώνυμου." + +#: modules/commands/ms_ignore.cpp:55 +#, fuzzy, c-format +msgid "Sorry, the memo ignore list for %s is full." +msgstr "Το μήνυμα χαιρετισμού για τον #%s# αφερέθηκε." + +#: modules/commands/cs_access.cpp:204 modules/commands/cs_flags.cpp:174 +#: modules/commands/cs_xop.cpp:201 +#, fuzzy, c-format +msgid "" +"Sorry, you can only have %d access entries on a channel, including access " +"entries from other channels." +msgstr "Συγνώμη, μπορείς μόνο να έχεις %d access στο κανάλι." + +#: modules/commands/cs_akick.cpp:177 +#, c-format +msgid "Sorry, you can only have %d autokick masks on a channel." +msgstr "Συγνώμη, μπορείς μόνο να έχεις %d autokick μάσκα στο κανάλι." + +#: modules/commands/bs_badwords.cpp:286 +#, fuzzy, c-format +msgid "Sorry, you can only have %d bad words entries on a channel." +msgstr "Συγνώμη, μπορείς μόνο να έχεις %d %s access στο κανάλι." + +#: include/language.h:103 +#, c-format +msgid "Sorry, you have already exceeded your limit of %d channels." +msgstr "Συγνώμη, μπορείς μόνο να έχεις %d κακές λέξεις για ένα κανάλι." + +#: include/language.h:102 +#, c-format +msgid "Sorry, you have already reached your limit of %d channels." +msgstr "Συγνώμη, μπορείς μόνο να έχεις %d κακές λέξεις για ένα κανάλι." + +#: modules/commands/os_dns.cpp:218 +msgid "State" +msgstr "" + +#: modules/commands/cs_seen.cpp:117 +msgid "Statistics and maintenance for seen data" +msgstr "" + +#: modules/commands/os_stats.cpp:131 +msgid "Statistics reset." +msgstr "Τα στατιστικά σβήστηκαν." + +#: modules/commands/ns_update.cpp:36 +msgid "Status updated (memos, vhost, chmodes, flags)." +msgstr "Το Status έγινε update (memos, vhost, chmodes, flags)." + +#: modules/commands/bs_kick.cpp:1432 +msgid "Stop flooding!" +msgstr "Μην επαναλαμβάνεις σε πολλές σειρές!" + +#: modules/commands/bs_kick.cpp:1448 +msgid "Stop repeating yourself!" +msgstr "Μην επαναλαμβάνεις τα ίδια!" + +# +#: modules/commands/cs_set.cpp:746 +msgid "Stricter control of channel founder status" +msgstr "Ασφάλεια του founder από το κανάλι" + +# +#: modules/commands/cs_set.cpp:810 +msgid "Stricter control of chanop status" +msgstr "Μόνο όσοι έχουν access θα έχουν op" + +#: modules/commands/ns_alist.cpp:75 modules/commands/cs_info.cpp:50 +msgid "Successor" +msgstr "" + +#: modules/commands/cs_set.cpp:1006 +#, fuzzy, c-format +msgid "Successor for %s changed to %s." +msgstr "Ο Successor του %s άλλαξε και πήγε στον #%s#." + +#: modules/commands/cs_set.cpp:1008 +#, c-format +msgid "Successor for %s unset." +msgstr "Ο Successor του #%s# δεν έχει οριστεί." + +#: modules/commands/os_set.cpp:81 +#, fuzzy +msgid "" +"Super admin can not be set because it is not enabled in the configuration." +msgstr "H ρύθμιση SuperAdmin δεν έχει ενεργοποιηθεί στο services.conf" + +# +#: modules/commands/ns_suspend.cpp:60 +msgid "Suspend a given nick" +msgstr "Κανει suspend ένα nick." + +#: modules/commands/cs_suspend.cpp:236 modules/commands/ns_suspend.cpp:250 +msgid "Suspend reason" +msgstr "" + +#: modules/commands/cs_suspend.cpp:232 modules/commands/ns_suspend.cpp:246 +msgid "Suspended" +msgstr "" + +#: modules/commands/cs_suspend.cpp:234 modules/commands/ns_suspend.cpp:248 +msgid "Suspended by" +msgstr "" + +# +#: modules/commands/cs_suspend.cpp:238 modules/commands/ns_suspend.cpp:252 +#, fuzzy +msgid "Suspended on" +msgstr "Κανει suspend ένα nick." + +#: modules/commands/ns_suspend.cpp:147 +#, fuzzy +msgid "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." +msgstr "" +"Syntax: #SUSPEND #channel# [#reason#]#\n" +"\n" +"Εμποδίζει τον οποιονδήποτε από το να κατοχυρώσει ή να χρησιμοποιήσει το\n" +"συγκεκριμένο κανάλι. Μπορεί να αναιρεθεί με τη χρήση της εντολής UNSUSPEND\n" +"η οποία επαναφέρει όλα τα προηγούμενα δεδομένα και ρυθμίσεις του καναλιού.\n" +"\n" +"Σε ορισμένα δίκτυα μπορεί να απαιτείται λόγος (reason) κατά τη χρήση της " +"εντολής." + +#: modules/commands/cs_suspend.cpp:240 modules/commands/ns_suspend.cpp:254 +#, fuzzy +msgid "Suspension expires" +msgstr " %s (δεν λήγει ποτέ)" + +# +#: modules/commands/cs_sync.cpp:19 +msgid "Sync users channel modes" +msgstr "Ο/η #%s# άλλαξε τα usermodes σας." + +#: modules/commands/cs_sync.cpp:49 +msgid "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." +msgstr "" + +# +#: modules/commands/hs_group.cpp:42 +msgid "Syncs the vhost for all nicks in a group" +msgstr "Συντονίζει την ίδια vhost για όλα τα nicks σε ένα group." + +#: src/command.cpp:146 +msgid "Syntax" +msgstr "" + +#: modules/commands/ns_group.cpp:373 +#, fuzzy, c-format +msgid "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." +msgstr "" +"Σύνταξη: #GLIST#\n" +"\n" +"Εμφανίζει όλα τα ψευδώνυμα που ανήκουν στην ίδια ομάδα." + +#: modules/commands/ns_group.cpp:363 +#, fuzzy, c-format +msgid "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." +msgstr "" +"Σύνταξη: #GLIST [#ψευδώνυμο#]#\n" +"\n" +"Χωρίς την παράμετρο, εμφανίζει όλα τα ψευδώνυμα που είναι \n" +"στην ομάδα σου.\n" +" \n" +"Με την παράμετρο, εμφανίζει όλα τα ψευδώνυμα που είναι στην ομάδα\n" +"του ζητούμενου ψευδώνυμου. Μόνο οι #Services Operators# \n" +"μπορούν να το κάνουν." + +# +#: modules/commands/os_set.cpp:227 +#, fuzzy +msgid "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." +msgstr "" +"Σύνταξη: #SET NOEXPIRE {ON | OFF}#\n" +"\n" +"Αλλάζει σε no expire mode on ή off. Σε no expire mode, ψευδώνυμα,\n" +"κανάλια, akills και exceptions δεν θα λήγουν εκτός και αν\n" +"αυτή η επιλογή δεν ρυθμιστεί.\n" +"\n" +"Αυτή η επιλογή είναι αντίστοιχη με την εντολή-line επιλογή\n" +"#-noexpire#." + +#: modules/commands/ms_set.cpp:287 +#, c-format +msgid "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." +msgstr "" +"Σύνταξη: #SET LIMIT [#κανάλι#] #όριο##\n" +"\n" +"Ορίζει τον μέγιστο αριθμό μηνυμάτων που μπορείτε να έχετε\n" +"εσείς ή το κανάλι που δίνεται. Αν οριστεί στο 0, κανείς\n" +"δε θα μπορεί να σας στείλει μηνύματα. Πάντως δε μπορείτε\n" +"να ορίσετε τον αριθμό πάνω από %d." + +#: modules/commands/ms_set.cpp:267 +#, fuzzy, c-format +msgid "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." +msgstr "" +"Σύνταξη: #SET LIMIT [#χρήστης# | #κανάλι#] {#όριο# | NONE} [HARD]#\n" +"\n" +"Ρυθμίζεις το μέγιστο νούμερο μηνυμάτων που θες να λάβεις είτε για\n" +"ψευδώνυμο ή για κανάλι. Αν βάλετε όριο το 0 απαλλάσεστε από\n" +"την υπηρεσία αυτή και δεν λαμβάνεται κανένα μήνυμα. Αν επιλέξετε #NONE#\n" +"επιτρέπει στο χρήστη να λάβει όσα θέλει αυτός. Αν δεν δώσετε\n" +"ψευδώνμο ή κανάλι, ρυθμίζετε το δικό σας όριο.\n" +" \n" +"Επιλέγοντας #HARD# εμποδίζεται το χρήστη να αλλάξει το όριο. Αν δεν\n" +"επιλέξετε #HARD# θα έχει το αντίθετο αποτέλεσμα, επιτρέποντας στο\n" +"χρήστη να αλλάξει το όριο \n" +"(ακόμα και αν η επιλογή η προηγούμενη ήταν #HARD#).\n" +" \n" +"Αυτή η χρήση της εντολής #SET LIMIT# είναι μόνο για \n" +"τους #Services# #admins#. Οι άλλοι χρήστες μπορούν να αλλάξουν το όριο\n" +"μόνο για τον εαυτό τους ή για τα κανάλια που έχουν κάποια δικαιώματα.\n" +"Δεν μπορούν να ξεπεράσουν το όριο των %d μηνυμάτων, και δεν μπορούν να\n" +"επιλέξουν hard limit." + +#: modules/commands/os_set.cpp:208 +#, fuzzy, c-format +msgid "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." +msgstr "" +"Syntax: #SET LIST\n" +"Παρουσιάζει διάφορες ρυθμίσεις του %s" + +# +#: modules/commands/os_set.cpp:234 +#, fuzzy +msgid "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." +msgstr "" +"Σύνταξη: #SET NOEXPIRE {ON | OFF}#\n" +"\n" +"Αλλάζει σε no expire mode on ή off. Σε no expire mode, ψευδώνυμα,\n" +"κανάλια, akills και exceptions δεν θα λήγουν εκτός και αν\n" +"αυτή η επιλογή δεν ρυθμιστεί.\n" +"\n" +"Αυτή η επιλογή είναι αντίστοιχη με την εντολή-line επιλογή\n" +"#-noexpire#." + +#: modules/commands/ms_set.cpp:246 +#, fuzzy +msgid "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." +msgstr "" +"Σύνταξη: #SET NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}#\n" +"\n" +"Αλλαγές για το πως θέλετε να ενημερώνεστε για νέα μηνύματα:\n" +"\n" +" ON Θα ενημερώνεστε για τα μηνύματα σας όταν θα κάνετε log on,\n" +" όταν θα επανέρχεστε από /AWAY, και όταν θα σας στέλνουν\n" +" μηνύματα.\n" +" LOGON Θα ενημερώνεστε για τα μηνύματα σας μόνο όταν θα κάνετε log\n" +" on ή όταν θα επανέρχεστε από /AWAY.\n" +" NEW Θα ενημερώνεστε για τα μηνύματα σας μόνο όταν θα σας\n" +" τα στέλνουν.\n" +" MAIL You will be notified of memos by email aswell as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF Δεν θα ενημερώνεστε ποτέ για νέα μηνύματα ή παλιά.\n" +"\n" +"Η επιλογή #ON# πιο ουσιώδης,η #LOGON# και η #NEW# συνδιαστική." + +#: modules/commands/os_set.cpp:212 +#, fuzzy +msgid "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." +msgstr "" +"Σύνταξη: #SET READONLY {ON | OFF}#\n" +"\n" +"Αλλάζετε σε read-only mode on ή off. Η read-only mode, normal\n" +"users δεν θα επιτρέψει να αλλάξει η βάση δεδομένων των Services,\n" +"συμπεριλαμβανομένου καναλιού και ψευδώνυμου access lists, klp. IRCops\n" +"me επαρκή δικαιώματα στα Services θα μπορούν να αλλάζουν τα\n" +"Services' την λίστα AKILL να κάνουν drop (διαγραφεί ψευδωνύμων) ή καταστολή\n" +"ψευδωνύμων και καναλιών, αλλά όποιες αλλαγές και να γίνονται\n" +"δεν θα γραφούν εκτός και αν η read-only mode είναι απενεργοποημένη πριν τα \n" +"Services τερματιστούν ή επανεκκινηθούν.\n" +" \n" +"Αυτή η επιλογή είναι αντίστοιχη με την εντολή-line επιλογή\n" +"#-readonly#." + +#: modules/commands/os_set.cpp:243 +#, fuzzy +msgid "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." +msgstr "" +"Syntax: #SET SUPERADMIN {ON | OFF}#\n" +"Αυτή η ρύθμιση σας δίνει extra προνόμια όπως\n" +"τη δυνατότητα να είστε \"founder\" σε όλα τα κανάλια,κτλπ\n" +"Αυτή η επιλογή δεν είναι μόνιμη και πρέπει να χρησιμοποιείται μόνο\n" +"όταν χρειάζεται, και να γίνεται OFF όταν δεν χρειάζεται." + +#: modules/commands/ns_identify.cpp:107 +#, c-format +msgid "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." +msgstr "" +"Σύνταξη: #IDENTIFY [account] #κωδικό##\n" +"\n" +"Λέει στον %s αν είσαι όντος ο κάτοχος αυτού του ψευδώνυμου.\n" +"Πολλές εντολές απαιτούν να κάνεις εντολή αναγνώρισης, δηλ με την εντολή\n" +"αυτή πριν χρησιμοποιήσεις άλλες εντολές. Ο κωδικός θα πρέπει να είναι\n" +"ο ίδιος με αυτόν που έδωσες για να κατοχυρώσης το ψευδώνυμο,\n" +"δηλ με την #REGISTER# εντολή." + +#: modules/commands/cs_invite.cpp:91 +#, fuzzy, c-format +msgid "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Σύνταξη: #INVITE #κανάλι##\n" +"\n" +"Ζητάει από τον %s να καλέσει το ανάλογο ψευδώνυμο να έρθει στο κανάλι. \n" +"\n" +"Από default, χρησιμοποιείται από τους AOPs ή από αυτούς που έχουν level 5 " +"και\n" +"παραπάνω στο κανάλι." + +#: modules/commands/cs_unban.cpp:103 +#, fuzzy, c-format +msgid "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Σύνταξη: #UNBAN #κανάλι# [#nick#]#\n" +"\n" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel.\n" +" \n" +"Από default, χρησιμοποιείται από τους AOPs ή αυτούς που έχουν level 5 και\n" +"παραπάνω στο κανάλι.\n" +" " + +# +#: modules/commands/os_jupe.cpp:56 +msgid "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." +msgstr "" +"Σύνταξη: #JUPE #server# [#λόγος#]#\n" +"\n" +"Κάνεις τα Services jupiter σε έναν server -- που είναι, να δημιουργήσει\n" +"ένα ψεύτικο \"server\" συνδεδεμένο με τα Services ο οποίος περιέχει\n" +"τον πραγματικό server που είναι συνδεδεμένα. Το jupe\n" +"μπορεί να αφαιρεθεί χρησιμοποιώντας την εντολή #SQUIT#. Αν ο λόγος δίνεται\n" +"θα γραφτεί στου server τις πληροφορίες;\n" +"αλλιώς, οι πληροφορίες θα περιέχουν ένα\n" +"text \"Juped by <ψευδώνυμο>\", δείχνοντας το ψευδώνυμο του\n" +"χρήστη που έκανε jupitered τον server.\n" +"\n" +"Μόνο για τους #Services Operators#." + +#: modules/commands/cs_seen.cpp:261 +msgid "Tells you about the last time a user was seen" +msgstr "" + +# +#: modules/commands/os_shutdown.cpp:19 +msgid "Terminate Services WITHOUT saving" +msgstr "Τερματίζει τα Services αποθηκεύοντας τις αλλαγές" + +# +#: modules/commands/os_shutdown.cpp:73 +msgid "Terminate services with save" +msgstr "Τερματίζει τα Services αποθηκεύοντας τις αλλαγές" + +#: modules/commands/os_news.cpp:156 +msgid "Text" +msgstr "" + +#: modules/commands/cs_access.cpp:576 +msgid "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." +msgstr "" + +#: modules/commands/cs_access.cpp:587 +msgid "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." +msgstr "" + +#: modules/commands/cs_access.cpp:593 +msgid "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." +msgstr "" +"Η εντολή #BADWORDS DEL# αφαιρεί τη δοσμένη λέξη από τη λίστα των\n" +"απαγορευμένων λέξεων. Σε περίπτωση που δοθεί μια λίστα με αριθμούς " +"καταχωρήσεων,\n" +"αυτές οι καταχωρήσεις διαγράφονται. (Βλέπε παράδειγμα για λίστα παρακάτω.)\n" +" \n" +"Η εντολή #BADWORDS LIST# προβάλλει τη λίστα των απαγορευμένων λέξεων. Αν " +"δοθεί\n" +"μια wildcard mask, τοτε μόνο οι καταχωρήσεις που αντιστοιχούν στη\n" +"mask προβάλλονται. Αν δοθεί μια λίστα με αριθμούς καταχωρήσεων,\n" +"τότε μόνο οι συγκεκριμένες καταχωρήσεις προβάλλονται. Για παράδειγμα:\n" +" #BADWORDS #channel LIST 2-5,7-9#\n" +" Προβάλλει τις καταχωρημένες απαγορευμένες λέξεις από το 2 εως το 5 " +"και\n" +" απο το 7 μέχρι το 9.\n" +" \n" +"Η εντολή #BADWORDS CLEAR# διαγράφει όλες τις καταχωρήσεις της λίστας\n" +"των απαγορευμένων λέξεων." + +#: modules/commands/cs_flags.cpp:447 +msgid "" +"The CLEAR command clears the channel access list. This requires channel " +"founder access." +msgstr "" + +#: modules/commands/cs_seen.cpp:173 +#, c-format +msgid "" +"The CLEAR command lets you clean the database by removing all entries from " +"the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." +msgstr "" + +#: modules/commands/bs_badwords.cpp:438 +#, fuzzy +msgid "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." +msgstr "" +"Η εντολή #BADWORDS DEL# αφαιρεί τη δοσμένη λέξη από τη λίστα των\n" +"απαγορευμένων λέξεων. Σε περίπτωση που δοθεί μια λίστα με αριθμούς " +"καταχωρήσεων,\n" +"αυτές οι καταχωρήσεις διαγράφονται. (Βλέπε παράδειγμα για λίστα παρακάτω.)\n" +" \n" +"Η εντολή #BADWORDS LIST# προβάλλει τη λίστα των απαγορευμένων λέξεων. Αν " +"δοθεί\n" +"μια wildcard mask, τοτε μόνο οι καταχωρήσεις που αντιστοιχούν στη\n" +"mask προβάλλονται. Αν δοθεί μια λίστα με αριθμούς καταχωρήσεων,\n" +"τότε μόνο οι συγκεκριμένες καταχωρήσεις προβάλλονται. Για παράδειγμα:\n" +" #BADWORDS #channel LIST 2-5,7-9#\n" +" Προβάλλει τις καταχωρημένες απαγορευμένες λέξεις από το 2 εως το 5 " +"και\n" +" απο το 7 μέχρι το 9.\n" +" \n" +"Η εντολή #BADWORDS CLEAR# διαγράφει όλες τις καταχωρήσεις της λίστας\n" +"των απαγορευμένων λέξεων." + +#: modules/commands/cs_entrymsg.cpp:241 +msgid "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:253 +msgid "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:245 +msgid "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:250 +msgid "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." +msgstr "" + +#: modules/commands/ns_set.cpp:713 +msgid "The IMMED option is not available on this network." +msgstr "Η #IMMED# επιλογή δεν είναι διαθέσιμη σε αυτό το δίκτυο." + +#: modules/commands/cs_access.cpp:821 +#, fuzzy, c-format +msgid "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." +msgstr "" +"Σύνταξη: #LEVELS #κανάλι# SET #τύπος# [#βαθμός#|FOUNDER]#\n" +" #LEVELS #κανάλι# {DIS | DISABLE} #τύπος##\n" +" #LEVELS #κανάλι# LIST#\n" +" #LEVELS #κανάλι# RESET#\n" +"\n" +"Η εντολή levels ορίζει τη σημασία της αριθμητικής access\n" +"που χρησιμοποιείται για τα κανάλια. Με αυτή την εντολή,\n" +"ορίζετε το επίπεδο access που απαιτείται για τις περισσότερες από τις " +"λειτουργίες του %s \n" +"(H εντολή SET FOUNDER και αυτή η εντολή \n" +"περιορίζονται πάντα στον καναλάρχη.)\n" +"\n" +"Η εντολη LEVELS SET επιτρέπει να αλλάξει το access level που απαιτείται για " +"μια σειρά λειτουργιών\n" +"Η εντολή LEVELS DISABLE (ή DIS)\n" +"απενεργοποιεί μια λειτουργία, έτσι ώστε κανένας, ούτε ο founder\n" +"δεν μπορεί να τη χρησιμοποιήσει.(παρόλα αυτά, ο founder \n" +"μπορεί πάντα να την ξαναενεργοποιήσει).\n" +"\n" +"Η εντολή LEVELS LIST δείχνει τη λίστα με τα access levels για όλες τις " +"λειτουργίες.\n" +"Η εντολή LEVELS RESET κάνει reset στα προκαθορισμένα access levels\n" +"ενός καναλιού που μόλις δημιουργήθηκε. (βλ\n" +"HELP ACCESS LEVELS).\n" +"\n" +"Για μια λίστα από λειτουργίες των οποίων το access level μπορείτε να " +"τροποποιήσετε, βλ: HELP LEVELS DESC." + +#: modules/commands/cs_flags.cpp:442 +msgid "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." +msgstr "" + +#: modules/commands/cs_flags.cpp:435 +msgid "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access " +"list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. " +"You are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of " +"what your access is." +msgstr "" + +#: modules/commands/cs_seen.cpp:172 +msgid "" +"The STATS command prints out statistics about stored nicks and memory usage." +msgstr "" + +#: modules/commands/ns_register.cpp:291 +#, fuzzy +msgid "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." +msgstr "" +"Γράψε #%s%s SET EMAIL #e-mail## για να προσθέσεις το e-mail στις πληροφορίες " +"του ψευδώνυμού σου.\n" +"Η μυστικότητα είναι σεβαστή; αυτό το e-mail και ο κωδικός του δεν πρέπει να " +"δωθεί σε\n" +"κανένα τρίτο πρόσωπο." + +#: modules/commands/cs_log.cpp:258 +#, c-format +msgid "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." +msgstr "" + +#: modules/commands/cs_ban.cpp:64 +#, fuzzy, c-format +msgid "The %s list for %s is full." +msgstr "Το μήνυμα χαιρετισμού για τον #%s# αφερέθηκε." + +#: modules/commands/os_sxline.cpp:220 +#, fuzzy, c-format +msgid "The %s list has been cleared." +msgstr "Η λίστα AKILL καθαρίστηκε." + +#: modules/commands/os_akill.cpp:377 +msgid "The AKILL list has been cleared." +msgstr "Η λίστα AKILL καθαρίστηκε." + +#: modules/commands/os_defcon.cpp:136 modules/commands/os_defcon.cpp:225 +#, c-format +msgid "The Defcon level is now at: %d" +msgstr "Το defcon επίπεδο είναι τώρα: #%d#" + +#: modules/commands/ns_info.cpp:171 +#, c-format +msgid "The E-mail address of %s will now be hidden from %s INFO displays." +msgstr "Το email του #%s# δεν θα φαίνεται τώρα στο %s INFO." + +#: modules/commands/ns_info.cpp:172 +#, c-format +msgid "The E-mail address of %s will now be shown in %s INFO displays." +msgstr "Το email του #%s# θα φαίνεται τώρα στο %s INFO." + +#: modules/commands/cs_flags.cpp:449 +msgid "The available flags are:" +msgstr "" + +#: modules/commands/os_defcon.cpp:240 +msgid "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." +msgstr "" +"Syntax: #DEFCON# [#1#|#2#|#3#|#4#|#5#]\n" +"Το σύστημα defcon μπορεί να χρησιμοποιηθεί για να ορίσετε \n" +"κάποιες προκαθωρισμένες ενέργειες των services σε περίπτωση\n" +"επίθεσης στο δίκτυο." + +#: modules/ns_maxemail.cpp:51 +#, c-format +msgid "The email address %s has reached its usage limit of %d users." +msgstr "" + +#: modules/ns_maxemail.cpp:49 +#, c-format +msgid "The email address %s has reached its usage limit of 1 user." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:142 +#, c-format +msgid "The entry message list for %s is full." +msgstr "Το μήνυμα χαιρετισμού για τον #%s# αφερέθηκε." + +#: modules/commands/cs_access.cpp:796 +msgid "The following feature/function names are available:" +msgstr "" + +#: modules/commands/cs_access.cpp:584 +msgid "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." +msgstr "" + +#: modules/commands/os_session.cpp:240 +#, fuzzy, c-format +msgid "" +"The host %s currently has %d sessions with a limit of %d because it matches " +"entry: %s." +msgstr "Το host #%s# έχει ως τώρα #%d# sessions με όριο το #%d#." + +#: modules/commands/ms_check.cpp:54 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has been read." +msgstr "Το τελευταίο memo που στείλατε στον %s (στις %s) έχει διαβαστεί." + +#: modules/commands/ms_check.cpp:52 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has not yet been read." +msgstr "" +"Το τελευταίο memo που στείλατε στον %s (στις %s) δεν έχει διαβαστεί ακόμη." + +#: modules/commands/ns_info.cpp:189 +#, c-format +msgid "The last quit message of %s will now be hidden from %s INFO displays." +msgstr "Το τελευταίο quit message του #%s# δεν θα φαίνεται τώρα στο %s INFO." + +#: modules/commands/ns_info.cpp:190 +#, c-format +msgid "The last quit message of %s will now be shown in %s INFO displays." +msgstr "Το τελευταίο quit message του #%s# θα φαίνεται τώρα στο %s INFO." + +#: modules/commands/ns_info.cpp:177 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." +msgstr "Η τελευταία user@host mask του #%s# δεν θα φαίνεται τώρα στο %s INFO." + +#: modules/commands/ns_info.cpp:178 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." +msgstr "Η τελευταία user@host mask του #%s# θα φαίνεται τώρα στο %s INFO." + +#: modules/commands/cs_enforce.cpp:190 +#, fuzzy, c-format +msgid "The limit on %s is not valid." +msgstr "Το όριο των μηνυμάτων για τον %s δεν μπορεί να αλλαχτεί." + +#: modules/commands/os_forbid.cpp:193 +msgid "The mask must contain at least one non wildcard character." +msgstr "" + +#: modules/commands/ms_set.cpp:153 +#, c-format +msgid "The memo limit for %s may not be changed." +msgstr "Το όριο των μηνυμάτων για τον %s δεν μπορεί να αλλαχτεί." + +#: modules/commands/cs_mode.cpp:347 +#, fuzzy, c-format +msgid "The mode lock list of %s is full." +msgstr "Το μήνυμα χαιρετισμού για τον #%s# αφερέθηκε." + +#: modules/commands/ns_set.cpp:355 +#, c-format +msgid "The new display MUST be a nickname of the nickname group %s." +msgstr "" + +#: include/language.h:98 +#, fuzzy, c-format +msgid "The new display is now %s." +msgstr "Το defcon επίπεδο είναι τώρα: #%d#" + +#: modules/commands/os_svs.cpp:57 +#, c-format +msgid "The nick %s is now being changed to %s." +msgstr "Tο nick #%s# άλλαξε σε #%s#." + +#: modules/commands/bs_bot.cpp:149 +msgid "The old information is the same as the new information specified." +msgstr "" + +#: modules/commands/os_info.cpp:157 +#, fuzzy, c-format +msgid "The oper info already exists on %s." +msgstr "Το Bot #%s# υπάρχει ήδη." + +#: modules/commands/os_info.cpp:147 +#, fuzzy, c-format +msgid "The oper info list for %s is full." +msgstr "Το μήνυμα χαιρετισμού για τον #%s# αφερέθηκε." + +#: modules/commands/ns_info.cpp:183 +#, c-format +msgid "" +"The services access status of %s will now be hidden from %s INFO displays." +msgstr "" +"Το επίπεδο πρόσβασης του #%s# στα Services δεν θα φαίνεται στο %s INFO." + +#: modules/commands/ns_info.cpp:184 +#, c-format +msgid "The services access status of %s will now be shown in %s INFO displays." +msgstr "Το επίπεδο πρόσβασης του #%s# στα Services θα φαίνεται στο %s INFO." + +# +#: modules/commands/os_session.cpp:433 +#, fuzzy +msgid "The session exception list is empty." +msgstr "Αλλάζεις την λίστα του session-limit exception" + +#: modules/commands/ns_recover.cpp:121 +msgid "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:195 +#, c-format +msgid "There are %d memos on channel %s." +msgstr "Υπάρχουν #%d# memos στο κανάλι %s." + +#: modules/commands/bs_botlist.cpp:47 +msgid "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" +msgstr "" +"Δεν υπάρχουν διαθέσιμα bots αυτή τη στιγμή.\n" +"Ρώτα τον Services Operator να σου φτιάξει ένα!" + +#: modules/commands/os_dns.cpp:213 +msgid "There are no configured servers." +msgstr "" + +#: modules/commands/os_forbid.cpp:392 +#, fuzzy, c-format +msgid "There are no forbids of type %s." +msgstr "Υπάρχουν #%d# memos στο κανάλι %s." + +# +#: modules/commands/ns_group.cpp:162 +#, fuzzy +msgid "There are too many nicks in your group." +msgstr "Διαγράφει τη vhost από όλα τα nicks σε ένα group" + +# +#: modules/commands/cs_log.cpp:123 +#, fuzzy, c-format +msgid "There currently are no logging configurations for %s." +msgstr "Λάθος στην επαναφόρτηση του αρχείου configuration" + +#: modules/pseudoclients/memoserv.cpp:193 +#, c-format +msgid "There is %d memo on channel %s." +msgstr "Υπάρχουν #%d# memo στο κανάλι %s." + +#: include/language.h:110 +#, fuzzy, c-format +msgid "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." +msgstr "Γράψε #/msg %s READ %d# για να διαβάσεις." + +#: modules/commands/bs_assign.cpp:132 +#, c-format +msgid "There is no bot assigned to %s anymore." +msgstr "Δεν υπάρχει bot που να είναι στο %s τώρα πια." + +#: modules/commands/os_news.cpp:33 +msgid "There is no logon news." +msgstr "Δεν υπάρχουν κανονισμοί ή πληροφορίες." + +#: modules/commands/os_news.cpp:43 +msgid "There is no oper news." +msgstr "Δεν υπάρχουν νέα για τους opers." + +#: modules/commands/os_news.cpp:53 +msgid "There is no random news." +msgstr "Δεν υπάρχουν νέα." + +# +#: modules/commands/os_config.cpp:41 +#, fuzzy, c-format +msgid "There is no such configuration block %s." +msgstr "Λάθος στην επαναφόρτηση του αρχείου configuration" + +#: modules/commands/cs_mode.cpp:706 +#, fuzzy, c-format +msgid "There is no such mode %s." +msgstr "Δεν υπάρχουν νέα για τους opers." + +#: modules/commands/ms_set.cpp:52 +msgid "There's no email address set for your nick." +msgstr "Δεν υπάρχει email που να συνδέεται με το nick σας." + +#: modules/commands/os_forbid.cpp:304 modules/commands/os_forbid.cpp:496 +#, fuzzy, c-format +msgid "This channel has been forbidden: %s" +msgstr "Αυτό το κανάλι δεν μπορεί να χρησιμοποιηθεί." + +#: modules/commands/cs_suspend.cpp:121 +msgid "This channel has been suspended." +msgstr "Αυτό το κανάλι δεν μπορεί να χρησιμοποιηθεί." + +#: modules/commands/cs_suspend.cpp:232 +#, fuzzy +msgid "This channel is suspended." +msgstr "Αυτό το κανάλι δεν μπορεί να χρησιμοποιηθεί." + +#: modules/commands/cs_suspend.cpp:268 +msgid "This channel may not be used." +msgstr "Αυτό το κανάλι δεν μπορεί να χρησιμοποιηθεί." + +#: modules/commands/os_dns.cpp:702 +msgid "" +"This command allows managing DNS zones used for controlling what servers " +"users\n" +"are directed to when connecting. Omitting all parameters prints out the " +"status of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to " +"this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, " +"the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given " +"zones." +msgstr "" + +#: modules/commands/hs_group.cpp:72 +msgid "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." +msgstr "" +"Αυτή η εντολή επιτρέπει στους χρήστες να ορίσουν τη vhost\n" +"του nick που χρησιμοποιούν, ώς vhost για όλα τα nicks στο group τους." + +#: modules/commands/ns_register.cpp:299 +msgid "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." +msgstr "" + +#: modules/m_rewrite.cpp:145 +#, c-format +msgid "This command is an alias to the command %s." +msgstr "" + +# +#: modules/commands/ns_register.cpp:95 +msgid "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." +msgstr "" +"Syntax: #CONFIRM #passcode##\n" +"\n" +"Αυτό είναι το δεύτερο μέρος της κατοχύρωσης ενός ψευδονύμου..\n" +"Πρέπει να εκτελέσετε αυτή την εντολή για να κατωχυρώσετε το \n" +"nick σας με το %s. Το passcode (ή αλλιώς auth code)\n" +"στέλνεται στο email σας στο πρώτο βήμα της κατωχύρωσης\n" +"Για περισσότερες πληροφορίες πληκτρολογήστε:\n" +"#/msg %s HELP REGISTER#\n" +"Αυτό γίνεται επίσης όταν η εντολή RESETPASS χρησιμοποιείται\n" +"για να αναγνοριστεί το nick σας και να αλλάξετε τον κωδικό σας." + +#: modules/commands/os_modinfo.cpp:70 +#, fuzzy +msgid "This command lists information about the specified loaded module." +msgstr "" +"Syntax: #MODINFO# #FileName#\n" +"Αυτή η εντολή δίνει πληροφορίες για ένα φορτωμένο module." + +#: modules/commands/hs_list.cpp:136 +#, fuzzy +msgid "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." +msgstr "" +"Syntax: #LIST# #[|<#X-Y>]#\n" +"Αυτή η εντολή εμφανίζει μια λίστα με όλα τα κατωχυρωμένα vhosts.\n" +"αν ορίσετε κάποιο key, μόνο οι vhosts που ταιριάζουν με το key\n" +"θα εμφανιστούν. π.χ. Ιάσονας* όλες τις εκχωρήσεις που\n" +"ξεκινούν με \"Ιάσονας\"\n" +"Αν χρησιμοποιηθεί μέθοδος #X-Y, μόνο εκχωρήσεις μεταξύ του Χ\n" +"και του Υ θα εμφανιστούν, π.χ. #1-3 θα εμφανίσει τις πρώτες 3\n" +"εκχωρήσεις.\n" + +#: modules/commands/os_module.cpp:45 +#, fuzzy +msgid "" +"This command loads the module named modname from the modules\n" +"directory." +msgstr "" +"Syntax: #MODLOAD# #FileName#\n" +"Αυτή η εντολή φορτώνει ένα module από τη λίστα των modules." + +#: modules/commands/ns_group.cpp:201 +#, fuzzy +msgid "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." +msgstr "" +"Σύνταξη: #GROUP #στόχος# #κωδικός##\n" +"\n" +"Αυτή η εντολή κάνει το ψευδώνυμο σου να μπένει στο #στόχο# των \n" +"ψευδωνύμων της ομαδοποίησης. #Κωδικός# είναι ο κωδικός του \n" +"στόχου,δηλ του άλλου ψευδωνύμου.\n" +"\n" +"Μπαίνοντας στην ομάδα έχεις πρόσβαση και μοιράζεσαι,τα μηνύματα \n" +"δηλ memos, και κυριαρχία στα κανάλια που αντιστοιχούν όλα\n" +"τα ψευδώνυμα σε αυτή την ομάδα, και πολλά άλλα!\n" +" \n" +"Η ομάδα φτιάχεται για να σας εξυπηρετεί καλύτερα. Αυτό σημαίνει \n" +"οτι αν διαγράψετε κάποιο ψευδώνυμο και είναι στην ομάδα,\n" +"δεν θα χάσετε τις πληροφορίες και τα μοιρασμένα πράγματα που \n" +"έχετε με τα άλλα ψευδώνυμα, αρκεί όμως στην ομάδα\n" +"να υπάρχει τουλάχιστον ένα ψευδώνυμο.\n" +" \n" +"Μπορείς να εκτελέσεις αυτή την εντολή ακόμα και όταν δεν\n" +"έχεις κατοχυρώσει κάποιο ψευδώνυμο ακόμα. Αν το ψευδώνυμο είναι\n" +"κατοχυρωμένο, θα πρέπει να κάνεις εντολή αναγνώρισης πρώτα και \n" +"μετά να χρησιμοποιήσεις αυτή την εντολή. Γράψε\n" +"#/msg %s HELP IDENTIFY# για περισσότερες πληροφορίες. Αυτό το \n" +"κομμάτι μπορεί να μην υπάρχει στο δικτυό σου.\n" +" \n" +"Είναι προτιμότερο να χρησιμοποιήσεις αυτή την εντολή με μη-κατοχυρωμένα \n" +"ψευδώνυμα γιατί θα γίνει αυτόματα η κατοχύρωση όταν θα χρησιμοποιήσεις \n" +"αυτή την εντολή. Μπορείς και να την χρησιμοποιήσεις και με κατοχυρωμένα \n" +"ψευδώνυμα (για να αλλάξεις την ομάδα σου) μόνο αν ο επικεφαλής των \n" +"υπηρεσιών σε αφήσει να το κάνεις.\n" +" \n" +"Μπορείς να είσαι σε μια ομάδα κάθε φορά. Σε πολλές ομάδες δεν είναι " +"δυνατόν.\n" +" \n" +"#Σημείωση#: όλα τα ψευδώνυμα που ανήκουν στην ίδια ομάδα έχουν τον ίδιο \n" +"κωδικό." + +#: modules/commands/ns_ajoin.cpp:292 +msgid "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." +msgstr "" + +#: modules/commands/ns_set.cpp:345 modules/commands/ns_set.cpp:669 +msgid "" +"This command may not be used on this network because nickname ownership is " +"disabled." +msgstr "" + +# +#: modules/commands/os_module.cpp:118 +#, fuzzy +msgid "This command reloads the module named modname." +msgstr "" +"Syntax: #MODLOAD# #FileName#\n" +"Αυτή η εντολή φορτώνει ένα module από τη λίστα των modules." + +#: modules/commands/hs_request.cpp:344 +msgid "This command retrieves the vhost requests." +msgstr "" + +#: modules/commands/os_logsearch.cpp:159 +msgid "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." +msgstr "" + +#: modules/commands/cs_status.cpp:106 +msgid "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." +msgstr "" + +#: modules/commands/ns_group.cpp:285 +#, fuzzy +msgid "" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." +msgstr "" +"Syntax: #UNGROUP #[nick]##\n" +"Αυτή η εντολή βγάζει το ψευδώνυμό σας ή, αν δοθεί, κάποιο άλλο ψευδώνυμο\n" +"από το γκρουπ στο οποίο βρίσκεται. Το ψευδώνυμο που βγήκε από το γκρουπ " +"διατηρεί\n" +"την ώρα κατοχύρωσης, το password, το email, το greet, τη γλώσσα, το url, και " +"το icq.\n" +"Ολα τα άλλα διαγράφονται. Δεν μπορείτε να βγάλετε τον εαυτό σας από το " +"γκρούπ αν\n" +"είστε το μόνο ψευδώνυμο/χρήστης μέσα σε αυτό." + +# +#: modules/commands/os_module.cpp:168 +#, fuzzy +msgid "This command unloads the module named modname." +msgstr "" +"Syntax: #MODLOAD# #FileName#\n" +"Αυτή η εντολή φορτώνει ένα module από τη λίστα των modules." + +#: modules/commands/ns_register.cpp:353 +msgid "This command will resend you the registration confirmation email." +msgstr "" + +#: include/language.h:90 +#, c-format +msgid "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" +msgstr "" + +#: modules/commands/os_forbid.cpp:469 +#, c-format +msgid "This nickname has been forbidden: %s" +msgstr "Αυτό το κανάλι έχει κατοχυρωθεί με τον %s." + +#: modules/commands/ns_recover.cpp:99 +#, fuzzy, c-format +msgid "This nickname has been recovered by %s." +msgstr "Αυτό το κανάλι έχει κατοχυρωθεί με τον %s." + +#: modules/commands/ns_recover.cpp:77 +#, c-format +msgid "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." +msgstr "" + +#: include/language.h:95 +msgid "This nickname has been registered; you may not use it." +msgstr "Αυτό το κανάλι έχει κατοχυρωθεί με τον %s." + +#: modules/commands/ns_suspend.cpp:246 +#, fuzzy +msgid "This nickname is suspended." +msgstr "Αυτό το κανάλι δεν μπορεί να χρησιμοποιηθεί." + +#: include/language.h:92 +#, c-format +msgid "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." +msgstr "" + +#: modules/commands/ms_read.cpp:95 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %d" +msgstr "Μήνυμα %d από %s (%s). Για να το σβήσεις, γράψε: #/msg %s DEL %s %d#" + +#: modules/commands/ms_read.cpp:93 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %s %d" +msgstr "Μήνυμα %d από %s (%s). Για να το σβήσεις, γράψε: #/msg %s DEL %s %d#" + +#: modules/commands/bs_kick.cpp:791 +msgid "To protect ops against bot kicks" +msgstr "" + +#: modules/commands/bs_kick.cpp:856 +msgid "To protect voices against bot kicks" +msgstr "" + +#: modules/commands/cs_list.cpp:46 +msgid "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." +msgstr "" +"Για να ψάξετε για κανάλια που αρχίζουν με #, ψάξτε για το όνομα\n" +"καναλιού χωρίς το '#'. (π.χ. #anope# αντί για ##anope#)." + +#: modules/commands/os_logsearch.cpp:139 +#, fuzzy, c-format +msgid "Too many results for %s." +msgstr "Λίστα πρόσβασης για #%s#:" + +#: modules/extra/stats/cs_fantasy_top.cpp:149 +#, c-format +msgid "Top %i of %s" +msgstr "" + +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Topic" +msgstr "Κλείδωμα του Topic" + +#: modules/commands/cs_topic.cpp:258 +#, fuzzy +msgid "Topic lock" +msgstr "Κλείδωμα του Topic" + +#: modules/commands/cs_topic.cpp:114 +#, c-format +msgid "Topic lock option for %s is now off." +msgstr "Topic lock επιλογή για το %s είναι τώρα #off#." + +#: modules/commands/cs_topic.cpp:97 +#, c-format +msgid "Topic lock option for %s is now on." +msgstr "Topic lock επιλογή για το %s είναι τώρα #ON#." + +#: modules/commands/cs_topic.cpp:256 +#, fuzzy +msgid "Topic retention" +msgstr "Topic ενναλαγής" + +#: modules/commands/cs_topic.cpp:60 +#, c-format +msgid "Topic retention option for %s is now off." +msgstr "Η διατήρηση του topic για το %s είναι τώρα #OFF#." + +#: modules/commands/cs_topic.cpp:54 +#, c-format +msgid "Topic retention option for %s is now on." +msgstr "Η διατήρηση του topic για το %s είναι τώρα #ON#." + +#: modules/commands/cs_topic.cpp:265 +msgid "Topic set by" +msgstr "" + +#: modules/commands/bs_kick.cpp:1323 +msgid "Turn caps lock OFF!" +msgstr "Μην γράφεις με κεφαλαία γράμματα!" + +# +#: modules/extra/stats/m_chanstats.cpp:17 +#: modules/extra/stats/m_chanstats.cpp:71 +#, fuzzy +msgid "Turn chanstats statistics on or off" +msgstr "Ενεργοποιεί/απενεργοποιεί τη λειτουργία ασφάλειας ψευδώνυμου" + +# +#: modules/commands/ns_set.cpp:1009 +msgid "Turn nickname security on or off" +msgstr "Ενεργοποιεί/απενεργοποιεί τη λειτουργία ασφάλειας ψευδώνυμου" + +# +#: modules/commands/ns_set.cpp:655 +msgid "Turn protection on or off" +msgstr "Ενεργοποιεί/απενεργοποιεί την προστασία με αποσύνδεση" + +#: modules/commands/ns_list.cpp:264 +#, c-format +msgid "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Syntax: #SASET #nickname# PRIVATE {ON | OFF}#\n" +"\n" +"Ανοίγει/Κλείνει την privacy επιλογή του %s's για το nick.\n" +"Με την επιλογή #PRIVATE# το nick δε θα φαίνεται στις\n" +"λίστες που φαίνονται με την εντολή #LIST# του %s .\n" +"(Παρόλα αυτά κάποιος που ξέρει το nickname μπορεί ακόμα να πάρει\n" +"πληροφορίες με την εντολή #INFO#.)" + +#: modules/commands/ns_list.cpp:236 +#, c-format +msgid "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Σύνταξη: #SET PRIVATE {ON | OFF}#\n" +"\n" +"Ενεργοποιεί/απενεργοποιεί την επιλογή ιδιώτευσης\n" +"του %s για το ψευδώνυμό σας. Με την ενεργοποίηση του\n" +"#PRIVATE# το ψευδώνυμό σας δε θα εμφανίζεται στη λίστα\n" +"ψευδωνύμων που προκύπτει με την εντολή #LIST# του %s.\n" +"(Βέβαια,οποιοσδήποτε γνωρίζει το ψευδώνυμό σας, μπορεί\n" +"ακόμη να πάρει πληροφορίες γι αυτό, χρησιμοποιώντας την\n" +"εντολή #INFO#)" + +#: modules/commands/ns_set.cpp:1059 modules/commands/ns_set.cpp:1088 +#, c-format +msgid "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." +msgstr "" +"Σύνταξη: #SET SECURE {ON | OFF}#\n" +"\n" +"Αλλάζει ο %s την ασφάλεια σε on ή off για το ψευδώνυμο\n" +"Με την #ΑΣΦΑΛΗ# επιλογή, πρέπει να γράψεις τον κωδικό αναγνώρισης\n" +"πριν αναγνωριστής σαν κάτοχος του ψευδώνυμου,\n" +"με την υπόληψη οτι η διεύθυνση είναι στην λίστα των access.\n" +"Όπως και ναχει, αν είσαι στην λίστα access, ο %s\n" +"δεν θα κάνει auto-kill με την υπόληψη της επιλογής #KILL#." + +# +#: modules/extra/stats/m_chanstats.cpp:142 +#, fuzzy +msgid "Turns chanstats channel statistics ON or OFF for this user." +msgstr "Ενεργοποιεί/απενεργοποιεί τη λειτουργία ασφάλειας ψευδώνυμου" + +# +#: modules/extra/stats/m_chanstats.cpp:61 +#: modules/extra/stats/m_chanstats.cpp:119 +#, fuzzy +msgid "Turns chanstats statistics ON or OFF." +msgstr "Ενεργοποιεί/απενεργοποιεί τη λειτουργία ασφάλειας ψευδώνυμου" + +#: modules/commands/ns_set.cpp:772 +#, c-format +msgid "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Ενεργοποιεί ή απενεργοποιεί την αυτόματη προστασία με\n" +"αποσύνδεση για ένα ψευδόνυμο. Ενεργοποιώντας την\n" +"προστασία με αποσύνδεση, αν κάποιος άλλος χρήστης\n" +"προσπαθήσει να πάρει το ψευδώνυμό σας, θα δωθεί ένα λεπτό\n" +"για να αλλάξει το ψευδώνυμό του, μετά από το οποίο θα\n" +"αποσυνδεθεί από το IRC από τον %s.\n" +"\n" +"Αν επιλέξετε #QUICK#, θα δωθούν μόνο 20 δευτερόλεπτα στο\n" +"χρήστη για να αλλάξει το ψευδώνυμό του, αντί για τα συνηθισμένα 60.\n" +"Αν επιλέξετε #IMMED#, ο χρήστης θα αποσυνδεθεί κατευθείαν #χωρίς#\n" +"πρώτα να προειδοποιηθεί ή να του δωθεί η ευκαιρία να αλλάξει το\n" +"ψευδώνυμό του;Παρακαλούμε μη χρησιμοποιείτε αυτή την επιλογή εκτός α\n" +"είναι απολύτως απαραίτητο. Επίσης, οι διαχειριστές του\n" +"δικτύου μπορεί να έχουν απενεργοποιήσει αυτή την επιλογή." + +#: modules/commands/ns_set.cpp:738 +#, fuzzy, c-format +msgid "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Σύνταξη: #SET KILL {ON | QUICK | IMMED | OFF}#\n" +"\n" +"Ενεργοποιεί ή απενεργοποιεί την αυτόματη προστασία με\n" +"αποσύνδεση για το ψευδώνυμό σας. Ενεργοποιώντας την\n" +"προστασία με αποσύνδεση, αν κάποιος άλλος χρήστης\n" +"προσπαθήσει να πάρει το ψευδώνυμό σας, θα δωθεί ένα λεπτό\n" +"για να αλλάξει το ψευδώνυμό του, μετά από το οποίο θα\n" +"αποσυνδεθεί από το IRC από τον %s.\n" +"\n" +"Αν επιλέξετε #QUICK#, θα δωθούν μόνο 20 δευτερόλεπτα στο\n" +"χρήστη για να αλλάξει το ψευδώνυμό του, αντί για τα συνηθισμένα 60.\n" +"Αν επιλέξετε #IMMED#, ο χρήστης θα αποσυνδεθεί κατευθείαν #χωρίς#\n" +"πρώτα να προειδοποιηθεί ή να του δωθεί η ευκαιρία να αλλάξει το\n" +"ψευδώνυμό του;Παρακαλούμε μη χρησιμοποιείτε αυτή την επιλογή εκτός α\n" +"είναι απολύτως απαραίτητο. Επίσης, οι διαχειριστές του\n" +"δικτύου μπορεί να έχουν απενεργοποιήσει αυτή την επιλογή." + +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_forbid.cpp:358 +msgid "Type" +msgstr "" + +#: modules/commands/ns_set.cpp:62 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Γράψε #/msg %s HELP #επιλογή## για περισσότερες πληροφορίες\n" +"για την κάθε εντολή." + +#: modules/commands/bs_kick.cpp:151 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." +msgstr "" +"Γράψτε #/msg %s HELP SASET #option## για περισσότερες πληροφορίες\n" +"πάνω σε μία επιλογή. Οι επιλογές θα ρυθμίζονται στο δωσμένο\n" +"#nickname#. " + +#: modules/commands/ns_set.cpp:107 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." +msgstr "" +"Γράψτε #/msg %s HELP SASET #option## για περισσότερες πληροφορίες\n" +"πάνω σε μία επιλογή. Οι επιλογές θα ρυθμίζονται στο δωσμένο\n" +"#nickname#. " + +#: modules/commands/bs_set.cpp:62 modules/commands/cs_set.cpp:63 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." +msgstr "" +"Γράψε #/msg %s HELP #επιλογή## για περισσότερες πληροφορίες\n" +"για την κάθε εντολή." + +#: modules/pseudoclients/nickserv.cpp:361 +#, c-format +msgid "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." +msgstr "" +"Γράψε #%s%s SET EMAIL #e-mail## για να προσθέσεις το e-mail στις πληροφορίες " +"του ψευδώνυμού σου.\n" +"Η μυστικότητα είναι σεβαστή; αυτό το e-mail και ο κωδικός του δεν πρέπει να " +"δωθεί σε\n" +"κανένα τρίτο πρόσωπο." + +# +#: modules/commands/os_module.cpp:128 +msgid "Un-Load a module" +msgstr "Κάνει unload ένα module." + +#: modules/commands/os_sxline.cpp:337 modules/commands/os_sxline.cpp:552 +#: modules/commands/os_akill.cpp:136 +#, fuzzy, c-format +msgid "Unable to find regex engine %s." +msgstr "Το module #%s# δεν μπόρεσε να αφαιρεθεί." + +#: modules/commands/os_module.cpp:36 modules/commands/os_module.cpp:108 +#, fuzzy, c-format +msgid "Unable to load module %s." +msgstr "Το module #%s# δεν μπόρεσε να φορτωθεί." + +#: modules/commands/os_module.cpp:73 modules/commands/os_module.cpp:90 +#: modules/commands/os_module.cpp:145 modules/commands/os_module.cpp:159 +#, fuzzy, c-format +msgid "Unable to remove module %s." +msgstr "Το module #%s# δεν μπόρεσε να αφαιρεθεί." + +# +#: modules/commands/bs_assign.cpp:90 +msgid "Unassigns a bot from a channel" +msgstr "Κάνει unassign ένα bot από ένα κανάλι." + +#: modules/commands/bs_assign.cpp:139 +#, fuzzy +msgid "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." +msgstr "" +"Σύνταξη: #UNASSIGN #κανάλι##\n" +"\n" +"Με την εντολή αυτή ζητάς από το bot να βγεί από το κανάλι σου.\n" +"Πάντως,οι ρυθμίσεις του bot για το κανάλι που ήταν είναι αποθηκευμένες,\n" +"για την περίπτωση που θες να το βάλεις αργότερα.\n" +" " + +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1193 +#: modules/commands/bs_kick.cpp:1196 +#, fuzzy +msgid "Underlines kicker" +msgstr " Υπογράμμιση με kick : %s" + +#: modules/commands/os_dns.cpp:595 +#, fuzzy +msgid "Unknown SET option." +msgstr "’γνωστη SASET επιλογή #%s#." + +#: modules/commands/os_stats.cpp:229 +#, fuzzy, c-format +msgid "Unknown STATS option: %s" +msgstr "’γνωστη STATS επιλογή #%s#." + +#: src/command.cpp:222 src/command.cpp:233 +#, c-format +msgid "Unknown command %s." +msgstr "’γνωστη επιλογή #%s#." + +#: src/command.cpp:220 src/command.cpp:231 +#, fuzzy, c-format +msgid "Unknown command %s. \"%s%s HELP\" for help." +msgstr "’γνωστη εντολή #%s#. \"%s%s HELP\" για βοήθεια." + +#: modules/commands/cs_mode.cpp:317 modules/commands/cs_mode.cpp:409 +#, c-format +msgid "Unknown mode character %c ignored." +msgstr "’γνωστη επιλογή χαρακτήρα #%c# αγνοήθηκε." + +#: modules/commands/os_logsearch.cpp:78 +#, c-format +msgid "Unknown parameter: %s" +msgstr "" + +#: modules/commands/os_dns.cpp:241 +msgid "Unpooled" +msgstr "" + +#: modules/commands/cs_drop.cpp:77 +#, fuzzy +msgid "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." +msgstr "" +"Σύνταξη: #DROP #κανάλι##\n" +"\n" +"Κάνει το κανάλι ξεκατοχυρώσημο,το αφήνει ελεύθερο χωρίς founder. Για να\n" +"γίνει αυτό πρέπει ο #founder#." + +#: modules/commands/cs_drop.cpp:74 +#, fuzzy +msgid "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." +msgstr "" +"Σύνταξη: #DROP #κανάλι##\n" +"\n" +"Ξε-κατοχυρώνει το ζητούμενο κανάλι. Μόνο οι #Services Operators#\n" +"μπορουν να το κάνουν αυτό σε ένα κανάλι, χωρίς να κάνουν εντολή αναγνώρισης\n" +"για το κανάλι." + +# +#: modules/commands/ns_suspend.cpp:160 +msgid "Unsuspend a given nick" +msgstr "Κάνει unsuspend ένα nick." + +#: modules/commands/ns_suspend.cpp:199 +msgid "Unsuspends a nickname which allows it to be used again." +msgstr "" + +#: modules/commands/cs_updown.cpp:126 +msgid "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." +msgstr "" + +# +#: modules/commands/cs_updown.cpp:48 +#, fuzzy +msgid "Updates a selected nicks status on a channel" +msgstr "Κάνει ban ένα συγκεκριμένο ψευδόνυμο σε ένα κανάλι" + +# +#: modules/commands/ns_update.cpp:19 +msgid "Updates your current status, i.e. it checks for new memos" +msgstr "Κάνει update τα στοιχεία σας, π.χ. ψάχνει για καινούρια memos." + +#: modules/commands/ns_update.cpp:43 +msgid "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." +msgstr "" +"Syntax: UPDATE\n" +"Κάνει update το τρέχων status σας, π.χ. ελέγχει για νέα memo,\n" +"ρυθμίζει τα απαιτούμενα chanmodes (ModeonID) και ενημερώνει τη vhost\n" +"και τα userflags (lastseentime κλπ)." + +#: modules/commands/os_update.cpp:25 +msgid "Updating databases." +msgstr "Γίνεται Update στις βάσεις δεδομένων." + +#: modules/commands/os_stats.cpp:154 +#, c-format +msgid "Uplink capab: %s" +msgstr "Uplink capab: %s" + +#: modules/commands/os_stats.cpp:153 +#, c-format +msgid "Uplink server: %s" +msgstr "Uplink server: %s" + +#: modules/commands/help.cpp:127 +#, c-format +msgid "Use the %s ALL command to list all commands and their descriptions." +msgstr "" + +#: modules/commands/bs_info.cpp:59 +msgid "Used on" +msgstr "" + +# +#: data/chanserv.example.conf:821 +#, fuzzy +msgid "Used to manage channels" +msgstr "Ο/η #%s# άλλαξε τα usermodes σας." + +# +#: data/chanserv.example.conf:809 +#, fuzzy +msgid "Used to manage the list of privileged users" +msgstr "Αλλάζει τη λίστα των εξουσιοδοτημένων χρηστών" + +#: data/chanserv.example.conf:815 +msgid "Used to modify the channel status of you or other users" +msgstr "" + +#: modules/commands/cs_akick.cpp:575 +#, fuzzy +msgid "User has been banned from the channel" +msgstr "γινες unban από το #%s#." + +#: modules/commands/os_dns.cpp:587 +#, fuzzy, c-format +msgid "User limit for %s removed." +msgstr "Η vhost για τον #%s# αφαιρέθηκε." + +#: modules/commands/os_dns.cpp:585 +#, fuzzy, c-format +msgid "User limit for %s set to %d." +msgstr "Το όριο μηνυμάτων για τον %s άλλαξε σε #%d#." + +# +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Users" +msgstr "Bot λίστα:" + +#: modules/commands/os_stats.cpp:172 +#, c-format +msgid "Users (nick): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:177 +#, c-format +msgid "Users (uid): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +# +#: modules/commands/os_list.cpp:184 +#, fuzzy +msgid "Users list:" +msgstr "Bot λίστα:" + +#: modules/commands/ns_info.cpp:105 modules/commands/ns_info.cpp:107 +msgid "VHost" +msgstr "" + +#: modules/commands/hs_set.cpp:92 +#, c-format +msgid "VHost for %s set to %s." +msgstr "Η vhost για τον #%s# έγινε #%s#." + +#: modules/commands/hs_set.cpp:90 +#, c-format +msgid "VHost for %s set to %s@%s." +msgstr "Η vhost για τον #%s# έγινε #%s#@#%s#." + +#: modules/commands/hs_set.cpp:199 +#, c-format +msgid "VHost for group %s set to %s." +msgstr "Η vhost για το group #%s# έγινε #%s#." + +#: modules/commands/hs_set.cpp:197 +#, c-format +msgid "VHost for group %s set to %s@%s." +msgstr "Η vhost για το group #%s# έγινε #%s#@#%s#." + +#: modules/commands/os_session.cpp:247 +msgid "VIEW host" +msgstr "" + +#: modules/commands/os_sxline.cpp:428 modules/commands/os_sxline.cpp:662 +#: modules/commands/os_akill.cpp:389 +msgid "VIEW [mask | list | id]" +msgstr "" + +#: modules/commands/os_session.cpp:526 +msgid "VIEW [mask | list]" +msgstr "" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +msgid "Value" +msgstr "" + +#: modules/commands/os_config.cpp:48 +#, c-format +msgid "Value of %s:%s changed to %s" +msgstr "Το value του %s:%s άλλαξε σε %s" + +#: modules/commands/hs_list.cpp:58 modules/commands/hs_request.cpp:305 +msgid "Vhost" +msgstr "" + +#: modules/commands/hs_del.cpp:38 +#, c-format +msgid "Vhost for %s removed." +msgstr "Η vhost για τον #%s# αφαιρέθηκε." + +#: modules/commands/os_oper.cpp:69 +#, fuzzy +msgid "View and change Services Operators" +msgstr "%s είναι services operator τού τύπου %s." + +#: modules/commands/os_config.cpp:19 +msgid "View and change configuration file settings" +msgstr "Δες και άλλαξε τις ρυθμίσεις του configuration file" + +# +#: modules/commands/os_session.cpp:245 +msgid "View the list of host sessions" +msgstr "Βλέπεις την λίστα με τα host sessions" + +#: modules/commands/bs_kick.cpp:1221 +msgid "Voices protection" +msgstr "Προστασία στους Voices" + +#: modules/commands/bs_kick.cpp:1406 +msgid "Watch your language!" +msgstr "Πρόσεχε την γλώσσα σου!" + +#: modules/commands/cs_list.cpp:237 +#, c-format +msgid "" +"When private is set, the channel will not appear in\n" +"%s's %s command." +msgstr "" + +#: modules/commands/ms_info.cpp:204 +#, fuzzy +msgid "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." +msgstr "" +"Σύνταξη: #INFO [#ψευδώνυμο# | #κανάλι#]#\n" +"\n" +"Χωρίς την παράμετρο, εμφανίζει πληροφορίες για τα νουμερα των\n" +"μηνυμάτων που έχετε, πόσα από αυτά δεν έχουν διαβαστεί, και πόσα\n" +"τελικά μηνύματα μπορείτε να λάβετε.\n" +"\n" +"Με την παράμετρο κανάλι,εμφανίζει τις ίδιες πληροφορίες για το\n" +"ανάλογο κανάλι.\n" +"\n" +"Με την παράμετρο ψευδώνυμο, εμφανίζει τις ίδιες πληροφορίες για το\n" +"ανάλογο ψευδώνυμο. Αυτή η εντολή είναι μόνο για τους #Services\n" +"admins#." + +#: modules/commands/ns_logout.cpp:66 +#, fuzzy +msgid "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." +msgstr "" +"Σύνταξη: #LOGOUT [#ψευδώνυμο# [REVALIDATE]]#\n" +"\n" +"Χωρίς καμία παράμετρο, κάνει το αντίθετο της εντολής #IDENTIFY# " +"(αναγνώρισης) \n" +"δηλ σε κάνει μη αναγνωρίσημο κάτοχο του ψευδώνυμου πλέον.\n" +"Σημείωση, όπως και ναχει, δεν θα σου ζητηθεί να ξανακάνεις εντολή " +"αναγνώρισης.\n" +" \n" +"Με την παράμετρο αυτή, κάνει το ίδιο για το δωσμένο ψευδώνυμο. Αν κάνεις \n" +"REVALIDATE, οι υπηρεσίες θα σε ρωτήσουν για ποιο ψευδώνυμο.\n" +"Αυτό το κάνουν μόνο οι (επικεφαλείς) #Services operators#." + +#: modules/commands/os_stats.cpp:236 +#, fuzzy +msgid "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." +msgstr "" +"Σύνταξη: #STATS [AKILL | ALL | RESET]#\n" +"\n" +"Χωρίς κάποια επιλογή, εμφανίζει το νούμερο των χρηστών και των\n" +"IRCops που είναι στο δίκτυο (μαζί και των Services), το μεγαλύτερο νούμερο\n" +"των χρηστών που είναι στο δίκτυο όταν τα Services ξεκινάνε, και την\n" +"διάρκεια που τα Services είναι στο δίκτυο.\n" +"\n" +"\n" +"Με την επιλογή #AKILL#, εμφανίζει την συγκεκριμένη λίστα.\n" +"\n" +"AKILL και τον default χρόνο λήξης.\n" +"\n" +"The #RESET# option currently resets the maximum user count\n" +"to the number of users currently present on the network." + +#: modules/commands/bs_badwords.cpp:194 +msgid "Word" +msgstr "" + +#: modules/commands/ns_group.cpp:158 +#, c-format +msgid "You are already a member of the group of %s." +msgstr "Είσαι ήδη μέλος της ομάδας του #%s#." + +#: modules/commands/os_login.cpp:34 modules/commands/ns_identify.cpp:87 +msgid "You are already identified." +msgstr "Είστε ήδη identified." + +#: modules/commands/cs_invite.cpp:64 +#, fuzzy, c-format +msgid "You are already in %s!" +msgstr "Είστε ήδη στο κανάλι #%s#! " + +#: modules/commands/os_set.cpp:91 +#, fuzzy +msgid "You are no longer a super admin." +msgstr "Δεν είστε πια ένας SuperAdmin" + +#: modules/commands/os_login.cpp:81 +#, fuzzy +msgid "You are not identified." +msgstr "Είστε ήδη identified." + +#: include/language.h:100 +msgid "You are not permitted to be on this channel." +msgstr "" +"Δεν έχεις το δικαίωμα να αλλάξεις το όριο των μηνυμάτων που θα λαμβάνεις." + +#: modules/commands/ms_set.cpp:158 +msgid "You are not permitted to change your memo limit." +msgstr "" +"Δεν έχεις το δικαίωμα να αλλάξεις το όριο των μηνυμάτων που θα λαμβάνεις." + +#: modules/commands/ns_cert.cpp:183 +#, fuzzy +msgid "You are not using a client certificate." +msgstr "Είστε ήδη identified." + +#: modules/commands/os_set.cpp:85 +#, fuzzy +msgid "You are now a super admin." +msgstr "Τώρα είστε ένας SuperAdmin" + +#: modules/commands/os_oline.cpp:36 +msgid "You are now an IRC Operator." +msgstr "Τώρα είστε IRC Operator." + +#: modules/commands/ns_resetpass.cpp:108 +#, fuzzy +msgid "You are now identified for your nick. Change your password now." +msgstr "" +"Έχετε γίνει identify για το nick σας. Αλλάξτε τον κωδικό σας με την εντολή " +"\"/msg SET PASSWORD #newpassword#\" τώρα." + +#: modules/commands/ns_group.cpp:64 +#, c-format +msgid "You are now in the group of %s." +msgstr "Είσαι τώρα μέσα στην ομάδα του #%s#." + +#: modules/pseudoclients/memoserv.cpp:147 +#, c-format +msgid "" +"You are over your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"#Προειδοποίηση:# Έχεις ξεπεράσει το νούμερο μηνυμάτων που μπορείς να λάβεις " +"(%d). Δεν θα μπορείς να λάβεις άλλα αν δεν σβήσεις μερικά από τα παλιά " +"μηνύματα που έχεις." + +#: modules/commands/os_noop.cpp:33 +msgid "You can not NOOP Services." +msgstr "" + +#: modules/commands/cs_access.cpp:672 +msgid "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." +msgstr "" + +#: modules/commands/os_jupe.cpp:34 +#, fuzzy +msgid "You can not jupe an already juped server." +msgstr "" +"Δεν μπορείτε να κάνετε jupe τον services server ή τον uplink server σας." + +#: modules/commands/os_jupe.cpp:32 +#, fuzzy +msgid "You can not jupe your Services' pseudoserver or your uplink server." +msgstr "" +"Δεν μπορείτε να κάνετε jupe τον services server ή τον uplink server σας." + +#: modules/commands/os_module.cpp:80 +#, c-format +msgid "You can not reload this module directly, instead reload %s." +msgstr "" + +#: modules/commands/ms_rsend.cpp:46 +msgid "You can not request a receipt when sending a memo to yourself." +msgstr "Δεν μπορείτε να ζητήσετε απόδειξη όταν στέλνετε memo στον εαυτό σας." + +#: modules/commands/ns_recover.cpp:163 +#, fuzzy, c-format +msgid "You can't %s yourself!" +msgstr "Δεν μπορείς να σκοτώσεις τον εαυτό σου!" + +#: modules/commands/cs_access.cpp:154 modules/commands/cs_flags.cpp:109 +#: modules/commands/cs_xop.cpp:151 +#, fuzzy +msgid "You can't add a channel to its own access list." +msgstr "Δεν βρέθηκαν θέσεις στου %s στην access list." + +#: modules/commands/ns_logout.cpp:37 +#, fuzzy, c-format +msgid "You can't logout %s, they are a Services Operator." +msgstr "Δεν μπορείτε να κάνετε Logout τον %s επειδή είναι Services Operator." + +#: modules/commands/ns_set.cpp:927 +#, fuzzy, c-format +msgid "You cannot %s on this network." +msgstr "" +"Δεν μπορείς να απενεργοποιήσεις την διεύθυνση του e-mail σε αυτό το δίκτυο." + +#: modules/commands/cs_flags.cpp:231 +#, fuzzy, c-format +msgid "You cannot set the %c flag." +msgstr "Δεν μπορείτε να χρησιμοποιήσετε αυτή την εντολή." + +#: modules/commands/ms_set.cpp:173 +#, c-format +msgid "You cannot set the memo limit for %s higher than %d." +msgstr "Δεν μπορείς να θέσεις ως όριο μηνυμάτων για τον %s μεγαλύτερο από %d." + +#: modules/commands/ms_set.cpp:175 +#, c-format +msgid "You cannot set your memo limit higher than %d." +msgstr "Δεν μπορείς να θέσεις ως όριο μηνυμάτων μεγαλύτερο από %d." + +#: modules/commands/bs_assign.cpp:124 +#, fuzzy +msgid "You cannot unassign bots while persist is set on the channel." +msgstr "" +"Δεν μπορείτε να κάνετε unassign τα bots όταν είναι ενεγοποιημένη η επιλογή " +"persist." + +#: modules/commands/ns_set.cpp:480 +msgid "You cannot unset the e-mail on this network." +msgstr "" +"Δεν μπορείς να απενεργοποιήσεις την διεύθυνση του e-mail σε αυτό το δίκτυο." + +#: modules/commands/help.cpp:177 +msgid "You cannot use this command." +msgstr "Δεν μπορείτε να χρησιμοποιήσετε αυτή την εντολή." + +#: modules/commands/ms_info.cpp:151 +#, c-format +msgid "You currently have %d memos, of which %d are unread." +msgstr "" +"Μέχρι στιγμής έχεις #%d# μηνύματα, εκ των οποίων #%d# δεν έχουν διαβαστεί." + +#: modules/commands/ms_info.cpp:149 +#, c-format +msgid "You currently have %d memos, of which 1 is unread." +msgstr "" +"Μέχρι στιγμής έχεις #%d# μηνύματα, εκ των οποίων #1# δεν έχει διαβαστεί." + +#: modules/commands/ms_info.cpp:147 +#, c-format +msgid "You currently have %d memos." +msgstr "Μέχρι στιγμής έχεις #%d# μηνύματα." + +#: modules/commands/ms_info.cpp:145 +#, c-format +msgid "You currently have %d memos; all of them are unread." +msgstr "" +"Μέχρι στιγμής έχεις #%d# μηνύματα; εκ των οποίων όλα δεν έχουν διαβαστεί." + +#: modules/commands/ms_info.cpp:134 +msgid "You currently have 1 memo, and it has not yet been read." +msgstr "Μέχρι στιγμής έχεις #1# memo, και δεν το έχεις διαβάσει." + +#: modules/commands/ms_info.cpp:136 +msgid "You currently have 1 memo." +msgstr "Μέχρι στιγμής έχεις #1# μήνυμα." + +#: modules/commands/ms_info.cpp:130 +msgid "You currently have no memos." +msgstr "Μέχρις στιγμής δεν έχεις κανένα μήνυμα." + +#: modules/commands/cs_mode.cpp:564 modules/commands/cs_mode.cpp:621 +#, c-format +msgid "You do not have access to set mode %c." +msgstr "Δεν έχετε πρόσβαση για να αλλάξετε το mode %c." + +#: modules/commands/cs_mode.cpp:578 modules/commands/cs_mode.cpp:590 +#: modules/commands/cs_mode.cpp:631 +#, c-format +msgid "You do not have the access to change %s's modes." +msgstr "Δεν έχετε πρόσβαση για να αλλάξετε τα modes του %s." + +#: modules/commands/cs_seen.cpp:198 +#, c-format +msgid "You found me, %s!" +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:143 +#, c-format +msgid "You have %d new memos." +msgstr "Έχεις %d νέα μηνύματα." + +#: modules/pseudoclients/memoserv.cpp:143 +msgid "You have 1 new memo." +msgstr "Έχεις 1 νέο μήνυμα." + +#: include/language.h:112 +#, fuzzy, c-format +msgid "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." +msgstr "Γράψε #/msg %s READ %d# για να διαβάσεις." + +#: modules/commands/cs_invite.cpp:76 +#, fuzzy, c-format +msgid "You have been invited to %s by %s." +msgstr "Έχετε γίνει invite στο κανάλι #%s#." + +#: modules/commands/cs_invite.cpp:81 +#, c-format +msgid "You have been invited to %s." +msgstr "Έχετε γίνει invite στο κανάλι #%s#." + +#: modules/protocol/ratbox.cpp:166 modules/commands/ns_recover.cpp:96 +#, fuzzy, c-format +msgid "You have been logged in as %s." +msgstr "" +"Το ψευδώνυμο σου δεν το κατέχεις τώρα,πρέπει να κάνεις πάλι εντολή " +"αναγνώρισης για να το κατέχεις." + +#: modules/commands/os_login.cpp:86 +#, fuzzy +msgid "You have been logged out." +msgstr "" +"Το ψευδώνυμο σου δεν το κατέχεις τώρα,πρέπει να κάνεις πάλι εντολή " +"αναγνώρισης για να το κατέχεις." + +#: modules/commands/cs_unban.cpp:94 +#, c-format +msgid "You have been unbanned from %s." +msgstr "γινες unban από το #%s#." + +#: modules/commands/cs_unban.cpp:54 +#, fuzzy, c-format +msgid "You have been unbanned from %d channels." +msgstr "γινες unban από το #%s#." + +#: modules/commands/ms_info.cpp:169 +msgid "You have no limit on the number of memos you may keep." +msgstr "Δεν έχεις θέσει κανένα αριθμό στο όριο ωστε να κρατήσεις μηνύματα." + +#: include/language.h:114 +msgid "You have no memos." +msgstr "Έχεις %d νέα μηνύματα." + +#: include/language.h:117 +msgid "You have no new memos." +msgstr "Έχεις %d νέα μηνύματα." + +#: modules/pseudoclients/memoserv.cpp:149 +#, c-format +msgid "" +"You have reached your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"#Προειδοποίηση:# Έχει φτάσει στο μέγιστο νούμερο μηνυμάτων (%d). Δεν θα " +"λάβεις καινούργια μηνύματα αν δεν σβήσεις μερικά από τα παλιά που έχεις." + +#: modules/commands/ns_recover.cpp:117 +#, fuzzy, c-format +msgid "You have regained control of %s." +msgstr "Έχετε γίνει invite στο κανάλι #%s#." + +# +#: modules/commands/ns_drop.cpp:66 +#, fuzzy +msgid "You may drop any nick within your group." +msgstr "Διαγράφει τη vhost από όλα τα nicks σε ένα group" + +#: modules/commands/cs_mode.cpp:322 modules/commands/cs_mode.cpp:414 +#, c-format +msgid "You may not (un)lock mode %c." +msgstr "" + +#: modules/commands/ns_set.cpp:485 +#, fuzzy +msgid "You may not change the e-mail of other Services Operators." +msgstr "" +"Δεν μπορείς να απενεργοποιήσεις την διεύθυνση του e-mail σε αυτό το δίκτυο." + +#: modules/commands/ns_set.cpp:474 +#, fuzzy +msgid "You may not change the email of an unconfirmed account." +msgstr "" +"Δεν μπορείς να απενεργοποιήσεις την διεύθυνση του e-mail σε αυτό το δίκτυο." + +#: modules/commands/ns_set.cpp:196 +#, fuzzy +msgid "You may not change the password of other Services Operators." +msgstr "Δεν μπορείτε να κάνετε Logout τον %s επειδή είναι Services Operator." + +#: modules/commands/ns_drop.cpp:45 +#, fuzzy +msgid "You may not drop other Services Operators' nicknames." +msgstr "%s είναι services operator τού τύπου %s." + +#: modules/commands/ns_getpass.cpp:32 +#, fuzzy +msgid "You may not get the password of other Services Operators." +msgstr "Δεν μπορείτε να κάνετε Logout τον %s επειδή είναι Services Operator." + +#: modules/commands/ns_suspend.cpp:100 +#, fuzzy +msgid "You may not suspend other Services Operators' nicknames." +msgstr "Δεν μπορείτε να κάνετε Logout τον %s επειδή είναι Services Operator." + +#: modules/commands/ns_access.cpp:136 +#, fuzzy +msgid "" +"You may view but not modify the access list of other Services Operators." +msgstr "Δεν μπορείτε να κάνετε Logout τον %s επειδή είναι Services Operator." + +#: modules/commands/ns_cert.cpp:292 +#, fuzzy +msgid "" +"You may view but not modify the certificate list of other Services Operators." +msgstr "Δεν μπορείτε να κάνετε Logout τον %s επειδή είναι Services Operator." + +#: modules/commands/cs_seen.cpp:287 +#, c-format +msgid "You might see yourself in the mirror, %s." +msgstr "" + +#: include/language.h:120 +msgid "You must assign a bot to the channel before using this command." +msgstr "" + +#: modules/commands/cs_register.cpp:49 +msgid "You must be a channel operator to register the channel." +msgstr "" +"Πρέπει να είσαι να έχεις operator status στο κανάλι για να το κατοχυρώσεις." + +#: modules/commands/cs_updown.cpp:94 modules/commands/cs_updown.cpp:192 +#, fuzzy, c-format +msgid "You must be in %s to use this command." +msgstr "" +"Θα πρέπει να έχετε κάνει identify για να χρησιμοποιήσετε αυτή την εντολή." + +# +#: modules/commands/cs_register.cpp:37 +msgid "You must confirm your account before you can register a channel." +msgstr "" +"Πρέπει να είσαι να έχεις operator status στο κανάλι για να το κατοχυρώσεις." + +# +#: modules/commands/hs_request.cpp:100 +#, fuzzy +msgid "You must confirm your account before you may request a vhost." +msgstr "" +"Πρέπει να είσαι να έχεις operator status στο κανάλι για να το κατοχυρώσεις." + +# +#: modules/commands/ms_send.cpp:44 +#, fuzzy +msgid "You must confirm your account before you may send a memo." +msgstr "" +"Πρέπει να είσαι να έχεις operator status στο κανάλι για να το κατοχυρώσεις." + +#: modules/commands/cs_drop.cpp:42 +#, c-format +msgid "" +"You must enter the channel name twice as a confirmation that you wish to drop" +" %s." +msgstr "" + +#: modules/commands/ns_register.cpp:153 +#, c-format +msgid "You must have been using this nick for at least %d seconds to register." +msgstr "" +"Πρέπει να είστε συνδεδεμένος περισσότερο από %d δευτερόλεπτα για να κάνετε " +"register." + +#: modules/commands/cs_mode.cpp:913 +#, fuzzy, c-format +msgid "You must have the %s(ME) privilege on the channel to use this command." +msgstr "" +"Θα πρέπει να έχετε κάνει identify για να χρησιμοποιήσετε αυτή την εντολή." + +#: modules/pseudoclients/nickserv.cpp:358 +msgid "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." +msgstr "" +"Πρέπει να προσθέσεις ένα e-mail για το ψευδώνυμό σου.\n" +"Με αυτό το e-mail θα μπορείς να επανακτήσεις τον κωδικό σου σε\n" +"περίπτωση που τον ξεχάσεις." + +#: modules/commands/help.cpp:172 +msgid "You need to be identified to use this command." +msgstr "" +"Θα πρέπει να έχετε κάνει identify για να χρησιμοποιήσετε αυτή την εντολή." + +#: modules/commands/ms_info.cpp:182 +#, fuzzy +msgid "You will be notified by message and by mail when new memos arrive." +msgstr "Θα ειδοποιηθείς για νέα μηνύματα όταν θα φτάσουν." + +#: modules/commands/ms_info.cpp:175 +#, fuzzy +msgid "" +"You will be notified of new memos at logon and when they arrive, and by mail " +"when they arrive." +msgstr "Θα ειδοποιηθείς για νέα μηνύματα όταν κάνεις logon και όταν φτάσουν." + +#: modules/commands/ms_info.cpp:177 +msgid "You will be notified of new memos at logon and when they arrive." +msgstr "Θα ειδοποιηθείς για νέα μηνύματα όταν κάνεις logon και όταν φτάσουν." + +#: modules/commands/ms_info.cpp:189 +#, fuzzy +msgid "" +"You will be notified of new memos at logon, and by mail when they arrive." +msgstr "Θα ειδοποιηθείς για νέα μηνύματα όταν κάνεις logon και όταν φτάσουν." + +#: modules/commands/ms_info.cpp:191 +msgid "You will be notified of new memos at logon." +msgstr "Θα ειδοποιηθείς για νέα μηνύματα στο logon." + +#: modules/commands/ms_info.cpp:184 +msgid "You will be notified when new memos arrive." +msgstr "Θα ειδοποιηθείς για νέα μηνύματα όταν θα φτάσουν." + +#: modules/commands/ms_set.cpp:190 +msgid "You will no longer be able to receive memos." +msgstr "Δεν θα είσαι ικανός να λάβεις άλλα μηνύματα." + +#: modules/commands/ms_set.cpp:57 +msgid "You will no longer be informed via email." +msgstr "Δε θα σας στέλνονται πια ειδοποιήσεις μέσω email." + +#: modules/commands/ms_info.cpp:195 +msgid "You will not be notified of new memos." +msgstr "Δεν θα σου γίνει ειδοποίηση για νέα μηνύματα." + +#: modules/commands/ms_set.cpp:49 +msgid "You will now be informed about new memos via email." +msgstr "Θα ενημερώνεστε για καινούρια memo μέσω email." + +#: modules/commands/os_svs.cpp:86 +msgid "Your IRCd does not support SVSJOIN." +msgstr "" + +#: modules/commands/os_svs.cpp:31 +msgid "Your IRCd does not support SVSNICK." +msgstr "" + +#: modules/commands/os_svs.cpp:130 +msgid "Your IRCd does not support SVSPART." +msgstr "" + +#: include/language.h:127 +msgid "" +"Your IRCd does not support vIdent's, if this is incorrect, please report " +"this as a possible bug" +msgstr "" + +#: modules/extra/m_ldap_authentication.cpp:110 +#: modules/extra/m_sql_authentication.cpp:55 +#, c-format +msgid "Your account %s has been successfully created." +msgstr "" + +# +#: modules/commands/ns_register.cpp:328 +msgid "Your account is already confirmed." +msgstr "Το account σας είναι ήδη επιβεβαιωμένο." + +#: modules/commands/ns_register.cpp:396 +#, fuzzy, c-format +msgid "Your account will expire, if not confirmed, in %s." +msgstr "Το account σας θα λήξει αν δεν το κάνετε confirm σε %s" + +#: modules/commands/ns_set.cpp:1274 +#, fuzzy, c-format +msgid "Your email address has been changed to %s." +msgstr "Το E-mail address για τον #%s# άλλαξε σε #%s#." + +#: modules/commands/os_forbid.cpp:544 modules/commands/os_forbid.cpp:553 +#, fuzzy +msgid "Your email address is not allowed, choose a different one." +msgstr "Η διεύθνση email #%s# έχει επιβεβαιωθεί." + +#: modules/commands/ns_register.cpp:260 modules/commands/ns_register.cpp:391 +#, fuzzy +msgid "" +"Your email address is not confirmed. To confirm it, follow the instructions " +"that were emailed to you." +msgstr "" +"Το email σας δεν έχει επιβεβαιωθεί. Για να το επιβεβαιώσετε, ακολουθήστετις " +"οδηγίες που σας στάλθηκαν στο email όταν κάνατε register." + +#: modules/commands/ns_register.cpp:67 +#, c-format +msgid "Your email address of %s has been confirmed." +msgstr "Η διεύθνση email #%s# έχει επιβεβαιωθεί." + +#: modules/extra/m_ldap_authentication.cpp:159 +#, fuzzy, c-format +msgid "Your email has been updated to %s" +msgstr "Το E-mail address για τον #%s# άλλαξε σε #%s#." + +#: modules/extra/m_sql_authentication.cpp:62 +#, fuzzy, c-format +msgid "Your email has been updated to %s." +msgstr "Το E-mail address για τον #%s# άλλαξε σε #%s#." + +#: modules/commands/ms_set.cpp:197 +msgid "Your memo limit has been disabled." +msgstr "Το όριο μηνυμάτων memo απενεργοποιήθηκε." + +#: modules/commands/ms_set.cpp:183 +#, c-format +msgid "Your memo limit has been set to %d." +msgstr "Το όριο μηνυμάτων memo άλλαξε σε #%d#." + +#: modules/commands/ms_info.cpp:164 +#, c-format +msgid "Your memo limit is %d, and may not be changed." +msgstr "Το όριο μηνυμάτων memo είναι #%d#, και δεν μπορεί να αλλαχτεί." + +#: modules/commands/ms_info.cpp:166 +#, c-format +msgid "Your memo limit is %d." +msgstr "Το όριο μηνυμάτων είναι #%d#." + +#: modules/commands/ms_info.cpp:159 +msgid "Your memo limit is 0; you will not receive any new memos." +msgstr "Το όριο μηνυμάτων είναι #0#; δεν θα λάβεις ποτέ κανένα άλλο μήνυμα." + +#: modules/commands/ms_info.cpp:157 +#, fuzzy +msgid "" +"Your memo limit is 0; you will not receive any new memos. You cannot change " +"this limit." +msgstr "" +"Το όριο μηνυμάτων είναι #0#; δεν θα λάβεις ποτέ κανένα άλλο μήνυμα. Δεν " +"μπορείς να αλλάξεις αυτό το όριο." + +#: modules/commands/ns_logout.cpp:50 +msgid "Your nick has been logged out." +msgstr "" +"Το ψευδώνυμο σου δεν το κατέχεις τώρα,πρέπει να κάνεις πάλι εντολή " +"αναγνώρισης για να το κατέχεις." + +#: modules/commands/ns_group.cpp:156 +msgid "Your nick is already registered." +msgstr "Το Nickname %s κατωχυρώθηκε." + +#: modules/commands/ns_group.cpp:246 +msgid "Your nick is not grouped to anything, you can't ungroup it." +msgstr "" +"Το nick σας δεν είναι σε κάποιο group. Δεν μπορείτε να το κάνετε ungroup." + +#: include/language.h:77 +msgid "Your nick isn't registered." +msgstr "Το Nickname %s κατωχυρώθηκε." + +#: modules/pseudoclients/nickserv.cpp:254 +#, c-format +msgid "Your nickname is now being changed to %s" +msgstr "Το ψευδώνυμό σου έχει αλλάξει σε #%s#" + +#: modules/commands/os_login.cpp:32 modules/commands/os_login.cpp:79 +msgid "Your oper block doesn't require logging in." +msgstr "To oper block σας δεν χρειάζεται login." + +#: modules/commands/ns_register.cpp:336 +#, c-format +msgid "Your passcode has been re-sent to %s." +msgstr "Το passcode σας, ξαναστάλθηκε στο %s." + +#: modules/commands/ns_register.cpp:232 +#, c-format +msgid "Your password is %s - remember this for later use." +msgstr "Ο κωδικός σου είναι #%s# - θυμηθείτε τον για μετέπειτα χρήση." + +#: include/language.h:76 +#, c-format +msgid "Your password is too long. It must not exceed %u characters." +msgstr "" + +#: modules/commands/ns_resetpass.cpp:96 +msgid "Your password reset request has expired." +msgstr "Το αίτημά σας για αλλαγή του password έληξε." + +#: modules/commands/hs_request.cpp:170 +#, fuzzy +msgid "Your vHost has been requested." +msgstr "Bot #%s# διαγράφηκε." + +#: modules/pseudoclients/hostserv.cpp:64 +#: modules/pseudoclients/hostserv.cpp:103 modules/commands/hs_on.cpp:37 +#, c-format +msgid "Your vhost of %s is now activated." +msgstr "Η vhost σας #%s# ενεργοποιήθηκε." + +#: modules/pseudoclients/hostserv.cpp:62 +#: modules/pseudoclients/hostserv.cpp:101 modules/commands/hs_on.cpp:35 +#, c-format +msgid "Your vhost of %s@%s is now activated." +msgstr "Η vhost σας #%s#@#%s# ενεργοποιήθηκε." + +#: modules/commands/hs_off.cpp:39 +msgid "Your vhost was removed and the normal cloaking restored." +msgstr "Η Vhost σας αφαιρέθηκε και το κανονικό cloaking επανακτήθηκε." + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Zone" +msgstr "Κανένα" + +#: modules/commands/os_dns.cpp:290 +#, fuzzy, c-format +msgid "Zone %s already exists." +msgstr "Το Bot #%s# υπάρχει ήδη." + +#: modules/commands/os_dns.cpp:310 modules/commands/os_dns.cpp:352 +#: modules/commands/os_dns.cpp:402 modules/commands/os_dns.cpp:438 +#, fuzzy, c-format +msgid "Zone %s does not exist." +msgstr " %s (δεν λήγει ποτέ)" + +#: modules/commands/os_dns.cpp:332 +#, fuzzy, c-format +msgid "Zone %s removed." +msgstr "Η vhost για τον #%s# αφαιρέθηκε." + +#: modules/commands/os_defcon.cpp:177 +msgid "[1|2|3|4|5]" +msgstr "" + +#: modules/commands/os_news.cpp:400 +#, c-format +msgid "[Logon News - %s] %s" +msgstr "[#Κανονισμοί ή πληροφορίες# - %s] %s" + +#: modules/commands/os_news.cpp:402 +#, c-format +msgid "[Oper News - %s] %s" +msgstr "[#Νέα για Opers# - %s] %s" + +#: modules/commands/os_news.cpp:404 +#, c-format +msgid "[Random News - %s] %s" +msgstr "[#Νέα σχετικά με το δίκτυο# - %s] %s" + +#: modules/commands/ns_identify.cpp:66 +msgid "[account] password" +msgstr "IDENTIFY ^_κωδικό^_" + +# +#: modules/commands/cs_updown.cpp:49 modules/commands/cs_updown.cpp:147 +#, fuzzy +msgid "[channel [nick]]" +msgstr "OP ##channel# [#nick#]#" + +# +#: modules/commands/ms_ignore.cpp:20 +#, fuzzy +msgid "[channel] ADD entry" +msgstr "AOP #channel# {ADD|DEL|LIST|CLEAR} [#nick# | #entry-list#]" + +#: modules/commands/ms_ignore.cpp:21 +#, fuzzy +msgid "[channel] DEL entry" +msgstr "UNBAN #κανάλι# [#nick#]" + +#: modules/commands/ms_ignore.cpp:22 +#, fuzzy +msgid "[channel] LIST" +msgstr "DROP #channel#" + +#: modules/commands/ms_list.cpp:20 +msgid "[channel] [list | NEW]" +msgstr "LIST [#κανάλι#] [#list# | NEW]" + +# +#: modules/extra/stats/cs_fantasy_stats.cpp:40 +#, fuzzy +msgid "[channel] [nick]" +msgstr "OP ##channel# [#nick#]#" + +#: modules/commands/ms_del.cpp:45 +msgid "[channel] {num | list | LAST | ALL}" +msgstr "DEL [#κανάλι#] {#νου# | #list# | ALL}" + +#: modules/commands/ms_read.cpp:113 +#, fuzzy +msgid "[channel] {num | list | LAST | NEW | ALL}" +msgstr "DEL [#κανάλι#] {#νου# | #list# | ALL}" + +#: modules/commands/hs_list.cpp:20 +msgid "[key|#X-Y]" +msgstr "" + +#: modules/commands/ms_info.cpp:20 +msgid "[nick | channel]" +msgstr "RSEND {#nick# | #channel#} #memo-text#" + +#: modules/commands/ns_group.cpp:237 +msgid "[nick]" +msgstr "" + +#: modules/commands/ns_logout.cpp:22 +msgid "[nickname [REVALIDATE]]" +msgstr "" + +#: modules/commands/ns_alist.cpp:25 modules/commands/ns_status.cpp:20 +#: modules/commands/ns_info.cpp:20 +msgid "[nickname]" +msgstr "" + +#: modules/commands/ns_set_misc.cpp:96 +msgid "[parameter]" +msgstr "" + +#: modules/commands/os_logsearch.cpp:33 +msgid "[+daysd] [+limitl] pattern" +msgstr "" + +#: modules/commands/os_chankill.cpp:22 +msgid "[+expiry] channel reason" +msgstr "CHANKILL [+#expiry#] {##channel#} [#reason#]" + +#: modules/commands/ns_list.cpp:110 +msgid "[Hostname hidden]" +msgstr "" + +#: modules/commands/ns_list.cpp:112 modules/commands/cs_list.cpp:115 +msgid "[Suspended]" +msgstr "" + +#: modules/commands/ns_list.cpp:114 +msgid "[Unconfirmed]" +msgstr "" + +#: modules/commands/hs_request.cpp:213 +msgid "[auto memo] Your requested vHost has been approved." +msgstr "#[auto-memo]# Το memo που στείλατε στο %s έχει διαβαστεί." + +#: modules/commands/hs_request.cpp:267 +msgid "[auto memo] Your requested vHost has been rejected." +msgstr "#[auto-memo]# Το memo που στείλατε στο %s έχει διαβαστεί." + +#: modules/commands/hs_request.cpp:265 +#, c-format +msgid "[auto memo] Your requested vHost has been rejected. Reason: %s" +msgstr "" + +#: modules/commands/hs_request.cpp:388 +#, fuzzy, c-format +msgid "[auto memo] vHost %s has been requested by %s." +msgstr "Το τελευταίο μήνυμα που πήγαινε για τον #%s# ακυρώθηκε." + +#: modules/commands/os_list.cpp:133 +msgid "[{pattern | channel} [INVISIBLE]]" +msgstr "" + +#: modules/commands/os_list.cpp:20 +msgid "[{pattern | nick} [SECRET]]" +msgstr "" + +#: src/misc.cpp:337 +msgid "day" +msgstr "" + +#: src/misc.cpp:337 +msgid "days" +msgstr "" + +#: include/language.h:88 +msgid "does not expire" +msgstr " %s (δεν λήγει ποτέ)" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d day" +msgstr "λήγει μέσα σε %d μέρα" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d days" +msgstr "λήγει μέσα σε %d μέρες" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minute" +msgstr "λήγει μέσα σε %d ώρα, %d λεπτά" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minutes" +msgstr "λήγει μέσα σε %d ώρα, %d λεπτά" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minute" +msgstr "λήγει μέσα σε %d ώρες, %d λεπτά" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minutes" +msgstr "λήγει μέσα σε %d ώρες, %d λεπτά" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minute" +msgstr "λήγει μέσα σε %d λεπτό" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minutes" +msgstr "λήγει μέσα σε %d λεπτά" + +#: src/misc.cpp:375 +#, fuzzy +msgid "expires momentarily" +msgstr "λήγει μέσα σε %d μέρα" + +#: src/misc.cpp:343 +msgid "hour" +msgstr "" + +#: src/misc.cpp:343 +msgid "hours" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:150 +#, c-format +msgid "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:349 +msgid "minute" +msgstr "" + +#: src/misc.cpp:349 +msgid "minutes" +msgstr "" + +#: modules/commands/bs_info.cpp:87 +msgid "not assigned yet" +msgstr "" + +#: src/misc.cpp:324 +msgid "second" +msgstr "" + +# +#: src/misc.cpp:324 +msgid "seconds" +msgstr "Οι εντολές του %s είναι::" + +#: modules/commands/hs_request.cpp:215 +#, fuzzy, c-format +msgid "vHost for %s has been activated." +msgstr "Η vhost σας #%s# ενεργοποιήθηκε." + +#: modules/commands/hs_request.cpp:272 +#, fuzzy, c-format +msgid "vHost for %s has been rejected." +msgstr "Bot #%s# διαγράφηκε." + +#: modules/commands/hs_request.cpp:79 +msgid "vhost" +msgstr "" + +#: modules/commands/hs_del.cpp:83 +#, c-format +msgid "vhosts for group %s have been removed." +msgstr "Οι vhosts για το group #%s# έχουν διαγραφεί." + +#: src/misc.cpp:331 +msgid "year" +msgstr "" + +#: src/misc.cpp:331 +msgid "years" +msgstr "" + +#: modules/commands/os_config.cpp:20 +msgid "{MODIFY|VIEW} [block name item name item value]" +msgstr "CONFIG {#MODIFY#|#VIEW#} [#block name# #item name# #item value#]" + +#: modules/commands/bs_info.cpp:41 +#, fuzzy +msgid "{channel | nickname}" +msgstr "UNBAN #κανάλι# [#nick#]" + +#: modules/commands/ms_cancel.cpp:20 +#, fuzzy +msgid "{nick | channel}" +msgstr "RSEND {#nick# | #channel#} #memo-text#" + +#: modules/commands/ms_rsend.cpp:25 modules/commands/ms_send.cpp:25 +#, fuzzy +msgid "{nick | channel} memo-text" +msgstr "RSEND {#nick# | #channel#} #memo-text#" diff --git a/language/anope.en_US.po b/language/anope.en_US.po new file mode 100644 index 0000000..76ae10f --- /dev/null +++ b/language/anope.en_US.po @@ -0,0 +1,11070 @@ +# Anope IRC Services language file +# Copyright (C) 2014-2020 +# This file is distributed under the same license as the Anope IRC Services package. +# Adam , 2014. +# +msgid "" +msgstr "" +"Project-Id-Version: Anope\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2020-01-06 17:08+0100\n" +"PO-Revision-Date: 2020-01-06 17:08+0100\n" +"Last-Translator: Adam \n" +"Language-Team: English\n" +"Language: en_US\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=ISO-8859-1\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" + +#: modules/commands/os_forbid.cpp:324 +#, c-format +msgid "%d channel(s) cleared, and %d channel(s) dropped." +msgstr "%d channel(s) cleared, and %d channel(s) dropped." + +#: modules/commands/os_forbid.cpp:265 +#, c-format +msgid "%d nickname(s) dropped." +msgstr "%d nickname(s) dropped." + +#: modules/commands/cs_xop.cpp:219 +#, c-format +msgid "%s added to %s %s list." +msgstr "%s added to %s %s list." + +#: modules/commands/cs_access.cpp:225 +#, c-format +msgid "%s added to %s access list at level %d." +msgstr "%s added to %s access list at level %d." + +#: modules/commands/cs_access.cpp:223 +#, c-format +msgid "%s added to %s access list at privilege %s (level %d)" +msgstr "%s added to %s access list at privilege %s (level %d)" + +#: modules/commands/cs_akick.cpp:190 +#, c-format +msgid "%s added to %s autokick list." +msgstr "%s added to %s autokick list." + +#: modules/commands/bs_badwords.cpp:307 +#, c-format +msgid "%s added to %s bad words list." +msgstr "%s added to %s bad words list." + +#: modules/commands/ns_access.cpp:45 +#, c-format +msgid "%s added to %s's access list." +msgstr "%s added to %s's access list." + +#: modules/commands/ns_cert.cpp:204 +#, c-format +msgid "%s added to %s's certificate list." +msgstr "%s added to %s's certificate list." + +#: modules/commands/ms_ignore.cpp:62 +#, c-format +msgid "%s added to ignore list." +msgstr "%s added to ignore list." + +#: modules/commands/os_sxline.cpp:415 modules/commands/os_sxline.cpp:649 +#, c-format +msgid "%s added to the %s list." +msgstr "%s added to the %s list." + +#: modules/commands/os_akill.cpp:203 +#, c-format +msgid "%s added to the AKILL list." +msgstr "%s added to the AKILL list." + +#: modules/pseudoclients/botserv.cpp:134 +#, c-format +msgid "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands " +"that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" +msgstr "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands " +"that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" + +#: modules/pseudoclients/botserv.cpp:148 +#, c-format +msgid "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" + +#: modules/pseudoclients/nickserv.cpp:466 +#, c-format +msgid "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" + +#: modules/pseudoclients/nickserv.cpp:473 +#, c-format +msgid "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" + +#: modules/pseudoclients/chanserv.cpp:255 +#, c-format +msgid "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" +msgstr "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" + +#: modules/commands/bs_badwords.cpp:298 +#, c-format +msgid "%s already exists in %s bad words list." +msgstr "%s already exists in %s bad words list." + +#: modules/commands/cs_akick.cpp:170 +#, c-format +msgid "%s already exists on %s autokick list." +msgstr "%s already exists on %s autokick list." + +#: modules/commands/os_session.cpp:361 +#, c-format +msgid "%s already exists on the EXCEPTION list." +msgstr "%s already exists on the EXCEPTION list." + +#: modules/commands/bs_kick.cpp:214 modules/commands/bs_kick.cpp:389 +#: modules/commands/bs_kick.cpp:520 modules/commands/bs_kick.cpp:651 +#, c-format +msgid "%s cannot be taken as times to ban." +msgstr "%s cannot be taken as times to ban." + +#: modules/commands/os_mode.cpp:163 +#, c-format +msgid "%s changed your usermodes to %s." +msgstr "%s changed your usermodes to %s." + +#: modules/commands/os_list.cpp:47 +#, c-format +msgid "%s channel list:" +msgstr "%s channel list:" + +#: modules/commands/cs_xop.cpp:343 +#, c-format +msgid "%s deleted from %s %s list." +msgstr "%s deleted from %s %s list." + +#: modules/commands/cs_access.cpp:326 +#, c-format +msgid "%s deleted from %s access list." +msgstr "%s deleted from %s access list." + +#: modules/commands/cs_akick.cpp:276 +#, c-format +msgid "%s deleted from %s autokick list." +msgstr "%s deleted from %s autokick list." + +#: modules/commands/bs_badwords.cpp:348 +#, c-format +msgid "%s deleted from %s bad words list." +msgstr "%s deleted from %s bad words list." + +#: modules/commands/ns_access.cpp:72 +#, c-format +msgid "%s deleted from %s's access list." +msgstr "%s deleted from %s's access list." + +#: modules/commands/ns_cert.cpp:233 +#, c-format +msgid "%s deleted from %s's certificate list." +msgstr "%s deleted from %s's certificate list." + +#: modules/commands/os_session.cpp:414 +#, c-format +msgid "%s deleted from session-limit exception list." +msgstr "%s deleted from session-limit exception list." + +#: modules/commands/os_sxline.cpp:99 +#, c-format +msgid "%s deleted from the %s list." +msgstr "%s deleted from the %s list." + +#: modules/commands/os_akill.cpp:246 +#, c-format +msgid "%s deleted from the AKILL list." +msgstr "%s deleted from the AKILL list." + +#: modules/commands/cs_access.cpp:685 +#, c-format +msgid "%s disabled on channel %s." +msgstr "%s disabled on channel %s." + +#: modules/commands/cs_invite.cpp:75 +#, c-format +msgid "%s has been invited to %s." +msgstr "%s has been invited to %s." + +#: modules/commands/os_svs.cpp:104 +#, c-format +msgid "%s has been joined to %s." +msgstr "%s has been joined to %s." + +#: modules/commands/os_svs.cpp:152 +#, c-format +msgid "%s has been parted from %s." +msgstr "%s has been parted from %s." + +#: modules/commands/cs_unban.cpp:96 +#, c-format +msgid "%s has been unbanned from %s." +msgstr "%s has been unbanned from %s." + +#: modules/commands/ns_alist.cpp:110 +#, c-format +msgid "%s has no access in any channels." +msgstr "%s has no access in any channels." + +#: modules/commands/cs_status.cpp:55 +#, c-format +msgid "%s has no access on %s." +msgstr "%s has no access on %s." + +#: modules/commands/cs_set.cpp:307 +#, c-format +msgid "%s has too many channels registered." +msgstr "%s has too many channels registered." + +#: modules/commands/cs_status.cpp:51 +#, c-format +msgid "%s is a super administrator." +msgstr "%s is a super administrator." + +#: modules/pseudoclients/memoserv.cpp:214 +#, c-format +msgid "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" +msgstr "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" + +#: modules/commands/cs_invite.cpp:66 +#, c-format +msgid "%s is already in %s!" +msgstr "%s is already in %s!" + +#: modules/commands/os_svs.cpp:99 +#, c-format +msgid "%s is already in %s." +msgstr "%s is already in %s." + +#: modules/commands/ms_ignore.cpp:65 +#, c-format +msgid "%s is already on the ignore list." +msgstr "%s is already on the ignore list." + +#: modules/commands/cs_suspend.cpp:97 modules/commands/ns_suspend.cpp:106 +#, c-format +msgid "%s is already suspended." +msgstr "%s is already suspended." + +#: modules/commands/ms_rsend.cpp:56 modules/commands/ms_send.cpp:55 +#, c-format +msgid "%s is not a registered unforbidden nick or channel." +msgstr "%s is not a registered unforbidden nick or channel." + +#: modules/commands/cs_set.cpp:178 +#, c-format +msgid "%s is not a valid ban type." +msgstr "%s is not a valid ban type." + +#: modules/commands/bs_info.cpp:101 +#, c-format +msgid "%s is not a valid bot or registered channel." +msgstr "%s is not a valid bot or registered channel." + +#: include/language.h:86 +#, c-format +msgid "%s is not a valid e-mail address." +msgstr "%s is not a valid e-mail address." + +#: include/language.h:80 +#, c-format +msgid "%s is not currently on channel %s." +msgstr "%s is not currently on channel %s." + +#: modules/commands/os_svs.cpp:144 +#, c-format +msgid "%s is not in %s." +msgstr "%s is not in %s." + +#: modules/commands/ms_ignore.cpp:77 +#, c-format +msgid "%s is not on the ignore list." +msgstr "%s is not on the ignore list." + +#: modules/commands/cs_status.cpp:90 +#, c-format +msgid "%s is on the auto kick list of %s (%s)." +msgstr "%s is on the auto kick list of %s (%s)." + +#: modules/commands/cs_status.cpp:53 +#, c-format +msgid "%s is the founder of %s." +msgstr "%s is the founder of %s." + +#: modules/commands/cs_status.cpp:78 +#, c-format +msgid "%s matches access entry %s (from entry %s), which has privilege %s." +msgstr "%s matches access entry %s (from entry %s), which has privilege %s." + +#: modules/commands/cs_status.cpp:71 +#, c-format +msgid "%s matches access entry %s, which has privilege %s." +msgstr "%s matches access entry %s, which has privilege %s." + +#: include/language.h:109 +#, c-format +msgid "" +"%s matches an except on %s and cannot be banned until the except has been " +"removed." +msgstr "" +"%s matches an except on %s and cannot be banned until the except has been " +"removed." + +#: modules/commands/cs_status.cpp:96 +#, c-format +msgid "%s matches auto kick entry %s on %s (%s)." +msgstr "%s matches auto kick entry %s on %s (%s)." + +#: modules/commands/cs_xop.cpp:353 +#, c-format +msgid "%s not found on %s %s list." +msgstr "%s not found on %s %s list." + +#: modules/commands/cs_access.cpp:338 modules/commands/cs_flags.cpp:255 +#, c-format +msgid "%s not found on %s access list." +msgstr "%s not found on %s access list." + +#: modules/commands/cs_akick.cpp:265 +#, c-format +msgid "%s not found on %s autokick list." +msgstr "%s not found on %s autokick list." + +#: modules/commands/bs_badwords.cpp:341 +#, c-format +msgid "%s not found on %s bad words list." +msgstr "%s not found on %s bad words list." + +#: modules/commands/ns_access.cpp:66 +#, c-format +msgid "%s not found on %s's access list." +msgstr "%s not found on %s's access list." + +#: modules/commands/ns_cert.cpp:226 +#, c-format +msgid "%s not found on %s's certificate list." +msgstr "%s not found on %s's certificate list." + +#: modules/commands/os_ignore.cpp:320 +#, c-format +msgid "%s not found on ignore list." +msgstr "%s not found on ignore list." + +#: modules/commands/os_session.cpp:238 +#, c-format +msgid "" +"%s not found on session list, but has a limit of %d because it matches entry:" +" %s." +msgstr "" +"%s not found on session list, but has a limit of %d because it matches entry:" +" %s." + +#: modules/commands/os_session.cpp:418 +#, c-format +msgid "%s not found on session-limit exception list." +msgstr "%s not found on session-limit exception list." + +#: modules/commands/os_sxline.cpp:92 +#, c-format +msgid "%s not found on the %s list." +msgstr "%s not found on the %s list." + +#: modules/commands/os_akill.cpp:237 +#, c-format +msgid "%s not found on the AKILL list." +msgstr "%s not found on the AKILL list." + +#: modules/commands/cs_flags.cpp:251 +#, c-format +msgid "%s removed from the %s access list." +msgstr "%s removed from the %s access list." + +#: modules/commands/ms_ignore.cpp:74 +#, c-format +msgid "%s removed from the ignore list." +msgstr "%s removed from the ignore list." + +#: modules/commands/os_list.cpp:157 +#, c-format +msgid "%s users list:" +msgstr "%s users list:" + +#: modules/commands/os_ignore.cpp:316 +#, c-format +msgid "%s will no longer be ignored." +msgstr "%s will no longer be ignored." + +#: modules/commands/os_ignore.cpp:238 +#, c-format +msgid "%s will now be ignored for %s." +msgstr "%s will now be ignored for %s." + +#: modules/commands/os_ignore.cpp:233 +#, c-format +msgid "%s will now permanently be ignored." +msgstr "%s will now permanently be ignored." + +#: include/language.h:66 +#, c-format +msgid "%s%s HELP %s for more information." +msgstr "%s%s HELP %s for more information." + +#: modules/commands/bs_bot.cpp:270 +msgid "ADD nick user host real" +msgstr "ADD nick user host real" + +#: modules/commands/bs_bot.cpp:271 +msgid "CHANGE oldnick newnick [user [host [real]]]" +msgstr "CHANGE oldnick newnick [user [host [real]]]" + +#: modules/commands/bs_bot.cpp:272 +msgid "DEL nick" +msgstr "DEL nick" + +#: modules/commands/os_session.cpp:560 +msgid "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." +msgstr "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." + +#: modules/commands/os_noop.cpp:68 +msgid "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." +msgstr "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." + +#: modules/commands/cs_access.cpp:611 +#, c-format +msgid "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." +msgstr "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." + +#: modules/commands/ms_read.cpp:35 +#, c-format +msgid "[auto-memo] The memo you sent to %s has been viewed." +msgstr "[auto-memo] The memo you sent to %s has been viewed." + +#: modules/commands/ns_group.cpp:92 +msgid "[target] [password]" +msgstr "[target] [password]" + +#: modules/commands/ns_set.cpp:453 +msgid "address" +msgstr "address" + +#: modules/commands/bs_set.cpp:162 +msgid "botname {ON|OFF}" +msgstr "botname {ON|OFF}" + +#: modules/extra/stats/cs_fantasy_top.cpp:39 +#: modules/extra/stats/cs_fantasy_top.cpp:51 +#: modules/commands/cs_suspend.cpp:152 modules/commands/cs_sync.cpp:20 +#: modules/commands/cs_log.cpp:106 modules/commands/bs_assign.cpp:91 +#: modules/commands/cs_info.cpp:20 modules/commands/cs_getkey.cpp:20 +msgid "channel" +msgstr "channel" + +#: modules/commands/cs_set.cpp:138 +msgid "channel bantype" +msgstr "channel bantype" + +#: modules/commands/cs_drop.cpp:20 +msgid "channel channel" +msgstr "channel channel" + +#: modules/commands/cs_log.cpp:107 +msgid "channel command method [status]" +msgstr "channel command method [status]" + +#: modules/commands/cs_kick.cpp:21 +msgid "channel mask [reason]" +msgstr "channel mask [reason]" + +#: modules/commands/os_mode.cpp:20 +msgid "channel modes" +msgstr "channel modes" + +#: modules/commands/cs_set.cpp:267 modules/commands/bs_assign.cpp:20 +msgid "channel nick" +msgstr "channel nick" + +#: modules/commands/cs_kick.cpp:20 +msgid "channel nick [reason]" +msgstr "channel nick [reason]" + +#: modules/commands/cs_clone.cpp:115 +msgid "channel target [what]" +msgstr "channel target [what]" + +#: modules/commands/bs_control.cpp:20 modules/commands/bs_control.cpp:80 +msgid "channel text" +msgstr "channel text" + +#: modules/commands/bs_set.cpp:91 +msgid "channel time" +msgstr "channel time" + +#: modules/commands/os_kick.cpp:20 +msgid "channel user reason" +msgstr "channel user reason" + +#: modules/commands/cs_enforce.cpp:228 +msgid "channel what" +msgstr "channel what" + +#: modules/commands/cs_xop.cpp:481 +msgid "channel ADD mask" +msgstr "channel ADD mask" + +#: modules/commands/cs_access.cpp:499 +msgid "channel ADD mask level" +msgstr "channel ADD mask level" + +#: modules/commands/cs_entrymsg.cpp:194 +msgid "channel ADD message" +msgstr "channel ADD message" + +#: modules/commands/bs_badwords.cpp:371 +msgid "channel ADD word [SINGLE | START | END]" +msgstr "channel ADD word [SINGLE | START | END]" + +#: modules/commands/cs_akick.cpp:435 +msgid "channel ADD {nick | mask} [reason]" +msgstr "channel ADD {nick | mask} [reason]" + +#: modules/commands/cs_topic.cpp:151 +msgid "channel APPEND topic" +msgstr "channel APPEND topic" + +#: modules/commands/cs_access.cpp:503 modules/commands/cs_flags.cpp:376 +#: modules/commands/cs_xop.cpp:484 modules/commands/cs_entrymsg.cpp:197 +#: modules/commands/bs_badwords.cpp:374 modules/commands/cs_akick.cpp:440 +msgid "channel CLEAR" +msgstr "channel CLEAR" + +#: modules/commands/cs_mode.cpp:736 +msgid "channel CLEAR [what]" +msgstr "channel CLEAR [what]" + +#: modules/commands/os_mode.cpp:21 +msgid "channel CLEAR [ALL]" +msgstr "channel CLEAR [ALL]" + +#: modules/commands/cs_entrymsg.cpp:195 +msgid "channel DEL num" +msgstr "channel DEL num" + +#: modules/commands/cs_access.cpp:500 modules/commands/cs_xop.cpp:482 +msgid "channel DEL {mask | entry-num | list}" +msgstr "channel DEL {mask | entry-num | list}" + +#: modules/commands/cs_akick.cpp:436 +msgid "channel DEL {nick | mask | entry-num | list}" +msgstr "channel DEL {nick | mask | entry-num | list}" + +#: modules/commands/bs_badwords.cpp:372 +msgid "channel DEL {word | entry-num | list}" +msgstr "channel DEL {word | entry-num | list}" + +#: modules/commands/cs_akick.cpp:439 +msgid "channel ENFORCE" +msgstr "channel ENFORCE" + +#: modules/commands/cs_access.cpp:744 modules/commands/cs_entrymsg.cpp:196 +msgid "channel LIST" +msgstr "channel LIST" + +#: modules/commands/cs_akick.cpp:437 +msgid "channel LIST [mask | entry-num | list]" +msgstr "channel LIST [mask | entry-num | list]" + +#: modules/commands/cs_access.cpp:501 modules/commands/cs_xop.cpp:483 +#: modules/commands/bs_badwords.cpp:373 +msgid "channel LIST [mask | list]" +msgstr "channel LIST [mask | list]" + +#: modules/commands/cs_flags.cpp:375 +msgid "channel LIST [mask | +flags]" +msgstr "channel LIST [mask | +flags]" + +#: modules/commands/cs_mode.cpp:734 +msgid "channel LOCK {ADD|DEL|SET|LIST} [what]" +msgstr "channel LOCK {ADD|DEL|SET|LIST} [what]" + +#: modules/commands/cs_access.cpp:745 +msgid "channel RESET" +msgstr "channel RESET" + +#: modules/commands/cs_mode.cpp:735 +msgid "channel SET modes" +msgstr "channel SET modes" + +#: modules/commands/cs_access.cpp:742 +msgid "channel SET type level" +msgstr "channel SET type level" + +#: modules/commands/cs_akick.cpp:438 +msgid "channel VIEW [mask | entry-num | list]" +msgstr "channel VIEW [mask | entry-num | list]" + +#: modules/commands/cs_access.cpp:502 +msgid "channel VIEW [mask | list]" +msgstr "channel VIEW [mask | list]" + +#: modules/commands/cs_register.cpp:20 modules/commands/cs_set.cpp:205 +msgid "channel [description]" +msgstr "channel [description]" + +#: modules/commands/cs_set.cpp:950 modules/commands/cs_invite.cpp:20 +#: modules/commands/cs_unban.cpp:20 +msgid "channel [nick]" +msgstr "channel [nick]" + +#: modules/commands/cs_set_misc.cpp:96 +msgid "channel [parameters]" +msgstr "channel [parameters]" + +#: modules/commands/cs_mode.cpp:807 modules/commands/cs_status.cpp:20 +msgid "channel [user]" +msgstr "channel [user]" + +#: modules/commands/cs_suspend.cpp:59 +msgid "channel [+expiry] [reason]" +msgstr "channel [+expiry] [reason]" + +#: modules/commands/cs_ban.cpp:40 +msgid "channel [+expiry] {nick | mask} [reason]" +msgstr "channel [+expiry] {nick | mask} [reason]" + +#: modules/commands/cs_flags.cpp:374 +msgid "channel [MODIFY] mask changes" +msgstr "channel [MODIFY] mask changes" + +#: modules/commands/cs_topic.cpp:150 +msgid "channel [SET] [topic]" +msgstr "channel [SET] [topic]" + +#: modules/commands/cs_topic.cpp:152 +msgid "channel [UNLOCK|LOCK]" +msgstr "channel [UNLOCK|LOCK]" + +#: modules/fantasy.cpp:20 modules/commands/greet.cpp:20 +#: modules/commands/bs_assign.cpp:154 +msgid "channel {ON|OFF}" +msgstr "channel {ON|OFF}" + +#: modules/commands/bs_kick.cpp:491 +msgid "channel {ON|OFF} [ttb [ln [secs]]]" +msgstr "channel {ON|OFF} [ttb [ln [secs]]]" + +#: modules/commands/bs_kick.cpp:361 +msgid "channel {ON|OFF} [ttb [min [percent]]]" +msgstr "channel {ON|OFF} [ttb [min [percent]]]" + +#: modules/commands/bs_kick.cpp:623 +msgid "channel {ON|OFF} [ttb [num]]" +msgstr "channel {ON|OFF} [ttb [num]]" + +#: modules/commands/bs_kick.cpp:252 modules/commands/bs_kick.cpp:288 +#: modules/commands/bs_kick.cpp:327 modules/commands/bs_kick.cpp:457 +#: modules/commands/bs_kick.cpp:589 modules/commands/bs_kick.cpp:724 +#: modules/commands/bs_kick.cpp:758 +msgid "channel {ON|OFF} [ttb]" +msgstr "channel {ON|OFF} [ttb]" + +#: modules/commands/cs_access.cpp:743 +msgid "channel {DIS | DISABLE} type" +msgstr "channel {DIS | DISABLE} type" + +#: modules/commands/cs_set.cpp:873 +msgid "channel {ON | LEVEL | OFF}" +msgstr "channel {ON | LEVEL | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:18 modules/commands/cs_set.cpp:75 +#: modules/commands/cs_set.cpp:336 modules/commands/cs_set.cpp:401 +#: modules/commands/cs_set.cpp:473 modules/commands/cs_set.cpp:622 +#: modules/commands/cs_set.cpp:684 modules/commands/cs_set.cpp:747 +#: modules/commands/cs_set.cpp:811 modules/commands/cs_set.cpp:1044 +#: modules/commands/bs_kick.cpp:792 modules/commands/bs_kick.cpp:857 +#: modules/commands/cs_topic.cpp:21 modules/commands/cs_list.cpp:181 +msgid "channel {ON | OFF}" +msgstr "channel {ON | OFF}" + +#: modules/commands/ns_getemail.cpp:24 +msgid "email" +msgstr "email" + +#: modules/commands/ns_set.cpp:794 +msgid "language" +msgstr "language" + +#: modules/commands/ms_sendall.cpp:25 modules/commands/ms_staff.cpp:25 +msgid "memo-text" +msgstr "memo-text" + +#: modules/commands/gl_global.cpp:22 modules/commands/greet.cpp:84 +msgid "message" +msgstr "message" + +#: modules/commands/os_modinfo.cpp:20 modules/commands/os_module.cpp:20 +#: modules/commands/os_module.cpp:57 modules/commands/os_module.cpp:129 +msgid "modname" +msgstr "modname" + +#: modules/commands/ns_set.cpp:330 +msgid "new-display" +msgstr "new-display" + +#: modules/commands/ns_set.cpp:120 +msgid "new-password" +msgstr "new-password" + +#: modules/extra/stats/cs_fantasy_stats.cpp:52 modules/commands/hs_del.cpp:20 +#: modules/commands/hs_del.cpp:60 modules/commands/ms_check.cpp:20 +#: modules/commands/hs_request.cpp:192 modules/commands/cs_seen.cpp:262 +msgid "nick" +msgstr "nick" + +#: modules/commands/os_svs.cpp:79 +msgid "nick channel" +msgstr "nick channel" + +#: modules/commands/os_svs.cpp:123 +msgid "nick channel [reason]" +msgstr "nick channel [reason]" + +#: modules/commands/os_oline.cpp:20 +msgid "nick flags" +msgstr "nick flags" + +#: modules/commands/hs_set.cpp:20 modules/commands/hs_set.cpp:126 +msgid "nick hostmask" +msgstr "nick hostmask" + +#: modules/commands/os_svs.cpp:20 +msgid "nick newnick" +msgstr "nick newnick" + +#: modules/commands/hs_request.cpp:241 +msgid "nick [reason]" +msgstr "nick [reason]" + +#: modules/commands/ns_getpass.cpp:20 modules/commands/ns_drop.cpp:19 +#: modules/commands/ns_suspend.cpp:161 +msgid "nickname" +msgstr "nickname" + +#: modules/commands/ns_set.cpp:546 +msgid "nickname address" +msgstr "nickname address" + +#: modules/commands/ns_resetpass.cpp:22 +msgid "nickname email" +msgstr "nickname email" + +#: modules/commands/ns_set.cpp:872 +msgid "nickname language" +msgstr "nickname language" + +#: modules/commands/greet.cpp:145 +msgid "nickname message" +msgstr "nickname message" + +#: modules/commands/ns_set.cpp:399 +msgid "nickname new-display" +msgstr "nickname new-display" + +#: modules/commands/ns_set.cpp:173 +msgid "nickname new-password" +msgstr "nickname new-password" + +#: modules/commands/ns_set_misc.cpp:170 +msgid "nickname [parameter]" +msgstr "nickname [parameter]" + +#: modules/commands/ns_recover.cpp:150 +msgid "nickname [password]" +msgstr "nickname [password]" + +#: modules/commands/ns_suspend.cpp:61 +msgid "nickname [+expiry] [reason]" +msgstr "nickname [+expiry] [reason]" + +#: modules/commands/ns_info.cpp:239 +msgid "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +msgstr "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:130 modules/commands/ns_set.cpp:302 +#: modules/commands/ns_set.cpp:631 modules/commands/ns_set.cpp:985 +#: modules/commands/ns_set.cpp:1076 modules/commands/ns_set.cpp:1105 +#: modules/commands/ns_list.cpp:252 +msgid "nickname {ON | OFF}" +msgstr "nickname {ON | OFF}" + +#: modules/commands/ns_set.cpp:760 +msgid "nickname {ON | QUICK | IMMED | OFF}" +msgstr "nickname {ON | QUICK | IMMED | OFF}" + +#: modules/commands/bs_set.cpp:20 +msgid "option (channel | bot) settings" +msgstr "option (channel | bot) settings" + +#: modules/commands/cs_set.cpp:21 +msgid "option channel parameters" +msgstr "option channel parameters" + +#: modules/commands/bs_kick.cpp:120 +msgid "option channel {ON|OFF} [settings]" +msgstr "option channel {ON|OFF} [settings]" + +#: modules/commands/ns_set.cpp:75 +msgid "option nickname parameters" +msgstr "option nickname parameters" + +#: modules/commands/ms_set.cpp:207 modules/commands/ns_set.cpp:20 +msgid "option parameters" +msgstr "option parameters" + +#: modules/commands/os_set.cpp:170 +msgid "option setting" +msgstr "option setting" + +#: modules/commands/ns_register.cpp:22 +msgid "passcode" +msgstr "passcode" + +#: modules/commands/os_login.cpp:19 +msgid "password" +msgstr "password" + +#: modules/commands/ns_register.cpp:124 +msgid "password [email]" +msgstr "password [email]" + +#: modules/commands/ns_register.cpp:122 +msgid "password email" +msgstr "password email" + +#: modules/commands/cs_list.cpp:21 +msgid "pattern [SUSPENDED] [NOEXPIRE]" +msgstr "pattern [SUSPENDED] [NOEXPIRE]" + +#: modules/commands/ns_list.cpp:20 +msgid "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" +msgstr "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/os_jupe.cpp:20 +msgid "server [reason]" +msgstr "server [reason]" + +#: modules/commands/os_mode.cpp:147 +msgid "user modes" +msgstr "user modes" + +#: modules/commands/os_kill.cpp:20 +msgid "user [reason]" +msgstr "user [reason]" + +#: modules/commands/os_sxline.cpp:440 +msgid "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." +msgstr "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." + +#: modules/commands/os_sxline.cpp:678 +msgid "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." + +#: modules/pseudoclients/nickserv.cpp:492 +#, c-format +msgid "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." +msgstr "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." + +#: modules/pseudoclients/botserv.cpp:143 +msgid "" +" \n" +"Available commands are:" +msgstr "" +" \n" +"Available commands are:" + +#: modules/pseudoclients/botserv.cpp:167 +#, c-format +msgid "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." +msgstr "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." + +#: modules/fantasy.cpp:69 +#, c-format +msgid "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." +msgstr "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." + +#: modules/commands/greet.cpp:69 +msgid "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." +msgstr "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." + +#: modules/commands/bs_kick.cpp:843 +msgid "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." + +#: modules/commands/bs_kick.cpp:908 +msgid "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." + +#: modules/pseudoclients/botserv.cpp:141 +#, c-format +msgid "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" +msgstr "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" + +#: modules/commands/cs_register.cpp:105 +msgid "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." +msgstr "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." + +#: modules/pseudoclients/chanserv.cpp:272 +#, c-format +msgid "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." +msgstr "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." + +#: modules/commands/cs_register.cpp:101 +#, c-format +msgid "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +msgstr "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" + +#: modules/pseudoclients/nickserv.cpp:486 +msgid "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." +msgstr "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." + +#: modules/pseudoclients/chanserv.cpp:277 +msgid "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." +msgstr "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." + +#: modules/commands/bs_set.cpp:147 +msgid "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." +msgstr "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." + +#: modules/commands/cs_xop.cpp:542 +#, c-format +msgid "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." +msgstr "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." + +#: modules/commands/cs_akick.cpp:508 +#, c-format +msgid "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." +msgstr "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." + +#: modules/commands/os_akill.cpp:448 +msgid "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." +msgstr "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." + +#: modules/commands/os_sxline.cpp:462 +msgid "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." +msgstr "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." + +#: modules/commands/os_sxline.cpp:697 +msgid "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." +msgstr "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." + +#: modules/commands/bs_assign.cpp:197 +msgid "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." +msgstr "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." + +#: modules/commands/bs_set.cpp:199 +msgid "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." +msgstr "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." + +#: modules/pseudoclients/memoserv.cpp:227 +#, c-format +msgid "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." +msgstr "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." + +#: modules/commands/os_oper.cpp:167 +#, c-format +msgid " %s is online using this oper block." +msgstr " %s is online using this oper block." + +#: modules/commands/os_modinfo.cpp:55 +#, c-format +msgid " Command %s on %s is linked to %s" +msgstr " Command %s on %s is linked to %s" + +#: modules/commands/os_modinfo.cpp:43 +#, c-format +msgid " Providing service: %s" +msgstr " Providing service: %s" + +#: modules/commands/os_oper.cpp:163 +msgid " This oper is configured in the configuration file." +msgstr " This oper is configured in the configuration file." + +#: modules/commands/os_modinfo.cpp:34 +#, c-format +msgid " Loaded at: %p" +msgstr " Loaded at: %p" + +#: modules/commands/cs_seen.cpp:303 +#, c-format +msgid " but %s mysteriously dematerialized." +msgstr " but %s mysteriously dematerialized." + +#: src/messages.cpp:339 +#, c-format +msgid "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." +msgstr "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." + +#: modules/commands/os_jupe.cpp:19 +msgid "\"Jupiter\" a server" +msgstr "\"Jupiter\" a server" + +#: modules/commands/os_oper.cpp:161 +#, c-format +msgid "%-8s %s" +msgstr "%-8s %s" + +#: modules/extra/stats/cs_fantasy_top.cpp:152 +#, c-format +msgid "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" + +#: src/misc.cpp:359 +msgid "%b %d %H:%M:%S %Y %Z" +msgstr "%b %d %H:%M:%S %Y %Z" + +#: modules/commands/cs_log.cpp:205 +#, c-format +msgid "%c is an unknown status mode." +msgstr "%c is an unknown status mode." + +#: modules/commands/cs_mode.cpp:431 +#, c-format +msgid "%c%c is not locked on %s." +msgstr "%c%c is not locked on %s." + +#: modules/commands/cs_mode.cpp:427 +#, c-format +msgid "%c%c%s has been unlocked from %s." +msgstr "%c%c%s has been unlocked from %s." + +#: modules/commands/cs_clone.cpp:56 +#, c-format +msgid "%d access entries from %s have been cloned to %s." +msgstr "%d access entries from %s have been cloned to %s." + +#: modules/commands/bs_botlist.cpp:56 +#, c-format +msgid "%d bots available." +msgstr "%d bots available." + +#: modules/commands/os_modinfo.cpp:189 +#, c-format +msgid "%d modules loaded." +msgstr "%d modules loaded." + +#: modules/commands/ns_group.cpp:357 +#, c-format +msgid "%d nickname(s) in the group." +msgstr "%d nickname(s) in the group." + +#: modules/commands/cs_seen.cpp:137 +#, c-format +msgid "%lu nicks are stored in the database, using %.2Lf kB of memory." +msgstr "%lu nicks are stored in the database, using %.2Lf kB of memory." + +#: modules/commands/cs_xop.cpp:241 modules/commands/cs_xop.cpp:372 +#: modules/commands/cs_xop.cpp:450 +#, c-format +msgid "%s %s list is empty." +msgstr "%s %s list is empty." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1181 +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1201 +#: modules/commands/bs_kick.cpp:1211 +#, c-format +msgid "%s (%d kick(s) to ban)" +msgstr "%s (%d kick(s) to ban)" + +#: modules/commands/bs_kick.cpp:1161 +#, c-format +msgid "%s (%d kick(s) to ban; %d lines in %ds)" +msgstr "%s (%d kick(s) to ban; %d lines in %ds)" + +#: modules/commands/bs_kick.cpp:1171 +#, c-format +msgid "%s (%d kick(s) to ban; %d times)" +msgstr "%s (%d kick(s) to ban; %d times)" + +#: modules/commands/bs_kick.cpp:1141 +#, c-format +msgid "%s (%d kick(s) to ban; minimum %d/%d%%)" +msgstr "%s (%d kick(s) to ban; minimum %d/%d%%)" + +#: modules/commands/bs_kick.cpp:1163 +#, c-format +msgid "%s (%d lines in %ds)" +msgstr "%s (%d lines in %ds)" + +#: modules/commands/bs_kick.cpp:1173 +#, c-format +msgid "%s (%d times)" +msgstr "%s (%d times)" + +#: modules/commands/cs_seen.cpp:358 +#, c-format +msgid "%s (%s) was kicked from %s (\"%s\") %s ago%s" +msgstr "%s (%s) was kicked from %s (\"%s\") %s ago%s" + +#: modules/commands/cs_seen.cpp:355 +#, c-format +msgid "%s (%s) was kicked from a secret channel %s ago%s" +msgstr "%s (%s) was kicked from a secret channel %s ago%s" + +#: modules/commands/cs_seen.cpp:326 +#, c-format +msgid "%s (%s) was last seen changing nick from %s to %s %s ago%s" +msgstr "%s (%s) was last seen changing nick from %s to %s %s ago%s" + +#: modules/commands/cs_seen.cpp:321 +#, c-format +msgid "%s (%s) was last seen changing nick to %s %s ago%s" +msgstr "%s (%s) was last seen changing nick to %s %s ago%s" + +#: modules/commands/cs_seen.cpp:310 +#, c-format +msgid "%s (%s) was last seen connecting %s ago (%s)%s" +msgstr "%s (%s) was last seen connecting %s ago (%s)%s" + +#: modules/commands/cs_seen.cpp:335 +#, c-format +msgid "%s (%s) was last seen joining %s %s ago%s" +msgstr "%s (%s) was last seen joining %s %s ago%s" + +#: modules/commands/cs_seen.cpp:332 +#, c-format +msgid "%s (%s) was last seen joining a secret channel %s ago%s" +msgstr "%s (%s) was last seen joining a secret channel %s ago%s" + +#: modules/commands/cs_seen.cpp:344 +#, c-format +msgid "%s (%s) was last seen parting %s %s ago%s" +msgstr "%s (%s) was last seen parting %s %s ago%s" + +#: modules/commands/cs_seen.cpp:341 +#, c-format +msgid "%s (%s) was last seen parting a secret channel %s ago%s" +msgstr "%s (%s) was last seen parting a secret channel %s ago%s" + +#: modules/commands/cs_seen.cpp:349 +#, c-format +msgid "%s (%s) was last seen quitting (%s) %s ago (%s)." +msgstr "%s (%s) was last seen quitting (%s) %s ago (%s)." + +#: modules/commands/bs_kick.cpp:1143 +#, c-format +msgid "%s (minimum %d/%d%%)" +msgstr "%s (minimum %d/%d%%)" + +#: modules/commands/cs_access.cpp:245 modules/commands/cs_access.cpp:349 +#: modules/commands/cs_access.cpp:454 modules/commands/cs_access.cpp:467 +#: modules/commands/cs_flags.cpp:295 +#, c-format +msgid "%s access list is empty." +msgstr "%s access list is empty." + +#: modules/commands/ns_ajoin.cpp:184 +#, c-format +msgid "%s added to %s's auto join list." +msgstr "%s added to %s's auto join list." + +#: src/xline.cpp:389 +#, c-format +msgid "%s already exists." +msgstr "%s already exists." + +#: modules/commands/cs_akick.cpp:202 modules/commands/cs_akick.cpp:387 +#: modules/commands/cs_akick.cpp:400 +#, c-format +msgid "%s autokick list is empty." +msgstr "%s autokick list is empty." + +#: modules/commands/bs_badwords.cpp:198 modules/commands/bs_badwords.cpp:316 +#, c-format +msgid "%s bad words list is empty." +msgstr "%s bad words list is empty." + +#: modules/commands/cs_set.cpp:993 +#, c-format +msgid "%s cannot be the successor on channel %s as they are the founder." +msgstr "%s cannot be the successor on channel %s as they are the founder." + +#: modules/pseudoclients/global.cpp:90 modules/pseudoclients/hostserv.cpp:78 +#: modules/pseudoclients/operserv.cpp:287 +#, c-format +msgid "%s commands:" +msgstr "%s commands:" + +#: include/language.h:69 +#, c-format +msgid "%s coverage is too wide; Please use a more specific mask." +msgstr "%s coverage is too wide; Please use a more specific mask." + +#: modules/commands/ms_info.cpp:94 +#, c-format +msgid "%s currently has %d memos, of which %d are unread." +msgstr "%s currently has %d memos, of which %d are unread." + +#: modules/commands/ms_info.cpp:92 +#, c-format +msgid "%s currently has %d memos, of which 1 is unread." +msgstr "%s currently has %d memos, of which 1 is unread." + +#: modules/commands/ms_info.cpp:90 +#, c-format +msgid "%s currently has %d memos." +msgstr "%s currently has %d memos." + +#: modules/commands/ms_info.cpp:88 +#, c-format +msgid "%s currently has %d memos; all of them are unread." +msgstr "%s currently has %d memos; all of them are unread." + +#: modules/commands/ms_info.cpp:77 +#, c-format +msgid "%s currently has 1 memo, and it has not yet been read." +msgstr "%s currently has 1 memo, and it has not yet been read." + +#: modules/commands/ms_info.cpp:79 +#, c-format +msgid "%s currently has 1 memo." +msgstr "%s currently has 1 memo." + +#: modules/commands/ms_info.cpp:73 +#, c-format +msgid "%s currently has no memos." +msgstr "%s currently has no memos." + +#: modules/commands/os_forbid.cpp:344 +#, c-format +msgid "%s deleted from the %s forbid list." +msgstr "%s deleted from the %s forbid list." + +#: include/language.h:105 +#, c-format +msgid "%s for %s set to %s." +msgstr "%s for %s set to %s." + +#: include/language.h:106 +#, c-format +msgid "%s for %s unset." +msgstr "%s for %s unset." + +#: modules/commands/ns_ajoin.cpp:176 +#, c-format +msgid "%s had an invalid key specified, and was thus ignored." +msgstr "%s had an invalid key specified, and was thus ignored." + +#: modules/commands/ms_info.cpp:111 +#, c-format +msgid "%s has no memo limit." +msgstr "%s has no memo limit." + +#: include/language.h:115 +#, c-format +msgid "%s has no memos." +msgstr "%s has no memos." + +#: include/language.h:118 +#, c-format +msgid "%s has no new memos." +msgstr "%s has no new memos." + +#: modules/commands/ns_info.cpp:53 +#, c-format +msgid "%s is %s" +msgstr "%s is %s" + +#: modules/commands/ns_info.cpp:59 +#, c-format +msgid "%s is a Services Operator of type %s." +msgstr "%s is a Services Operator of type %s." + +#: modules/commands/cs_seen.cpp:281 +#, c-format +msgid "%s is a client on services." +msgstr "%s is a client on services." + +#: modules/commands/cs_seen.cpp:200 +#, c-format +msgid "%s is a network service." +msgstr "%s is a network service." + +#: src/xline.cpp:407 +#, c-format +msgid "%s is already covered by %s." +msgstr "%s is already covered by %s." + +#: modules/commands/ns_ajoin.cpp:170 +#, c-format +msgid "%s is already on %s's auto join list." +msgstr "%s is already on %s's auto join list." + +#: modules/commands/ns_info.cpp:56 +#, c-format +msgid "%s is an unconfirmed nickname." +msgstr "%s is an unconfirmed nickname." + +#: modules/commands/cs_flags.cpp:432 +#, c-format +msgid "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." +msgstr "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." + +#: modules/commands/ns_info.cpp:74 +#, c-format +msgid "%s is currently online." +msgstr "%s is currently online." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is disabled" +msgstr "%s is disabled" + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is enabled" +msgstr "%s is enabled" + +#: modules/commands/os_dns.cpp:507 +#, c-format +msgid "%s is not a valid IP address." +msgstr "%s is not a valid IP address." + +#: modules/commands/cs_log.cpp:167 modules/commands/cs_log.cpp:192 +#, c-format +msgid "%s is not a valid command." +msgstr "%s is not a valid command." + +#: modules/commands/cs_log.cpp:198 +#, c-format +msgid "%s is not a valid logging method." +msgstr "%s is not a valid logging method." + +#: modules/commands/ms_info.cpp:124 +#, c-format +msgid "%s is not notified of new memos." +msgstr "%s is not notified of new memos." + +#: modules/commands/ms_info.cpp:118 +#, c-format +msgid "%s is notified of new memos at logon and when they arrive." +msgstr "%s is notified of new memos at logon and when they arrive." + +#: modules/commands/ms_info.cpp:122 +#, c-format +msgid "%s is notified of new memos at logon." +msgstr "%s is notified of new memos at logon." + +#: modules/commands/ms_info.cpp:120 +#, c-format +msgid "%s is notified when new memos arrive." +msgstr "%s is notified when new memos arrive." + +#: modules/commands/cs_seen.cpp:232 +#, c-format +msgid "%s is on the channel right now (as %s)!" +msgstr "%s is on the channel right now (as %s)!" + +#: modules/commands/cs_seen.cpp:221 +#, c-format +msgid "%s is on the channel right now!" +msgstr "%s is on the channel right now!" + +#: modules/commands/cs_xop.cpp:434 +#, c-format +msgid "%s list for %s" +msgstr "%s list for %s" + +#: modules/commands/os_sxline.cpp:69 modules/commands/os_sxline.cpp:113 +#, c-format +msgid "%s list is empty." +msgstr "%s list is empty." + +#: modules/commands/cs_mode.cpp:376 +#, c-format +msgid "%s locked on %s." +msgstr "%s locked on %s." + +#: modules/extra/stats/cs_fantasy_stats.cpp:120 +#, c-format +msgid "%s not found." +msgstr "%s not found." + +#: modules/commands/os_config.cpp:79 +#, c-format +msgid "%s settings:" +msgstr "%s settings:" + +#: modules/commands/cs_seen.cpp:255 +#, c-format +msgid "%s was last seen here %s ago." +msgstr "%s was last seen here %s ago." + +#: modules/commands/ns_ajoin.cpp:213 +#, c-format +msgid "%s was not found on %s's auto join list." +msgstr "%s was not found on %s's auto join list." + +#: modules/commands/ns_ajoin.cpp:221 +#, c-format +msgid "%s was removed from %s's auto join list." +msgstr "%s was removed from %s's auto join list." + +#: modules/commands/ms_set.cpp:64 +#, c-format +msgid "%s will not send you any notification of memos." +msgstr "%s will not send you any notification of memos." + +#: modules/commands/ms_set.cpp:42 +#, c-format +msgid "%s will now notify you of memos when they are sent to you." +msgstr "%s will now notify you of memos when they are sent to you." + +#: modules/commands/ms_set.cpp:30 +#, c-format +msgid "" +"%s will now notify you of memos when you log on and when they are sent to " +"you." +msgstr "" +"%s will now notify you of memos when you log on and when they are sent to " +"you." + +#: modules/commands/ms_set.cpp:36 +#, c-format +msgid "%s will now notify you of memos when you log on or unset /AWAY." +msgstr "%s will now notify you of memos when you log on or unset /AWAY." + +#: modules/commands/bs_bot.cpp:89 +#, c-format +msgid "%s!%s@%s (%s) added to the bot list." +msgstr "%s!%s@%s (%s) added to the bot list." + +#: modules/commands/ns_access.cpp:83 +#, c-format +msgid "%s's access list is empty." +msgstr "%s's access list is empty." + +#: modules/commands/ns_ajoin.cpp:96 +#, c-format +msgid "%s's auto join list is empty." +msgstr "%s's auto join list is empty." + +#: modules/commands/ns_ajoin.cpp:111 +#, c-format +msgid "%s's auto join list:" +msgstr "%s's auto join list:" + +#: modules/commands/ns_cert.cpp:242 +#, c-format +msgid "%s's certificate list is empty." +msgstr "%s's certificate list is empty." + +#: modules/commands/ms_info.cpp:99 modules/commands/ms_info.cpp:106 +#, c-format +msgid "%s's memo limit is %d, and may not be changed." +msgstr "%s's memo limit is %d, and may not be changed." + +#: modules/commands/ms_info.cpp:101 modules/commands/ms_info.cpp:108 +#, c-format +msgid "%s's memo limit is %d." +msgstr "%s's memo limit is %d." + +#: src/misc.cpp:363 +#, c-format +msgid "(%s ago)" +msgstr "(%s ago)" + +#: src/misc.cpp:365 +#, c-format +msgid "(%s from now)" +msgstr "(%s from now)" + +#: modules/commands/os_dns.cpp:244 +msgid "(Split)" +msgstr "(Split)" + +#: modules/commands/os_info.cpp:268 +#, c-format +msgid "(by %s on %s) %s" +msgstr "(by %s on %s) %s" + +#: modules/commands/cs_access.cpp:710 +msgid "(disabled)" +msgstr "(disabled)" + +#: modules/commands/cs_access.cpp:712 +msgid "(founder only)" +msgstr "(founder only)" + +#: src/misc.cpp:367 +msgid "(now)" +msgstr "(now)" + +#: modules/commands/os_defcon.cpp:168 +msgid "* AKILL any new clients connecting" +msgstr "* AKILL any new clients connecting" + +#: modules/commands/os_defcon.cpp:158 +#, c-format +msgid "* Force channel modes (%s) to be set on all channels" +msgstr "* Force channel modes (%s) to be set on all channels" + +#: modules/commands/os_defcon.cpp:164 +msgid "* Ignore non-opers with a message" +msgstr "* Ignore non-opers with a message" + +#: modules/commands/os_defcon.cpp:162 +msgid "* Kill any new clients connecting" +msgstr "* Kill any new clients connecting" + +#: modules/commands/os_defcon.cpp:156 +msgid "* No mode lock changes" +msgstr "* No mode lock changes" + +#: modules/commands/os_defcon.cpp:152 +msgid "* No new channel registrations" +msgstr "* No new channel registrations" + +#: modules/commands/os_defcon.cpp:170 +msgid "* No new memos sent" +msgstr "* No new memos sent" + +#: modules/commands/os_defcon.cpp:154 +msgid "* No new nick registrations" +msgstr "* No new nick registrations" + +#: modules/commands/os_defcon.cpp:166 +msgid "* Silently ignore non-opers" +msgstr "* Silently ignore non-opers" + +#: modules/commands/os_defcon.cpp:160 +#, c-format +msgid "* Use the reduced session limit of %d" +msgstr "* Use the reduced session limit of %d" + +#: modules/commands/cs_seen.cpp:319 +#, c-format +msgid ", but %s mysteriously dematerialized." +msgstr ", but %s mysteriously dematerialized." + +#: modules/commands/cs_seen.cpp:317 +#, c-format +msgid ". %s is still online." +msgstr ". %s is still online." + +#: include/language.h:87 +msgid "" +msgstr "" + +#: modules/commands/ns_set.cpp:504 +#, c-format +msgid "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." +msgstr "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." + +#: modules/commands/ms_sendall.cpp:45 +msgid "A massmemo has been sent to all registered users." +msgstr "A massmemo has been sent to all registered users." + +#: modules/commands/hs_request.cpp:285 +msgid "" +"A memo informing the user will also be sent, which includes the reason for " +"the rejection if supplied." +msgstr "" +"A memo informing the user will also be sent, which includes the reason for " +"the rejection if supplied." + +#: modules/commands/hs_request.cpp:229 +msgid "A memo informing the user will also be sent." +msgstr "A memo informing the user will also be sent." + +#: modules/commands/ms_read.cpp:42 +#, c-format +msgid "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." +msgstr "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." + +#: include/language.h:123 +msgid "A vHost ident must be in the format of a valid ident." +msgstr "A vHost ident must be in the format of a valid ident." + +#: include/language.h:122 +msgid "A vHost must be in the format of a valid hostname." +msgstr "A vHost must be in the format of a valid hostname." + +#: modules/commands/os_ignore.cpp:342 +msgid "ADD expiry {nick|mask} [reason]" +msgstr "ADD expiry {nick|mask} [reason]" + +#: modules/commands/os_oper.cpp:70 +msgid "ADD oper type" +msgstr "ADD oper type" + +#: modules/commands/os_info.cpp:102 +msgid "ADD target info" +msgstr "ADD target info" + +#: modules/commands/os_news.cpp:278 +msgid "ADD text" +msgstr "ADD text" + +#: modules/commands/os_session.cpp:523 +msgid "ADD [+expiry] mask limit reason" +msgstr "ADD [+expiry] mask limit reason" + +#: modules/commands/ns_ajoin.cpp:231 +msgid "ADD [nickname] channel [key]" +msgstr "ADD [nickname] channel [key]" + +#: modules/commands/ns_access.cpp:102 +msgid "ADD [nickname] mask" +msgstr "ADD [nickname] mask" + +#: modules/commands/ns_cert.cpp:258 +msgid "ADD [nickname] [fingerprint]" +msgstr "ADD [nickname] [fingerprint]" + +#: modules/commands/os_sxline.cpp:659 modules/commands/os_akill.cpp:386 +msgid "ADD [+expiry] mask reason" +msgstr "ADD [+expiry] mask reason" + +#: modules/commands/os_sxline.cpp:425 +msgid "ADD [+expiry] mask:reason" +msgstr "ADD [+expiry] mask:reason" + +#: modules/commands/os_forbid.cpp:157 +msgid "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" +msgstr "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" + +#: modules/commands/os_dns.cpp:665 +msgid "ADDIP server.name ip" +msgstr "ADDIP server.name ip" + +#: modules/commands/os_dns.cpp:663 +msgid "ADDSERVER server.name [zone.name]" +msgstr "ADDSERVER server.name [zone.name]" + +#: modules/commands/os_dns.cpp:661 +msgid "ADDZONE zone.name" +msgstr "ADDZONE zone.name" + +#: modules/commands/cs_akick.cpp:38 +#, c-format +msgid "AKICK ENFORCE for %s complete; %d users were affected." +msgstr "AKICK ENFORCE for %s complete; %d users were affected." + +#: modules/commands/os_chankill.cpp:21 +msgid "AKILL all users on a specific channel" +msgstr "AKILL all users on a specific channel" + +#: modules/commands/os_akill.cpp:222 modules/commands/os_akill.cpp:339 +#: modules/commands/os_akill.cpp:353 +msgid "AKILL list is empty." +msgstr "AKILL list is empty." + +#: modules/commands/bs_kick.cpp:1211 modules/commands/bs_kick.cpp:1213 +#: modules/commands/bs_kick.cpp:1216 +msgid "AMSG kicker" +msgstr "AMSG kicker" + +#: modules/commands/ns_alist.cpp:48 +msgid "Access" +msgstr "Access" + +#: include/language.h:72 +msgid "Access denied." +msgstr "Access denied." + +#: modules/commands/cs_status.cpp:58 +#, c-format +msgid "Access for %s on %s:" +msgstr "Access for %s on %s:" + +#: include/language.h:107 +#, c-format +msgid "Access level must be between %d and %d inclusive." +msgstr "Access level must be between %d and %d inclusive." + +#: modules/commands/cs_access.cpp:108 +msgid "Access level must be non-zero." +msgstr "Access level must be non-zero." + +#: modules/commands/cs_access.cpp:694 +#, c-format +msgid "Access level settings for channel %s:" +msgstr "Access level settings for channel %s:" + +#: modules/commands/cs_access.cpp:734 +#, c-format +msgid "Access levels for %s reset to defaults." +msgstr "Access levels for %s reset to defaults." + +#: modules/commands/cs_access.cpp:439 modules/commands/ns_access.cpp:87 +#, c-format +msgid "Access list for %s:" +msgstr "Access list for %s:" + +#: modules/commands/help.cpp:166 +#, c-format +msgid "" +"Access to this command requires the permission %s to be present in your " +"opertype." +msgstr "" +"Access to this command requires the permission %s to be present in your " +"opertype." + +#: modules/commands/ns_cert.cpp:368 modules/commands/ns_cert.cpp:392 +#: modules/commands/ns_identify.cpp:94 +#, c-format +msgid "" +"Account %s has already reached the maximum number of simultaneous logins " +"(%u)." +msgstr "" +"Account %s has already reached the maximum number of simultaneous logins " +"(%u)." + +#: modules/commands/cs_set.cpp:683 +msgid "Activate security features" +msgstr "Activate security features" + +#: modules/commands/hs_request.cpp:227 +msgid "Activate the requested vHost for the given nick." +msgstr "Activate the requested vHost for the given nick." + +#: modules/commands/hs_on.cpp:55 +msgid "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." +msgstr "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." + +#: modules/commands/hs_on.cpp:19 +msgid "Activates your assigned vhost" +msgstr "Activates your assigned vhost" + +#: modules/commands/os_info.cpp:243 +msgid "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." +msgstr "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." + +#: modules/commands/os_dns.cpp:515 +#, c-format +msgid "Added IP %s to %s." +msgstr "Added IP %s to %s." + +#: modules/commands/os_forbid.cpp:239 +#, c-format +msgid "Added a forbid on %s of type %s to expire on %s." +msgstr "Added a forbid on %s of type %s to expire on %s." + +#: modules/commands/os_info.cpp:164 +#, c-format +msgid "Added info to %s." +msgstr "Added info to %s." + +#: modules/commands/os_news.cpp:34 +msgid "Added new logon news item." +msgstr "Added new logon news item." + +#: modules/commands/os_news.cpp:44 +msgid "Added new oper news item." +msgstr "Added new oper news item." + +#: modules/commands/os_news.cpp:54 +msgid "Added new random news item." +msgstr "Added new random news item." + +#: modules/commands/os_dns.cpp:395 +#, c-format +msgid "Added server %s." +msgstr "Added server %s." + +#: modules/commands/os_dns.cpp:300 +#, c-format +msgid "Added zone %s." +msgstr "Added zone %s." + +#: modules/commands/cs_entrymsg.cpp:257 +msgid "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." +msgstr "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." + +#: modules/commands/ns_register.cpp:104 +msgid "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." +msgstr "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." + +#: modules/pseudoclients/botserv.cpp:172 +#, c-format +msgid "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" +msgstr "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" + +#: modules/commands/os_noop.cpp:58 +#, c-format +msgid "All O:lines of %s have been reset." +msgstr "All O:lines of %s have been reset." + +#: modules/commands/cs_clone.cpp:71 +#, c-format +msgid "All akick entries from %s have been cloned to %s." +msgstr "All akick entries from %s have been cloned to %s." + +#: modules/commands/help.cpp:57 +#, c-format +msgid "All available commands for %s:" +msgstr "All available commands for %s:" + +#: modules/commands/cs_clone.cpp:96 +#, c-format +msgid "All badword entries from %s have been cloned to %s." +msgstr "All badword entries from %s have been cloned to %s." + +#: modules/commands/cs_clone.cpp:108 +#, c-format +msgid "All level entries from %s have been cloned into %s." +msgstr "All level entries from %s have been cloned into %s." + +#: modules/commands/os_news.cpp:38 +msgid "All logon news items deleted." +msgstr "All logon news items deleted." + +#: modules/commands/ms_del.cpp:115 +#, c-format +msgid "All memos for channel %s have been deleted." +msgstr "All memos for channel %s have been deleted." + +#: modules/commands/os_mode.cpp:61 +#, c-format +msgid "All modes cleared on %s." +msgstr "All modes cleared on %s." + +#: modules/commands/ns_register.cpp:258 modules/commands/ns_register.cpp:389 +msgid "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." +msgstr "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." + +#: modules/commands/ms_del.cpp:119 +msgid "All of your memos have been deleted." +msgstr "All of your memos have been deleted." + +#: modules/commands/os_news.cpp:48 +msgid "All oper news items deleted." +msgstr "All oper news items deleted." + +#: modules/commands/os_noop.cpp:41 +#, c-format +msgid "All operators from %s have been removed." +msgstr "All operators from %s have been removed." + +#: modules/commands/os_news.cpp:58 +msgid "All random news items deleted." +msgstr "All random news items deleted." + +#: modules/commands/cs_clone.cpp:211 +#, c-format +msgid "All settings from %s have been cloned to %s." +msgstr "All settings from %s have been cloned to %s." + +#: modules/commands/cs_sync.cpp:41 +#, c-format +msgid "All user modes on %s have been synced." +msgstr "All user modes on %s have been synced." + +#: modules/commands/hs_group.cpp:60 +#, c-format +msgid "All vhosts in the group %s have been set to %s." +msgstr "All vhosts in the group %s have been set to %s." + +#: modules/commands/hs_group.cpp:58 +#, c-format +msgid "All vhosts in the group %s have been set to %s@%s." +msgstr "All vhosts in the group %s have been set to %s@%s." + +#: src/access.cpp:40 +msgid "Allowed to (de)halfop him/herself" +msgstr "Allowed to (de)halfop him/herself" + +#: src/access.cpp:39 +msgid "Allowed to (de)halfop users" +msgstr "Allowed to (de)halfop users" + +#: src/access.cpp:48 +msgid "Allowed to (de)op him/herself" +msgstr "Allowed to (de)op him/herself" + +#: src/access.cpp:47 +msgid "Allowed to (de)op users" +msgstr "Allowed to (de)op users" + +#: src/access.cpp:50 +msgid "Allowed to (de)owner him/herself" +msgstr "Allowed to (de)owner him/herself" + +#: src/access.cpp:49 +msgid "Allowed to (de)owner users" +msgstr "Allowed to (de)owner users" + +#: src/access.cpp:52 +msgid "Allowed to (de)protect him/herself" +msgstr "Allowed to (de)protect him/herself" + +#: src/access.cpp:51 +msgid "Allowed to (de)protect users" +msgstr "Allowed to (de)protect users" + +#: src/access.cpp:59 +msgid "Allowed to (de)voice him/herself" +msgstr "Allowed to (de)voice him/herself" + +#: src/access.cpp:58 +msgid "Allowed to (de)voice users" +msgstr "Allowed to (de)voice users" + +#: src/access.cpp:27 +msgid "Allowed to assign/unassign a bot" +msgstr "Allowed to assign/unassign a bot" + +#: src/access.cpp:34 +msgid "Allowed to ban users" +msgstr "Allowed to ban users" + +#: src/access.cpp:56 +msgid "Allowed to change channel topics" +msgstr "Allowed to change channel topics" + +#: src/access.cpp:41 +msgid "Allowed to get full INFO output" +msgstr "Allowed to get full INFO output" + +#: src/access.cpp:36 +msgid "Allowed to issue commands restricted to channel founders" +msgstr "Allowed to issue commands restricted to channel founders" + +#: src/access.cpp:33 +msgid "Allowed to modify channel badwords list" +msgstr "Allowed to modify channel badwords list" + +#: src/access.cpp:24 +msgid "Allowed to modify the access list" +msgstr "Allowed to modify the access list" + +#: src/access.cpp:44 +msgid "Allowed to read channel memos" +msgstr "Allowed to read channel memos" + +#: src/access.cpp:54 +msgid "Allowed to set channel settings" +msgstr "Allowed to set channel settings" + +#: src/access.cpp:57 +msgid "Allowed to unban users" +msgstr "Allowed to unban users" + +#: src/access.cpp:37 +msgid "Allowed to use GETKEY command" +msgstr "Allowed to use GETKEY command" + +#: src/access.cpp:53 +msgid "Allowed to use SAY and ACT commands" +msgstr "Allowed to use SAY and ACT commands" + +#: src/access.cpp:35 +msgid "Allowed to use fantasy commands" +msgstr "Allowed to use fantasy commands" + +#: src/access.cpp:26 +msgid "Allowed to use the AKICK command" +msgstr "Allowed to use the AKICK command" + +#: src/access.cpp:42 +msgid "Allowed to use the INVITE command" +msgstr "Allowed to use the INVITE command" + +#: src/access.cpp:43 +msgid "Allowed to use the KICK command" +msgstr "Allowed to use the KICK command" + +#: src/access.cpp:45 +msgid "Allowed to use the MODE command" +msgstr "Allowed to use the MODE command" + +#: src/access.cpp:25 +msgid "Allowed to view the access list" +msgstr "Allowed to view the access list" + +#: modules/commands/gl_global.cpp:42 +#, c-format +msgid "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." +msgstr "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." + +#: modules/commands/os_mode.cpp:133 +msgid "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." +msgstr "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." + +#: modules/commands/os_mode.cpp:173 +msgid "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." +msgstr "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." + +#: modules/commands/bs_bot.cpp:352 +msgid "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." +msgstr "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." + +#: modules/commands/os_oline.cpp:56 +msgid "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." +msgstr "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." + +#: modules/commands/os_ignore.cpp:370 +msgid "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." +msgstr "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." + +#: modules/commands/os_akill.cpp:420 +msgid "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." + +#: modules/commands/os_sxline.cpp:436 +msgid "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." +msgstr "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." + +#: modules/commands/os_sxline.cpp:670 +msgid "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." +msgstr "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." + +#: modules/commands/os_session.cpp:551 +msgid "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." +msgstr "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." + +#: modules/commands/os_session.cpp:270 +msgid "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." +msgstr "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." + +#: modules/commands/cs_topic.cpp:193 +msgid "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do " +"not have\n" +"the TOPIC privilege." +msgstr "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do " +"not have\n" +"the TOPIC privilege." + +#: modules/commands/os_kick.cpp:62 +#, c-format +msgid "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" +msgstr "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" + +#: modules/commands/cs_set.cpp:33 +msgid "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" +msgstr "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" + +#: modules/commands/os_oper.cpp:250 +msgid "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." +msgstr "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." + +#: modules/commands/os_config.cpp:127 +msgid "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" +msgstr "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" + +#: modules/commands/ns_set.cpp:992 +msgid "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." +msgstr "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." + +#: modules/commands/ns_set.cpp:966 +#, c-format +msgid "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." +msgstr "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." + +#: modules/commands/ms_ignore.cpp:113 +msgid "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." +msgstr "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." + +#: modules/commands/os_kill.cpp:48 +msgid "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." +msgstr "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." + +#: modules/commands/ns_info.cpp:252 +#, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." + +#: modules/commands/ns_info.cpp:223 +#, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." + +#: modules/commands/bs_info.cpp:118 +#, c-format +msgid "Allows you to see %s information about a channel or a bot" +msgstr "Allows you to see %s information about a channel or a bot" + +#: modules/commands/bs_info.cpp:108 +#, c-format +msgid "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." +msgstr "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." + +#: modules/commands/cs_xop.cpp:567 +msgid "" +"Alternative methods of modifying channel access lists are\n" +"available. " +msgstr "" +"Alternative methods of modifying channel access lists are\n" +"available. " + +#: modules/commands/hs_request.cpp:191 +msgid "Approve the requested vHost of a user" +msgstr "Approve the requested vHost of a user" + +#: modules/commands/ns_drop.cpp:68 +msgid "As a Services Operator, you may drop any nick." +msgstr "As a Services Operator, you may drop any nick." + +#: modules/commands/bs_assign.cpp:19 +msgid "Assigns a bot to a channel" +msgstr "Assigns a bot to a channel" + +#: modules/commands/bs_assign.cpp:78 +msgid "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." +msgstr "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." + +#: data/chanserv.example.conf:1197 +msgid "Associate a URL with the channel" +msgstr "Associate a URL with the channel" + +#: data/nickserv.example.conf:594 +msgid "Associate a URL with this account" +msgstr "Associate a URL with this account" + +#: data/nickserv.example.conf:593 +msgid "Associate a URL with your account" +msgstr "Associate a URL with your account" + +#: modules/commands/greet.cpp:83 +msgid "Associate a greet message with your nickname" +msgstr "Associate a greet message with your nickname" + +#: data/chanserv.example.conf:1198 +msgid "Associate an E-mail address with the channel" +msgstr "Associate an E-mail address with the channel" + +#: modules/commands/ns_set.cpp:452 +msgid "Associate an E-mail address with your nickname" +msgstr "Associate an E-mail address with your nickname" + +#: modules/commands/os_info.cpp:101 +msgid "Associate oper info with a nick or channel" +msgstr "Associate oper info with a nick or channel" + +#: modules/commands/ns_set.cpp:558 +msgid "Associates the given E-mail address with the nickname." +msgstr "Associates the given E-mail address with the nickname." + +#: modules/commands/ns_set.cpp:533 +msgid "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." +msgstr "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." + +#: modules/commands/ns_set.cpp:1315 +msgid "Auto-op" +msgstr "Auto-op" + +#: modules/commands/cs_akick.cpp:374 +#, c-format +msgid "Autokick list for %s:" +msgstr "Autokick list for %s:" + +#: src/access.cpp:29 +msgid "Automatic channel operator status upon join" +msgstr "Automatic channel operator status upon join" + +#: src/access.cpp:28 +msgid "Automatic halfop upon join" +msgstr "Automatic halfop upon join" + +#: src/access.cpp:30 +msgid "Automatic owner upon join" +msgstr "Automatic owner upon join" + +#: src/access.cpp:31 +msgid "Automatic protect upon join" +msgstr "Automatic protect upon join" + +#: src/access.cpp:32 +msgid "Automatic voice on join" +msgstr "Automatic voice on join" + +#: modules/commands/os_oper.cpp:196 +#, c-format +msgid "Available commands for %s:" +msgstr "Available commands for %s:" + +#: modules/commands/os_oper.cpp:175 +msgid "Available opertypes:" +msgstr "Available opertypes:" + +#: modules/commands/os_oper.cpp:218 +#, c-format +msgid "Available privileges for %s:" +msgstr "Available privileges for %s:" + +#: modules/commands/cs_enforce.cpp:162 +msgid "BANS enforced by " +msgstr "BANS enforced by " + +#: modules/commands/bs_kick.cpp:1121 modules/commands/bs_kick.cpp:1123 +#: modules/commands/bs_kick.cpp:1126 +msgid "Bad words kicker" +msgstr "Bad words kicker" + +#: modules/commands/bs_badwords.cpp:252 +#, c-format +msgid "Bad words list for %s:" +msgstr "Bad words list for %s:" + +#: modules/commands/bs_badwords.cpp:364 +msgid "Bad words list is now empty." +msgstr "Bad words list is now empty." + +#: modules/commands/bs_set.cpp:129 +msgid "Ban expiry may not be longer than 1 day." +msgstr "Ban expiry may not be longer than 1 day." + +#: modules/commands/cs_ban.cpp:140 modules/commands/cs_ban.cpp:175 +#, c-format +msgid "Ban on %s expires in %s." +msgstr "Ban on %s expires in %s." + +#: modules/commands/cs_info.cpp:60 +msgid "Ban type" +msgstr "Ban type" + +#: modules/commands/cs_set.cpp:174 +#, c-format +msgid "Ban type for channel %s is now #%d." +msgstr "Ban type for channel %s is now #%d." + +#: modules/commands/cs_ban.cpp:39 +msgid "Bans a given nick or mask on a channel" +msgstr "Bans a given nick or mask on a channel" + +#: modules/commands/cs_ban.cpp:227 +msgid "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." +msgstr "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." + +#: modules/commands/cs_enforce.cpp:166 +#, c-format +msgid "Bans enforced on %s." +msgstr "Bans enforced on %s." + +#: modules/commands/bs_kick.cpp:1131 modules/commands/bs_kick.cpp:1133 +#: modules/commands/bs_kick.cpp:1136 +msgid "Bolds kicker" +msgstr "Bolds kicker" + +#: modules/commands/bs_bot.cpp:26 modules/commands/bs_bot.cpp:175 +#, c-format +msgid "Bot %s already exists." +msgstr "Bot %s already exists." + +#: include/language.h:119 +#, c-format +msgid "Bot %s does not exist." +msgstr "Bot %s does not exist." + +#: modules/commands/bs_assign.cpp:71 modules/commands/bs_assign.cpp:246 +#, c-format +msgid "Bot %s has been assigned to %s." +msgstr "Bot %s has been assigned to %s." + +#: modules/commands/bs_bot.cpp:228 +#, c-format +msgid "Bot %s has been changed to %s!%s@%s (%s)." +msgstr "Bot %s has been changed to %s!%s@%s (%s)." + +#: modules/commands/bs_bot.cpp:262 +#, c-format +msgid "Bot %s has been deleted." +msgstr "Bot %s has been deleted." + +#: modules/commands/bs_assign.cpp:63 modules/commands/bs_assign.cpp:241 +#, c-format +msgid "Bot %s is already assigned to channel %s." +msgstr "Bot %s is already assigned to channel %s." + +#: modules/commands/bs_kick.cpp:832 +#, c-format +msgid "Bot will kick ops on channel %s." +msgstr "Bot will kick ops on channel %s." + +#: modules/commands/bs_kick.cpp:897 +#, c-format +msgid "Bot will kick voices on channel %s." +msgstr "Bot will kick voices on channel %s." + +#: modules/commands/bs_kick.cpp:824 +#, c-format +msgid "Bot won't kick ops on channel %s." +msgstr "Bot won't kick ops on channel %s." + +#: modules/commands/bs_kick.cpp:889 +#, c-format +msgid "Bot won't kick voices on channel %s." +msgstr "Bot won't kick voices on channel %s." + +#: modules/commands/bs_bot.cpp:118 +#, c-format +msgid "Bot %s is not changeable." +msgstr "Bot %s is not changeable." + +#: modules/commands/bs_bot.cpp:254 +#, c-format +msgid "Bot %s is not deletable." +msgstr "Bot %s is not deletable." + +#: modules/commands/bs_set.cpp:141 +#, c-format +msgid "Bot bans will automatically expire after %s." +msgstr "Bot bans will automatically expire after %s." + +#: modules/commands/bs_set.cpp:139 +msgid "Bot bans will no longer automatically expire." +msgstr "Bot bans will no longer automatically expire." + +#: modules/commands/bs_bot.cpp:46 modules/commands/bs_bot.cpp:138 +#, c-format +msgid "Bot hosts may only be %d characters long." +msgstr "Bot hosts may only be %d characters long." + +#: modules/commands/bs_bot.cpp:64 modules/commands/bs_bot.cpp:167 +msgid "Bot hosts may only contain valid host characters." +msgstr "Bot hosts may only contain valid host characters." + +#: modules/commands/bs_bot.cpp:40 modules/commands/bs_bot.cpp:132 +#, c-format +msgid "Bot idents may only be %d characters long." +msgstr "Bot idents may only be %d characters long." + +#: modules/commands/bs_bot.cpp:58 modules/commands/bs_bot.cpp:161 +msgid "Bot idents may only contain valid ident characters." +msgstr "Bot idents may only contain valid ident characters." + +#: include/language.h:121 +#, c-format +msgid "Bot is not on channel %s." +msgstr "Bot is not on channel %s." + +#: modules/commands/bs_botlist.cpp:51 +msgid "Bot list:" +msgstr "Bot list:" + +#: modules/commands/bs_info.cpp:87 +msgid "Bot nick" +msgstr "Bot nick" + +#: modules/commands/bs_bot.cpp:34 modules/commands/bs_bot.cpp:126 +#, c-format +msgid "Bot nicks may only be %d characters long." +msgstr "Bot nicks may only be %d characters long." + +#: modules/commands/bs_bot.cpp:52 modules/commands/bs_bot.cpp:155 +msgid "Bot nicks may only contain valid nick characters." +msgstr "Bot nicks may only contain valid nick characters." + +#: modules/commands/bs_kick.cpp:225 +#, c-format +msgid "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." +msgstr "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." + +#: modules/commands/bs_kick.cpp:228 +#, c-format +msgid "Bot will now kick for %s." +msgstr "Bot will now kick for %s." + +#: modules/commands/bs_kick.cpp:416 +#, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." +msgstr "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." + +#: modules/commands/bs_kick.cpp:420 +#, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." +msgstr "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." + +#: modules/commands/bs_kick.cpp:551 +#, c-format +msgid "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." +msgstr "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." + +#: modules/commands/bs_kick.cpp:554 +#, c-format +msgid "Bot will now kick for flood (%d lines in %d seconds)." +msgstr "Bot will now kick for flood (%d lines in %d seconds)." + +#: modules/commands/bs_kick.cpp:677 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." + +#: modules/commands/bs_kick.cpp:687 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." +msgstr "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." + +#: modules/commands/bs_kick.cpp:673 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." + +#: modules/commands/bs_kick.cpp:684 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." +msgstr "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." + +#: modules/commands/bs_kick.cpp:239 +#, c-format +msgid "Bot won't kick for %s anymore." +msgstr "Bot won't kick for %s anymore." + +#: modules/commands/bs_kick.cpp:426 +msgid "Bot won't kick for caps anymore." +msgstr "Bot won't kick for caps anymore." + +#: modules/commands/bs_kick.cpp:559 +msgid "Bot won't kick for flood anymore." +msgstr "Bot won't kick for flood anymore." + +#: modules/commands/bs_kick.cpp:694 +msgid "Bot won't kick for repeats anymore." +msgstr "Bot won't kick for repeats anymore." + +#: modules/commands/cs_access.cpp:472 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_session.cpp:514 +msgid "By" +msgstr "By" + +#: modules/commands/os_info.cpp:104 +msgid "CLEAR target" +msgstr "CLEAR target" + +#: modules/commands/cs_seen.cpp:119 +msgid "CLEAR time" +msgstr "CLEAR time" + +#: modules/commands/ms_cancel.cpp:19 +msgid "Cancel the last memo you sent" +msgstr "Cancel the last memo you sent" + +#: modules/commands/cs_drop.cpp:19 +msgid "Cancel the registration of a channel" +msgstr "Cancel the registration of a channel" + +#: modules/commands/ns_drop.cpp:20 +msgid "Cancel the registration of a nickname" +msgstr "Cancel the registration of a nickname" + +#: modules/commands/ms_cancel.cpp:84 +msgid "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." +msgstr "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." + +#: modules/commands/cs_clone.cpp:149 +#, c-format +msgid "Cannot clone channel %s to itself!" +msgstr "Cannot clone channel %s to itself!" + +#: modules/commands/ns_register.cpp:332 +msgid "Cannot send mail now; please retry a little later." +msgstr "Cannot send mail now; please retry a little later." + +#: modules/commands/bs_kick.cpp:1141 modules/commands/bs_kick.cpp:1143 +#: modules/commands/bs_kick.cpp:1146 +msgid "Caps kicker" +msgstr "Caps kicker" + +#: modules/commands/os_shutdown.cpp:34 +msgid "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." +msgstr "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." + +#: modules/commands/os_reload.cpp:47 +msgid "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." +msgstr "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." + +#: modules/commands/os_shutdown.cpp:62 +msgid "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." +msgstr "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." + +#: modules/commands/os_shutdown.cpp:89 +msgid "Causes Services to save all databases and then shut down." +msgstr "Causes Services to save all databases and then shut down." + +#: modules/commands/os_update.cpp:34 +msgid "" +"Causes Services to update all database files as soon as you\n" +"send the command." +msgstr "" +"Causes Services to update all database files as soon as you\n" +"send the command." + +#: modules/commands/ns_cert.cpp:246 +#, c-format +msgid "Certificate list for %s:" +msgstr "Certificate list for %s:" + +#: modules/commands/cs_set.cpp:528 modules/commands/cs_set.cpp:570 +msgid "ChanServ is required to enable persist on this network." +msgstr "ChanServ is required to enable persist on this network." + +#: modules/commands/os_mode.cpp:19 +msgid "Change channel modes" +msgstr "Change channel modes" + +#: modules/commands/ns_set.cpp:905 +msgid "Change the communication method of Services" +msgstr "Change the communication method of Services" + +#: modules/commands/os_mode.cpp:146 +msgid "Change user modes" +msgstr "Change user modes" + +#: modules/commands/os_mode.cpp:161 +#, c-format +msgid "Changed usermodes of %s to %s." +msgstr "Changed usermodes of %s to %s." + +#: modules/commands/ns_set.cpp:411 +msgid "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." +msgstr "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." + +#: modules/commands/ns_set.cpp:387 +msgid "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." +msgstr "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." + +#: modules/commands/cs_set.cpp:324 +msgid "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." +msgstr "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." + +#: modules/commands/ns_set.cpp:884 +msgid "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" + +#: modules/commands/ns_set.cpp:848 +msgid "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" + +#: modules/commands/ns_set.cpp:227 +msgid "Changes the password used to identify as the nick's owner." +msgstr "Changes the password used to identify as the nick's owner." + +#: modules/commands/ns_set.cpp:161 +msgid "" +"Changes the password used to identify you as the nick's\n" +"owner." +msgstr "" +"Changes the password used to identify you as the nick's\n" +"owner." + +#: modules/commands/cs_set.cpp:1017 +msgid "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." +msgstr "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." + +#: modules/commands/ns_alist.cpp:48 modules/commands/ns_ajoin.cpp:100 +msgid "Channel" +msgstr "Channel" + +#: include/language.h:84 +#, c-format +msgid "Channel %s doesn't exist." +msgstr "Channel %s doesn't exist." + +#: modules/commands/cs_drop.cpp:63 +#, c-format +msgid "Channel %s has been dropped." +msgstr "Channel %s has been dropped." + +#: modules/commands/cs_getkey.cpp:43 +#, c-format +msgid "Channel %s has no key." +msgstr "Channel %s has no key." + +#: modules/commands/cs_register.cpp:47 +#, c-format +msgid "Channel %s is already registered!" +msgstr "Channel %s is already registered!" + +#: modules/commands/os_forbid.cpp:524 +#, c-format +msgid "Channel %s is forbidden by %s: %s" +msgstr "Channel %s is forbidden by %s: %s" + +#: modules/commands/os_forbid.cpp:526 +#, c-format +msgid "Channel %s is forbidden." +msgstr "Channel %s is forbidden." + +#: modules/commands/cs_set.cpp:580 +#, c-format +msgid "Channel %s is no longer persistent." +msgstr "Channel %s is no longer persistent." + +#: modules/commands/cs_set.cpp:542 +#, c-format +msgid "Channel %s is now persistent." +msgstr "Channel %s is now persistent." + +#: modules/commands/cs_suspend.cpp:180 +#, c-format +msgid "Channel %s is now released." +msgstr "Channel %s is now released." + +#: modules/commands/cs_suspend.cpp:125 +#, c-format +msgid "Channel %s is now suspended." +msgstr "Channel %s is now suspended." + +#: include/language.h:83 +#, c-format +msgid "Channel %s isn't registered." +msgstr "Channel %s isn't registered." + +#: modules/commands/cs_suspend.cpp:172 +#, c-format +msgid "Channel %s isn't suspended." +msgstr "Channel %s isn't suspended." + +#: modules/commands/cs_register.cpp:68 +#, c-format +msgid "Channel %s registered under your account: %s" +msgstr "Channel %s registered under your account: %s" + +#: modules/commands/cs_set.cpp:1078 +#, c-format +msgid "Channel %s will expire." +msgstr "Channel %s will expire." + +#: modules/commands/cs_set.cpp:1072 +#, c-format +msgid "Channel %s will not expire." +msgstr "Channel %s will not expire." + +#: modules/commands/cs_xop.cpp:475 +#, c-format +msgid "Channel %s %s list has been cleared." +msgstr "Channel %s %s list has been cleared." + +#: modules/commands/cs_access.cpp:486 modules/commands/cs_flags.cpp:361 +#, c-format +msgid "Channel %s access list has been cleared." +msgstr "Channel %s access list has been cleared." + +#: modules/commands/cs_akick.cpp:428 +#, c-format +msgid "Channel %s akick list has been cleared." +msgstr "Channel %s akick list has been cleared." + +#: modules/commands/cs_mode.cpp:444 +#, c-format +msgid "Channel %s has no mode locks." +msgstr "Channel %s has no mode locks." + +#: include/language.h:82 +#, c-format +msgid "Channel %s is currently suspended." +msgstr "Channel %s is currently suspended." + +#: include/language.h:101 +#, c-format +msgid "Channel %s is not a valid channel." +msgstr "Channel %s is not a valid channel." + +#: modules/commands/os_list.cpp:70 +msgid "Channel list:" +msgstr "Channel list:" + +#: modules/extra/stats/cs_fantasy_stats.cpp:148 +#, c-format +msgid "Channel stats for %s on %s:" +msgstr "Channel stats for %s on %s:" + +#: modules/commands/cs_access.cpp:142 modules/commands/cs_flags.cpp:97 +#: modules/commands/cs_xop.cpp:139 +msgid "Channels may not be on access lists." +msgstr "Channels may not be on access lists." + +#: modules/commands/ns_alist.cpp:114 +#, c-format +msgid "Channels that %s has access on:" +msgstr "Channels that %s has access on:" + +#: modules/commands/os_stats.cpp:181 +#, c-format +msgid "Channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "Channels: %lu entries, %lu buckets, longest chain is %d" + +#: modules/extra/stats/m_chanstats.cpp:517 +#: modules/extra/stats/m_chanstats.cpp:525 +msgid "Chanstats" +msgstr "Chanstats" + +#: modules/extra/stats/m_chanstats.cpp:102 +#, c-format +msgid "Chanstats statistics are now disabled for %s" +msgstr "Chanstats statistics are now disabled for %s" + +#: modules/extra/stats/m_chanstats.cpp:51 +msgid "Chanstats statistics are now disabled for this channel." +msgstr "Chanstats statistics are now disabled for this channel." + +#: modules/extra/stats/m_chanstats.cpp:104 +msgid "Chanstats statistics are now disabled for your nick." +msgstr "Chanstats statistics are now disabled for your nick." + +#: modules/extra/stats/m_chanstats.cpp:93 +#, c-format +msgid "Chanstats statistics are now enabled for %s" +msgstr "Chanstats statistics are now enabled for %s" + +#: modules/extra/stats/m_chanstats.cpp:44 +msgid "Chanstats statistics are now enabled for this channel." +msgstr "Chanstats statistics are now enabled for this channel." + +#: modules/extra/stats/m_chanstats.cpp:95 +msgid "Chanstats statistics are now enabled for your nick." +msgstr "Chanstats statistics are now enabled for your nick." + +#: modules/commands/cs_seen.cpp:367 +msgid "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." +msgstr "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." + +#: modules/commands/ms_check.cpp:19 +msgid "Checks if last memo to a nick was read" +msgstr "Checks if last memo to a nick was read" + +#: modules/commands/ms_check.cpp:69 +msgid "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." +msgstr "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." + +#: modules/commands/os_info.cpp:227 +#, c-format +msgid "Cleared info from %s." +msgstr "Cleared info from %s." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1153 +#: modules/commands/bs_kick.cpp:1156 +msgid "Colors kicker" +msgstr "Colors kicker" + +#: modules/commands/cs_log.cpp:127 +msgid "Command" +msgstr "Command" + +#: modules/commands/bs_kick.cpp:251 +msgid "Configures AMSG kicker" +msgstr "Configures AMSG kicker" + +#: modules/commands/bs_kick.cpp:287 +msgid "Configures badwords kicker" +msgstr "Configures badwords kicker" + +#: modules/commands/bs_kick.cpp:326 +msgid "Configures bolds kicker" +msgstr "Configures bolds kicker" + +#: modules/commands/bs_kick.cpp:132 +msgid "Configures bot kickers. option can be one of:" +msgstr "Configures bot kickers. option can be one of:" + +#: modules/commands/bs_set.cpp:19 +msgid "Configures bot options" +msgstr "Configures bot options" + +#: modules/commands/bs_set.cpp:32 +msgid "" +"Configures bot options.\n" +" \n" +"Available options:" +msgstr "" +"Configures bot options.\n" +" \n" +"Available options:" + +#: modules/commands/bs_kick.cpp:360 +msgid "Configures caps kicker" +msgstr "Configures caps kicker" + +#: modules/commands/cs_log.cpp:105 +msgid "Configures channel logging settings" +msgstr "Configures channel logging settings" + +#: modules/commands/bs_kick.cpp:456 +msgid "Configures color kicker" +msgstr "Configures color kicker" + +#: modules/commands/bs_kick.cpp:490 +msgid "Configures flood kicker" +msgstr "Configures flood kicker" + +#: modules/commands/bs_kick.cpp:588 +msgid "Configures italics kicker" +msgstr "Configures italics kicker" + +#: modules/commands/bs_kick.cpp:119 +msgid "Configures kickers" +msgstr "Configures kickers" + +#: modules/commands/bs_kick.cpp:622 +msgid "Configures repeat kicker" +msgstr "Configures repeat kicker" + +#: modules/commands/bs_kick.cpp:723 +msgid "Configures reverses kicker" +msgstr "Configures reverses kicker" + +#: modules/commands/bs_set.cpp:90 +msgid "Configures the time bot bans expire in" +msgstr "Configures the time bot bans expire in" + +#: modules/commands/bs_kick.cpp:757 +msgid "Configures underlines kicker" +msgstr "Configures underlines kicker" + +#: modules/commands/ns_register.cpp:21 +msgid "Confirm a passcode" +msgstr "Confirm a passcode" + +#: modules/commands/cs_mode.cpp:733 +msgid "Control modes and mode locks on a channel" +msgstr "Control modes and mode locks on a channel" + +#: modules/commands/cs_entrymsg.cpp:239 +msgid "" +"Controls what messages will be sent to users when they join the channel." +msgstr "" +"Controls what messages will be sent to users when they join the channel." + +#: modules/commands/cs_clone.cpp:242 +msgid "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." +msgstr "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." + +#: modules/commands/cs_clone.cpp:114 +msgid "Copy all settings from one channel to another" +msgstr "Copy all settings from one channel to another" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/bs_info.cpp:57 +#: modules/commands/os_akill.cpp:358 +msgid "Created" +msgstr "Created" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_ignore.cpp:266 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_news.cpp:156 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_akill.cpp:358 +msgid "Creator" +msgstr "Creator" + +#: modules/commands/os_sxline.cpp:180 +#, c-format +msgid "Current %s list:" +msgstr "Current %s list:" + +#: modules/commands/os_akill.cpp:323 +msgid "Current AKILL list:" +msgstr "Current AKILL list:" + +#: modules/commands/os_session.cpp:493 +msgid "Current Session Limit Exception list:" +msgstr "Current Session Limit Exception list:" + +#: modules/commands/os_modinfo.cpp:116 +msgid "Current module list:" +msgstr "Current module list:" + +#: modules/commands/os_stats.cpp:69 +#, c-format +msgid "Current number of AKILLs: %d" +msgstr "Current number of AKILLs: %d" + +#: modules/commands/os_stats.cpp:89 +#, c-format +msgid "Current number of SNLINEs: %d" +msgstr "Current number of SNLINEs: %d" + +#: modules/commands/os_stats.cpp:109 +#, c-format +msgid "Current number of SQLINEs: %d" +msgstr "Current number of SQLINEs: %d" + +#: modules/commands/os_stats.cpp:138 +#, c-format +msgid "Current users: %d (%d ops)" +msgstr "Current users: %d (%d ops)" + +#: modules/commands/os_oper.cpp:71 +msgid "DEL oper" +msgstr "DEL oper" + +#: modules/commands/os_info.cpp:103 +msgid "DEL target info" +msgstr "DEL target info" + +#: modules/commands/ns_ajoin.cpp:232 +msgid "DEL [nickname] channel" +msgstr "DEL [nickname] channel" + +#: modules/commands/ns_cert.cpp:259 +msgid "DEL [nickname] fingerprint" +msgstr "DEL [nickname] fingerprint" + +#: modules/commands/ns_access.cpp:103 +msgid "DEL [nickname] mask" +msgstr "DEL [nickname] mask" + +#: modules/commands/os_sxline.cpp:426 modules/commands/os_sxline.cpp:660 +#: modules/commands/os_akill.cpp:387 +msgid "DEL {mask | entry-num | list | id}" +msgstr "DEL {mask | entry-num | list | id}" + +#: modules/commands/os_session.cpp:524 +msgid "DEL {mask | entry-num | list}" +msgstr "DEL {mask | entry-num | list}" + +#: modules/commands/os_ignore.cpp:343 +msgid "DEL {nick|mask}" +msgstr "DEL {nick|mask}" + +#: modules/commands/os_news.cpp:279 +msgid "DEL {num | ALL}" +msgstr "DEL {num | ALL}" + +#: modules/commands/os_forbid.cpp:158 +msgid "DEL {NICK|CHAN|EMAIL|REGISTER} entry" +msgstr "DEL {NICK|CHAN|EMAIL|REGISTER} entry" + +#: modules/commands/os_dns.cpp:666 +msgid "DELIP server.name ip" +msgstr "DELIP server.name ip" + +#: modules/commands/os_dns.cpp:664 +msgid "DELSERVER server.name [zone.name]" +msgstr "DELSERVER server.name [zone.name]" + +#: modules/commands/os_dns.cpp:662 +msgid "DELZONE zone.name" +msgstr "DELZONE zone.name" + +#: modules/commands/os_dns.cpp:669 +msgid "DEPOOL server.name" +msgstr "DEPOOL server.name" + +#: modules/commands/cs_seen.cpp:162 +#, c-format +msgid "Database cleared, removed %lu nicks that were added after %s." +msgstr "Database cleared, removed %lu nicks that were added after %s." + +#: modules/commands/ms_list.cpp:64 +msgid "Date/Time" +msgstr "Date/Time" + +#: modules/commands/hs_off.cpp:49 +msgid "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." +msgstr "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." + +#: modules/commands/hs_off.cpp:19 +msgid "Deactivates your assigned vhost" +msgstr "Deactivates your assigned vhost" + +#: modules/commands/os_stats.cpp:72 +#, c-format +msgid "Default AKILL expiry time: %d days" +msgstr "Default AKILL expiry time: %d days" + +#: modules/commands/os_stats.cpp:76 +#, c-format +msgid "Default AKILL expiry time: %d hours" +msgstr "Default AKILL expiry time: %d hours" + +#: modules/commands/os_stats.cpp:80 +#, c-format +msgid "Default AKILL expiry time: %d minutes" +msgstr "Default AKILL expiry time: %d minutes" + +#: modules/commands/os_stats.cpp:74 +msgid "Default AKILL expiry time: 1 day" +msgstr "Default AKILL expiry time: 1 day" + +#: modules/commands/os_stats.cpp:78 +msgid "Default AKILL expiry time: 1 hour" +msgstr "Default AKILL expiry time: 1 hour" + +#: modules/commands/os_stats.cpp:82 +msgid "Default AKILL expiry time: 1 minute" +msgstr "Default AKILL expiry time: 1 minute" + +#: modules/commands/os_stats.cpp:84 +msgid "Default AKILL expiry time: No expiration" +msgstr "Default AKILL expiry time: No expiration" + +#: modules/commands/os_stats.cpp:92 +#, c-format +msgid "Default SNLINE expiry time: %d days" +msgstr "Default SNLINE expiry time: %d days" + +#: modules/commands/os_stats.cpp:96 +#, c-format +msgid "Default SNLINE expiry time: %d hours" +msgstr "Default SNLINE expiry time: %d hours" + +#: modules/commands/os_stats.cpp:100 +#, c-format +msgid "Default SNLINE expiry time: %d minutes" +msgstr "Default SNLINE expiry time: %d minutes" + +#: modules/commands/os_stats.cpp:94 +msgid "Default SNLINE expiry time: 1 day" +msgstr "Default SNLINE expiry time: 1 day" + +#: modules/commands/os_stats.cpp:98 +msgid "Default SNLINE expiry time: 1 hour" +msgstr "Default SNLINE expiry time: 1 hour" + +#: modules/commands/os_stats.cpp:102 +msgid "Default SNLINE expiry time: 1 minute" +msgstr "Default SNLINE expiry time: 1 minute" + +#: modules/commands/os_stats.cpp:104 +msgid "Default SNLINE expiry time: No expiration" +msgstr "Default SNLINE expiry time: No expiration" + +#: modules/commands/os_stats.cpp:112 +#, c-format +msgid "Default SQLINE expiry time: %d days" +msgstr "Default SQLINE expiry time: %d days" + +#: modules/commands/os_stats.cpp:116 +#, c-format +msgid "Default SQLINE expiry time: %d hours" +msgstr "Default SQLINE expiry time: %d hours" + +#: modules/commands/os_stats.cpp:120 +#, c-format +msgid "Default SQLINE expiry time: %d minutes" +msgstr "Default SQLINE expiry time: %d minutes" + +#: modules/commands/os_stats.cpp:114 +msgid "Default SQLINE expiry time: 1 day" +msgstr "Default SQLINE expiry time: 1 day" + +#: modules/commands/os_stats.cpp:118 +msgid "Default SQLINE expiry time: 1 hour" +msgstr "Default SQLINE expiry time: 1 hour" + +#: modules/commands/os_stats.cpp:122 +msgid "Default SQLINE expiry time: 1 minute" +msgstr "Default SQLINE expiry time: 1 minute" + +#: modules/commands/os_stats.cpp:124 +msgid "Default SQLINE expiry time: No expiration" +msgstr "Default SQLINE expiry time: No expiration" + +#: modules/commands/os_news.cpp:351 +msgid "Define messages to be randomly shown to users at logon" +msgstr "Define messages to be randomly shown to users at logon" + +#: modules/commands/os_news.cpp:297 +msgid "Define messages to be shown to users at logon" +msgstr "Define messages to be shown to users at logon" + +#: modules/commands/os_news.cpp:324 +msgid "Define messages to be shown to users who oper" +msgstr "Define messages to be shown to users who oper" + +#: modules/commands/ms_del.cpp:44 +msgid "Delete a memo or memos" +msgstr "Delete a memo or memos" + +#: modules/commands/hs_del.cpp:19 +msgid "Delete the vhost of another user" +msgstr "Delete the vhost of another user" + +#: modules/commands/cs_xop.cpp:302 +#, c-format +msgid "Deleted %d entries from %s %s list." +msgstr "Deleted %d entries from %s %s list." + +#: modules/commands/cs_access.cpp:277 +#, c-format +msgid "Deleted %d entries from %s access list." +msgstr "Deleted %d entries from %s access list." + +#: modules/commands/cs_akick.cpp:228 +#, c-format +msgid "Deleted %d entries from %s autokick list." +msgstr "Deleted %d entries from %s autokick list." + +#: modules/commands/bs_badwords.cpp:170 +#, c-format +msgid "Deleted %d entries from %s bad words list." +msgstr "Deleted %d entries from %s bad words list." + +#: modules/commands/os_session.cpp:149 +#, c-format +msgid "Deleted %d entries from session-limit exception list." +msgstr "Deleted %d entries from session-limit exception list." + +#: modules/commands/os_sxline.cpp:32 +#, c-format +msgid "Deleted %d entries from the %s list." +msgstr "Deleted %d entries from the %s list." + +#: modules/commands/os_akill.cpp:33 +#, c-format +msgid "Deleted %d entries from the AKILL list." +msgstr "Deleted %d entries from the AKILL list." + +#: modules/commands/cs_access.cpp:275 +#, c-format +msgid "Deleted 1 entry from %s access list." +msgstr "Deleted 1 entry from %s access list." + +#: modules/commands/cs_akick.cpp:226 +#, c-format +msgid "Deleted 1 entry from %s autokick list." +msgstr "Deleted 1 entry from %s autokick list." + +#: modules/commands/bs_badwords.cpp:168 +#, c-format +msgid "Deleted 1 entry from %s bad words list." +msgstr "Deleted 1 entry from %s bad words list." + +#: modules/commands/os_session.cpp:147 +msgid "Deleted 1 entry from session-limit exception list." +msgstr "Deleted 1 entry from session-limit exception list." + +#: modules/commands/os_sxline.cpp:30 +#, c-format +msgid "Deleted 1 entry from the %s list." +msgstr "Deleted 1 entry from the %s list." + +#: modules/commands/os_akill.cpp:31 +msgid "Deleted 1 entry from the AKILL list." +msgstr "Deleted 1 entry from the AKILL list." + +#: modules/commands/os_info.cpp:208 +#, c-format +msgid "Deleted info from %s." +msgstr "Deleted info from %s." + +#: modules/commands/cs_xop.cpp:300 +#, c-format +msgid "Deleted one entry from %s %s list." +msgstr "Deleted one entry from %s %s list." + +#: modules/commands/ms_del.cpp:129 +msgid "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." + +#: modules/commands/hs_del.cpp:48 +msgid "" +"Deletes the vhost assigned to the given nick from the\n" +"database." +msgstr "" +"Deletes the vhost assigned to the given nick from the\n" +"database." + +#: modules/commands/hs_del.cpp:59 +msgid "Deletes the vhost for all nicks in a group" +msgstr "Deletes the vhost for all nicks in a group" + +#: modules/commands/hs_del.cpp:93 +msgid "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." +msgstr "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." + +#: modules/commands/os_dns.cpp:653 +#, c-format +msgid "Depooled %s." +msgstr "Depooled %s." + +#: modules/commands/cs_access.cpp:799 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_list.cpp:75 modules/commands/cs_info.cpp:53 +msgid "Description" +msgstr "Description" + +#: modules/commands/cs_set.cpp:239 +#, c-format +msgid "Description of %s changed to %s." +msgstr "Description of %s changed to %s." + +#: modules/commands/cs_set.cpp:245 +#, c-format +msgid "Description of %s unset." +msgstr "Description of %s unset." + +#: modules/commands/bs_kick.cpp:1115 modules/commands/bs_info.cpp:90 +msgid "Disabled" +msgstr "Disabled" + +#: modules/commands/cs_suspend.cpp:134 +msgid "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." +msgstr "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." + +#: modules/commands/hs_request.cpp:337 +#, c-format +msgid "Displayed %d records (%d total)." +msgstr "Displayed %d records (%d total)." + +#: modules/commands/hs_list.cpp:122 +#, c-format +msgid "Displayed all records (count: %d)." +msgstr "Displayed all records (count: %d)." + +#: modules/commands/hs_list.cpp:120 +#, c-format +msgid "Displayed records from %d to %d." +msgstr "Displayed records from %d to %d." + +#: modules/commands/hs_list.cpp:116 +#, c-format +msgid "Displayed records matching key %s (count: %d)." +msgstr "Displayed records matching key %s (count: %d)." + +#: modules/commands/ns_info.cpp:19 +msgid "Displays information about a given nickname" +msgstr "Displays information about a given nickname" + +#: modules/commands/ns_info.cpp:125 +msgid "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." +msgstr "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." + +#: modules/commands/ms_info.cpp:19 +msgid "Displays information about your memos" +msgstr "Displays information about your memos" + +#: modules/commands/hs_list.cpp:19 +msgid "Displays one or more vhost entries" +msgstr "Displays one or more vhost entries" + +#: modules/extra/stats/cs_fantasy_top.cpp:50 +msgid "Displays the top 10 users of a channel" +msgstr "Displays the top 10 users of a channel" + +#: modules/extra/stats/cs_fantasy_top.cpp:73 +msgid "Displays the top 10 users of the network" +msgstr "Displays the top 10 users of the network" + +#: modules/extra/stats/cs_fantasy_top.cpp:38 +msgid "Displays the top 3 users of a channel" +msgstr "Displays the top 3 users of a channel" + +#: modules/extra/stats/cs_fantasy_top.cpp:62 +msgid "Displays the top 3 users of the network" +msgstr "Displays the top 3 users of the network" + +#: modules/commands/help.cpp:33 +msgid "Displays this list and give information about commands" +msgstr "Displays this list and give information about commands" + +#: modules/extra/stats/cs_fantasy_stats.cpp:39 +msgid "Displays your Channel Stats" +msgstr "Displays your Channel Stats" + +#: modules/extra/stats/cs_fantasy_stats.cpp:51 +msgid "Displays your Global Stats" +msgstr "Displays your Global Stats" + +#: modules/commands/bs_kick.cpp:1463 +msgid "Don't use AMSGs!" +msgstr "Don't use AMSGs!" + +#: modules/commands/bs_kick.cpp:1266 +msgid "Don't use bolds on this channel!" +msgstr "Don't use bolds on this channel!" + +#: modules/commands/bs_kick.cpp:1274 +msgid "Don't use colors on this channel!" +msgstr "Don't use colors on this channel!" + +#: modules/commands/bs_kick.cpp:1290 +msgid "Don't use italics on this channel!" +msgstr "Don't use italics on this channel!" + +#: modules/commands/bs_kick.cpp:1282 +msgid "Don't use reverses on this channel!" +msgstr "Don't use reverses on this channel!" + +#: modules/commands/bs_kick.cpp:1408 +#, c-format +msgid "Don't use the word \"%s\" on this channel!" +msgstr "Don't use the word \"%s\" on this channel!" + +#: modules/commands/bs_kick.cpp:1298 +msgid "Don't use underlines on this channel!" +msgstr "Don't use underlines on this channel!" + +#: modules/commands/ns_drop.cpp:61 +msgid "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." +msgstr "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." + +#: modules/commands/ns_set.cpp:513 +#, c-format +msgid "E-mail address for %s changed to %s." +msgstr "E-mail address for %s changed to %s." + +#: modules/commands/ns_set.cpp:519 +#, c-format +msgid "E-mail address for %s unset." +msgstr "E-mail address for %s unset." + +#: src/mail.cpp:80 +#, c-format +msgid "E-mail for %s is invalid." +msgstr "E-mail for %s is invalid." + +#: modules/commands/os_news.cpp:309 +#, c-format +msgid "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." + +#: modules/commands/os_news.cpp:336 +#, c-format +msgid "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." + +#: modules/commands/os_news.cpp:363 +msgid "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." +msgstr "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." + +#: modules/commands/ns_info.cpp:98 +msgid "Email address" +msgstr "Email address" + +#: modules/commands/ns_getemail.cpp:41 +#, c-format +msgid "Email matched: %s (%s) to %s." +msgstr "Email matched: %s (%s) to %s." + +#: modules/fantasy.cpp:19 +msgid "Enable fantaisist commands" +msgstr "Enable fantaisist commands" + +#: modules/commands/greet.cpp:19 +msgid "Enable greet messages" +msgstr "Enable greet messages" + +#: modules/commands/ns_set.cpp:568 +msgid "Enable or disable keep modes" +msgstr "Enable or disable keep modes" + +#: modules/commands/bs_kick.cpp:1114 modules/commands/bs_info.cpp:89 +msgid "Enabled" +msgstr "Enabled" + +#: modules/commands/cs_set.cpp:124 +#, c-format +msgid "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." +msgstr "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." + +#: modules/commands/cs_set.cpp:388 +msgid "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." +msgstr "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." + +#: modules/commands/ns_set.cpp:643 +msgid "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." +msgstr "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." + +#: modules/commands/ns_set.cpp:618 +msgid "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." +msgstr "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." + +#: modules/commands/cs_set.cpp:733 +msgid "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." +msgstr "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." + +#: modules/commands/cs_set.cpp:932 +msgid "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." +msgstr "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." + +#: modules/commands/cs_set.cpp:452 +#, c-format +msgid "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." +msgstr "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." + +#: modules/commands/cs_list.cpp:232 +msgid "Enables or disables the private option for a channel." +msgstr "Enables or disables the private option for a channel." + +#: modules/commands/cs_set.cpp:671 +msgid "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." +msgstr "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." + +#: modules/commands/cs_set.cpp:796 +msgid "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." +msgstr "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." + +#: modules/commands/cs_set.cpp:860 +msgid "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." +msgstr "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." + +#: modules/commands/cs_topic.cpp:70 +#, c-format +msgid "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." +msgstr "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." + +#: modules/commands/cs_set.cpp:592 +#, c-format +msgid "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." +msgstr "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." + +#: modules/commands/os_akill.cpp:331 +msgid "End of AKILL list." +msgstr "End of AKILL list." + +#: modules/commands/cs_access.cpp:444 +msgid "End of access list" +msgstr "End of access list" + +#: modules/commands/cs_flags.cpp:347 +#, c-format +msgid "End of access list - %d/%d entries shown." +msgstr "End of access list - %d/%d entries shown." + +#: modules/commands/cs_flags.cpp:345 +msgid "End of access list." +msgstr "End of access list." + +#: modules/commands/cs_akick.cpp:379 +msgid "End of autokick list" +msgstr "End of autokick list" + +#: modules/commands/bs_badwords.cpp:257 +msgid "End of bad words list." +msgstr "End of bad words list." + +#: modules/commands/os_list.cpp:100 +#, c-format +msgid "End of channel list. %u channels shown." +msgstr "End of channel list. %u channels shown." + +#: modules/commands/os_config.cpp:117 +msgid "End of configuration." +msgstr "End of configuration." + +#: modules/commands/cs_entrymsg.cpp:134 +msgid "End of entry message list." +msgstr "End of entry message list." + +#: modules/commands/os_forbid.cpp:407 +#, c-format +msgid "End of forbid list - %d/%d entries shown." +msgstr "End of forbid list - %d/%d entries shown." + +#: modules/commands/os_forbid.cpp:405 +msgid "End of forbid list." +msgstr "End of forbid list." + +#: modules/commands/ns_alist.cpp:119 +#, c-format +msgid "End of list - %d channels shown." +msgstr "End of list - %d channels shown." + +#: modules/commands/ns_list.cpp:131 modules/commands/cs_list.cpp:130 +#, c-format +msgid "End of list - %d/%d matches shown." +msgstr "End of list - %d/%d matches shown." + +#: modules/commands/os_news.cpp:176 +msgid "End of news list." +msgstr "End of news list." + +#: modules/commands/os_list.cpp:235 +#, c-format +msgid "End of users list. %u users shown." +msgstr "End of users list. %u users shown." + +#: modules/commands/cs_enforce.cpp:227 +msgid "Enforce various channel modes and set options" +msgstr "Enforce various channel modes and set options" + +#: modules/commands/cs_enforce.cpp:263 +msgid "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." +msgstr "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." + +#: src/language.cpp:43 modules/commands/ns_set.cpp:836 +#: modules/commands/ns_set.cpp:856 modules/commands/ns_set.cpp:891 +msgid "English" +msgstr "English" + +#: modules/commands/cs_entrymsg.cpp:170 +#, c-format +msgid "Entry message %i for %s deleted." +msgstr "Entry message %i for %s deleted." + +#: modules/commands/cs_entrymsg.cpp:177 +#, c-format +msgid "Entry message %s not found on channel %s." +msgstr "Entry message %s not found on channel %s." + +#: modules/commands/cs_entrymsg.cpp:147 +#, c-format +msgid "Entry message added to %s" +msgstr "Entry message added to %s" + +#: modules/commands/cs_entrymsg.cpp:109 modules/commands/cs_entrymsg.cpp:158 +#, c-format +msgid "Entry message list for %s is empty." +msgstr "Entry message list for %s is empty." + +#: modules/commands/cs_entrymsg.cpp:113 +#, c-format +msgid "Entry message list for %s:" +msgstr "Entry message list for %s:" + +#: modules/commands/cs_entrymsg.cpp:187 +#, c-format +msgid "Entry messages for %s have been cleared." +msgstr "Entry messages for %s have been cleared." + +#: modules/commands/os_reload.cpp:39 +#, c-format +msgid "Error reloading configuration file: %s" +msgstr "Error reloading configuration file: %s" + +#: include/language.h:125 +#, c-format +msgid "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." +msgstr "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." + +#: include/language.h:124 +#, c-format +msgid "" +"Error! The vHost is too long, please use a hostname shorter than %d " +"characters." +msgstr "" +"Error! The vHost is too long, please use a hostname shorter than %d " +"characters." + +#: modules/commands/ns_cert.cpp:325 +msgid "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." +msgstr "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." + +#: modules/commands/os_session.cpp:358 +#, c-format +msgid "Exception for %s has been updated to %d." +msgstr "Exception for %s has been updated to %d." + +#: modules/pseudoclients/chanserv.cpp:465 +#: modules/pseudoclients/nickserv.cpp:557 +#: modules/pseudoclients/nickserv.cpp:562 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_session.cpp:514 modules/commands/ns_group.cpp:327 +#: modules/commands/os_akill.cpp:358 +msgid "Expires" +msgstr "Expires" + +#: src/xline.cpp:397 +#, c-format +msgid "Expiry and reason updated for %s." +msgstr "Expiry and reason updated for %s." + +#: src/xline.cpp:400 +#, c-format +msgid "Expiry for %s updated." +msgstr "Expiry for %s updated." + +#: modules/fantasy.cpp:214 +msgid "Fantasy" +msgstr "Fantasy" + +#: modules/fantasy.cpp:60 +#, c-format +msgid "Fantasy mode is now off on channel %s." +msgstr "Fantasy mode is now off on channel %s." + +#: modules/fantasy.cpp:52 +#, c-format +msgid "Fantasy mode is now on on channel %s." +msgstr "Fantasy mode is now on on channel %s." + +#: modules/commands/cs_status.cpp:19 +msgid "Find a user's status on a channel" +msgstr "Find a user's status on a channel" + +#: modules/commands/ns_cert.cpp:192 +#, c-format +msgid "Fingerprint %s already present on %s's certificate list." +msgstr "Fingerprint %s already present on %s's certificate list." + +#: modules/commands/ns_cert.cpp:198 +#, c-format +msgid "Fingerprint %s is already in use." +msgstr "Fingerprint %s is already in use." + +#: modules/commands/cs_flags.cpp:301 +msgid "Flags" +msgstr "Flags" + +#: modules/commands/cs_flags.cpp:286 +#, c-format +msgid "Flags for %s on %s set to +%s" +msgstr "Flags for %s on %s set to +%s" + +#: modules/commands/cs_flags.cpp:341 +#, c-format +msgid "Flags list for %s" +msgstr "Flags list for %s" + +#: modules/commands/bs_kick.cpp:1161 modules/commands/bs_kick.cpp:1163 +#: modules/commands/bs_kick.cpp:1166 +msgid "Flood kicker" +msgstr "Flood kicker" + +#: modules/commands/os_forbid.cpp:421 +msgid "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." +msgstr "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." + +#: modules/commands/os_forbid.cpp:354 +msgid "Forbid list is empty." +msgstr "Forbid list is empty." + +#: modules/commands/os_forbid.cpp:396 +msgid "Forbid list:" +msgstr "Forbid list:" + +#: modules/commands/os_forbid.cpp:348 +#, c-format +msgid "Forbid on %s was not found." +msgstr "Forbid on %s was not found." + +#: modules/commands/os_forbid.cpp:156 +msgid "Forbid usage of nicknames, channels, and emails" +msgstr "Forbid usage of nicknames, channels, and emails" + +#: modules/commands/os_update.cpp:19 +msgid "Force the Services databases to be updated immediately" +msgstr "Force the Services databases to be updated immediately" + +#: modules/commands/os_svs.cpp:19 +msgid "Forcefully change a user's nickname" +msgstr "Forcefully change a user's nickname" + +#: modules/commands/os_svs.cpp:68 +msgid "Forcefully changes a user's nickname from nick to newnick." +msgstr "Forcefully changes a user's nickname from nick to newnick." + +#: modules/commands/os_svs.cpp:78 +msgid "Forcefully join a user to a channel" +msgstr "Forcefully join a user to a channel" + +#: modules/commands/os_svs.cpp:112 +msgid "Forcefully join a user to a channel." +msgstr "Forcefully join a user to a channel." + +#: modules/commands/os_svs.cpp:122 +msgid "Forcefully part a user from a channel" +msgstr "Forcefully part a user from a channel" + +#: modules/commands/os_svs.cpp:160 +msgid "Forcefully part a user from a channel." +msgstr "Forcefully part a user from a channel." + +#: modules/commands/ns_alist.cpp:64 modules/commands/cs_info.cpp:47 +msgid "Founder" +msgstr "Founder" + +#: modules/commands/cs_set.cpp:315 +#, c-format +msgid "Founder of %s changed to %s." +msgstr "Founder of %s changed to %s." + +#: modules/commands/ns_getpass.cpp:41 +msgid "GETPASS command unavailable because encryption is in use." +msgstr "GETPASS command unavailable because encryption is in use." + +#: modules/commands/ns_recover.cpp:84 +msgid "Ghost with your nick has been killed." +msgstr "Ghost with your nick has been killed." + +#: modules/commands/os_oline.cpp:19 +msgid "Give Operflags to a certain user" +msgstr "Give Operflags to a certain user" + +#: modules/commands/cs_mode.cpp:905 +#, c-format +msgid "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." +msgstr "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." + +#: modules/commands/cs_mode.cpp:888 +#, c-format +msgid "Gives you or the specified nick %s status on a channel" +msgstr "Gives you or the specified nick %s status on a channel" + +#: modules/commands/greet.cpp:206 modules/commands/greet.cpp:212 +msgid "Greet" +msgstr "Greet" + +#: src/access.cpp:38 +msgid "Greet message displayed on join" +msgstr "Greet message displayed on join" + +#: modules/commands/greet.cpp:112 +#, c-format +msgid "Greet message for %s changed to %s." +msgstr "Greet message for %s changed to %s." + +#: modules/commands/greet.cpp:118 +#, c-format +msgid "Greet message for %s unset." +msgstr "Greet message for %s unset." + +#: modules/commands/greet.cpp:60 +#, c-format +msgid "Greet mode is now off on channel %s." +msgstr "Greet mode is now off on channel %s." + +#: modules/commands/greet.cpp:52 +#, c-format +msgid "Greet mode is now on on channel %s." +msgstr "Greet mode is now on on channel %s." + +#: modules/commands/ns_resetpass.cpp:21 +msgid "Helps you reset lost passwords" +msgstr "Helps you reset lost passwords" + +#: modules/commands/ns_info.cpp:141 +msgid "Hide certain pieces of nickname information" +msgstr "Hide certain pieces of nickname information" + +#: modules/commands/cs_list.cpp:180 +msgid "Hide channel from the LIST command" +msgstr "Hide channel from the LIST command" + +#: modules/commands/os_session.cpp:192 +msgid "Host" +msgstr "Host" + +#: modules/commands/os_session.cpp:207 +#, c-format +msgid "Hosts with at least %d sessions:" +msgstr "Hosts with at least %d sessions:" + +#: modules/commands/cs_seen.cpp:207 +#, c-format +msgid "I don't know who %s is." +msgstr "I don't know who %s is." + +#: modules/commands/cs_seen.cpp:253 +#, c-format +msgid "I've never seen %s on this channel." +msgstr "I've never seen %s on this channel." + +#: modules/commands/os_sxline.cpp:203 modules/commands/os_akill.cpp:360 +msgid "ID" +msgstr "ID" + +#: modules/commands/os_oper.cpp:72 +msgid "INFO [type]" +msgstr "INFO [type]" + +#: modules/commands/os_dns.cpp:218 +msgid "IP" +msgstr "IP" + +#: modules/commands/os_dns.cpp:500 +#, c-format +msgid "IP %s already exists for %s." +msgstr "IP %s already exists for %s." + +#: modules/commands/os_dns.cpp:562 +#, c-format +msgid "IP %s does not exist for %s." +msgstr "IP %s does not exist for %s." + +#: modules/commands/ns_identify.cpp:65 +msgid "Identify yourself with your password" +msgstr "Identify yourself with your password" + +#: modules/pseudoclients/nickserv.cpp:205 +#: modules/pseudoclients/nickserv.cpp:211 +#, c-format +msgid "If you do not change within %s, I will change your nick." +msgstr "If you do not change within %s, I will change your nick." + +#: modules/commands/os_ignore.cpp:333 +msgid "Ignore list has been cleared." +msgstr "Ignore list has been cleared." + +#: modules/commands/os_ignore.cpp:262 +msgid "Ignore list is empty." +msgstr "Ignore list is empty." + +#: modules/commands/ms_ignore.cpp:94 +msgid "Ignore list:" +msgstr "Ignore list:" + +#: modules/commands/ns_set.cpp:1305 +msgid "Immediate protection" +msgstr "Immediate protection" + +#: modules/commands/ns_resetpass.cpp:33 +msgid "Incorrect email address." +msgstr "Incorrect email address." + +#: include/language.h:89 +msgid "Incorrect range specified. The correct syntax is #from-to." +msgstr "Incorrect range specified. The correct syntax is #from-to." + +#: modules/commands/os_modinfo.cpp:19 +msgid "Info about a loaded module" +msgstr "Info about a loaded module" + +#: modules/commands/bs_info.cpp:54 +#, c-format +msgid "Information for bot %s:" +msgstr "Information for bot %s:" + +#: include/language.h:108 +#, c-format +msgid "Information for channel %s:" +msgstr "Information for channel %s:" + +#: modules/commands/os_logsearch.cpp:57 +#, c-format +msgid "Invalid duration %s, using %d days." +msgstr "Invalid duration %s, using %d days." + +#: include/language.h:68 +msgid "Invalid expiry time." +msgstr "Invalid expiry time." + +#: modules/commands/os_session.cpp:346 +msgid "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not " +"matched against nicks or usernames." +msgstr "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not " +"matched against nicks or usernames." + +#: modules/commands/os_logsearch.cpp:73 +#, c-format +msgid "Invalid limit %s, using %d." +msgstr "Invalid limit %s, using %d." + +#: include/language.h:99 +msgid "" +"Invalid passcode has been entered, please check the e-mail again, and retry." +msgstr "" +"Invalid passcode has been entered, please check the e-mail again, and retry." + +#: modules/commands/ns_register.cpp:83 modules/commands/ns_register.cpp:86 +msgid "Invalid passcode." +msgstr "Invalid passcode." + +#: modules/commands/os_session.cpp:339 +#, c-format +msgid "" +"Invalid session limit. It must be a valid integer greater than or equal to " +"zero and less than %d." +msgstr "" +"Invalid session limit. It must be a valid integer greater than or equal to " +"zero and less than %d." + +#: modules/commands/os_session.cpp:188 +msgid "Invalid threshold value. It must be a valid integer greater than 1." +msgstr "Invalid threshold value. It must be a valid integer greater than 1." + +#: modules/commands/os_dns.cpp:591 +msgid "Invalid value for LIMIT. Must be numerical." +msgstr "Invalid value for LIMIT. Must be numerical." + +#: modules/commands/cs_invite.cpp:19 +msgid "Invites you or an optionally specified nick into a channel" +msgstr "Invites you or an optionally specified nick into a channel" + +#: modules/commands/bs_kick.cpp:1201 modules/commands/bs_kick.cpp:1203 +#: modules/commands/bs_kick.cpp:1206 +msgid "Italics kicker" +msgstr "Italics kicker" + +#: modules/commands/ns_group.cpp:91 +msgid "Join a group" +msgstr "Join a group" + +#: modules/commands/cs_set.cpp:1305 modules/commands/ns_set.cpp:1319 +msgid "Keep modes" +msgstr "Keep modes" + +#: modules/commands/cs_set.cpp:377 modules/commands/ns_set.cpp:603 +#, c-format +msgid "Keep modes for %s is now off." +msgstr "Keep modes for %s is now off." + +#: modules/commands/cs_set.cpp:369 modules/commands/ns_set.cpp:597 +#, c-format +msgid "Keep modes for %s is now on." +msgstr "Keep modes for %s is now on." + +#: modules/commands/ns_ajoin.cpp:100 +msgid "Key" +msgstr "Key" + +#: modules/commands/cs_getkey.cpp:50 +#, c-format +msgid "Key for channel %s is %s." +msgstr "Key for channel %s is %s." + +#: modules/commands/os_kick.cpp:19 +msgid "Kick a user from a channel" +msgstr "Kick a user from a channel" + +#: modules/commands/cs_ban.cpp:217 modules/commands/cs_kick.cpp:116 +#, c-format +msgid "Kicked %d/%d users matching %s from %s." +msgstr "Kicked %d/%d users matching %s from %s." + +#: modules/commands/cs_kick.cpp:19 +msgid "Kicks a specified nick from a channel" +msgstr "Kicks a specified nick from a channel" + +#: modules/commands/cs_kick.cpp:128 +msgid "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." +msgstr "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." + +#: modules/commands/os_kill.cpp:19 +msgid "Kill a user" +msgstr "Kill a user" + +#: modules/commands/cs_enforce.cpp:217 +msgid "LIMIT enforced by " +msgstr "LIMIT enforced by " + +#: modules/commands/cs_enforce.cpp:221 +#, c-format +msgid "LIMIT enforced on %s, %d users removed." +msgstr "LIMIT enforced on %s, %d users removed." + +#: modules/commands/os_session.cpp:246 +msgid "LIST threshold" +msgstr "LIST threshold" + +#: modules/commands/os_sxline.cpp:427 modules/commands/os_sxline.cpp:661 +#: modules/commands/os_akill.cpp:388 +msgid "LIST [mask | list | id]" +msgstr "LIST [mask | list | id]" + +#: modules/commands/os_session.cpp:525 +msgid "LIST [mask | list]" +msgstr "LIST [mask | list]" + +#: modules/commands/ns_access.cpp:104 modules/commands/ns_cert.cpp:260 +#: modules/commands/ns_ajoin.cpp:233 +msgid "LIST [nickname]" +msgstr "LIST [nickname]" + +#: modules/commands/os_news.cpp:31 +msgid "LOGONNEWS {ADD|DEL|LIST} [text|num]" +msgstr "LOGONNEWS {ADD|DEL|LIST} [text|num]" + +#: modules/commands/ns_set.cpp:834 +msgid "Language changed to English." +msgstr "Language changed to English." + +#: modules/commands/ns_set.cpp:836 +#, c-format +msgid "Language for %s changed to %s." +msgstr "Language for %s changed to %s." + +#: modules/commands/ms_cancel.cpp:72 +#, c-format +msgid "Last memo to %s has been cancelled." +msgstr "Last memo to %s has been cancelled." + +#: modules/commands/ns_info.cpp:95 +msgid "Last quit message" +msgstr "Last quit message" + +#: modules/commands/cs_access.cpp:472 modules/commands/ns_info.cpp:92 +msgid "Last seen" +msgstr "Last seen" + +#: modules/commands/ns_info.cpp:81 modules/commands/ns_info.cpp:86 +msgid "Last seen address" +msgstr "Last seen address" + +#: modules/commands/cs_topic.cpp:264 +msgid "Last topic" +msgstr "Last topic" + +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_info.cpp:56 +msgid "Last used" +msgstr "Last used" + +#: modules/commands/ns_list.cpp:75 +msgid "Last usermask" +msgstr "Last usermask" + +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +#: modules/commands/cs_access.cpp:697 +msgid "Level" +msgstr "Level" + +#: modules/commands/cs_access.cpp:660 +#, c-format +msgid "Level for %s on channel %s changed to %d." +msgstr "Level for %s on channel %s changed to %d." + +#: modules/commands/cs_access.cpp:658 +#, c-format +msgid "Level for %s on channel %s changed to founder only." +msgstr "Level for %s on channel %s changed to founder only." + +#: modules/commands/cs_access.cpp:643 +#, c-format +msgid "Level must be between %d and %d inclusive." +msgstr "Level must be between %d and %d inclusive." + +#: modules/commands/os_dns.cpp:218 modules/commands/os_session.cpp:506 +#: modules/commands/os_session.cpp:514 +msgid "Limit" +msgstr "Limit" + +#: modules/commands/ns_list.cpp:19 +msgid "List all registered nicknames that match a given pattern" +msgstr "List all registered nicknames that match a given pattern" + +#: modules/commands/ns_alist.cpp:24 +msgid "List channels you have access on" +msgstr "List channels you have access on" + +#: modules/commands/cs_mode.cpp:341 +#, c-format +msgid "List for mode %c is full." +msgstr "List for mode %c is full." + +#: modules/commands/os_modinfo.cpp:80 +msgid "List loaded modules" +msgstr "List loaded modules" + +#: modules/commands/ns_list.cpp:123 modules/commands/cs_list.cpp:72 +#, c-format +msgid "List of entries matching %s:" +msgstr "List of entries matching %s:" + +#: modules/commands/ns_group.cpp:350 +#, c-format +msgid "List of nicknames in the group of %s:" +msgstr "List of nicknames in the group of %s:" + +#: modules/commands/ns_group.cpp:350 +msgid "List of nicknames in your group:" +msgstr "List of nicknames in your group:" + +#: modules/commands/ms_list.cpp:19 +msgid "List your memos" +msgstr "List your memos" + +#: modules/commands/bs_botlist.cpp:64 +msgid "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." +msgstr "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." + +#: modules/commands/os_list.cpp:19 +msgid "Lists all channel records" +msgstr "Lists all channel records" + +#: modules/commands/os_list.cpp:107 +msgid "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." +msgstr "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." + +#: modules/commands/ns_alist.cpp:127 +msgid "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" +msgstr "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" + +#: modules/commands/ns_group.cpp:299 +msgid "Lists all nicknames in your group" +msgstr "Lists all nicknames in your group" + +#: modules/commands/cs_list.cpp:20 +msgid "Lists all registered channels matching the given pattern" +msgstr "Lists all registered channels matching the given pattern" + +#: modules/commands/cs_list.cpp:137 +msgid "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." +msgstr "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." + +#: modules/commands/ns_list.cpp:139 +msgid "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." +msgstr "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." + +#: modules/commands/os_list.cpp:132 +msgid "Lists all user records" +msgstr "Lists all user records" + +#: modules/commands/os_list.cpp:243 +msgid "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only " +"users\n" +"with the +i flag will be listed." +msgstr "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only " +"users\n" +"with the +i flag will be listed." + +#: modules/commands/ms_list.cpp:142 +msgid "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." + +#: modules/commands/bs_botlist.cpp:19 +msgid "Lists available bots" +msgstr "Lists available bots" + +#: modules/commands/os_modinfo.cpp:196 +msgid "Lists currently loaded modules." +msgstr "Lists currently loaded modules." + +#: modules/commands/cs_info.cpp:19 +msgid "Lists information about the specified registered channel" +msgstr "Lists information about the specified registered channel" + +#: modules/commands/cs_info.cpp:76 +msgid "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." +msgstr "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." + +#: modules/commands/os_module.cpp:19 +msgid "Load a module" +msgstr "Load a module" + +#: modules/commands/cs_register.cpp:39 +msgid "Local channels cannot be registered." +msgstr "Local channels cannot be registered." + +#: modules/commands/cs_log.cpp:142 +#, c-format +msgid "Log list for %s:" +msgstr "Log list for %s:" + +#: modules/commands/cs_log.cpp:227 +#, c-format +msgid "Logging changed for command %s on %s, now using log method %s%s%s." +msgstr "Logging changed for command %s on %s, now using log method %s%s%s." + +#: modules/commands/cs_log.cpp:220 +#, c-format +msgid "Logging for command %s on %s with log method %s%s%s has been removed." +msgstr "Logging for command %s on %s with log method %s%s%s has been removed." + +#: modules/commands/cs_log.cpp:248 +#, c-format +msgid "Logging is now active for command %s on %s, using log method %s%s%s." +msgstr "Logging is now active for command %s on %s, using log method %s%s%s." + +#: modules/commands/os_login.cpp:60 +#, c-format +msgid "Login to %s" +msgstr "Login to %s" + +#: modules/commands/os_news.cpp:36 +#, c-format +msgid "Logon news item #%d deleted." +msgstr "Logon news item #%d deleted." + +#: modules/commands/os_news.cpp:35 +#, c-format +msgid "Logon news item #%s not found!" +msgstr "Logon news item #%s not found!" + +#: modules/commands/os_news.cpp:32 +msgid "Logon news items:" +msgstr "Logon news items:" + +#: modules/commands/os_login.cpp:102 +#, c-format +msgid "Logout from %s" +msgstr "Logout from %s" + +#: modules/commands/os_login.cpp:52 +#, c-format +msgid "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." +msgstr "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." + +#: modules/commands/os_login.cpp:94 +#, c-format +msgid "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." +msgstr "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." + +#: modules/commands/cs_seen.cpp:213 +#, c-format +msgid "Looking for yourself, eh %s?" +msgstr "Looking for yourself, eh %s?" + +#: modules/commands/cs_mode.cpp:773 +#, c-format +msgid "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a " +"channel.\n" +"If a mode is locked on or off, services will not allow that mode to be " +"changed. The SET\n" +"command will clear all existing mode locks and set the new one given, while " +"ADD and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * " +"and ? may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may " +"be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, " +"halfops, and voices. If what\n" +"is not given then all basic modes are removed." +msgstr "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a " +"channel.\n" +"If a mode is locked on or off, services will not allow that mode to be " +"changed. The SET\n" +"command will clear all existing mode locks and set the new one given, while " +"ADD and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * " +"and ? may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may " +"be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, " +"halfops, and voices. If what\n" +"is not given then all basic modes are removed." + +#: modules/commands/cs_akick.cpp:434 +msgid "Maintain the AutoKick list" +msgstr "Maintain the AutoKick list" + +#: modules/commands/bs_bot.cpp:269 +msgid "Maintains network bot list" +msgstr "Maintains network bot list" + +#: modules/commands/cs_xop.cpp:522 +#, c-format +msgid "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " +msgstr "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " + +#: modules/commands/cs_akick.cpp:493 +#, c-format +msgid "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" +msgstr "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" + +#: modules/commands/cs_access.cpp:568 +#, c-format +msgid "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." +msgstr "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." + +#: modules/commands/bs_badwords.cpp:424 +#, c-format +msgid "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" +msgstr "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" + +#: modules/commands/bs_badwords.cpp:370 +msgid "Maintains the bad words list" +msgstr "Maintains the bad words list" + +#: modules/commands/bs_control.cpp:79 +msgid "Makes the bot do the equivalent of a \"/me\" command" +msgstr "Makes the bot do the equivalent of a \"/me\" command" + +#: modules/commands/bs_control.cpp:127 +msgid "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." +msgstr "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." + +#: modules/commands/bs_control.cpp:19 +msgid "Makes the bot say the specified text on the specified channel" +msgstr "Makes the bot say the specified text on the specified channel" + +#: modules/commands/bs_control.cpp:69 +msgid "Makes the bot say the specified text on the specified channel." +msgstr "Makes the bot say the specified text on the specified channel." + +#: modules/commands/greet.cpp:157 +msgid "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." +msgstr "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." + +#: modules/commands/greet.cpp:131 +msgid "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." +msgstr "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." + +#: modules/commands/os_dns.cpp:660 +msgid "Manage DNS zones for this network" +msgstr "Manage DNS zones for this network" + +#: modules/commands/cs_entrymsg.cpp:193 +msgid "Manage the channel's entry messages" +msgstr "Manage the channel's entry messages" + +#: modules/commands/ms_ignore.cpp:19 +msgid "Manage the memo ignore list" +msgstr "Manage the memo ignore list" + +#: modules/commands/ns_ajoin.cpp:230 +msgid "Manage your auto join list" +msgstr "Manage your auto join list" + +#: modules/commands/os_sxline.cpp:233 +#, c-format +msgid "Manipulate the %s list" +msgstr "Manipulate the %s list" + +#: modules/commands/os_akill.cpp:385 +msgid "Manipulate the AKILL list" +msgstr "Manipulate the AKILL list" + +#: modules/commands/os_defcon.cpp:176 +msgid "Manipulate the DefCon system" +msgstr "Manipulate the DefCon system" + +#: modules/commands/cs_topic.cpp:149 +msgid "Manipulate the topic of the specified channel" +msgstr "Manipulate the topic of the specified channel" + +#: modules/commands/bs_botlist.cpp:27 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_forbid.cpp:358 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/ms_ignore.cpp:86 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_list.cpp:153 modules/commands/bs_info.cpp:55 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +msgid "Mask" +msgstr "Mask" + +#: modules/commands/ns_access.cpp:39 +#, c-format +msgid "Mask %s already present on %s's access list." +msgstr "Mask %s already present on %s's access list." + +#: include/language.h:67 +msgid "Mask must be in the form user@host." +msgstr "Mask must be in the form user@host." + +#: modules/commands/cs_access.cpp:166 modules/commands/cs_flags.cpp:120 +#: modules/commands/cs_xop.cpp:162 +msgid "Masks and unregistered users may not be on access lists." +msgstr "Masks and unregistered users may not be on access lists." + +#: modules/commands/ns_getemail.cpp:23 +msgid "Matches and returns all users that registered using given email" +msgstr "Matches and returns all users that registered using given email" + +#: modules/commands/os_logsearch.cpp:148 +#, c-format +msgid "Matches for %s:" +msgstr "Matches for %s:" + +#: modules/commands/os_stats.cpp:139 +#, c-format +msgid "Maximum users: %d (%s)" +msgstr "Maximum users: %d (%s)" + +#: modules/commands/ms_read.cpp:84 modules/commands/ms_read.cpp:86 +#, c-format +msgid "Memo %d from %s (%s)." +msgstr "Memo %d from %s (%s)." + +#: modules/commands/ms_del.cpp:33 modules/commands/ms_del.cpp:101 +#, c-format +msgid "Memo %d has been deleted." +msgstr "Memo %d has been deleted." + +#: modules/commands/ms_ignore.cpp:82 +msgid "Memo ignore list is empty." +msgstr "Memo ignore list is empty." + +#: modules/commands/ms_set.cpp:199 +#, c-format +msgid "Memo limit disabled for %s." +msgstr "Memo limit disabled for %s." + +#: modules/commands/ms_set.cpp:185 +#, c-format +msgid "Memo limit for %s set to %d." +msgstr "Memo limit for %s set to %d." + +#: modules/commands/ms_set.cpp:192 +#, c-format +msgid "Memo limit for %s set to 0." +msgstr "Memo limit for %s set to 0." + +#: modules/commands/ms_rsend.cpp:63 modules/commands/ms_send.cpp:51 +#, c-format +msgid "Memo sent to %s." +msgstr "Memo sent to %s." + +#: modules/commands/ms_list.cpp:131 +#, c-format +msgid "Memos for %s:" +msgstr "Memos for %s:" + +#: modules/commands/cs_entrymsg.cpp:116 +msgid "Message" +msgstr "Message" + +#: modules/commands/ns_set.cpp:1313 +msgid "Message mode" +msgstr "Message mode" + +#: modules/commands/cs_log.cpp:127 +msgid "Method" +msgstr "Method" + +#: modules/commands/cs_mode.cpp:329 modules/commands/cs_mode.cpp:420 +#, c-format +msgid "Missing parameter for mode %c." +msgstr "Missing parameter for mode %c." + +#: modules/commands/cs_mode.cpp:449 +msgid "Mode" +msgstr "Mode" + +#: modules/commands/cs_mode.cpp:718 +#, c-format +msgid "Mode %s is a virtual mode and can't be cleared." +msgstr "Mode %s is a virtual mode and can't be cleared." + +#: modules/commands/cs_mode.cpp:712 +#, c-format +msgid "Mode %s is not a status or list mode." +msgstr "Mode %s is not a status or list mode." + +#: modules/commands/cs_mode.cpp:1065 +msgid "Mode lock" +msgstr "Mode lock" + +#: modules/commands/cs_mode.cpp:466 +#, c-format +msgid "Mode locks for %s:" +msgstr "Mode locks for %s:" + +#: modules/commands/os_list.cpp:43 +msgid "Modes" +msgstr "Modes" + +#: modules/commands/os_mode.cpp:44 +#, c-format +msgid "Modes cleared on %s and the channel destroyed." +msgstr "Modes cleared on %s and the channel destroyed." + +#: modules/commands/ns_access.cpp:166 +#, c-format +msgid "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." +msgstr "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." + +#: modules/commands/ns_cert.cpp:319 +msgid "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" +msgstr "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" + +#: modules/commands/os_ignore.cpp:341 +msgid "Modify the Services ignore list" +msgstr "Modify the Services ignore list" + +#: modules/commands/cs_xop.cpp:489 +#, c-format +msgid "Modify the list of %s users" +msgstr "Modify the list of %s users" + +#: modules/commands/ns_access.cpp:101 +msgid "Modify the list of authorized addresses" +msgstr "Modify the list of authorized addresses" + +#: modules/commands/cs_access.cpp:498 modules/commands/cs_flags.cpp:373 +msgid "Modify the list of privileged users" +msgstr "Modify the list of privileged users" + +#: modules/commands/ns_cert.cpp:257 +msgid "Modify the nickname client certificate list" +msgstr "Modify the nickname client certificate list" + +#: modules/commands/os_session.cpp:522 +msgid "Modify the session-limit exception list" +msgstr "Modify the session-limit exception list" + +#: modules/commands/os_module.cpp:34 +#, c-format +msgid "Module %s is already loaded." +msgstr "Module %s is already loaded." + +#: modules/commands/os_module.cpp:67 modules/commands/os_module.cpp:139 +#, c-format +msgid "Module %s isn't loaded." +msgstr "Module %s isn't loaded." + +#: modules/commands/os_module.cpp:31 +#, c-format +msgid "Module %s loaded." +msgstr "Module %s loaded." + +#: modules/commands/os_module.cpp:98 +#, c-format +msgid "Module %s reloaded." +msgstr "Module %s reloaded." + +#: modules/commands/os_module.cpp:156 +#, c-format +msgid "Module %s unloaded." +msgstr "Module %s unloaded." + +#: modules/commands/os_config.cpp:88 +msgid "Module Name" +msgstr "Module Name" + +#: modules/commands/os_config.cpp:112 +msgid "Module settings:" +msgstr "Module settings:" + +#: modules/commands/os_modinfo.cpp:32 +#, c-format +msgid "Module: %s Version: %s Author: %s Loaded: %s" +msgstr "Module: %s Version: %s Author: %s Loaded: %s" + +#: modules/commands/os_modinfo.cpp:183 +#, c-format +msgid "Module: %s [%s] [%s]" +msgstr "Module: %s [%s] [%s]" + +#: modules/commands/cs_access.cpp:697 modules/commands/cs_access.cpp:799 +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +#: modules/commands/cs_list.cpp:75 modules/commands/os_list.cpp:43 +#: modules/commands/os_list.cpp:153 +msgid "Name" +msgstr "Name" + +#: modules/commands/os_oper.cpp:153 +msgid "Name Type" +msgstr "Name Type" + +#: modules/extra/stats/cs_fantasy_stats.cpp:146 +#, c-format +msgid "Network stats for %s:" +msgstr "Network stats for %s:" + +#: modules/commands/os_forbid.cpp:384 +msgid "Never" +msgstr "Never" + +#: modules/commands/hs_list.cpp:58 modules/commands/bs_botlist.cpp:27 +#: modules/commands/hs_request.cpp:305 modules/commands/ns_list.cpp:75 +#: modules/commands/ns_group.cpp:327 +msgid "Nick" +msgstr "Nick" + +#: modules/commands/ns_register.cpp:42 +#, c-format +msgid "Nick %s has been confirmed." +msgstr "Nick %s has been confirmed." + +#: modules/commands/os_oper.cpp:95 +#, c-format +msgid "Nick %s is already an operator." +msgstr "Nick %s is already an operator." + +#: modules/commands/ns_register.cpp:36 +#, c-format +msgid "Nick %s is already confirmed." +msgstr "Nick %s is already confirmed." + +#: modules/commands/os_svs.cpp:46 +#, c-format +msgid "Nick %s is an illegal nickname and cannot be used." +msgstr "Nick %s is an illegal nickname and cannot be used." + +#: modules/commands/bs_bot.cpp:81 modules/commands/bs_bot.cpp:181 +#: modules/commands/os_svs.cpp:54 +#, c-format +msgid "Nick %s is currently in use." +msgstr "Nick %s is currently in use." + +#: modules/commands/os_forbid.cpp:512 +#, c-format +msgid "Nick %s is forbidden by %s: %s" +msgstr "Nick %s is forbidden by %s: %s" + +#: modules/commands/os_forbid.cpp:514 +#, c-format +msgid "Nick %s is forbidden." +msgstr "Nick %s is forbidden." + +#: modules/commands/os_oper.cpp:134 +#, c-format +msgid "Nick %s is not a Services Operator." +msgstr "Nick %s is not a Services Operator." + +#: modules/commands/ns_info.cpp:34 +#, c-format +msgid "Nick %s is part of this Network's Services." +msgstr "Nick %s is part of this Network's Services." + +#: include/language.h:79 +#, c-format +msgid "Nick %s isn't currently in use." +msgstr "Nick %s isn't currently in use." + +#: include/language.h:78 +#, c-format +msgid "Nick %s isn't registered." +msgstr "Nick %s isn't registered." + +#: modules/commands/os_svs.cpp:39 +#, c-format +msgid "Nick %s was truncated to %d characters." +msgstr "Nick %s was truncated to %d characters." + +#: modules/commands/ns_set.cpp:1135 +#, c-format +msgid "Nick %s will expire." +msgstr "Nick %s will expire." + +#: modules/commands/ns_set.cpp:1129 +#, c-format +msgid "Nick %s will not expire." +msgstr "Nick %s will not expire." + +#: modules/commands/ms_check.cpp:60 +#, c-format +msgid "Nick %s doesn't have a memo from you." +msgstr "Nick %s doesn't have a memo from you." + +#: modules/commands/ns_logout.cpp:48 +#, c-format +msgid "Nick %s has been logged out." +msgstr "Nick %s has been logged out." + +#: modules/commands/ns_group.cpp:272 +#, c-format +msgid "Nick %s has been ungrouped from %s." +msgstr "Nick %s has been ungrouped from %s." + +#: include/language.h:81 +#, c-format +msgid "Nick %s is currently suspended." +msgstr "Nick %s is currently suspended." + +#: modules/commands/ns_group.cpp:250 +#, c-format +msgid "Nick %s is not in your group." +msgstr "Nick %s is not in your group." + +#: modules/commands/ns_suspend.cpp:180 +#, c-format +msgid "Nick %s is not suspended." +msgstr "Nick %s is not suspended." + +#: modules/commands/ns_suspend.cpp:190 +#, c-format +msgid "Nick %s is now released." +msgstr "Nick %s is now released." + +#: modules/commands/ns_suspend.cpp:138 +#, c-format +msgid "Nick %s is now suspended." +msgstr "Nick %s is now suspended." + +#: modules/commands/cs_seen.cpp:275 +#, c-format +msgid "Nick too long, max length is %u characters." +msgstr "Nick too long, max length is %u characters." + +#: modules/commands/ns_drop.cpp:53 +#, c-format +msgid "Nickname %s has been dropped." +msgstr "Nickname %s has been dropped." + +#: include/language.h:97 +#, c-format +msgid "Nickname %s is already registered!" +msgstr "Nickname %s is already registered!" + +#: include/language.h:96 +#, c-format +msgid "Nickname %s may not be registered." +msgstr "Nickname %s may not be registered." + +#: modules/commands/ns_register.cpp:226 +#, c-format +msgid "Nickname %s registered under your user@host-mask: %s" +msgstr "Nickname %s registered under your user@host-mask: %s" + +#: modules/commands/ns_register.cpp:228 +#, c-format +msgid "Nickname %s registered." +msgstr "Nickname %s registered." + +#: modules/commands/cs_set.cpp:1307 +msgid "No auto-op" +msgstr "No auto-op" + +#: modules/commands/bs_assign.cpp:252 +msgid "No bot" +msgstr "No bot" + +#: modules/commands/cs_set.cpp:1303 modules/commands/ns_set.cpp:1317 +msgid "No expire" +msgstr "No expire" + +#: modules/commands/help.cpp:184 +#, c-format +msgid "No help available for %s." +msgstr "No help available for %s." + +#: modules/commands/os_modinfo.cpp:61 +#, c-format +msgid "No information about module %s is available." +msgstr "No information about module %s is available." + +#: modules/commands/cs_enforce.cpp:177 +#, c-format +msgid "No limit is set on %s." +msgstr "No limit is set on %s." + +#: modules/commands/os_news.cpp:37 +msgid "No logon news items to delete!" +msgstr "No logon news items to delete!" + +#: modules/commands/os_logsearch.cpp:133 +#, c-format +msgid "No matches for %s found." +msgstr "No matches for %s found." + +#: modules/commands/cs_xop.cpp:294 +#, c-format +msgid "No matching entries on %s %s list." +msgstr "No matching entries on %s %s list." + +#: modules/commands/cs_access.cpp:269 modules/commands/cs_access.cpp:433 +#: modules/commands/cs_flags.cpp:335 modules/commands/cs_xop.cpp:428 +#, c-format +msgid "No matching entries on %s access list." +msgstr "No matching entries on %s access list." + +#: modules/commands/cs_akick.cpp:224 modules/commands/cs_akick.cpp:368 +#, c-format +msgid "No matching entries on %s autokick list." +msgstr "No matching entries on %s autokick list." + +#: modules/commands/bs_badwords.cpp:166 modules/commands/bs_badwords.cpp:246 +#, c-format +msgid "No matching entries on %s bad words list." +msgstr "No matching entries on %s bad words list." + +#: modules/commands/os_session.cpp:145 modules/commands/os_session.cpp:490 +msgid "No matching entries on session-limit exception list." +msgstr "No matching entries on session-limit exception list." + +#: modules/commands/os_sxline.cpp:28 modules/commands/os_sxline.cpp:177 +#, c-format +msgid "No matching entries on the %s list." +msgstr "No matching entries on the %s list." + +#: modules/commands/os_akill.cpp:29 modules/commands/os_akill.cpp:320 +msgid "No matching entries on the AKILL list." +msgstr "No matching entries on the AKILL list." + +#: modules/commands/ms_cancel.cpp:77 +msgid "No memo was cancelable." +msgstr "No memo was cancelable." + +#: modules/commands/ms_read.cpp:65 +msgid "No memos to display." +msgstr "No memos to display." + +#: modules/commands/os_modinfo.cpp:187 +msgid "No modules currently loaded matching that criteria." +msgstr "No modules currently loaded matching that criteria." + +#: modules/commands/ns_recover.cpp:55 +msgid "No one is using your nick, and services are not holding it." +msgstr "No one is using your nick, and services are not holding it." + +#: modules/commands/os_login.cpp:30 modules/commands/os_login.cpp:77 +msgid "No oper block for your nick." +msgstr "No oper block for your nick." + +#: modules/commands/os_news.cpp:47 +msgid "No oper news items to delete!" +msgstr "No oper news items to delete!" + +#: modules/commands/os_news.cpp:57 +msgid "No random news items to delete!" +msgstr "No random news items to delete!" + +#: modules/commands/hs_list.cpp:111 +msgid "No records to display." +msgstr "No records to display." + +#: modules/commands/ns_getemail.cpp:47 +#, c-format +msgid "No registrations matching %s were found." +msgstr "No registrations matching %s were found." + +#: modules/commands/hs_request.cpp:220 modules/commands/hs_request.cpp:276 +#, c-format +msgid "No request for nick %s found." +msgstr "No request for nick %s found." + +#: src/access.cpp:55 +msgid "No signed kick when SIGNKICK LEVEL is used" +msgstr "No signed kick when SIGNKICK LEVEL is used" + +#: modules/extra/stats/cs_fantasy_top.cpp:159 +#: modules/extra/stats/cs_fantasy_stats.cpp:156 +#, c-format +msgid "No stats for %s." +msgstr "No stats for %s." + +#: modules/commands/os_info.cpp:201 +#, c-format +msgid "No such info \"%s\" on %s." +msgstr "No such info \"%s\" on %s." + +#: modules/commands/cs_ban.cpp:219 modules/commands/cs_kick.cpp:118 +#, c-format +msgid "No users on %s match %s." +msgstr "No users on %s match %s." + +#: modules/commands/bs_assign.cpp:188 +#, c-format +msgid "No-bot mode is now off on channel %s." +msgstr "No-bot mode is now off on channel %s." + +#: modules/commands/bs_assign.cpp:181 +#, c-format +msgid "No-bot mode is now on on channel %s." +msgstr "No-bot mode is now on on channel %s." + +#: modules/commands/os_mode.cpp:64 +#, c-format +msgid "Non-status modes cleared on %s." +msgstr "Non-status modes cleared on %s." + +#: modules/commands/os_dns.cpp:226 modules/commands/bs_info.cpp:58 +msgid "None" +msgstr "None" + +#: modules/commands/cs_set.cpp:1029 +#, c-format +msgid "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." +msgstr "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." + +#: modules/commands/cs_mode.cpp:380 modules/commands/cs_mode.cpp:437 +msgid "Nothing to do." +msgstr "Nothing to do." + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:201 modules/commands/ms_list.cpp:64 +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_log.cpp:127 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +#: modules/commands/ns_ajoin.cpp:100 +msgid "Number" +msgstr "Number" + +#: modules/commands/os_news.cpp:41 +msgid "OPERNEWS {ADD|DEL|LIST} [text|num]" +msgstr "OPERNEWS {ADD|DEL|LIST} [text|num]" + +#: modules/commands/ns_info.cpp:68 modules/commands/ns_info.cpp:72 +msgid "Online from" +msgstr "Online from" + +#: modules/commands/os_oper.cpp:138 +#, c-format +msgid "" +"Oper %s is configured in the configuration file(s) and can not be removed by " +"this command." +msgstr "" +"Oper %s is configured in the configuration file(s) and can not be removed by " +"this command." + +#: modules/commands/os_info.cpp:268 +msgid "Oper Info" +msgstr "Oper Info" + +#: modules/commands/os_info.cpp:182 modules/commands/os_info.cpp:221 +#, c-format +msgid "Oper info list for %s is empty." +msgstr "Oper info list for %s is empty." + +#: modules/commands/os_news.cpp:46 +#, c-format +msgid "Oper news item #%d deleted." +msgstr "Oper news item #%d deleted." + +#: modules/commands/os_news.cpp:45 +#, c-format +msgid "Oper news item #%s not found!" +msgstr "Oper news item #%s not found!" + +#: modules/commands/os_news.cpp:42 +msgid "Oper news items:" +msgstr "Oper news items:" + +#: modules/commands/os_oper.cpp:148 +#, c-format +msgid "Oper privileges removed from %s (%s)." +msgstr "Oper privileges removed from %s (%s)." + +#: modules/commands/os_oper.cpp:101 modules/commands/os_oper.cpp:189 +#, c-format +msgid "Oper type %s has not been configured." +msgstr "Oper type %s has not been configured." + +#: modules/commands/os_oline.cpp:37 +#, c-format +msgid "Operflags %s have been added for %s." +msgstr "Operflags %s have been added for %s." + +#: modules/commands/os_oline.cpp:43 +#, c-format +msgid "Operflags %s have been removed from %s." +msgstr "Operflags %s have been removed from %s." + +#: modules/commands/os_oper.cpp:193 +#, c-format +msgid "Opertype %s has no allowed commands." +msgstr "Opertype %s has no allowed commands." + +#: modules/commands/os_oper.cpp:215 +#, c-format +msgid "Opertype %s has no allowed privileges." +msgstr "Opertype %s has no allowed privileges." + +#: modules/commands/os_oper.cpp:237 +#, c-format +msgid "Opertype %s receives modes %s once identified." +msgstr "Opertype %s receives modes %s once identified." + +#: modules/commands/bs_kick.cpp:1219 +msgid "Ops protection" +msgstr "Ops protection" + +#: src/misc.cpp:258 modules/commands/bs_info.cpp:58 +msgid "Options" +msgstr "Options" + +#: modules/commands/os_dns.cpp:668 +msgid "POOL server.name" +msgstr "POOL server.name" + +#: modules/commands/cs_mode.cpp:449 +msgid "Param" +msgstr "Param" + +#: modules/commands/ns_identify.cpp:38 +msgid "Password accepted - you are now recognized." +msgstr "Password accepted - you are now recognized." + +#: modules/commands/os_login.cpp:44 +msgid "Password accepted." +msgstr "Password accepted." + +#: include/language.h:85 +msgid "Password authentication required for that command." +msgstr "Password authentication required for that command." + +#: modules/commands/ns_set.cpp:152 modules/commands/ns_set.cpp:218 +#, c-format +msgid "Password for %s changed to %s." +msgstr "Password for %s changed to %s." + +#: modules/commands/ns_set.cpp:154 modules/commands/ns_set.cpp:220 +#, c-format +msgid "Password for %s changed." +msgstr "Password for %s changed." + +#: modules/commands/ns_getpass.cpp:38 +#, c-format +msgid "Password for %s is %s." +msgstr "Password for %s is %s." + +#: include/language.h:71 +msgid "Password incorrect." +msgstr "Password incorrect." + +#: modules/commands/ns_resetpass.cpp:39 +#, c-format +msgid "Password reset email for %s has been sent." +msgstr "Password reset email for %s has been sent." + +#: modules/commands/cs_set.cpp:1289 +msgid "Peace" +msgstr "Peace" + +#: modules/commands/cs_set.cpp:440 +#, c-format +msgid "Peace option for %s is now off." +msgstr "Peace option for %s is now off." + +#: modules/commands/cs_set.cpp:434 +#, c-format +msgid "Peace option for %s is now on." +msgstr "Peace option for %s is now on." + +#: modules/commands/cs_set.cpp:1301 +msgid "Persistent" +msgstr "Persistent" + +#: include/language.h:126 +msgid "Please contact an Operator to get a vHost assigned to this nick." +msgstr "Please contact an Operator to get a vHost assigned to this nick." + +#: include/language.h:73 +msgid "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." +msgstr "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." + +#: modules/commands/os_jupe.cpp:30 +msgid "Please use a valid server name when juping." +msgstr "Please use a valid server name when juping." + +#: include/language.h:104 +msgid "Please use the symbol of # when attempting to register." +msgstr "Please use the symbol of # when attempting to register." + +#: src/mail.cpp:78 +#, c-format +msgid "Please wait %d seconds and retry." +msgstr "Please wait %d seconds and retry." + +#: modules/commands/hs_request.cpp:158 +#, c-format +msgid "Please wait %d seconds before requesting a new vHost." +msgstr "Please wait %d seconds before requesting a new vHost." + +#: modules/commands/ms_rsend.cpp:58 modules/commands/ms_send.cpp:57 +#, c-format +msgid "Please wait %d seconds before using the %s command again." +msgstr "Please wait %d seconds before using the %s command again." + +#: modules/commands/ns_group.cpp:149 +#, c-format +msgid "Please wait %d seconds before using the GROUP command again." +msgstr "Please wait %d seconds before using the GROUP command again." + +#: modules/commands/ns_register.cpp:198 +#, c-format +msgid "Please wait %d seconds before using the REGISTER command again." +msgstr "Please wait %d seconds before using the REGISTER command again." + +#: modules/commands/os_dns.cpp:628 +#, c-format +msgid "Pooled %s." +msgstr "Pooled %s." + +#: modules/commands/os_dns.cpp:237 +msgid "Pooled/Active" +msgstr "Pooled/Active" + +#: modules/commands/os_dns.cpp:239 +msgid "Pooled/Not Active" +msgstr "Pooled/Not Active" + +#: modules/commands/bs_set.cpp:161 +msgid "Prevent a bot from being assigned by non IRC operators" +msgstr "Prevent a bot from being assigned by non IRC operators" + +#: modules/commands/bs_assign.cpp:153 +msgid "Prevent a bot from being assigned to a channel" +msgstr "Prevent a bot from being assigned to a channel" + +#: modules/commands/cs_suspend.cpp:58 +msgid "Prevent a channel from being used preserving channel data and settings" +msgstr "Prevent a channel from being used preserving channel data and settings" + +#: modules/commands/cs_set.cpp:1043 +msgid "Prevent the channel from expiring" +msgstr "Prevent the channel from expiring" + +#: modules/commands/ns_list.cpp:186 +msgid "Prevent the nickname from appearing in the LIST command" +msgstr "Prevent the nickname from appearing in the LIST command" + +#: modules/commands/ns_set.cpp:1104 +msgid "Prevent the nickname from expiring" +msgstr "Prevent the nickname from expiring" + +#: src/access.cpp:46 +msgid "Prevents users being kicked by Services" +msgstr "Prevents users being kicked by Services" + +#: modules/commands/ns_list.cpp:297 modules/commands/cs_list.cpp:262 +#: modules/commands/bs_info.cpp:58 +msgid "Private" +msgstr "Private" + +#: modules/commands/bs_set.cpp:190 +#, c-format +msgid "Private mode of bot %s is now off." +msgstr "Private mode of bot %s is now off." + +#: modules/commands/bs_set.cpp:185 +#, c-format +msgid "Private mode of bot %s is now on." +msgstr "Private mode of bot %s is now on." + +#: modules/commands/cs_list.cpp:220 +#, c-format +msgid "Private option for %s is now off." +msgstr "Private option for %s is now off." + +#: modules/commands/cs_list.cpp:214 +#, c-format +msgid "Private option for %s is now on." +msgstr "Private option for %s is now on." + +#: modules/commands/ns_list.cpp:221 +#, c-format +msgid "Private option is now off for %s." +msgstr "Private option is now off for %s." + +#: modules/commands/ns_list.cpp:215 +#, c-format +msgid "Private option is now on for %s." +msgstr "Private option is now on for %s." + +#: modules/commands/cs_flags.cpp:281 +#, c-format +msgid "Privilege %s added to %s on %s, new flags are +%s" +msgstr "Privilege %s added to %s on %s, new flags are +%s" + +#: modules/commands/cs_flags.cpp:283 +#, c-format +msgid "Privilege %s removed from %s on %s, new flags are +%s" +msgstr "Privilege %s removed from %s on %s, new flags are +%s" + +#: modules/commands/ns_set.cpp:1309 +msgid "Protection" +msgstr "Protection" + +#: modules/commands/ns_set.cpp:721 +#, c-format +msgid "Protection is now off for %s." +msgstr "Protection is now off for %s." + +#: modules/commands/ns_set.cpp:700 +#, c-format +msgid "Protection is now on for %s, with a reduced delay." +msgstr "Protection is now on for %s, with a reduced delay." + +#: modules/commands/ns_set.cpp:710 +#, c-format +msgid "Protection is now on for %s, with no delay." +msgstr "Protection is now on for %s, with no delay." + +#: modules/commands/ns_set.cpp:692 +#, c-format +msgid "Protection is now on for %s." +msgstr "Protection is now on for %s." + +#: modules/commands/os_chankill.cpp:100 +msgid "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." +msgstr "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." + +#: modules/commands/ns_set.cpp:1307 +msgid "Quick protection" +msgstr "Quick protection" + +#: modules/commands/os_news.cpp:51 +msgid "RANDOMNEWS {ADD|DEL|LIST} [text|num]" +msgstr "RANDOMNEWS {ADD|DEL|LIST} [text|num]" + +#: modules/commands/cs_enforce.cpp:99 +msgid "REGONLY enforced by " +msgstr "REGONLY enforced by " + +#: modules/commands/cs_enforce.cpp:68 +msgid "RESTRICTED enforced by " +msgstr "RESTRICTED enforced by " + +#: modules/commands/os_noop.cpp:21 +msgid "REVOKE server" +msgstr "REVOKE server" + +#: modules/commands/os_news.cpp:56 +#, c-format +msgid "Random news item #%d deleted." +msgstr "Random news item #%d deleted." + +#: modules/commands/os_news.cpp:55 +#, c-format +msgid "Random news item #%s not found!" +msgstr "Random news item #%s not found!" + +#: modules/commands/os_news.cpp:52 +msgid "Random news items:" +msgstr "Random news items:" + +#: modules/commands/ms_read.cpp:112 +msgid "Read a memo or memos" +msgstr "Read a memo or memos" + +#: modules/commands/bs_info.cpp:56 +msgid "Real name" +msgstr "Real name" + +#: modules/commands/os_list.cpp:153 +msgid "Realname" +msgstr "Realname" + +#: modules/commands/os_ignore.cpp:266 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:204 modules/commands/os_forbid.cpp:358 +#: modules/commands/cs_akick.cpp:392 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:361 +msgid "Reason" +msgstr "Reason" + +#: src/xline.cpp:386 +#, c-format +msgid "Reason for %s updated." +msgstr "Reason for %s updated." + +#: modules/commands/ns_recover.cpp:214 +msgid "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." +msgstr "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." + +#: modules/commands/cs_access.cpp:741 +msgid "Redefine the meanings of access levels" +msgstr "Redefine the meanings of access levels" + +#: modules/commands/ns_recover.cpp:149 +msgid "Regains control of your nick" +msgstr "Regains control of your nick" + +#: modules/commands/os_sxline.cpp:330 modules/commands/os_sxline.cpp:545 +#: modules/commands/os_akill.cpp:129 +msgid "Regex is disabled." +msgstr "Regex is disabled." + +#: modules/commands/os_sxline.cpp:459 modules/commands/os_sxline.cpp:694 +#: modules/commands/os_akill.cpp:444 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." +msgstr "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." + +#: modules/commands/os_ignore.cpp:386 modules/commands/os_forbid.cpp:428 +#: modules/commands/ns_list.cpp:172 modules/commands/cs_list.cpp:167 +#: modules/commands/os_list.cpp:119 modules/commands/os_list.cpp:255 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." +msgstr "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." + +#: modules/commands/cs_register.cpp:19 +msgid "Register a channel" +msgstr "Register a channel" + +#: modules/commands/ns_register.cpp:120 +msgid "Register a nickname" +msgstr "Register a nickname" + +#: modules/commands/ns_info.cpp:89 modules/commands/cs_info.cpp:55 +msgid "Registered" +msgstr "Registered" + +#: modules/commands/os_stats.cpp:184 +#, c-format +msgid "Registered channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "Registered channels: %lu entries, %lu buckets, longest chain is %d" + +#: modules/commands/os_stats.cpp:190 +#, c-format +msgid "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" +msgstr "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" + +#: modules/commands/os_stats.cpp:187 +#, c-format +msgid "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" +msgstr "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" + +#: modules/commands/cs_enforce.cpp:105 +#, c-format +msgid "Registered only enforced on %s." +msgstr "Registered only enforced on %s." + +#: modules/commands/cs_register.cpp:86 +#, c-format +msgid "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." +msgstr "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." + +#: modules/commands/ns_register.cpp:269 +#, c-format +msgid "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." +msgstr "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." + +#: modules/commands/ns_register.cpp:145 +msgid "Registration is currently disabled." +msgstr "Registration is currently disabled." + +#: modules/commands/cs_set.cpp:400 +msgid "Regulate the use of critical commands" +msgstr "Regulate the use of critical commands" + +#: modules/commands/hs_request.cpp:283 +msgid "Reject the requested vHost for the given nick." +msgstr "Reject the requested vHost for the given nick." + +#: modules/commands/hs_request.cpp:240 +msgid "Reject the requested vHost of a user" +msgstr "Reject the requested vHost of a user" + +#: modules/commands/cs_suspend.cpp:151 +msgid "Releases a suspended channel" +msgstr "Releases a suspended channel" + +#: modules/commands/cs_suspend.cpp:191 +msgid "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." +msgstr "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." + +#: modules/commands/os_module.cpp:56 +msgid "Reload a module" +msgstr "Reload a module" + +#: modules/commands/os_reload.cpp:19 +msgid "Reload services' configuration file" +msgstr "Reload services' configuration file" + +#: modules/commands/ns_group.cpp:236 +msgid "Remove a nick from a group" +msgstr "Remove a nick from a group" + +#: modules/commands/cs_unban.cpp:19 +msgid "Remove all bans preventing a user from entering a channel" +msgstr "Remove all bans preventing a user from entering a channel" + +#: modules/commands/os_noop.cpp:19 +msgid "Remove all operators from a server remotely" +msgstr "Remove all operators from a server remotely" + +#: modules/commands/os_dns.cpp:543 +#, c-format +msgid "Removed IP %s from %s." +msgstr "Removed IP %s from %s." + +#: modules/commands/os_dns.cpp:460 +#, c-format +msgid "Removed server %s from zone %s." +msgstr "Removed server %s from zone %s." + +#: modules/commands/os_dns.cpp:483 +#, c-format +msgid "Removed server %s." +msgstr "Removed server %s." + +#: modules/commands/cs_mode.cpp:909 +#, c-format +msgid "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." +msgstr "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." + +#: modules/commands/cs_mode.cpp:890 +#, c-format +msgid "Removes %s status from you or the specified nick on a channel" +msgstr "Removes %s status from you or the specified nick on a channel" + +#: modules/commands/cs_updown.cpp:146 +msgid "Removes a selected nicks status from a channel" +msgstr "Removes a selected nicks status from a channel" + +#: modules/commands/cs_updown.cpp:223 +msgid "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." +msgstr "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." + +#: src/xline.cpp:412 +#, c-format +msgid "Removing %s because %s covers it." +msgstr "Removing %s because %s covers it." + +#: modules/commands/bs_kick.cpp:1171 modules/commands/bs_kick.cpp:1173 +#: modules/commands/bs_kick.cpp:1176 +msgid "Repeat kicker" +msgstr "Repeat kicker" + +#: modules/commands/hs_request.cpp:78 +msgid "Request a vHost for your nick" +msgstr "Request a vHost for your nick" + +#: modules/commands/hs_request.cpp:179 +msgid "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." +msgstr "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." + +#: modules/commands/ns_register.cpp:312 +msgid "Resend registration confirmation email" +msgstr "Resend registration confirmation email" + +#: modules/commands/cs_set.cpp:621 +msgid "Restrict access to the channel" +msgstr "Restrict access to the channel" + +#: modules/commands/cs_set.cpp:1291 +msgid "Restricted access" +msgstr "Restricted access" + +#: modules/commands/cs_set.cpp:661 +#, c-format +msgid "Restricted access option for %s is now off." +msgstr "Restricted access option for %s is now off." + +#: modules/commands/cs_set.cpp:655 +#, c-format +msgid "Restricted access option for %s is now on." +msgstr "Restricted access option for %s is now on." + +#: modules/commands/cs_enforce.cpp:73 +#, c-format +msgid "Restricted enforced on %s." +msgstr "Restricted enforced on %s." + +#: modules/commands/cs_set.cpp:335 +msgid "Retain modes when channel is not in use" +msgstr "Retain modes when channel is not in use" + +#: modules/commands/cs_topic.cpp:20 +msgid "Retain topic when channel is not in use" +msgstr "Retain topic when channel is not in use" + +#: modules/commands/ns_getpass.cpp:19 +msgid "Retrieve the password for a nickname" +msgstr "Retrieve the password for a nickname" + +#: modules/commands/hs_request.cpp:296 +msgid "Retrieves the vhost requests" +msgstr "Retrieves the vhost requests" + +#: modules/commands/cs_getkey.cpp:19 +msgid "Returns the key of the given channel" +msgstr "Returns the key of the given channel" + +#: modules/commands/cs_getkey.cpp:57 +msgid "Returns the key of the given channel." +msgstr "Returns the key of the given channel." + +#: modules/commands/ns_getemail.cpp:58 +msgid "Returns the matching accounts that used given email." +msgstr "Returns the matching accounts that used given email." + +#: modules/commands/ns_status.cpp:19 +msgid "Returns the owner status of the given nickname" +msgstr "Returns the owner status of the given nickname" + +#: modules/commands/ns_getpass.cpp:50 +msgid "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." +msgstr "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." + +#: modules/commands/ns_status.cpp:55 +msgid "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." +msgstr "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." + +#: modules/commands/bs_kick.cpp:1181 modules/commands/bs_kick.cpp:1183 +#: modules/commands/bs_kick.cpp:1186 +msgid "Reverses kicker" +msgstr "Reverses kicker" + +#: modules/commands/ns_logout.cpp:21 +msgid "Reverses the effect of the IDENTIFY command" +msgstr "Reverses the effect of the IDENTIFY command" + +#: modules/commands/os_noop.cpp:20 +msgid "SET server" +msgstr "SET server" + +#: modules/commands/os_dns.cpp:667 +msgid "SET server.name option value" +msgstr "SET server.name option value" + +#: modules/commands/ns_cert.cpp:378 +#, c-format +msgid "SSL certificate fingerprint accepted, you are now identified to %s." +msgstr "SSL certificate fingerprint accepted, you are now identified to %s." + +#: modules/commands/ns_cert.cpp:398 +msgid "SSL certificate fingerprint accepted, you are now identified." +msgstr "SSL certificate fingerprint accepted, you are now identified." + +#: modules/commands/cs_enforce.cpp:137 +#, c-format +msgid "SSL only enforced on %s." +msgstr "SSL only enforced on %s." + +#: modules/commands/cs_enforce.cpp:131 +msgid "SSLONLY enforced by " +msgstr "SSLONLY enforced by " + +#: modules/commands/os_shutdown.cpp:47 +msgid "Save databases and restart Services" +msgstr "Save databases and restart Services" + +#: modules/commands/os_logsearch.cpp:32 +msgid "Searches logs for a matching pattern" +msgstr "Searches logs for a matching pattern" + +#: modules/commands/cs_set.cpp:1295 +msgid "Secure founder" +msgstr "Secure founder" + +#: modules/commands/cs_set.cpp:786 +#, c-format +msgid "Secure founder option for %s is now off." +msgstr "Secure founder option for %s is now off." + +#: modules/commands/cs_set.cpp:780 +#, c-format +msgid "Secure founder option for %s is now on." +msgstr "Secure founder option for %s is now on." + +#: modules/commands/cs_set.cpp:1297 +msgid "Secure ops" +msgstr "Secure ops" + +#: modules/commands/cs_set.cpp:850 +#, c-format +msgid "Secure ops option for %s is now off." +msgstr "Secure ops option for %s is now off." + +#: modules/commands/cs_set.cpp:844 +#, c-format +msgid "Secure ops option for %s is now on." +msgstr "Secure ops option for %s is now on." + +#: modules/commands/cs_set.cpp:723 +#, c-format +msgid "Secure option for %s is now off." +msgstr "Secure option for %s is now off." + +#: modules/commands/cs_set.cpp:717 +#, c-format +msgid "Secure option for %s is now on." +msgstr "Secure option for %s is now on." + +#: modules/commands/ns_set.cpp:1044 +#, c-format +msgid "Secure option is now off for %s." +msgstr "Secure option is now off for %s." + +#: modules/commands/ns_set.cpp:1038 +#, c-format +msgid "Secure option is now on for %s." +msgstr "Secure option is now on for %s." + +#: modules/commands/cs_enforce.cpp:42 +#, c-format +msgid "Secureops enforced on %s." +msgstr "Secureops enforced on %s." + +#: modules/commands/cs_set.cpp:1293 modules/commands/ns_set.cpp:1311 +msgid "Security" +msgstr "Security" + +#: modules/commands/cs_xop.cpp:570 +#, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the access list." +msgstr "" +"See %s%s HELP %s for more information\n" +"about the access list." + +#: modules/commands/cs_xop.cpp:573 +#, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the flags system." +msgstr "" +"See %s%s HELP %s for more information\n" +"about the flags system." + +#: modules/commands/ms_send.cpp:24 +msgid "Send a memo to a nick or channel" +msgstr "Send a memo to a nick or channel" + +#: modules/commands/ms_staff.cpp:24 +msgid "Send a memo to all opers/admins" +msgstr "Send a memo to all opers/admins" + +#: modules/commands/ms_sendall.cpp:24 +msgid "Send a memo to all registered users" +msgstr "Send a memo to all registered users" + +#: modules/commands/gl_global.cpp:21 +msgid "Send a message to all users" +msgstr "Send a message to all users" + +#: modules/commands/ms_list.cpp:64 +msgid "Sender" +msgstr "Sender" + +#: modules/commands/ms_rsend.cpp:24 +msgid "Sends a memo and requests a read receipt" +msgstr "Sends a memo and requests a read receipt" + +#: modules/commands/ns_resetpass.cpp:50 +msgid "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." +msgstr "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." + +#: modules/commands/ms_sendall.cpp:52 +msgid "Sends all registered users a memo containing memo-text." +msgstr "Sends all registered users a memo containing memo-text." + +#: modules/commands/ms_staff.cpp:48 +msgid "Sends all services staff a memo containing memo-text." +msgstr "Sends all services staff a memo containing memo-text." + +#: modules/commands/ms_send.cpp:66 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." +msgstr "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." + +#: modules/commands/ms_rsend.cpp:80 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." +msgstr "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." + +#: modules/commands/ms_read.cpp:199 +msgid "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." + +#: modules/commands/os_dns.cpp:218 +msgid "Server" +msgstr "Server" + +#: modules/commands/os_dns.cpp:375 +#, c-format +msgid "Server %s added to zone %s." +msgstr "Server %s added to zone %s." + +#: modules/commands/os_dns.cpp:345 +#, c-format +msgid "Server %s already exists." +msgstr "Server %s already exists." + +#: modules/commands/os_noop.cpp:31 modules/commands/os_dns.cpp:430 +#: modules/commands/os_dns.cpp:493 modules/commands/os_dns.cpp:532 +#: modules/commands/os_dns.cpp:571 modules/commands/os_dns.cpp:604 +#: modules/commands/os_dns.cpp:639 +#, c-format +msgid "Server %s does not exist." +msgstr "Server %s does not exist." + +#: modules/commands/os_dns.cpp:619 +#, c-format +msgid "Server %s has no configured IPs." +msgstr "Server %s has no configured IPs." + +#: modules/commands/os_dns.cpp:357 +#, c-format +msgid "Server %s is already in zone %s." +msgstr "Server %s is already in zone %s." + +#: modules/commands/os_dns.cpp:614 +#, c-format +msgid "Server %s is already pooled." +msgstr "Server %s is already pooled." + +#: modules/commands/os_dns.cpp:609 +#, c-format +msgid "Server %s is not currently linked." +msgstr "Server %s is not currently linked." + +#: modules/commands/os_dns.cpp:443 +#, c-format +msgid "Server %s is not in zone %s." +msgstr "Server %s is not in zone %s." + +#: modules/commands/os_dns.cpp:384 +#, c-format +msgid "Server %s is not linked to the network." +msgstr "Server %s is not linked to the network." + +#: modules/commands/os_dns.cpp:644 +#, c-format +msgid "Server %s is not pooled." +msgstr "Server %s is not pooled." + +#: modules/commands/os_dns.cpp:465 +#, c-format +msgid "Server %s must be quit before it can be deleted." +msgstr "Server %s must be quit before it can be deleted." + +#: modules/commands/os_dns.cpp:255 +msgid "Servers" +msgstr "Servers" + +#: modules/commands/os_stats.cpp:155 +#, c-format +msgid "Servers found: %d" +msgstr "Servers found: %d" + +#: modules/commands/cs_log.cpp:127 +msgid "Service" +msgstr "Service" + +#: modules/commands/ns_recover.cpp:51 +#, c-format +msgid "Service's hold on %s has been released." +msgstr "Service's hold on %s has been released." + +#: data/nickserv.example.conf:236 data/chanserv.example.conf:827 +msgid "Services Operator commands" +msgstr "Services Operator commands" + +#: modules/commands/os_defcon.cpp:443 modules/commands/os_defcon.cpp:454 +#: modules/commands/os_defcon.cpp:462 modules/commands/os_defcon.cpp:470 +#: modules/commands/os_defcon.cpp:478 +msgid "Services are in DefCon mode, please try again later." +msgstr "Services are in DefCon mode, please try again later." + +#: include/language.h:70 +msgid "Services are in read-only mode!" +msgstr "Services are in read-only mode!" + +#: modules/commands/os_defcon.cpp:186 modules/commands/os_defcon.cpp:213 +#, c-format +msgid "Services are now at DEFCON %d." +msgstr "Services are now at DEFCON %d." + +#: modules/commands/os_set.cpp:128 +#, c-format +msgid "Services are now in debug mode (level %d)." +msgstr "Services are now in debug mode (level %d)." + +#: modules/commands/os_set.cpp:114 +msgid "Services are now in debug mode." +msgstr "Services are now in debug mode." + +#: modules/commands/os_set.cpp:159 +msgid "Services are now in expire mode." +msgstr "Services are now in expire mode." + +#: modules/commands/os_set.cpp:153 +msgid "Services are now in no expire mode." +msgstr "Services are now in no expire mode." + +#: modules/commands/os_set.cpp:120 +msgid "Services are now in non-debug mode." +msgstr "Services are now in non-debug mode." + +#: modules/commands/os_set.cpp:47 +msgid "Services are now in read-only mode." +msgstr "Services are now in read-only mode." + +#: modules/commands/os_set.cpp:53 +msgid "Services are now in read-write mode." +msgstr "Services are now in read-write mode." + +#: src/mail.cpp:76 +msgid "Services have been configured to not send mail." +msgstr "Services have been configured to not send mail." + +#: modules/commands/os_ignore.cpp:280 +msgid "Services ignore list:" +msgstr "Services ignore list:" + +#: modules/commands/os_mode.cpp:33 modules/commands/os_kick.cpp:39 +msgid "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" +msgstr "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" + +#: modules/commands/os_stats.cpp:140 +#, c-format +msgid "Services up %s." +msgstr "Services up %s." + +#: modules/commands/ns_set.cpp:266 +#, c-format +msgid "Services will from now on set status modes on %s in channels." +msgstr "Services will from now on set status modes on %s in channels." + +#: modules/commands/cs_set.cpp:114 +#, c-format +msgid "Services will no longer automatically give modes to users in %s." +msgstr "Services will no longer automatically give modes to users in %s." + +#: modules/commands/ns_set.cpp:272 +#, c-format +msgid "Services will no longer set status modes on %s in channels." +msgstr "Services will no longer set status modes on %s in channels." + +#: modules/commands/cs_set.cpp:108 +#, c-format +msgid "Services will now automatically give modes to users in %s." +msgstr "Services will now automatically give modes to users in %s." + +#: modules/commands/ns_set.cpp:940 +#, c-format +msgid "Services will now reply to %s with messages." +msgstr "Services will now reply to %s with messages." + +#: modules/commands/ns_set.cpp:946 +#, c-format +msgid "Services will now reply to %s with notices." +msgstr "Services will now reply to %s with notices." + +#: modules/commands/os_reload.cpp:34 +msgid "Services' configuration has been reloaded." +msgstr "Services' configuration has been reloaded." + +#: modules/commands/os_session.cpp:192 +msgid "Session" +msgstr "Session" + +#: modules/commands/os_session.cpp:382 +#, c-format +msgid "Session limit for %s set to %d." +msgstr "Session limit for %s set to %d." + +#: modules/commands/os_session.cpp:257 modules/commands/os_session.cpp:534 +msgid "Session limiting is disabled." +msgstr "Session limiting is disabled." + +#: modules/commands/os_stats.cpp:195 +#, c-format +msgid "Sessions: %lu entries, %lu buckets, longest chain is %d" +msgstr "Sessions: %lu entries, %lu buckets, longest chain is %d" + +#: modules/commands/ns_set.cpp:74 +msgid "Set SET-options on another nickname" +msgstr "Set SET-options on another nickname" + +#: modules/commands/cs_set.cpp:20 +msgid "Set channel options and information" +msgstr "Set channel options and information" + +#: modules/commands/cs_set.cpp:137 +msgid "Set how Services make bans on the channel" +msgstr "Set how Services make bans on the channel" + +#: modules/commands/ms_set.cpp:206 +msgid "Set options related to memos" +msgstr "Set options related to memos" + +#: modules/commands/ns_set.cpp:19 +msgid "Set options, including kill protection" +msgstr "Set options, including kill protection" + +#: modules/commands/cs_set.cpp:472 +msgid "Set the channel as permanent" +msgstr "Set the channel as permanent" + +#: modules/commands/cs_set.cpp:204 +msgid "Set the channel description" +msgstr "Set the channel description" + +#: modules/commands/ns_set.cpp:329 +msgid "Set the display of your group in Services" +msgstr "Set the display of your group in Services" + +#: modules/commands/cs_set.cpp:266 +msgid "Set the founder of a channel" +msgstr "Set the founder of a channel" + +#: modules/commands/ns_set.cpp:793 +msgid "Set the language Services will use when messaging you" +msgstr "Set the language Services will use when messaging you" + +#: modules/commands/ns_set.cpp:172 +msgid "Set the nickname password" +msgstr "Set the nickname password" + +#: modules/commands/cs_set.cpp:949 +msgid "Set the successor for a channel" +msgstr "Set the successor for a channel" + +#: modules/commands/hs_set.cpp:125 +msgid "Set the vhost for all nicks in a group" +msgstr "Set the vhost for all nicks in a group" + +#: modules/commands/hs_set.cpp:19 +msgid "Set the vhost of another user" +msgstr "Set the vhost of another user" + +#: modules/commands/os_set.cpp:169 +msgid "Set various global Services options" +msgstr "Set various global Services options" + +#: modules/commands/ns_set.cpp:119 +msgid "Set your nickname password" +msgstr "Set your nickname password" + +#: modules/commands/bs_kick.cpp:271 +#, c-format +msgid "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:307 +#, c-format +msgid "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/cs_set.cpp:186 +msgid "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" +msgstr "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" + +#: modules/commands/bs_kick.cpp:345 +msgid "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:436 +#, c-format +msgid "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:475 +msgid "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/cs_set.cpp:255 +msgid "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." +msgstr "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." + +#: modules/commands/bs_kick.cpp:571 +msgid "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:607 +msgid "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:706 +msgid "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:742 +msgid "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:776 +msgid "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/hs_set.cpp:206 +msgid "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." +msgstr "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." + +#: modules/commands/hs_set.cpp:99 +msgid "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." +msgstr "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." + +#: modules/commands/os_set.cpp:199 +msgid "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" +msgstr "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" + +#: modules/commands/ms_set.cpp:235 +#, c-format +msgid "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." + +#: modules/commands/ns_set.cpp:33 modules/commands/ns_set.cpp:88 +msgid "Sets various nickname options. option can be one of:" +msgstr "Sets various nickname options. option can be one of:" + +#: modules/commands/ns_set.cpp:237 +msgid "" +"Sets whether services should set channel status modes on you automatically." +msgstr "" +"Sets whether services should set channel status modes on you automatically." + +#: modules/commands/cs_set.cpp:1090 +msgid "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." +msgstr "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." + +#: modules/commands/ns_set.cpp:315 +#, c-format +msgid "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." +msgstr "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." + +#: modules/commands/ns_set.cpp:1145 +msgid "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." +msgstr "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." + +#: modules/commands/ns_set.cpp:288 +#, c-format +msgid "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." +msgstr "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." + +#: modules/commands/cs_access.cpp:648 modules/commands/cs_access.cpp:689 +#, c-format +msgid "" +"Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." +msgstr "" +"Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." + +#: modules/commands/os_set.cpp:133 +msgid "Setting for DEBUG must be ON, OFF, or a positive number." +msgstr "Setting for DEBUG must be ON, OFF, or a positive number." + +#: modules/commands/os_set.cpp:162 +msgid "Setting for NOEXPIRE must be ON or OFF." +msgstr "Setting for NOEXPIRE must be ON or OFF." + +#: modules/commands/os_set.cpp:56 +msgid "Setting for READONLY must be ON or OFF." +msgstr "Setting for READONLY must be ON or OFF." + +#: modules/commands/os_set.cpp:95 +msgid "Setting for super admin must be ON or OFF." +msgstr "Setting for super admin must be ON or OFF." + +#: modules/commands/cs_set.cpp:74 +msgid "Should services automatically give status to users" +msgstr "Should services automatically give status to users" + +#: modules/commands/os_stats.cpp:203 +msgid "Show status of Services and network" +msgstr "Show status of Services and network" + +#: modules/commands/os_logsearch.cpp:152 +#, c-format +msgid "Showed %d/%d matches for %s." +msgstr "Showed %d/%d matches for %s." + +#: modules/commands/cs_set.cpp:872 +msgid "Sign kicks that are done with the KICK command" +msgstr "Sign kicks that are done with the KICK command" + +#: modules/commands/cs_set.cpp:921 +#, c-format +msgid "Signed kick option for %s is now off." +msgstr "Signed kick option for %s is now off." + +#: modules/commands/cs_set.cpp:913 +#, c-format +msgid "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." +msgstr "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." + +#: modules/commands/cs_set.cpp:906 +#, c-format +msgid "Signed kick option for %s is now on." +msgstr "Signed kick option for %s is now on." + +#: modules/commands/cs_set.cpp:1299 +msgid "Signed kicks" +msgstr "Signed kicks" + +#: modules/commands/ms_rsend.cpp:60 modules/commands/ms_send.cpp:59 +#, c-format +msgid "Sorry, %s currently has too many memos and cannot receive more." +msgstr "Sorry, %s currently has too many memos and cannot receive more." + +#: modules/commands/cs_seen.cpp:294 +#, c-format +msgid "Sorry, I have not seen %s." +msgstr "Sorry, I have not seen %s." + +#: modules/commands/bs_badwords.cpp:404 +msgid "Sorry, bad words list modification is temporarily disabled." +msgstr "Sorry, bad words list modification is temporarily disabled." + +#: modules/commands/bs_assign.cpp:30 modules/commands/bs_assign.cpp:98 +msgid "Sorry, bot assignment is temporarily disabled." +msgstr "Sorry, bot assignment is temporarily disabled." + +#: modules/commands/bs_bot.cpp:281 modules/commands/bs_assign.cpp:164 +msgid "Sorry, bot modification is temporarily disabled." +msgstr "Sorry, bot modification is temporarily disabled." + +#: modules/fantasy.cpp:42 modules/commands/bs_kick.cpp:813 +#: modules/commands/bs_kick.cpp:878 +msgid "Sorry, bot option setting is temporarily disabled." +msgstr "Sorry, bot option setting is temporarily disabled." + +#: modules/commands/bs_set.cpp:115 +msgid "Sorry, changing bot options is temporarily disabled." +msgstr "Sorry, changing bot options is temporarily disabled." + +#: modules/commands/cs_xop.cpp:112 modules/commands/cs_xop.cpp:235 +#: modules/commands/cs_xop.cpp:444 +#, c-format +msgid "Sorry, channel %s list modification is temporarily disabled." +msgstr "Sorry, channel %s list modification is temporarily disabled." + +#: modules/commands/cs_access.cpp:547 modules/commands/cs_flags.cpp:405 +msgid "Sorry, channel access list modification is temporarily disabled." +msgstr "Sorry, channel access list modification is temporarily disabled." + +#: modules/commands/cs_akick.cpp:469 +msgid "Sorry, channel autokick list modification is temporarily disabled." +msgstr "Sorry, channel autokick list modification is temporarily disabled." + +#: modules/commands/cs_drop.cpp:29 +msgid "Sorry, channel de-registration is temporarily disabled." +msgstr "Sorry, channel de-registration is temporarily disabled." + +#: modules/commands/cs_register.cpp:35 +msgid "Sorry, channel registration is temporarily disabled." +msgstr "Sorry, channel registration is temporarily disabled." + +#: modules/commands/bs_kick.cpp:181 +msgid "Sorry, kicker configuration is temporarily disabled." +msgstr "Sorry, kicker configuration is temporarily disabled." + +#: modules/commands/ms_set.cpp:216 +msgid "Sorry, memo option setting is temporarily disabled." +msgstr "Sorry, memo option setting is temporarily disabled." + +#: include/language.h:116 +msgid "Sorry, memo sending is temporarily disabled." +msgstr "Sorry, memo sending is temporarily disabled." + +#: modules/commands/ns_drop.cpp:29 +msgid "Sorry, nickname de-registration is temporarily disabled." +msgstr "Sorry, nickname de-registration is temporarily disabled." + +#: modules/commands/ns_group.cpp:120 +msgid "Sorry, nickname grouping is temporarily disabled." +msgstr "Sorry, nickname grouping is temporarily disabled." + +#: modules/commands/ns_register.cpp:139 +msgid "Sorry, nickname registration is temporarily disabled." +msgstr "Sorry, nickname registration is temporarily disabled." + +#: modules/commands/ns_access.cpp:33 +#, c-format +msgid "Sorry, the maximum of %d access entries has been reached." +msgstr "Sorry, the maximum of %d access entries has been reached." + +#: modules/commands/ns_ajoin.cpp:141 +#, c-format +msgid "Sorry, the maximum of %d auto join entries has been reached." +msgstr "Sorry, the maximum of %d auto join entries has been reached." + +#: modules/commands/ns_cert.cpp:173 +#, c-format +msgid "Sorry, the maximum of %d certificate entries has been reached." +msgstr "Sorry, the maximum of %d certificate entries has been reached." + +#: modules/commands/ms_ignore.cpp:55 +#, c-format +msgid "Sorry, the memo ignore list for %s is full." +msgstr "Sorry, the memo ignore list for %s is full." + +#: modules/commands/cs_access.cpp:204 modules/commands/cs_flags.cpp:174 +#: modules/commands/cs_xop.cpp:201 +#, c-format +msgid "" +"Sorry, you can only have %d access entries on a channel, including access " +"entries from other channels." +msgstr "" +"Sorry, you can only have %d access entries on a channel, including access " +"entries from other channels." + +#: modules/commands/cs_akick.cpp:177 +#, c-format +msgid "Sorry, you can only have %d autokick masks on a channel." +msgstr "Sorry, you can only have %d autokick masks on a channel." + +#: modules/commands/bs_badwords.cpp:286 +#, c-format +msgid "Sorry, you can only have %d bad words entries on a channel." +msgstr "Sorry, you can only have %d bad words entries on a channel." + +#: include/language.h:103 +#, c-format +msgid "Sorry, you have already exceeded your limit of %d channels." +msgstr "Sorry, you have already exceeded your limit of %d channels." + +#: include/language.h:102 +#, c-format +msgid "Sorry, you have already reached your limit of %d channels." +msgstr "Sorry, you have already reached your limit of %d channels." + +#: modules/commands/os_dns.cpp:218 +msgid "State" +msgstr "State" + +#: modules/commands/cs_seen.cpp:117 +msgid "Statistics and maintenance for seen data" +msgstr "Statistics and maintenance for seen data" + +#: modules/commands/os_stats.cpp:131 +msgid "Statistics reset." +msgstr "Statistics reset." + +#: modules/commands/ns_update.cpp:36 +msgid "Status updated (memos, vhost, chmodes, flags)." +msgstr "Status updated (memos, vhost, chmodes, flags)." + +#: modules/commands/bs_kick.cpp:1432 +msgid "Stop flooding!" +msgstr "Stop flooding!" + +#: modules/commands/bs_kick.cpp:1448 +msgid "Stop repeating yourself!" +msgstr "Stop repeating yourself!" + +#: modules/commands/cs_set.cpp:746 +msgid "Stricter control of channel founder status" +msgstr "Stricter control of channel founder status" + +#: modules/commands/cs_set.cpp:810 +msgid "Stricter control of chanop status" +msgstr "Stricter control of chanop status" + +#: modules/commands/ns_alist.cpp:75 modules/commands/cs_info.cpp:50 +msgid "Successor" +msgstr "Successor" + +#: modules/commands/cs_set.cpp:1006 +#, c-format +msgid "Successor for %s changed to %s." +msgstr "Successor for %s changed to %s." + +#: modules/commands/cs_set.cpp:1008 +#, c-format +msgid "Successor for %s unset." +msgstr "Successor for %s unset." + +#: modules/commands/os_set.cpp:81 +msgid "" +"Super admin can not be set because it is not enabled in the configuration." +msgstr "" +"Super admin can not be set because it is not enabled in the configuration." + +#: modules/commands/ns_suspend.cpp:60 +msgid "Suspend a given nick" +msgstr "Suspend a given nick" + +#: modules/commands/cs_suspend.cpp:236 modules/commands/ns_suspend.cpp:250 +msgid "Suspend reason" +msgstr "Suspend reason" + +#: modules/commands/cs_suspend.cpp:232 modules/commands/ns_suspend.cpp:246 +msgid "Suspended" +msgstr "Suspended" + +#: modules/commands/cs_suspend.cpp:234 modules/commands/ns_suspend.cpp:248 +msgid "Suspended by" +msgstr "Suspended by" + +#: modules/commands/cs_suspend.cpp:238 modules/commands/ns_suspend.cpp:252 +msgid "Suspended on" +msgstr "Suspended on" + +#: modules/commands/ns_suspend.cpp:147 +msgid "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." +msgstr "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." + +#: modules/commands/cs_suspend.cpp:240 modules/commands/ns_suspend.cpp:254 +msgid "Suspension expires" +msgstr "Suspension expires" + +#: modules/commands/cs_sync.cpp:19 +msgid "Sync users channel modes" +msgstr "Sync users channel modes" + +#: modules/commands/cs_sync.cpp:49 +msgid "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." +msgstr "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." + +#: modules/commands/hs_group.cpp:42 +msgid "Syncs the vhost for all nicks in a group" +msgstr "Syncs the vhost for all nicks in a group" + +#: src/command.cpp:146 +msgid "Syntax" +msgstr "Syntax" + +#: modules/commands/ns_group.cpp:373 +#, c-format +msgid "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." +msgstr "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." + +#: modules/commands/ns_group.cpp:363 +#, c-format +msgid "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." +msgstr "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." + +#: modules/commands/os_set.cpp:227 +msgid "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." +msgstr "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." + +#: modules/commands/ms_set.cpp:287 +#, c-format +msgid "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." +msgstr "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." + +#: modules/commands/ms_set.cpp:267 +#, c-format +msgid "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." +msgstr "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." + +#: modules/commands/os_set.cpp:208 +#, c-format +msgid "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." +msgstr "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." + +#: modules/commands/os_set.cpp:234 +msgid "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." +msgstr "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." + +#: modules/commands/ms_set.cpp:246 +msgid "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." +msgstr "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." + +#: modules/commands/os_set.cpp:212 +msgid "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." +msgstr "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." + +#: modules/commands/os_set.cpp:243 +msgid "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." +msgstr "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." + +#: modules/commands/ns_identify.cpp:107 +#, c-format +msgid "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." +msgstr "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." + +#: modules/commands/cs_invite.cpp:91 +#, c-format +msgid "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." + +#: modules/commands/cs_unban.cpp:103 +#, c-format +msgid "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." + +#: modules/commands/os_jupe.cpp:56 +msgid "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." +msgstr "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." + +#: modules/commands/cs_seen.cpp:261 +msgid "Tells you about the last time a user was seen" +msgstr "Tells you about the last time a user was seen" + +#: modules/commands/os_shutdown.cpp:19 +msgid "Terminate Services WITHOUT saving" +msgstr "Terminate Services WITHOUT saving" + +#: modules/commands/os_shutdown.cpp:73 +msgid "Terminate services with save" +msgstr "Terminate services with save" + +#: modules/commands/os_news.cpp:156 +msgid "Text" +msgstr "Text" + +#: modules/commands/cs_access.cpp:576 +msgid "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." +msgstr "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." + +#: modules/commands/cs_access.cpp:587 +msgid "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." +msgstr "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." + +#: modules/commands/cs_access.cpp:593 +msgid "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." +msgstr "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." + +#: modules/commands/cs_flags.cpp:447 +msgid "" +"The CLEAR command clears the channel access list. This requires channel " +"founder access." +msgstr "" +"The CLEAR command clears the channel access list. This requires channel " +"founder access." + +#: modules/commands/cs_seen.cpp:173 +#, c-format +msgid "" +"The CLEAR command lets you clean the database by removing all entries from " +"the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." +msgstr "" +"The CLEAR command lets you clean the database by removing all entries from " +"the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." + +#: modules/commands/bs_badwords.cpp:438 +msgid "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." +msgstr "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." + +#: modules/commands/cs_entrymsg.cpp:241 +msgid "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." +msgstr "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." + +#: modules/commands/cs_entrymsg.cpp:253 +msgid "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." +msgstr "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." + +#: modules/commands/cs_entrymsg.cpp:245 +msgid "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." +msgstr "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." + +#: modules/commands/cs_entrymsg.cpp:250 +msgid "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." +msgstr "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." + +#: modules/commands/ns_set.cpp:713 +msgid "The IMMED option is not available on this network." +msgstr "The IMMED option is not available on this network." + +#: modules/commands/cs_access.cpp:821 +#, c-format +msgid "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." +msgstr "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." + +#: modules/commands/cs_flags.cpp:442 +msgid "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." +msgstr "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." + +#: modules/commands/cs_flags.cpp:435 +msgid "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access " +"list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. " +"You are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of " +"what your access is." +msgstr "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access " +"list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. " +"You are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of " +"what your access is." + +#: modules/commands/cs_seen.cpp:172 +msgid "" +"The STATS command prints out statistics about stored nicks and memory usage." +msgstr "" +"The STATS command prints out statistics about stored nicks and memory usage." + +#: modules/commands/ns_register.cpp:291 +msgid "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." +msgstr "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." + +#: modules/commands/cs_log.cpp:258 +#, c-format +msgid "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." +msgstr "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." + +#: modules/commands/cs_ban.cpp:64 +#, c-format +msgid "The %s list for %s is full." +msgstr "The %s list for %s is full." + +#: modules/commands/os_sxline.cpp:220 +#, c-format +msgid "The %s list has been cleared." +msgstr "The %s list has been cleared." + +#: modules/commands/os_akill.cpp:377 +msgid "The AKILL list has been cleared." +msgstr "The AKILL list has been cleared." + +#: modules/commands/os_defcon.cpp:136 modules/commands/os_defcon.cpp:225 +#, c-format +msgid "The Defcon level is now at: %d" +msgstr "The Defcon level is now at: %d" + +#: modules/commands/ns_info.cpp:171 +#, c-format +msgid "The E-mail address of %s will now be hidden from %s INFO displays." +msgstr "The E-mail address of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:172 +#, c-format +msgid "The E-mail address of %s will now be shown in %s INFO displays." +msgstr "The E-mail address of %s will now be shown in %s INFO displays." + +#: modules/commands/cs_flags.cpp:449 +msgid "The available flags are:" +msgstr "The available flags are:" + +#: modules/commands/os_defcon.cpp:240 +msgid "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." +msgstr "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." + +#: modules/ns_maxemail.cpp:51 +#, c-format +msgid "The email address %s has reached its usage limit of %d users." +msgstr "The email address %s has reached its usage limit of %d users." + +#: modules/ns_maxemail.cpp:49 +#, c-format +msgid "The email address %s has reached its usage limit of 1 user." +msgstr "The email address %s has reached its usage limit of 1 user." + +#: modules/commands/cs_entrymsg.cpp:142 +#, c-format +msgid "The entry message list for %s is full." +msgstr "The entry message list for %s is full." + +#: modules/commands/cs_access.cpp:796 +msgid "The following feature/function names are available:" +msgstr "The following feature/function names are available:" + +#: modules/commands/cs_access.cpp:584 +msgid "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." +msgstr "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." + +#: modules/commands/os_session.cpp:240 +#, c-format +msgid "" +"The host %s currently has %d sessions with a limit of %d because it matches " +"entry: %s." +msgstr "" +"The host %s currently has %d sessions with a limit of %d because it matches " +"entry: %s." + +#: modules/commands/ms_check.cpp:54 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has been read." +msgstr "The last memo you sent to %s (sent on %s) has been read." + +#: modules/commands/ms_check.cpp:52 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has not yet been read." +msgstr "The last memo you sent to %s (sent on %s) has not yet been read." + +#: modules/commands/ns_info.cpp:189 +#, c-format +msgid "The last quit message of %s will now be hidden from %s INFO displays." +msgstr "The last quit message of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:190 +#, c-format +msgid "The last quit message of %s will now be shown in %s INFO displays." +msgstr "The last quit message of %s will now be shown in %s INFO displays." + +#: modules/commands/ns_info.cpp:177 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." +msgstr "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:178 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." +msgstr "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." + +#: modules/commands/cs_enforce.cpp:190 +#, c-format +msgid "The limit on %s is not valid." +msgstr "The limit on %s is not valid." + +#: modules/commands/os_forbid.cpp:193 +msgid "The mask must contain at least one non wildcard character." +msgstr "The mask must contain at least one non wildcard character." + +#: modules/commands/ms_set.cpp:153 +#, c-format +msgid "The memo limit for %s may not be changed." +msgstr "The memo limit for %s may not be changed." + +#: modules/commands/cs_mode.cpp:347 +#, c-format +msgid "The mode lock list of %s is full." +msgstr "The mode lock list of %s is full." + +#: modules/commands/ns_set.cpp:355 +#, c-format +msgid "The new display MUST be a nickname of the nickname group %s." +msgstr "The new display MUST be a nickname of the nickname group %s." + +#: include/language.h:98 +#, c-format +msgid "The new display is now %s." +msgstr "The new display is now %s." + +#: modules/commands/os_svs.cpp:57 +#, c-format +msgid "The nick %s is now being changed to %s." +msgstr "The nick %s is now being changed to %s." + +#: modules/commands/bs_bot.cpp:149 +msgid "The old information is the same as the new information specified." +msgstr "The old information is the same as the new information specified." + +#: modules/commands/os_info.cpp:157 +#, c-format +msgid "The oper info already exists on %s." +msgstr "The oper info already exists on %s." + +#: modules/commands/os_info.cpp:147 +#, c-format +msgid "The oper info list for %s is full." +msgstr "The oper info list for %s is full." + +#: modules/commands/ns_info.cpp:183 +#, c-format +msgid "" +"The services access status of %s will now be hidden from %s INFO displays." +msgstr "" +"The services access status of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:184 +#, c-format +msgid "The services access status of %s will now be shown in %s INFO displays." +msgstr "" +"The services access status of %s will now be shown in %s INFO displays." + +#: modules/commands/os_session.cpp:433 +msgid "The session exception list is empty." +msgstr "The session exception list is empty." + +#: modules/commands/ns_recover.cpp:121 +msgid "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." +msgstr "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." + +#: modules/pseudoclients/memoserv.cpp:195 +#, c-format +msgid "There are %d memos on channel %s." +msgstr "There are %d memos on channel %s." + +#: modules/commands/bs_botlist.cpp:47 +msgid "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" +msgstr "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" + +#: modules/commands/os_dns.cpp:213 +msgid "There are no configured servers." +msgstr "There are no configured servers." + +#: modules/commands/os_forbid.cpp:392 +#, c-format +msgid "There are no forbids of type %s." +msgstr "There are no forbids of type %s." + +#: modules/commands/ns_group.cpp:162 +msgid "There are too many nicks in your group." +msgstr "There are too many nicks in your group." + +#: modules/commands/cs_log.cpp:123 +#, c-format +msgid "There currently are no logging configurations for %s." +msgstr "There currently are no logging configurations for %s." + +#: modules/pseudoclients/memoserv.cpp:193 +#, c-format +msgid "There is %d memo on channel %s." +msgstr "There is %d memo on channel %s." + +#: include/language.h:110 +#, c-format +msgid "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." +msgstr "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." + +#: modules/commands/bs_assign.cpp:132 +#, c-format +msgid "There is no bot assigned to %s anymore." +msgstr "There is no bot assigned to %s anymore." + +#: modules/commands/os_news.cpp:33 +msgid "There is no logon news." +msgstr "There is no logon news." + +#: modules/commands/os_news.cpp:43 +msgid "There is no oper news." +msgstr "There is no oper news." + +#: modules/commands/os_news.cpp:53 +msgid "There is no random news." +msgstr "There is no random news." + +#: modules/commands/os_config.cpp:41 +#, c-format +msgid "There is no such configuration block %s." +msgstr "There is no such configuration block %s." + +#: modules/commands/cs_mode.cpp:706 +#, c-format +msgid "There is no such mode %s." +msgstr "There is no such mode %s." + +#: modules/commands/ms_set.cpp:52 +msgid "There's no email address set for your nick." +msgstr "There's no email address set for your nick." + +#: modules/commands/os_forbid.cpp:304 modules/commands/os_forbid.cpp:496 +#, c-format +msgid "This channel has been forbidden: %s" +msgstr "This channel has been forbidden: %s" + +#: modules/commands/cs_suspend.cpp:121 +msgid "This channel has been suspended." +msgstr "This channel has been suspended." + +#: modules/commands/cs_suspend.cpp:232 +msgid "This channel is suspended." +msgstr "This channel is suspended." + +#: modules/commands/cs_suspend.cpp:268 +msgid "This channel may not be used." +msgstr "This channel may not be used." + +#: modules/commands/os_dns.cpp:702 +msgid "" +"This command allows managing DNS zones used for controlling what servers " +"users\n" +"are directed to when connecting. Omitting all parameters prints out the " +"status of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to " +"this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, " +"the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given " +"zones." +msgstr "" +"This command allows managing DNS zones used for controlling what servers " +"users\n" +"are directed to when connecting. Omitting all parameters prints out the " +"status of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to " +"this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, " +"the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given " +"zones." + +#: modules/commands/hs_group.cpp:72 +msgid "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." +msgstr "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." + +#: modules/commands/ns_register.cpp:299 +msgid "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." +msgstr "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." + +#: modules/m_rewrite.cpp:145 +#, c-format +msgid "This command is an alias to the command %s." +msgstr "This command is an alias to the command %s." + +#: modules/commands/ns_register.cpp:95 +msgid "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." +msgstr "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." + +#: modules/commands/os_modinfo.cpp:70 +msgid "This command lists information about the specified loaded module." +msgstr "This command lists information about the specified loaded module." + +#: modules/commands/hs_list.cpp:136 +msgid "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." +msgstr "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." + +#: modules/commands/os_module.cpp:45 +msgid "" +"This command loads the module named modname from the modules\n" +"directory." +msgstr "" +"This command loads the module named modname from the modules\n" +"directory." + +#: modules/commands/ns_group.cpp:201 +msgid "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." +msgstr "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." + +#: modules/commands/ns_ajoin.cpp:292 +msgid "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." +msgstr "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." + +#: modules/commands/ns_set.cpp:345 modules/commands/ns_set.cpp:669 +msgid "" +"This command may not be used on this network because nickname ownership is " +"disabled." +msgstr "" +"This command may not be used on this network because nickname ownership is " +"disabled." + +#: modules/commands/os_module.cpp:118 +msgid "This command reloads the module named modname." +msgstr "This command reloads the module named modname." + +#: modules/commands/hs_request.cpp:344 +msgid "This command retrieves the vhost requests." +msgstr "This command retrieves the vhost requests." + +#: modules/commands/os_logsearch.cpp:159 +msgid "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." +msgstr "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." + +#: modules/commands/cs_status.cpp:106 +msgid "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." +msgstr "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." + +#: modules/commands/ns_group.cpp:285 +msgid "" +"This command ungroups your nick, or if given, the specified nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." +msgstr "" +"This command ungroups your nick, or if given, the specified nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." + +#: modules/commands/os_module.cpp:168 +msgid "This command unloads the module named modname." +msgstr "This command unloads the module named modname." + +#: modules/commands/ns_register.cpp:353 +msgid "This command will resend you the registration confirmation email." +msgstr "This command will resend you the registration confirmation email." + +#: include/language.h:90 +#, c-format +msgid "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" +msgstr "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" + +#: modules/commands/os_forbid.cpp:469 +#, c-format +msgid "This nickname has been forbidden: %s" +msgstr "This nickname has been forbidden: %s" + +#: modules/commands/ns_recover.cpp:99 +#, c-format +msgid "This nickname has been recovered by %s." +msgstr "This nickname has been recovered by %s." + +#: modules/commands/ns_recover.cpp:77 +#, c-format +msgid "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." +msgstr "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." + +#: include/language.h:95 +msgid "This nickname has been registered; you may not use it." +msgstr "This nickname has been registered; you may not use it." + +#: modules/commands/ns_suspend.cpp:246 +msgid "This nickname is suspended." +msgstr "This nickname is suspended." + +#: include/language.h:92 +#, c-format +msgid "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." +msgstr "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." + +#: modules/commands/ms_read.cpp:95 +#, c-format +msgid "To delete, type: %s%s %s %d" +msgstr "To delete, type: %s%s %s %d" + +#: modules/commands/ms_read.cpp:93 +#, c-format +msgid "To delete, type: %s%s %s %s %d" +msgstr "To delete, type: %s%s %s %s %d" + +#: modules/commands/bs_kick.cpp:791 +msgid "To protect ops against bot kicks" +msgstr "To protect ops against bot kicks" + +#: modules/commands/bs_kick.cpp:856 +msgid "To protect voices against bot kicks" +msgstr "To protect voices against bot kicks" + +#: modules/commands/cs_list.cpp:46 +msgid "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." +msgstr "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." + +#: modules/commands/os_logsearch.cpp:139 +#, c-format +msgid "Too many results for %s." +msgstr "Too many results for %s." + +#: modules/extra/stats/cs_fantasy_top.cpp:149 +#, c-format +msgid "Top %i of %s" +msgstr "Top %i of %s" + +#: modules/commands/os_list.cpp:43 +msgid "Topic" +msgstr "Topic" + +#: modules/commands/cs_topic.cpp:258 +msgid "Topic lock" +msgstr "Topic lock" + +#: modules/commands/cs_topic.cpp:114 +#, c-format +msgid "Topic lock option for %s is now off." +msgstr "Topic lock option for %s is now off." + +#: modules/commands/cs_topic.cpp:97 +#, c-format +msgid "Topic lock option for %s is now on." +msgstr "Topic lock option for %s is now on." + +#: modules/commands/cs_topic.cpp:256 +msgid "Topic retention" +msgstr "Topic retention" + +#: modules/commands/cs_topic.cpp:60 +#, c-format +msgid "Topic retention option for %s is now off." +msgstr "Topic retention option for %s is now off." + +#: modules/commands/cs_topic.cpp:54 +#, c-format +msgid "Topic retention option for %s is now on." +msgstr "Topic retention option for %s is now on." + +#: modules/commands/cs_topic.cpp:265 +msgid "Topic set by" +msgstr "Topic set by" + +#: modules/commands/bs_kick.cpp:1323 +msgid "Turn caps lock OFF!" +msgstr "Turn caps lock OFF!" + +#: modules/extra/stats/m_chanstats.cpp:17 +#: modules/extra/stats/m_chanstats.cpp:71 +msgid "Turn chanstats statistics on or off" +msgstr "Turn chanstats statistics on or off" + +#: modules/commands/ns_set.cpp:1009 +msgid "Turn nickname security on or off" +msgstr "Turn nickname security on or off" + +#: modules/commands/ns_set.cpp:655 +msgid "Turn protection on or off" +msgstr "Turn protection on or off" + +#: modules/commands/ns_list.cpp:264 +#, c-format +msgid "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" + +#: modules/commands/ns_list.cpp:236 +#, c-format +msgid "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" + +#: modules/commands/ns_set.cpp:1059 modules/commands/ns_set.cpp:1088 +#, c-format +msgid "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." +msgstr "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." + +#: modules/extra/stats/m_chanstats.cpp:142 +msgid "Turns chanstats channel statistics ON or OFF for this user." +msgstr "Turns chanstats channel statistics ON or OFF for this user." + +#: modules/extra/stats/m_chanstats.cpp:61 +#: modules/extra/stats/m_chanstats.cpp:119 +msgid "Turns chanstats statistics ON or OFF." +msgstr "Turns chanstats statistics ON or OFF." + +#: modules/commands/ns_set.cpp:772 +#, c-format +msgid "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." + +#: modules/commands/ns_set.cpp:738 +#, c-format +msgid "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." + +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_forbid.cpp:358 +msgid "Type" +msgstr "Type" + +#: modules/commands/ns_set.cpp:62 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." + +#: modules/commands/bs_kick.cpp:151 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." +msgstr "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." + +#: modules/commands/ns_set.cpp:107 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." +msgstr "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." + +#: modules/commands/bs_set.cpp:62 modules/commands/cs_set.cpp:63 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." +msgstr "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." + +#: modules/pseudoclients/nickserv.cpp:361 +#, c-format +msgid "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." +msgstr "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." + +#: modules/commands/os_module.cpp:128 +msgid "Un-Load a module" +msgstr "Un-Load a module" + +#: modules/commands/os_sxline.cpp:337 modules/commands/os_sxline.cpp:552 +#: modules/commands/os_akill.cpp:136 +#, c-format +msgid "Unable to find regex engine %s." +msgstr "Unable to find regex engine %s." + +#: modules/commands/os_module.cpp:36 modules/commands/os_module.cpp:108 +#, c-format +msgid "Unable to load module %s." +msgstr "Unable to load module %s." + +#: modules/commands/os_module.cpp:73 modules/commands/os_module.cpp:90 +#: modules/commands/os_module.cpp:145 modules/commands/os_module.cpp:159 +#, c-format +msgid "Unable to remove module %s." +msgstr "Unable to remove module %s." + +#: modules/commands/bs_assign.cpp:90 +msgid "Unassigns a bot from a channel" +msgstr "Unassigns a bot from a channel" + +#: modules/commands/bs_assign.cpp:139 +msgid "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." +msgstr "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." + +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1193 +#: modules/commands/bs_kick.cpp:1196 +msgid "Underlines kicker" +msgstr "Underlines kicker" + +#: modules/commands/os_dns.cpp:595 +msgid "Unknown SET option." +msgstr "Unknown SET option." + +#: modules/commands/os_stats.cpp:229 +#, c-format +msgid "Unknown STATS option: %s" +msgstr "Unknown STATS option: %s" + +#: src/command.cpp:222 src/command.cpp:233 +#, c-format +msgid "Unknown command %s." +msgstr "Unknown command %s." + +#: src/command.cpp:220 src/command.cpp:231 +#, c-format +msgid "Unknown command %s. \"%s%s HELP\" for help." +msgstr "Unknown command %s. \"%s%s HELP\" for help." + +#: modules/commands/cs_mode.cpp:317 modules/commands/cs_mode.cpp:409 +#, c-format +msgid "Unknown mode character %c ignored." +msgstr "Unknown mode character %c ignored." + +#: modules/commands/os_logsearch.cpp:78 +#, c-format +msgid "Unknown parameter: %s" +msgstr "Unknown parameter: %s" + +#: modules/commands/os_dns.cpp:241 +msgid "Unpooled" +msgstr "Unpooled" + +#: modules/commands/cs_drop.cpp:77 +msgid "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." +msgstr "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." + +#: modules/commands/cs_drop.cpp:74 +msgid "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." +msgstr "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." + +#: modules/commands/ns_suspend.cpp:160 +msgid "Unsuspend a given nick" +msgstr "Unsuspend a given nick" + +#: modules/commands/ns_suspend.cpp:199 +msgid "Unsuspends a nickname which allows it to be used again." +msgstr "Unsuspends a nickname which allows it to be used again." + +#: modules/commands/cs_updown.cpp:126 +msgid "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." +msgstr "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." + +#: modules/commands/cs_updown.cpp:48 +msgid "Updates a selected nicks status on a channel" +msgstr "Updates a selected nicks status on a channel" + +#: modules/commands/ns_update.cpp:19 +msgid "Updates your current status, i.e. it checks for new memos" +msgstr "Updates your current status, i.e. it checks for new memos" + +#: modules/commands/ns_update.cpp:43 +msgid "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." +msgstr "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." + +#: modules/commands/os_update.cpp:25 +msgid "Updating databases." +msgstr "Updating databases." + +#: modules/commands/os_stats.cpp:154 +#, c-format +msgid "Uplink capab: %s" +msgstr "Uplink capab: %s" + +#: modules/commands/os_stats.cpp:153 +#, c-format +msgid "Uplink server: %s" +msgstr "Uplink server: %s" + +#: modules/commands/help.cpp:127 +#, c-format +msgid "Use the %s ALL command to list all commands and their descriptions." +msgstr "Use the %s ALL command to list all commands and their descriptions." + +#: modules/commands/bs_info.cpp:59 +msgid "Used on" +msgstr "Used on" + +#: data/chanserv.example.conf:821 +msgid "Used to manage channels" +msgstr "Used to manage channels" + +#: data/chanserv.example.conf:809 +msgid "Used to manage the list of privileged users" +msgstr "Used to manage the list of privileged users" + +#: data/chanserv.example.conf:815 +msgid "Used to modify the channel status of you or other users" +msgstr "Used to modify the channel status of you or other users" + +#: modules/commands/cs_akick.cpp:575 +msgid "User has been banned from the channel" +msgstr "User has been banned from the channel" + +#: modules/commands/os_dns.cpp:587 +#, c-format +msgid "User limit for %s removed." +msgstr "User limit for %s removed." + +#: modules/commands/os_dns.cpp:585 +#, c-format +msgid "User limit for %s set to %d." +msgstr "User limit for %s set to %d." + +#: modules/commands/os_list.cpp:43 +msgid "Users" +msgstr "Users" + +#: modules/commands/os_stats.cpp:172 +#, c-format +msgid "Users (nick): %lu entries, %lu buckets, longest chain is %d" +msgstr "Users (nick): %lu entries, %lu buckets, longest chain is %d" + +#: modules/commands/os_stats.cpp:177 +#, c-format +msgid "Users (uid): %lu entries, %lu buckets, longest chain is %d" +msgstr "Users (uid): %lu entries, %lu buckets, longest chain is %d" + +#: modules/commands/os_list.cpp:184 +msgid "Users list:" +msgstr "Users list:" + +#: modules/commands/ns_info.cpp:105 modules/commands/ns_info.cpp:107 +msgid "VHost" +msgstr "VHost" + +#: modules/commands/hs_set.cpp:92 +#, c-format +msgid "VHost for %s set to %s." +msgstr "VHost for %s set to %s." + +#: modules/commands/hs_set.cpp:90 +#, c-format +msgid "VHost for %s set to %s@%s." +msgstr "VHost for %s set to %s@%s." + +#: modules/commands/hs_set.cpp:199 +#, c-format +msgid "VHost for group %s set to %s." +msgstr "VHost for group %s set to %s." + +#: modules/commands/hs_set.cpp:197 +#, c-format +msgid "VHost for group %s set to %s@%s." +msgstr "VHost for group %s set to %s@%s." + +#: modules/commands/os_session.cpp:247 +msgid "VIEW host" +msgstr "VIEW host" + +#: modules/commands/os_sxline.cpp:428 modules/commands/os_sxline.cpp:662 +#: modules/commands/os_akill.cpp:389 +msgid "VIEW [mask | list | id]" +msgstr "VIEW [mask | list | id]" + +#: modules/commands/os_session.cpp:526 +msgid "VIEW [mask | list]" +msgstr "VIEW [mask | list]" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +msgid "Value" +msgstr "Value" + +#: modules/commands/os_config.cpp:48 +#, c-format +msgid "Value of %s:%s changed to %s" +msgstr "Value of %s:%s changed to %s" + +#: modules/commands/hs_list.cpp:58 modules/commands/hs_request.cpp:305 +msgid "Vhost" +msgstr "Vhost" + +#: modules/commands/hs_del.cpp:38 +#, c-format +msgid "Vhost for %s removed." +msgstr "Vhost for %s removed." + +#: modules/commands/os_oper.cpp:69 +msgid "View and change Services Operators" +msgstr "View and change Services Operators" + +#: modules/commands/os_config.cpp:19 +msgid "View and change configuration file settings" +msgstr "View and change configuration file settings" + +#: modules/commands/os_session.cpp:245 +msgid "View the list of host sessions" +msgstr "View the list of host sessions" + +#: modules/commands/bs_kick.cpp:1221 +msgid "Voices protection" +msgstr "Voices protection" + +#: modules/commands/bs_kick.cpp:1406 +msgid "Watch your language!" +msgstr "Watch your language!" + +#: modules/commands/cs_list.cpp:237 +#, c-format +msgid "" +"When private is set, the channel will not appear in\n" +"%s's %s command." +msgstr "" +"When private is set, the channel will not appear in\n" +"%s's %s command." + +#: modules/commands/ms_info.cpp:204 +msgid "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." +msgstr "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." + +#: modules/commands/ns_logout.cpp:66 +msgid "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." +msgstr "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." + +#: modules/commands/os_stats.cpp:236 +msgid "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." +msgstr "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." + +#: modules/commands/bs_badwords.cpp:194 +msgid "Word" +msgstr "Word" + +#: modules/commands/ns_group.cpp:158 +#, c-format +msgid "You are already a member of the group of %s." +msgstr "You are already a member of the group of %s." + +#: modules/commands/os_login.cpp:34 modules/commands/ns_identify.cpp:87 +msgid "You are already identified." +msgstr "You are already identified." + +#: modules/commands/cs_invite.cpp:64 +#, c-format +msgid "You are already in %s!" +msgstr "You are already in %s!" + +#: modules/commands/os_set.cpp:91 +msgid "You are no longer a super admin." +msgstr "You are no longer a super admin." + +#: modules/commands/os_login.cpp:81 +msgid "You are not identified." +msgstr "You are not identified." + +#: include/language.h:100 +msgid "You are not permitted to be on this channel." +msgstr "You are not permitted to be on this channel." + +#: modules/commands/ms_set.cpp:158 +msgid "You are not permitted to change your memo limit." +msgstr "You are not permitted to change your memo limit." + +#: modules/commands/ns_cert.cpp:183 +msgid "You are not using a client certificate." +msgstr "You are not using a client certificate." + +#: modules/commands/os_set.cpp:85 +msgid "You are now a super admin." +msgstr "You are now a super admin." + +#: modules/commands/os_oline.cpp:36 +msgid "You are now an IRC Operator." +msgstr "You are now an IRC Operator." + +#: modules/commands/ns_resetpass.cpp:108 +msgid "You are now identified for your nick. Change your password now." +msgstr "You are now identified for your nick. Change your password now." + +#: modules/commands/ns_group.cpp:64 +#, c-format +msgid "You are now in the group of %s." +msgstr "You are now in the group of %s." + +#: modules/pseudoclients/memoserv.cpp:147 +#, c-format +msgid "" +"You are over your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"You are over your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." + +#: modules/commands/os_noop.cpp:33 +msgid "You can not NOOP Services." +msgstr "You can not NOOP Services." + +#: modules/commands/cs_access.cpp:672 +msgid "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." +msgstr "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." + +#: modules/commands/os_jupe.cpp:34 +msgid "You can not jupe an already juped server." +msgstr "You can not jupe an already juped server." + +#: modules/commands/os_jupe.cpp:32 +msgid "You can not jupe your Services' pseudoserver or your uplink server." +msgstr "You can not jupe your Services' pseudoserver or your uplink server." + +#: modules/commands/os_module.cpp:80 +#, c-format +msgid "You can not reload this module directly, instead reload %s." +msgstr "You can not reload this module directly, instead reload %s." + +#: modules/commands/ms_rsend.cpp:46 +msgid "You can not request a receipt when sending a memo to yourself." +msgstr "You can not request a receipt when sending a memo to yourself." + +#: modules/commands/ns_recover.cpp:163 +#, c-format +msgid "You can't %s yourself!" +msgstr "You can't %s yourself!" + +#: modules/commands/cs_access.cpp:154 modules/commands/cs_flags.cpp:109 +#: modules/commands/cs_xop.cpp:151 +msgid "You can't add a channel to its own access list." +msgstr "You can't add a channel to its own access list." + +#: modules/commands/ns_logout.cpp:37 +#, c-format +msgid "You can't logout %s, they are a Services Operator." +msgstr "You can't logout %s, they are a Services Operator." + +#: modules/commands/ns_set.cpp:927 +#, c-format +msgid "You cannot %s on this network." +msgstr "You cannot %s on this network." + +#: modules/commands/cs_flags.cpp:231 +#, c-format +msgid "You cannot set the %c flag." +msgstr "You cannot set the %c flag." + +#: modules/commands/ms_set.cpp:173 +#, c-format +msgid "You cannot set the memo limit for %s higher than %d." +msgstr "You cannot set the memo limit for %s higher than %d." + +#: modules/commands/ms_set.cpp:175 +#, c-format +msgid "You cannot set your memo limit higher than %d." +msgstr "You cannot set your memo limit higher than %d." + +#: modules/commands/bs_assign.cpp:124 +msgid "You cannot unassign bots while persist is set on the channel." +msgstr "You cannot unassign bots while persist is set on the channel." + +#: modules/commands/ns_set.cpp:480 +msgid "You cannot unset the e-mail on this network." +msgstr "You cannot unset the e-mail on this network." + +#: modules/commands/help.cpp:177 +msgid "You cannot use this command." +msgstr "You cannot use this command." + +#: modules/commands/ms_info.cpp:151 +#, c-format +msgid "You currently have %d memos, of which %d are unread." +msgstr "You currently have %d memos, of which %d are unread." + +#: modules/commands/ms_info.cpp:149 +#, c-format +msgid "You currently have %d memos, of which 1 is unread." +msgstr "You currently have %d memos, of which 1 is unread." + +#: modules/commands/ms_info.cpp:147 +#, c-format +msgid "You currently have %d memos." +msgstr "You currently have %d memos." + +#: modules/commands/ms_info.cpp:145 +#, c-format +msgid "You currently have %d memos; all of them are unread." +msgstr "You currently have %d memos; all of them are unread." + +#: modules/commands/ms_info.cpp:134 +msgid "You currently have 1 memo, and it has not yet been read." +msgstr "You currently have 1 memo, and it has not yet been read." + +#: modules/commands/ms_info.cpp:136 +msgid "You currently have 1 memo." +msgstr "You currently have 1 memo." + +#: modules/commands/ms_info.cpp:130 +msgid "You currently have no memos." +msgstr "You currently have no memos." + +#: modules/commands/cs_mode.cpp:564 modules/commands/cs_mode.cpp:621 +#, c-format +msgid "You do not have access to set mode %c." +msgstr "You do not have access to set mode %c." + +#: modules/commands/cs_mode.cpp:578 modules/commands/cs_mode.cpp:590 +#: modules/commands/cs_mode.cpp:631 +#, c-format +msgid "You do not have the access to change %s's modes." +msgstr "You do not have the access to change %s's modes." + +#: modules/commands/cs_seen.cpp:198 +#, c-format +msgid "You found me, %s!" +msgstr "You found me, %s!" + +#: modules/pseudoclients/memoserv.cpp:143 +#, c-format +msgid "You have %d new memos." +msgstr "You have %d new memos." + +#: modules/pseudoclients/memoserv.cpp:143 +msgid "You have 1 new memo." +msgstr "You have 1 new memo." + +#: include/language.h:112 +#, c-format +msgid "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." +msgstr "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." + +#: modules/commands/cs_invite.cpp:76 +#, c-format +msgid "You have been invited to %s by %s." +msgstr "You have been invited to %s by %s." + +#: modules/commands/cs_invite.cpp:81 +#, c-format +msgid "You have been invited to %s." +msgstr "You have been invited to %s." + +#: modules/protocol/ratbox.cpp:166 modules/commands/ns_recover.cpp:96 +#, c-format +msgid "You have been logged in as %s." +msgstr "You have been logged in as %s." + +#: modules/commands/os_login.cpp:86 +msgid "You have been logged out." +msgstr "You have been logged out." + +#: modules/commands/cs_unban.cpp:94 +#, c-format +msgid "You have been unbanned from %s." +msgstr "You have been unbanned from %s." + +#: modules/commands/cs_unban.cpp:54 +#, c-format +msgid "You have been unbanned from %d channels." +msgstr "You have been unbanned from %d channels." + +#: modules/commands/ms_info.cpp:169 +msgid "You have no limit on the number of memos you may keep." +msgstr "You have no limit on the number of memos you may keep." + +#: include/language.h:114 +msgid "You have no memos." +msgstr "You have no memos." + +#: include/language.h:117 +msgid "You have no new memos." +msgstr "You have no new memos." + +#: modules/pseudoclients/memoserv.cpp:149 +#, c-format +msgid "" +"You have reached your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"You have reached your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." + +#: modules/commands/ns_recover.cpp:117 +#, c-format +msgid "You have regained control of %s." +msgstr "You have regained control of %s." + +#: modules/commands/ns_drop.cpp:66 +msgid "You may drop any nick within your group." +msgstr "You may drop any nick within your group." + +#: modules/commands/cs_mode.cpp:322 modules/commands/cs_mode.cpp:414 +#, c-format +msgid "You may not (un)lock mode %c." +msgstr "You may not (un)lock mode %c." + +#: modules/commands/ns_set.cpp:485 +msgid "You may not change the e-mail of other Services Operators." +msgstr "You may not change the e-mail of other Services Operators." + +#: modules/commands/ns_set.cpp:474 +msgid "You may not change the email of an unconfirmed account." +msgstr "You may not change the email of an unconfirmed account." + +#: modules/commands/ns_set.cpp:196 +msgid "You may not change the password of other Services Operators." +msgstr "You may not change the password of other Services Operators." + +#: modules/commands/ns_drop.cpp:45 +msgid "You may not drop other Services Operators' nicknames." +msgstr "You may not drop other Services Operators' nicknames." + +#: modules/commands/ns_getpass.cpp:32 +msgid "You may not get the password of other Services Operators." +msgstr "You may not get the password of other Services Operators." + +#: modules/commands/ns_suspend.cpp:100 +msgid "You may not suspend other Services Operators' nicknames." +msgstr "You may not suspend other Services Operators' nicknames." + +#: modules/commands/ns_access.cpp:136 +msgid "" +"You may view but not modify the access list of other Services Operators." +msgstr "" +"You may view but not modify the access list of other Services Operators." + +#: modules/commands/ns_cert.cpp:292 +msgid "" +"You may view but not modify the certificate list of other Services Operators." +msgstr "" +"You may view but not modify the certificate list of other Services Operators." + +#: modules/commands/cs_seen.cpp:287 +#, c-format +msgid "You might see yourself in the mirror, %s." +msgstr "You might see yourself in the mirror, %s." + +#: include/language.h:120 +msgid "You must assign a bot to the channel before using this command." +msgstr "You must assign a bot to the channel before using this command." + +#: modules/commands/cs_register.cpp:49 +msgid "You must be a channel operator to register the channel." +msgstr "You must be a channel operator to register the channel." + +#: modules/commands/cs_updown.cpp:94 modules/commands/cs_updown.cpp:192 +#, c-format +msgid "You must be in %s to use this command." +msgstr "You must be in %s to use this command." + +#: modules/commands/cs_register.cpp:37 +msgid "You must confirm your account before you can register a channel." +msgstr "You must confirm your account before you can register a channel." + +#: modules/commands/hs_request.cpp:100 +msgid "You must confirm your account before you may request a vhost." +msgstr "You must confirm your account before you may request a vhost." + +#: modules/commands/ms_send.cpp:44 +msgid "You must confirm your account before you may send a memo." +msgstr "You must confirm your account before you may send a memo." + +#: modules/commands/cs_drop.cpp:42 +#, c-format +msgid "" +"You must enter the channel name twice as a confirmation that you wish to drop" +" %s." +msgstr "" +"You must enter the channel name twice as a confirmation that you wish to drop" +" %s." + +#: modules/commands/ns_register.cpp:153 +#, c-format +msgid "You must have been using this nick for at least %d seconds to register." +msgstr "" +"You must have been using this nick for at least %d seconds to register." + +#: modules/commands/cs_mode.cpp:913 +#, c-format +msgid "You must have the %s(ME) privilege on the channel to use this command." +msgstr "You must have the %s(ME) privilege on the channel to use this command." + +#: modules/pseudoclients/nickserv.cpp:358 +msgid "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." +msgstr "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." + +#: modules/commands/help.cpp:172 +msgid "You need to be identified to use this command." +msgstr "You need to be identified to use this command." + +#: modules/commands/ms_info.cpp:182 +msgid "You will be notified by message and by mail when new memos arrive." +msgstr "You will be notified by message and by mail when new memos arrive." + +#: modules/commands/ms_info.cpp:175 +msgid "" +"You will be notified of new memos at logon and when they arrive, and by mail " +"when they arrive." +msgstr "" +"You will be notified of new memos at logon and when they arrive, and by mail " +"when they arrive." + +#: modules/commands/ms_info.cpp:177 +msgid "You will be notified of new memos at logon and when they arrive." +msgstr "You will be notified of new memos at logon and when they arrive." + +#: modules/commands/ms_info.cpp:189 +msgid "" +"You will be notified of new memos at logon, and by mail when they arrive." +msgstr "" +"You will be notified of new memos at logon, and by mail when they arrive." + +#: modules/commands/ms_info.cpp:191 +msgid "You will be notified of new memos at logon." +msgstr "You will be notified of new memos at logon." + +#: modules/commands/ms_info.cpp:184 +msgid "You will be notified when new memos arrive." +msgstr "You will be notified when new memos arrive." + +#: modules/commands/ms_set.cpp:190 +msgid "You will no longer be able to receive memos." +msgstr "You will no longer be able to receive memos." + +#: modules/commands/ms_set.cpp:57 +msgid "You will no longer be informed via email." +msgstr "You will no longer be informed via email." + +#: modules/commands/ms_info.cpp:195 +msgid "You will not be notified of new memos." +msgstr "You will not be notified of new memos." + +#: modules/commands/ms_set.cpp:49 +msgid "You will now be informed about new memos via email." +msgstr "You will now be informed about new memos via email." + +#: modules/commands/os_svs.cpp:86 +msgid "Your IRCd does not support SVSJOIN." +msgstr "Your IRCd does not support SVSJOIN." + +#: modules/commands/os_svs.cpp:31 +msgid "Your IRCd does not support SVSNICK." +msgstr "Your IRCd does not support SVSNICK." + +#: modules/commands/os_svs.cpp:130 +msgid "Your IRCd does not support SVSPART." +msgstr "Your IRCd does not support SVSPART." + +#: include/language.h:127 +msgid "" +"Your IRCd does not support vIdent's, if this is incorrect, please report " +"this as a possible bug" +msgstr "" +"Your IRCd does not support vIdent's, if this is incorrect, please report " +"this as a possible bug" + +#: modules/extra/m_ldap_authentication.cpp:110 +#: modules/extra/m_sql_authentication.cpp:55 +#, c-format +msgid "Your account %s has been successfully created." +msgstr "Your account %s has been successfully created." + +#: modules/commands/ns_register.cpp:328 +msgid "Your account is already confirmed." +msgstr "Your account is already confirmed." + +#: modules/commands/ns_register.cpp:396 +#, c-format +msgid "Your account will expire, if not confirmed, in %s." +msgstr "Your account will expire, if not confirmed, in %s." + +#: modules/commands/ns_set.cpp:1274 +#, c-format +msgid "Your email address has been changed to %s." +msgstr "Your email address has been changed to %s." + +#: modules/commands/os_forbid.cpp:544 modules/commands/os_forbid.cpp:553 +msgid "Your email address is not allowed, choose a different one." +msgstr "Your email address is not allowed, choose a different one." + +#: modules/commands/ns_register.cpp:260 modules/commands/ns_register.cpp:391 +msgid "" +"Your email address is not confirmed. To confirm it, follow the instructions " +"that were emailed to you." +msgstr "" +"Your email address is not confirmed. To confirm it, follow the instructions " +"that were emailed to you." + +#: modules/commands/ns_register.cpp:67 +#, c-format +msgid "Your email address of %s has been confirmed." +msgstr "Your email address of %s has been confirmed." + +#: modules/extra/m_ldap_authentication.cpp:159 +#, c-format +msgid "Your email has been updated to %s" +msgstr "Your email has been updated to %s" + +#: modules/extra/m_sql_authentication.cpp:62 +#, c-format +msgid "Your email has been updated to %s." +msgstr "Your email has been updated to %s." + +#: modules/commands/ms_set.cpp:197 +msgid "Your memo limit has been disabled." +msgstr "Your memo limit has been disabled." + +#: modules/commands/ms_set.cpp:183 +#, c-format +msgid "Your memo limit has been set to %d." +msgstr "Your memo limit has been set to %d." + +#: modules/commands/ms_info.cpp:164 +#, c-format +msgid "Your memo limit is %d, and may not be changed." +msgstr "Your memo limit is %d, and may not be changed." + +#: modules/commands/ms_info.cpp:166 +#, c-format +msgid "Your memo limit is %d." +msgstr "Your memo limit is %d." + +#: modules/commands/ms_info.cpp:159 +msgid "Your memo limit is 0; you will not receive any new memos." +msgstr "Your memo limit is 0; you will not receive any new memos." + +#: modules/commands/ms_info.cpp:157 +msgid "" +"Your memo limit is 0; you will not receive any new memos. You cannot change " +"this limit." +msgstr "" +"Your memo limit is 0; you will not receive any new memos. You cannot change " +"this limit." + +#: modules/commands/ns_logout.cpp:50 +msgid "Your nick has been logged out." +msgstr "Your nick has been logged out." + +#: modules/commands/ns_group.cpp:156 +msgid "Your nick is already registered." +msgstr "Your nick is already registered." + +#: modules/commands/ns_group.cpp:246 +msgid "Your nick is not grouped to anything, you can't ungroup it." +msgstr "Your nick is not grouped to anything, you can't ungroup it." + +#: include/language.h:77 +msgid "Your nick isn't registered." +msgstr "Your nick isn't registered." + +#: modules/pseudoclients/nickserv.cpp:254 +#, c-format +msgid "Your nickname is now being changed to %s" +msgstr "Your nickname is now being changed to %s" + +#: modules/commands/os_login.cpp:32 modules/commands/os_login.cpp:79 +msgid "Your oper block doesn't require logging in." +msgstr "Your oper block doesn't require logging in." + +#: modules/commands/ns_register.cpp:336 +#, c-format +msgid "Your passcode has been re-sent to %s." +msgstr "Your passcode has been re-sent to %s." + +#: modules/commands/ns_register.cpp:232 +#, c-format +msgid "Your password is %s - remember this for later use." +msgstr "Your password is %s - remember this for later use." + +#: include/language.h:76 +#, c-format +msgid "Your password is too long. It must not exceed %u characters." +msgstr "Your password is too long. It must not exceed %u characters." + +#: modules/commands/ns_resetpass.cpp:96 +msgid "Your password reset request has expired." +msgstr "Your password reset request has expired." + +#: modules/commands/hs_request.cpp:170 +msgid "Your vHost has been requested." +msgstr "Your vHost has been requested." + +#: modules/pseudoclients/hostserv.cpp:64 +#: modules/pseudoclients/hostserv.cpp:103 modules/commands/hs_on.cpp:37 +#, c-format +msgid "Your vhost of %s is now activated." +msgstr "Your vhost of %s is now activated." + +#: modules/pseudoclients/hostserv.cpp:62 +#: modules/pseudoclients/hostserv.cpp:101 modules/commands/hs_on.cpp:35 +#, c-format +msgid "Your vhost of %s@%s is now activated." +msgstr "Your vhost of %s@%s is now activated." + +#: modules/commands/hs_off.cpp:39 +msgid "Your vhost was removed and the normal cloaking restored." +msgstr "Your vhost was removed and the normal cloaking restored." + +#: modules/commands/os_dns.cpp:255 +msgid "Zone" +msgstr "Zone" + +#: modules/commands/os_dns.cpp:290 +#, c-format +msgid "Zone %s already exists." +msgstr "Zone %s already exists." + +#: modules/commands/os_dns.cpp:310 modules/commands/os_dns.cpp:352 +#: modules/commands/os_dns.cpp:402 modules/commands/os_dns.cpp:438 +#, c-format +msgid "Zone %s does not exist." +msgstr "Zone %s does not exist." + +#: modules/commands/os_dns.cpp:332 +#, c-format +msgid "Zone %s removed." +msgstr "Zone %s removed." + +#: modules/commands/os_defcon.cpp:177 +msgid "[1|2|3|4|5]" +msgstr "[1|2|3|4|5]" + +#: modules/commands/os_news.cpp:400 +#, c-format +msgid "[Logon News - %s] %s" +msgstr "[Logon News - %s] %s" + +#: modules/commands/os_news.cpp:402 +#, c-format +msgid "[Oper News - %s] %s" +msgstr "[Oper News - %s] %s" + +#: modules/commands/os_news.cpp:404 +#, c-format +msgid "[Random News - %s] %s" +msgstr "[Random News - %s] %s" + +#: modules/commands/ns_identify.cpp:66 +msgid "[account] password" +msgstr "[account] password" + +#: modules/commands/cs_updown.cpp:49 modules/commands/cs_updown.cpp:147 +msgid "[channel [nick]]" +msgstr "[channel [nick]]" + +#: modules/commands/ms_ignore.cpp:20 +msgid "[channel] ADD entry" +msgstr "[channel] ADD entry" + +#: modules/commands/ms_ignore.cpp:21 +msgid "[channel] DEL entry" +msgstr "[channel] DEL entry" + +#: modules/commands/ms_ignore.cpp:22 +msgid "[channel] LIST" +msgstr "[channel] LIST" + +#: modules/commands/ms_list.cpp:20 +msgid "[channel] [list | NEW]" +msgstr "[channel] [list | NEW]" + +#: modules/extra/stats/cs_fantasy_stats.cpp:40 +msgid "[channel] [nick]" +msgstr "[channel] [nick]" + +#: modules/commands/ms_del.cpp:45 +msgid "[channel] {num | list | LAST | ALL}" +msgstr "[channel] {num | list | LAST | ALL}" + +#: modules/commands/ms_read.cpp:113 +msgid "[channel] {num | list | LAST | NEW | ALL}" +msgstr "[channel] {num | list | LAST | NEW | ALL}" + +#: modules/commands/hs_list.cpp:20 +msgid "[key|#X-Y]" +msgstr "[key|#X-Y]" + +#: modules/commands/ms_info.cpp:20 +msgid "[nick | channel]" +msgstr "[nick | channel]" + +#: modules/commands/ns_group.cpp:237 +msgid "[nick]" +msgstr "[nick]" + +#: modules/commands/ns_logout.cpp:22 +msgid "[nickname [REVALIDATE]]" +msgstr "[nickname [REVALIDATE]]" + +#: modules/commands/ns_alist.cpp:25 modules/commands/ns_status.cpp:20 +#: modules/commands/ns_info.cpp:20 +msgid "[nickname]" +msgstr "[nickname]" + +#: modules/commands/ns_set_misc.cpp:96 +msgid "[parameter]" +msgstr "[parameter]" + +#: modules/commands/os_logsearch.cpp:33 +msgid "[+daysd] [+limitl] pattern" +msgstr "[+daysd] [+limitl] pattern" + +#: modules/commands/os_chankill.cpp:22 +msgid "[+expiry] channel reason" +msgstr "[+expiry] channel reason" + +#: modules/commands/ns_list.cpp:110 +msgid "[Hostname hidden]" +msgstr "[Hostname hidden]" + +#: modules/commands/ns_list.cpp:112 modules/commands/cs_list.cpp:115 +msgid "[Suspended]" +msgstr "[Suspended]" + +#: modules/commands/ns_list.cpp:114 +msgid "[Unconfirmed]" +msgstr "[Unconfirmed]" + +#: modules/commands/hs_request.cpp:213 +msgid "[auto memo] Your requested vHost has been approved." +msgstr "[auto memo] Your requested vHost has been approved." + +#: modules/commands/hs_request.cpp:267 +msgid "[auto memo] Your requested vHost has been rejected." +msgstr "[auto memo] Your requested vHost has been rejected." + +#: modules/commands/hs_request.cpp:265 +#, c-format +msgid "[auto memo] Your requested vHost has been rejected. Reason: %s" +msgstr "[auto memo] Your requested vHost has been rejected. Reason: %s" + +#: modules/commands/hs_request.cpp:388 +#, c-format +msgid "[auto memo] vHost %s has been requested by %s." +msgstr "[auto memo] vHost %s has been requested by %s." + +#: modules/commands/os_list.cpp:133 +msgid "[{pattern | channel} [INVISIBLE]]" +msgstr "[{pattern | channel} [INVISIBLE]]" + +#: modules/commands/os_list.cpp:20 +msgid "[{pattern | nick} [SECRET]]" +msgstr "[{pattern | nick} [SECRET]]" + +#: src/misc.cpp:337 +msgid "day" +msgstr "day" + +#: src/misc.cpp:337 +msgid "days" +msgstr "days" + +#: include/language.h:88 +msgid "does not expire" +msgstr "does not expire" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d day" +msgstr "expires in %d day" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d days" +msgstr "expires in %d days" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minute" +msgstr "expires in %d hour, %d minute" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minutes" +msgstr "expires in %d hour, %d minutes" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minute" +msgstr "expires in %d hours, %d minute" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minutes" +msgstr "expires in %d hours, %d minutes" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minute" +msgstr "expires in %d minute" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minutes" +msgstr "expires in %d minutes" + +#: src/misc.cpp:375 +msgid "expires momentarily" +msgstr "expires momentarily" + +#: src/misc.cpp:343 +msgid "hour" +msgstr "hour" + +#: src/misc.cpp:343 +msgid "hours" +msgstr "hours" + +#: modules/extra/stats/cs_fantasy_stats.cpp:150 +#, c-format +msgid "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" + +#: src/misc.cpp:349 +msgid "minute" +msgstr "minute" + +#: src/misc.cpp:349 +msgid "minutes" +msgstr "minutes" + +#: modules/commands/bs_info.cpp:87 +msgid "not assigned yet" +msgstr "not assigned yet" + +#: src/misc.cpp:324 +msgid "second" +msgstr "second" + +#: src/misc.cpp:324 +msgid "seconds" +msgstr "seconds" + +#: modules/commands/hs_request.cpp:215 +#, c-format +msgid "vHost for %s has been activated." +msgstr "vHost for %s has been activated." + +#: modules/commands/hs_request.cpp:272 +#, c-format +msgid "vHost for %s has been rejected." +msgstr "vHost for %s has been rejected." + +#: modules/commands/hs_request.cpp:79 +msgid "vhost" +msgstr "vhost" + +#: modules/commands/hs_del.cpp:83 +#, c-format +msgid "vhosts for group %s have been removed." +msgstr "vhosts for group %s have been removed." + +#: src/misc.cpp:331 +msgid "year" +msgstr "year" + +#: src/misc.cpp:331 +msgid "years" +msgstr "years" + +#: modules/commands/os_config.cpp:20 +msgid "{MODIFY|VIEW} [block name item name item value]" +msgstr "{MODIFY|VIEW} [block name item name item value]" + +#: modules/commands/bs_info.cpp:41 +msgid "{channel | nickname}" +msgstr "{channel | nickname}" + +#: modules/commands/ms_cancel.cpp:20 +msgid "{nick | channel}" +msgstr "{nick | channel}" + +#: modules/commands/ms_rsend.cpp:25 modules/commands/ms_send.cpp:25 +msgid "{nick | channel} memo-text" +msgstr "{nick | channel} memo-text" diff --git a/language/anope.es_ES.po b/language/anope.es_ES.po new file mode 100644 index 0000000..0c2f6d4 --- /dev/null +++ b/language/anope.es_ES.po @@ -0,0 +1,11198 @@ +# Anope IRC Services language file +# Copyright (C) 2011 +# This file is distributed under the same license as the Anope IRC Services package. +# Adam , 2011. +# +msgid "" +msgstr "" +"Project-Id-Version: Anope\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2020-01-06 18:19+0100\n" +"PO-Revision-Date: 2014-02-24 20:45+0100\n" +"Last-Translator: Isaac Fontal \n" +"Language-Team: Spanish\n" +"Language: es_ES\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" +"X-Generator: Poedit 1.5.5\n" +"X-Poedit-SourceCharset: UTF-8\n" + +#: modules/commands/os_forbid.cpp:324 +#, c-format +msgid "%d channel(s) cleared, and %d channel(s) dropped." +msgstr "%d canale(s) limpiado(s), y %d canale(s) borrado(s)." + +#: modules/commands/os_forbid.cpp:265 +#, c-format +msgid "%d nickname(s) dropped." +msgstr "%d nick(s) borrado(s)." + +#: modules/commands/cs_xop.cpp:219 +#, c-format +msgid "%s added to %s %s list." +msgstr "%s añadido a la lista de %s de %s." + +#: modules/commands/cs_access.cpp:225 +#, c-format +msgid "%s added to %s access list at level %d." +msgstr "%s añadido a la lista de acceso de %s con nivel %d." + +#: modules/commands/cs_access.cpp:223 +#, c-format +msgid "%s added to %s access list at privilege %s (level %d)" +msgstr "%s añadido a la lista de acceso de %s con privilegios de %s (nivel %d)" + +#: modules/commands/cs_akick.cpp:190 +#, c-format +msgid "%s added to %s autokick list." +msgstr "%s añadido a la lista de kicks automaticos en el canal %s." + +#: modules/commands/bs_badwords.cpp:307 +#, c-format +msgid "%s added to %s bad words list." +msgstr "%s añadido a la lista de bad words de %s." + +#: modules/commands/ns_access.cpp:45 +#, c-format +msgid "%s added to %s's access list." +msgstr "%s añadido a la lista de acceso de %s." + +#: modules/commands/ns_cert.cpp:204 +#, c-format +msgid "%s added to %s's certificate list." +msgstr "%s añadido a la lista de certificados de %s." + +#: modules/commands/ms_ignore.cpp:62 +#, c-format +msgid "%s added to ignore list." +msgstr "%s añadido a la lista de ignorados." + +#: modules/commands/os_sxline.cpp:415 modules/commands/os_sxline.cpp:649 +#, c-format +msgid "%s added to the %s list." +msgstr "%s añadido a la lista %s." + +#: modules/commands/os_akill.cpp:203 +#, c-format +msgid "%s added to the AKILL list." +msgstr "%s añadido a la lista de AKILLs." + +#: modules/pseudoclients/botserv.cpp:134 +#, c-format +msgid "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands " +"that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" +msgstr "" +"%s te permite ejecutar comandos \"fantasía\" en el canal.\n" +"Los comandos fantasía son comandos que pueden ser ejecutados enviado un\n" +"mensaje a un canal y proporcionan una forma más cómoda de ejecutar " +"comandos.\n" +"Los comandos que requieren un canal como parámetro ya obtendrán ese\n" +"parámetro automáticamente.\n" + +#: modules/pseudoclients/botserv.cpp:148 +#, c-format +msgid "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s te permite crear un bot en tu propio canal.\n" +"Esto ha sido creado para usuarios que no puedan\n" +"hostear o configurar un bot, o para usar en redes\n" +"que no permitan bots de usuarios. Los comandos\n" +"disponibles están listados mas abajo; para usarlos,\n" +"escribe %s%s comando. Para más\n" +"información sobre un comando específico, escribe\n" +"%s%s %s comando.\n" + +#: modules/pseudoclients/nickserv.cpp:466 +#, c-format +msgid "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s te permite registrar un nick y evitar\n" +"que otros lo usen. Los siguientes comandos\n" +"permiten el registro y el mantenimiento de nicks;\n" +"para usarlos, escribe %s%s comando.\n" +"Para más información acerca de un comando específico,\n" +"escribe %s%s %s comando.\n" + +#: modules/pseudoclients/nickserv.cpp:473 +#, c-format +msgid "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s te permite registrar una cuenta.\n" +"Los siguientes comandos permiten el registro y mantenimiento de\n" +"cuentas; para usarlos, escribe %s%s comando.\n" +"Para más información acerca de un comando específico,\n" +"escribe %s%s %s comando.\n" + +#: modules/pseudoclients/chanserv.cpp:255 +#, c-format +msgid "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" +msgstr "" +"%s te permite registrar y controlar varios\n" +"aspectos de los canales. Normalmente, %s puede\n" +"prevenir a usuarios maliciosos \"tomar\" canales\n" +"limitando quienes pueden tener privilegios de operador.\n" +"Los comandos disponibles están listados más abajo;\n" +"para usarlos, escribe %s%s comando. Para más\n" +"información acerca de un comando específico, escribe\n" +"%s%s HELP comando.\n" + +#: modules/commands/bs_badwords.cpp:298 +#, c-format +msgid "%s already exists in %s bad words list." +msgstr "%s ya existe en la lista de bad words de %s." + +#: modules/commands/cs_akick.cpp:170 +#, c-format +msgid "%s already exists on %s autokick list." +msgstr "%s ya existe en la lista de kick automático de %s." + +#: modules/commands/os_session.cpp:361 +#, c-format +msgid "%s already exists on the EXCEPTION list." +msgstr "%s ya existe en la lista de EXCEPCIONES." + +#: modules/commands/bs_kick.cpp:214 modules/commands/bs_kick.cpp:389 +#: modules/commands/bs_kick.cpp:520 modules/commands/bs_kick.cpp:651 +#, c-format +msgid "%s cannot be taken as times to ban." +msgstr "%s no es válido como veces para banear." + +#: modules/commands/os_mode.cpp:163 +#, c-format +msgid "%s changed your usermodes to %s." +msgstr "%s cambió tus modos de usuario a %s." + +#: modules/commands/os_list.cpp:47 +#, c-format +msgid "%s channel list:" +msgstr "Lista de canales de %s." + +#: modules/commands/cs_xop.cpp:343 +#, c-format +msgid "%s deleted from %s %s list." +msgstr "%s borrado de la lista de %s de %s." + +#: modules/commands/cs_access.cpp:326 +#, c-format +msgid "%s deleted from %s access list." +msgstr "%s borrado de la lista de acceso de %s." + +#: modules/commands/cs_akick.cpp:276 +#, c-format +msgid "%s deleted from %s autokick list." +msgstr "%s borrado de la lista de kicks automáticos del canal %s." + +#: modules/commands/bs_badwords.cpp:348 +#, c-format +msgid "%s deleted from %s bad words list." +msgstr "%s borrado de la lista de bad words de %s." + +#: modules/commands/ns_access.cpp:72 +#, c-format +msgid "%s deleted from %s's access list." +msgstr "%s borrado de la lista de acceso de %s." + +#: modules/commands/ns_cert.cpp:233 +#, c-format +msgid "%s deleted from %s's certificate list." +msgstr "%s borrado de la lista de certificados de %s." + +#: modules/commands/os_session.cpp:414 +#, c-format +msgid "%s deleted from session-limit exception list." +msgstr "%s borrado de la lista de excepciones al limite de sesiones." + +#: modules/commands/os_sxline.cpp:99 +#, c-format +msgid "%s deleted from the %s list." +msgstr "%s borrado de la lista %s." + +#: modules/commands/os_akill.cpp:246 +#, c-format +msgid "%s deleted from the AKILL list." +msgstr "%s borrado de la lista de AKILLs." + +#: modules/commands/cs_access.cpp:685 +#, c-format +msgid "%s disabled on channel %s." +msgstr "%s deshabilitado en el canal %s." + +#: modules/commands/cs_invite.cpp:75 +#, c-format +msgid "%s has been invited to %s." +msgstr "%s ha sido invitado a %s." + +#: modules/commands/os_svs.cpp:104 +#, c-format +msgid "%s has been joined to %s." +msgstr "%s ha sido introducido en %s." + +#: modules/commands/os_svs.cpp:152 +#, c-format +msgid "%s has been parted from %s." +msgstr "%s ha sido sacado de %s." + +#: modules/commands/cs_unban.cpp:96 +#, c-format +msgid "%s has been unbanned from %s." +msgstr "%s ha sido desbaneado de %s." + +#: modules/commands/ns_alist.cpp:110 +#, c-format +msgid "%s has no access in any channels." +msgstr "%s no tiene acceso en ningún canal." + +#: modules/commands/cs_status.cpp:55 +#, c-format +msgid "%s has no access on %s." +msgstr "%s no tiene acceso en %s." + +#: modules/commands/cs_set.cpp:307 +#, c-format +msgid "%s has too many channels registered." +msgstr "%s tiene demasiados canales registrados." + +#: modules/commands/cs_status.cpp:51 +#, c-format +msgid "%s is a super administrator." +msgstr "%s es un super administrador." + +#: modules/pseudoclients/memoserv.cpp:214 +#, c-format +msgid "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" +msgstr "" +"%s es una utilidad que permite a usuarios de IRC\n" +"enviar mensajes cortos a otros usuarios de IRC, estén\n" +"en línea o no, o a canales(*). Tanto el nick del remitente\n" +"como el del destinatario, o el canal, deben estar\n" +"registrados para enviar un memo.\n" +"Los comandos de %s incluyen:" + +#: modules/commands/cs_invite.cpp:66 +#, c-format +msgid "%s is already in %s!" +msgstr "¡%s ya está en %s!" + +#: modules/commands/os_svs.cpp:99 +#, c-format +msgid "%s is already in %s." +msgstr "%s ya está en %s." + +#: modules/commands/ms_ignore.cpp:65 +#, c-format +msgid "%s is already on the ignore list." +msgstr "%s ya está en la lista de ignorados." + +#: modules/commands/cs_suspend.cpp:97 modules/commands/ns_suspend.cpp:106 +#, c-format +msgid "%s is already suspended." +msgstr "%s ya está suspendido." + +#: modules/commands/ms_rsend.cpp:56 modules/commands/ms_send.cpp:55 +#, c-format +msgid "%s is not a registered unforbidden nick or channel." +msgstr "%s no es un nick o canal registrado." + +#: modules/commands/cs_set.cpp:178 +#, c-format +msgid "%s is not a valid ban type." +msgstr "%s no es un tipo de ban válido." + +#: modules/commands/bs_info.cpp:101 +#, c-format +msgid "%s is not a valid bot or registered channel." +msgstr "%s no es un bot o canal registrado válidos." + +#: include/language.h:86 +#, c-format +msgid "%s is not a valid e-mail address." +msgstr "%s no es e-mail válido." + +#: include/language.h:80 +#, c-format +msgid "%s is not currently on channel %s." +msgstr "%s no está actualmente en el canal %s." + +#: modules/commands/os_svs.cpp:144 +#, c-format +msgid "%s is not in %s." +msgstr "%s no está en %s." + +#: modules/commands/ms_ignore.cpp:77 +#, c-format +msgid "%s is not on the ignore list." +msgstr "%s no está en la lista de ignorados." + +#: modules/commands/cs_status.cpp:90 +#, c-format +msgid "%s is on the auto kick list of %s (%s)." +msgstr "%s está en la lista de kicks automáticos de %s (%s)." + +#: modules/commands/cs_status.cpp:53 +#, c-format +msgid "%s is the founder of %s." +msgstr "%s es el fundador de %s." + +#: modules/commands/cs_status.cpp:78 +#, fuzzy, c-format +msgid "%s matches access entry %s (from entry %s), which has privilege %s." +msgstr "%s está en la lista de acceso de %s, con el nivel de %s." + +#: modules/commands/cs_status.cpp:71 +#, c-format +msgid "%s matches access entry %s, which has privilege %s." +msgstr "%s está en la lista de acceso de %s, con el nivel de %s." + +#: include/language.h:109 +#, fuzzy, c-format +msgid "" +"%s matches an except on %s and cannot be banned until the except has been " +"removed." +msgstr "" +"%s concuerda con una excepción en %s y no puede ser baneado hasta que se " +"haya eliminado la excepción." + +#: modules/commands/cs_status.cpp:96 +#, c-format +msgid "%s matches auto kick entry %s on %s (%s)." +msgstr "" +"%s concuerda con la entrada %s de la lista de kicks automáticos en %s (%s)." + +#: modules/commands/cs_xop.cpp:353 +#, c-format +msgid "%s not found on %s %s list." +msgstr "%s no encontrado en la lista de %s de %s." + +#: modules/commands/cs_access.cpp:338 modules/commands/cs_flags.cpp:255 +#, c-format +msgid "%s not found on %s access list." +msgstr "%s no encontrado en la lista de acceso de %s." + +#: modules/commands/cs_akick.cpp:265 +#, c-format +msgid "%s not found on %s autokick list." +msgstr "%s no encontrado en la lista de kicks automáticos en el canal %s." + +#: modules/commands/bs_badwords.cpp:341 +#, c-format +msgid "%s not found on %s bad words list." +msgstr "%s no encontrado en la lista de bad words de %s." + +#: modules/commands/ns_access.cpp:66 +#, c-format +msgid "%s not found on %s's access list." +msgstr "%s no encontrado en la lista de acceso de %s." + +#: modules/commands/ns_cert.cpp:226 +#, c-format +msgid "%s not found on %s's certificate list." +msgstr "%s no encontrado en la lista de certificados de %s." + +#: modules/commands/os_ignore.cpp:320 +#, c-format +msgid "%s not found on ignore list." +msgstr "%s no encontrado en la lista de ignorados." + +#: modules/commands/os_session.cpp:238 +#, c-format +msgid "" +"%s not found on session list, but has a limit of %d because it matches entry:" +" %s." +msgstr "" +"%s no se encuentra en la lista de sesiones, pero tiene un límite de %d " +"porque coincide con la entrada: %s." + +#: modules/commands/os_session.cpp:418 +#, c-format +msgid "%s not found on session-limit exception list." +msgstr "%s no encontrado en la lista de excepciones al límite de sesiones." + +#: modules/commands/os_sxline.cpp:92 +#, c-format +msgid "%s not found on the %s list." +msgstr "%s no encontrado en la lista %s." + +#: modules/commands/os_akill.cpp:237 +#, c-format +msgid "%s not found on the AKILL list." +msgstr "%s no encontrado en la lista de AKILLs." + +#: modules/commands/cs_flags.cpp:251 +#, c-format +msgid "%s removed from the %s access list." +msgstr "%s borrado de la lista de acceso de %s." + +#: modules/commands/ms_ignore.cpp:74 +#, c-format +msgid "%s removed from the ignore list." +msgstr "%s borrado de tu lista de ignorados." + +#: modules/commands/os_list.cpp:157 +#, c-format +msgid "%s users list:" +msgstr "Lista de usuarios de %s:" + +#: modules/commands/os_ignore.cpp:316 +#, c-format +msgid "%s will no longer be ignored." +msgstr "%s ya no sera ignorado." + +#: modules/commands/os_ignore.cpp:238 +#, c-format +msgid "%s will now be ignored for %s." +msgstr "%s será ignorado por %s." + +#: modules/commands/os_ignore.cpp:233 +#, c-format +msgid "%s will now permanently be ignored." +msgstr "%s será ignorado permanentemente." + +#: include/language.h:66 +#, c-format +msgid "%s%s HELP %s for more information." +msgstr "%s%s HELP %s para más información." + +#: modules/commands/bs_bot.cpp:270 +msgid "ADD nick user host real" +msgstr "ADD nick usuario host nom-real" + +#: modules/commands/bs_bot.cpp:271 +msgid "CHANGE oldnick newnick [user [host [real]]]" +msgstr "CHANGE viejo-nick nuevo-nick [usuario [host [nombre-real]]]" + +#: modules/commands/bs_bot.cpp:272 +msgid "DEL nick" +msgstr "DEL nick" + +#: modules/commands/os_session.cpp:560 +#, fuzzy +msgid "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." +msgstr "" +"EXCEPTION ADD añade la máscara dada a la lista de excepciones.\n" +"Ten en cuenta que las máscaras nick!user@host y user@host\n" +"no son válidas.\n" +"Solo se permiten máscaras de host reales como box.host.dom y\n" +" *.host.dom,ya que el límite de sesiones no tiene en cuenta nicks o\n" +"nombres de usaurio. límite debe ser un número mayor o igual a\n" +"cero. Esto determina cuantas sesiones puede usar a la vez este host.\n" +"Un valor de cero significa que el host puede tener un número de\n" +"sesiones ilimitado. Mira la ayuda del comando AKILL para\n" +"detalles sobre el formato del parámetro opcional expiración.\n" +" \n" +"EXCEPTION DEL elimina la máscara dada de la lista de excepciones.\n" +" \n" +"EXCEPTION MOVE mueve la excepción num a posición. El\n" +"resto de sesiones se reordenarán para rellenar el hueco.\n" +" \n" +"EXCEPTION LIST y EXCEPTION VIEW muestra las sesiones\n" +"actuales; si se proporciona una máscara, la lista solo mostrará las\n" +"sesiones que concuerden con ella. La diferencia es que\n" +"EXCEPTION VIEW proporciona más detalles, mostrando el nombre\n" +"de la persona que añadió la excepción, el límite, la razón, la máscara y\n" +"la fecha y hora de expiración.\n" +" \n" +"Ten en cuenta que los clientes \"usarán\" la primera excepción con la\n" +"concuerden sus hosts." + +#: modules/commands/os_noop.cpp:68 +msgid "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." +msgstr "" +"SET expulsa a todos los operadores del servidor\n" +"dado y evita que adquieran estado de operadores.\n" +"REVOKE elimina esta restricción." + +#: modules/commands/cs_access.cpp:611 +#, c-format +msgid "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." +msgstr "" +"Los niveles de acceso de los usuarios se pueden ver\n" +"usando el comando %s; escribe %s%s HELP LEVELS\n" +"para obtener información." + +#: modules/commands/ms_read.cpp:35 +#, c-format +msgid "[auto-memo] The memo you sent to %s has been viewed." +msgstr "[auto-memo] El memo que enviaste a %s ha sido leido." + +#: modules/commands/ns_group.cpp:92 +#, fuzzy +msgid "[target] [password]" +msgstr "objetivo contraseña" + +#: modules/commands/ns_set.cpp:453 +msgid "address" +msgstr "dirección" + +#: modules/commands/bs_set.cpp:162 +msgid "botname {ON|OFF}" +msgstr "nombre-de-bot {ON|OFF}" + +#: modules/extra/stats/cs_fantasy_top.cpp:39 +#: modules/extra/stats/cs_fantasy_top.cpp:51 +#: modules/commands/cs_suspend.cpp:152 modules/commands/cs_sync.cpp:20 +#: modules/commands/cs_log.cpp:106 modules/commands/bs_assign.cpp:91 +#: modules/commands/cs_info.cpp:20 modules/commands/cs_getkey.cpp:20 +msgid "channel" +msgstr "canal" + +#: modules/commands/cs_set.cpp:138 +msgid "channel bantype" +msgstr "canal tipo-de-ban" + +#: modules/commands/cs_drop.cpp:20 +msgid "channel channel" +msgstr "canal canal" + +#: modules/commands/cs_log.cpp:107 +msgid "channel command method [status]" +msgstr "canal comando método [estado]" + +#: modules/commands/cs_kick.cpp:21 +msgid "channel mask [reason]" +msgstr "canal máscara [razón]" + +#: modules/commands/os_mode.cpp:20 +msgid "channel modes" +msgstr "canal modos" + +#: modules/commands/cs_set.cpp:267 modules/commands/bs_assign.cpp:20 +msgid "channel nick" +msgstr "canal nick" + +#: modules/commands/cs_kick.cpp:20 +msgid "channel nick [reason]" +msgstr "canal nick [razón]" + +#: modules/commands/cs_clone.cpp:115 +msgid "channel target [what]" +msgstr "canal objetivo [que]" + +#: modules/commands/bs_control.cpp:20 modules/commands/bs_control.cpp:80 +msgid "channel text" +msgstr "canal texto" + +#: modules/commands/bs_set.cpp:91 +msgid "channel time" +msgstr "canal tiempo" + +#: modules/commands/os_kick.cpp:20 +msgid "channel user reason" +msgstr "canal usuario razón" + +#: modules/commands/cs_enforce.cpp:228 +msgid "channel what" +msgstr "canal que" + +#: modules/commands/cs_xop.cpp:481 +msgid "channel ADD mask" +msgstr "canal ADD máscara" + +#: modules/commands/cs_access.cpp:499 +msgid "channel ADD mask level" +msgstr "canal ADD máscara nivel" + +#: modules/commands/cs_entrymsg.cpp:194 +msgid "channel ADD message" +msgstr "canal ADD mensaje" + +#: modules/commands/bs_badwords.cpp:371 +msgid "channel ADD word [SINGLE | START | END]" +msgstr "canal ADD palabra [SINGLE | START | END]" + +#: modules/commands/cs_akick.cpp:435 +msgid "channel ADD {nick | mask} [reason]" +msgstr "canal ADD {nick | máscara} [razón]" + +#: modules/commands/cs_topic.cpp:151 +msgid "channel APPEND topic" +msgstr "canal APPEND topic" + +#: modules/commands/cs_access.cpp:503 modules/commands/cs_flags.cpp:376 +#: modules/commands/cs_xop.cpp:484 modules/commands/cs_entrymsg.cpp:197 +#: modules/commands/bs_badwords.cpp:374 modules/commands/cs_akick.cpp:440 +msgid "channel CLEAR" +msgstr "canal CLEAR" + +#: modules/commands/cs_mode.cpp:736 +msgid "channel CLEAR [what]" +msgstr "canal CLEAR [que]" + +#: modules/commands/os_mode.cpp:21 +msgid "channel CLEAR [ALL]" +msgstr "canal CLEAR [ALL]" + +#: modules/commands/cs_entrymsg.cpp:195 +msgid "channel DEL num" +msgstr "canal DEL num" + +#: modules/commands/cs_access.cpp:500 modules/commands/cs_xop.cpp:482 +msgid "channel DEL {mask | entry-num | list}" +msgstr "canal DEL {máscara | num-entrada | lista}" + +#: modules/commands/cs_akick.cpp:436 +msgid "channel DEL {nick | mask | entry-num | list}" +msgstr "canal DEL {nick | máscara | num-entrada | lista}" + +#: modules/commands/bs_badwords.cpp:372 +msgid "channel DEL {word | entry-num | list}" +msgstr "canal DEL {palabra | num-entrada | lista}" + +#: modules/commands/cs_akick.cpp:439 +msgid "channel ENFORCE" +msgstr "canal ENFORCE" + +#: modules/commands/cs_access.cpp:744 modules/commands/cs_entrymsg.cpp:196 +msgid "channel LIST" +msgstr "canal LIST" + +#: modules/commands/cs_akick.cpp:437 +msgid "channel LIST [mask | entry-num | list]" +msgstr "canal LIST [máscara | num-entrada | lista]" + +#: modules/commands/cs_access.cpp:501 modules/commands/cs_xop.cpp:483 +#: modules/commands/bs_badwords.cpp:373 +msgid "channel LIST [mask | list]" +msgstr "canal LIST [máscara | lista]" + +#: modules/commands/cs_flags.cpp:375 +msgid "channel LIST [mask | +flags]" +msgstr "canal LIST [máscara | +marcas]" + +#: modules/commands/cs_mode.cpp:734 +msgid "channel LOCK {ADD|DEL|SET|LIST} [what]" +msgstr "canal LOCK {ADD|DEL|SET|LIST} [que]" + +#: modules/commands/cs_access.cpp:745 +msgid "channel RESET" +msgstr "canal RESET" + +#: modules/commands/cs_mode.cpp:735 +msgid "channel SET modes" +msgstr "canal SET modos" + +#: modules/commands/cs_access.cpp:742 +msgid "channel SET type level" +msgstr "canal SET tipo nivel" + +#: modules/commands/cs_akick.cpp:438 +msgid "channel VIEW [mask | entry-num | list]" +msgstr "canal VIEW [máscara | num-entrada | lista]" + +#: modules/commands/cs_access.cpp:502 +msgid "channel VIEW [mask | list]" +msgstr "canal VIEW [máscara | lista]" + +#: modules/commands/cs_register.cpp:20 modules/commands/cs_set.cpp:205 +msgid "channel [description]" +msgstr "canal [descripción]" + +#: modules/commands/cs_set.cpp:950 modules/commands/cs_invite.cpp:20 +#: modules/commands/cs_unban.cpp:20 +msgid "channel [nick]" +msgstr "canal [nick]" + +#: modules/commands/cs_set_misc.cpp:96 +msgid "channel [parameters]" +msgstr "canal [parámetros]" + +#: modules/commands/cs_mode.cpp:807 modules/commands/cs_status.cpp:20 +msgid "channel [user]" +msgstr "canal [usuario]" + +#: modules/commands/cs_suspend.cpp:59 +msgid "channel [+expiry] [reason]" +msgstr "canal [+expiración] [razón]" + +#: modules/commands/cs_ban.cpp:40 +msgid "channel [+expiry] {nick | mask} [reason]" +msgstr "canal [+expiración] {nick | máscara} [razón]" + +#: modules/commands/cs_flags.cpp:374 +#, fuzzy +msgid "channel [MODIFY] mask changes" +msgstr "canal MODIFY máscara cambios" + +#: modules/commands/cs_topic.cpp:150 +#, fuzzy +msgid "channel [SET] [topic]" +msgstr "canal SET [topic]" + +#: modules/commands/cs_topic.cpp:152 +msgid "channel [UNLOCK|LOCK]" +msgstr "canal [UNLOCK|LOCK]" + +#: modules/fantasy.cpp:20 modules/commands/greet.cpp:20 +#: modules/commands/bs_assign.cpp:154 +msgid "channel {ON|OFF}" +msgstr "canal {ON|OFF}" + +#: modules/commands/bs_kick.cpp:491 +msgid "channel {ON|OFF} [ttb [ln [secs]]]" +msgstr "canal {ON|OFF} [ttb [ln [segs]]]" + +#: modules/commands/bs_kick.cpp:361 +msgid "channel {ON|OFF} [ttb [min [percent]]]" +msgstr "canal {ON|OFF} [ttb [min [porcentaje]]]" + +#: modules/commands/bs_kick.cpp:623 +msgid "channel {ON|OFF} [ttb [num]]" +msgstr "canal {ON|OFF} [ttb [num]]" + +#: modules/commands/bs_kick.cpp:252 modules/commands/bs_kick.cpp:288 +#: modules/commands/bs_kick.cpp:327 modules/commands/bs_kick.cpp:457 +#: modules/commands/bs_kick.cpp:589 modules/commands/bs_kick.cpp:724 +#: modules/commands/bs_kick.cpp:758 +msgid "channel {ON|OFF} [ttb]" +msgstr "canal {ON|OFF} [ttb]" + +#: modules/commands/cs_access.cpp:743 +msgid "channel {DIS | DISABLE} type" +msgstr "canal {DIS | DISABLE} tipo" + +#: modules/commands/cs_set.cpp:873 +msgid "channel {ON | LEVEL | OFF}" +msgstr "canal {ON | LEVEL | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:18 modules/commands/cs_set.cpp:75 +#: modules/commands/cs_set.cpp:336 modules/commands/cs_set.cpp:401 +#: modules/commands/cs_set.cpp:473 modules/commands/cs_set.cpp:622 +#: modules/commands/cs_set.cpp:684 modules/commands/cs_set.cpp:747 +#: modules/commands/cs_set.cpp:811 modules/commands/cs_set.cpp:1044 +#: modules/commands/bs_kick.cpp:792 modules/commands/bs_kick.cpp:857 +#: modules/commands/cs_topic.cpp:21 modules/commands/cs_list.cpp:181 +msgid "channel {ON | OFF}" +msgstr "canal {ON | OFF}" + +#: modules/commands/ns_getemail.cpp:24 +msgid "email" +msgstr "email" + +#: modules/commands/ns_set.cpp:794 +msgid "language" +msgstr "idioma" + +#: modules/commands/ms_sendall.cpp:25 modules/commands/ms_staff.cpp:25 +msgid "memo-text" +msgstr "texto-del-memo" + +#: modules/commands/gl_global.cpp:22 modules/commands/greet.cpp:84 +msgid "message" +msgstr "mensaje" + +#: modules/commands/os_modinfo.cpp:20 modules/commands/os_module.cpp:20 +#: modules/commands/os_module.cpp:57 modules/commands/os_module.cpp:129 +msgid "modname" +msgstr "nombre-del-módulo" + +#: modules/commands/ns_set.cpp:330 +msgid "new-display" +msgstr "nuevo-display" + +#: modules/commands/ns_set.cpp:120 +msgid "new-password" +msgstr "nueva-contraseña" + +#: modules/extra/stats/cs_fantasy_stats.cpp:52 modules/commands/hs_del.cpp:20 +#: modules/commands/hs_del.cpp:60 modules/commands/ms_check.cpp:20 +#: modules/commands/hs_request.cpp:192 modules/commands/cs_seen.cpp:262 +msgid "nick" +msgstr "nick" + +#: modules/commands/os_svs.cpp:79 +msgid "nick channel" +msgstr "nick canal" + +#: modules/commands/os_svs.cpp:123 +#, fuzzy +msgid "nick channel [reason]" +msgstr "nick [razón]" + +#: modules/commands/os_oline.cpp:20 +msgid "nick flags" +msgstr "nick marcas" + +#: modules/commands/hs_set.cpp:20 modules/commands/hs_set.cpp:126 +msgid "nick hostmask" +msgstr "nick máscara" + +#: modules/commands/os_svs.cpp:20 +msgid "nick newnick" +msgstr "nick nuevo-nick" + +#: modules/commands/hs_request.cpp:241 +msgid "nick [reason]" +msgstr "nick [razón]" + +#: modules/commands/ns_getpass.cpp:20 modules/commands/ns_drop.cpp:19 +#: modules/commands/ns_suspend.cpp:161 +msgid "nickname" +msgstr "nick" + +#: modules/commands/ns_set.cpp:546 +msgid "nickname address" +msgstr "nick dirección" + +#: modules/commands/ns_resetpass.cpp:22 +msgid "nickname email" +msgstr "nick email" + +#: modules/commands/ns_set.cpp:872 +msgid "nickname language" +msgstr "nick idioma" + +#: modules/commands/greet.cpp:145 +msgid "nickname message" +msgstr "nick mensaje" + +#: modules/commands/ns_set.cpp:399 +msgid "nickname new-display" +msgstr "nick nuevo-display" + +#: modules/commands/ns_set.cpp:173 +msgid "nickname new-password" +msgstr "nick nueva-contraseña" + +#: modules/commands/ns_set_misc.cpp:170 +msgid "nickname [parameter]" +msgstr "nick [parámetro]" + +#: modules/commands/ns_recover.cpp:150 +msgid "nickname [password]" +msgstr "nick [contraseña]" + +#: modules/commands/ns_suspend.cpp:61 +msgid "nickname [+expiry] [reason]" +msgstr "nick [+expiración] [razón]" + +#: modules/commands/ns_info.cpp:239 +msgid "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +msgstr "nick {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:130 modules/commands/ns_set.cpp:302 +#: modules/commands/ns_set.cpp:631 modules/commands/ns_set.cpp:985 +#: modules/commands/ns_set.cpp:1076 modules/commands/ns_set.cpp:1105 +#: modules/commands/ns_list.cpp:252 +msgid "nickname {ON | OFF}" +msgstr "nick {ON | OFF}" + +#: modules/commands/ns_set.cpp:760 +msgid "nickname {ON | QUICK | IMMED | OFF}" +msgstr "nick {ON | QUICK | IMMED | OFF}" + +#: modules/commands/bs_set.cpp:20 +msgid "option (channel | bot) settings" +msgstr "opción (canal | bot) configuración" + +#: modules/commands/cs_set.cpp:21 +msgid "option channel parameters" +msgstr "opción canal parámetros" + +#: modules/commands/bs_kick.cpp:120 +msgid "option channel {ON|OFF} [settings]" +msgstr "opción canal {ON|OFF} [configuración]" + +#: modules/commands/ns_set.cpp:75 +msgid "option nickname parameters" +msgstr "opción nick parámetros" + +#: modules/commands/ms_set.cpp:207 modules/commands/ns_set.cpp:20 +msgid "option parameters" +msgstr "opción parámetros" + +#: modules/commands/os_set.cpp:170 +msgid "option setting" +msgstr "opción configuración" + +#: modules/commands/ns_register.cpp:22 +msgid "passcode" +msgstr "código" + +#: modules/commands/os_login.cpp:19 +msgid "password" +msgstr "contraseña" + +#: modules/commands/ns_register.cpp:124 +msgid "password [email]" +msgstr "contraseña [email]" + +#: modules/commands/ns_register.cpp:122 +msgid "password email" +msgstr "contraseña email" + +#: modules/commands/cs_list.cpp:21 +msgid "pattern [SUSPENDED] [NOEXPIRE]" +msgstr "patrón [SUSPENDED] [NOEXPIRE]" + +#: modules/commands/ns_list.cpp:20 +msgid "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" +msgstr "patrón [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/os_jupe.cpp:20 +msgid "server [reason]" +msgstr "servidor [razón]" + +#: modules/commands/os_mode.cpp:147 +msgid "user modes" +msgstr "usuario modos" + +#: modules/commands/os_kill.cpp:20 +msgid "user [reason]" +msgstr "usuario [razón]" + +#: modules/commands/os_sxline.cpp:440 +msgid "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." +msgstr "" +" \n" +"SNLINE ADD añade la máscara (nombre real) dada a\n" +"la lista SNLINE con la razón dada (que es obligatoria).\n" +"expiración debe ser un entero seguido de d(días),\n" +"h (horas), o m (minutos). No se permiten combinaciones\n" +"(como1h30m). Si no se especifica la unidad, se tomará como\n" +"días (así que +30 significa por sí mismo 30 days).\n" +"Para añadir una SNLINE que no expire, usa +0. Si la máscara\n" +"a añadir comienza con un +, se debe dar la expiración\n" +"incluso si es la misma que la predeterminada. El tiempo de\n" +"expiración predeterminado de una SNLINE se puede ver con\n" +"el comandoSTATS AKILL.\n" +" \n" +"Aviso: ya que la máscara (nombre real) puede contener espcios,\n" +"el separador entre ella y la razón debe ser una coma." + +#: modules/commands/os_sxline.cpp:678 +msgid "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +" \n" +"SQLINE ADD añade la máscara (nick) dada a la lista\n" +"SQNLINE con la razón dada (que es obligatoria).\n" +"expiración debe ser un entero seguido de d(días),\n" +"h (horas), o m (minutos). No se permiten combinaciones\n" +"(como1h30m). Si no se especifica la unidad, se tomará como\n" +"días (así que +30 significa por sí mismo 30 days).\n" +"Para añadir una SQLINE que no expire, usa +0. Si la máscara\n" +"a añadir comienza con un +, se debe dar la expiración\n" +"incluso si es la misma que la predeterminada. El tiempo de\n" +"expiración predeterminado de una SQLINE se puede ver con\n" +"el comandoSTATS AKILL." + +#: modules/pseudoclients/nickserv.cpp:492 +#, c-format +msgid "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." +msgstr "" +" \n" +"Las cuentas que no se usen son susceptibles de expirar\n" +"automáticamente, por ejemplo, serán borradas después\n" +"de %d días sin usar." + +#: modules/pseudoclients/botserv.cpp:143 +msgid "" +" \n" +"Available commands are:" +msgstr "" +" \n" +"Los comandos disponibles son:" + +#: modules/pseudoclients/botserv.cpp:167 +#, c-format +msgid "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." +msgstr "" +" \n" +"El bot entrará al canal cuando haya al menos\n" +"%d usuario(s) en él." + +#: modules/fantasy.cpp:69 +#, c-format +msgid "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." +msgstr "" +" \n" +"Habilita o deshabilita el modo fantasía en un canal.\n" +"Cuando está activado, los usuarios podrán usar los\n" +"comandos fantasía en un canal cuando vayan precedidos\n" +"con uno de los siguientes caracteres: %s\n" +" \n" +"Ten en cuenta que los usuarios que quieran usar los\n" +"comandos fantasía DEBEN tener nivel suficiente tanto\n" +"para usar FANTASIA como para usar el comando en\n" +"cuestión." + +#: modules/commands/greet.cpp:69 +msgid "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." +msgstr "" +" \n" +"Habilita o deshabilita el modo saludo en un canal.\n" +"Cuando está habilitado, el bot mostrará los mensajes\n" +"de saludo de los usuarios cuando entran al canal, si\n" +"tienen nivel suficiente." + +#: modules/commands/bs_kick.cpp:843 +msgid "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Habilita o deshabilita el modo de proteccion de ops\n" +"en un canal. Al habilitarlo, los ops no serán kickeados\n" +"por el bot, incluso si no concuerdan con el nivel NOKICK." + +#: modules/commands/bs_kick.cpp:908 +msgid "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Habilita o deshabilita el modo de proteccion de voices\n" +"en un canal. Al habilitarlo, los voices no serán kickeados\n" +"por el bot, incluso si no concuerdan con el nivel NOKICK." + +#: modules/pseudoclients/botserv.cpp:141 +#, c-format +msgid "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" +msgstr "" +" \n" +"Los comandos fantasía pueden ser prefijados con uno de estos caracteres: %s\n" + +#: modules/commands/cs_register.cpp:105 +msgid "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." +msgstr "" +" \n" +"AVISO: Para registrar un canal, primero debes registrar\n" +"tu nick." + +#: modules/pseudoclients/chanserv.cpp:272 +#, c-format +msgid "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." +msgstr "" +" \n" +"Ten en cuenta que cualquier canal que no sea usado en\n" +"%d dias (por ejemplo, no entra ningun usuario de la lista\n" +"de acceso en ese periodo de tiempo) será eliminado\n" +"automáticamente." + +#: modules/commands/cs_register.cpp:101 +#, c-format +msgid "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +msgstr "" +" \n" +"Mira el comando %s (%s%s HELP ACCESS) para\n" +"obtener información sobre como dar parte de estos privilegios\n" +"a otros usuarios del canal.\n" + +#: modules/pseudoclients/nickserv.cpp:486 +msgid "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." +msgstr "" +" \n" +"Los Operadores de Servicios también pueden eliminar\n" +"cualquier nick y pueden ver la lista de acceso de cualquier\n" +"nick sin necesidad de conocer la contraseña." + +#: modules/pseudoclients/chanserv.cpp:277 +msgid "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." +msgstr "" +" \n" +"Los Operadores de Servicios también pueden, dependiendo\n" +"de su acceso, eliminar cualquier canal, ver (y modicar) las listas\n" +"de acceso, niveles y akicks, y configuraciones de cualquier canal." + +#: modules/commands/bs_set.cpp:147 +msgid "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." +msgstr "" +" \n" +"Establece el tiempo de expiración de los bans del bot. Si se activa,\n" +"cualquier ban puesto por el bot, se eliminará automáticamente\n" +"después del tiempo dado. Ponlo en 0 para deshabilitar la expiración\n" +"automática." + +#: modules/commands/cs_xop.cpp:542 +#, c-format +msgid "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." +msgstr "" +" \n" +"El comando %s ADD añade el nick dado a la lista %s.\n" +" \n" +"El comando %s DEL borra el nick dado de la lista %s.\n" +"Si se introduce una lista de números, se borrarán dichas\n" +"entradas. (Mira los ejemplos para LIST)\n" +" \n" +"El comando %s LIST muestra la lista %s. Si se proporciona\n" +"una máscara, solo se muestran las entradas que concuerdan\n" +"con la máscara. Si se proporciona una lista de números, solo\n" +"se muestran dichas entradas; por ejemplo:\n" +" %s #canal LIST 2-5,7-9\n" +" Lista las entradas %s números 2 a 5 y número 7 a 9.\n" +" \n" +"El comando %s CLEAR borra todas las entradas de la\n" +"lista %s." + +#: modules/commands/cs_akick.cpp:508 +#, c-format +msgid "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." +msgstr "" +" \n" +"El comando AKICK DEL elimina el nick o máscara dados\n" +"de la lista de Kick Automático. Sin embargo, no elimina ningún\n" +"ban puesto por un Kick Automático; esos deben eliminarse\n" +"manualmente.\n" +" \n" +"El comando AKICK LIST muestra la lista de Kick Automático\n" +"o solo las entradas que concuerden con la máscara dada.\n" +" \n" +"El comando AKICK VIEW proporciona más detalles que el comando\n" +"AKICK LIST.\n" +" \n" +"El comando AKICK ENFORCE provoca que se fuerce la lista\n" +"AKICK de %s eliminando a aquellos usuarios que concuerda con\n" +"una máscara AKICK.\n" +" \n" +"El comando AKICK CLEAR borra todas las entradas de la\n" +"list akick." + +#: modules/commands/os_akill.cpp:448 +msgid "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." +msgstr "" +" \n" +"El comando AKILL DEL elimina la máscara dada de la lista\n" +"AKILL si está presente. Si se proporciona una lista de números,\n" +"se eliminan dichas entradas. (Mira el ejemplo para LIST más\n" +"abajo.)\n" +" \n" +"El comando AKILL LIST muestra la lista AKILL.\n" +"Si se proporciona una máscara, solo se muestran las entradas\n" +"que coinciden con la máscara. Si se proporciona una lista de\n" +"números, solo se muestran dichas entradas; por ejemplo:\n" +" AKILL LIST 2-5,7-9\n" +" Lista las entradas AKILL números 2 a 5 y 7 a 9.\n" +" \n" +"AKILL VIEW es una versión más completa de AKILL LIST, y\n" +"mostrará quien añadió el AKILL, la fecha en la que lo hizo, cuando\n" +"expira, la máscara usuario@host/ip y la razón.\n" +" \n" +"AKILL CLEAR borra todas las entradas de la lista AKILL." + +#: modules/commands/os_sxline.cpp:462 +msgid "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." +msgstr "" +" \n" +"El comando SNLINE DEL elimina la máscara dada de la lista\n" +"SNLINE si está presente. Si se proporciona una lista de números,\n" +"se eliminan dichas entradas. (Mira el ejemplo para LIST más\n" +"abajo.)\n" +" \n" +"El comando SNLINE LIST muestra la lista SNLINE.\n" +"Si se proporciona una máscara, solo se muestran las entradas\n" +"que coinciden con la máscara. Si se proporciona una lista de\n" +"números, solo se muestran dichas entradas; por ejemplo:\n" +" SNLINE LIST 2-5,7-9\n" +" Lista las entradas SNLINE números 2 a 5 y 7 a 9.\n" +" \n" +"SNLINE VIEW es una versión más completa de SNLINE LIST, y\n" +"mostrará quien añadió la SNLINE, la fecha en la que lo hizo, cuando\n" +"expira, la máscara de nombre real y la razón.\n" +" \n" +"SNLINE CLEAR borra todas las entradas de la lista SNLINE." + +#: modules/commands/os_sxline.cpp:697 +msgid "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." +msgstr "" +" \n" +"El comando SQLINE DEL elimina la máscara dada de la lista\n" +"SQLINE si está presente. Si se proporciona una lista de números,\n" +"se eliminan dichas entradas. (Mira el ejemplo para LIST más\n" +"abajo.)\n" +" \n" +"El comando SQLINE LIST muestra la lista SQLINE.\n" +"Si se proporciona una máscara, solo se muestran las entradas\n" +"que coinciden con la máscara. Si se proporciona una lista de\n" +"números, solo se muestran dichas entradas; por ejemplo:\n" +" SQLINE LIST 2-5,7-9\n" +" Lista las entradas SQLINE números 2 a 5 y 7 a 9.\n" +" \n" +"SQLINE VIEW es una versión más completa de SQLINE LIST, y\n" +"mostrará quien añadió la SQLINE, la fecha en la que lo hizo, cuando\n" +"expira, la máscara y la razón.\n" +" \n" +"SQLINE CLEAR borra todas las entradas de la lista SQLINE." + +#: modules/commands/bs_assign.cpp:197 +#, fuzzy +msgid "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." +msgstr "" +" \n" +"Esta opción hace al canal no asignable. Si un bot ya\n" +"está asignado al canal, es desasignado automáticamente\n" +"cuando habilitas esta opción." + +#: modules/commands/bs_set.cpp:199 +msgid "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." +msgstr "" +" \n" +"Esta opción evita que un bot sea asignado a un canal\n" +"por usuarios que no sean IRCOps." + +#: modules/pseudoclients/memoserv.cpp:227 +#, c-format +msgid "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." +msgstr "" +" \n" +"Escribe %s%s HELP comando para ayuda sobre cualquiera\n" +"de los comandos anteriores." + +#: modules/commands/os_oper.cpp:167 +#, c-format +msgid " %s is online using this oper block." +msgstr " %s está en línea usando este bloque de operador." + +#: modules/commands/os_modinfo.cpp:55 +#, c-format +msgid " Command %s on %s is linked to %s" +msgstr " El comando %s en %s está asociado a %s" + +#: modules/commands/os_modinfo.cpp:43 +#, c-format +msgid " Providing service: %s" +msgstr " Servicio proporcionado: %s" + +#: modules/commands/os_oper.cpp:163 +msgid " This oper is configured in the configuration file." +msgstr " Este operador está definido en el archivo de configuración." + +#: modules/commands/os_modinfo.cpp:34 +#, c-format +msgid " Loaded at: %p" +msgstr " Cargado en: %p" + +#: modules/commands/cs_seen.cpp:303 +#, c-format +msgid " but %s mysteriously dematerialized." +msgstr " pero %s misteriosamente desmaterializado." + +#: src/messages.cpp:339 +#, c-format +msgid "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." +msgstr "" +"\"/msg %s\" ya no está soportado. Usa \"/msg %s@%s\" o \"/%s\" en su lugar." + +#: modules/commands/os_jupe.cpp:19 +msgid "\"Jupiter\" a server" +msgstr "\"Jupitear\" un servidor" + +#: modules/commands/os_oper.cpp:161 +#, c-format +msgid "%-8s %s" +msgstr "%-8s %s" + +#: modules/extra/stats/cs_fantasy_top.cpp:152 +#, c-format +msgid "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" +"%2lu %-16s letras: %s, palabras: %s, líneas: %s, smileys: %s, acciones: %s" + +#: src/misc.cpp:359 +msgid "%b %d %H:%M:%S %Y %Z" +msgstr "%b %d %H:%M:%S %Y %Z" + +#: modules/commands/cs_log.cpp:205 +#, c-format +msgid "%c is an unknown status mode." +msgstr "%c es un modo de estado desconocido." + +#: modules/commands/cs_mode.cpp:431 +#, c-format +msgid "%c%c is not locked on %s." +msgstr "%c%c no está bloqueado en %s." + +#: modules/commands/cs_mode.cpp:427 +#, c-format +msgid "%c%c%s has been unlocked from %s." +msgstr "%c%c%s ha sido desbloqueado desde %s." + +#: modules/commands/cs_clone.cpp:56 +#, c-format +msgid "%d access entries from %s have been cloned to %s." +msgstr "%d entradas de acceso de %s han sido clonadas a %s." + +#: modules/commands/bs_botlist.cpp:56 +#, c-format +msgid "%d bots available." +msgstr "%d bots disponibles." + +#: modules/commands/os_modinfo.cpp:189 +#, c-format +msgid "%d modules loaded." +msgstr "%d módulos cargados." + +#: modules/commands/ns_group.cpp:357 +#, c-format +msgid "%d nickname(s) in the group." +msgstr "%d nick(s) en el grupo." + +#: modules/commands/cs_seen.cpp:137 +#, c-format +msgid "%lu nicks are stored in the database, using %.2Lf kB of memory." +msgstr "" +"%lu nicks están almacenados en la base de datos, usando %.2Lf kB de memoria." + +#: modules/commands/cs_xop.cpp:241 modules/commands/cs_xop.cpp:372 +#: modules/commands/cs_xop.cpp:450 +#, c-format +msgid "%s %s list is empty." +msgstr "La lista de %s de %s está vacía." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1181 +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1201 +#: modules/commands/bs_kick.cpp:1211 +#, c-format +msgid "%s (%d kick(s) to ban)" +msgstr "%s (%d kick(s) para banear)" + +#: modules/commands/bs_kick.cpp:1161 +#, c-format +msgid "%s (%d kick(s) to ban; %d lines in %ds)" +msgstr "%s (%d kick(s) para banear; %d líneas en %ds)" + +#: modules/commands/bs_kick.cpp:1171 +#, c-format +msgid "%s (%d kick(s) to ban; %d times)" +msgstr "%s (%d kick(s) para banear; %d veces)" + +#: modules/commands/bs_kick.cpp:1141 +#, c-format +msgid "%s (%d kick(s) to ban; minimum %d/%d%%)" +msgstr "%s (%d kick(s) para banear; mínimo %d/%d%%)" + +#: modules/commands/bs_kick.cpp:1163 +#, c-format +msgid "%s (%d lines in %ds)" +msgstr "%s (%d líneas en %ds)" + +#: modules/commands/bs_kick.cpp:1173 +#, c-format +msgid "%s (%d times)" +msgstr "%s (%d veces)" + +#: modules/commands/cs_seen.cpp:358 +#, c-format +msgid "%s (%s) was kicked from %s (\"%s\") %s ago%s" +msgstr "%s (%s) fue kickeado de %s (\"%s\") hace%s%s" + +#: modules/commands/cs_seen.cpp:355 +#, c-format +msgid "%s (%s) was kicked from a secret channel %s ago%s" +msgstr "%s (%s) fue kickeado de un canal secreto hace %s%s" + +#: modules/commands/cs_seen.cpp:326 +#, c-format +msgid "%s (%s) was last seen changing nick from %s to %s %s ago%s" +msgstr "%s (%s) cambió el nick por última vez de %s a %s hace %s%s" + +#: modules/commands/cs_seen.cpp:321 +#, c-format +msgid "%s (%s) was last seen changing nick to %s %s ago%s" +msgstr "%s (%s) cambió el nick por última vez a %s hace %s%s" + +#: modules/commands/cs_seen.cpp:310 +#, c-format +msgid "%s (%s) was last seen connecting %s ago (%s)%s" +msgstr "%s (%s) fue visto por última vez conectando hace %s (%s)%s" + +#: modules/commands/cs_seen.cpp:335 +#, c-format +msgid "%s (%s) was last seen joining %s %s ago%s" +msgstr "%s (%s) fue visto por última vez entrando a %s hace %s %s" + +#: modules/commands/cs_seen.cpp:332 +#, c-format +msgid "%s (%s) was last seen joining a secret channel %s ago%s" +msgstr "%s (%s) fue visto por última vez entrando a un canal secreto hace %s%s" + +#: modules/commands/cs_seen.cpp:344 +#, c-format +msgid "%s (%s) was last seen parting %s %s ago%s" +msgstr "%s (%s) fue visto por última vez saliendo de %s hace %s%s" + +#: modules/commands/cs_seen.cpp:341 +#, c-format +msgid "%s (%s) was last seen parting a secret channel %s ago%s" +msgstr "" +"%s (%s) fue visto por última vez saliendo de un canal secreto hace %s%s" + +#: modules/commands/cs_seen.cpp:349 +#, c-format +msgid "%s (%s) was last seen quitting (%s) %s ago (%s)." +msgstr "%s (%s) fue visto por última vez desconectando (%s) hace %s (%s)." + +#: modules/commands/bs_kick.cpp:1143 +#, c-format +msgid "%s (minimum %d/%d%%)" +msgstr "%s (mínimo %d/%d%%)" + +#: modules/commands/cs_access.cpp:245 modules/commands/cs_access.cpp:349 +#: modules/commands/cs_access.cpp:454 modules/commands/cs_access.cpp:467 +#: modules/commands/cs_flags.cpp:295 +#, c-format +msgid "%s access list is empty." +msgstr "La lista de acceso de %s esta vacía." + +#: modules/commands/ns_ajoin.cpp:184 +#, c-format +msgid "%s added to %s's auto join list." +msgstr "%s añadido a la lista de auto join de %s." + +#: src/xline.cpp:389 +#, c-format +msgid "%s already exists." +msgstr "%s ya existe." + +#: modules/commands/cs_akick.cpp:202 modules/commands/cs_akick.cpp:387 +#: modules/commands/cs_akick.cpp:400 +#, c-format +msgid "%s autokick list is empty." +msgstr "La lista de kicks automáticos del canal %s está vacía." + +#: modules/commands/bs_badwords.cpp:198 modules/commands/bs_badwords.cpp:316 +#, c-format +msgid "%s bad words list is empty." +msgstr "La lista de bad words de %s está vacía." + +#: modules/commands/cs_set.cpp:993 +#, c-format +msgid "%s cannot be the successor on channel %s as they are the founder." +msgstr "%s no puede ser el sucesor en el canal %s ya que es el fundador." + +#: modules/pseudoclients/global.cpp:90 modules/pseudoclients/hostserv.cpp:78 +#: modules/pseudoclients/operserv.cpp:287 +#, c-format +msgid "%s commands:" +msgstr "Comandos para %s:" + +#: include/language.h:69 +#, c-format +msgid "%s coverage is too wide; Please use a more specific mask." +msgstr "%s cubre un rango muy amplio; usa una máscara más específica." + +#: modules/commands/ms_info.cpp:94 +#, c-format +msgid "%s currently has %d memos, of which %d are unread." +msgstr "" +"%s actualmente tiene %d memos, de los cuales %d aún no han sido leídos." + +#: modules/commands/ms_info.cpp:92 +#, c-format +msgid "%s currently has %d memos, of which 1 is unread." +msgstr "%s actualmente tiene %d memos, de los cuales 1 aún no ha sido leído." + +#: modules/commands/ms_info.cpp:90 +#, c-format +msgid "%s currently has %d memos." +msgstr "%s actualmente tiene %d memos." + +#: modules/commands/ms_info.cpp:88 +#, c-format +msgid "%s currently has %d memos; all of them are unread." +msgstr "%s actualmente tiene %d memos, de los cuales ninguno ha sido leído ." + +#: modules/commands/ms_info.cpp:77 +#, c-format +msgid "%s currently has 1 memo, and it has not yet been read." +msgstr "%s actualmente tiene 1 memo y aún no ha sido leído." + +#: modules/commands/ms_info.cpp:79 +#, c-format +msgid "%s currently has 1 memo." +msgstr "%s tiene 1 memo." + +#: modules/commands/ms_info.cpp:73 +#, c-format +msgid "%s currently has no memos." +msgstr "%s no tiene memos." + +#: modules/commands/os_forbid.cpp:344 +#, c-format +msgid "%s deleted from the %s forbid list." +msgstr "%s borrado de la lista de prohibiciones de %s." + +#: include/language.h:105 +#, c-format +msgid "%s for %s set to %s." +msgstr "%s para %s establecido a %s." + +#: include/language.h:106 +#, c-format +msgid "%s for %s unset." +msgstr "%s para %s eliminado." + +#: modules/commands/ns_ajoin.cpp:176 +#, c-format +msgid "%s had an invalid key specified, and was thus ignored." +msgstr "La clave especificada para %s no es válida, y fue ignorada." + +#: modules/commands/ms_info.cpp:111 +#, c-format +msgid "%s has no memo limit." +msgstr "%s no tiene límite de memos." + +#: include/language.h:115 +#, c-format +msgid "%s has no memos." +msgstr "%s no tiene memos." + +#: include/language.h:118 +#, c-format +msgid "%s has no new memos." +msgstr "%s no tiene nuevos memos." + +#: modules/commands/ns_info.cpp:53 +#, c-format +msgid "%s is %s" +msgstr "%s es %s" + +#: modules/commands/ns_info.cpp:59 +#, c-format +msgid "%s is a Services Operator of type %s." +msgstr "%s es un Operador de Servicios del tipo %s." + +#: modules/commands/cs_seen.cpp:281 +#, c-format +msgid "%s is a client on services." +msgstr "%s es un cliente en los Servicios." + +#: modules/commands/cs_seen.cpp:200 +#, c-format +msgid "%s is a network service." +msgstr "%s es un servicio de red." + +#: src/xline.cpp:407 +#, c-format +msgid "%s is already covered by %s." +msgstr "%s ya está cubierto por %s." + +#: modules/commands/ns_ajoin.cpp:170 +#, c-format +msgid "%s is already on %s's auto join list." +msgstr "%s ya está en la lista de auto join de %s." + +#: modules/commands/ns_info.cpp:56 +#, c-format +msgid "%s is an unconfirmed nickname." +msgstr "%s es un nick no confirmado." + +#: modules/commands/cs_flags.cpp:432 +#, c-format +msgid "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." +msgstr "" +"%s es otra forma de modificar la lista de acceso del canal, similar a\n" +"los métodos XOP y ACCESS." + +#: modules/commands/ns_info.cpp:74 +#, c-format +msgid "%s is currently online." +msgstr "%s está actualmente en línea. " + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is disabled" +msgstr "%s está deshabilitado" + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is enabled" +msgstr "%s está habilitado" + +#: modules/commands/os_dns.cpp:507 +#, c-format +msgid "%s is not a valid IP address." +msgstr "%s no es una IP válida." + +#: modules/commands/cs_log.cpp:167 modules/commands/cs_log.cpp:192 +#, c-format +msgid "%s is not a valid command." +msgstr "%s no es un comando válido." + +#: modules/commands/cs_log.cpp:198 +#, c-format +msgid "%s is not a valid logging method." +msgstr "%s no es un método de registro válido." + +#: modules/commands/ms_info.cpp:124 +#, c-format +msgid "%s is not notified of new memos." +msgstr "%s no es notificado de memos nuevos." + +#: modules/commands/ms_info.cpp:118 +#, c-format +msgid "%s is notified of new memos at logon and when they arrive." +msgstr "" +"%s es notificado de memos nuevos cuando se conecta y cuando le son enviados." + +#: modules/commands/ms_info.cpp:122 +#, c-format +msgid "%s is notified of new memos at logon." +msgstr "%s es notificado de nuevos memos cuando se conecta." + +#: modules/commands/ms_info.cpp:120 +#, c-format +msgid "%s is notified when new memos arrive." +msgstr "%s es notificado cuando nuevos memos le son enviados." + +#: modules/commands/cs_seen.cpp:232 +#, c-format +msgid "%s is on the channel right now (as %s)!" +msgstr "¡%s está en el canal ahora mismo (como %s)!" + +#: modules/commands/cs_seen.cpp:221 +#, c-format +msgid "%s is on the channel right now!" +msgstr "¡%s está en el canal ahora mismo!" + +#: modules/commands/cs_xop.cpp:434 +#, c-format +msgid "%s list for %s" +msgstr "Lista %s para %s" + +#: modules/commands/os_sxline.cpp:69 modules/commands/os_sxline.cpp:113 +#, c-format +msgid "%s list is empty." +msgstr "La lista %s esta vacia." + +#: modules/commands/cs_mode.cpp:376 +#, c-format +msgid "%s locked on %s." +msgstr "%s bloqueado en %s." + +#: modules/extra/stats/cs_fantasy_stats.cpp:120 +#, c-format +msgid "%s not found." +msgstr "%s no encontrado." + +#: modules/commands/os_config.cpp:79 +#, c-format +msgid "%s settings:" +msgstr "Configuración de %s:" + +#: modules/commands/cs_seen.cpp:255 +#, c-format +msgid "%s was last seen here %s ago." +msgstr "%s fue visto por última aquí hace %s." + +#: modules/commands/ns_ajoin.cpp:213 +#, c-format +msgid "%s was not found on %s's auto join list." +msgstr "%s no encontrado en la lista auto join de %s." + +#: modules/commands/ns_ajoin.cpp:221 +#, c-format +msgid "%s was removed from %s's auto join list." +msgstr "%s borrado de la lista de auto join de %s." + +#: modules/commands/ms_set.cpp:64 +#, c-format +msgid "%s will not send you any notification of memos." +msgstr "%s no te enviará ninguna notificación acerca de tus memos." + +#: modules/commands/ms_set.cpp:42 +#, c-format +msgid "%s will now notify you of memos when they are sent to you." +msgstr "%s ahora te notificará de tus memos cuando te sean enviados." + +#: modules/commands/ms_set.cpp:30 +#, c-format +msgid "" +"%s will now notify you of memos when you log on and when they are sent to " +"you." +msgstr "" +"%s ahora te notificará de tus memos cuando te conectes y cuando te sean " +"enviados." + +#: modules/commands/ms_set.cpp:36 +#, c-format +msgid "%s will now notify you of memos when you log on or unset /AWAY." +msgstr "" +"%s ahora te notificará de tus memos cuando te conectes o saques tu /AWAY." + +#: modules/commands/bs_bot.cpp:89 +#, c-format +msgid "%s!%s@%s (%s) added to the bot list." +msgstr "%s!%s@%s (%s) añadido a la lista de bots." + +#: modules/commands/ns_access.cpp:83 +#, c-format +msgid "%s's access list is empty." +msgstr "La lista de acceso de %s está vacía." + +#: modules/commands/ns_ajoin.cpp:96 +#, c-format +msgid "%s's auto join list is empty." +msgstr "La lista de auto join de %s está vacía." + +#: modules/commands/ns_ajoin.cpp:111 +#, c-format +msgid "%s's auto join list:" +msgstr "Lista de auto join de %s:" + +#: modules/commands/ns_cert.cpp:242 +#, c-format +msgid "%s's certificate list is empty." +msgstr "La lista de certificados de %s está vacía." + +#: modules/commands/ms_info.cpp:99 modules/commands/ms_info.cpp:106 +#, c-format +msgid "%s's memo limit is %d, and may not be changed." +msgstr "El límite de memos para %s es %d, y no puede ser cambiado." + +#: modules/commands/ms_info.cpp:101 modules/commands/ms_info.cpp:108 +#, c-format +msgid "%s's memo limit is %d." +msgstr "El límite de memos para %s es %d." + +#: src/misc.cpp:363 +#, c-format +msgid "(%s ago)" +msgstr "(hace %s)" + +#: src/misc.cpp:365 +#, c-format +msgid "(%s from now)" +msgstr "(%s desde ahora)" + +#: modules/commands/os_dns.cpp:244 +msgid "(Split)" +msgstr "(Split)" + +#: modules/commands/os_info.cpp:268 +#, c-format +msgid "(by %s on %s) %s" +msgstr "(por %s en %s) %s" + +#: modules/commands/cs_access.cpp:710 +msgid "(disabled)" +msgstr "(deshabilitado)" + +#: modules/commands/cs_access.cpp:712 +msgid "(founder only)" +msgstr "(solo fundador)" + +#: src/misc.cpp:367 +msgid "(now)" +msgstr "(ahora)" + +#: modules/commands/os_defcon.cpp:168 +msgid "* AKILL any new clients connecting" +msgstr "* AKILL a cualquier nuevo cliente que se conecte" + +#: modules/commands/os_defcon.cpp:158 +#, c-format +msgid "* Force channel modes (%s) to be set on all channels" +msgstr "* Fuerza los Modos de Canal (%s) en todos los canales" + +#: modules/commands/os_defcon.cpp:164 +msgid "* Ignore non-opers with a message" +msgstr "* Ignora a cualquier no-operador con un mensaje" + +#: modules/commands/os_defcon.cpp:162 +msgid "* Kill any new clients connecting" +msgstr "* Kill a cualquier nuevo cliente que se conecte" + +#: modules/commands/os_defcon.cpp:156 +msgid "* No mode lock changes" +msgstr "* No hay cambios en los modos bloqueados" + +#: modules/commands/os_defcon.cpp:152 +msgid "* No new channel registrations" +msgstr "* No hay nuevos registros de canales" + +#: modules/commands/os_defcon.cpp:170 +msgid "* No new memos sent" +msgstr "* No hay nuevos memos enviados" + +#: modules/commands/os_defcon.cpp:154 +msgid "* No new nick registrations" +msgstr "* No hay nuevos registros de nicks" + +#: modules/commands/os_defcon.cpp:166 +msgid "* Silently ignore non-opers" +msgstr "* Ignora silenciosamente a los no-operadores" + +#: modules/commands/os_defcon.cpp:160 +#, c-format +msgid "* Use the reduced session limit of %d" +msgstr "* Usa el límite de sesion reducido de %d" + +#: modules/commands/cs_seen.cpp:319 +#, c-format +msgid ", but %s mysteriously dematerialized." +msgstr ", pero %s se desmaterializó misteriosamente." + +#: modules/commands/cs_seen.cpp:317 +#, c-format +msgid ". %s is still online." +msgstr ". %s todavía está en línea." + +#: include/language.h:87 +msgid "" +msgstr "" + +#: modules/commands/ns_set.cpp:504 +#, c-format +msgid "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." +msgstr "" +"Se ha enviado un e-mail de confirmación a %s. Sigue las instrucciones en él " +"para cambiar tu dirección de e-mail." + +#: modules/commands/ms_sendall.cpp:45 +msgid "A massmemo has been sent to all registered users." +msgstr "Un massmemo ha sido enviado a todos los usuarios registrados." + +#: modules/commands/hs_request.cpp:285 +msgid "" +"A memo informing the user will also be sent, which includes the reason for " +"the rejection if supplied." +msgstr "" +"También se enviará un memo informando al usuario, que incluirá la razón si " +"se proporciona." + +#: modules/commands/hs_request.cpp:229 +msgid "A memo informing the user will also be sent." +msgstr "También se enviará un memo informando al usuario." + +#: modules/commands/ms_read.cpp:42 +#, c-format +msgid "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." +msgstr "" +"Se ha enviado una notificación a %s informando de que has leído su memo." + +#: include/language.h:123 +msgid "A vHost ident must be in the format of a valid ident." +msgstr "El ident de un vHost debe estar en un formato de ident válido" + +#: include/language.h:122 +msgid "A vHost must be in the format of a valid hostname." +msgstr "Un vhost debe estar en el formato de un host válido." + +#: modules/commands/os_ignore.cpp:342 +msgid "ADD expiry {nick|mask} [reason]" +msgstr "ADD expiración {nick|máscara} [razón]" + +#: modules/commands/os_oper.cpp:70 +msgid "ADD oper type" +msgstr "ADD operador tipo" + +#: modules/commands/os_info.cpp:102 +msgid "ADD target info" +msgstr "ADD objetivo info" + +#: modules/commands/os_news.cpp:278 +msgid "ADD text" +msgstr "ADD texto" + +#: modules/commands/os_session.cpp:523 +msgid "ADD [+expiry] mask limit reason" +msgstr "ADD [+expiración] máscara límite razón" + +#: modules/commands/ns_ajoin.cpp:231 +msgid "ADD [nickname] channel [key]" +msgstr "ADD [nick] canal [clave]" + +#: modules/commands/ns_access.cpp:102 +msgid "ADD [nickname] mask" +msgstr "ADD [nick] máscara" + +#: modules/commands/ns_cert.cpp:258 +#, fuzzy +msgid "ADD [nickname] [fingerprint]" +msgstr "ADD [nick] huella" + +#: modules/commands/os_sxline.cpp:659 modules/commands/os_akill.cpp:386 +msgid "ADD [+expiry] mask reason" +msgstr "ADD [+expiración] máscara razón" + +#: modules/commands/os_sxline.cpp:425 +msgid "ADD [+expiry] mask:reason" +msgstr "ADD [+expiración] máscara:razón" + +#: modules/commands/os_forbid.cpp:157 +msgid "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" +msgstr "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiración] entrada razón" + +#: modules/commands/os_dns.cpp:665 +msgid "ADDIP server.name ip" +msgstr "ADDIP nombre-de-servidor ip" + +#: modules/commands/os_dns.cpp:663 +msgid "ADDSERVER server.name [zone.name]" +msgstr "ADDSERVER nombre-de-servidor [nombre-de-zona]" + +#: modules/commands/os_dns.cpp:661 +msgid "ADDZONE zone.name" +msgstr "ADDZONE nombre-de-zona" + +#: modules/commands/cs_akick.cpp:38 +#, c-format +msgid "AKICK ENFORCE for %s complete; %d users were affected." +msgstr "AKICK ENFORCE en %s completo; %d usuarios afectados." + +#: modules/commands/os_chankill.cpp:21 +msgid "AKILL all users on a specific channel" +msgstr "AKILL todos los usuarios de un canal específico" + +#: modules/commands/os_akill.cpp:222 modules/commands/os_akill.cpp:339 +#: modules/commands/os_akill.cpp:353 +msgid "AKILL list is empty." +msgstr "La lista de AKILLS está vacía." + +#: modules/commands/bs_kick.cpp:1211 modules/commands/bs_kick.cpp:1213 +#: modules/commands/bs_kick.cpp:1216 +msgid "AMSG kicker" +msgstr "Kick por AMSG" + +#: modules/commands/ns_alist.cpp:48 +msgid "Access" +msgstr "Acceso" + +#: include/language.h:72 +msgid "Access denied." +msgstr "Acceso denegado." + +#: modules/commands/cs_status.cpp:58 +#, c-format +msgid "Access for %s on %s:" +msgstr "Acceso para %s en %s:" + +#: include/language.h:107 +#, c-format +msgid "Access level must be between %d and %d inclusive." +msgstr "El nivel de acceso debe estar entre %d y %d inclusive." + +#: modules/commands/cs_access.cpp:108 +msgid "Access level must be non-zero." +msgstr "El nivel de acceso no puede ser cero." + +#: modules/commands/cs_access.cpp:694 +#, c-format +msgid "Access level settings for channel %s:" +msgstr "Opciones del nivel de acceso para el canal %s:" + +#: modules/commands/cs_access.cpp:734 +#, c-format +msgid "Access levels for %s reset to defaults." +msgstr "Niveles de acceso para %s resetados a los valores originales." + +#: modules/commands/cs_access.cpp:439 modules/commands/ns_access.cpp:87 +#, c-format +msgid "Access list for %s:" +msgstr "Lista de acceso para %s:" + +#: modules/commands/help.cpp:166 +#, c-format +msgid "" +"Access to this command requires the permission %s to be present in your " +"opertype." +msgstr "" +"El acceso a este comando requiere que el permiso %s esté presente en tu tipo " +"de oper." + +#: modules/commands/ns_cert.cpp:368 modules/commands/ns_cert.cpp:392 +#: modules/commands/ns_identify.cpp:94 +#, c-format +msgid "" +"Account %s has already reached the maximum number of simultaneous logins " +"(%u)." +msgstr "" + +#: modules/commands/cs_set.cpp:683 +msgid "Activate security features" +msgstr "Activar características de seguridad" + +#: modules/commands/hs_request.cpp:227 +msgid "Activate the requested vHost for the given nick." +msgstr "Activar el vHost solicitado para el nick dado." + +#: modules/commands/hs_on.cpp:55 +msgid "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." +msgstr "" +"Activa el vhost actualmente asignado al nick en uso.\n" +"Cuando uses este comando cualquier usuario que te haga\n" +"un /whois verá el vhost en vez de tu host/IP real." + +#: modules/commands/hs_on.cpp:19 +msgid "Activates your assigned vhost" +msgstr "Activa tu vhost asignado." + +#: modules/commands/os_info.cpp:243 +msgid "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." +msgstr "" +"Añade o borra información de oper para el nick o canal dados.\n" +"Esto se mostrará a los opers con el respectivo comando para el\n" +"nick o canal." + +#: modules/commands/os_dns.cpp:515 +#, c-format +msgid "Added IP %s to %s." +msgstr "Añadida IP %s a %s." + +#: modules/commands/os_forbid.cpp:239 +#, c-format +msgid "Added a forbid on %s of type %s to expire on %s." +msgstr "Añadida una prohibición en %s del tipo %s que expirará en %s" + +#: modules/commands/os_info.cpp:164 +#, c-format +msgid "Added info to %s." +msgstr "Añadida información a %s." + +#: modules/commands/os_news.cpp:34 +msgid "Added new logon news item." +msgstr "Nueva noticia de entrada añadida." + +#: modules/commands/os_news.cpp:44 +msgid "Added new oper news item." +msgstr "Nueva noticia de oper añadida." + +#: modules/commands/os_news.cpp:54 +msgid "Added new random news item." +msgstr "Nueva noticia al azar anadida." + +#: modules/commands/os_dns.cpp:395 +#, c-format +msgid "Added server %s." +msgstr "Añadido servidor %s." + +#: modules/commands/os_dns.cpp:300 +#, c-format +msgid "Added zone %s." +msgstr "Añadida zona %s." + +#: modules/commands/cs_entrymsg.cpp:257 +msgid "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." +msgstr "" + +#: modules/commands/ns_register.cpp:104 +msgid "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." +msgstr "" +"Adicionalmente, los Operadores de Servicios con el permiso nickserv/confirm " +"pueden\n" +"remplazar código con el nick del usuario para forzar su validación." + +#: modules/pseudoclients/botserv.cpp:172 +#, c-format +msgid "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" +msgstr "" +"Adicionalmente, si el modo fantasía está activado, los\n" +"comandos fantasía pueden usarse precediendo el nombre\n" +"del comando con uno de los caracteres siguientes: %s" + +#: modules/commands/os_noop.cpp:58 +#, c-format +msgid "All O:lines of %s have been reset." +msgstr "Todas las O:lines de %s han sido reseteadas." + +#: modules/commands/cs_clone.cpp:71 +#, c-format +msgid "All akick entries from %s have been cloned to %s." +msgstr "Todas las entradas akick de %s han sido clonadas a %s." + +#: modules/commands/help.cpp:57 +#, c-format +msgid "All available commands for %s:" +msgstr "Comandos disponibles para %s:" + +#: modules/commands/cs_clone.cpp:96 +#, c-format +msgid "All badword entries from %s have been cloned to %s." +msgstr "Todas las bad words de %s han sido clonadas a %s." + +#: modules/commands/cs_clone.cpp:108 +#, fuzzy, c-format +msgid "All level entries from %s have been cloned into %s." +msgstr "Todas las entradas akick de %s han sido clonadas a %s." + +#: modules/commands/os_news.cpp:38 +msgid "All logon news items deleted." +msgstr "Todas las noticias de entrada borradas." + +#: modules/commands/ms_del.cpp:115 +#, c-format +msgid "All memos for channel %s have been deleted." +msgstr "Todos los memos para el canal %s han sido borrados." + +#: modules/commands/os_mode.cpp:61 +#, c-format +msgid "All modes cleared on %s." +msgstr "Se han limpiado todos los modos en %s." + +#: modules/commands/ns_register.cpp:258 modules/commands/ns_register.cpp:389 +msgid "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." +msgstr "" +"Todas las cuentas nuevas deben ser validadas por un administrador. Por " +"favor, espera hasta que tu registro sea confirmado." + +#: modules/commands/ms_del.cpp:119 +msgid "All of your memos have been deleted." +msgstr "Todos tus memos han sido borrados." + +#: modules/commands/os_news.cpp:48 +msgid "All oper news items deleted." +msgstr "Todas las noticias de oper borradas." + +#: modules/commands/os_noop.cpp:41 +#, c-format +msgid "All operators from %s have been removed." +msgstr "Todos los operadores de %s han sido borrados." + +#: modules/commands/os_news.cpp:58 +msgid "All random news items deleted." +msgstr "Todas las noticias al azar borradas." + +#: modules/commands/cs_clone.cpp:211 +#, c-format +msgid "All settings from %s have been cloned to %s." +msgstr "Todas la configuración de %s ha sido clonada a %s." + +#: modules/commands/cs_sync.cpp:41 +#, c-format +msgid "All user modes on %s have been synced." +msgstr "Todas los modos de usuario en %s han sido sincronizados." + +#: modules/commands/hs_group.cpp:60 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s." +msgstr "Todos los vhosts en el grupo %s han sido establecidos a %s" + +#: modules/commands/hs_group.cpp:58 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s@%s." +msgstr "Todos los vhosts en el grupo %s han sido establecidos a %s@%s." + +#: src/access.cpp:40 +msgid "Allowed to (de)halfop him/herself" +msgstr "Puede darse/quitarse halfop a sí mismo" + +#: src/access.cpp:39 +msgid "Allowed to (de)halfop users" +msgstr "Puede dar/quitar halfop a los usuarios" + +#: src/access.cpp:48 +msgid "Allowed to (de)op him/herself" +msgstr "Puede darse/quitarse op a sí mismo" + +#: src/access.cpp:47 +msgid "Allowed to (de)op users" +msgstr "Puede dar/quitar op a los usuarios" + +#: src/access.cpp:50 +msgid "Allowed to (de)owner him/herself" +msgstr "Puede darse/quitarse status de fundador a sí mismo" + +#: src/access.cpp:49 +msgid "Allowed to (de)owner users" +msgstr "Puede dar/quitar status de fundador a los usuarios" + +#: src/access.cpp:52 +msgid "Allowed to (de)protect him/herself" +msgstr "Puede (des)protegerse a sí mismo" + +#: src/access.cpp:51 +msgid "Allowed to (de)protect users" +msgstr "Puede (des)proteger a los usuarios" + +#: src/access.cpp:59 +msgid "Allowed to (de)voice him/herself" +msgstr "Puede darse/quitarse voz a sí mismo" + +#: src/access.cpp:58 +msgid "Allowed to (de)voice users" +msgstr "Puede dar/quitar voz a los usuarios" + +#: src/access.cpp:27 +msgid "Allowed to assign/unassign a bot" +msgstr "Puede asignar o quitar un bot" + +#: src/access.cpp:34 +msgid "Allowed to ban users" +msgstr "Puede banear usuarios" + +#: src/access.cpp:56 +msgid "Allowed to change channel topics" +msgstr "Puede cambiar el topic del canal" + +#: src/access.cpp:41 +msgid "Allowed to get full INFO output" +msgstr "Puede ver la salida completa del comando INFO" + +#: src/access.cpp:36 +msgid "Allowed to issue commands restricted to channel founders" +msgstr "Puede usar comandos reservados a fundadores del canal" + +#: src/access.cpp:33 +msgid "Allowed to modify channel badwords list" +msgstr "Puede modificar la lista de badwords del canal" + +#: src/access.cpp:24 +msgid "Allowed to modify the access list" +msgstr "Puede modificar la lista de acceso" + +#: src/access.cpp:44 +msgid "Allowed to read channel memos" +msgstr "Puede leer los memos del canal" + +#: src/access.cpp:54 +msgid "Allowed to set channel settings" +msgstr "Puede cambiar la configuración del canal" + +#: src/access.cpp:57 +msgid "Allowed to unban users" +msgstr "Puede desbanear usuarios" + +#: src/access.cpp:37 +msgid "Allowed to use GETKEY command" +msgstr "Puede usar el comando GETKEY" + +#: src/access.cpp:53 +msgid "Allowed to use SAY and ACT commands" +msgstr "Puede usar los comandos SAY y ACT" + +#: src/access.cpp:35 +msgid "Allowed to use fantasy commands" +msgstr "Puede usar los comandos fantasía" + +#: src/access.cpp:26 +msgid "Allowed to use the AKICK command" +msgstr "Puede usar el comando AKICK" + +#: src/access.cpp:42 +msgid "Allowed to use the INVITE command" +msgstr "Puede usar el comando INVITE" + +#: src/access.cpp:43 +msgid "Allowed to use the KICK command" +msgstr "Puede usar el comando KICK" + +#: src/access.cpp:45 +msgid "Allowed to use the MODE command" +msgstr "Puede usar el comando MODE" + +#: src/access.cpp:25 +msgid "Allowed to view the access list" +msgstr "Puede ver la lista de acceso" + +#: modules/commands/gl_global.cpp:42 +#, c-format +msgid "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." +msgstr "" +"Permite a los Administrators a enviar mensajes a todos los\n" +"usuarios de la red. El mensaje será enviado desde el nick %s." + +#: modules/commands/os_mode.cpp:133 +msgid "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." +msgstr "" +"Permite a los Operadores de Servicios cambiar los modos para\n" +"cualquier canal. Los parámetros son los mismos que para el\n" +"comando estándar /MODE. También se puede especificar\n" +"CLEAR para borrar todos los modos del canal. Si se especifica\n" +"CLEAR ALL se limpian también los status de usuarios." + +#: modules/commands/os_mode.cpp:173 +msgid "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." +msgstr "" +"Permite a los Operadores de Servicios cambiar los modos para\n" +"cualquier usuario. Los parámetros son los mismos que para el\n" +"comando estándar /MODE." + +#: modules/commands/bs_bot.cpp:352 +#, fuzzy +msgid "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." +msgstr "" +"Permite a los Operadores de Servicios crear, modificar\n" +"y borrar bots que usuarios podran usar en sus propios\n" +"canales.\n" +" \n" +"BOT ADD añade un bot con el nick, usuario, host\n" +"y nombre real dados. Ten mucho cuidado, ya que no se hacen\n" +"comprobaciones de la integridad de estas configuraciones.\n" +"BOT CHANGE permite cambiar el nick, usuario, host\n" +"o nombre real de un bot sin tener que borrar el bot (ni la\n" +"información asociada a él).\n" +"BOT DEL elimina el bot dado de la lista de bots.\n" +" \n" +"Aviso: no puedes crear un bot que tenga un nick que ya\n" +"esté registrado. Si un usuario no registrado esta usando\n" +"el nick, será expulsado de la red." + +#: modules/commands/os_oline.cpp:56 +msgid "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." +msgstr "" +"Permite a los Operadores de Servicios dar marcas de IRCOp a\n" +"cualquier usuario. Los marcas tienen que estar precedidos con\n" +"un \"+\" o un \"-\". Para eliminar todas las marca, escribe\n" +"un \"-\" en vez de cualquier marca." + +#: modules/commands/os_ignore.cpp:370 +msgid "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." +msgstr "" +"Permite a los Operadores de Servicios hacer que éstos ignoren un\n" +"nick o una máscara durante cierto tiempo o hasta el próximo reinicio.\n" +"El formato de tiempo predeterminado es en segundos, pero puedes\n" +"especificar unidades\n" +"Las unidades válidas son: s para segundos, m para minutos,\n" +"h para horas y d para días.\n" +"Las combinaciones de esas unidades no están permitidas.\n" +"Para hacer que el ignore sea permanente, establece 0 como tiempo.\n" +"Cuando añades una máscara, debe estar en formato nick!usuario@host,\n" +"todo lo demás será considerado un nick. Se permiten comodines.\n" +" \n" +"Los ignores no funcionarán con IRCOps." + +#: modules/commands/os_akill.cpp:420 +msgid "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Permite a los Operadores de Servicios manipular la lista de\n" +"AKILLS. Si un usuario coincindente con una mascara en la\n" +"lista de AKILLS se intenta conectar, los Servicios enviarán\n" +"un KILL a ese usuario y, en los tipos de servidores soportados,\n" +"ordenará a todos los servidores añadir un ban a la máscara\n" +"de dicho usuario.\n" +" \n" +"AKILL ADD añade la mascara dada a la lista AKILL con la\n" +"razón dada, la cual es obligatoria .\n" +"La máscara debe estar en formato nick!usuario@host#nombre real,\n" +"siendo obligatorios el usuario y el host. Si se especifica un nombre\n" +"real, la razón debe ir precedida de :.\n" +"expiración debe ser un número entero seguido de d (días), h\n" +"(horas), o m (minutos). Las combinaciones (como 1h30m) no se\n" +"permiten. Si no se especifican las unidades, lo predeterminado es días\n" +"(así que +30 por sí mismo significa 30 días). Para añadir un AKILL que\n" +"no expire, usa +0. Si la máscara a ser añadida comienza por un +, se\n" +"debe especificar la expiración, incluso si es igual a la predeterminada.\n" +"La expiración predeterminada para un AKILL se puede ver con el comando\n" +"STATS AKILL." + +#: modules/commands/os_sxline.cpp:436 +msgid "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." +msgstr "" +"Permite a los Operadores de Servicios manipular la lista SNLINE.\n" +"Si un usuario con nombre real coincidente con una SNLINE intenta\n" +"conectar, los Servicios no lo permitirán." + +#: modules/commands/os_sxline.cpp:670 +#, fuzzy +msgid "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." +msgstr "" +"Permite a los Operadores de Servicios manipular la lista SQLINE.\n" +"Si un usuario con nick coincidente con una máscara SQLINE intenta\n" +"conectar, los Servicios no lo permitirán.\n" +"Si el primer caracter de la máscara es #, los servicios evitarán el uso\n" +"de los canales coincidentes." + +#: modules/commands/os_session.cpp:551 +msgid "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." +msgstr "" +"Permite a los Operadores de Servicios manipular la lista de host\n" +"que tienen un límite de sesión específico - permitiendo a ciertas\n" +"máquinas conectar más clientes al mismo tiempo que el número\n" +"predeterminado. Una vez que un host alcanza su límite, todos los\n" +"clientes que intentan conectar desde el mismo host serán expulsados\n" +"Antes de que el usuario sea expulsado, se le notifica el motivo de la\n" +"expulsión. El contenido de dicha notificación está en el archivo de\n" +"configuración." + +#: modules/commands/os_session.cpp:270 +msgid "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." +msgstr "" +"Permite a los Operadores de Servicios ver la lista de sesiones.\n" +" \n" +"SESSION LIST lista hosts con al menos umbral sesiones.\n" +"El umbral debe ser un número mayor a 1. Esto es para evitar\n" +"listados enormes de host con una sola sesión accidentalmente.\n" +" \n" +"SESSION VIEW muestra información detallada acerca de un host \n" +"específico - incluyendo el número de sesiones actuales y el límite\n" +"de sesion.\n" +"El valor host no puede incluir comodines.\n" +" \n" +"Mira la ayuda sobre EXCEPTION para más informacion acerca de\n" +"limites de sesion y como establecerlos para ciertos hosts y grupos." + +#: modules/commands/cs_topic.cpp:193 +#, fuzzy +msgid "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do " +"not have\n" +"the TOPIC privilege." +msgstr "" +"Permite manipular el topic del canal especificado.\n" +"El comando SET cambia el topic del canal al topic dado o borra el topic\n" +"si no se especifica uno. El comando APPEND anexa el topic dado al topic\n" +"existente.\n" +" \n" +"LOCK y UNLOCK se pueden usar para activar o desactivar el bloque de\n" +"topic. Cuando el bloque está activo, el topic no se puede cambiar excepto " +"con\n" +"este comando." + +#: modules/commands/os_kick.cpp:62 +#, c-format +msgid "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" +msgstr "" +"Permite a los IRCops kickear un usuario de cualquier canal.\n" +"Los parámetros son los mismos que para el comando /KICK\n" +"estándar. El mensaje del kick irá precedido por el nick del IRCop\n" +"que usó el comando KICK; por ejemplo:\n" +" \n" +"*** SpamMan ha sido kickeado del canal #mi_canal por %s (Alcan (Flood))" + +#: modules/commands/cs_set.cpp:33 +msgid "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" +msgstr "" +"Permite al fundador del canal configurar varias opciones\n" +"del canal y otra informacion.\n" +" \n" +"Opciones disponibles:" + +#: modules/commands/os_oper.cpp:250 +msgid "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." +msgstr "" +"Te permite cambiar y ver los Operadores de Servicios.\n" +"Ten en cuenta que los operadores eliminados con este comando,\n" +"pero que permanezcan en el archivo de configuración, no estarán\n" +"afectados permanentemente por esto." + +#: modules/commands/os_config.cpp:127 +msgid "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" +msgstr "" +"Te permite cambiar y ver opciones de configuración.\n" +"La configuración cambiada con este comando es temporal y no se verá\n" +"reflejada en el archivo de configuración, por lo que se perderán si Anope\n" +"se apaga, se reinicia, o se usa el comando RELOAD.\n" +" \n" +"Ejemplo:\n" +" MODIFY nickserv forcemail no" + +#: modules/commands/ns_set.cpp:992 +msgid "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." +msgstr "" +"Te permite escoger la forma en que los Servicios se comunican con\n" +"el usuario dado. Con MSG establecido, los Servicios usarán mensajes,\n" +"si no, usarán notices." + +#: modules/commands/ns_set.cpp:966 +#, c-format +msgid "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." +msgstr "" +"Te permite escoger la forma en que los Servicios se comunican\n" +"contigo. Con %s establecido, los Servicios usarán mensajes,\n" +"si no, usarán notices." + +#: modules/commands/ms_ignore.cpp:113 +msgid "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." +msgstr "" +"Te permite ignorar usuarios por nick o host para evitar que te\n" +"envíen memos a ti o a un canal. Si alguien en la lista de ignorados\n" +"intenta enviarte un memo a ti o a un canal, no se enterará de que\n" +"lo has ignorado." + +#: modules/commands/os_kill.cpp:48 +msgid "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." +msgstr "" +"Te permite expulsar a un usuario de la red.\n" +"Los parámetros son los mismos que para el comando\n" +"/KILL estándar." + +#: modules/commands/ns_info.cpp:252 +#, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Te permite evitar que se muestren ciertas partes de información\n" +"cuando alguien hace un %s INFO al nick dado. Puedes ocultar la\n" +"dirección email (EMAIL), la última máscara usuario@host usada\n" +"(USERMASK), el status de acceso a los servicios (STATUS) y el\n" +"último mensaje de salida (QUIT).\n" +"El segundo parámetro especifica si la información será mostrada\n" +"(OFF) u ocultada (ON)." + +#: modules/commands/ns_info.cpp:223 +#, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Te permite evitar que se muestren ciertas partes de información\n" +"cuando alguien hace un %s INFO a tu nick. Puedes ocultar tu\n" +"dirección email (EMAIL), la última máscara usuario@host usada\n" +"(USERMASK), tu status de acceso a los servicios (STATUS) y tu\n" +"último mensaje de salida (QUIT).\n" +"El segundo parámetro especifica si la información será mostrada\n" +"(OFF) u ocultada (ON)." + +#: modules/commands/bs_info.cpp:118 +#, c-format +msgid "Allows you to see %s information about a channel or a bot" +msgstr "Te permite ver la información de %s para un canal o bot" + +#: modules/commands/bs_info.cpp:108 +#, c-format +msgid "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." +msgstr "" +"Te permite ver la información de %s sobre un canal o un\n" +"bot. Si el parámetro es un canal, recibirás información\n" +"tal como kicks activados. Si el parametro es un nick,\n" +"recibirás información acerca de un bot, tal como la fecha\n" +"de creación o el número de canales en los que está." + +#: modules/commands/cs_xop.cpp:567 +msgid "" +"Alternative methods of modifying channel access lists are\n" +"available. " +msgstr "" +"Están disponibles métodos alternativos de modificar las listas\n" +"de acceso." + +#: modules/commands/hs_request.cpp:191 +msgid "Approve the requested vHost of a user" +msgstr "Aprueba el vHost solicitado por un usuario" + +#: modules/commands/ns_drop.cpp:68 +msgid "As a Services Operator, you may drop any nick." +msgstr "Como Operador de Servicios, puedes borrar cualquier nick." + +#: modules/commands/bs_assign.cpp:19 +msgid "Assigns a bot to a channel" +msgstr "Asigna un bot a un canal" + +#: modules/commands/bs_assign.cpp:78 +#, fuzzy +msgid "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." +msgstr "" +"Assigna un bot denominado por el nick dado al canal dado.\n" +"Luego puedes configurar el bot para acomodarlo a tus\n" +"necesidades." + +#: data/chanserv.example.conf:1197 +msgid "Associate a URL with the channel" +msgstr "Asociar una URL con el canal" + +#: data/nickserv.example.conf:594 +msgid "Associate a URL with this account" +msgstr "Asociar una URL con esta cuenta" + +#: data/nickserv.example.conf:593 +msgid "Associate a URL with your account" +msgstr "Asociar una URL con tu cuenta" + +#: modules/commands/greet.cpp:83 +msgid "Associate a greet message with your nickname" +msgstr "Asociar un saludo con tu nick" + +#: data/chanserv.example.conf:1198 +msgid "Associate an E-mail address with the channel" +msgstr "Asociar un e-mail con el canal" + +#: modules/commands/ns_set.cpp:452 +msgid "Associate an E-mail address with your nickname" +msgstr "Asociar un e-mail con tu nick" + +#: modules/commands/os_info.cpp:101 +msgid "Associate oper info with a nick or channel" +msgstr "Asociar información de operador con un nick o con un canal" + +#: modules/commands/ns_set.cpp:558 +msgid "Associates the given E-mail address with the nickname." +msgstr "Asocia el e-mail dado con el nick." + +#: modules/commands/ns_set.cpp:533 +msgid "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." +msgstr "" +"Asocia el e-mail dado con tu nick. La direccion será\n" +"mostrada cuando alguien pida información sobre el\n" +"nick con el comando INFO." + +#: modules/commands/ns_set.cpp:1315 +msgid "Auto-op" +msgstr "Auto-op" + +#: modules/commands/cs_akick.cpp:374 +#, c-format +msgid "Autokick list for %s:" +msgstr "Lista de kicks automáticos para el canal %s:" + +#: src/access.cpp:29 +msgid "Automatic channel operator status upon join" +msgstr "Status de operador del canal automáticamente al entrar" + +#: src/access.cpp:28 +msgid "Automatic halfop upon join" +msgstr "Status de halfop automáticamente al entrar" + +#: src/access.cpp:30 +msgid "Automatic owner upon join" +msgstr "Status de fundador del canal automáticamente al entrar" + +#: src/access.cpp:31 +msgid "Automatic protect upon join" +msgstr "Protección automáticamente al entrar" + +#: src/access.cpp:32 +msgid "Automatic voice on join" +msgstr "Voz automáticamente al entrar" + +#: modules/commands/os_oper.cpp:196 +#, c-format +msgid "Available commands for %s:" +msgstr "Comandos disponibles para %s:" + +#: modules/commands/os_oper.cpp:175 +#, fuzzy +msgid "Available opertypes:" +msgstr "" +" \n" +"Los comandos disponibles son:" + +#: modules/commands/os_oper.cpp:218 +#, c-format +msgid "Available privileges for %s:" +msgstr "Privilegios disponibles para %s:" + +#: modules/commands/cs_enforce.cpp:162 +msgid "BANS enforced by " +msgstr "BANS forzado por " + +#: modules/commands/bs_kick.cpp:1121 modules/commands/bs_kick.cpp:1123 +#: modules/commands/bs_kick.cpp:1126 +msgid "Bad words kicker" +msgstr "Kick por Bad words" + +#: modules/commands/bs_badwords.cpp:252 +#, c-format +msgid "Bad words list for %s:" +msgstr "Lista de bad words para %s:" + +#: modules/commands/bs_badwords.cpp:364 +msgid "Bad words list is now empty." +msgstr "La lista de bad words esta ahora vacía." + +#: modules/commands/bs_set.cpp:129 +msgid "Ban expiry may not be longer than 1 day." +msgstr "La expiración del ban no puede ser superior a 1 día." + +#: modules/commands/cs_ban.cpp:140 modules/commands/cs_ban.cpp:175 +#, c-format +msgid "Ban on %s expires in %s." +msgstr "El ban en %s expira en %s." + +#: modules/commands/cs_info.cpp:60 +msgid "Ban type" +msgstr "Tipo de ban" + +#: modules/commands/cs_set.cpp:174 +#, c-format +msgid "Ban type for channel %s is now #%d." +msgstr "El tipo de ban para el canal %s es ahora #%d." + +#: modules/commands/cs_ban.cpp:39 +msgid "Bans a given nick or mask on a channel" +msgstr "Banea el nick o máscara dados en un canal" + +#: modules/commands/cs_ban.cpp:227 +msgid "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." +msgstr "" +"Banea el nick o máscara dados en un canal. Se puede proporcionar\n" +"de forma opcional una expiración que quitará el ban después del\n" +"tiempo dado.\n" +" \n" +"Por defecto, limitado a AOPs o aquellos con nivel 5 o superior en\n" +"el canal. Los fundadores pueden banear máscaras." + +#: modules/commands/cs_enforce.cpp:166 +#, c-format +msgid "Bans enforced on %s." +msgstr "Bans forzados en %s." + +#: modules/commands/bs_kick.cpp:1131 modules/commands/bs_kick.cpp:1133 +#: modules/commands/bs_kick.cpp:1136 +msgid "Bolds kicker" +msgstr "Kick por negritas" + +#: modules/commands/bs_bot.cpp:26 modules/commands/bs_bot.cpp:175 +#, c-format +msgid "Bot %s already exists." +msgstr "El bot %s ya existe." + +#: include/language.h:119 +#, c-format +msgid "Bot %s does not exist." +msgstr "El bot %s no existe." + +#: modules/commands/bs_assign.cpp:71 modules/commands/bs_assign.cpp:246 +#, c-format +msgid "Bot %s has been assigned to %s." +msgstr "El bot %s ha sido asignado al canal %s." + +#: modules/commands/bs_bot.cpp:228 +#, c-format +msgid "Bot %s has been changed to %s!%s@%s (%s)." +msgstr "El bot %s ha sido cambiado a %s!%s@%s (%s)." + +#: modules/commands/bs_bot.cpp:262 +#, c-format +msgid "Bot %s has been deleted." +msgstr "El bot %s ha sido borrado." + +#: modules/commands/bs_assign.cpp:63 modules/commands/bs_assign.cpp:241 +#, c-format +msgid "Bot %s is already assigned to channel %s." +msgstr "El bot %s ya está asignado al canal %s." + +#: modules/commands/bs_kick.cpp:832 +#, c-format +msgid "Bot will kick ops on channel %s." +msgstr "El bot kickeará ops en el canal %s." + +#: modules/commands/bs_kick.cpp:897 +#, c-format +msgid "Bot will kick voices on channel %s." +msgstr "El bot kickeará voices en el canal %s." + +#: modules/commands/bs_kick.cpp:824 +#, c-format +msgid "Bot won't kick ops on channel %s." +msgstr "El bot no kickeará ops en el canal %s." + +#: modules/commands/bs_kick.cpp:889 +#, c-format +msgid "Bot won't kick voices on channel %s." +msgstr "El bot no kickeará voices en el canal %s." + +#: modules/commands/bs_bot.cpp:118 +#, c-format +msgid "Bot %s is not changeable." +msgstr "El bot %s no se puede cambiar." + +#: modules/commands/bs_bot.cpp:254 +#, c-format +msgid "Bot %s is not deletable." +msgstr "El bot %s no se puede borrar." + +#: modules/commands/bs_set.cpp:141 +#, c-format +msgid "Bot bans will automatically expire after %s." +msgstr "Los bans del bot expirarán automáticamente después de %s." + +#: modules/commands/bs_set.cpp:139 +msgid "Bot bans will no longer automatically expire." +msgstr "Los bans del bot ya no expirarán automáticamente." + +#: modules/commands/bs_bot.cpp:46 modules/commands/bs_bot.cpp:138 +#, c-format +msgid "Bot hosts may only be %d characters long." +msgstr "Los hosts de bots solo pueden tener %d caracteres." + +#: modules/commands/bs_bot.cpp:64 modules/commands/bs_bot.cpp:167 +msgid "Bot hosts may only contain valid host characters." +msgstr "Los hosts de bots solo pueden contener caracteres de hosts válidos." + +#: modules/commands/bs_bot.cpp:40 modules/commands/bs_bot.cpp:132 +#, c-format +msgid "Bot idents may only be %d characters long." +msgstr "Los idents de bots solo pueden tener %d caracteres." + +#: modules/commands/bs_bot.cpp:58 modules/commands/bs_bot.cpp:161 +msgid "Bot idents may only contain valid ident characters." +msgstr "Los idents de bots solo pueden contener caracteres de ident válidos." + +#: include/language.h:121 +#, c-format +msgid "Bot is not on channel %s." +msgstr "El bot no está en el canal %s." + +#: modules/commands/bs_botlist.cpp:51 +msgid "Bot list:" +msgstr "Lista de bots:" + +#: modules/commands/bs_info.cpp:87 +msgid "Bot nick" +msgstr "Nick del bot" + +#: modules/commands/bs_bot.cpp:34 modules/commands/bs_bot.cpp:126 +#, c-format +msgid "Bot nicks may only be %d characters long." +msgstr "Los nicks de bots solo pueden tener %d caracteres." + +#: modules/commands/bs_bot.cpp:52 modules/commands/bs_bot.cpp:155 +msgid "Bot nicks may only contain valid nick characters." +msgstr "Los nicks de bots solo pueden contener caracteres de nicks válidos." + +#: modules/commands/bs_kick.cpp:225 +#, c-format +msgid "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." +msgstr "" +"El bot ahora kickeará por %s, y baneará después\n" +"de %d kicks al mismo usuario." + +#: modules/commands/bs_kick.cpp:228 +#, c-format +msgid "Bot will now kick for %s." +msgstr "El bot ahora kickeará por %s." + +#: modules/commands/bs_kick.cpp:416 +#, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." +msgstr "" +"El bot ahora kickeará por mayúsculas (deben ser al menos\n" +"%d caracteres y %d%% del mensaje entero) y baneará\n" +"después de %d kicks al mismo usuario." + +#: modules/commands/bs_kick.cpp:420 +#, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." +msgstr "" +"El bot ahora kickeará por mayúsculas (deben ser al menos\n" +"%d caracteres y %d%% del mensaje entero)." + +#: modules/commands/bs_kick.cpp:551 +#, c-format +msgid "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." +msgstr "" +"El bot ahora kickeará por flood (%d líneas en %d segundos)\n" +"y baneará después de %d kicks al mismo usuario." + +#: modules/commands/bs_kick.cpp:554 +#, c-format +msgid "Bot will now kick for flood (%d lines in %d seconds)." +msgstr "El bot ahora kickeará por flood (%d líneas en %d segundos)." + +#: modules/commands/bs_kick.cpp:677 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"El bot ahora kickeará por repetir (usuarios que\n" +"repitan %d veces lo mismo), y baneará después de\n" +"%d kicks al mismo usuario." + +#: modules/commands/bs_kick.cpp:687 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." +msgstr "" +"El bot ahora kickeará por repetir (usuarios que\n" +"repitan %d veces lo mismo)." + +#: modules/commands/bs_kick.cpp:673 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"El bot ahora kickeará por repetir (usuarios que\n" +"repitan %d veces lo mismo), y baneará después de\n" +"%d kicks al mismo usuario." + +#: modules/commands/bs_kick.cpp:684 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." +msgstr "" +"El bot ahora kickeará por repetir (usuarios que\n" +"repitan %d veces lo mismo)." + +#: modules/commands/bs_kick.cpp:239 +#, c-format +msgid "Bot won't kick for %s anymore." +msgstr "El bot ya no kickeará por %s." + +#: modules/commands/bs_kick.cpp:426 +msgid "Bot won't kick for caps anymore." +msgstr "El bot ya no kickeará por mayúsculas." + +#: modules/commands/bs_kick.cpp:559 +msgid "Bot won't kick for flood anymore." +msgstr "El bot ya no kickeará por flood." + +#: modules/commands/bs_kick.cpp:694 +msgid "Bot won't kick for repeats anymore." +msgstr "El bot ya no kickeará por repetir." + +#: modules/commands/cs_access.cpp:472 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_session.cpp:514 +msgid "By" +msgstr "Por" + +#: modules/commands/os_info.cpp:104 +msgid "CLEAR target" +msgstr "CLEAR objetivo" + +#: modules/commands/cs_seen.cpp:119 +msgid "CLEAR time" +msgstr "CLEAR hora" + +#: modules/commands/ms_cancel.cpp:19 +msgid "Cancel the last memo you sent" +msgstr "Cancelar el último memo que enviaste" + +#: modules/commands/cs_drop.cpp:19 +msgid "Cancel the registration of a channel" +msgstr "Cancelar el registro de un canal" + +#: modules/commands/ns_drop.cpp:20 +msgid "Cancel the registration of a nickname" +msgstr "Cancelar el registro de un nick" + +#: modules/commands/ms_cancel.cpp:84 +msgid "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." +msgstr "" +"Cancela el último memo que enviaste al nick o canal dado,\n" +"siempre y cuando no haya sido leído en el momento en el que\n" +"usaste el comando." + +#: modules/commands/cs_clone.cpp:149 +#, c-format +msgid "Cannot clone channel %s to itself!" +msgstr "¡No se puede clonar el canal %s a sí mismo!" + +#: modules/commands/ns_register.cpp:332 +msgid "Cannot send mail now; please retry a little later." +msgstr "Imposible enviar el e-mail ahora; por favor inténtalo más tarde." + +#: modules/commands/bs_kick.cpp:1141 modules/commands/bs_kick.cpp:1143 +#: modules/commands/bs_kick.cpp:1146 +msgid "Caps kicker" +msgstr "Kick por mayúsculas" + +#: modules/commands/os_shutdown.cpp:34 +msgid "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." +msgstr "" +"Hace que los Servicios se apaguen inmediatamente; la base de\n" +"datos no se guarda. Este comando no debe ser usado a\n" +"menos que la copia de la base de datos cargada en memoria\n" +"esté dañada y no deba ser guardada." + +#: modules/commands/os_reload.cpp:47 +msgid "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." +msgstr "" +"Hace que los Servicios recarguen el archivo de configuración.\n" +"Ten en cuenta que algunas directivas todavía necesitan que los\n" +"Servicios reinicien para tener efecto. (como los nicks de los\n" +"Servicios, la activación del límite de sesion, etc.)" + +#: modules/commands/os_shutdown.cpp:62 +msgid "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." +msgstr "" +"Hace que los Servicios actualicen la base de datos y luego\n" +"reinicien." + +#: modules/commands/os_shutdown.cpp:89 +msgid "Causes Services to save all databases and then shut down." +msgstr "" +"Hace que los Servicios actualicen la base de datos y luego\n" +"se apaguen." + +#: modules/commands/os_update.cpp:34 +msgid "" +"Causes Services to update all database files as soon as you\n" +"send the command." +msgstr "" +"Hace que los Servicios actualicen la base de datos en\n" +"cuanto envíes el comando." + +#: modules/commands/ns_cert.cpp:246 +#, c-format +msgid "Certificate list for %s:" +msgstr "Lista de certificados para %s:" + +#: modules/commands/cs_set.cpp:528 modules/commands/cs_set.cpp:570 +msgid "ChanServ is required to enable persist on this network." +msgstr "" +"Se necesita a ChanServ para habilitar la persistencia de canales en esta red." + +#: modules/commands/os_mode.cpp:19 +msgid "Change channel modes" +msgstr "Cambiar modos de canal" + +#: modules/commands/ns_set.cpp:905 +msgid "Change the communication method of Services" +msgstr "Cambiar el método de comunicacion con los Servicios" + +#: modules/commands/os_mode.cpp:146 +msgid "Change user modes" +msgstr "Cambiar modos de usuario" + +#: modules/commands/os_mode.cpp:161 +#, c-format +msgid "Changed usermodes of %s to %s." +msgstr "Cambiados los modos de usuario de %s a %s." + +#: modules/commands/ns_set.cpp:411 +msgid "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." +msgstr "" +"Cambia el display usado para referirte a un grupo de\n" +"nicks. El nuevo display DEBE ser un nick del grupo." + +#: modules/commands/ns_set.cpp:387 +msgid "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." +msgstr "" +"Cambia el display usado para referirte a tu grupo de\n" +"nicks. El nuevo display DEBE ser un nick de tu grupo." + +#: modules/commands/cs_set.cpp:324 +msgid "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." +msgstr "" +"Cambia el fundador de un canal. El nuevo nick debe estar\n" +"registrado." + +#: modules/commands/ns_set.cpp:884 +msgid "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Cambia el idioma que los Servicios usan para enviar mensajes al\n" +"usuario dado (por ejemplo, al responder a un comando que envíe).\n" +"idioma debe ser uno de los de la siguiente lista de idiomas\n" +"soportados:" + +#: modules/commands/ns_set.cpp:848 +msgid "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Cambia el idioma que los Servicios usan para enviarte mensajes\n" +"(por ejemplo, al responder a un comando que envíes).\n" +"idioma debe ser uno de los de la siguiente lista de idiomas\n" +"soportados:" + +#: modules/commands/ns_set.cpp:227 +msgid "Changes the password used to identify as the nick's owner." +msgstr "Cambia la contraseña usada para identificarse como dueño del nick." + +#: modules/commands/ns_set.cpp:161 +msgid "" +"Changes the password used to identify you as the nick's\n" +"owner." +msgstr "" +"Cambia la contraseña usada para identificarte como\n" +"dueño del nick." + +#: modules/commands/cs_set.cpp:1017 +#, fuzzy +msgid "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." +msgstr "" +"Cambia el sucesor de un canal. Si el nick fundador\n" +"expira o se borra mientras el canal está aún registrado,\n" +"el sucesor se convertirá en el nuevo fundador del canal.\n" +"El nuevo nick debe estar registrado." + +#: modules/commands/ns_alist.cpp:48 modules/commands/ns_ajoin.cpp:100 +msgid "Channel" +msgstr "Canal" + +#: include/language.h:84 +#, c-format +msgid "Channel %s doesn't exist." +msgstr "El canal %s no existe." + +#: modules/commands/cs_drop.cpp:63 +#, c-format +msgid "Channel %s has been dropped." +msgstr "El canal %s ha sido eliminado." + +#: modules/commands/cs_getkey.cpp:43 +#, c-format +msgid "Channel %s has no key." +msgstr "El canal %s no tiene clave." + +#: modules/commands/cs_register.cpp:47 +#, c-format +msgid "Channel %s is already registered!" +msgstr "¡El canal %s ya está registrado!" + +#: modules/commands/os_forbid.cpp:524 +#, c-format +msgid "Channel %s is forbidden by %s: %s" +msgstr "El canal %s está prohibido por %s: %s" + +#: modules/commands/os_forbid.cpp:526 +#, c-format +msgid "Channel %s is forbidden." +msgstr "El canal %s está prohibido." + +#: modules/commands/cs_set.cpp:580 +#, c-format +msgid "Channel %s is no longer persistent." +msgstr "El canal %s ya no es persistente." + +#: modules/commands/cs_set.cpp:542 +#, c-format +msgid "Channel %s is now persistent." +msgstr "El canal %s ahora es persistente." + +#: modules/commands/cs_suspend.cpp:180 +#, c-format +msgid "Channel %s is now released." +msgstr "El canal %s está ahora liberado." + +#: modules/commands/cs_suspend.cpp:125 +#, c-format +msgid "Channel %s is now suspended." +msgstr "El canal %s está ahora prohibido." + +#: include/language.h:83 +#, c-format +msgid "Channel %s isn't registered." +msgstr "El canal %s no está registrado." + +#: modules/commands/cs_suspend.cpp:172 +#, c-format +msgid "Channel %s isn't suspended." +msgstr "El canal %s no está suspendido." + +#: modules/commands/cs_register.cpp:68 +#, c-format +msgid "Channel %s registered under your account: %s" +msgstr "Canal %s registrado bajo tu cuenta: %s" + +#: modules/commands/cs_set.cpp:1078 +#, c-format +msgid "Channel %s will expire." +msgstr "El canal %s expirará." + +#: modules/commands/cs_set.cpp:1072 +#, c-format +msgid "Channel %s will not expire." +msgstr "El canal %s no expirará." + +#: modules/commands/cs_xop.cpp:475 +#, c-format +msgid "Channel %s %s list has been cleared." +msgstr "La lista de %s de %s ha sido limpiada." + +#: modules/commands/cs_access.cpp:486 modules/commands/cs_flags.cpp:361 +#, c-format +msgid "Channel %s access list has been cleared." +msgstr "La lista de acceso para el canal %s ha sido limpiada." + +#: modules/commands/cs_akick.cpp:428 +#, c-format +msgid "Channel %s akick list has been cleared." +msgstr "La lista de kicks automáticos del canal %s ha sido limpiada." + +#: modules/commands/cs_mode.cpp:444 +#, c-format +msgid "Channel %s has no mode locks." +msgstr "El canal %s no tiene modos bloqueados." + +#: include/language.h:82 +#, c-format +msgid "Channel %s is currently suspended." +msgstr "El canal %s está actualmente suspendido." + +#: include/language.h:101 +#, c-format +msgid "Channel %s is not a valid channel." +msgstr "%s no es un canal válido." + +#: modules/commands/os_list.cpp:70 +msgid "Channel list:" +msgstr "Lista de canales:" + +#: modules/extra/stats/cs_fantasy_stats.cpp:148 +#, c-format +msgid "Channel stats for %s on %s:" +msgstr "Estadísticas de canal para %s en %s:" + +#: modules/commands/cs_access.cpp:142 modules/commands/cs_flags.cpp:97 +#: modules/commands/cs_xop.cpp:139 +msgid "Channels may not be on access lists." +msgstr "Los canales no pueden estar en las listas de acceso." + +#: modules/commands/ns_alist.cpp:114 +#, c-format +msgid "Channels that %s has access on:" +msgstr "Canales en los que %s tiene acceso:" + +#: modules/commands/os_stats.cpp:181 +#, c-format +msgid "Channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "Canales: %lu entradas, %lu buckets, la cadena más larga es %d" + +#: modules/extra/stats/m_chanstats.cpp:517 +#: modules/extra/stats/m_chanstats.cpp:525 +msgid "Chanstats" +msgstr "Estadísticas de Canal" + +#: modules/extra/stats/m_chanstats.cpp:102 +#, c-format +msgid "Chanstats statistics are now disabled for %s" +msgstr "Las estadísticas de canal están ahora deshabilitadas para %s" + +#: modules/extra/stats/m_chanstats.cpp:51 +msgid "Chanstats statistics are now disabled for this channel." +msgstr "Las estadísticas están ahora deshabilitadas para este canal." + +#: modules/extra/stats/m_chanstats.cpp:104 +msgid "Chanstats statistics are now disabled for your nick." +msgstr "Las estadísticas de canal están ahora deshabilitadas para tu nick." + +#: modules/extra/stats/m_chanstats.cpp:93 +#, c-format +msgid "Chanstats statistics are now enabled for %s" +msgstr "Las estadísticas de canal están ahora habilitadas para %s" + +#: modules/extra/stats/m_chanstats.cpp:44 +msgid "Chanstats statistics are now enabled for this channel." +msgstr "Las estadísticas están ahora habilitadas para este canal." + +#: modules/extra/stats/m_chanstats.cpp:95 +msgid "Chanstats statistics are now enabled for your nick." +msgstr "Las estadísticas de canal están ahora habilitadas para tu nick." + +#: modules/commands/cs_seen.cpp:367 +msgid "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." +msgstr "" +"Comprueba la última vez que nick fue visto entrando, saliendo,\n" +"o cambiando el nick en la red y te dice cuando y, dependiendo\n" +"del canal o de la configuración del usuario, donde estaba." + +#: modules/commands/ms_check.cpp:19 +msgid "Checks if last memo to a nick was read" +msgstr "Comprueba si el último memo enviado a un nick ha sido leído" + +#: modules/commands/ms_check.cpp:69 +#, fuzzy +msgid "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." +msgstr "" +"Verifica si el _último_ memo que enviaste a nick ha sido leído.\n" +"Ten en cuenta solo funciona para nicks, no para canales." + +#: modules/commands/os_info.cpp:227 +#, c-format +msgid "Cleared info from %s." +msgstr "Borrada información de %s" + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1153 +#: modules/commands/bs_kick.cpp:1156 +msgid "Colors kicker" +msgstr "Kick por colores" + +#: modules/commands/cs_log.cpp:127 +msgid "Command" +msgstr "Comando" + +#: modules/commands/bs_kick.cpp:251 +msgid "Configures AMSG kicker" +msgstr "Configura kicks por AMSG" + +#: modules/commands/bs_kick.cpp:287 +msgid "Configures badwords kicker" +msgstr "Configura kicks por badwords" + +#: modules/commands/bs_kick.cpp:326 +#, fuzzy +msgid "Configures bolds kicker" +msgstr "Configura kicks por badwords" + +#: modules/commands/bs_kick.cpp:132 +msgid "Configures bot kickers. option can be one of:" +msgstr "Configura kicks del bot. opción puede ser:" + +#: modules/commands/bs_set.cpp:19 +msgid "Configures bot options" +msgstr "Configura opciones del bot" + +#: modules/commands/bs_set.cpp:32 +msgid "" +"Configures bot options.\n" +" \n" +"Available options:" +msgstr "" +"Configura las opciones del bot.\n" +" \n" +"Opciones disponibles:" + +#: modules/commands/bs_kick.cpp:360 +msgid "Configures caps kicker" +msgstr "Configura kicks por mayúsculas" + +#: modules/commands/cs_log.cpp:105 +msgid "Configures channel logging settings" +msgstr "Configura las opciones de registros del canal" + +#: modules/commands/bs_kick.cpp:456 +msgid "Configures color kicker" +msgstr "Configura kicks por color" + +#: modules/commands/bs_kick.cpp:490 +msgid "Configures flood kicker" +msgstr "Configura kicks por flood" + +#: modules/commands/bs_kick.cpp:588 +msgid "Configures italics kicker" +msgstr "Configura kicks por cursivas" + +#: modules/commands/bs_kick.cpp:119 +msgid "Configures kickers" +msgstr "Configura kicks" + +#: modules/commands/bs_kick.cpp:622 +msgid "Configures repeat kicker" +msgstr "Configura kicks por repetir" + +#: modules/commands/bs_kick.cpp:723 +msgid "Configures reverses kicker" +msgstr "Configura kicks por fondos" + +#: modules/commands/bs_set.cpp:90 +msgid "Configures the time bot bans expire in" +msgstr "Configura el tiempo de expiración de los bans del bot" + +#: modules/commands/bs_kick.cpp:757 +msgid "Configures underlines kicker" +msgstr "Configura kicks por subrayados" + +#: modules/commands/ns_register.cpp:21 +msgid "Confirm a passcode" +msgstr "Confirmar un código" + +#: modules/commands/cs_mode.cpp:733 +msgid "Control modes and mode locks on a channel" +msgstr "Controlar modos y bloqueos de modos en un canal" + +#: modules/commands/cs_entrymsg.cpp:239 +msgid "" +"Controls what messages will be sent to users when they join the channel." +msgstr "" +"Controla que mensajes son enviados a los usuarios cuando entran al canal." + +#: modules/commands/cs_clone.cpp:242 +#, fuzzy +msgid "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." +msgstr "" +"Copia toda la configuración, accesos, akicks, etc de canal al canal\n" +"objetivo. Si que es ACCESS, AKICK, or BADWORDS\n" +"solo se clonan las respectivas opciones.\n" +"Debes ser el fundador de canal y objetivo." + +#: modules/commands/cs_clone.cpp:114 +msgid "Copy all settings from one channel to another" +msgstr "Copia toda la configuración de un canal a otro" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/bs_info.cpp:57 +#: modules/commands/os_akill.cpp:358 +msgid "Created" +msgstr "Creado" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_ignore.cpp:266 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_news.cpp:156 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_akill.cpp:358 +msgid "Creator" +msgstr "Creador" + +#: modules/commands/os_sxline.cpp:180 +#, c-format +msgid "Current %s list:" +msgstr "Lista %s actual:" + +#: modules/commands/os_akill.cpp:323 +msgid "Current AKILL list:" +msgstr "Lista actual de AKILLs:" + +#: modules/commands/os_session.cpp:493 +msgid "Current Session Limit Exception list:" +msgstr "Lista de excepciones al límite de sesiones actual:" + +#: modules/commands/os_modinfo.cpp:116 +msgid "Current module list:" +msgstr "Lista actual de módulos:" + +#: modules/commands/os_stats.cpp:69 +#, c-format +msgid "Current number of AKILLs: %d" +msgstr "Número actual de AKILLs: %d" + +#: modules/commands/os_stats.cpp:89 +#, c-format +msgid "Current number of SNLINEs: %d" +msgstr "Número actual de SNLINEs: %d" + +#: modules/commands/os_stats.cpp:109 +#, c-format +msgid "Current number of SQLINEs: %d" +msgstr "Número actual de SQLINEs: %d" + +#: modules/commands/os_stats.cpp:138 +#, c-format +msgid "Current users: %d (%d ops)" +msgstr "Usuarios actuales: %d (%d ops)" + +#: modules/commands/os_oper.cpp:71 +msgid "DEL oper" +msgstr "DEL oper" + +#: modules/commands/os_info.cpp:103 +msgid "DEL target info" +msgstr "DEL objetivo info" + +#: modules/commands/ns_ajoin.cpp:232 +msgid "DEL [nickname] channel" +msgstr "DEL [nick] canal" + +#: modules/commands/ns_cert.cpp:259 +msgid "DEL [nickname] fingerprint" +msgstr "DEL [nick] huella" + +#: modules/commands/ns_access.cpp:103 +msgid "DEL [nickname] mask" +msgstr "DEL [nick] máscara" + +#: modules/commands/os_sxline.cpp:426 modules/commands/os_sxline.cpp:660 +#: modules/commands/os_akill.cpp:387 +msgid "DEL {mask | entry-num | list | id}" +msgstr "DEL {máscara | entrada-num | lista | id}" + +#: modules/commands/os_session.cpp:524 +msgid "DEL {mask | entry-num | list}" +msgstr "DEL {máscara | entrada-num | lista}" + +#: modules/commands/os_ignore.cpp:343 +msgid "DEL {nick|mask}" +msgstr "DEL {nick|máscara}" + +#: modules/commands/os_news.cpp:279 +msgid "DEL {num | ALL}" +msgstr "DEL {num | ALL}" + +#: modules/commands/os_forbid.cpp:158 +msgid "DEL {NICK|CHAN|EMAIL|REGISTER} entry" +msgstr "DEL {NICK|CHAN|EMAIL|REGISTER} entrada" + +#: modules/commands/os_dns.cpp:666 +msgid "DELIP server.name ip" +msgstr "DELIP nombre-de-servidor ip" + +#: modules/commands/os_dns.cpp:664 +msgid "DELSERVER server.name [zone.name]" +msgstr "DELSERVER nombre-de-servidor [nombre-de-zona]" + +#: modules/commands/os_dns.cpp:662 +msgid "DELZONE zone.name" +msgstr "DELZONE nombre-de-zona" + +#: modules/commands/os_dns.cpp:669 +msgid "DEPOOL server.name" +msgstr "DEPOOL nombre-de-servidor" + +#: modules/commands/cs_seen.cpp:162 +#, c-format +msgid "Database cleared, removed %lu nicks that were added after %s." +msgstr "" +"Base de datos limpiada, se han eliminado %lu nicks que fueron añadidos " +"después de %s." + +#: modules/commands/ms_list.cpp:64 +msgid "Date/Time" +msgstr "Fecha/Hora" + +#: modules/commands/hs_off.cpp:49 +msgid "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." +msgstr "" +"Desactiva el vhost actualmente asignado al nick en uso.\n" +"Cuando uses este comando cualquier usuario que te haga\n" +"un /whois verá tu host/IP real." + +#: modules/commands/hs_off.cpp:19 +msgid "Deactivates your assigned vhost" +msgstr "Desactiva tu vhost asignado." + +#: modules/commands/os_stats.cpp:72 +#, c-format +msgid "Default AKILL expiry time: %d days" +msgstr "Tiempo de expiración por defecto de AKILL: %d días" + +#: modules/commands/os_stats.cpp:76 +#, c-format +msgid "Default AKILL expiry time: %d hours" +msgstr "Tiempo de expiración por defecto de AKILL: %d horas" + +#: modules/commands/os_stats.cpp:80 +#, c-format +msgid "Default AKILL expiry time: %d minutes" +msgstr "Tiempo de expiración por defecto de AKILL: %d minutos" + +#: modules/commands/os_stats.cpp:74 +msgid "Default AKILL expiry time: 1 day" +msgstr "Tiempo de expiración por defecto de AKILL: 1 día" + +#: modules/commands/os_stats.cpp:78 +msgid "Default AKILL expiry time: 1 hour" +msgstr "Tiempo de expiración por defecto de AKILL: 1 hora" + +#: modules/commands/os_stats.cpp:82 +msgid "Default AKILL expiry time: 1 minute" +msgstr "Tiempo de expiración por defecto de AKILL: 1 minuto" + +#: modules/commands/os_stats.cpp:84 +msgid "Default AKILL expiry time: No expiration" +msgstr "Tiempo de expiración por defecto de AKILL: Sin expiración " + +#: modules/commands/os_stats.cpp:92 +#, c-format +msgid "Default SNLINE expiry time: %d days" +msgstr "Tiempo de expiración por defecto de SNLINE: %d días" + +#: modules/commands/os_stats.cpp:96 +#, c-format +msgid "Default SNLINE expiry time: %d hours" +msgstr "Tiempo de expiración por defecto de SNLINE: %d horas" + +#: modules/commands/os_stats.cpp:100 +#, c-format +msgid "Default SNLINE expiry time: %d minutes" +msgstr "Tiempo de expiración por defecto de SNLINE: %d minutos" + +#: modules/commands/os_stats.cpp:94 +msgid "Default SNLINE expiry time: 1 day" +msgstr "Tiempo de expiración por defecto de SNLINE: 1 día" + +#: modules/commands/os_stats.cpp:98 +msgid "Default SNLINE expiry time: 1 hour" +msgstr "Tiempo de expiración por defecto de SNLINE: 1 hora" + +#: modules/commands/os_stats.cpp:102 +msgid "Default SNLINE expiry time: 1 minute" +msgstr "Tiempo de expiración por defecto de SNLINE: 1 minuto" + +#: modules/commands/os_stats.cpp:104 +msgid "Default SNLINE expiry time: No expiration" +msgstr "Tiempo de expiración por defecto de SNLINE: Sin expiración" + +#: modules/commands/os_stats.cpp:112 +#, c-format +msgid "Default SQLINE expiry time: %d days" +msgstr "Tiempo de expiración por defecto de SQLINE: %d días" + +#: modules/commands/os_stats.cpp:116 +#, c-format +msgid "Default SQLINE expiry time: %d hours" +msgstr "Tiempo de expiración por defecto de SQLINE: %d horas" + +#: modules/commands/os_stats.cpp:120 +#, c-format +msgid "Default SQLINE expiry time: %d minutes" +msgstr "Tiempo de expiración por defecto de SQLINE: %d minutos" + +#: modules/commands/os_stats.cpp:114 +msgid "Default SQLINE expiry time: 1 day" +msgstr "Tiempo de expiración por defecto de SQLINE: 1 día" + +#: modules/commands/os_stats.cpp:118 +msgid "Default SQLINE expiry time: 1 hour" +msgstr "Tiempo de expiración por defecto de SQLINE: 1 hora" + +#: modules/commands/os_stats.cpp:122 +msgid "Default SQLINE expiry time: 1 minute" +msgstr "Tiempo de expiración por defecto de SQLINE: 1 minuto" + +#: modules/commands/os_stats.cpp:124 +msgid "Default SQLINE expiry time: No expiration" +msgstr "Tiempo de expiración por defecto de SQLINE: Sin expiración" + +#: modules/commands/os_news.cpp:351 +msgid "Define messages to be randomly shown to users at logon" +msgstr "" +"Define mensajes para ser mostrados aleatoriamente a los\n" +" usuarios al conectarse" + +#: modules/commands/os_news.cpp:297 +msgid "Define messages to be shown to users at logon" +msgstr "" +"Define mensajes para ser mostrados a los usuarios\n" +" al conectarse" + +#: modules/commands/os_news.cpp:324 +msgid "Define messages to be shown to users who oper" +msgstr "" +"Define mensajes a ser mostrados a los usuarios al\n" +" transformarse en operadores" + +#: modules/commands/ms_del.cpp:44 +msgid "Delete a memo or memos" +msgstr "Borra uno o más memos" + +#: modules/commands/hs_del.cpp:19 +msgid "Delete the vhost of another user" +msgstr "Borra el vhost de otro usuario" + +#: modules/commands/cs_xop.cpp:302 +#, c-format +msgid "Deleted %d entries from %s %s list." +msgstr "Borradas %d entradas de la lista de %s de %s." + +#: modules/commands/cs_access.cpp:277 +#, c-format +msgid "Deleted %d entries from %s access list." +msgstr "%d entradas borradas de la lista de acceso de %s." + +#: modules/commands/cs_akick.cpp:228 +#, c-format +msgid "Deleted %d entries from %s autokick list." +msgstr "%d entradas borradas de la lista de kicks automáticos del canal %s." + +#: modules/commands/bs_badwords.cpp:170 +#, c-format +msgid "Deleted %d entries from %s bad words list." +msgstr "%d entradas borradas de la lista de bad words de %s." + +#: modules/commands/os_session.cpp:149 +#, c-format +msgid "Deleted %d entries from session-limit exception list." +msgstr "%d entradas borradas de la lista de excepciones al límite de sesiones." + +#: modules/commands/os_sxline.cpp:32 +#, c-format +msgid "Deleted %d entries from the %s list." +msgstr "Borradas %d entradas de la lista de %s." + +#: modules/commands/os_akill.cpp:33 +#, c-format +msgid "Deleted %d entries from the AKILL list." +msgstr "%d entradas borradas de la lista de AKILLs." + +#: modules/commands/cs_access.cpp:275 +#, c-format +msgid "Deleted 1 entry from %s access list." +msgstr "1 entrada borrada de la lista de acceso de %s." + +#: modules/commands/cs_akick.cpp:226 +#, c-format +msgid "Deleted 1 entry from %s autokick list." +msgstr "1 entrada borrada de la lista de kicks automáticos del canal %s." + +#: modules/commands/bs_badwords.cpp:168 +#, c-format +msgid "Deleted 1 entry from %s bad words list." +msgstr "1 palabra borrada de la lista de bad words de %s." + +#: modules/commands/os_session.cpp:147 +msgid "Deleted 1 entry from session-limit exception list." +msgstr "1 entrada borrada de la lista de excepciones al límite de sesiones." + +#: modules/commands/os_sxline.cpp:30 +#, c-format +msgid "Deleted 1 entry from the %s list." +msgstr "Borrada 1 entrada de la lista de %s." + +#: modules/commands/os_akill.cpp:31 +msgid "Deleted 1 entry from the AKILL list." +msgstr "1 entrada borrada de la lista de AKILLs." + +#: modules/commands/os_info.cpp:208 +#, c-format +msgid "Deleted info from %s." +msgstr "Borrada información de %s." + +#: modules/commands/cs_xop.cpp:300 +#, c-format +msgid "Deleted one entry from %s %s list." +msgstr "Borrada una entrada de la lista de %s de %s." + +#: modules/commands/ms_del.cpp:129 +msgid "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Borra el o los memos especificados. Puedes especificar múltiples\n" +"números o rangos de numeros en vez de uno solo, como en el\n" +"ejemplo de abajo.\n" +" \n" +"Si se especifica LAST se elimina el último memo.\n" +"Si se especifica ALL se borran todos tus memos.\n" +" \n" +"Ejemplos:\n" +" \n" +" DEL 1\n" +" Borra tu primer memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Borra los memos número 2 a 5 y 7 a 9." + +#: modules/commands/hs_del.cpp:48 +msgid "" +"Deletes the vhost assigned to the given nick from the\n" +"database." +msgstr "Elimina el vhost asignado al nick dado de la base de datos." + +#: modules/commands/hs_del.cpp:59 +#, fuzzy +msgid "Deletes the vhost for all nicks in a group" +msgstr "Borra el vhost de todos los nicks en un grupo" + +#: modules/commands/hs_del.cpp:93 +msgid "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." +msgstr "" +"Elimina el vhost para todos los nicks en el mismo grupo que el\n" +"nick dado." + +#: modules/commands/os_dns.cpp:653 +#, c-format +msgid "Depooled %s." +msgstr "%s sacado del pool dns." + +#: modules/commands/cs_access.cpp:799 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_list.cpp:75 modules/commands/cs_info.cpp:53 +msgid "Description" +msgstr "Descripción" + +#: modules/commands/cs_set.cpp:239 +#, c-format +msgid "Description of %s changed to %s." +msgstr "Descripción de %s cambiada a%s." + +#: modules/commands/cs_set.cpp:245 +#, c-format +msgid "Description of %s unset." +msgstr "Descripción de %s eliminada." + +#: modules/commands/bs_kick.cpp:1115 modules/commands/bs_info.cpp:90 +msgid "Disabled" +msgstr "Deshabilitado" + +#: modules/commands/cs_suspend.cpp:134 +msgid "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." +msgstr "" +"Impide a cualquiera usar el canal dado.\n" +"Puede ser cancelado usando el comando UNSUSPEND\n" +"para conservar los datos/configuraciones previos.\n" +"Si se proporciona una expiración, la suspensión se levantará\n" +"después de ese periodo de tiempo; si no, se usará la expiración\n" +"predeterminada en el archivo de configuración.\n" +" \n" +"La razón puede ser obligatoria en algunas redes." + +#: modules/commands/hs_request.cpp:337 +#, c-format +msgid "Displayed %d records (%d total)." +msgstr "Mostrados %d registros (%d en total)." + +#: modules/commands/hs_list.cpp:122 +#, c-format +msgid "Displayed all records (count: %d)." +msgstr "Todos los registros mostrados (cuenta: %d)" + +#: modules/commands/hs_list.cpp:120 +#, c-format +msgid "Displayed records from %d to %d." +msgstr "Registros mostrados de %d a %d." + +#: modules/commands/hs_list.cpp:116 +#, c-format +msgid "Displayed records matching key %s (count: %d)." +msgstr "Registros mostrados que coinciden con la clave %s (cuenta: %d)." + +#: modules/commands/ns_info.cpp:19 +msgid "Displays information about a given nickname" +msgstr "Muestra información sobre un nick dado" + +#: modules/commands/ns_info.cpp:125 +msgid "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." +msgstr "" +"Muestra información relativa al nick que especifiques,\n" +"como el propietario del nick, la ultima direccion usada,\n" +"el tiempo, y las opciones del nick. Si no proporcionas un\n" +"nick y estás identificado, se usa el nombre de tu cuenta,\n" +"si no, se usa tu nick actual." + +#: modules/commands/ms_info.cpp:19 +msgid "Displays information about your memos" +msgstr "Muestra información acerca de tus memos" + +#: modules/commands/hs_list.cpp:19 +msgid "Displays one or more vhost entries" +msgstr "Muestra una o mas entradas vhost" + +#: modules/extra/stats/cs_fantasy_top.cpp:50 +msgid "Displays the top 10 users of a channel" +msgstr "Muestra el top 10 de usuarios de un canal" + +#: modules/extra/stats/cs_fantasy_top.cpp:73 +msgid "Displays the top 10 users of the network" +msgstr "Muestra el top 10 de usuarios en la red" + +#: modules/extra/stats/cs_fantasy_top.cpp:38 +msgid "Displays the top 3 users of a channel" +msgstr "Muestra el top 3 de usuarios de un canal" + +#: modules/extra/stats/cs_fantasy_top.cpp:62 +msgid "Displays the top 3 users of the network" +msgstr "Muestra el top 3 de usuarios en la red" + +#: modules/commands/help.cpp:33 +msgid "Displays this list and give information about commands" +msgstr "Muestra esta lista y da información sobre comandos" + +#: modules/extra/stats/cs_fantasy_stats.cpp:39 +msgid "Displays your Channel Stats" +msgstr "Muestra tus Estadísticas de Canal" + +#: modules/extra/stats/cs_fantasy_stats.cpp:51 +msgid "Displays your Global Stats" +msgstr "Muestra tus Estadísticas Globales" + +#: modules/commands/bs_kick.cpp:1463 +msgid "Don't use AMSGs!" +msgstr "¡No uses AMSGs!" + +#: modules/commands/bs_kick.cpp:1266 +msgid "Don't use bolds on this channel!" +msgstr "¡No uses negritas en este canal!" + +#: modules/commands/bs_kick.cpp:1274 +msgid "Don't use colors on this channel!" +msgstr "¡No uses colores en este canal!" + +#: modules/commands/bs_kick.cpp:1290 +msgid "Don't use italics on this channel!" +msgstr "¡No uses cursivas en este canal!" + +#: modules/commands/bs_kick.cpp:1282 +msgid "Don't use reverses on this channel!" +msgstr "¡No uses fondos en este canal!" + +#: modules/commands/bs_kick.cpp:1408 +#, c-format +msgid "Don't use the word \"%s\" on this channel!" +msgstr "¡No uses la palabra \"%s\" en este canal!" + +#: modules/commands/bs_kick.cpp:1298 +msgid "Don't use underlines on this channel!" +msgstr "¡No uses subrayados en este canal!" + +#: modules/commands/ns_drop.cpp:61 +msgid "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." +msgstr "" +"Borra el nick dado de la base de datos. Cuando se borra tu nick\n" +"perderás tus accesos y los canales que poseas. Cualquier otro\n" +"usuario podrá tomar el control de ese nick." + +#: modules/commands/ns_set.cpp:513 +#, c-format +msgid "E-mail address for %s changed to %s." +msgstr "Dirección e-mail para %s cambiada a %s." + +#: modules/commands/ns_set.cpp:519 +#, c-format +msgid "E-mail address for %s unset." +msgstr "Dirección e-mail para %s borrada." + +#: src/mail.cpp:80 +#, c-format +msgid "E-mail for %s is invalid." +msgstr "El e-mail para %s no es válido." + +#: modules/commands/os_news.cpp:309 +#, c-format +msgid "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Edita o muestra la lista de noticias de entrada. Cuando un\n" +"usuario se conecta a la red, se le enviarán estos mensajes.\n" +"(Sin embargo, no se enviarán más de %d mensajes para\n" +"evitar inundar al usuario. Si hay más, solo se mostrarán los\n" +"más recientes." + +#: modules/commands/os_news.cpp:336 +#, c-format +msgid "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Edita o muestra la lista de noticias de Operado. Cuando un\n" +"usuario se hace Operador (con el comando /OPER), se le enviarán\n" +"estos mensajes. (Sin embargo, no se enviarán más de %d\n" +"mensajes para evitar inundar al usuario. Si hay más, solo se\n" +"mostrarán los más recientes." + +#: modules/commands/os_news.cpp:363 +msgid "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." +msgstr "" +"Edita o muestra la lista de noticias aleatorias. Cuando un\n" +"usuario se conecta a la red, se escogerá una (y solo una) de\n" +"de estas noticias y se le enviará." + +#: modules/commands/ns_info.cpp:98 +msgid "Email address" +msgstr "Dirección email" + +#: modules/commands/ns_getemail.cpp:41 +#, fuzzy, c-format +msgid "Email matched: %s (%s) to %s." +msgstr "Emails que coinciden: %s a %s." + +#: modules/fantasy.cpp:19 +msgid "Enable fantaisist commands" +msgstr "Habilitar comandos fantasía" + +#: modules/commands/greet.cpp:19 +msgid "Enable greet messages" +msgstr "Activar mensajes de saludo" + +#: modules/commands/ns_set.cpp:568 +msgid "Enable or disable keep modes" +msgstr "Activa o desactiva la conservación de modos" + +#: modules/commands/bs_kick.cpp:1114 modules/commands/bs_info.cpp:89 +msgid "Enabled" +msgstr "Habilitado" + +#: modules/commands/cs_set.cpp:124 +#, c-format +msgid "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." +msgstr "" +"Habilita o deshabilita la característica autoop de %s\n" +"para un canal. Cuando está deshabilitada, los usuarios que\n" +"entran al canal no obtendrán ningún status de %s\n" +"automáticamente." + +#: modules/commands/cs_set.cpp:388 +msgid "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." +msgstr "" +"Activa o desactiva la conservación de modos para el nick dado.\n" +"Si la conservación de modos está activada, los servicios recordarán\n" +"los modos del usuario e intentarán restablecerlos la próxima vez que\n" +"se cree el canal." + +#: modules/commands/ns_set.cpp:643 +msgid "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." +msgstr "" +"Activa o desactiva la conservación de modos para el nick dado.\n" +"Si la conservación de modos está activada, los servicios recordarán\n" +"los modos del usuario e intentarán restablecerlos la próxima vez que\n" +"se identifique." + +#: modules/commands/ns_set.cpp:618 +msgid "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." +msgstr "" +"Activa o desactiva la conservación de modos para tu nick.\n" +"Si la conservación de modos está activada, los servicios\n" +"recordarán tus modos de usuario e intentarán restablecerlos\n" +"la próxima vez que te identifiques." + +#: modules/commands/cs_set.cpp:733 +#, fuzzy +msgid "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." +msgstr "" +"Habilita o deshabilita las características de seguridad\n" +"para un canal. Cuando %s está activado, solo los\n" +"usuarios registrados e IDENTIFICADOS con su contraseña\n" +"tendrán acceso en el canal controlado por la lista de acceso." + +#: modules/commands/cs_set.cpp:932 +msgid "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." +msgstr "" +"Habilita o deshabilita los kicks firmados para un\n" +"canal. Cuando SIGNKICK está activado, los kicks\n" +"hechos con el comando KICK contendrán el nick\n" +"que usó el comando en la razón.\n" +" \n" +"Si usas LEVEL, aquellos que tienen nivel superior o\n" +"igual al nivel SIGNKICK en el canal no firmarán sus kicks." + +#: modules/commands/cs_set.cpp:452 +#, c-format +msgid "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." +msgstr "" +"Habilita o deshabilita la opcion de paz para un\n" +"canal. Cuando paz está activado, un usuario no\n" +"podrá kickear, banear o quitar el status de canal\n" +"de un usuario con nivel igual o superior a él, con\n" +"los comandos de %s." + +#: modules/commands/cs_list.cpp:232 +msgid "Enables or disables the private option for a channel." +msgstr "Activa o desactiva la opción de privacidad para un canal." + +#: modules/commands/cs_set.cpp:671 +msgid "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." +msgstr "" +"Habilita o deshabilita la opción de acceso restringido para un\n" +"canal. Cuando acceso restringido está activado, los usuarios que no estén\n" +"en la lista de acceso serán kickeados y baneados del canal." + +#: modules/commands/cs_set.cpp:796 +msgid "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." +msgstr "" +"Habilita o deshabilita la opcion seguridad de fundador para\n" +"un canal. Cuando seguridad de fundador está activado, solo\n" +"el fundador real podrá borrar el canal, cambiar su clave, su\n" +"fundador y su sucesor, y no aquellos usuarios que tengan nivel\n" +"de fundador con el comando access/qop." + +#: modules/commands/cs_set.cpp:860 +#, fuzzy +msgid "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." +msgstr "" +"Habilita o deshabilita la opcion seguridad de ops para un\n" +"canal. Cuando seguridad de ops está activado, los usuarios\n" +"que no están en la lista de acceso no podrán obtener status de\n" +"operador del canal." + +#: modules/commands/cs_topic.cpp:70 +#, c-format +msgid "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." +msgstr "" +"Habilita o deshabilita la opción de retención de topic \n" +"para un canal. Cuando %s está activado, el topic para\n" +"el canal sera recordado por %s incluso después de que el\n" +"último usuario salga del canal, y será restaurado la próxima\n" +"vez que el canal sea creado." + +#: modules/commands/cs_set.cpp:592 +#, fuzzy, c-format +msgid "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." +msgstr "" +"Activa o desactiva la persistencia de un canal.\n" +"Cuando la persistencia está activa, el bot permanecerá\n" +"en el canal cuando salgan todos los usuarios.\n" +" \n" +"Si tu IRCd no tiene un modo de canal permanente (persistente),\n" +"debes tener un bot en tu canal para activar la persistencia\n" +"y no puede ser desasignado mientras la persistencia esté\n" +"activada.\n" +" \n" +"Si esta red no tiene habilitado %s y no tiene un\n" +"modo de canal permanente, %s entrará a tu canal\n" +"cuando actives la persistencia (y saldrá cuando la desactives).\n" +" \n" +"Si tu IRCd tiene un modo de canal permanente (persistente)\n" +"y está activado o desactivado (de cualquier modo, incluyendo\n" +"MLOCK), la persistencia está activada o desactivada automáticamente\n" +"para el canal. Adicionalmente, los servicios pondrán o quitarán\n" +"dicho modo cuando actives o desactives la persistencia." + +#: modules/commands/os_akill.cpp:331 +msgid "End of AKILL list." +msgstr "Fin de la lista AKILL." + +#: modules/commands/cs_access.cpp:444 +msgid "End of access list" +msgstr "Fin de la lista de acceso" + +#: modules/commands/cs_flags.cpp:347 +#, c-format +msgid "End of access list - %d/%d entries shown." +msgstr "Fin de la lista de acceso - %d/%d resultado(s) mostrado(s)." + +#: modules/commands/cs_flags.cpp:345 +msgid "End of access list." +msgstr "Fin de la lista de acceso." + +#: modules/commands/cs_akick.cpp:379 +msgid "End of autokick list" +msgstr "Fin de la lista autokick" + +#: modules/commands/bs_badwords.cpp:257 +msgid "End of bad words list." +msgstr "Fin de la lista de bad words." + +#: modules/commands/os_list.cpp:100 +#, fuzzy, c-format +msgid "End of channel list. %u channels shown." +msgstr "Fin de la lista - %d canales mostrados." + +#: modules/commands/os_config.cpp:117 +msgid "End of configuration." +msgstr "Fin de la configuración." + +#: modules/commands/cs_entrymsg.cpp:134 +msgid "End of entry message list." +msgstr "Fin de la lista de mensajes de entrada." + +#: modules/commands/os_forbid.cpp:407 +#, c-format +msgid "End of forbid list - %d/%d entries shown." +msgstr "Fin de la lista de prohibiciones - %d/%d entradas mostradas." + +#: modules/commands/os_forbid.cpp:405 +msgid "End of forbid list." +msgstr "Fin de la lista de prohibiciones." + +#: modules/commands/ns_alist.cpp:119 +#, c-format +msgid "End of list - %d channels shown." +msgstr "Fin de la lista - %d canales mostrados." + +#: modules/commands/ns_list.cpp:131 modules/commands/cs_list.cpp:130 +#, c-format +msgid "End of list - %d/%d matches shown." +msgstr "Fin de la lista - %d/%d resultado(s) mostrado(s)." + +#: modules/commands/os_news.cpp:176 +msgid "End of news list." +msgstr "Fin de la lista de noticias." + +#: modules/commands/os_list.cpp:235 +#, fuzzy, c-format +msgid "End of users list. %u users shown." +msgstr "Fin de la lista de acceso - %d/%d resultado(s) mostrado(s)." + +#: modules/commands/cs_enforce.cpp:227 +msgid "Enforce various channel modes and set options" +msgstr "Fuerza varios modos de canal y opciones de configuración" + +#: modules/commands/cs_enforce.cpp:263 +msgid "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." +msgstr "" +"Fuerza varios modos de canal y opciones de configuración. La\n" +"opción channel indica en que canal forzar los modos y opciones.\n" +"La opción que indica que modos y opciones forzar, y puede ser\n" +"una de estas: SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, o LIMIT.\n" +" \n" +"Usa SECUREOPS para forzar la opción SECUREOPS incluso si no está\n" +"activada. Usa RESTRICTED para forzar la opción RESTRICTED, también\n" +"si no está activada. Usa REGONLY para kickear del canal a usuarios no\n" +"registrados. Usa SSLONLY para kickear del canal a usuarios que no usen\n" +"una conexión segura. BANS forzará los bans del canal kickeando a los\n" +"usuarios afectados por ellos, y LIMIT kickeará usuarios hasta que el número\n" +"de usuarios en el canal sea inferior al límite del canal, si está " +"establecido." + +#: src/language.cpp:43 modules/commands/ns_set.cpp:836 +#: modules/commands/ns_set.cpp:856 modules/commands/ns_set.cpp:891 +msgid "English" +msgstr "Español" + +#: modules/commands/cs_entrymsg.cpp:170 +#, c-format +msgid "Entry message %i for %s deleted." +msgstr "Mensaje de entrada %i para %s borrado." + +#: modules/commands/cs_entrymsg.cpp:177 +#, c-format +msgid "Entry message %s not found on channel %s." +msgstr "Mensaje de entrada %s no encontrado en el canal %s." + +#: modules/commands/cs_entrymsg.cpp:147 +#, c-format +msgid "Entry message added to %s" +msgstr "Mensaje de entrada añadido a %s" + +#: modules/commands/cs_entrymsg.cpp:109 modules/commands/cs_entrymsg.cpp:158 +#, c-format +msgid "Entry message list for %s is empty." +msgstr "La lista de mesnsajes de entrada para %s está vacía." + +#: modules/commands/cs_entrymsg.cpp:113 +#, c-format +msgid "Entry message list for %s:" +msgstr "Lista de mensajes de entrada para %s:" + +#: modules/commands/cs_entrymsg.cpp:187 +#, c-format +msgid "Entry messages for %s have been cleared." +msgstr "El mensaje de entrada para %s ha sido borrado." + +#: modules/commands/os_reload.cpp:39 +#, c-format +msgid "Error reloading configuration file: %s" +msgstr "Error recargando el archivo de configuración: %s" + +#: include/language.h:125 +#, c-format +msgid "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." +msgstr "" +"¡Error! El Ident es demasiado largo, por favor, usa un ident de menos de %d " +"caracteres." + +#: include/language.h:124 +#, c-format +msgid "" +"Error! The vHost is too long, please use a hostname shorter than %d " +"characters." +msgstr "" +"¡Error! El vhost es demasiado largo, por favor, usa un host de menos de %d " +"caracteres." + +#: modules/commands/ns_cert.cpp:325 +#, fuzzy +msgid "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." +msgstr "" +"Ejemplos:\n" +" \n" +" CERT ADD \n" +" Añade esta huella a la lista de certificados y te identifica\n" +" automáticamente cuando conectas al IRC usando\n" +" este certificado.\n" +" \n" +" CERT DEL \n" +" Revierte el comando anterior.\n" +" \n" +" CERT LIST\n" +" Muestra la lista de certificados actual." + +#: modules/commands/os_session.cpp:358 +#, c-format +msgid "Exception for %s has been updated to %d." +msgstr "La excepción para %s ha sido actualizada a %d." + +#: modules/pseudoclients/chanserv.cpp:465 +#: modules/pseudoclients/nickserv.cpp:557 +#: modules/pseudoclients/nickserv.cpp:562 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_session.cpp:514 modules/commands/ns_group.cpp:327 +#: modules/commands/os_akill.cpp:358 +msgid "Expires" +msgstr "Expira" + +#: src/xline.cpp:397 +#, c-format +msgid "Expiry and reason updated for %s." +msgstr "Tiempo de expiración y razón actualizados para %s." + +#: src/xline.cpp:400 +#, c-format +msgid "Expiry for %s updated." +msgstr "Tiempo de expiración para %s actualizado." + +#: modules/fantasy.cpp:214 +msgid "Fantasy" +msgstr "Fantasía" + +#: modules/fantasy.cpp:60 +#, c-format +msgid "Fantasy mode is now off on channel %s." +msgstr "Modo fantasía ahora Desactivado en el canal %s." + +#: modules/fantasy.cpp:52 +#, c-format +msgid "Fantasy mode is now on on channel %s." +msgstr "Modo fantasía ahora Activado en el canal %s." + +#: modules/commands/cs_status.cpp:19 +msgid "Find a user's status on a channel" +msgstr "Encontrar el status de un usuario en un canal" + +#: modules/commands/ns_cert.cpp:192 +#, c-format +msgid "Fingerprint %s already present on %s's certificate list." +msgstr "La huella %s ya está presente en la lista de certificados de %s." + +#: modules/commands/ns_cert.cpp:198 +#, fuzzy, c-format +msgid "Fingerprint %s is already in use." +msgstr "%s ya está en %s." + +#: modules/commands/cs_flags.cpp:301 +msgid "Flags" +msgstr "Marcas" + +#: modules/commands/cs_flags.cpp:286 +#, c-format +msgid "Flags for %s on %s set to +%s" +msgstr "Marcas para %s en %s establecidas a +%s" + +#: modules/commands/cs_flags.cpp:341 +#, c-format +msgid "Flags list for %s" +msgstr "Lista de marcas para %s" + +#: modules/commands/bs_kick.cpp:1161 modules/commands/bs_kick.cpp:1163 +#: modules/commands/bs_kick.cpp:1166 +msgid "Flood kicker" +msgstr "Kick por flood" + +#: modules/commands/os_forbid.cpp:421 +msgid "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." +msgstr "" +"Esto te permite prohibir el uso de ciertos nicks, canales y\n" +"direcciones de email. Todas las entradas aceptan comodines." + +#: modules/commands/os_forbid.cpp:354 +msgid "Forbid list is empty." +msgstr "La lista de prohibiciones está vacía." + +#: modules/commands/os_forbid.cpp:396 +msgid "Forbid list:" +msgstr "Lista de prohibiciones:" + +#: modules/commands/os_forbid.cpp:348 +#, c-format +msgid "Forbid on %s was not found." +msgstr "No se encontraron prohibiciones en %s." + +#: modules/commands/os_forbid.cpp:156 +msgid "Forbid usage of nicknames, channels, and emails" +msgstr "Prohibir el uso de nicks, canales y emails" + +#: modules/commands/os_update.cpp:19 +msgid "Force the Services databases to be updated immediately" +msgstr "Fuerza a los Servicios a actualizar la base de datos inmediatamente" + +#: modules/commands/os_svs.cpp:19 +msgid "Forcefully change a user's nickname" +msgstr "Cambia, a la fuerza, el nick de un usuario" + +#: modules/commands/os_svs.cpp:68 +msgid "Forcefully changes a user's nickname from nick to newnick." +msgstr "Cambia, a la fuerza, el nick de un usuario de nick a nuevonick." + +#: modules/commands/os_svs.cpp:78 +msgid "Forcefully join a user to a channel" +msgstr "Fuerza la entrada de un usuario del canal." + +#: modules/commands/os_svs.cpp:112 +msgid "Forcefully join a user to a channel." +msgstr "Fuerza la entrada de un usuario del canal." + +#: modules/commands/os_svs.cpp:122 +msgid "Forcefully part a user from a channel" +msgstr "Fuerza la salida de un usuario del canal." + +#: modules/commands/os_svs.cpp:160 +msgid "Forcefully part a user from a channel." +msgstr "Fuerza la salida de un usuario del canal." + +#: modules/commands/ns_alist.cpp:64 modules/commands/cs_info.cpp:47 +msgid "Founder" +msgstr "Fundador" + +#: modules/commands/cs_set.cpp:315 +#, c-format +msgid "Founder of %s changed to %s." +msgstr "Fundador de %s cambiado a %s." + +#: modules/commands/ns_getpass.cpp:41 +msgid "GETPASS command unavailable because encryption is in use." +msgstr "El comando GETPASS no está disponible debido al uso de encriptación." + +#: modules/commands/ns_recover.cpp:84 +msgid "Ghost with your nick has been killed." +msgstr "El fantasma con tu nick ha sido killeado." + +#: modules/commands/os_oline.cpp:19 +msgid "Give Operflags to a certain user" +msgstr "Otorga marcas de IRCOp a cierto usuario" + +#: modules/commands/cs_mode.cpp:905 +#, c-format +msgid "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." +msgstr "" +"Da status de %s al nick seleccionado en el canal. Si no se\n" +"proporciona nick te dará status de %s a ti" + +#: modules/commands/cs_mode.cpp:888 +#, c-format +msgid "Gives you or the specified nick %s status on a channel" +msgstr "Te da a ti o al nick especificado status de %s en un canal" + +#: modules/commands/greet.cpp:206 modules/commands/greet.cpp:212 +msgid "Greet" +msgstr "Saludo" + +#: src/access.cpp:38 +msgid "Greet message displayed on join" +msgstr "Mensaje de bienvenida mostrado al entrar" + +#: modules/commands/greet.cpp:112 +#, c-format +msgid "Greet message for %s changed to %s." +msgstr "Mensaje de bienvenida para %s cambiado a %s." + +#: modules/commands/greet.cpp:118 +#, c-format +msgid "Greet message for %s unset." +msgstr "Mensaje de bienvenida para %s borrado." + +#: modules/commands/greet.cpp:60 +#, c-format +msgid "Greet mode is now off on channel %s." +msgstr "Modo saludo ahora Desactivado en el canal %s." + +#: modules/commands/greet.cpp:52 +#, c-format +msgid "Greet mode is now on on channel %s." +msgstr "Modo saludo ahora Activado en el canal %s." + +#: modules/commands/ns_resetpass.cpp:21 +msgid "Helps you reset lost passwords" +msgstr "Te ayuda a restaurar contraseñas perdidas" + +#: modules/commands/ns_info.cpp:141 +msgid "Hide certain pieces of nickname information" +msgstr "Esconde algunas partes de la información del nick" + +#: modules/commands/cs_list.cpp:180 +msgid "Hide channel from the LIST command" +msgstr "Esconde el canal del comando LIST" + +#: modules/commands/os_session.cpp:192 +msgid "Host" +msgstr "Host" + +#: modules/commands/os_session.cpp:207 +#, c-format +msgid "Hosts with at least %d sessions:" +msgstr "Hosts con al menos %d sesiones:" + +#: modules/commands/cs_seen.cpp:207 +#, c-format +msgid "I don't know who %s is." +msgstr "No sé quien es %s." + +#: modules/commands/cs_seen.cpp:253 +#, c-format +msgid "I've never seen %s on this channel." +msgstr "Nunca he visto a %s en este canal." + +#: modules/commands/os_sxline.cpp:203 modules/commands/os_akill.cpp:360 +msgid "ID" +msgstr "" + +#: modules/commands/os_oper.cpp:72 +#, fuzzy +msgid "INFO [type]" +msgstr "INFO tipo" + +#: modules/commands/os_dns.cpp:218 +msgid "IP" +msgstr "IP" + +#: modules/commands/os_dns.cpp:500 +#, c-format +msgid "IP %s already exists for %s." +msgstr "La IP %s ya existe para %s." + +#: modules/commands/os_dns.cpp:562 +#, c-format +msgid "IP %s does not exist for %s." +msgstr "La IP %s no existe para %s." + +#: modules/commands/ns_identify.cpp:65 +msgid "Identify yourself with your password" +msgstr "Te identifica con tu contraseña" + +#: modules/pseudoclients/nickserv.cpp:205 +#: modules/pseudoclients/nickserv.cpp:211 +#, c-format +msgid "If you do not change within %s, I will change your nick." +msgstr "Si no lo cambias en %s, yo cambiaré tu nick." + +#: modules/commands/os_ignore.cpp:333 +msgid "Ignore list has been cleared." +msgstr "La lista de ignorados ha sido vaciada." + +#: modules/commands/os_ignore.cpp:262 +msgid "Ignore list is empty." +msgstr "La lista de ignorados está vacía." + +#: modules/commands/ms_ignore.cpp:94 +msgid "Ignore list:" +msgstr "Lista de ignorados:" + +#: modules/commands/ns_set.cpp:1305 +msgid "Immediate protection" +msgstr "Proteccion inmediata" + +#: modules/commands/ns_resetpass.cpp:33 +msgid "Incorrect email address." +msgstr "Dirección de email incorrecta." + +#: include/language.h:89 +msgid "Incorrect range specified. The correct syntax is #from-to." +msgstr "Rango especificado incorrecto. La sintaxis correcta es #desde-hasta." + +#: modules/commands/os_modinfo.cpp:19 +msgid "Info about a loaded module" +msgstr "Info sobre un módulo cargado" + +#: modules/commands/bs_info.cpp:54 +#, c-format +msgid "Information for bot %s:" +msgstr "Información para el bot %s:" + +#: include/language.h:108 +#, c-format +msgid "Information for channel %s:" +msgstr "Informacion para el canal %s:" + +#: modules/commands/os_logsearch.cpp:57 +#, c-format +msgid "Invalid duration %s, using %d days." +msgstr "Duración %s no válida, usando %d días." + +#: include/language.h:68 +msgid "Invalid expiry time." +msgstr "Tiempo de expiración no válido." + +#: modules/commands/os_session.cpp:346 +msgid "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not " +"matched against nicks or usernames." +msgstr "" +"Máscara no válida. Solo son válidos host reales, ya que las excepciones no " +"son comparadas con nicks o idents." + +#: modules/commands/os_logsearch.cpp:73 +#, c-format +msgid "Invalid limit %s, using %d." +msgstr "Límite %s no válido, usando %d." + +#: include/language.h:99 +msgid "" +"Invalid passcode has been entered, please check the e-mail again, and retry." +msgstr "" +"Se ha introducido un código no válido, por favor, revisa otra vez el email e " +"inténtalo de nuevo" + +#: modules/commands/ns_register.cpp:83 modules/commands/ns_register.cpp:86 +msgid "Invalid passcode." +msgstr "Código no válido." + +#: modules/commands/os_session.cpp:339 +#, c-format +msgid "" +"Invalid session limit. It must be a valid integer greater than or equal to " +"zero and less than %d." +msgstr "" +"Limite de sesion no válido. Debe ser un entero válido mayor o igual a cero y " +"menor a %d." + +#: modules/commands/os_session.cpp:188 +msgid "Invalid threshold value. It must be a valid integer greater than 1." +msgstr "Valor de umbral no válido. Debe ser un entero válido mayor a 1." + +#: modules/commands/os_dns.cpp:591 +msgid "Invalid value for LIMIT. Must be numerical." +msgstr "Valor no válido para LIMIT. Debe ser un número." + +#: modules/commands/cs_invite.cpp:19 +msgid "Invites you or an optionally specified nick into a channel" +msgstr "Te invita a ti u opcionalmente al nick especificado a un canal" + +#: modules/commands/bs_kick.cpp:1201 modules/commands/bs_kick.cpp:1203 +#: modules/commands/bs_kick.cpp:1206 +msgid "Italics kicker" +msgstr "Kick por cursivas" + +#: modules/commands/ns_group.cpp:91 +msgid "Join a group" +msgstr "Entrar en un grupo" + +#: modules/commands/cs_set.cpp:1305 modules/commands/ns_set.cpp:1319 +msgid "Keep modes" +msgstr "Guardar modos" + +#: modules/commands/cs_set.cpp:377 modules/commands/ns_set.cpp:603 +#, c-format +msgid "Keep modes for %s is now off." +msgstr "Guardar modos para %s Desactivado." + +#: modules/commands/cs_set.cpp:369 modules/commands/ns_set.cpp:597 +#, c-format +msgid "Keep modes for %s is now on." +msgstr "Guardar modos para %s Activado." + +#: modules/commands/ns_ajoin.cpp:100 +msgid "Key" +msgstr "Clave" + +#: modules/commands/cs_getkey.cpp:50 +#, c-format +msgid "Key for channel %s is %s." +msgstr "La clave para el canal %s es %s." + +#: modules/commands/os_kick.cpp:19 +msgid "Kick a user from a channel" +msgstr "Kickear un usuario de un canal" + +#: modules/commands/cs_ban.cpp:217 modules/commands/cs_kick.cpp:116 +#, c-format +msgid "Kicked %d/%d users matching %s from %s." +msgstr "Kickeados %d/%d usuarios que coinciden con %s en %s." + +#: modules/commands/cs_kick.cpp:19 +msgid "Kicks a specified nick from a channel" +msgstr "Kickea un nick especificado de un canal" + +#: modules/commands/cs_kick.cpp:128 +#, fuzzy +msgid "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." +msgstr "" +"Kickea al nick especificado del canal.\n" +" \n" +"Por defecto, limitado a AOPs o aquellos con nivel de\n" +"acceso 5 o superior en el canal. Los fundadores también\n" +"pueden usar máscaras." + +#: modules/commands/os_kill.cpp:19 +msgid "Kill a user" +msgstr "Expulsar a un usuario de la red" + +#: modules/commands/cs_enforce.cpp:217 +msgid "LIMIT enforced by " +msgstr "LIMIT forzado por " + +#: modules/commands/cs_enforce.cpp:221 +#, c-format +msgid "LIMIT enforced on %s, %d users removed." +msgstr "LIMIT forzado en %s, %d usuarios eliminados." + +#: modules/commands/os_session.cpp:246 +msgid "LIST threshold" +msgstr "LIST umbral" + +#: modules/commands/os_sxline.cpp:427 modules/commands/os_sxline.cpp:661 +#: modules/commands/os_akill.cpp:388 +msgid "LIST [mask | list | id]" +msgstr "LIST [máscara | lista | id]" + +#: modules/commands/os_session.cpp:525 +msgid "LIST [mask | list]" +msgstr "LIST [máscara | lista]" + +#: modules/commands/ns_access.cpp:104 modules/commands/ns_cert.cpp:260 +#: modules/commands/ns_ajoin.cpp:233 +msgid "LIST [nickname]" +msgstr "LIST [nick]" + +#: modules/commands/os_news.cpp:31 +msgid "LOGONNEWS {ADD|DEL|LIST} [text|num]" +msgstr "LOGONNEWS {ADD|DEL|LIST} [texto|número]" + +#: modules/commands/ns_set.cpp:834 +msgid "Language changed to English." +msgstr "Idioma cambiado a Español." + +#: modules/commands/ns_set.cpp:836 +#, fuzzy, c-format +msgid "Language for %s changed to %s." +msgstr "Sucesor de %s cambiado a %s." + +#: modules/commands/ms_cancel.cpp:72 +#, c-format +msgid "Last memo to %s has been cancelled." +msgstr "El último memo enviado a %s ha sido cancelado." + +#: modules/commands/ns_info.cpp:95 +msgid "Last quit message" +msgstr "Último mensaje quit" + +#: modules/commands/cs_access.cpp:472 modules/commands/ns_info.cpp:92 +msgid "Last seen" +msgstr "Última vez visto" + +#: modules/commands/ns_info.cpp:81 modules/commands/ns_info.cpp:86 +msgid "Last seen address" +msgstr "Última dirección vista" + +#: modules/commands/cs_topic.cpp:264 +msgid "Last topic" +msgstr "Último topic" + +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_info.cpp:56 +msgid "Last used" +msgstr "Usado por última vez" + +#: modules/commands/ns_list.cpp:75 +msgid "Last usermask" +msgstr "Última máscara" + +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +#: modules/commands/cs_access.cpp:697 +msgid "Level" +msgstr "Nivel" + +#: modules/commands/cs_access.cpp:660 +#, c-format +msgid "Level for %s on channel %s changed to %d." +msgstr "El nivel para %s en el canal %s cambiado a %d." + +#: modules/commands/cs_access.cpp:658 +#, c-format +msgid "Level for %s on channel %s changed to founder only." +msgstr "El nivel para %s en el canal %s cambiado a solo fundador." + +#: modules/commands/cs_access.cpp:643 +#, c-format +msgid "Level must be between %d and %d inclusive." +msgstr "El nivel debe estar entre %d y %d inclusive." + +#: modules/commands/os_dns.cpp:218 modules/commands/os_session.cpp:506 +#: modules/commands/os_session.cpp:514 +msgid "Limit" +msgstr "Límite" + +#: modules/commands/ns_list.cpp:19 +msgid "List all registered nicknames that match a given pattern" +msgstr "Listar todos los nick registrados que concuerdan con el patrón dado" + +#: modules/commands/ns_alist.cpp:24 +msgid "List channels you have access on" +msgstr "Listar canales en los que tienes acceso" + +#: modules/commands/cs_mode.cpp:341 +#, c-format +msgid "List for mode %c is full." +msgstr "La lista para el modo %c está llena." + +#: modules/commands/os_modinfo.cpp:80 +msgid "List loaded modules" +msgstr "Listar módulos cargados" + +#: modules/commands/ns_list.cpp:123 modules/commands/cs_list.cpp:72 +#, c-format +msgid "List of entries matching %s:" +msgstr "Lista de entradas que coinciden con %s:" + +#: modules/commands/ns_group.cpp:350 +#, c-format +msgid "List of nicknames in the group of %s:" +msgstr "Lista de nicks en el grupo de %s:" + +#: modules/commands/ns_group.cpp:350 +msgid "List of nicknames in your group:" +msgstr "Lista de nicks en tu grupo:" + +#: modules/commands/ms_list.cpp:19 +msgid "List your memos" +msgstr "Listar tus memos" + +#: modules/commands/bs_botlist.cpp:64 +msgid "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." +msgstr "" +"Lista todos los bot disponibles en esta red.\n" +"Los bots precedidos por un * están reservados a IRCOps." + +#: modules/commands/os_list.cpp:19 +msgid "Lists all channel records" +msgstr "Lista todos los registros de canales" + +#: modules/commands/os_list.cpp:107 +msgid "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." +msgstr "" +"Lista todos los canales actualmente en uso en la red IRC,\n" +"estén registrados o no.\n" +" \n" +"Si se proporciona patrón, lista solo los canales que concuerden\n" +"con él. Si se proporciona un nick, lista solo los canales en los que\n" +"esté el usuario. Si se especifica SECRET, lista solo los canales que\n" +"concuerden con patrón y que tengan los modos +s o +p." + +#: modules/commands/ns_alist.cpp:127 +msgid "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" +msgstr "" +"Lista todos los canales en los que tienes acceso.\n" +" \n" +"Los canales que tienen la opción NOEXPIRE activada llevarán\n" +"delante una marca de exclamación. El parámetro nick está limitado\n" +"a Operadores de Servicios" + +#: modules/commands/ns_group.cpp:299 +msgid "Lists all nicknames in your group" +msgstr "Lista todos los nicks en tu grupo" + +#: modules/commands/cs_list.cpp:20 +msgid "Lists all registered channels matching the given pattern" +msgstr "Lista todos los canales registrados que concuerdan con el patrón dado" + +#: modules/commands/cs_list.cpp:137 +msgid "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." +msgstr "" +"Lista todos los canales registrados que concuerden con el\n" +"patrón dado. Los canales con la opción PRIVATE activada\n" +"solo se mostrarán a Operadores de Servicios con el acceso\n" +"apropiado. Los canales con la opción NOEXPIRE activada\n" +"tendrán un ! delante, solo visible para Operadores de Servicios.\n" +" \n" +"Ten en cuenta que un '#' delante especifica un rango.\n" +" \n" +"Si se especifica SUSPENDED o NOEXPIRE, solo se mostrarán los canales\n" +"con las respectivas opciones activadas. Si se especifican múltiples " +"opciones,\n" +"se mostrarán todos los canales con al menos una de ellas activada. Ten en\n" +"cuenta que estas opciones están limitadas a Operadores de Servicios.\n" +" \n" +"Ejemplos:\n" +" \n" +" LIST *anope*\n" +" Lista todos los canales registrados con anope en su\n" +" nombre (no sensible a mayúsculas y minúsculas).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lista todos los canales registrados que no expirarán.\n" +" \n" +" LIST #51-100\n" +" Lista todos los canales registrados en el rango dado (51-100)." + +#: modules/commands/ns_list.cpp:139 +msgid "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." +msgstr "" +"Lista todos los nicks registrados que concuerden con el patrón\n" +"dado, en el formato nick!usuario@host. Los nicks con la opción\n" +"PRIVATE activada solo se mostrarán a Operadores de Servicios con\n" +"el acceso apropiado. Los nicks con la opción NOEXPIRE activada\n" +"tendrán un ! antes del nick, solo visible por Operadores de Servicios.\n" +" \n" +"Ten en cuenta que un '#' delante especifica un rango.\n" +" \n" +"Si se especifica SUSPENDED, UNCONFIRMED o NOEXPIRE, solo se mostrarán\n" +"los nicks con las respectivas opciones activadas. Si se especifican " +"múltiples\n" +"opciones, se mostrarán todos los nicks con al menos una de ellas activada.\n" +"Ten en cuenta que estas opciones estan limitadas a Operadores de Servicios.\n" +" \n" +"Ejemplos:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lista todos los nicks registrados propiedad de joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lista todos los nicks registrados con Bot en\n" +" sus nombres (no sensible a mayúsculas y minúsculas).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lista todos los nicks registrados que no expiren.\n" +" \n" +" LIST #51-100\n" +" Lista todos los nicks registrados en el rango dado (51-100)." + +#: modules/commands/os_list.cpp:132 +msgid "Lists all user records" +msgstr "Lista todos los registros de usuarios" + +#: modules/commands/os_list.cpp:243 +#, fuzzy +msgid "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only " +"users\n" +"with the +i flag will be listed." +msgstr "" +"Lista todos los usuarios actualmente en linea en la red IRC,\n" +"estén registrados o no.\n" +" \n" +"Si se proporciona patrón, lista solo los usuarios que concuerden\n" +"con él (debe estar en formato nick!usuario@host). Si se proporciona\n" +"canal, lista solo usuarios que estén en el canal dado. Si se especifica\n" +"INVISIBLE, solo se listarán los usuarios con el modo de usuario +i." + +#: modules/commands/ms_list.cpp:142 +msgid "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Lista los memos que tienes actualmente. Con NEW, lista\n" +"solo los memos nuevos (no leidos). Los memos nuevos están\n" +"marcados con un \"*\" a la izquierda del número del memo.\n" +"También puedes especificar una lista de números, como en el\n" +"ejemplo:\n" +" LIST 2-5,7-9\n" +" Lista los memos números 2 a 5 y 7 a 9." + +#: modules/commands/bs_botlist.cpp:19 +msgid "Lists available bots" +msgstr "Lista los bots disponibles" + +#: modules/commands/os_modinfo.cpp:196 +msgid "Lists currently loaded modules." +msgstr "Lista todos los módulos cargados." + +#: modules/commands/cs_info.cpp:19 +#, fuzzy +msgid "Lists information about the specified registered channel" +msgstr "Lista información sobre el canal registrado dado" + +#: modules/commands/cs_info.cpp:76 +#, fuzzy +msgid "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." +msgstr "" +"Lista información sobre el canal registrado dado,\n" +"incluyendo su fundador, tiempo de registro, y última vez\n" +"usado. Si el usuario tiene el acceso apropiado, también\n" +"se mostrará la descripción, el sucesor, el último topic, la\n" +"configuración y el tiempo de expiración cuando sean\n" +"aplicables." + +#: modules/commands/os_module.cpp:19 +msgid "Load a module" +msgstr "Carga un módulo" + +#: modules/commands/cs_register.cpp:39 +msgid "Local channels cannot be registered." +msgstr "Los canales locales no pueden ser registrados." + +#: modules/commands/cs_log.cpp:142 +#, c-format +msgid "Log list for %s:" +msgstr "Lista de registros para %s:" + +#: modules/commands/cs_log.cpp:227 +#, c-format +msgid "Logging changed for command %s on %s, now using log method %s%s%s." +msgstr "" +"Registro cambiado para el comando %s en %s, ahora se usa el método de " +"registro %s%s%s." + +#: modules/commands/cs_log.cpp:220 +#, c-format +msgid "Logging for command %s on %s with log method %s%s%s has been removed." +msgstr "" +"Se ha eliminado el registro para el comando %s en %s con el método de " +"registro %s%s%s." + +#: modules/commands/cs_log.cpp:248 +#, c-format +msgid "Logging is now active for command %s on %s, using log method %s%s%s." +msgstr "" +"El registro está ahora activado para el comando %s en %s, con el método de " +"registro %s%s%s." + +#: modules/commands/os_login.cpp:60 +#, c-format +msgid "Login to %s" +msgstr "Iniciar sesión en %s" + +#: modules/commands/os_news.cpp:36 +#, c-format +msgid "Logon news item #%d deleted." +msgstr "Noticia de entrada #%d borrada." + +#: modules/commands/os_news.cpp:35 +#, c-format +msgid "Logon news item #%s not found!" +msgstr "¡Noticia de entrada #%s no encontrada!" + +#: modules/commands/os_news.cpp:32 +msgid "Logon news items:" +msgstr "Noticias de entrada:" + +#: modules/commands/os_login.cpp:102 +#, c-format +msgid "Logout from %s" +msgstr "Cerrar sesión en %s" + +#: modules/commands/os_login.cpp:52 +#, c-format +msgid "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." +msgstr "" +"Inicia sesión en %s para obtener privilegios de Operador\n" +"de Servicios. Este comando puede ser innecesario si tu bloque\n" +"de operador está configurado sin una contraseña." + +#: modules/commands/os_login.cpp:94 +#, c-format +msgid "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." +msgstr "" +"Te desconecta de %s perdiendo tus privilegios de Operador\n" +"de Servicios. Este comando solo es útil si tu bloque de operador\n" +"está configurado sin una contraseña." + +#: modules/commands/cs_seen.cpp:213 +#, c-format +msgid "Looking for yourself, eh %s?" +msgstr "Buscándote a ti mismo, ¿eh %s?" + +#: modules/commands/cs_mode.cpp:773 +#, c-format +msgid "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a " +"channel.\n" +"If a mode is locked on or off, services will not allow that mode to be " +"changed. The SET\n" +"command will clear all existing mode locks and set the new one given, while " +"ADD and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * " +"and ? may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may " +"be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, " +"halfops, and voices. If what\n" +"is not given then all basic modes are removed." +msgstr "" +"Controla principalmente bloqueos de modos y modos de acceso (que es " +"diferente de los\n" +"niveles de acceso al canal) en un canal.\n" +" \n" +"El comando %s LOCK te permite añadir, borrar y ver los bloqueos de modos en " +"un canal.\n" +"Si un modo está bloqueado a encendido o apagado, los servicios no permitirán " +"que se cambie\n" +"ese modo. El comando SET limpiará todos los bloqueos existentes y " +"establecerá el nuevo dado,\n" +"mientras que ADD y DEL modificarán los bloqueos existentes.\n" +"Ejemplo:\n" +" MODE #canal LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"El comando %s SET te permite establecer modos con los servicios. Se pueden " +"usar comodines\n" +"como * y ?\n" +"Ejemplo:\n" +" MODE #canal SET +v *\n" +" Establece status de voz para todos los usuarios del canal.\n" +" \n" +" MODE #canal SET -b ~c:*\n" +" Borra todos los bans extendidos que comiencen por ~c:\n" +" \n" +"El comando %s CLEAR es una forma fácil de limpiar modos en un canal. que " +"pueden ser\n" +"bans, excepciones, ops, halfops, o voices. Si no se especifica que, se " +"eliminarán\n" +"todos los modos básicos." + +#: modules/commands/cs_akick.cpp:434 +msgid "Maintain the AutoKick list" +msgstr "Mantiene la lista de AutoKick" + +#: modules/commands/bs_bot.cpp:269 +msgid "Maintains network bot list" +msgstr "Mantiene la lista de bots de la red" + +#: modules/commands/cs_xop.cpp:522 +#, c-format +msgid "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " +msgstr "" +"Mantiene la lista %s para un canal. Los usuarios que coinciden con una\n" +"entrada de la lista %s reciben los siguientes privilegios:\n" +" " + +#: modules/commands/cs_akick.cpp:493 +#, c-format +msgid "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" +msgstr "" +"Mantiene la lista AutoKick para un canal. Si un usuario\n" +"en la lista AutoKick intenta entrar al canal, %s lo\n" +"baneará y luego lo kickeará.\n" +" \n" +"El comando AKICK ADD añade el nick o máscara dados\n" +"a la lista AutoKick. Si se especifica una razón con el comando,\n" +"se usará dicha razón al kickear al usuario; si no, la razón por\n" +"defecto será \"El usuario ha sido baneado del canal\".\n" +"Cuando se especifica un nick registrado, se añadirá a la\n" +"lista la cuenta de %s en vez de la máscara; es decir, todos\n" +"los usuarios en el grupo serán también kickeados.\n" + +#: modules/commands/cs_access.cpp:568 +#, c-format +msgid "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." +msgstr "" +"Mantiene la lista de acceso para un canal. La lista de\n" +"acceso especifica que usuarios pueden tener acceso al\n" +"status de operador o a los comandos %s. Diferentes niveles\n" +"permiten el acceso a diferentes subconjuntos de privilegios.\n" +"Cualquier usuario que no esté en la lista de acceso tendrá\n" +"nivel 0, y cualquier usuario no registrado tendrá nivel -1." + +#: modules/commands/bs_badwords.cpp:424 +#, c-format +msgid "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" +msgstr "" +"Mantiene la lista de bad words para un canal. La lista\n" +"de bad words determina que palabras deben ser kickeadas\n" +"cuando el kick por bad words está habilitado. Para más\n" +"información, escribe %s%s HELP KICK %s.\n" +"\n" +"El comando ADD añade una palabra a la lista\n" +"de bad words. Si se especifica SINGLE, se dará kick\n" +"solo si el usuario dice la palabra completa. Si se\n" +"especifica START, el kick se producirá solo si el\n" +"usuario dice una palabra que comience con palabra.\n" +"Si se especifica END, el kick se producirá solo si el\n" +"usuario dice una palabra que termine con palabra. Si\n" +"no especificas nada, habrá un kick cada vez que\n" +"palabra sea dicho por un usuario.\n" +"\n" + +#: modules/commands/bs_badwords.cpp:370 +msgid "Maintains the bad words list" +msgstr "Mantiene lista de bad words" + +#: modules/commands/bs_control.cpp:79 +msgid "Makes the bot do the equivalent of a \"/me\" command" +msgstr "Hace que el bot haga el equivalente al comando \"/me\" " + +#: modules/commands/bs_control.cpp:127 +#, fuzzy +msgid "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." +msgstr "" +"Hace que el bot haga el equivalente al comando \"/me\" \n" +"en el canal dado usando el texto dado." + +#: modules/commands/bs_control.cpp:19 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel" +msgstr "Hace que el bot diga el texto dado en el canal dado" + +#: modules/commands/bs_control.cpp:69 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel." +msgstr "Hace que el bot diga el texto dado en el canal dado." + +#: modules/commands/greet.cpp:157 +msgid "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." +msgstr "" +"Convierte el mensaje dado en el saludo del nick, el cual\n" +"será mostrado al entrar a un canal que tenga la opción\n" +"GREET habilitada, siempre que el usuario tenga acceso\n" +"suficiente en dicho canal." + +#: modules/commands/greet.cpp:131 +msgid "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." +msgstr "" +"Convierte el mensaje dado en el saludo de tu nick, el cual\n" +"será mostrado al entrar a un canal que tenga la opción\n" +"GREET habilitada, siempre que tengas acceso suficiente\n" +"en dicho canal." + +#: modules/commands/os_dns.cpp:660 +msgid "Manage DNS zones for this network" +msgstr "Administra las zonas DNS para esta red" + +#: modules/commands/cs_entrymsg.cpp:193 +msgid "Manage the channel's entry messages" +msgstr "Administrar los mensajes de entrada al canal" + +#: modules/commands/ms_ignore.cpp:19 +msgid "Manage the memo ignore list" +msgstr "Administra la lista de ignorados en los memos" + +#: modules/commands/ns_ajoin.cpp:230 +msgid "Manage your auto join list" +msgstr "Administra tu lista de auto join" + +#: modules/commands/os_sxline.cpp:233 +#, c-format +msgid "Manipulate the %s list" +msgstr "Manipula la lista %s" + +#: modules/commands/os_akill.cpp:385 +msgid "Manipulate the AKILL list" +msgstr "Manipula la lista AKILL" + +#: modules/commands/os_defcon.cpp:176 +msgid "Manipulate the DefCon system" +msgstr "Manipula el sistema DefCon" + +#: modules/commands/cs_topic.cpp:149 +msgid "Manipulate the topic of the specified channel" +msgstr "Manipula el topic del canal especificado" + +#: modules/commands/bs_botlist.cpp:27 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_forbid.cpp:358 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/ms_ignore.cpp:86 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_list.cpp:153 modules/commands/bs_info.cpp:55 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +msgid "Mask" +msgstr "Máscara" + +#: modules/commands/ns_access.cpp:39 +#, c-format +msgid "Mask %s already present on %s's access list." +msgstr "La máscara %s ya está presente en la lista de acceso de %s." + +#: include/language.h:67 +msgid "Mask must be in the form user@host." +msgstr "La máscara debe ser en formato usuario@host" + +#: modules/commands/cs_access.cpp:166 modules/commands/cs_flags.cpp:120 +#: modules/commands/cs_xop.cpp:162 +msgid "Masks and unregistered users may not be on access lists." +msgstr "" +"Las listas de acceso no pueden contener máscaras o usuarios no registrados." + +#: modules/commands/ns_getemail.cpp:23 +msgid "Matches and returns all users that registered using given email" +msgstr "Devuelve todos los usuarios que se registraron usando el email dado" + +#: modules/commands/os_logsearch.cpp:148 +#, c-format +msgid "Matches for %s:" +msgstr "Coincidencias para %s:" + +#: modules/commands/os_stats.cpp:139 +#, c-format +msgid "Maximum users: %d (%s)" +msgstr "Máximo número de usuarios: %d (%s)" + +#: modules/commands/ms_read.cpp:84 modules/commands/ms_read.cpp:86 +#, c-format +msgid "Memo %d from %s (%s)." +msgstr "Memo %d de %s (%s)." + +#: modules/commands/ms_del.cpp:33 modules/commands/ms_del.cpp:101 +#, c-format +msgid "Memo %d has been deleted." +msgstr "El memo %d ha sido borrado." + +#: modules/commands/ms_ignore.cpp:82 +msgid "Memo ignore list is empty." +msgstr "La lista de ignorados está vacía." + +#: modules/commands/ms_set.cpp:199 +#, c-format +msgid "Memo limit disabled for %s." +msgstr "Límite de memos para %s deshabilitado." + +#: modules/commands/ms_set.cpp:185 +#, c-format +msgid "Memo limit for %s set to %d." +msgstr "Límite de memos para %s establecido a %d." + +#: modules/commands/ms_set.cpp:192 +#, c-format +msgid "Memo limit for %s set to 0." +msgstr "Límite de memos para %s establecido a 0." + +#: modules/commands/ms_rsend.cpp:63 modules/commands/ms_send.cpp:51 +#, c-format +msgid "Memo sent to %s." +msgstr "Memo enviado a %s." + +#: modules/commands/ms_list.cpp:131 +#, c-format +msgid "Memos for %s:" +msgstr "Memos para %s:" + +#: modules/commands/cs_entrymsg.cpp:116 +msgid "Message" +msgstr "Mensaje" + +#: modules/commands/ns_set.cpp:1313 +msgid "Message mode" +msgstr "Modo de mensaje" + +#: modules/commands/cs_log.cpp:127 +msgid "Method" +msgstr "Método" + +#: modules/commands/cs_mode.cpp:329 modules/commands/cs_mode.cpp:420 +#, c-format +msgid "Missing parameter for mode %c." +msgstr "Falta un parámetro para el modo %c." + +#: modules/commands/cs_mode.cpp:449 +msgid "Mode" +msgstr "Modo" + +#: modules/commands/cs_mode.cpp:718 +#, fuzzy, c-format +msgid "Mode %s is a virtual mode and can't be cleared." +msgstr "El nick %ses un nick ilegal, y no puede ser usado." + +#: modules/commands/cs_mode.cpp:712 +#, c-format +msgid "Mode %s is not a status or list mode." +msgstr "El modo %s no es un modo de status." + +#: modules/commands/cs_mode.cpp:1065 +msgid "Mode lock" +msgstr "Bloqueo de modos" + +#: modules/commands/cs_mode.cpp:466 +#, c-format +msgid "Mode locks for %s:" +msgstr "Modos bloqueado para %s:" + +#: modules/commands/os_list.cpp:43 +msgid "Modes" +msgstr "Modos" + +#: modules/commands/os_mode.cpp:44 +#, fuzzy, c-format +msgid "Modes cleared on %s and the channel destroyed." +msgstr "%d canale(s) limpiado(s), y %d canale(s) borrado(s)." + +#: modules/commands/ns_access.cpp:166 +#, c-format +msgid "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." +msgstr "" +"Modifica o muestra la lista de acceso para tu nick. Esta\n" +"es la lista de direcciones que serán automáticamente\n" +"reconocidas por %s como autorizadas a usar el nick. Si\n" +"quieres usar el nick desde una direccion diferente,\n" +"debes enviar un comando IDENTIFY para hacer que %s\n" +"te reconozca. Los Operadores de Servicios pueden\n" +"especificar un nick para modificar la lista de otros usuarios.\n" +" \n" +"Ejemplos:\n" +" \n" +" ACCESS ADD alguien@*.bepeg.com\n" +" Permite acceso al usuario alguien desde\n" +" cualquier maquina en el dominio bepeg.com.\n" +" \n" +" ACCESS DEL alguien@*.bepeg.com\n" +" Revierte el comando anterior.\n" +" \n" +" ACCESS LIST\n" +" Muestra la lista de acceso actual." + +#: modules/commands/ns_cert.cpp:319 +#, fuzzy +msgid "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" +msgstr "" +"Modifica o muestra la lista de certificados para tu nick.\n" +"Si conectas al IRC y proporcionas un certificado de cliente\n" +"con una huella que coincida con alguna entrada de la lista,\n" +"tu nick será identificado automáticamente por los servicios.\n" +" \n" + +#: modules/commands/os_ignore.cpp:341 +msgid "Modify the Services ignore list" +msgstr "Modificar la lista de ignorados por los Servicios" + +#: modules/commands/cs_xop.cpp:489 +#, c-format +msgid "Modify the list of %s users" +msgstr "Modificar la lista de usuarios %s" + +#: modules/commands/ns_access.cpp:101 +msgid "Modify the list of authorized addresses" +msgstr "Modificar la lista de direcciones autorizadas" + +#: modules/commands/cs_access.cpp:498 modules/commands/cs_flags.cpp:373 +msgid "Modify the list of privileged users" +msgstr "Modificar la lista de usuarios privilegiados" + +#: modules/commands/ns_cert.cpp:257 +msgid "Modify the nickname client certificate list" +msgstr "Modificar la lista de certificados del nick" + +#: modules/commands/os_session.cpp:522 +msgid "Modify the session-limit exception list" +msgstr "Modifica la lista de excepciones al límite de sesión" + +#: modules/commands/os_module.cpp:34 +#, c-format +msgid "Module %s is already loaded." +msgstr "El módule %s ya está cargado." + +#: modules/commands/os_module.cpp:67 modules/commands/os_module.cpp:139 +#, c-format +msgid "Module %s isn't loaded." +msgstr "El módulo %s no está cargado." + +#: modules/commands/os_module.cpp:31 +#, c-format +msgid "Module %s loaded." +msgstr "Módulo %s cargado." + +#: modules/commands/os_module.cpp:98 +#, c-format +msgid "Module %s reloaded." +msgstr "Módulo %s recargado ." + +#: modules/commands/os_module.cpp:156 +#, c-format +msgid "Module %s unloaded." +msgstr "Módulo %s descargado." + +#: modules/commands/os_config.cpp:88 +msgid "Module Name" +msgstr "Nombre del módule" + +#: modules/commands/os_config.cpp:112 +msgid "Module settings:" +msgstr "Configuración del módulo:" + +#: modules/commands/os_modinfo.cpp:32 +#, c-format +msgid "Module: %s Version: %s Author: %s Loaded: %s" +msgstr "Módulo: %s Versión: %s Autor: %s Cargado: %s" + +#: modules/commands/os_modinfo.cpp:183 +#, c-format +msgid "Module: %s [%s] [%s]" +msgstr "Módulo: %s [%s] [%s]" + +#: modules/commands/cs_access.cpp:697 modules/commands/cs_access.cpp:799 +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +#: modules/commands/cs_list.cpp:75 modules/commands/os_list.cpp:43 +#: modules/commands/os_list.cpp:153 +msgid "Name" +msgstr "Nombre" + +#: modules/commands/os_oper.cpp:153 +msgid "Name Type" +msgstr "Nombre Tipo" + +#: modules/extra/stats/cs_fantasy_stats.cpp:146 +#, c-format +msgid "Network stats for %s:" +msgstr "Estadísticas de red para %s:" + +#: modules/commands/os_forbid.cpp:384 +msgid "Never" +msgstr "Nunca" + +#: modules/commands/hs_list.cpp:58 modules/commands/bs_botlist.cpp:27 +#: modules/commands/hs_request.cpp:305 modules/commands/ns_list.cpp:75 +#: modules/commands/ns_group.cpp:327 +msgid "Nick" +msgstr "Nick" + +#: modules/commands/ns_register.cpp:42 +#, c-format +msgid "Nick %s has been confirmed." +msgstr "El nick %s ha sido confirmado." + +#: modules/commands/os_oper.cpp:95 +#, c-format +msgid "Nick %s is already an operator." +msgstr "El nick %s ya es un operador." + +#: modules/commands/ns_register.cpp:36 +#, c-format +msgid "Nick %s is already confirmed." +msgstr "El nick %s ya está confirmado." + +#: modules/commands/os_svs.cpp:46 +#, c-format +msgid "Nick %s is an illegal nickname and cannot be used." +msgstr "El nick %ses un nick ilegal, y no puede ser usado." + +#: modules/commands/bs_bot.cpp:81 modules/commands/bs_bot.cpp:181 +#: modules/commands/os_svs.cpp:54 +#, c-format +msgid "Nick %s is currently in use." +msgstr "El nick %s está actualmente en uso." + +#: modules/commands/os_forbid.cpp:512 +#, c-format +msgid "Nick %s is forbidden by %s: %s" +msgstr "El nick %s está prohibido por %s: %s" + +#: modules/commands/os_forbid.cpp:514 +#, c-format +msgid "Nick %s is forbidden." +msgstr "El nick %s está prohibido." + +#: modules/commands/os_oper.cpp:134 +#, c-format +msgid "Nick %s is not a Services Operator." +msgstr "El nick %s no es un Operador de Servicios." + +#: modules/commands/ns_info.cpp:34 +#, c-format +msgid "Nick %s is part of this Network's Services." +msgstr "El nick %s es parte de los Servicios de esta Red." + +#: include/language.h:79 +#, c-format +msgid "Nick %s isn't currently in use." +msgstr "El nick %s no está actualmente en uso." + +#: include/language.h:78 +#, c-format +msgid "Nick %s isn't registered." +msgstr "El nick %s no está registrado." + +#: modules/commands/os_svs.cpp:39 +#, c-format +msgid "Nick %s was truncated to %d characters." +msgstr "El nick %s fue reducido a %d caracteres." + +#: modules/commands/ns_set.cpp:1135 +#, c-format +msgid "Nick %s will expire." +msgstr "El nick %s sí expirará." + +#: modules/commands/ns_set.cpp:1129 +#, c-format +msgid "Nick %s will not expire." +msgstr "El nick %s no expirará." + +#: modules/commands/ms_check.cpp:60 +#, c-format +msgid "Nick %s doesn't have a memo from you." +msgstr "El nick %s no ha recibido ningun memo tuyo." + +#: modules/commands/ns_logout.cpp:48 +#, c-format +msgid "Nick %s has been logged out." +msgstr "El nick %s ha sido desconectado." + +#: modules/commands/ns_group.cpp:272 +#, c-format +msgid "Nick %s has been ungrouped from %s." +msgstr "El nick %s ha sido desagrupado de %s." + +#: include/language.h:81 +#, c-format +msgid "Nick %s is currently suspended." +msgstr "El nick %s está actualmente suspendido." + +#: modules/commands/ns_group.cpp:250 +#, c-format +msgid "Nick %s is not in your group." +msgstr "El nick %s no está en tu grupo." + +#: modules/commands/ns_suspend.cpp:180 +#, c-format +msgid "Nick %s is not suspended." +msgstr "El nick %s no está suspendido." + +#: modules/commands/ns_suspend.cpp:190 +#, c-format +msgid "Nick %s is now released." +msgstr "El nick %s ahora está liberado." + +#: modules/commands/ns_suspend.cpp:138 +#, c-format +msgid "Nick %s is now suspended." +msgstr "El nick %s ahora está suspendido." + +#: modules/commands/cs_seen.cpp:275 +#, c-format +msgid "Nick too long, max length is %u characters." +msgstr "Nick demasiado largo, la longitud máxima es %u caracteres." + +#: modules/commands/ns_drop.cpp:53 +#, c-format +msgid "Nickname %s has been dropped." +msgstr "El nick %s ha sido borrado." + +#: include/language.h:97 +#, c-format +msgid "Nickname %s is already registered!" +msgstr "¡El nick %s ya está registrado!" + +#: include/language.h:96 +#, c-format +msgid "Nickname %s may not be registered." +msgstr "El nick %s no puede ser registrado." + +#: modules/commands/ns_register.cpp:226 +#, c-format +msgid "Nickname %s registered under your user@host-mask: %s" +msgstr "Nick %s registrado bajo tu máscara usuario@host: %s" + +#: modules/commands/ns_register.cpp:228 +#, c-format +msgid "Nickname %s registered." +msgstr "Nick %s registrado." + +#: modules/commands/cs_set.cpp:1307 +msgid "No auto-op" +msgstr "No auto-op" + +#: modules/commands/bs_assign.cpp:252 +msgid "No bot" +msgstr "No hay bot" + +#: modules/commands/cs_set.cpp:1303 modules/commands/ns_set.cpp:1317 +msgid "No expire" +msgstr "No expira" + +#: modules/commands/help.cpp:184 +#, c-format +msgid "No help available for %s." +msgstr "No existe ayuda para %s." + +#: modules/commands/os_modinfo.cpp:61 +#, c-format +msgid "No information about module %s is available." +msgstr "No hay informacion disponible para el módulo %s" + +#: modules/commands/cs_enforce.cpp:177 +#, c-format +msgid "No limit is set on %s." +msgstr "No se han establecido límites en %s." + +#: modules/commands/os_news.cpp:37 +msgid "No logon news items to delete!" +msgstr "¡No hay noticias de entrada para borrar!" + +#: modules/commands/os_logsearch.cpp:133 +#, c-format +msgid "No matches for %s found." +msgstr "No se encontraron coincidencias para %s." + +#: modules/commands/cs_xop.cpp:294 +#, c-format +msgid "No matching entries on %s %s list." +msgstr "No hay entradas que coincidan en la lista de %s de %s." + +#: modules/commands/cs_access.cpp:269 modules/commands/cs_access.cpp:433 +#: modules/commands/cs_flags.cpp:335 modules/commands/cs_xop.cpp:428 +#, c-format +msgid "No matching entries on %s access list." +msgstr "No hay entradas que concuerden en la lista de acceso de %s ." + +#: modules/commands/cs_akick.cpp:224 modules/commands/cs_akick.cpp:368 +#, c-format +msgid "No matching entries on %s autokick list." +msgstr "" +"No hay entradas que concuerden en la lista de kicks automaticos en el canal " +"%s." + +#: modules/commands/bs_badwords.cpp:166 modules/commands/bs_badwords.cpp:246 +#, c-format +msgid "No matching entries on %s bad words list." +msgstr "No existen palabras que concuerden en la lista de bad words de %s." + +#: modules/commands/os_session.cpp:145 modules/commands/os_session.cpp:490 +msgid "No matching entries on session-limit exception list." +msgstr "" +"No hay entradas que concuerden en la lista de excepciones al límite de " +"sesiones." + +#: modules/commands/os_sxline.cpp:28 modules/commands/os_sxline.cpp:177 +#, c-format +msgid "No matching entries on the %s list." +msgstr "No hay entradas que coincidan en la lista de %s." + +#: modules/commands/os_akill.cpp:29 modules/commands/os_akill.cpp:320 +msgid "No matching entries on the AKILL list." +msgstr "No hay entradas que concuerden en la lista de AKILLs." + +#: modules/commands/ms_cancel.cpp:77 +msgid "No memo was cancelable." +msgstr "¡Ningun memo pudo ser cancelado." + +#: modules/commands/ms_read.cpp:65 +#, fuzzy +msgid "No memos to display." +msgstr "No hay registros para mostrar." + +#: modules/commands/os_modinfo.cpp:187 +msgid "No modules currently loaded matching that criteria." +msgstr "Actualmente no hay módulos cargados que coincidan con ese patrón." + +#: modules/commands/ns_recover.cpp:55 +msgid "No one is using your nick, and services are not holding it." +msgstr "Nadie está usando tu nick, y los servicios no lo están reteniendo." + +#: modules/commands/os_login.cpp:30 modules/commands/os_login.cpp:77 +msgid "No oper block for your nick." +msgstr "Tu nick no está en ningún bloque de operador." + +#: modules/commands/os_news.cpp:47 +msgid "No oper news items to delete!" +msgstr "¡No hay noticias de oper para borrar!" + +#: modules/commands/os_news.cpp:57 +msgid "No random news items to delete!" +msgstr "¡No hay noticias al azar para borrar!" + +#: modules/commands/hs_list.cpp:111 +msgid "No records to display." +msgstr "No hay registros para mostrar." + +#: modules/commands/ns_getemail.cpp:47 +#, fuzzy, c-format +msgid "No registrations matching %s were found." +msgstr "No se encontraron nicks registrados que concuerden con %s." + +#: modules/commands/hs_request.cpp:220 modules/commands/hs_request.cpp:276 +#, c-format +msgid "No request for nick %s found." +msgstr "No se encontraron peticiones para el nick %s." + +#: src/access.cpp:55 +msgid "No signed kick when SIGNKICK LEVEL is used" +msgstr "No se firman los kicks cuando se usa SIGNKICK LEVEL" + +#: modules/extra/stats/cs_fantasy_top.cpp:159 +#: modules/extra/stats/cs_fantasy_stats.cpp:156 +#, c-format +msgid "No stats for %s." +msgstr "No hay estadísticas para %s." + +#: modules/commands/os_info.cpp:201 +#, c-format +msgid "No such info \"%s\" on %s." +msgstr "No existe la información \"%s\" en %s." + +#: modules/commands/cs_ban.cpp:219 modules/commands/cs_kick.cpp:118 +#, c-format +msgid "No users on %s match %s." +msgstr "Ningún usuario en %s concuerda con %s." + +#: modules/commands/bs_assign.cpp:188 +#, c-format +msgid "No-bot mode is now off on channel %s." +msgstr "El modo no bot está ahora Desactivado en el canal %s." + +#: modules/commands/bs_assign.cpp:181 +#, c-format +msgid "No-bot mode is now on on channel %s." +msgstr "El modo no bot está ahora Activado en el canal %s." + +#: modules/commands/os_mode.cpp:64 +#, c-format +msgid "Non-status modes cleared on %s." +msgstr "Modos no-status borrados en %s" + +#: modules/commands/os_dns.cpp:226 modules/commands/bs_info.cpp:58 +msgid "None" +msgstr "Ninguno" + +#: modules/commands/cs_set.cpp:1029 +#, fuzzy, c-format +msgid "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." +msgstr "" +"Sin embargo, si el sucesor ya tiene muchos canales\n" +"registrados (%d), el canal se borrará como si no hubiese\n" +"un sucesor." + +#: modules/commands/cs_mode.cpp:380 modules/commands/cs_mode.cpp:437 +msgid "Nothing to do." +msgstr "Nada que hacer." + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:201 modules/commands/ms_list.cpp:64 +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_log.cpp:127 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +#: modules/commands/ns_ajoin.cpp:100 +msgid "Number" +msgstr "Número" + +#: modules/commands/os_news.cpp:41 +msgid "OPERNEWS {ADD|DEL|LIST} [text|num]" +msgstr "OPERNEWS {ADD|DEL|LIST} [texto|número]" + +#: modules/commands/ns_info.cpp:68 modules/commands/ns_info.cpp:72 +msgid "Online from" +msgstr "En línea desde" + +#: modules/commands/os_oper.cpp:138 +#, fuzzy, c-format +msgid "" +"Oper %s is configured in the configuration file(s) and can not be removed by " +"this command." +msgstr " Este operador está definido en el archivo de configuración." + +#: modules/commands/os_info.cpp:268 +msgid "Oper Info" +msgstr "Información de Operador" + +#: modules/commands/os_info.cpp:182 modules/commands/os_info.cpp:221 +#, c-format +msgid "Oper info list for %s is empty." +msgstr "La lista de información de oper para %s está vacía." + +#: modules/commands/os_news.cpp:46 +#, c-format +msgid "Oper news item #%d deleted." +msgstr "Noticia de oper #%d borrada." + +#: modules/commands/os_news.cpp:45 +#, c-format +msgid "Oper news item #%s not found!" +msgstr "¡Noticia de oper #%s no encontrada!" + +#: modules/commands/os_news.cpp:42 +msgid "Oper news items:" +msgstr "Noticias de oper:" + +#: modules/commands/os_oper.cpp:148 +#, c-format +msgid "Oper privileges removed from %s (%s)." +msgstr "Privilegios de Oper eliminados para %s (%s)." + +#: modules/commands/os_oper.cpp:101 modules/commands/os_oper.cpp:189 +#, c-format +msgid "Oper type %s has not been configured." +msgstr "El tipo de operador %s no ha sido configurado." + +#: modules/commands/os_oline.cpp:37 +#, c-format +msgid "Operflags %s have been added for %s." +msgstr "Se han añadido los marcas de IRCOp %s para %s." + +#: modules/commands/os_oline.cpp:43 +#, c-format +msgid "Operflags %s have been removed from %s." +msgstr "Las marcas de IRCOp %s se han eliminado para %s." + +#: modules/commands/os_oper.cpp:193 +#, c-format +msgid "Opertype %s has no allowed commands." +msgstr "El Operador de tipo %s no tiene comandos permitidos." + +#: modules/commands/os_oper.cpp:215 +#, c-format +msgid "Opertype %s has no allowed privileges." +msgstr "El Operador de tipo %s no tiene privilegios permitidos." + +#: modules/commands/os_oper.cpp:237 +#, c-format +msgid "Opertype %s receives modes %s once identified." +msgstr "El Operador de tipo %s recibe los modos %s una vez identificado." + +#: modules/commands/bs_kick.cpp:1219 +msgid "Ops protection" +msgstr "Proteccion de Ops" + +#: src/misc.cpp:258 modules/commands/bs_info.cpp:58 +msgid "Options" +msgstr "Opciones" + +#: modules/commands/os_dns.cpp:668 +msgid "POOL server.name" +msgstr "POOL nombre-de-servidor" + +#: modules/commands/cs_mode.cpp:449 +msgid "Param" +msgstr "Parámetro" + +#: modules/commands/ns_identify.cpp:38 +msgid "Password accepted - you are now recognized." +msgstr "Contraseña aceptada - Has sido reconocido." + +#: modules/commands/os_login.cpp:44 +msgid "Password accepted." +msgstr "Contraseña aceptada." + +#: include/language.h:85 +msgid "Password authentication required for that command." +msgstr "Este comando requiere identificación por contraseña" + +#: modules/commands/ns_set.cpp:152 modules/commands/ns_set.cpp:218 +#, c-format +msgid "Password for %s changed to %s." +msgstr "Contraseña de %s cambiada a %s." + +#: modules/commands/ns_set.cpp:154 modules/commands/ns_set.cpp:220 +#, c-format +msgid "Password for %s changed." +msgstr "Contraseña de %s cambiada." + +#: modules/commands/ns_getpass.cpp:38 +#, c-format +msgid "Password for %s is %s." +msgstr "La contraseña para %s es %s." + +#: include/language.h:71 +msgid "Password incorrect." +msgstr "Contraseña incorrecta." + +#: modules/commands/ns_resetpass.cpp:39 +#, c-format +msgid "Password reset email for %s has been sent." +msgstr "Ha sido enviado un email de restablecimiento de contraseña para %s." + +#: modules/commands/cs_set.cpp:1289 +msgid "Peace" +msgstr "Paz" + +#: modules/commands/cs_set.cpp:440 +#, c-format +msgid "Peace option for %s is now off." +msgstr "Opción de paz para %s Desactivada." + +#: modules/commands/cs_set.cpp:434 +#, c-format +msgid "Peace option for %s is now on." +msgstr "Opción de paz para %s Activada." + +#: modules/commands/cs_set.cpp:1301 +msgid "Persistent" +msgstr "Persistente" + +#: include/language.h:126 +msgid "Please contact an Operator to get a vHost assigned to this nick." +msgstr "" +"Por favor, contacta con un Operador para tener un vHost asignado a este nick." + +#: include/language.h:73 +msgid "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." +msgstr "" +"Por favor, inténtalo de nuevo con una contraseña más difícil. Las " +"contraseñas\n" +"deben tener por lo menos cinco caracteres y no ser fácilmente adivinables\n" +"(p.e., tu nombre real o tu nick), y no pueden contener espacios o " +"tabulaciones." + +#: modules/commands/os_jupe.cpp:30 +msgid "Please use a valid server name when juping." +msgstr "Por favor usa un nombre de servidor valido cuando lo jupitees." + +#: include/language.h:104 +msgid "Please use the symbol of # when attempting to register." +msgstr "Por favor, usa el símbolo # cuando intentes registrar un canal." + +#: src/mail.cpp:78 +#, c-format +msgid "Please wait %d seconds and retry." +msgstr "Por favor, espera %d segundos e inténtalo de nuevo." + +#: modules/commands/hs_request.cpp:158 +#, c-format +msgid "Please wait %d seconds before requesting a new vHost." +msgstr "Por favor, espera %d segundos antes de solicitar un nuevo vHost." + +#: modules/commands/ms_rsend.cpp:58 modules/commands/ms_send.cpp:57 +#, c-format +msgid "Please wait %d seconds before using the %s command again." +msgstr "" +"Por favor, espera %d segundos antes de utilizar el comando %s nuevamente." + +#: modules/commands/ns_group.cpp:149 +#, c-format +msgid "Please wait %d seconds before using the GROUP command again." +msgstr "" +"Por favor, espera %d segundos antes de usar el comando GROUP nuevamente." + +#: modules/commands/ns_register.cpp:198 +#, c-format +msgid "Please wait %d seconds before using the REGISTER command again." +msgstr "" +"Por favor, espera %d segundos antes de usar el comando REGISTER nuevamente." + +#: modules/commands/os_dns.cpp:628 +#, c-format +msgid "Pooled %s." +msgstr "%s añadido al pool dns." + +#: modules/commands/os_dns.cpp:237 +msgid "Pooled/Active" +msgstr "En el pool/Activo" + +#: modules/commands/os_dns.cpp:239 +msgid "Pooled/Not Active" +msgstr "En el pool/No Activo" + +#: modules/commands/bs_set.cpp:161 +msgid "Prevent a bot from being assigned by non IRC operators" +msgstr "Evita que un bot sea asignado por usuarios que no son IRCOps" + +#: modules/commands/bs_assign.cpp:153 +msgid "Prevent a bot from being assigned to a channel" +msgstr "Evita que un bot sea asignado a un canal" + +#: modules/commands/cs_suspend.cpp:58 +msgid "Prevent a channel from being used preserving channel data and settings" +msgstr "Evita que un canal sea usado conservando toda su configuración" + +#: modules/commands/cs_set.cpp:1043 +msgid "Prevent the channel from expiring" +msgstr "Evita que el canal expire" + +#: modules/commands/ns_list.cpp:186 +msgid "Prevent the nickname from appearing in the LIST command" +msgstr "Evita que el nick aparezca en el comando LIST" + +#: modules/commands/ns_set.cpp:1104 +msgid "Prevent the nickname from expiring" +msgstr "Evita que el nick expire" + +#: src/access.cpp:46 +msgid "Prevents users being kicked by Services" +msgstr "Evita que los usuarios sean kickeados por los Servicios" + +#: modules/commands/ns_list.cpp:297 modules/commands/cs_list.cpp:262 +#: modules/commands/bs_info.cpp:58 +msgid "Private" +msgstr "Privado" + +#: modules/commands/bs_set.cpp:190 +#, c-format +msgid "Private mode of bot %s is now off." +msgstr "El modo privado del bot %s está ahora Desactivado." + +#: modules/commands/bs_set.cpp:185 +#, c-format +msgid "Private mode of bot %s is now on." +msgstr "El modo privado del bot %s está ahora Activado." + +#: modules/commands/cs_list.cpp:220 +#, c-format +msgid "Private option for %s is now off." +msgstr "Privacidad para %s Desactivada." + +#: modules/commands/cs_list.cpp:214 +#, c-format +msgid "Private option for %s is now on." +msgstr "Privacidad para %s Activada." + +#: modules/commands/ns_list.cpp:221 +#, c-format +msgid "Private option is now off for %s." +msgstr "Privacidad Desactivada para %s." + +#: modules/commands/ns_list.cpp:215 +#, c-format +msgid "Private option is now on for %s." +msgstr "Privacidad Activada para %s." + +#: modules/commands/cs_flags.cpp:281 +#, c-format +msgid "Privilege %s added to %s on %s, new flags are +%s" +msgstr "Privilegios de %s dados a %s en %s, las nuevas marcas son +%s" + +#: modules/commands/cs_flags.cpp:283 +#, c-format +msgid "Privilege %s removed from %s on %s, new flags are +%s" +msgstr "Privilegios de %s quitados a %s en %s, las nuevas marcas son +%s" + +#: modules/commands/ns_set.cpp:1309 +msgid "Protection" +msgstr "Protección" + +#: modules/commands/ns_set.cpp:721 +#, c-format +msgid "Protection is now off for %s." +msgstr "La protección para %sahora está Desactivada." + +#: modules/commands/ns_set.cpp:700 +#, c-format +msgid "Protection is now on for %s, with a reduced delay." +msgstr "" +"La protección está ahora Activada para %s, con tiempo de espera reducido." + +#: modules/commands/ns_set.cpp:710 +#, c-format +msgid "Protection is now on for %s, with no delay." +msgstr "La protección está ahora Activada para %s, sin tiempo de espera." + +#: modules/commands/ns_set.cpp:692 +#, c-format +msgid "Protection is now on for %s." +msgstr "La protección para %sahora está Activada." + +#: modules/commands/os_chankill.cpp:100 +msgid "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." +msgstr "" +"Pone un AKILL para cada nick en el canal especificado. Usa\n" +"la máscara completa ident@host para cada nick, luego\n" +"fuerza el AKILL." + +#: modules/commands/ns_set.cpp:1307 +msgid "Quick protection" +msgstr "Proteccion rápida" + +#: modules/commands/os_news.cpp:51 +msgid "RANDOMNEWS {ADD|DEL|LIST} [text|num]" +msgstr "RANDOMNEWS {ADD|DEL|LIST} [texto|número]" + +#: modules/commands/cs_enforce.cpp:99 +msgid "REGONLY enforced by " +msgstr "REGONLY forzado por " + +#: modules/commands/cs_enforce.cpp:68 +msgid "RESTRICTED enforced by " +msgstr "RESTRICTED forzado por " + +#: modules/commands/os_noop.cpp:21 +msgid "REVOKE server" +msgstr "REVOKE servidor" + +#: modules/commands/os_news.cpp:56 +#, c-format +msgid "Random news item #%d deleted." +msgstr "Noticia al azar #%d borrada." + +#: modules/commands/os_news.cpp:55 +#, c-format +msgid "Random news item #%s not found!" +msgstr "¡Noticia al azar #%s no encontrada!" + +#: modules/commands/os_news.cpp:52 +msgid "Random news items:" +msgstr "Noticias al Azar:" + +#: modules/commands/ms_read.cpp:112 +msgid "Read a memo or memos" +msgstr "Leer un memo o memos" + +#: modules/commands/bs_info.cpp:56 +msgid "Real name" +msgstr "Nombre real" + +#: modules/commands/os_list.cpp:153 +#, fuzzy +msgid "Realname" +msgstr "Nombre real" + +#: modules/commands/os_ignore.cpp:266 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:204 modules/commands/os_forbid.cpp:358 +#: modules/commands/cs_akick.cpp:392 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:361 +msgid "Reason" +msgstr "Razón" + +#: src/xline.cpp:386 +#, c-format +msgid "Reason for %s updated." +msgstr "Razón para %s actualizada." + +#: modules/commands/ns_recover.cpp:214 +msgid "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." +msgstr "" +"Recupera tu nick usado por otro usuario o por los servicios.\n" +"Si los servicios están reteniendo tu nick, se liberará. Si otro\n" +"usuario está reteniendo tu nick y está identificado, será\n" +"expulsado de la red (similar al viejo comando GHOST). Si no\n" +"está identificado, se forzará el cambio de nick." + +#: modules/commands/cs_access.cpp:741 +msgid "Redefine the meanings of access levels" +msgstr "Redefine el significado de los niveles de acceso" + +#: modules/commands/ns_recover.cpp:149 +msgid "Regains control of your nick" +msgstr "Recupera el control de tu nick" + +#: modules/commands/os_sxline.cpp:330 modules/commands/os_sxline.cpp:545 +#: modules/commands/os_akill.cpp:129 +msgid "Regex is disabled." +msgstr "Regex está deshabilitado." + +#: modules/commands/os_sxline.cpp:459 modules/commands/os_sxline.cpp:694 +#: modules/commands/os_akill.cpp:444 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." +msgstr "" +"También se pueden usar expresiones regulares usando el motor %s.\n" +"Encierra tu máscara entre // si lo deseas." + +#: modules/commands/os_ignore.cpp:386 modules/commands/os_forbid.cpp:428 +#: modules/commands/ns_list.cpp:172 modules/commands/cs_list.cpp:167 +#: modules/commands/os_list.cpp:119 modules/commands/os_list.cpp:255 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." +msgstr "" +"También se pueden usar expresiones regulares usando el motor %s.\n" +"Encierra tu patrón entre // si lo deseas." + +#: modules/commands/cs_register.cpp:19 +msgid "Register a channel" +msgstr "Registrar un canal" + +#: modules/commands/ns_register.cpp:120 +msgid "Register a nickname" +msgstr "Registrar un nick" + +#: modules/commands/ns_info.cpp:89 modules/commands/cs_info.cpp:55 +msgid "Registered" +msgstr "Registrado" + +#: modules/commands/os_stats.cpp:184 +#, c-format +msgid "Registered channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" +"Canales registrados: %lu entradas, %lu buckets, la cadena más larga es %d" + +#: modules/commands/os_stats.cpp:190 +#, c-format +msgid "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" +msgstr "" +"Grupos de nicks registrados: %lu entradas, %lu buckets, la cadena más larga " +"es %d" + +#: modules/commands/os_stats.cpp:187 +#, c-format +msgid "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" +msgstr "" +"Nicks registrados: %lu entradas, %lu buckets, la cadena más larga es %d" + +#: modules/commands/cs_enforce.cpp:105 +#, c-format +msgid "Registered only enforced on %s." +msgstr "Solo registrados forzado en %s" + +#: modules/commands/cs_register.cpp:86 +#, c-format +msgid "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." +msgstr "" +"Registra un canal en la base de datos de %s. Para\n" +"usar este comando, primero debes ser operador\n" +"en el canal que intentas registrar.\n" +"La descripción, que es opcional, es una\n" +"descripción general del propósito del canal.\n" +" \n" +"Cuando registras un canal, te conviertes en el\n" +"\"fundador\" del canal. El fundador puede cambiar\n" +"toda la configuración del canal; además, %s\n" +"le dará status de operador del canal automáticamente\n" +"al entrar al canal." + +#: modules/commands/ns_register.cpp:269 +#, c-format +msgid "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." +msgstr "" +"Registra tu nick en la base de datos de %s. Una vez\n" +"registrado, puedes usar los comandos SET y ACCESS\n" +"para modificar la configuración de tu nick.\n" +"Asegúrate de recordar la contrasña que usaste para\n" +"registrarte - la necesitarás para hacer cambios a tu nick\n" +"(Ten en cuenta que las mayúsculas importan ANOPE,\n" +"Anope, y anope son todas contraseñas diferentes)\n" +"\n" +"Instrucciones para elegir contraseñas:\n" +"\n" +"Las contraseñas no deben ser fáciles de adivinar. Por ejemplo,\n" +"usar tu nombre real como contraseña es una mala idea. Usar\n" +"tu nick como contraseña es una idea mucho peor ;) y de hecho,\n" +"%s no lo permitirá. Además, las contraseñas cortas\n" +"son vulnerables a ataques de prueba y error, así que deberías\n" +"elegir una contraseña de al menos 5 caracteres.\n" +"Por último, las contraseñas no pueden contener espacios." + +#: modules/commands/ns_register.cpp:145 +msgid "Registration is currently disabled." +msgstr "El registro está deshabilitado en este momento." + +#: modules/commands/cs_set.cpp:400 +msgid "Regulate the use of critical commands" +msgstr "Regular el uso de comandos críticos" + +#: modules/commands/hs_request.cpp:283 +msgid "Reject the requested vHost for the given nick." +msgstr "Rechazar el vHost solicitado para el nick dado" + +#: modules/commands/hs_request.cpp:240 +msgid "Reject the requested vHost of a user" +msgstr "Rechazar el vHost solicitado por un usuario" + +#: modules/commands/cs_suspend.cpp:151 +msgid "Releases a suspended channel" +msgstr "Libera un canal suspendido" + +#: modules/commands/cs_suspend.cpp:191 +msgid "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." +msgstr "" +"Libera un canal suspendido. Se conservará toda la\n" +"configuración anterior a la suspensión." + +#: modules/commands/os_module.cpp:56 +msgid "Reload a module" +msgstr "Recargar un módule" + +#: modules/commands/os_reload.cpp:19 +msgid "Reload services' configuration file" +msgstr "Recargar la configuración de los Servicios" + +#: modules/commands/ns_group.cpp:236 +msgid "Remove a nick from a group" +msgstr "Eliminar un nick de un grupo" + +#: modules/commands/cs_unban.cpp:19 +msgid "Remove all bans preventing a user from entering a channel" +msgstr "Eliminar todos los bans que evitan que un usuario entre a un canal" + +#: modules/commands/os_noop.cpp:19 +msgid "Remove all operators from a server remotely" +msgstr "Elimina todos los operadores de un servidor remotamente" + +#: modules/commands/os_dns.cpp:543 +#, c-format +msgid "Removed IP %s from %s." +msgstr "Eliminada IP %s de %s" + +#: modules/commands/os_dns.cpp:460 +#, c-format +msgid "Removed server %s from zone %s." +msgstr "Servidor %s eliminado de la zona %s." + +#: modules/commands/os_dns.cpp:483 +#, c-format +msgid "Removed server %s." +msgstr "Servidor %s eliminado." + +#: modules/commands/cs_mode.cpp:909 +#, c-format +msgid "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." +msgstr "" +"Quita el status de %s del nick seleccionado en un canal. Si no se\n" +"especifica nick, te quitará es status de %s a ti" + +#: modules/commands/cs_mode.cpp:890 +#, c-format +msgid "Removes %s status from you or the specified nick on a channel" +msgstr "Te quita el status de %s a ti o al nick especificado en un canal" + +#: modules/commands/cs_updown.cpp:146 +msgid "Removes a selected nicks status from a channel" +msgstr "Elimina el status del nick especificado de un canal" + +#: modules/commands/cs_updown.cpp:223 +#, fuzzy +msgid "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." +msgstr "" +"Elimina los modos de status del nick especificado en un canal. Si\n" +"se omite nick se eliminará tu status. Si se omite canal se eliminará\n" +"tu status en todos los canales en los que estés." + +#: src/xline.cpp:412 +#, c-format +msgid "Removing %s because %s covers it." +msgstr "Eliminando %s porque lo cubre %s." + +#: modules/commands/bs_kick.cpp:1171 modules/commands/bs_kick.cpp:1173 +#: modules/commands/bs_kick.cpp:1176 +msgid "Repeat kicker" +msgstr "Kick por repeticion" + +#: modules/commands/hs_request.cpp:78 +msgid "Request a vHost for your nick" +msgstr "Solicitar un vHost para tu nick" + +#: modules/commands/hs_request.cpp:179 +#, fuzzy +msgid "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." +msgstr "" +"Solicitar que el vHost dado sea activado para tu nick por los\n" +"administradores de la red. Por favor, ten paciencia mientras\n" +"tu petición es considerada." + +#: modules/commands/ns_register.cpp:312 +msgid "Resend registration confirmation email" +msgstr "Reenviar email de confirmación" + +#: modules/commands/cs_set.cpp:621 +msgid "Restrict access to the channel" +msgstr "Restringir el acceso al canal" + +#: modules/commands/cs_set.cpp:1291 +msgid "Restricted access" +msgstr "Acceso restringido" + +#: modules/commands/cs_set.cpp:661 +#, c-format +msgid "Restricted access option for %s is now off." +msgstr "Acceso restringido para %s Desactivado." + +#: modules/commands/cs_set.cpp:655 +#, c-format +msgid "Restricted access option for %s is now on." +msgstr "Acceso restringido para %s Activado." + +#: modules/commands/cs_enforce.cpp:73 +#, c-format +msgid "Restricted enforced on %s." +msgstr "Acceso restringido forzado en %s" + +#: modules/commands/cs_set.cpp:335 +msgid "Retain modes when channel is not in use" +msgstr "Retiene los modos cuando el canal no está en uso" + +#: modules/commands/cs_topic.cpp:20 +msgid "Retain topic when channel is not in use" +msgstr "Retiene el topic cuando el canal no está en uso" + +#: modules/commands/ns_getpass.cpp:19 +msgid "Retrieve the password for a nickname" +msgstr "Recupera la contraseña de un nick" + +#: modules/commands/hs_request.cpp:296 +msgid "Retrieves the vhost requests" +msgstr "Devuelve las solicitudes de vhost" + +#: modules/commands/cs_getkey.cpp:19 +msgid "Returns the key of the given channel" +msgstr "Devuelve la clave del canal dado" + +#: modules/commands/cs_getkey.cpp:57 +msgid "Returns the key of the given channel." +msgstr "Devuelve la clave del canal dado." + +#: modules/commands/ns_getemail.cpp:58 +#, fuzzy +msgid "Returns the matching accounts that used given email." +msgstr "Devuelve la clave del canal dado." + +#: modules/commands/ns_status.cpp:19 +msgid "Returns the owner status of the given nickname" +msgstr "Devuelve el status del propietario del nick dado" + +#: modules/commands/ns_getpass.cpp:50 +msgid "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." +msgstr "" +"Devuelve la contraseña para el nick dado. Ten en cuenta\n" +"que cuando se usa este comando, se registrará y se enviará\n" +"un mensaje WALLOPS/GLOBOPS incluyendo la persona que\n" +"usó el comando y el nick que fue usado." + +#: modules/commands/ns_status.cpp:55 +msgid "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." +msgstr "" +"Informa de si el usuario usando el nick dado ha sido\n" +"reconocido como el propietario del nickname.\n" +"La respuesta tiene el siguiente formato:\n" +" \n" +" nick codigo-del-status cuenta\n" +" \n" +"donde nick es el nick enviado con el comando,\n" +"codigo-del-status es uno de los siguientes, y\n" +"cuenta es la cuenta con la que está identificado.\n" +" \n" +" 0 - el usuario no esta en línea o el nick no esta registrado\n" +" 1 - usuario no reconocido como el propietario del nick\n" +" 2 - usuario reconocido solo mediante la lista de acceso\n" +" 3 - usuario reconocido mediante autentificacion por contraseña\n" +" \n" +"Si no se proporciona nick, se mostrará tu status." + +#: modules/commands/bs_kick.cpp:1181 modules/commands/bs_kick.cpp:1183 +#: modules/commands/bs_kick.cpp:1186 +msgid "Reverses kicker" +msgstr "Kick por fondos" + +#: modules/commands/ns_logout.cpp:21 +msgid "Reverses the effect of the IDENTIFY command" +msgstr "Revierte el efecto del comando IDENTIFY" + +#: modules/commands/os_noop.cpp:20 +msgid "SET server" +msgstr "SET servidor" + +#: modules/commands/os_dns.cpp:667 +msgid "SET server.name option value" +msgstr "SET nombre-servidor opción valor" + +#: modules/commands/ns_cert.cpp:378 +#, c-format +msgid "SSL certificate fingerprint accepted, you are now identified to %s." +msgstr "Huella SSL aceptada, ahora estás identificado en %s." + +#: modules/commands/ns_cert.cpp:398 +msgid "SSL certificate fingerprint accepted, you are now identified." +msgstr "Huella SSL aceptada, ahora estás identificado." + +#: modules/commands/cs_enforce.cpp:137 +#, c-format +msgid "SSL only enforced on %s." +msgstr "Solo SSL forzado en %s." + +#: modules/commands/cs_enforce.cpp:131 +msgid "SSLONLY enforced by " +msgstr "SSLONLY forzado por " + +#: modules/commands/os_shutdown.cpp:47 +msgid "Save databases and restart Services" +msgstr "Guardar la base de datos y reiniciar los Servicios" + +#: modules/commands/os_logsearch.cpp:32 +msgid "Searches logs for a matching pattern" +msgstr "Busca registros con el patrón dado" + +#: modules/commands/cs_set.cpp:1295 +msgid "Secure founder" +msgstr "Fundador Seguro" + +#: modules/commands/cs_set.cpp:786 +#, c-format +msgid "Secure founder option for %s is now off." +msgstr "Seguridad de fundador para %s Desactivada." + +#: modules/commands/cs_set.cpp:780 +#, c-format +msgid "Secure founder option for %s is now on." +msgstr "Seguridad de fundador para %s Activada." + +#: modules/commands/cs_set.cpp:1297 +msgid "Secure ops" +msgstr "Ops Seguros" + +#: modules/commands/cs_set.cpp:850 +#, c-format +msgid "Secure ops option for %s is now off." +msgstr "Seguridad de OPs para %s Desactivada." + +#: modules/commands/cs_set.cpp:844 +#, c-format +msgid "Secure ops option for %s is now on." +msgstr "Seguridad de OPs para %s Activada." + +#: modules/commands/cs_set.cpp:723 +#, c-format +msgid "Secure option for %s is now off." +msgstr "Seguridad para %s ahora Desactivada." + +#: modules/commands/cs_set.cpp:717 +#, c-format +msgid "Secure option for %s is now on." +msgstr "Seguridad para %s ahora Activada." + +#: modules/commands/ns_set.cpp:1044 +#, c-format +msgid "Secure option is now off for %s." +msgstr "Seguridad Desactivada para %s." + +#: modules/commands/ns_set.cpp:1038 +#, c-format +msgid "Secure option is now on for %s." +msgstr "Seguridad Activada para %s." + +#: modules/commands/cs_enforce.cpp:42 +#, c-format +msgid "Secureops enforced on %s." +msgstr "Seguridad de OPs forzada en %s." + +#: modules/commands/cs_set.cpp:1293 modules/commands/ns_set.cpp:1311 +msgid "Security" +msgstr "Seguridad" + +#: modules/commands/cs_xop.cpp:570 +#, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the access list." +msgstr "" +"%s%s HELP %s para más información sobre\n" +"la lista de acceso." + +#: modules/commands/cs_xop.cpp:573 +#, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the flags system." +msgstr "" +"%s%s HELP %s para más información sobre\n" +"el sistema de marcas." + +#: modules/commands/ms_send.cpp:24 +msgid "Send a memo to a nick or channel" +msgstr "Enviar un memo a un nick o canal" + +#: modules/commands/ms_staff.cpp:24 +msgid "Send a memo to all opers/admins" +msgstr "Enviar un memo a todos los opers/admins" + +#: modules/commands/ms_sendall.cpp:24 +msgid "Send a memo to all registered users" +msgstr "Enviar un memo a todos los usuarios registrados" + +#: modules/commands/gl_global.cpp:21 +msgid "Send a message to all users" +msgstr "Enviar un mensaje a todos los usuarios" + +#: modules/commands/ms_list.cpp:64 +msgid "Sender" +msgstr "Remitente" + +#: modules/commands/ms_rsend.cpp:24 +msgid "Sends a memo and requests a read receipt" +msgstr "Envía un memo con confirmación de lectura" + +#: modules/commands/ns_resetpass.cpp:50 +msgid "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." +msgstr "" +"Envía un código al nick con instrucciones para restaurar\n" +"su contraseña. Email debe ser la dirección de email asociada\n" +"al nick." + +#: modules/commands/ms_sendall.cpp:52 +msgid "Sends all registered users a memo containing memo-text." +msgstr "Envía a todos los usuarios registrados un memo conteniendo texto-memo." + +#: modules/commands/ms_staff.cpp:48 +msgid "Sends all services staff a memo containing memo-text." +msgstr "Envía a todo el staff de servicios un memo conteniendo texto-memo." + +#: modules/commands/ms_send.cpp:66 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." +msgstr "" +"Envía un memo al nick o canal dado, conteniendo\n" +"texto-del-memo. Al enviar a un nick, el receptor recibirá un\n" +"notice informándole de que tiene un nuevo memo. El nick o\n" +"canal al cual se le enviará el memo deben estar registrados." + +#: modules/commands/ms_rsend.cpp:80 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." +msgstr "" +"Envía a nick o canal un memo conteniendo texto-del-memo.\n" +"Cuando se envía a un nick, el receptor recibirá un notice informándole\n" +"de que tiene un nuevo memo. El nick o canal al cual se le enviará el\n" +"memo debe estar registrado.\n" +"Una vez que el memo ha sido leído, quien envió el memo recibirá una \n" +"notificación automática informando de que el memo ha sido leído." + +#: modules/commands/ms_read.cpp:199 +#, fuzzy +msgid "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Te envía el texto de los memos especificados. Si se especifica\n" +"LAST, te envía el memo más reciente. Si se especifica NEW\n" +"te envía todos tus memos nuevosmemos. De otro modo,\n" +"te envía el memo número num. También puedes proporcionar\n" +"una lista de números, como en este ejemplo:\n" +" \n" +" READ 2-5,7-9\n" +" Muestra los memos número 2 a 5 y 7 a 9." + +#: modules/commands/os_dns.cpp:218 +msgid "Server" +msgstr "Servidor" + +#: modules/commands/os_dns.cpp:375 +#, c-format +msgid "Server %s added to zone %s." +msgstr "Servidor %s añadido a la zona %s." + +#: modules/commands/os_dns.cpp:345 +#, c-format +msgid "Server %s already exists." +msgstr "El servidor %s ya existe." + +#: modules/commands/os_noop.cpp:31 modules/commands/os_dns.cpp:430 +#: modules/commands/os_dns.cpp:493 modules/commands/os_dns.cpp:532 +#: modules/commands/os_dns.cpp:571 modules/commands/os_dns.cpp:604 +#: modules/commands/os_dns.cpp:639 +#, c-format +msgid "Server %s does not exist." +msgstr "El servidor %s no existe." + +#: modules/commands/os_dns.cpp:619 +#, c-format +msgid "Server %s has no configured IPs." +msgstr "El servidor %s no tiene IPs configuradas." + +#: modules/commands/os_dns.cpp:357 +#, c-format +msgid "Server %s is already in zone %s." +msgstr "El servidor %s ya está en la zona %s." + +#: modules/commands/os_dns.cpp:614 +#, c-format +msgid "Server %s is already pooled." +msgstr "El servidor %s ya está en el pool dns." + +#: modules/commands/os_dns.cpp:609 +#, c-format +msgid "Server %s is not currently linked." +msgstr "El servidor %s no está conectado." + +#: modules/commands/os_dns.cpp:443 +#, c-format +msgid "Server %s is not in zone %s." +msgstr "El servidor %s no está en la zona %s." + +#: modules/commands/os_dns.cpp:384 +#, c-format +msgid "Server %s is not linked to the network." +msgstr "El servidor %s no está conectado a la red." + +#: modules/commands/os_dns.cpp:644 +#, c-format +msgid "Server %s is not pooled." +msgstr "El servidor %s no está en el pool dns." + +#: modules/commands/os_dns.cpp:465 +#, c-format +msgid "Server %s must be quit before it can be deleted." +msgstr "El servidor %s debe desconectarse antes de ser borrado." + +#: modules/commands/os_dns.cpp:255 +msgid "Servers" +msgstr "Servidores" + +#: modules/commands/os_stats.cpp:155 +#, c-format +msgid "Servers found: %d" +msgstr "Servidores encontrados: %d" + +#: modules/commands/cs_log.cpp:127 +msgid "Service" +msgstr "Servicio" + +#: modules/commands/ns_recover.cpp:51 +#, c-format +msgid "Service's hold on %s has been released." +msgstr "El nick %s retenido por los servicios ha sido liberado." + +#: data/nickserv.example.conf:236 data/chanserv.example.conf:827 +#, fuzzy +msgid "Services Operator commands" +msgstr "%s es un Operador de Servicios del tipo %s." + +#: modules/commands/os_defcon.cpp:443 modules/commands/os_defcon.cpp:454 +#: modules/commands/os_defcon.cpp:462 modules/commands/os_defcon.cpp:470 +#: modules/commands/os_defcon.cpp:478 +msgid "Services are in DefCon mode, please try again later." +msgstr "Los servicios están en modo DefCon, por favor, inténtalo más tarde." + +#: include/language.h:70 +msgid "Services are in read-only mode!" +msgstr "¡Los Servicios están en modo read-only!" + +#: modules/commands/os_defcon.cpp:186 modules/commands/os_defcon.cpp:213 +#, c-format +msgid "Services are now at DEFCON %d." +msgstr "Los Servicios están ahora en DEFCON %d." + +#: modules/commands/os_set.cpp:128 +#, c-format +msgid "Services are now in debug mode (level %d)." +msgstr "Los Servicios están ahora en modo debug (nivel %d)." + +#: modules/commands/os_set.cpp:114 +msgid "Services are now in debug mode." +msgstr "Los Servicios están ahora en modo debug." + +#: modules/commands/os_set.cpp:159 +msgid "Services are now in expire mode." +msgstr "Servicios ahora en modo expire." + +#: modules/commands/os_set.cpp:153 +msgid "Services are now in no expire mode." +msgstr "Servicios ahora en modo no expire." + +#: modules/commands/os_set.cpp:120 +msgid "Services are now in non-debug mode." +msgstr "Los Servicios están ahora en modo no-debug." + +#: modules/commands/os_set.cpp:47 +msgid "Services are now in read-only mode." +msgstr "Servicios ahora en modo read-only." + +#: modules/commands/os_set.cpp:53 +msgid "Services are now in read-write mode." +msgstr "Servicios ahora en modo de read-write." + +#: src/mail.cpp:76 +msgid "Services have been configured to not send mail." +msgstr "Los servicios han sido configurados para no enviar e-mails." + +#: modules/commands/os_ignore.cpp:280 +msgid "Services ignore list:" +msgstr "Lista de ignorados de los Servicios:" + +#: modules/commands/os_mode.cpp:33 modules/commands/os_kick.cpp:39 +msgid "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" +msgstr "" +"Los Servicios no han podido cambiar modos. ¿Están las lineas U: de tus " +"servidores configuradas correctamente?" + +#: modules/commands/os_stats.cpp:140 +#, c-format +msgid "Services up %s." +msgstr "Servicios en línea %s." + +#: modules/commands/ns_set.cpp:266 +#, c-format +msgid "Services will from now on set status modes on %s in channels." +msgstr "" +"Los servicios ahora establecerán los modos de status de %s en los canales." + +#: modules/commands/cs_set.cpp:114 +#, c-format +msgid "Services will no longer automatically give modes to users in %s." +msgstr "" +"Los Servicios ya no establecerán automáticamente los modos de los usuarios en" +" %s." + +#: modules/commands/ns_set.cpp:272 +#, c-format +msgid "Services will no longer set status modes on %s in channels." +msgstr "" +"Los servicios ya no establecerán los modos de status de %s en los canales." + +#: modules/commands/cs_set.cpp:108 +#, c-format +msgid "Services will now automatically give modes to users in %s." +msgstr "" +"Los Servicios establecerán automáticamente los modos de los usuarios en %s." + +#: modules/commands/ns_set.cpp:940 +#, c-format +msgid "Services will now reply to %s with messages." +msgstr "Los Services ahora responderán a %s con mensajes." + +#: modules/commands/ns_set.cpp:946 +#, c-format +msgid "Services will now reply to %s with notices." +msgstr "Los Services ahora responderán a %s con notices." + +#: modules/commands/os_reload.cpp:34 +msgid "Services' configuration has been reloaded." +msgstr "El archivo de configuración de los Servicios ha sido recargado." + +#: modules/commands/os_session.cpp:192 +msgid "Session" +msgstr "Sesión" + +#: modules/commands/os_session.cpp:382 +#, c-format +msgid "Session limit for %s set to %d." +msgstr "Límite de sesión para %s establecido a %d." + +#: modules/commands/os_session.cpp:257 modules/commands/os_session.cpp:534 +msgid "Session limiting is disabled." +msgstr "Límites de sesión no disponibles." + +#: modules/commands/os_stats.cpp:195 +#, c-format +msgid "Sessions: %lu entries, %lu buckets, longest chain is %d" +msgstr "Sesiones: %lu entradas, %lu buckets, la cadena más larga es %d" + +#: modules/commands/ns_set.cpp:74 +msgid "Set SET-options on another nickname" +msgstr "Establece las opciones SET de otro nick" + +#: modules/commands/cs_set.cpp:20 +msgid "Set channel options and information" +msgstr "Configura opciones e información de un canal" + +#: modules/commands/cs_set.cpp:137 +msgid "Set how Services make bans on the channel" +msgstr "Configura como ponen bans los Servicios en el canal" + +#: modules/commands/ms_set.cpp:206 +msgid "Set options related to memos" +msgstr "Configura opciones relacionadas con los memos" + +#: modules/commands/ns_set.cpp:19 +msgid "Set options, including kill protection" +msgstr "Configura opciones, incluyendo protecciones" + +#: modules/commands/cs_set.cpp:472 +msgid "Set the channel as permanent" +msgstr "Establece el canal como permanente" + +#: modules/commands/cs_set.cpp:204 +msgid "Set the channel description" +msgstr "Establece la descripción del canal" + +#: modules/commands/ns_set.cpp:329 +msgid "Set the display of your group in Services" +msgstr "Establece el display de tu grupo en los Servicios" + +#: modules/commands/cs_set.cpp:266 +msgid "Set the founder of a channel" +msgstr "Establece el fundador de un canal" + +#: modules/commands/ns_set.cpp:793 +msgid "Set the language Services will use when messaging you" +msgstr "Establece el idioma en el que los Servicios te enviarán mensajes" + +#: modules/commands/ns_set.cpp:172 +msgid "Set the nickname password" +msgstr "Establece la contraseña del nick" + +#: modules/commands/cs_set.cpp:949 +msgid "Set the successor for a channel" +msgstr "Establece el sucesor de un canal" + +#: modules/commands/hs_set.cpp:125 +msgid "Set the vhost for all nicks in a group" +msgstr "Establece el vhost de todos los nicks en un grupo" + +#: modules/commands/hs_set.cpp:19 +msgid "Set the vhost of another user" +msgstr "Establece el vhost de otro usuario" + +#: modules/commands/os_set.cpp:169 +msgid "Set various global Services options" +msgstr "Establece varias opciones globales de los Servicios" + +#: modules/commands/ns_set.cpp:119 +msgid "Set your nickname password" +msgstr "Establece la contraseña de tu nick" + +#: modules/commands/bs_kick.cpp:271 +#, c-format +msgid "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Activa o desactiva el kick por AMSG. Cuando está activo, el bot\n" +"kickeará a los usuarios que envíen el mismo mensaje a múltiples\n" +"canales donde estén los bots de %s.\n" +" \n" +"ttb es el número de veces que el usuario será kickeado\n" +"antes de ser baneado. Si no se especifica ttb, el usuario\n" +"nunca será baneado." + +#: modules/commands/bs_kick.cpp:307 +#, c-format +msgid "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Activa o desactiva el kick por badwords. Cuando está activo\n" +"el bot que kickeará a los usuarios que dicen ciertas palabras\n" +"en el canal.\n" +"Puedes definir las badwords para tu canal usando el\n" +"comandoBADWORDS. Escribe %s%s HELP BADWORDS\n" +"para más información.\n" +" \n" +"ttb es el número de veces que se kickeará al usuario\n" +"antes de ser baneado. Si no se establece, el usuario\n" +"nunca será baneado." + +#: modules/commands/cs_set.cpp:186 +msgid "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" +msgstr "" +"Establece el tipo de ban que será usado por los\n" +"Servicios cuando necesiten banear a alguien\n" +"de tu canal.\n" +" \n" +"tipo-de-ban es un numero entre 0 y 3 que significa:\n" +" \n" +"0: ban en la forma *!usuario@host\n" +"1: ban en la forma *!*usuario@host\n" +"2: ban en la forma *!*@host\n" +"3: ban en la forma *!*usuario@*.dominio" + +#: modules/commands/bs_kick.cpp:345 +msgid "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Activa o desactiva el kick por negritas. Cuando está\n" +"activo, el bot kickeará a los usuarios que usen texto en\n" +"negrita.\n" +" \n" +"ttb es el número de veces que el usuario será\n" +"kickeado antes de ser baneado. Si no se especifica ttb, el\n" +"usuario nunca será baneado." + +#: modules/commands/bs_kick.cpp:436 +#, c-format +msgid "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Activa o desactiva el kick por mayúsculas. Cuando está\n" +"activo, el bot kickeará a los usurios que usen texto en\n" +"mayúsculas.\n" +"El bot solo kickeará si hay al menos min mayúsculas y\n" +"constituyen al menos el porcentaje%% del texto total de\n" +"la línea (si no se especifica, por defecto son 10 caracteres y\n" +"un 25%%).\n" +" \n" +"ttb es el número de veces que el usuario será kickeado antes\n" +"de ser baneado. Si no se especifica ttb, el usuario nunca\n" +"será baneado." + +#: modules/commands/bs_kick.cpp:475 +msgid "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Activa o desactiva el kick por color. Cuando está\n" +"activo, el bot kickeará a los usuarios que usen texto\n" +"en color.\n" +" \n" +"ttb es el número de veces que el usuario\n" +"será kickeado antes de ser baneado. Si no se especifica\n" +"ttb, el usuario nunca será baneado." + +#: modules/commands/cs_set.cpp:255 +msgid "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." +msgstr "" +"Establece la descripción para el canal, la que se muestra\n" +"con los comandos LIST e INFO." + +#: modules/commands/bs_kick.cpp:571 +msgid "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Activa o desactiva el kick por flood. Cuando está activado,\n" +"el bot kickeará a los usuarios que hagan flood enviando más\n" +"de ln líneas en segs segundos\n" +"(si no se especifica, por defecto son 6 líneas en 10 segundos).\n" +" \n" +"ttb es el número de veces que el usuario será kickeado\n" +"antes de ser baneado. Si no se especifica ttb, el usuario\n" +"nunca será baneado." + +#: modules/commands/bs_kick.cpp:607 +msgid "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Activa o desactiva el kick por cursivas. Cuando está\n" +"activo, el bot kickeará a los usuarios que usen texto\n" +"en cursiva.\n" +" \n" +"ttb es el número de veces que el usuario\n" +"será kickeado antes de ser baneado. Si no se especifica\n" +"ttb, el usuario nunca será baneado." + +#: modules/commands/bs_kick.cpp:706 +msgid "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Activa o desactiva el kick por repetir. Cuando está activo,\n" +"el bot kickeará a usuarios que repitan el mismo mensaje\n" +"num veces (si no se especifica num, por defecto son\n" +"3 veces).\n" +" \n" +"ttb es el número de veces que el usuario será kickeado\n" +"antes de ser baneado. Si no se especifica ttb, el usuario\n" +"nunca será baneado." + +#: modules/commands/bs_kick.cpp:742 +msgid "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Activa o desactiva el kick por fondos. Cuando está\n" +"activo, el bot kickeará a los usuarios que usen fondos\n" +"de colores.\n" +" \n" +"ttb es el número de veces que el usuario\n" +"será kickeado antes de ser baneado. Si no se especifica\n" +"ttb, el usuario nunca será baneado." + +#: modules/commands/bs_kick.cpp:776 +msgid "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Activa o desactiva el kick por subrayados. Cuando está\n" +"activo, el bot kickeará a los usuarios que usen texto\n" +"subrayado.\n" +" \n" +"ttb es el número de veces que el usuario\n" +"será kickeado antes de ser baneado. Si no se especifica\n" +"ttb, el usuario nunca será baneado." + +#: modules/commands/hs_set.cpp:206 +msgid "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." +msgstr "" +"Establece el vhost para todos los nicks en el grupo\n" +"del nick dado. Si tu IRCD soporta vIdents, usando\n" +"el formato SETALL @ establecerá\n" +"el ident además del vhost.\n" +"* ATENCION, esto no actualizará el vhost para los nicks\n" +"agrupados después de usar el comando." + +#: modules/commands/hs_set.cpp:99 +msgid "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." +msgstr "" +"Establece el vhost para el nick dado.\n" +"Si tu IRCD soporta vIdents, se puede usar el formato\n" +"SET @ para establecer el ident\n" +"además del vhost." + +#: modules/commands/os_set.cpp:199 +msgid "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" +msgstr "" +"Configura varias opciones globales de los Servicios. Los\n" +"nombres de las opciones definidas actualmente son:\n" +" READONLY Establece el modo read-only o read-write\n" +" DEBUG Activa o desactiva el modo debug\n" +" NOEXPIRE Activa o desactiva el modo no expire\n" +" SUPERADMIN Activa o desactiva el modo SuperAdmin\n" +" LIST Lista las opciones" + +#: modules/commands/ms_set.cpp:235 +#, c-format +msgid "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Configura varias opciones de los memos. opción puede ser:\n" +" \n" +" NOTIFY Cambia cuando seras notificado sobre de\n" +" nuevos memos (solo para nicks)\n" +" LIMIT Establece el máximo número de memos que\n" +" puedes recibir\n" +" \n" +"Escribe %s%s HELP %s opción para más información\n" +"acerca de una opción específica." + +#: modules/commands/ns_set.cpp:33 modules/commands/ns_set.cpp:88 +msgid "Sets various nickname options. option can be one of:" +msgstr "Configura varias opciones de nick. opción puede ser:" + +#: modules/commands/ns_set.cpp:237 +msgid "" +"Sets whether services should set channel status modes on you automatically." +msgstr "" +"Configura si los servicios deben establecer tus modos de status en los " +"canales automáticamente." + +#: modules/commands/cs_set.cpp:1090 +msgid "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." +msgstr "" +"Configura la expiración para el canal dado. Si se pone\n" +"a ON evita que el canal expire." + +#: modules/commands/ns_set.cpp:315 +#, c-format +msgid "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." +msgstr "" +"Configura si el nick dado recibirá los modos de status de canal\n" +"automáticamente. Ponlo a ON para que %s le asigne los status\n" +"automáticamente al entrar a los canales (por ejemplo, recibirá +o\n" +"automáticamente si tiene dicho acceso). Ten en cuenta que, dependiendo\n" +"de la configuración del canal, algún modo puede no ser establecido\n" +"automáticamente." + +#: modules/commands/ns_set.cpp:1145 +msgid "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." +msgstr "" +"Configura la expiración para el nick dado. Si se pone\n" +"a ON evita que el nick expire." + +#: modules/commands/ns_set.cpp:288 +#, c-format +msgid "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." +msgstr "" +"Configura cuando recibirás los modos de status de canal automáticamente.\n" +"Ponlo a ON para que %s te asigne los status automáticamente al entrar\n" +"a los canales (por ejemplo, recibirás +o automáticamente si tienes dicho " +"acceso)\n" +"Ten en cuenta que, dependiendo de la configuración del canal, algún modo " +"puede\n" +"no ser establecido automáticamente." + +#: modules/commands/cs_access.cpp:648 modules/commands/cs_access.cpp:689 +#, c-format +msgid "" +"Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." +msgstr "" +"Opcion %s desconocida. Escribe %s%s HELP LEVELS para una lista de opciones " +"válidas." + +#: modules/commands/os_set.cpp:133 +msgid "Setting for DEBUG must be ON, OFF, or a positive number." +msgstr "La configuración para DEBUG debe ser ON u OFF, o un número positivo." + +#: modules/commands/os_set.cpp:162 +msgid "Setting for NOEXPIRE must be ON or OFF." +msgstr "La configuración para NOEXPIRE debe ser ON u OFF." + +#: modules/commands/os_set.cpp:56 +msgid "Setting for READONLY must be ON or OFF." +msgstr "La configuración para READONLY debe ser ON u OFF." + +#: modules/commands/os_set.cpp:95 +msgid "Setting for super admin must be ON or OFF." +msgstr "La configuración para SuperAdmin debe ser ON u OFF." + +#: modules/commands/cs_set.cpp:74 +msgid "Should services automatically give status to users" +msgstr "Los servicios darán el status a los usuarios automáticamente" + +#: modules/commands/os_stats.cpp:203 +msgid "Show status of Services and network" +msgstr "Muestra el estado de los Servicios y la red" + +#: modules/commands/os_logsearch.cpp:152 +#, c-format +msgid "Showed %d/%d matches for %s." +msgstr "Mostradas %d/%d coincidencias para %s." + +#: modules/commands/cs_set.cpp:872 +msgid "Sign kicks that are done with the KICK command" +msgstr "Firma los kicks hechos con el comando KICK" + +#: modules/commands/cs_set.cpp:921 +#, c-format +msgid "Signed kick option for %s is now off." +msgstr "Opción de kick firmado para %s Desactivada." + +#: modules/commands/cs_set.cpp:913 +#, c-format +msgid "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." +msgstr "" +"Opción de kick firmado para %s Activada, pero depende\n" +"del nivel del usuario que use el comando." + +#: modules/commands/cs_set.cpp:906 +#, c-format +msgid "Signed kick option for %s is now on." +msgstr "Opción de kick firmado para %s Activada." + +#: modules/commands/cs_set.cpp:1299 +msgid "Signed kicks" +msgstr "Kicks Firmados" + +#: modules/commands/ms_rsend.cpp:60 modules/commands/ms_send.cpp:59 +#, c-format +msgid "Sorry, %s currently has too many memos and cannot receive more." +msgstr "Lo siento, %s tiene muchos memos actualmente y no puede recibir más." + +#: modules/commands/cs_seen.cpp:294 +#, c-format +msgid "Sorry, I have not seen %s." +msgstr "Lo siento, no he visto a %s." + +#: modules/commands/bs_badwords.cpp:404 +#, fuzzy +msgid "Sorry, bad words list modification is temporarily disabled." +msgstr "" +"Lo siento, la lista de bad words para canales está temporalmente " +"dehabilitada." + +#: modules/commands/bs_assign.cpp:30 modules/commands/bs_assign.cpp:98 +msgid "Sorry, bot assignment is temporarily disabled." +msgstr "Lo siento, la asignación de bots está temporalmente deshabilitada." + +#: modules/commands/bs_bot.cpp:281 modules/commands/bs_assign.cpp:164 +msgid "Sorry, bot modification is temporarily disabled." +msgstr "Lo siento, la modificación de bots está temporalmente deshabilitada." + +#: modules/fantasy.cpp:42 modules/commands/bs_kick.cpp:813 +#: modules/commands/bs_kick.cpp:878 +msgid "Sorry, bot option setting is temporarily disabled." +msgstr "" +"Lo siento, la configuración de opciones del bot está temporalmente " +"deshabilitada." + +#: modules/commands/bs_set.cpp:115 +#, fuzzy +msgid "Sorry, changing bot options is temporarily disabled." +msgstr "" +"Lo siento, la configuración de opciones del bot está temporalmente " +"deshabilitada." + +#: modules/commands/cs_xop.cpp:112 modules/commands/cs_xop.cpp:235 +#: modules/commands/cs_xop.cpp:444 +#, c-format +msgid "Sorry, channel %s list modification is temporarily disabled." +msgstr "" +"Lo siento, la modificación de la lista %s de canal está temporalmente " +"deshabilitada." + +#: modules/commands/cs_access.cpp:547 modules/commands/cs_flags.cpp:405 +msgid "Sorry, channel access list modification is temporarily disabled." +msgstr "" +"Lo siento, la modificación de acceso a canales está temporalmete " +"deshabilitada." + +#: modules/commands/cs_akick.cpp:469 +msgid "Sorry, channel autokick list modification is temporarily disabled." +msgstr "" +"Lo siento, la modificación de kicks automaticos en canales está " +"temporalmente deshabilitada." + +#: modules/commands/cs_drop.cpp:29 +msgid "Sorry, channel de-registration is temporarily disabled." +msgstr "Lo siento, el borrado de canales está temporalmente deshabilitado." + +#: modules/commands/cs_register.cpp:35 +msgid "Sorry, channel registration is temporarily disabled." +msgstr "Lo siento, el registro de canales está temporalmente deshabilitado." + +#: modules/commands/bs_kick.cpp:181 +msgid "Sorry, kicker configuration is temporarily disabled." +msgstr "" +"Lo siento, la configuración de kicker está temporalmente deshabilitada." + +#: modules/commands/ms_set.cpp:216 +msgid "Sorry, memo option setting is temporarily disabled." +msgstr "" +"Lo siento, la configuración de opciones para memos está temporalmente " +"deshabilitada." + +#: include/language.h:116 +msgid "Sorry, memo sending is temporarily disabled." +msgstr "Lo siento, el envío de memos está temporalmente deshabilitado." + +#: modules/commands/ns_drop.cpp:29 +msgid "Sorry, nickname de-registration is temporarily disabled." +msgstr "Lo siento, el borrado de nicks esta temporalmente deshabilitado." + +#: modules/commands/ns_group.cpp:120 +msgid "Sorry, nickname grouping is temporarily disabled." +msgstr "Lo siento, la agrupación de nicks esta temporalmente deshabilitada." + +#: modules/commands/ns_register.cpp:139 +msgid "Sorry, nickname registration is temporarily disabled." +msgstr "Lo siento, el registro de nicks está temporalmente deshabilitado." + +#: modules/commands/ns_access.cpp:33 +#, c-format +msgid "Sorry, the maximum of %d access entries has been reached." +msgstr "Lo siento, solo puedes tener %d entradas en tu lista de acceso." + +#: modules/commands/ns_ajoin.cpp:141 +#, c-format +msgid "Sorry, the maximum of %d auto join entries has been reached." +msgstr "" +"Lo siento, se ha alcanzado el máximo de %d entradas de la lista de auto join." + +#: modules/commands/ns_cert.cpp:173 +#, c-format +msgid "Sorry, the maximum of %d certificate entries has been reached." +msgstr "Lo siento, solo puedes tener %d entradas en tu lista de certificados." + +#: modules/commands/ms_ignore.cpp:55 +#, fuzzy, c-format +msgid "Sorry, the memo ignore list for %s is full." +msgstr "La lista de información de oper para %s está llena." + +#: modules/commands/cs_access.cpp:204 modules/commands/cs_flags.cpp:174 +#: modules/commands/cs_xop.cpp:201 +#, c-format +msgid "" +"Sorry, you can only have %d access entries on a channel, including access " +"entries from other channels." +msgstr "" +"Lo siento, solo puedes tener %d entradas de acceso en un canal, incluyendo " +"entradas de acceso de otros canales." + +#: modules/commands/cs_akick.cpp:177 +#, c-format +msgid "Sorry, you can only have %d autokick masks on a channel." +msgstr "" +"Lo siento, solo puedes tener %d máscaras para kicks automáticos en un canal." + +#: modules/commands/bs_badwords.cpp:286 +#, c-format +msgid "Sorry, you can only have %d bad words entries on a channel." +msgstr "Lo siento, solo puedes tener %d bad words en un canal." + +#: include/language.h:103 +#, c-format +msgid "Sorry, you have already exceeded your limit of %d channels." +msgstr "Lo siento, ya has excedido tu límite de %d canales." + +#: include/language.h:102 +#, c-format +msgid "Sorry, you have already reached your limit of %d channels." +msgstr "Lo siento, ya has alcanzado tu límite de %d canales." + +#: modules/commands/os_dns.cpp:218 +msgid "State" +msgstr "Estado" + +#: modules/commands/cs_seen.cpp:117 +msgid "Statistics and maintenance for seen data" +msgstr "Estadísticas y mantenimento para los datos de avistamiento" + +#: modules/commands/os_stats.cpp:131 +msgid "Statistics reset." +msgstr "Estadísticas reseteadas." + +#: modules/commands/ns_update.cpp:36 +msgid "Status updated (memos, vhost, chmodes, flags)." +msgstr "Status actualizado (memos, vhost, modos de canal, marcas)." + +#: modules/commands/bs_kick.cpp:1432 +msgid "Stop flooding!" +msgstr "¡Para de floodear!" + +#: modules/commands/bs_kick.cpp:1448 +msgid "Stop repeating yourself!" +msgstr "¡Para de repetir!" + +#: modules/commands/cs_set.cpp:746 +msgid "Stricter control of channel founder status" +msgstr "Control estricto del estatus de fundador de canal" + +#: modules/commands/cs_set.cpp:810 +msgid "Stricter control of chanop status" +msgstr "Control estricto del estatus de operador de canal" + +#: modules/commands/ns_alist.cpp:75 modules/commands/cs_info.cpp:50 +msgid "Successor" +msgstr "Sucesor" + +#: modules/commands/cs_set.cpp:1006 +#, c-format +msgid "Successor for %s changed to %s." +msgstr "Sucesor de %s cambiado a %s." + +#: modules/commands/cs_set.cpp:1008 +#, c-format +msgid "Successor for %s unset." +msgstr "Sucesor de %s eliminado." + +#: modules/commands/os_set.cpp:81 +msgid "" +"Super admin can not be set because it is not enabled in the configuration." +msgstr "" +"No se puede activar el SuperAdmin por no está habilitado en la configuración." + +#: modules/commands/ns_suspend.cpp:60 +msgid "Suspend a given nick" +msgstr "Suspende un nick dado" + +#: modules/commands/cs_suspend.cpp:236 modules/commands/ns_suspend.cpp:250 +msgid "Suspend reason" +msgstr "Razón de la suspensión" + +#: modules/commands/cs_suspend.cpp:232 modules/commands/ns_suspend.cpp:246 +msgid "Suspended" +msgstr "Suspendido" + +#: modules/commands/cs_suspend.cpp:234 modules/commands/ns_suspend.cpp:248 +msgid "Suspended by" +msgstr "Suspendido por" + +#: modules/commands/cs_suspend.cpp:238 modules/commands/ns_suspend.cpp:252 +msgid "Suspended on" +msgstr "Suspendido el" + +#: modules/commands/ns_suspend.cpp:147 +msgid "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." +msgstr "" +"Suspende un nick registrado, lo que evita que sea usado\n" +"mientras se mantienen todos sus datos. Si se especifica una\n" +"expiración, la suspensión terminará después de ese periodo de\n" +"tiempo, si no, se usará el tiempo de expiración predeterminado." + +#: modules/commands/cs_suspend.cpp:240 modules/commands/ns_suspend.cpp:254 +msgid "Suspension expires" +msgstr "La suspensión expira" + +#: modules/commands/cs_sync.cpp:19 +msgid "Sync users channel modes" +msgstr "Sincroniza los modos de canal de los usuarios" + +#: modules/commands/cs_sync.cpp:49 +msgid "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." +msgstr "" +"Sincroniza todos los modos establecidos a los usuarios de un\n" +"canal con los modos que deberían tener en función de su acceso." + +#: modules/commands/hs_group.cpp:42 +msgid "Syncs the vhost for all nicks in a group" +msgstr "Sincroniza el vhost con todos los nicks del grupo" + +#: src/command.cpp:146 +msgid "Syntax" +msgstr "Sintaxis" + +#: modules/commands/ns_group.cpp:373 +#, c-format +msgid "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." +msgstr "" +"Sintaxis: %s\n" +" \n" +"Lista todos los nicks en tu grupo." + +#: modules/commands/ns_group.cpp:363 +#, c-format +msgid "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." +msgstr "" +"Sintaxis: %s [nick]\n" +"\n" +"Sin un parámetro, lista todos los nicks en tu grupo.\n" +"\n" +"Con un parámetro, lista todos los nicks que hay en\n" +"el grupo del nick dado.\n" +"Especificar un nick está limitado a Operadores de Servicios." + +#: modules/commands/os_set.cpp:227 +msgid "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." +msgstr "" +"Sintaxis: DEBUG {ON | OFF}\n" +" \n" +"Activa o desactiva el modo debug.\n" +" \n" +"Esta opción es equivalente a la opcion --debug\n" +"en la línea de comandos." + +#: modules/commands/ms_set.cpp:287 +#, c-format +msgid "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." +msgstr "" +"Sintaxis: LIMIT [canal] límite\n" +"\n" +"Configura el máximo número de memos que tú (o el canal\n" +"dado) puedes tener. Si lo configuras a 0, nadie podrá\n" +"enviarte memos. Además, no puedes configurar el límite por\n" +"encima de %d." + +#: modules/commands/ms_set.cpp:267 +#, c-format +msgid "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." +msgstr "" +"Sintaxis: LIMIT [usuario | canal] {límite | NONE} [HARD]\n" +" \n" +"Configura el máximo número de memos que un usuario o\n" +"canal pueden tener. Configurar el límite a 0 evita que el usuario\n" +"reciba memos; configurarlo a NONE permite al usuario\n" +"recibir y guardar cuantos memos quiera. Si no proporcionas un\n" +"nick o un canal, se cambia tu propio límite.\n" +"\n" +"Añadir HARD evita que el usuario pueda cambiar el límite. No\n" +"añadir HARD tiene el efecto contrario, permitiendo al\n" +"usuario cambiar el limite (incluso si un límite anterior fue configurado\n" +"con HARD).\n" +"\n" +"El uso del comando SET LIMIT esta limitado a\n" +"Administradores de Servicios. El resto de usuarios solo\n" +"pueden configurar sus propios límites o los de un canal en\n" +"el que tengan ciertos privilegios, no pueden eliminar su\n" +"límite, no pueden configurar el límite por encima de %d, y no\n" +"pueden configurar un límite hard." + +#: modules/commands/os_set.cpp:208 +#, c-format +msgid "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." +msgstr "" +"Syntax: LIST\n" +" \n" +"Muestra varias configuraciones de %s." + +#: modules/commands/os_set.cpp:234 +msgid "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." +msgstr "" +"Sintaxis: NOEXPIRE {ON | OFF}\n" +" \n" +"Activa o desactiva el modo no expire. En el modo\n" +"no expire, nicks, canales, akills y excepciones no\n" +"expirarán hasta que se desactive el modo.\n" +" \n" +"Esta opción es equivalente a la opcion --noexpire\n" +"en la línea de comandos." + +#: modules/commands/ms_set.cpp:246 +#, fuzzy +msgid "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." +msgstr "" +"Sintaxis: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Cambia cuando serás notificado sobre nuevos memos:\n" +"\n" +" ON Serás notificado cuando te conectes, cuando\n" +" saques tu /AWAY, o en cuanto te sean enviados.\n" +" LOGON Solo serás notificado cuando te conectes\n" +" o cuando saques tu /AWAY.\n" +" NEW Solo serás notificado cuando te sean enviados.\n" +" MAIL Serás notificado por email además de la otra\n" +" configuración que tengas.\n" +" NOMAIL No serás notificado por email.\n" +" OFF No recibiras ninguna notificación.\n" +" \n" +"ON es esencialmente LOGON y NEW combinados." + +#: modules/commands/os_set.cpp:212 +msgid "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." +msgstr "" +"Sintaxis: READONLY {ON | OFF}\n" +"\n" +"Activa o desactiva el modo de solo lectura. En modo de\n" +"solo lectura, los usuarios normales no podrán modificar\n" +"datos de los Servicios, incluyendo acceso a listas de\n" +"canales y nick, etc. Los IRCops con suficientes privilegios\n" +"podrán modificar la lista AKILL y eliminar o prohibir nicks\n" +"y canales, pero ninguno de estos cambios serán guardados\n" +"a menos que se desactive el modo solo lectura antes de\n" +"terminar o reiniciar los Servicios.\n" +" \n" +"Esta opción es equivalente a la opción --readonly en\n" +"la linea de comandos." + +#: modules/commands/os_set.cpp:243 +msgid "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." +msgstr "" +"Sintaxis: SUPERADMIN {ON | OFF}\n" +" \n" +"Esto te da privilegios extra como la habilidad de ser\n" +"\"fundador\" en todos los canales, etc.\n" +"Esta opción no es persistente y debe ser usada\n" +"solo cuando sea necesario." + +#: modules/commands/ns_identify.cpp:107 +#, c-format +msgid "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." +msgstr "" +"Le dice a %s que eres realmente el propietario de este\n" +"nick. Muchos comandos requieren que te identifiques\n" +"primero con este comando. La contraseña debe ser la\n" +"misma que usaste con el comando REGISTER (si no\n" +"la has cambiado)." + +#: modules/commands/cs_invite.cpp:91 +#, fuzzy, c-format +msgid "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Le dice a %s que te invite a ti, u opcionalmente al nick\n" +"especificado, al canal dadol.\n" +" \n" +"Por defecto, limitado a AOPs o aquellos con nivel 5 o\n" +"superior en el canal." + +#: modules/commands/cs_unban.cpp:103 +#, fuzzy, c-format +msgid "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Le dice a %s que elimine todos los bans que evitan que\n" +"tú o el usuario dado entre al canal. Si no se proporciona\n" +"el canal, se eliminarán todos los bans que te afecten en\n" +"todos los canales donde tengas acceso.\n" +" \n" +"Por defecto, limitado a AOPs o aquellos con nivel 5 o\n" +"superior en el canal." + +#: modules/commands/os_jupe.cpp:56 +msgid "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." +msgstr "" +"Le dice a los Servicios que jupiteen un servidor -- esto es,\n" +"crear un \"server\" falso conectado a los Servicios, lo que\n" +"evitará que un servidor real con ese nombre se conecte.\n" +"El jupiteado se puede eliminar usando un SQUITestándar.\n" +"Si se proporciona una razón, se pondrá en el campo de\n" +"información del servidor; si no, el campo contendrá el texto\n" +"\"Jupiteado por \", mostrando el nick de la persona\n" +"que jupiteó el servidor." + +#: modules/commands/cs_seen.cpp:261 +msgid "Tells you about the last time a user was seen" +msgstr "Te dice cuando fue visto por última vez un usuario" + +#: modules/commands/os_shutdown.cpp:19 +msgid "Terminate Services WITHOUT saving" +msgstr "Termina el programa de Servicios SIN guardar los cambios" + +#: modules/commands/os_shutdown.cpp:73 +msgid "Terminate services with save" +msgstr "Termina el programa de Servicios guardando los cambios" + +#: modules/commands/os_news.cpp:156 +msgid "Text" +msgstr "Texto" + +#: modules/commands/cs_access.cpp:576 +msgid "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." +msgstr "" +"El comando ACCESS ADD añade la máscara dada a la\n" +"lista de acceso con el nivel dado; si la máscara ya está en\n" +"la lista, se cambia su acceso al especificado en el comando.\n" +"El nivel especificado debe ser un nivel numérico a un privilegio\n" +"(por ejemplo AUTOOP). Cuando un usuario entra al canal, el status\n" +"que recibe es el mayor de los que tenga en la lista." + +#: modules/commands/cs_access.cpp:587 +msgid "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." +msgstr "" +"El comando ACCESS DEL elimina el nick dado de la lista de\n" +"acceso. Si se proporciona una lista de números, se borran dichas\n" +"entradas. (Mira el ejemplo para LIST más abajo.)\n" +"Puede eliminarte a ti mismo de la lista incluso si no tienes acceso\n" +"para modificarla de otro modo." + +#: modules/commands/cs_access.cpp:593 +msgid "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." +msgstr "" +"El comando ACCESS LIST muestra la lista de acceso. Si se\n" +"proporciona una máscara, solo se muestran las entradas que\n" +"concuerden con la máscara. Si se proporciona una lista de\n" +"números, solo se muestran dichas entradas; por ejemplo:\n" +" ACCESS #canal LIST 2-5,7-9\n" +" Lista las entradas números 2 a 5 y 7 a 9.\n" +" \n" +"El comando ACCESS VIEW muestra la lista de acceso de\n" +"forma similar a ACCESS LIST pero muestra además el creador\n" +"y la última vez que se usó.\n" +" \n" +"El comando ACCESS CLEAR borra todas las entradas de la\n" +"lista de acceso." + +#: modules/commands/cs_flags.cpp:447 +#, fuzzy +msgid "" +"The CLEAR command clears the channel access list. This requires channel " +"founder access." +msgstr "" +"El comando CLEAR limpia la lista de acceso del canal, lo que requiere " +"permisos de fundador." + +#: modules/commands/cs_seen.cpp:173 +#, fuzzy, c-format +msgid "" +"The CLEAR command lets you clean the database by removing all entries from " +"the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." +msgstr "" +"El comando CLEAR te permite limpiar la base de datos, eliminando todas las\n" +"entradas añadidas el último tiempo especificado.\n" +" \n" +"Ejemplo:\n" +" %s CLEAR 30m\n" +" Eliminará todas las entradas añadidas en los últimos 30 minutos." + +#: modules/commands/bs_badwords.cpp:438 +#, fuzzy +msgid "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." +msgstr "" +"El comando DEL elimina la palabra dada de la lista\n" +"de bad words. Si se introduce una lista de números, se\n" +"borrarán dichas entradas. (Mira los ejemplos para LIST)\n" +" \n" +"El comando LIST muestra la lista de bad words. Si se\n" +"proporciona una máscara, solo se muestran las entradas\n" +"que concuerdan con la máscara. Si se proporciona una lista\n" +"de números, solo se muestran dichas entradas; por ejemplo:\n" +" #canal LIST 2-5,7-9\n" +" Lista las bad words número 2 a 5 y número 7 a 9.\n" +" \n" +"El comando CLEAR borra todas las entradas de la lista." + +#: modules/commands/cs_entrymsg.cpp:241 +#, fuzzy +msgid "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." +msgstr "" +"El comando ENTRYMSG ADD añade el mensaje dado a la lista\n" +"de mensajes a ser mostrados a los usuarios cuando entran al canal." + +#: modules/commands/cs_entrymsg.cpp:253 +#, fuzzy +msgid "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." +msgstr "" +"El comando ENTRYMSG CLEAR borra todas las entradas de\n" +"la lista de mensajes a ser mostrados a los usuarios cuando entran\n" +"al canal." + +#: modules/commands/cs_entrymsg.cpp:245 +#, fuzzy +msgid "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." +msgstr "" +"El comando ENTRYMSG DEL borra el mensaje dado de la lista de\n" +"mensajes a ser mostrados a los usuarios cuando entran al canal.\n" +"Puedes borrar el mensaje especificando su número, el cual puedes\n" +"obtener listando todos los mensajes como se explica más abajo." + +#: modules/commands/cs_entrymsg.cpp:250 +#, fuzzy +msgid "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." +msgstr "" +"El comando ENTRYMSG LIST muestra una lista de mensajes a ser\n" +"mostrados a los usuario al entrar al canal." + +#: modules/commands/ns_set.cpp:713 +msgid "The IMMED option is not available on this network." +msgstr "La opcion IMMED no está disponible en esta red." + +#: modules/commands/cs_access.cpp:821 +#, c-format +msgid "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." +msgstr "" +"El comando LEVELS te permite un control más fino sobre\n" +"el significado de los niveles de acceso al canal. Con este\n" +"comando, puedes definir el nivel de acceso requerido para la\n" +"mayoría de funciones de %s. (El comando SET FOUNDER y\n" +"este comando siempre están restringidos al fundador del canal.)\n" +" \n" +"LEVELS SET te permite cambiar el nivel de acceso para una\n" +"función o grupo de funciones. LEVELS DISABLE (o DIS)\n" +"deshabilita una característica automática o el acceso a una\n" +"función en particular, INCLUYENDO al fundador (aunque el\n" +"fundador siempre puede volver a habilitarla).\n" +" \n" +"LEVELS LIST muetra los niveles actuales para cada función\n" +"o grupo de funciones. LEVELS RESET resetea los niveles a los\n" +"predeterminados (mira HELP ACCESS LEVELS).\n" +" \n" +"Para obtener una lista de todas las funciones cuyos niveles\n" +"pueden ser cambiados, mira HELP LEVELS DESC." + +#: modules/commands/cs_flags.cpp:442 +msgid "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." +msgstr "" +"El comando LIST te permite ver las entradas existentes en la lista de acceso " +"del canal.\n" +"Si se proporciona una máscara, solo se muestras las entradas que concuerden " +"con\n" +"dicha máscara. Si se proporcionan una serie de marcas, solo se muestran las " +"entradas que\n" +"tengan dichas marcas." + +#: modules/commands/cs_flags.cpp:435 +#, fuzzy +msgid "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access " +"list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. " +"You are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of " +"what your access is." +msgstr "" +"El comando MODIFY te permite modificar la lista de acceso. Si la máscara\n" +"no está ya en la lista, se añade; después se aplican los cambios.\n" +"Si la máscara no tiene más marcas, se elimina de la lista.\n" +"Adicionalmente, puedes usar +* o -* para añadir o eliminar todas las marcas. " +"Solo\n" +"puedes modificar la lista de acceso si tienes los permisos suficientes en el " +"canal,\n" +"e incluso así, solo puedes darle acceso a los usuarios hasta el que tú ya " +"tengas." + +#: modules/commands/cs_seen.cpp:172 +msgid "" +"The STATS command prints out statistics about stored nicks and memory usage." +msgstr "" +"El comando STATS imprime estadísticas sobre nicks almacenados y uso de " +"memoria." + +#: modules/commands/ns_register.cpp:291 +msgid "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." +msgstr "" +"El parámetro email es opcional y establecerá el email\n" +"para tu nick inmediatamente.\n" +"Respetamos tu privacidad; este e-mail no se compartirá\n" +"con terceros. Puedes querer usar SET HIDE para ocultarlo\n" +"si no está ya como opción predeterminada." + +#: modules/commands/cs_log.cpp:258 +#, fuzzy, c-format +msgid "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." +msgstr "" +"El comando %s permite a los usuarios configurar las opciones\n" +"registros para su canal. Si no se especifican parámetros, lista los\n" +"métodos de registro actuales para el canal dado.\n" +" \n" +"De otro modo, comando debe ser el nombre de un comando\n" +"y método debe ser uno de los siguientes:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Los cuales se usan para enviar mensajes, notices o memos al canal,\n" +"respectivamente.\n" +"Con MESSAGE o NOTICE debes tener un bot asignado al canal.\n" +"Status debe ser un status de canal como @ o +.\n" +" \n" +"Para eliminar un método de registro usa la misma sintaxis que para " +"añadirlo.\n" +" \n" +"Ejemplo:\n" +" %s #anope chanserv/access MESSAGE @%\n" +" Enviará un mensaje a cualquier operador del canal siempre que alguein use\n" +" el comando ACCESS en el canal." + +#: modules/commands/cs_ban.cpp:64 +#, fuzzy, c-format +msgid "The %s list for %s is full." +msgstr "La lista de bans de %s está llena." + +#: modules/commands/os_sxline.cpp:220 +#, c-format +msgid "The %s list has been cleared." +msgstr "La lista %s ha sido limpiada." + +#: modules/commands/os_akill.cpp:377 +msgid "The AKILL list has been cleared." +msgstr "La lista de AKILLs ha sido limpiada." + +#: modules/commands/os_defcon.cpp:136 modules/commands/os_defcon.cpp:225 +#, c-format +msgid "The Defcon level is now at: %d" +msgstr "El Nivel de Defcon ahora es: %d" + +#: modules/commands/ns_info.cpp:171 +#, c-format +msgid "The E-mail address of %s will now be hidden from %s INFO displays." +msgstr "La dirección de e-mail de %s ahora se ocultará en la salida %s INFO." + +#: modules/commands/ns_info.cpp:172 +#, c-format +msgid "The E-mail address of %s will now be shown in %s INFO displays." +msgstr "La dirección de e-mail de %s ahora se mostrará en la salida %s INFO." + +#: modules/commands/cs_flags.cpp:449 +msgid "The available flags are:" +msgstr "Las marcas disponibles son:" + +#: modules/commands/os_defcon.cpp:240 +msgid "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." +msgstr "" +"El sistema defcon puede ser usado para implementar un conjunto\n" +"pre-definido de restricciones que son muy útiles en un eventual\n" +"ataque a la red." + +#: modules/ns_maxemail.cpp:51 +#, fuzzy, c-format +msgid "The email address %s has reached its usage limit of %d users." +msgstr "Este email ha alcanzado su límite de uso de %d usuarios." + +#: modules/ns_maxemail.cpp:49 +#, fuzzy, c-format +msgid "The email address %s has reached its usage limit of 1 user." +msgstr "Este email ha alcanzado su límite de uso de 1 usuario." + +#: modules/commands/cs_entrymsg.cpp:142 +#, c-format +msgid "The entry message list for %s is full." +msgstr "La lista de mensajes de entrada para %s está llena." + +#: modules/commands/cs_access.cpp:796 +msgid "The following feature/function names are available:" +msgstr "Están disponibles las siguientes funciones/características:" + +#: modules/commands/cs_access.cpp:584 +msgid "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." +msgstr "" +"La máscara dada también puede ser un canal, lo que usará\n" +"la lista de acceso del otro canal hasta el nivel dado" + +#: modules/commands/os_session.cpp:240 +#, c-format +msgid "" +"The host %s currently has %d sessions with a limit of %d because it matches " +"entry: %s." +msgstr "" +"El host %s actualmente tiene %d sesiones con un límite de %d porque coincide " +"con la entrada: %s." + +#: modules/commands/ms_check.cpp:54 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has been read." +msgstr "El último memo que enviaste a %s (enviado el %s) ha sido leído." + +#: modules/commands/ms_check.cpp:52 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has not yet been read." +msgstr "El último memo que enviaste a %s (enviado el %s) aún no ha sido leído." + +#: modules/commands/ns_info.cpp:189 +#, c-format +msgid "The last quit message of %s will now be hidden from %s INFO displays." +msgstr "El último mensaje quit de %s ahora se ocultará en la salida %s INFO." + +#: modules/commands/ns_info.cpp:190 +#, c-format +msgid "The last quit message of %s will now be shown in %s INFO displays." +msgstr "El último mensaje quit de %s ahora se mostrará en la salida %s INFO." + +#: modules/commands/ns_info.cpp:177 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." +msgstr "" +"La última máscara usuario@host vista de %s ahora se ocultará en la salida %s " +"INFO." + +#: modules/commands/ns_info.cpp:178 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." +msgstr "" +"La última máscara usuario@host vista de %s ahora se mostrará en la salida %s " +"INFO." + +#: modules/commands/cs_enforce.cpp:190 +#, c-format +msgid "The limit on %s is not valid." +msgstr "El límite en %s no es válido." + +#: modules/commands/os_forbid.cpp:193 +msgid "The mask must contain at least one non wildcard character." +msgstr "La máscara debe contener al menos un caracter no comodín." + +#: modules/commands/ms_set.cpp:153 +#, c-format +msgid "The memo limit for %s may not be changed." +msgstr "El límite de memos para %s no puede ser cambiado." + +#: modules/commands/cs_mode.cpp:347 +#, fuzzy, c-format +msgid "The mode lock list of %s is full." +msgstr "La lista de información de oper para %s está llena." + +#: modules/commands/ns_set.cpp:355 +#, c-format +msgid "The new display MUST be a nickname of the nickname group %s." +msgstr "El nuevo display DEBE ser un nick de tu grupo %s." + +#: include/language.h:98 +#, c-format +msgid "The new display is now %s." +msgstr "El nuevo display ahora es %s." + +#: modules/commands/os_svs.cpp:57 +#, c-format +msgid "The nick %s is now being changed to %s." +msgstr "El nick %s está siendo cambiado a %s." + +#: modules/commands/bs_bot.cpp:149 +msgid "The old information is the same as the new information specified." +msgstr "" + +#: modules/commands/os_info.cpp:157 +#, c-format +msgid "The oper info already exists on %s." +msgstr "La información de operador ya existe en %s." + +#: modules/commands/os_info.cpp:147 +#, c-format +msgid "The oper info list for %s is full." +msgstr "La lista de información de oper para %s está llena." + +#: modules/commands/ns_info.cpp:183 +#, c-format +msgid "" +"The services access status of %s will now be hidden from %s INFO displays." +msgstr "" +"El estado de acceso a los Servicios de %s ahora se ocultará en la salida %s " +"INFO." + +#: modules/commands/ns_info.cpp:184 +#, c-format +msgid "The services access status of %s will now be shown in %s INFO displays." +msgstr "" +"El estado de acceso a los Servicios de %s ahora se mostrará en la salida %s " +"INFO." + +#: modules/commands/os_session.cpp:433 +msgid "The session exception list is empty." +msgstr "La lista de excepciones al límite de sesión está vacía." + +#: modules/commands/ns_recover.cpp:121 +msgid "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." +msgstr "" +"El usuario con tu nick ha sido eliminado. Usa este comando de nuevo\n" +"para liberar el nick retenido por los servicios." + +#: modules/pseudoclients/memoserv.cpp:195 +#, c-format +msgid "There are %d memos on channel %s." +msgstr "Hay %d memos en el canal %s." + +#: modules/commands/bs_botlist.cpp:47 +msgid "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" +msgstr "" +"No hay bots disponibles en este momento.\n" +"¡Pídele a un administrador de servicios que cree uno!" + +#: modules/commands/os_dns.cpp:213 +msgid "There are no configured servers." +msgstr "No hay servidores configurados." + +#: modules/commands/os_forbid.cpp:392 +#, c-format +msgid "There are no forbids of type %s." +msgstr "No hay prohibiciones del tipo %s." + +#: modules/commands/ns_group.cpp:162 +msgid "There are too many nicks in your group." +msgstr "Hay demasiados nicks en tu grupo." + +#: modules/commands/cs_log.cpp:123 +#, c-format +msgid "There currently are no logging configurations for %s." +msgstr "No hay configuraciones de registro para %s." + +#: modules/pseudoclients/memoserv.cpp:193 +#, c-format +msgid "There is %d memo on channel %s." +msgstr "Hay %d memo en el canal %s." + +#: include/language.h:110 +#, c-format +msgid "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." +msgstr "" +"Hay un memo nuevo en el canal %s.\n" +"Escribe %s%s READ %s %d para leerlo." + +#: modules/commands/bs_assign.cpp:132 +#, c-format +msgid "There is no bot assigned to %s anymore." +msgstr "Ya no hay un bot asignado a %s." + +#: modules/commands/os_news.cpp:33 +msgid "There is no logon news." +msgstr "No hay Noticias de Entrada." + +#: modules/commands/os_news.cpp:43 +msgid "There is no oper news." +msgstr "No hay Noticias de Oper." + +#: modules/commands/os_news.cpp:53 +msgid "There is no random news." +msgstr "No hay Noticias al Azar." + +#: modules/commands/os_config.cpp:41 +#, c-format +msgid "There is no such configuration block %s." +msgstr "No existe el bloque de configuración %s." + +#: modules/commands/cs_mode.cpp:706 +#, c-format +msgid "There is no such mode %s." +msgstr "No existe el modo %s." + +#: modules/commands/ms_set.cpp:52 +msgid "There's no email address set for your nick." +msgstr "Tu nick no tiene una direccion de e-mail." + +#: modules/commands/os_forbid.cpp:304 modules/commands/os_forbid.cpp:496 +#, c-format +msgid "This channel has been forbidden: %s" +msgstr "Este canal ha sido prohibido: %s" + +#: modules/commands/cs_suspend.cpp:121 +msgid "This channel has been suspended." +msgstr "Este canal ha sido suspendido." + +#: modules/commands/cs_suspend.cpp:232 +msgid "This channel is suspended." +msgstr "Este canal está suspendido." + +#: modules/commands/cs_suspend.cpp:268 +msgid "This channel may not be used." +msgstr "Este canal esta prohibido." + +#: modules/commands/os_dns.cpp:702 +msgid "" +"This command allows managing DNS zones used for controlling what servers " +"users\n" +"are directed to when connecting. Omitting all parameters prints out the " +"status of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to " +"this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, " +"the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given " +"zones." +msgstr "" +"Este comando permite administrar zonas DNS usadas para controlar a que " +"servidores\n" +"son redirigidos los usuarios cuando conectan. Si no se proporcionan " +"parámetros, muestra\n" +"el estado de la zona DNS.\n" +" \n" +"ADDZONE añade una zona, por ejemplo es.tudomino.tld. Pueden entonces " +"añadirse\n" +"servidores a la zona con el comando ADDSERVER.\n" +" \n" +"El comando ADDSERVER añade un servidor a la zona dada. Cuando se hace una\n" +"consulta dns, se sirve la zona en cuestión, si existe, si no, se sirven " +"todos los servidores\n" +"en todas las zonas.\n" +"Un servidor puede estar en más de una zona.\n" +" \n" +"El comando ADDIP asocia una IP con un servidor.\n" +" \n" +"Los comandos POOL y DEPOOL realmente añaden y eliminan servidores de sus " +"zonas dadas." + +#: modules/commands/hs_group.cpp:72 +msgid "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." +msgstr "" +"Este comando permite a los usuarios establecer el vhost\n" +"de su nick ACTUAL como vhost para todos los nicks del\n" +"mismo grupo." + +#: modules/commands/ns_register.cpp:299 +msgid "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." +msgstr "" +"Este comando también crea un nuevo grupo para tu nick,\n" +"que te permitirá registrar otros nicks más tarde, compartiendo\n" +"la misma configuración, los mismos memos y los mismos privilegios." + +#: modules/m_rewrite.cpp:145 +#, c-format +msgid "This command is an alias to the command %s." +msgstr "Este comando es un alias del comando %s." + +#: modules/commands/ns_register.cpp:95 +msgid "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." +msgstr "" +"Este comando es usado por varios comandos para confirmar\n" +"cambios hechos en tu cuenta.\n" +" \n" +"Es usado comúnmente para confirmar tu email cuando te\n" +"registras o lo cambias.\n" +" \n" +"También es usado después de usar el comando RESETPASS\n" +"para identificarte para que puedas cambiar la contraseña." + +#: modules/commands/os_modinfo.cpp:70 +msgid "This command lists information about the specified loaded module." +msgstr "Este comando lista información sobre el módulo cargado especificado. " + +#: modules/commands/hs_list.cpp:136 +#, fuzzy +msgid "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." +msgstr "" +"Este comando lista al operador los vhosts registrados.\n" +"Si se especifica clave, solo se mostrarán las entradas\n" +"que concuerden con ese patrón. Por ejemplo, Rob*\n" +"mostrará todas las entradas que empiecen por \"Rob\"\n" +"Si se usa la forma #X-Y, solo se mostrarán las entradas\n" +"entre el rango de X e Y, por ejemplo, #1-3\n" +"mostrarán las 3 primeras entradas nick/vhost.\n" +"La lista usa el valor de NSListMax como límite para el\n" +"número de elementos a mostrar a la vez." + +#: modules/commands/os_module.cpp:45 +msgid "" +"This command loads the module named modname from the modules\n" +"directory." +msgstr "" +"Este comando carga el módulo llamado nombre-del-módulo desde el\n" +"directorio de módulos." + +#: modules/commands/ns_group.cpp:201 +msgid "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." +msgstr "" +"Este comando hace que tu nick entre al grupo del nick\n" +"objetivo. contraseña es la contraseña del nick objetivo.\n" +" \n" +"Entrar en un grupo te permite compartir tu configuración,\n" +"memos, y privilegios de canal con todos los nicks del\n" +"grupo, ¡y mucho más!\n" +" \n" +"Un grupo existe siempre y cuando sea útil. Esto significa que incluso\n" +"si se elimina un nick del grupo, no perderás las cosas compartidas\n" +"descritar arriba, siempre y cuando permanezca al menos un nick en\n" +"el grupo.\n" +" \n" +"Podrás usar este comando incluso si aún no has registrado tu\n" +"nick. Si tu nick ya está registrado, necesitarás identificarte primero\n" +"antes de usar este comando.\n" +" \n" +"Se recomienda usar este comando con un nick no registrado\n" +"porque el nick se registrará automáticamente al usar este\n" +"comando. Puedes usarlo con un nick registrado (para cambiar\n" +"su grupo) solo si el administrador de la red lo ha permitido.\n" +" \n" +"Solo puedes estar en un grupo a la vez. La fusión de grupos no\n" +"es posible.\n" +" \n" +"Aviso: todos los nicks de un grupo tienen la misma contraseña." + +#: modules/commands/ns_ajoin.cpp:292 +msgid "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." +msgstr "" +"Este comando administra la lista de auto join. Cuando te identificas\n" +"entrarás automáticamente a los canales de tu lista de auto join.\n" +"Los Operadores de Servicios pueden especificar un nick para modificar\n" +"las listas auto join de otros usuarios." + +#: modules/commands/ns_set.cpp:345 modules/commands/ns_set.cpp:669 +msgid "" +"This command may not be used on this network because nickname ownership is " +"disabled." +msgstr "" +"Este comando no se puede usar en esta red porque la posesión de nicks está " +"deshabilitada." + +#: modules/commands/os_module.cpp:118 +msgid "This command reloads the module named modname." +msgstr "Este comando recarga el módulo llamado nombre-del-módulo." + +#: modules/commands/hs_request.cpp:344 +msgid "This command retrieves the vhost requests." +msgstr "Este comando devuelve las solicitudes de vhost." + +#: modules/commands/os_logsearch.cpp:159 +msgid "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." +msgstr "" +"Este comando busca, en los archivos de registro, mensajes\n" +"que coincidan con el patrón dado. Los argumentos día y\n" +"límite pueden usarse para especificar cuantos días de registro\n" +"se deben buscar, y cuantas entradas se deben mostrar. Por\n" +"defecto, este comando busca una semana de registros y los\n" +"resultados se limitan a 50.\n" +" \n" +"Por ejemplo:\n" +" LOGSEARCH +21d +500l Anope\n" +" Busca mensajes de los últimos 21 días que contengan\n" +" la palabra Anope y lista los 500 más recientes." + +#: modules/commands/cs_status.cpp:106 +msgid "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." +msgstr "" +"Este comando te dice que acceso tiene un usuario en el canal\n" +"y que entradas de acceso, si las hay, concuerdan con él. Además\n" +"te muestra cualquier entrada de la lista auto kick que concuerde\n" +"con el usuario. El uso de este comando está limitado a los usuarios\n" +"que pueden modificar la lista de acceso del canal." + +#: modules/commands/ns_group.cpp:285 +msgid "" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." +msgstr "" +"Este comando desagrupa tu nick, o el nick especificado, del grupo\n" +"en el que está. El nick desagrupado mantiene su fecha de registro\n" +"su contraseña, su email, su saludo, su idioma y su url. Todo lo demás\n" +"es reseteado. No puedes desagruparte a ti mismo si solo hay un nick\n" +"en tu grupo." + +#: modules/commands/os_module.cpp:168 +msgid "This command unloads the module named modname." +msgstr "Este comando descarga el módulo llamado nombre-del-módulo." + +#: modules/commands/ns_register.cpp:353 +msgid "This command will resend you the registration confirmation email." +msgstr "Este comando te reenviará el email de confirmación del registro." + +#: include/language.h:90 +#, c-format +msgid "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" +msgstr "" +"Este nick es propiedad de alguien. Por favor, escoge otro.\n" +"(Si es tu nick, escribe %s%s IDENTIFY contraseña.)" + +#: modules/commands/os_forbid.cpp:469 +#, c-format +msgid "This nickname has been forbidden: %s" +msgstr "Este nick ha sido prohibido: %s" + +#: modules/commands/ns_recover.cpp:99 +#, c-format +msgid "This nickname has been recovered by %s." +msgstr "Este nick ha sido recuperado por %s." + +#: modules/commands/ns_recover.cpp:77 +#, c-format +msgid "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." +msgstr "" +"Este nick ha sido recuperado por %s. Si no fuiste tú, entonces\n" +"%s puede tener tu contraseña y deberías cambiarla." + +#: include/language.h:95 +msgid "This nickname has been registered; you may not use it." +msgstr "Este nick ha sido registrado; no puedes usarlo." + +#: modules/commands/ns_suspend.cpp:246 +msgid "This nickname is suspended." +msgstr "Este nick está suspendido." + +#: include/language.h:92 +#, c-format +msgid "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." +msgstr "" +"Este nick está registrado y protegido. Si es tu nick,\n" +"escribe %s%s IDENTIFY contraseña. Si no,\n" +"por favor, elige un nick diferente." + +#: modules/commands/ms_read.cpp:95 +#, c-format +msgid "To delete, type: %s%s %s %d" +msgstr "Para borrar, escribe: %s%s %s %d" + +#: modules/commands/ms_read.cpp:93 +#, c-format +msgid "To delete, type: %s%s %s %s %d" +msgstr "Para borrar, escribe: %s%s %s %s %d" + +#: modules/commands/bs_kick.cpp:791 +msgid "To protect ops against bot kicks" +msgstr "Para proteger a los OPs de los kicks del bot" + +#: modules/commands/bs_kick.cpp:856 +msgid "To protect voices against bot kicks" +msgstr "Para proteger usuarios con voz de los kicks del bot" + +#: modules/commands/cs_list.cpp:46 +msgid "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." +msgstr "" +"Para buscar canales que comienzan por #, busca por el nombre\n" +"del canal sin el prefijo # (anope en vez de #anope)." + +#: modules/commands/os_logsearch.cpp:139 +#, fuzzy, c-format +msgid "Too many results for %s." +msgstr "No hay estadísticas para %s." + +#: modules/extra/stats/cs_fantasy_top.cpp:149 +#, c-format +msgid "Top %i of %s" +msgstr "Top %i de %s" + +#: modules/commands/os_list.cpp:43 +msgid "Topic" +msgstr "Topic" + +#: modules/commands/cs_topic.cpp:258 +msgid "Topic lock" +msgstr "Bloqueo de topic" + +#: modules/commands/cs_topic.cpp:114 +#, c-format +msgid "Topic lock option for %s is now off." +msgstr "Bloqueo de topic para %s Desactivado." + +#: modules/commands/cs_topic.cpp:97 +#, c-format +msgid "Topic lock option for %s is now on." +msgstr "Bloqueo de topic para %s Activado." + +#: modules/commands/cs_topic.cpp:256 +msgid "Topic retention" +msgstr "Retención de topic" + +#: modules/commands/cs_topic.cpp:60 +#, c-format +msgid "Topic retention option for %s is now off." +msgstr "Retención de topic para %s Desactivada." + +#: modules/commands/cs_topic.cpp:54 +#, c-format +msgid "Topic retention option for %s is now on." +msgstr "Retención de topic para %s Activada." + +#: modules/commands/cs_topic.cpp:265 +msgid "Topic set by" +msgstr "Topic puesto por" + +#: modules/commands/bs_kick.cpp:1323 +msgid "Turn caps lock OFF!" +msgstr "¡Apaga las mayusculas!" + +#: modules/extra/stats/m_chanstats.cpp:17 +#: modules/extra/stats/m_chanstats.cpp:71 +msgid "Turn chanstats statistics on or off" +msgstr "Pone las estadísticas de canal a on u off." + +#: modules/commands/ns_set.cpp:1009 +msgid "Turn nickname security on or off" +msgstr "Pone la seguridad del nick a on u off." + +#: modules/commands/ns_set.cpp:655 +msgid "Turn protection on or off" +msgstr "Pone la protección a on u off." + +#: modules/commands/ns_list.cpp:264 +#, c-format +msgid "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Pone las caracteristicas de privacidad de %s para el nick a on\n" +"u off. Con PRIVATE activado, el nick no aparecerá en las\n" +"listas de nicks generadas con el comando LIST de %s.\n" +"(Sin embargo, cualquier persona que sepa el nick podrá\n" +"comprobar la información usando el comando INFO.)" + +#: modules/commands/ns_list.cpp:236 +#, c-format +msgid "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Pone las caracteristicas de privacidad de %s para tu nick a on\n" +"u off. Con PRIVATE activado, tu nick no aparecerá en las\n" +"listas de nicks generadas con el comando LIST de %s.\n" +"(Sin embargo, cualquier persona que sepa tu nick podrá\n" +"comprobar tu información usando el comando INFO.)" + +#: modules/commands/ns_set.cpp:1059 modules/commands/ns_set.cpp:1088 +#, c-format +msgid "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." +msgstr "" +"Pone las caracteristicas de seguridad de %s para tu nick a on\n" +"u off. Con SECURE activado, debes ingresar tu contraseña\n" +"para ser reconocido como propietario del nick, aunque tu\n" +"dirección esté en la lista de acceso. Sin embargo, si estás en la\n" +"lista de acceso, %s no te auto-killeara sin importar como esté\n" +"la opciónKILL." + +#: modules/extra/stats/m_chanstats.cpp:142 +msgid "Turns chanstats channel statistics ON or OFF for this user." +msgstr "Pone las estadísticas de canal para este usuario a ON u OFF." + +#: modules/extra/stats/m_chanstats.cpp:61 +#: modules/extra/stats/m_chanstats.cpp:119 +msgid "Turns chanstats statistics ON or OFF." +msgstr "Pone las estadísticas de canal a ON u OFF." + +#: modules/commands/ns_set.cpp:772 +#, c-format +msgid "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Cambia la protección automática del nick a on u off.\n" +"Con protección on, si otro usuario intenta usar el nick,\n" +"tendrá un minuto para cambiar de nick, luego del cual\n" +"%s cambiará su nick automáticamente.\n" +"\n" +"Si estableces QUICK, el usuario tendrá solo 20 segundos\n" +"para cambiar el nick en vez de los normales 60. Si seleccionas\n" +"IMMED, el nick del usuario será cambiado inmediatamente\n" +"sin ser advertido o dado oportunidad de cambiarlo antes;\n" +"Por favor no uses esta opcion a menos que lo consideres\n" +"necesario. Además, los administradores de la red pueden haber\n" +"deshabilitado esta opción." + +#: modules/commands/ns_set.cpp:738 +#, c-format +msgid "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Cambia la protección automática de tu nick a on u off.\n" +"Con protección on, si otro usuario intenta usar tu nick,\n" +"tendrá un minuto para cambiar de nick, luego del cual\n" +"%s cambiará su nick automáticamente.\n" +"\n" +"Si estableces QUICK, el usuario tendrá solo 20 segundos\n" +"para cambiar el nick en vez de los normales 60. Si seleccionas\n" +"IMMED, el nick del usuario será cambiado inmediatamente\n" +"sin ser advertido o dado oportunidad de cambiarlo antes;\n" +"Por favor no uses esta opcion a menos que lo consideres\n" +"necesario. Además, los administradores de la red pueden haber\n" +"deshabilitado esta opción." + +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_forbid.cpp:358 +msgid "Type" +msgstr "Tipo" + +#: modules/commands/ns_set.cpp:62 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Escribe %s%s HELP %s opción para más información\n" +"sobre una opción específica." + +#: modules/commands/bs_kick.cpp:151 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." +msgstr "" +"Escribe %s%s HELP %s opción para más información\n" +"acerca de una opción específica.\n" +" \n" +"Aviso: el acceso a este comando está controlado por\n" +"el nivel SET." + +#: modules/commands/ns_set.cpp:107 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." +msgstr "" +"Escribe %s%s HELP %s opción para más información\n" +"acerca de una opción específica. Las opciones se establecerán\n" +"para el nick dado." + +#: modules/commands/bs_set.cpp:62 modules/commands/cs_set.cpp:63 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." +msgstr "" +"Escribe %s%s HELP %s opción para más información\n" +"sobre una opción en particular." + +#: modules/pseudoclients/nickserv.cpp:361 +#, c-format +msgid "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." +msgstr "" +"Escribe %s%s SET EMAIL e-mail para establecer tu e-mail.\n" +"Respetamos tu privacidad; este e-mail no será dado a terceros." + +#: modules/commands/os_module.cpp:128 +msgid "Un-Load a module" +msgstr "Descargar un módulo" + +#: modules/commands/os_sxline.cpp:337 modules/commands/os_sxline.cpp:552 +#: modules/commands/os_akill.cpp:136 +#, c-format +msgid "Unable to find regex engine %s." +msgstr "Imposible encontrar el motor regex %s." + +#: modules/commands/os_module.cpp:36 modules/commands/os_module.cpp:108 +#, c-format +msgid "Unable to load module %s." +msgstr "Imposible cargar módulo %s." + +#: modules/commands/os_module.cpp:73 modules/commands/os_module.cpp:90 +#: modules/commands/os_module.cpp:145 modules/commands/os_module.cpp:159 +#, c-format +msgid "Unable to remove module %s." +msgstr "Imposible quitar módulo %s." + +#: modules/commands/bs_assign.cpp:90 +msgid "Unassigns a bot from a channel" +msgstr "Desasigna un bot de un canal" + +#: modules/commands/bs_assign.cpp:139 +msgid "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." +msgstr "" +"Desasigna un bot de un canal. Cuando usas este comando,\n" +"el bot no entrará más al canal. Sin embargo, la configuración\n" +"del bot se conservará, así que siempre podrás reasignar el bot\n" +"en un futuro sin tener que reconfigurarlo completamente." + +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1193 +#: modules/commands/bs_kick.cpp:1196 +msgid "Underlines kicker" +msgstr "Kicker por subrayados" + +#: modules/commands/os_dns.cpp:595 +msgid "Unknown SET option." +msgstr "Opción SET desconocida." + +#: modules/commands/os_stats.cpp:229 +#, c-format +msgid "Unknown STATS option: %s" +msgstr "Opción STATS desconocida: %s" + +#: src/command.cpp:222 src/command.cpp:233 +#, c-format +msgid "Unknown command %s." +msgstr "Comando %s desconocido." + +#: src/command.cpp:220 src/command.cpp:231 +#, c-format +msgid "Unknown command %s. \"%s%s HELP\" for help." +msgstr "Comando %s desconocido. \"%s%s HELP\" para ayuda." + +#: modules/commands/cs_mode.cpp:317 modules/commands/cs_mode.cpp:409 +#, c-format +msgid "Unknown mode character %c ignored." +msgstr "Caracter de modo %c desconocido e ignorado." + +#: modules/commands/os_logsearch.cpp:78 +#, c-format +msgid "Unknown parameter: %s" +msgstr "Parámetro desconocido: %s" + +#: modules/commands/os_dns.cpp:241 +msgid "Unpooled" +msgstr "Fuera del pool dns." + +#: modules/commands/cs_drop.cpp:77 +msgid "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." +msgstr "" +"Borra el canal dado. Solo puede ser usado por\n" +"el fundador del canal." + +#: modules/commands/cs_drop.cpp:74 +#, fuzzy +msgid "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." +msgstr "" +"Borra el canal dado. Solo los Operadores de Servicios\n" +"pueden borrar un canal del que no son fundadores." + +#: modules/commands/ns_suspend.cpp:160 +msgid "Unsuspend a given nick" +msgstr "De-suspende el nick dado" + +#: modules/commands/ns_suspend.cpp:199 +msgid "Unsuspends a nickname which allows it to be used again." +msgstr "Quita la suspensión de un nick para que pueda ser usado de nuevo." + +#: modules/commands/cs_updown.cpp:126 +#, fuzzy +msgid "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." +msgstr "" +"Actualiza el modo de status de un canal para el nick especificado. Si\n" +"se omite nick se actualiza tu propio status. Si se omite canal se\n" +"actualiza tu status en todos los canales en los que estás." + +#: modules/commands/cs_updown.cpp:48 +msgid "Updates a selected nicks status on a channel" +msgstr "Actualiza el estado de los nicks seleccionados en un canal" + +#: modules/commands/ns_update.cpp:19 +msgid "Updates your current status, i.e. it checks for new memos" +msgstr "" +"Actualiza tu estado actual, por ejemplo, comprueba si tienes\n" +"memos nuevos" + +#: modules/commands/ns_update.cpp:43 +msgid "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." +msgstr "" +"Actualiza tu status actual, por ejemplo, comprueba si tienes\n" +"memos nuevos, cambia tus modos de canal y actualiza tu\n" +"vhost y tus marcas de usuario (ultima vez visto, etc)." + +#: modules/commands/os_update.cpp:25 +msgid "Updating databases." +msgstr "Actualizando las bases de datos." + +#: modules/commands/os_stats.cpp:154 +#, c-format +msgid "Uplink capab: %s" +msgstr "Capacidades del enlace: %s" + +#: modules/commands/os_stats.cpp:153 +#, c-format +msgid "Uplink server: %s" +msgstr "Servidor enlace: %s" + +#: modules/commands/help.cpp:127 +#, c-format +msgid "Use the %s ALL command to list all commands and their descriptions." +msgstr "" +"Usa el comando %s ALL para listar todos los comandos y sus descripciones." + +#: modules/commands/bs_info.cpp:59 +msgid "Used on" +msgstr "Usado el" + +#: data/chanserv.example.conf:821 +#, fuzzy +msgid "Used to manage channels" +msgstr "Puede cambiar el topic del canal" + +#: data/chanserv.example.conf:809 +#, fuzzy +msgid "Used to manage the list of privileged users" +msgstr "Modificar la lista de usuarios privilegiados" + +#: data/chanserv.example.conf:815 +msgid "Used to modify the channel status of you or other users" +msgstr "" + +#: modules/commands/cs_akick.cpp:575 +msgid "User has been banned from the channel" +msgstr "El usuario ha sido baneado del canal" + +#: modules/commands/os_dns.cpp:587 +#, c-format +msgid "User limit for %s removed." +msgstr "Límite de usuarios para %s eliminado." + +#: modules/commands/os_dns.cpp:585 +#, c-format +msgid "User limit for %s set to %d." +msgstr "Límite de usuarios para %s establecido a %d." + +#: modules/commands/os_list.cpp:43 +msgid "Users" +msgstr "Usuarios" + +#: modules/commands/os_stats.cpp:172 +#, c-format +msgid "Users (nick): %lu entries, %lu buckets, longest chain is %d" +msgstr "Usuarios (nick): %lu entradas, %lu buckets, la cadena más larga es %d" + +#: modules/commands/os_stats.cpp:177 +#, c-format +msgid "Users (uid): %lu entries, %lu buckets, longest chain is %d" +msgstr "Usuarios (uid): %lu entriadas, %lu buckets, la cadena más larga es %d" + +#: modules/commands/os_list.cpp:184 +msgid "Users list:" +msgstr "Lista de usuarios:" + +#: modules/commands/ns_info.cpp:105 modules/commands/ns_info.cpp:107 +msgid "VHost" +msgstr "VHost" + +#: modules/commands/hs_set.cpp:92 +#, c-format +msgid "VHost for %s set to %s." +msgstr "VHost para %s establecido a %s." + +#: modules/commands/hs_set.cpp:90 +#, c-format +msgid "VHost for %s set to %s@%s." +msgstr "VHost para %s establecido a %s@%s." + +#: modules/commands/hs_set.cpp:199 +#, c-format +msgid "VHost for group %s set to %s." +msgstr "VHost para el grupo %s establecido a %s." + +#: modules/commands/hs_set.cpp:197 +#, c-format +msgid "VHost for group %s set to %s@%s." +msgstr "VHost para el grupo %s establecido a %s@%s." + +#: modules/commands/os_session.cpp:247 +msgid "VIEW host" +msgstr "VIEW host" + +#: modules/commands/os_sxline.cpp:428 modules/commands/os_sxline.cpp:662 +#: modules/commands/os_akill.cpp:389 +msgid "VIEW [mask | list | id]" +msgstr "VIEW [máscara | lista | id]" + +#: modules/commands/os_session.cpp:526 +msgid "VIEW [mask | list]" +msgstr "VIEW [máscara | lista]" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +msgid "Value" +msgstr "Valor" + +#: modules/commands/os_config.cpp:48 +#, c-format +msgid "Value of %s:%s changed to %s" +msgstr "El valor de %s:%s ha sido cambiado a %s" + +#: modules/commands/hs_list.cpp:58 modules/commands/hs_request.cpp:305 +msgid "Vhost" +msgstr "Vhost" + +#: modules/commands/hs_del.cpp:38 +#, c-format +msgid "Vhost for %s removed." +msgstr "El Vhost para %s ha sido eliminado." + +#: modules/commands/os_oper.cpp:69 +msgid "View and change Services Operators" +msgstr "Ver y cambiar Operadores de Servicios" + +#: modules/commands/os_config.cpp:19 +msgid "View and change configuration file settings" +msgstr "Ver y cambiar la configuración del archivo de configuración." + +#: modules/commands/os_session.cpp:245 +msgid "View the list of host sessions" +msgstr "Ver la lista de sesiones" + +#: modules/commands/bs_kick.cpp:1221 +msgid "Voices protection" +msgstr "Proteccion de Voices" + +#: modules/commands/bs_kick.cpp:1406 +msgid "Watch your language!" +msgstr "¡Cuida tu lenguaje!" + +#: modules/commands/cs_list.cpp:237 +#, c-format +msgid "" +"When private is set, the channel will not appear in\n" +"%s's %s command." +msgstr "" +"Cuando la privacidad está activada, el canal no aparecerá\n" +"en el comando %s's %s." + +#: modules/commands/ms_info.cpp:204 +msgid "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." +msgstr "" +"Sin un parámetro, muestra información del número de\n" +"memos que tienes, cuantos están sin leer, y cuantos puedes\n" +"recibir en total.\n" +" \n" +"Con un parámetro de canal, muestra la misma información\n" +"para el canal dado.\n" +" \n" +"Con un parámetro de nick, muestra la misma información\n" +"para el nick dado. Esto está limitado a Operadores\n" +"de Servicios." + +#: modules/commands/ns_logout.cpp:66 +msgid "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." +msgstr "" +"Sin parámetros, revierte el efecto del comando IDENTIFY,\n" +"por ejemplo, hace que ya no seas reconocido como el propietario\n" +"real del nick. Ten en cuenta que no se te pedirá que te identifiques\n" +"de nuevo.\n" +" \n" +"Con un parámetro, hace lo mismo para el nick dado. Si especificas\n" +"la opción REVALIDATE , los Servicios pedirán a dicho nick que\n" +"se re-identifique. Esto está limitado a Operadores de Servicios." + +#: modules/commands/os_stats.cpp:236 +msgid "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." +msgstr "" +"Sin opciones, muestra el número de usuarios en línea,\n" +"y el número máximo de usuarios desde que se iniciaron\n" +"los Servicios, y el tiempo que llevan los Servicios corriendo.\n" +" \n" +"Con la opción AKILL , muestra el tamaño actual de la\n" +"lista AKILL y el tiempo de expiración predeterminado.\n" +" \n" +"La opción RESET resetea el máximo número de usuarios\n" +"al número de usuarios presentes actualmente en la red.\n" +" \n" +"La opción UPLINK muestra información sobre el servidor\n" +"que usa Anope para unirse a la red.\n" +" \n" +"La opción HASH muestra información sobre los mapas de hash.\n" +" \n" +"La opción ALL muestra todas las estadísticas anteriores." + +#: modules/commands/bs_badwords.cpp:194 +msgid "Word" +msgstr "Palabra" + +#: modules/commands/ns_group.cpp:158 +#, c-format +msgid "You are already a member of the group of %s." +msgstr "Ya eres miembro del grupo de %s." + +#: modules/commands/os_login.cpp:34 modules/commands/ns_identify.cpp:87 +msgid "You are already identified." +msgstr "Ya estás identificado." + +#: modules/commands/cs_invite.cpp:64 +#, c-format +msgid "You are already in %s!" +msgstr "¡Ya estás en %s!" + +#: modules/commands/os_set.cpp:91 +msgid "You are no longer a super admin." +msgstr "Ya no eres un SuperAdmin." + +#: modules/commands/os_login.cpp:81 +msgid "You are not identified." +msgstr "No estás identificado." + +#: include/language.h:100 +msgid "You are not permitted to be on this channel." +msgstr "No se te permite estar en este canal." + +#: modules/commands/ms_set.cpp:158 +msgid "You are not permitted to change your memo limit." +msgstr "No estas autorizado a cambiar tu límite de memos." + +#: modules/commands/ns_cert.cpp:183 +#, fuzzy +msgid "You are not using a client certificate." +msgstr "No estás identificado." + +#: modules/commands/os_set.cpp:85 +msgid "You are now a super admin." +msgstr "Ahora eres un SuperAdmin." + +#: modules/commands/os_oline.cpp:36 +msgid "You are now an IRC Operator." +msgstr "Eres ahora un operador de IRC." + +#: modules/commands/ns_resetpass.cpp:108 +msgid "You are now identified for your nick. Change your password now." +msgstr "Ahora estás identificado para tu nick. Cambia tu contraseña ahora." + +#: modules/commands/ns_group.cpp:64 +#, c-format +msgid "You are now in the group of %s." +msgstr "Ahora eres miembro del grupo de %s." + +#: modules/pseudoclients/memoserv.cpp:147 +#, c-format +msgid "" +"You are over your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Has sobrepasado tu máximo de memos (%d). No podrás recibir nuevos memos " +"hasta que borres alguno de los actuales." + +#: modules/commands/os_noop.cpp:33 +msgid "You can not NOOP Services." +msgstr "No puedes usar NOOP con los Servicios." + +#: modules/commands/cs_access.cpp:672 +msgid "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." +msgstr "" +"No puedes deshabilitar los privilegios de fundador porque sería imposible " +"restablecerlos después." + +#: modules/commands/os_jupe.cpp:34 +msgid "You can not jupe an already juped server." +msgstr "No puedes jupitear un servidor ya jupiteado." + +#: modules/commands/os_jupe.cpp:32 +msgid "You can not jupe your Services' pseudoserver or your uplink server." +msgstr "" +"No puedes jupitear tu pseudoservidor de Servicios o tu servidor uplink." + +#: modules/commands/os_module.cpp:80 +#, c-format +msgid "You can not reload this module directly, instead reload %s." +msgstr "No puedes recargar este módulo directamente, en vez de eso recarga %s." + +#: modules/commands/ms_rsend.cpp:46 +msgid "You can not request a receipt when sending a memo to yourself." +msgstr "" +"No puedes solicitar una confirmación cuando te envías un memo a ti mismo." + +#: modules/commands/ns_recover.cpp:163 +#, c-format +msgid "You can't %s yourself!" +msgstr "¡No puedes %s a ti mismo!" + +#: modules/commands/cs_access.cpp:154 modules/commands/cs_flags.cpp:109 +#: modules/commands/cs_xop.cpp:151 +msgid "You can't add a channel to its own access list." +msgstr "No puedes añadir un canal a su propia lista de acceso." + +#: modules/commands/ns_logout.cpp:37 +#, c-format +msgid "You can't logout %s, they are a Services Operator." +msgstr "No puedes desconectar a %s porque es un Operador de Servicios." + +#: modules/commands/ns_set.cpp:927 +#, c-format +msgid "You cannot %s on this network." +msgstr "No puedes %s en esta red." + +#: modules/commands/cs_flags.cpp:231 +#, fuzzy, c-format +msgid "You cannot set the %c flag." +msgstr "No puedes establecer la marca %c." + +#: modules/commands/ms_set.cpp:173 +#, c-format +msgid "You cannot set the memo limit for %s higher than %d." +msgstr "No puedes establecer el límite de memos para %s a más de %d." + +#: modules/commands/ms_set.cpp:175 +#, c-format +msgid "You cannot set your memo limit higher than %d." +msgstr "No puedes establecer tu límite de memos a más de %d." + +#: modules/commands/bs_assign.cpp:124 +#, fuzzy +msgid "You cannot unassign bots while persist is set on the channel." +msgstr "" +"No puedes desasignar bots mientras el modo persistente esté establecido en " +"el canal." + +#: modules/commands/ns_set.cpp:480 +msgid "You cannot unset the e-mail on this network." +msgstr "No puedes borrar tu direccion de e-mail en esta red." + +#: modules/commands/help.cpp:177 +msgid "You cannot use this command." +msgstr "No puedes usar este comando." + +#: modules/commands/ms_info.cpp:151 +#, c-format +msgid "You currently have %d memos, of which %d are unread." +msgstr "Tienes %d memos, de los cuales %d aún no han sido leídos." + +#: modules/commands/ms_info.cpp:149 +#, c-format +msgid "You currently have %d memos, of which 1 is unread." +msgstr "Tienes %d memos, de los cuales 1 aún no ha sido leído." + +#: modules/commands/ms_info.cpp:147 +#, c-format +msgid "You currently have %d memos." +msgstr "Tienes %d memos." + +#: modules/commands/ms_info.cpp:145 +#, c-format +msgid "You currently have %d memos; all of them are unread." +msgstr "Tienes %d memos, ninguno de ellos leído." + +#: modules/commands/ms_info.cpp:134 +msgid "You currently have 1 memo, and it has not yet been read." +msgstr "Tienes 1 memo y aún no ha sido leído." + +#: modules/commands/ms_info.cpp:136 +msgid "You currently have 1 memo." +msgstr "Tienes 1 memo." + +#: modules/commands/ms_info.cpp:130 +msgid "You currently have no memos." +msgstr "No tienes memos." + +#: modules/commands/cs_mode.cpp:564 modules/commands/cs_mode.cpp:621 +#, c-format +msgid "You do not have access to set mode %c." +msgstr "No tienes acceso para establecer el modo %c." + +#: modules/commands/cs_mode.cpp:578 modules/commands/cs_mode.cpp:590 +#: modules/commands/cs_mode.cpp:631 +#, c-format +msgid "You do not have the access to change %s's modes." +msgstr "No tienes acceso para cambiar los modos de %s" + +#: modules/commands/cs_seen.cpp:198 +#, c-format +msgid "You found me, %s!" +msgstr "¡Me encontraste, %s!" + +#: modules/pseudoclients/memoserv.cpp:143 +#, c-format +msgid "You have %d new memos." +msgstr "Tienes %d memos nuevos." + +#: modules/pseudoclients/memoserv.cpp:143 +msgid "You have 1 new memo." +msgstr "Tienes 1 memo nuevo." + +#: include/language.h:112 +#, c-format +msgid "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." +msgstr "" +"Tienes un nuevo memo de %s.\n" +"Escribe %s%s READ %d para leerlo." + +#: modules/commands/cs_invite.cpp:76 +#, fuzzy, c-format +msgid "You have been invited to %s by %s." +msgstr "Has sido invitado a %s." + +#: modules/commands/cs_invite.cpp:81 +#, c-format +msgid "You have been invited to %s." +msgstr "Has sido invitado a %s." + +#: modules/protocol/ratbox.cpp:166 modules/commands/ns_recover.cpp:96 +#, c-format +msgid "You have been logged in as %s." +msgstr "Te has identificado como %s." + +#: modules/commands/os_login.cpp:86 +msgid "You have been logged out." +msgstr "Has sido desconectado." + +#: modules/commands/cs_unban.cpp:94 +#, c-format +msgid "You have been unbanned from %s." +msgstr "Has sido desbaneado de %s." + +#: modules/commands/cs_unban.cpp:54 +#, c-format +msgid "You have been unbanned from %d channels." +msgstr "Has sido desbaneado de %d canales." + +#: modules/commands/ms_info.cpp:169 +msgid "You have no limit on the number of memos you may keep." +msgstr "No tienes límite en el número de memos que puedes guardar." + +#: include/language.h:114 +msgid "You have no memos." +msgstr "No tienes memos." + +#: include/language.h:117 +msgid "You have no new memos." +msgstr "No tienes memos nuevos." + +#: modules/pseudoclients/memoserv.cpp:149 +#, c-format +msgid "" +"You have reached your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Has alcanzado el máximo número de memos (%d). No podrás recibir más memos " +"hasta que borres algunos de los existentes." + +#: modules/commands/ns_recover.cpp:117 +#, fuzzy, c-format +msgid "You have regained control of %s." +msgstr "Has sido invitado a %s." + +#: modules/commands/ns_drop.cpp:66 +msgid "You may drop any nick within your group." +msgstr "Puedes borrar cualquier nick de tu grupo." + +#: modules/commands/cs_mode.cpp:322 modules/commands/cs_mode.cpp:414 +#, c-format +msgid "You may not (un)lock mode %c." +msgstr "No puedes (des)bloquear el modo %c" + +#: modules/commands/ns_set.cpp:485 +msgid "You may not change the e-mail of other Services Operators." +msgstr "No puedes cambiar el e-mail de otro Operador de Servicios." + +#: modules/commands/ns_set.cpp:474 +#, fuzzy +msgid "You may not change the email of an unconfirmed account." +msgstr "No puedes cambiar el e-mail de otro Operador de Servicios." + +#: modules/commands/ns_set.cpp:196 +msgid "You may not change the password of other Services Operators." +msgstr "No puedes cambiar la contraseña de otro Operador de Servicios." + +#: modules/commands/ns_drop.cpp:45 +msgid "You may not drop other Services Operators' nicknames." +msgstr "No puedes eliminar el nick de otro Operador de Servicios." + +#: modules/commands/ns_getpass.cpp:32 +msgid "You may not get the password of other Services Operators." +msgstr "No puedes obtener la contraseña de otro Operador de Servicios." + +#: modules/commands/ns_suspend.cpp:100 +msgid "You may not suspend other Services Operators' nicknames." +msgstr "No puedes suspender el nick de otro Operador de Servicios." + +#: modules/commands/ns_access.cpp:136 +msgid "" +"You may view but not modify the access list of other Services Operators." +msgstr "" +"Puedes ver pero no modificar la lista de acceso de otro Operador de " +"Servicios." + +#: modules/commands/ns_cert.cpp:292 +msgid "" +"You may view but not modify the certificate list of other Services Operators." +msgstr "" +"Puedes ver pero no modificar la lista de certificados de otro Operador de " +"Servicios." + +#: modules/commands/cs_seen.cpp:287 +#, c-format +msgid "You might see yourself in the mirror, %s." +msgstr "Podrías mirarte al espejo, %s." + +#: include/language.h:120 +msgid "You must assign a bot to the channel before using this command." +msgstr "Debes asignar un bot al canal antes de usar este comando." + +#: modules/commands/cs_register.cpp:49 +msgid "You must be a channel operator to register the channel." +msgstr "Debes ser un operador de canal para registrar el canal." + +#: modules/commands/cs_updown.cpp:94 modules/commands/cs_updown.cpp:192 +#, fuzzy, c-format +msgid "You must be in %s to use this command." +msgstr "Tienes que estar identificado para usar este comando." + +#: modules/commands/cs_register.cpp:37 +msgid "You must confirm your account before you can register a channel." +msgstr "Debes confirmar tu cuenta antes de que puedas registar un canal." + +#: modules/commands/hs_request.cpp:100 +#, fuzzy +msgid "You must confirm your account before you may request a vhost." +msgstr "Debes confirmar tu cuenta antes de que puedas registar un canal." + +#: modules/commands/ms_send.cpp:44 +#, fuzzy +msgid "You must confirm your account before you may send a memo." +msgstr "Debes confirmar tu cuenta antes de que puedas registar un canal." + +#: modules/commands/cs_drop.cpp:42 +#, c-format +msgid "" +"You must enter the channel name twice as a confirmation that you wish to drop" +" %s." +msgstr "" +"Debes introducir el nombre del canal dos veces como confirmación de que " +"quieres borrar %s." + +#: modules/commands/ns_register.cpp:153 +#, c-format +msgid "You must have been using this nick for at least %d seconds to register." +msgstr "Debes estar conectado más de %d segundos para registrar tu nick." + +#: modules/commands/cs_mode.cpp:913 +#, c-format +msgid "You must have the %s(ME) privilege on the channel to use this command." +msgstr "Debes tener el privilegio %s(ME) en el canal para usar este comando." + +#: modules/pseudoclients/nickserv.cpp:358 +msgid "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." +msgstr "" +"Ahora debes proporcionar un e-mail para tu nick.\n" +"Este e-mail te permitirá recuperar tu clave en\n" +"caso de que la olvides." + +#: modules/commands/help.cpp:172 +msgid "You need to be identified to use this command." +msgstr "Tienes que estar identificado para usar este comando." + +#: modules/commands/ms_info.cpp:182 +#, fuzzy +msgid "You will be notified by message and by mail when new memos arrive." +msgstr "Serás notificado cuando te envíen nuevos memos." + +#: modules/commands/ms_info.cpp:175 +#, fuzzy +msgid "" +"You will be notified of new memos at logon and when they arrive, and by mail " +"when they arrive." +msgstr "" +"Serás notificado de nuevos memos cuando te conectes y en cuanto te sean " +"enviados." + +#: modules/commands/ms_info.cpp:177 +msgid "You will be notified of new memos at logon and when they arrive." +msgstr "" +"Serás notificado de nuevos memos cuando te conectes y en cuanto te sean " +"enviados." + +#: modules/commands/ms_info.cpp:189 +#, fuzzy +msgid "" +"You will be notified of new memos at logon, and by mail when they arrive." +msgstr "" +"Serás notificado de nuevos memos cuando te conectes y en cuanto te sean " +"enviados." + +#: modules/commands/ms_info.cpp:191 +msgid "You will be notified of new memos at logon." +msgstr "Serás notificado de nuevos memos cuando te conectes." + +#: modules/commands/ms_info.cpp:184 +msgid "You will be notified when new memos arrive." +msgstr "Serás notificado cuando te envíen nuevos memos." + +#: modules/commands/ms_set.cpp:190 +msgid "You will no longer be able to receive memos." +msgstr "No te será posible recibir más memos." + +#: modules/commands/ms_set.cpp:57 +msgid "You will no longer be informed via email." +msgstr "No serás informado de nuevos memos via email." + +#: modules/commands/ms_info.cpp:195 +msgid "You will not be notified of new memos." +msgstr "No serás notificado de nuevos memos." + +#: modules/commands/ms_set.cpp:49 +msgid "You will now be informed about new memos via email." +msgstr "Serás informado de nuevos memos via email." + +#: modules/commands/os_svs.cpp:86 +msgid "Your IRCd does not support SVSJOIN." +msgstr "Tu IRCd no soporta SVSJOIN." + +#: modules/commands/os_svs.cpp:31 +msgid "Your IRCd does not support SVSNICK." +msgstr "Tu IRCd no soporta SVSNICK." + +#: modules/commands/os_svs.cpp:130 +msgid "Your IRCd does not support SVSPART." +msgstr "Tu IRCd no soporta SVSPART." + +#: include/language.h:127 +msgid "" +"Your IRCd does not support vIdent's, if this is incorrect, please report " +"this as a possible bug" +msgstr "" +"Tu IRCd no soporta vIdent's, si esto no es correcto, por favor, repórtalo " +"como posible bug." + +#: modules/extra/m_ldap_authentication.cpp:110 +#: modules/extra/m_sql_authentication.cpp:55 +#, c-format +msgid "Your account %s has been successfully created." +msgstr "Tu cuenta %s ha sido creada correctamente." + +#: modules/commands/ns_register.cpp:328 +msgid "Your account is already confirmed." +msgstr "Tu cuenta ya está confirmada." + +#: modules/commands/ns_register.cpp:396 +#, c-format +msgid "Your account will expire, if not confirmed, in %s." +msgstr "Tu cuenta expirará si no es confirmada en %s" + +#: modules/commands/ns_set.cpp:1274 +#, c-format +msgid "Your email address has been changed to %s." +msgstr "Tu dirección email ha sido cambiada a %s." + +#: modules/commands/os_forbid.cpp:544 modules/commands/os_forbid.cpp:553 +msgid "Your email address is not allowed, choose a different one." +msgstr "Tu dirección de email no está permitida, escoje otra diferente." + +#: modules/commands/ns_register.cpp:260 modules/commands/ns_register.cpp:391 +msgid "" +"Your email address is not confirmed. To confirm it, follow the instructions " +"that were emailed to you." +msgstr "" +"Tu dirección de email no está confirmada. Para confirmarla, sigue las " +"instrucciones que se enviaron a tu email." + +#: modules/commands/ns_register.cpp:67 +#, c-format +msgid "Your email address of %s has been confirmed." +msgstr "Tu dirección email de %s ha sido confirmada." + +#: modules/extra/m_ldap_authentication.cpp:159 +#, c-format +msgid "Your email has been updated to %s" +msgstr "Tu email ha sido actualizado a %s" + +#: modules/extra/m_sql_authentication.cpp:62 +#, c-format +msgid "Your email has been updated to %s." +msgstr "Tu email ha sido actualizado a %s." + +#: modules/commands/ms_set.cpp:197 +msgid "Your memo limit has been disabled." +msgstr "Tu límite de memos ha sido deshabilitado." + +#: modules/commands/ms_set.cpp:183 +#, c-format +msgid "Your memo limit has been set to %d." +msgstr "Tu límite de memos ha sido establecido a %d." + +#: modules/commands/ms_info.cpp:164 +#, c-format +msgid "Your memo limit is %d, and may not be changed." +msgstr "Tu límite de memos es %d y no puede ser cambiado." + +#: modules/commands/ms_info.cpp:166 +#, c-format +msgid "Your memo limit is %d." +msgstr "Tu límite de memos es %d." + +#: modules/commands/ms_info.cpp:159 +msgid "Your memo limit is 0; you will not receive any new memos." +msgstr "Tu límite de memos es 0; no recibirás nuevos memos." + +#: modules/commands/ms_info.cpp:157 +msgid "" +"Your memo limit is 0; you will not receive any new memos. You cannot change " +"this limit." +msgstr "" +"Tu límite de memos es 0; no recibirás nuevos memos. No puedes cambiar este " +"límite." + +#: modules/commands/ns_logout.cpp:50 +msgid "Your nick has been logged out." +msgstr "Tu nick ha sido desconectado." + +#: modules/commands/ns_group.cpp:156 +msgid "Your nick is already registered." +msgstr "Tu nick ya está registrado." + +#: modules/commands/ns_group.cpp:246 +msgid "Your nick is not grouped to anything, you can't ungroup it." +msgstr "Tu nick no está agrupado a nada, no puedes desagruparlo." + +#: include/language.h:77 +msgid "Your nick isn't registered." +msgstr "Tu nick no está registrado." + +#: modules/pseudoclients/nickserv.cpp:254 +#, c-format +msgid "Your nickname is now being changed to %s" +msgstr "Tu nick se ha cambiado a %s" + +#: modules/commands/os_login.cpp:32 modules/commands/os_login.cpp:79 +msgid "Your oper block doesn't require logging in." +msgstr "Tu bloque de operador no requiere inicio de sesión." + +#: modules/commands/ns_register.cpp:336 +#, c-format +msgid "Your passcode has been re-sent to %s." +msgstr "Tu contraseña ha sido reenviada a %s." + +#: modules/commands/ns_register.cpp:232 +#, c-format +msgid "Your password is %s - remember this for later use." +msgstr "Tu contraseña es %s - Recuérdala para usos futuros." + +#: include/language.h:76 +#, fuzzy, c-format +msgid "Your password is too long. It must not exceed %u characters." +msgstr "" +"Tu contraseña es demasiado larga. Por favor, inténtalo de nuevo con una más " +"corta." + +#: modules/commands/ns_resetpass.cpp:96 +msgid "Your password reset request has expired." +msgstr "Tu petición de restablecimiento de contraseña ha expirado." + +#: modules/commands/hs_request.cpp:170 +msgid "Your vHost has been requested." +msgstr "Tu vHost ha sido solicitado." + +#: modules/pseudoclients/hostserv.cpp:64 +#: modules/pseudoclients/hostserv.cpp:103 modules/commands/hs_on.cpp:37 +#, c-format +msgid "Your vhost of %s is now activated." +msgstr "Tu vhost %s ha sido activado." + +#: modules/pseudoclients/hostserv.cpp:62 +#: modules/pseudoclients/hostserv.cpp:101 modules/commands/hs_on.cpp:35 +#, c-format +msgid "Your vhost of %s@%s is now activated." +msgstr "Tu vhost %s@%s ha sido activado." + +#: modules/commands/hs_off.cpp:39 +msgid "Your vhost was removed and the normal cloaking restored." +msgstr "Tu vhost ha sido eliminado y el enmascaramiento normal restaurado." + +#: modules/commands/os_dns.cpp:255 +msgid "Zone" +msgstr "Zona" + +#: modules/commands/os_dns.cpp:290 +#, c-format +msgid "Zone %s already exists." +msgstr "La zona %s ya existe." + +#: modules/commands/os_dns.cpp:310 modules/commands/os_dns.cpp:352 +#: modules/commands/os_dns.cpp:402 modules/commands/os_dns.cpp:438 +#, c-format +msgid "Zone %s does not exist." +msgstr "La zona %s no existe." + +#: modules/commands/os_dns.cpp:332 +#, c-format +msgid "Zone %s removed." +msgstr "Zona %s eliminada." + +#: modules/commands/os_defcon.cpp:177 +msgid "[1|2|3|4|5]" +msgstr "[1|2|3|4|5]" + +#: modules/commands/os_news.cpp:400 +#, c-format +msgid "[Logon News - %s] %s" +msgstr "[Noticias de Entrada - %s] %s" + +#: modules/commands/os_news.cpp:402 +#, c-format +msgid "[Oper News - %s] %s" +msgstr "[Noticias de Oper - %s] %s" + +#: modules/commands/os_news.cpp:404 +#, c-format +msgid "[Random News - %s] %s" +msgstr "[Noticias al Azar - %s] %s" + +#: modules/commands/ns_identify.cpp:66 +msgid "[account] password" +msgstr "[cuenta] contraseña" + +#: modules/commands/cs_updown.cpp:49 modules/commands/cs_updown.cpp:147 +msgid "[channel [nick]]" +msgstr "[canal [nick]]" + +#: modules/commands/ms_ignore.cpp:20 +msgid "[channel] ADD entry" +msgstr "[canal] ADD entrada" + +#: modules/commands/ms_ignore.cpp:21 +msgid "[channel] DEL entry" +msgstr "[canal] DEL entrada" + +#: modules/commands/ms_ignore.cpp:22 +msgid "[channel] LIST" +msgstr "[canal] LIST" + +#: modules/commands/ms_list.cpp:20 +msgid "[channel] [list | NEW]" +msgstr "[canal] [lista | NEW]" + +#: modules/extra/stats/cs_fantasy_stats.cpp:40 +msgid "[channel] [nick]" +msgstr "[canal] [nick]" + +#: modules/commands/ms_del.cpp:45 +msgid "[channel] {num | list | LAST | ALL}" +msgstr "[canal] {num | lista | LAST | ALL}" + +#: modules/commands/ms_read.cpp:113 +#, fuzzy +msgid "[channel] {num | list | LAST | NEW | ALL}" +msgstr "[canal] {num | lista | LAST | ALL}" + +#: modules/commands/hs_list.cpp:20 +msgid "[key|#X-Y]" +msgstr "[clave|#X-Y]" + +#: modules/commands/ms_info.cpp:20 +msgid "[nick | channel]" +msgstr "[nick | canal]" + +#: modules/commands/ns_group.cpp:237 +msgid "[nick]" +msgstr "[nick]" + +#: modules/commands/ns_logout.cpp:22 +msgid "[nickname [REVALIDATE]]" +msgstr "[nick [REVALIDATE]]" + +#: modules/commands/ns_alist.cpp:25 modules/commands/ns_status.cpp:20 +#: modules/commands/ns_info.cpp:20 +msgid "[nickname]" +msgstr "[nick]" + +#: modules/commands/ns_set_misc.cpp:96 +msgid "[parameter]" +msgstr "[parámetro]" + +#: modules/commands/os_logsearch.cpp:33 +msgid "[+daysd] [+limitl] pattern" +msgstr "[+díasd] [+límitel] patrón" + +#: modules/commands/os_chankill.cpp:22 +msgid "[+expiry] channel reason" +msgstr "[+expiración] canal razón" + +#: modules/commands/ns_list.cpp:110 +msgid "[Hostname hidden]" +msgstr "[Host oculto]" + +#: modules/commands/ns_list.cpp:112 modules/commands/cs_list.cpp:115 +msgid "[Suspended]" +msgstr "[Suspendido]" + +#: modules/commands/ns_list.cpp:114 +msgid "[Unconfirmed]" +msgstr "[No confirmado]" + +#: modules/commands/hs_request.cpp:213 +msgid "[auto memo] Your requested vHost has been approved." +msgstr "[auto memo] Tu vHost solicitado ha sido aprobado." + +#: modules/commands/hs_request.cpp:267 +msgid "[auto memo] Your requested vHost has been rejected." +msgstr "[auto memo] Tu vHost solicitado ha sido rechazado." + +#: modules/commands/hs_request.cpp:265 +#, c-format +msgid "[auto memo] Your requested vHost has been rejected. Reason: %s" +msgstr "[auto memo] Tu solicitud de vHost ha sido rechazada. Razón: %s" + +#: modules/commands/hs_request.cpp:388 +#, c-format +msgid "[auto memo] vHost %s has been requested by %s." +msgstr "[auto memo] El vHost %s ha sido solicitado por %s." + +#: modules/commands/os_list.cpp:133 +msgid "[{pattern | channel} [INVISIBLE]]" +msgstr "[{patrón | canal} [INVISIBLE]]" + +#: modules/commands/os_list.cpp:20 +msgid "[{pattern | nick} [SECRET]]" +msgstr "[{patrón | nick} [SECRET]]" + +#: src/misc.cpp:337 +msgid "day" +msgstr "día" + +#: src/misc.cpp:337 +msgid "days" +msgstr "días" + +#: include/language.h:88 +msgid "does not expire" +msgstr "no expira" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d day" +msgstr "expira en %d día" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d days" +msgstr "expira en %d días" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minute" +msgstr "expira en %d hora, %d minuto" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minutes" +msgstr "expira en %d hora, %d minutos" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minute" +msgstr "expira en %d horas, %d minuto" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minutes" +msgstr "expira en %d horas, %d minutos" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minute" +msgstr "expira en %d minuto" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minutes" +msgstr "expira en %d minutos" + +#: src/misc.cpp:375 +msgid "expires momentarily" +msgstr "expires momentaneamente" + +#: src/misc.cpp:343 +msgid "hour" +msgstr "hora" + +#: src/misc.cpp:343 +msgid "hours" +msgstr "horas" + +#: modules/extra/stats/cs_fantasy_stats.cpp:150 +#, c-format +msgid "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "letras: %s, palabras: %s, líneas: %s, smileys: %s, acciones: %s" + +#: src/misc.cpp:349 +msgid "minute" +msgstr "minuto" + +#: src/misc.cpp:349 +msgid "minutes" +msgstr "minutos" + +#: modules/commands/bs_info.cpp:87 +msgid "not assigned yet" +msgstr "no asignado aún" + +#: src/misc.cpp:324 +msgid "second" +msgstr "segundo" + +#: src/misc.cpp:324 +msgid "seconds" +msgstr "segundos" + +#: modules/commands/hs_request.cpp:215 +#, c-format +msgid "vHost for %s has been activated." +msgstr "El vHost para %s ha sido activado." + +#: modules/commands/hs_request.cpp:272 +#, c-format +msgid "vHost for %s has been rejected." +msgstr "El vHost para %s ha sido rechazado." + +#: modules/commands/hs_request.cpp:79 +msgid "vhost" +msgstr "vhost" + +#: modules/commands/hs_del.cpp:83 +#, c-format +msgid "vhosts for group %s have been removed." +msgstr "El vhost para el group %s ha sido eliminado." + +#: src/misc.cpp:331 +msgid "year" +msgstr "año" + +#: src/misc.cpp:331 +msgid "years" +msgstr "años" + +#: modules/commands/os_config.cpp:20 +msgid "{MODIFY|VIEW} [block name item name item value]" +msgstr "{MODIFY|VIEW} [nombre-bloque nombre-item valor-item]" + +#: modules/commands/bs_info.cpp:41 +msgid "{channel | nickname}" +msgstr "{canal | nick}" + +#: modules/commands/ms_cancel.cpp:20 +msgid "{nick | channel}" +msgstr "{nick | canal}" + +#: modules/commands/ms_rsend.cpp:25 modules/commands/ms_send.cpp:25 +msgid "{nick | channel} memo-text" +msgstr "{nick | canal} texto-del-memo" diff --git a/language/anope.fr_FR.po b/language/anope.fr_FR.po new file mode 100644 index 0000000..c301c62 --- /dev/null +++ b/language/anope.fr_FR.po @@ -0,0 +1,11321 @@ +# Anope IRC Services language file +# Copyright (C) 2011 +# This file is distributed under the same license as the Anope IRC Services package. +# Adam , 2011. +# +msgid "" +msgstr "" +"Project-Id-Version: Anope\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2020-01-06 18:19+0100\n" +"PO-Revision-Date: 2019-01-24 17:28+0100\n" +"Last-Translator: Thomas Fargeix \n" +"Language-Team: French\n" +"Language: fr_FR\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n > 1);\n" + +#: modules/commands/os_forbid.cpp:324 +#, c-format +msgid "%d channel(s) cleared, and %d channel(s) dropped." +msgstr "%d canau(x) vidé(s) et %d canau(x) supprimé(s)." + +#: modules/commands/os_forbid.cpp:265 +#, c-format +msgid "%d nickname(s) dropped." +msgstr "%d pseudo(s) effacé(s)." + +#: modules/commands/cs_xop.cpp:219 +#, c-format +msgid "%s added to %s %s list." +msgstr "%1$s ajouté à la liste des %3$s de %2$s." + +#: modules/commands/cs_access.cpp:225 +#, c-format +msgid "%s added to %s access list at level %d." +msgstr "%s ajouté à la liste d'accès de %s avec le niveau %d." + +#: modules/commands/cs_access.cpp:223 +#, c-format +msgid "%s added to %s access list at privilege %s (level %d)" +msgstr "%s ajouté à la liste d'accès de %s avec le privilège %s (niveau %d)" + +#: modules/commands/cs_akick.cpp:190 +#, c-format +msgid "%s added to %s autokick list." +msgstr "%s ajouté à la liste de kicks automatiques de %s." + +#: modules/commands/bs_badwords.cpp:307 +#, c-format +msgid "%s added to %s bad words list." +msgstr "%s ajouté à la liste des mots interdits de %s." + +#: modules/commands/ns_access.cpp:45 +#, c-format +msgid "%s added to %s's access list." +msgstr "%s ajouté à la liste d'accès de %s." + +#: modules/commands/ns_cert.cpp:204 +#, c-format +msgid "%s added to %s's certificate list." +msgstr "%s ajouté à la liste des certificats de %s." + +#: modules/commands/ms_ignore.cpp:62 +#, c-format +msgid "%s added to ignore list." +msgstr "%s ajouté à la liste d'ignore." + +#: modules/commands/os_sxline.cpp:415 modules/commands/os_sxline.cpp:649 +#, c-format +msgid "%s added to the %s list." +msgstr "%s ajouté à la liste des %s." + +#: modules/commands/os_akill.cpp:203 +#, c-format +msgid "%s added to the AKILL list." +msgstr "%s ajouté à la liste d'AKILL." + +#: modules/pseudoclients/botserv.cpp:134 +#, c-format +msgid "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands " +"that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" +msgstr "" +"%s vous permet d'exécuter les commandes \"fantaisie\" sur le canal.\n" +"Les commandes fantaisie sont des commandes qui peuvent être exécutées en\n" +"envoyant un message sur un canal, et fournissent une façon plus pratique " +"d'exécuter\n" +"les commandes. Les commandes qui nécessitent un paramètre de canal auront " +"ce\n" +"paramètre automatiquement.\n" + +#: modules/pseudoclients/botserv.cpp:148 +#, c-format +msgid "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s vous permet d'avoir un bot sur votre canal.\n" +"Il a été conçu pour les utilisateurs qui ne peuvent\n" +"pas héberger ou configurer un bot, ou pour\n" +"être utilisé sur les réseaux qui n'autorisent pas\n" +"les bots d'utilisateurs. Les commandes disponibles\n" +"sont listées ci-dessous. Pour les utiliser, tapez\n" +"%s%s commande. Pour plus d'informations sur\n" +"une commande spécifique, tapez %s%s %s commande.\n" + +#: modules/pseudoclients/nickserv.cpp:466 +#, c-format +msgid "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s vous permet d'enregistrer un pseudo et d'empêcher les\n" +"autres de l'utiliser. Les commandes suivantes permettent\n" +" l'enregistrement et la gestion des pseudos. Pour les\n" +"utiliser, tapez %s%s commande. Pour plus\n" +"d'informations sur une certaine commande, tapez\n" +"%s%s %s commande.\n" + +#: modules/pseudoclients/nickserv.cpp:473 +#, c-format +msgid "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s vous permet d'enregistrer un compte.\n" +"Les commandes suivantes permettent l'enregistrement et\n" +"la maintenance de comptes.\n" +"Pour les utiliser, tapez %s%s commande.\n" +"Pour plus d'informations sur une commande spécifique, tapez\n" +"%s%s %s commande.\n" + +#: modules/pseudoclients/chanserv.cpp:255 +#, c-format +msgid "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" +msgstr "" +"%s vous permet d'enregistrer et de contrôler divers\n" +"aspects des canaux. %s empêche souvent les utilisateurs\n" +"malveillants de faire des \"take overs\" sur les canaux\n" +"en limitant ceux qui sont autorisés à être OP.\n" +"Les commandes disponibles sont listées ci-dessous,\n" +"pour les utiliser, tapez %s%s commande. Pour plus \n" +"d'informations sur une commande spécifique, tapez\n" +"%s%s HELP commande.\n" + +#: modules/commands/bs_badwords.cpp:298 +#, c-format +msgid "%s already exists in %s bad words list." +msgstr "%s existe déjà dans la liste des mots interdits de %s." + +#: modules/commands/cs_akick.cpp:170 +#, c-format +msgid "%s already exists on %s autokick list." +msgstr "%s existe déjà dans la liste de kicks automatiques de %s." + +#: modules/commands/os_session.cpp:361 +#, c-format +msgid "%s already exists on the EXCEPTION list." +msgstr "%s existe déjà dans la liste des exceptions." + +#: modules/commands/bs_kick.cpp:214 modules/commands/bs_kick.cpp:389 +#: modules/commands/bs_kick.cpp:520 modules/commands/bs_kick.cpp:651 +#, c-format +msgid "%s cannot be taken as times to ban." +msgstr "%s ne peut être utilisé comme nombre de fois avant un ban." + +#: modules/commands/os_mode.cpp:163 +#, c-format +msgid "%s changed your usermodes to %s." +msgstr "%s a changé vos modes utilisateur en %s." + +#: modules/commands/os_list.cpp:47 +#, c-format +msgid "%s channel list:" +msgstr "Liste de canaux de %s :" + +#: modules/commands/cs_xop.cpp:343 +#, c-format +msgid "%s deleted from %s %s list." +msgstr "%1$s supprimé de la liste des %3$s de %2$s." + +#: modules/commands/cs_access.cpp:326 +#, c-format +msgid "%s deleted from %s access list." +msgstr "%s supprimé de la liste d'accès de %s." + +#: modules/commands/cs_akick.cpp:276 +#, c-format +msgid "%s deleted from %s autokick list." +msgstr "%s supprimé de la liste de kicks automatiques de %s." + +#: modules/commands/bs_badwords.cpp:348 +#, c-format +msgid "%s deleted from %s bad words list." +msgstr "%s supprimé de la liste des mots interdits de %s." + +#: modules/commands/ns_access.cpp:72 +#, c-format +msgid "%s deleted from %s's access list." +msgstr "%s supprimé de la liste d'accès de %s." + +#: modules/commands/ns_cert.cpp:233 +#, c-format +msgid "%s deleted from %s's certificate list." +msgstr "%s supprimé de la liste de certificats de %s." + +#: modules/commands/os_session.cpp:414 +#, c-format +msgid "%s deleted from session-limit exception list." +msgstr "%s supprimé de la liste des exceptions à la limitation de sessions." + +#: modules/commands/os_sxline.cpp:99 +#, c-format +msgid "%s deleted from the %s list." +msgstr "%s supprimé de la liste des %s." + +#: modules/commands/os_akill.cpp:246 +#, c-format +msgid "%s deleted from the AKILL list." +msgstr "%s supprimé de la liste d'AKILL." + +#: modules/commands/cs_access.cpp:685 +#, c-format +msgid "%s disabled on channel %s." +msgstr "Le niveau %s est maintenant désactivé sur le canal %s." + +#: modules/commands/cs_invite.cpp:75 +#, c-format +msgid "%s has been invited to %s." +msgstr "%s a été invité sur %s." + +#: modules/commands/os_svs.cpp:104 +#, c-format +msgid "%s has been joined to %s." +msgstr "%s a été JOIN à %s." + +#: modules/commands/os_svs.cpp:152 +#, c-format +msgid "%s has been parted from %s." +msgstr "%s a été PART de %s." + +#: modules/commands/cs_unban.cpp:96 +#, c-format +msgid "%s has been unbanned from %s." +msgstr "%s a été débanni de %s." + +#: modules/commands/ns_alist.cpp:110 +#, c-format +msgid "%s has no access in any channels." +msgstr "%s n'a accès à aucun canal." + +#: modules/commands/cs_status.cpp:55 +#, c-format +msgid "%s has no access on %s." +msgstr "%s n'a pas d'accès sur %s." + +#: modules/commands/cs_set.cpp:307 +#, c-format +msgid "%s has too many channels registered." +msgstr "%s a trop de canaux enregistrés." + +#: modules/commands/cs_status.cpp:51 +#, c-format +msgid "%s is a super administrator." +msgstr "%s est un super-administrateur." + +#: modules/pseudoclients/memoserv.cpp:214 +#, c-format +msgid "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" +msgstr "" +"%s est un utilitaire permettant aux utilisateurs IRC\n" +"d'envoyer de courts messages aux autres utilisateurs IRC,\n" +"qu'ils soient connectés à ce moment là ou non, ou aux \n" +"canaux(*). Le pseudo de l'expéditeur et du destinataire (ou\n" +"du canal) doivent être enregistrés pour pouvoir envoyer un\n" +"mémo.\n" +"Les commandes de %s sont :" + +#: modules/commands/cs_invite.cpp:66 +#, c-format +msgid "%s is already in %s!" +msgstr "%s est déjà sur %s ! " + +#: modules/commands/os_svs.cpp:99 +#, c-format +msgid "%s is already in %s." +msgstr "%s est déjà sur %s." + +#: modules/commands/ms_ignore.cpp:65 +#, c-format +msgid "%s is already on the ignore list." +msgstr "%s ajouté à votre liste d'ignore." + +#: modules/commands/cs_suspend.cpp:97 modules/commands/ns_suspend.cpp:106 +#, c-format +msgid "%s is already suspended." +msgstr "%s est déjà suspendu." + +#: modules/commands/ms_rsend.cpp:56 modules/commands/ms_send.cpp:55 +#, c-format +msgid "%s is not a registered unforbidden nick or channel." +msgstr "%s n'est pas un pseudo ou canal enregistré qui n'est pas interdit." + +#: modules/commands/cs_set.cpp:178 +#, c-format +msgid "%s is not a valid ban type." +msgstr "%s n'est pas un type de ban valide." + +#: modules/commands/bs_info.cpp:101 +#, c-format +msgid "%s is not a valid bot or registered channel." +msgstr "%s n'est pas un bot ou canal enregistré valide." + +#: include/language.h:86 +#, c-format +msgid "%s is not a valid e-mail address." +msgstr "%s n'est pas une adresse email valide." + +#: include/language.h:80 +#, c-format +msgid "%s is not currently on channel %s." +msgstr "%s n'est pas actuellement sur le canal %s." + +#: modules/commands/os_svs.cpp:144 +#, c-format +msgid "%s is not in %s." +msgstr "%s n'est pas sur %s." + +#: modules/commands/ms_ignore.cpp:77 +#, c-format +msgid "%s is not on the ignore list." +msgstr "%s n'a pas été trouvé dans la liste des ignorés." + +#: modules/commands/cs_status.cpp:90 +#, c-format +msgid "%s is on the auto kick list of %s (%s)." +msgstr "%s est dans la liste de kicks automatiques de %s (%s)." + +#: modules/commands/cs_status.cpp:53 +#, c-format +msgid "%s is the founder of %s." +msgstr "%s est le fondateur de %s." + +#: modules/commands/cs_status.cpp:78 +#, c-format +msgid "%s matches access entry %s (from entry %s), which has privilege %s." +msgstr "" +"%s correspond à l'entrée d'accès %s (venant de %s), qui a le privilège %s." + +#: modules/commands/cs_status.cpp:71 +#, c-format +msgid "%s matches access entry %s, which has privilege %s." +msgstr "%s correspond à l'entrée d'accès %s, qui a le privilège %s." + +#: include/language.h:109 +#, c-format +msgid "" +"%s matches an except on %s and cannot be banned until the except has been " +"removed." +msgstr "" +"%s correspond à une exception sur %s et ne peut pas être banni tant que " +"l'exception n'a pas été supprimée." + +#: modules/commands/cs_status.cpp:96 +#, c-format +msgid "%s matches auto kick entry %s on %s (%s)." +msgstr "%s correspond à l'entrée d'auto kick %s sur %s (%s)." + +#: modules/commands/cs_xop.cpp:353 +#, c-format +msgid "%s not found on %s %s list." +msgstr "%1$s introuvable sur la liste des %3$s de %2$s." + +#: modules/commands/cs_access.cpp:338 modules/commands/cs_flags.cpp:255 +#, c-format +msgid "%s not found on %s access list." +msgstr "%s introuvable sur la liste d'accès de %s." + +#: modules/commands/cs_akick.cpp:265 +#, c-format +msgid "%s not found on %s autokick list." +msgstr "%s introuvable sur la liste de kicks automatiques de %s." + +#: modules/commands/bs_badwords.cpp:341 +#, c-format +msgid "%s not found on %s bad words list." +msgstr "%s introuvable sur la liste des mots interdits de %s." + +#: modules/commands/ns_access.cpp:66 +#, c-format +msgid "%s not found on %s's access list." +msgstr "%s introuvable sur la liste d'accès de %s." + +#: modules/commands/ns_cert.cpp:226 +#, c-format +msgid "%s not found on %s's certificate list." +msgstr "%s introuvable dans la liste de certificats de %s." + +#: modules/commands/os_ignore.cpp:320 +#, c-format +msgid "%s not found on ignore list." +msgstr "%s n'a pas été trouvé dans la liste des ignorés." + +#: modules/commands/os_session.cpp:238 +#, c-format +msgid "" +"%s not found on session list, but has a limit of %d because it matches entry:" +" %s." +msgstr "" +"%s non trouvé sur la liste de sessions, mais a une limite de %d parce " +"l'entrée suivante correspond : %s." + +#: modules/commands/os_session.cpp:418 +#, c-format +msgid "%s not found on session-limit exception list." +msgstr "%s non trouvé sur la liste des exceptions à la limitation de sessions." + +#: modules/commands/os_sxline.cpp:92 +#, c-format +msgid "%s not found on the %s list." +msgstr "%s introuvable sur la liste des %s." + +#: modules/commands/os_akill.cpp:237 +#, c-format +msgid "%s not found on the AKILL list." +msgstr "%s introuvable sur la liste d'AKILL." + +#: modules/commands/cs_flags.cpp:251 +#, c-format +msgid "%s removed from the %s access list." +msgstr "%s supprimé de la liste d'accès de %s." + +#: modules/commands/ms_ignore.cpp:74 +#, c-format +msgid "%s removed from the ignore list." +msgstr "%s supprimé de la liste d'ignorés." + +#: modules/commands/os_list.cpp:157 +#, c-format +msgid "%s users list:" +msgstr "Liste des utilisateurs de %s :" + +#: modules/commands/os_ignore.cpp:316 +#, c-format +msgid "%s will no longer be ignored." +msgstr "%s n'est plus ignoré." + +#: modules/commands/os_ignore.cpp:238 +#, c-format +msgid "%s will now be ignored for %s." +msgstr "%s est ignoré pour %s." + +#: modules/commands/os_ignore.cpp:233 +#, c-format +msgid "%s will now permanently be ignored." +msgstr "%s est ignoré définitivement." + +#: include/language.h:66 +#, c-format +msgid "%s%s HELP %s for more information." +msgstr "%s%s HELP %s pour plus d'informations." + +#: modules/commands/bs_bot.cpp:270 +msgid "ADD nick user host real" +msgstr "ADD pseudo user host realname" + +#: modules/commands/bs_bot.cpp:271 +msgid "CHANGE oldnick newnick [user [host [real]]]" +msgstr "CHANGE ancien-pseudo nouveau-pseudo [user [host [realname]]]" + +#: modules/commands/bs_bot.cpp:272 +msgid "DEL nick" +msgstr "DEL pseudo" + +#: modules/commands/os_session.cpp:560 +msgid "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." +msgstr "" +"EXCEPTION ADD ajoute le masque donné à la liste des exceptions.\n" +"Notez que les masques pseudo!user@host et user@host sont invalides !\n" +"Seuls les masques d'hôtes réels, tels que box.host.dom ou *.host.dom,\n" +"sont autorisés parce que la limitation de sessions ne prend pas en compte " +"le\n" +"pseudo ou l'utilisateur. limite doit être un nombre supérieur ou égal à\n" +"zéro. Cette limite définit combien de sessions sont autorisées " +"simultanément\n" +"pour cet hôte. Une valeur de zéro signifie que l'hôte n'a pas de limite de\n" +"sessions. Consultez l'aide de AKILL pour les détails sur le format du\n" +"paramètre optionnel expiration.\n" +" \n" +"EXCEPTION DEL supprime le masque donné de la liste des exceptions.\n" +" \n" +"EXCEPTION LIST et EXCEPTION VIEW montrent toutes les \n" +"exceptions actuelles. Si un masque est indiqué, la liste ne montre que\n" +"les exceptions correspondantes au masque. La différence est que\n" +"EXCEPTION VIEW est plus détaillée, puisqu'elle affiche\n" +"également le pseudo de la personne qui a ajouté l'exception, la \n" +"limite de sessions, la raison, le masque et la date d'échéance.\n" +" \n" +"Notez qu'un client se connectant \"utilisera\" la première \n" +"exception à laquelle son hôte correspond." + +#: modules/commands/os_noop.cpp:68 +msgid "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." +msgstr "" +"SET kill tous les opérateurs du serveur indiqué\n" +"et empêche les opérateurs d'opérer sur le serveur indiqué.\n" +"REVOKE supprime cette restriction." + +#: modules/commands/cs_access.cpp:611 +#, c-format +msgid "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." +msgstr "" +"Les niveaux d'accès utilisateur peuvent être vus en utilisant\n" +"la commande %s. Tapez %s%s HELP LEVELS pour\n" +"plus d'informations." + +#: modules/commands/ms_read.cpp:35 +#, c-format +msgid "[auto-memo] The memo you sent to %s has been viewed." +msgstr "[auto-memo] Le mémo que vous avez envoyé a %s a été vu." + +#: modules/commands/ns_group.cpp:92 +msgid "[target] [password]" +msgstr "[cible] [motdepasse]" + +#: modules/commands/ns_set.cpp:453 +msgid "address" +msgstr "adresse" + +#: modules/commands/bs_set.cpp:162 +msgid "botname {ON|OFF}" +msgstr "nom-du-bot {ON|OFF}" + +#: modules/extra/stats/cs_fantasy_top.cpp:39 +#: modules/extra/stats/cs_fantasy_top.cpp:51 +#: modules/commands/cs_suspend.cpp:152 modules/commands/cs_sync.cpp:20 +#: modules/commands/cs_log.cpp:106 modules/commands/bs_assign.cpp:91 +#: modules/commands/cs_info.cpp:20 modules/commands/cs_getkey.cpp:20 +msgid "channel" +msgstr "canal" + +#: modules/commands/cs_set.cpp:138 +msgid "channel bantype" +msgstr "canal type-du-ban" + +#: modules/commands/cs_drop.cpp:20 +msgid "channel channel" +msgstr "canal canal" + +#: modules/commands/cs_log.cpp:107 +msgid "channel command method [status]" +msgstr "canal commande méthode [statut]" + +#: modules/commands/cs_kick.cpp:21 +msgid "channel mask [reason]" +msgstr "canal masque [raison]" + +#: modules/commands/os_mode.cpp:20 +msgid "channel modes" +msgstr "canal modes" + +#: modules/commands/cs_set.cpp:267 modules/commands/bs_assign.cpp:20 +msgid "channel nick" +msgstr "canal pseudo" + +#: modules/commands/cs_kick.cpp:20 +msgid "channel nick [reason]" +msgstr "canal pseudo [raison]" + +#: modules/commands/cs_clone.cpp:115 +msgid "channel target [what]" +msgstr "canal cible [quoi]" + +#: modules/commands/bs_control.cpp:20 modules/commands/bs_control.cpp:80 +msgid "channel text" +msgstr "canal texte" + +#: modules/commands/bs_set.cpp:91 +msgid "channel time" +msgstr "canal temps" + +#: modules/commands/os_kick.cpp:20 +msgid "channel user reason" +msgstr "canal utilisateur raison" + +#: modules/commands/cs_enforce.cpp:228 +msgid "channel what" +msgstr "canal [quoi]" + +#: modules/commands/cs_xop.cpp:481 +msgid "channel ADD mask" +msgstr "canal ADD masque" + +#: modules/commands/cs_access.cpp:499 +msgid "channel ADD mask level" +msgstr "canal ADD masque niveau" + +#: modules/commands/cs_entrymsg.cpp:194 +msgid "channel ADD message" +msgstr "canal ADD message" + +#: modules/commands/bs_badwords.cpp:371 +msgid "channel ADD word [SINGLE | START | END]" +msgstr "canal ADD mot [SINGLE | START | END]" + +#: modules/commands/cs_akick.cpp:435 +msgid "channel ADD {nick | mask} [reason]" +msgstr "canal ADD {pseudo | masque} [raison]" + +#: modules/commands/cs_topic.cpp:151 +msgid "channel APPEND topic" +msgstr "canal APPEND sujet" + +#: modules/commands/cs_access.cpp:503 modules/commands/cs_flags.cpp:376 +#: modules/commands/cs_xop.cpp:484 modules/commands/cs_entrymsg.cpp:197 +#: modules/commands/bs_badwords.cpp:374 modules/commands/cs_akick.cpp:440 +msgid "channel CLEAR" +msgstr "canal CLEAR" + +#: modules/commands/cs_mode.cpp:736 +msgid "channel CLEAR [what]" +msgstr "canal CLEAR [quoi]" + +#: modules/commands/os_mode.cpp:21 +msgid "channel CLEAR [ALL]" +msgstr "canal CLEAR [ALL]" + +#: modules/commands/cs_entrymsg.cpp:195 +msgid "channel DEL num" +msgstr "canal DEL num" + +#: modules/commands/cs_access.cpp:500 modules/commands/cs_xop.cpp:482 +msgid "channel DEL {mask | entry-num | list}" +msgstr "canal DEL {masque | numéro-entrée | liste}" + +#: modules/commands/cs_akick.cpp:436 +msgid "channel DEL {nick | mask | entry-num | list}" +msgstr "canal DEL {pseudo | masque | numéro-entrée | liste}" + +#: modules/commands/bs_badwords.cpp:372 +msgid "channel DEL {word | entry-num | list}" +msgstr "canal DEL {mot | numéro-entrée | liste}" + +#: modules/commands/cs_akick.cpp:439 +msgid "channel ENFORCE" +msgstr "canal ENFORCE" + +#: modules/commands/cs_access.cpp:744 modules/commands/cs_entrymsg.cpp:196 +msgid "channel LIST" +msgstr "canal LIST" + +#: modules/commands/cs_akick.cpp:437 +msgid "channel LIST [mask | entry-num | list]" +msgstr "canal LIST [masque | numéro-entrée | liste]" + +#: modules/commands/cs_access.cpp:501 modules/commands/cs_xop.cpp:483 +#: modules/commands/bs_badwords.cpp:373 +msgid "channel LIST [mask | list]" +msgstr "canal LIST [masque | liste]" + +#: modules/commands/cs_flags.cpp:375 +msgid "channel LIST [mask | +flags]" +msgstr "canal LIST [masque | +flags]" + +#: modules/commands/cs_mode.cpp:734 +msgid "channel LOCK {ADD|DEL|SET|LIST} [what]" +msgstr "canal LOCK {ADD|DEL|SET|LIST} [quoi]" + +#: modules/commands/cs_access.cpp:745 +msgid "channel RESET" +msgstr "canal RESET" + +#: modules/commands/cs_mode.cpp:735 +msgid "channel SET modes" +msgstr "canal SET modes" + +#: modules/commands/cs_access.cpp:742 +msgid "channel SET type level" +msgstr "canal SET type niveau" + +#: modules/commands/cs_akick.cpp:438 +msgid "channel VIEW [mask | entry-num | list]" +msgstr "canal VIEW [masque | numéro-entrée | liste]" + +#: modules/commands/cs_access.cpp:502 +msgid "channel VIEW [mask | list]" +msgstr "canal VIEW [masque | liste]" + +#: modules/commands/cs_register.cpp:20 modules/commands/cs_set.cpp:205 +msgid "channel [description]" +msgstr "canal [description]" + +#: modules/commands/cs_set.cpp:950 modules/commands/cs_invite.cpp:20 +#: modules/commands/cs_unban.cpp:20 +msgid "channel [nick]" +msgstr "canal [pseudo]" + +#: modules/commands/cs_set_misc.cpp:96 +msgid "channel [parameters]" +msgstr "canal [paramètres]" + +#: modules/commands/cs_mode.cpp:807 modules/commands/cs_status.cpp:20 +msgid "channel [user]" +msgstr "canal [user]" + +#: modules/commands/cs_suspend.cpp:59 +msgid "channel [+expiry] [reason]" +msgstr "canal [+expiration] [raison]" + +#: modules/commands/cs_ban.cpp:40 +msgid "channel [+expiry] {nick | mask} [reason]" +msgstr "canal [+expiration] {pseudo | masque} [raison]" + +#: modules/commands/cs_flags.cpp:374 +msgid "channel [MODIFY] mask changes" +msgstr "canal [MODIFY] masque modifications" + +#: modules/commands/cs_topic.cpp:150 +msgid "channel [SET] [topic]" +msgstr "canal [SET] [sujet]" + +#: modules/commands/cs_topic.cpp:152 +msgid "channel [UNLOCK|LOCK]" +msgstr "canal [UNLOCK|LOCK]" + +#: modules/fantasy.cpp:20 modules/commands/greet.cpp:20 +#: modules/commands/bs_assign.cpp:154 +msgid "channel {ON|OFF}" +msgstr "canal {ON|OFF}" + +#: modules/commands/bs_kick.cpp:491 +msgid "channel {ON|OFF} [ttb [ln [secs]]]" +msgstr "canal {ON|OFF} [ttb [ln [secs]]]" + +#: modules/commands/bs_kick.cpp:361 +msgid "channel {ON|OFF} [ttb [min [percent]]]" +msgstr "canal {ON|OFF} [ttb [min [pourcentage]]]" + +#: modules/commands/bs_kick.cpp:623 +msgid "channel {ON|OFF} [ttb [num]]" +msgstr "canal {ON|OFF} [ttb [num]]" + +#: modules/commands/bs_kick.cpp:252 modules/commands/bs_kick.cpp:288 +#: modules/commands/bs_kick.cpp:327 modules/commands/bs_kick.cpp:457 +#: modules/commands/bs_kick.cpp:589 modules/commands/bs_kick.cpp:724 +#: modules/commands/bs_kick.cpp:758 +msgid "channel {ON|OFF} [ttb]" +msgstr "canal {ON|OFF} [ttb]" + +#: modules/commands/cs_access.cpp:743 +msgid "channel {DIS | DISABLE} type" +msgstr "canal {DIS | DISABLE} type" + +#: modules/commands/cs_set.cpp:873 +msgid "channel {ON | LEVEL | OFF}" +msgstr "canal {ON | LEVEL | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:18 modules/commands/cs_set.cpp:75 +#: modules/commands/cs_set.cpp:336 modules/commands/cs_set.cpp:401 +#: modules/commands/cs_set.cpp:473 modules/commands/cs_set.cpp:622 +#: modules/commands/cs_set.cpp:684 modules/commands/cs_set.cpp:747 +#: modules/commands/cs_set.cpp:811 modules/commands/cs_set.cpp:1044 +#: modules/commands/bs_kick.cpp:792 modules/commands/bs_kick.cpp:857 +#: modules/commands/cs_topic.cpp:21 modules/commands/cs_list.cpp:181 +msgid "channel {ON | OFF}" +msgstr "canal {ON | OFF}" + +#: modules/commands/ns_getemail.cpp:24 +msgid "email" +msgstr "email" + +#: modules/commands/ns_set.cpp:794 +msgid "language" +msgstr "langue" + +#: modules/commands/ms_sendall.cpp:25 modules/commands/ms_staff.cpp:25 +msgid "memo-text" +msgstr "texte-mémo" + +#: modules/commands/gl_global.cpp:22 modules/commands/greet.cpp:84 +msgid "message" +msgstr "message" + +#: modules/commands/os_modinfo.cpp:20 modules/commands/os_module.cpp:20 +#: modules/commands/os_module.cpp:57 modules/commands/os_module.cpp:129 +msgid "modname" +msgstr "nom-module" + +#: modules/commands/ns_set.cpp:330 +msgid "new-display" +msgstr "nouvel-affichage" + +#: modules/commands/ns_set.cpp:120 +msgid "new-password" +msgstr "nouveau-motdepasse" + +#: modules/extra/stats/cs_fantasy_stats.cpp:52 modules/commands/hs_del.cpp:20 +#: modules/commands/hs_del.cpp:60 modules/commands/ms_check.cpp:20 +#: modules/commands/hs_request.cpp:192 modules/commands/cs_seen.cpp:262 +msgid "nick" +msgstr "pseudo" + +#: modules/commands/os_svs.cpp:79 +msgid "nick channel" +msgstr "pseudo canal" + +#: modules/commands/os_svs.cpp:123 +msgid "nick channel [reason]" +msgstr "pseudo canal [raison]" + +#: modules/commands/os_oline.cpp:20 +msgid "nick flags" +msgstr "pseudo flags" + +#: modules/commands/hs_set.cpp:20 modules/commands/hs_set.cpp:126 +msgid "nick hostmask" +msgstr "pseudo hostmask" + +#: modules/commands/os_svs.cpp:20 +msgid "nick newnick" +msgstr "pseudo nouveau-pseudo " + +#: modules/commands/hs_request.cpp:241 +msgid "nick [reason]" +msgstr "pseudo [raison]" + +#: modules/commands/ns_getpass.cpp:20 modules/commands/ns_drop.cpp:19 +#: modules/commands/ns_suspend.cpp:161 +msgid "nickname" +msgstr "pseudo" + +#: modules/commands/ns_set.cpp:546 +msgid "nickname address" +msgstr "pseudo adresse" + +#: modules/commands/ns_resetpass.cpp:22 +msgid "nickname email" +msgstr "pseudo email" + +#: modules/commands/ns_set.cpp:872 +msgid "nickname language" +msgstr "pseudo langue" + +#: modules/commands/greet.cpp:145 +msgid "nickname message" +msgstr "pseudo message" + +#: modules/commands/ns_set.cpp:399 +msgid "nickname new-display" +msgstr "pseudo nouvel-affichage" + +#: modules/commands/ns_set.cpp:173 +msgid "nickname new-password" +msgstr "pseudo nouveau-motdepasse" + +#: modules/commands/ns_set_misc.cpp:170 +msgid "nickname [parameter]" +msgstr "pseudo [paramètre]" + +#: modules/commands/ns_recover.cpp:150 +msgid "nickname [password]" +msgstr "pseudo [motdepasse]" + +#: modules/commands/ns_suspend.cpp:61 +msgid "nickname [+expiry] [reason]" +msgstr "pseudo [+expiration] [raison]" + +#: modules/commands/ns_info.cpp:239 +msgid "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +msgstr "pseudo {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:130 modules/commands/ns_set.cpp:302 +#: modules/commands/ns_set.cpp:631 modules/commands/ns_set.cpp:985 +#: modules/commands/ns_set.cpp:1076 modules/commands/ns_set.cpp:1105 +#: modules/commands/ns_list.cpp:252 +msgid "nickname {ON | OFF}" +msgstr "pseudo {ON | OFF}" + +#: modules/commands/ns_set.cpp:760 +msgid "nickname {ON | QUICK | IMMED | OFF}" +msgstr "pseudo {ON | QUICK | IMMED | OFF}" + +#: modules/commands/bs_set.cpp:20 +msgid "option (channel | bot) settings" +msgstr "option (canal | bot) paramètres" + +#: modules/commands/cs_set.cpp:21 +msgid "option channel parameters" +msgstr "option canal paramètres" + +#: modules/commands/bs_kick.cpp:120 +msgid "option channel {ON|OFF} [settings]" +msgstr "option canal {ON|OFF} [paramètres]" + +#: modules/commands/ns_set.cpp:75 +msgid "option nickname parameters" +msgstr "option pseudo paramètres" + +#: modules/commands/ms_set.cpp:207 modules/commands/ns_set.cpp:20 +msgid "option parameters" +msgstr "option paramètres" + +#: modules/commands/os_set.cpp:170 +msgid "option setting" +msgstr "option paramètre" + +#: modules/commands/ns_register.cpp:22 +msgid "passcode" +msgstr "mot-code" + +#: modules/commands/os_login.cpp:19 +msgid "password" +msgstr "motdepasse" + +#: modules/commands/ns_register.cpp:124 +msgid "password [email]" +msgstr "motdepasse [email]" + +#: modules/commands/ns_register.cpp:122 +msgid "password email" +msgstr "motdepasse email" + +#: modules/commands/cs_list.cpp:21 +msgid "pattern [SUSPENDED] [NOEXPIRE]" +msgstr "modèle [SUSPENDED] [NOEXPIRE]" + +#: modules/commands/ns_list.cpp:20 +msgid "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" +msgstr "modèle [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/os_jupe.cpp:20 +msgid "server [reason]" +msgstr "nom-du-serveur [raison]" + +#: modules/commands/os_mode.cpp:147 +msgid "user modes" +msgstr "pseudo modes" + +#: modules/commands/os_kill.cpp:20 +msgid "user [reason]" +msgstr "user [raison]" + +#: modules/commands/os_sxline.cpp:440 +msgid "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." +msgstr "" +" \n" +"SNLINE ADD ajoute le masque de realname indiqué à la liste des\n" +"SNLINE avec la raison indiquée (qui doit être précisée).\n" +"expiration est spécifiée par un nombre entier suivi d'un d\n" +"(jours), h (heures), ou m (minutes). Les combinaisons (comme\n" +"1h30m) ne sont pas permises. Si l'unité n'est pas indiquée,\n" +"la valeur par défaut est 'jours' (donc +30 signifie 30 jours).\n" +"Pour ajouter une SNLINE qui n'expire pas, utilisez +0. Si le\n" +"masque de realname à ajouter commence par un +, une échéance\n" +"doit être donnée, même si c'est la même que celle par défaut.\n" +"L'échéance de SNLINE par défaut peut être trouvée avec la commande\n" +"STATS AKILL.\n" +" \n" +"Note : Puisque le masque de realname peut contenir des espaces, le\n" +"séparateur entre le masque et la raison est le caractère ':'." + +#: modules/commands/os_sxline.cpp:678 +msgid "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +" \n" +"SQLINE ADD ajoute le masque de pseudo indiqué à la liste des\n" +"SQLINE avec la raison indiquée (qui doit être précisée).\n" +"expiration est spécifiée par un nombre entier suivi d'un d\n" +"(jours), h (heures), ou m (minutes). Les combinaisons (comme\n" +"1h30m) ne sont pas permises. Si l'unité n'est pas indiquée,\n" +"la valeur par défaut est 'jours' (donc +30 signifie 30 jours).\n" +"Pour ajouter une SQLINE qui n'expire pas, utilisez +0. Si le\n" +"masque à ajouter commence par un +, une échéance\n" +"doit être donnée, même si c'est la même que celle par défaut.\n" +"L'échéance de SQLINE par défaut peut être trouvée avec la commande\n" +"STATS AKILL." + +#: modules/pseudoclients/nickserv.cpp:492 +#, c-format +msgid "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." +msgstr "" +" \n" +"Les comptes qui ne sont plus utilisés sont sujets à \n" +"l'expiration automatique, c'est-à-dire qu'ils seront effacés\n" +"après %d jours de non utilisation." + +#: modules/pseudoclients/botserv.cpp:143 +msgid "" +" \n" +"Available commands are:" +msgstr "" +" \n" +"Les commandes disponibles sont :" + +#: modules/pseudoclients/botserv.cpp:167 +#, c-format +msgid "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." +msgstr "" +" \n" +"Le bot rejoindra le canal dès qu'il y a au moins\n" +"%d utilisateur(s) dessus." + +#: modules/fantasy.cpp:69 +#, c-format +msgid "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." +msgstr "" +" \n" +"Active ou désactive le mode fantaisie sur un\n" +"canal. Quand elle est active, cette option\n" +"permet aux utilisateurs d'utiliser les commandes\n" +"précédées par l'un des caractères suivants : %s\n" +" \n" +"Notez que les utilisateurs souhaitant utiliser\n" +"les commandes fantaisistes DOIVENT avoir\n" +"accès à la fois au niveau FANTASIA et le niveau\n" +"correspondant à la commande." + +#: modules/commands/greet.cpp:69 +msgid "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." +msgstr "" +" \n" +"Active ou désactive le mode message d'accueil\n" +"sur un canal. Quand elle est active, cette option\n" +"fait afficher au bot les messages d'accueil de chaque\n" +"utilisateur qui a un accès suffisant au canal." + +#: modules/commands/bs_kick.cpp:843 +msgid "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Active ou désactive la protection des OPs sur un \n" +"canal. Quand elle est active, cette option empêche\n" +"le bot de kicker les OPs même s'ils sont en-deçà\n" +"du niveau NOKICK." + +#: modules/commands/bs_kick.cpp:908 +msgid "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Active ou désactive la protection des Voices sur un \n" +"canal. Quand elle est active, cette option empêche\n" +"le bot de kicker les Voices même s'ils sont en-deçà\n" +"du niveau NOKICK." + +#: modules/pseudoclients/botserv.cpp:141 +#, c-format +msgid "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" +msgstr "" +" \n" +"Les commandes fantaisie peuvent être préfixées par un des caractères " +"suivant : %s\n" + +#: modules/commands/cs_register.cpp:105 +msgid "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." +msgstr "" +" \n" +"Note : pour enregistrer un canal, vous devez d'abord\n" +"enregistrer votre pseudo." + +#: modules/pseudoclients/chanserv.cpp:272 +#, c-format +msgid "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." +msgstr "" +" \n" +"Notez que tout canal non utilisé pendant %d jours\n" +"(c'est-à-dire une période pendant laquelle aucun\n" +"utilisateur figurant sur la liste d'accès du canal\n" +"ne vient sur le canal) il sera automatiquement effacé." + +#: modules/commands/cs_register.cpp:101 +#, c-format +msgid "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +msgstr "" +" \n" +"Voir la commande %s (%s%s HELP ACCESS) pour\n" +"plus d'informations sur comment donner des privilèges\n" +"à d'autres utilisateurs du canal.\n" + +#: modules/pseudoclients/nickserv.cpp:486 +msgid "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." +msgstr "" +" \n" +"Les Opérateurs des Services peuvent également effacer n'importe quel\n" +"pseudo et peuvent voir la liste d'accès pour n'importe quel pseudo." + +#: modules/pseudoclients/chanserv.cpp:277 +msgid "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." +msgstr "" +" \n" +"Les Opérateurs des Services peuvent aussi, en fonction de leurs\n" +"accès, effacer tout canal, voir (et modifier) les listes d'accès, des\n" +"niveaux et des kicks automatiques, ainsi que les paramètres de\n" +"tout canal." + +#: modules/commands/bs_set.cpp:147 +msgid "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." +msgstr "" +" \n" +"Définit le délai d'expiration des bans du bot. Si activé, tous les bans " +"placés par\n" +"les bots, par exemple pour les floods ou les mots interdis, seront " +"automatiquement\n" +"supprimés après le délai donné. Le définir à 0 désactive l'expiration " +"automatique des bans." + +#: modules/commands/cs_xop.cpp:542 +#, c-format +msgid "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." +msgstr "" +" \n" +"La commande %s ADD ajoute le pseudo donné à la liste\n" +"des %s.\n" +" \n" +"La commande %s DEL supprime le pseudo donné de la\n" +"liste des %s. Si des numéros d'entrées sont donnés, ces\n" +"entrées seront supprimées (voir l'exemple ci-dessous).\n" +" \n" +"La commande %s LIST affiche la liste %s. Si un masque\n" +"avec joker est fourni, seules les entrées qui correspondent au\n" +"masque seront affichées. Si une liste de numéros d'entrées est\n" +"donnée, seuls ces entrées seront affichées. Par exemple :\n" +" %s #canal LIST 2-5,7-9\n" +" Affiche les entrées de %s numérotées entre 2 et 5 puis\n" +" entre 7 et 9.\n" +" \n" +"La commande %s CLEAR vide les entrées de la liste\n" +"de %s." + +#: modules/commands/cs_akick.cpp:508 +#, c-format +msgid "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." +msgstr "" +" \n" +"La commande AKICK DEL supprime le pseudo ou masque\n" +"donné de la liste des kicks automatiques. Cependant, elle ne\n" +"supprime pas les bans placés par ceux-ci. Ils doivent être\n" +"supprimés manuellement.\n" +" \n" +"La commande AKICK LIST affiche la liste des kicks\n" +"automatique, ou éventuellement seulement ceux qui\n" +"correspondent au masque indiqué.\n" +" \n" +"La commande AKICK VIEW est une version plus détaillée\n" +"de la commande AKICK LIST.\n" +" \n" +"La commande AKICK ENFORCE fait appliquer la liste des\n" +"AKICK par %s en expulsant les utilisateurs qui correspondent à\n" +"un masque de la liste des kicks automatiques.\n" +" \n" +"La commande AKICK CLEAR vide la liste des kicks\n" +"automatiques." + +#: modules/commands/os_akill.cpp:448 +msgid "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." +msgstr "" +" \n" +"La commande AKILL DEL supprime le masque donné de\n" +"la liste des AKILL s'il y est présent. Si une liste de numéros d'entrées\n" +"est donnée, ces entrées seront supprimées (voir l'exemple pour LIST\n" +"ci-dessous).\n" +" \n" +"La commande AKILL LIST affiche la liste des AKILL.\n" +"Si un masque avec joker est donné, seuls les entrées correspondantes\n" +"sont affichées. Si une liste de numéros est donnée, seules ces entrées\n" +"sont affichées. Par exemple :\n" +" AKILL LIST 2-5,7-9\n" +" Liste les entrées d'AKILL numérotées entre 2 et 5 puis\n" +" entre 7 et 9.\n" +" \n" +"La commande AKILL VIEW est une version plus détaillée de\n" +"AKILL LIST. Elle montrera qui a ajouté un AKILL, la date d'ajout,\n" +"le délai d'expiration, ainsi que le masque user@host/ip et la raison.\n" +" \n" +"La commande AKILL CLEAR vide la liste des AKILL." + +#: modules/commands/os_sxline.cpp:462 +msgid "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." +msgstr "" +" \n" +"La commande SNLINE DEL supprime le masque donné de la\n" +"liste des SNLINE s'il y est présent. Si une liste de numéros d'entrée\n" +"est donnée, ces entrées seront supprimées (voir l'exemple pour LIST\n" +"ci-dessous).\n" +" \n" +"La commande SNLINE LIST affiche la liste des SNLINE.\n" +"Si un masque avec joker est donné, seuls les entrées correspondantes\n" +"sont affichées. Si une liste de numéros est donnée, seules ces entrées\n" +"sont affichées. Par exemple :\n" +" SNLINE LIST 2-5,7-9\n" +" Liste les entrées de SNLINE numérotées entre 2 et 5 puis\n" +" entre 7 et 9.\n" +" \n" +"SNLINE VIEW est une version plus détaillée de SNLINE LIST,\n" +"elle montrera qui a ajouté le masque, la date d'ajout et d'expiration,\n" +"ainsi que le masque de realname et la raison.\n" +" \n" +"SNLINE CLEAR vide toutes les entrées de la liste des SNLINE." + +#: modules/commands/os_sxline.cpp:697 +msgid "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." +msgstr "" +" \n" +"La commande SQLINE DEL supprime le masque donné de la\n" +"liste des SQLINE s'il y est présent. Si une liste de numéros d'entrée\n" +"est donnée, ces entrées seront supprimées (voir l'exemple pour LIST\n" +"ci-dessous).\n" +" \n" +"La commande SQLINE LIST affiche la liste des SQLINE.\n" +"Si un masque avec joker est donné, seuls les entrées correspondantes\n" +"sont affichées. Si une liste de numéros est donnée, seules ces entrées\n" +"sont affichées. Par exemple :\n" +" SQLINE LIST 2-5,7-9\n" +" Liste les entrées de SQLINE numérotées entre 2 et 5 puis\n" +" entre 7 et 9.\n" +" \n" +"SQLINE VIEW est une version plus détaillée de SQLINE LIST,\n" +"elle montrera qui a ajouté le masque, la date d'ajout et d'expiration,\n" +"ainsi que le masque et la raison.\n" +" \n" +"SQLINE CLEAR vide toutes les entrées de la liste des SQLINE." + +#: modules/commands/bs_assign.cpp:197 +msgid "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." +msgstr "" +" \n" +"Cette option empêche le canal de se voir attribuer un bot.\n" +"Si un bot est déjà attribué, il est enlevé automatiquement\n" +"quand vous activez l'option." + +#: modules/commands/bs_set.cpp:199 +msgid "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." +msgstr "" +" \n" +"Cette option empêche un bot d'être attribué à un\n" +"canal par des utilisateurs qui ne sont pas Opérateurs\n" +"IRC." + +#: modules/pseudoclients/memoserv.cpp:227 +#, c-format +msgid "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." +msgstr "" +" \n" +"Tapez %s%s HELP command pour obtenir de l'aide sur\n" +"les commandes ci-dessus." + +#: modules/commands/os_oper.cpp:167 +#, c-format +msgid " %s is online using this oper block." +msgstr " %s est connecté en utilisant ce bloc oper." + +#: modules/commands/os_modinfo.cpp:55 +#, c-format +msgid " Command %s on %s is linked to %s" +msgstr " La commande %s de %s est liée à %s" + +#: modules/commands/os_modinfo.cpp:43 +#, c-format +msgid " Providing service: %s" +msgstr " Fournit le service : %s" + +#: modules/commands/os_oper.cpp:163 +msgid " This oper is configured in the configuration file." +msgstr " Cet oper est configuré dans le fichier de configuration." + +#: modules/commands/os_modinfo.cpp:34 +#, c-format +msgid " Loaded at: %p" +msgstr " Chargé à : %p" + +#: modules/commands/cs_seen.cpp:303 +#, c-format +msgid " but %s mysteriously dematerialized." +msgstr " mais %s s'est mystérieusement dématérialisé." + +#: src/messages.cpp:339 +#, c-format +msgid "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." +msgstr "" +"\"/msg %s\" n'est plus supporté. Utilisez \"/msg %s@%s\" ou \"/%s\" à la " +"place." + +#: modules/commands/os_jupe.cpp:19 +msgid "\"Jupiter\" a server" +msgstr "\"Jupiter\" un serveur" + +#: modules/commands/os_oper.cpp:161 +#, c-format +msgid "%-8s %s" +msgstr "%-8s %s" + +#: modules/extra/stats/cs_fantasy_top.cpp:152 +#, c-format +msgid "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" +"%2lu %-16s lettres : %s, mots : %s, lignes : %s, smileys : %s, actions : %s" + +#: src/misc.cpp:359 +msgid "%b %d %H:%M:%S %Y %Z" +msgstr "%d %b %Y %H:%M:%S %Z" + +#: modules/commands/cs_log.cpp:205 +#, c-format +msgid "%c is an unknown status mode." +msgstr "%c est un mode de statut inconnu." + +#: modules/commands/cs_mode.cpp:431 +#, c-format +msgid "%c%c is not locked on %s." +msgstr "%c%c n'est pas verrouillé sur %s." + +#: modules/commands/cs_mode.cpp:427 +#, c-format +msgid "%c%c%s has been unlocked from %s." +msgstr "%c%c%s a été déverrouillé sur %s." + +#: modules/commands/cs_clone.cpp:56 +#, c-format +msgid "%d access entries from %s have been cloned to %s." +msgstr "%d accès de %s ont été clonés sur %s." + +#: modules/commands/bs_botlist.cpp:56 +#, c-format +msgid "%d bots available." +msgstr "%d bots disponibles." + +#: modules/commands/os_modinfo.cpp:189 +#, c-format +msgid "%d modules loaded." +msgstr "%d modules chargés." + +#: modules/commands/ns_group.cpp:357 +#, c-format +msgid "%d nickname(s) in the group." +msgstr "%d pseudo(s) dans le groupe." + +#: modules/commands/cs_seen.cpp:137 +#, c-format +msgid "%lu nicks are stored in the database, using %.2Lf kB of memory." +msgstr "" +"%lu pseudos sont stockés dans la base de données, utilisant %.2Lf ko de " +"mémoire." + +#: modules/commands/cs_xop.cpp:241 modules/commands/cs_xop.cpp:372 +#: modules/commands/cs_xop.cpp:450 +#, c-format +msgid "%s %s list is empty." +msgstr "La liste des %2$s de %1$s est vide." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1181 +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1201 +#: modules/commands/bs_kick.cpp:1211 +#, c-format +msgid "%s (%d kick(s) to ban)" +msgstr "%s (%d kick(s) pour un ban)" + +#: modules/commands/bs_kick.cpp:1161 +#, c-format +msgid "%s (%d kick(s) to ban; %d lines in %ds)" +msgstr "%s (%d kick(s) pour un ban, %d lignes en %ds)" + +#: modules/commands/bs_kick.cpp:1171 +#, c-format +msgid "%s (%d kick(s) to ban; %d times)" +msgstr "%s (%d kick(s) pour un ban, %d répétitions)" + +#: modules/commands/bs_kick.cpp:1141 +#, c-format +msgid "%s (%d kick(s) to ban; minimum %d/%d%%)" +msgstr "%s (%d kick(s) pour un ban ; minimum %d/%d%%)" + +#: modules/commands/bs_kick.cpp:1163 +#, c-format +msgid "%s (%d lines in %ds)" +msgstr "%s (%d lignes en %ds)" + +#: modules/commands/bs_kick.cpp:1173 +#, c-format +msgid "%s (%d times)" +msgstr "%s (%d répétitions)" + +#: modules/commands/cs_seen.cpp:358 +#, c-format +msgid "%s (%s) was kicked from %s (\"%s\") %s ago%s" +msgstr "%s (%s) a été kické de %s (\"%s\") il y a %s%s" + +#: modules/commands/cs_seen.cpp:355 +#, c-format +msgid "%s (%s) was kicked from a secret channel %s ago%s" +msgstr "%s (%s) a été kické d'un canal secret il y a %s%s" + +#: modules/commands/cs_seen.cpp:326 +#, c-format +msgid "%s (%s) was last seen changing nick from %s to %s %s ago%s" +msgstr "" +"%s (%s) a été vu pour la dernière fois, changeant son pseudo de %s en %s il " +"y a %s%s" + +#: modules/commands/cs_seen.cpp:321 +#, c-format +msgid "%s (%s) was last seen changing nick to %s %s ago%s" +msgstr "" +"%s (%s) a été vu pour la dernière fois, changeant son pseudo en %s il y a %s" +"%s" + +#: modules/commands/cs_seen.cpp:310 +#, c-format +msgid "%s (%s) was last seen connecting %s ago (%s)%s" +msgstr "%s (%s) s'est connecté pour la dernière fois il y a %s (%s)%s" + +#: modules/commands/cs_seen.cpp:335 +#, c-format +msgid "%s (%s) was last seen joining %s %s ago%s" +msgstr "%s (%s) a été vu pour la dernière fois, joignant %s il y a %s%s" + +#: modules/commands/cs_seen.cpp:332 +#, c-format +msgid "%s (%s) was last seen joining a secret channel %s ago%s" +msgstr "" +"%s (%s) a été vu pour la dernière fois, joignant un canal secret il y a %s%s" + +#: modules/commands/cs_seen.cpp:344 +#, c-format +msgid "%s (%s) was last seen parting %s %s ago%s" +msgstr "" +"%s (%s) a été vu pour la dernière fois, quittant le canal %s, il y a %s%s" + +#: modules/commands/cs_seen.cpp:341 +#, c-format +msgid "%s (%s) was last seen parting a secret channel %s ago%s" +msgstr "" +"%s (%s) a été vu pour la dernière fois, quittant un canal secret, il y a %s%s" + +#: modules/commands/cs_seen.cpp:349 +#, c-format +msgid "%s (%s) was last seen quitting (%s) %s ago (%s)." +msgstr "" +"%s (%s) a été vu pour la dernière fois, quittant le serveur (%s) il y a %s " +"(%s)." + +#: modules/commands/bs_kick.cpp:1143 +#, c-format +msgid "%s (minimum %d/%d%%)" +msgstr "%s (minimum %d/%d%%)" + +#: modules/commands/cs_access.cpp:245 modules/commands/cs_access.cpp:349 +#: modules/commands/cs_access.cpp:454 modules/commands/cs_access.cpp:467 +#: modules/commands/cs_flags.cpp:295 +#, c-format +msgid "%s access list is empty." +msgstr "La liste d'accès de %s est vide." + +#: modules/commands/ns_ajoin.cpp:184 +#, c-format +msgid "%s added to %s's auto join list." +msgstr "%s ajouté à la liste de JOIN automatiques de %s." + +#: src/xline.cpp:389 +#, c-format +msgid "%s already exists." +msgstr "%s existe déjà." + +#: modules/commands/cs_akick.cpp:202 modules/commands/cs_akick.cpp:387 +#: modules/commands/cs_akick.cpp:400 +#, c-format +msgid "%s autokick list is empty." +msgstr "La liste de kicks automatiques de %s est vide." + +#: modules/commands/bs_badwords.cpp:198 modules/commands/bs_badwords.cpp:316 +#, c-format +msgid "%s bad words list is empty." +msgstr "La liste des mots interdits de %s est vide." + +#: modules/commands/cs_set.cpp:993 +#, c-format +msgid "%s cannot be the successor on channel %s as they are the founder." +msgstr "%s ne peut être successeur du canal %s car il en est le fondateur." + +#: modules/pseudoclients/global.cpp:90 modules/pseudoclients/hostserv.cpp:78 +#: modules/pseudoclients/operserv.cpp:287 +#, c-format +msgid "%s commands:" +msgstr "Commandes %s :" + +#: include/language.h:69 +#, c-format +msgid "%s coverage is too wide; Please use a more specific mask." +msgstr "" +"%s correspond à trop d'utilisateurs. Merci d'indiquer un masque plus " +"spécifique." + +#: modules/commands/ms_info.cpp:94 +#, c-format +msgid "%s currently has %d memos, of which %d are unread." +msgstr "%s a actuellement %d mémos, dont %d n'ont pas été lus." + +#: modules/commands/ms_info.cpp:92 +#, c-format +msgid "%s currently has %d memos, of which 1 is unread." +msgstr "%s a actuellement %d mémos, dont 1 n'a pas été lu." + +#: modules/commands/ms_info.cpp:90 +#, c-format +msgid "%s currently has %d memos." +msgstr "%s a actuellement %d mémos." + +#: modules/commands/ms_info.cpp:88 +#, c-format +msgid "%s currently has %d memos; all of them are unread." +msgstr "%s a actuellement %d mémos, dont aucun n'a été lu." + +#: modules/commands/ms_info.cpp:77 +#, c-format +msgid "%s currently has 1 memo, and it has not yet been read." +msgstr "%s a actuellement 1 mémo, qui n'a pas encore été lu." + +#: modules/commands/ms_info.cpp:79 +#, c-format +msgid "%s currently has 1 memo." +msgstr "%s a actuellement 1 mémo." + +#: modules/commands/ms_info.cpp:73 +#, c-format +msgid "%s currently has no memos." +msgstr "%s n'a actuellement aucun mémo." + +#: modules/commands/os_forbid.cpp:344 +#, c-format +msgid "%s deleted from the %s forbid list." +msgstr "%s supprimé de la liste des %s interdits." + +#: include/language.h:105 +#, c-format +msgid "%s for %s set to %s." +msgstr "%s pour %s changé pour %s." + +#: include/language.h:106 +#, c-format +msgid "%s for %s unset." +msgstr "%s pour %s retiré." + +#: modules/commands/ns_ajoin.cpp:176 +#, c-format +msgid "%s had an invalid key specified, and was thus ignored." +msgstr "%s avait une clé de canal invalide spécifiée, et a été ignoré." + +#: modules/commands/ms_info.cpp:111 +#, c-format +msgid "%s has no memo limit." +msgstr "%s n'a aucune limitation de mémos." + +#: include/language.h:115 +#, c-format +msgid "%s has no memos." +msgstr "%s n'a aucun mémo." + +#: include/language.h:118 +#, c-format +msgid "%s has no new memos." +msgstr "%s n'a aucun nouveau mémo." + +#: modules/commands/ns_info.cpp:53 +#, c-format +msgid "%s is %s" +msgstr "%s est %s" + +#: modules/commands/ns_info.cpp:59 +#, c-format +msgid "%s is a Services Operator of type %s." +msgstr "%s est un Opérateur des Services du type %s." + +#: modules/commands/cs_seen.cpp:281 +#, c-format +msgid "%s is a client on services." +msgstr "%s est un client des services." + +#: modules/commands/cs_seen.cpp:200 +#, c-format +msgid "%s is a network service." +msgstr "%s est un service du réseau." + +#: src/xline.cpp:407 +#, c-format +msgid "%s is already covered by %s." +msgstr "%s est déjà couvert par %s." + +#: modules/commands/ns_ajoin.cpp:170 +#, c-format +msgid "%s is already on %s's auto join list." +msgstr "%s est déjà sur la liste de JOIN automatiques de %s." + +#: modules/commands/ns_info.cpp:56 +#, c-format +msgid "%s is an unconfirmed nickname." +msgstr "%s est un pseudo non confirmé." + +#: modules/commands/cs_flags.cpp:432 +#, c-format +msgid "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." +msgstr "" +"%s est une autre façon de modifier la liste d'accès du canal,\n" +"similaire aux méthodes XOP et ACCESS." + +#: modules/commands/ns_info.cpp:74 +#, c-format +msgid "%s is currently online." +msgstr "%s est actuellement connecté." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is disabled" +msgstr "%s est désactivé" + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is enabled" +msgstr "%s est activé" + +#: modules/commands/os_dns.cpp:507 +#, c-format +msgid "%s is not a valid IP address." +msgstr "%s n'est pas une adresse IP valide." + +#: modules/commands/cs_log.cpp:167 modules/commands/cs_log.cpp:192 +#, c-format +msgid "%s is not a valid command." +msgstr "%s n'est pas une commande valide." + +#: modules/commands/cs_log.cpp:198 +#, c-format +msgid "%s is not a valid logging method." +msgstr "%s n'est pas une méthode de log valide." + +#: modules/commands/ms_info.cpp:124 +#, c-format +msgid "%s is not notified of new memos." +msgstr "%s n'est pas notifié pour les nouveaux mémos." + +#: modules/commands/ms_info.cpp:118 +#, c-format +msgid "%s is notified of new memos at logon and when they arrive." +msgstr "" +"%s est notifié pour les nouveaux mémos quand ils arrivent et à la connexion." + +#: modules/commands/ms_info.cpp:122 +#, c-format +msgid "%s is notified of new memos at logon." +msgstr "%s est notifié pour les nouveaux mémos à la connexion." + +#: modules/commands/ms_info.cpp:120 +#, c-format +msgid "%s is notified when new memos arrive." +msgstr "%s est notifié quand de nouveaux mémos arrivent." + +#: modules/commands/cs_seen.cpp:232 +#, c-format +msgid "%s is on the channel right now (as %s)!" +msgstr "%s est sur le canal en ce moment (en tant que %s) !" + +#: modules/commands/cs_seen.cpp:221 +#, c-format +msgid "%s is on the channel right now!" +msgstr "%s est sur le canal en ce moment même !" + +#: modules/commands/cs_xop.cpp:434 +#, c-format +msgid "%s list for %s" +msgstr "Liste de %s pour %s" + +#: modules/commands/os_sxline.cpp:69 modules/commands/os_sxline.cpp:113 +#, c-format +msgid "%s list is empty." +msgstr "La liste des %s est vide." + +#: modules/commands/cs_mode.cpp:376 +#, c-format +msgid "%s locked on %s." +msgstr "%s est verrouillé sur %s." + +#: modules/extra/stats/cs_fantasy_stats.cpp:120 +#, c-format +msgid "%s not found." +msgstr "%s non trouvé." + +#: modules/commands/os_config.cpp:79 +#, c-format +msgid "%s settings:" +msgstr "Paramètres %s :" + +#: modules/commands/cs_seen.cpp:255 +#, c-format +msgid "%s was last seen here %s ago." +msgstr "%s a été vu il y a %s." + +#: modules/commands/ns_ajoin.cpp:213 +#, c-format +msgid "%s was not found on %s's auto join list." +msgstr "%s introuvable sur la liste de JOIN automatiques de %s." + +#: modules/commands/ns_ajoin.cpp:221 +#, c-format +msgid "%s was removed from %s's auto join list." +msgstr "%s supprimé de la liste de JOIN automatiques de %s." + +#: modules/commands/ms_set.cpp:64 +#, c-format +msgid "%s will not send you any notification of memos." +msgstr "%s ne vous enverra aucune notification de mémo." + +#: modules/commands/ms_set.cpp:42 +#, c-format +msgid "%s will now notify you of memos when they are sent to you." +msgstr "%s vous notifiera désormais des mémos quand ils vous seront envoyés." + +#: modules/commands/ms_set.cpp:30 +#, c-format +msgid "" +"%s will now notify you of memos when you log on and when they are sent to " +"you." +msgstr "" +"%s vous notifiera désormais des mémos quand vous vous connecterez et quand " +"ils vous seront envoyés." + +#: modules/commands/ms_set.cpp:36 +#, c-format +msgid "%s will now notify you of memos when you log on or unset /AWAY." +msgstr "" +"%s vous notifiera désormais des mémos quand vous vous connecterez ou " +"enlèverez /AWAY." + +#: modules/commands/bs_bot.cpp:89 +#, c-format +msgid "%s!%s@%s (%s) added to the bot list." +msgstr "%s!%s@%s (%s) ajouté à la liste des bots." + +#: modules/commands/ns_access.cpp:83 +#, c-format +msgid "%s's access list is empty." +msgstr "La liste d'accès de %s est vide." + +#: modules/commands/ns_ajoin.cpp:96 +#, c-format +msgid "%s's auto join list is empty." +msgstr "La liste de JOIN automatiques de %s est vide." + +#: modules/commands/ns_ajoin.cpp:111 +#, c-format +msgid "%s's auto join list:" +msgstr "Liste de JOIN automatiques de %s :" + +#: modules/commands/ns_cert.cpp:242 +#, c-format +msgid "%s's certificate list is empty." +msgstr "Liste de certificats de %s vide." + +#: modules/commands/ms_info.cpp:99 modules/commands/ms_info.cpp:106 +#, c-format +msgid "%s's memo limit is %d, and may not be changed." +msgstr "La limite de mémos de %s est de %d, et ne peut pas être changée." + +#: modules/commands/ms_info.cpp:101 modules/commands/ms_info.cpp:108 +#, c-format +msgid "%s's memo limit is %d." +msgstr "La limite de mémos de %s est de %d." + +#: src/misc.cpp:363 +#, c-format +msgid "(%s ago)" +msgstr "(il y a %s)" + +#: src/misc.cpp:365 +#, c-format +msgid "(%s from now)" +msgstr "(dans %s)" + +#: modules/commands/os_dns.cpp:244 +msgid "(Split)" +msgstr "(Déconnecté)" + +#: modules/commands/os_info.cpp:268 +#, c-format +msgid "(by %s on %s) %s" +msgstr "(par %s sur %s) %s" + +#: modules/commands/cs_access.cpp:710 +msgid "(disabled)" +msgstr "(désactivé)" + +#: modules/commands/cs_access.cpp:712 +msgid "(founder only)" +msgstr "(fondateur seulement)" + +#: src/misc.cpp:367 +msgid "(now)" +msgstr "(maintenant)" + +#: modules/commands/os_defcon.cpp:168 +msgid "* AKILL any new clients connecting" +msgstr "* AKILL tous les nouveaux clients qui se connectent" + +#: modules/commands/os_defcon.cpp:158 +#, c-format +msgid "* Force channel modes (%s) to be set on all channels" +msgstr "* Impose les modes %s sur tous les canaux." + +#: modules/commands/os_defcon.cpp:164 +msgid "* Ignore non-opers with a message" +msgstr "* Ignore les utilisateurs non opers avec un avertissement" + +#: modules/commands/os_defcon.cpp:162 +msgid "* Kill any new clients connecting" +msgstr "* Kill tous les nouveaux clients qui se connectent" + +#: modules/commands/os_defcon.cpp:156 +msgid "* No mode lock changes" +msgstr "* Pas de changement de modes verrouillés" + +#: modules/commands/os_defcon.cpp:152 +msgid "* No new channel registrations" +msgstr "* Pas d'enregistrement de nouveaux canaux" + +#: modules/commands/os_defcon.cpp:170 +msgid "* No new memos sent" +msgstr "* Pas d'envoi de nouveaux mémos" + +#: modules/commands/os_defcon.cpp:154 +msgid "* No new nick registrations" +msgstr "* Pas d'enregistrement de nouveaux pseudos" + +#: modules/commands/os_defcon.cpp:166 +msgid "* Silently ignore non-opers" +msgstr "* Ignore silencieusement les utilisateurs non opers" + +#: modules/commands/os_defcon.cpp:160 +#, c-format +msgid "* Use the reduced session limit of %d" +msgstr "* Réduction de la limite de sessions à %d" + +#: modules/commands/cs_seen.cpp:319 +#, c-format +msgid ", but %s mysteriously dematerialized." +msgstr ", mais %s s'est mystérieusement dématérialisé." + +#: modules/commands/cs_seen.cpp:317 +#, c-format +msgid ". %s is still online." +msgstr "%s est toujours connecté." + +#: include/language.h:87 +msgid "" +msgstr "" + +#: modules/commands/ns_set.cpp:504 +#, c-format +msgid "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." +msgstr "" +"Un mot-code a été envoyé à %s, merci de suivre les instructions que vous " +"avez reçu pour changer votre adresse email." + +#: modules/commands/ms_sendall.cpp:45 +msgid "A massmemo has been sent to all registered users." +msgstr "Un mémo de masse a été envoyé à tous les pseudos enregistrés." + +#: modules/commands/hs_request.cpp:285 +msgid "" +"A memo informing the user will also be sent, which includes the reason for " +"the rejection if supplied." +msgstr "" +"Un mémo informant l'utilisateur sera également envoyé, incluant la raison " +"pour le rejet, si elle a été communiquée." + +#: modules/commands/hs_request.cpp:229 +msgid "A memo informing the user will also be sent." +msgstr "Un mémo informant l'utilisateur sera également envoyé." + +#: modules/commands/ms_read.cpp:42 +#, c-format +msgid "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." +msgstr "Un accusé de réception a été envoyé a %s." + +#: include/language.h:123 +msgid "A vHost ident must be in the format of a valid ident." +msgstr "L'ident d'un vhost doit être d'un format valide pour un ident." + +#: include/language.h:122 +msgid "A vHost must be in the format of a valid hostname." +msgstr "Un vhost doit être d'un format valide pour un nom de domaine." + +#: modules/commands/os_ignore.cpp:342 +msgid "ADD expiry {nick|mask} [reason]" +msgstr "ADD expiration {pseudo|masque} [raison]" + +#: modules/commands/os_oper.cpp:70 +msgid "ADD oper type" +msgstr "ADD oper type" + +#: modules/commands/os_info.cpp:102 +msgid "ADD target info" +msgstr "ADD cible info" + +#: modules/commands/os_news.cpp:278 +msgid "ADD text" +msgstr "ADD texte" + +#: modules/commands/os_session.cpp:523 +msgid "ADD [+expiry] mask limit reason" +msgstr "ADD [+expiration] masque limite raison" + +#: modules/commands/ns_ajoin.cpp:231 +msgid "ADD [nickname] channel [key]" +msgstr "ADD [pseudo] canal [clé]" + +#: modules/commands/ns_access.cpp:102 +msgid "ADD [nickname] mask" +msgstr "ADD [pseudo] masque" + +#: modules/commands/ns_cert.cpp:258 +msgid "ADD [nickname] [fingerprint]" +msgstr "ADD [pseudo] [fingerprint]" + +#: modules/commands/os_sxline.cpp:659 modules/commands/os_akill.cpp:386 +msgid "ADD [+expiry] mask reason" +msgstr "ADD [+expiration] masque raison" + +#: modules/commands/os_sxline.cpp:425 +msgid "ADD [+expiry] mask:reason" +msgstr "ADD [+expiration] masque:raison" + +#: modules/commands/os_forbid.cpp:157 +msgid "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" +msgstr "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiration] entrée raison" + +#: modules/commands/os_dns.cpp:665 +msgid "ADDIP server.name ip" +msgstr "ADDIP nom.du.serveur ip" + +#: modules/commands/os_dns.cpp:663 +msgid "ADDSERVER server.name [zone.name]" +msgstr "ADDSERVER nom.du.serveur [nom.de.la.zone]" + +#: modules/commands/os_dns.cpp:661 +msgid "ADDZONE zone.name" +msgstr "ADDZONE nom.de.la.zone" + +#: modules/commands/cs_akick.cpp:38 +#, c-format +msgid "AKICK ENFORCE for %s complete; %d users were affected." +msgstr "" +"L'application des kicks automatiques pour %s est terminée : %d utilisateurs " +"expulsés." + +#: modules/commands/os_chankill.cpp:21 +msgid "AKILL all users on a specific channel" +msgstr "AKILL tous les utilisateurs d'un canal spécifique." + +#: modules/commands/os_akill.cpp:222 modules/commands/os_akill.cpp:339 +#: modules/commands/os_akill.cpp:353 +msgid "AKILL list is empty." +msgstr "La liste d'AKILL est vide." + +#: modules/commands/bs_kick.cpp:1211 modules/commands/bs_kick.cpp:1213 +#: modules/commands/bs_kick.cpp:1216 +msgid "AMSG kicker" +msgstr "Kicker d'AMSG" + +#: modules/commands/ns_alist.cpp:48 +msgid "Access" +msgstr "Accès" + +#: include/language.h:72 +msgid "Access denied." +msgstr "Accès refusé." + +#: modules/commands/cs_status.cpp:58 +#, c-format +msgid "Access for %s on %s:" +msgstr "Accès de %s sur %s :" + +#: include/language.h:107 +#, c-format +msgid "Access level must be between %d and %d inclusive." +msgstr "Le niveau doit être compris entre %d et %d inclus." + +#: modules/commands/cs_access.cpp:108 +msgid "Access level must be non-zero." +msgstr "Le niveau d'accès doit être différent de zéro." + +#: modules/commands/cs_access.cpp:694 +#, c-format +msgid "Access level settings for channel %s:" +msgstr "Configuration des niveaux d'accès du canal %s :" + +#: modules/commands/cs_access.cpp:734 +#, c-format +msgid "Access levels for %s reset to defaults." +msgstr "" +"Les niveaux d'accès de %s ont été réinitialisés à leur valeur par défaut." + +#: modules/commands/cs_access.cpp:439 modules/commands/ns_access.cpp:87 +#, c-format +msgid "Access list for %s:" +msgstr "Liste d'accès de %s :" + +#: modules/commands/help.cpp:166 +#, c-format +msgid "" +"Access to this command requires the permission %s to be present in your " +"opertype." +msgstr "" +"L'accès à cette commande requiert que la permission %s soit présente pour " +"votre type d'opérateur." + +#: modules/commands/ns_cert.cpp:368 modules/commands/ns_cert.cpp:392 +#: modules/commands/ns_identify.cpp:94 +#, c-format +msgid "" +"Account %s has already reached the maximum number of simultaneous logins " +"(%u)." +msgstr "" +"Le compte %s a déjà atteint le nombre maximum de connexions simultanées (%u)." + +#: modules/commands/cs_set.cpp:683 +msgid "Activate security features" +msgstr "Active les fonctions de sécurité" + +#: modules/commands/hs_request.cpp:227 +msgid "Activate the requested vHost for the given nick." +msgstr "Active la demande de vHost pour le pseudo donné." + +#: modules/commands/hs_on.cpp:55 +msgid "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." +msgstr "" +"Active le vhost actuellement configuré pour ce pseudo.\n" +"Lorsque vous utilisez cette commande, tous les utilisateurs\n" +"qui feront un /whois sur vous verront ce vhost à la place de\n" +"votre host ou votre adresse ip réels." + +#: modules/commands/hs_on.cpp:19 +msgid "Activates your assigned vhost" +msgstr "Active votre vHost assigné" + +#: modules/commands/os_info.cpp:243 +msgid "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." +msgstr "" +"Ajoute ou supprime des informations pour oper pour un canal ou un pseudo " +"donné.\n" +"Ces informations s'afficheront pour les opers dans les commandes INFO sur le " +"pseudo ou\n" +"le canal." + +#: modules/commands/os_dns.cpp:515 +#, c-format +msgid "Added IP %s to %s." +msgstr "Adresse IP %s ajoutée à %s." + +#: modules/commands/os_forbid.cpp:239 +#, c-format +msgid "Added a forbid on %s of type %s to expire on %s." +msgstr "Un interdit sur %s de type %s a été ajouté. Il expire le %s." + +#: modules/commands/os_info.cpp:164 +#, c-format +msgid "Added info to %s." +msgstr "Informations ajoutées à %s." + +#: modules/commands/os_news.cpp:34 +msgid "Added new logon news item." +msgstr "Nouvelle news de connexion ajoutée." + +#: modules/commands/os_news.cpp:44 +msgid "Added new oper news item." +msgstr "Nouvelle news pour opers ajoutée." + +#: modules/commands/os_news.cpp:54 +msgid "Added new random news item." +msgstr "News aléatoire ajoutée." + +#: modules/commands/os_dns.cpp:395 +#, c-format +msgid "Added server %s." +msgstr "Serveur %s ajouté." + +#: modules/commands/os_dns.cpp:300 +#, c-format +msgid "Added zone %s." +msgstr "Zone %s ajoutée." + +#: modules/commands/cs_entrymsg.cpp:257 +msgid "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." +msgstr "" +"Ajouter ou supprimer les messages d'entrées nécessite la\n" +"permission SET." + +#: modules/commands/ns_register.cpp:104 +msgid "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." +msgstr "" +"De plus, les Opérateurs des Services avec la permission nickserv/confirm\n" +"peuvent remplacer mot-code par un pseudo pour le valider." + +#: modules/pseudoclients/botserv.cpp:172 +#, c-format +msgid "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" +msgstr "" +"De plus, si la fantaisie est activée, des commandes\n" +"fantaisies peuvent être exécutées en préfixant la commande par\n" +"un des caractères suivants : %s" + +#: modules/commands/os_noop.cpp:58 +#, c-format +msgid "All O:lines of %s have been reset." +msgstr "Toutes les O:lines de %s ont été réinitialisées." + +#: modules/commands/cs_clone.cpp:71 +#, c-format +msgid "All akick entries from %s have been cloned to %s." +msgstr "Tous les kicks automatiques de %s ont été clonés sur %s." + +#: modules/commands/help.cpp:57 +#, c-format +msgid "All available commands for %s:" +msgstr "Toutes les commandes disponibles pour %s :" + +#: modules/commands/cs_clone.cpp:96 +#, c-format +msgid "All badword entries from %s have been cloned to %s." +msgstr "Tous les mots interdits de %s ont été clonés sur %s." + +#: modules/commands/cs_clone.cpp:108 +#, c-format +msgid "All level entries from %s have been cloned into %s." +msgstr "Toutes les niveaux d'accès de %s ont été clonés sur %s." + +#: modules/commands/os_news.cpp:38 +msgid "All logon news items deleted." +msgstr "Toutes les news de connexion ont été supprimées." + +#: modules/commands/ms_del.cpp:115 +#, c-format +msgid "All memos for channel %s have been deleted." +msgstr "Tous les mémos du canal %s ont été supprimés." + +#: modules/commands/os_mode.cpp:61 +#, c-format +msgid "All modes cleared on %s." +msgstr "Tous les modes ont été retirés de %s." + +#: modules/commands/ns_register.cpp:258 modules/commands/ns_register.cpp:389 +msgid "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." +msgstr "" +"Tous les nouveaux comptes doivent être validés par un administrateur. Merci " +"d'attendre que votre enregistrement soit confirmé." + +#: modules/commands/ms_del.cpp:119 +msgid "All of your memos have been deleted." +msgstr "Tous vos mémos ont été supprimés." + +#: modules/commands/os_news.cpp:48 +msgid "All oper news items deleted." +msgstr "Toutes les news pour opers ont été supprimées." + +#: modules/commands/os_noop.cpp:41 +#, c-format +msgid "All operators from %s have been removed." +msgstr "Tous les opérateurs de %s ont été supprimés." + +#: modules/commands/os_news.cpp:58 +msgid "All random news items deleted." +msgstr "Toutes les news aléatoires ont été supprimées." + +#: modules/commands/cs_clone.cpp:211 +#, c-format +msgid "All settings from %s have been cloned to %s." +msgstr "Tous les paramètres de %s ont été clonés sur %s." + +#: modules/commands/cs_sync.cpp:41 +#, c-format +msgid "All user modes on %s have been synced." +msgstr "Tous les modes utilisateurs de %s ont été synchronisés." + +#: modules/commands/hs_group.cpp:60 +#, c-format +msgid "All vhosts in the group %s have been set to %s." +msgstr "Tous les vhosts du groupe %s ont été changés en %s." + +#: modules/commands/hs_group.cpp:58 +#, c-format +msgid "All vhosts in the group %s have been set to %s@%s." +msgstr "Tous les vhosts du groupe %s ont été changés en %s@%s." + +#: src/access.cpp:40 +msgid "Allowed to (de)halfop him/herself" +msgstr "Autorisé à se (dé)halfop soi-même" + +#: src/access.cpp:39 +msgid "Allowed to (de)halfop users" +msgstr "Autorisé à (dé)halfoper des utilisateurs" + +#: src/access.cpp:48 +msgid "Allowed to (de)op him/herself" +msgstr "Autorisé à se (dé)oper soi-même" + +#: src/access.cpp:47 +msgid "Allowed to (de)op users" +msgstr "Autorisé à (dé)op des utilisateurs" + +#: src/access.cpp:50 +msgid "Allowed to (de)owner him/herself" +msgstr "Autorisé à se (dé)owner soi-même" + +#: src/access.cpp:49 +msgid "Allowed to (de)owner users" +msgstr "Autorisé à (dé)owner des utilisateurs" + +#: src/access.cpp:52 +msgid "Allowed to (de)protect him/herself" +msgstr "Autorisé à se (dé)protect soi-même" + +#: src/access.cpp:51 +msgid "Allowed to (de)protect users" +msgstr "Autorisé à (dé)protect des utilisateurs" + +#: src/access.cpp:59 +msgid "Allowed to (de)voice him/herself" +msgstr "Autorisé à se (dé)voice soi-même" + +#: src/access.cpp:58 +msgid "Allowed to (de)voice users" +msgstr "Autorisé à (dé)voicer des utilisateurs" + +#: src/access.cpp:27 +msgid "Allowed to assign/unassign a bot" +msgstr "Autorisé à assigner/désassigner un bot" + +#: src/access.cpp:34 +msgid "Allowed to ban users" +msgstr "Autorisé à bannir des utilisateurs" + +#: src/access.cpp:56 +msgid "Allowed to change channel topics" +msgstr "Autorisation de changer le sujet du canal" + +#: src/access.cpp:41 +msgid "Allowed to get full INFO output" +msgstr "Autorisé à voir toutes les infos avec INFO" + +#: src/access.cpp:36 +msgid "Allowed to issue commands restricted to channel founders" +msgstr "Autorisé à exécuter des commandes restreintes aux fondateurs" + +#: src/access.cpp:33 +msgid "Allowed to modify channel badwords list" +msgstr "Autorisé à modifier la liste des mots interdits du canal" + +#: src/access.cpp:24 +msgid "Allowed to modify the access list" +msgstr "Autorisé à modifier la liste d'accès" + +#: src/access.cpp:44 +msgid "Allowed to read channel memos" +msgstr "Autorisé à lire les mémos du canal" + +#: src/access.cpp:54 +msgid "Allowed to set channel settings" +msgstr "Autorisé à changer les paramètres du canal" + +#: src/access.cpp:57 +msgid "Allowed to unban users" +msgstr "Autorisé à débannir des utilisateurs" + +#: src/access.cpp:37 +msgid "Allowed to use GETKEY command" +msgstr "Autorisé à utiliser la commande GETKEY" + +#: src/access.cpp:53 +msgid "Allowed to use SAY and ACT commands" +msgstr "Autorisé à utiliser les commandes SAY et ACT" + +#: src/access.cpp:35 +msgid "Allowed to use fantasy commands" +msgstr "Autorisé à utiliser les commandes fantaisies." + +#: src/access.cpp:26 +msgid "Allowed to use the AKICK command" +msgstr "Autorisé à utiliser la commande AKICK" + +#: src/access.cpp:42 +msgid "Allowed to use the INVITE command" +msgstr "Autorisé à utiliser la commande INVITE" + +#: src/access.cpp:43 +msgid "Allowed to use the KICK command" +msgstr "Autorisé à utiliser la commande KICK" + +#: src/access.cpp:45 +msgid "Allowed to use the MODE command" +msgstr "Autorisé à utiliser la commande MODE" + +#: src/access.cpp:25 +msgid "Allowed to view the access list" +msgstr "Autorisé à voir la liste d'accès" + +#: modules/commands/gl_global.cpp:42 +#, c-format +msgid "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." +msgstr "" +"Permet aux Administrateurs d'envoyer des messages à tous\n" +"les utilisateurs connectés au réseau. Le message sera envoyé\n" +"avec le pseudo %s." + +#: modules/commands/os_mode.cpp:133 +msgid "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." +msgstr "" +"Permet aux Opérateurs des Services de changer n'importe quel mode\n" +"de n'importe quel canal. Les paramètres sont les mêmes que la commande\n" +"/MODE normale. On peut aussi indiquer CLEAR pour vider tous les modes du\n" +"canal. Si CLEAR ALL est indiqué, alors tous les modes et statuts des\n" +"utilisateurs sont supprimés." + +#: modules/commands/os_mode.cpp:173 +msgid "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." +msgstr "" +"Permet aux Opérateurs des Services de changer les modes de n'importe\n" +"quel utilisateur. Les paramètres sont les mêmes que pour la commande\n" +"/MODE normale." + +#: modules/commands/bs_bot.cpp:352 +msgid "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." +msgstr "" +"Permet aux Opérateurs des Services de créer, modifier, et\n" +"supprimer les bots que les utilisateurs pourront\n" +"utiliser sur leurs canaux.\n" +" \n" +"BOT ADD ajoute un bot avec les pseudo, username, hostname\n" +"et realname donnés. Aucun test de validité n'est effectué\n" +"pour ces données, donc faites très attention.\n" +" \n" +"BOT CHANGE permet de changer le pseudo, username, hostname\n" +"ou realname d'un bot tout en conservant les données qui\n" +"lui sont associées.\n" +" \n" +"BOT DEL supprime le bot donné de la liste des bots.\n" +" \n" +"Note: vous ne pouvez pas créer un bot avec un pseudo\n" +"déjà enregistré. Si un utilisateur utilise le pseudo sans l'avoir\n" +" enregistré, il sera déconnecté lors de la création du bot." + +#: modules/commands/os_oline.cpp:56 +msgid "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." +msgstr "" +"Permet aux Opérateurs des Services de mettre des Operflags à un " +"utilisateur.\n" +"Les flags doivent être préfixés de : \"+\" ou \"-\". \n" +"Pour supprimer tous les flags, indiquez seulement \"-\" à la place." + +#: modules/commands/os_ignore.cpp:370 +msgid "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." +msgstr "" +"Permet aux Opérateurs des Services de faire en sorte que les services\n" +"ignorent un pseudo ou un masque pour un certain temps ou jusqu'au\n" +"prochain redémarrage. Le format par défaut pour la durée est en\n" +"secondes. Vous pouvez toutefois le définir différemment. Les unités\n" +"valides sont: s pour secondes, m pour minutes, h pour heures\n" +"et d pour jours. Il n'est pas possible de combiner ces unités.\n" +"Pour ignorer cet utilisateur de façon permanente, indiquez 0 comme durée.\n" +"Pour ajouter un masque, vous devez le définir au format user@host\n" +"ou pseudo!user@host, n'importe quoi d'autre sera considéré comme un\n" +"pseudo. Les jokers sont autorisés.\n" +" \n" +"Cette commande ne fonctionnera pas sur les Opérateurs IRC." + +#: modules/commands/os_akill.cpp:420 +msgid "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Permet aux Opérateurs des Services de manipuler la liste\n" +"d'AKILL. Si un utilisateur correspondant à un masque d'AKILL\n" +"tente de se connecter, les Services enverront un KILL pour\n" +"cet utilisateur et, sur les serveurs le supportant, demandera\n" +"à tous les serveurs d'ajouter un ban du masque qui correspondait.\n" +" \n" +"AKILL ADD ajoute le masque user@host donné à la liste \n" +"d'AKILL pour la raison précisée (qui doit être donnée).\n" +"échéance est un nombre entier suivi par un d (jours), h\n" +"(heures), ou m (minutes). Les combinaisons (telles que\n" +"1h30m) ne sont pas permises. Si l'unité n'est pas incluse,\n" +"la valeur est en jours par défaut (donc +30 est équivalent\n" +"à 30 jours). Pour ajouter une AKILL qui n'expire pas, utilisez\n" +"+0. Si le masque utilisateur à ajouter commence par un +,\n" +"une échéance doit être donnée, même si c'est la même que\n" +"celle par défaut. L'échéance par défaut pour les AKILLs peut \n" +"être consultée par la commande STATS AKILL." + +#: modules/commands/os_sxline.cpp:436 +msgid "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." +msgstr "" +"Permet aux Opérateurs des Services de manipuler la liste des SNLINE.\n" +"Si un utilisateur avec un realname correspond à un masque SNLINE tente\n" +"de se connecter, les Services n'autoriseront pas la session IRC\n" +"à se poursuivre." + +#: modules/commands/os_sxline.cpp:670 +msgid "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." +msgstr "" +"Permet aux Opérateurs des Services de manipuler la liste de SQLINE.\n" +"Si un utilisateur avec un pseudo correspondant à un masque SQLINE\n" +"tente de se connecter, les Services le déconnecteront.\n" +"Si le premier caractère du masque est #, les services empêcheront\n" +"d'utiliser les canaux correspondants au masque. Si le masque est\n" +"une expression régulière, elle sera utilisée pour bloquer des\n" +"canaux." + +#: modules/commands/os_session.cpp:551 +msgid "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." +msgstr "" +"Permet aux Opérateurs des Services de manipuler la liste de hosts qui\n" +"ont une limite de sessions spécifique, autorisant certaines machines,\n" +"comme les hébergeurs de shell, à avoir plus du nombre par défaut\n" +"de clients à la fois. Une fois qu'un host atteint la limite de sessions,\n" +"tous les clients qui tentent de se connecter depuis ce host seront\n" +"killés. Avant que l'utilisateur soit killé, on lui envoie une notice\n" +"d'aide sur les limites de sessions. Le contenu de la notice est\n" +"défini dans la configuration." + +#: modules/commands/os_session.cpp:270 +msgid "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." +msgstr "" +"Permet aux Opérateurs des Services de voir la liste des sessions.\n" +" \n" +"SESSION LIST liste les hôtes ayant au minimum seuil\n" +"sessions. La limite minimale doit être un nombre supérieur à 1,\n" +"afin d'éviter d'afficher un très grand nombre d'hôtes avec uneseule " +"session.\n" +" \n" +"SESSION VIEW affiche des informations détaillées sur un\n" +"hôte spécifique, notamment le nombre de sessions actuelles\n" +"ainsi que la limite de sessions. La valeur host ne peut\n" +"pas contenir de joker.\n" +" \n" +"Consultez l'aide de EXCEPTION pour plus d'informations \n" +"concernant la limitation et comment définir les limites de\n" +"sessions pour certains hôtes et groupes d'hôtes." + +#: modules/commands/cs_topic.cpp:193 +msgid "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do " +"not have\n" +"the TOPIC privilege." +msgstr "" +"Permet de manipuler le topic du canal indiqué.\n" +"La commande SET définit le topic du canal avec le topic donné\n" +"ou retire le topic, si aucun n'est donné. La commande APPEND\n" +"ajoute le topic donné à la fin du topic existant.\n" +" \n" +"LOCK et UNLOCK peuvent être utilisés pour activer ou désactiver\n" +"le verrouillage du topic. Lorsque le topic est bloqué, il ne sera pas " +"modifiable,\n" +"sauf par les utilisateurs qui ont le privilège TOPIC." + +#: modules/commands/os_kick.cpp:62 +#, c-format +msgid "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" +msgstr "" +"Permet au staff de kicker un utilisateur d'un canal.\n" +"Les paramètres sont les mêmes que pour la commande /KICK\n" +"normale. Le message de kick sera préfixé par le pseudo de\n" +"l'IRCop ayant utilisé la commande KICK, par exemple :\n" +" \n" +"*** SpamMan a été kické du canal #canal par %s (Alcan (Flood))" + +#: modules/commands/cs_set.cpp:33 +msgid "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" +msgstr "" +"Permet au fondateur du canal de configurer diverses options\n" +"du canal et d'autres informations.\n" +" \n" +"Options disponibles :" + +#: modules/commands/os_oper.cpp:250 +msgid "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." +msgstr "" +"Vous permet de voir et de modifier les Opérateurs des Services.\n" +"Notez que les opérateurs supprimés par cette commande mais\n" +"toujours présents dans le fichier de configuration ne sont pas supprimés\n" +"de manière permanente." + +#: modules/commands/os_config.cpp:127 +msgid "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" +msgstr "" +"Vous permet de voir et de modifier les paramètres de configuration.\n" +"Les paramètres modifiés par cette commande le sont temporairement\n" +"et ne seront pas sauvegardés dans le fichier de configuration. Ils seront " +"perdus\n" +"si Anope est arrêté, redémarré ou que la configuration est rechargée.\n" +" \n" +"Exemple :\n" +" MODIFY nickserv forcemail no" + +#: modules/commands/ns_set.cpp:992 +msgid "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." +msgstr "" +"Vous permet de choisir la façon dont les Services communiquent avec\n" +"le pseudo donné. Si MSG est activé, ils utiliseront des messages,\n" +"sinon ils utiliseront des notices." + +#: modules/commands/ns_set.cpp:966 +#, c-format +msgid "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." +msgstr "" +"Vous permet de choisir la façon dont les Services communiquent\n" +"avec vous. Si %s est activé, les services utiliseront des\n" +"messages, sinon ils utiliseront des notices." + +#: modules/commands/ms_ignore.cpp:113 +msgid "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." +msgstr "" +"Vous permet d'ignorer les mémos des utilisateurs par pseudo ou host\n" +"envoyés à un canal ou à vous-même. Si quelqu'un sur la liste des ignorés\n" +"essaye de vous envoyer un mémo (ou à un canal), il ne sera pas averti que\n" +"vous l'avez ignoré." + +#: modules/commands/os_kill.cpp:48 +msgid "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." +msgstr "" +"Vous permet de killer un utilisateur du réseau.\n" +"Les paramètres sont les mêmes que pour la commande /KILL\n" +"normale." + +#: modules/commands/ns_info.cpp:252 +#, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Vous permet d'empêcher l'affichage de certaines informations\n" +"quand quelqu'un fait un %s INFO sur le pseudo indiqué. Vous pouvez\n" +"cacher son adresse email (EMAIL), son dernier masque\n" +"user@host utilisé (USERMASK), son statut d'accès aux services\n" +"(STATUS) et sa dernière raison de /QUIT (QUIT).\n" +"Le second paramètre indique si l'option doit être affichée\n" +"(OFF) ou cachée (ON)." + +#: modules/commands/ns_info.cpp:223 +#, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Vous permet d'empêcher l'affichage de certaines informations\n" +"quand quelqu'un fait un %s INFO sur votre pseudo. Vous pouvez\n" +"cacher votre adresse email (EMAIL), votre dernier masque\n" +"user@host utilisé (USERMASK), votre statut d'accès aux services\n" +"(STATUS) et votre dernière raison de /QUIT (QUIT).\n" +"Le second paramètre indique si l'option doit être affichée\n" +"(OFF) ou cachée (ON)." + +#: modules/commands/bs_info.cpp:118 +#, c-format +msgid "Allows you to see %s information about a channel or a bot" +msgstr "" +"Vous permet de voir les informations de %s à propos d'un canal ou d'un bot" + +#: modules/commands/bs_info.cpp:108 +#, c-format +msgid "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." +msgstr "" +"Vous permet de voir les informations de %s pour un canal\n" +"ou un bot. Si le paramètre est un canal, vous verrez\n" +"des informations sur le canal telles que les kickers\n" +"actifs. Si le paramètre est un pseudo, vous verrez des\n" +"informations à propos d'un bot, comme le temps de\n" +"création ou le nombre de canaux auxquels il a été\n" +"assigné." + +#: modules/commands/cs_xop.cpp:567 +msgid "" +"Alternative methods of modifying channel access lists are\n" +"available. " +msgstr "" +"Des méthodes alternatives de modification de la liste d'accès sont\n" +"disponibles." + +#: modules/commands/hs_request.cpp:191 +msgid "Approve the requested vHost of a user" +msgstr "Approuve la requête de vHost d'un utilisateur" + +#: modules/commands/ns_drop.cpp:68 +msgid "As a Services Operator, you may drop any nick." +msgstr "" +"En tant qu'Opérateur des Services vous pouvez supprimer n'importe quel " +"pseudo." + +#: modules/commands/bs_assign.cpp:19 +msgid "Assigns a bot to a channel" +msgstr "Attribue un bot à un canal" + +#: modules/commands/bs_assign.cpp:78 +msgid "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." +msgstr "" +"Attribue le bot désigné au canal. Vous pouvez\n" +"ensuite configurer le bot pour qu'il convienne à\n" +"vos besoins sur ce canal." + +#: data/chanserv.example.conf:1197 +msgid "Associate a URL with the channel" +msgstr "Associe un URL à un canal" + +#: data/nickserv.example.conf:594 +msgid "Associate a URL with this account" +msgstr "Associe un URL avec ce compte" + +#: data/nickserv.example.conf:593 +msgid "Associate a URL with your account" +msgstr "Attribue un URL à votre compte" + +#: modules/commands/greet.cpp:83 +msgid "Associate a greet message with your nickname" +msgstr "Associe un message d'accueil à votre pseudo" + +#: data/chanserv.example.conf:1198 +msgid "Associate an E-mail address with the channel" +msgstr "Associe une adresse email au canal" + +#: modules/commands/ns_set.cpp:452 +msgid "Associate an E-mail address with your nickname" +msgstr "Associe une adresse email à votre pseudo" + +#: modules/commands/os_info.cpp:101 +msgid "Associate oper info with a nick or channel" +msgstr "Associe une info oper à un pseudo ou un canal" + +#: modules/commands/ns_set.cpp:558 +msgid "Associates the given E-mail address with the nickname." +msgstr "Associe une adresse email donnée à un pseudo" + +#: modules/commands/ns_set.cpp:533 +msgid "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." +msgstr "" +"Associe l'email donnée avec votre pseudo. L'adresse email\n" +"sera affichée lorsque quelqu'un demandera des informations \n" +"sur votre pseudo avec la commande INFO." + +#: modules/commands/ns_set.cpp:1315 +msgid "Auto-op" +msgstr "Auto-op" + +#: modules/commands/cs_akick.cpp:374 +#, c-format +msgid "Autokick list for %s:" +msgstr "Liste de kicks automatiques de %s :" + +#: src/access.cpp:29 +msgid "Automatic channel operator status upon join" +msgstr "Statut d'opérateur automatique lors du join" + +#: src/access.cpp:28 +msgid "Automatic halfop upon join" +msgstr "Halfop automatique lors du join" + +#: src/access.cpp:30 +msgid "Automatic owner upon join" +msgstr "Owner automatique lors du join" + +#: src/access.cpp:31 +msgid "Automatic protect upon join" +msgstr "Protect automatique lors du join" + +#: src/access.cpp:32 +msgid "Automatic voice on join" +msgstr "Voice automatique lors du join" + +#: modules/commands/os_oper.cpp:196 +#, c-format +msgid "Available commands for %s:" +msgstr "Aide disponible pour %s :" + +#: modules/commands/os_oper.cpp:175 +msgid "Available opertypes:" +msgstr "Types d'opérateurs disponibles :" + +#: modules/commands/os_oper.cpp:218 +#, c-format +msgid "Available privileges for %s:" +msgstr "Privilèges disponibles pour %s :" + +#: modules/commands/cs_enforce.cpp:162 +msgid "BANS enforced by " +msgstr "Bans appliqués par" + +#: modules/commands/bs_kick.cpp:1121 modules/commands/bs_kick.cpp:1123 +#: modules/commands/bs_kick.cpp:1126 +msgid "Bad words kicker" +msgstr "Kicker de mots interdits" + +#: modules/commands/bs_badwords.cpp:252 +#, c-format +msgid "Bad words list for %s:" +msgstr "Liste de mots interdits sur %s :" + +#: modules/commands/bs_badwords.cpp:364 +msgid "Bad words list is now empty." +msgstr "La liste des mots interdits est maintenant vide." + +#: modules/commands/bs_set.cpp:129 +msgid "Ban expiry may not be longer than 1 day." +msgstr "Le délai d'expiration ne peut pas être plus d'un jour." + +#: modules/commands/cs_ban.cpp:140 modules/commands/cs_ban.cpp:175 +#, c-format +msgid "Ban on %s expires in %s." +msgstr "Le ban sur %s expire dans %s." + +#: modules/commands/cs_info.cpp:60 +msgid "Ban type" +msgstr "Type de ban" + +#: modules/commands/cs_set.cpp:174 +#, c-format +msgid "Ban type for channel %s is now #%d." +msgstr "Le type de ban du canal %s est maintenant le numéro %d." + +#: modules/commands/cs_ban.cpp:39 +msgid "Bans a given nick or mask on a channel" +msgstr "Bannit un pseudo ou un masque sur un canal" + +#: modules/commands/cs_ban.cpp:227 +msgid "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." +msgstr "" +"Bannit le pseudo ou le masque désigné sur un canal.\n" +"Un temps d'expiration peut être donné pour que les\n" +"services suppriment ce ban après ce délai.\n" +" \n" +"Par défaut, limité aux AOPs ou à ceux ayant un niveau \n" +"d'accès de 5 ou plus sur le canal. Les fondateurs peuvent\n" +"bannir des masques." + +#: modules/commands/cs_enforce.cpp:166 +#, c-format +msgid "Bans enforced on %s." +msgstr "Bans appliqués sur %s." + +#: modules/commands/bs_kick.cpp:1131 modules/commands/bs_kick.cpp:1133 +#: modules/commands/bs_kick.cpp:1136 +msgid "Bolds kicker" +msgstr "Kicker de caractères gras" + +#: modules/commands/bs_bot.cpp:26 modules/commands/bs_bot.cpp:175 +#, c-format +msgid "Bot %s already exists." +msgstr "Le bot %s existe déjà." + +#: include/language.h:119 +#, c-format +msgid "Bot %s does not exist." +msgstr "Le bot %s n'existe pas." + +#: modules/commands/bs_assign.cpp:71 modules/commands/bs_assign.cpp:246 +#, c-format +msgid "Bot %s has been assigned to %s." +msgstr "Le bot %s a été assigné à %s." + +#: modules/commands/bs_bot.cpp:228 +#, c-format +msgid "Bot %s has been changed to %s!%s@%s (%s)." +msgstr "Le bot %s a été changé en %s!%s@%s (%s)" + +#: modules/commands/bs_bot.cpp:262 +#, c-format +msgid "Bot %s has been deleted." +msgstr "Le bot %s a été supprimé." + +#: modules/commands/bs_assign.cpp:63 modules/commands/bs_assign.cpp:241 +#, c-format +msgid "Bot %s is already assigned to channel %s." +msgstr "Le bot %s est déjà assigné au canal %s." + +#: modules/commands/bs_kick.cpp:832 +#, c-format +msgid "Bot will kick ops on channel %s." +msgstr "Le bot kickera les OPs du canal %s." + +#: modules/commands/bs_kick.cpp:897 +#, c-format +msgid "Bot will kick voices on channel %s." +msgstr "Le bot kickera les voices du canal %s." + +#: modules/commands/bs_kick.cpp:824 +#, c-format +msgid "Bot won't kick ops on channel %s." +msgstr "Le bot ne kickera pas les OPs du canal %s." + +#: modules/commands/bs_kick.cpp:889 +#, c-format +msgid "Bot won't kick voices on channel %s." +msgstr "Le bot ne kickera pas les voices du canal %s." + +#: modules/commands/bs_bot.cpp:118 +#, c-format +msgid "Bot %s is not changeable." +msgstr "Le bot %s n'est pas modifiable." + +#: modules/commands/bs_bot.cpp:254 +#, c-format +msgid "Bot %s is not deletable." +msgstr "Le bot %s ne peut pas être supprimé." + +#: modules/commands/bs_set.cpp:141 +#, c-format +msgid "Bot bans will automatically expire after %s." +msgstr "Les bans du bot expireront automatiquement après %s." + +#: modules/commands/bs_set.cpp:139 +msgid "Bot bans will no longer automatically expire." +msgstr "Le bans du bot n'expireront plus automatiquement." + +#: modules/commands/bs_bot.cpp:46 modules/commands/bs_bot.cpp:138 +#, c-format +msgid "Bot hosts may only be %d characters long." +msgstr "Les hosts des bots ne doivent contenir que %d caractères." + +#: modules/commands/bs_bot.cpp:64 modules/commands/bs_bot.cpp:167 +msgid "Bot hosts may only contain valid host characters." +msgstr "" +"Les hosts des bots ne doivent contenir que des caractères valides pour un " +"host." + +#: modules/commands/bs_bot.cpp:40 modules/commands/bs_bot.cpp:132 +#, c-format +msgid "Bot idents may only be %d characters long." +msgstr "Les ident des bots ne doivent contenir que %d caractères." + +#: modules/commands/bs_bot.cpp:58 modules/commands/bs_bot.cpp:161 +msgid "Bot idents may only contain valid ident characters." +msgstr "" +"Les ident des bots ne doivent contenir que des caractères valides pour un " +"ident." + +#: include/language.h:121 +#, c-format +msgid "Bot is not on channel %s." +msgstr "Le bot n'est pas sur le canal %s." + +#: modules/commands/bs_botlist.cpp:51 +msgid "Bot list:" +msgstr "Liste des bots :" + +#: modules/commands/bs_info.cpp:87 +msgid "Bot nick" +msgstr "Pseudo du bot" + +#: modules/commands/bs_bot.cpp:34 modules/commands/bs_bot.cpp:126 +#, c-format +msgid "Bot nicks may only be %d characters long." +msgstr "Les pseudos des bots ne doivent contenir que %d caractères." + +#: modules/commands/bs_bot.cpp:52 modules/commands/bs_bot.cpp:155 +msgid "Bot nicks may only contain valid nick characters." +msgstr "Les pseudos des bots ne peuvent contenir que des caractères valides." + +#: modules/commands/bs_kick.cpp:225 +#, c-format +msgid "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." +msgstr "" +"Le bot kickera pour la raison : %s.\n" +"Il placera un ban après %d kicks du même utilisateur." + +#: modules/commands/bs_kick.cpp:228 +#, c-format +msgid "Bot will now kick for %s." +msgstr "Le bot kickera pour la raison : %s." + +#: modules/commands/bs_kick.cpp:416 +#, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." +msgstr "" +"Le bot kickera maintenant les majuscules (qui doivent\n" +"constituer au moins %d caractères et %d%% du message \n" +"entier), et bannira après %d kicks du même utilisateur." + +#: modules/commands/bs_kick.cpp:420 +#, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." +msgstr "" +"Le bot kickera maintenant les majuscules (qui doivent\n" +"constituer au moins %d caractères et %d%% du message \n" +"entier)." + +#: modules/commands/bs_kick.cpp:551 +#, c-format +msgid "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." +msgstr "" +"Le bot kickera maintenant le flood (%d lignes en %d \n" +"secondes), et bannira après %d kicks du même utilisateur." + +#: modules/commands/bs_kick.cpp:554 +#, c-format +msgid "Bot will now kick for flood (%d lines in %d seconds)." +msgstr "" +"Le bot kickera maintenant le flood (%d lignes en %d \n" +"secondes)." + +#: modules/commands/bs_kick.cpp:677 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Le bot kickera maintenant les répétitions (les \n" +"utilisateurs qui répètent %d fois la même chose), et \n" +"bannira après %d kicks du même utilisateur." + +#: modules/commands/bs_kick.cpp:687 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." +msgstr "" +"Le bot kickera maintenant les répétitions (les \n" +"utilisateurs qui répètent %d fois la même chose)." + +#: modules/commands/bs_kick.cpp:673 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Le bot kickera maintenant les répétitions (les \n" +"utilisateurs qui répètent %d fois la même chose), et \n" +"bannira après %d kicks du même utilisateur." + +#: modules/commands/bs_kick.cpp:684 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." +msgstr "" +"Le bot kickera maintenant les répétitions (les \n" +"utilisateurs qui répètent %d fois la même chose)." + +#: modules/commands/bs_kick.cpp:239 +#, c-format +msgid "Bot won't kick for %s anymore." +msgstr "Le bot ne kickera plus pour la raison : %s." + +#: modules/commands/bs_kick.cpp:426 +msgid "Bot won't kick for caps anymore." +msgstr "Le bot ne kickera plus les majuscules." + +#: modules/commands/bs_kick.cpp:559 +msgid "Bot won't kick for flood anymore." +msgstr "Le bot ne kickera plus le flood." + +#: modules/commands/bs_kick.cpp:694 +msgid "Bot won't kick for repeats anymore." +msgstr "Le bot ne kickera plus les répétitions." + +#: modules/commands/cs_access.cpp:472 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_session.cpp:514 +msgid "By" +msgstr "Par" + +#: modules/commands/os_info.cpp:104 +msgid "CLEAR target" +msgstr "CLEAR cible" + +#: modules/commands/cs_seen.cpp:119 +msgid "CLEAR time" +msgstr "CLEAR temps" + +#: modules/commands/ms_cancel.cpp:19 +msgid "Cancel the last memo you sent" +msgstr "Annule le dernier mémo que vous avez envoyé." + +#: modules/commands/cs_drop.cpp:19 +msgid "Cancel the registration of a channel" +msgstr "Annule l'enregistrement d'un canal" + +#: modules/commands/ns_drop.cpp:20 +msgid "Cancel the registration of a nickname" +msgstr "Annule l'enregistrement d'un pseudo" + +#: modules/commands/ms_cancel.cpp:84 +msgid "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." +msgstr "" +"Supprime le dernier mémo que vous avez envoyé à un pseudo ou\n" +"canal donné, à condition qu'il n'ait pas déjà été lu lorsque vous\n" +"utilisez la commande." + +#: modules/commands/cs_clone.cpp:149 +#, c-format +msgid "Cannot clone channel %s to itself!" +msgstr "Impossible de cloner le canal %s sur lui-même !" + +#: modules/commands/ns_register.cpp:332 +msgid "Cannot send mail now; please retry a little later." +msgstr "" +"Impossible d'envoyer un email maintenant, veuillez réessayez un peu\n" +"plus tard." + +#: modules/commands/bs_kick.cpp:1141 modules/commands/bs_kick.cpp:1143 +#: modules/commands/bs_kick.cpp:1146 +msgid "Caps kicker" +msgstr "Kicker de majuscules" + +#: modules/commands/os_shutdown.cpp:34 +msgid "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." +msgstr "" +"Provoque un arrêt immédiat des Services, les bases de données\n" +"ne sont pas sauvegardées. Cette commande ne devrait pas être\n" +"utilisée à moins que des dommages dans la copie en mémoire des\n" +"bases de données ne soient soupçonnés." + +#: modules/commands/os_reload.cpp:47 +msgid "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." +msgstr "" +"Provoque le rechargement du fichier de configuration des\n" +"Services. Notez que certaines directives demandent tout\n" +"de même le redémarrage des Services pour prendre effet\n" +"(comme les pseudos des services, l'activation de la limite\n" +"de sessions, etc.)" + +#: modules/commands/os_shutdown.cpp:62 +msgid "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." +msgstr "" +"Provoque la sauvegarde de toutes les bases de données et\n" +"le redémarrage des Services (c'est à dire qu'elle stoppe\n" +"le programme et le relance immédiatement)." + +#: modules/commands/os_shutdown.cpp:89 +msgid "Causes Services to save all databases and then shut down." +msgstr "" +"Provoque la sauvegarde de toutes les bases de données puis\n" +"l'arrêt des Services." + +#: modules/commands/os_update.cpp:34 +msgid "" +"Causes Services to update all database files as soon as you\n" +"send the command." +msgstr "" +"Provoque la sauvegarde de toutes les bases de données dès\n" +"que vous le demandez." + +#: modules/commands/ns_cert.cpp:246 +#, c-format +msgid "Certificate list for %s:" +msgstr "Liste de certificats pour %s :" + +#: modules/commands/cs_set.cpp:528 modules/commands/cs_set.cpp:570 +msgid "ChanServ is required to enable persist on this network." +msgstr "ChanServ est requis pour activer les canaux persistants sur ce réseau." + +#: modules/commands/os_mode.cpp:19 +msgid "Change channel modes" +msgstr "Modifie les modes des canaux" + +#: modules/commands/ns_set.cpp:905 +msgid "Change the communication method of Services" +msgstr "Change le mode de communication des Services" + +#: modules/commands/os_mode.cpp:146 +msgid "Change user modes" +msgstr "Modifie les modes des utilisateurs." + +#: modules/commands/os_mode.cpp:161 +#, c-format +msgid "Changed usermodes of %s to %s." +msgstr "Modes utilisateurs de %s changés en %s." + +#: modules/commands/ns_set.cpp:411 +msgid "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." +msgstr "" +"Change le pseudo utilisé pour nommer le groupe de\n" +"pseudos dans les Services. Le nouvel affichage DOIT être un\n" +"pseudo de ce groupe." + +#: modules/commands/ns_set.cpp:387 +msgid "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." +msgstr "" +"Change le pseudo utilisé pour nommer votre groupe de\n" +"pseudos dans les Services. Le nouvel affichage DOIT être un\n" +"pseudo de votre groupe." + +#: modules/commands/cs_set.cpp:324 +msgid "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." +msgstr "" +"Change le fondateur d'un canal. Le nouveau pseudo doit être\n" +"enregistré." + +#: modules/commands/ns_set.cpp:884 +msgid "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Change la langue utilisée par les Services lorsqu'ils envoient un message\n" +"à un utilisateur donné (par exemple, quand ils répondent à une\n" +"commande qu'il a envoyé). La langue doit être choisie\n" +"dans la liste suivante des langues supportées :" + +#: modules/commands/ns_set.cpp:848 +msgid "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Change la langue utilisée par les Services lorsqu'ils vous\n" +"envoient un message (par exemple, quand ils répondent à une\n" +"commande que vous avez envoyé). La langue doit être choisi\n" +"dans la liste suivante des langues supportées :" + +#: modules/commands/ns_set.cpp:227 +msgid "Changes the password used to identify as the nick's owner." +msgstr "" +"Change le mot de passe utilisé pour s'identifier en tant\n" +"que propriétaire du pseudo." + +#: modules/commands/ns_set.cpp:161 +msgid "" +"Changes the password used to identify you as the nick's\n" +"owner." +msgstr "" +"Change le mot de passe utilisé pour vous identifier en tant\n" +"que propriétaire du pseudo." + +#: modules/commands/cs_set.cpp:1017 +#, fuzzy +msgid "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." +msgstr "" +"Change le successeur d'un canal. Si le pseudo du fondateur\n" +"expire ou est effacé alors que le canal est toujours enregistré,\n" +" le successeur deviendra le nouveau fondateur du canal. Le\n" +"nouveau pseudo doit être enregistré." + +#: modules/commands/ns_alist.cpp:48 modules/commands/ns_ajoin.cpp:100 +msgid "Channel" +msgstr "Canal" + +#: include/language.h:84 +#, c-format +msgid "Channel %s doesn't exist." +msgstr "Le canal %s n'existe pas." + +#: modules/commands/cs_drop.cpp:63 +#, c-format +msgid "Channel %s has been dropped." +msgstr "Le canal %s a été effacé." + +#: modules/commands/cs_getkey.cpp:43 +#, c-format +msgid "Channel %s has no key." +msgstr "Le canal %s n'a pas de clé." + +#: modules/commands/cs_register.cpp:47 +#, c-format +msgid "Channel %s is already registered!" +msgstr "Le canal %s est déjà enregistré !" + +#: modules/commands/os_forbid.cpp:524 +#, c-format +msgid "Channel %s is forbidden by %s: %s" +msgstr "Le canal %s est interdit par %s : %s" + +#: modules/commands/os_forbid.cpp:526 +#, c-format +msgid "Channel %s is forbidden." +msgstr "Le canal %s est interdit." + +#: modules/commands/cs_set.cpp:580 +#, c-format +msgid "Channel %s is no longer persistent." +msgstr "Le canal %s n'est plus persistant." + +#: modules/commands/cs_set.cpp:542 +#, c-format +msgid "Channel %s is now persistent." +msgstr "Le canal %s est maintenant persistant." + +#: modules/commands/cs_suspend.cpp:180 +#, c-format +msgid "Channel %s is now released." +msgstr "Le canal %s est maintenant libéré." + +#: modules/commands/cs_suspend.cpp:125 +#, c-format +msgid "Channel %s is now suspended." +msgstr "Le canal %s est maintenant suspendu." + +#: include/language.h:83 +#, c-format +msgid "Channel %s isn't registered." +msgstr "Le canal %s n'est pas enregistré." + +#: modules/commands/cs_suspend.cpp:172 +#, c-format +msgid "Channel %s isn't suspended." +msgstr "Le canal %s n'est pas suspendu." + +#: modules/commands/cs_register.cpp:68 +#, c-format +msgid "Channel %s registered under your account: %s" +msgstr "Le canal %s est enregistré dans votre compte : %s" + +#: modules/commands/cs_set.cpp:1078 +#, c-format +msgid "Channel %s will expire." +msgstr "Le canal %s expirera." + +#: modules/commands/cs_set.cpp:1072 +#, c-format +msgid "Channel %s will not expire." +msgstr "Le canal %s n'expirera pas." + +#: modules/commands/cs_xop.cpp:475 +#, c-format +msgid "Channel %s %s list has been cleared." +msgstr "La liste %2$s de %1$s est maintenant vide." + +#: modules/commands/cs_access.cpp:486 modules/commands/cs_flags.cpp:361 +#, c-format +msgid "Channel %s access list has been cleared." +msgstr "La liste d'accès de %s est maintenant vide." + +#: modules/commands/cs_akick.cpp:428 +#, c-format +msgid "Channel %s akick list has been cleared." +msgstr "La liste de kicks automatiques de %s est maintenant vide." + +#: modules/commands/cs_mode.cpp:444 +#, c-format +msgid "Channel %s has no mode locks." +msgstr "Le canal %s n'a pas de modes verrouillés." + +#: include/language.h:82 +#, c-format +msgid "Channel %s is currently suspended." +msgstr "Le canal %s est actuellement suspendu." + +#: include/language.h:101 +#, c-format +msgid "Channel %s is not a valid channel." +msgstr "%s n'est pas un canal valide." + +#: modules/commands/os_list.cpp:70 +msgid "Channel list:" +msgstr "Liste des canaux :" + +#: modules/extra/stats/cs_fantasy_stats.cpp:148 +#, c-format +msgid "Channel stats for %s on %s:" +msgstr "Statistiques de canal pour %s sur %s :" + +#: modules/commands/cs_access.cpp:142 modules/commands/cs_flags.cpp:97 +#: modules/commands/cs_xop.cpp:139 +msgid "Channels may not be on access lists." +msgstr "Les canaux ne peuvent pas ajoutés aux listes d'accès." + +#: modules/commands/ns_alist.cpp:114 +#, c-format +msgid "Channels that %s has access on:" +msgstr "Liste des canaux auxquels %s a accès :" + +#: modules/commands/os_stats.cpp:181 +#, c-format +msgid "Channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "Canaux : %lu entrées, %lu paniers, plus longue chaîne : %d" + +#: modules/extra/stats/m_chanstats.cpp:517 +#: modules/extra/stats/m_chanstats.cpp:525 +msgid "Chanstats" +msgstr "Chanstats" + +#: modules/extra/stats/m_chanstats.cpp:102 +#, c-format +msgid "Chanstats statistics are now disabled for %s" +msgstr "Les statistiques Chanstats sont maintenant désactivées pour %s." + +#: modules/extra/stats/m_chanstats.cpp:51 +msgid "Chanstats statistics are now disabled for this channel." +msgstr "Les statistiques Chanstats sont maintenant désactivées pour ce canal." + +#: modules/extra/stats/m_chanstats.cpp:104 +msgid "Chanstats statistics are now disabled for your nick." +msgstr "" +"Les statistiques Chanstats sont maintenant désactivées pour votre pseudo." + +#: modules/extra/stats/m_chanstats.cpp:93 +#, c-format +msgid "Chanstats statistics are now enabled for %s" +msgstr "Les statistiques Chanstats sont maintenant activées pour %s." + +#: modules/extra/stats/m_chanstats.cpp:44 +msgid "Chanstats statistics are now enabled for this channel." +msgstr "Les statistiques Chanstats sont maintenant activées pour ce canal." + +#: modules/extra/stats/m_chanstats.cpp:95 +msgid "Chanstats statistics are now enabled for your nick." +msgstr "Les statistiques Chanstats sont maintenant activées pour votre pseudo." + +#: modules/commands/cs_seen.cpp:367 +msgid "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." +msgstr "" +"Vérifie la dernière fois que pseudo a rejoint ou quitté un canal, ou\n" +"modifié son pseudo sur le réseau, et selon les paramètres du canal et\n" +"de l'utilisateur, sur quel canal." + +#: modules/commands/ms_check.cpp:19 +msgid "Checks if last memo to a nick was read" +msgstr "Vérifie si le dernier mémo envoyé à un pseudo a été lu" + +#: modules/commands/ms_check.cpp:69 +msgid "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." +msgstr "" +"Vérifie si le _dernier_ mémo que vous avez envoyé au pseudo donné\n" +"a été lu ou pas.\n" +"Note : Cela fonctionne uniquement avec un pseudo et non pas avec un\n" +"canal." + +#: modules/commands/os_info.cpp:227 +#, c-format +msgid "Cleared info from %s." +msgstr "Informations supprimées pour %s." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1153 +#: modules/commands/bs_kick.cpp:1156 +msgid "Colors kicker" +msgstr "Kicker pour les couleurs" + +#: modules/commands/cs_log.cpp:127 +msgid "Command" +msgstr "Commande" + +#: modules/commands/bs_kick.cpp:251 +msgid "Configures AMSG kicker" +msgstr "Configure les kickers pour les AMSG" + +#: modules/commands/bs_kick.cpp:287 +msgid "Configures badwords kicker" +msgstr "Configure les kickers pour les mots interdits" + +#: modules/commands/bs_kick.cpp:326 +msgid "Configures bolds kicker" +msgstr "Configure les kickers pour le gras" + +#: modules/commands/bs_kick.cpp:132 +msgid "Configures bot kickers. option can be one of:" +msgstr "Configure les kickers du bot. option peut être :" + +#: modules/commands/bs_set.cpp:19 +msgid "Configures bot options" +msgstr "Configure les options du bot" + +#: modules/commands/bs_set.cpp:32 +msgid "" +"Configures bot options.\n" +" \n" +"Available options:" +msgstr "" +"Configure les options du bot\n" +" \n" +"Options disponibles :" + +#: modules/commands/bs_kick.cpp:360 +msgid "Configures caps kicker" +msgstr "Configure les kickers pour les majuscules" + +#: modules/commands/cs_log.cpp:105 +msgid "Configures channel logging settings" +msgstr "Configure les paramètres de logs du canal." + +#: modules/commands/bs_kick.cpp:456 +msgid "Configures color kicker" +msgstr "Configure les kickers pour les couleurs" + +#: modules/commands/bs_kick.cpp:490 +msgid "Configures flood kicker" +msgstr "Configure les kickers pour le flood" + +#: modules/commands/bs_kick.cpp:588 +msgid "Configures italics kicker" +msgstr "Configure les kickers pour les caractères italiques" + +#: modules/commands/bs_kick.cpp:119 +msgid "Configures kickers" +msgstr "Configure les kickers" + +#: modules/commands/bs_kick.cpp:622 +msgid "Configures repeat kicker" +msgstr "Configure les kickers pour les répétitions" + +#: modules/commands/bs_kick.cpp:723 +msgid "Configures reverses kicker" +msgstr "Configure les kickers pour les caractères reverse" + +#: modules/commands/bs_set.cpp:90 +msgid "Configures the time bot bans expire in" +msgstr "Configure les expirations de ban du bot" + +#: modules/commands/bs_kick.cpp:757 +msgid "Configures underlines kicker" +msgstr "Configure les kickers pour les caractères soulignés" + +#: modules/commands/ns_register.cpp:21 +msgid "Confirm a passcode" +msgstr "Confirme un mot-code" + +#: modules/commands/cs_mode.cpp:733 +msgid "Control modes and mode locks on a channel" +msgstr "Contrôle les modes et les modes verrouillés sur un canal" + +#: modules/commands/cs_entrymsg.cpp:239 +msgid "" +"Controls what messages will be sent to users when they join the channel." +msgstr "" +"Contrôle quels messages sont envoyés aux utilisateurs lorsqu'ils joignent le " +"canal." + +#: modules/commands/cs_clone.cpp:242 +msgid "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." +msgstr "" +"Copie tous les paramètres, accès, akicks, etc. de canal sur le canal\n" +"cible. Si quoi est ACCESS, AKICK, BADWORDS ou\n" +"LEVELS alors seuls ces paramètres sont clonés.\n" +"Vous devez être fondateur de canal et cible." + +#: modules/commands/cs_clone.cpp:114 +msgid "Copy all settings from one channel to another" +msgstr "Copie tous les paramètres d'un canal à un autre" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/bs_info.cpp:57 +#: modules/commands/os_akill.cpp:358 +msgid "Created" +msgstr "Créé" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_ignore.cpp:266 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_news.cpp:156 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_akill.cpp:358 +msgid "Creator" +msgstr "Créateur" + +#: modules/commands/os_sxline.cpp:180 +#, c-format +msgid "Current %s list:" +msgstr "Liste de %s actuelle :" + +#: modules/commands/os_akill.cpp:323 +msgid "Current AKILL list:" +msgstr "Liste d'AKILL actuelle :" + +#: modules/commands/os_session.cpp:493 +msgid "Current Session Limit Exception list:" +msgstr "Liste actuelle des exceptions à la limitation de sessions :" + +#: modules/commands/os_modinfo.cpp:116 +msgid "Current module list:" +msgstr "Liste des modules actuels :" + +#: modules/commands/os_stats.cpp:69 +#, c-format +msgid "Current number of AKILLs: %d" +msgstr "Nombre d'AKILLs : %d" + +#: modules/commands/os_stats.cpp:89 +#, c-format +msgid "Current number of SNLINEs: %d" +msgstr "Nombre de SNLINEs : %d" + +#: modules/commands/os_stats.cpp:109 +#, c-format +msgid "Current number of SQLINEs: %d" +msgstr "Nombre de SQLINEs : %d" + +#: modules/commands/os_stats.cpp:138 +#, c-format +msgid "Current users: %d (%d ops)" +msgstr "Utilisateurs actuels : %d (%d ops)" + +#: modules/commands/os_oper.cpp:71 +msgid "DEL oper" +msgstr "DEL oper" + +#: modules/commands/os_info.cpp:103 +msgid "DEL target info" +msgstr "DEL cible info" + +#: modules/commands/ns_ajoin.cpp:232 +msgid "DEL [nickname] channel" +msgstr "DEL [pseudo] canal" + +#: modules/commands/ns_cert.cpp:259 +msgid "DEL [nickname] fingerprint" +msgstr "DEL [pseudo] fingerprint" + +#: modules/commands/ns_access.cpp:103 +msgid "DEL [nickname] mask" +msgstr "DEL [pseudo] masque" + +#: modules/commands/os_sxline.cpp:426 modules/commands/os_sxline.cpp:660 +#: modules/commands/os_akill.cpp:387 +msgid "DEL {mask | entry-num | list | id}" +msgstr "DEL {masque | num | liste | id}" + +#: modules/commands/os_session.cpp:524 +msgid "DEL {mask | entry-num | list}" +msgstr "DEL {masque | num | liste}" + +#: modules/commands/os_ignore.cpp:343 +msgid "DEL {nick|mask}" +msgstr "DEL {pseudo|masque}" + +#: modules/commands/os_news.cpp:279 +msgid "DEL {num | ALL}" +msgstr "DEL {num | ALL}" + +#: modules/commands/os_forbid.cpp:158 +msgid "DEL {NICK|CHAN|EMAIL|REGISTER} entry" +msgstr "DEL {NICK|CHAN|EMAIL|REGISTER} entrée" + +#: modules/commands/os_dns.cpp:666 +msgid "DELIP server.name ip" +msgstr "DELIP nom.du.serveur ip" + +#: modules/commands/os_dns.cpp:664 +msgid "DELSERVER server.name [zone.name]" +msgstr "DELSERVER nom.du.serveur [nom.de.la.zone]" + +#: modules/commands/os_dns.cpp:662 +msgid "DELZONE zone.name" +msgstr "DELZONE nom.de.la.zone" + +#: modules/commands/os_dns.cpp:669 +msgid "DEPOOL server.name" +msgstr "DEPOOL nom.du.serveur" + +#: modules/commands/cs_seen.cpp:162 +#, c-format +msgid "Database cleared, removed %lu nicks that were added after %s." +msgstr "" +"Base de donnée nettoyée, %lu pseudos supprimés qui avaient été ajoutés après " +"%s." + +#: modules/commands/ms_list.cpp:64 +msgid "Date/Time" +msgstr "Date/Heure" + +#: modules/commands/hs_off.cpp:49 +msgid "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." +msgstr "" +"Désactive le vhost que vous utilisez actuellement.\n" +"L'utilisation de cette commande rendra visible votre host/IP pour\n" +"les utilisateurs qui exécutent un /whois sur vous." + +#: modules/commands/hs_off.cpp:19 +msgid "Deactivates your assigned vhost" +msgstr "Désactive votre vHost assigné" + +#: modules/commands/os_stats.cpp:72 +#, c-format +msgid "Default AKILL expiry time: %d days" +msgstr "Temps d'échéance des AKILLs par défaut: %d jours" + +#: modules/commands/os_stats.cpp:76 +#, c-format +msgid "Default AKILL expiry time: %d hours" +msgstr "Temps d'échéance des AKILLs par défaut: %d heures" + +#: modules/commands/os_stats.cpp:80 +#, c-format +msgid "Default AKILL expiry time: %d minutes" +msgstr "Temps d'échéance des AKILLs par défaut: %d minutes" + +#: modules/commands/os_stats.cpp:74 +msgid "Default AKILL expiry time: 1 day" +msgstr "Temps d'échéance des AKILLs par défaut: 1 jour" + +#: modules/commands/os_stats.cpp:78 +msgid "Default AKILL expiry time: 1 hour" +msgstr "Temps d'échéance des AKILLs par défaut: 1 heure" + +#: modules/commands/os_stats.cpp:82 +msgid "Default AKILL expiry time: 1 minute" +msgstr "Temps d'échéance des AKILLs par défaut: 1 minute" + +#: modules/commands/os_stats.cpp:84 +msgid "Default AKILL expiry time: No expiration" +msgstr "Temps d'échéance des AKILLs par défaut: Pas d'échéance" + +#: modules/commands/os_stats.cpp:92 +#, c-format +msgid "Default SNLINE expiry time: %d days" +msgstr "Temps d'échéance des SNLINEs par défaut: %d jours" + +#: modules/commands/os_stats.cpp:96 +#, c-format +msgid "Default SNLINE expiry time: %d hours" +msgstr "Temps d'échéance des SNLINEs par défaut: %d heures" + +#: modules/commands/os_stats.cpp:100 +#, c-format +msgid "Default SNLINE expiry time: %d minutes" +msgstr "Temps d'échéance des SNLINEs par défaut: %d minutes" + +#: modules/commands/os_stats.cpp:94 +msgid "Default SNLINE expiry time: 1 day" +msgstr "Temps d'échéance des SNLINEs par défaut: 1 jour" + +#: modules/commands/os_stats.cpp:98 +msgid "Default SNLINE expiry time: 1 hour" +msgstr "Temps d'échéance des SNLINEs par défaut: 1 heure" + +#: modules/commands/os_stats.cpp:102 +msgid "Default SNLINE expiry time: 1 minute" +msgstr "Temps d'échéance des SNLINEs par défaut: 1 minute" + +#: modules/commands/os_stats.cpp:104 +msgid "Default SNLINE expiry time: No expiration" +msgstr "Temps d'échéance des SNLINEs par défaut: Pas d'échéance" + +#: modules/commands/os_stats.cpp:112 +#, c-format +msgid "Default SQLINE expiry time: %d days" +msgstr "Temps d'échéance des SQLINEs par défaut: %d jours" + +#: modules/commands/os_stats.cpp:116 +#, c-format +msgid "Default SQLINE expiry time: %d hours" +msgstr "Temps d'échéance des SQLINEs par défaut: %d heures" + +#: modules/commands/os_stats.cpp:120 +#, c-format +msgid "Default SQLINE expiry time: %d minutes" +msgstr "Temps d'échéance des SQLINEs par défaut: %d minutes" + +#: modules/commands/os_stats.cpp:114 +msgid "Default SQLINE expiry time: 1 day" +msgstr "Temps d'échéance des SQLINEs par défaut: 1 jour" + +#: modules/commands/os_stats.cpp:118 +msgid "Default SQLINE expiry time: 1 hour" +msgstr "Temps d'échéance des SQLINEs par défaut: 1 heure" + +#: modules/commands/os_stats.cpp:122 +msgid "Default SQLINE expiry time: 1 minute" +msgstr "Temps d'échéance des SQLINEs par défaut: 1 minute" + +#: modules/commands/os_stats.cpp:124 +msgid "Default SQLINE expiry time: No expiration" +msgstr "Temps d'échéance des SQLINEs par défaut: Pas d'échéance" + +#: modules/commands/os_news.cpp:351 +msgid "Define messages to be randomly shown to users at logon" +msgstr "" +"Définit les messages affichés aléatoirement aux utilisateurs à la connexion" + +#: modules/commands/os_news.cpp:297 +msgid "Define messages to be shown to users at logon" +msgstr "Définit les messages affichés aux utilisateurs à la connexion" + +#: modules/commands/os_news.cpp:324 +msgid "Define messages to be shown to users who oper" +msgstr "" +"Définit les messages affichés aux utilisateurs qui deviennent opérateurs IRC" + +#: modules/commands/ms_del.cpp:44 +msgid "Delete a memo or memos" +msgstr "Efface un ou des mémos" + +#: modules/commands/hs_del.cpp:19 +msgid "Delete the vhost of another user" +msgstr "Supprime le vhost d'un autre pseudo" + +#: modules/commands/cs_xop.cpp:302 +#, c-format +msgid "Deleted %d entries from %s %s list." +msgstr "%1$d entrées supprimées de la liste des %3$s de %2$s." + +#: modules/commands/cs_access.cpp:277 +#, c-format +msgid "Deleted %d entries from %s access list." +msgstr "%d entrées supprimées de la liste d'accès de %s." + +#: modules/commands/cs_akick.cpp:228 +#, c-format +msgid "Deleted %d entries from %s autokick list." +msgstr "%d entrées supprimées de la liste des kicks automatiques de %s." + +#: modules/commands/bs_badwords.cpp:170 +#, c-format +msgid "Deleted %d entries from %s bad words list." +msgstr "%d entrées supprimées de la liste des mots interdits de %s." + +#: modules/commands/os_session.cpp:149 +#, c-format +msgid "Deleted %d entries from session-limit exception list." +msgstr "" +"%d entrées supprimées de la liste des exceptions à la limitation de sessions." + +#: modules/commands/os_sxline.cpp:32 +#, c-format +msgid "Deleted %d entries from the %s list." +msgstr "%d entrées supprimées de la liste de %s." + +#: modules/commands/os_akill.cpp:33 +#, c-format +msgid "Deleted %d entries from the AKILL list." +msgstr "%d entrées supprimées de la liste d'AKILL." + +#: modules/commands/cs_access.cpp:275 +#, c-format +msgid "Deleted 1 entry from %s access list." +msgstr "1 entrée supprimée de la liste d'accès de %s." + +#: modules/commands/cs_akick.cpp:226 +#, c-format +msgid "Deleted 1 entry from %s autokick list." +msgstr "1 entrée supprimée de la liste des kicks automatiques de %s." + +#: modules/commands/bs_badwords.cpp:168 +#, c-format +msgid "Deleted 1 entry from %s bad words list." +msgstr "1 entrée supprimée de la liste des mots interdits de %s." + +#: modules/commands/os_session.cpp:147 +msgid "Deleted 1 entry from session-limit exception list." +msgstr "" +"1 entrée supprimée de la liste des exceptions à la limitation de sessions." + +#: modules/commands/os_sxline.cpp:30 +#, c-format +msgid "Deleted 1 entry from the %s list." +msgstr "1 entrée supprimée de la liste %s." + +#: modules/commands/os_akill.cpp:31 +msgid "Deleted 1 entry from the AKILL list." +msgstr "1 entrée supprimée de la liste d'AKILL." + +#: modules/commands/os_info.cpp:208 +#, c-format +msgid "Deleted info from %s." +msgstr "Information supprimée de %s." + +#: modules/commands/cs_xop.cpp:300 +#, c-format +msgid "Deleted one entry from %s %s list." +msgstr "Une entrée a été supprimée de la liste %2$s de %1$s." + +#: modules/commands/ms_del.cpp:129 +msgid "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Supprime le ou les mémos spécifiés. Vous pouvez\n" +"fournir plusieurs numéros de mémos ou des ranges de nombres\n" +"au lieu d'un nombre unique, comme dans le second exemple\n" +"ci-dessous.\n" +" \n" +"Si LAST est donné, le dernier mémo sera supprimé.\n" +"Si ALL est donné, cela supprimera tous vos mémos.\n" +" \n" +"Exemples :\n" +" \n" +" DEL 1\n" +" Supprime votre premier mémo.\n" +" \n" +" DEL 2-5,7-9\n" +" Supprime les mémos compris entre 2 et 5 et entre 7 et 9." + +#: modules/commands/hs_del.cpp:48 +msgid "" +"Deletes the vhost assigned to the given nick from the\n" +"database." +msgstr "" +"Supprime le vhost pour le pseudo indiqué de la base de\n" +"données." + +#: modules/commands/hs_del.cpp:59 +msgid "Deletes the vhost for all nicks in a group" +msgstr "Supprime le vhost pour tous les pseudos d'un groupe" + +#: modules/commands/hs_del.cpp:93 +msgid "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." +msgstr "" +"Supprime tous les vhosts pour tous les pseudos du même\n" +"groupe que le pseudo donné." + +#: modules/commands/os_dns.cpp:653 +#, c-format +msgid "Depooled %s." +msgstr "%s retiré de la pool." + +#: modules/commands/cs_access.cpp:799 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_list.cpp:75 modules/commands/cs_info.cpp:53 +msgid "Description" +msgstr "Description" + +#: modules/commands/cs_set.cpp:239 +#, c-format +msgid "Description of %s changed to %s." +msgstr "La description de %s est maintenant %s." + +#: modules/commands/cs_set.cpp:245 +#, c-format +msgid "Description of %s unset." +msgstr "La description de %s a été supprimée." + +#: modules/commands/bs_kick.cpp:1115 modules/commands/bs_info.cpp:90 +msgid "Disabled" +msgstr "Désactivé" + +#: modules/commands/cs_suspend.cpp:134 +msgid "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." +msgstr "" +"Interdit à tout le monde d'utiliser le canal indiqué.\n" +"Ceci peut être annulé avec la commande UNSUSPEND\n" +"pour conserver les données et configurations du canal.\n" +"Si une expiration est fournie, le canal sera réactivé après\n" +"cette période de temps. Dans le cas contraire, le temps défini\n" +"dans le fichier de configuration sera utilisé.\n" +" \n" +"Une raison peut être requise sur certains réseaux." + +#: modules/commands/hs_request.cpp:337 +#, c-format +msgid "Displayed %d records (%d total)." +msgstr "%d enregistrements affichés (Total : %d)" + +#: modules/commands/hs_list.cpp:122 +#, c-format +msgid "Displayed all records (count: %d)." +msgstr "Tous les enregistrements sont affichés (Total : %d) " + +#: modules/commands/hs_list.cpp:120 +#, c-format +msgid "Displayed records from %d to %d." +msgstr "Les enregistrements de %d à %d sont affichés" + +#: modules/commands/hs_list.cpp:116 +#, c-format +msgid "Displayed records matching key %s (count: %d)." +msgstr "Les enregistrements contenant %s sont affichés (Nombre : %d)" + +#: modules/commands/ns_info.cpp:19 +msgid "Displays information about a given nickname" +msgstr "Affiche des informations sur un pseudo" + +#: modules/commands/ns_info.cpp:125 +msgid "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." +msgstr "" +"Affiche des informations sur le pseudo indiqué, telles que\n" +"le propriétaire du pseudo, l'adresse avec laquelle il était\n" +"connecté pour la dernière fois, et les options du pseudo. Si\n" +"aucun pseudo n'est donné et que vous êtes identifié, votre compte\n" +"sera utilisé, autrement, votre pseudo sera utilisé." + +#: modules/commands/ms_info.cpp:19 +msgid "Displays information about your memos" +msgstr "Affiche des informations à propos de vos mémos" + +#: modules/commands/hs_list.cpp:19 +msgid "Displays one or more vhost entries" +msgstr "Affiche une ou plusieurs entrées vHost" + +#: modules/extra/stats/cs_fantasy_top.cpp:50 +msgid "Displays the top 10 users of a channel" +msgstr "Affiche le top 10 des utilisateurs d'un canal" + +#: modules/extra/stats/cs_fantasy_top.cpp:73 +msgid "Displays the top 10 users of the network" +msgstr "Affiche le top 10 des utilisateurs du réseau" + +#: modules/extra/stats/cs_fantasy_top.cpp:38 +msgid "Displays the top 3 users of a channel" +msgstr "Affiche le top 3 des utilisateurs d'un canal" + +#: modules/extra/stats/cs_fantasy_top.cpp:62 +msgid "Displays the top 3 users of the network" +msgstr "Affiche le top 3 des utilisateurs du réseau" + +#: modules/commands/help.cpp:33 +msgid "Displays this list and give information about commands" +msgstr "Affiche cette liste et donne des informations sur les commandes" + +#: modules/extra/stats/cs_fantasy_stats.cpp:39 +msgid "Displays your Channel Stats" +msgstr "Affiche vos statistiques de canal" + +#: modules/extra/stats/cs_fantasy_stats.cpp:51 +msgid "Displays your Global Stats" +msgstr "Affiche vos statistiques globales" + +#: modules/commands/bs_kick.cpp:1463 +msgid "Don't use AMSGs!" +msgstr "N'utilisez pas de AMSG !" + +#: modules/commands/bs_kick.cpp:1266 +msgid "Don't use bolds on this channel!" +msgstr "N'utilisez pas de caractères gras sur ce canal !" + +#: modules/commands/bs_kick.cpp:1274 +msgid "Don't use colors on this channel!" +msgstr "N'utilisez pas de couleurs sur ce canal !" + +#: modules/commands/bs_kick.cpp:1290 +msgid "Don't use italics on this channel!" +msgstr "N'utilisez pas d'italique sur le canal !" + +#: modules/commands/bs_kick.cpp:1282 +msgid "Don't use reverses on this channel!" +msgstr "N'utilisez pas de caractères inversés sur ce canal !" + +#: modules/commands/bs_kick.cpp:1408 +#, c-format +msgid "Don't use the word \"%s\" on this channel!" +msgstr "Ne dites pas %s sur ce canal !" + +#: modules/commands/bs_kick.cpp:1298 +msgid "Don't use underlines on this channel!" +msgstr "N'utilisez pas de caractères soulignés sur ce canal !" + +#: modules/commands/ns_drop.cpp:61 +msgid "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." +msgstr "" +"Efface le pseudo indiqué de la base de données. Une fois que votre pseudo\n" +"est effacé, vous perdez tous les accès et les canaux que vous possédez.\n" +"N'importe quel utilisateur pourra prendre le contrôle de ce pseudo." + +#: modules/commands/ns_set.cpp:513 +#, c-format +msgid "E-mail address for %s changed to %s." +msgstr "L'adresse email pour %s a été changée en %s." + +#: modules/commands/ns_set.cpp:519 +#, c-format +msgid "E-mail address for %s unset." +msgstr "L'adresse email pour %s a été effacée." + +#: src/mail.cpp:80 +#, c-format +msgid "E-mail for %s is invalid." +msgstr "L'adresse email pour %s est invalide." + +#: modules/commands/os_news.cpp:309 +#, c-format +msgid "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Modifie ou affiche la liste des news de connexion. Lorsqu'un\n" +"utilisateur se connecte au réseau, ces messages lui seront\n" +"envoyés. Cependant, pas plus de %d messages ne seront\n" +"envoyés pour éviter le flood des utilisateurs. S'il y a\n" +"trop de messages de news, seuls les plus récents seront envoyés." + +#: modules/commands/os_news.cpp:336 +#, c-format +msgid "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Modifie ou affiche la liste des news pour opers. Quand un\n" +"utilisateur utilise la commande /OPER, ces messages lui seront\n" +"envoyés. Cependant, pas plus de %d messages seront \n" +"envoyés afin de ne pas flooder l'utilisateur. S'il y a trop de \n" +"messages news, seuls les plus récents seront envoyés." + +#: modules/commands/os_news.cpp:363 +msgid "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." +msgstr "" +"Modifie ou affiche la liste des news aléatoires. Lorsqu'un\n" +"utilisateur se connecte au réseau, une (et une seule) de ces\n" +"news sera choisie et lui sera envoyée." + +#: modules/commands/ns_info.cpp:98 +msgid "Email address" +msgstr "Adresse email" + +#: modules/commands/ns_getemail.cpp:41 +#, c-format +msgid "Email matched: %s (%s) to %s." +msgstr "Email trouvé : %s (%s) pour %s." + +#: modules/fantasy.cpp:19 +msgid "Enable fantaisist commands" +msgstr "Active les commandes fantaisistes" + +#: modules/commands/greet.cpp:19 +msgid "Enable greet messages" +msgstr "Active les messages d'accueil" + +#: modules/commands/ns_set.cpp:568 +msgid "Enable or disable keep modes" +msgstr "Active ou désactive le maintien des modes" + +#: modules/commands/bs_kick.cpp:1114 modules/commands/bs_info.cpp:89 +msgid "Enabled" +msgstr "Activé" + +#: modules/commands/cs_set.cpp:124 +#, c-format +msgid "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." +msgstr "" +"Active ou désactive l'auto op par %s sur un canal. Lorsque l'auto op\n" +"est inactif, les utilisateurs qui joignent le canal ne recevront aucun\n" +"statut de la part de %s." + +#: modules/commands/cs_set.cpp:388 +msgid "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." +msgstr "" +"Active ou désactive l'option de maintien des modes d'un canal. Si le " +"maintien\n" +"des modes est activé, les services se rappelleront des modes ajoutés sur le " +"canal\n" +"et tenteront de les remettre la prochaine fois que le canal sera créé." + +#: modules/commands/ns_set.cpp:643 +msgid "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." +msgstr "" +"Active ou désactive l'option de maintien des modes d'un pseudo. Si le " +"maintien\n" +"des modes est activé, les services se rappelleront des modes utilisateurs de " +"l'utilisateur\n" +"et tenteront de les remettre la prochaine fois que cet utilisateur se " +"connectera." + +#: modules/commands/ns_set.cpp:618 +msgid "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." +msgstr "" +"Active ou désactive l'option de maintien des modes de votre pseudo. Si le " +"maintien\n" +"des modes est activé, les services se rappelleront de vos modes " +"utilisateurs\n" +"et tenteront de les remettre la prochaine fois que vous vous connecterez." + +#: modules/commands/cs_set.cpp:733 +msgid "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." +msgstr "" +"Active ou désactive les sécurités pour un canal.\n" +"Lorsque SECURE est activé, seuls les utilisateurs\n" +"qui se sont authentifiés auprès des services, et qui ne\n" +"sont pas seulement reconnus par ceux-ci, auront accès\n" +"au canal, sur la base de la liste d'accès." + +#: modules/commands/cs_set.cpp:932 +msgid "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." +msgstr "" +"Active ou désactive les kicks signés sur un canal.\n" +"Quand cette option est utilisée, les kicks générés\n" +"par la commande KICK contiendront dans la raison\n" +"le pseudo qui a utilisé la commande.\n" +" \n" +"Si vous utilisez LEVEL, ceux qui ont un niveau\n" +"supérieur ou égal au niveau SIGNKICK sur le canal\n" +"n'auront pas leurs kicks signés." + +#: modules/commands/cs_set.cpp:452 +#, c-format +msgid "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." +msgstr "" +"Active ou désactive l'option de paix pour un canal.\n" +"Quand elle est active, cette option empêche un \n" +"utilisateur de kicker, bannir ou enlever un privilège\n" +"de canal d'un user qui a un niveau supérieur ou\n" +"égal au sien via les commandes de %s." + +#: modules/commands/cs_list.cpp:232 +msgid "Enables or disables the private option for a channel." +msgstr "Active ou désactive l'option privée pour un canal." + +#: modules/commands/cs_set.cpp:671 +msgid "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." +msgstr "" +"Active ou désactive l'option d'accès restreint pour un canal.\n" +"Quand l'accès restreint est activé, les utilisateurs qui ne sont\n" +"pas inscrits à la liste d'accès seront kickés et bannis du canal." + +#: modules/commands/cs_set.cpp:796 +msgid "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." +msgstr "" +"Active ou désactive l'option contrôle du fondateur pour un canal.\n" +"Lorsque le contrôle du fondateur est activé, seul le vrai \n" +"fondateur pourra effacer le canal, changer son fondateur \n" +"et son successeur, et non pas ceux qui ont le level propriétaire\n" +"en utilisant l'accès/la commande qop." + +#: modules/commands/cs_set.cpp:860 +msgid "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." +msgstr "" +"Active ou désactive le contrôle des OPs sur un canal.\n" +"Lorsque le contrôle des OPs est actif, les utilisateurs \n" +"qui ne sont pas sur la liste d'accès ne pourront être opérateurs\n" +"du salon." + +#: modules/commands/cs_topic.cpp:70 +#, c-format +msgid "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." +msgstr "" +"Active ou désactive l'option de maintien du sujet pour\n" +"un canal. Lorsque %s est défini, le \n" +"sujet pour le canal sera retenu par %s même après que le\n" +"dernier utilisateur ait quitté le canal, et sera restauré\n" +"la prochaine fois que le canal sera créé. " + +#: modules/commands/cs_set.cpp:592 +#, c-format +msgid "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." +msgstr "" +"Active ou désactive la persistance du canal. Lorsqu'un canal\n" +"est persistant, le bot restera dessus lorsqu'il n'y a plus\n" +"d'utilisateur sur le canal.\n" +" \n" +"Si votre serveur IRC n'a pas de mode de canaux permanents (persistants)\n" +"vous devez avoir un bot des services sur votre canal pour le rendre\n" +"persistant et il ne peut pas pas être désassigné tant que la persistance\n" +"est activée.\n" +" \n" +"Si ce réseau n'a pas %s activé et n'a pas de mode de canal persistant\n" +"%s joindra votre canal lorsque vous activez la persistance (et partira\n" +"lorsqu'elle est désactivée).\n" +" \n" +"Si votre serveur IRC a un mode de canal permanent (persistant)\n" +"et qu'il activé ou désactivé (pour n'importe quelle raison, incluant\n" +"MODE LOCK), la persistance est également automatiquement\n" +"activée et désactivée pour le canal. De plus les services activeront\n" +"ou désactiveront ce mode lorsque la persistance est modifiée." + +#: modules/commands/os_akill.cpp:331 +msgid "End of AKILL list." +msgstr "Fin de la liste des AKILL." + +#: modules/commands/cs_access.cpp:444 +msgid "End of access list" +msgstr "Fin de la liste d'accès." + +#: modules/commands/cs_flags.cpp:347 +#, c-format +msgid "End of access list - %d/%d entries shown." +msgstr "Fin de la liste d'accès - %d/%d correspondances affichées." + +#: modules/commands/cs_flags.cpp:345 +msgid "End of access list." +msgstr "Fin de la liste d'accès." + +#: modules/commands/cs_akick.cpp:379 +msgid "End of autokick list" +msgstr "Fin de la liste des kicks automatiques." + +#: modules/commands/bs_badwords.cpp:257 +msgid "End of bad words list." +msgstr "Fin de la liste des mots interdits." + +#: modules/commands/os_list.cpp:100 +#, c-format +msgid "End of channel list. %u channels shown." +msgstr "Fin de la liste de canaux. %u canaux affichés." + +#: modules/commands/os_config.cpp:117 +msgid "End of configuration." +msgstr "Fin de configuration." + +#: modules/commands/cs_entrymsg.cpp:134 +msgid "End of entry message list." +msgstr "Fin de la liste de messages d'entrée." + +#: modules/commands/os_forbid.cpp:407 +#, c-format +msgid "End of forbid list - %d/%d entries shown." +msgstr "Fin de la liste des interdits - %d/%d correspondances affichées." + +#: modules/commands/os_forbid.cpp:405 +msgid "End of forbid list." +msgstr "Fin de la liste des interdits." + +#: modules/commands/ns_alist.cpp:119 +#, c-format +msgid "End of list - %d channels shown." +msgstr "Fin de la liste - %d canaux affichés." + +#: modules/commands/ns_list.cpp:131 modules/commands/cs_list.cpp:130 +#, c-format +msgid "End of list - %d/%d matches shown." +msgstr "Fin de la liste - %d/%d correspondances affichées." + +#: modules/commands/os_news.cpp:176 +msgid "End of news list." +msgstr "Fin de la liste des news." + +#: modules/commands/os_list.cpp:235 +#, c-format +msgid "End of users list. %u users shown." +msgstr "Fin de la liste des utilisateurs. %u utilisateurs affichées." + +#: modules/commands/cs_enforce.cpp:227 +msgid "Enforce various channel modes and set options" +msgstr "Applique les modes et les paramètres divers d'un canal" + +#: modules/commands/cs_enforce.cpp:263 +msgid "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." +msgstr "" +"Applique divers modes et paramètres du canal. L'option canal\n" +"indique sur quel canal appliquer les modes et paramètres.\n" +"L'option quoi indique quels modes et paramètres sont à appliquer,\n" +"et peut être : SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS ou LIMIT.\n" +" \n" +"Utilisez SECUREOPS pour faire appliquer l'option SECUREOPS, même si\n" +"elle n'est pas activée. Utilisez RESTRICTED pour faire appliquer l'option " +"RESTRICTED,\n" +"même si elle n'est pas activée. Utilisez REGONLY pour kicker tous les\n" +"utilisateurs non enregistrés du canal. Utilisez SSLONLY pour kicker tous les " +"utilisateurs\n" +"qui n'utilisent pas une connexion sécurisée sur le canal. BANS forcera les " +"bans sur le canal\n" +"en kickant les utilisateurs affectés, et LIMIT kickera les utilisateurs\n" +"jusqu'à ce que leur nombre ne dépasse plus la limite du canal, si elle est " +"définie." + +#: src/language.cpp:43 modules/commands/ns_set.cpp:836 +#: modules/commands/ns_set.cpp:856 modules/commands/ns_set.cpp:891 +msgid "English" +msgstr "Français" + +#: modules/commands/cs_entrymsg.cpp:170 +#, c-format +msgid "Entry message %i for %s deleted." +msgstr "Le message d'accueil %i de %s a été effacé." + +#: modules/commands/cs_entrymsg.cpp:177 +#, c-format +msgid "Entry message %s not found on channel %s." +msgstr "Le message d'accueil %s n'a pas été trouvé sur le canal %s." + +#: modules/commands/cs_entrymsg.cpp:147 +#, c-format +msgid "Entry message added to %s" +msgstr "Le message d'accueil a été changé en %s" + +#: modules/commands/cs_entrymsg.cpp:109 modules/commands/cs_entrymsg.cpp:158 +#, c-format +msgid "Entry message list for %s is empty." +msgstr "La liste de messages d'accueil de %s est vide." + +#: modules/commands/cs_entrymsg.cpp:113 +#, c-format +msgid "Entry message list for %s:" +msgstr "Liste des messages d'accueil de %s :" + +#: modules/commands/cs_entrymsg.cpp:187 +#, c-format +msgid "Entry messages for %s have been cleared." +msgstr "Tous les messages d'accueil du canal %s ont été supprimés." + +#: modules/commands/os_reload.cpp:39 +#, c-format +msgid "Error reloading configuration file: %s" +msgstr "Erreur en rechargeant le fichier de configuration : %s" + +#: include/language.h:125 +#, c-format +msgid "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." +msgstr "" +"Erreur ! L'ident du vHost est trop long, merci d'utiliser un ident plus " +"court que %d caractères." + +#: include/language.h:124 +#, c-format +msgid "" +"Error! The vHost is too long, please use a hostname shorter than %d " +"characters." +msgstr "" +"Erreur ! Le vHost est trop long, merci d'utiliser un hostname plus court que " +"%d caractères." + +#: modules/commands/ns_cert.cpp:325 +msgid "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." +msgstr "" +"Exemples :\n" +" \n" +" CERT ADD\n" +" Ajoute le fingerprint de votre certificat actuel à la liste\n" +" des certificats et vous identifie automatiquement lorsque\n" +" vous vous connectez à IRC en utilisant ce certificat.\n" +" \n" +" CERT DEL \n" +" Supprime le fingerprint de votre liste de certificats.\n" +" \n" +" CERT LIST\n" +" Affiche votre liste actuelle de certificats." + +#: modules/commands/os_session.cpp:358 +#, c-format +msgid "Exception for %s has been updated to %d." +msgstr "L'exception pour %s a été changée pour %d sessions." + +#: modules/pseudoclients/chanserv.cpp:465 +#: modules/pseudoclients/nickserv.cpp:557 +#: modules/pseudoclients/nickserv.cpp:562 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_session.cpp:514 modules/commands/ns_group.cpp:327 +#: modules/commands/os_akill.cpp:358 +msgid "Expires" +msgstr "Expire" + +#: src/xline.cpp:397 +#, c-format +msgid "Expiry and reason updated for %s." +msgstr "Expiration et raison mises à jour pour %s." + +#: src/xline.cpp:400 +#, c-format +msgid "Expiry for %s updated." +msgstr "L'expiration de %s a été changée." + +#: modules/fantasy.cpp:214 +msgid "Fantasy" +msgstr "Fantaisie" + +#: modules/fantasy.cpp:60 +#, c-format +msgid "Fantasy mode is now off on channel %s." +msgstr "Le mode fantaisie est maintenant desactivé sur le canal %s." + +#: modules/fantasy.cpp:52 +#, c-format +msgid "Fantasy mode is now on on channel %s." +msgstr "Le mode fantaisie est maintenant activé sur le canal %s." + +#: modules/commands/cs_status.cpp:19 +msgid "Find a user's status on a channel" +msgstr "Trouve le statut d'un utilisateur sur un canal" + +#: modules/commands/ns_cert.cpp:192 +#, c-format +msgid "Fingerprint %s already present on %s's certificate list." +msgstr "Le fingerprint %s existe déjà dans la liste de certificats de %s." + +#: modules/commands/ns_cert.cpp:198 +#, c-format +msgid "Fingerprint %s is already in use." +msgstr "L'empreinte %s est déjà utilisée." + +#: modules/commands/cs_flags.cpp:301 +msgid "Flags" +msgstr "Flags" + +#: modules/commands/cs_flags.cpp:286 +#, c-format +msgid "Flags for %s on %s set to +%s" +msgstr "Les flags pour %s sur %s sont maintenant +%s" + +#: modules/commands/cs_flags.cpp:341 +#, c-format +msgid "Flags list for %s" +msgstr "Liste de flags pour %s" + +#: modules/commands/bs_kick.cpp:1161 modules/commands/bs_kick.cpp:1163 +#: modules/commands/bs_kick.cpp:1166 +msgid "Flood kicker" +msgstr "Kicker de flood" + +#: modules/commands/os_forbid.cpp:421 +msgid "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." +msgstr "" +"Forbid vous autorise à interdire l'utilisation de certains pseudos, canaux\n" +"et adresses email. Les jokers sont acceptés pour toutes les entrées." + +#: modules/commands/os_forbid.cpp:354 +msgid "Forbid list is empty." +msgstr "La liste des interdits est vide." + +#: modules/commands/os_forbid.cpp:396 +msgid "Forbid list:" +msgstr "Liste des interdits :" + +#: modules/commands/os_forbid.cpp:348 +#, c-format +msgid "Forbid on %s was not found." +msgstr "Interdiction sur %s non trouvée." + +#: modules/commands/os_forbid.cpp:156 +msgid "Forbid usage of nicknames, channels, and emails" +msgstr "Interdit l'utilisation de pseudos, canaux et adresses email." + +#: modules/commands/os_update.cpp:19 +msgid "Force the Services databases to be updated immediately" +msgstr "" +"Oblige les bases de données des Services à être sauvegardées immédiatement." + +#: modules/commands/os_svs.cpp:19 +msgid "Forcefully change a user's nickname" +msgstr "Force le changement de pseudo d'un utilisateur" + +#: modules/commands/os_svs.cpp:68 +msgid "Forcefully changes a user's nickname from nick to newnick." +msgstr "" +"Force le changement de pseudo d'un utilisateur de pseudo à nouveau-pseudo." + +#: modules/commands/os_svs.cpp:78 +msgid "Forcefully join a user to a channel" +msgstr "Oblige un utilisateur à joindre un canal." + +#: modules/commands/os_svs.cpp:112 +msgid "Forcefully join a user to a channel." +msgstr "Oblige un utilisateur à joindre un canal." + +#: modules/commands/os_svs.cpp:122 +msgid "Forcefully part a user from a channel" +msgstr "Oblige un utilisateur à partir d'un canal." + +#: modules/commands/os_svs.cpp:160 +msgid "Forcefully part a user from a channel." +msgstr "Oblige un utilisateur à partir d'un canal." + +#: modules/commands/ns_alist.cpp:64 modules/commands/cs_info.cpp:47 +msgid "Founder" +msgstr "Fondateur" + +#: modules/commands/cs_set.cpp:315 +#, c-format +msgid "Founder of %s changed to %s." +msgstr "Le fondateur de %s est maintenant %s." + +#: modules/commands/ns_getpass.cpp:41 +msgid "GETPASS command unavailable because encryption is in use." +msgstr "La commande GETPASS est indisponible car le chiffrement est utilisé." + +#: modules/commands/ns_recover.cpp:84 +msgid "Ghost with your nick has been killed." +msgstr "L'utilisateur fantôme utilisant votre pseudo a été déconnecté." + +#: modules/commands/os_oline.cpp:19 +msgid "Give Operflags to a certain user" +msgstr "Donne certains Operflags à un utilisateur" + +#: modules/commands/cs_mode.cpp:905 +#, c-format +msgid "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." +msgstr "" +"Donne le statut %s au pseudo choisi sur un canal. Si pseudo n'est\n" +"pas précisé vous aurez le statut %s." + +#: modules/commands/cs_mode.cpp:888 +#, c-format +msgid "Gives you or the specified nick %s status on a channel" +msgstr "Vous donne à vous ou à un pseudo spécifié, un accès %s sur un canal" + +#: modules/commands/greet.cpp:206 modules/commands/greet.cpp:212 +msgid "Greet" +msgstr "Message d'accueil" + +#: src/access.cpp:38 +msgid "Greet message displayed on join" +msgstr "Le message d'accueil sera affiché lors d'un JOIN" + +#: modules/commands/greet.cpp:112 +#, c-format +msgid "Greet message for %s changed to %s." +msgstr "Le message d'accueil de %s a été changé en %s" + +#: modules/commands/greet.cpp:118 +#, c-format +msgid "Greet message for %s unset." +msgstr "Le message d'accueil de %s a été effacé." + +#: modules/commands/greet.cpp:60 +#, c-format +msgid "Greet mode is now off on channel %s." +msgstr "Le message d'accueil est maintenant désactivé sur le canal %s." + +#: modules/commands/greet.cpp:52 +#, c-format +msgid "Greet mode is now on on channel %s." +msgstr "Le message d'accueil est maintenant activé sur le canal %s." + +#: modules/commands/ns_resetpass.cpp:21 +msgid "Helps you reset lost passwords" +msgstr "Vous aide pour réinitialiser les mots de passe perdus" + +#: modules/commands/ns_info.cpp:141 +msgid "Hide certain pieces of nickname information" +msgstr "Cache certaines informations du pseudo" + +#: modules/commands/cs_list.cpp:180 +msgid "Hide channel from the LIST command" +msgstr "Cacher le canal de la commande LIST" + +#: modules/commands/os_session.cpp:192 +msgid "Host" +msgstr "Hôte" + +#: modules/commands/os_session.cpp:207 +#, c-format +msgid "Hosts with at least %d sessions:" +msgstr "Hôtes ayant au moins %d sessions :" + +#: modules/commands/cs_seen.cpp:207 +#, c-format +msgid "I don't know who %s is." +msgstr "Je ne sais pas qui est %s." + +#: modules/commands/cs_seen.cpp:253 +#, c-format +msgid "I've never seen %s on this channel." +msgstr "Je n'ai jamais vu %s sur ce canal." + +#: modules/commands/os_sxline.cpp:203 modules/commands/os_akill.cpp:360 +msgid "ID" +msgstr "ID" + +#: modules/commands/os_oper.cpp:72 +msgid "INFO [type]" +msgstr "INFO [type]" + +#: modules/commands/os_dns.cpp:218 +msgid "IP" +msgstr "IP" + +#: modules/commands/os_dns.cpp:500 +#, c-format +msgid "IP %s already exists for %s." +msgstr "L'adresse IP %s existe déjà pour %s." + +#: modules/commands/os_dns.cpp:562 +#, c-format +msgid "IP %s does not exist for %s." +msgstr "L'adresse IP %s n'existe pas pour %s." + +#: modules/commands/ns_identify.cpp:65 +msgid "Identify yourself with your password" +msgstr "Vous identifie avec votre mot de passe" + +#: modules/pseudoclients/nickserv.cpp:205 +#: modules/pseudoclients/nickserv.cpp:211 +#, c-format +msgid "If you do not change within %s, I will change your nick." +msgstr "Si vous n'en changez pas d'ici %s, je changerai votre pseudo." + +#: modules/commands/os_ignore.cpp:333 +msgid "Ignore list has been cleared." +msgstr "La liste des ignorés a été vidée." + +#: modules/commands/os_ignore.cpp:262 +msgid "Ignore list is empty." +msgstr "La liste des ignorés est vide." + +#: modules/commands/ms_ignore.cpp:94 +msgid "Ignore list:" +msgstr "Liste des ignorés :" + +#: modules/commands/ns_set.cpp:1305 +msgid "Immediate protection" +msgstr "Protection immédiate" + +#: modules/commands/ns_resetpass.cpp:33 +msgid "Incorrect email address." +msgstr "Adresse email incorrecte." + +#: include/language.h:89 +msgid "Incorrect range specified. The correct syntax is #from-to." +msgstr "Intervalle spécifié incorrect. La syntaxe correcte est #début-fin." + +#: modules/commands/os_modinfo.cpp:19 +msgid "Info about a loaded module" +msgstr "Informations à propos d'un module chargé" + +#: modules/commands/bs_info.cpp:54 +#, c-format +msgid "Information for bot %s:" +msgstr "Information à propos du bot %s :" + +#: include/language.h:108 +#, c-format +msgid "Information for channel %s:" +msgstr "Informations à propos du canal %s :" + +#: modules/commands/os_logsearch.cpp:57 +#, c-format +msgid "Invalid duration %s, using %d days." +msgstr "Durée %s invalide, %d jours seront utilisés." + +#: include/language.h:68 +msgid "Invalid expiry time." +msgstr "Temps d'expiration invalide." + +#: modules/commands/os_session.cpp:346 +msgid "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not " +"matched against nicks or usernames." +msgstr "" +"Masque d'hôte invalide. Seuls les masques d'hôtes réels sont valides puisque " +"les exceptions ne sont pas comparées aux pseudos et utilisateurs." + +#: modules/commands/os_logsearch.cpp:73 +#, c-format +msgid "Invalid limit %s, using %d." +msgstr "Limite %s invalide, %d sera utilisé." + +#: include/language.h:99 +msgid "" +"Invalid passcode has been entered, please check the e-mail again, and retry." +msgstr "" +"Un mot-code invalide a été entré, merci de re-vérifier votre email et de " +"réessayer." + +#: modules/commands/ns_register.cpp:83 modules/commands/ns_register.cpp:86 +msgid "Invalid passcode." +msgstr "Mot code invalide." + +#: modules/commands/os_session.cpp:339 +#, c-format +msgid "" +"Invalid session limit. It must be a valid integer greater than or equal to " +"zero and less than %d." +msgstr "" +"Limite de sessions invalide. Elle doit être un entier supérieur ou égal à " +"zéro et plus petit que %d." + +#: modules/commands/os_session.cpp:188 +msgid "Invalid threshold value. It must be a valid integer greater than 1." +msgstr "Valeur minimale invalide. Elle doit être un entier supérieur à 1." + +#: modules/commands/os_dns.cpp:591 +msgid "Invalid value for LIMIT. Must be numerical." +msgstr "Valeur pour LIMIT invalide. Cette valeur doit être un nombre." + +#: modules/commands/cs_invite.cpp:19 +msgid "Invites you or an optionally specified nick into a channel" +msgstr "Vous invite vous ou un pseudo indiqué sur un canal" + +#: modules/commands/bs_kick.cpp:1201 modules/commands/bs_kick.cpp:1203 +#: modules/commands/bs_kick.cpp:1206 +msgid "Italics kicker" +msgstr "Kicker d'italique" + +#: modules/commands/ns_group.cpp:91 +msgid "Join a group" +msgstr "Rejoint un groupe" + +#: modules/commands/cs_set.cpp:1305 modules/commands/ns_set.cpp:1319 +msgid "Keep modes" +msgstr "Maintien des modes" + +#: modules/commands/cs_set.cpp:377 modules/commands/ns_set.cpp:603 +#, c-format +msgid "Keep modes for %s is now off." +msgstr "Le maintien des modes pour %s est maintenant inactif." + +#: modules/commands/cs_set.cpp:369 modules/commands/ns_set.cpp:597 +#, c-format +msgid "Keep modes for %s is now on." +msgstr "Le maintien des modes pour %s est maintenant actif." + +#: modules/commands/ns_ajoin.cpp:100 +msgid "Key" +msgstr "Clé" + +#: modules/commands/cs_getkey.cpp:50 +#, c-format +msgid "Key for channel %s is %s." +msgstr "La clé du canal %s est %s." + +#: modules/commands/os_kick.cpp:19 +msgid "Kick a user from a channel" +msgstr "Expulse un utilisateur d'un canal" + +#: modules/commands/cs_ban.cpp:217 modules/commands/cs_kick.cpp:116 +#, c-format +msgid "Kicked %d/%d users matching %s from %s." +msgstr "A kické %d/%d utilisateurs correspondant à %s sur %s." + +#: modules/commands/cs_kick.cpp:19 +msgid "Kicks a specified nick from a channel" +msgstr "Expulse le pseudo spécifié d'un canal" + +#: modules/commands/cs_kick.cpp:128 +msgid "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." +msgstr "" +"Kicke le pseudo désigné d'un canal.\n" +" \n" +"Par défaut, limité aux AOPs ou à ceux ayant un niveau \n" +"d'accès de 5 ou plus sur le canal. Les fondateurs du salon\n" +"peuvent aussi spécifier un masque." + +#: modules/commands/os_kill.cpp:19 +msgid "Kill a user" +msgstr "Kill un utilisateur" + +#: modules/commands/cs_enforce.cpp:217 +msgid "LIMIT enforced by " +msgstr "LIMIT appliquée par" + +#: modules/commands/cs_enforce.cpp:221 +#, c-format +msgid "LIMIT enforced on %s, %d users removed." +msgstr "LIMIT appliquée sur %s, %d utilisateurs supprimés." + +#: modules/commands/os_session.cpp:246 +msgid "LIST threshold" +msgstr "LIST seuil" + +#: modules/commands/os_sxline.cpp:427 modules/commands/os_sxline.cpp:661 +#: modules/commands/os_akill.cpp:388 +msgid "LIST [mask | list | id]" +msgstr "LIST [masque | liste | id]" + +#: modules/commands/os_session.cpp:525 +msgid "LIST [mask | list]" +msgstr "LIST [masque] [liste]" + +#: modules/commands/ns_access.cpp:104 modules/commands/ns_cert.cpp:260 +#: modules/commands/ns_ajoin.cpp:233 +msgid "LIST [nickname]" +msgstr "LIST [pseudo]" + +#: modules/commands/os_news.cpp:31 +msgid "LOGONNEWS {ADD|DEL|LIST} [text|num]" +msgstr "LOGONNEWS {ADD|DEL|LIST} [texte|numéro]" + +#: modules/commands/ns_set.cpp:834 +msgid "Language changed to English." +msgstr "Votre langue est maintenant le Français." + +#: modules/commands/ns_set.cpp:836 +#, c-format +msgid "Language for %s changed to %s." +msgstr "La langue utilisée par %s est désormais %s." + +#: modules/commands/ms_cancel.cpp:72 +#, c-format +msgid "Last memo to %s has been cancelled." +msgstr "Le dernier mémo envoyé à %s a été supprimé." + +#: modules/commands/ns_info.cpp:95 +msgid "Last quit message" +msgstr "Dernier message de quit" + +#: modules/commands/cs_access.cpp:472 modules/commands/ns_info.cpp:92 +msgid "Last seen" +msgstr "Dernière connexion" + +#: modules/commands/ns_info.cpp:81 modules/commands/ns_info.cpp:86 +msgid "Last seen address" +msgstr "Dernière adresse vue" + +#: modules/commands/cs_topic.cpp:264 +msgid "Last topic" +msgstr "Dernier topic" + +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_info.cpp:56 +msgid "Last used" +msgstr "Utilisé dernièrement" + +#: modules/commands/ns_list.cpp:75 +msgid "Last usermask" +msgstr "Dernier usermask" + +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +#: modules/commands/cs_access.cpp:697 +msgid "Level" +msgstr "Niveau" + +#: modules/commands/cs_access.cpp:660 +#, c-format +msgid "Level for %s on channel %s changed to %d." +msgstr "Le niveau pour %s du channel %s est maintenant de %d." + +#: modules/commands/cs_access.cpp:658 +#, c-format +msgid "Level for %s on channel %s changed to founder only." +msgstr "" +"Le niveau pour %s sur le canal %s est désormais restreint au fondateur." + +#: modules/commands/cs_access.cpp:643 +#, c-format +msgid "Level must be between %d and %d inclusive." +msgstr "Le niveau doit être compris entre %d et %d inclus." + +#: modules/commands/os_dns.cpp:218 modules/commands/os_session.cpp:506 +#: modules/commands/os_session.cpp:514 +msgid "Limit" +msgstr "Limite" + +#: modules/commands/ns_list.cpp:19 +msgid "List all registered nicknames that match a given pattern" +msgstr "Liste tous les pseudos enregistrés en rapport avec la recherche" + +#: modules/commands/ns_alist.cpp:24 +msgid "List channels you have access on" +msgstr "Liste tous les canaux auxquels vous avez accès" + +#: modules/commands/cs_mode.cpp:341 +#, c-format +msgid "List for mode %c is full." +msgstr "La liste pour le mode %c est pleine." + +#: modules/commands/os_modinfo.cpp:80 +msgid "List loaded modules" +msgstr "Liste les modules chargés" + +#: modules/commands/ns_list.cpp:123 modules/commands/cs_list.cpp:72 +#, c-format +msgid "List of entries matching %s:" +msgstr "Liste des entrées correspondantes à %s :" + +#: modules/commands/ns_group.cpp:350 +#, c-format +msgid "List of nicknames in the group of %s:" +msgstr "Liste des pseudos dans le groupe de %s :" + +#: modules/commands/ns_group.cpp:350 +msgid "List of nicknames in your group:" +msgstr "Liste des pseudos dans votre groupe :" + +#: modules/commands/ms_list.cpp:19 +msgid "List your memos" +msgstr "Liste vos mémos" + +#: modules/commands/bs_botlist.cpp:64 +msgid "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." +msgstr "" +"Liste tous les bots disponibles sur ce réseau.\n" +"Les bots préfixés par * sont réservés aux Opérateurs IRC." + +#: modules/commands/os_list.cpp:19 +msgid "Lists all channel records" +msgstr "Liste tous les canaux" + +#: modules/commands/os_list.cpp:107 +msgid "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." +msgstr "" +"Liste tous les canaux actuellement utilisés sur le réseau IRC, qu'ils\n" +"soient enregistrés ou non.\n" +" \n" +"Si modèle est donné, seuls les canaux correspondants sont listés. Si\n" +"un pseudo est donné, les canaux sur lesquels est l'utilisateur ayant\n" +"ce pseudo seront listés. Si SECRET est spécifié, liste seulement les " +"canaux \n" +"correspondants à modèle qui ont le mode +s ou +p." + +#: modules/commands/ns_alist.cpp:127 +msgid "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" +msgstr "" +"Liste tous les canaux auxquels vous avez accès.\n" +" \n" +"Les canaux qui ont l'option NOEXPIRE activée seront\n" +"préfixés d'un point d'exclamation. Le paramètre pseudo est\n" +"restreint aux Opérateurs des Services." + +#: modules/commands/ns_group.cpp:299 +msgid "Lists all nicknames in your group" +msgstr "Liste les pseudos dans votre groupe" + +#: modules/commands/cs_list.cpp:20 +msgid "Lists all registered channels matching the given pattern" +msgstr "Liste tous les canaux enregistrés en rapport avec la recherche" + +#: modules/commands/cs_list.cpp:137 +msgid "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." +msgstr "" +"Liste tous les canaux enregistrés qui correspondent au modèle donné. Les\n" +"canaux ayant l'option PRIVATE ne seront affichés qu'aux Opérateurs\n" +"des Services avec les accès nécessaires. Les canaux ayant l'option\n" +"NOEXPIRE seront préfixés par un ! pour les Opérateurs des \n" +"Services.\n" +"Notez qu'un modèle dont le premier caractère est '#' est une plage de\n" +"numéros. Les noms de canaux doivent être écrits sans '#'.\n" +" \n" +"Si les options SUSPENDED ou NOEXPIRE sont données,\n" +"seuls les canaux qui sont respectivement SUSPENDED ou NOEXPIRE\n" +"seront affichés. Si plusieurs options sont données, tous les canaux\n" +"correspondant à au moins une des options seront affichés.\n" +"Notez que ces options sont limitées aux Opérateurs des Services.\n" +" \n" +"Exemples :\n" +" \n" +" LIST *anope*\n" +" Liste tous les canaux avec anope dans leur\n" +" nom (non sensible à la casse).\n" +" \n" +" LIST * NOEXPIRE\n" +" Liste tous les canaux qui ont été configurés pour ne pas expirer.\n" +" \n" +" LIST #51-100\n" +" Liste tous les canaux entre les n°51 et n°100." + +#: modules/commands/ns_list.cpp:139 +msgid "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." +msgstr "" +"Liste tous les pseudos enregistrés qui correspondent au modèle\n" +"donné, de format pseudo!user@host. Les pseudos ayant l'option\n" +"PRIVATE ne seront affichés qu'aux Opérateurs des Services. Les\n" +"pseudos ayant l'option NOEXPIRE auront leur pseudo préfixé\n" +"par un ! pour les Opérateurs des Services.\n" +" \n" +"Notez que si le premier caractère est '#', il s'agit d'une plage de " +"numéros.\n" +" \n" +"Si les options SUSPENDED, UNCONFIRMED ou NOEXPIRE sont données,\n" +"seuls les pseudos qui sont suspendus, non-confirmés ou qui n'expirent pas\n" +"seront affichés. Si plus d'une option sont indiquées, tous les pseudos\n" +"correspondants à un des critères seront affichés. Ces options sont " +"restreintes\n" +"aux Opérateurs des Services. \n" +" \n" +"Exemples :\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Liste tous les pseudos enregistrés appartenant à \n" +" joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Liste tous les pseudos enregistrés ayant Bot dans\n" +" leur nom (ne respecte pas les majuscules).\n" +" \n" +" LIST * NOEXPIRE\n" +" Liste tous les pseudos qui n'expireront pas. \n" +" \n" +" LIST #51-100\n" +" Liste tous les pseudos enregistrés entre 51 et 100." + +#: modules/commands/os_list.cpp:132 +msgid "Lists all user records" +msgstr "Liste tous les utilisateurs" + +#: modules/commands/os_list.cpp:243 +#, fuzzy +msgid "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only " +"users\n" +"with the +i flag will be listed." +msgstr "" +"Liste tous les utilisateurs connectés sur le réseau IRC, enregistrés\n" +"ou non.\n" +" \n" +"Si modèle est donné (format pseudo!user@host), seuls les utilisateurs \n" +"correspondants seront listés. Si canal est donné, seuls les \n" +"utilisateurs du canal seront listés. Si INVISIBLE est indiqué,\n" +"seuls les utilisateurs avec le mode +i seront listés." + +#: modules/commands/ms_list.cpp:142 +msgid "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Liste tous les mémos que vous avez actuellement. Avec NEW,\n" +"liste uniquement les nouveaux mémos (non lus). Les mémos non\n" +"lus sont marqués avec une \"*\" à gauche du numéro du mémo. Vous\n" +"pouvez également spécifier une liste de numéros, comme dans\n" +"l'exemple ci dessous :\n" +" LIST 2-5,7-9\n" +" Liste les mémos 2 à 5 et 7 à 9." + +#: modules/commands/bs_botlist.cpp:19 +msgid "Lists available bots" +msgstr "Liste les bots disponibles" + +#: modules/commands/os_modinfo.cpp:196 +msgid "Lists currently loaded modules." +msgstr "Liste les modules chargés." + +#: modules/commands/cs_info.cpp:19 +msgid "Lists information about the specified registered channel" +msgstr "Liste les informations à propos d'un canal enregistré" + +#: modules/commands/cs_info.cpp:76 +msgid "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." +msgstr "" +"Liste les informations concernant un canal enregistré,\n" +"notamment son fondateur, la date d'enregistrement,\n" +"la date de dernière utilisation et la description. Si l'utilisateur\n" +"qui exécute la commande a les accès appropriés, alors le successeur,\n" +"le dernier topic défini, les paramètres et le délai d'expiration\n" +" seront également affichés s'ils sont disponibles." + +#: modules/commands/os_module.cpp:19 +msgid "Load a module" +msgstr "Charge un module" + +#: modules/commands/cs_register.cpp:39 +msgid "Local channels cannot be registered." +msgstr "Les canaux locaux ne peuvent être enregistrés." + +#: modules/commands/cs_log.cpp:142 +#, c-format +msgid "Log list for %s:" +msgstr "Liste de log pour %s :" + +#: modules/commands/cs_log.cpp:227 +#, c-format +msgid "Logging changed for command %s on %s, now using log method %s%s%s." +msgstr "" +"Les logs ont changé pour la commande %s de %s, la méthode utilisée est " +"maintenant %s%s%s." + +#: modules/commands/cs_log.cpp:220 +#, c-format +msgid "Logging for command %s on %s with log method %s%s%s has been removed." +msgstr "" +"Les logs pour la commande %s sur %s avec la méthode %s%s%s ont été " +"désactivés." + +#: modules/commands/cs_log.cpp:248 +#, c-format +msgid "Logging is now active for command %s on %s, using log method %s%s%s." +msgstr "" +"Les logs sont maintenant actifs pour la commande %s sur %s, en utilisant la " +"méthode %s%s%s." + +#: modules/commands/os_login.cpp:60 +#, c-format +msgid "Login to %s" +msgstr "S'identifier à %s" + +#: modules/commands/os_news.cpp:36 +#, c-format +msgid "Logon news item #%d deleted." +msgstr "News de connexion n°%d supprimée." + +#: modules/commands/os_news.cpp:35 +#, c-format +msgid "Logon news item #%s not found!" +msgstr "News de connexion n°%s non trouvée !" + +#: modules/commands/os_news.cpp:32 +msgid "Logon news items:" +msgstr "News de connexion :" + +#: modules/commands/os_login.cpp:102 +#, c-format +msgid "Logout from %s" +msgstr "Déconnexion de %s" + +#: modules/commands/os_login.cpp:52 +#, c-format +msgid "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." +msgstr "" +"Vous connecte à %s pour obtenir les privilèges d'Opérateur des Services.\n" +"Cette commande est utile uniquement si votre bloc oper est configuré\n" +"avec un mot de passe." + +#: modules/commands/os_login.cpp:94 +#, c-format +msgid "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." +msgstr "" +"Vous déconnecte de %s pour que vous n'ayez plus les privilèges\n" +"d'Opérateur des Services. Cette commande est utile uniquement si\n" +"votre bloc oper est configuré avec un mot de passe." + +#: modules/commands/cs_seen.cpp:213 +#, c-format +msgid "Looking for yourself, eh %s?" +msgstr "Alors ? On se cherche soi-même, %s ?" + +#: modules/commands/cs_mode.cpp:773 +#, c-format +msgid "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a " +"channel.\n" +"If a mode is locked on or off, services will not allow that mode to be " +"changed. The SET\n" +"command will clear all existing mode locks and set the new one given, while " +"ADD and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * " +"and ? may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may " +"be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, " +"halfops, and voices. If what\n" +"is not given then all basic modes are removed." +msgstr "" +"Contrôle le verrouillage de modes et les modes d'accès (ce qui est " +"différents desaccès au canal)\n" +"sur un canal.\n" +" \n" +"La commande %s LOCK vous permet d'ajouter, de supprimer et de voir les modes " +"verrouillés\n" +"d'un canal. Si un mode est verrouillé en position activée ou désactivée, les " +"services n'autoriseront\n" +"pas la modification de ce mode. La commande SET supprimera tous les modes " +"existants et\n" +"définira le(s) nouveau(x) mode(s) indiqué(s), tandis que ADD et DEL " +"modifient les modes\n" +"verrouillés existants.\n" +"Exemple :\n" +" MODE #canal LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"La commande %s SET vous permet de définir les modes via les services. Les " +"joker * et ?\n" +"peuvent être donnés en tant que paramètre pour les modes de statut et de " +"listes.\n" +"Exemple :\n" +" MODE #canal SET +v *\n" +" Donne le statut voice à tous les utilisateurs du canal.\n" +" \n" +" MODE #canal SET -b ~c:*\n" +" Supprime tous les bans étendus qui commencent par ~c:\n" +" \n" +"La commande %s CLEAR est une façon simple de supprimer tous les modes d'un " +"canal. quoi\n" +"peut être n'importe quel nom de mode. Par exemple, 'bans', 'excepts', " +"'inviteoverrides', 'ops',\n" +"'halfops' ou 'voices'. Si quoi n'est pas donné, alors tous les modes " +"basiques sont supprimés." + +#: modules/commands/cs_akick.cpp:434 +msgid "Maintain the AutoKick list" +msgstr "Gère la liste des kicks automatiques" + +#: modules/commands/bs_bot.cpp:269 +msgid "Maintains network bot list" +msgstr "Gère la liste des bots du réseau" + +#: modules/commands/cs_xop.cpp:522 +#, c-format +msgid "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " +msgstr "" +"Gère la liste des %s pour un canal. Les utilisateurs qui correspondent à un\n" +"une entrée sur la liste des %s recevront les privilèges suivants :" + +#: modules/commands/cs_akick.cpp:493 +#, c-format +msgid "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" +msgstr "" +"Gère la liste des AutoKicks sur un canal. Si un utilisateur\n" +"sur la liste des kicks automatiques tente de joindre le canal, %s\n" +"bannira cet utilisateur du canal, puis le kickera.\n" +" \n" +"La commande AKICK ADD ajoute le pseudo ou le masque\n" +"utilisateur donné à la liste des kicks automatiques. Si une raison est\n" +"donnée avec la commande, cette raison sera utilisée lors du kick\n" +"de l'utilisateur, sinon, la raison par défaut \"L'utilisateur a été banni\n" +"du canal\".\n" +"Si le pseudo est enregistré le compte %s\n" +"sera ajouté à la liste des kicks automatiques à la place du masque.\n" +"Tous les utilisateurs de ce groupe seront akick.\n" + +#: modules/commands/cs_access.cpp:568 +#, c-format +msgid "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." +msgstr "" +"Gère la liste d'accès d'un canal. La liste d'accès spécifie\n" +"quels utilisateurs doivent obtenir le statut d'opérateur ou\n" +"accéder aux commandes %s du canal. Des niveaux d'utilisateur\n" +"différents existent pour des accès à différents types de privilèges.\n" +"Un utilisateur enregistré qui n'est pas sur la liste d'accès a un niveau\n" +"utilisateur de 0 et un utilisateur non-enregistré a un niveau de -1." + +#: modules/commands/bs_badwords.cpp:424 +#, c-format +msgid "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" +msgstr "" +"Gère la liste des mots interdits d'un canal. La liste\n" +"des mots interdits détermine quels mots doivent être kickés\n" +"quand le kicker de mots interdits est activé. Pour plus\n" +"d'information, tapez %s%s HELP KICK %s.\n" +" \n" +"La commande ADD ajoute le mot donné à la liste\n" +"de mots interdits. Si SINGLE est donné, un kick ne sera\n" +"effectué que si un utilisateur dit le mot en entier. Si\n" +"START est donné, un kick ne sera effectué que si un\n" +"utilisateur dit un mot qui commence par mot. Si END\n" +"est spécifié, un kick ne sera effectué que si un utilisateur\n" +"dit un mot qui se termine par mot. Si vous ne spécifiez\n" +"rien, un kick sera effectué chaque fois que mot est dit\n" +"par un utilisateur.\n" +" \n" + +#: modules/commands/bs_badwords.cpp:370 +msgid "Maintains the bad words list" +msgstr "Gère la liste des mots interdits" + +#: modules/commands/bs_control.cpp:79 +msgid "Makes the bot do the equivalent of a \"/me\" command" +msgstr "Fait faire au bot l'équivalent de la commande \"/me\"" + +#: modules/commands/bs_control.cpp:127 +msgid "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." +msgstr "" +"Fait faire au bot l'équivalent d'une commande \"/me\"\n" +"sur le canal donné avec le texte donné." + +#: modules/commands/bs_control.cpp:19 +msgid "Makes the bot say the specified text on the specified channel" +msgstr "Fait dire au bot le texte donné sur un canal." + +#: modules/commands/bs_control.cpp:69 +msgid "Makes the bot say the specified text on the specified channel." +msgstr "Fait dire au bot le texte donné sur un canal." + +#: modules/commands/greet.cpp:157 +msgid "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." +msgstr "" +"Définit un message d'accueil au pseudo, qui sera\n" +"affiché lorsqu'il rejoint un canal qui a l'option\n" +"GREET active, à condition d'avoir un niveau d'accès\n" +"suffisant." + +#: modules/commands/greet.cpp:131 +msgid "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." +msgstr "" +"Définit un message d'accueil pour votre pseudo, qui sera\n" +"affiché lorsque vous joignez un canal qui a l'option\n" +"GREET active, à condition d'avoir un niveau d'accès\n" +"suffisant." + +#: modules/commands/os_dns.cpp:660 +msgid "Manage DNS zones for this network" +msgstr "Gère les zones DNS pour ce réseau" + +#: modules/commands/cs_entrymsg.cpp:193 +msgid "Manage the channel's entry messages" +msgstr "Gère les messages d'entrée du canal" + +#: modules/commands/ms_ignore.cpp:19 +msgid "Manage the memo ignore list" +msgstr "Gère la liste d'ignore de mémos" + +#: modules/commands/ns_ajoin.cpp:230 +msgid "Manage your auto join list" +msgstr "Gère la liste des JOIN automatiques" + +#: modules/commands/os_sxline.cpp:233 +#, c-format +msgid "Manipulate the %s list" +msgstr "Contrôle la liste des %s" + +#: modules/commands/os_akill.cpp:385 +msgid "Manipulate the AKILL list" +msgstr "Contrôle la liste des AKILLs" + +#: modules/commands/os_defcon.cpp:176 +msgid "Manipulate the DefCon system" +msgstr "Active/Désactive DefCon" + +#: modules/commands/cs_topic.cpp:149 +msgid "Manipulate the topic of the specified channel" +msgstr "Change le sujet sur un canal spécifié" + +#: modules/commands/bs_botlist.cpp:27 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_forbid.cpp:358 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/ms_ignore.cpp:86 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_list.cpp:153 modules/commands/bs_info.cpp:55 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +msgid "Mask" +msgstr "Masque" + +#: modules/commands/ns_access.cpp:39 +#, c-format +msgid "Mask %s already present on %s's access list." +msgstr "Le masque %s existe déjà dans la liste d'accès de %s." + +#: include/language.h:67 +msgid "Mask must be in the form user@host." +msgstr "Le masque doit être de la forme user@host." + +#: modules/commands/cs_access.cpp:166 modules/commands/cs_flags.cpp:120 +#: modules/commands/cs_xop.cpp:162 +msgid "Masks and unregistered users may not be on access lists." +msgstr "" +"Les masques et les utilisateurs non enregistrés ne peuvent pas être dans la " +"liste d'accès." + +#: modules/commands/ns_getemail.cpp:23 +msgid "Matches and returns all users that registered using given email" +msgstr "" +"Cherche et retourne la liste des pseudos enregistrés avec l'email donné" + +#: modules/commands/os_logsearch.cpp:148 +#, c-format +msgid "Matches for %s:" +msgstr "Correspondances pour %s :" + +#: modules/commands/os_stats.cpp:139 +#, c-format +msgid "Maximum users: %d (%s)" +msgstr "Record d'utilisateurs : %d (%s)" + +#: modules/commands/ms_read.cpp:84 modules/commands/ms_read.cpp:86 +#, c-format +msgid "Memo %d from %s (%s)." +msgstr "Mémo %d par %s (%s)." + +#: modules/commands/ms_del.cpp:33 modules/commands/ms_del.cpp:101 +#, c-format +msgid "Memo %d has been deleted." +msgstr "Le mémo %d a été supprimé." + +#: modules/commands/ms_ignore.cpp:82 +msgid "Memo ignore list is empty." +msgstr "La liste des ignorés est vide." + +#: modules/commands/ms_set.cpp:199 +#, c-format +msgid "Memo limit disabled for %s." +msgstr "La limite de mémos de %s a été désactivée." + +#: modules/commands/ms_set.cpp:185 +#, c-format +msgid "Memo limit for %s set to %d." +msgstr "La limite de mémos de %s a été définie à %d." + +#: modules/commands/ms_set.cpp:192 +#, c-format +msgid "Memo limit for %s set to 0." +msgstr "La limite de mémos de %s a été définie à 0." + +#: modules/commands/ms_rsend.cpp:63 modules/commands/ms_send.cpp:51 +#, c-format +msgid "Memo sent to %s." +msgstr "Mémo envoyé à %s." + +#: modules/commands/ms_list.cpp:131 +#, c-format +msgid "Memos for %s:" +msgstr "Mémos pour %s :" + +#: modules/commands/cs_entrymsg.cpp:116 +msgid "Message" +msgstr "Message" + +#: modules/commands/ns_set.cpp:1313 +msgid "Message mode" +msgstr "Mode message" + +#: modules/commands/cs_log.cpp:127 +msgid "Method" +msgstr "Méthode" + +#: modules/commands/cs_mode.cpp:329 modules/commands/cs_mode.cpp:420 +#, c-format +msgid "Missing parameter for mode %c." +msgstr "Paramètre manquant pour le mode %c." + +#: modules/commands/cs_mode.cpp:449 +msgid "Mode" +msgstr "Mode" + +#: modules/commands/cs_mode.cpp:718 +#, c-format +msgid "Mode %s is a virtual mode and can't be cleared." +msgstr "Le mode %s est un mode virtuel et ne peut pas être supprimer." + +#: modules/commands/cs_mode.cpp:712 +#, c-format +msgid "Mode %s is not a status or list mode." +msgstr "Le mode %s n'est pas un mode de statut ou de liste." + +#: modules/commands/cs_mode.cpp:1065 +msgid "Mode lock" +msgstr "Modes verrouillés" + +#: modules/commands/cs_mode.cpp:466 +#, c-format +msgid "Mode locks for %s:" +msgstr "Modes verrouillés pour %s :" + +#: modules/commands/os_list.cpp:43 +msgid "Modes" +msgstr "Modes" + +#: modules/commands/os_mode.cpp:44 +#, c-format +msgid "Modes cleared on %s and the channel destroyed." +msgstr "Modes supprimés sur %s et canal détruit." + +#: modules/commands/ns_access.cpp:166 +#, c-format +msgid "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." +msgstr "" +"Modifie ou affiche la liste d'accès de votre pseudo. C'est\n" +"la liste des adresses qui seront automatiquement reconnues\n" +"par %s comme autorisées à utiliser le pseudo. Si vous voulez\n" +"utiliser le pseudo depuis une adresse différente, vous devez\n" +"envoyer une commande IDENTIFY pour que %s vous reconnaisse.\n" +"Les Opérateurs des Services peuvent indiquer un pseudo pour\n" +"modifier la liste d'accès d'un autre utilisateur.\n" +" \n" +"Exemples :\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Autorise l'accès à l'utilisateur anyone d'une\n" +" machine avec le domaine bepeg.com.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Inverse de la commande précédente.\n" +" \n" +" ACCESS LIST\n" +" Affiche votre liste d'accès." + +#: modules/commands/ns_cert.cpp:319 +msgid "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" +msgstr "" +"Modifie ou affiche la liste de certificats pour votre pseudo.\n" +"Si vous vous connectez à IRC et fournissez un certificat avec\n" +"une empreinte (fingerprint) dans la liste des certificats, votre\n" +"pseudo sera automatiquement identifié auprès des services.\n" +"Les Opérateurs des Services peuvent fournir un pseudo\n" +"pour modifier la liste de certificats d'autres utilisateurs\n" +" \n" + +#: modules/commands/os_ignore.cpp:341 +msgid "Modify the Services ignore list" +msgstr "Modifie la liste d'ignore des Services" + +#: modules/commands/cs_xop.cpp:489 +#, c-format +msgid "Modify the list of %s users" +msgstr "Modifie la liste des utilisateurs %s" + +#: modules/commands/ns_access.cpp:101 +msgid "Modify the list of authorized addresses" +msgstr "Modifie la liste des adresses autorisées" + +#: modules/commands/cs_access.cpp:498 modules/commands/cs_flags.cpp:373 +msgid "Modify the list of privileged users" +msgstr "Modifie la liste des utilisateurs privilégiés" + +#: modules/commands/ns_cert.cpp:257 +msgid "Modify the nickname client certificate list" +msgstr "Modifie la liste de certificats du pseudo" + +#: modules/commands/os_session.cpp:522 +msgid "Modify the session-limit exception list" +msgstr "Modifie la liste d'exceptions à la limite de sessions" + +#: modules/commands/os_module.cpp:34 +#, c-format +msgid "Module %s is already loaded." +msgstr "Le module %s est déjà chargé." + +#: modules/commands/os_module.cpp:67 modules/commands/os_module.cpp:139 +#, c-format +msgid "Module %s isn't loaded." +msgstr "Le module %s n'est pas chargé." + +#: modules/commands/os_module.cpp:31 +#, c-format +msgid "Module %s loaded." +msgstr "Module %s chargé." + +#: modules/commands/os_module.cpp:98 +#, c-format +msgid "Module %s reloaded." +msgstr "Module %s rechargé." + +#: modules/commands/os_module.cpp:156 +#, c-format +msgid "Module %s unloaded." +msgstr "Module %s déchargé." + +#: modules/commands/os_config.cpp:88 +msgid "Module Name" +msgstr "Nom du module" + +#: modules/commands/os_config.cpp:112 +msgid "Module settings:" +msgstr "Paramètres du module :" + +#: modules/commands/os_modinfo.cpp:32 +#, c-format +msgid "Module: %s Version: %s Author: %s Loaded: %s" +msgstr "Module : %s Version : %s Auteur : %s Chargé : %s" + +#: modules/commands/os_modinfo.cpp:183 +#, c-format +msgid "Module: %s [%s] [%s]" +msgstr "Module : %s [%s] [%s]" + +#: modules/commands/cs_access.cpp:697 modules/commands/cs_access.cpp:799 +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +#: modules/commands/cs_list.cpp:75 modules/commands/os_list.cpp:43 +#: modules/commands/os_list.cpp:153 +msgid "Name" +msgstr "Nom" + +#: modules/commands/os_oper.cpp:153 +msgid "Name Type" +msgstr "Nom Type" + +#: modules/extra/stats/cs_fantasy_stats.cpp:146 +#, c-format +msgid "Network stats for %s:" +msgstr "Statistiques de réseau pour %s :" + +#: modules/commands/os_forbid.cpp:384 +msgid "Never" +msgstr "Jamais" + +#: modules/commands/hs_list.cpp:58 modules/commands/bs_botlist.cpp:27 +#: modules/commands/hs_request.cpp:305 modules/commands/ns_list.cpp:75 +#: modules/commands/ns_group.cpp:327 +msgid "Nick" +msgstr "Pseudo" + +#: modules/commands/ns_register.cpp:42 +#, c-format +msgid "Nick %s has been confirmed." +msgstr "Le pseudo %s a été confirmé." + +#: modules/commands/os_oper.cpp:95 +#, c-format +msgid "Nick %s is already an operator." +msgstr "Le pseudo %s est déjà un opérateur." + +#: modules/commands/ns_register.cpp:36 +#, c-format +msgid "Nick %s is already confirmed." +msgstr "Le pseudo %s a déjà été confirmé." + +#: modules/commands/os_svs.cpp:46 +#, c-format +msgid "Nick %s is an illegal nickname and cannot be used." +msgstr "Le pseudo %s est un pseudo illégal et ne peut pas être utilisé." + +#: modules/commands/bs_bot.cpp:81 modules/commands/bs_bot.cpp:181 +#: modules/commands/os_svs.cpp:54 +#, c-format +msgid "Nick %s is currently in use." +msgstr "Le pseudo %s est déjà utilisé." + +#: modules/commands/os_forbid.cpp:512 +#, c-format +msgid "Nick %s is forbidden by %s: %s" +msgstr "Le pseudo %s est interdit par %s : %s" + +#: modules/commands/os_forbid.cpp:514 +#, c-format +msgid "Nick %s is forbidden." +msgstr "Le pseudo %s est interdit." + +#: modules/commands/os_oper.cpp:134 +#, c-format +msgid "Nick %s is not a Services Operator." +msgstr "%s n'est pas un Opérateur des Services." + +#: modules/commands/ns_info.cpp:34 +#, c-format +msgid "Nick %s is part of this Network's Services." +msgstr "Le pseudo %s fait partie des Services du réseau." + +#: include/language.h:79 +#, c-format +msgid "Nick %s isn't currently in use." +msgstr "Le pseudo %s n'est pas utilisé actuellement." + +#: include/language.h:78 +#, c-format +msgid "Nick %s isn't registered." +msgstr "Le pseudo %s n'est pas enregistré." + +#: modules/commands/os_svs.cpp:39 +#, c-format +msgid "Nick %s was truncated to %d characters." +msgstr "Le pseudo %s a été tronqué à %d caractères." + +#: modules/commands/ns_set.cpp:1135 +#, c-format +msgid "Nick %s will expire." +msgstr "Le pseudo %s expirera." + +#: modules/commands/ns_set.cpp:1129 +#, c-format +msgid "Nick %s will not expire." +msgstr "Le pseudo %s n'expirera pas." + +#: modules/commands/ms_check.cpp:60 +#, c-format +msgid "Nick %s doesn't have a memo from you." +msgstr "Le pseudo %s n'a aucun mémo de votre part." + +#: modules/commands/ns_logout.cpp:48 +#, c-format +msgid "Nick %s has been logged out." +msgstr "Le pseudo %s a été déconnecté." + +#: modules/commands/ns_group.cpp:272 +#, c-format +msgid "Nick %s has been ungrouped from %s." +msgstr "Le pseudo %s a été retiré du groupe %s." + +#: include/language.h:81 +#, c-format +msgid "Nick %s is currently suspended." +msgstr "Le pseudo %s est actuellement suspendu." + +#: modules/commands/ns_group.cpp:250 +#, c-format +msgid "Nick %s is not in your group." +msgstr "Le pseudo %s n'est pas dans votre groupe." + +#: modules/commands/ns_suspend.cpp:180 +#, c-format +msgid "Nick %s is not suspended." +msgstr "Le pseudo %s n'est pas suspendu." + +#: modules/commands/ns_suspend.cpp:190 +#, c-format +msgid "Nick %s is now released." +msgstr "Le pseudo %s a été libéré." + +#: modules/commands/ns_suspend.cpp:138 +#, c-format +msgid "Nick %s is now suspended." +msgstr "Le pseudo %s a été suspendu." + +#: modules/commands/cs_seen.cpp:275 +#, c-format +msgid "Nick too long, max length is %u characters." +msgstr "Pseudo trop long, la taille maximale est de %u caractères." + +#: modules/commands/ns_drop.cpp:53 +#, c-format +msgid "Nickname %s has been dropped." +msgstr "Le pseudo %s a été effacé." + +#: include/language.h:97 +#, c-format +msgid "Nickname %s is already registered!" +msgstr "Le pseudo %s est déjà enregistré !" + +#: include/language.h:96 +#, c-format +msgid "Nickname %s may not be registered." +msgstr "Le pseudo %s ne peut pas être enregistré." + +#: modules/commands/ns_register.cpp:226 +#, c-format +msgid "Nickname %s registered under your user@host-mask: %s" +msgstr "Le pseudo %s est maintenant enregistré sous votre masque : %s" + +#: modules/commands/ns_register.cpp:228 +#, c-format +msgid "Nickname %s registered." +msgstr "Le pseudo %s est maintenant enregistré." + +#: modules/commands/cs_set.cpp:1307 +msgid "No auto-op" +msgstr "Pas d'auto-op" + +#: modules/commands/bs_assign.cpp:252 +msgid "No bot" +msgstr "Pas de bot" + +#: modules/commands/cs_set.cpp:1303 modules/commands/ns_set.cpp:1317 +msgid "No expire" +msgstr "N'expire pas" + +#: modules/commands/help.cpp:184 +#, c-format +msgid "No help available for %s." +msgstr "Aucune aide disponible sur %s." + +#: modules/commands/os_modinfo.cpp:61 +#, c-format +msgid "No information about module %s is available." +msgstr "Aucune information sur le module %s n'est disponible." + +#: modules/commands/cs_enforce.cpp:177 +#, c-format +msgid "No limit is set on %s." +msgstr "Pas de limite définie pour %s." + +#: modules/commands/os_news.cpp:37 +msgid "No logon news items to delete!" +msgstr "Aucune news de connexion à supprimer !" + +#: modules/commands/os_logsearch.cpp:133 +#, c-format +msgid "No matches for %s found." +msgstr "Aucune correspondance pour %s trouvée." + +#: modules/commands/cs_xop.cpp:294 +#, c-format +msgid "No matching entries on %s %s list." +msgstr "Aucune entrée correspondante sur la liste des %2$s de %1$s." + +#: modules/commands/cs_access.cpp:269 modules/commands/cs_access.cpp:433 +#: modules/commands/cs_flags.cpp:335 modules/commands/cs_xop.cpp:428 +#, c-format +msgid "No matching entries on %s access list." +msgstr "Aucune entrée correspondante sur la liste d'accès de %s." + +#: modules/commands/cs_akick.cpp:224 modules/commands/cs_akick.cpp:368 +#, c-format +msgid "No matching entries on %s autokick list." +msgstr "Aucune entrée correspondante sur la liste de kicks automatiques de %s." + +#: modules/commands/bs_badwords.cpp:166 modules/commands/bs_badwords.cpp:246 +#, c-format +msgid "No matching entries on %s bad words list." +msgstr "" +"Aucune entrée correspondante sur la liste des mots interdits \n" +"de %s." + +#: modules/commands/os_session.cpp:145 modules/commands/os_session.cpp:490 +msgid "No matching entries on session-limit exception list." +msgstr "" +"Aucune entrée correspondante sur la liste des exceptions à la limite de " +"sessions." + +#: modules/commands/os_sxline.cpp:28 modules/commands/os_sxline.cpp:177 +#, c-format +msgid "No matching entries on the %s list." +msgstr "Aucune entrée correspondante sur la liste de %s." + +#: modules/commands/os_akill.cpp:29 modules/commands/os_akill.cpp:320 +msgid "No matching entries on the AKILL list." +msgstr "Aucune entrée correspondante sur la liste d'AKILL." + +#: modules/commands/ms_cancel.cpp:77 +msgid "No memo was cancelable." +msgstr "Aucun mémo n'était annulable." + +#: modules/commands/ms_read.cpp:65 +msgid "No memos to display." +msgstr "Aucun mémo à afficher." + +#: modules/commands/os_modinfo.cpp:187 +msgid "No modules currently loaded matching that criteria." +msgstr "Aucun module actuellement chargé ne correspond à ce critère." + +#: modules/commands/ns_recover.cpp:55 +msgid "No one is using your nick, and services are not holding it." +msgstr "Personne n'utilise votre pseudo et les services ne l'ont pas suspendu." + +#: modules/commands/os_login.cpp:30 modules/commands/os_login.cpp:77 +msgid "No oper block for your nick." +msgstr "Pas de bloc oper pour votre pseudo." + +#: modules/commands/os_news.cpp:47 +msgid "No oper news items to delete!" +msgstr "Aucune news d'oper à supprimer !" + +#: modules/commands/os_news.cpp:57 +msgid "No random news items to delete!" +msgstr "Aucune news aléatoire à supprimer !" + +#: modules/commands/hs_list.cpp:111 +msgid "No records to display." +msgstr "Pas d'enregistrement à afficher." + +#: modules/commands/ns_getemail.cpp:47 +#, c-format +msgid "No registrations matching %s were found." +msgstr "Pas d'enregistrement correspondant à %s." + +#: modules/commands/hs_request.cpp:220 modules/commands/hs_request.cpp:276 +#, c-format +msgid "No request for nick %s found." +msgstr "Pas de requête trouvée pour le pseudo %s." + +#: src/access.cpp:55 +msgid "No signed kick when SIGNKICK LEVEL is used" +msgstr "Pas de kick signés lorsque SIGNKICK LEVEL est utilisé." + +#: modules/extra/stats/cs_fantasy_top.cpp:159 +#: modules/extra/stats/cs_fantasy_stats.cpp:156 +#, c-format +msgid "No stats for %s." +msgstr "Aucune statistique pour %s." + +#: modules/commands/os_info.cpp:201 +#, c-format +msgid "No such info \"%s\" on %s." +msgstr "Aucune informations \"%s\" sur %s." + +#: modules/commands/cs_ban.cpp:219 modules/commands/cs_kick.cpp:118 +#, c-format +msgid "No users on %s match %s." +msgstr "Aucun utilisateur sur %s ne correspond à %s." + +#: modules/commands/bs_assign.cpp:188 +#, c-format +msgid "No-bot mode is now off on channel %s." +msgstr "Le mode sans bot est maintenant désactivé sur le canal %s." + +#: modules/commands/bs_assign.cpp:181 +#, c-format +msgid "No-bot mode is now on on channel %s." +msgstr "Le mode sans bot est maintenant activé sur le canal %s." + +#: modules/commands/os_mode.cpp:64 +#, c-format +msgid "Non-status modes cleared on %s." +msgstr "Les modes, sauf ceux de statut, ont été vidés sur %s." + +#: modules/commands/os_dns.cpp:226 modules/commands/bs_info.cpp:58 +msgid "None" +msgstr "Aucune" + +#: modules/commands/cs_set.cpp:1029 +#, fuzzy, c-format +msgid "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." +msgstr "" +"Cependant, si le successeur a déjà trop de canaux\n" +"enregistrés (%d), le canal sera effacé à la place,\n" +"comme si aucun successeur n'avait été défini." + +#: modules/commands/cs_mode.cpp:380 modules/commands/cs_mode.cpp:437 +msgid "Nothing to do." +msgstr "Rien à faire." + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:201 modules/commands/ms_list.cpp:64 +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_log.cpp:127 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +#: modules/commands/ns_ajoin.cpp:100 +msgid "Number" +msgstr "Numéro" + +#: modules/commands/os_news.cpp:41 +msgid "OPERNEWS {ADD|DEL|LIST} [text|num]" +msgstr "OPERNEWS {ADD|DEL|LIST} [texte|numéro]" + +#: modules/commands/ns_info.cpp:68 modules/commands/ns_info.cpp:72 +msgid "Online from" +msgstr "Connecté depuis" + +#: modules/commands/os_oper.cpp:138 +#, c-format +msgid "" +"Oper %s is configured in the configuration file(s) and can not be removed by " +"this command." +msgstr "" +"L'oper %s est configuré dans le(s) fichier(s) de configuration et ne peut " +"pas être supprimé avec cette commande." + +#: modules/commands/os_info.cpp:268 +msgid "Oper Info" +msgstr "Info oper" + +#: modules/commands/os_info.cpp:182 modules/commands/os_info.cpp:221 +#, c-format +msgid "Oper info list for %s is empty." +msgstr "La liste d'informations oper de %s est vide." + +#: modules/commands/os_news.cpp:46 +#, c-format +msgid "Oper news item #%d deleted." +msgstr "News d'oper n°%d supprimée." + +#: modules/commands/os_news.cpp:45 +#, c-format +msgid "Oper news item #%s not found!" +msgstr "News d'oper n°%s non trouvée !" + +#: modules/commands/os_news.cpp:42 +msgid "Oper news items:" +msgstr "News d'oper :" + +#: modules/commands/os_oper.cpp:148 +#, c-format +msgid "Oper privileges removed from %s (%s)." +msgstr "Privilèges d'oper retirés de %s (%s)." + +#: modules/commands/os_oper.cpp:101 modules/commands/os_oper.cpp:189 +#, c-format +msgid "Oper type %s has not been configured." +msgstr "Le type d'opérateur %s n'a pas été configuré." + +#: modules/commands/os_oline.cpp:37 +#, c-format +msgid "Operflags %s have been added for %s." +msgstr "Les operflags %s ont été ajoutés à %s." + +#: modules/commands/os_oline.cpp:43 +#, c-format +msgid "Operflags %s have been removed from %s." +msgstr "Les operflags %s ont été retirés de %s." + +#: modules/commands/os_oper.cpp:193 +#, c-format +msgid "Opertype %s has no allowed commands." +msgstr "Le type d'opérateur %s n'a aucune commande autorisée." + +#: modules/commands/os_oper.cpp:215 +#, c-format +msgid "Opertype %s has no allowed privileges." +msgstr "Le type d'opérateur %s n'a aucun privilège autorisé." + +#: modules/commands/os_oper.cpp:237 +#, c-format +msgid "Opertype %s receives modes %s once identified." +msgstr "Le type d'opérateur %s reçoit les modes %s une fois identifié." + +#: modules/commands/bs_kick.cpp:1219 +msgid "Ops protection" +msgstr "Protection des OPs" + +#: src/misc.cpp:258 modules/commands/bs_info.cpp:58 +msgid "Options" +msgstr "Options" + +#: modules/commands/os_dns.cpp:668 +msgid "POOL server.name" +msgstr "POOL nom.du.serveur" + +#: modules/commands/cs_mode.cpp:449 +msgid "Param" +msgstr "Paramètre" + +#: modules/commands/ns_identify.cpp:38 +msgid "Password accepted - you are now recognized." +msgstr "Mot de passe accepté - vous êtes maintenant identifié." + +#: modules/commands/os_login.cpp:44 +msgid "Password accepted." +msgstr "Mot de passe accepté." + +#: include/language.h:85 +msgid "Password authentication required for that command." +msgstr "Authentification par mot de passe requise pour cette commande." + +#: modules/commands/ns_set.cpp:152 modules/commands/ns_set.cpp:218 +#, c-format +msgid "Password for %s changed to %s." +msgstr "Le mot de passe de %s a été changé en %s." + +#: modules/commands/ns_set.cpp:154 modules/commands/ns_set.cpp:220 +#, c-format +msgid "Password for %s changed." +msgstr "Le mot de passe de %s a été changé." + +#: modules/commands/ns_getpass.cpp:38 +#, c-format +msgid "Password for %s is %s." +msgstr "Le mot de passe de %s est %s." + +#: include/language.h:71 +msgid "Password incorrect." +msgstr "Mot de passe incorrect." + +#: modules/commands/ns_resetpass.cpp:39 +#, c-format +msgid "Password reset email for %s has been sent." +msgstr "Un email de réinitialisation de mot de passe pour %s a été envoyé." + +#: modules/commands/cs_set.cpp:1289 +msgid "Peace" +msgstr "Paix" + +#: modules/commands/cs_set.cpp:440 +#, c-format +msgid "Peace option for %s is now off." +msgstr "Le mode 'paix' est désormais INACTIF pour %s." + +#: modules/commands/cs_set.cpp:434 +#, c-format +msgid "Peace option for %s is now on." +msgstr "Le mode 'paix' est désormais ACTIF pour %s." + +#: modules/commands/cs_set.cpp:1301 +msgid "Persistent" +msgstr "Persistant" + +#: include/language.h:126 +msgid "Please contact an Operator to get a vHost assigned to this nick." +msgstr "" +"Merci de contacter un Opérateur pour obtenir un vHost assigné pour ce pseudo." + +#: include/language.h:73 +msgid "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." +msgstr "" +"Merci de réessayer avec un mot de passe plus difficile à deviner. Les mots " +"de passe\n" +"devraient comporter au moins cinq caractères, ne pas être facilement " +"devinables\n" +"(comme votre nom ou votre pseudo) et ne peuvent pas contenir d'espace ou de\n" +"tabulation." + +#: modules/commands/os_jupe.cpp:30 +msgid "Please use a valid server name when juping." +msgstr "Veuillez indiquer un nom de serveur valide pour JUPE." + +#: include/language.h:104 +msgid "Please use the symbol of # when attempting to register." +msgstr "" +"Merci d'utiliser le symbole # lorsque vous tentez d'enregistrer un canal." + +#: src/mail.cpp:78 +#, c-format +msgid "Please wait %d seconds and retry." +msgstr "Attendez %d secondes et réessayez." + +#: modules/commands/hs_request.cpp:158 +#, c-format +msgid "Please wait %d seconds before requesting a new vHost." +msgstr "Veuillez patienter %d secondes avant de redemander un nouveau vHost." + +#: modules/commands/ms_rsend.cpp:58 modules/commands/ms_send.cpp:57 +#, c-format +msgid "Please wait %d seconds before using the %s command again." +msgstr "" +"Veuillez patienter %d secondes avant d'utiliser la commande %s à nouveau." + +#: modules/commands/ns_group.cpp:149 +#, c-format +msgid "Please wait %d seconds before using the GROUP command again." +msgstr "" +"Veuillez patienter %d secondes avant d'utiliser la commande GROUP à nouveau." + +#: modules/commands/ns_register.cpp:198 +#, c-format +msgid "Please wait %d seconds before using the REGISTER command again." +msgstr "" +"Veuillez patienter %d secondes avant d'utiliser la commande REGISTER à " +"nouveau." + +#: modules/commands/os_dns.cpp:628 +#, c-format +msgid "Pooled %s." +msgstr "%s a été ajouté à la pool." + +#: modules/commands/os_dns.cpp:237 +msgid "Pooled/Active" +msgstr "Dans la pool/Actif" + +#: modules/commands/os_dns.cpp:239 +msgid "Pooled/Not Active" +msgstr "Dans la pool/Inactif" + +#: modules/commands/bs_set.cpp:161 +msgid "Prevent a bot from being assigned by non IRC operators" +msgstr "Empêche un bot d'être assigné par un utilisateur non opérateur IRC." + +#: modules/commands/bs_assign.cpp:153 +msgid "Prevent a bot from being assigned to a channel" +msgstr "Empêche un bot d'être assigné à un canal" + +#: modules/commands/cs_suspend.cpp:58 +msgid "Prevent a channel from being used preserving channel data and settings" +msgstr "" +"Suspend un canal pour ne pas qu'il soit utilisé tout en conservant les " +"données et configurations." + +#: modules/commands/cs_set.cpp:1043 +msgid "Prevent the channel from expiring" +msgstr "Empêche le canal d'expirer" + +#: modules/commands/ns_list.cpp:186 +msgid "Prevent the nickname from appearing in the LIST command" +msgstr "Empêche le pseudo d'apparaître dans la commande LIST" + +#: modules/commands/ns_set.cpp:1104 +msgid "Prevent the nickname from expiring" +msgstr "Empêche le pseudo d'expirer" + +#: src/access.cpp:46 +msgid "Prevents users being kicked by Services" +msgstr "Empêche des utilisateurs d'être kickés par les services" + +#: modules/commands/ns_list.cpp:297 modules/commands/cs_list.cpp:262 +#: modules/commands/bs_info.cpp:58 +msgid "Private" +msgstr "Privé" + +#: modules/commands/bs_set.cpp:190 +#, c-format +msgid "Private mode of bot %s is now off." +msgstr "Le mode privé du bot %s est maintenant désactivé." + +#: modules/commands/bs_set.cpp:185 +#, c-format +msgid "Private mode of bot %s is now on." +msgstr "Le mode privé du bot %s est maintenant activé." + +#: modules/commands/cs_list.cpp:220 +#, c-format +msgid "Private option for %s is now off." +msgstr "L'option privé pour %s est maintenant INACTIVE." + +#: modules/commands/cs_list.cpp:214 +#, c-format +msgid "Private option for %s is now on." +msgstr "L'option privé pour %s est maintenant ACTIVE." + +#: modules/commands/ns_list.cpp:221 +#, c-format +msgid "Private option is now off for %s." +msgstr "L'option privé est maintenant INACTIVE pour %s." + +#: modules/commands/ns_list.cpp:215 +#, c-format +msgid "Private option is now on for %s." +msgstr "L'option privé est maintenant ACTIVE pour %s." + +#: modules/commands/cs_flags.cpp:281 +#, c-format +msgid "Privilege %s added to %s on %s, new flags are +%s" +msgstr "Privilège %s ajouté à %s sur %s, les nouveaux flags sont +%s" + +#: modules/commands/cs_flags.cpp:283 +#, c-format +msgid "Privilege %s removed from %s on %s, new flags are +%s" +msgstr "Privilège %s supprimé de %s sur %s, les nouveaux flags sont +%s" + +#: modules/commands/ns_set.cpp:1309 +msgid "Protection" +msgstr "Protection" + +#: modules/commands/ns_set.cpp:721 +#, c-format +msgid "Protection is now off for %s." +msgstr "La protection est maintenant INACTIVE pour %s." + +#: modules/commands/ns_set.cpp:700 +#, c-format +msgid "Protection is now on for %s, with a reduced delay." +msgstr "La protection est maintenant ACTIVE pour %s, avec un délai réduit." + +#: modules/commands/ns_set.cpp:710 +#, c-format +msgid "Protection is now on for %s, with no delay." +msgstr "La protection est maintenant ACTIVE pour %s, sans aucun délai." + +#: modules/commands/ns_set.cpp:692 +#, c-format +msgid "Protection is now on for %s." +msgstr "La protection est maintenant ACTIVE pour %s." + +#: modules/commands/os_chankill.cpp:100 +msgid "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." +msgstr "" +"Inflige un AKILL à toutes les personnes qui sont sur le canal spécifié.\n" +"Ceci utilise le masque ident@host réel de tous les pseudos et\n" +"applique le AKILL. " + +#: modules/commands/ns_set.cpp:1307 +msgid "Quick protection" +msgstr "Protection rapide" + +#: modules/commands/os_news.cpp:51 +msgid "RANDOMNEWS {ADD|DEL|LIST} [text|num]" +msgstr "RANDOMNEWS {ADD|DEL|LIST} [texte|numéro]" + +#: modules/commands/cs_enforce.cpp:99 +msgid "REGONLY enforced by " +msgstr "REGONLY appliqué par" + +#: modules/commands/cs_enforce.cpp:68 +msgid "RESTRICTED enforced by " +msgstr "RESTRICTED appliqué par" + +#: modules/commands/os_noop.cpp:21 +msgid "REVOKE server" +msgstr "REVOKE serveur" + +#: modules/commands/os_news.cpp:56 +#, c-format +msgid "Random news item #%d deleted." +msgstr "News aléatoire n°%d supprimée." + +#: modules/commands/os_news.cpp:55 +#, c-format +msgid "Random news item #%s not found!" +msgstr "News aléatoire n°%s non trouvée !" + +#: modules/commands/os_news.cpp:52 +msgid "Random news items:" +msgstr "News aléatoires :" + +#: modules/commands/ms_read.cpp:112 +msgid "Read a memo or memos" +msgstr "Lit un ou plusieurs mémos" + +#: modules/commands/bs_info.cpp:56 +msgid "Real name" +msgstr "Vrai nom" + +#: modules/commands/os_list.cpp:153 +msgid "Realname" +msgstr "Vrai nom" + +#: modules/commands/os_ignore.cpp:266 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:204 modules/commands/os_forbid.cpp:358 +#: modules/commands/cs_akick.cpp:392 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:361 +msgid "Reason" +msgstr "Raison" + +#: src/xline.cpp:386 +#, c-format +msgid "Reason for %s updated." +msgstr "Raison mise à jour pour %s." + +#: modules/commands/ns_recover.cpp:214 +msgid "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." +msgstr "" +"Récupère votre pseudo pris par un autre utilisateur ou par\n" +"les services. Si les services détiennent votre pseudo, la\n" +"détention sera annulée. Si un autre utilisateur détient votre\n" +"pseudo et est identifié, il sera déconnecté du serveur (comme\n" +"avec l'ancienne commande GHOST). S'il n'est pas identifié, son\n" +"pseudo sera changé de force." + +#: modules/commands/cs_access.cpp:741 +msgid "Redefine the meanings of access levels" +msgstr "Redéfinit la signification des niveaux d'accès" + +#: modules/commands/ns_recover.cpp:149 +msgid "Regains control of your nick" +msgstr "Reprendre le contrôle de votre pseudo" + +#: modules/commands/os_sxline.cpp:330 modules/commands/os_sxline.cpp:545 +#: modules/commands/os_akill.cpp:129 +msgid "Regex is disabled." +msgstr "Les expressions régulières (regex) sont désactivées." + +#: modules/commands/os_sxline.cpp:459 modules/commands/os_sxline.cpp:694 +#: modules/commands/os_akill.cpp:444 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." +msgstr "" +"L'utilisation d'expressions régulières (regex) est aussi supportée, en " +"utilisant\n" +"le moteur de regex %s. Mettez le masque entre // pour l'utiliser." + +#: modules/commands/os_ignore.cpp:386 modules/commands/os_forbid.cpp:428 +#: modules/commands/ns_list.cpp:172 modules/commands/cs_list.cpp:167 +#: modules/commands/os_list.cpp:119 modules/commands/os_list.cpp:255 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." +msgstr "" +"L'utilisation d'expressions régulières (regex) est aussi supportée, en " +"utilisant\n" +"le moteur de regex %s. Mettez le masque entre // pour l'utiliser." + +#: modules/commands/cs_register.cpp:19 +msgid "Register a channel" +msgstr "Enregistre un canal" + +#: modules/commands/ns_register.cpp:120 +msgid "Register a nickname" +msgstr "Enregistre un pseudo" + +#: modules/commands/ns_info.cpp:89 modules/commands/cs_info.cpp:55 +msgid "Registered" +msgstr "Enregistré" + +#: modules/commands/os_stats.cpp:184 +#, c-format +msgid "Registered channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "Canaux enregistrés : %lu entrées, %lu paniers, plus longue chaîne : %d" + +#: modules/commands/os_stats.cpp:190 +#, c-format +msgid "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" +msgstr "" +"Groupe de pseudos enregistrés : %lu entrées, %lu paniers, plus longue " +"chaîne : %d" + +#: modules/commands/os_stats.cpp:187 +#, c-format +msgid "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" +msgstr "" +"Pseudos enregistrés : %lu entrées, %lu paniers, plus longue chaîne : %d" + +#: modules/commands/cs_enforce.cpp:105 +#, c-format +msgid "Registered only enforced on %s." +msgstr "Application sur %s de la restriction aux seuls pseudos enregistrés" + +#: modules/commands/cs_register.cpp:86 +#, c-format +msgid "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." +msgstr "" +"Enregistre un canal dans la base de données de %s. Pour utiliser\n" +"cette commande, vous devez d'abord être opérateur du canal\n" +"que vous souhaitez enregistrer. La description, qui est facultative,\n" +"est une description générale de l'utilité du canal.\n" +" \n" +"Lorsque vous enregistrez un canal, vous êtes défini en tant que \"fondateur" +"\"\n" +"du canal. Le fondateur est autorisé à changer tous les paramètres du canal.\n" +"%s lui donnera automatiquement les privilèges de propriétaire\n" +"du canal lorsqu'il joindra le canal." + +#: modules/commands/ns_register.cpp:269 +#, c-format +msgid "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." +msgstr "" +"Enregistre votre pseudo dans la base de données de %s.\n" +"Une fois que votre pseudo est enregistré, vous pouvez utiliser les\n" +"commandes SET et ACCESS pour configurer votre pseudo\n" +"comme vous le souhaitez. Rappelez-vous bien du mot de passe utilisé\n" +"pendant l'enregistrement car vous en aurez besoin pour effectuer\n" +"des changements sur votre pseudo plus tard.\n" +"(Notez que les majuscules comptent ! ANOPE, Anope\n" +"et anope sont trois mots de passe différents !)\n" +" \n" +"Conseils pour choisir un mot de passe :\n" +" \n" +"Les mots de passe ne doivent pas être trop facilement\n" +"devinables. Par exemple, c'est une mauvaise idée d'utiliser\n" +"votre vrai nom comme mot de passe. Utiliser votre pseudo\n" +"comme mot de passe est encore pire ;-) et d'ailleurs, %s\n" +"ne vous laissera pas faire.. De même, les mots de passe\n" +"courts sont vulnérables aux recherches méthodiques,\n" +"donc vous devez choisir un mot de passe d'au moins \n" +"5 caractères. Le caractère espace ne peut pas être \n" +"utilisé dans les mots de passe." + +#: modules/commands/ns_register.cpp:145 +msgid "Registration is currently disabled." +msgstr "L'enregistrement des pseudos est temporairement désactivé." + +#: modules/commands/cs_set.cpp:400 +msgid "Regulate the use of critical commands" +msgstr "Régule l'utilisation de commandes sensibles" + +#: modules/commands/hs_request.cpp:283 +msgid "Reject the requested vHost for the given nick." +msgstr "Refuse la demande de vHost par le pseudo indiqué." + +#: modules/commands/hs_request.cpp:240 +msgid "Reject the requested vHost of a user" +msgstr "Refuse la demande de vhost d'un pseudo" + +#: modules/commands/cs_suspend.cpp:151 +msgid "Releases a suspended channel" +msgstr "Libère un canal suspendu" + +#: modules/commands/cs_suspend.cpp:191 +msgid "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." +msgstr "" +"Libère un canal qui a été suspendu. Toutes les données\n" +"et configurations seront restaurées tel qu'elles étaient\n" +"avant la suspension." + +#: modules/commands/os_module.cpp:56 +msgid "Reload a module" +msgstr "Recharge un module" + +#: modules/commands/os_reload.cpp:19 +msgid "Reload services' configuration file" +msgstr "Recharge le fichier de configuration des Services" + +#: modules/commands/ns_group.cpp:236 +msgid "Remove a nick from a group" +msgstr "Enlève un pseudo d'un groupe" + +#: modules/commands/cs_unban.cpp:19 +msgid "Remove all bans preventing a user from entering a channel" +msgstr "" +"Supprime tous les bans qui empêche un utilisateur d'entrer sur un canal" + +#: modules/commands/os_noop.cpp:19 +msgid "Remove all operators from a server remotely" +msgstr "Supprime tous les Opérateurs d'un serveur" + +#: modules/commands/os_dns.cpp:543 +#, c-format +msgid "Removed IP %s from %s." +msgstr "Adresse IP %s supprimée de %s." + +#: modules/commands/os_dns.cpp:460 +#, c-format +msgid "Removed server %s from zone %s." +msgstr "Serveur %s supprimé de la zone %s." + +#: modules/commands/os_dns.cpp:483 +#, c-format +msgid "Removed server %s." +msgstr "Serveur %s supprimé." + +#: modules/commands/cs_mode.cpp:909 +#, c-format +msgid "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." +msgstr "" +"Retire le statut %s du pseudo désigné sur un canal. Si pseudo n'est\n" +"pas donné, votre statut %s vous sera retiré." + +#: modules/commands/cs_mode.cpp:890 +#, c-format +msgid "Removes %s status from you or the specified nick on a channel" +msgstr "Retire le statut %s au pseudo spécifié ou à vous-même sur un canal" + +#: modules/commands/cs_updown.cpp:146 +msgid "Removes a selected nicks status from a channel" +msgstr "Retire les modes de statut d'un pseudo spécifié sur un canal" + +#: modules/commands/cs_updown.cpp:223 +msgid "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." +msgstr "" +"Retire les modes de statut au pseudo spécifié sur un canal. Si pseudo est\n" +"omis, alors votre propre statut est retiré. Si canal est omis, alors votre\n" +"statut de canal est supprimé sur tous les canaux sur lesquels vous êtes." + +#: src/xline.cpp:412 +#, c-format +msgid "Removing %s because %s covers it." +msgstr "Supprime %s parce que %s le couvre." + +#: modules/commands/bs_kick.cpp:1171 modules/commands/bs_kick.cpp:1173 +#: modules/commands/bs_kick.cpp:1176 +msgid "Repeat kicker" +msgstr "Kicker de répétition" + +#: modules/commands/hs_request.cpp:78 +msgid "Request a vHost for your nick" +msgstr "Fait une requête de vHost pour votre pseudo" + +#: modules/commands/hs_request.cpp:179 +msgid "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." +msgstr "" +"Demande que le vhost indiqué soit activé pour votre pseudo par les\n" +"administrateurs du réseau. Merci d'être patient pendant que votre\n" +"requête est examinée." + +#: modules/commands/ns_register.cpp:312 +msgid "Resend registration confirmation email" +msgstr "Renvoyer l'email de confirmation d'enregistrement" + +#: modules/commands/cs_set.cpp:621 +msgid "Restrict access to the channel" +msgstr "Restreindre l'accès au canal" + +#: modules/commands/cs_set.cpp:1291 +msgid "Restricted access" +msgstr "Accès restreint" + +#: modules/commands/cs_set.cpp:661 +#, c-format +msgid "Restricted access option for %s is now off." +msgstr "L'option d'accès restreint pour %s est maintenant INACTIVE." + +#: modules/commands/cs_set.cpp:655 +#, c-format +msgid "Restricted access option for %s is now on." +msgstr "L'option d'accès restreint pour %s est maintenant ACTIVE." + +#: modules/commands/cs_enforce.cpp:73 +#, c-format +msgid "Restricted enforced on %s." +msgstr "Restrictions d'accès appliquées sur %s" + +#: modules/commands/cs_set.cpp:335 +msgid "Retain modes when channel is not in use" +msgstr "Maintient les modes quand le canal n'est pas utilisé" + +#: modules/commands/cs_topic.cpp:20 +msgid "Retain topic when channel is not in use" +msgstr "Maintient le topic quand le canal n'est pas utilisé" + +#: modules/commands/ns_getpass.cpp:19 +msgid "Retrieve the password for a nickname" +msgstr "Récupère le mot de passe d'un pseudo" + +#: modules/commands/hs_request.cpp:296 +msgid "Retrieves the vhost requests" +msgstr "Récupère les requêtes de vhosts" + +#: modules/commands/cs_getkey.cpp:19 +msgid "Returns the key of the given channel" +msgstr "Retourne la clé du canal spécifié" + +#: modules/commands/cs_getkey.cpp:57 +msgid "Returns the key of the given channel." +msgstr "Retourne la clé du canal spécifié" + +#: modules/commands/ns_getemail.cpp:58 +msgid "Returns the matching accounts that used given email." +msgstr "Retourne les comptes utilisant l'adresse email indiquée." + +#: modules/commands/ns_status.cpp:19 +msgid "Returns the owner status of the given nickname" +msgstr "Renvoie le niveau d'identification du pseudo donné" + +#: modules/commands/ns_getpass.cpp:50 +msgid "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." +msgstr "" +"Retourne le mot de passe du pseudo donné.\n" +"Note : Lorsque cette commande est utilisée, un message indiquant\n" +"la personne qui a utilisé la commande et le pseudo recherché\n" +"est ajouté dans les logs et envoyé en WALLOPS/GLOBOPS." + +#: modules/commands/ns_status.cpp:55 +msgid "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." +msgstr "" +"Retourne si l'utilisateur utilisant le pseudo donné est reconnu\n" +"en tant que propriétaire du pseudo. La réponse est de ce format :\n" +" \n" +" pseudo code-statut compte\n" +" \n" +"Où pseudo est le pseudo concerné,\n" +"code-statut est l'un des codes suivants, et compte\n" +"le compte avec lequel il est connecté.\n" +" \n" +" 0 - aucun utilisateur connecté avec ce pseudo ou\n" +" le pseudo n'est pas enregistré\n" +" 1 - utilisateur non reconnu comme propriétaire\n" +" 2 - utilisateur reconnu comme propriétaire uniquement via\n" +" la liste d'accès\n" +" 3 - utilisateur reconnu comme propriétaire via l'identification\n" +" \n" +"Si aucun pseudo n'est donné, votre propre statut sera retourné." + +#: modules/commands/bs_kick.cpp:1181 modules/commands/bs_kick.cpp:1183 +#: modules/commands/bs_kick.cpp:1186 +msgid "Reverses kicker" +msgstr "Kicker de reverses" + +#: modules/commands/ns_logout.cpp:21 +msgid "Reverses the effect of the IDENTIFY command" +msgstr "Inverse les effets de la commande IDENTIFY" + +#: modules/commands/os_noop.cpp:20 +msgid "SET server" +msgstr "SET serveur" + +#: modules/commands/os_dns.cpp:667 +msgid "SET server.name option value" +msgstr "SET nom.du.serveur option valeur" + +#: modules/commands/ns_cert.cpp:378 +#, c-format +msgid "SSL certificate fingerprint accepted, you are now identified to %s." +msgstr "" +"Empreinte de certificat SSL acceptée, vous êtes maintenant identifié(e) en " +"tant que %s." + +#: modules/commands/ns_cert.cpp:398 +msgid "SSL certificate fingerprint accepted, you are now identified." +msgstr "" +"Empreinte de certificat SSL acceptée, vous êtes maintenant identifié(e)." + +#: modules/commands/cs_enforce.cpp:137 +#, c-format +msgid "SSL only enforced on %s." +msgstr "" +"Application sur %s de la restriction aux seuls utilisateurs connectés en SSL." + +#: modules/commands/cs_enforce.cpp:131 +msgid "SSLONLY enforced by " +msgstr "SSLONLY appliqué par" + +#: modules/commands/os_shutdown.cpp:47 +msgid "Save databases and restart Services" +msgstr "Sauvegarde les bases de données et relance les services." + +#: modules/commands/os_logsearch.cpp:32 +msgid "Searches logs for a matching pattern" +msgstr "Recherche les correspondances au modèle dans le fichier de logs." + +#: modules/commands/cs_set.cpp:1295 +msgid "Secure founder" +msgstr "Sécurité du fondateur" + +#: modules/commands/cs_set.cpp:786 +#, c-format +msgid "Secure founder option for %s is now off." +msgstr "L'option de sécurité du fondateur sur %s est INACTIVE." + +#: modules/commands/cs_set.cpp:780 +#, c-format +msgid "Secure founder option for %s is now on." +msgstr "L'option de sécurité du fondateur sur %s est ACTIVE." + +#: modules/commands/cs_set.cpp:1297 +msgid "Secure ops" +msgstr "Sécurité des OPs" + +#: modules/commands/cs_set.cpp:850 +#, c-format +msgid "Secure ops option for %s is now off." +msgstr "La sécurité des OPs sur %s est maintenant INACTIVE." + +#: modules/commands/cs_set.cpp:844 +#, c-format +msgid "Secure ops option for %s is now on." +msgstr "La sécurité des OPs sur %s est maintenant ACTIVE." + +#: modules/commands/cs_set.cpp:723 +#, c-format +msgid "Secure option for %s is now off." +msgstr "L'option de sécurité sur %s est INACTIVE." + +#: modules/commands/cs_set.cpp:717 +#, c-format +msgid "Secure option for %s is now on." +msgstr "L'option de sécurité sur %s est ACTIVE." + +#: modules/commands/ns_set.cpp:1044 +#, c-format +msgid "Secure option is now off for %s." +msgstr "L'option de sécurité est maintenant INACTIVE pour %s." + +#: modules/commands/ns_set.cpp:1038 +#, c-format +msgid "Secure option is now on for %s." +msgstr "L'option de sécurité est maintenant ACTIVE pour %s." + +#: modules/commands/cs_enforce.cpp:42 +#, c-format +msgid "Secureops enforced on %s." +msgstr "Application sur %s de la sécurité des OPs." + +#: modules/commands/cs_set.cpp:1293 modules/commands/ns_set.cpp:1311 +msgid "Security" +msgstr "Sécurité" + +#: modules/commands/cs_xop.cpp:570 +#, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the access list." +msgstr "" +"Tapez %s%s HELP %s pour plus d'informations sur\n" +"la liste d'accès." + +#: modules/commands/cs_xop.cpp:573 +#, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the flags system." +msgstr "" +"Tapez %s%s HELP %s pour plus d'informations sur\n" +"le système des flags." + +#: modules/commands/ms_send.cpp:24 +msgid "Send a memo to a nick or channel" +msgstr "Envoie un mémo à un pseudo ou un canal" + +#: modules/commands/ms_staff.cpp:24 +msgid "Send a memo to all opers/admins" +msgstr "Envoie un mémo à tous les opérateurs." + +#: modules/commands/ms_sendall.cpp:24 +msgid "Send a memo to all registered users" +msgstr "Envoie un mémo à tous les pseudos enregistrés" + +#: modules/commands/gl_global.cpp:21 +msgid "Send a message to all users" +msgstr "Envoie un message à tous les utilisateurs" + +#: modules/commands/ms_list.cpp:64 +msgid "Sender" +msgstr "Expéditeur" + +#: modules/commands/ms_rsend.cpp:24 +msgid "Sends a memo and requests a read receipt" +msgstr "Envoie un mémo et demande un accusé de réception" + +#: modules/commands/ns_resetpass.cpp:50 +msgid "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." +msgstr "" +"Envoie un mot-code au pseudo avec les instructions pour réinitialiser\n" +"son mot de passe. L'email doit être celui associé avec le pseudo." + +#: modules/commands/ms_sendall.cpp:52 +msgid "Sends all registered users a memo containing memo-text." +msgstr "" +"Envoie un mémo dont le message est texte à tous les pseudos enregistrés." + +#: modules/commands/ms_staff.cpp:48 +msgid "Sends all services staff a memo containing memo-text." +msgstr "Envoie un mémo dont le message est texte à tous le staff des services." + +#: modules/commands/ms_send.cpp:66 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." +msgstr "" +"Envoie un mémo dont le teste est texte au pseudo ou canal\n" +"indiqué. En envoyant à un pseudo, le destinataire recevra une notice " +"l'informant\n" +"qu'il ou elle a reçu un nouveau mémo. Le destinataire doit être un pseudo " +"ou\n" +"un canal enregistré." + +#: modules/commands/ms_rsend.cpp:80 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." +msgstr "" +"Envoie un mémo dont le teste est texte au pseudo ou canal\n" +"indiqué. En envoyant à un pseudo, le destinataire recevra une notice " +"l'informant\n" +"qu'il ou elle a reçu un nouveau mémo. Le destinataire doit être un pseudo " +"ou\n" +"un canal enregistré.\n" +"Une fois le mémo lu, un accusé de réception vous est automatiquement\n" +"envoyé afin de vous prévenir que le mémo a été lu." + +#: modules/commands/ms_read.cpp:199 +#, fuzzy +msgid "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Vous envoie le texte des mémos spécifiés. Si LAST est donné,\n" +"vous envoie le dernier mémo reçu. Si NEW est donné, vous\n" +"envoie tous vos nouveaux mémos. Sinon, vous envoie le mémo\n" +"numéro numéro. Vous pouvez également donner une liste\n" +"de nombres, comme dans cet exemple :\n" +" \n" +" READ 2-5,7-9\n" +" Affiche les mémos 2 à 5 et 7 à 9." + +#: modules/commands/os_dns.cpp:218 +msgid "Server" +msgstr "Serveur" + +#: modules/commands/os_dns.cpp:375 +#, c-format +msgid "Server %s added to zone %s." +msgstr "Serveur %s ajouté à la zone %s." + +#: modules/commands/os_dns.cpp:345 +#, c-format +msgid "Server %s already exists." +msgstr "Le serveur %s existe déjà." + +#: modules/commands/os_noop.cpp:31 modules/commands/os_dns.cpp:430 +#: modules/commands/os_dns.cpp:493 modules/commands/os_dns.cpp:532 +#: modules/commands/os_dns.cpp:571 modules/commands/os_dns.cpp:604 +#: modules/commands/os_dns.cpp:639 +#, c-format +msgid "Server %s does not exist." +msgstr "Le serveur %s n'existe pas." + +#: modules/commands/os_dns.cpp:619 +#, c-format +msgid "Server %s has no configured IPs." +msgstr "Le serveur %s n'a pas d'adresse IP configurée." + +#: modules/commands/os_dns.cpp:357 +#, c-format +msgid "Server %s is already in zone %s." +msgstr "Le serveur %s est déjà dans la zone %s " + +#: modules/commands/os_dns.cpp:614 +#, c-format +msgid "Server %s is already pooled." +msgstr "Le serveur %s est déjà dans la pool." + +#: modules/commands/os_dns.cpp:609 +#, c-format +msgid "Server %s is not currently linked." +msgstr "Le serveur %s n'est pas actuellement linké." + +#: modules/commands/os_dns.cpp:443 +#, c-format +msgid "Server %s is not in zone %s." +msgstr "Le serveur %s n'est pas dans la zone %s." + +#: modules/commands/os_dns.cpp:384 +#, c-format +msgid "Server %s is not linked to the network." +msgstr "Le serveur %s n'est pas linké au réseau." + +#: modules/commands/os_dns.cpp:644 +#, c-format +msgid "Server %s is not pooled." +msgstr "Le serveur %s n'est pas dans la pool." + +#: modules/commands/os_dns.cpp:465 +#, c-format +msgid "Server %s must be quit before it can be deleted." +msgstr "Le serveur %s doit être quitté avant de pouvoir être supprimé." + +#: modules/commands/os_dns.cpp:255 +msgid "Servers" +msgstr "Serveurs" + +#: modules/commands/os_stats.cpp:155 +#, c-format +msgid "Servers found: %d" +msgstr "Serveurs trouvés : %d" + +#: modules/commands/cs_log.cpp:127 +msgid "Service" +msgstr "Service" + +#: modules/commands/ns_recover.cpp:51 +#, c-format +msgid "Service's hold on %s has been released." +msgstr "La tutelle des Services sur %s a été enlevée." + +#: data/nickserv.example.conf:236 data/chanserv.example.conf:827 +msgid "Services Operator commands" +msgstr "Commandes pour Opérateur des Services" + +#: modules/commands/os_defcon.cpp:443 modules/commands/os_defcon.cpp:454 +#: modules/commands/os_defcon.cpp:462 modules/commands/os_defcon.cpp:470 +#: modules/commands/os_defcon.cpp:478 +msgid "Services are in DefCon mode, please try again later." +msgstr "Les Services sont en mode DEFCON, veuillez réessayer ultérieurement." + +#: include/language.h:70 +msgid "Services are in read-only mode!" +msgstr "Les Services sont en mode lecture-seule !" + +#: modules/commands/os_defcon.cpp:186 modules/commands/os_defcon.cpp:213 +#, c-format +msgid "Services are now at DEFCON %d." +msgstr "Les Services sont maintenant en alerte DEFCON %d." + +#: modules/commands/os_set.cpp:128 +#, c-format +msgid "Services are now in debug mode (level %d)." +msgstr "Les Services sont maintenant en mode debug (niveau %d)." + +#: modules/commands/os_set.cpp:114 +msgid "Services are now in debug mode." +msgstr "Les Services sont maintenant en mode debug." + +#: modules/commands/os_set.cpp:159 +msgid "Services are now in expire mode." +msgstr "Les Services sont maintenant en mode expiration." + +#: modules/commands/os_set.cpp:153 +msgid "Services are now in no expire mode." +msgstr "Les Services sont maintenant en mode sans expiration." + +#: modules/commands/os_set.cpp:120 +msgid "Services are now in non-debug mode." +msgstr "Les Services sont maintenant en mode normal (non debug)." + +#: modules/commands/os_set.cpp:47 +msgid "Services are now in read-only mode." +msgstr "Les Services sont maintenant en mode lecture-seule." + +#: modules/commands/os_set.cpp:53 +msgid "Services are now in read-write mode." +msgstr "Les Services sont maintenant en mode lecture-écriture." + +#: src/mail.cpp:76 +msgid "Services have been configured to not send mail." +msgstr "Les Services ont été configurés pour ne pas envoyer de mail." + +#: modules/commands/os_ignore.cpp:280 +msgid "Services ignore list:" +msgstr "Liste d'ignore des services :" + +#: modules/commands/os_mode.cpp:33 modules/commands/os_kick.cpp:39 +msgid "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" +msgstr "" +"Les Services ne peuvent changer les modes. Les U:lines de vos serveurs sont-" +"elles configurées correctement ?" + +#: modules/commands/os_stats.cpp:140 +#, c-format +msgid "Services up %s." +msgstr "Services actifs depuis %s" + +#: modules/commands/ns_set.cpp:266 +#, c-format +msgid "Services will from now on set status modes on %s in channels." +msgstr "" +"Les services définiront désormais des modes de statuts pour %s sur les " +"canaux." + +#: modules/commands/cs_set.cpp:114 +#, c-format +msgid "Services will no longer automatically give modes to users in %s." +msgstr "" +"Les services n'appliqueront plus automatiquement de modes utilisateurs sur" +" %s." + +#: modules/commands/ns_set.cpp:272 +#, c-format +msgid "Services will no longer set status modes on %s in channels." +msgstr "" +"Les services ne définiront plus des modes de statuts pour %s sur les canaux." + +#: modules/commands/cs_set.cpp:108 +#, c-format +msgid "Services will now automatically give modes to users in %s." +msgstr "" +"Les services appliqueront automatiquement des modes utilisateurs sur %s." + +#: modules/commands/ns_set.cpp:940 +#, c-format +msgid "Services will now reply to %s with messages." +msgstr "Les services répondront à %s par des messages." + +#: modules/commands/ns_set.cpp:946 +#, c-format +msgid "Services will now reply to %s with notices." +msgstr "Les services répondront à %s par des notices." + +#: modules/commands/os_reload.cpp:34 +msgid "Services' configuration has been reloaded." +msgstr "Le fichier de configuration des Services a été rechargé." + +#: modules/commands/os_session.cpp:192 +msgid "Session" +msgstr "Session" + +#: modules/commands/os_session.cpp:382 +#, c-format +msgid "Session limit for %s set to %d." +msgstr "La limite de sessions de %s est maintenant de %d." + +#: modules/commands/os_session.cpp:257 modules/commands/os_session.cpp:534 +msgid "Session limiting is disabled." +msgstr "La limitation de sessions est désactivée." + +#: modules/commands/os_stats.cpp:195 +#, c-format +msgid "Sessions: %lu entries, %lu buckets, longest chain is %d" +msgstr "Sessions : %lu entrées, %lu paniers, plus longue chaîne : %d" + +#: modules/commands/ns_set.cpp:74 +msgid "Set SET-options on another nickname" +msgstr "Configure des options sur d'autres pseudos" + +#: modules/commands/cs_set.cpp:20 +msgid "Set channel options and information" +msgstr "Configure les options et informations du canal" + +#: modules/commands/cs_set.cpp:137 +msgid "Set how Services make bans on the channel" +msgstr "Définit comment les Services mettent les bans sur le canal" + +#: modules/commands/ms_set.cpp:206 +msgid "Set options related to memos" +msgstr "Définit des options relatives aux mémos" + +#: modules/commands/ns_set.cpp:19 +msgid "Set options, including kill protection" +msgstr "Configure les options, protection comprise" + +#: modules/commands/cs_set.cpp:472 +msgid "Set the channel as permanent" +msgstr "Définit le canal comme permanent" + +#: modules/commands/cs_set.cpp:204 +msgid "Set the channel description" +msgstr "Définit la description du canal" + +#: modules/commands/ns_set.cpp:329 +msgid "Set the display of your group in Services" +msgstr "Change l'affichage de votre groupe dans les services" + +#: modules/commands/cs_set.cpp:266 +msgid "Set the founder of a channel" +msgstr "Définit le fondateur d'un canal" + +#: modules/commands/ns_set.cpp:793 +msgid "Set the language Services will use when messaging you" +msgstr "" +"Change la langue dans laquelle les Services vous envoient leurs messages" + +#: modules/commands/ns_set.cpp:172 +msgid "Set the nickname password" +msgstr "Change le mot de passe du pseudo donné" + +#: modules/commands/cs_set.cpp:949 +msgid "Set the successor for a channel" +msgstr "Définit le successeur d'un canal" + +#: modules/commands/hs_set.cpp:125 +msgid "Set the vhost for all nicks in a group" +msgstr "Configure le vhost pour tous les pseudos d'un groupe" + +#: modules/commands/hs_set.cpp:19 +msgid "Set the vhost of another user" +msgstr "Configure le vhost d'un autre pseudo" + +#: modules/commands/os_set.cpp:169 +msgid "Set various global Services options" +msgstr "Configure des options globales des Services" + +#: modules/commands/ns_set.cpp:119 +msgid "Set your nickname password" +msgstr "Change le mot de passe de votre pseudo" + +#: modules/commands/bs_kick.cpp:271 +#, c-format +msgid "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Active ou désactive le kicker pour les AMSG.\n" +"Lorsque cette option est active, le bot kickera les\n" +"utilisateurs qui envoient le même message à plusieurs\n" +"canaux où se trouvent des bots de %s.\n" +" \n" +"ttb est le nombre de fois qu'un utilisateur peut\n" +"se faire kicker avant d'être banni. N'indiquez pas ttb\n" +"pour désactiver les bans." + +#: modules/commands/bs_kick.cpp:307 +#, c-format +msgid "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Active ou désactive le kicker pour les mots interdits.\n" +"Lorsque cette option est active, le bot kickera les\n" +"utilisateurs qui disent certains mots interdits \n" +"sur le canal.\n" +"Vous pouvez définir les mots interdits pour votre\n" +"canal en utilisant la commande BADWORDS. Tapez\n" +"%s%s HELP BADWORDS pour plus d'informations.\n" +" \n" +"ttb est le nombre de fois qu'un utilisateur peut\n" +"se faire kicker avant d'être banni. N'indiquez pas ttb\n" +"pour désactiver les bans." + +#: modules/commands/cs_set.cpp:186 +msgid "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" +msgstr "" +"Définit le type de ban qui sera utilisé par les services\n" +"lorsqu'ils doivent bannir quelqu'un de votre canal.\n" +" \n" +"typedeban est un nombre entre 0 et 3 qui signifie:\n" +" \n" +"0 : ban de style *!user@host\n" +"1 : ban de style *!*user@host\n" +"2 : ban de style *!*@host\n" +"3 : ban de style *!*user@*.domain" + +#: modules/commands/bs_kick.cpp:345 +msgid "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Active ou désactive le kicker pour les caractères gras.\n" +"Lorsque cette option est active, le bot kickera les\n" +"utilisateurs qui utilisent des caractères gras.\n" +" \n" +"ttb est le nombre de fois qu'un utilisateur peut\n" +"se faire kicker avant d'être banni. N'indiquez pas ttb\n" +"pour désactiver les bans." + +#: modules/commands/bs_kick.cpp:436 +#, c-format +msgid "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Active ou désactive le kicker pour les majuscules.\n" +"Lorsque cette option est active, le bot kickera les\n" +"utilisateurs qui parlent en MAJUSCULES.\n" +"Le bot ne kicke que si il y a au moins min majuscules\n" +"et qu'elles constituent au moins pourcentage%% des\n" +"caractères de la ligne de texte. (Si elles ne sont pas\n" +"précisées, les valeurs par défaut sont 10 caractères et\n" +"25%%).\n" +" \n" +"ttb est le nombre de fois qu'un utilisateur peut\n" +"se faire kicker avant d'être banni. N'indiquez pas ttb\n" +"pour désactiver les bans." + +#: modules/commands/bs_kick.cpp:475 +msgid "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Active ou désactive le kicker pour les couleurs.\n" +"Lorsque cette option est active, le bot kickera les\n" +"utilisateurs qui utilisent des couleurs.\n" +" \n" +"ttb est le nombre de fois qu'un utilisateur peut\n" +"se faire kicker avant d'être banni. N'indiquez pas ttb\n" +"pour désactiver les bans." + +#: modules/commands/cs_set.cpp:255 +msgid "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." +msgstr "" +"Définit la description du canal, qui apparaît dans les\n" +"commandes LIST et INFO." + +#: modules/commands/bs_kick.cpp:571 +msgid "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Active ou désactive le kicker pour le flood.\n" +"Lorsque cette option est active, le bot kickera les\n" +"utilisateurs qui floodent le canal, en envoyant\n" +"au moins ln lignes en secs secondes.\n" +"(Si elles ne sont pas précisées, les valeurs par défaut\n" +"sont 6 lignes en 10 secondes).\n" +" \n" +"ttb est le nombre de fois qu'un utilisateur peut\n" +"se faire kicker avant d'être banni. N'indiquez pas ttb\n" +"pour désactiver les bans." + +#: modules/commands/bs_kick.cpp:607 +msgid "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Active ou désactive le kicker pour l'italique.\n" +"Lorsque cette option est active, le bot kickera les\n" +"utilisateurs qui utilisent des caractères italiques.\n" +" \n" +"ttb est le nombre de fois qu'un utilisateur peut\n" +"se faire kicker avant d'être banni. N'indiquez pas ttb\n" +"pour désactiver les bans." + +#: modules/commands/bs_kick.cpp:706 +msgid "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Active ou désactive le kicker pour les répétitions.\n" +"Lorsque cette option est active, le bot kickera les\n" +"utilisateurs qui répètent le même message num fois.\n" +"(Si elle n'est pas précisée, la valeur par défaut est\n" +"3 fois).\n" +"ttb est le nombre de fois qu'un utilisateur peut\n" +"se faire kicker avant d'être banni. N'indiquez pas ttb\n" +"pour désactiver les bans." + +#: modules/commands/bs_kick.cpp:742 +msgid "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Active ou désactive le kicker pour les caractères inversés.\n" +"Lorsque cette option est active, le bot kickera les\n" +"utilisateurs qui utilisent des caractères inversés.\n" +" \n" +"ttb est le nombre de fois qu'un utilisateur peut\n" +"se faire kicker avant d'être banni. N'indiquez pas ttb\n" +"pour désactiver les bans." + +#: modules/commands/bs_kick.cpp:776 +msgid "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Active ou désactive le kicker pour les caractères soulignés.\n" +"Lorsque cette option est active, le bot kickera les\n" +"utilisateurs qui utilisent des caractères soulignés.\n" +" \n" +"ttb est le nombre de fois qu'un utilisateur peut\n" +"se faire kicker avant d'être banni. N'indiquez pas ttb\n" +"pour désactiver les bans." + +#: modules/commands/hs_set.cpp:206 +msgid "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." +msgstr "" +"Configure le vhost de tous les pseudos d'un même groupe comme égal\n" +"à celui du pseudo indiqué. Si le serveur IRC supporte la modification\n" +"de l'ident, alors utiliser SETALL @\n" +"modifiera aussi l'ident en même temps que le vhost.\n" +"Note : les vhosts des pseudos ajoutés au groupe après l'utilisation\n" +"de cette commande ne seront pas mis à jour." + +#: modules/commands/hs_set.cpp:99 +msgid "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." +msgstr "" +"Configure le vhost du pseudo indiqué.\n" +"Si le serveur IRC supporte la modification de l'ident, alors\n" +"utiliser SET @ modifiera aussi\n" +"l'ident en même temps que le vhost." + +#: modules/commands/os_set.cpp:199 +msgid "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" +msgstr "" +"Contrôle différentes options globales des Services. \n" +"Les noms des options actuelles sont :\n" +" \n" +" READONLY Active ou désactive le mode lecture-seule.\n" +" DEBUG Active ou désactive le mode de déboguage\n" +" NOEXPIRE Active ou désactive le mode sans expiration\n" +" SUPERADMIN Active ou désactive le mode super-admin\n" +" LIST Liste les options" + +#: modules/commands/ms_set.cpp:235 +#, c-format +msgid "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Définit plusieurs options des mémos. option peut être :\n" +" \n" +" NOTIFY Définit si vous serez notifié de vos nouveaux\n" +" mémos (seulement pour les pseudos)\n" +" LIMIT Définit le nombre de mémos maximum que \n" +" vous pouvez recevoir\n" +" \n" +"Tapez %s%s HELP %s option pour plus \n" +"d'informations sur une option spécifique." + +#: modules/commands/ns_set.cpp:33 modules/commands/ns_set.cpp:88 +msgid "Sets various nickname options. option can be one of:" +msgstr "Configure diverses options du pseudo. option peut être :" + +#: modules/commands/ns_set.cpp:237 +msgid "" +"Sets whether services should set channel status modes on you automatically." +msgstr "" +"Définit si les services doivent vous donner automatiquement des modes de " +"statut de canal." + +#: modules/commands/cs_set.cpp:1090 +msgid "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." +msgstr "" +"Définit si le canal donné expirera. Mettre ceci sur ON\n" +"empêche le canal d'expirer." + +#: modules/commands/ns_set.cpp:315 +#, c-format +msgid "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." +msgstr "" +"Définit si le pseudo donné aura des modes attribués\n" +"automatiquement sur les canaux. Définir à ON pour\n" +"autoriser %s à appliquer des modes sur le pseudo\n" +"indiqué lorsqu'il entre sur les canaux. Notez que selon\n" +"les paramètres du canal, certains modes pourraient ne\n" +"pas être appliqués automatiquement." + +#: modules/commands/ns_set.cpp:1145 +msgid "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." +msgstr "" +"Configurez ce paramètre sur ON pour que le \n" +"pseudo n'expire pas." + +#: modules/commands/ns_set.cpp:288 +#, c-format +msgid "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." +msgstr "" +"Définit si les services vous donnent automatiquement des\n" +"modes de statut sur les canaux. Définir à ON pour\n" +"autoriser %s à vous appliquer des modes de statut\n" +"lorsque vous entrez sur les canaux. Notez que selon\n" +"les paramètres du canal, certains modes pourraient ne\n" +"pas être appliqués automatiquement." + +#: modules/commands/cs_access.cpp:648 modules/commands/cs_access.cpp:689 +#, c-format +msgid "" +"Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." +msgstr "" +"L'option %s est inconnue. Tapez %s%s HELP LEVELS pour une \n" +"liste d'options valides." + +#: modules/commands/os_set.cpp:133 +msgid "Setting for DEBUG must be ON, OFF, or a positive number." +msgstr "La valeur pour DEBUG doit être ON, OFF, ou un nombre positif." + +#: modules/commands/os_set.cpp:162 +msgid "Setting for NOEXPIRE must be ON or OFF." +msgstr "La valeur de NOEXPIRE doit être ON ou OFF." + +#: modules/commands/os_set.cpp:56 +msgid "Setting for READONLY must be ON or OFF." +msgstr "La valeur pour READONLY doit être ON ou OFF." + +#: modules/commands/os_set.cpp:95 +msgid "Setting for super admin must be ON or OFF." +msgstr "La valeur pour SUPERADMIN doit être ON ou OFF." + +#: modules/commands/cs_set.cpp:74 +msgid "Should services automatically give status to users" +msgstr "Les services doivent-ils donner automatiquement les modes de statut ?" + +#: modules/commands/os_stats.cpp:203 +msgid "Show status of Services and network" +msgstr "Affiche le statut des Services et du réseau" + +#: modules/commands/os_logsearch.cpp:152 +#, c-format +msgid "Showed %d/%d matches for %s." +msgstr "%d/%d correspondances affichées pour %s." + +#: modules/commands/cs_set.cpp:872 +msgid "Sign kicks that are done with the KICK command" +msgstr "Signe les kicks générés par la commande KICK" + +#: modules/commands/cs_set.cpp:921 +#, c-format +msgid "Signed kick option for %s is now off." +msgstr "Les kicks seront maintenant non-signés sur %s." + +#: modules/commands/cs_set.cpp:913 +#, c-format +msgid "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." +msgstr "" +"Les kicks seront maintenant signés sur %s, en fonction du\n" +"niveau d'accès de celui qui utilise la commande." + +#: modules/commands/cs_set.cpp:906 +#, c-format +msgid "Signed kick option for %s is now on." +msgstr "Les kicks seront maintenant signés sur %s." + +#: modules/commands/cs_set.cpp:1299 +msgid "Signed kicks" +msgstr "Kicks signés" + +#: modules/commands/ms_rsend.cpp:60 modules/commands/ms_send.cpp:59 +#, c-format +msgid "Sorry, %s currently has too many memos and cannot receive more." +msgstr "Désolé, %s a trop de mémos et ne peut en recevoir plus." + +#: modules/commands/cs_seen.cpp:294 +#, c-format +msgid "Sorry, I have not seen %s." +msgstr "Désolé, je n'ai pas vu %s." + +#: modules/commands/bs_badwords.cpp:404 +msgid "Sorry, bad words list modification is temporarily disabled." +msgstr "" +"Désolé, la modification de la liste des mots interdits\n" +"est temporairement désactivée." + +#: modules/commands/bs_assign.cpp:30 modules/commands/bs_assign.cpp:98 +msgid "Sorry, bot assignment is temporarily disabled." +msgstr "Désolé, l'assignation du bot est temporairement désactivée." + +#: modules/commands/bs_bot.cpp:281 modules/commands/bs_assign.cpp:164 +msgid "Sorry, bot modification is temporarily disabled." +msgstr "Désolé, la modification des bots est temporairement désactivée." + +#: modules/fantasy.cpp:42 modules/commands/bs_kick.cpp:813 +#: modules/commands/bs_kick.cpp:878 +msgid "Sorry, bot option setting is temporarily disabled." +msgstr "" +"Désolé, la configuration des options du bot est \n" +"temporairement désactivée." + +#: modules/commands/bs_set.cpp:115 +msgid "Sorry, changing bot options is temporarily disabled." +msgstr "" +"Désolé, la configuration des options du bot est \n" +"temporairement désactivée." + +#: modules/commands/cs_xop.cpp:112 modules/commands/cs_xop.cpp:235 +#: modules/commands/cs_xop.cpp:444 +#, c-format +msgid "Sorry, channel %s list modification is temporarily disabled." +msgstr "" +"Désolé, la modification des listes des %s des canaux est temporairement " +"désactivée." + +#: modules/commands/cs_access.cpp:547 modules/commands/cs_flags.cpp:405 +msgid "Sorry, channel access list modification is temporarily disabled." +msgstr "" +"Désolé, la modification des listes d'accès des canaux est temporairement " +"désactivée." + +#: modules/commands/cs_akick.cpp:469 +msgid "Sorry, channel autokick list modification is temporarily disabled." +msgstr "" +"Désolé, la modification de la liste de kicks automatiques du canal \n" +"est temporairement désactivée." + +#: modules/commands/cs_drop.cpp:29 +msgid "Sorry, channel de-registration is temporarily disabled." +msgstr "Désolé, l'effacement de canaux est temporairement désactivé." + +#: modules/commands/cs_register.cpp:35 +msgid "Sorry, channel registration is temporarily disabled." +msgstr "Désolé, l'enregistrement de canaux est temporairement désactivé." + +#: modules/commands/bs_kick.cpp:181 +msgid "Sorry, kicker configuration is temporarily disabled." +msgstr "" +"Désolé, la configuration des kickers est temporairement\n" +"désactivée." + +#: modules/commands/ms_set.cpp:216 +msgid "Sorry, memo option setting is temporarily disabled." +msgstr "Désolé, la configuration des options est temporairement désactivée." + +#: include/language.h:116 +msgid "Sorry, memo sending is temporarily disabled." +msgstr "Désolé, l'envoi de mémo est temporairement désactivé." + +#: modules/commands/ns_drop.cpp:29 +msgid "Sorry, nickname de-registration is temporarily disabled." +msgstr "Désolé, l'effacement des pseudos est temporairement désactivé." + +#: modules/commands/ns_group.cpp:120 +msgid "Sorry, nickname grouping is temporarily disabled." +msgstr "Désolé, le regroupement de pseudos est temporairement désactivé." + +#: modules/commands/ns_register.cpp:139 +msgid "Sorry, nickname registration is temporarily disabled." +msgstr "Désolé, l'enregistrement de pseudos est temporairement désactivé." + +#: modules/commands/ns_access.cpp:33 +#, c-format +msgid "Sorry, the maximum of %d access entries has been reached." +msgstr "Désolé, vous ne pouvez avoir que %d entrées sur la liste d'accès." + +#: modules/commands/ns_ajoin.cpp:141 +#, c-format +msgid "Sorry, the maximum of %d auto join entries has been reached." +msgstr "Désolé, vous ne pouvez avoir que %d joins automatiques." + +#: modules/commands/ns_cert.cpp:173 +#, c-format +msgid "Sorry, the maximum of %d certificate entries has been reached." +msgstr "Désolé, vous ne pouvez avoir que %d empreintes de certificats." + +#: modules/commands/ms_ignore.cpp:55 +#, c-format +msgid "Sorry, the memo ignore list for %s is full." +msgstr "" +"Désolé, la liste de pseudos ignorés pour les mémos\n" +"de %s est pleine." + +#: modules/commands/cs_access.cpp:204 modules/commands/cs_flags.cpp:174 +#: modules/commands/cs_xop.cpp:201 +#, c-format +msgid "" +"Sorry, you can only have %d access entries on a channel, including access " +"entries from other channels." +msgstr "" +"Désolé, vous ne pouvez avoir que %d entrées sur la liste d'accès d'un " +"canal,\n" +"en comptant les entrées d'autres canaux." + +#: modules/commands/cs_akick.cpp:177 +#, c-format +msgid "Sorry, you can only have %d autokick masks on a channel." +msgstr "" +"Désolé, vous ne pouvez avoir que %d entrées de kicks automatiques\n" +"sur un canal." + +#: modules/commands/bs_badwords.cpp:286 +#, c-format +msgid "Sorry, you can only have %d bad words entries on a channel." +msgstr "" +"Désolé, vous ne pouvez avoir que %d entrées sur la\n" +"liste des mots interdits." + +#: include/language.h:103 +#, c-format +msgid "Sorry, you have already exceeded your limit of %d channels." +msgstr "Désolé, vous avez déjà dépassé la limite de %d canaux." + +#: include/language.h:102 +#, c-format +msgid "Sorry, you have already reached your limit of %d channels." +msgstr "Désolé, vous avez déjà atteint la limite de %d canaux." + +#: modules/commands/os_dns.cpp:218 +msgid "State" +msgstr "État" + +#: modules/commands/cs_seen.cpp:117 +msgid "Statistics and maintenance for seen data" +msgstr "Statistiques et maintenance pour les données 'seen'." + +#: modules/commands/os_stats.cpp:131 +msgid "Statistics reset." +msgstr "Statistiques réinitialisées." + +#: modules/commands/ns_update.cpp:36 +msgid "Status updated (memos, vhost, chmodes, flags)." +msgstr "Statut mis à jour (mémos, vhost, modes, flags)." + +#: modules/commands/bs_kick.cpp:1432 +msgid "Stop flooding!" +msgstr "Arrêtez d'envoyer autant de messages !" + +#: modules/commands/bs_kick.cpp:1448 +msgid "Stop repeating yourself!" +msgstr "Arrêtez de vous répéter !" + +#: modules/commands/cs_set.cpp:746 +msgid "Stricter control of channel founder status" +msgstr "Contrôle plus strict du statut de fondateur du canal" + +#: modules/commands/cs_set.cpp:810 +msgid "Stricter control of chanop status" +msgstr "Contrôle plus strict du statut d'opérateur du canal" + +#: modules/commands/ns_alist.cpp:75 modules/commands/cs_info.cpp:50 +msgid "Successor" +msgstr "Successeur" + +#: modules/commands/cs_set.cpp:1006 +#, c-format +msgid "Successor for %s changed to %s." +msgstr "Le successeur de %s est désormais %s." + +#: modules/commands/cs_set.cpp:1008 +#, c-format +msgid "Successor for %s unset." +msgstr "Il n'y a plus de successeur sur %s." + +#: modules/commands/os_set.cpp:81 +msgid "" +"Super admin can not be set because it is not enabled in the configuration." +msgstr "" +"Le mode super-admin ne peut pas être utilisé, parce qu'il n'est pas activé " +"dans la configuration." + +#: modules/commands/ns_suspend.cpp:60 +msgid "Suspend a given nick" +msgstr "Suspend le pseudo indiqué" + +#: modules/commands/cs_suspend.cpp:236 modules/commands/ns_suspend.cpp:250 +msgid "Suspend reason" +msgstr "Raison de la suspension" + +#: modules/commands/cs_suspend.cpp:232 modules/commands/ns_suspend.cpp:246 +msgid "Suspended" +msgstr "Suspendu" + +#: modules/commands/cs_suspend.cpp:234 modules/commands/ns_suspend.cpp:248 +msgid "Suspended by" +msgstr "Suspendu par" + +#: modules/commands/cs_suspend.cpp:238 modules/commands/ns_suspend.cpp:252 +msgid "Suspended on" +msgstr "Suspendu le" + +#: modules/commands/ns_suspend.cpp:147 +msgid "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." +msgstr "" +"Suspend un pseudo enregistré, ce qui empêche qu'il soit utilisé tout en\n" +"conservant les données associées à ce pseudo. Si une expiration est " +"indiquée,\n" +"la suspension sera retirée après cette période de temps, dans le cas " +"contraire,\n" +"le temps d'expiration par défaut de la configuration sera utilisé." + +#: modules/commands/cs_suspend.cpp:240 modules/commands/ns_suspend.cpp:254 +msgid "Suspension expires" +msgstr "Expiration" + +#: modules/commands/cs_sync.cpp:19 +msgid "Sync users channel modes" +msgstr "Synchronise les modes utilisateurs d'un canal" + +#: modules/commands/cs_sync.cpp:49 +msgid "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." +msgstr "" +"Synchronise tous les modes appliqués sur les utilisateurs du canal avec les " +"modes\n" +"qu'ils devraient avoir en se basant sur leurs accès." + +#: modules/commands/hs_group.cpp:42 +msgid "Syncs the vhost for all nicks in a group" +msgstr "Synchronise le vhost pour tous les pseudos d'un groupe" + +#: src/command.cpp:146 +msgid "Syntax" +msgstr "Syntaxe " + +#: modules/commands/ns_group.cpp:373 +#, c-format +msgid "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." +msgstr "" +"Syntaxe : %s\n" +" \n" +"Liste tous les pseudos de votre groupe." + +#: modules/commands/ns_group.cpp:363 +#, c-format +msgid "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." +msgstr "" +"Syntaxe : %s [pseudo]\n" +" \n" +"Sans paramètre, liste tous les pseudos qui sont dans\n" +"votre groupe.\n" +" \n" +"Avec un paramètre, liste tous les pseudos qui sont dans\n" +"le groupe du pseudo donné.\n" +"Le paramètre est restreint aux Opérateurs des Services." + +#: modules/commands/os_set.cpp:227 +msgid "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." +msgstr "" +"Syntaxe : DEBUG {ON | OFF}\n" +" \n" +"Définit le mode debug à on ou off.\n" +" \n" +"Cette option est équivalente à l'option de ligne de commande\n" +"--debug." + +#: modules/commands/ms_set.cpp:287 +#, c-format +msgid "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." +msgstr "" +"Syntaxe : SET LIMIT [canal] limite\n" +" \n" +"Définit le nombre maximum de mémos que vous (ou le canal\n" +"donné) est autorisé à stocker. Si vous définissez ceci à 0,\n" +"personne ne pourra vous envoyer de mémo. Cependant, vous\n" +"ne pouvez pas définir la limite à plus de %d." + +#: modules/commands/ms_set.cpp:267 +#, c-format +msgid "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." +msgstr "" +"Syntaxe : SET LIMIT [utilisateur | canal] {limite | NONE} [HARD]\n" +" \n" +"Définit le nombre maximum de mémos qu'un utilisateur ou\n" +"un canal est autorisé à stocker. Définir la limite à 0\n" +"empêche l'utilisateur de recevoir des mémos, définir ceci\n" +"à NONE permet à l'utilisateur de recevoir et garder\n" +"autant de mémos qu'il souhaite. Si vous ne donnez pas de\n" +"pseudo ou de canal, vous changez votre propre limite.\n" +" \n" +"Ajouter HARD empêche l'utilisateur de changer cette limite.\n" +"Ne pas ajouter HARD a l'effet inverse, permettant à \n" +"l'utilisateur de changer cette limite (même si une limite\n" +"antérieure a été définie avec HARD).\n" +" \n" +"Cette utilisation de la commande SET LIMIT est réservée aux\n" +"Opérateurs des Services. Les autres utilisateurs peuvent uniquement\n" +"entrer une limite pour eux-mêmes ou un canal sur lequel ils ont\n" +"les privilèges requis, ne peuvent indiquer une limite supérieur à %d, et\n" +"ne peuvent définir de limite stricte." + +#: modules/commands/os_set.cpp:208 +#, c-format +msgid "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." +msgstr "" +"Syntaxe : SET LIST\n" +" \n" +"Afficher diverses options à propos de %s." + +#: modules/commands/os_set.cpp:234 +msgid "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." +msgstr "" +"Syntaxe : SET NOEXPIRE {ON | OFF}\n" +" \n" +"Active ou désactive le mode sans expiration. Dans le mode \n" +"sans expiration, les pseudos, canaux, akills et exceptions \n" +"n'expireront pas jusqu'à ce que l'option soit désactivée.\n" +" \n" +"Cette option est équivalente à l'option de la ligne de commande\n" +"--noexpire." + +#: modules/commands/ms_set.cpp:246 +msgid "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." +msgstr "" +"Syntaxe : SET NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Définit à quel moment vous serez notifié de vos nouveaux mémos:\n" +" \n" +" ON Vous serez notifié lorsque vous vous connectez,\n" +" lorsque vous enlevez /AWAY, et quand les mémos vous\n" +" sont envoyés.\n" +" LOGON Vous serez uniquement notifié des mémos lorsque\n" +" vous vous connectez ou quand vous enlevez\n" +" /AWAY.\n" +" NEW Vous serez uniquement notifié des mémos \n" +" lorsqu'ils vous sont envoyés.\n" +" MAIL Vous serez prévenu pour les mémos par email,\n" +" en plus des autres paramètres.\n" +" NOMAIL Vous ne serez pas prévenu par email.\n" +" OFF Vous ne recevrez aucune notification.\n" +" \n" +"ON est la combinaison de LOGON et NEW." + +#: modules/commands/os_set.cpp:212 +msgid "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." +msgstr "" +"Syntaxe : SET READONLY {ON | OFF}\n" +" \n" +"Active ou désactive le mode lecture seule. Dans le mode \n" +"lecture-seule, les utilisateurs normaux ne seront pas \n" +"autorisés à modifier les données des Services, notamment\n" +"les listes d'accès des canaux et pseudos, etc.\n" +"Les Opérateurs avec suffisamment de droits sur les Services\n" +"pourront modifier les listes d'AKILL, de SQLINE, de SNLINE\n" +"et d'utilisateurs ignorés par les Services, ainsi que supprimer,\n" +"suspendre ou interdire des pseudos et des canaux, et gérer les\n" +"news de connexion et d'oper et les DNS. Mais ces changements\n" +"ne seront pas sauvegardés, à moins que le mode lecture-seule ne\n" +"soit désactivé avant que les Services ne soient éteints ou\n" +"redémarrés.\n" +" \n" +"Cette option est équivalente à l'option de la ligne de commande\n" +"--readonly." + +#: modules/commands/os_set.cpp:243 +msgid "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." +msgstr "" +"Syntaxe : SET SUPERADMIN {ON | OFF}\n" +" \n" +"Vous permet d'avoir des privilèges supplémentaires comme le droit\n" +"d'être reconnu \"fondateur\" de tous les canaux, etc ...\n" +" \n" +"Cette option n'est pas persistante et ne devrait être utilisée que lorsque\n" +"vraiment nécessaire, puis remise à OFF quand elle n'est plus nécessaire." + +#: modules/commands/ns_identify.cpp:107 +#, c-format +msgid "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." +msgstr "" +"Informe %s que vous êtes vraiment le propriétaire de\n" +"ce pseudo. Beaucoup de commandes nécessitent que vous soyez\n" +"identifié avec cette commande avant de les utiliser. Le\n" +"mot de passe est celui que vous avez donné avec la commande \n" +"REGISTER." + +#: modules/commands/cs_invite.cpp:91 +#, c-format +msgid "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Demande à %s de vous inviter vous ou un pseudo indiqué\n" +"sur le canal donné. \n" +" \n" +"Par défaut, limité aux AOPs ou à ceux ayant un niveau \n" +"d'accès de 5 ou plus sur le canal." + +#: modules/commands/cs_unban.cpp:103 +#, c-format +msgid "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Demande à %s de supprimer les bans vous empêchant ou empêchant\n" +"l'utilisateur désigné de rejoindre le canal fourni. Si aucun canal n'est " +"fourni,\n" +"tous les bans vous affectant sur les canaux auxquels vous avez accès seront " +"supprimés.\n" +" \n" +"Par défaut, limité aux AOPs, ou ceux qui ont un level supérieur ou égal à 5\n" +"sur le canal." + +#: modules/commands/os_jupe.cpp:56 +msgid "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." +msgstr "" +"Demande aux Services de \"jupiter\" un serveur -- c'est à dire,\n" +"créer un faux serveur connecté aux Services, ce qui empêche\n" +"le vrai serveur ayant ce nom de se connecter. Le jupe peut\n" +"être enlevé en utilisant un SQUIT normal. Si une raison\n" +"est donnée, elle est placée dans le champ d'information du\n" +"serveur, sinon l'information du serveur contiendra le \n" +"texte \"Juped by \", laissant apparaître le pseudo\n" +"de la personne qui a \"jupiter\" le serveur." + +#: modules/commands/cs_seen.cpp:261 +msgid "Tells you about the last time a user was seen" +msgstr "Vous informe à propos de la dernière fois qu'un utilisateur a été vu." + +#: modules/commands/os_shutdown.cpp:19 +msgid "Terminate Services WITHOUT saving" +msgstr "Arrête les Services SANS sauvegarde" + +#: modules/commands/os_shutdown.cpp:73 +msgid "Terminate services with save" +msgstr "Arrête les Services avec sauvegarde" + +#: modules/commands/os_news.cpp:156 +msgid "Text" +msgstr "Texte" + +#: modules/commands/cs_access.cpp:576 +msgid "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." +msgstr "" +"La commande ACCESS ADD ajoute le masque indiqué à la liste\n" +"d'accès avec le niveau donné. Si le masque est déjà présent sur la liste,\n" +"son niveau d'accès est changé en celui qui est spécifié dans la commande.\n" +"Le niveau spécifié doit être une valeur numérique représentant le level\n" +"ou le nom du privilège (ex. AUTOOP).\n" +"Lorsqu'un utilisateur rejoint le canal, l'accès qu'il reçoit est le plus " +"grand\n" +"présent dans la liste d'accès." + +#: modules/commands/cs_access.cpp:587 +msgid "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." +msgstr "" +"La commande ACCESS DEL supprime le pseudo donné de\n" +"la liste d'accès. Si une liste de numéros d'entrées sont donnés, ces " +"entrées\n" +"seront supprimées (voir l'exemple pour LIST, ci-dessous),\n" +"Vous pouvez vous supprimer vous-même de la liste d'accès même si\n" +"vous n'avez pas l'accès pour modifier la liste." + +#: modules/commands/cs_access.cpp:593 +msgid "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." +msgstr "" +"La commande ACCESS LIST affiche la liste d'accès. Si\n" +"un masque avec joker est donné, seules les entrées\n" +"correspondantes sont affichées. Si une liste de numéros d'entrées\n" +"est donnée, alors ceux-ci seront affichés ; par exemple :\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Liste les entrées d'accès numérotées entre 2 et 5 puis entre\n" +" 7 et 9.\n" +" \n" +"La commande ACCESS VIEW affiche la liste d'accès de manière\n" +"similaire à ACCESS LIST mais affiche le créateur et la dernière " +"utilisation.\n" +" \n" +"La commande ACCESS CLEAR vide toutes les entrées de la liste\n" +"d'accès." + +#: modules/commands/cs_flags.cpp:447 +msgid "" +"The CLEAR command clears the channel access list. This requires channel " +"founder access." +msgstr "" +"La commande CLEAR vide la liste d'accès du canal, ce qui requiert d'être " +"fondateur du canal." + +#: modules/commands/cs_seen.cpp:173 +#, c-format +msgid "" +"The CLEAR command lets you clean the database by removing all entries from " +"the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." +msgstr "" +"La commande CLEAR vous permet de nettoyer la base de données en supprimant " +"toutes les\n" +"entrées de la base qui ont été ajoutées sous le délai temps.\n" +" \n" +"Exemple :\n" +" %s CLEAR 30m\n" +" Supprimera toutes les entrées qui ont été ajoutées depuis les 30 dernières " +"minutes." + +#: modules/commands/bs_badwords.cpp:438 +msgid "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." +msgstr "" +"La commande DEL supprime le mot fourni de la liste des\n" +"mots interdits. Si une liste de numéros d'entrée est donnée, ces\n" +"entrées seront supprimées. (Voir l'exemple pour LIST ci-dessus).\n" +" \n" +"La commande LIST affiche la liste des mots interdits. Si\n" +"un masque avec jokers est donné, seules les entrées correspondantes\n" +"au masque sont affichées. Si une liste de numéros d'entrée est donnée,\n" +"seules celles qui correspondent à ces entrées seront affichées, par " +"exemple :\n" +" #canal LIST 2-5,7-9\n" +" Liste les entrées de mots interdits entre les numéros 2 et 5 puis " +"entre\n" +" 7 et 9.\n" +" \n" +"La commande CLEAR vide les entrées de la liste de mots interdits." + +#: modules/commands/cs_entrymsg.cpp:241 +msgid "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." +msgstr "" +"La commande ENTRYMSG ADD ajoute le message donné\n" +"à la liste des messages à montrer aux utilisateurs lorsqu'ils joignent\n" +"le canal." + +#: modules/commands/cs_entrymsg.cpp:253 +msgid "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." +msgstr "" +"La commande ENTRYMSG CLEAR efface toutes les entrées\n" +"de la liste des messages à montrer lorsque les utilisateurs joignent le " +"canal,\n" +"en désactivant ces messages." + +#: modules/commands/cs_entrymsg.cpp:245 +msgid "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." +msgstr "" +"La commande ENTRYMSG DEL supprime le message donné de la liste\n" +"des messages à montrer aux utilisateurs lorsqu'ils rejoignent le canal.\n" +"Vous pouvez supprimer le message en spécifiant son numéro, que vous pouvez\n" +"obtenir en listant les messages, comme c'est expliqué ci-dessous." + +#: modules/commands/cs_entrymsg.cpp:250 +msgid "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." +msgstr "" +"La commande ENTRYMSG LIST affiche la liste des messages qui seront\n" +"montrés aux utilisateurs lorsqu'ils joignent le canal." + +#: modules/commands/ns_set.cpp:713 +msgid "The IMMED option is not available on this network." +msgstr "L'option IMMED n'est pas disponible sur ce réseau." + +#: modules/commands/cs_access.cpp:821 +#, c-format +msgid "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." +msgstr "" +"La commande LEVELS permet un contrôle précis de la \n" +"signification des niveaux d'accès utilisés pour les canaux.\n" +"Avec cette commande, vous pouvez définir les niveaux d'accès\n" +"requis pour la majorité des fonctions de %s. (Les commandes\n" +"SET FOUNDER, ainsi que cette commande,\n" +"sont toujours réservées au fondateur du canal.)\n" +" \n" +"LEVELS SET permet au niveau d'accès pour une fonction ou un\n" +"groupe de fonctions d'être changé. LEVELS DISABLE (ou DIS\n" +"en abrégé) désactive une fonction automatique ou empêche l'accès\n" +"à une fonction par quiconque incluant le fondateur du canal (même si celui-" +"ci\n" +"peut toujours le ré-activer)\n" +" \n" +"LEVELS LIST montre les niveaux actuels pour chaque fonction\n" +"ou groupe de fonctions. LEVELS RESET réinitialise les niveaux\n" +"avec les valeurs par défaut d'un canal fraîchement créé.\n" +" \n" +"Pour une liste de caractéristiques et fonctions pour lesquelles\n" +"des niveaux peuvent être définis, consultez HELP LEVELS DESC." + +#: modules/commands/cs_flags.cpp:442 +msgid "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." +msgstr "" +"La commande LIST vous permet de lister les entrées existantes sur la liste\n" +"d'accès du canal. Si un masque est donné, le masque est comparé aux entrées\n" +"existantes dans la liste d'accès, et seules les entrées concernées sont " +"retournées.\n" +"Si une suite de flags est donnée, alors seuls les accès avec les flags " +"spécifiés sont retournés." + +#: modules/commands/cs_flags.cpp:435 +msgid "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access " +"list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. " +"You are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of " +"what your access is." +msgstr "" +"La commande MODIFY vous permet de modifier la liste d'accès. Si le\n" +"masque n'est pas déjà dans la liste d'accès, il y est ajouté, puis les " +"modifications\n" +"sont appliquées. Si le masque n'a plus aucun flag, le masque est alors " +"retiré de la liste.\n" +"Additionnellement, vous pouvez utiliser +* ou -* pour ajouter ou supprimer " +"tous les flags.\n" +"Vous pouvez modifier la liste d'accès seulement si vous avez les permissions " +"nécessaires\n" +"sur le canal et vous ne pouvez donner seulement les permissions que vous " +"avez déjà\n" +"vous même." + +#: modules/commands/cs_seen.cpp:172 +msgid "" +"The STATS command prints out statistics about stored nicks and memory usage." +msgstr "" +"La commande STATS affiche des statistiques à propos des pseudos stockés et " +"de la mémoire utilisée." + +#: modules/commands/ns_register.cpp:291 +msgid "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." +msgstr "" +"Le paramètre email est optionnel et rajoute cet email\n" +"à votre pseudo immédiatement.\n" +"Votre vie privée est respectée, cet email ne sera communiqué à\n" +"aucune tierce personne. Si vous le souhaitez, vous pouvez utiliser SET HIDE\n" +"après votre enregistrement si ce n'est pas déjà la configuration par défaut." + +#: modules/commands/cs_log.cpp:258 +#, c-format +msgid "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." +msgstr "" +"La commande %s permet aux utilisateurs de configurer les paramètres\n" +"de log pour leur canal. Si aucun paramètre n'est donné, cette commande\n" +"listera toutes les méthodes actuelles de log en place pour ce canal.\n" +" \n" +"Dans le cas contraire, commande doit être un nom de commande et\n" +"méthode doit être une des méthodes de log suivantes :\n" +" \n" +" MESSAGE [statut], NOTICE [statut], MEMO\n" +" \n" +"Qui sont utilisées pour envoyer un message, une notice ou un mémo au canal.\n" +"Avec MESSAGE ou NOTICE vous devez avoir un bot assigné et présent sur\n" +"votre canal. Statut peut être un statut de canal comme @ ou +.\n" +" \n" +"Pour supprimer une méthode de log, utilisez la même syntaxe que vous\n" +"utiliseriez pour en ajouter une.\n" +" \n" +"Exemple :\n" +" %s #anope chanserv/access MESSAGE @\n" +" Envoi un message à tous les opérateurs à chaque fois que quelqu'un\n" +" utilise la commande ACCESS de ChanServ sur le canal." + +#: modules/commands/cs_ban.cpp:64 +#, c-format +msgid "The %s list for %s is full." +msgstr "La liste de %s pour %s est pleine." + +#: modules/commands/os_sxline.cpp:220 +#, c-format +msgid "The %s list has been cleared." +msgstr "La liste des %s a été vidée." + +#: modules/commands/os_akill.cpp:377 +msgid "The AKILL list has been cleared." +msgstr "La liste d'AKILL a été vidée." + +#: modules/commands/os_defcon.cpp:136 modules/commands/os_defcon.cpp:225 +#, c-format +msgid "The Defcon level is now at: %d" +msgstr "Le niveau d'alerte DEFCON est maintenant : %d." + +#: modules/commands/ns_info.cpp:171 +#, c-format +msgid "The E-mail address of %s will now be hidden from %s INFO displays." +msgstr "" +"L'adresse email de %s sera désormais cachée dans la commande INFO de %s." + +#: modules/commands/ns_info.cpp:172 +#, c-format +msgid "The E-mail address of %s will now be shown in %s INFO displays." +msgstr "" +"L'adresse email de %s sera désormais affichée dans la commande INFO de %s." + +#: modules/commands/cs_flags.cpp:449 +msgid "The available flags are:" +msgstr "Les flags disponibles sont :" + +#: modules/commands/os_defcon.cpp:240 +msgid "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." +msgstr "" +"Le système DEFCON peut être utilisé pour appliquer des restrictions\n" +"configurées au préalable, qui peuvent être utiles lors d'une tentative\n" +"d'attaque sur le réseau." + +#: modules/ns_maxemail.cpp:51 +#, c-format +msgid "The email address %s has reached its usage limit of %d users." +msgstr "" +"L'adresse email %s a atteint sa limite d'utilisation de %d utilisateurs." + +#: modules/ns_maxemail.cpp:49 +#, c-format +msgid "The email address %s has reached its usage limit of 1 user." +msgstr "L'adresse email %s a atteint sa limite d'utilisation d'un utilisateur." + +#: modules/commands/cs_entrymsg.cpp:142 +#, c-format +msgid "The entry message list for %s is full." +msgstr "La liste de messages d'accueil de %s est pleine." + +#: modules/commands/cs_access.cpp:796 +msgid "The following feature/function names are available:" +msgstr "Les fonctionnalités suivantes sont disponibles :" + +#: modules/commands/cs_access.cpp:584 +msgid "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." +msgstr "" +"Le masque indiqué peut également être un canal, ce qui utilisera\n" +"la liste d'accès de l'autre canal jusqu'au niveau indiqué." + +#: modules/commands/os_session.cpp:240 +#, c-format +msgid "" +"The host %s currently has %d sessions with a limit of %d because it matches " +"entry: %s." +msgstr "" +"L'hôte %s a actuellement %d sessions avec une limite de %d parce qu'il " +"correspond à l'entrée : %s." + +#: modules/commands/ms_check.cpp:54 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has been read." +msgstr "Le dernier mémo que vous avez envoyé à %s (le %s) a été lu." + +#: modules/commands/ms_check.cpp:52 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has not yet been read." +msgstr "" +"Le dernier mémo que vous avez envoyé à %s (le %s) n'a pas encore été lu." + +#: modules/commands/ns_info.cpp:189 +#, c-format +msgid "The last quit message of %s will now be hidden from %s INFO displays." +msgstr "" +"Le dernier message de quit de %s ne sera plus affiché dans la commande INFO " +"de %s." + +#: modules/commands/ns_info.cpp:190 +#, c-format +msgid "The last quit message of %s will now be shown in %s INFO displays." +msgstr "" +"Le dernier message de quit de %s sera affiché dans la commande INFO de %s." + +#: modules/commands/ns_info.cpp:177 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." +msgstr "" +"Le dernier masque user@host de %s sera maintenant caché dans la commande " +"INFO\n" +"de %s." + +#: modules/commands/ns_info.cpp:178 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." +msgstr "" +"Le dernier masque user@host de %s sera maintenant affiché dans la commande " +"INFO\n" +"de %s." + +#: modules/commands/cs_enforce.cpp:190 +#, c-format +msgid "The limit on %s is not valid." +msgstr "La limite sur %s est invalide." + +#: modules/commands/os_forbid.cpp:193 +msgid "The mask must contain at least one non wildcard character." +msgstr "Le masque doit contenir au moins un caractère non joker." + +#: modules/commands/ms_set.cpp:153 +#, c-format +msgid "The memo limit for %s may not be changed." +msgstr "La limite de mémos pour %s ne peut être changée." + +#: modules/commands/cs_mode.cpp:347 +#, c-format +msgid "The mode lock list of %s is full." +msgstr "La liste des modes verrouillés pour %s est pleine." + +#: modules/commands/ns_set.cpp:355 +#, c-format +msgid "The new display MUST be a nickname of the nickname group %s." +msgstr "Le nouvel affichage DOIT être un pseudo du groupe %s." + +#: include/language.h:98 +#, c-format +msgid "The new display is now %s." +msgstr "Le nouvel affichage est maintenant %s." + +#: modules/commands/os_svs.cpp:57 +#, c-format +msgid "The nick %s is now being changed to %s." +msgstr "Le pseudo de %s a été changé en %s." + +#: modules/commands/bs_bot.cpp:149 +msgid "The old information is the same as the new information specified." +msgstr "Les anciennes informations sont les mêmes que les nouvelles indiquées." + +#: modules/commands/os_info.cpp:157 +#, c-format +msgid "The oper info already exists on %s." +msgstr "L'information oper existe déjà sur %s." + +#: modules/commands/os_info.cpp:147 +#, c-format +msgid "The oper info list for %s is full." +msgstr "L'information oper pour %s est pleine." + +#: modules/commands/ns_info.cpp:183 +#, c-format +msgid "" +"The services access status of %s will now be hidden from %s INFO displays." +msgstr "" +"Les accès aux services de %s seront maintenant cachés dans la commande INFO " +"de %s." + +#: modules/commands/ns_info.cpp:184 +#, c-format +msgid "The services access status of %s will now be shown in %s INFO displays." +msgstr "" +"Les accès aux services de %s seront maintenant affichés dans la commande " +"INFO de %s." + +#: modules/commands/os_session.cpp:433 +msgid "The session exception list is empty." +msgstr "La liste d'exceptions est vide." + +#: modules/commands/ns_recover.cpp:121 +msgid "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." +msgstr "" +"L'utilisateur utilisant votre pseudo a été déconnecté. Utilisez cette " +"commande\n" +"à nouveau pour relâcher la détention de votre pseudo par les services." + +#: modules/pseudoclients/memoserv.cpp:195 +#, c-format +msgid "There are %d memos on channel %s." +msgstr "Il y a %d mémos sur le canal %s." + +#: modules/commands/bs_botlist.cpp:47 +msgid "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" +msgstr "" +"Il n'y a aucun bot disponible actuellement.\n" +"Demandez à un Opérateur des Services d'en créer un !" + +#: modules/commands/os_dns.cpp:213 +msgid "There are no configured servers." +msgstr "Il n'y a pas de serveur configuré." + +#: modules/commands/os_forbid.cpp:392 +#, c-format +msgid "There are no forbids of type %s." +msgstr "Il n'y a pas d'interdit de type %s." + +#: modules/commands/ns_group.cpp:162 +msgid "There are too many nicks in your group." +msgstr "Il y a trop de pseudos dans votre groupe." + +#: modules/commands/cs_log.cpp:123 +#, c-format +msgid "There currently are no logging configurations for %s." +msgstr "Il n'y a actuellement pas de configuration de logging pour %s." + +#: modules/pseudoclients/memoserv.cpp:193 +#, c-format +msgid "There is %d memo on channel %s." +msgstr "Il y a %d mémo sur le canal %s." + +#: include/language.h:110 +#, c-format +msgid "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." +msgstr "" +"Il y a un nouveau mémo sur le canal %s.\n" +"Tapez %s%s READ %s %d pour le lire." + +#: modules/commands/bs_assign.cpp:132 +#, c-format +msgid "There is no bot assigned to %s anymore." +msgstr "Il n'y a plus de bot attribué à %s." + +#: modules/commands/os_news.cpp:33 +msgid "There is no logon news." +msgstr "Il n'y a pas de news de connexion." + +#: modules/commands/os_news.cpp:43 +msgid "There is no oper news." +msgstr "Il n'y a pas de news d'oper." + +#: modules/commands/os_news.cpp:53 +msgid "There is no random news." +msgstr "Il n'y a pas de news aléatoires." + +#: modules/commands/os_config.cpp:41 +#, c-format +msgid "There is no such configuration block %s." +msgstr "Il n'y a pas de bloc de configuration %s." + +#: modules/commands/cs_mode.cpp:706 +#, c-format +msgid "There is no such mode %s." +msgstr "Il n'y a pas de mode %s." + +#: modules/commands/ms_set.cpp:52 +msgid "There's no email address set for your nick." +msgstr "Vous n'avez configuré aucune adresse email pour votre pseudo." + +#: modules/commands/os_forbid.cpp:304 modules/commands/os_forbid.cpp:496 +#, c-format +msgid "This channel has been forbidden: %s" +msgstr "Ce canal a été interdit : %s" + +#: modules/commands/cs_suspend.cpp:121 +msgid "This channel has been suspended." +msgstr "Ce canal a été suspendu." + +#: modules/commands/cs_suspend.cpp:232 +msgid "This channel is suspended." +msgstr "Ce canal est suspendu." + +#: modules/commands/cs_suspend.cpp:268 +msgid "This channel may not be used." +msgstr "Ce canal ne peut pas être utilisé." + +#: modules/commands/os_dns.cpp:702 +msgid "" +"This command allows managing DNS zones used for controlling what servers " +"users\n" +"are directed to when connecting. Omitting all parameters prints out the " +"status of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to " +"this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, " +"the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given " +"zones." +msgstr "" +"Cette commande permet de gérer les zones DNS utilisées pour contrôler sur " +"quels\n" +"serveurs les utilisateurs se connectent. Si vous ne mettez aucun paramètre, " +"la\n" +"commande affiche le statut actuel de la zone DNS.\n" +" \n" +"ADDZONE crée une nouvelle zone, par exemple us.yournetwork.tld. Vous pouvez\n" +"ensuite ajouter des serveurs à cette zone avec la commande ADDSERVER.\n" +" \n" +"ADDSERVER ajoute un serveur à la zone indiquée. Lorsqu'une requête DNS est " +"faite\n" +"pour une zone particulière, si cette zone existe, Anope envoie les IPs des " +"serveurs\n" +"assignés à cette zone, sinon Anope répond avec les IPs de tous les " +"serveurs.\n" +"Un serveur peut être dans aucune ou plusieurs zones.\n" +" \n" +"ADDIP associe une IP à un serveur. Un serveur peut avoir plusieurs IPs.\n" +" \n" +"POOL et DEPOOL activent ou désactivent le serveur indiqué dans l'ensemble\n" +"de ses zones. Seuls les serveurs dans la pool sont insérés dans les réponses " +"DNS." + +#: modules/commands/hs_group.cpp:72 +msgid "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." +msgstr "" +"Permet aux utilisateurs d'appliquer le vhost de leur pseudo\n" +"actuellement utilisé à tous les pseudos de leur groupe de pseudos." + +#: modules/commands/ns_register.cpp:299 +msgid "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." +msgstr "" +"Cette commande créé également un nouveau groupe pour votre\n" +"pseudo, ce qui vous permettra d'enregistrer d'autres pseudos\n" +"plus tard, qui partageront la même configuration, les mêmes mémos\n" +"et les mêmes privilèges de canal." + +#: modules/m_rewrite.cpp:145 +#, c-format +msgid "This command is an alias to the command %s." +msgstr "Cette commande est un alias de la commande %s." + +#: modules/commands/ns_register.cpp:95 +msgid "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." +msgstr "" +"Cette commande est utilisée par plusieurs commandes pour confirmer\n" +"des changements effectués sur votre compte.\n" +" \n" +"Elle est principalement utilisée pour confirmer votre adresse email\n" +"lorsque vous vous enregistrez, ou que vous changez d'email.\n" +" \n" +"Elle est aussi utilisée lors de l'utilisation de RESETPASS pour vous\n" +"réidentifier pour que vous puissiez changer votre mot de passe." + +#: modules/commands/os_modinfo.cpp:70 +msgid "This command lists information about the specified loaded module." +msgstr "Cette commande donne des informations sur un module chargé." + +#: modules/commands/hs_list.cpp:136 +msgid "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." +msgstr "" +"Cette commande liste tous les vhosts enregistrés. Si une clé\n" +"est spécifiée, seuls les résultats contenant le pseudo ou\n" +"le vhost seront affichés, par exemple : Rob* pour toutes les\n" +"entrées contenant \"Rob\"\n" +"Si le style #X-Y est utilisé, seules les entrées entre X et Y\n" +"seront affichées, par exemple: #1-3 affichera les 3 premières\n" +"entrées." + +#: modules/commands/os_module.cpp:45 +msgid "" +"This command loads the module named modname from the modules\n" +"directory." +msgstr "" +"Cette commande charge le module nom-module depuis le fichier situé dans le " +"répertoire\n" +"des modules." + +#: modules/commands/ns_group.cpp:201 +msgid "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." +msgstr "" +"Cette commande fait rejoindre votre pseudo au groupe du pseudo cible.\n" +"motdepasse est le mot de passe du pseudo cible.\n" +" \n" +"Rejoindre un groupe vous permettra de partager votre configuration,\n" +"vos mémos et vos privilèges de canal avec tous les pseudos\n" +"du groupe, et bien plus encore !\n" +" \n" +"Un groupe existe tant qu'il est utile. Cela signifie que même\n" +"si un des pseudos du groupe est effacé, les éléments partagés\n" +"ci-dessous sont conservés pour peu qu'il reste d'autres pseudos\n" +"dans le groupe.\n" +" \n" +"Vous pouvez utiliser cette commande même si vous n'avez pas encore\n" +"enregistré votre pseudo. Si votre pseudo est déjà enregistré, vous devez\n" +"vous identifier avant de pouvoir utiliser cette commande.\n" +" \n" +"Il est préférable d'utiliser cette commande avec un pseudo\n" +"non enregistré puisqu'il sera automatiquement enregistré\n" +"lorsque vous utiliserez cette commande. Vous pouvez l'utiliser\n" +"avec un pseudo enregistré (pour changer votre groupe) uniquement\n" +"si vos administrateurs l'autorisent. \n" +"Vous ne pouvez être que dans un groupe à la fois. La fusion\n" +"de groupes n'est pas possible.\n" +" \n" +"Note : tous les pseudos du groupe ont le même mot de passe." + +#: modules/commands/ns_ajoin.cpp:292 +msgid "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." +msgstr "" +"Cette commande gère votre liste d'auto join. Lorsque vous vous identifiez,\n" +"vous joindrez automatiquement les canaux de votre liste d'auto join.\n" +"Les Opérateurs des Services peuvent fournir un pseudo pour modifier\n" +"la liste d'auto join d'autres utilisateurs." + +#: modules/commands/ns_set.cpp:345 modules/commands/ns_set.cpp:669 +msgid "" +"This command may not be used on this network because nickname ownership is " +"disabled." +msgstr "" +"Cette commande ne peut pas être utilisée sur ce réseau parce que la " +"possession de pseudo est désactivée." + +#: modules/commands/os_module.cpp:118 +msgid "This command reloads the module named modname." +msgstr "Cette commande recharge le module nommé nom-module." + +#: modules/commands/hs_request.cpp:344 +msgid "This command retrieves the vhost requests." +msgstr "Cette commande récupère la liste des demandes de vhost." + +#: modules/commands/os_logsearch.cpp:159 +msgid "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." +msgstr "" +"Cette commande cherche dans les fichiers de log des Services des\n" +"messages qui correspondent au modèle donné. Les paramètres jour et limite\n" +"peuvent être utilisés pour indiquer parmi combien de jours de logs chercher\n" +"et combien de messages afficher. Par défaut, cette commande cherche dans\n" +"une semaine de logs et limite la réponse aux 50 dernières entrées.\n" +" \n" +"Par exemple :\n" +" LOGSEARCH +21d +500l Anope\n" +" Cherche dans les 21 derniers jours de logs des messages\n" +" contenant Anope et liste les 500 plus récents." + +#: modules/commands/cs_status.cpp:106 +msgid "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." +msgstr "" +"Cette commande vous indique quels utilisateurs ont accès sur un canal,\n" +"et quelles entrées correspondent. De plus, cela vous indique les kicks\n" +"automatiques qui correspondent, s'il y en a. L'utilisation de cette " +"commande\n" +"est limitée aux utilisateurs qui ont la possibilité de modifier les accès du " +"canal." + +#: modules/commands/ns_group.cpp:285 +msgid "" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." +msgstr "" +"Cette commande dé-groupe votre pseudo, ou si fourni, le pseudo spécifié,\n" +"du groupe dans lequel il est. Le pseudo dé-groupé garde sa date\n" +"d'enregistrement, son mot de passe, email, message d'accueil, sa langue et\n" +"son URL. Tout le reste est réinitialisé. Vous ne pouvez pas vous dé-grouper\n" +"vous-même s'il n'y a plus qu'un pseudo dans votre groupe." + +#: modules/commands/os_module.cpp:168 +msgid "This command unloads the module named modname." +msgstr "Cette commande décharge le module nommé nom-module." + +#: modules/commands/ns_register.cpp:353 +msgid "This command will resend you the registration confirmation email." +msgstr "Cette commande vous renverra l'email de confirmation d'enregistrement." + +#: include/language.h:90 +#, c-format +msgid "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" +msgstr "" +"Ce pseudo appartient à quelqu'un d'autre. Merci d'en choisir un autre.\n" +"(Si c'est votre pseudo, tapez %s%s IDENTIFY mot-de-passe.)" + +#: modules/commands/os_forbid.cpp:469 +#, c-format +msgid "This nickname has been forbidden: %s" +msgstr "Ce pseudo a été interdit : %s" + +#: modules/commands/ns_recover.cpp:99 +#, c-format +msgid "This nickname has been recovered by %s." +msgstr "Ce pseudo a été récupéré par %s." + +#: modules/commands/ns_recover.cpp:77 +#, c-format +msgid "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." +msgstr "" +"Ce pseudo a été récupéré par %s. Si vous ne l'avez pas fait vous-même\n" +"alors %s pourrait avoir votre mot de passe, et vous devriez le changer." + +#: include/language.h:95 +msgid "This nickname has been registered; you may not use it." +msgstr "Ce pseudo a été enregistré, vous ne pouvez pas l'utiliser." + +#: modules/commands/ns_suspend.cpp:246 +msgid "This nickname is suspended." +msgstr "Ce pseudo est suspendu." + +#: include/language.h:92 +#, c-format +msgid "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." +msgstr "" +"Le pseudo est enregistré et protégé. Si c'est votre pseudo,\n" +"tapez %s%s IDENTIFY mot-de-passe.\n" +"Dans le cas contraire, merci de choisir un pseudo différent." + +#: modules/commands/ms_read.cpp:95 +#, c-format +msgid "To delete, type: %s%s %s %d" +msgstr "Pour supprimer, tapez : %s%s %s %d" + +#: modules/commands/ms_read.cpp:93 +#, c-format +msgid "To delete, type: %s%s %s %s %d" +msgstr "Pour supprimer, tapez : %s%s %s %s %d" + +#: modules/commands/bs_kick.cpp:791 +msgid "To protect ops against bot kicks" +msgstr "Pour protéger les ops des kicks du bot" + +#: modules/commands/bs_kick.cpp:856 +msgid "To protect voices against bot kicks" +msgstr "Pour protéger les voices des kicks du bot" + +#: modules/commands/cs_list.cpp:46 +msgid "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." +msgstr "" +"Pour rechercher des canaux commençant par #, cherchez le nom\n" +"du canal sans le signe # (anope au lieu de #anope)." + +#: modules/commands/os_logsearch.cpp:139 +#, c-format +msgid "Too many results for %s." +msgstr "Trop de résultats pour %s." + +#: modules/extra/stats/cs_fantasy_top.cpp:149 +#, c-format +msgid "Top %i of %s" +msgstr "Top %i de %s" + +#: modules/commands/os_list.cpp:43 +msgid "Topic" +msgstr "Topic" + +#: modules/commands/cs_topic.cpp:258 +msgid "Topic lock" +msgstr "Verrouillage du topic" + +#: modules/commands/cs_topic.cpp:114 +#, c-format +msgid "Topic lock option for %s is now off." +msgstr "Le verrouillage du sujet pour %s est maintenant INACTIF." + +#: modules/commands/cs_topic.cpp:97 +#, c-format +msgid "Topic lock option for %s is now on." +msgstr "Le verrouillage du sujet pour %s est maintenant ACTIF." + +#: modules/commands/cs_topic.cpp:256 +msgid "Topic retention" +msgstr "Maintien du topic" + +#: modules/commands/cs_topic.cpp:60 +#, c-format +msgid "Topic retention option for %s is now off." +msgstr "Le maintient du topic est maintenant INACTIF sur %s." + +#: modules/commands/cs_topic.cpp:54 +#, c-format +msgid "Topic retention option for %s is now on." +msgstr "Le maintient du topic est maintenant ACTIF sur %s." + +#: modules/commands/cs_topic.cpp:265 +msgid "Topic set by" +msgstr "Topic défini par" + +#: modules/commands/bs_kick.cpp:1323 +msgid "Turn caps lock OFF!" +msgstr "Cessez d'utiliser tant de majuscules !" + +#: modules/extra/stats/m_chanstats.cpp:17 +#: modules/extra/stats/m_chanstats.cpp:71 +msgid "Turn chanstats statistics on or off" +msgstr "Active ou désactive les statistiques de ChanStats." + +#: modules/commands/ns_set.cpp:1009 +msgid "Turn nickname security on or off" +msgstr "Active ou désactive la sécurité du pseudo" + +#: modules/commands/ns_set.cpp:655 +msgid "Turn protection on or off" +msgstr "Active ou désactive la protection" + +#: modules/commands/ns_list.cpp:264 +#, c-format +msgid "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Active ou désactive le mode privé de %s du pseudo indiqué.\n" +"Si PRIVATE est actif, son pseudo n’apparaîtra pas\n" +"dans les listes de pseudos générée par la commande LIST\n" +"de %s. (Cependant, quiconque connaissant son pseudo peut\n" +"tout de même avoir des informations en utilisant la commande\n" +"INFO)." + +#: modules/commands/ns_list.cpp:236 +#, c-format +msgid "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Active ou désactive le mode privé de %s de votre pseudo.\n" +"Si le mode privé est actif, votre pseudo n’apparaîtra pas\n" +"dans les listes de pseudos générée par la commande LIST\n" +"de %s. (Cependant, quiconque connaissant votre pseudo peut\n" +"tout de même avoir des informations en utilisant la commande\n" +"INFO)." + +#: modules/commands/ns_set.cpp:1059 modules/commands/ns_set.cpp:1088 +#, c-format +msgid "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." +msgstr "" +"Active ou désactive la sécurité de %s pour votre pseudo.\n" +"Si SECURE est actif, vous devrez obligatoirement\n" +"entrer votre mot de passe pour être reconnu en tant que \n" +"propriétaire du pseudo, que votre masque soit dans la liste d'accès\n" +"ou non. Cependant, si vous êtes sur la liste d'accès, %s n'utilisera pas\n" +"d'auto-kill quelque soit l'état de l'option KILL." + +#: modules/extra/stats/m_chanstats.cpp:142 +msgid "Turns chanstats channel statistics ON or OFF for this user." +msgstr "" +"Active ou désactive les statistiques de canal de ChanStats pour cet " +"utilisateur." + +#: modules/extra/stats/m_chanstats.cpp:61 +#: modules/extra/stats/m_chanstats.cpp:119 +msgid "Turns chanstats statistics ON or OFF." +msgstr "Active ou désactive les statistiques de ChanStats." + +#: modules/commands/ns_set.cpp:772 +#, c-format +msgid "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Active ou désactive la protection automatique pour le pseudo donné.\n" +"Avec la protection activée, si un autre utilisateur essaie de \n" +"prendre son pseudo, il aura une minute pour changer de pseudo,\n" +"après quoi son pseudo sera changé de force par %s.\n" +" \n" +"Si vous sélectionnez QUICK, l'utilisateur aura seulement 20\n" +"secondes pour changer de pseudo au lieu des 60 habituelles. Si\n" +"vous sélectionnez IMMED, l'utilisateur verra son pseudo changé\n" +"immédiatement sans être prévenu et sans avoir de chance\n" +"de changer son pseudo, n'utilisez cette option que si nécessaire.\n" +"Les administrateurs de votre réseau peuvent avoir désactivé cette option." + +#: modules/commands/ns_set.cpp:738 +#, c-format +msgid "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Active ou désactive la protection automatique pour votre pseudo.\n" +"Avec la protection activée, si un autre utilisateur essaie de prendre\n" +"votre pseudo, il aura une minute pour changer de pseudo, après quoi\n" +"son pseudo sera changé de force par %s.\n" +" \n" +"Si vous sélectionnez QUICK, l'utilisateur aura seulement 20\n" +"secondes pour changer de pseudo au lieu des 60 habituelles. Si\n" +"vous sélectionnez IMMED, l'utilisateur verra son pseudo changé\n" +"immédiatement sans être prévenu et sans avoir de chance\n" +"de changer son pseudo, n'utilisez cette option que si nécessaire.\n" +"Les administrateurs de votre réseau peuvent avoir désactivé cette option." + +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_forbid.cpp:358 +msgid "Type" +msgstr "Type" + +#: modules/commands/ns_set.cpp:62 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Tapez %s%s HELP %s option pour plus d'informations sur\n" +"une option particulière." + +#: modules/commands/bs_kick.cpp:151 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." +msgstr "" +"Tapez %s%s HELP %s option pour plus d'informations\n" +"sur une option particulière.\n" +" \n" +"Note : l'accès à cette commande est contrôlé par le niveau SET." + +#: modules/commands/ns_set.cpp:107 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." +msgstr "" +"Tapez %s%s HELP %s option pour plus d'informations\n" +"sur une option particulière. Les options seront définies pour le\n" +"pseudo indiqué." + +#: modules/commands/bs_set.cpp:62 modules/commands/cs_set.cpp:63 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." +msgstr "" +"Tapez %s%s HELP %s option pour plus d'informations sur\n" +"une option particulière." + +#: modules/pseudoclients/nickserv.cpp:361 +#, c-format +msgid "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." +msgstr "" +"Tapez %s%s SET EMAIL email pour définir votre email.\n" +"Votre vie privée est respectée, cet email ne sera pas divulguée\n" +"à des tierces personnes." + +#: modules/commands/os_module.cpp:128 +msgid "Un-Load a module" +msgstr "Décharge un module" + +#: modules/commands/os_sxline.cpp:337 modules/commands/os_sxline.cpp:552 +#: modules/commands/os_akill.cpp:136 +#, c-format +msgid "Unable to find regex engine %s." +msgstr "Impossible de trouver le moteur de regex %s." + +#: modules/commands/os_module.cpp:36 modules/commands/os_module.cpp:108 +#, c-format +msgid "Unable to load module %s." +msgstr "Impossible de charger le module %s." + +#: modules/commands/os_module.cpp:73 modules/commands/os_module.cpp:90 +#: modules/commands/os_module.cpp:145 modules/commands/os_module.cpp:159 +#, c-format +msgid "Unable to remove module %s." +msgstr "Impossible de décharger le module %s." + +#: modules/commands/bs_assign.cpp:90 +msgid "Unassigns a bot from a channel" +msgstr "Retire le bot d'un canal" + +#: modules/commands/bs_assign.cpp:139 +msgid "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." +msgstr "" +"Retire le bot d'un canal. Si vous utilisez cette commande,\n" +"le bot ne joindra plus le canal. Cependant, la configuration\n" +"du bot est conservée donc vous aurez toujours la possibilité\n" +"de réattribuer un bot plus tard sans avoir à le reconfigurer\n" +"entièrement." + +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1193 +#: modules/commands/bs_kick.cpp:1196 +msgid "Underlines kicker" +msgstr "Kicker de caractères soulignés" + +#: modules/commands/os_dns.cpp:595 +msgid "Unknown SET option." +msgstr "Option SET inconnue." + +#: modules/commands/os_stats.cpp:229 +#, c-format +msgid "Unknown STATS option: %s" +msgstr "Option STATS inconnue : %s." + +#: src/command.cpp:222 src/command.cpp:233 +#, c-format +msgid "Unknown command %s." +msgstr "Commande %s inconnue." + +#: src/command.cpp:220 src/command.cpp:231 +#, c-format +msgid "Unknown command %s. \"%s%s HELP\" for help." +msgstr "Commande %s inconnue. Tapez \"%s%s HELP\" pour obtenir de l'aide." + +#: modules/commands/cs_mode.cpp:317 modules/commands/cs_mode.cpp:409 +#, c-format +msgid "Unknown mode character %c ignored." +msgstr "Mode %c ignoré car inconnu." + +#: modules/commands/os_logsearch.cpp:78 +#, c-format +msgid "Unknown parameter: %s" +msgstr "Paramètre inconnu : %s" + +#: modules/commands/os_dns.cpp:241 +msgid "Unpooled" +msgstr "Retiré de la pool." + +#: modules/commands/cs_drop.cpp:77 +msgid "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." +msgstr "" +"Efface le canal indiqué. Peut uniquement être utilisé par\n" +"le fondateur du canal." + +#: modules/commands/cs_drop.cpp:74 +msgid "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." +msgstr "" +"Efface le canal indiqué. Seuls les Opérateurs des Services\n" +"peuvent effacer un canal duquel ils ne sont pas le fondateur." + +#: modules/commands/ns_suspend.cpp:160 +msgid "Unsuspend a given nick" +msgstr "Relâche un pseudo suspendu" + +#: modules/commands/ns_suspend.cpp:199 +msgid "Unsuspends a nickname which allows it to be used again." +msgstr "" +"Relâche un pseudo suspendu, ce qui permet qu'il soit utilisé à nouveau." + +#: modules/commands/cs_updown.cpp:126 +msgid "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." +msgstr "" +"Met à jour les modes de statut de canal du pseudo indiqué. Si pseudo\n" +"est omis, alors votre statut est mis à jour. Si canal est omis, alors votre\n" +"statut de canal est mis à jour sur tous les canaux sur lesquels vous vous " +"trouvez." + +#: modules/commands/cs_updown.cpp:48 +msgid "Updates a selected nicks status on a channel" +msgstr "Met à jour le statut des pseudos sur un canal." + +#: modules/commands/ns_update.cpp:19 +msgid "Updates your current status, i.e. it checks for new memos" +msgstr "Met à jour votre statut, ex : vérification de nouveaux mémos" + +#: modules/commands/ns_update.cpp:43 +msgid "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." +msgstr "" +"Actualise votre statut, ex : vérification de l'arrivée de\n" +"nouveaux mémos, l'application des modes sur les canaux,\n" +"mise à jour de votre vhost et vos données sauvegardées\n" +"(dernière fois vu, etc)." + +#: modules/commands/os_update.cpp:25 +msgid "Updating databases." +msgstr "Mise à jour des bases de données." + +#: modules/commands/os_stats.cpp:154 +#, c-format +msgid "Uplink capab: %s" +msgstr "Capacités du lien : %s" + +#: modules/commands/os_stats.cpp:153 +#, c-format +msgid "Uplink server: %s" +msgstr "Connecté à : %s" + +#: modules/commands/help.cpp:127 +#, c-format +msgid "Use the %s ALL command to list all commands and their descriptions." +msgstr "" +"Utilisez la commande %s ALL pour lister toutes les commandes et leur " +"description." + +#: modules/commands/bs_info.cpp:59 +msgid "Used on" +msgstr "Utilisé sur" + +#: data/chanserv.example.conf:821 +msgid "Used to manage channels" +msgstr "Permet de gérer les canaux" + +#: data/chanserv.example.conf:809 +msgid "Used to manage the list of privileged users" +msgstr "Permet de modifier la liste des utilisateurs privilégiés" + +#: data/chanserv.example.conf:815 +msgid "Used to modify the channel status of you or other users" +msgstr "" +"Permet de modifier votre statut sur le canal ou celui des autres utilisateurs" + +#: modules/commands/cs_akick.cpp:575 +msgid "User has been banned from the channel" +msgstr "L'utilisateur a été banni du canal." + +#: modules/commands/os_dns.cpp:587 +#, c-format +msgid "User limit for %s removed." +msgstr "Limite d'utilisateurs pour %s supprimée." + +#: modules/commands/os_dns.cpp:585 +#, c-format +msgid "User limit for %s set to %d." +msgstr "Limite d'utilisateurs pour %s fixée à %d utilisateurs." + +#: modules/commands/os_list.cpp:43 +msgid "Users" +msgstr "Utilisateurs" + +#: modules/commands/os_stats.cpp:172 +#, c-format +msgid "Users (nick): %lu entries, %lu buckets, longest chain is %d" +msgstr "" +"Utilisateurs (pseudos) : %lu entrées, %lu paniers, plus longue chaîne : %d" + +#: modules/commands/os_stats.cpp:177 +#, c-format +msgid "Users (uid): %lu entries, %lu buckets, longest chain is %d" +msgstr "Utilisateurs (uid) : %lu entrées, %lu paniers, plus longue chaîne : %d" + +#: modules/commands/os_list.cpp:184 +msgid "Users list:" +msgstr "Liste des utilisateurs :" + +#: modules/commands/ns_info.cpp:105 modules/commands/ns_info.cpp:107 +msgid "VHost" +msgstr "VHost" + +#: modules/commands/hs_set.cpp:92 +#, c-format +msgid "VHost for %s set to %s." +msgstr "Le vhost pour %s fixé à %s." + +#: modules/commands/hs_set.cpp:90 +#, c-format +msgid "VHost for %s set to %s@%s." +msgstr "Le vhost pour %s fixé à %s@%s." + +#: modules/commands/hs_set.cpp:199 +#, c-format +msgid "VHost for group %s set to %s." +msgstr "Le vhost pour le groupe %s fixé à %s." + +#: modules/commands/hs_set.cpp:197 +#, c-format +msgid "VHost for group %s set to %s@%s." +msgstr "Le vhost pour le groupe %s fixé à %s@%s." + +#: modules/commands/os_session.cpp:247 +msgid "VIEW host" +msgstr "VIEW host" + +#: modules/commands/os_sxline.cpp:428 modules/commands/os_sxline.cpp:662 +#: modules/commands/os_akill.cpp:389 +msgid "VIEW [mask | list | id]" +msgstr "VIEW [masque | liste | id]" + +#: modules/commands/os_session.cpp:526 +msgid "VIEW [mask | list]" +msgstr "VIEW [masque | liste]" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +msgid "Value" +msgstr "Valeur" + +#: modules/commands/os_config.cpp:48 +#, c-format +msgid "Value of %s:%s changed to %s" +msgstr "Valeur de %s:%s changée en %s" + +#: modules/commands/hs_list.cpp:58 modules/commands/hs_request.cpp:305 +msgid "Vhost" +msgstr "Vhost" + +#: modules/commands/hs_del.cpp:38 +#, c-format +msgid "Vhost for %s removed." +msgstr "Le vhost pour %s a été supprimé." + +#: modules/commands/os_oper.cpp:69 +msgid "View and change Services Operators" +msgstr "Affiche et modifie les Opérateurs des Services" + +#: modules/commands/os_config.cpp:19 +msgid "View and change configuration file settings" +msgstr "Voir et modifier les paramètres de configuration" + +#: modules/commands/os_session.cpp:245 +msgid "View the list of host sessions" +msgstr "Affiche la liste des sessions par hôte" + +#: modules/commands/bs_kick.cpp:1221 +msgid "Voices protection" +msgstr "Protection des voices" + +#: modules/commands/bs_kick.cpp:1406 +msgid "Watch your language!" +msgstr "Surveillez votre langage !" + +#: modules/commands/cs_list.cpp:237 +#, c-format +msgid "" +"When private is set, the channel will not appear in\n" +"%s's %s command." +msgstr "" +"Lorsque PRIVATE est défini, le canal n'apparaîtra plus\n" +"dans la commande %s de %s." + +#: modules/commands/ms_info.cpp:204 +msgid "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." +msgstr "" +"Sans paramètre, affiche les informations sur le nombre\n" +"de mémos que vous avez, combien sont non lus, et combien\n" +"de mémos vous pouvez recevoir au total.\n" +" \n" +"Si un nom de canal est indiqué, affiche les mêmes informations\n" +"pour le canal.\n" +" \n" +"Si un pseudo est indiqué, affiche les mêmes informations pour \n" +"le pseudo donné. Ceci est restreint aux Opérateurs des Services." + +#: modules/commands/ns_logout.cpp:66 +msgid "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." +msgstr "" +"Sans paramètre, inverse l'effet de la commande IDENTIFY,\n" +"c'est-à-dire qu'elle fait en sorte que vous ne soyez plus\n" +"reconnu en tant que propriétaire réel du pseudo. Notez\n" +"cependant que l'on ne vous demandera pas de vous réidentifier.\n" +" \n" +"Avec un paramètre, fait la même chose avec le pseudo donné. Si\n" +"vous spécifiez également REVALIDATE, les Services demanderont\n" +"au pseudo donné de se ré-identifier. Cette utilisation est \n" +"réservée aux Opérateurs des Services." + +#: modules/commands/os_stats.cpp:236 +msgid "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." +msgstr "" +"Sans option, affiche le nombre d'utilisateurs actuellement en ligne,\n" +"le plus grand nombre d'utilisateurs connectés depuis que les\n" +"Services ont été démarrés, et la période pendant laquelle les services\n" +"sont en état de marche.\n" +" \n" +"Avec l'option AKILL, affiche la taille actuelle de la liste\n" +"d'AKILL et le temps d'échéance par défaut.\n" +" \n" +"L'option RESET réinitialise le nombre maximum d'utilisateurs\n" +"au nombre courant d'utilisateurs sur le réseau.\n" +" \n" +"L'option UPLINK affiche les informations sur le serveur qui est\n" +"utilisé pour linker Anope au réseau.\n" +" \n" +"L'option HASH affiche des informations sur les hashmaps (la mémoire). \n" +" \n" +"L'option ALL affiche toutes les statistiques citées." + +#: modules/commands/bs_badwords.cpp:194 +msgid "Word" +msgstr "Mot" + +#: modules/commands/ns_group.cpp:158 +#, c-format +msgid "You are already a member of the group of %s." +msgstr "Vous êtes déjà membre du groupe de %s." + +#: modules/commands/os_login.cpp:34 modules/commands/ns_identify.cpp:87 +msgid "You are already identified." +msgstr "Vous êtes déjà identifié." + +#: modules/commands/cs_invite.cpp:64 +#, c-format +msgid "You are already in %s!" +msgstr "Vous êtes déjà sur %s ! " + +#: modules/commands/os_set.cpp:91 +msgid "You are no longer a super admin." +msgstr "Vous n'êtes plus super-administrateur." + +#: modules/commands/os_login.cpp:81 +msgid "You are not identified." +msgstr "Vous n'êtes pas identifié." + +#: include/language.h:100 +msgid "You are not permitted to be on this channel." +msgstr "Vous n'êtes pas autorisé à être sur ce canal." + +#: modules/commands/ms_set.cpp:158 +msgid "You are not permitted to change your memo limit." +msgstr "Vous n'êtes pas autorisé à changer votre limite de mémos." + +#: modules/commands/ns_cert.cpp:183 +msgid "You are not using a client certificate." +msgstr "Vous n'utilisez pas de certificat client." + +#: modules/commands/os_set.cpp:85 +msgid "You are now a super admin." +msgstr "Vous êtes maintenant super-administrateur." + +#: modules/commands/os_oline.cpp:36 +msgid "You are now an IRC Operator." +msgstr "Vous êtes maintenant un Opérateur IRC." + +#: modules/commands/ns_resetpass.cpp:108 +msgid "You are now identified for your nick. Change your password now." +msgstr "" +"Vous êtes désormais identifié pour votre pseudo. Vous pouvez changer de mot " +"de passe maintenant." + +#: modules/commands/ns_group.cpp:64 +#, c-format +msgid "You are now in the group of %s." +msgstr "Vous êtes maintenant dans le groupe de %s." + +#: modules/pseudoclients/memoserv.cpp:147 +#, c-format +msgid "" +"You are over your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Vous avez dépassé votre nombre maximum de mémos (%d). Vous ne pourrez plus " +"recevoir de nouveaux mémos sauf si vous supprimez quelques-uns de vos mémos " +"actuels. " + +#: modules/commands/os_noop.cpp:33 +msgid "You can not NOOP Services." +msgstr "Vous ne pouvez pas NOOP les Services." + +#: modules/commands/cs_access.cpp:672 +msgid "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." +msgstr "" +"Vous ne pouvez pas désactiver les privilèges de fondateur puisqu'il serait " +"impossible de les réactiver plus tard." + +#: modules/commands/os_jupe.cpp:34 +msgid "You can not jupe an already juped server." +msgstr "Vous ne pouvez pas jupe un serveur déjà jupé." + +#: modules/commands/os_jupe.cpp:32 +msgid "You can not jupe your Services' pseudoserver or your uplink server." +msgstr "" +"Vous ne pouvez pas jupe le pseudo-serveur des Services ou le serveur auquel " +"sont connectés les Services." + +#: modules/commands/os_module.cpp:80 +#, c-format +msgid "You can not reload this module directly, instead reload %s." +msgstr "" +"Vous ne pouvez pas recharger ce module directement, rechargez %s à la place." + +#: modules/commands/ms_rsend.cpp:46 +msgid "You can not request a receipt when sending a memo to yourself." +msgstr "" +"Vous ne pouvez pas recevoir d'accusé de réception quand vous vous\n" +"êtes envoyé un message à vous-même." + +#: modules/commands/ns_recover.cpp:163 +#, c-format +msgid "You can't %s yourself!" +msgstr "Vous ne pouvez pas utiliser %s sur vous-même !" + +#: modules/commands/cs_access.cpp:154 modules/commands/cs_flags.cpp:109 +#: modules/commands/cs_xop.cpp:151 +msgid "You can't add a channel to its own access list." +msgstr "Vous ne pouvez pas ajouter un canal dans sa propre liste d'accès." + +#: modules/commands/ns_logout.cpp:37 +#, c-format +msgid "You can't logout %s, they are a Services Operator." +msgstr "Vous ne pouvez pas déconnecter %s, car il est Opérateur des Services." + +#: modules/commands/ns_set.cpp:927 +#, c-format +msgid "You cannot %s on this network." +msgstr "Vous ne pouvez pas utiliser %s sur ce réseau." + +#: modules/commands/cs_flags.cpp:231 +#, c-format +msgid "You cannot set the %c flag." +msgstr "Vous ne pouvez pas définir le flag %c." + +#: modules/commands/ms_set.cpp:173 +#, c-format +msgid "You cannot set the memo limit for %s higher than %d." +msgstr "Vous ne pouvez mettre la limite de mémos de %s à plus de %d." + +#: modules/commands/ms_set.cpp:175 +#, c-format +msgid "You cannot set your memo limit higher than %d." +msgstr "Vous ne pouvez mettre votre limite de mémos à plus de %d." + +#: modules/commands/bs_assign.cpp:124 +msgid "You cannot unassign bots while persist is set on the channel." +msgstr "" +"Vous ne pouvez pas assigner de bot lorsque persist est actif pour ce canal." + +#: modules/commands/ns_set.cpp:480 +msgid "You cannot unset the e-mail on this network." +msgstr "Vous ne pouvez pas effacer votre email sur ce réseau." + +#: modules/commands/help.cpp:177 +msgid "You cannot use this command." +msgstr "Vous ne pouvez pas utiliser cette commande." + +#: modules/commands/ms_info.cpp:151 +#, c-format +msgid "You currently have %d memos, of which %d are unread." +msgstr "Vous avez actuellement %d mémos, dont %d n'ont pas été lus." + +#: modules/commands/ms_info.cpp:149 +#, c-format +msgid "You currently have %d memos, of which 1 is unread." +msgstr "Vous avez actuellement %d mémos, dont 1 n'a pas été lu." + +#: modules/commands/ms_info.cpp:147 +#, c-format +msgid "You currently have %d memos." +msgstr "Vous avez actuellement %d mémos." + +#: modules/commands/ms_info.cpp:145 +#, c-format +msgid "You currently have %d memos; all of them are unread." +msgstr "Vous avez actuellement %d mémos, dont aucun n'a été lu." + +#: modules/commands/ms_info.cpp:134 +msgid "You currently have 1 memo, and it has not yet been read." +msgstr "Vous avez actuellement 1 mémo, qui n'a pas encore été lu." + +#: modules/commands/ms_info.cpp:136 +msgid "You currently have 1 memo." +msgstr "Vous avez actuellement 1 mémo." + +#: modules/commands/ms_info.cpp:130 +msgid "You currently have no memos." +msgstr "Vous n'avez aucun mémo actuellement." + +#: modules/commands/cs_mode.cpp:564 modules/commands/cs_mode.cpp:621 +#, c-format +msgid "You do not have access to set mode %c." +msgstr "Vous n'avez pas les accès pour définir le mode %c." + +#: modules/commands/cs_mode.cpp:578 modules/commands/cs_mode.cpp:590 +#: modules/commands/cs_mode.cpp:631 +#, c-format +msgid "You do not have the access to change %s's modes." +msgstr "Vous n'avez pas les accès pour changer les modes de %s." + +#: modules/commands/cs_seen.cpp:198 +#, c-format +msgid "You found me, %s!" +msgstr "Vous m'avez trouvé, %s !" + +#: modules/pseudoclients/memoserv.cpp:143 +#, c-format +msgid "You have %d new memos." +msgstr "Vous avez %d nouveaux mémos." + +#: modules/pseudoclients/memoserv.cpp:143 +msgid "You have 1 new memo." +msgstr "Vous avez 1 nouveau mémo." + +#: include/language.h:112 +#, c-format +msgid "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." +msgstr "" +"Vous avez un nouveau mémo de %s,\n" +"Tapez %s%s READ %d pour le lire." + +#: modules/commands/cs_invite.cpp:76 +#, c-format +msgid "You have been invited to %s by %s." +msgstr "Vous avez été invité à rejoindre %s par %s." + +#: modules/commands/cs_invite.cpp:81 +#, c-format +msgid "You have been invited to %s." +msgstr "Vous avez été invité à rejoindre %s." + +#: modules/protocol/ratbox.cpp:166 modules/commands/ns_recover.cpp:96 +#, c-format +msgid "You have been logged in as %s." +msgstr "Vous vous êtes identifié en tant que %s." + +#: modules/commands/os_login.cpp:86 +msgid "You have been logged out." +msgstr "Vous n'êtes plus identifié." + +#: modules/commands/cs_unban.cpp:94 +#, c-format +msgid "You have been unbanned from %s." +msgstr "Vous avez été débanni de %s." + +#: modules/commands/cs_unban.cpp:54 +#, c-format +msgid "You have been unbanned from %d channels." +msgstr "Vous avez été débanni de %d canaux." + +#: modules/commands/ms_info.cpp:169 +msgid "You have no limit on the number of memos you may keep." +msgstr "" +"Vous n'avez aucune limite sur le nombre de mémos que vous pouvez garder." + +#: include/language.h:114 +msgid "You have no memos." +msgstr "Vous n'avez pas de mémo." + +#: include/language.h:117 +msgid "You have no new memos." +msgstr "Vous n'avez pas de nouveau mémo." + +#: modules/pseudoclients/memoserv.cpp:149 +#, c-format +msgid "" +"You have reached your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Vous avez atteint votre nombre maximum de mémos (%d). Vous ne pourrez plus " +"recevoir de nouveaux mémos sauf si vous supprimez quelques-uns de vos mémos " +"actuels. " + +#: modules/commands/ns_recover.cpp:117 +#, c-format +msgid "You have regained control of %s." +msgstr "Vous avez repris le contrôle de %s." + +#: modules/commands/ns_drop.cpp:66 +msgid "You may drop any nick within your group." +msgstr "Vous pouvez supprimer n'importe quel pseudo de votre groupe." + +#: modules/commands/cs_mode.cpp:322 modules/commands/cs_mode.cpp:414 +#, c-format +msgid "You may not (un)lock mode %c." +msgstr "Vous ne pouvez pas (dé)verrouiller le mode %c." + +#: modules/commands/ns_set.cpp:485 +msgid "You may not change the e-mail of other Services Operators." +msgstr "" +"Vous ne pouvez pas changer l'adresse email d'autres Opérateurs des Services." + +#: modules/commands/ns_set.cpp:474 +msgid "You may not change the email of an unconfirmed account." +msgstr "Vous ne pouvez pas changer l'adresse email d'un compte non confirmé." + +#: modules/commands/ns_set.cpp:196 +msgid "You may not change the password of other Services Operators." +msgstr "" +"Vous ne pouvez pas changer le mot de passe d'autres Opérateurs des Services." + +#: modules/commands/ns_drop.cpp:45 +msgid "You may not drop other Services Operators' nicknames." +msgstr "" +"Vous ne pouvez pas supprimer le pseudo d'autres Opérateurs des Services." + +#: modules/commands/ns_getpass.cpp:32 +msgid "You may not get the password of other Services Operators." +msgstr "" +"Vous ne pouvez pas obtenir le mot de passe d'autres Opérateurs des Services." + +#: modules/commands/ns_suspend.cpp:100 +msgid "You may not suspend other Services Operators' nicknames." +msgstr "" +"Vous ne pouvez pas suspendre le pseudo d'autres Opérateurs des Services." + +#: modules/commands/ns_access.cpp:136 +msgid "" +"You may view but not modify the access list of other Services Operators." +msgstr "" +"Vous pouvez voir mais pas modifier la liste d'accès d'autres Opérateurs des " +"Services." + +#: modules/commands/ns_cert.cpp:292 +msgid "" +"You may view but not modify the certificate list of other Services Operators." +msgstr "" +"Vous pouvez voir mais pas modifier la liste de certificats d'autres " +"Opérateurs des Services." + +#: modules/commands/cs_seen.cpp:287 +#, c-format +msgid "You might see yourself in the mirror, %s." +msgstr "Vous pouvez vous voir vous-même dans le miroir, %s." + +#: include/language.h:120 +msgid "You must assign a bot to the channel before using this command." +msgstr "Vous devez assigner un bot au canal avant d'utiliser cette commande." + +#: modules/commands/cs_register.cpp:49 +msgid "You must be a channel operator to register the channel." +msgstr "Vous devez être un opérateur du canal pour l'enregistrer." + +#: modules/commands/cs_updown.cpp:94 modules/commands/cs_updown.cpp:192 +#, c-format +msgid "You must be in %s to use this command." +msgstr "Vous devez être sur %s pour utiliser cette commande." + +#: modules/commands/cs_register.cpp:37 +msgid "You must confirm your account before you can register a channel." +msgstr "" +"Vous devez confirmer votre compte avant de pouvoir enregistrer un canal." + +#: modules/commands/hs_request.cpp:100 +msgid "You must confirm your account before you may request a vhost." +msgstr "Vous devez confirmer votre compte avant de pouvoir demander un vhost." + +#: modules/commands/ms_send.cpp:44 +msgid "You must confirm your account before you may send a memo." +msgstr "Vous devez confirmer votre compte avant de pouvoir envoyer un mémo." + +#: modules/commands/cs_drop.cpp:42 +#, c-format +msgid "" +"You must enter the channel name twice as a confirmation that you wish to drop" +" %s." +msgstr "" +"Vous devez entrer le nom du canal deux fois pour confirmer que vous voulez " +"vraiment effacer %s." + +#: modules/commands/ns_register.cpp:153 +#, c-format +msgid "You must have been using this nick for at least %d seconds to register." +msgstr "" +"Vous devez rester connecté plus de %d secondes avant d'enregistrer votre " +"pseudo." + +#: modules/commands/cs_mode.cpp:913 +#, c-format +msgid "You must have the %s(ME) privilege on the channel to use this command." +msgstr "" +"Vous devez avoir le privilège %s(ME) sur le canal pour utiliser cette " +"commande." + +#: modules/pseudoclients/nickserv.cpp:358 +msgid "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." +msgstr "" +"Vous devez maintenant fournir un email pour votre pseudo.\n" +"Cet email vous permettra de retrouver votre mot de passe\n" +"au cas où vous le perdriez." + +#: modules/commands/help.cpp:172 +msgid "You need to be identified to use this command." +msgstr "Vous devez être identifié pour utiliser cette commande." + +#: modules/commands/ms_info.cpp:182 +msgid "You will be notified by message and by mail when new memos arrive." +msgstr "" +"Vous serez notifié par message et par email quand vous recevrez de nouveaux " +"mémos." + +#: modules/commands/ms_info.cpp:175 +msgid "" +"You will be notified of new memos at logon and when they arrive, and by mail " +"when they arrive." +msgstr "" +"Vous serez notifié par message et par email quand vous recevrez de nouveaux " +"mémos, et par message à votre connexion." + +#: modules/commands/ms_info.cpp:177 +msgid "You will be notified of new memos at logon and when they arrive." +msgstr "" +"Vous serez notifié pour les nouveaux mémos à la connexion et quand ils " +"arrivent." + +#: modules/commands/ms_info.cpp:189 +msgid "" +"You will be notified of new memos at logon, and by mail when they arrive." +msgstr "" +"Vous serez notifié par email quand vous recevrez de nouveaux mémos, et par " +"message à votre connexion." + +#: modules/commands/ms_info.cpp:191 +msgid "You will be notified of new memos at logon." +msgstr "Vous serez notifié pour les nouveaux mémos à la connexion." + +#: modules/commands/ms_info.cpp:184 +msgid "You will be notified when new memos arrive." +msgstr "Vous serez notifié quand de nouveaux mémos arrivent." + +#: modules/commands/ms_set.cpp:190 +msgid "You will no longer be able to receive memos." +msgstr "Vous ne pourrez désormais plus recevoir de mémos." + +#: modules/commands/ms_set.cpp:57 +msgid "You will no longer be informed via email." +msgstr "Vous ne serez plus averti par mail de l'arrivée de nouveau mémo." + +#: modules/commands/ms_info.cpp:195 +msgid "You will not be notified of new memos." +msgstr "Vous ne serez plus notifié pour les nouveaux mémos." + +#: modules/commands/ms_set.cpp:49 +msgid "You will now be informed about new memos via email." +msgstr "Vous serez maintenant averti par mail de l'arrivée de nouveaux mémos." + +#: modules/commands/os_svs.cpp:86 +msgid "Your IRCd does not support SVSJOIN." +msgstr "Votre IRCd ne supporte pas SVSJOIN." + +#: modules/commands/os_svs.cpp:31 +msgid "Your IRCd does not support SVSNICK." +msgstr "Votre IRCd ne supporte pas SVSNICK." + +#: modules/commands/os_svs.cpp:130 +msgid "Your IRCd does not support SVSPART." +msgstr "Votre IRCd ne supporte pas SVSPART." + +#: include/language.h:127 +msgid "" +"Your IRCd does not support vIdent's, if this is incorrect, please report " +"this as a possible bug" +msgstr "" +"Votre IRCd ne supporte pas les vIdent. Si ceci est incorrect, merci de le " +"reporter, il s'agit peut être d'un bug." + +#: modules/extra/m_ldap_authentication.cpp:110 +#: modules/extra/m_sql_authentication.cpp:55 +#, c-format +msgid "Your account %s has been successfully created." +msgstr "Votre compte %s a été créé avec succès." + +#: modules/commands/ns_register.cpp:328 +msgid "Your account is already confirmed." +msgstr "Votre compte est déjà confirmé." + +#: modules/commands/ns_register.cpp:396 +#, c-format +msgid "Your account will expire, if not confirmed, in %s." +msgstr "En cas de non confirmation, votre compte expirera dans %s." + +#: modules/commands/ns_set.cpp:1274 +#, c-format +msgid "Your email address has been changed to %s." +msgstr "Votre adresse email a été changée en %s." + +#: modules/commands/os_forbid.cpp:544 modules/commands/os_forbid.cpp:553 +msgid "Your email address is not allowed, choose a different one." +msgstr "Votre adresse email n'est pas autorisée, merci d'en choisir une autre." + +#: modules/commands/ns_register.cpp:260 modules/commands/ns_register.cpp:391 +msgid "" +"Your email address is not confirmed. To confirm it, follow the instructions " +"that were emailed to you." +msgstr "" +"Votre adresse email n'est pas confirmée. Pour la confirmer, suivez les " +"instructions qui vous ont été envoyées lors de votre enregistrement." + +#: modules/commands/ns_register.cpp:67 +#, c-format +msgid "Your email address of %s has been confirmed." +msgstr "Votre adresse email pour %s a été confirmée." + +#: modules/extra/m_ldap_authentication.cpp:159 +#, c-format +msgid "Your email has been updated to %s" +msgstr "Votre adresse email a été changée en %s." + +#: modules/extra/m_sql_authentication.cpp:62 +#, c-format +msgid "Your email has been updated to %s." +msgstr "Votre adresse email a été changée en %s." + +#: modules/commands/ms_set.cpp:197 +msgid "Your memo limit has been disabled." +msgstr "Votre limite de mémos a été désactivée." + +#: modules/commands/ms_set.cpp:183 +#, c-format +msgid "Your memo limit has been set to %d." +msgstr "Votre limite de mémos a été fixée à %d." + +#: modules/commands/ms_info.cpp:164 +#, c-format +msgid "Your memo limit is %d, and may not be changed." +msgstr "Votre limite de mémos est de %d, et ne peut être changée." + +#: modules/commands/ms_info.cpp:166 +#, c-format +msgid "Your memo limit is %d." +msgstr "Votre limite de mémos est de %d." + +#: modules/commands/ms_info.cpp:159 +msgid "Your memo limit is 0; you will not receive any new memos." +msgstr "Votre limite de mémos est de 0, vous ne recevrez aucun nouveau mémo." + +#: modules/commands/ms_info.cpp:157 +msgid "" +"Your memo limit is 0; you will not receive any new memos. You cannot change " +"this limit." +msgstr "" +"Votre limite de mémos est de 0, vous ne recevrez aucun nouveau mémo. Vous ne " +"pouvez pas changer cette limite." + +#: modules/commands/ns_logout.cpp:50 +msgid "Your nick has been logged out." +msgstr "Votre pseudo n'est plus identifié." + +#: modules/commands/ns_group.cpp:156 +msgid "Your nick is already registered." +msgstr "Votre pseudo est déjà enregistré." + +#: modules/commands/ns_group.cpp:246 +msgid "Your nick is not grouped to anything, you can't ungroup it." +msgstr "" +"Votre pseudo n'est pas groupé à quoi que ce soit, vous ne pouvez pas le " +"dégrouper." + +#: include/language.h:77 +msgid "Your nick isn't registered." +msgstr "Votre pseudo n'est pas enregistré." + +#: modules/pseudoclients/nickserv.cpp:254 +#, c-format +msgid "Your nickname is now being changed to %s" +msgstr "Votre pseudo est maintenant changé en %s." + +#: modules/commands/os_login.cpp:32 modules/commands/os_login.cpp:79 +msgid "Your oper block doesn't require logging in." +msgstr "Votre bloc oper ne nécessite pas de s'authentifier." + +#: modules/commands/ns_register.cpp:336 +#, c-format +msgid "Your passcode has been re-sent to %s." +msgstr "Votre mot-code a été renvoyé à %s." + +#: modules/commands/ns_register.cpp:232 +#, c-format +msgid "Your password is %s - remember this for later use." +msgstr "Votre mot de passe est %s - notez-le pour une utilisation ultérieure." + +#: include/language.h:76 +#, c-format +msgid "Your password is too long. It must not exceed %u characters." +msgstr "" +"Votre mot de passe est trop long. Il ne doit pas dépasser %u caractères." + +#: modules/commands/ns_resetpass.cpp:96 +msgid "Your password reset request has expired." +msgstr "Votre demande de réinitialisation de mot de passe a expiré." + +#: modules/commands/hs_request.cpp:170 +msgid "Your vHost has been requested." +msgstr "Votre demande de vHost a été enregistrée." + +#: modules/pseudoclients/hostserv.cpp:64 +#: modules/pseudoclients/hostserv.cpp:103 modules/commands/hs_on.cpp:37 +#, c-format +msgid "Your vhost of %s is now activated." +msgstr "Votre vhost %s est activé." + +#: modules/pseudoclients/hostserv.cpp:62 +#: modules/pseudoclients/hostserv.cpp:101 modules/commands/hs_on.cpp:35 +#, c-format +msgid "Your vhost of %s@%s is now activated." +msgstr "Votre vhost %s@%s est activé." + +#: modules/commands/hs_off.cpp:39 +msgid "Your vhost was removed and the normal cloaking restored." +msgstr "Votre vhost a été supprimé et le masquage normal a été restauré." + +#: modules/commands/os_dns.cpp:255 +msgid "Zone" +msgstr "Zone" + +#: modules/commands/os_dns.cpp:290 +#, c-format +msgid "Zone %s already exists." +msgstr "La zone %s existe déjà." + +#: modules/commands/os_dns.cpp:310 modules/commands/os_dns.cpp:352 +#: modules/commands/os_dns.cpp:402 modules/commands/os_dns.cpp:438 +#, c-format +msgid "Zone %s does not exist." +msgstr "La zone %s n'existe pas." + +#: modules/commands/os_dns.cpp:332 +#, c-format +msgid "Zone %s removed." +msgstr "Zone %s supprimée." + +#: modules/commands/os_defcon.cpp:177 +msgid "[1|2|3|4|5]" +msgstr "[1|2|3|4|5]" + +#: modules/commands/os_news.cpp:400 +#, c-format +msgid "[Logon News - %s] %s" +msgstr "[News - %s] %s" + +#: modules/commands/os_news.cpp:402 +#, c-format +msgid "[Oper News - %s] %s" +msgstr "[News d'Oper - %s] %s" + +#: modules/commands/os_news.cpp:404 +#, c-format +msgid "[Random News - %s] %s" +msgstr "[News Aléatoire - %s] %s" + +#: modules/commands/ns_identify.cpp:66 +msgid "[account] password" +msgstr "[compte] mot-de-passe" + +#: modules/commands/cs_updown.cpp:49 modules/commands/cs_updown.cpp:147 +msgid "[channel [nick]]" +msgstr "[canal [pseudo]]" + +#: modules/commands/ms_ignore.cpp:20 +msgid "[channel] ADD entry" +msgstr "[canal] ADD entrée" + +#: modules/commands/ms_ignore.cpp:21 +msgid "[channel] DEL entry" +msgstr "[canal] DEL entrée" + +#: modules/commands/ms_ignore.cpp:22 +msgid "[channel] LIST" +msgstr "[canal] LIST" + +#: modules/commands/ms_list.cpp:20 +msgid "[channel] [list | NEW]" +msgstr "[canal] [liste | NEW]" + +#: modules/extra/stats/cs_fantasy_stats.cpp:40 +msgid "[channel] [nick]" +msgstr "[canal] [pseudo]" + +#: modules/commands/ms_del.cpp:45 +msgid "[channel] {num | list | LAST | ALL}" +msgstr "[canal] {num | liste | LAST | ALL}" + +#: modules/commands/ms_read.cpp:113 +msgid "[channel] {num | list | LAST | NEW | ALL}" +msgstr "[canal] {num | liste | LAST | NEW | ALL}" + +#: modules/commands/hs_list.cpp:20 +msgid "[key|#X-Y]" +msgstr "[clé|#X-Y]" + +#: modules/commands/ms_info.cpp:20 +msgid "[nick | channel]" +msgstr "{pseudo | canal}" + +#: modules/commands/ns_group.cpp:237 +msgid "[nick]" +msgstr "[pseudo]" + +#: modules/commands/ns_logout.cpp:22 +msgid "[nickname [REVALIDATE]]" +msgstr "[pseudo [REVALIDATE]]" + +#: modules/commands/ns_alist.cpp:25 modules/commands/ns_status.cpp:20 +#: modules/commands/ns_info.cpp:20 +msgid "[nickname]" +msgstr "[pseudo]" + +#: modules/commands/ns_set_misc.cpp:96 +msgid "[parameter]" +msgstr "[paramètre]" + +#: modules/commands/os_logsearch.cpp:33 +msgid "[+daysd] [+limitl] pattern" +msgstr "[+joursd] [+limitel] modèle" + +#: modules/commands/os_chankill.cpp:22 +msgid "[+expiry] channel reason" +msgstr "[+expiration] canal raison" + +#: modules/commands/ns_list.cpp:110 +msgid "[Hostname hidden]" +msgstr "[Nom d'hôte caché]" + +#: modules/commands/ns_list.cpp:112 modules/commands/cs_list.cpp:115 +msgid "[Suspended]" +msgstr "[Suspendu]" + +#: modules/commands/ns_list.cpp:114 +msgid "[Unconfirmed]" +msgstr "[Non confirmé]" + +#: modules/commands/hs_request.cpp:213 +msgid "[auto memo] Your requested vHost has been approved." +msgstr "[auto memo] Votre requête de vHost a été approuvée." + +#: modules/commands/hs_request.cpp:267 +msgid "[auto memo] Your requested vHost has been rejected." +msgstr "[auto memo] Votre requête de vHost a été rejetée." + +#: modules/commands/hs_request.cpp:265 +#, c-format +msgid "[auto memo] Your requested vHost has been rejected. Reason: %s" +msgstr "[auto memo] Votre requête de vHost a été rejetée. Raison : %s" + +#: modules/commands/hs_request.cpp:388 +#, c-format +msgid "[auto memo] vHost %s has been requested by %s." +msgstr "[auto memo] Le vHost %s a été demandé par %s." + +#: modules/commands/os_list.cpp:133 +msgid "[{pattern | channel} [INVISIBLE]]" +msgstr "[{modèle | canal} [INVISIBLE]]" + +#: modules/commands/os_list.cpp:20 +msgid "[{pattern | nick} [SECRET]]" +msgstr "[{modèle | pseudo} [SECRET]]" + +#: src/misc.cpp:337 +msgid "day" +msgstr "jour" + +#: src/misc.cpp:337 +msgid "days" +msgstr "jours" + +#: include/language.h:88 +msgid "does not expire" +msgstr "n'expire pas" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d day" +msgstr "expire dans %d jour" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d days" +msgstr "expire dans %d jours" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minute" +msgstr "expire dans %d heure, %d minute" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minutes" +msgstr "expire dans %d heure, %d minutes" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minute" +msgstr "expire dans %d heures, %d minute" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minutes" +msgstr "expire dans %d heures, %d minutes" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minute" +msgstr "expire dans %d minute" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minutes" +msgstr "expire dans %d minutes" + +#: src/misc.cpp:375 +msgid "expires momentarily" +msgstr "expire d'un instant à l'autre" + +#: src/misc.cpp:343 +msgid "hour" +msgstr "heure" + +#: src/misc.cpp:343 +msgid "hours" +msgstr "heures" + +#: modules/extra/stats/cs_fantasy_stats.cpp:150 +#, c-format +msgid "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "lettres : %s, mots : %s, lignes : %s, smileys : %s, actions : %s" + +#: src/misc.cpp:349 +msgid "minute" +msgstr "minute" + +#: src/misc.cpp:349 +msgid "minutes" +msgstr "minutes" + +#: modules/commands/bs_info.cpp:87 +msgid "not assigned yet" +msgstr "pas encore assigné" + +#: src/misc.cpp:324 +msgid "second" +msgstr "seconde" + +#: src/misc.cpp:324 +msgid "seconds" +msgstr "secondes" + +#: modules/commands/hs_request.cpp:215 +#, c-format +msgid "vHost for %s has been activated." +msgstr "Le vHost pour %s a été activé." + +#: modules/commands/hs_request.cpp:272 +#, c-format +msgid "vHost for %s has been rejected." +msgstr "Le vHost pour %s a été rejeté." + +#: modules/commands/hs_request.cpp:79 +msgid "vhost" +msgstr "vhost" + +#: modules/commands/hs_del.cpp:83 +#, c-format +msgid "vhosts for group %s have been removed." +msgstr "Le vhost pour le groupe %s a été supprimé." + +#: src/misc.cpp:331 +msgid "year" +msgstr "année" + +#: src/misc.cpp:331 +msgid "years" +msgstr "années" + +#: modules/commands/os_config.cpp:20 +msgid "{MODIFY|VIEW} [block name item name item value]" +msgstr "{MODIFY|VIEW} [nom bloc nom item item valeur]" + +#: modules/commands/bs_info.cpp:41 +msgid "{channel | nickname}" +msgstr "{canal | pseudo}" + +#: modules/commands/ms_cancel.cpp:20 +msgid "{nick | channel}" +msgstr "{pseudo | canal}" + +#: modules/commands/ms_rsend.cpp:25 modules/commands/ms_send.cpp:25 +msgid "{nick | channel} memo-text" +msgstr "{pseudo | canal} texte" diff --git a/language/anope.hu_HU.po b/language/anope.hu_HU.po new file mode 100644 index 0000000..90dba2d --- /dev/null +++ b/language/anope.hu_HU.po @@ -0,0 +1,11829 @@ +# Anope IRC Services language file +# Copyright (C) 2011 +# This file is distributed under the same license as the Anope IRC Services package. +# Adam , 2011. +# +msgid "" +msgstr "" +"Project-Id-Version: Anope\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2020-01-06 18:19+0100\n" +"PO-Revision-Date: 2010-09-19 20:37-0400\n" +"Last-Translator: Adam \n" +"Language-Team: Hungarian\n" +"Language: hu_HU\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" + +#: modules/commands/os_forbid.cpp:324 +#, c-format +msgid "%d channel(s) cleared, and %d channel(s) dropped." +msgstr "" + +#: modules/commands/os_forbid.cpp:265 +#, fuzzy, c-format +msgid "%d nickname(s) dropped." +msgstr "A nickneved dropolva lett," + +#: modules/commands/cs_xop.cpp:219 +#, fuzzy, c-format +msgid "%s added to %s %s list." +msgstr "%s hozzáadva az AKILL listához." + +#: modules/commands/cs_access.cpp:225 +#, c-format +msgid "%s added to %s access list at level %d." +msgstr "" +"%s hozzáadva a %s hozzáférési listájához.\n" +"A hozzáférési szintje a ChanServ parancsokhoz: %d." + +#: modules/commands/cs_access.cpp:223 +#, fuzzy, c-format +msgid "%s added to %s access list at privilege %s (level %d)" +msgstr "" +"%s hozzáadva a %s hozzáférési listájához.\n" +"A hozzáférési szintje a ChanServ parancsokhoz: %d." + +#: modules/commands/cs_akick.cpp:190 +#, c-format +msgid "%s added to %s autokick list." +msgstr "%s hozzáadva a (%s) csatorna autokick listájához" + +#: modules/commands/bs_badwords.cpp:307 +#, c-format +msgid "%s added to %s bad words list." +msgstr "A %s szó hozzáadva a %s tiltott szavak listájához." + +#: modules/commands/ns_access.cpp:45 +#, fuzzy, c-format +msgid "%s added to %s's access list." +msgstr "%s hozzáadva a hozzáférési listádhoz." + +#: modules/commands/ns_cert.cpp:204 +#, fuzzy, c-format +msgid "%s added to %s's certificate list." +msgstr "%s hozzáadva a hozzáférési listádhoz." + +#: modules/commands/ms_ignore.cpp:62 +#, fuzzy, c-format +msgid "%s added to ignore list." +msgstr "%s hozzáadva a hozzáférési listádhoz." + +#: modules/commands/os_sxline.cpp:415 modules/commands/os_sxline.cpp:649 +#, fuzzy, c-format +msgid "%s added to the %s list." +msgstr "%s hozzáadva az AKILL listához." + +#: modules/commands/os_akill.cpp:203 +#, c-format +msgid "%s added to the AKILL list." +msgstr "%s hozzáadva az AKILL listához." + +#: modules/pseudoclients/botserv.cpp:134 +#, c-format +msgid "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands " +"that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" +msgstr "" + +#: modules/pseudoclients/botserv.cpp:148 +#, fuzzy, c-format +msgid "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s lehetővé teszi, hogy botod legyen a csatornádon.\n" +"Ezt olyan felhasználók számára készítették, akik\n" +"nem tudnak saját botot futtatni, vagy a hálózaton nem\n" +"engedélyezik ezt. Az elérhető parancsok listája alább \n" +"található; használatukhoz írd be /msg %s parancs.\n" +"Bővebb információt így kaphatsz az adott parancsról:\n" +"/msg %s HELP parancs." + +#: modules/pseudoclients/nickserv.cpp:466 +#, fuzzy, c-format +msgid "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s lehetőséget nyújt a \"register\" parancs használatával\n" +"a nickneved regisztrálására, ezzel megelőzi, hogy más is\n" +"használhassa a nicked. A NickServ parancsokkal\n" +"írányítható. Az adott parancs szintaktikáját megkapod, ha\n" +"beírod, hogy: /msg %s parancs, lásd még a\n" +"/msg %s HELP parancs." + +#: modules/pseudoclients/nickserv.cpp:473 +#, fuzzy, c-format +msgid "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s lehetőséget nyújt a \"register\" parancs használatával\n" +"a nickneved regisztrálására, ezzel megelőzi, hogy más is\n" +"használhassa a nicked. A NickServ parancsokkal\n" +"írányítható. Az adott parancs szintaktikáját megkapod, ha\n" +"beírod, hogy: /msg %s parancs, lásd még a\n" +"/msg %s HELP parancs." + +#: modules/pseudoclients/chanserv.cpp:255 +#, fuzzy, c-format +msgid "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" +msgstr "" +"%s lehetőséget ad arra, hogy regisztráld a csatornádat.\n" +"%s használatával elkerülhető a \"take over\" jelenség,\n" +"amit az opjoggal visszaélő userek okozhatnak. Még pedig\n" +"úgy, hogy meghatározható az, hogy ki kapjon a csatornán\n" +"operátori kiváltságokat. A parancsok használatához írd be:\n" +"/msg %s parancs, ha több információ kell a paranccsal\n" +"kapcsolatban, akkor írd be: /msg %s HELP parancs.\n" +" " + +#: modules/commands/bs_badwords.cpp:298 +#, c-format +msgid "%s already exists in %s bad words list." +msgstr "A %s szót már tartalmazza a %s tiltott szavak listája" + +#: modules/commands/cs_akick.cpp:170 +#, c-format +msgid "%s already exists on %s autokick list." +msgstr "%s már szerepel a (%s) csatorna autokick listáján." + +#: modules/commands/os_session.cpp:361 +#, c-format +msgid "%s already exists on the EXCEPTION list." +msgstr "%s already exists on the EXCEPTION list." + +#: modules/commands/bs_kick.cpp:214 modules/commands/bs_kick.cpp:389 +#: modules/commands/bs_kick.cpp:520 modules/commands/bs_kick.cpp:651 +#, c-format +msgid "%s cannot be taken as times to ban." +msgstr "%s nem fogadható el banolási időnek." + +#: modules/commands/os_mode.cpp:163 +#, fuzzy, c-format +msgid "%s changed your usermodes to %s." +msgstr "%s váltóztatott a módodon." + +#: modules/commands/os_list.cpp:47 +#, fuzzy, c-format +msgid "%s channel list:" +msgstr "Vége a szoba listának." + +#: modules/commands/cs_xop.cpp:343 +#, fuzzy, c-format +msgid "%s deleted from %s %s list." +msgstr "%s törölve lett a %s AOP listáról." + +#: modules/commands/cs_access.cpp:326 +#, c-format +msgid "%s deleted from %s access list." +msgstr "%s törölve lett a (%s) csatorna hozzáférési listájáról." + +#: modules/commands/cs_akick.cpp:276 +#, c-format +msgid "%s deleted from %s autokick list." +msgstr "%s törölve a (%s) csatorna autokick listájáról." + +#: modules/commands/bs_badwords.cpp:348 +#, c-format +msgid "%s deleted from %s bad words list." +msgstr "A %s szó törölve %s tiltott szavak listájából." + +#: modules/commands/ns_access.cpp:72 +#, fuzzy, c-format +msgid "%s deleted from %s's access list." +msgstr "%s törölve lett a (%s) csatorna hozzáférési listájáról." + +#: modules/commands/ns_cert.cpp:233 +#, fuzzy, c-format +msgid "%s deleted from %s's certificate list." +msgstr "%s törölve a hozzáférési listádról." + +#: modules/commands/os_session.cpp:414 +#, c-format +msgid "%s deleted from session-limit exception list." +msgstr "%s törölve a session-korlát kivétel listáról." + +#: modules/commands/os_sxline.cpp:99 +#, fuzzy, c-format +msgid "%s deleted from the %s list." +msgstr "%s törölve lett a %s AOP listáról." + +#: modules/commands/os_akill.cpp:246 +#, c-format +msgid "%s deleted from the AKILL list." +msgstr "%s törölve az AKILL listáról." + +#: modules/commands/cs_access.cpp:685 +#, c-format +msgid "%s disabled on channel %s." +msgstr "%s letiltva a (%s) csatornán." + +#: modules/commands/cs_invite.cpp:75 +#, c-format +msgid "%s has been invited to %s." +msgstr "%s has been invited to %s." + +#: modules/commands/os_svs.cpp:104 +#, fuzzy, c-format +msgid "%s has been joined to %s." +msgstr "%s has been invited to %s." + +#: modules/commands/os_svs.cpp:152 +#, fuzzy, c-format +msgid "%s has been parted from %s." +msgstr "%s has been unbanned from %s." + +#: modules/commands/cs_unban.cpp:96 +#, c-format +msgid "%s has been unbanned from %s." +msgstr "%s has been unbanned from %s." + +#: modules/commands/ns_alist.cpp:110 +#, fuzzy, c-format +msgid "%s has no access in any channels." +msgstr "%s letiltva a (%s) csatornán." + +#: modules/commands/cs_status.cpp:55 +#, fuzzy, c-format +msgid "%s has no access on %s." +msgstr "%s has been invited to %s." + +#: modules/commands/cs_set.cpp:307 +#, c-format +msgid "%s has too many channels registered." +msgstr "%s részére túl sok csatorna van regisztrálva." + +#: modules/commands/cs_status.cpp:51 +#, fuzzy, c-format +msgid "%s is a super administrator." +msgstr "%s is a services operator of type %s." + +#: modules/pseudoclients/memoserv.cpp:214 +#, fuzzy, c-format +msgid "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" +msgstr "" +"%s lehetőséget nyújt az IRC felhasználókank, hogy rövid\n" +"üzeneteket küldjenek más IRC felhasználók részére,\n" +"akkor is, ha a fogadó fél nem online, és csatornákra (*).\n" +"Ahhoz, hogy üzenetet lehessen küldeni, mind a küldő és a\n" +"fogadó fél nicknevének regisztráltnak kell lennie.\n" +"\t\n" +"%s parancsok a következőket tartalmazzák:" + +#: modules/commands/cs_invite.cpp:66 +#, fuzzy, c-format +msgid "%s is already in %s!" +msgstr "You are already in %s! " + +#: modules/commands/os_svs.cpp:99 +#, fuzzy, c-format +msgid "%s is already in %s." +msgstr "You are already in %s! " + +#: modules/commands/ms_ignore.cpp:65 +#, fuzzy, c-format +msgid "%s is already on the ignore list." +msgstr "%s hozzáadva a hozzáférési listádhoz." + +#: modules/commands/cs_suspend.cpp:97 modules/commands/ns_suspend.cpp:106 +#, fuzzy, c-format +msgid "%s is already suspended." +msgstr "You are already in %s! " + +#: modules/commands/ms_rsend.cpp:56 modules/commands/ms_send.cpp:55 +#, fuzzy, c-format +msgid "%s is not a registered unforbidden nick or channel." +msgstr "%s nem érvényes bot vagy regisztrált szoba." + +#: modules/commands/cs_set.cpp:178 +#, c-format +msgid "%s is not a valid ban type." +msgstr "%s nem érvényes ban típus." + +#: modules/commands/bs_info.cpp:101 +#, c-format +msgid "%s is not a valid bot or registered channel." +msgstr "%s nem érvényes bot vagy regisztrált szoba." + +#: include/language.h:86 +#, fuzzy, c-format +msgid "%s is not a valid e-mail address." +msgstr "%s nem érvényes ban típus." + +#: include/language.h:80 +#, fuzzy, c-format +msgid "%s is not currently on channel %s." +msgstr "%s letiltva a (%s) csatornán." + +#: modules/commands/os_svs.cpp:144 +#, fuzzy, c-format +msgid "%s is not in %s." +msgstr "You are already in %s! " + +#: modules/commands/ms_ignore.cpp:77 +#, fuzzy, c-format +msgid "%s is not on the ignore list." +msgstr "%s nick nem található a mellőzöttek listáján." + +#: modules/commands/cs_status.cpp:90 +#, fuzzy, c-format +msgid "%s is on the auto kick list of %s (%s)." +msgstr "%s hozzáadva a (%s) csatorna autokick listájához" + +#: modules/commands/cs_status.cpp:53 +#, fuzzy, c-format +msgid "%s is the founder of %s." +msgstr "%s letiltva a (%s) csatornán." + +#: modules/commands/cs_status.cpp:78 +#, c-format +msgid "%s matches access entry %s (from entry %s), which has privilege %s." +msgstr "" + +#: modules/commands/cs_status.cpp:71 +#, c-format +msgid "%s matches access entry %s, which has privilege %s." +msgstr "" + +#: include/language.h:109 +#, c-format +msgid "" +"%s matches an except on %s and cannot be banned until the except has been " +"removed." +msgstr "" + +#: modules/commands/cs_status.cpp:96 +#, fuzzy, c-format +msgid "%s matches auto kick entry %s on %s (%s)." +msgstr "%s hozzáadva a (%s) csatorna autokick listájához" + +#: modules/commands/cs_xop.cpp:353 +#, fuzzy, c-format +msgid "%s not found on %s %s list." +msgstr "%s nem találatható a %s AOP listán." + +#: modules/commands/cs_access.cpp:338 modules/commands/cs_flags.cpp:255 +#, c-format +msgid "%s not found on %s access list." +msgstr "%s nem található a (%s) csatorna hozzáférési listáján." + +#: modules/commands/cs_akick.cpp:265 +#, c-format +msgid "%s not found on %s autokick list." +msgstr "%s nem szerepel a (%s) csatorna autokick listáján." + +#: modules/commands/bs_badwords.cpp:341 +#, c-format +msgid "%s not found on %s bad words list." +msgstr "A %s szó nem található a %s tiltott szavak listáján." + +#: modules/commands/ns_access.cpp:66 +#, fuzzy, c-format +msgid "%s not found on %s's access list." +msgstr "%s nem található a (%s) csatorna hozzáférési listáján." + +#: modules/commands/ns_cert.cpp:226 +#, fuzzy, c-format +msgid "%s not found on %s's certificate list." +msgstr "%s nem található a hozzáférési listádon." + +#: modules/commands/os_ignore.cpp:320 +#, fuzzy, c-format +msgid "%s not found on ignore list." +msgstr "%s nick nem található a mellőzöttek listáján." + +#: modules/commands/os_session.cpp:238 +#, c-format +msgid "" +"%s not found on session list, but has a limit of %d because it matches entry:" +" %s." +msgstr "" + +#: modules/commands/os_session.cpp:418 +#, c-format +msgid "%s not found on session-limit exception list." +msgstr "%s nem található a session-korlát kivétel listán." + +#: modules/commands/os_sxline.cpp:92 +#, fuzzy, c-format +msgid "%s not found on the %s list." +msgstr "%s nem találatható a %s AOP listán." + +#: modules/commands/os_akill.cpp:237 +#, c-format +msgid "%s not found on the AKILL list." +msgstr "%s nem található az AKILL listán." + +#: modules/commands/cs_flags.cpp:251 +#, fuzzy, c-format +msgid "%s removed from the %s access list." +msgstr "%s törölve lett a (%s) csatorna hozzáférési listájáról." + +#: modules/commands/ms_ignore.cpp:74 +#, fuzzy, c-format +msgid "%s removed from the ignore list." +msgstr "%s törölve a hozzáférési listádról." + +#: modules/commands/os_list.cpp:157 +#, fuzzy, c-format +msgid "%s users list:" +msgstr "Vége a felhasználó listának." + +#: modules/commands/os_ignore.cpp:316 +#, c-format +msgid "%s will no longer be ignored." +msgstr "%s nick most már nics mellőzve." + +#: modules/commands/os_ignore.cpp:238 +#, c-format +msgid "%s will now be ignored for %s." +msgstr "%s nick most mellőzte %s nicket." + +#: modules/commands/os_ignore.cpp:233 +#, c-format +msgid "%s will now permanently be ignored." +msgstr "%s nick most véglegesen mellőzve van." + +#: include/language.h:66 +#, fuzzy, c-format +msgid "%s%s HELP %s for more information." +msgstr "" +"Írd be: /msg %s HELP SET opció bővebb információért az\n" +"adott opcióról." + +#: modules/commands/bs_bot.cpp:270 +msgid "ADD nick user host real" +msgstr "" + +#: modules/commands/bs_bot.cpp:271 +#, fuzzy +msgid "CHANGE oldnick newnick [user [host [real]]]" +msgstr "" +"BOT ADD nick user hoszt valósnév\n" +"BOT CHANGE réginickújnick [user [hoszt [valósnév]]]\n" +"BOT DEL nick" + +#: modules/commands/bs_bot.cpp:272 +#, fuzzy +msgid "DEL nick" +msgstr "DEL ." + +#: modules/commands/os_session.cpp:560 +#, fuzzy +msgid "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." +msgstr "" +"Syntax: EXCEPTION ADD [+lejárat] maszkkorlátindok\n" +" EXCEPTION DEL {maszk| list}\n" +" EXCEPTION MOVE szám helyzet\n" +" EXCEPTION LIST [maszk | lista]\n" +" EXCEPTION VIEW [maszk | lista]\n" +"\n" +"Lehetőséget nyújt a szervíz adminnak, hogy karbantartsák\n" +"azon hostok listáját, amelyeknek korlátozásuk van,\n" +"engedélyezve bizonyos gépeket,úgymint a shell szervereket,\n" +"hogy egyidőben felvigyenek klienseket alapértelmezettnél\n" +"nagyobb számban. Amennyiben a gép eléri a korlátot, minden\n" +"csatlakozni próbáló kliens killelve lesz.Mielőtt a kill\n" +"megtörténne, figyelmeztetést kapnak %s /NOTICE üzeneten \n" +"keresztül. Az üzenet tartalma a konfigurációtól függ.\n" +"\n" +"EXCEPTION ADD hozzáadja a hostmaszkot a kivétellistához.\n" +"Vedd figyelembe, hogy a nick!user@host és user@host\n" +"maszkok érvénytelenek! Csak valós hostmaszkok, mint pl.\n" +"box.host.dom és *.host.dom, megengedettek, a session\n" +"korlátozásmaszkja nem vesz fel nicknevet/felhasználónevet.\n" +"A korlátlegyen egy nullával egyenlő vagy nagyobb szám.\n" +"Ez határozza meg, hogy hány sessiont vihet magával a host\n" +"egyidőben. A nulla azt jelenti, hogy a hostnak korlátlan\n" +"számú sessionja lehet. Lásd az AKILL helpet a részletek\n" +"felöl a formáról a szükséges lejárati parameterről.\n" +"EXCEPTION DEL Törli a megadott maszkot a kivétel litáról\t\n" +"EXCEPTION MOVE módisítja a kivétel poziciószámát. A \n" +"kivételek fel-le mozgatja, az üres helyekre is.\n" +"EXCEPTION LIST és EXCEPTION VIEW Mutatja az összes\n" +"aktuális kivételt; ha megadsz egy tetszőleges maszkot,\n" +"korlátozza azokat a kivételeket, melyekre ráillik a maszk.\n" +"A különbség a két parancs között az, hogy az\n" +"EXCEPTION VIEW sokkal részletesebb, megjeleníti a\n" +"kivételt felrakó nevét a session korlátot, indokot, \n" +"hostmaszkot és a lejárati időt,éa a kivétel legutolsó\n" +"\"használati\" idejét.\n" +"\n" +"Vedd figyelembe, a csatlakozó kliens a ráillő kivételek\n" +"közül mindig az elsőt használja. Hatalmas kivétellisták\n" +"és széleskörű kivételmaszkok csökkenthetik a Szervíz \n" +"teljesítményét.\n" +"\n" +"Korlátozva Szervíz adminnak." + +#: modules/commands/os_noop.cpp:68 +msgid "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." +msgstr "" + +#: modules/commands/cs_access.cpp:611 +#, c-format +msgid "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." +msgstr "" + +#: modules/commands/ms_read.cpp:35 +#, c-format +msgid "[auto-memo] The memo you sent to %s has been viewed." +msgstr "[auto-memo] A memo, amit %s számára küldtél meg lett tekintve." + +#: modules/commands/ns_group.cpp:92 +#, fuzzy +msgid "[target] [password]" +msgstr "GROUP célnick jelszó" + +#: modules/commands/ns_set.cpp:453 +msgid "address" +msgstr "" + +#: modules/commands/bs_set.cpp:162 +#, fuzzy +msgid "botname {ON|OFF}" +msgstr "SASET nickname AUTOOP {ON | OFF}" + +#: modules/extra/stats/cs_fantasy_top.cpp:39 +#: modules/extra/stats/cs_fantasy_top.cpp:51 +#: modules/commands/cs_suspend.cpp:152 modules/commands/cs_sync.cpp:20 +#: modules/commands/cs_log.cpp:106 modules/commands/bs_assign.cpp:91 +#: modules/commands/cs_info.cpp:20 modules/commands/cs_getkey.cpp:20 +#, fuzzy +msgid "channel" +msgstr "DROP #szoba" + +#: modules/commands/cs_set.cpp:138 +#, fuzzy +msgid "channel bantype" +msgstr "ACT #szoba szöveg" + +#: modules/commands/cs_drop.cpp:20 +#, fuzzy +msgid "channel channel" +msgstr "TOPIC #szoba [topic]" + +#: modules/commands/cs_log.cpp:107 +#, fuzzy +msgid "channel command method [status]" +msgstr "KICK #szoba opció {ON|OFF} [beállítások]" + +#: modules/commands/cs_kick.cpp:21 +#, fuzzy +msgid "channel mask [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_mode.cpp:20 +#, fuzzy +msgid "channel modes" +msgstr "MODE szoba mód" + +#: modules/commands/cs_set.cpp:267 modules/commands/bs_assign.cpp:20 +#, fuzzy +msgid "channel nick" +msgstr "UNBAN #szoba [nick]" + +#: modules/commands/cs_kick.cpp:20 +#, fuzzy +msgid "channel nick [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_clone.cpp:115 +#, fuzzy +msgid "channel target [what]" +msgstr "CLEAR #szoba mit?" + +#: modules/commands/bs_control.cpp:20 modules/commands/bs_control.cpp:80 +#, fuzzy +msgid "channel text" +msgstr "ACT #szoba szöveg" + +#: modules/commands/bs_set.cpp:91 +#, fuzzy +msgid "channel time" +msgstr "ACT #szoba szöveg" + +#: modules/commands/os_kick.cpp:20 +#, fuzzy +msgid "channel user reason" +msgstr "KICK #szoba user indok" + +#: modules/commands/cs_enforce.cpp:228 +#, fuzzy +msgid "channel what" +msgstr "TOPIC #szoba [topic]" + +#: modules/commands/cs_xop.cpp:481 +#, fuzzy +msgid "channel ADD mask" +msgstr "MODE szoba mód" + +#: modules/commands/cs_access.cpp:499 +msgid "channel ADD mask level" +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:194 +#, fuzzy +msgid "channel ADD message" +msgstr "MODE szoba mód" + +#: modules/commands/bs_badwords.cpp:371 +msgid "channel ADD word [SINGLE | START | END]" +msgstr "" + +#: modules/commands/cs_akick.cpp:435 +#, fuzzy +msgid "channel ADD {nick | mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_topic.cpp:151 +#, fuzzy +msgid "channel APPEND topic" +msgstr "TOPIC #szoba [topic]" + +#: modules/commands/cs_access.cpp:503 modules/commands/cs_flags.cpp:376 +#: modules/commands/cs_xop.cpp:484 modules/commands/cs_entrymsg.cpp:197 +#: modules/commands/bs_badwords.cpp:374 modules/commands/cs_akick.cpp:440 +#, fuzzy +msgid "channel CLEAR" +msgstr "DROP #szoba" + +#: modules/commands/cs_mode.cpp:736 +#, fuzzy +msgid "channel CLEAR [what]" +msgstr "TOPIC #szoba [topic]" + +#: modules/commands/os_mode.cpp:21 +#, fuzzy +msgid "channel CLEAR [ALL]" +msgstr "DROP #szoba" + +#: modules/commands/cs_entrymsg.cpp:195 +#, fuzzy +msgid "channel DEL num" +msgstr "MODE szoba mód" + +#: modules/commands/cs_access.cpp:500 modules/commands/cs_xop.cpp:482 +#, fuzzy +msgid "channel DEL {mask | entry-num | list}" +msgstr "DEL [#szoba] { szám | list | ALL}" + +#: modules/commands/cs_akick.cpp:436 +#, fuzzy +msgid "channel DEL {nick | mask | entry-num | list}" +msgstr "AOP #szoba { ADD | DEL | LIST | CLEAR } [ nick | sorszám ]" + +#: modules/commands/bs_badwords.cpp:372 +#, fuzzy +msgid "channel DEL {word | entry-num | list}" +msgstr "DEL [#szoba] { szám | list | ALL}" + +#: modules/commands/cs_akick.cpp:439 +msgid "channel ENFORCE" +msgstr "" + +#: modules/commands/cs_access.cpp:744 modules/commands/cs_entrymsg.cpp:196 +#, fuzzy +msgid "channel LIST" +msgstr "DROP #szoba" + +#: modules/commands/cs_akick.cpp:437 +#, fuzzy +msgid "channel LIST [mask | entry-num | list]" +msgstr "AOP #szoba { ADD | DEL | LIST | CLEAR } [ nick | sorszám ]" + +#: modules/commands/cs_access.cpp:501 modules/commands/cs_xop.cpp:483 +#: modules/commands/bs_badwords.cpp:373 +#, fuzzy +msgid "channel LIST [mask | list]" +msgstr "AOP #szoba { ADD | DEL | LIST | CLEAR } [ nick | sorszám ]" + +#: modules/commands/cs_flags.cpp:375 +msgid "channel LIST [mask | +flags]" +msgstr "" + +#: modules/commands/cs_mode.cpp:734 +#, fuzzy +msgid "channel LOCK {ADD|DEL|SET|LIST} [what]" +msgstr "AOP #szoba { ADD | DEL | LIST | CLEAR } [ nick | sorszám ]" + +#: modules/commands/cs_access.cpp:745 +#, fuzzy +msgid "channel RESET" +msgstr "SET szoba GREET {ON|OFF}" + +#: modules/commands/cs_mode.cpp:735 +#, fuzzy +msgid "channel SET modes" +msgstr "MODE szoba mód" + +#: modules/commands/cs_access.cpp:742 +msgid "channel SET type level" +msgstr "" + +#: modules/commands/cs_akick.cpp:438 +#, fuzzy +msgid "channel VIEW [mask | entry-num | list]" +msgstr "AOP #szoba { ADD | DEL | LIST | CLEAR } [ nick | sorszám ]" + +#: modules/commands/cs_access.cpp:502 +#, fuzzy +msgid "channel VIEW [mask | list]" +msgstr "DEL [#szoba] { szám | list | ALL}" + +#: modules/commands/cs_register.cpp:20 modules/commands/cs_set.cpp:205 +#, fuzzy +msgid "channel [description]" +msgstr "REGISTER #szoba leírás" + +#: modules/commands/cs_set.cpp:950 modules/commands/cs_invite.cpp:20 +#: modules/commands/cs_unban.cpp:20 +#, fuzzy +msgid "channel [nick]" +msgstr "UNBAN #szoba [nick]" + +#: modules/commands/cs_set_misc.cpp:96 +#, fuzzy +msgid "channel [parameters]" +msgstr "CLEAR #szoba mit?" + +#: modules/commands/cs_mode.cpp:807 modules/commands/cs_status.cpp:20 +#, fuzzy +msgid "channel [user]" +msgstr "UNBAN #szoba [nick]" + +#: modules/commands/cs_suspend.cpp:59 +#, fuzzy +msgid "channel [+expiry] [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_ban.cpp:40 +#, fuzzy +msgid "channel [+expiry] {nick | mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_flags.cpp:374 +#, fuzzy +msgid "channel [MODIFY] mask changes" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_topic.cpp:150 +#, fuzzy +msgid "channel [SET] [topic]" +msgstr "TOPIC #szoba [topic]" + +#: modules/commands/cs_topic.cpp:152 +#, fuzzy +msgid "channel [UNLOCK|LOCK]" +msgstr "DROP #szoba" + +#: modules/fantasy.cpp:20 modules/commands/greet.cpp:20 +#: modules/commands/bs_assign.cpp:154 +#, fuzzy +msgid "channel {ON|OFF}" +msgstr "SET #szoba XOP {ON | OFF}" + +#: modules/commands/bs_kick.cpp:491 +#, fuzzy +msgid "channel {ON|OFF} [ttb [ln [secs]]]" +msgstr "KICK #szoba opció {ON|OFF} [beállítások]" + +#: modules/commands/bs_kick.cpp:361 +#, fuzzy +msgid "channel {ON|OFF} [ttb [min [percent]]]" +msgstr "KICK #szoba opció {ON|OFF} [beállítások]" + +#: modules/commands/bs_kick.cpp:623 +#, fuzzy +msgid "channel {ON|OFF} [ttb [num]]" +msgstr "KICK #szoba opció {ON|OFF} [beállítások]" + +#: modules/commands/bs_kick.cpp:252 modules/commands/bs_kick.cpp:288 +#: modules/commands/bs_kick.cpp:327 modules/commands/bs_kick.cpp:457 +#: modules/commands/bs_kick.cpp:589 modules/commands/bs_kick.cpp:724 +#: modules/commands/bs_kick.cpp:758 +#, fuzzy +msgid "channel {ON|OFF} [ttb]" +msgstr "SET #szoba XOP {ON | OFF}" + +#: modules/commands/cs_access.cpp:743 +msgid "channel {DIS | DISABLE} type" +msgstr "" + +#: modules/commands/cs_set.cpp:873 +#, fuzzy +msgid "channel {ON | LEVEL | OFF}" +msgstr "SET #szoba SIGNKICK {ON | LEVEL | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:18 modules/commands/cs_set.cpp:75 +#: modules/commands/cs_set.cpp:336 modules/commands/cs_set.cpp:401 +#: modules/commands/cs_set.cpp:473 modules/commands/cs_set.cpp:622 +#: modules/commands/cs_set.cpp:684 modules/commands/cs_set.cpp:747 +#: modules/commands/cs_set.cpp:811 modules/commands/cs_set.cpp:1044 +#: modules/commands/bs_kick.cpp:792 modules/commands/bs_kick.cpp:857 +#: modules/commands/cs_topic.cpp:21 modules/commands/cs_list.cpp:181 +#, fuzzy +msgid "channel {ON | OFF}" +msgstr "SET #szoba XOP {ON | OFF}" + +#: modules/commands/ns_getemail.cpp:24 +msgid "email" +msgstr "" + +#: modules/commands/ns_set.cpp:794 +#, fuzzy +msgid "language" +msgstr "SET LANGUAGE szám" + +#: modules/commands/ms_sendall.cpp:25 modules/commands/ms_staff.cpp:25 +#, fuzzy +msgid "memo-text" +msgstr "STAFF memo-text" + +#: modules/commands/gl_global.cpp:22 modules/commands/greet.cpp:84 +#, fuzzy +msgid "message" +msgstr "GLOBAL üzenet" + +#: modules/commands/os_modinfo.cpp:20 modules/commands/os_module.cpp:20 +#: modules/commands/os_module.cpp:57 modules/commands/os_module.cpp:129 +msgid "modname" +msgstr "" + +#: modules/commands/ns_set.cpp:330 +msgid "new-display" +msgstr "" + +#: modules/commands/ns_set.cpp:120 +#, fuzzy +msgid "new-password" +msgstr "GROUP célnick jelszó" + +#: modules/extra/stats/cs_fantasy_stats.cpp:52 modules/commands/hs_del.cpp:20 +#: modules/commands/hs_del.cpp:60 modules/commands/ms_check.cpp:20 +#: modules/commands/hs_request.cpp:192 modules/commands/cs_seen.cpp:262 +#, fuzzy +msgid "nick" +msgstr "INFO nick" + +#: modules/commands/os_svs.cpp:79 +#, fuzzy +msgid "nick channel" +msgstr "CANCEL {nick | #szoba}" + +#: modules/commands/os_svs.cpp:123 +#, fuzzy +msgid "nick channel [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_oline.cpp:20 +#, fuzzy +msgid "nick flags" +msgstr "OLINE nick flagek" + +#: modules/commands/hs_set.cpp:20 modules/commands/hs_set.cpp:126 +#, fuzzy +msgid "nick hostmask" +msgstr "SET  ." + +#: modules/commands/os_svs.cpp:20 +#, fuzzy +msgid "nick newnick" +msgstr "SVSNICK nick újnick " + +#: modules/commands/hs_request.cpp:241 +#, fuzzy +msgid "nick [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/ns_getpass.cpp:20 modules/commands/ns_drop.cpp:19 +#: modules/commands/ns_suspend.cpp:161 +#, fuzzy +msgid "nickname" +msgstr "CHECK nicknév " + +#: modules/commands/ns_set.cpp:546 +#, fuzzy +msgid "nickname address" +msgstr "FORBID nicknév indok" + +#: modules/commands/ns_resetpass.cpp:22 +#, fuzzy +msgid "nickname email" +msgstr "FORBID nicknév indok" + +#: modules/commands/ns_set.cpp:872 +#, fuzzy +msgid "nickname language" +msgstr "FORBID nicknév indok" + +#: modules/commands/greet.cpp:145 +#, fuzzy +msgid "nickname message" +msgstr "FORBID nicknév indok" + +#: modules/commands/ns_set.cpp:399 +#, fuzzy +msgid "nickname new-display" +msgstr "FORBID nicknév indok" + +#: modules/commands/ns_set.cpp:173 +#, fuzzy +msgid "nickname new-password" +msgstr "GHOST nicknév [jelszó]" + +#: modules/commands/ns_set_misc.cpp:170 +#, fuzzy +msgid "nickname [parameter]" +msgstr "GHOST nicknév [jelszó]" + +#: modules/commands/ns_recover.cpp:150 +#, fuzzy +msgid "nickname [password]" +msgstr "GHOST nicknév [jelszó]" + +#: modules/commands/ns_suspend.cpp:61 +#, fuzzy +msgid "nickname [+expiry] [reason]" +msgstr "FORBID nicknév indok" + +#: modules/commands/ns_info.cpp:239 +#, fuzzy +msgid "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +msgstr "SET HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:130 modules/commands/ns_set.cpp:302 +#: modules/commands/ns_set.cpp:631 modules/commands/ns_set.cpp:985 +#: modules/commands/ns_set.cpp:1076 modules/commands/ns_set.cpp:1105 +#: modules/commands/ns_list.cpp:252 +#, fuzzy +msgid "nickname {ON | OFF}" +msgstr "SASET nickname AUTOOP {ON | OFF}" + +#: modules/commands/ns_set.cpp:760 +#, fuzzy +msgid "nickname {ON | QUICK | IMMED | OFF}" +msgstr "SASET nickname KILL {ON | QUICK | IMMED | OFF}" + +#: modules/commands/bs_set.cpp:20 +#, fuzzy +msgid "option (channel | bot) settings" +msgstr "SET #szoba opció beállítások" + +#: modules/commands/cs_set.cpp:21 +#, fuzzy +msgid "option channel parameters" +msgstr "SEND {nick | #szoba} memo-szöveg" + +#: modules/commands/bs_kick.cpp:120 +#, fuzzy +msgid "option channel {ON|OFF} [settings]" +msgstr "KICK #szoba opció {ON|OFF} [beállítások]" + +#: modules/commands/ns_set.cpp:75 +msgid "option nickname parameters" +msgstr "" + +#: modules/commands/ms_set.cpp:207 modules/commands/ns_set.cpp:20 +#, fuzzy +msgid "option parameters" +msgstr "SET opció beállítás" + +#: modules/commands/os_set.cpp:170 +#, fuzzy +msgid "option setting" +msgstr "SET opció beállítás" + +#: modules/commands/ns_register.cpp:22 +#, fuzzy +msgid "passcode" +msgstr "REGISTER jelszó email" + +#: modules/commands/os_login.cpp:19 +#, fuzzy +msgid "password" +msgstr "GROUP célnick jelszó" + +#: modules/commands/ns_register.cpp:124 +#, fuzzy +msgid "password [email]" +msgstr "REGISTER jelszó email" + +#: modules/commands/ns_register.cpp:122 +#, fuzzy +msgid "password email" +msgstr "REGISTER jelszó email" + +#: modules/commands/cs_list.cpp:21 +#, fuzzy +msgid "pattern [SUSPENDED] [NOEXPIRE]" +msgstr "LIST pattern [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/ns_list.cpp:20 +#, fuzzy +msgid "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" +msgstr "LIST pattern [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/os_jupe.cpp:20 +#, fuzzy +msgid "server [reason]" +msgstr "JUPE szervernév [leírás]" + +#: modules/commands/os_mode.cpp:147 +#, fuzzy +msgid "user modes" +msgstr "MODE szoba mód" + +#: modules/commands/os_kill.cpp:20 +#, fuzzy +msgid "user [reason]" +msgstr "JUPE szervernév [leírás]" + +#: modules/commands/os_sxline.cpp:440 +#, fuzzy +msgid "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." +msgstr "" +"Syntax: AKILL ADD [ +lejárat] maszk indok\n" +" AKILL DEL {maszk | sor-szám | list}\n" +" AKILL LIST [maszk | list]\n" +" AKILL VIEW [maszk | list]\n" +" AKILL CLEAR\n" +"\n" +"Lehetőséget ad a szervíz opoknak, hogy karbantartsák az\n" +"AKILL listát. Ha egy felhasználó az AKILL maszkkal egyező\n" +"cimről próbál csatlakozni , akkor szervíz kiad egy KILL \n" +"parancsot a nickre, és a támogatott szervertípusokon arra\n" +"utasít minden szervert, hogy adjon K-linet a maszknak.\n" +"\n" +"AKILL ADD hozzáadja a megadott user@host/ip maszkot az\n" +"AKILL listára a megadott indokkal (amit meg kell adnod).\n" +"Az elévülést egész számmot kovet egy időparaméter d (nap),\n" +"h (óra), m (perc).Ezek kombinálása nem lehetséges(1h30m).\n" +"ha nem adsz meg időegységet akkor önmagában napot jelent.\n" +"(+30 az 30 napot jelent).Ha +0-át adsz meg akkor nem \n" +"elévülő lesz.Ha a usermaszk + -al kezdődik akkor elévülést\n" +"meg kell adni akkor is ha megegyezik az alapértelmezéssel.\n" +"Az AKILL jelenlegi alapértelmezett elévüólési ideje \n" +"megnézhető a STATS AKILL paranccsal.\n" +"AKILL DEL törli a maszkot az AKILL listáról, ha rajta\n" +"van. Ha bejegyzés sorszámot adsz meg akkor azok fognak\n" +"törlődni.(lásd a példát alább)\n" +"AKILL LIST kiirja a jelenlegi AKILL listát. Ha egy \n" +"\"*\" karakteres maszk van megadva, akkor csak azokat az\n" +"AKILL-eket listázza, amelyek ráillenek a megadott maszkra.\n" +"Ha sorszámot adsz meg akkor azok fognak törlődni. Példa:\n" +"\tAKILL LIST 2-5,7-9\n" +" Listázza az AKILL-en lévoket 2-től 5-ig és 7-től 9-ig\n" +" az AKILL listából\n" +"AKILL VIEW részletesebb verziója az AKILL LIST-nek,\n" +"amely megmutatja, hogy ki vette fel az AKILL-t,\tmikor lett\n" +"felvéve és mikor jár le, éppúgy, felhasználó@gazdanév \n" +"maszkot és indokot.\n" +"\t\n" +"AKILL CLEAR töröli az összes AKILL bejegyzést.\n" +"\n" +"Korlátozva Szervíz operatornak." + +#: modules/commands/os_sxline.cpp:678 +#, fuzzy +msgid "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Syntax: AKILL ADD [ +lejárat] maszk indok\n" +" AKILL DEL {maszk | sor-szám | list}\n" +" AKILL LIST [maszk | list]\n" +" AKILL VIEW [maszk | list]\n" +" AKILL CLEAR\n" +"\n" +"Lehetőséget ad a szervíz opoknak, hogy karbantartsák az\n" +"AKILL listát. Ha egy felhasználó az AKILL maszkkal egyező\n" +"cimről próbál csatlakozni , akkor szervíz kiad egy KILL \n" +"parancsot a nickre, és a támogatott szervertípusokon arra\n" +"utasít minden szervert, hogy adjon K-linet a maszknak.\n" +"\n" +"AKILL ADD hozzáadja a megadott user@host/ip maszkot az\n" +"AKILL listára a megadott indokkal (amit meg kell adnod).\n" +"Az elévülést egész számmot kovet egy időparaméter d (nap),\n" +"h (óra), m (perc).Ezek kombinálása nem lehetséges(1h30m).\n" +"ha nem adsz meg időegységet akkor önmagában napot jelent.\n" +"(+30 az 30 napot jelent).Ha +0-át adsz meg akkor nem \n" +"elévülő lesz.Ha a usermaszk + -al kezdődik akkor elévülést\n" +"meg kell adni akkor is ha megegyezik az alapértelmezéssel.\n" +"Az AKILL jelenlegi alapértelmezett elévüólési ideje \n" +"megnézhető a STATS AKILL paranccsal.\n" +"AKILL DEL törli a maszkot az AKILL listáról, ha rajta\n" +"van. Ha bejegyzés sorszámot adsz meg akkor azok fognak\n" +"törlődni.(lásd a példát alább)\n" +"AKILL LIST kiirja a jelenlegi AKILL listát. Ha egy \n" +"\"*\" karakteres maszk van megadva, akkor csak azokat az\n" +"AKILL-eket listázza, amelyek ráillenek a megadott maszkra.\n" +"Ha sorszámot adsz meg akkor azok fognak törlődni. Példa:\n" +"\tAKILL LIST 2-5,7-9\n" +" Listázza az AKILL-en lévoket 2-től 5-ig és 7-től 9-ig\n" +" az AKILL listából\n" +"AKILL VIEW részletesebb verziója az AKILL LIST-nek,\n" +"amely megmutatja, hogy ki vette fel az AKILL-t,\tmikor lett\n" +"felvéve és mikor jár le, éppúgy, felhasználó@gazdanév \n" +"maszkot és indokot.\n" +"\t\n" +"AKILL CLEAR töröli az összes AKILL bejegyzést.\n" +"\n" +"Korlátozva Szervíz operatornak." + +#: modules/pseudoclients/nickserv.cpp:492 +#, fuzzy, c-format +msgid "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." +msgstr "" +"Ha egy regisztrált nicknevet %d napig nem használnak, akkor\n" +"a regisztrációja elévül, a nicknevet bárki regisztrálhatja,\n" +"és használhatja." + +#: modules/pseudoclients/botserv.cpp:143 +#, fuzzy +msgid "" +" \n" +"Available commands are:" +msgstr "Nincs ezzel kapcsolatban segítség: %s." + +#: modules/pseudoclients/botserv.cpp:167 +#, c-format +msgid "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." +msgstr "" + +#: modules/fantasy.cpp:69 +#, fuzzy, c-format +msgid "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." +msgstr "" +"Syntax: SET #szoba FANTASY { ON|OFF }\n" +"\n" +"Engedélyezi vagy tiltja fantasy módot a csatornán.\n" +"Ha engedélyezve van, akkor a következő parancsok\n" +"használhatók a csatornán: !op, !deop, !voice, !devoice,\n" +"!kick, !kb, !unban, !seen (találd ki hogyan kell\n" +"használni őket; próbáld meg nick megadásával, a nélkül\n" +"is)\n" +"\n" +"Azoknak akik ezeket a parancsokat akarják használni\n" +"rendelkezniük KELL a szükség szinttel mind a FANTASIA\n" +"mind pedig az egyéb szintekkel, ami a parancshoz\n" +"szükséges. (például, az !op használatához, meg kell\n" +"legyen a megfelelő szintjük az OPDEOP parancsokhoz.)." + +#: modules/commands/greet.cpp:69 +#, fuzzy +msgid "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." +msgstr "" +"Syntax: SET #szoba GREET { ON|OFF }\n" +"\n" +"Engedélyezi vagy tiltja Köszöntő módot a csatornán.\n" +"Ha engedélyezve van, akkor a bot megjeleníti azoknak\n" +"a köszöntő üzenetét, akiknek a szintjük megfelelő ehhez." + +#: modules/commands/bs_kick.cpp:843 +#, fuzzy +msgid "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +"Syntax: SET #szoba DONTKICKOPS {ON|OFF}\n" +"\n" +"Engedélyezi vagy tiltja opok védelmét a csatornán.\n" +"Ha engedélyezve van, akkor az opokat nem fogja a bot\n" +"kirúgni, akkor se, ha nem egyeznek meg a NOKICK szinttel\n" +"\t" + +#: modules/commands/bs_kick.cpp:908 +#, fuzzy +msgid "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +"Syntax: SET #szoba DONTKICKVOICES { ON|OFF }\n" +"\n" +"Engedélyezi vagy tiltja hangadók védelmét a csatornán.\n" +"Ha engedélyezve van, akkor a hangadókat nem fogja a bot\n" +"kirúgni, akkor se, ha nem egyeznek meg a NOKICK szinttel" + +#: modules/pseudoclients/botserv.cpp:141 +#, c-format +msgid "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" +msgstr "" + +#: modules/commands/cs_register.cpp:105 +msgid "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." +msgstr "" + +#: modules/pseudoclients/chanserv.cpp:272 +#, fuzzy, c-format +msgid "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." +msgstr "" +"Megjegyzés: azok a csatornák, amelyeket nem használnak %d\n" +"napig, automatikusan elvesztik regisztrációjukat.\n" +"Automatikusan dropolásra kerülnek." + +#: modules/commands/cs_register.cpp:101 +#, c-format +msgid "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +msgstr "" + +#: modules/pseudoclients/nickserv.cpp:486 +#, fuzzy +msgid "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." +msgstr "" +"Szervíz adminok is droppolhatnak nickeket, akkor ha\n" +"beazonosíttotak a nicknevükre, és megnézhetik a nickek\n" +"hozzáférési listáját. (/msg %s ACCESS LIST nick)" + +#: modules/pseudoclients/chanserv.cpp:277 +#, fuzzy +msgid "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." +msgstr "" +" \n" +"Szervíz adminok tudják droppolni a csatornákat anélkül, \n" +"hogy a szoba jelszót használnának, és megnézhetika az\n" +"access, AKICK, és beállitási szint listát a csatornán." + +#: modules/commands/bs_set.cpp:147 +msgid "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." +msgstr "" + +#: modules/commands/cs_xop.cpp:542 +#, fuzzy, c-format +msgid "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." +msgstr "" +"Syntax: HOP #szoba ADD nick\n" +" HOP #szoba DEL { nick | sorszám | lista}\n" +" HOP #szoba LIST [ maszk | lista ]\n" +" HOP #szoba CLEAR\n" +"\n" +"Karbantartja az HOP (HALFOP) listát a csatornán. A HOP\n" +"listán szereplő userek automatikusan megkapják belépéskor\n" +"a féloperátor státuszt.\n" +"\n" +"HOP ADD paranccsal hozzáadhatsz egy nickenevet csatornád\n" +"HOP listájához.\n" +"\n" +"HOP DEL paranccsal eltávolíthatsz egy megadott nicknevet\n" +"a csatornád HOP listájáról. Ha sorszámokat intervallumban\n" +"adunk meg (lásd a listázásnál),akkor a megadott bejegyzések\n" +"kerülnek törlésre.\n" +"\n" +"Az HOP LIST parancs megadja az HOP listát. Ha nem vagy \n" +"kiváncsi a teljes listára akkor a listában szereplő HOP \n" +"sorszámát megadva is megtudhatjuk a nevét, megadhatunk \n" +"intervallumot is.\n" +"\n" +"Példák:\n" +"\n" +"\tHOP #szoba LIST 2-5,7-9\n" +"\tListázza az HOP-okat 2 és 5 között és\n" +"\t7-tol 9-ig.\n" +" \n" +"Az HOP CLEAR parancs kiüriti a szoba HOP listáját.\n" +"\n" +"Az HOP ADD és HOP DEL parancsokat csak AOP / magasabb\n" +"szinttel rendelkező userek használhatják,de az HOP CLEAR\n" +"parancsot csak a szoba foundere adhatja ki.\n" +"Habár, minden HOP listán szereplo user használhatja az\n" +"HOP LIST parancsot.\n" +"\n" +"Ezt a parancsot letilthatod a csatornádon, és helyette \n" +"használhatod az access lista rendszert. Nézd meg: /msg \n" +"%s HELP ACCESS bővebb információért az access listáról,\n" +"és írd be: /msg %s HELP SET XOP hogy megnézd, hogyan \n" +"tudsz váltani az xOP rendszerről access lista rendszerre." + +#: modules/commands/cs_akick.cpp:508 +#, c-format +msgid "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." +msgstr "" + +#: modules/commands/os_akill.cpp:448 +#, fuzzy +msgid "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." +msgstr "" +"Syntax: HOP #szoba ADD nick\n" +" HOP #szoba DEL { nick | sorszám | lista}\n" +" HOP #szoba LIST [ maszk | lista ]\n" +" HOP #szoba CLEAR\n" +"\n" +"Karbantartja az HOP (HALFOP) listát a csatornán. A HOP\n" +"listán szereplő userek automatikusan megkapják belépéskor\n" +"a féloperátor státuszt.\n" +"\n" +"HOP ADD paranccsal hozzáadhatsz egy nickenevet csatornád\n" +"HOP listájához.\n" +"\n" +"HOP DEL paranccsal eltávolíthatsz egy megadott nicknevet\n" +"a csatornád HOP listájáról. Ha sorszámokat intervallumban\n" +"adunk meg (lásd a listázásnál),akkor a megadott bejegyzések\n" +"kerülnek törlésre.\n" +"\n" +"Az HOP LIST parancs megadja az HOP listát. Ha nem vagy \n" +"kiváncsi a teljes listára akkor a listában szereplő HOP \n" +"sorszámát megadva is megtudhatjuk a nevét, megadhatunk \n" +"intervallumot is.\n" +"\n" +"Példák:\n" +"\n" +"\tHOP #szoba LIST 2-5,7-9\n" +"\tListázza az HOP-okat 2 és 5 között és\n" +"\t7-tol 9-ig.\n" +" \n" +"Az HOP CLEAR parancs kiüriti a szoba HOP listáját.\n" +"\n" +"Az HOP ADD és HOP DEL parancsokat csak AOP / magasabb\n" +"szinttel rendelkező userek használhatják,de az HOP CLEAR\n" +"parancsot csak a szoba foundere adhatja ki.\n" +"Habár, minden HOP listán szereplo user használhatja az\n" +"HOP LIST parancsot.\n" +"\n" +"Ezt a parancsot letilthatod a csatornádon, és helyette \n" +"használhatod az access lista rendszert. Nézd meg: /msg \n" +"%s HELP ACCESS bővebb információért az access listáról,\n" +"és írd be: /msg %s HELP SET XOP hogy megnézd, hogyan \n" +"tudsz váltani az xOP rendszerről access lista rendszerre." + +#: modules/commands/os_sxline.cpp:462 +#, fuzzy +msgid "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." +msgstr "" +"Syntax: HOP #szoba ADD nick\n" +" HOP #szoba DEL { nick | sorszám | lista}\n" +" HOP #szoba LIST [ maszk | lista ]\n" +" HOP #szoba CLEAR\n" +"\n" +"Karbantartja az HOP (HALFOP) listát a csatornán. A HOP\n" +"listán szereplő userek automatikusan megkapják belépéskor\n" +"a féloperátor státuszt.\n" +"\n" +"HOP ADD paranccsal hozzáadhatsz egy nickenevet csatornád\n" +"HOP listájához.\n" +"\n" +"HOP DEL paranccsal eltávolíthatsz egy megadott nicknevet\n" +"a csatornád HOP listájáról. Ha sorszámokat intervallumban\n" +"adunk meg (lásd a listázásnál),akkor a megadott bejegyzések\n" +"kerülnek törlésre.\n" +"\n" +"Az HOP LIST parancs megadja az HOP listát. Ha nem vagy \n" +"kiváncsi a teljes listára akkor a listában szereplő HOP \n" +"sorszámát megadva is megtudhatjuk a nevét, megadhatunk \n" +"intervallumot is.\n" +"\n" +"Példák:\n" +"\n" +"\tHOP #szoba LIST 2-5,7-9\n" +"\tListázza az HOP-okat 2 és 5 között és\n" +"\t7-tol 9-ig.\n" +" \n" +"Az HOP CLEAR parancs kiüriti a szoba HOP listáját.\n" +"\n" +"Az HOP ADD és HOP DEL parancsokat csak AOP / magasabb\n" +"szinttel rendelkező userek használhatják,de az HOP CLEAR\n" +"parancsot csak a szoba foundere adhatja ki.\n" +"Habár, minden HOP listán szereplo user használhatja az\n" +"HOP LIST parancsot.\n" +"\n" +"Ezt a parancsot letilthatod a csatornádon, és helyette \n" +"használhatod az access lista rendszert. Nézd meg: /msg \n" +"%s HELP ACCESS bővebb információért az access listáról,\n" +"és írd be: /msg %s HELP SET XOP hogy megnézd, hogyan \n" +"tudsz váltani az xOP rendszerről access lista rendszerre." + +#: modules/commands/os_sxline.cpp:697 +#, fuzzy +msgid "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." +msgstr "" +"Syntax: HOP #szoba ADD nick\n" +" HOP #szoba DEL { nick | sorszám | lista}\n" +" HOP #szoba LIST [ maszk | lista ]\n" +" HOP #szoba CLEAR\n" +"\n" +"Karbantartja az HOP (HALFOP) listát a csatornán. A HOP\n" +"listán szereplő userek automatikusan megkapják belépéskor\n" +"a féloperátor státuszt.\n" +"\n" +"HOP ADD paranccsal hozzáadhatsz egy nickenevet csatornád\n" +"HOP listájához.\n" +"\n" +"HOP DEL paranccsal eltávolíthatsz egy megadott nicknevet\n" +"a csatornád HOP listájáról. Ha sorszámokat intervallumban\n" +"adunk meg (lásd a listázásnál),akkor a megadott bejegyzések\n" +"kerülnek törlésre.\n" +"\n" +"Az HOP LIST parancs megadja az HOP listát. Ha nem vagy \n" +"kiváncsi a teljes listára akkor a listában szereplő HOP \n" +"sorszámát megadva is megtudhatjuk a nevét, megadhatunk \n" +"intervallumot is.\n" +"\n" +"Példák:\n" +"\n" +"\tHOP #szoba LIST 2-5,7-9\n" +"\tListázza az HOP-okat 2 és 5 között és\n" +"\t7-tol 9-ig.\n" +" \n" +"Az HOP CLEAR parancs kiüriti a szoba HOP listáját.\n" +"\n" +"Az HOP ADD és HOP DEL parancsokat csak AOP / magasabb\n" +"szinttel rendelkező userek használhatják,de az HOP CLEAR\n" +"parancsot csak a szoba foundere adhatja ki.\n" +"Habár, minden HOP listán szereplo user használhatja az\n" +"HOP LIST parancsot.\n" +"\n" +"Ezt a parancsot letilthatod a csatornádon, és helyette \n" +"használhatod az access lista rendszert. Nézd meg: /msg \n" +"%s HELP ACCESS bővebb információért az access listáról,\n" +"és írd be: /msg %s HELP SET XOP hogy megnézd, hogyan \n" +"tudsz váltani az xOP rendszerről access lista rendszerre." + +#: modules/commands/bs_assign.cpp:197 +#, fuzzy +msgid "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." +msgstr "" +"Syntax: SET #szoba NOBOT {ON|OFF}\n" +"\n" +"Ez az opció a botot szobához társíthatatlanná teszi.\n" +"Ha egy bot már társítva van egy csatornához\n" +"akkor törlödik onnan, ha ezt az opciót bekapcsolod.\n" +"\n" +"Korlátozva Szervíz adminoknak." + +#: modules/commands/bs_set.cpp:199 +#, fuzzy +msgid "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." +msgstr "" +"Syntax: SET bot-nick PRIVATE {ON|OFF}\n" +"\n" +"Ez az opció megelőzi, hogy az adott botot a csatornához\n" +"nem IRC operátor személyek társíthassák.\n" +"\n" +"Korlátozva Szervíz adminoknak." + +#: modules/pseudoclients/memoserv.cpp:227 +#, c-format +msgid "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." +msgstr "" + +#: modules/commands/os_oper.cpp:167 +#, c-format +msgid " %s is online using this oper block." +msgstr "" + +#: modules/commands/os_modinfo.cpp:55 +#, c-format +msgid " Command %s on %s is linked to %s" +msgstr "" + +#: modules/commands/os_modinfo.cpp:43 +#, fuzzy, c-format +msgid " Providing service: %s" +msgstr "Modul parancsai: /msg %s %s" + +#: modules/commands/os_oper.cpp:163 +msgid " This oper is configured in the configuration file." +msgstr "" + +#: modules/commands/os_modinfo.cpp:34 +#, c-format +msgid " Loaded at: %p" +msgstr "" + +#: modules/commands/cs_seen.cpp:303 +#, c-format +msgid " but %s mysteriously dematerialized." +msgstr "" + +#: src/messages.cpp:339 +#, c-format +msgid "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." +msgstr "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." + +#: modules/commands/os_jupe.cpp:19 +#, fuzzy +msgid "\"Jupiter\" a server" +msgstr " JUPE Létrehoz egy \"Jupiter\" álszervert." + +#: modules/commands/os_oper.cpp:161 +#, fuzzy, c-format +msgid "%-8s %s" +msgstr "%-20s %s@%s" + +#: modules/extra/stats/cs_fantasy_top.cpp:152 +#, c-format +msgid "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:359 +msgid "%b %d %H:%M:%S %Y %Z" +msgstr "" + +#: modules/commands/cs_log.cpp:205 +#, c-format +msgid "%c is an unknown status mode." +msgstr "" + +#: modules/commands/cs_mode.cpp:431 +#, fuzzy, c-format +msgid "%c%c is not locked on %s." +msgstr "%s nem kért értesítést az üzeneteiről." + +#: modules/commands/cs_mode.cpp:427 +#, fuzzy, c-format +msgid "%c%c%s has been unlocked from %s." +msgstr "Nick %s has been ungrouped from %s." + +#: modules/commands/cs_clone.cpp:56 +#, fuzzy, c-format +msgid "%d access entries from %s have been cloned to %s." +msgstr "Az összes user vhosztja a(z) %s csoportba %s lett" + +#: modules/commands/bs_botlist.cpp:56 +#, c-format +msgid "%d bots available." +msgstr "%d botok rendelkezésre állnak." + +#: modules/commands/os_modinfo.cpp:189 +#, fuzzy, c-format +msgid "%d modules loaded." +msgstr "%d Modul betöltve." + +#: modules/commands/ns_group.cpp:357 +#, fuzzy, c-format +msgid "%d nickname(s) in the group." +msgstr "%d nicknév van a csoportban." + +#: modules/commands/cs_seen.cpp:137 +#, c-format +msgid "%lu nicks are stored in the database, using %.2Lf kB of memory." +msgstr "" + +#: modules/commands/cs_xop.cpp:241 modules/commands/cs_xop.cpp:372 +#: modules/commands/cs_xop.cpp:450 +#, fuzzy, c-format +msgid "%s %s list is empty." +msgstr "%s AOP listája üres." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1181 +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1201 +#: modules/commands/bs_kick.cpp:1211 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban)" +msgstr "\tFélkövér betűkért kirúgás: %s (%d kirúgás után kitiltás)" + +#: modules/commands/bs_kick.cpp:1161 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; %d lines in %ds)" +msgstr "\tFloodért kirúgás: %s (%d kirúgás után kitiltás; %d sor %ds mp alatt)" + +#: modules/commands/bs_kick.cpp:1171 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; %d times)" +msgstr "\tIsmétlésért kirúgás: %s (%d kirúgás után kitiltás; %d időre)" + +#: modules/commands/bs_kick.cpp:1141 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; minimum %d/%d%%)" +msgstr "\tCaps Lockért kirúgás: %s (%d kirúgás után kitiltás; min. %d/%d%%)" + +#: modules/commands/bs_kick.cpp:1163 +#, fuzzy, c-format +msgid "%s (%d lines in %ds)" +msgstr " %s (expires in %s)" + +#: modules/commands/bs_kick.cpp:1173 +#, c-format +msgid "%s (%d times)" +msgstr "" + +#: modules/commands/cs_seen.cpp:358 +#, c-format +msgid "%s (%s) was kicked from %s (\"%s\") %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:355 +#, c-format +msgid "%s (%s) was kicked from a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:326 +#, c-format +msgid "%s (%s) was last seen changing nick from %s to %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:321 +#, c-format +msgid "%s (%s) was last seen changing nick to %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:310 +#, c-format +msgid "%s (%s) was last seen connecting %s ago (%s)%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:335 +#, c-format +msgid "%s (%s) was last seen joining %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:332 +#, c-format +msgid "%s (%s) was last seen joining a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:344 +#, c-format +msgid "%s (%s) was last seen parting %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:341 +#, c-format +msgid "%s (%s) was last seen parting a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:349 +#, c-format +msgid "%s (%s) was last seen quitting (%s) %s ago (%s)." +msgstr "" + +#: modules/commands/bs_kick.cpp:1143 +#, fuzzy, c-format +msgid "%s (minimum %d/%d%%)" +msgstr "\tCaps Lockért kirúgás: %s (minimum %d/%d%%)" + +#: modules/commands/cs_access.cpp:245 modules/commands/cs_access.cpp:349 +#: modules/commands/cs_access.cpp:454 modules/commands/cs_access.cpp:467 +#: modules/commands/cs_flags.cpp:295 +#, c-format +msgid "%s access list is empty." +msgstr "%s hozzáférési listája üres." + +#: modules/commands/ns_ajoin.cpp:184 +#, fuzzy, c-format +msgid "%s added to %s's auto join list." +msgstr "%s hozzáadva a (%s) csatorna autokick listájához" + +#: src/xline.cpp:389 +#, fuzzy, c-format +msgid "%s already exists." +msgstr "%s nevű bot már létezik." + +#: modules/commands/cs_akick.cpp:202 modules/commands/cs_akick.cpp:387 +#: modules/commands/cs_akick.cpp:400 +#, c-format +msgid "%s autokick list is empty." +msgstr "%s autokick listája üres." + +#: modules/commands/bs_badwords.cpp:198 modules/commands/bs_badwords.cpp:316 +#, c-format +msgid "%s bad words list is empty." +msgstr "%s tiltott szavak listája üres." + +#: modules/commands/cs_set.cpp:993 +#, fuzzy, c-format +msgid "%s cannot be the successor on channel %s as they are the founder." +msgstr "%s nem lehet a %s csatorna successora, mert ő a founder is." + +#: modules/pseudoclients/global.cpp:90 modules/pseudoclients/hostserv.cpp:78 +#: modules/pseudoclients/operserv.cpp:287 +#, c-format +msgid "%s commands:" +msgstr "%s parancsok:" + +#: include/language.h:69 +#, c-format +msgid "%s coverage is too wide; Please use a more specific mask." +msgstr "" + +#: modules/commands/ms_info.cpp:94 +#, c-format +msgid "%s currently has %d memos, of which %d are unread." +msgstr "%s számára %d üzenet érkezett, ebből %d olvasatlan." + +#: modules/commands/ms_info.cpp:92 +#, c-format +msgid "%s currently has %d memos, of which 1 is unread." +msgstr "%s számára %d üzenet érkezett, ebből 1 olvasatlan." + +#: modules/commands/ms_info.cpp:90 +#, c-format +msgid "%s currently has %d memos." +msgstr "%s számára %d üzenet érkezett." + +#: modules/commands/ms_info.cpp:88 +#, c-format +msgid "%s currently has %d memos; all of them are unread." +msgstr "%s számára %d üzenet érkezett, és mind olvasatlan." + +#: modules/commands/ms_info.cpp:77 +#, c-format +msgid "%s currently has 1 memo, and it has not yet been read." +msgstr "%s listáján van 1 olvasatlan üzenet." + +#: modules/commands/ms_info.cpp:79 +#, c-format +msgid "%s currently has 1 memo." +msgstr "%s listáján van 1 üzenet." + +#: modules/commands/ms_info.cpp:73 +#, c-format +msgid "%s currently has no memos." +msgstr "%s üzenetlistája üres." + +#: modules/commands/os_forbid.cpp:344 +#, fuzzy, c-format +msgid "%s deleted from the %s forbid list." +msgstr "A %s szó törölve %s tiltott szavak listájából." + +#: include/language.h:105 +#, fuzzy, c-format +msgid "%s for %s set to %s." +msgstr "%s vhostja erre változott: %s." + +#: include/language.h:106 +#, fuzzy, c-format +msgid "%s for %s unset." +msgstr "A megadott csatorna %s successora törölve." + +#: modules/commands/ns_ajoin.cpp:176 +#, c-format +msgid "%s had an invalid key specified, and was thus ignored." +msgstr "" + +#: modules/commands/ms_info.cpp:111 +#, c-format +msgid "%s has no memo limit." +msgstr "%s korlátlan számú üzenetet fogadhat." + +#: include/language.h:115 +#, fuzzy, c-format +msgid "%s has no memos." +msgstr "%s korlátlan számú üzenetet fogadhat." + +#: include/language.h:118 +#, fuzzy, c-format +msgid "%s has no new memos." +msgstr "%s korlátlan számú üzenetet fogadhat." + +#: modules/commands/ns_info.cpp:53 +#, c-format +msgid "%s is %s" +msgstr "%s az %s" + +#: modules/commands/ns_info.cpp:59 +#, fuzzy, c-format +msgid "%s is a Services Operator of type %s." +msgstr "%s is a services operator of type %s." + +#: modules/commands/cs_seen.cpp:281 +#, fuzzy, c-format +msgid "%s is a client on services." +msgstr "%s jelenleg online." + +#: modules/commands/cs_seen.cpp:200 +#, fuzzy, c-format +msgid "%s is a network service." +msgstr "%s jelenleg online." + +#: src/xline.cpp:407 +#, fuzzy, c-format +msgid "%s is already covered by %s." +msgstr "%s van már %s ilyen bejegyzés." + +#: modules/commands/ns_ajoin.cpp:170 +#, fuzzy, c-format +msgid "%s is already on %s's auto join list." +msgstr "%s hozzáadva a hozzáférési listádhoz." + +#: modules/commands/ns_info.cpp:56 +#, fuzzy, c-format +msgid "%s is an unconfirmed nickname." +msgstr "Ez a nicknév nem fog elévülni." + +#: modules/commands/cs_flags.cpp:432 +#, c-format +msgid "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." +msgstr "" + +#: modules/commands/ns_info.cpp:74 +#, c-format +msgid "%s is currently online." +msgstr "%s jelenleg online." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is disabled" +msgstr "%s is disabled" + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is enabled" +msgstr "%s is enable" + +#: modules/commands/os_dns.cpp:507 +#, fuzzy, c-format +msgid "%s is not a valid IP address." +msgstr "%s nem érvényes ban típus." + +#: modules/commands/cs_log.cpp:167 modules/commands/cs_log.cpp:192 +#, fuzzy, c-format +msgid "%s is not a valid command." +msgstr "%s nem érvényes ban típus." + +#: modules/commands/cs_log.cpp:198 +#, fuzzy, c-format +msgid "%s is not a valid logging method." +msgstr "%s nem érvényes ban típus." + +#: modules/commands/ms_info.cpp:124 +#, c-format +msgid "%s is not notified of new memos." +msgstr "%s nem kért értesítést az üzeneteiről." + +#: modules/commands/ms_info.cpp:118 +#, c-format +msgid "%s is notified of new memos at logon and when they arrive." +msgstr "%s értesítést kért csatlakozáskor,és ha új üzenete van," + +#: modules/commands/ms_info.cpp:122 +#, c-format +msgid "%s is notified of new memos at logon." +msgstr "%s kérte, csatlakozáskor értesítést kapjon,üzeneteiről." + +#: modules/commands/ms_info.cpp:120 +#, c-format +msgid "%s is notified when new memos arrive." +msgstr "%s értesítést kért, ha új üzenete érkezik." + +#: modules/commands/cs_seen.cpp:232 +#, c-format +msgid "%s is on the channel right now (as %s)!" +msgstr "" + +#: modules/commands/cs_seen.cpp:221 +#, fuzzy, c-format +msgid "%s is on the channel right now!" +msgstr "%s letiltva a (%s) csatornán." + +#: modules/commands/cs_xop.cpp:434 +#, fuzzy, c-format +msgid "%s list for %s" +msgstr "%s hozzáférési listája:" + +#: modules/commands/os_sxline.cpp:69 modules/commands/os_sxline.cpp:113 +#, fuzzy, c-format +msgid "%s list is empty." +msgstr "%s AOP listája üres." + +#: modules/commands/cs_mode.cpp:376 +#, fuzzy, c-format +msgid "%s locked on %s." +msgstr "%s nem kért értesítést az üzeneteiről." + +#: modules/extra/stats/cs_fantasy_stats.cpp:120 +#, fuzzy, c-format +msgid "%s not found." +msgstr "%s nem találatható a %s AOP listán." + +#: modules/commands/os_config.cpp:79 +#, c-format +msgid "%s settings:" +msgstr "" + +#: modules/commands/cs_seen.cpp:255 +#, c-format +msgid "%s was last seen here %s ago." +msgstr "" + +#: modules/commands/ns_ajoin.cpp:213 +#, fuzzy, c-format +msgid "%s was not found on %s's auto join list." +msgstr "%s nem szerepel a (%s) csatorna autokick listáján." + +#: modules/commands/ns_ajoin.cpp:221 +#, fuzzy, c-format +msgid "%s was removed from %s's auto join list." +msgstr "%s törölve a (%s) csatorna autokick listájáról." + +#: modules/commands/ms_set.cpp:64 +#, c-format +msgid "%s will not send you any notification of memos." +msgstr "%s mostmár nem fog értestíteni, ha új üzeneted érkezik." + +#: modules/commands/ms_set.cpp:42 +#, c-format +msgid "%s will now notify you of memos when they are sent to you." +msgstr "%s mostmár értesíteni fog, ha új üzeneted érkezik." + +#: modules/commands/ms_set.cpp:30 +#, c-format +msgid "" +"%s will now notify you of memos when you log on and when they are sent to " +"you." +msgstr "%s értesíteni fog az üzenetekről csatlakozáskor." + +#: modules/commands/ms_set.cpp:36 +#, c-format +msgid "%s will now notify you of memos when you log on or unset /AWAY." +msgstr "%s értesít az üzenetekről csatlakozáskor/AWAY OFF-kor." + +#: modules/commands/bs_bot.cpp:89 +#, c-format +msgid "%s!%s@%s (%s) added to the bot list." +msgstr "%s!%s@%s (%s) hozzáadva a bot listához." + +#: modules/commands/ns_access.cpp:83 +#, fuzzy, c-format +msgid "%s's access list is empty." +msgstr "%s hozzáférési listája üres." + +#: modules/commands/ns_ajoin.cpp:96 +#, fuzzy, c-format +msgid "%s's auto join list is empty." +msgstr "%s autokick listája üres." + +#: modules/commands/ns_ajoin.cpp:111 +#, fuzzy, c-format +msgid "%s's auto join list:" +msgstr " AKICK AutoKirúgás listára teheted a \"rossz\" usereket" + +#: modules/commands/ns_cert.cpp:242 +#, fuzzy, c-format +msgid "%s's certificate list is empty." +msgstr "Your access list is empty." + +#: modules/commands/ms_info.cpp:99 modules/commands/ms_info.cpp:106 +#, c-format +msgid "%s's memo limit is %d, and may not be changed." +msgstr "%s max. fogadható üzenteinek száma: %d, és ez fix érték." + +#: modules/commands/ms_info.cpp:101 modules/commands/ms_info.cpp:108 +#, c-format +msgid "%s's memo limit is %d." +msgstr "%s maximálisan fogadható üzeneteinek száma: %d." + +#: src/misc.cpp:363 +#, c-format +msgid "(%s ago)" +msgstr "" + +#: src/misc.cpp:365 +#, c-format +msgid "(%s from now)" +msgstr "" + +#: modules/commands/os_dns.cpp:244 +msgid "(Split)" +msgstr "" + +#: modules/commands/os_info.cpp:268 +#, c-format +msgid "(by %s on %s) %s" +msgstr "" + +#: modules/commands/cs_access.cpp:710 +#, fuzzy +msgid "(disabled)" +msgstr "%s is enable" + +#: modules/commands/cs_access.cpp:712 +msgid "(founder only)" +msgstr "" + +#: src/misc.cpp:367 +msgid "(now)" +msgstr "" + +#: modules/commands/os_defcon.cpp:168 +msgid "* AKILL any new clients connecting" +msgstr "* AKILL minden új kliensre csatlakozáskor." + +#: modules/commands/os_defcon.cpp:158 +#, fuzzy, c-format +msgid "* Force channel modes (%s) to be set on all channels" +msgstr "* Beállítja a következő módokat: (%s) az összes csatornán." + +#: modules/commands/os_defcon.cpp:164 +#, fuzzy +msgid "* Ignore non-opers with a message" +msgstr "* Mellőzve minden nem operátortól jövő üzenet" + +#: modules/commands/os_defcon.cpp:162 +#, fuzzy +msgid "* Kill any new clients connecting" +msgstr "* Killelve lesz minden új felhasználó csatlakozásnál. " + +#: modules/commands/os_defcon.cpp:156 +#, fuzzy +msgid "* No mode lock changes" +msgstr "* Nincs MLOCK módosítás" + +#: modules/commands/os_defcon.cpp:152 +msgid "* No new channel registrations" +msgstr "* Nem lehet új csatornát regisztrálni." + +#: modules/commands/os_defcon.cpp:170 +msgid "* No new memos sent" +msgstr "* Nem lehet új memot küldeni" + +#: modules/commands/os_defcon.cpp:154 +msgid "* No new nick registrations" +msgstr "* Nem lehet új nicket regisztrálni." + +#: modules/commands/os_defcon.cpp:166 +msgid "* Silently ignore non-opers" +msgstr "* Csendes mellőzés, csak operátorok" + +#: modules/commands/os_defcon.cpp:160 +#, c-format +msgid "* Use the reduced session limit of %d" +msgstr "* Használva a csökkentett session korlát: %d." + +#: modules/commands/cs_seen.cpp:319 +#, c-format +msgid ", but %s mysteriously dematerialized." +msgstr "" + +#: modules/commands/cs_seen.cpp:317 +#, fuzzy, c-format +msgid ". %s is still online." +msgstr "%s jelenleg online." + +#: include/language.h:87 +msgid "" +msgstr "" + +#: modules/commands/ns_set.cpp:504 +#, fuzzy, c-format +msgid "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." +msgstr "" +"A kód a %s címre lett küldve, írd be /msg %s confirm a regisztráció " +"befejezéséhez." + +#: modules/commands/ms_sendall.cpp:45 +msgid "A massmemo has been sent to all registered users." +msgstr "Egy massmemo elküldve minden regisztrált felhasználónak." + +#: modules/commands/hs_request.cpp:285 +msgid "" +"A memo informing the user will also be sent, which includes the reason for " +"the rejection if supplied." +msgstr "" + +#: modules/commands/hs_request.cpp:229 +msgid "A memo informing the user will also be sent." +msgstr "" + +#: modules/commands/ms_read.cpp:42 +#, c-format +msgid "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." +msgstr "" +"Az értesítő üzenet %s részére el lett küldve, informálva\n" +"őt arról, hogy elolvastad a memoját." + +#: include/language.h:123 +msgid "A vHost ident must be in the format of a valid ident." +msgstr "" + +#: include/language.h:122 +msgid "A vHost must be in the format of a valid hostname." +msgstr "" + +#: modules/commands/os_ignore.cpp:342 +#, fuzzy +msgid "ADD expiry {nick|mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_oper.cpp:70 +msgid "ADD oper type" +msgstr "" + +#: modules/commands/os_info.cpp:102 +#, fuzzy +msgid "ADD target info" +msgstr "GROUP célnick jelszó" + +#: modules/commands/os_news.cpp:278 +msgid "ADD text" +msgstr "" + +#: modules/commands/os_session.cpp:523 +#, fuzzy +msgid "ADD [+expiry] mask limit reason" +msgstr "CHANKILL [+lejárat] {#szoba} [indok]" + +#: modules/commands/ns_ajoin.cpp:231 +#, fuzzy +msgid "ADD [nickname] channel [key]" +msgstr "CHANKILL [+lejárat] {#szoba} [indok]" + +#: modules/commands/ns_access.cpp:102 +#, fuzzy +msgid "ADD [nickname] mask" +msgstr "CHANKILL [+lejárat] {#szoba} [indok]" + +#: modules/commands/ns_cert.cpp:258 +#, fuzzy +msgid "ADD [nickname] [fingerprint]" +msgstr "FORBID nicknév indok" + +#: modules/commands/os_sxline.cpp:659 modules/commands/os_akill.cpp:386 +#, fuzzy +msgid "ADD [+expiry] mask reason" +msgstr "CHANKILL [+lejárat] {#szoba} [indok]" + +#: modules/commands/os_sxline.cpp:425 +#, fuzzy +msgid "ADD [+expiry] mask:reason" +msgstr "CHANKILL [+lejárat] {#szoba} [indok]" + +#: modules/commands/os_forbid.cpp:157 +#, fuzzy +msgid "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" +msgstr "CHANKILL [+lejárat] {#szoba} [indok]" + +#: modules/commands/os_dns.cpp:665 +msgid "ADDIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:663 +msgid "ADDSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:661 +msgid "ADDZONE zone.name" +msgstr "" + +#: modules/commands/cs_akick.cpp:38 +#, c-format +msgid "AKICK ENFORCE for %s complete; %d users were affected." +msgstr "" +"Az AKICK ENFORCE a(z) %s csatornán teljesítve;\n" +"%d user eltávolítva." + +#: modules/commands/os_chankill.cpp:21 +#, fuzzy +msgid "AKILL all users on a specific channel" +msgstr " CHANKILL AKILL az összes usert a csatornáról" + +#: modules/commands/os_akill.cpp:222 modules/commands/os_akill.cpp:339 +#: modules/commands/os_akill.cpp:353 +msgid "AKILL list is empty." +msgstr "AKILL lista üres." + +#: modules/commands/bs_kick.cpp:1211 modules/commands/bs_kick.cpp:1213 +#: modules/commands/bs_kick.cpp:1216 +#, fuzzy +msgid "AMSG kicker" +msgstr "\tCaps Lockért kirúgás : %s" + +#: modules/commands/ns_alist.cpp:48 +#, fuzzy +msgid "Access" +msgstr "Hozzáférési lista:" + +#: include/language.h:72 +#, fuzzy +msgid "Access denied." +msgstr "Hozzáférési lista:" + +#: modules/commands/cs_status.cpp:58 +#, fuzzy, c-format +msgid "Access for %s on %s:" +msgstr "%s hozzáférése a (%s) csatornán változott: %d." + +#: include/language.h:107 +#, fuzzy, c-format +msgid "Access level must be between %d and %d inclusive." +msgstr "A szintnek kizárólag %d és %d között kell lennie." + +#: modules/commands/cs_access.cpp:108 +msgid "Access level must be non-zero." +msgstr "A hozzáférési szint nem lehet nulla." + +#: modules/commands/cs_access.cpp:694 +#, c-format +msgid "Access level settings for channel %s:" +msgstr "%s hozzáférési szintjeinek beállításai:" + +#: modules/commands/cs_access.cpp:734 +#, c-format +msgid "Access levels for %s reset to defaults." +msgstr "%s szintjei visszaállítva az alapértékekre." + +#: modules/commands/cs_access.cpp:439 modules/commands/ns_access.cpp:87 +#, fuzzy, c-format +msgid "Access list for %s:" +msgstr "%s hozzáférési listája:" + +#: modules/commands/help.cpp:166 +#, c-format +msgid "" +"Access to this command requires the permission %s to be present in your " +"opertype." +msgstr "" +"Access to this command requires the permission %s to be present in your " +"opertype." + +#: modules/commands/ns_cert.cpp:368 modules/commands/ns_cert.cpp:392 +#: modules/commands/ns_identify.cpp:94 +#, c-format +msgid "" +"Account %s has already reached the maximum number of simultaneous logins " +"(%u)." +msgstr "" + +#: modules/commands/cs_set.cpp:683 +#, fuzzy +msgid "Activate security features" +msgstr " SECURE Aktiválja a %s biztonsági lehetőségeit" + +#: modules/commands/hs_request.cpp:227 +msgid "Activate the requested vHost for the given nick." +msgstr "" + +#: modules/commands/hs_on.cpp:55 +#, fuzzy +msgid "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." +msgstr "" +"Syntax: ON\n" +"Aktiválja a vhostodat, ami a nickhez lett társítva.\n" +"Ha valaki csinál egy /whois parancsot a nickeden,\n" +"akkor a vhostodat fogja látni a valódi IP címed vagy\n" +"hosztneved helyett." + +#: modules/commands/hs_on.cpp:19 +#, fuzzy +msgid "Activates your assigned vhost" +msgstr " ON Aktiválja a társított vhostot" + +#: modules/commands/os_info.cpp:243 +msgid "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." +msgstr "" + +#: modules/commands/os_dns.cpp:515 +#, c-format +msgid "Added IP %s to %s." +msgstr "" + +#: modules/commands/os_forbid.cpp:239 +#, c-format +msgid "Added a forbid on %s of type %s to expire on %s." +msgstr "" + +#: modules/commands/os_info.cpp:164 +#, fuzzy, c-format +msgid "Added info to %s." +msgstr "Üzenet elküldve %s részére." + +#: modules/commands/os_news.cpp:34 +#, fuzzy +msgid "Added new logon news item." +msgstr "Hozzáadva az új fellépési hír: (#%d)." + +#: modules/commands/os_news.cpp:44 +#, fuzzy +msgid "Added new oper news item." +msgstr "Hozzáadva az új oper hír:(#%d)." + +#: modules/commands/os_news.cpp:54 +#, fuzzy +msgid "Added new random news item." +msgstr "Hozzáadva az új random news tétel (#%d)." + +#: modules/commands/os_dns.cpp:395 +#, fuzzy, c-format +msgid "Added server %s." +msgstr "Uplink server: %s" + +#: modules/commands/os_dns.cpp:300 +#, c-format +msgid "Added zone %s." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:257 +msgid "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." +msgstr "" + +#: modules/commands/ns_register.cpp:104 +msgid "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." +msgstr "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." + +#: modules/pseudoclients/botserv.cpp:172 +#, c-format +msgid "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" +msgstr "" + +#: modules/commands/os_noop.cpp:58 +#, c-format +msgid "All O:lines of %s have been reset." +msgstr "Összes O:lines %s újra aktív." + +#: modules/commands/cs_clone.cpp:71 +#, fuzzy, c-format +msgid "All akick entries from %s have been cloned to %s." +msgstr "Az összes user vhosztja a(z) %s csoportba %s lett" + +#: modules/commands/help.cpp:57 +#, fuzzy, c-format +msgid "All available commands for %s:" +msgstr "Nincs ezzel kapcsolatban segítség: %s." + +#: modules/commands/cs_clone.cpp:96 +#, fuzzy, c-format +msgid "All badword entries from %s have been cloned to %s." +msgstr "Az összes user vhosztja a(z) %s csoportba %s lett" + +#: modules/commands/cs_clone.cpp:108 +#, fuzzy, c-format +msgid "All level entries from %s have been cloned into %s." +msgstr "Az összes user vhosztja a(z) %s csoportba %s lett" + +#: modules/commands/os_news.cpp:38 +msgid "All logon news items deleted." +msgstr "Összes fellépési hír tétel törölve." + +#: modules/commands/ms_del.cpp:115 +#, c-format +msgid "All memos for channel %s have been deleted." +msgstr "Minden üzenetet töröltem a %s csatornán." + +#: modules/commands/os_mode.cpp:61 +#, c-format +msgid "All modes cleared on %s." +msgstr "" + +#: modules/commands/ns_register.cpp:258 modules/commands/ns_register.cpp:389 +msgid "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." +msgstr "" + +#: modules/commands/ms_del.cpp:119 +msgid "All of your memos have been deleted." +msgstr "Minden üzenetet töröltem." + +#: modules/commands/os_news.cpp:48 +msgid "All oper news items deleted." +msgstr "Összes oper hír törölve." + +#: modules/commands/os_noop.cpp:41 +#, fuzzy, c-format +msgid "All operators from %s have been removed." +msgstr "Összes O:lines %s módosítva." + +#: modules/commands/os_news.cpp:58 +msgid "All random news items deleted." +msgstr "Összes random news tétel törölve." + +#: modules/commands/cs_clone.cpp:211 +#, fuzzy, c-format +msgid "All settings from %s have been cloned to %s." +msgstr "Az összes user vhosztja a(z) %s csoportba %s lett" + +#: modules/commands/cs_sync.cpp:41 +#, fuzzy, c-format +msgid "All user modes on %s have been synced." +msgstr "Összes O:lines %s újra aktív." + +#: modules/commands/hs_group.cpp:60 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s." +msgstr "Az összes user vhosztja a(z) %s csoportba %s lett" + +#: modules/commands/hs_group.cpp:58 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s@%s." +msgstr "Az összes user vhosztja a(z) %s csoportba %s@%s lett" + +#: src/access.cpp:40 +msgid "Allowed to (de)halfop him/herself" +msgstr "" + +#: src/access.cpp:39 +msgid "Allowed to (de)halfop users" +msgstr "" + +#: src/access.cpp:48 +msgid "Allowed to (de)op him/herself" +msgstr "" + +#: src/access.cpp:47 +msgid "Allowed to (de)op users" +msgstr "" + +#: src/access.cpp:50 +msgid "Allowed to (de)owner him/herself" +msgstr "" + +#: src/access.cpp:49 +msgid "Allowed to (de)owner users" +msgstr "" + +#: src/access.cpp:52 +msgid "Allowed to (de)protect him/herself" +msgstr "" + +#: src/access.cpp:51 +msgid "Allowed to (de)protect users" +msgstr "" + +#: src/access.cpp:59 +msgid "Allowed to (de)voice him/herself" +msgstr "" + +#: src/access.cpp:58 +msgid "Allowed to (de)voice users" +msgstr "" + +#: src/access.cpp:27 +msgid "Allowed to assign/unassign a bot" +msgstr "" + +#: src/access.cpp:34 +msgid "Allowed to ban users" +msgstr "" + +#: src/access.cpp:56 +#, fuzzy +msgid "Allowed to change channel topics" +msgstr "%s váltóztatott a módodon." + +#: src/access.cpp:41 +msgid "Allowed to get full INFO output" +msgstr "" + +#: src/access.cpp:36 +msgid "Allowed to issue commands restricted to channel founders" +msgstr "" + +#: src/access.cpp:33 +msgid "Allowed to modify channel badwords list" +msgstr "" + +#: src/access.cpp:24 +#, fuzzy +msgid "Allowed to modify the access list" +msgstr "%s törölve lett a (%s) csatorna hozzáférési listájáról." + +#: src/access.cpp:44 +msgid "Allowed to read channel memos" +msgstr "" + +#: src/access.cpp:54 +#, fuzzy +msgid "Allowed to set channel settings" +msgstr "* Nem lehet új csatornát regisztrálni." + +#: src/access.cpp:57 +msgid "Allowed to unban users" +msgstr "" + +#: src/access.cpp:37 +msgid "Allowed to use GETKEY command" +msgstr "" + +#: src/access.cpp:53 +msgid "Allowed to use SAY and ACT commands" +msgstr "" + +#: src/access.cpp:35 +#, fuzzy +msgid "Allowed to use fantasy commands" +msgstr " PEACE Szabályozza a kritikus parancsok használatát" + +#: src/access.cpp:26 +#, fuzzy +msgid "Allowed to use the AKICK command" +msgstr "You cannot use this command." + +#: src/access.cpp:42 +msgid "Allowed to use the INVITE command" +msgstr "" + +#: src/access.cpp:43 +#, fuzzy +msgid "Allowed to use the KICK command" +msgstr "You cannot use this command." + +#: src/access.cpp:45 +#, fuzzy +msgid "Allowed to use the MODE command" +msgstr "You cannot use this command." + +#: src/access.cpp:25 +#, fuzzy +msgid "Allowed to view the access list" +msgstr "%s törölve lett a (%s) csatorna hozzáférési listájáról." + +#: modules/commands/gl_global.cpp:42 +#, fuzzy, c-format +msgid "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." +msgstr "" +"Syntax: GLOBAL üzenet\n" +"\n" +"Megengedi, hogy az IRCopok üzenetet küldjenek az összes \n" +"felhasználónak a hálózaton. Üzenetet a %s nickről küldi." + +#: modules/commands/os_mode.cpp:133 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." +msgstr "" +"Syntax: MODE #szoba módok\n" +"\n" +"Megengedi a szervíz operátornak, hogy szoba módokat \n" +"állítson. Parameterek ugyanazok mint a szabvány\n" +"/MODE parancsnál\n" +"\t\n" +"Korlátozva Szervíz operatornak." + +#: modules/commands/os_mode.cpp:173 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." +msgstr "" +"Syntax: MODE #szoba módok\n" +"\n" +"Megengedi a szervíz operátornak, hogy szoba módokat \n" +"állítson. Parameterek ugyanazok mint a szabvány\n" +"/MODE parancsnál\n" +"\t\n" +"Korlátozva Szervíz operatornak." + +#: modules/commands/bs_bot.cpp:352 +#, fuzzy +msgid "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." +msgstr "" +"Syntax:\tBOT ADD nick user hoszt valós\n" +"\t\tBOT CHANGE réginick újnick [user [ hoszt [ valós ]]]\n" +"\t\tBOT DEL nick\n" +"\n" +"Lehetővé teszi a Services Operatoroknak, hogy létrehozzanak\n" +"töröljenek, módosítsanak botokat, amiket a userek\n" +"használhatnak a csatornáikon.\n" +"\n" +"BOT ADD hozzáad egy botot a megadott nick, usernév,\n" +"hostnév és valósnév használatával. Amióta nincs ellenőrzés\n" +"kérlek óvatósan használd ezt a parancsot.\n" +"BOT CHANGE megváltoztatja egy bot nickjét, usernevét,\n" +"hostnevét, valósnevét, anélkül hogy törölni kellene\n" +"(minden adat, beállítás megmarad benne.)\n" +"BOT DEL törli a megadott botot a listából. \n" +"\n" +"Megjegyzés: ha létrehozol egy botot, egy már regisztrált\n" +"nickkel, akkor a nick dropolva lesz. Akkor is, ha a user\n" +"éppen használja a nicket; killelve lesz." + +#: modules/commands/os_oline.cpp:56 +#, fuzzy +msgid "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." +msgstr "" +"Syntax: OLINE user flagek\n" +"\n" +"Lehetőséget ad a szervíz adminnak, hogy egy usernek \n" +"operflaget adjon. Előjelként \"+\" vagy \"-\" adható meg.\n" +"Ha csak a \"-\" paraméter adod meg akkor mindent eltávolít." + +#: modules/commands/os_ignore.cpp:370 +#, fuzzy +msgid "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." +msgstr "" +"Syntax: IGNORE {ADD|DEL|LIST|CLEAR} [time] [nick | mask]\n" +"\n" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes, \n" +"h for hours and d for days. \n" +"Combinations of these units are not permitted. To make\n" +"Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format user@host\n" +"or nick!user@host, everything else will be considered a nick.\n" +"Wildcards are permitted.\n" +"\n" +"Ignores will not be enforced on IRC Operators.\n" +"\t" + +#: modules/commands/os_akill.cpp:420 +#, fuzzy +msgid "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Syntax: AKILL ADD [ +lejárat] maszk indok\n" +" AKILL DEL {maszk | sor-szám | list}\n" +" AKILL LIST [maszk | list]\n" +" AKILL VIEW [maszk | list]\n" +" AKILL CLEAR\n" +"\n" +"Lehetőséget ad a szervíz opoknak, hogy karbantartsák az\n" +"AKILL listát. Ha egy felhasználó az AKILL maszkkal egyező\n" +"cimről próbál csatlakozni , akkor szervíz kiad egy KILL \n" +"parancsot a nickre, és a támogatott szervertípusokon arra\n" +"utasít minden szervert, hogy adjon K-linet a maszknak.\n" +"\n" +"AKILL ADD hozzáadja a megadott user@host/ip maszkot az\n" +"AKILL listára a megadott indokkal (amit meg kell adnod).\n" +"Az elévülést egész számmot kovet egy időparaméter d (nap),\n" +"h (óra), m (perc).Ezek kombinálása nem lehetséges(1h30m).\n" +"ha nem adsz meg időegységet akkor önmagában napot jelent.\n" +"(+30 az 30 napot jelent).Ha +0-át adsz meg akkor nem \n" +"elévülő lesz.Ha a usermaszk + -al kezdődik akkor elévülést\n" +"meg kell adni akkor is ha megegyezik az alapértelmezéssel.\n" +"Az AKILL jelenlegi alapértelmezett elévüólési ideje \n" +"megnézhető a STATS AKILL paranccsal.\n" +"AKILL DEL törli a maszkot az AKILL listáról, ha rajta\n" +"van. Ha bejegyzés sorszámot adsz meg akkor azok fognak\n" +"törlődni.(lásd a példát alább)\n" +"AKILL LIST kiirja a jelenlegi AKILL listát. Ha egy \n" +"\"*\" karakteres maszk van megadva, akkor csak azokat az\n" +"AKILL-eket listázza, amelyek ráillenek a megadott maszkra.\n" +"Ha sorszámot adsz meg akkor azok fognak törlődni. Példa:\n" +"\tAKILL LIST 2-5,7-9\n" +" Listázza az AKILL-en lévoket 2-től 5-ig és 7-től 9-ig\n" +" az AKILL listából\n" +"AKILL VIEW részletesebb verziója az AKILL LIST-nek,\n" +"amely megmutatja, hogy ki vette fel az AKILL-t,\tmikor lett\n" +"felvéve és mikor jár le, éppúgy, felhasználó@gazdanév \n" +"maszkot és indokot.\n" +"\t\n" +"AKILL CLEAR töröli az összes AKILL bejegyzést.\n" +"\n" +"Korlátozva Szervíz operatornak." + +#: modules/commands/os_sxline.cpp:436 +msgid "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." +msgstr "" + +#: modules/commands/os_sxline.cpp:670 +msgid "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." +msgstr "" + +#: modules/commands/os_session.cpp:551 +msgid "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." +msgstr "" + +#: modules/commands/os_session.cpp:270 +#, fuzzy +msgid "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." +msgstr "" +"Syntax: SESSION LIST threshold\n" +" SESSION VIEW host\n" +"\n" +"Megengedi a Szervíz adminoknak, hogy megtekintsék a \n" +"session listát.\n" +"SESSION LIST kilistázza azokat a hostokat, amelyeknek\n" +"legalább határértéksessionjuk van. Érték legyen 1-nél\n" +"nagyobb szám,hogy megelőzze az egy sessionúak kilistázását\n" +"SESSION VIEWmegjeleníti a host részletes információit,\n" +"tartalmazva a jelenlegi session számot, session korlátot.\n" +"A host értéke nem tartalmazhat maszkkaraktereket.\n" +"\n" +"Lásd az EXCEPTION helpjét további információért a \n" +"session-korlátozással és azzal kapcsolatban,hogyan állíts\n" +"be különleges korlátokat bizonyos hostokra és csoportokra.\n" +"\n" +"\n" +"Korlátozva Szervíz adminoknak." + +#: modules/commands/cs_topic.cpp:193 +msgid "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do " +"not have\n" +"the TOPIC privilege." +msgstr "" + +#: modules/commands/os_kick.cpp:62 +#, fuzzy, c-format +msgid "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" +msgstr "" +"Syntax: KICK #szoba user indok\n" +"\n" +"Lehetoséget nyújt az IRCopoknak, hogy bármelyik szobából\n" +"kirúgjanak egy felhasználót. A paraméterek ugyanazok,\n" +"mint a szabványos /KICK parancsnál. A kirúgási üzenetben\n" +"benne lesz a KIK parancsot küldő IRCop nickneve; például:\n" +"\n" +"***xy ki lett rúgva a #csatornáról %s által.(op(csak))\n" +"\n" +"Korlátozva Szervíz operatornak." + +#: modules/commands/cs_set.cpp:33 +#, fuzzy +msgid "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" +msgstr "" +"Syntax: SET #szoba opció paraméterek\n" +"\n" +"Lehetőséget ad a foundernek, hogy a beállításokat\n" +"és információkat megváltoztassa.\n" +"\n" +"Elérhető opciók:" + +#: modules/commands/os_oper.cpp:250 +msgid "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." +msgstr "" + +#: modules/commands/os_config.cpp:127 +msgid "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" +msgstr "" + +#: modules/commands/ns_set.cpp:992 +#, fuzzy +msgid "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." +msgstr "" +"Syntax: SASET nickname MSG {ON | OFF}\n" +"\n" +"Allows you to choose the way Services are communicating with \n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." + +#: modules/commands/ns_set.cpp:966 +#, fuzzy, c-format +msgid "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." +msgstr "" +"Syntax: SET MSG {ON | OFF}\n" +"\n" +"Lehetőséget nyújt arra, hogy megválaszd azt, hogy a szervíz\n" +"hogyan kommunikáljon veled.\n" +"Az MSG beállítással, a szervíz, privát üzeneteket fog\n" +"használni, egyébként pedig noticeokat." + +#: modules/commands/ms_ignore.cpp:113 +msgid "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." +msgstr "" + +#: modules/commands/os_kill.cpp:48 +msgid "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." +msgstr "" + +#: modules/commands/ns_info.cpp:252 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Syntax: SASET nickname HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}\n" +"\n" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." + +#: modules/commands/ns_info.cpp:223 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Syntax: SET HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}\n" +"\n" +"Lehetőséget nyújt arra, hogy megelőzd néhány adatnak a\n" +"szerepelését a %s INFO parancs használatakor .\n" +"Elrejtheted az E-mail címed (EMAIL), az utoljára használt\n" +"user@host maszkod (USERMASK), és az utolsó kilépő \n" +"üzeneted(QUIT).\tA második paraméter meghatározza, hogy \n" +"az opció ki legyen kapcsolva(OFF)\tvagy el legyen rejtve\n" +"az információ(ON)." + +#: modules/commands/bs_info.cpp:118 +#, fuzzy, c-format +msgid "Allows you to see %s information about a channel or a bot" +msgstr "" +"INFO Allows you to see BotServ information about a channel or " +"a bot" + +#: modules/commands/bs_info.cpp:108 +#, fuzzy, c-format +msgid "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." +msgstr "" +"Syntax: INFO {#szoba | nick}\n" +"\n" +"Lehetővé teszi, hogy megnézd a %s információkat egy\n" +"csatornával vagy bottal kapcsolatban. Ha a paraméter\n" +"szobanév, akkor megkapod a szobára vonatkozó bot\n" +"beállításokat. Ha a paraméter nick, akkor a botról\n" +"kapsz információkat, például létrehozás ideje, csatornák\n" +"száma." + +#: modules/commands/cs_xop.cpp:567 +msgid "" +"Alternative methods of modifying channel access lists are\n" +"available. " +msgstr "" + +#: modules/commands/hs_request.cpp:191 +#, fuzzy +msgid "Approve the requested vHost of a user" +msgstr " DEL Törli egy felhasználónak a vhostját" + +#: modules/commands/ns_drop.cpp:68 +#, fuzzy +msgid "As a Services Operator, you may drop any nick." +msgstr "%s is a services operator of type %s." + +#: modules/commands/bs_assign.cpp:19 +#, fuzzy +msgid "Assigns a bot to a channel" +msgstr "ASSIGN Társít egy botot a csatornához" + +#: modules/commands/bs_assign.cpp:78 +#, fuzzy +msgid "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." +msgstr "" +"Syntax: ASSIGN #szoba nick\n" +"\n" +"Társítja a megnevezett botot a szobához. Beállíthatod a\n" +"botodat a csatornád igényeidnek megfelelően.\n" +"Kellemes botozást! :-)" + +#: data/chanserv.example.conf:1197 +#, fuzzy +msgid "Associate a URL with the channel" +msgstr "ASSIGN Társít egy botot a csatornához" + +#: data/nickserv.example.conf:594 +msgid "Associate a URL with this account" +msgstr "" + +#: data/nickserv.example.conf:593 +#, fuzzy +msgid "Associate a URL with your account" +msgstr " GREET Köszöntő üzenet társítása a nicknevedhez" + +#: modules/commands/greet.cpp:83 +#, fuzzy +msgid "Associate a greet message with your nickname" +msgstr " GREET Köszöntő üzenet társítása a nicknevedhez" + +#: data/chanserv.example.conf:1198 +#, fuzzy +msgid "Associate an E-mail address with the channel" +msgstr " EMAIL Egy E-mail cím társítása a nicknevedhez" + +#: modules/commands/ns_set.cpp:452 +#, fuzzy +msgid "Associate an E-mail address with your nickname" +msgstr " EMAIL Egy E-mail cím társítása a nicknevedhez" + +#: modules/commands/os_info.cpp:101 +#, fuzzy +msgid "Associate oper info with a nick or channel" +msgstr "ASSIGN Társít egy botot a csatornához" + +#: modules/commands/ns_set.cpp:558 +#, fuzzy +msgid "Associates the given E-mail address with the nickname." +msgstr " EMAIL Egy E-mail cím társítása a nicknevedhez" + +#: modules/commands/ns_set.cpp:533 +#, fuzzy +msgid "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." +msgstr "" +"Syntax: SET EMAIL cím\n" +"\n" +"Egy E-mail cím társítása a nicknevedhez.\n" +"Ez az E-mail cím szerepelni fog az INFO-id között,\n" +"amit bárki lekérhet az INFO paranccsal." + +#: modules/commands/ns_set.cpp:1315 +msgid "Auto-op" +msgstr "Auto-op" + +#: modules/commands/cs_akick.cpp:374 +#, c-format +msgid "Autokick list for %s:" +msgstr "%s autokick listája:" + +#: src/access.cpp:29 +msgid "Automatic channel operator status upon join" +msgstr "" + +#: src/access.cpp:28 +msgid "Automatic halfop upon join" +msgstr "" + +#: src/access.cpp:30 +msgid "Automatic owner upon join" +msgstr "" + +#: src/access.cpp:31 +msgid "Automatic protect upon join" +msgstr "" + +#: src/access.cpp:32 +msgid "Automatic voice on join" +msgstr "" + +#: modules/commands/os_oper.cpp:196 +#, fuzzy, c-format +msgid "Available commands for %s:" +msgstr "Nincs ezzel kapcsolatban segítség: %s." + +#: modules/commands/os_oper.cpp:175 +#, fuzzy +msgid "Available opertypes:" +msgstr "Nincs ezzel kapcsolatban segítség: %s." + +#: modules/commands/os_oper.cpp:218 +#, c-format +msgid "Available privileges for %s:" +msgstr "" + +#: modules/commands/cs_enforce.cpp:162 +msgid "BANS enforced by " +msgstr "" + +#: modules/commands/bs_kick.cpp:1121 modules/commands/bs_kick.cpp:1123 +#: modules/commands/bs_kick.cpp:1126 +#, fuzzy +msgid "Bad words kicker" +msgstr "\tCsúnya szavakért kirúgás: %s" + +#: modules/commands/bs_badwords.cpp:252 +#, fuzzy, c-format +msgid "Bad words list for %s:" +msgstr "%s hozzáférési listája:" + +#: modules/commands/bs_badwords.cpp:364 +msgid "Bad words list is now empty." +msgstr "Tiltott szó lista üres." + +#: modules/commands/bs_set.cpp:129 +msgid "Ban expiry may not be longer than 1 day." +msgstr "" + +#: modules/commands/cs_ban.cpp:140 modules/commands/cs_ban.cpp:175 +#, fuzzy, c-format +msgid "Ban on %s expires in %s." +msgstr "%s nevű bot már létezik." + +#: modules/commands/cs_info.cpp:60 +msgid "Ban type" +msgstr "" + +#: modules/commands/cs_set.cpp:174 +#, c-format +msgid "Ban type for channel %s is now #%d." +msgstr "A megadott csatorna (%s) új ban típusa: #%d." + +#: modules/commands/cs_ban.cpp:39 +#, fuzzy +msgid "Bans a given nick or mask on a channel" +msgstr " BAN Bans a selected nick on a channel" + +#: modules/commands/cs_ban.cpp:227 +#, fuzzy +msgid "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." +msgstr "" +"Syntax: BAN #szoba nick [indok]\n" +"\n" +"Kitilt egy kiválaszott nicket a csatornáról.\n" +"\n" +"Alapbeállítás szerint, minimum AOP vagy 5-ös access \n" +"szinttel kell rendelkezned a csatornán, hogy használhasd." + +#: modules/commands/cs_enforce.cpp:166 +#, fuzzy, c-format +msgid "Bans enforced on %s." +msgstr "%s nem kért értesítést az üzeneteiről." + +#: modules/commands/bs_kick.cpp:1131 modules/commands/bs_kick.cpp:1133 +#: modules/commands/bs_kick.cpp:1136 +#, fuzzy +msgid "Bolds kicker" +msgstr "\tFélkövér betűkért kirúgás: %s" + +#: modules/commands/bs_bot.cpp:26 modules/commands/bs_bot.cpp:175 +#, c-format +msgid "Bot %s already exists." +msgstr "%s nevű bot már létezik." + +#: include/language.h:119 +#, fuzzy, c-format +msgid "Bot %s does not exist." +msgstr "%s nevű bot már létezik." + +#: modules/commands/bs_assign.cpp:71 modules/commands/bs_assign.cpp:246 +#, c-format +msgid "Bot %s has been assigned to %s." +msgstr "A %s nevű bot társítva a %s szobához." + +#: modules/commands/bs_bot.cpp:228 +#, fuzzy, c-format +msgid "Bot %s has been changed to %s!%s@%s (%s)." +msgstr "A %s nevű bot megváltoztatva %s!%s@%s (%s)" + +#: modules/commands/bs_bot.cpp:262 +#, c-format +msgid "Bot %s has been deleted." +msgstr "A %s nevű bot törölve." + +#: modules/commands/bs_assign.cpp:63 modules/commands/bs_assign.cpp:241 +#, c-format +msgid "Bot %s is already assigned to channel %s." +msgstr "A %s nevű bot már társítva van a %s szobához." + +#: modules/commands/bs_kick.cpp:832 +#, c-format +msgid "Bot will kick ops on channel %s." +msgstr "A Bot most már opot is kirúg a %s szobából." + +#: modules/commands/bs_kick.cpp:897 +#, c-format +msgid "Bot will kick voices on channel %s." +msgstr "A Bot most már a hangadókat is kirúgja a %s szobában." + +#: modules/commands/bs_kick.cpp:824 +#, c-format +msgid "Bot won't kick ops on channel %s." +msgstr "A Bot nem fog opot kirúgni a %s szobából." + +#: modules/commands/bs_kick.cpp:889 +#, c-format +msgid "Bot won't kick voices on channel %s." +msgstr "A Bot nem fogja a hangadókat kirúgni a %s szobában." + +#: modules/commands/bs_bot.cpp:118 +#, fuzzy, c-format +msgid "Bot %s is not changeable." +msgstr "Nincs Bot mód most ONa %s szobán." + +#: modules/commands/bs_bot.cpp:254 +#, fuzzy, c-format +msgid "Bot %s is not deletable." +msgstr "A %s nevű bot törölve." + +#: modules/commands/bs_set.cpp:141 +#, c-format +msgid "Bot bans will automatically expire after %s." +msgstr "" + +#: modules/commands/bs_set.cpp:139 +#, fuzzy +msgid "Bot bans will no longer automatically expire." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/bs_bot.cpp:46 modules/commands/bs_bot.cpp:138 +#, fuzzy, c-format +msgid "Bot hosts may only be %d characters long." +msgstr "Bot Hosts may only contain %d characters." + +#: modules/commands/bs_bot.cpp:64 modules/commands/bs_bot.cpp:167 +#, fuzzy +msgid "Bot hosts may only contain valid host characters." +msgstr "Bot Hoszt csak érvényes karaktereket tartalmazhat." + +#: modules/commands/bs_bot.cpp:40 modules/commands/bs_bot.cpp:132 +#, fuzzy, c-format +msgid "Bot idents may only be %d characters long." +msgstr "Bot Idents may only contain %d characters." + +#: modules/commands/bs_bot.cpp:58 modules/commands/bs_bot.cpp:161 +#, fuzzy +msgid "Bot idents may only contain valid ident characters." +msgstr "Bot Ident csak érvényes karaktereket tartalmazhat." + +#: include/language.h:121 +#, fuzzy, c-format +msgid "Bot is not on channel %s." +msgstr "A Bot most már opot is kirúg a %s szobából." + +#: modules/commands/bs_botlist.cpp:51 +msgid "Bot list:" +msgstr "Botok listája:" + +#: modules/commands/bs_info.cpp:87 +msgid "Bot nick" +msgstr "" + +#: modules/commands/bs_bot.cpp:34 modules/commands/bs_bot.cpp:126 +#, fuzzy, c-format +msgid "Bot nicks may only be %d characters long." +msgstr "Bot Idents may only contain %d characters." + +#: modules/commands/bs_bot.cpp:52 modules/commands/bs_bot.cpp:155 +#, fuzzy +msgid "Bot nicks may only contain valid nick characters." +msgstr "Bot Nick csak érvényes karaktereket tartalmazhat." + +#: modules/commands/bs_kick.cpp:225 +#, fuzzy, c-format +msgid "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." +msgstr "" +"Bot will now kick italics, and will place a ban after %d\n" +"kicks for the same user." + +#: modules/commands/bs_kick.cpp:228 +#, fuzzy, c-format +msgid "Bot will now kick for %s." +msgstr "A Bot kirúgja félkövér betű használat miatt a usert." + +#: modules/commands/bs_kick.cpp:416 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." +msgstr "" +"Bot most már kirúgja caps lock miatt, (legalább\n" +"%d karakter és ennek %d%%-a nagybetű), kitiltja \n" +"%d kirúgás után a usert." + +#: modules/commands/bs_kick.cpp:420 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." +msgstr "" +"Bot most már kirúgja caps lock miatt a usert (legalább\n" +"%d karakter és ennek %d%%-a nagybetű)." + +#: modules/commands/bs_kick.cpp:551 +#, fuzzy, c-format +msgid "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." +msgstr "" +"A Bot kirúgja flood miatt (%d sor %d mp alatt),\n" +"és kitiltja %d kirúgás után a usert." + +#: modules/commands/bs_kick.cpp:554 +#, fuzzy, c-format +msgid "Bot will now kick for flood (%d lines in %d seconds)." +msgstr "Bot kirúgja flood miatt a usert. (%d sor %d mp alatt)" + +#: modules/commands/bs_kick.cpp:677 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"A Bot kirúgja ismétlés miatt (ha %d alkalommal ismétli\n" +"ugyanazt a sort), és kitiltja %d kirúgás után a usert." + +#: modules/commands/bs_kick.cpp:687 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." +msgstr "" +"A Bot kirúgja ismétlés miatt a usert (ha %d alkalommal\n" +"ismétli ugyanazt a sort)." + +#: modules/commands/bs_kick.cpp:673 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"A Bot kirúgja ismétlés miatt (ha %d alkalommal ismétli\n" +"ugyanazt a sort), és kitiltja %d kirúgás után a usert." + +#: modules/commands/bs_kick.cpp:684 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." +msgstr "" +"A Bot kirúgja ismétlés miatt a usert (ha %d alkalommal\n" +"ismétli ugyanazt a sort)." + +#: modules/commands/bs_kick.cpp:239 +#, fuzzy, c-format +msgid "Bot won't kick for %s anymore." +msgstr "Bot nem fog kirúgni caps lock miatt." + +#: modules/commands/bs_kick.cpp:426 +#, fuzzy +msgid "Bot won't kick for caps anymore." +msgstr "Bot nem fog kirúgni caps lock miatt." + +#: modules/commands/bs_kick.cpp:559 +#, fuzzy +msgid "Bot won't kick for flood anymore." +msgstr "A Bot nem fog kirúgni flood miatt." + +#: modules/commands/bs_kick.cpp:694 +#, fuzzy +msgid "Bot won't kick for repeats anymore." +msgstr "A Bot nem fog kirúgni ismétlés miatt." + +#: modules/commands/cs_access.cpp:472 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_session.cpp:514 +msgid "By" +msgstr "" + +#: modules/commands/os_info.cpp:104 +msgid "CLEAR target" +msgstr "" + +#: modules/commands/cs_seen.cpp:119 +msgid "CLEAR time" +msgstr "" + +#: modules/commands/ms_cancel.cpp:19 +#, fuzzy +msgid "Cancel the last memo you sent" +msgstr " CANCEL Visszavonja az utoljára küldött memot" + +#: modules/commands/cs_drop.cpp:19 +#, fuzzy +msgid "Cancel the registration of a channel" +msgstr " DROP Törölheted a csatornád regisztrációját" + +#: modules/commands/ns_drop.cpp:20 +#, fuzzy +msgid "Cancel the registration of a nickname" +msgstr " DROP Nicknév regisztrációjának törlése" + +#: modules/commands/ms_cancel.cpp:84 +#, fuzzy +msgid "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." +msgstr "" +"Syntax: CANCEL { nick | #szoba }\n" +"\n" +"Visszavonja az utolsó memo üzenetet, amit a nicknek\n" +"vagy csatornának küldtél." + +#: modules/commands/cs_clone.cpp:149 +#, fuzzy, c-format +msgid "Cannot clone channel %s to itself!" +msgstr "A Bot most már opot is kirúg a %s szobából." + +#: modules/commands/ns_register.cpp:332 +msgid "Cannot send mail now; please retry a little later." +msgstr "Nem lehet most levelet küldeni; próbáld újra később." + +#: modules/commands/bs_kick.cpp:1141 modules/commands/bs_kick.cpp:1143 +#: modules/commands/bs_kick.cpp:1146 +#, fuzzy +msgid "Caps kicker" +msgstr "\tCaps Lockért kirúgás : %s" + +#: modules/commands/os_shutdown.cpp:34 +#, fuzzy +msgid "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." +msgstr "" +"Syntax: QUIT\n" +"\n" +"A Szervíz azonnal leáll; az adatbázist nem menti el.\n" +"Ez a parancs annak elkerülésére hasznos, hogy a memóriában\n" +"lévő adatok másolata bekerüljön az adatbázisba.\n" +"Normál leállításokhoz használd kérlek a\n" +"SHUTDOWN parancsot!\n" +"\n" +"Korlátozva Services Operatoroknak." + +#: modules/commands/os_reload.cpp:47 +#, fuzzy +msgid "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." +msgstr "" +"Syntax: RELOAD\n" +"\n" +"Újratölti a Szervíz konfigurációs fájlját. Jegyzet: néhány\n" +"direktívának ettől függetlenül restart kell, hogy hatása\n" +"életbe lépjen. (Például a Szervíz egységek nicknév váltása \n" +"vagy session korlátozás aktíválása, stb.)\n" +"\n" +"Korlátozva Szervíz adminoknak." + +#: modules/commands/os_shutdown.cpp:62 +#, fuzzy +msgid "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." +msgstr "" +"Syntax: RESTART\n" +"\n" +"Menti a Szervíz adatbázisát, majd újraindítja a programot.\n" +"(Kilép, majd újraindul.)\n" +"\n" +"Korlátozva Szervíz adminoknak.\t" + +#: modules/commands/os_shutdown.cpp:89 +#, fuzzy +msgid "Causes Services to save all databases and then shut down." +msgstr "" +"Syntax: SHUTDOWN\n" +"\n" +"Menti a Szervíz adatbázisát, majd leállítja a programot.\n" +"\n" +"Korlátozva Szervíz adminoknak." + +#: modules/commands/os_update.cpp:34 +#, fuzzy +msgid "" +"Causes Services to update all database files as soon as you\n" +"send the command." +msgstr "" +"Syntax: UPDATE\n" +"\n" +"Menti a Szervíz adatbázisát, azonnal amint kiadtad\n" +"a parancsot.\n" +"\n" +"Korlátozva Szervíz adminoknak." + +#: modules/commands/ns_cert.cpp:246 +#, fuzzy, c-format +msgid "Certificate list for %s:" +msgstr "%s hozzáférési listája:" + +#: modules/commands/cs_set.cpp:528 modules/commands/cs_set.cpp:570 +msgid "ChanServ is required to enable persist on this network." +msgstr "" + +#: modules/commands/os_mode.cpp:19 +#, fuzzy +msgid "Change channel modes" +msgstr "%s váltóztatott a módodon." + +#: modules/commands/ns_set.cpp:905 +#, fuzzy +msgid "Change the communication method of Services" +msgstr " MSG Megváltoztatja a szervízzel való kommunikációt" + +#: modules/commands/os_mode.cpp:146 +#, fuzzy +msgid "Change user modes" +msgstr "%s váltóztatott a módodon." + +#: modules/commands/os_mode.cpp:161 +#, fuzzy, c-format +msgid "Changed usermodes of %s to %s." +msgstr "%s usermódjai megváltoztatva." + +#: modules/commands/ns_set.cpp:411 +#, fuzzy +msgid "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." +msgstr "" +"Syntax: SET DISPLAY új-megjelenítés\n" +"\n" +"Megváltoztatja a nicknév csoportod megjelenítését a \n" +"szervízben.\tAz új megjelenítésnek a csoport egyik\n" +"nickjének KELL lennie." + +#: modules/commands/ns_set.cpp:387 +#, fuzzy +msgid "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." +msgstr "" +"Syntax: SET DISPLAY új-megjelenítés\n" +"\n" +"Megváltoztatja a nicknév csoportod megjelenítését a \n" +"szervízben.\tAz új megjelenítésnek a csoport egyik\n" +"nickjének KELL lennie." + +#: modules/commands/cs_set.cpp:324 +#, fuzzy +msgid "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." +msgstr "" +"Syntax: %s #szoba FOUNDER nick\n" +"\n" +"Megváltoztatja a szoba founderjét.\n" +"Az új nicknév regisztrált kell hogy legyen!" + +#: modules/commands/ns_set.cpp:884 +#, fuzzy +msgid "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Syntax: SET LANGUAGE sorszám\n" +"Megváltoztatja a SERVICES nyelvezetét, amin az üzenteket\n" +"írja.(Például: amikor válaszol egy parancsra, amit te \n" +"adtál ki). A sorszám alapján válaszd ki a nyelvezetet:" + +#: modules/commands/ns_set.cpp:848 +#, fuzzy +msgid "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Syntax: SET LANGUAGE sorszám\n" +"Megváltoztatja a SERVICES nyelvezetét, amin az üzenteket\n" +"írja.(Például: amikor válaszol egy parancsra, amit te \n" +"adtál ki). A sorszám alapján válaszd ki a nyelvezetet:" + +#: modules/commands/ns_set.cpp:227 +#, fuzzy +msgid "Changes the password used to identify as the nick's owner." +msgstr "" +"Syntax: SET PASSWORD új-jelszó\n" +"\n" +"Megváltoztatja a nicknév tulajdonosának jelszavát." + +#: modules/commands/ns_set.cpp:161 +#, fuzzy +msgid "" +"Changes the password used to identify you as the nick's\n" +"owner." +msgstr "" +"Syntax: SET PASSWORD új-jelszó\n" +"\n" +"Megváltoztatja a nicknév tulajdonosának jelszavát." + +#: modules/commands/cs_set.cpp:1017 +#, fuzzy +msgid "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." +msgstr "" +"Syntax: %s #szoba SUCCESSOR nick\n" +"\n" +"Megváltoztatja a successort a csatornán. Ha a founder neve\n" +"elévül vagy törlődik, de a szoba még regisztrált, akkor\n" +"a successor lesz a szoba új founderje.\n" +"Ha, a successornak már túl sok regisztrált csatornája van \n" +"(%d), a csatornának megszűnik a regisztrációja, akkor\n" +"is ez történik, ha nem volt megadva successor.\n" +"A nicknek regisztrálnak kell lennie." + +#: modules/commands/ns_alist.cpp:48 modules/commands/ns_ajoin.cpp:100 +#, fuzzy +msgid "Channel" +msgstr "DROP #szoba" + +#: include/language.h:84 +#, fuzzy, c-format +msgid "Channel %s doesn't exist." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_drop.cpp:63 +#, c-format +msgid "Channel %s has been dropped." +msgstr "%s csatorna regisztrációjának törlése sikerült." + +#: modules/commands/cs_getkey.cpp:43 +#, fuzzy, c-format +msgid "Channel %s has no key." +msgstr "The channel %s has no key." + +#: modules/commands/cs_register.cpp:47 +#, c-format +msgid "Channel %s is already registered!" +msgstr "A megadott csatorna %s már regisztrált!" + +#: modules/commands/os_forbid.cpp:524 +#, fuzzy, c-format +msgid "Channel %s is forbidden by %s: %s" +msgstr "Ez a szoba a %s adatbázisában regisztrált." + +#: modules/commands/os_forbid.cpp:526 +#, fuzzy, c-format +msgid "Channel %s is forbidden." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_set.cpp:580 +#, fuzzy, c-format +msgid "Channel %s is no longer persistent." +msgstr "Channel %s is no longer persistant." + +#: modules/commands/cs_set.cpp:542 +#, fuzzy, c-format +msgid "Channel %s is now persistent." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_suspend.cpp:180 +#, c-format +msgid "Channel %s is now released." +msgstr "(%s) szoba újra használható." + +#: modules/commands/cs_suspend.cpp:125 +#, c-format +msgid "Channel %s is now suspended." +msgstr "(%s) szoba használata felfüggesztve." + +#: include/language.h:83 +#, fuzzy, c-format +msgid "Channel %s isn't registered." +msgstr "Ez a csatorna %s nem regisztrálható. " + +#: modules/commands/cs_suspend.cpp:172 +#, fuzzy, c-format +msgid "Channel %s isn't suspended." +msgstr "(%s) szoba használata felfüggesztve." + +#: modules/commands/cs_register.cpp:68 +#, fuzzy, c-format +msgid "Channel %s registered under your account: %s" +msgstr "Ez a nicknév: %s számodra lett regisztrálva: %s" + +#: modules/commands/cs_set.cpp:1078 +#, c-format +msgid "Channel %s will expire." +msgstr "A megadott csatorna (%s) el fog évülni." + +#: modules/commands/cs_set.cpp:1072 +#, c-format +msgid "Channel %s will not expire." +msgstr "A megadott csatorna (%s) nem fog elévülni." + +#: modules/commands/cs_xop.cpp:475 +#, fuzzy, c-format +msgid "Channel %s %s list has been cleared." +msgstr "Channel %s AOP list has been cleared." + +#: modules/commands/cs_access.cpp:486 modules/commands/cs_flags.cpp:361 +#, c-format +msgid "Channel %s access list has been cleared." +msgstr "Channel %s access list has been cleared." + +#: modules/commands/cs_akick.cpp:428 +#, c-format +msgid "Channel %s akick list has been cleared." +msgstr "Channel %s akick list has been cleared." + +#: modules/commands/cs_mode.cpp:444 +#, fuzzy, c-format +msgid "Channel %s has no mode locks." +msgstr "(%s) szoba újra használható." + +#: include/language.h:82 +#, fuzzy, c-format +msgid "Channel %s is currently suspended." +msgstr "(%s) szoba használata felfüggesztve." + +#: include/language.h:101 +#, fuzzy, c-format +msgid "Channel %s is not a valid channel." +msgstr "%s nem érvényes ban típus." + +#: modules/commands/os_list.cpp:70 +#, fuzzy +msgid "Channel list:" +msgstr "Botok listája:" + +#: modules/extra/stats/cs_fantasy_stats.cpp:148 +#, fuzzy, c-format +msgid "Channel stats for %s on %s:" +msgstr "" +"Azon csatornák, ahol %s nicknek hozzáférése van:\n" +" Sorszám Csatorna Szint Meghatározás" + +#: modules/commands/cs_access.cpp:142 modules/commands/cs_flags.cpp:97 +#: modules/commands/cs_xop.cpp:139 +#, fuzzy +msgid "Channels may not be on access lists." +msgstr "%s nem található a (%s) csatorna hozzáférési listáján." + +#: modules/commands/ns_alist.cpp:114 +#, fuzzy, c-format +msgid "Channels that %s has access on:" +msgstr "" +"Azon csatornák, ahol %s nicknek hozzáférése van:\n" +" Sorszám Csatorna Szint Meghatározás" + +#: modules/commands/os_stats.cpp:181 +#, c-format +msgid "Channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:517 +#: modules/extra/stats/m_chanstats.cpp:525 +msgid "Chanstats" +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:102 +#, fuzzy, c-format +msgid "Chanstats statistics are now disabled for %s" +msgstr " SECURE A nickneved védelmének be-,kikapcsolása" + +#: modules/extra/stats/m_chanstats.cpp:51 +msgid "Chanstats statistics are now disabled for this channel." +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:104 +#, fuzzy +msgid "Chanstats statistics are now disabled for your nick." +msgstr " SECURE A nickneved védelmének be-,kikapcsolása" + +#: modules/extra/stats/m_chanstats.cpp:93 +#, fuzzy, c-format +msgid "Chanstats statistics are now enabled for %s" +msgstr " SECURE A nickneved védelmének be-,kikapcsolása" + +#: modules/extra/stats/m_chanstats.cpp:44 +msgid "Chanstats statistics are now enabled for this channel." +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:95 +#, fuzzy +msgid "Chanstats statistics are now enabled for your nick." +msgstr " SECURE A nickneved védelmének be-,kikapcsolása" + +#: modules/commands/cs_seen.cpp:367 +msgid "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." +msgstr "" + +#: modules/commands/ms_check.cpp:19 +#, fuzzy +msgid "Checks if last memo to a nick was read" +msgstr " CHECK Ellenőrzi, hogy a címzett elolvasta-e már az üzit" + +#: modules/commands/ms_check.cpp:69 +#, fuzzy +msgid "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." +msgstr "" +"Syntax: CHECK nick\n" +"\n" +"Ellenőrzi, hogy az _utolsó_ üzenet, amit a nick számára\n" +"küldtél már olvasott-e vagy még olvasatlan.\n" +"Megjegyzés, ez csak nickekkel működik szobákkal nem." + +#: modules/commands/os_info.cpp:227 +#, c-format +msgid "Cleared info from %s." +msgstr "" + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1153 +#: modules/commands/bs_kick.cpp:1156 +#, fuzzy +msgid "Colors kicker" +msgstr "KICK Konfigurálja a kirúgásokat" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Command" +msgstr "%s parancsok:" + +#: modules/commands/bs_kick.cpp:251 +#, fuzzy +msgid "Configures AMSG kicker" +msgstr "KICK Konfigurálja a kirúgásokat" + +#: modules/commands/bs_kick.cpp:287 +#, fuzzy +msgid "Configures badwords kicker" +msgstr "KICK Konfigurálja a kirúgásokat" + +#: modules/commands/bs_kick.cpp:326 +#, fuzzy +msgid "Configures bolds kicker" +msgstr "KICK Konfigurálja a kirúgásokat" + +#: modules/commands/bs_kick.cpp:132 +#, fuzzy +msgid "Configures bot kickers. option can be one of:" +msgstr "" +"Syntax: SET opció paraméterek\n" +"\n" +"Beállítható nicknév opciók. Az opció ezek egyike lehet:" + +#: modules/commands/bs_set.cpp:19 +#, fuzzy +msgid "Configures bot options" +msgstr "SET Konfigurálja a bot opcióit" + +#: modules/commands/bs_set.cpp:32 +#, fuzzy +msgid "" +"Configures bot options.\n" +" \n" +"Available options:" +msgstr "SET Konfigurálja a bot opcióit" + +#: modules/commands/bs_kick.cpp:360 +#, fuzzy +msgid "Configures caps kicker" +msgstr "KICK Konfigurálja a kirúgásokat" + +#: modules/commands/cs_log.cpp:105 +#, fuzzy +msgid "Configures channel logging settings" +msgstr "* Nem lehet új csatornát regisztrálni." + +#: modules/commands/bs_kick.cpp:456 +#, fuzzy +msgid "Configures color kicker" +msgstr "KICK Konfigurálja a kirúgásokat" + +#: modules/commands/bs_kick.cpp:490 +#, fuzzy +msgid "Configures flood kicker" +msgstr "KICK Konfigurálja a kirúgásokat" + +#: modules/commands/bs_kick.cpp:588 +#, fuzzy +msgid "Configures italics kicker" +msgstr "KICK Konfigurálja a kirúgásokat" + +#: modules/commands/bs_kick.cpp:119 +#, fuzzy +msgid "Configures kickers" +msgstr "KICK Konfigurálja a kirúgásokat" + +#: modules/commands/bs_kick.cpp:622 +#, fuzzy +msgid "Configures repeat kicker" +msgstr "KICK Konfigurálja a kirúgásokat" + +#: modules/commands/bs_kick.cpp:723 +#, fuzzy +msgid "Configures reverses kicker" +msgstr "KICK Konfigurálja a kirúgásokat" + +#: modules/commands/bs_set.cpp:90 +#, fuzzy +msgid "Configures the time bot bans expire in" +msgstr "SET Konfigurálja a bot opcióit" + +#: modules/commands/bs_kick.cpp:757 +#, fuzzy +msgid "Configures underlines kicker" +msgstr "KICK Konfigurálja a kirúgásokat" + +#: modules/commands/ns_register.cpp:21 +#, fuzzy +msgid "Confirm a passcode" +msgstr " CONFIRM Confirm a nickserv auth code" + +#: modules/commands/cs_mode.cpp:733 +#, fuzzy +msgid "Control modes and mode locks on a channel" +msgstr " CLEARMODES Törli a szoba módot" + +#: modules/commands/cs_entrymsg.cpp:239 +msgid "" +"Controls what messages will be sent to users when they join the channel." +msgstr "" + +#: modules/commands/cs_clone.cpp:242 +msgid "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." +msgstr "" + +#: modules/commands/cs_clone.cpp:114 +#, fuzzy +msgid "Copy all settings from one channel to another" +msgstr "" +" UNBAN Remove all bans preventing a user from entering a channel" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/bs_info.cpp:57 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Created" +msgstr "Született: %s" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_ignore.cpp:266 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_news.cpp:156 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Creator" +msgstr "Született: %s" + +#: modules/commands/os_sxline.cpp:180 +#, fuzzy, c-format +msgid "Current %s list:" +msgstr "Aktuális AKILL lista:" + +#: modules/commands/os_akill.cpp:323 +#, fuzzy +msgid "Current AKILL list:" +msgstr "Aktuális AKILL lista:" + +#: modules/commands/os_session.cpp:493 +msgid "Current Session Limit Exception list:" +msgstr "Aktuális Session korlát kivétel lista:" + +#: modules/commands/os_modinfo.cpp:116 +#, fuzzy +msgid "Current module list:" +msgstr "Jelenlegi Modul lista:" + +#: modules/commands/os_stats.cpp:69 +#, c-format +msgid "Current number of AKILLs: %d" +msgstr "Aktuális AKILLek száma: %d" + +#: modules/commands/os_stats.cpp:89 +#, c-format +msgid "Current number of SNLINEs: %d" +msgstr "Aktuális SNLINEok száma: %d" + +#: modules/commands/os_stats.cpp:109 +#, c-format +msgid "Current number of SQLINEs: %d" +msgstr "Aktuális SQLINEok száma : %d" + +#: modules/commands/os_stats.cpp:138 +#, c-format +msgid "Current users: %d (%d ops)" +msgstr "Aktuális felhasználók: %d (%d op)" + +#: modules/commands/os_oper.cpp:71 +#, fuzzy +msgid "DEL oper" +msgstr "DEL ." + +#: modules/commands/os_info.cpp:103 +#, fuzzy +msgid "DEL target info" +msgstr "GROUP célnick jelszó" + +#: modules/commands/ns_ajoin.cpp:232 +#, fuzzy +msgid "DEL [nickname] channel" +msgstr "MODE szoba mód" + +#: modules/commands/ns_cert.cpp:259 +#, fuzzy +msgid "DEL [nickname] fingerprint" +msgstr "FORBID nicknév indok" + +#: modules/commands/ns_access.cpp:103 +#, fuzzy +msgid "DEL [nickname] mask" +msgstr "MODE szoba mód" + +#: modules/commands/os_sxline.cpp:426 modules/commands/os_sxline.cpp:660 +#: modules/commands/os_akill.cpp:387 +#, fuzzy +msgid "DEL {mask | entry-num | list | id}" +msgstr "DEL [#szoba] { szám | list | ALL}" + +#: modules/commands/os_session.cpp:524 +#, fuzzy +msgid "DEL {mask | entry-num | list}" +msgstr "DEL [#szoba] { szám | list | ALL}" + +#: modules/commands/os_ignore.cpp:343 +#, fuzzy +msgid "DEL {nick|mask}" +msgstr "DEL ." + +#: modules/commands/os_news.cpp:279 +#, fuzzy +msgid "DEL {num | ALL}" +msgstr "Syntax: OPERNEWS DEL {szám | ALL}" + +#: modules/commands/os_forbid.cpp:158 +msgid "DEL {NICK|CHAN|EMAIL|REGISTER} entry" +msgstr "" + +#: modules/commands/os_dns.cpp:666 +msgid "DELIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:664 +msgid "DELSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:662 +msgid "DELZONE zone.name" +msgstr "" + +#: modules/commands/os_dns.cpp:669 +#, fuzzy +msgid "DEPOOL server.name" +msgstr "NOOP {SET|REVOKE} szerver" + +#: modules/commands/cs_seen.cpp:162 +#, c-format +msgid "Database cleared, removed %lu nicks that were added after %s." +msgstr "" + +#: modules/commands/ms_list.cpp:64 +msgid "Date/Time" +msgstr "" + +#: modules/commands/hs_off.cpp:49 +#, fuzzy +msgid "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." +msgstr "" +"Syntax: OFF\n" +"Kikapcsolja a vhostodat,ez most társitva van a nickedhez.\n" +"Ha valaki használ /whois parancsot a nickeden, akkor a\n" +"valós IP címed vagy hosztod fogja látni." + +#: modules/commands/hs_off.cpp:19 +#, fuzzy +msgid "Deactivates your assigned vhost" +msgstr " OFF Kikapcsolja a társított vhostot" + +#: modules/commands/os_stats.cpp:72 +#, c-format +msgid "Default AKILL expiry time: %d days" +msgstr "Alap AKILL lejárati idő: %d nap" + +#: modules/commands/os_stats.cpp:76 +#, c-format +msgid "Default AKILL expiry time: %d hours" +msgstr "Alap AKILL lejárati idő: %d óra" + +#: modules/commands/os_stats.cpp:80 +#, c-format +msgid "Default AKILL expiry time: %d minutes" +msgstr "Alap AKILL lejárati idő: %d perc" + +#: modules/commands/os_stats.cpp:74 +msgid "Default AKILL expiry time: 1 day" +msgstr "Alap AKILL lejárati idő: 1 nap" + +#: modules/commands/os_stats.cpp:78 +msgid "Default AKILL expiry time: 1 hour" +msgstr "Alap AKILL lejárati idő: 1 óra" + +#: modules/commands/os_stats.cpp:82 +msgid "Default AKILL expiry time: 1 minute" +msgstr "Alap AKILL lejárati idő: 1 perc" + +#: modules/commands/os_stats.cpp:84 +msgid "Default AKILL expiry time: No expiration" +msgstr "Alap AKILL lejárati idő: Nem elévülő" + +#: modules/commands/os_stats.cpp:92 +#, c-format +msgid "Default SNLINE expiry time: %d days" +msgstr "Alap SNLINE lejárati idő: %d nap" + +#: modules/commands/os_stats.cpp:96 +#, c-format +msgid "Default SNLINE expiry time: %d hours" +msgstr "Alap SNLINE lejárati idő: %d óra" + +#: modules/commands/os_stats.cpp:100 +#, c-format +msgid "Default SNLINE expiry time: %d minutes" +msgstr "Alap SNLINE lejárati idő: %d perc" + +#: modules/commands/os_stats.cpp:94 +msgid "Default SNLINE expiry time: 1 day" +msgstr "Alap SNLINE lejárati idő: 1 nap" + +#: modules/commands/os_stats.cpp:98 +msgid "Default SNLINE expiry time: 1 hour" +msgstr "Alap SNLINE lejárati idő: 1 óra" + +#: modules/commands/os_stats.cpp:102 +msgid "Default SNLINE expiry time: 1 minute" +msgstr "Alap SNLINE lejárati idő: 1 perc" + +#: modules/commands/os_stats.cpp:104 +msgid "Default SNLINE expiry time: No expiration" +msgstr "Alap SNLINE lejárati ido: Nem elévülő" + +#: modules/commands/os_stats.cpp:112 +#, c-format +msgid "Default SQLINE expiry time: %d days" +msgstr "Alap SQLINE lejárati idő: %d nap" + +#: modules/commands/os_stats.cpp:116 +#, c-format +msgid "Default SQLINE expiry time: %d hours" +msgstr "Alap SQLINE lejárati idő: %d óra" + +#: modules/commands/os_stats.cpp:120 +#, c-format +msgid "Default SQLINE expiry time: %d minutes" +msgstr "Alap SQLINE lejárati idő: %d perc" + +#: modules/commands/os_stats.cpp:114 +msgid "Default SQLINE expiry time: 1 day" +msgstr "Alap SQLINE lejárati idő: 1 nap" + +#: modules/commands/os_stats.cpp:118 +msgid "Default SQLINE expiry time: 1 hour" +msgstr "Alap SQLINE lejárati idő: 1 óra" + +#: modules/commands/os_stats.cpp:122 +msgid "Default SQLINE expiry time: 1 minute" +msgstr "Alap SQLINE lejárati idő: 1 perc" + +#: modules/commands/os_stats.cpp:124 +msgid "Default SQLINE expiry time: No expiration" +msgstr "Alap SQLINE lejárati idő Nem elévülő" + +#: modules/commands/os_news.cpp:351 +#, fuzzy +msgid "Define messages to be randomly shown to users at logon" +msgstr " LOGONNEWS Fellépő üzenetek beállítása" + +#: modules/commands/os_news.cpp:297 +#, fuzzy +msgid "Define messages to be shown to users at logon" +msgstr " LOGONNEWS Fellépő üzenetek beállítása" + +#: modules/commands/os_news.cpp:324 +#, fuzzy +msgid "Define messages to be shown to users who oper" +msgstr " OPERNEWS Operek részére megjelenő üzenetet állít be" + +#: modules/commands/ms_del.cpp:44 +#, fuzzy +msgid "Delete a memo or memos" +msgstr " DEL Törli a megadott üzenete(ke)t" + +#: modules/commands/hs_del.cpp:19 +#, fuzzy +msgid "Delete the vhost of another user" +msgstr " DEL Törli egy felhasználónak a vhostját" + +#: modules/commands/cs_xop.cpp:302 +#, fuzzy, c-format +msgid "Deleted %d entries from %s %s list." +msgstr "%d bejegyzés törölve a %s AOP listáról." + +#: modules/commands/cs_access.cpp:277 +#, c-format +msgid "Deleted %d entries from %s access list." +msgstr "%d bejegyzés törölve (%s) csatorna hozzáférési listájáról." + +#: modules/commands/cs_akick.cpp:228 +#, c-format +msgid "Deleted %d entries from %s autokick list." +msgstr "%d bejegyzés törölve a (%s) csatorna autokick listájáról." + +#: modules/commands/bs_badwords.cpp:170 +#, c-format +msgid "Deleted %d entries from %s bad words list." +msgstr "Törölve %d bejegyzés %s tiltott szavak listájáról." + +#: modules/commands/os_session.cpp:149 +#, c-format +msgid "Deleted %d entries from session-limit exception list." +msgstr "Törölve %d bejegyzés a session-korlát kivétel listáról." + +#: modules/commands/os_sxline.cpp:32 +#, fuzzy, c-format +msgid "Deleted %d entries from the %s list." +msgstr "%d bejegyzés törölve a %s AOP listáról." + +#: modules/commands/os_akill.cpp:33 +#, c-format +msgid "Deleted %d entries from the AKILL list." +msgstr "Törölve %d bejegyzés az AKILL listáról." + +#: modules/commands/cs_access.cpp:275 +#, c-format +msgid "Deleted 1 entry from %s access list." +msgstr "1 bejegyzés törölve a (%s) csatorna hozzáférési listájáról" + +#: modules/commands/cs_akick.cpp:226 +#, c-format +msgid "Deleted 1 entry from %s autokick list." +msgstr "1 bejegyzés törölve a (%s) csatorna autokick listájáról." + +#: modules/commands/bs_badwords.cpp:168 +#, c-format +msgid "Deleted 1 entry from %s bad words list." +msgstr "Törölve 1 bejegyzés %s tiltott szavak listájáról." + +#: modules/commands/os_session.cpp:147 +msgid "Deleted 1 entry from session-limit exception list." +msgstr "Törölve 1 bejegyzés a session-korlát kivétel listáról." + +#: modules/commands/os_sxline.cpp:30 +#, fuzzy, c-format +msgid "Deleted 1 entry from the %s list." +msgstr "Törölve 1 bejegyzés az AKILL listáról." + +#: modules/commands/os_akill.cpp:31 +msgid "Deleted 1 entry from the AKILL list." +msgstr "Törölve 1 bejegyzés az AKILL listáról." + +#: modules/commands/os_info.cpp:208 +#, fuzzy, c-format +msgid "Deleted info from %s." +msgstr "Törölve 1 bejegyzés az AKILL listáról." + +#: modules/commands/cs_xop.cpp:300 +#, fuzzy, c-format +msgid "Deleted one entry from %s %s list." +msgstr "1 bejegyzés törölve a %s AOP listáról." + +#: modules/commands/ms_del.cpp:129 +#, fuzzy +msgid "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Syntax: DEL [#szoba] {sorszám | list | LAST | ALL}\n" +"\n" +"Törli a megadott memo üzenete(ke)t. \n" +"Több számot is megadhatsz, intervallumot is használhatsz,\n" +"az egyszerű sorszám helyett.\n" +"\n" +"Ha a LAST meg van adva, az utolsó memo üzenetet törli\n" +"Ha az ALL van megadve, akkor minden memo üzenetet töröl.\n" +"\n" +"Példák:\n" +"\n" +"\tDEL 1\n" +"\t\tTörli az első memo üzenetet.\n" +"\n" +"\tDEL 2-5,7-9\n" +"\t\tTörli a memo üzeneteket 2 és 5, illetve 7 és 9 között." + +#: modules/commands/hs_del.cpp:48 +#, fuzzy +msgid "" +"Deletes the vhost assigned to the given nick from the\n" +"database." +msgstr "" +"Syntax: DEL \n" +"A vhost törölve az adott nick adatbázisából.\n" +"Korlátozva Hoszt változtatókra." + +#: modules/commands/hs_del.cpp:59 +#, fuzzy +msgid "Deletes the vhost for all nicks in a group" +msgstr " DELALL Törli a vhosztot a nickekröl a csoportban" + +#: modules/commands/hs_del.cpp:93 +#, fuzzy +msgid "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." +msgstr "" +"Syntax: DELALL .\n" +"Törlődik a vhost az összes nickről a csoportban ahol az\n" +"adott nick van és ez a vhosztot használta \n" +"\n" +"Korlátozva Hoszt változtatókra." + +#: modules/commands/os_dns.cpp:653 +#, c-format +msgid "Depooled %s." +msgstr "" + +#: modules/commands/cs_access.cpp:799 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_list.cpp:75 modules/commands/cs_info.cpp:53 +#, fuzzy +msgid "Description" +msgstr "%s csatorna leírás megváltoztatva: %s." + +#: modules/commands/cs_set.cpp:239 +#, c-format +msgid "Description of %s changed to %s." +msgstr "%s csatorna leírás megváltoztatva: %s." + +#: modules/commands/cs_set.cpp:245 +#, fuzzy, c-format +msgid "Description of %s unset." +msgstr "%s csatorna leírás megváltoztatva: %s." + +#: modules/commands/bs_kick.cpp:1115 modules/commands/bs_info.cpp:90 +#, fuzzy +msgid "Disabled" +msgstr "%s is enable" + +#: modules/commands/cs_suspend.cpp:134 +#, fuzzy +msgid "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." +msgstr "" +"Syntax: SUSPEND #szoba [indok]\n" +"Elutasít minden szobahasználatot. Lehet törölni a\n" +"UNSUSPEND paranccsal és akkor használható az öüsszes \n" +"megörzött szoba adat/beállítás.\n" +"\n" +"Indoklást kér némelyik hálózat.\n" +"\n" +"Korlátozva Szervíz adminnak." + +#: modules/commands/hs_request.cpp:337 +#, fuzzy, c-format +msgid "Displayed %d records (%d total)." +msgstr "Kiírja az összes bejegyzést (Számláló: %d)" + +#: modules/commands/hs_list.cpp:122 +#, fuzzy, c-format +msgid "Displayed all records (count: %d)." +msgstr "Kiírja az összes bejegyzést (Számláló: %d)" + +#: modules/commands/hs_list.cpp:120 +#, fuzzy, c-format +msgid "Displayed records from %d to %d." +msgstr "Kiírja a bejegyzéseket %d-tól %d-ig" + +#: modules/commands/hs_list.cpp:116 +#, fuzzy, c-format +msgid "Displayed records matching key %s (count: %d)." +msgstr "" +"Kiírja azokat a hosztokat melyben a %s szó szerepel.\n" +"(számláló: %d)" + +#: modules/commands/ns_info.cpp:19 +#, fuzzy +msgid "Displays information about a given nickname" +msgstr " INFO Displays information about a given nickname" + +#: modules/commands/ns_info.cpp:125 +#, fuzzy +msgid "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." +msgstr "" +"Syntax: INFO nicknév\n" +"\n" +"Megmutatja a nicknévvel kapcsolatos információkat, mint a\n" +"nick tulajdonosa, utoljára látott címe, regisztrálás ideje,\n" +"a nick opciókat. Ha beazonosítasz egy nickre, akkor minden \n" +"informaciót megkaphatsz az ALL paraméter használatával \n" +"és így látni fogod a rejtett információkat is." + +#: modules/commands/ms_info.cpp:19 +#, fuzzy +msgid "Displays information about your memos" +msgstr " INFO Kiírja az üzenetekkel kapcsolatos információkat" + +#: modules/commands/hs_list.cpp:19 +#, fuzzy +msgid "Displays one or more vhost entries" +msgstr " LIST Kiír egy vagy több vhost bejegyzést" + +#: modules/extra/stats/cs_fantasy_top.cpp:50 +#, fuzzy +msgid "Displays the top 10 users of a channel" +msgstr " FOUNDER A founder megváltoztatása" + +#: modules/extra/stats/cs_fantasy_top.cpp:73 +msgid "Displays the top 10 users of the network" +msgstr "" + +#: modules/extra/stats/cs_fantasy_top.cpp:38 +#, fuzzy +msgid "Displays the top 3 users of a channel" +msgstr " FOUNDER A founder megváltoztatása" + +#: modules/extra/stats/cs_fantasy_top.cpp:62 +msgid "Displays the top 3 users of the network" +msgstr "" + +#: modules/commands/help.cpp:33 +#, fuzzy +msgid "Displays this list and give information about commands" +msgstr " INFO Kiírja az üzenetekkel kapcsolatos információkat" + +#: modules/extra/stats/cs_fantasy_stats.cpp:39 +msgid "Displays your Channel Stats" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:51 +msgid "Displays your Global Stats" +msgstr "" + +#: modules/commands/bs_kick.cpp:1463 +msgid "Don't use AMSGs!" +msgstr "" + +#: modules/commands/bs_kick.cpp:1266 +msgid "Don't use bolds on this channel!" +msgstr "Nem használható kiemelt betű ezen a csatornán!" + +#: modules/commands/bs_kick.cpp:1274 +msgid "Don't use colors on this channel!" +msgstr "Nem szinezhetsz ezen a csatornán!" + +#: modules/commands/bs_kick.cpp:1290 +msgid "Don't use italics on this channel!" +msgstr "Don't use italics on this channel!" + +#: modules/commands/bs_kick.cpp:1282 +msgid "Don't use reverses on this channel!" +msgstr "Nem írj visszafelé ezen a csatornán!" + +#: modules/commands/bs_kick.cpp:1408 +#, c-format +msgid "Don't use the word \"%s\" on this channel!" +msgstr "Nem használható ez a szó: %s!" + +#: modules/commands/bs_kick.cpp:1298 +msgid "Don't use underlines on this channel!" +msgstr "Nem használj aláhúzásokat ezen a csatornán!" + +#: modules/commands/ns_drop.cpp:61 +msgid "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." +msgstr "" + +#: modules/commands/ns_set.cpp:513 +#, c-format +msgid "E-mail address for %s changed to %s." +msgstr "E-mail address for %s changed to %s." + +#: modules/commands/ns_set.cpp:519 +#, c-format +msgid "E-mail address for %s unset." +msgstr "E-mail address for %s unset." + +#: src/mail.cpp:80 +#, c-format +msgid "E-mail for %s is invalid." +msgstr "%sEmail címe nem érvényes." + +#: modules/commands/os_news.cpp:309 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Syntax: LOGONNEWS ADD text\n" +" LOGONNEWS DEL {num | ALL}\n" +" LOGONNEWS LIST\n" +"\n" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. (However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent.)\n" +"NewsCount can be configured in services.conf.\n" +"\n" +"LOGONNEWS may only be used by Services Operators." + +#: modules/commands/os_news.cpp:336 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Syntax: OPERNEWS ADD text\n" +" OPERNEWS DEL {num | ALL}\n" +" OPERNEWS LIST\n" +"\n" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. (However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent.)\n" +"NewsCount can be configured in services.conf.\n" +"\n" +"OPERNEWS may only be used by Services Operators." + +#: modules/commands/os_news.cpp:363 +#, fuzzy +msgid "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." +msgstr "" +"Syntax: RANDOMNEWS ADD szöveg\n" +" RANDOMNEWS DEL {sorszám | ALL}\n" +" RANDOMNEWS LIST\n" +"\n" +"Szerkeszti és listázza a random news üzeneteket. Amikor\n" +"egy felhasználó csatlakozik a hálózathoz, egy (csak egy)\n" +"random newst fog véletlenszerűen elküldeni részére.\n" +"\n" +"RANDOMNEWS may only be used by Services Operators." + +#: modules/commands/ns_info.cpp:98 +#, fuzzy +msgid "Email address" +msgstr "E-mail cím: %s" + +#: modules/commands/ns_getemail.cpp:41 +#, fuzzy, c-format +msgid "Email matched: %s (%s) to %s." +msgstr "Egyező emailek %s ehhez: %s." + +#: modules/fantasy.cpp:19 +msgid "Enable fantaisist commands" +msgstr "" + +#: modules/commands/greet.cpp:19 +msgid "Enable greet messages" +msgstr "" + +#: modules/commands/ns_set.cpp:568 +msgid "Enable or disable keep modes" +msgstr "" + +#: modules/commands/bs_kick.cpp:1114 modules/commands/bs_info.cpp:89 +#, fuzzy +msgid "Enabled" +msgstr "%s is enable" + +#: modules/commands/cs_set.cpp:124 +#, fuzzy, c-format +msgid "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." +msgstr "" +"Syntax: %s #szoba SECUREOPS {ON | OFF}\n" +"\n" +"Bekapcsolja vagy letiltja a secure ops opciót.\n" +"Amikor a secure ops be van kapcsolva, akkor azok, akik \n" +"nem szerepelnek a hozzáférési listán nem kaphatnak szoba\n" +"operátori státuszt." + +#: modules/commands/cs_set.cpp:388 +#, fuzzy +msgid "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." +msgstr "" +"Syntax: %s #szoba KEEPTOPIC {ON | OFF}\n" +"\n" +"Engedélyezi vagy letiltja a topic megtartása opciót a\n" +"szoba részére. Ha a topic megtartása be van állítva,\n" +"a topicot a %s megjegyzi miután az utolsó user elhagyja a\n" +"szobát, és visszaállítja a következő megnyitáskor." + +#: modules/commands/ns_set.cpp:643 +msgid "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." +msgstr "" + +#: modules/commands/ns_set.cpp:618 +msgid "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." +msgstr "" + +#: modules/commands/cs_set.cpp:733 +#, fuzzy +msgid "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." +msgstr "" +"Syntax: %s #szoba SECURE {ON | OFF}\n" +"\n" +"Engedélyezi vagy letitlja a %s biztonsági lehetőségeit\n" +"a szobában. Ha SECURE működik, csak azok a felhasználók\n" +"akik regisztráltak és beazonosítottak a %s-be a\t\n" +"jelszavukkal (használván az IDENTIFY parancsot) kaphatnak\n" +"a szobában jogokat, ha szerepelnek a hozzáférési listán." + +#: modules/commands/cs_set.cpp:932 +#, fuzzy +msgid "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." +msgstr "" +"Syntax: %s #szoba SIGNKICK {ON | SZINT | OFF}\n" +"\n" +"Engedélyezi vagy letiltja a signed kick opciót a csatornán\n" +"Amikor a SIGNKICK be van állítva, a %s KICK parancsával\n" +"végrehajtott kirúgásokban az indokban szerepel az op neve.\n" +"\n" +"Ha használod a LEVEL-t, akkor azok, akiknek a szintje\n" +"megegyezik vagy magasabb, mint a signkick szintje, azoknak\n" +"a neve nem fog szerepelni a kick indokjában.\n" +"Lásd még: /msg %s HELP LEVELS bővebb információkért. " + +#: modules/commands/cs_set.cpp:452 +#, fuzzy, c-format +msgid "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." +msgstr "" +"Syntax: %s #szoba PEACE {ON | OFF}\n" +"\n" +"Engedélyezi vagy letiltja a peace opciót.\n" +"Amikor a peace be van állítva, akkor a userek nem,\n" +"rúghatnak ki, tilthatnak ki olyan usert akinek az övékkel\n" +"egyenlő vagy magasabb szintje van a %s parancsokhoz." + +#: modules/commands/cs_list.cpp:232 +msgid "Enables or disables the private option for a channel." +msgstr "" + +#: modules/commands/cs_set.cpp:671 +#, fuzzy +msgid "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." +msgstr "" +"Syntax: %s #szoba RESTRICTED {ON | OFF}\n" +"\n" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." + +#: modules/commands/cs_set.cpp:796 +#, fuzzy +msgid "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." +msgstr "" +"Syntax: %s #szoba SECUREFOUNDER {ON | OFF}\n" +"\n" +"Engedélyezi vagy letiltja a secure founder opciót a \n" +"csatornán. Amikor a secure founder be van állítva, csak\n" +"a valódi founder tudja dropolni a csatornát, átírni a \n" +"szoba jelszavát, founderét, jogutódját, de azok nem,\n" +"akik csak az IDENTIFY parancsot használták a %s-ben." + +#: modules/commands/cs_set.cpp:860 +#, fuzzy +msgid "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." +msgstr "" +"Syntax: %s #szoba SECUREOPS {ON | OFF}\n" +"\n" +"Bekapcsolja vagy letiltja a secure ops opciót.\n" +"Amikor a secure ops be van kapcsolva, akkor azok, akik \n" +"nem szerepelnek a hozzáférési listán nem kaphatnak szoba\n" +"operátori státuszt." + +#: modules/commands/cs_topic.cpp:70 +#, fuzzy, c-format +msgid "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." +msgstr "" +"Syntax: %s #szoba KEEPTOPIC {ON | OFF}\n" +"\n" +"Engedélyezi vagy letiltja a topic megtartása opciót a\n" +"szoba részére. Ha a topic megtartása be van állítva,\n" +"a topicot a %s megjegyzi miután az utolsó user elhagyja a\n" +"szobát, és visszaállítja a következő megnyitáskor." + +#: modules/commands/cs_set.cpp:592 +#, fuzzy, c-format +msgid "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." +msgstr "" +"Syntax: %s channel PERSIST {ON | OFF}\n" +"Enables or disables the persistant channel setting.\n" +"When persistant is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +"\n" +"If your IRCd does not a permanent (persistant) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +"\n" +"If this network does not have BotServ enabled and does\n" +"not have a permanent channel mode, ChanServ will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +"\n" +"If your IRCd has a permanent (persistant) channel mode\n" +"and is is set or unset (for any reason, including MLOCK),\n" +"persist is automatically set and unset for the channel aswell.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." + +#: modules/commands/os_akill.cpp:331 +#, fuzzy +msgid "End of AKILL list." +msgstr "Vége a felhasználó listának." + +#: modules/commands/cs_access.cpp:444 +#, fuzzy +msgid "End of access list" +msgstr "Hozzáférési lista vége." + +#: modules/commands/cs_flags.cpp:347 +#, fuzzy, c-format +msgid "End of access list - %d/%d entries shown." +msgstr "Lista vége - %d / %d találat megjelenítve." + +#: modules/commands/cs_flags.cpp:345 +msgid "End of access list." +msgstr "Hozzáférési lista vége." + +#: modules/commands/cs_akick.cpp:379 +#, fuzzy +msgid "End of autokick list" +msgstr "Hozzáférési lista vége." + +#: modules/commands/bs_badwords.cpp:257 +#, fuzzy +msgid "End of bad words list." +msgstr "Vége a felhasználó listának." + +#: modules/commands/os_list.cpp:100 +#, fuzzy, c-format +msgid "End of channel list. %u channels shown." +msgstr "Lista vége - %d / %d találat megjelenítve." + +#: modules/commands/os_config.cpp:117 +msgid "End of configuration." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:134 +#, fuzzy +msgid "End of entry message list." +msgstr "Vége a felhasználó listának." + +#: modules/commands/os_forbid.cpp:407 +#, fuzzy, c-format +msgid "End of forbid list - %d/%d entries shown." +msgstr "Lista vége - %d / %d találat megjelenítve." + +#: modules/commands/os_forbid.cpp:405 +#, fuzzy +msgid "End of forbid list." +msgstr "Vége a felhasználó listának." + +#: modules/commands/ns_alist.cpp:119 +#, fuzzy, c-format +msgid "End of list - %d channels shown." +msgstr "Lista vége - %d / %d találat megjelenítve." + +#: modules/commands/ns_list.cpp:131 modules/commands/cs_list.cpp:130 +#, c-format +msgid "End of list - %d/%d matches shown." +msgstr "Lista vége - %d / %d találat megjelenítve." + +#: modules/commands/os_news.cpp:176 +#, fuzzy +msgid "End of news list." +msgstr "Vége a felhasználó listának." + +#: modules/commands/os_list.cpp:235 +#, fuzzy, c-format +msgid "End of users list. %u users shown." +msgstr "Lista vége - %d / %d találat megjelenítve." + +#: modules/commands/cs_enforce.cpp:227 +msgid "Enforce various channel modes and set options" +msgstr "" + +#: modules/commands/cs_enforce.cpp:263 +msgid "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." +msgstr "" + +#: src/language.cpp:43 modules/commands/ns_set.cpp:836 +#: modules/commands/ns_set.cpp:856 modules/commands/ns_set.cpp:891 +msgid "English" +msgstr "Magyar" + +#: modules/commands/cs_entrymsg.cpp:170 +#, fuzzy, c-format +msgid "Entry message %i for %s deleted." +msgstr "Greet message for %s unset." + +#: modules/commands/cs_entrymsg.cpp:177 +#, fuzzy, c-format +msgid "Entry message %s not found on channel %s." +msgstr "Fantasy mód most ON a %s csatornán." + +#: modules/commands/cs_entrymsg.cpp:147 +#, fuzzy, c-format +msgid "Entry message added to %s" +msgstr "Greet message for %s changed to %s." + +#: modules/commands/cs_entrymsg.cpp:109 modules/commands/cs_entrymsg.cpp:158 +#, fuzzy, c-format +msgid "Entry message list for %s is empty." +msgstr "Access list for %s is empty." + +#: modules/commands/cs_entrymsg.cpp:113 +#, fuzzy, c-format +msgid "Entry message list for %s:" +msgstr "%s hozzáférési listája:" + +#: modules/commands/cs_entrymsg.cpp:187 +#, fuzzy, c-format +msgid "Entry messages for %s have been cleared." +msgstr "Minden üzenetet töröltem a %s csatornán." + +#: modules/commands/os_reload.cpp:39 +#, fuzzy, c-format +msgid "Error reloading configuration file: %s" +msgstr " RELOAD Újratölti a szervíz Konfigurációs fájlját" + +#: include/language.h:125 +#, c-format +msgid "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." +msgstr "" + +#: include/language.h:124 +#, c-format +msgid "" +"Error! The vHost is too long, please use a hostname shorter than %d " +"characters." +msgstr "" + +#: modules/commands/ns_cert.cpp:325 +msgid "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." +msgstr "" + +#: modules/commands/os_session.cpp:358 +#, c-format +msgid "Exception for %s has been updated to %d." +msgstr "Exception for %s has been updated to %d." + +#: modules/pseudoclients/chanserv.cpp:465 +#: modules/pseudoclients/nickserv.cpp:557 +#: modules/pseudoclients/nickserv.cpp:562 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_session.cpp:514 modules/commands/ns_group.cpp:327 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Expires" +msgstr "Expires in: %s" + +#: src/xline.cpp:397 +#, fuzzy, c-format +msgid "Expiry and reason updated for %s." +msgstr "Exception for %s has been updated to %d." + +#: src/xline.cpp:400 +#, fuzzy, c-format +msgid "Expiry for %s updated." +msgstr "Lejárati idő megváltozott: %s." + +#: modules/fantasy.cpp:214 +msgid "Fantasy" +msgstr "Fantasy" + +#: modules/fantasy.cpp:60 +#, fuzzy, c-format +msgid "Fantasy mode is now off on channel %s." +msgstr "Fantasy mód most ON a %s csatornán." + +#: modules/fantasy.cpp:52 +#, fuzzy, c-format +msgid "Fantasy mode is now on on channel %s." +msgstr "Fantasy mód most ON a %s csatornán." + +#: modules/commands/cs_status.cpp:19 +#, fuzzy +msgid "Find a user's status on a channel" +msgstr " DEOWNER Removes your owner status on a channel" + +#: modules/commands/ns_cert.cpp:192 +#, fuzzy, c-format +msgid "Fingerprint %s already present on %s's certificate list." +msgstr "Ez a maszk: %s már szerepel a hozzáférési listádon." + +#: modules/commands/ns_cert.cpp:198 +#, fuzzy, c-format +msgid "Fingerprint %s is already in use." +msgstr "You are already in %s! " + +#: modules/commands/cs_flags.cpp:301 +msgid "Flags" +msgstr "" + +#: modules/commands/cs_flags.cpp:286 +#, fuzzy, c-format +msgid "Flags for %s on %s set to +%s" +msgstr "%s hozzáférése a (%s) csatornán változott: %d." + +#: modules/commands/cs_flags.cpp:341 +#, fuzzy, c-format +msgid "Flags list for %s" +msgstr "%s hozzáférési listája:" + +#: modules/commands/bs_kick.cpp:1161 modules/commands/bs_kick.cpp:1163 +#: modules/commands/bs_kick.cpp:1166 +#, fuzzy +msgid "Flood kicker" +msgstr "\tFloodért kirúgás: %s" + +#: modules/commands/os_forbid.cpp:421 +msgid "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." +msgstr "" + +#: modules/commands/os_forbid.cpp:354 +#, fuzzy +msgid "Forbid list is empty." +msgstr "Mellőzöttek lista üres." + +#: modules/commands/os_forbid.cpp:396 +#, fuzzy +msgid "Forbid list:" +msgstr "Botok listája:" + +#: modules/commands/os_forbid.cpp:348 +#, c-format +msgid "Forbid on %s was not found." +msgstr "" + +#: modules/commands/os_forbid.cpp:156 +msgid "Forbid usage of nicknames, channels, and emails" +msgstr "" + +#: modules/commands/os_update.cpp:19 +#, fuzzy +msgid "Force the Services databases to be updated immediately" +msgstr "" +" UPDATE A Szervíz adatbázist frissíti, felülírja\n" +" lemezre közvetlenül" + +#: modules/commands/os_svs.cpp:19 +#, fuzzy +msgid "Forcefully change a user's nickname" +msgstr " SVSNICK Megváltoztatja a felhasználó nicknevét" + +#: modules/commands/os_svs.cpp:68 +#, fuzzy +msgid "Forcefully changes a user's nickname from nick to newnick." +msgstr "" +"Syntax: SVSNICK nick újnick\n" +"\n" +"Erőszakkal meváltóztatja a user nickevét újnicknévre." + +#: modules/commands/os_svs.cpp:78 +#, fuzzy +msgid "Forcefully join a user to a channel" +msgstr " SVSNICK Megváltoztatja a felhasználó nicknevét" + +#: modules/commands/os_svs.cpp:112 +#, fuzzy +msgid "Forcefully join a user to a channel." +msgstr " SVSNICK Megváltoztatja a felhasználó nicknevét" + +#: modules/commands/os_svs.cpp:122 +#, fuzzy +msgid "Forcefully part a user from a channel" +msgstr " KICK Kirúgja a felhasználót csatornáról" + +#: modules/commands/os_svs.cpp:160 +#, fuzzy +msgid "Forcefully part a user from a channel." +msgstr " KICK Kirúgja a felhasználót csatornáról" + +#: modules/commands/ns_alist.cpp:64 modules/commands/cs_info.cpp:47 +#, fuzzy +msgid "Founder" +msgstr "Founderjog védelme" + +#: modules/commands/cs_set.cpp:315 +#, fuzzy, c-format +msgid "Founder of %s changed to %s." +msgstr "A megadott csatorna (%s) új foundere: %s." + +#: modules/commands/ns_getpass.cpp:41 +msgid "GETPASS command unavailable because encryption is in use." +msgstr "GETPASS nem elérhető, amíg az encryption használatban van" + +#: modules/commands/ns_recover.cpp:84 +msgid "Ghost with your nick has been killed." +msgstr "A befagyott kliens killelve." + +#: modules/commands/os_oline.cpp:19 +#, fuzzy +msgid "Give Operflags to a certain user" +msgstr " OLINE Operflaget ad a biztos felhasználónak" + +#: modules/commands/cs_mode.cpp:905 +#, c-format +msgid "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." +msgstr "" + +#: modules/commands/cs_mode.cpp:888 +#, fuzzy, c-format +msgid "Gives you or the specified nick %s status on a channel" +msgstr " OWNER Gives you owner status on channel" + +#: modules/commands/greet.cpp:206 modules/commands/greet.cpp:212 +msgid "Greet" +msgstr "Üdvözlés" + +#: src/access.cpp:38 +#, fuzzy +msgid "Greet message displayed on join" +msgstr "Greet message for %s changed to %s." + +#: modules/commands/greet.cpp:112 +#, c-format +msgid "Greet message for %s changed to %s." +msgstr "Greet message for %s changed to %s." + +#: modules/commands/greet.cpp:118 +#, c-format +msgid "Greet message for %s unset." +msgstr "Greet message for %s unset." + +#: modules/commands/greet.cpp:60 +#, fuzzy, c-format +msgid "Greet mode is now off on channel %s." +msgstr "Üdvözlő mód most ON a %s szobán." + +#: modules/commands/greet.cpp:52 +#, fuzzy, c-format +msgid "Greet mode is now on on channel %s." +msgstr "Üdvözlő mód most ON a %s szobán." + +#: modules/commands/ns_resetpass.cpp:21 +#, fuzzy +msgid "Helps you reset lost passwords" +msgstr " RESETPASS Helps you reset lost passwords." + +#: modules/commands/ns_info.cpp:141 +#, fuzzy +msgid "Hide certain pieces of nickname information" +msgstr " HIDE A nicknévhez tartozó információk elrejtése" + +#: modules/commands/cs_list.cpp:180 +#, fuzzy +msgid "Hide channel from the LIST command" +msgstr " PRIVATE A szoba elrejtése a listából" + +#: modules/commands/os_session.cpp:192 +msgid "Host" +msgstr "" + +#: modules/commands/os_session.cpp:207 +#, c-format +msgid "Hosts with at least %d sessions:" +msgstr "Hosztok legalább %d sessionnel:" + +#: modules/commands/cs_seen.cpp:207 +#, c-format +msgid "I don't know who %s is." +msgstr "" + +#: modules/commands/cs_seen.cpp:253 +#, fuzzy, c-format +msgid "I've never seen %s on this channel." +msgstr "Nem írj visszafelé ezen a csatornán!" + +#: modules/commands/os_sxline.cpp:203 modules/commands/os_akill.cpp:360 +msgid "ID" +msgstr "" + +#: modules/commands/os_oper.cpp:72 +msgid "INFO [type]" +msgstr "" + +#: modules/commands/os_dns.cpp:218 +msgid "IP" +msgstr "" + +#: modules/commands/os_dns.cpp:500 +#, fuzzy, c-format +msgid "IP %s already exists for %s." +msgstr "%s nevű bot már létezik." + +#: modules/commands/os_dns.cpp:562 +#, fuzzy, c-format +msgid "IP %s does not exist for %s." +msgstr "%s nevű bot már létezik." + +#: modules/commands/ns_identify.cpp:65 +#, fuzzy +msgid "Identify yourself with your password" +msgstr " IDENTIFY Jelszavas azonosítás" + +#: modules/pseudoclients/nickserv.cpp:205 +#: modules/pseudoclients/nickserv.cpp:211 +#, fuzzy, c-format +msgid "If you do not change within %s, I will change your nick." +msgstr "Ha nem váltasz nevet 20 sec.-en belül, én megváltoztatom." + +#: modules/commands/os_ignore.cpp:333 +msgid "Ignore list has been cleared." +msgstr "Mellőzöttek lista törölve." + +#: modules/commands/os_ignore.cpp:262 +msgid "Ignore list is empty." +msgstr "Mellőzöttek lista üres." + +#: modules/commands/ms_ignore.cpp:94 +#, fuzzy +msgid "Ignore list:" +msgstr "Botok listája:" + +#: modules/commands/ns_set.cpp:1305 +#, fuzzy +msgid "Immediate protection" +msgstr "Voices védelme" + +#: modules/commands/ns_resetpass.cpp:33 +#, fuzzy +msgid "Incorrect email address." +msgstr "E-mail cím: %s" + +#: include/language.h:89 +msgid "Incorrect range specified. The correct syntax is #from-to." +msgstr "" + +#: modules/commands/os_modinfo.cpp:19 +#, fuzzy +msgid "Info about a loaded module" +msgstr " MODINFO Információ a betöltött modulokról" + +#: modules/commands/bs_info.cpp:54 +#, c-format +msgid "Information for bot %s:" +msgstr "Információk a %s nevű botról:" + +#: include/language.h:108 +#, fuzzy, c-format +msgid "Information for channel %s:" +msgstr "Információk a %s nevű botról:" + +#: modules/commands/os_logsearch.cpp:57 +#, c-format +msgid "Invalid duration %s, using %d days." +msgstr "" + +#: include/language.h:68 +msgid "Invalid expiry time." +msgstr "" + +#: modules/commands/os_session.cpp:346 +#, fuzzy +msgid "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not " +"matched against nicks or usernames." +msgstr "" +"Érvénytelen hosztmaszk. Csak érvényes hosztmaszk lehet,\n" +"a kivétel nem lehet nick vagy usernév." + +#: modules/commands/os_logsearch.cpp:73 +#, c-format +msgid "Invalid limit %s, using %d." +msgstr "" + +#: include/language.h:99 +msgid "" +"Invalid passcode has been entered, please check the e-mail again, and retry." +msgstr "" + +#: modules/commands/ns_register.cpp:83 modules/commands/ns_register.cpp:86 +msgid "Invalid passcode." +msgstr "" + +#: modules/commands/os_session.cpp:339 +#, c-format +msgid "" +"Invalid session limit. It must be a valid integer greater than or equal to " +"zero and less than %d." +msgstr "" +"Érvénytelen session korlát. Érvényes számnak kell lennie\n" +"és nagyobbnak vagy egyenlőnek mint zéró és kissebbnek \n" +"mint %d." + +#: modules/commands/os_session.cpp:188 +msgid "Invalid threshold value. It must be a valid integer greater than 1." +msgstr "" +"Érvénytelen küszöb érték. 1-nél nagyobb egész számnak\n" +"kell lennie." + +#: modules/commands/os_dns.cpp:591 +msgid "Invalid value for LIMIT. Must be numerical." +msgstr "" + +#: modules/commands/cs_invite.cpp:19 +#, fuzzy +msgid "Invites you or an optionally specified nick into a channel" +msgstr " OP Gives Op status to a selected nick on a channel" + +#: modules/commands/bs_kick.cpp:1201 modules/commands/bs_kick.cpp:1203 +#: modules/commands/bs_kick.cpp:1206 +#, fuzzy +msgid "Italics kicker" +msgstr "\tItalics kicker : %s" + +#: modules/commands/ns_group.cpp:91 +#, fuzzy +msgid "Join a group" +msgstr " GROUP Csatlakozás egy csoporthoz" + +#: modules/commands/cs_set.cpp:1305 modules/commands/ns_set.cpp:1319 +#, fuzzy +msgid "Keep modes" +msgstr "Üzenet mód" + +#: modules/commands/cs_set.cpp:377 modules/commands/ns_set.cpp:603 +#, fuzzy, c-format +msgid "Keep modes for %s is now off." +msgstr "Peace option for %s is now ON." + +#: modules/commands/cs_set.cpp:369 modules/commands/ns_set.cpp:597 +#, fuzzy, c-format +msgid "Keep modes for %s is now on." +msgstr "Peace option for %s is now ON." + +#: modules/commands/ns_ajoin.cpp:100 +msgid "Key" +msgstr "" + +#: modules/commands/cs_getkey.cpp:50 +#, c-format +msgid "Key for channel %s is %s." +msgstr "Key for channel %s is %s." + +#: modules/commands/os_kick.cpp:19 +#, fuzzy +msgid "Kick a user from a channel" +msgstr " KICK Kirúgja a felhasználót csatornáról" + +#: modules/commands/cs_ban.cpp:217 modules/commands/cs_kick.cpp:116 +#, c-format +msgid "Kicked %d/%d users matching %s from %s." +msgstr "" + +#: modules/commands/cs_kick.cpp:19 +#, fuzzy +msgid "Kicks a specified nick from a channel" +msgstr " KICK Kicks a selected nick from a channel" + +#: modules/commands/cs_kick.cpp:128 +#, fuzzy +msgid "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." +msgstr "" +"Syntax: KICK #szoba nick [indok]\n" +"\n" +"A ChanServ kirúgja a megadott nicknevet a csatornáról.\n" +"\n" +"Alapbeállítás szerint, min. AOP vagy 5-ös access szinttel\n" +"kell rendelkezned a csatornán, hogy használhasd." + +#: modules/commands/os_kill.cpp:19 +msgid "Kill a user" +msgstr "" + +#: modules/commands/cs_enforce.cpp:217 +msgid "LIMIT enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:221 +#, c-format +msgid "LIMIT enforced on %s, %d users removed." +msgstr "" + +#: modules/commands/os_session.cpp:246 +msgid "LIST threshold" +msgstr "" + +#: modules/commands/os_sxline.cpp:427 modules/commands/os_sxline.cpp:661 +#: modules/commands/os_akill.cpp:388 +#, fuzzy +msgid "LIST [mask | list | id]" +msgstr "LIST [#szoba] [list | NEW ]" + +#: modules/commands/os_session.cpp:525 +#, fuzzy +msgid "LIST [mask | list]" +msgstr "LIST [#szoba] [list | NEW ]" + +#: modules/commands/ns_access.cpp:104 modules/commands/ns_cert.cpp:260 +#: modules/commands/ns_ajoin.cpp:233 +#, fuzzy +msgid "LIST [nickname]" +msgstr "CHECK nicknév " + +#: modules/commands/os_news.cpp:31 +msgid "LOGONNEWS {ADD|DEL|LIST} [text|num]" +msgstr "LOGONNEWS { ADD | DEL | LIST } [szöveg|szám]" + +#: modules/commands/ns_set.cpp:834 +msgid "Language changed to English." +msgstr "Új nyelvezet: Magyar." + +#: modules/commands/ns_set.cpp:836 +#, fuzzy, c-format +msgid "Language for %s changed to %s." +msgstr "A megadott csatorna (%s) új successora: %s." + +#: modules/commands/ms_cancel.cpp:72 +#, c-format +msgid "Last memo to %s has been cancelled." +msgstr "%s részére küldött utolsó memo üzenet visszavonva." + +#: modules/commands/ns_info.cpp:95 +#, fuzzy +msgid "Last quit message" +msgstr "Utolsó kilépő üzenet: %s" + +#: modules/commands/cs_access.cpp:472 modules/commands/ns_info.cpp:92 +#, fuzzy +msgid "Last seen" +msgstr "Utoljára ekkor volt: %s" + +#: modules/commands/ns_info.cpp:81 modules/commands/ns_info.cpp:86 +#, fuzzy +msgid "Last seen address" +msgstr "Utoljára látott cím: %s" + +#: modules/commands/cs_topic.cpp:264 +msgid "Last topic" +msgstr "" + +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_info.cpp:56 +#, fuzzy +msgid "Last used" +msgstr "Utoljára ekkor volt: %s" + +#: modules/commands/ns_list.cpp:75 +#, fuzzy +msgid "Last usermask" +msgstr "Utoljára ekkor volt: %s" + +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +#: modules/commands/cs_access.cpp:697 +msgid "Level" +msgstr "" + +#: modules/commands/cs_access.cpp:660 +#, c-format +msgid "Level for %s on channel %s changed to %d." +msgstr "%s szintjének új értéke a (%s) csatornán: %d." + +#: modules/commands/cs_access.cpp:658 +#, c-format +msgid "Level for %s on channel %s changed to founder only." +msgstr "Level for %s on channel %s changed to founder only." + +#: modules/commands/cs_access.cpp:643 +#, c-format +msgid "Level must be between %d and %d inclusive." +msgstr "A szintnek kizárólag %d és %d között kell lennie." + +#: modules/commands/os_dns.cpp:218 modules/commands/os_session.cpp:506 +#: modules/commands/os_session.cpp:514 +msgid "Limit" +msgstr "" + +#: modules/commands/ns_list.cpp:19 +#, fuzzy +msgid "List all registered nicknames that match a given pattern" +msgstr "" +" LIST List all registered nicknames that match a given pattern" + +#: modules/commands/ns_alist.cpp:24 +#, fuzzy +msgid "List channels you have access on" +msgstr " ALIST List channels you have access on" + +#: modules/commands/cs_mode.cpp:341 +#, c-format +msgid "List for mode %c is full." +msgstr "" + +#: modules/commands/os_modinfo.cpp:80 +#, fuzzy +msgid "List loaded modules" +msgstr " MODLIST Listázza a betöltött modulokat" + +#: modules/commands/ns_list.cpp:123 modules/commands/cs_list.cpp:72 +#, fuzzy, c-format +msgid "List of entries matching %s:" +msgstr "%s csoportjába tartozó nickek listája:" + +#: modules/commands/ns_group.cpp:350 +#, c-format +msgid "List of nicknames in the group of %s:" +msgstr "%s csoportjába tartozó nickek listája:" + +#: modules/commands/ns_group.cpp:350 +msgid "List of nicknames in your group:" +msgstr "A csoportodba tartozó nickek listája:" + +#: modules/commands/ms_list.cpp:19 +#, fuzzy +msgid "List your memos" +msgstr " LIST Megjeleníti az üzenetek listáját" + +#: modules/commands/bs_botlist.cpp:64 +#, fuzzy +msgid "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." +msgstr "" +"Syntax: BOTLIST\n" +"\n" +"Listázza az összes érvényes botot a hálózatról." + +#: modules/commands/os_list.cpp:19 +#, fuzzy +msgid "Lists all channel records" +msgstr " CHANLIST Listázza az összes csatornát " + +#: modules/commands/os_list.cpp:107 +#, fuzzy +msgid "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." +msgstr "" +"Syntax: CHANLIST [{pattern | nick} [SECRET]]\n" +"\n" +"Listáz minden csatornát, ami most aktív az IRC hálózaton\n" +"attól függetlenül, hogy regisztrált vagy sem.\n" +"\n" +"Ha a pattern meg van adva, akkor csak az egyezőket\n" +"listázza. Ha a nicknév van megadva, akkor listázza azokat\n" +"a csatornákat, ahol az adott user bent van. Ha a SECRET\n" +"van megadva, akkor listáz minden pattern-nek megfelelő\n" +"csatornár, melyen +s vagy +p mód van fent.\n" +"\n" +"Korlátozva Szervíz adminoknak." + +#: modules/commands/ns_alist.cpp:127 +msgid "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" +msgstr "" + +#: modules/commands/ns_group.cpp:299 +#, fuzzy +msgid "Lists all nicknames in your group" +msgstr "A csoportodba tartozó nickek listája:" + +#: modules/commands/cs_list.cpp:20 +#, fuzzy +msgid "Lists all registered channels matching the given pattern" +msgstr "" +" LIST Lists all registered channels matching the given pattern" + +#: modules/commands/cs_list.cpp:137 +#, fuzzy +msgid "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." +msgstr "" +"Syntax: LIST pattern [FORBIDDEN] [SUSPENDED] [NOEXPIRE]\n" +"\n" +"Listáz minden regisztrált nicknevet, amely vagy nicknév\n" +"vagy az utoljára látott cím (user@hostformában), amely\n" +"azonos a megadott sablonnal. Nickek PRIVATE opcióval\n" +"beállítva csak szervíz adminoknak jelennek meg. A nickek\n" +"NOEXPIRE opcióval beállítva !prefixel jelennek meg\n" +"a szervíz adminoknak.\n" +"\n" +"Ha a FORBIDDEN, SUSPENDED vagy NOEXPIRE opció meg van adva, csak azok\n" +"a nickek amelyek vagy forbidoltak vagy NOEXPIRE flegjük van\n" +"fognak megjelenik. Ha mindkét opció meg van adva mindkét\n" +"tipus megjelenik. Az opciók korlátozva Services Operatoroknak.\n" +"\n" +"Példák:\n" +"\n" +"\tLIST *!joeuser@foo.com\n" +" Kiírja a felhasználókat, akiknek a hosztja joeuser@foo.com\n" +"\n" +"\tLIST *Bot*!*@*\n" +" Kiírja az összes regisztrált nicket, melyek nevében \n" +" szerepel a Bot (betű érzéketlen).\n" +"\n" +" LIST * NOEXPIRE\n" +" Listázza az összes felhasználót, akinek a beállítása\n" +" nem elévülő." + +#: modules/commands/ns_list.cpp:139 +#, fuzzy +msgid "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." +msgstr "" +"Syntax: LIST pattern [FORBIDDEN] [SUSPENDED] [NOEXPIRE]\n" +"\n" +"Listáz minden regisztrált nicknevet, amely vagy nicknév\n" +"vagy az utoljára látott cím (user@hostformában), amely\n" +"azonos a megadott sablonnal. Nickek PRIVATE opcióval\n" +"beállítva csak szervíz adminoknak jelennek meg. A nickek\n" +"NOEXPIRE opcióval beállítva !prefixel jelennek meg\n" +"a szervíz adminoknak.\n" +"\n" +"Ha a FORBIDDEN, SUSPENDED vagy NOEXPIRE opció meg van adva, csak azok\n" +"a nickek amelyek vagy forbidoltak vagy NOEXPIRE flegjük van\n" +"fognak megjelenik. Ha mindkét opció meg van adva mindkét\n" +"tipus megjelenik. Az opciók korlátozva Services Operatoroknak.\n" +"\n" +"Példák:\n" +"\n" +"\tLIST *!joeuser@foo.com\n" +" Kiírja a felhasználókat, akiknek a hosztja joeuser@foo.com\n" +"\n" +"\tLIST *Bot*!*@*\n" +" Kiírja az összes regisztrált nicket, melyek nevében \n" +" szerepel a Bot (betű érzéketlen).\n" +"\n" +" LIST * NOEXPIRE\n" +" Listázza az összes felhasználót, akinek a beállítása\n" +" nem elévülő." + +#: modules/commands/os_list.cpp:132 +#, fuzzy +msgid "Lists all user records" +msgstr " USERLIST Listázza az összes felhasználót " + +#: modules/commands/os_list.cpp:243 +#, fuzzy +msgid "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only " +"users\n" +"with the +i flag will be listed." +msgstr "" +"Syntax: USERLIST [{pattern | #szoba} [INVISIBLE]]\n" +"\n" +"Listáz minden jelenleg online usert az IRC hálózaton,\n" +"attól függetlenül, hogy regisztrált vagy sem.\n" +"\n" +"Ha a pattern meg van adva, akkor csak az egyezőket \n" +"listázza (formátum: nick!user@host). Ha a #szoba\n" +"meg van adva, akkor csak az adott csatornán lévőket\n" +"listázza. Ha az INVISIBLE meg van adva, akkor csak a\n" +"+i flages usereket listázza.\n" +"\n" +"Korlátozva Szervíz adminoknak." + +#: modules/commands/ms_list.cpp:142 +#, fuzzy +msgid "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Syntax: LIST [#szoba] [list | NEW]\n" +"\n" +"Megjelenít egy listát a jelenlegi üzenteteidrol. A NEW\n" +"opcióval csak az új (olvasatlan) üzenteket listázza.\n" +"listázza. Az olvasatlan üzeneteket jelöli egy \"*\" jellel\n" +"az üzenetszámtól balra. Megadhatsz számlistát is, mint\n" +"ahogy az alábbi példa mutatja:\n" +"\n" +"\tLIST 2-5,7-9\n" +"\t\tListázza az üzeneteket 2 és 5, illetve 7 és 9 között." + +#: modules/commands/bs_botlist.cpp:19 +#, fuzzy +msgid "Lists available bots" +msgstr "BOTLIST Listázza az elérhető botokat" + +#: modules/commands/os_modinfo.cpp:196 +#, fuzzy +msgid "Lists currently loaded modules." +msgstr " MODLIST Listázza a betöltött modulokat" + +#: modules/commands/cs_info.cpp:19 +#, fuzzy +msgid "Lists information about the specified registered channel" +msgstr " INFO Lists information about the named registered channel" + +#: modules/commands/cs_info.cpp:76 +#, fuzzy +msgid "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." +msgstr "" +"Syntax: INFO #szoba\n" +"\n" +"Listázza az összes információt a megnevezett regisztrált\n" +"csatornáról, pl a foundert, a regisztrálás időpontját,\n" +"az utolsó használat idejét, a leírást, az mlock-ot. \n" +"Ha beazonosítottad magad a szoba founderjének, akkor\n" +"teljes információt az ALL paraméterrel kaphatsz, az \n" +"entrymessage, a successor és a rejtett infók is látszódnak\n" +"\n" +"Alapból az ALL opció csak a foundernek engedélyezett." + +#: modules/commands/os_module.cpp:19 +#, fuzzy +msgid "Load a module" +msgstr " MODLOAD Betölti a modult" + +#: modules/commands/cs_register.cpp:39 +msgid "Local channels cannot be registered." +msgstr "Helyi csatornák nem regisztrálhatók." + +#: modules/commands/cs_log.cpp:142 +#, fuzzy, c-format +msgid "Log list for %s:" +msgstr "%s hozzáférési listája:" + +#: modules/commands/cs_log.cpp:227 +#, c-format +msgid "Logging changed for command %s on %s, now using log method %s%s%s." +msgstr "" + +#: modules/commands/cs_log.cpp:220 +#, c-format +msgid "Logging for command %s on %s with log method %s%s%s has been removed." +msgstr "" + +#: modules/commands/cs_log.cpp:248 +#, c-format +msgid "Logging is now active for command %s on %s, using log method %s%s%s." +msgstr "" + +#: modules/commands/os_login.cpp:60 +#, c-format +msgid "Login to %s" +msgstr "" + +#: modules/commands/os_news.cpp:36 +#, c-format +msgid "Logon news item #%d deleted." +msgstr "Logon news tétel #%d törölve." + +#: modules/commands/os_news.cpp:35 +#, fuzzy, c-format +msgid "Logon news item #%s not found!" +msgstr "Logon news tétel #%d nem található!" + +#: modules/commands/os_news.cpp:32 +msgid "Logon news items:" +msgstr "Fellépési hírek:" + +#: modules/commands/os_login.cpp:102 +#, fuzzy, c-format +msgid "Logout from %s" +msgstr "%s hozzáférési listája:" + +#: modules/commands/os_login.cpp:52 +#, c-format +msgid "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." +msgstr "" + +#: modules/commands/os_login.cpp:94 +#, c-format +msgid "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." +msgstr "" + +#: modules/commands/cs_seen.cpp:213 +#, c-format +msgid "Looking for yourself, eh %s?" +msgstr "" + +#: modules/commands/cs_mode.cpp:773 +#, c-format +msgid "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a " +"channel.\n" +"If a mode is locked on or off, services will not allow that mode to be " +"changed. The SET\n" +"command will clear all existing mode locks and set the new one given, while " +"ADD and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * " +"and ? may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may " +"be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, " +"halfops, and voices. If what\n" +"is not given then all basic modes are removed." +msgstr "" + +#: modules/commands/cs_akick.cpp:434 +#, fuzzy +msgid "Maintain the AutoKick list" +msgstr " AKICK AutoKirúgás listára teheted a \"rossz\" usereket" + +#: modules/commands/bs_bot.cpp:269 +#, fuzzy +msgid "Maintains network bot list" +msgstr "BOT Karbantartja a hálózat botjainak listáját" + +#: modules/commands/cs_xop.cpp:522 +#, c-format +msgid "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " +msgstr "" + +#: modules/commands/cs_akick.cpp:493 +#, c-format +msgid "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" +msgstr "" + +#: modules/commands/cs_access.cpp:568 +#, c-format +msgid "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." +msgstr "" + +#: modules/commands/bs_badwords.cpp:424 +#, fuzzy, c-format +msgid "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" +msgstr "" +"Syntax:BADWORDS #szoba ADD szó [SINGLE | START | END]\n" +"\t BADWORDS #szoba DEL { szó | sorszám | list}\n" +"\t BADWORDS #szoba LIST [ maszk | list]\n" +"\t BADWORDS #szoba CLEAR\n" +"Karbantartja a szoba csúnyaszó listáját. A tiltott\n" +"szavak listája meghatározza, hogy mely szavak kiejtésére\n" +"rúgja ki a bot a usert, ha a kirúgás engedélyezve van,\n" +"erről bővebb információk: /msg %s HELP KICK BADWORDS.\n" +"\n" +"A BADWORDS ADD parancs hozzáad egy szót a listához.\n" +"Ha a SINGLE van megadva, akkor lesz kirúgja a user, ha\n" +"a konkrét szót mondja ki.\n" +"Ha a START van megadva, akkor a szó elejét figyeli a bot.\n" +"Ha az END van megadva, akkor a szó végét figyeli a bot.\n" +"Ha nem adsz meg semmit, akkor\ta user minden alkalommal\n" +"kirúgásra kerül, ha kiejti a szót.\n" +"Ha nem beszél csúnyán, akkor semmi baja nem lesz! :-)\n" +"A BADWORDS DEL parancs eltávolítja a megadott szót\n" +"a tiltott szavak listájáról. Ha egy sorozatot adsz meg\n" +"a bejegyzések számával, akkor azok a bejegyzések kerülnek\n" +"törlésre. (Lásd lentebb a listázást.)\n" +"\n" +"A BADWORDS LIST parancs megjeleníti a tiltott szavakat.\n" +"Ha használod a * karaktert, akkor csak az egyező\n" +"bejegyzések kerülnek listázásra. Ha egy sorozatot adsz meg\n" +"akkor azok a bejegyzések kerülnek megjelenítésre; példa:\n" +" BADWORDS #szoba LIST 2-5,7-9\n" +" Listázza a csúnyaszavakat 2-től 5-ig és a 7-től\n" +" 9-ig.\n" +" \n" +"BADWORDS CLEAR parancs törli az összes bejegyzést\n" +"a tiltott szavak listájáról" + +#: modules/commands/bs_badwords.cpp:370 +#, fuzzy +msgid "Maintains the bad words list" +msgstr "BADWORDS Szerkeszti a tiltott szavak listáját" + +#: modules/commands/bs_control.cpp:79 +#, fuzzy +msgid "Makes the bot do the equivalent of a \"/me\" command" +msgstr "" +"ACT Makes the bot do the equivalent of a \"/me\" command" + +#: modules/commands/bs_control.cpp:127 +#, fuzzy +msgid "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." +msgstr "" +"Syntax: ACT #szoba szöveg\n" +"\n" +"A bot \"/me\" akcióval küldi el a megadott szöveget\n" +"a csatornára." + +#: modules/commands/bs_control.cpp:19 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel" +msgstr "" +"SAY Makes the bot say the given text on the given channel" + +#: modules/commands/bs_control.cpp:69 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel." +msgstr "" +"SAY Makes the bot say the given text on the given channel" + +#: modules/commands/greet.cpp:157 +#, fuzzy +msgid "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." +msgstr "" +"Syntax: SASET nickname GREET message\n" +"\n" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary \n" +"access on it." + +#: modules/commands/greet.cpp:131 +#, fuzzy +msgid "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." +msgstr "" +"Syntax: SET GREET üzenet\n" +"\n" +"Ez az opció társít egy üzenetet a nicknevedhez,\n" +"ami akkor fog megjelenni belépéskor, ha a csatornán\n" +"a GREET opció engedélyezve van és te rendelkezel a\n" +"megfelelő szinttel, ami az üzenet megjelenitéséhez\n" +"szükséges a csatornán." + +#: modules/commands/os_dns.cpp:660 +#, fuzzy +msgid "Manage DNS zones for this network" +msgstr "Nem törölheted ezen a hálózaton az e-mail címed." + +#: modules/commands/cs_entrymsg.cpp:193 +#, fuzzy +msgid "Manage the channel's entry messages" +msgstr " PERSIST Set the channel as permanent" + +#: modules/commands/ms_ignore.cpp:19 +#, fuzzy +msgid "Manage the memo ignore list" +msgstr " IGNORE Módosítja a Szervíz mellőzési listáját" + +#: modules/commands/ns_ajoin.cpp:230 +#, fuzzy +msgid "Manage your auto join list" +msgstr " AKICK AutoKirúgás listára teheted a \"rossz\" usereket" + +#: modules/commands/os_sxline.cpp:233 +#, fuzzy, c-format +msgid "Manipulate the %s list" +msgstr " AKILL Szerkeszti az AKILL listát" + +#: modules/commands/os_akill.cpp:385 +#, fuzzy +msgid "Manipulate the AKILL list" +msgstr " AKILL Szerkeszti az AKILL listát" + +#: modules/commands/os_defcon.cpp:176 +#, fuzzy +msgid "Manipulate the DefCon system" +msgstr " DEFCON Manipulálja a DefCon rendszert" + +#: modules/commands/cs_topic.cpp:149 +#, fuzzy +msgid "Manipulate the topic of the specified channel" +msgstr " TOPIC Manipulate the topic of the specified channel" + +#: modules/commands/bs_botlist.cpp:27 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_forbid.cpp:358 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/ms_ignore.cpp:86 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_list.cpp:153 modules/commands/bs_info.cpp:55 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +msgid "Mask" +msgstr "" + +#: modules/commands/ns_access.cpp:39 +#, fuzzy, c-format +msgid "Mask %s already present on %s's access list." +msgstr "Ez a maszk: %s már szerepel a hozzáférési listádon." + +#: include/language.h:67 +msgid "Mask must be in the form user@host." +msgstr "" + +#: modules/commands/cs_access.cpp:166 modules/commands/cs_flags.cpp:120 +#: modules/commands/cs_xop.cpp:162 +#, fuzzy +msgid "Masks and unregistered users may not be on access lists." +msgstr "Ez a maszk: %s már szerepel a hozzáférési listádon." + +#: modules/commands/ns_getemail.cpp:23 +#, fuzzy +msgid "Matches and returns all users that registered using given email" +msgstr "" +" GETEMAIL Kiírja az ilyen e-mail címmel regisztrált\n" +" felhasználókat" + +#: modules/commands/os_logsearch.cpp:148 +#, fuzzy, c-format +msgid "Matches for %s:" +msgstr "\tRögzített módok: %s" + +#: modules/commands/os_stats.cpp:139 +#, c-format +msgid "Maximum users: %d (%s)" +msgstr "Legtöbb felhasználó: %d (%s)" + +#: modules/commands/ms_read.cpp:84 modules/commands/ms_read.cpp:86 +#, fuzzy, c-format +msgid "Memo %d from %s (%s)." +msgstr "\tRögzített módok: %s" + +#: modules/commands/ms_del.cpp:33 modules/commands/ms_del.cpp:101 +#, c-format +msgid "Memo %d has been deleted." +msgstr "A megadott üzenetet (%d) töröltem." + +#: modules/commands/ms_ignore.cpp:82 +#, fuzzy +msgid "Memo ignore list is empty." +msgstr "Mellőzöttek lista üres." + +#: modules/commands/ms_set.cpp:199 +#, c-format +msgid "Memo limit disabled for %s." +msgstr "%s ezentúl korlátlan számú üzenetet fogadhat." + +#: modules/commands/ms_set.cpp:185 +#, c-format +msgid "Memo limit for %s set to %d." +msgstr "%s maximálisan fogadható üzeneteinek száma: %d." + +#: modules/commands/ms_set.cpp:192 +#, c-format +msgid "Memo limit for %s set to 0." +msgstr "%s ezentúl nem fogadhat üzeneteket." + +#: modules/commands/ms_rsend.cpp:63 modules/commands/ms_send.cpp:51 +#, c-format +msgid "Memo sent to %s." +msgstr "Üzenet elküldve %s részére." + +#: modules/commands/ms_list.cpp:131 +#, fuzzy, c-format +msgid "Memos for %s:" +msgstr "\tRögzített módok: %s" + +#: modules/commands/cs_entrymsg.cpp:116 +#, fuzzy +msgid "Message" +msgstr "GLOBAL üzenet" + +#: modules/commands/ns_set.cpp:1313 +msgid "Message mode" +msgstr "Üzenet mód" + +#: modules/commands/cs_log.cpp:127 +msgid "Method" +msgstr "" + +#: modules/commands/cs_mode.cpp:329 modules/commands/cs_mode.cpp:420 +#, c-format +msgid "Missing parameter for mode %c." +msgstr "" + +#: modules/commands/cs_mode.cpp:449 +msgid "Mode" +msgstr "" + +#: modules/commands/cs_mode.cpp:718 +#, fuzzy, c-format +msgid "Mode %s is a virtual mode and can't be cleared." +msgstr " %snick illegális nicknév vagy nem használható." + +#: modules/commands/cs_mode.cpp:712 +#, fuzzy, c-format +msgid "Mode %s is not a status or list mode." +msgstr "%s nick nem található a mellőzöttek listáján." + +#: modules/commands/cs_mode.cpp:1065 +#, fuzzy +msgid "Mode lock" +msgstr "\tRögzített módok: %s" + +#: modules/commands/cs_mode.cpp:466 +#, fuzzy, c-format +msgid "Mode locks for %s:" +msgstr "\tRögzített módok: %s" + +#: modules/commands/os_list.cpp:43 +msgid "Modes" +msgstr "" + +#: modules/commands/os_mode.cpp:44 +#, c-format +msgid "Modes cleared on %s and the channel destroyed." +msgstr "" + +#: modules/commands/ns_access.cpp:166 +#, fuzzy, c-format +msgid "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." +msgstr "" +"Syntax: ACCESS ADD maszk\n" +" ACCESS DEL maszk\n" +" ACCESS LIST\n" +"\n" +"Módosítja vagy kiirja a hozzáférési listát a nickedhez.\n" +"Ez azon címeknek a listája, amelyek automatikusan úgy \n" +"tekintődnek a %s-ben, hogy engedélyük van a nicket \n" +"használni. Ha a nicked más címekről akarod használni,\n" +"akkor nem kell IDENTIFY parancsot küldened, hogy úgy\n" +"legyél tekintve, a %s-ben, mint a nick tulajdonosa.\n" +"\n" +"Példák:\n" +"\n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Hozzáférést engedélyez az anyone identnek bármely\n" +" gépről aminek a bepeg.com a domainje.\n" +"\n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Törli az elöző parancsot.\n" +"\n" +" ACCESS LIST\n" +" Megmutatja a hozzáférési listát." + +#: modules/commands/ns_cert.cpp:319 +msgid "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" +msgstr "" + +#: modules/commands/os_ignore.cpp:341 +#, fuzzy +msgid "Modify the Services ignore list" +msgstr " IGNORE Módosítja a Szervíz mellőzési listáját" + +#: modules/commands/cs_xop.cpp:489 +#, fuzzy, c-format +msgid "Modify the list of %s users" +msgstr " AOP AutoOperátor lista beállítása" + +#: modules/commands/ns_access.cpp:101 +#, fuzzy +msgid "Modify the list of authorized addresses" +msgstr " ACCESS A hozzáférési lista módosítása" + +#: modules/commands/cs_access.cpp:498 modules/commands/cs_flags.cpp:373 +#, fuzzy +msgid "Modify the list of privileged users" +msgstr " ACCESS A szoba hozzáférési listájának beállítása" + +#: modules/commands/ns_cert.cpp:257 +#, fuzzy +msgid "Modify the nickname client certificate list" +msgstr " IGNORE Módosítja a Szervíz mellőzési listáját" + +#: modules/commands/os_session.cpp:522 +#, fuzzy +msgid "Modify the session-limit exception list" +msgstr " EXCEPTION Módosítja a session-korlát/kivétel listát" + +#: modules/commands/os_module.cpp:34 +#, c-format +msgid "Module %s is already loaded." +msgstr "Module %s is already loaded." + +#: modules/commands/os_module.cpp:67 modules/commands/os_module.cpp:139 +#, c-format +msgid "Module %s isn't loaded." +msgstr "Module %s isn't loaded." + +#: modules/commands/os_module.cpp:31 +#, fuzzy, c-format +msgid "Module %s loaded." +msgstr "%s modul betöltve" + +#: modules/commands/os_module.cpp:98 +#, fuzzy, c-format +msgid "Module %s reloaded." +msgstr "%s modul betöltve" + +#: modules/commands/os_module.cpp:156 +#, fuzzy, c-format +msgid "Module %s unloaded." +msgstr "%s modul kitöltve" + +#: modules/commands/os_config.cpp:88 +#, fuzzy +msgid "Module Name" +msgstr "%s modul betöltve" + +#: modules/commands/os_config.cpp:112 +msgid "Module settings:" +msgstr "" + +#: modules/commands/os_modinfo.cpp:32 +#, fuzzy, c-format +msgid "Module: %s Version: %s Author: %s Loaded: %s" +msgstr "Modul: %s Verzió: %s Szerző: %s Betöltve: %s" + +#: modules/commands/os_modinfo.cpp:183 +#, c-format +msgid "Module: %s [%s] [%s]" +msgstr "Modul: %s [%s] [%s]" + +#: modules/commands/cs_access.cpp:697 modules/commands/cs_access.cpp:799 +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +#: modules/commands/cs_list.cpp:75 modules/commands/os_list.cpp:43 +#: modules/commands/os_list.cpp:153 +msgid "Name" +msgstr "" + +#: modules/commands/os_oper.cpp:153 +msgid "Name Type" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:146 +#, fuzzy, c-format +msgid "Network stats for %s:" +msgstr "%s hozzáférési listája:" + +#: modules/commands/os_forbid.cpp:384 +msgid "Never" +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/bs_botlist.cpp:27 +#: modules/commands/hs_request.cpp:305 modules/commands/ns_list.cpp:75 +#: modules/commands/ns_group.cpp:327 +#, fuzzy +msgid "Nick" +msgstr "INFO nick" + +#: modules/commands/ns_register.cpp:42 +#, fuzzy, c-format +msgid "Nick %s has been confirmed." +msgstr "A %s nicknevet dropoltad." + +#: modules/commands/os_oper.cpp:95 +#, fuzzy, c-format +msgid "Nick %s is already an operator." +msgstr "Ez a nicknév: %s már regisztrált!" + +#: modules/commands/ns_register.cpp:36 +#, fuzzy, c-format +msgid "Nick %s is already confirmed." +msgstr "Ez a nicknév: %s már regisztrált!" + +#: modules/commands/os_svs.cpp:46 +#, c-format +msgid "Nick %s is an illegal nickname and cannot be used." +msgstr " %snick illegális nicknév vagy nem használható." + +#: modules/commands/bs_bot.cpp:81 modules/commands/bs_bot.cpp:181 +#: modules/commands/os_svs.cpp:54 +#, c-format +msgid "Nick %s is currently in use." +msgstr "Ez a nick: %s jelenleg használatban van." + +#: modules/commands/os_forbid.cpp:512 +#, fuzzy, c-format +msgid "Nick %s is forbidden by %s: %s" +msgstr "Ez a nick: %s jelenleg használatban van." + +#: modules/commands/os_forbid.cpp:514 +#, fuzzy, c-format +msgid "Nick %s is forbidden." +msgstr "Ezt a nicket %s nem fogja a services." + +#: modules/commands/os_oper.cpp:134 +#, fuzzy, c-format +msgid "Nick %s is not a Services Operator." +msgstr "%s is a services operator of type %s." + +#: modules/commands/ns_info.cpp:34 +#, c-format +msgid "Nick %s is part of this Network's Services." +msgstr "A %s nick a Hálózat Szervízének egysége." + +#: include/language.h:79 +#, fuzzy, c-format +msgid "Nick %s isn't currently in use." +msgstr "Ez a nick: %s jelenleg használatban van." + +#: include/language.h:78 +#, fuzzy, c-format +msgid "Nick %s isn't registered." +msgstr "Nickname %s registered." + +#: modules/commands/os_svs.cpp:39 +#, c-format +msgid "Nick %s was truncated to %d characters." +msgstr "A nicked %s meg lett csonkítva %d karakter hosszúságúra." + +#: modules/commands/ns_set.cpp:1135 +#, c-format +msgid "Nick %s will expire." +msgstr "Nick %s will expire." + +#: modules/commands/ns_set.cpp:1129 +#, c-format +msgid "Nick %s will not expire." +msgstr "Nick %s will not expire." + +#: modules/commands/ms_check.cpp:60 +#, c-format +msgid "Nick %s doesn't have a memo from you." +msgstr "%s nickre nem érkezett memo üzenet tőled." + +#: modules/commands/ns_logout.cpp:48 +#, c-format +msgid "Nick %s has been logged out." +msgstr " %s nick sikeresen kijelentkezett." + +#: modules/commands/ns_group.cpp:272 +#, c-format +msgid "Nick %s has been ungrouped from %s." +msgstr "Nick %s has been ungrouped from %s." + +#: include/language.h:81 +#, fuzzy, c-format +msgid "Nick %s is currently suspended." +msgstr "Nick %s is now suspended." + +#: modules/commands/ns_group.cpp:250 +#, fuzzy, c-format +msgid "Nick %s is not in your group." +msgstr "The nick %s is not in your group." + +#: modules/commands/ns_suspend.cpp:180 +#, fuzzy, c-format +msgid "Nick %s is not suspended." +msgstr "Nick %s is now suspended." + +#: modules/commands/ns_suspend.cpp:190 +#, c-format +msgid "Nick %s is now released." +msgstr "Nick %s is now released." + +#: modules/commands/ns_suspend.cpp:138 +#, c-format +msgid "Nick %s is now suspended." +msgstr "Nick %s is now suspended." + +#: modules/commands/cs_seen.cpp:275 +#, c-format +msgid "Nick too long, max length is %u characters." +msgstr "" + +#: modules/commands/ns_drop.cpp:53 +#, c-format +msgid "Nickname %s has been dropped." +msgstr "A %s nicknevet dropoltad." + +#: include/language.h:97 +#, fuzzy, c-format +msgid "Nickname %s is already registered!" +msgstr "A megadott csatorna %s már regisztrált!" + +#: include/language.h:96 +#, fuzzy, c-format +msgid "Nickname %s may not be registered." +msgstr "Ez a csatorna %s nem regisztrálható. " + +#: modules/commands/ns_register.cpp:226 +#, fuzzy, c-format +msgid "Nickname %s registered under your user@host-mask: %s" +msgstr "Ez a nicknév: %s számodra lett regisztrálva: %s" + +#: modules/commands/ns_register.cpp:228 +#, fuzzy, c-format +msgid "Nickname %s registered." +msgstr "Nickname %s registered." + +#: modules/commands/cs_set.cpp:1307 +#, fuzzy +msgid "No auto-op" +msgstr "Auto-op" + +#: modules/commands/bs_assign.cpp:252 +msgid "No bot" +msgstr "Nincs bot" + +#: modules/commands/cs_set.cpp:1303 modules/commands/ns_set.cpp:1317 +#, fuzzy +msgid "No expire" +msgstr "nem fog elévülni" + +#: modules/commands/help.cpp:184 +#, c-format +msgid "No help available for %s." +msgstr "Nincs ezzel kapcsolatban segítség: %s." + +#: modules/commands/os_modinfo.cpp:61 +#, fuzzy, c-format +msgid "No information about module %s is available." +msgstr "Nincs elérhető információ a %s modulról" + +#: modules/commands/cs_enforce.cpp:177 +#, fuzzy, c-format +msgid "No limit is set on %s." +msgstr "%s maximálisan fogadható üzeneteinek száma: %d." + +#: modules/commands/os_news.cpp:37 +msgid "No logon news items to delete!" +msgstr "Nincs törölhető fellépési hír!" + +#: modules/commands/os_logsearch.cpp:133 +#, fuzzy, c-format +msgid "No matches for %s found." +msgstr "Nincs Email listázva ehhez: %s." + +#: modules/commands/cs_xop.cpp:294 +#, fuzzy, c-format +msgid "No matching entries on %s %s list." +msgstr "Nincs ilyen bejegyzés a %s AOP listán." + +#: modules/commands/cs_access.cpp:269 modules/commands/cs_access.cpp:433 +#: modules/commands/cs_flags.cpp:335 modules/commands/cs_xop.cpp:428 +#, c-format +msgid "No matching entries on %s access list." +msgstr "Nincs ilyen bejegyzés a (%s) csatorna hozzáférési listáján." + +#: modules/commands/cs_akick.cpp:224 modules/commands/cs_akick.cpp:368 +#, c-format +msgid "No matching entries on %s autokick list." +msgstr "Nincs ilyen bejegyzés a (%s) csatorna autokick listáján." + +#: modules/commands/bs_badwords.cpp:166 modules/commands/bs_badwords.cpp:246 +#, c-format +msgid "No matching entries on %s bad words list." +msgstr "Nincs ilyen szó %s a tiltott szavak listáján." + +#: modules/commands/os_session.cpp:145 modules/commands/os_session.cpp:490 +msgid "No matching entries on session-limit exception list." +msgstr "Nincs ilyen bejegyzés a session-korlát kivétel listán." + +#: modules/commands/os_sxline.cpp:28 modules/commands/os_sxline.cpp:177 +#, fuzzy, c-format +msgid "No matching entries on the %s list." +msgstr "Nincs ilyen bejegyzés a %s AOP listán." + +#: modules/commands/os_akill.cpp:29 modules/commands/os_akill.cpp:320 +msgid "No matching entries on the AKILL list." +msgstr "Nincs ilyen bejegyzés az AKILL listán." + +#: modules/commands/ms_cancel.cpp:77 +msgid "No memo was cancelable." +msgstr "Nincs visszavont memo üzenet." + +#: modules/commands/ms_read.cpp:65 +msgid "No memos to display." +msgstr "" + +#: modules/commands/os_modinfo.cpp:187 +#, fuzzy +msgid "No modules currently loaded matching that criteria." +msgstr "Jelenleg nincs modul betöltve." + +#: modules/commands/ns_recover.cpp:55 +msgid "No one is using your nick, and services are not holding it." +msgstr "" + +#: modules/commands/os_login.cpp:30 modules/commands/os_login.cpp:77 +msgid "No oper block for your nick." +msgstr "" + +#: modules/commands/os_news.cpp:47 +msgid "No oper news items to delete!" +msgstr "Nincs törölhető opernews tétel!" + +#: modules/commands/os_news.cpp:57 +msgid "No random news items to delete!" +msgstr "Nincs törölhető random news tétel!" + +#: modules/commands/hs_list.cpp:111 +msgid "No records to display." +msgstr "" + +#: modules/commands/ns_getemail.cpp:47 +#, fuzzy, c-format +msgid "No registrations matching %s were found." +msgstr "* Nem lehet új nicket regisztrálni." + +#: modules/commands/hs_request.cpp:220 modules/commands/hs_request.cpp:276 +#, c-format +msgid "No request for nick %s found." +msgstr "" + +#: src/access.cpp:55 +msgid "No signed kick when SIGNKICK LEVEL is used" +msgstr "" + +#: modules/extra/stats/cs_fantasy_top.cpp:159 +#: modules/extra/stats/cs_fantasy_stats.cpp:156 +#, fuzzy, c-format +msgid "No stats for %s." +msgstr "%s hozzáférési listája:" + +#: modules/commands/os_info.cpp:201 +#, fuzzy, c-format +msgid "No such info \"%s\" on %s." +msgstr "%s has been invited to %s." + +#: modules/commands/cs_ban.cpp:219 modules/commands/cs_kick.cpp:118 +#, fuzzy, c-format +msgid "No users on %s match %s." +msgstr "%s usermódjai megváltoztatva." + +#: modules/commands/bs_assign.cpp:188 +#, fuzzy, c-format +msgid "No-bot mode is now off on channel %s." +msgstr "Nincs Bot mód most ONa %s szobán." + +#: modules/commands/bs_assign.cpp:181 +#, fuzzy, c-format +msgid "No-bot mode is now on on channel %s." +msgstr "Nincs Bot mód most ONa %s szobán." + +#: modules/commands/os_mode.cpp:64 +#, c-format +msgid "Non-status modes cleared on %s." +msgstr "" + +#: modules/commands/os_dns.cpp:226 modules/commands/bs_info.cpp:58 +msgid "None" +msgstr "Nincs" + +#: modules/commands/cs_set.cpp:1029 +#, c-format +msgid "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." +msgstr "" + +#: modules/commands/cs_mode.cpp:380 modules/commands/cs_mode.cpp:437 +msgid "Nothing to do." +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:201 modules/commands/ms_list.cpp:64 +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_log.cpp:127 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +#: modules/commands/ns_ajoin.cpp:100 +msgid "Number" +msgstr "" + +#: modules/commands/os_news.cpp:41 +msgid "OPERNEWS {ADD|DEL|LIST} [text|num]" +msgstr "OPERNEWS { ADD | DEL |LIST } [ szöveg | szám ]" + +#: modules/commands/ns_info.cpp:68 modules/commands/ns_info.cpp:72 +#, fuzzy +msgid "Online from" +msgstr "Jelenleg online erről a címről: %s" + +#: modules/commands/os_oper.cpp:138 +#, c-format +msgid "" +"Oper %s is configured in the configuration file(s) and can not be removed by " +"this command." +msgstr "" + +#: modules/commands/os_info.cpp:268 +msgid "Oper Info" +msgstr "" + +#: modules/commands/os_info.cpp:182 modules/commands/os_info.cpp:221 +#, fuzzy, c-format +msgid "Oper info list for %s is empty." +msgstr "Access list for %s is empty." + +#: modules/commands/os_news.cpp:46 +#, c-format +msgid "Oper news item #%d deleted." +msgstr "Oper news tétel #%d törölve." + +#: modules/commands/os_news.cpp:45 +#, fuzzy, c-format +msgid "Oper news item #%s not found!" +msgstr "Oper news tétel #%d nem található!" + +#: modules/commands/os_news.cpp:42 +msgid "Oper news items:" +msgstr "Oper hírek listája:" + +#: modules/commands/os_oper.cpp:148 +#, c-format +msgid "Oper privileges removed from %s (%s)." +msgstr "" + +#: modules/commands/os_oper.cpp:101 modules/commands/os_oper.cpp:189 +#, fuzzy, c-format +msgid "Oper type %s has not been configured." +msgstr "A %s nicknevet dropoltad." + +#: modules/commands/os_oline.cpp:37 +#, c-format +msgid "Operflags %s have been added for %s." +msgstr "%s operflagek megadva a %s nicknek." + +#: modules/commands/os_oline.cpp:43 +#, fuzzy, c-format +msgid "Operflags %s have been removed from %s." +msgstr "%s operflagek megadva a %s nicknek." + +#: modules/commands/os_oper.cpp:193 +#, c-format +msgid "Opertype %s has no allowed commands." +msgstr "" + +#: modules/commands/os_oper.cpp:215 +#, c-format +msgid "Opertype %s has no allowed privileges." +msgstr "" + +#: modules/commands/os_oper.cpp:237 +#, c-format +msgid "Opertype %s receives modes %s once identified." +msgstr "" + +#: modules/commands/bs_kick.cpp:1219 +msgid "Ops protection" +msgstr "Opok védelme" + +#: src/misc.cpp:258 modules/commands/bs_info.cpp:58 +#, fuzzy +msgid "Options" +msgstr "Beállításai: %s" + +#: modules/commands/os_dns.cpp:668 +#, fuzzy +msgid "POOL server.name" +msgstr "NOOP {SET|REVOKE} szerver" + +#: modules/commands/cs_mode.cpp:449 +msgid "Param" +msgstr "" + +#: modules/commands/ns_identify.cpp:38 +msgid "Password accepted - you are now recognized." +msgstr "Jelszavad elfogadva - azonosítás sikeres." + +#: modules/commands/os_login.cpp:44 +#, fuzzy +msgid "Password accepted." +msgstr "Hibás jelszó." + +#: include/language.h:85 +msgid "Password authentication required for that command." +msgstr "" + +#: modules/commands/ns_set.cpp:152 modules/commands/ns_set.cpp:218 +#, fuzzy, c-format +msgid "Password for %s changed to %s." +msgstr "A megadott csatorna (%s) új successora: %s." + +#: modules/commands/ns_set.cpp:154 modules/commands/ns_set.cpp:220 +#, fuzzy, c-format +msgid "Password for %s changed." +msgstr "%s nick jelszava elküldve." + +#: modules/commands/ns_getpass.cpp:38 +#, c-format +msgid "Password for %s is %s." +msgstr "%s jelszava: %s." + +#: include/language.h:71 +#, fuzzy +msgid "Password incorrect." +msgstr "Hibás jelszó." + +#: modules/commands/ns_resetpass.cpp:39 +#, c-format +msgid "Password reset email for %s has been sent." +msgstr "Password reset email for %s has been sent." + +#: modules/commands/cs_set.cpp:1289 +msgid "Peace" +msgstr "Békesség" + +#: modules/commands/cs_set.cpp:440 +#, fuzzy, c-format +msgid "Peace option for %s is now off." +msgstr "Peace option for %s is now ON." + +#: modules/commands/cs_set.cpp:434 +#, fuzzy, c-format +msgid "Peace option for %s is now on." +msgstr "Peace option for %s is now ON." + +#: modules/commands/cs_set.cpp:1301 +#, fuzzy +msgid "Persistent" +msgstr "Persistant" + +#: include/language.h:126 +msgid "Please contact an Operator to get a vHost assigned to this nick." +msgstr "" + +#: include/language.h:73 +msgid "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." +msgstr "" + +#: modules/commands/os_jupe.cpp:30 +#, fuzzy +msgid "Please use a valid server name when juping." +msgstr "Kérlek használj érvényes szerver nevet amikor jupolsz!" + +#: include/language.h:104 +msgid "Please use the symbol of # when attempting to register." +msgstr "" + +#: src/mail.cpp:78 +#, c-format +msgid "Please wait %d seconds and retry." +msgstr "Kérlek várj %d másodpercet és próbáld újra." + +#: modules/commands/hs_request.cpp:158 +#, fuzzy, c-format +msgid "Please wait %d seconds before requesting a new vHost." +msgstr "Kérlek, várj %d másodpercet mielőtt SEND parancsot újra használod!" + +#: modules/commands/ms_rsend.cpp:58 modules/commands/ms_send.cpp:57 +#, fuzzy, c-format +msgid "Please wait %d seconds before using the %s command again." +msgstr "Kérlek, várj %d másodpercet mielőtt SEND parancsot újra használod!" + +#: modules/commands/ns_group.cpp:149 +#, c-format +msgid "Please wait %d seconds before using the GROUP command again." +msgstr "Kérlek várj %d másodpercet, mielőtt ismét használod a GROUP parancsot." + +#: modules/commands/ns_register.cpp:198 +#, c-format +msgid "Please wait %d seconds before using the REGISTER command again." +msgstr " Várj %d másodpercet mielőtt használnád ezt a parancsot!" + +#: modules/commands/os_dns.cpp:628 +#, c-format +msgid "Pooled %s." +msgstr "" + +#: modules/commands/os_dns.cpp:237 +msgid "Pooled/Active" +msgstr "" + +#: modules/commands/os_dns.cpp:239 +msgid "Pooled/Not Active" +msgstr "" + +#: modules/commands/bs_set.cpp:161 +msgid "Prevent a bot from being assigned by non IRC operators" +msgstr "" + +#: modules/commands/bs_assign.cpp:153 +#, fuzzy +msgid "Prevent a bot from being assigned to a channel" +msgstr "" +" SUSPEND Felfüggeszti a szoba használatát de\n" +" megőrzi az adatokat és beállításokat." + +#: modules/commands/cs_suspend.cpp:58 +#, fuzzy +msgid "Prevent a channel from being used preserving channel data and settings" +msgstr "" +" SUSPEND Felfüggeszti a szoba használatát de\n" +" megőrzi az adatokat és beállításokat." + +#: modules/commands/cs_set.cpp:1043 +#, fuzzy +msgid "Prevent the channel from expiring" +msgstr " NOEXPIRE Prevent the channel from expiring" + +#: modules/commands/ns_list.cpp:186 +#, fuzzy +msgid "Prevent the nickname from appearing in the LIST command" +msgstr "" +" PRIVATE Prevent the nickname from appearing in a\n" +" /msg %s LIST" + +#: modules/commands/ns_set.cpp:1104 +#, fuzzy +msgid "Prevent the nickname from expiring" +msgstr " NOEXPIRE Prevent the nickname from expiring" + +#: src/access.cpp:46 +msgid "Prevents users being kicked by Services" +msgstr "" + +#: modules/commands/ns_list.cpp:297 modules/commands/cs_list.cpp:262 +#: modules/commands/bs_info.cpp:58 +msgid "Private" +msgstr "Privát" + +#: modules/commands/bs_set.cpp:190 +#, fuzzy, c-format +msgid "Private mode of bot %s is now off." +msgstr "Private mód a %s botban most ON." + +#: modules/commands/bs_set.cpp:185 +#, fuzzy, c-format +msgid "Private mode of bot %s is now on." +msgstr "Private mód a %s botban most ON." + +#: modules/commands/cs_list.cpp:220 +#, fuzzy, c-format +msgid "Private option for %s is now off." +msgstr "Private option for %s is now ON." + +#: modules/commands/cs_list.cpp:214 +#, fuzzy, c-format +msgid "Private option for %s is now on." +msgstr "Private option for %s is now ON." + +#: modules/commands/ns_list.cpp:221 +#, fuzzy, c-format +msgid "Private option is now off for %s." +msgstr "Private option is now ON for %s." + +#: modules/commands/ns_list.cpp:215 +#, fuzzy, c-format +msgid "Private option is now on for %s." +msgstr "Private option is now ON for %s." + +#: modules/commands/cs_flags.cpp:281 +#, c-format +msgid "Privilege %s added to %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/cs_flags.cpp:283 +#, c-format +msgid "Privilege %s removed from %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/ns_set.cpp:1309 +msgid "Protection" +msgstr "Kill védelem" + +#: modules/commands/ns_set.cpp:721 +#, fuzzy, c-format +msgid "Protection is now off for %s." +msgstr "Protection is now ON for %s." + +#: modules/commands/ns_set.cpp:700 +#, fuzzy, c-format +msgid "Protection is now on for %s, with a reduced delay." +msgstr "Protection is now ON for %s, with a reduced delay." + +#: modules/commands/ns_set.cpp:710 +#, fuzzy, c-format +msgid "Protection is now on for %s, with no delay." +msgstr "Protection is now ON for %s, with no delay." + +#: modules/commands/ns_set.cpp:692 +#, fuzzy, c-format +msgid "Protection is now on for %s." +msgstr "Protection is now ON for %s." + +#: modules/commands/os_chankill.cpp:100 +#, fuzzy +msgid "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." +msgstr "" +"Syntax: CHANKILL [+lejárat] #szobaindok\n" +"Akillre tesz minden nicket az adott csatornán. Ez a létezo\n" +"és teljesen valós ident@host maszkot használja, minden \n" +"nick esetében végrehajtja az AKILLt." + +#: modules/commands/ns_set.cpp:1307 +#, fuzzy +msgid "Quick protection" +msgstr "Voices védelme" + +#: modules/commands/os_news.cpp:51 +msgid "RANDOMNEWS {ADD|DEL|LIST} [text|num]" +msgstr "RANDOMNEWS { ADD | DEL | LIST } [ szöveg | szám ]" + +#: modules/commands/cs_enforce.cpp:99 +msgid "REGONLY enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:68 +msgid "RESTRICTED enforced by " +msgstr "" + +#: modules/commands/os_noop.cpp:21 +#, fuzzy +msgid "REVOKE server" +msgstr "NOOP {SET|REVOKE} szerver" + +#: modules/commands/os_news.cpp:56 +#, c-format +msgid "Random news item #%d deleted." +msgstr "Random news tétel #%d törölve." + +#: modules/commands/os_news.cpp:55 +#, fuzzy, c-format +msgid "Random news item #%s not found!" +msgstr "Random news tétel #%d nem található!" + +#: modules/commands/os_news.cpp:52 +msgid "Random news items:" +msgstr "Véletlenszerű hírek listája:" + +#: modules/commands/ms_read.cpp:112 +#, fuzzy +msgid "Read a memo or memos" +msgstr " READ Elolvassa a megadott üzenete(ke)t" + +#: modules/commands/bs_info.cpp:56 +#, fuzzy +msgid "Real name" +msgstr "Valódi neve: %s" + +#: modules/commands/os_list.cpp:153 +#, fuzzy +msgid "Realname" +msgstr "Valódi neve: %s" + +#: modules/commands/os_ignore.cpp:266 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:204 modules/commands/os_forbid.cpp:358 +#: modules/commands/cs_akick.cpp:392 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:361 +msgid "Reason" +msgstr "" + +#: src/xline.cpp:386 +#, fuzzy, c-format +msgid "Reason for %s updated." +msgstr "A megadott csatorna %s successora törölve." + +#: modules/commands/ns_recover.cpp:214 +msgid "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." +msgstr "" + +#: modules/commands/cs_access.cpp:741 +#, fuzzy +msgid "Redefine the meanings of access levels" +msgstr " LEVELS Átállíthatod a szoba hozzáférési szintjeit" + +#: modules/commands/ns_recover.cpp:149 +#, fuzzy +msgid "Regains control of your nick" +msgstr " RELEASE Visszaadja a neved a RECOVER után" + +#: modules/commands/os_sxline.cpp:330 modules/commands/os_sxline.cpp:545 +#: modules/commands/os_akill.cpp:129 +#, fuzzy +msgid "Regex is disabled." +msgstr "%s is enable" + +#: modules/commands/os_sxline.cpp:459 modules/commands/os_sxline.cpp:694 +#: modules/commands/os_akill.cpp:444 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." +msgstr "" + +#: modules/commands/os_ignore.cpp:386 modules/commands/os_forbid.cpp:428 +#: modules/commands/ns_list.cpp:172 modules/commands/cs_list.cpp:167 +#: modules/commands/os_list.cpp:119 modules/commands/os_list.cpp:255 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." +msgstr "" + +#: modules/commands/cs_register.cpp:19 +#, fuzzy +msgid "Register a channel" +msgstr " REGISTER Nicknév regisztráció" + +#: modules/commands/ns_register.cpp:120 +#, fuzzy +msgid "Register a nickname" +msgstr " REGISTER Nicknév regisztráció" + +#: modules/commands/ns_info.cpp:89 modules/commands/cs_info.cpp:55 +#, fuzzy +msgid "Registered" +msgstr "Regisztrálás ideje: %s" + +#: modules/commands/os_stats.cpp:184 +#, c-format +msgid "Registered channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:190 +#, c-format +msgid "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:187 +#, c-format +msgid "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/cs_enforce.cpp:105 +#, c-format +msgid "Registered only enforced on %s." +msgstr "" + +#: modules/commands/cs_register.cpp:86 +#, fuzzy, c-format +msgid "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." +msgstr "" +"Syntax: REGISTER #szoba leírás\n" +"\n" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which must be included, is a\n" +"general description of the channel's purpose.\n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel.\n" +"See the ACCESS command (/msg %s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname. If you haven't,\n" +"/msg %s HELP for information on how to do so." + +#: modules/commands/ns_register.cpp:269 +#, fuzzy, c-format +msgid "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." +msgstr "" +"Syntax: REGISTER jelszó [email]\n" +"\n" +"Regisztrálja a nickneved a %s adatbázisába. Amint a nicked\n" +"regisztráltad, használhatod a SET és ACCESS parancsokat,\n" +"hogy konfiguráljad a nicked beállításait. Olyan jelszót \n" +"válassz, amire emlékezni fogsz, hogy használni tudd a neved\n" +"és a beállításokat eszközölhesd. Később szükséged lehet a\n" +"nickeddel kapcsolatos beállítások végrehajtására.\n" +"(Jegyzet: PROBLÉMÁT OKOZHAT FIDO, Fido, és fido\n" +"mind különböző jelszavak!)\n" +"Útikalaúz jelszó választáshoz:\n" +"\n" +"A jelszavad ne legyen könnyen kitalálható. Például az\n" +"általad használt valósnevet megadni jelszónak rossz ötlet.\n" +"A nickneved használni jelszónak még rosszabb ötlet ;) és\n" +"a %s nem is engedi. A rövid jelszavak is rosszak a védelem\n" +"szempontjából, ezért válassz legalább 5 karakter hosszút.\n" +"Végezetül ne használhatsz szóközt a jelszóban.\n" +"\n" +"Aze-mail paraméter megadás lehetséges, megadásakor\n" +"beállítja a nickedhez. Megadása a legtöbb hálózaton\n" +"szükséges. Az e-mail címed nem kerül harmadik személy\n" +"tudtára, bizalmasan kezeljük.\n" +"\n" +"Ez a parancs létrehoz egy új csoportot a nickeddel, ami\n" +"lehetővé teszi számodra, hogy másik nickeket regisztrálva\n" +"megoszthasd a hozzáféréseidet és beállításaidat a nickjeid\n" +"között. Bővebb információkért írd be: /msg %s HELP GROUP" + +#: modules/commands/ns_register.cpp:145 +#, fuzzy +msgid "Registration is currently disabled." +msgstr "Sajnálom, a csatorna regisztráció jelenleg szünetel." + +#: modules/commands/cs_set.cpp:400 +#, fuzzy +msgid "Regulate the use of critical commands" +msgstr " PEACE Szabályozza a kritikus parancsok használatát" + +#: modules/commands/hs_request.cpp:283 +#, fuzzy +msgid "Reject the requested vHost for the given nick." +msgstr " STATUS Returns the owner status of the given nickname" + +#: modules/commands/hs_request.cpp:240 +#, fuzzy +msgid "Reject the requested vHost of a user" +msgstr " DEL Törli egy felhasználónak a vhostját" + +#: modules/commands/cs_suspend.cpp:151 +#, fuzzy +msgid "Releases a suspended channel" +msgstr " UNSUSPEND Törli a suspendet a csatornáról." + +#: modules/commands/cs_suspend.cpp:191 +#, fuzzy +msgid "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." +msgstr "" +"Syntax: UNSUSPEND #szoba\n" +"\n" +"Törli a suspendet a csatornáról. Összes adat és beállítás\n" +"megőrizve a suspend használat előttröl.\n" +"\n" +"Korlátozva Szervíz adminnak." + +#: modules/commands/os_module.cpp:56 +#, fuzzy +msgid "Reload a module" +msgstr " MODLOAD Betölti a modult" + +#: modules/commands/os_reload.cpp:19 +#, fuzzy +msgid "Reload services' configuration file" +msgstr " RELOAD Újratölti a szervíz Konfigurációs fájlját" + +#: modules/commands/ns_group.cpp:236 +#, fuzzy +msgid "Remove a nick from a group" +msgstr " UNGROUP Remove a nick from a group" + +#: modules/commands/cs_unban.cpp:19 +#, fuzzy +msgid "Remove all bans preventing a user from entering a channel" +msgstr "" +" UNBAN Remove all bans preventing a user from entering a channel" + +#: modules/commands/os_noop.cpp:19 +#, fuzzy +msgid "Remove all operators from a server remotely" +msgstr "" +" NOOP Ideiglenesen törli az összes O:line-t a szerver\n" +" távollétében" + +#: modules/commands/os_dns.cpp:543 +#, fuzzy, c-format +msgid "Removed IP %s from %s." +msgstr "\tRögzített módok: %s" + +#: modules/commands/os_dns.cpp:460 +#, c-format +msgid "Removed server %s from zone %s." +msgstr "" + +#: modules/commands/os_dns.cpp:483 +#, c-format +msgid "Removed server %s." +msgstr "" + +#: modules/commands/cs_mode.cpp:909 +#, c-format +msgid "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." +msgstr "" + +#: modules/commands/cs_mode.cpp:890 +#, fuzzy, c-format +msgid "Removes %s status from you or the specified nick on a channel" +msgstr " OP Gives Op status to a selected nick on a channel" + +#: modules/commands/cs_updown.cpp:146 +#, fuzzy +msgid "Removes a selected nicks status from a channel" +msgstr " KICK Kicks a selected nick from a channel" + +#: modules/commands/cs_updown.cpp:223 +msgid "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." +msgstr "" + +#: src/xline.cpp:412 +#, c-format +msgid "Removing %s because %s covers it." +msgstr "" + +#: modules/commands/bs_kick.cpp:1171 modules/commands/bs_kick.cpp:1173 +#: modules/commands/bs_kick.cpp:1176 +#, fuzzy +msgid "Repeat kicker" +msgstr "\tIsmétlésért kirúgás: %s" + +#: modules/commands/hs_request.cpp:78 +#, fuzzy +msgid "Request a vHost for your nick" +msgstr "Nincs beállítva email cím a nevedhez." + +#: modules/commands/hs_request.cpp:179 +msgid "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." +msgstr "" + +#: modules/commands/ns_register.cpp:312 +#, fuzzy +msgid "Resend registration confirmation email" +msgstr " RELOAD Újratölti a szervíz Konfigurációs fájlját" + +#: modules/commands/cs_set.cpp:621 +#, fuzzy +msgid "Restrict access to the channel" +msgstr " RESTRICTED Restrict access to the channel" + +#: modules/commands/cs_set.cpp:1291 +#, fuzzy +msgid "Restricted access" +msgstr "Korlátozott hozzáférés" + +#: modules/commands/cs_set.cpp:661 +#, fuzzy, c-format +msgid "Restricted access option for %s is now off." +msgstr "Restricted access option for %s is now ON." + +#: modules/commands/cs_set.cpp:655 +#, fuzzy, c-format +msgid "Restricted access option for %s is now on." +msgstr "Restricted access option for %s is now ON." + +#: modules/commands/cs_enforce.cpp:73 +#, fuzzy, c-format +msgid "Restricted enforced on %s." +msgstr "Korlátozott hozzáférés" + +#: modules/commands/cs_set.cpp:335 +#, fuzzy +msgid "Retain modes when channel is not in use" +msgstr " KEEPTOPIC Topic megtartása ha a szoba nincs használatban" + +#: modules/commands/cs_topic.cpp:20 +#, fuzzy +msgid "Retain topic when channel is not in use" +msgstr " KEEPTOPIC Topic megtartása ha a szoba nincs használatban" + +#: modules/commands/ns_getpass.cpp:19 +#, fuzzy +msgid "Retrieve the password for a nickname" +msgstr "" +" GETPASS Kiirja a jeszavát a nicknévnek\n" +" (encryption esetén nem használható)" + +#: modules/commands/hs_request.cpp:296 +msgid "Retrieves the vhost requests" +msgstr "" + +#: modules/commands/cs_getkey.cpp:19 +#, fuzzy +msgid "Returns the key of the given channel" +msgstr " GETKEY Returns the key of the given channel" + +#: modules/commands/cs_getkey.cpp:57 +#, fuzzy +msgid "Returns the key of the given channel." +msgstr " GETKEY Returns the key of the given channel" + +#: modules/commands/ns_getemail.cpp:58 +#, fuzzy +msgid "Returns the matching accounts that used given email." +msgstr " GETKEY Returns the key of the given channel" + +#: modules/commands/ns_status.cpp:19 +#, fuzzy +msgid "Returns the owner status of the given nickname" +msgstr " STATUS Returns the owner status of the given nickname" + +#: modules/commands/ns_getpass.cpp:50 +#, fuzzy +msgid "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." +msgstr "" +"Syntax: GETPASS nicknév\n" +"\n" +"Visszadja a megadott nicknév jelszavát. Jegyzet Ezt \n" +"a parancsot amaikor használod, üzenetet küld arról \n" +"hogy ki használta és kinek a jelszavát kérte le. \n" +"Naplózva lesz és WALLOPS/GLOBOPS üzenetben is megjelenik.\n" +"\t\n" +"Korlátozva Szervíz adminokra.\n" +"\n" +"A parancs nem elérhető, ha az encryption használatban van." + +#: modules/commands/ns_status.cpp:55 +#, fuzzy +msgid "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." +msgstr "" +"Syntax: STATUS nicknév...\n" +"\n" +"A következőket kapod, ha a nicknévre, amit a felhasználó \n" +"használ azonosította magát, mint tulajdonos. \n" +"Az eredmény formája a következő:\n" +"\n" +"\tnicknév státusz-kód account\n" +"\n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +"\n" +" 0 - Nincs ilyen user online vagy a nick nem regisztrált\n" +" 1 - A felhasználó nem azonosított be, mint a nick tulajdonosa\n" +" 2 - A felhasználó beazonosított, mint tulajdonos de csak a \n" +" hozzáférési lista alapján\n" +" 3 - A felhasználó beazonosított tulajdonosként a jelszavával\n" +" \n" +"Tizenhat nicknév küldhető el parancsonként; a többit \n" +"figyelmen kívül hagyja. If no nickname is given, your status\n" +"will be returned." + +#: modules/commands/bs_kick.cpp:1181 modules/commands/bs_kick.cpp:1183 +#: modules/commands/bs_kick.cpp:1186 +#, fuzzy +msgid "Reverses kicker" +msgstr "\tVisszafelé írásért kirúgás: %s" + +#: modules/commands/ns_logout.cpp:21 +#, fuzzy +msgid "Reverses the effect of the IDENTIFY command" +msgstr " LOGOUT Reverses the effect of the IDENTIFY command" + +#: modules/commands/os_noop.cpp:20 +#, fuzzy +msgid "SET server" +msgstr "NOOP {SET|REVOKE} szerver" + +#: modules/commands/os_dns.cpp:667 +msgid "SET server.name option value" +msgstr "" + +#: modules/commands/ns_cert.cpp:378 +#, fuzzy, c-format +msgid "SSL certificate fingerprint accepted, you are now identified to %s." +msgstr "Jelszavad elfogadva - azonosítás sikeres." + +#: modules/commands/ns_cert.cpp:398 +#, fuzzy +msgid "SSL certificate fingerprint accepted, you are now identified." +msgstr "Jelszavad elfogadva - azonosítás sikeres." + +#: modules/commands/cs_enforce.cpp:137 +#, c-format +msgid "SSL only enforced on %s." +msgstr "" + +#: modules/commands/cs_enforce.cpp:131 +msgid "SSLONLY enforced by " +msgstr "" + +#: modules/commands/os_shutdown.cpp:47 +#, fuzzy +msgid "Save databases and restart Services" +msgstr " RESTART Menti az adatbázist, és újraindítja a szervízt" + +#: modules/commands/os_logsearch.cpp:32 +msgid "Searches logs for a matching pattern" +msgstr "" + +#: modules/commands/cs_set.cpp:1295 +#, fuzzy +msgid "Secure founder" +msgstr "Founderjog védelme" + +#: modules/commands/cs_set.cpp:786 +#, fuzzy, c-format +msgid "Secure founder option for %s is now off." +msgstr "Secure founder option for %s is now ON." + +#: modules/commands/cs_set.cpp:780 +#, fuzzy, c-format +msgid "Secure founder option for %s is now on." +msgstr "Secure founder option for %s is now ON." + +#: modules/commands/cs_set.cpp:1297 +#, fuzzy +msgid "Secure ops" +msgstr "Opjog védelme" + +#: modules/commands/cs_set.cpp:850 +#, fuzzy, c-format +msgid "Secure ops option for %s is now off." +msgstr "Secure ops option for %s is now ON." + +#: modules/commands/cs_set.cpp:844 +#, fuzzy, c-format +msgid "Secure ops option for %s is now on." +msgstr "Secure ops option for %s is now ON." + +#: modules/commands/cs_set.cpp:723 +#, fuzzy, c-format +msgid "Secure option for %s is now off." +msgstr "Secure option for %s is now ON." + +#: modules/commands/cs_set.cpp:717 +#, fuzzy, c-format +msgid "Secure option for %s is now on." +msgstr "Secure option for %s is now ON." + +#: modules/commands/ns_set.cpp:1044 +#, fuzzy, c-format +msgid "Secure option is now off for %s." +msgstr "Secure option is now ON for %s." + +#: modules/commands/ns_set.cpp:1038 +#, fuzzy, c-format +msgid "Secure option is now on for %s." +msgstr "Secure option is now ON for %s." + +#: modules/commands/cs_enforce.cpp:42 +#, fuzzy, c-format +msgid "Secureops enforced on %s." +msgstr "Secure option is now ON for %s." + +#: modules/commands/cs_set.cpp:1293 modules/commands/ns_set.cpp:1311 +msgid "Security" +msgstr "Biztonság" + +#: modules/commands/cs_xop.cpp:570 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the access list." +msgstr "" +"Írd be: /msg %s HELP SET opció bővebb információért az\n" +"adott opcióról." + +#: modules/commands/cs_xop.cpp:573 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the flags system." +msgstr "" +"Írd be: /msg %s HELP SET opció bővebb információért az\n" +"adott opcióról." + +#: modules/commands/ms_send.cpp:24 +#, fuzzy +msgid "Send a memo to a nick or channel" +msgstr " SEND Üzenetet küld egy nicknek vagy csatornára" + +#: modules/commands/ms_staff.cpp:24 +#, fuzzy +msgid "Send a memo to all opers/admins" +msgstr " STAFF Memo küldése minden opernek/adminnak." + +#: modules/commands/ms_sendall.cpp:24 +#, fuzzy +msgid "Send a memo to all registered users" +msgstr " SENDALL Memo küldése minden regisztrált felhasználónak." + +#: modules/commands/gl_global.cpp:21 +#, fuzzy +msgid "Send a message to all users" +msgstr " GLOBAL Üzenetet küld összes felhasználónak" + +#: modules/commands/ms_list.cpp:64 +#, fuzzy +msgid "Sender" +msgstr "Founderjog védelme" + +#: modules/commands/ms_rsend.cpp:24 +#, fuzzy +msgid "Sends a memo and requests a read receipt" +msgstr " RSEND Memo üzenetet küld és olvasási visszaigazolást kér" + +#: modules/commands/ns_resetpass.cpp:50 +#, fuzzy +msgid "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." +msgstr "" +"Syntax: RESETPASS nickname\n" +"\n" +"Sends a code key to the nickname with instructions on how to\n" +"reset their password." + +#: modules/commands/ms_sendall.cpp:52 +#, fuzzy +msgid "Sends all registered users a memo containing memo-text." +msgstr "" +"Syntax: SENDALL memo-üzenet\n" +"\n" +"Memo üzenet küldése minden regisztrált felhasználónak." + +#: modules/commands/ms_staff.cpp:48 +#, fuzzy +msgid "Sends all services staff a memo containing memo-text." +msgstr "" +"Syntax: STAFF memo-üzenet\n" +"\n" +"Memo üzenet küldése az opereknek/adminoknak." + +#: modules/commands/ms_send.cpp:66 +#, fuzzy +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." +msgstr "" +"Syntax: SEND { nick | #szoba } memo-szöveg\n" +"\n" +"Üzenetet küld a megnevezett nicknek vagy csatornára\n" +"a üzenet-szövegét tartalmazva. Amikor nicknévnek küldesz\n" +"a címzett kap egy üzenetet az új üzenet érkezéséről\n" +"A címzett csatornának vagy nicknévnek regisztráltnak kell\n" +"lennie." + +#: modules/commands/ms_rsend.cpp:80 +#, fuzzy +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." +msgstr "" +"Syntax: RSEND {nick | #szoba} memo-üzenet\n" +"\n" +"Memot küld a megadott névnek, szobának a memo-üzenet\n" +"tartalmával. Ha nicknévnek küldöd, akkor értesítést fog\n" +"kapni, hogy új üzenete érkezett. A cél nicknévnek vagy\n" +"csatornának regisztráltnak kell lennie.\n" +"Amint a címzett elolvasta a memot, egy automatikus értesítést\n" +"fog kapni a feladó arról, hogy az üzenetét elolvasták." + +#: modules/commands/ms_read.cpp:199 +#, fuzzy +msgid "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Syntax: READ [#szoba] {sorszám| list| LAST | NEW}\n" +"\n" +"Elküldi a megadott üzenetek tartalmát. A LAST opcióval\n" +"megjeleníti a legutolsó üzenetet. A NEW opcióval\n" +"minden új üzenetet. Egyébként a megadott számú üzenetet.\n" +"Megadhatsz számlistát is, mint a LIST parancsnál.\n" +"\n" +"Példák:\n" +"\n" +"\tREAD 2-5,7-9\n" +"\t\tMegjeleníti 2 és 5, a 7 és 9 között a memo üzeneteket" + +#: modules/commands/os_dns.cpp:218 +#, fuzzy +msgid "Server" +msgstr "NOOP {SET|REVOKE} szerver" + +#: modules/commands/os_dns.cpp:375 +#, fuzzy, c-format +msgid "Server %s added to zone %s." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:345 +#, fuzzy, c-format +msgid "Server %s already exists." +msgstr "%s nevű bot már létezik." + +#: modules/commands/os_noop.cpp:31 modules/commands/os_dns.cpp:430 +#: modules/commands/os_dns.cpp:493 modules/commands/os_dns.cpp:532 +#: modules/commands/os_dns.cpp:571 modules/commands/os_dns.cpp:604 +#: modules/commands/os_dns.cpp:639 +#, fuzzy, c-format +msgid "Server %s does not exist." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:619 +#, fuzzy, c-format +msgid "Server %s has no configured IPs." +msgstr "A %s nicknevet dropoltad." + +#: modules/commands/os_dns.cpp:357 +#, fuzzy, c-format +msgid "Server %s is already in zone %s." +msgstr "You are already in %s! " + +#: modules/commands/os_dns.cpp:614 +#, fuzzy, c-format +msgid "Server %s is already pooled." +msgstr "Module %s is already loaded." + +#: modules/commands/os_dns.cpp:609 +#, fuzzy, c-format +msgid "Server %s is not currently linked." +msgstr "%s jelenleg online." + +#: modules/commands/os_dns.cpp:443 +#, fuzzy, c-format +msgid "Server %s is not in zone %s." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:384 +#, fuzzy, c-format +msgid "Server %s is not linked to the network." +msgstr "Nincsen bot kijelölve %s szobában többet." + +#: modules/commands/os_dns.cpp:644 +#, fuzzy, c-format +msgid "Server %s is not pooled." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:465 +#, c-format +msgid "Server %s must be quit before it can be deleted." +msgstr "" + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Servers" +msgstr "NOOP {SET|REVOKE} szerver" + +#: modules/commands/os_stats.cpp:155 +#, c-format +msgid "Servers found: %d" +msgstr "Servers found: %d" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Service" +msgstr "Servers found: %d" + +#: modules/commands/ns_recover.cpp:51 +#, fuzzy, c-format +msgid "Service's hold on %s has been released." +msgstr "A Services rendelkezésedre bocsájtotta a nicket." + +#: data/nickserv.example.conf:236 data/chanserv.example.conf:827 +#, fuzzy +msgid "Services Operator commands" +msgstr "%s is a services operator of type %s." + +#: modules/commands/os_defcon.cpp:443 modules/commands/os_defcon.cpp:454 +#: modules/commands/os_defcon.cpp:462 modules/commands/os_defcon.cpp:470 +#: modules/commands/os_defcon.cpp:478 +#, fuzzy +msgid "Services are in DefCon mode, please try again later." +msgstr "Szervíz Defcon módban fut, próbáld később." + +#: include/language.h:70 +#, fuzzy +msgid "Services are in read-only mode!" +msgstr "Szervíz most  csak olvas módban." + +#: modules/commands/os_defcon.cpp:186 modules/commands/os_defcon.cpp:213 +#, fuzzy, c-format +msgid "Services are now at DEFCON %d." +msgstr "Szervíz új DEFCON szintje %d" + +#: modules/commands/os_set.cpp:128 +#, fuzzy, c-format +msgid "Services are now in debug mode (level %d)." +msgstr "Szervíz most debug módban (szint: %d)." + +#: modules/commands/os_set.cpp:114 +#, fuzzy +msgid "Services are now in debug mode." +msgstr "Szervíz most debug módban fut." + +#: modules/commands/os_set.cpp:159 +msgid "Services are now in expire mode." +msgstr "Szervíz elévülő módban van." + +#: modules/commands/os_set.cpp:153 +msgid "Services are now in no expire mode." +msgstr "Szervíz nem elévülő módban van." + +#: modules/commands/os_set.cpp:120 +#, fuzzy +msgid "Services are now in non-debug mode." +msgstr "Szervíz most már nem fut debug módban." + +#: modules/commands/os_set.cpp:47 +msgid "Services are now in read-only mode." +msgstr "Szervíz most  csak olvas módban." + +#: modules/commands/os_set.cpp:53 +msgid "Services are now in read-write mode." +msgstr "Szervíz most olvas ír módban." + +#: src/mail.cpp:76 +msgid "Services have been configured to not send mail." +msgstr "A Szervíz úgy van beállítva, hogy nem küld mailt." + +#: modules/commands/os_ignore.cpp:280 +#, fuzzy +msgid "Services ignore list:" +msgstr " IGNORE Módosítja a Szervíz mellőzési listáját" + +#: modules/commands/os_mode.cpp:33 modules/commands/os_kick.cpp:39 +#, fuzzy +msgid "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" +msgstr "" +"Szervíz nem tudja változtatni a módokat.\n" +"A szerverek U:lines beállitása helyes?" + +#: modules/commands/os_stats.cpp:140 +#, fuzzy, c-format +msgid "Services up %s." +msgstr "Servers found: %d" + +#: modules/commands/ns_set.cpp:266 +#, fuzzy, c-format +msgid "Services will from now on set status modes on %s in channels." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/cs_set.cpp:114 +#, fuzzy, c-format +msgid "Services will no longer automatically give modes to users in %s." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/ns_set.cpp:272 +#, fuzzy, c-format +msgid "Services will no longer set status modes on %s in channels." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/cs_set.cpp:108 +#, fuzzy, c-format +msgid "Services will now automatically give modes to users in %s." +msgstr "Services will now autoop %s in channels." + +#: modules/commands/ns_set.cpp:940 +#, c-format +msgid "Services will now reply to %s with messages." +msgstr "Services will now reply to %s with messages." + +#: modules/commands/ns_set.cpp:946 +#, c-format +msgid "Services will now reply to %s with notices." +msgstr "Services will now reply to %s with notices." + +#: modules/commands/os_reload.cpp:34 +#, fuzzy +msgid "Services' configuration has been reloaded." +msgstr "Szervíz konfigurációs fájl újratöltve." + +#: modules/commands/os_session.cpp:192 +msgid "Session" +msgstr "" + +#: modules/commands/os_session.cpp:382 +#, c-format +msgid "Session limit for %s set to %d." +msgstr "Session korlát %s részére %d-re állítva." + +#: modules/commands/os_session.cpp:257 modules/commands/os_session.cpp:534 +msgid "Session limiting is disabled." +msgstr "Session korlátozás tiltva." + +#: modules/commands/os_stats.cpp:195 +#, c-format +msgid "Sessions: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/ns_set.cpp:74 +#, fuzzy +msgid "Set SET-options on another nickname" +msgstr " SASET Set SET-options on another nickname" + +#: modules/commands/cs_set.cpp:20 +#, fuzzy +msgid "Set channel options and information" +msgstr " SET Beállíthatod a csatornád opcióit" + +#: modules/commands/cs_set.cpp:137 +#, fuzzy +msgid "Set how Services make bans on the channel" +msgstr " BANTYPE A banolás tipusának beállítása" + +#: modules/commands/ms_set.cpp:206 +#, fuzzy +msgid "Set options related to memos" +msgstr " SET Üzenetekkel kapcsolatos beállításokat hajt végre" + +#: modules/commands/ns_set.cpp:19 +#, fuzzy +msgid "Set options, including kill protection" +msgstr " SET Opciók beállítása, például kill védelem" + +#: modules/commands/cs_set.cpp:472 +#, fuzzy +msgid "Set the channel as permanent" +msgstr " PERSIST Set the channel as permanent" + +#: modules/commands/cs_set.cpp:204 +#, fuzzy +msgid "Set the channel description" +msgstr " DESC A szobameghatározás állítás" + +#: modules/commands/ns_set.cpp:329 +#, fuzzy +msgid "Set the display of your group in Services" +msgstr " DISPLAY Set the display of your group in Services" + +#: modules/commands/cs_set.cpp:266 +#, fuzzy +msgid "Set the founder of a channel" +msgstr " FOUNDER A founder megváltoztatása" + +#: modules/commands/ns_set.cpp:793 +#, fuzzy +msgid "Set the language Services will use when messaging you" +msgstr " LANGUAGE A szervíz nyelvezetének megválasztása" + +#: modules/commands/ns_set.cpp:172 +#, fuzzy +msgid "Set the nickname password" +msgstr " PASSWORD Set the nickname password" + +#: modules/commands/cs_set.cpp:949 +#, fuzzy +msgid "Set the successor for a channel" +msgstr " SUCCESSOR A successor megadása" + +#: modules/commands/hs_set.cpp:125 +#, fuzzy +msgid "Set the vhost for all nicks in a group" +msgstr " SETALL Beállítja a vhosztot összes nicknek a csoportban" + +#: modules/commands/hs_set.cpp:19 +#, fuzzy +msgid "Set the vhost of another user" +msgstr " SET Beállít egy vhosztot a felhasználónak" + +#: modules/commands/os_set.cpp:169 +#, fuzzy +msgid "Set various global Services options" +msgstr " SET Beállítja szervíz általános változóit" + +#: modules/commands/ns_set.cpp:119 +#, fuzzy +msgid "Set your nickname password" +msgstr " PASSWORD Set your nickname password" + +#: modules/commands/bs_kick.cpp:271 +#, fuzzy, c-format +msgid "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK channel ITALICS {ON|OFF} [ttb]\n" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +"ttb is the number of times a user can be kicked\n" +"before it get banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:307 +#, fuzzy, c-format +msgid "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK #szoba BADWORDS {ON|OFF} [ttb]\n" +"\n" +"Beállítja a csúnyaszavak miatti kirúgást. Ha engedélyezve\n" +"van, akkor a bot kirúgja azt, aki kiejt egy olyan szót,\n" +"ami szerepel a csúnyaszavak listáján.\n" +"\n" +"A csúnyaszavak listáját a csatornádhoz neked kell megadnod\n" +"A BADWORDS paranccsal. Írd be /msg %s HELP BADWORDS \n" +"bővebb információkért.\n" +"\n" +"A ttb a banolás elotti kickek száma.\n" +"Ha nem adod meg, akkor csak kirúgást eszközöl a bot.\n" +"Ha megadod a ttb-t, akkor x kirúgás után banol a bot." + +#: modules/commands/cs_set.cpp:186 +#, fuzzy +msgid "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" +msgstr "" +"Syntax: %s #szoba BANTYPE bantípus\n" +"\n" +"A banolás típusának beállítása, amit a Services akkor fog\n" +"használni, ha valakit banolni kell a csatornáról.\n" +"\n" +"A bantípus egy szám 0 és 3 között a jelentése:\n" +"\n" +"0: *!user@host formátumú tiltás\n" +"1: *!*user@host formátumú tiltás\n" +"2: *!*@host formátumú tiltás\n" +"3: *!*user@*.domain formátumú tiltás" + +#: modules/commands/bs_kick.cpp:345 +#, fuzzy +msgid "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK #szoba BOLDS { ON|OFF } [ ttb ]\n" +"\n" +"Beállítja a félkövér írásért járó kirúgást.\n" +"Ha engedélyezve van akkor a bot kirúg a félkövér betűkért.\n" +"\n" +"A ttb a banolás elotti kickek száma.\n" +"Ha nem adod meg, akkor csak kirúgást eszközöl a bot.\n" +"Ha megadod a ttb-t, akkor x kirúgás után banol a bot." + +#: modules/commands/bs_kick.cpp:436 +#, fuzzy, c-format +msgid "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK #szobaCAPS { ON|OFF } [ ttb [ min [ százalék ]]]\n" +"\n" +"Beállítja a túlzott caps miatt járó kirúgást.\n" +"Ha engedélyezve van, akkor a bot kirúgja a \"kiabálókat\".\n" +"\n" +"A bot csak akkor rúgja ki a usert, ha legalább min számú\n" +"betű van és ez legalább százaléka%% az összes szövegnek\n" +"a sorban (ha nincs megadva, akkor 10 karakter a min és\n" +"annak legalább a 25%-a az alapbeállítás)\n" +"\n" +"A ttb a banolás előtti kickek száma.\n" +"Ha nem adod meg, akkor csak kirúgást eszközöl a bot.\n" +"Ha megadod a ttb-t, akkor x kirúgás után banol a bot." + +#: modules/commands/bs_kick.cpp:475 +#, fuzzy +msgid "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK #szoba COLORS { ON|OFF } [ ttb ]\n" +"\n" +"Beállítja a szines írásért járó kirúgást.\n" +"Ha engedélyezve van akkor a bot kirúgja a színesen írókat.\n" +"\n" +"A ttb a banolás előtti kickek száma.\n" +"Ha nem adod meg, akkor csak kirúgást eszközöl a bot.\n" +"Ha megadod a ttb-t, akkor x kirúgás után banol a bot." + +#: modules/commands/cs_set.cpp:255 +#, fuzzy +msgid "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." +msgstr "" +"Syntax: %s #szoba DESC leírás\n" +"\n" +"Beállítható a szoba általános meghatározása, ami látszódni\n" +"fog a LIST és INFO parancs használata esetén." + +#: modules/commands/bs_kick.cpp:571 +#, fuzzy +msgid "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK #szoba FLOOD { ON|OFF } [ ttb [ sor [ mp ]]]\n" +"\n" +"Beállítja a flood miatti kirúgást. Ha engedélyezve van\n" +"akkor a bot kirúgja a floodoló usereket, ha legalább\n" +"sor számú sort írtak mp másodpercnyi idő alatt.\n" +"(ha nincs megadva, akkor 6 sor és 10 mp alatt).\n" +"\n" +"A ttb a banolás előtti kickek száma.\n" +"Ha nem adod meg, akkor csak kirúgást eszközöl a bot.\n" +"Ha megadod a ttb-t, akkor x kirúgás után banol a bot." + +#: modules/commands/bs_kick.cpp:607 +#, fuzzy +msgid "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK channel ITALICS {ON|OFF} [ttb]\n" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +"ttb is the number of times a user can be kicked\n" +"before it get banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:706 +#, fuzzy +msgid "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK #szoba REPEAT { ON|OFF } [ ttb [ szám ]]\n" +"\n" +"Beállítja az ismétlés miatti kirúgást. Ha engedélyezve\n" +"van az opció, akkor a bot kirúgja az önmagukat ismétlő\n" +"usereket, ha szám alkalommal ismételtek. \n" +"(Ha nem adsz meg értéket, akkor az érték 3 lesz)\n" +"\n" +"A ttb a banolás előtti kickek száma.\n" +"Ha nem adod meg, akkor csak kirúgást eszközöl a bot.\n" +"Ha megadod a ttb-t, akkor x kirúgás után banol a bot." + +#: modules/commands/bs_kick.cpp:742 +#, fuzzy +msgid "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK #szobaREVERSES { ON|OFF } [ ttb ]\n" +"\n" +"Beállítja a visszafelé írásért járó kirúgást.\n" +"Ha engedélyezve van akkor a bot kirúgja a reverse írókat.\n" +"\n" +"A ttb a banolás előtti kickek száma.\n" +"Ha nem adod meg, akkor csak kirúgást eszközöl a bot.\n" +"Ha megadod a ttb-t, akkor x kirúgás után banol a bot.\t" + +#: modules/commands/bs_kick.cpp:776 +#, fuzzy +msgid "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK #szobaUNDERLINES { ON|OFF } [ ttb ]\n" +"\n" +"Beállítja az aláhúzott írásért járó kirúgást.\n" +"Ha engedélyezve van akkor a bot kirúgja az aláhúzva írókat\n" +"\n" +"A ttb a banolás előtti kickek száma.\n" +"Ha nem adod meg, akkor csak kirúgást eszközöl a bot.\n" +"Ha megadod a ttb-t, akkor x kirúgás után banol a bot." + +#: modules/commands/hs_set.cpp:206 +#, fuzzy +msgid "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." +msgstr "" +"Syntax: SETALL  .\n" +"Beállítja a vhosztot összes nick részére aki a csoportban \n" +"van. Ha az IRCD támogatja a vIdent, akkor használja a \n" +"settall @ parancsot, ez beállítja\n" +"az adott identet és hosztot az összes tag részére vhosztként.\n" +"*Jegyzet: ez nem fogja frissíteni a vhostot azoknak, akik\n" +"a nickeket a csoportban a parancs után jegyezték\t\n" +"Korlátozva Hoszt változtatókra." + +#: modules/commands/hs_set.cpp:99 +#, fuzzy +msgid "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." +msgstr "" +"Syntax: SET  .\n" +"\n" +"Beállítja vhostnak a nick részére a hosztmaszkot.\n" +"Ha az IRCD támogatja a vIdentet használd a SET\n" +" @, beállitja az identet\n" +" és a hosztot a nick vhosztjaként.\n" +"\n" +"Korlátozva Hoszt változtatókra." + +#: modules/commands/os_set.cpp:199 +#, fuzzy +msgid "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" +msgstr "" +"Syntax: SET opció beállítás\n" +"\n" +"Beállítja a Services általános opcióit.\n" +"A lehetséges opciók:\n" +" READONLY Csak-olvasás vagy olvasás-írás mód beállítása\n" +" LOGCHAN Kiírja a naplózott üzeneteket a csatornára\n" +" DEBUG Bekapcsolja/kikapcsolja a debug módot\n" +" NOEXPIRE Bekapcsolja/kikapcsolja a nem elévülő módot\n" +" SUPERADMIN Bekapcsolja/kikapcsolja a super-admin módot\n" +" IGNORE Activate or deactivate ignore mode\n" +" LIST List the options\n" +"\n" +"Korlátozva Szervíz adminnak." + +#: modules/commands/ms_set.cpp:235 +#, fuzzy, c-format +msgid "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Syntax: SET opció paraméterek\n" +"\n" +"Beállít különbözo memo opciókat. \n" +"Az opció lehet az alábbiak egyike:\n" +"\n" +" NOTIFY Itt állíthatod be, ha figyelmeztetést szeretnél\n" +" kapni az új üzenetekrol (csak nicknevehez)\n" +" LIMIT Beállítja a maximális üzenetek számát\n" +"\n" +"További információért írd be: /msg %s HELP SET opció" + +#: modules/commands/ns_set.cpp:33 modules/commands/ns_set.cpp:88 +#, fuzzy +msgid "Sets various nickname options. option can be one of:" +msgstr "" +"Syntax: SET opció paraméterek\n" +"\n" +"Beállítható nicknév opciók. Az opció ezek egyike lehet:" + +#: modules/commands/ns_set.cpp:237 +msgid "" +"Sets whether services should set channel status modes on you automatically." +msgstr "" + +#: modules/commands/cs_set.cpp:1090 +#, fuzzy +msgid "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." +msgstr "" +"Syntax: SET #szoba NOEXPIRE {ON | OFF}\n" +"\n" +"Beállítja a szoba elévülését. Beállitva az\n" +"ON paranmétert megelőzi az elévülő csatornákat.\n" +"\n" +"Korlátozva Szervíz adminnak." + +#: modules/commands/ns_set.cpp:315 +#, fuzzy, c-format +msgid "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." +msgstr "" +"Syntax: SASET nickname AUTOOP {ON | OFF}\n" +"\n" +"Sets whether the given nickname will be opped automatically.\n" +"Set to ON to allow ChanServ to op the given nickname \n" +"automatically when joining channels." + +#: modules/commands/ns_set.cpp:1145 +#, fuzzy +msgid "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." +msgstr "" +"Syntax: SASET nickname NOEXPIRE {ON | OFF}\n" +"\n" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." + +#: modules/commands/ns_set.cpp:288 +#, fuzzy, c-format +msgid "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." +msgstr "" +"Syntax: SET AUTOOP {ON | OFF}\n" +"\n" +"Sets whether you will be opped automatically. Set to ON to \n" +"allow ChanServ to op you automatically when entering channels." + +#: modules/commands/cs_access.cpp:648 modules/commands/cs_access.cpp:689 +#, fuzzy, c-format +msgid "" +"Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." +msgstr "" +"%s beállítás nem ismert. Írd be /msg %s HELP LEVELS DESC\n" +"az érvényes beállítások listájának megtekintéséhez. " + +#: modules/commands/os_set.cpp:133 +#, fuzzy +msgid "Setting for DEBUG must be ON, OFF, or a positive number." +msgstr "A DEBUG beállításhoz kell ON,/OFF,/ pozitív szám." + +#: modules/commands/os_set.cpp:162 +#, fuzzy +msgid "Setting for NOEXPIRE must be ON or OFF." +msgstr "Az NOEXPIRE beállításhoz kell ON vagy OFF." + +#: modules/commands/os_set.cpp:56 +#, fuzzy +msgid "Setting for READONLY must be ON or OFF." +msgstr "READONLY beállitáshoz kell lenni ON vagy OFF." + +#: modules/commands/os_set.cpp:95 +#, fuzzy +msgid "Setting for super admin must be ON or OFF." +msgstr "READONLY beállitáshoz kell lenni ON vagy OFF." + +#: modules/commands/cs_set.cpp:74 +#, fuzzy +msgid "Should services automatically give status to users" +msgstr " AUTOOP Should services op you automatically. " + +#: modules/commands/os_stats.cpp:203 +#, fuzzy +msgid "Show status of Services and network" +msgstr " STATS Mutatja a Szervít és hálózat állapotát" + +#: modules/commands/os_logsearch.cpp:152 +#, c-format +msgid "Showed %d/%d matches for %s." +msgstr "" + +#: modules/commands/cs_set.cpp:872 +#, fuzzy +msgid "Sign kicks that are done with the KICK command" +msgstr " SIGNKICK Sign kickek, melyek a KICK paranccsal történnek" + +#: modules/commands/cs_set.cpp:921 +#, fuzzy, c-format +msgid "Signed kick option for %s is now off." +msgstr "Signed kick option for %s is now ON." + +#: modules/commands/cs_set.cpp:913 +#, fuzzy, c-format +msgid "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." +msgstr "" +"Signed kick option for %s is now ON, but depends of the\n" +"level of the user that is using the command." + +#: modules/commands/cs_set.cpp:906 +#, fuzzy, c-format +msgid "Signed kick option for %s is now on." +msgstr "Signed kick option for %s is now ON." + +#: modules/commands/cs_set.cpp:1299 +msgid "Signed kicks" +msgstr "Signed kicks" + +#: modules/commands/ms_rsend.cpp:60 modules/commands/ms_send.cpp:59 +#, fuzzy, c-format +msgid "Sorry, %s currently has too many memos and cannot receive more." +msgstr "%s túl sok üzenettel rendelkezik, és nem fogadhat többet." + +#: modules/commands/cs_seen.cpp:294 +#, c-format +msgid "Sorry, I have not seen %s." +msgstr "" + +#: modules/commands/bs_badwords.cpp:404 +#, fuzzy +msgid "Sorry, bad words list modification is temporarily disabled." +msgstr "Csatornán tiltott szaval listájának változtatása letiltva." + +#: modules/commands/bs_assign.cpp:30 modules/commands/bs_assign.cpp:98 +#, fuzzy +msgid "Sorry, bot assignment is temporarily disabled." +msgstr "Bot beállítás időlegesen szünetel." + +#: modules/commands/bs_bot.cpp:281 modules/commands/bs_assign.cpp:164 +msgid "Sorry, bot modification is temporarily disabled." +msgstr "A bot módosítás ideiglenesen szünetel." + +#: modules/fantasy.cpp:42 modules/commands/bs_kick.cpp:813 +#: modules/commands/bs_kick.cpp:878 +msgid "Sorry, bot option setting is temporarily disabled." +msgstr "Bot beállítás időlegesen szünetel." + +#: modules/commands/bs_set.cpp:115 +#, fuzzy +msgid "Sorry, changing bot options is temporarily disabled." +msgstr "Bot beállítás időlegesen szünetel." + +#: modules/commands/cs_xop.cpp:112 modules/commands/cs_xop.cpp:235 +#: modules/commands/cs_xop.cpp:444 +#, fuzzy, c-format +msgid "Sorry, channel %s list modification is temporarily disabled." +msgstr "Csatorna AOP lista módosítás szünetel." + +#: modules/commands/cs_access.cpp:547 modules/commands/cs_flags.cpp:405 +msgid "Sorry, channel access list modification is temporarily disabled." +msgstr "A csatorna hozzáférési listájának módosítása szünetel." + +#: modules/commands/cs_akick.cpp:469 +msgid "Sorry, channel autokick list modification is temporarily disabled." +msgstr "Csatorna autokick listájának módosítása szünetel." + +#: modules/commands/cs_drop.cpp:29 +msgid "Sorry, channel de-registration is temporarily disabled." +msgstr "A csatornák regisztrációjának törlése jelenleg szünetel." + +#: modules/commands/cs_register.cpp:35 +msgid "Sorry, channel registration is temporarily disabled." +msgstr "Sajnálom, a csatorna regisztráció jelenleg szünetel." + +#: modules/commands/bs_kick.cpp:181 +msgid "Sorry, kicker configuration is temporarily disabled." +msgstr "Kirúgás használata ideiglenesen letiltva." + +#: modules/commands/ms_set.cpp:216 +msgid "Sorry, memo option setting is temporarily disabled." +msgstr "Üzenet opcióinak beállítása szünetel." + +#: include/language.h:116 +#, fuzzy +msgid "Sorry, memo sending is temporarily disabled." +msgstr "Üzenet opcióinak beállítása szünetel." + +#: modules/commands/ns_drop.cpp:29 +msgid "Sorry, nickname de-registration is temporarily disabled." +msgstr "Sajnálom, a nicknevek regisztrációjának törlése szünetel." + +#: modules/commands/ns_group.cpp:120 +msgid "Sorry, nickname grouping is temporarily disabled." +msgstr "Sajnálom, a csoportok használata ideiglenesen le van tiltva." + +#: modules/commands/ns_register.cpp:139 +msgid "Sorry, nickname registration is temporarily disabled." +msgstr "Sajnálom, a nickregisztráció jelenleg nem működik." + +#: modules/commands/ns_access.cpp:33 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d access entries has been reached." +msgstr "Neked csak %d helyed van a csatorna listáján." + +#: modules/commands/ns_ajoin.cpp:141 +#, c-format +msgid "Sorry, the maximum of %d auto join entries has been reached." +msgstr "" + +#: modules/commands/ns_cert.cpp:173 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d certificate entries has been reached." +msgstr "Neked csak %d bejegyzésed lehet a hozzáférési listán." + +#: modules/commands/ms_ignore.cpp:55 +#, fuzzy, c-format +msgid "Sorry, the memo ignore list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/cs_access.cpp:204 modules/commands/cs_flags.cpp:174 +#: modules/commands/cs_xop.cpp:201 +#, fuzzy, c-format +msgid "" +"Sorry, you can only have %d access entries on a channel, including access " +"entries from other channels." +msgstr "Neked csak %d helyed van a csatorna listáján." + +#: modules/commands/cs_akick.cpp:177 +#, c-format +msgid "Sorry, you can only have %d autokick masks on a channel." +msgstr "%d bejegyzésnél nem lehet több a listán." + +#: modules/commands/bs_badwords.cpp:286 +#, c-format +msgid "Sorry, you can only have %d bad words entries on a channel." +msgstr "Csak %d tiltott szó lehet a csatornán." + +#: include/language.h:103 +#, fuzzy, c-format +msgid "Sorry, you have already exceeded your limit of %d channels." +msgstr "Csak %d tiltott szó lehet a csatornán." + +#: include/language.h:102 +#, fuzzy, c-format +msgid "Sorry, you have already reached your limit of %d channels." +msgstr "Csak %d tiltott szó lehet a csatornán." + +#: modules/commands/os_dns.cpp:218 +msgid "State" +msgstr "" + +#: modules/commands/cs_seen.cpp:117 +msgid "Statistics and maintenance for seen data" +msgstr "" + +#: modules/commands/os_stats.cpp:131 +msgid "Statistics reset." +msgstr "Statisztika nullázva." + +#: modules/commands/ns_update.cpp:36 +msgid "Status updated (memos, vhost, chmodes, flags)." +msgstr "Státusz frissítve (memok, vhost, chmodok, flagek)." + +#: modules/commands/bs_kick.cpp:1432 +msgid "Stop flooding!" +msgstr "Ne floodolj!" + +#: modules/commands/bs_kick.cpp:1448 +msgid "Stop repeating yourself!" +msgstr "Ne ismételd magad!" + +#: modules/commands/cs_set.cpp:746 +#, fuzzy +msgid "Stricter control of channel founder status" +msgstr " SECUREFOUNDER Csatornán a founder státusz szigorú kezelése" + +#: modules/commands/cs_set.cpp:810 +#, fuzzy +msgid "Stricter control of chanop status" +msgstr " SECUREOPS A csatornán az op státusz szigorú kezelése" + +#: modules/commands/ns_alist.cpp:75 modules/commands/cs_info.cpp:50 +msgid "Successor" +msgstr "" + +#: modules/commands/cs_set.cpp:1006 +#, fuzzy, c-format +msgid "Successor for %s changed to %s." +msgstr "A megadott csatorna (%s) új successora: %s." + +#: modules/commands/cs_set.cpp:1008 +#, c-format +msgid "Successor for %s unset." +msgstr "A megadott csatorna %s successora törölve." + +#: modules/commands/os_set.cpp:81 +#, fuzzy +msgid "" +"Super admin can not be set because it is not enabled in the configuration." +msgstr "SuperAdmin setting not enabled in services.conf" + +#: modules/commands/ns_suspend.cpp:60 +#, fuzzy +msgid "Suspend a given nick" +msgstr " SUSPEND Suspend a given nick" + +#: modules/commands/cs_suspend.cpp:236 modules/commands/ns_suspend.cpp:250 +#, fuzzy +msgid "Suspend reason" +msgstr "JUPE szervernév [leírás]" + +#: modules/commands/cs_suspend.cpp:232 modules/commands/ns_suspend.cpp:246 +msgid "Suspended" +msgstr "" + +#: modules/commands/cs_suspend.cpp:234 modules/commands/ns_suspend.cpp:248 +msgid "Suspended by" +msgstr "" + +#: modules/commands/cs_suspend.cpp:238 modules/commands/ns_suspend.cpp:252 +#, fuzzy +msgid "Suspended on" +msgstr " SUSPEND Suspend a given nick" + +#: modules/commands/ns_suspend.cpp:147 +#, fuzzy +msgid "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." +msgstr "" +"Syntax: SUSPEND #szoba [indok]\n" +"Elutasít minden szobahasználatot. Lehet törölni a\n" +"UNSUSPEND paranccsal és akkor használható az öüsszes \n" +"megörzött szoba adat/beállítás.\n" +"\n" +"Indoklást kér némelyik hálózat.\n" +"\n" +"Korlátozva Szervíz adminnak." + +#: modules/commands/cs_suspend.cpp:240 modules/commands/ns_suspend.cpp:254 +#, fuzzy +msgid "Suspension expires" +msgstr " %s (does not expire)" + +#: modules/commands/cs_sync.cpp:19 +#, fuzzy +msgid "Sync users channel modes" +msgstr "%s váltóztatott a módodon." + +#: modules/commands/cs_sync.cpp:49 +msgid "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." +msgstr "" + +#: modules/commands/hs_group.cpp:42 +#, fuzzy +msgid "Syncs the vhost for all nicks in a group" +msgstr " GROUP A vhostot a csoport minden tagjára állítja" + +#: src/command.cpp:146 +msgid "Syntax" +msgstr "" + +#: modules/commands/ns_group.cpp:373 +#, fuzzy, c-format +msgid "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." +msgstr "" +"Syntax: GLIST\n" +"\n" +"Listáz minden nicket a csoportodból." + +#: modules/commands/ns_group.cpp:363 +#, fuzzy, c-format +msgid "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." +msgstr "" +"Syntax: GLIST [nicknév]\n" +"\n" +"Paraméter nélkül, listázza az összes nicknevet \n" +"a csoportodban.\n" +"Paraméterrel listázza az összes nicknevet, abból a \n" +"csoportból ahol az adott nicknév van.\t\n" +"\n" +"Ennek a használata korlátozva Szervíz adminra." + +#: modules/commands/os_set.cpp:227 +#, fuzzy +msgid "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." +msgstr "" +"Syntax: SET NOEXPIRE {ON | OFF}\n" +"\n" +"Bekapcsolja a nem elévülést. A nem elévülő módban nickek,\n" +"csatornák, akillek és kivételek rakhatóak nem elévülőre is\n" +"amíg ezt az opciót nem kapcsolod ki.\n" +"\n" +"Ez az opció megegyezik a parancs-sorban kiadható opcióval:\n" +"-noexpire." + +#: modules/commands/ms_set.cpp:287 +#, fuzzy, c-format +msgid "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." +msgstr "" +"Syntax: SET LIMIT [#szoba] limit\n" +"\n" +"Beállítja, hogy max. hány üzenetet fogadhatsz a nickedre\n" +"(vagy a csatornára). Ha 0-ra állítod, senki nem\n" +"küldhet üzenetet a nickedre/csatornára. Mindamellett,\n" +"nem állíthatod ezt a számot többre, mint %d." + +#: modules/commands/ms_set.cpp:267 +#, fuzzy, c-format +msgid "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." +msgstr "" +"Syntax: SET LIMIT [user | #szoba]{korlát|NONE}[HARD]\n" +"\n" +"Beállítja egy felhasználó vagy szoba max.fogadható\n" +"memo üzenetienek számát, ha a limitet 0-ra állitod \n" +"akkor a felhasználó nem fogadhat üzeneteket.Ha a \n" +"NONE-vel állítod be akkor annyit fogadhat és tarthat\n" +"meg amennyit akar.Ha nem adsz meg nicknevet, vagy csatornát\n" +"akkor a saját korlátaidat állitja.\n" +"\n" +"HARD-al hozzáadva nem állíthatja a felhasználó a korlát \n" +"értékét Ha nem adod hozzá a HARD-ot akkor a felhasználó \n" +"kedve szerint váltóztathatja a korlát értékét (akkor is ha\n" +"az előző értéket a HARD-al adtad meg)\n" +"\n" +"SET LIMIT parancs használata korlátozható Szervíz\n" +"adminokra. Egyéb felhasználók csak saját maguknak és a \n" +"csatornáknak ahol megfelelő hozzáférésük van állíthatnak\n" +"korlátot de nem törölhetik, és nem állíthatnak %d érték \n" +"felett valamint HARD korlátot." + +#: modules/commands/os_set.cpp:208 +#, fuzzy, c-format +msgid "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." +msgstr "" +"Syntax: SET LIST\n" +"Display the various %s settings" + +#: modules/commands/os_set.cpp:234 +#, fuzzy +msgid "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." +msgstr "" +"Syntax: SET NOEXPIRE {ON | OFF}\n" +"\n" +"Bekapcsolja a nem elévülést. A nem elévülő módban nickek,\n" +"csatornák, akillek és kivételek rakhatóak nem elévülőre is\n" +"amíg ezt az opciót nem kapcsolod ki.\n" +"\n" +"Ez az opció megegyezik a parancs-sorban kiadható opcióval:\n" +"-noexpire." + +#: modules/commands/ms_set.cpp:246 +#, fuzzy +msgid "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." +msgstr "" +"Syntax: SET NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +"\n" +"Itt tudod beállítani, ha értesítést szeretnél kapni\n" +"az új üzenetekről:\n" +"\n" +" ON Értesítést kapsz az új üzenetről csatlakozáskor,\n" +" amikor visszajössz /AWAY-ból, vagy ha küldenek neked.\n" +" LOGON Értesítést kapsz az új üzenetekről csatlakozáskor\n" +" vagy ha visszajössz /AWAY-ból.\n" +" NEW Csak akkor kapsz értesítést, ha új üzenet érkezett.\n" +" MAIL You will be notified of memos by email aswell as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF Nem kapsz értesítést az üzeneteidről.\n" +"\n" +"Az ON ekvivalens a LOGON és a NEW kombinálásával." + +#: modules/commands/os_set.cpp:212 +#, fuzzy +msgid "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." +msgstr "" +"Syntax: SET READONLY {ON | OFF}\n" +"\n" +"Csak-olvasás mód aktiválása/kikapcsolása. A csak-olvasás\n" +"mód, a normal felhasználó részére nem engedi, hogy bármit\n" +"módosítson a szervízben, beleértve a nicknév, a\n" +"hozzáférés listát, stb. IRCoperátorok a megfelelő flaggel\n" +"módosítani tudja a szervíz akill listát és a droppolhat\n" +"vagy forbidolhat nickneveket és szobákat, de ez nem fog\n" +"kerül mentésre, amíg a csak olvasni módot kikapcsolja\n" +"és restartolja a szervízt.\n" +"\n" +"Ez a parancs egyenértéku a parancs-sorban kiadott\n" +"-readonly opcióval.\t" + +#: modules/commands/os_set.cpp:243 +#, fuzzy +msgid "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." +msgstr "" +"Syntax: SET SUPERADMIN {ON | OFF}\n" +"\n" +"Ez a beállítás extra jogokat biztosít számodra, például\n" +"az \"összes szoba founderje\" stb...\n" +"\n" +"Ez az opció nem ajánlott, csak akkor használd, ha \n" +"szükséges és kapcsold ki, ha már nem." + +#: modules/commands/ns_identify.cpp:107 +#, fuzzy, c-format +msgid "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." +msgstr "" +"Syntax: IDENTIFY [account] jelszó\n" +"\n" +"Tudatja a %s-vel, hogy te vagy a tulajdonosa ennek a \n" +"nicknek. Jelszónak ugyanannak kell lennie amit a \n" +"regisztrációnál megadtál, vagy amire módosítottad." + +#: modules/commands/cs_invite.cpp:91 +#, fuzzy, c-format +msgid "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Syntax: INVITE #szoba\n" +"\t\n" +"Utasítja a %s-et, hogy hívjon meg a megadott csatornára.\n" +"\n" +"Alapbeállítás szerint, min. AOP vagy 5-ös access szinttel\n" +"kell rendelkezned a csatornán, hogy használhasd." + +#: modules/commands/cs_unban.cpp:103 +#, fuzzy, c-format +msgid "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Syntax: UNBAN #szoba [nick]\n" +"\n" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel.\n" +"\n" +"Alapbeállítás szerint, min. AOP vagy 5-ös access szinttel\n" +"kell rendelkezned, hogy használhasd.\t" + +#: modules/commands/os_jupe.cpp:56 +#, fuzzy +msgid "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." +msgstr "" +"Syntax: JUPE server [leirás]\n" +"\n" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server.\n" +"\n" +"Korlátozva Szervíz adminoknak." + +#: modules/commands/cs_seen.cpp:261 +msgid "Tells you about the last time a user was seen" +msgstr "" + +#: modules/commands/os_shutdown.cpp:19 +#, fuzzy +msgid "Terminate Services WITHOUT saving" +msgstr " SHUTDOWN Leállítja a szervíz programot mentéssel" + +#: modules/commands/os_shutdown.cpp:73 +#, fuzzy +msgid "Terminate services with save" +msgstr " SHUTDOWN Leállítja a szervíz programot mentéssel" + +#: modules/commands/os_news.cpp:156 +msgid "Text" +msgstr "" + +#: modules/commands/cs_access.cpp:576 +msgid "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." +msgstr "" + +#: modules/commands/cs_access.cpp:587 +msgid "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." +msgstr "" + +#: modules/commands/cs_access.cpp:593 +msgid "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." +msgstr "" + +#: modules/commands/cs_flags.cpp:447 +msgid "" +"The CLEAR command clears the channel access list. This requires channel " +"founder access." +msgstr "" + +#: modules/commands/cs_seen.cpp:173 +#, c-format +msgid "" +"The CLEAR command lets you clean the database by removing all entries from " +"the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." +msgstr "" + +#: modules/commands/bs_badwords.cpp:438 +#, fuzzy +msgid "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." +msgstr "" +"Syntax: HOP #szoba ADD nick\n" +" HOP #szoba DEL { nick | sorszám | lista}\n" +" HOP #szoba LIST [ maszk | lista ]\n" +" HOP #szoba CLEAR\n" +"\n" +"Karbantartja az HOP (HALFOP) listát a csatornán. A HOP\n" +"listán szereplő userek automatikusan megkapják belépéskor\n" +"a féloperátor státuszt.\n" +"\n" +"HOP ADD paranccsal hozzáadhatsz egy nickenevet csatornád\n" +"HOP listájához.\n" +"\n" +"HOP DEL paranccsal eltávolíthatsz egy megadott nicknevet\n" +"a csatornád HOP listájáról. Ha sorszámokat intervallumban\n" +"adunk meg (lásd a listázásnál),akkor a megadott bejegyzések\n" +"kerülnek törlésre.\n" +"\n" +"Az HOP LIST parancs megadja az HOP listát. Ha nem vagy \n" +"kiváncsi a teljes listára akkor a listában szereplő HOP \n" +"sorszámát megadva is megtudhatjuk a nevét, megadhatunk \n" +"intervallumot is.\n" +"\n" +"Példák:\n" +"\n" +"\tHOP #szoba LIST 2-5,7-9\n" +"\tListázza az HOP-okat 2 és 5 között és\n" +"\t7-tol 9-ig.\n" +" \n" +"Az HOP CLEAR parancs kiüriti a szoba HOP listáját.\n" +"\n" +"Az HOP ADD és HOP DEL parancsokat csak AOP / magasabb\n" +"szinttel rendelkező userek használhatják,de az HOP CLEAR\n" +"parancsot csak a szoba foundere adhatja ki.\n" +"Habár, minden HOP listán szereplo user használhatja az\n" +"HOP LIST parancsot.\n" +"\n" +"Ezt a parancsot letilthatod a csatornádon, és helyette \n" +"használhatod az access lista rendszert. Nézd meg: /msg \n" +"%s HELP ACCESS bővebb információért az access listáról,\n" +"és írd be: /msg %s HELP SET XOP hogy megnézd, hogyan \n" +"tudsz váltani az xOP rendszerről access lista rendszerre." + +#: modules/commands/cs_entrymsg.cpp:241 +msgid "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:253 +msgid "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:245 +msgid "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:250 +msgid "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." +msgstr "" + +#: modules/commands/ns_set.cpp:713 +msgid "The IMMED option is not available on this network." +msgstr "Az IMMED opció nem elérhető ezen a hálózaton." + +#: modules/commands/cs_access.cpp:821 +#, fuzzy, c-format +msgid "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." +msgstr "" +"Syntax:\tLEVELS #szoba SET típus [szint|FOUNDER]\n" +"\t\tLEVELS #szoba {DIS | DISABLE} típus\n" +"\t\tLEVELS #szoba LIST\n" +"\t\tLEVELS #szoba RESET\n" +"\n" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +"\n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it).\n" +"\n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel (see\n" +"HELP ACCESS LEVELS).\n" +"\n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." + +#: modules/commands/cs_flags.cpp:442 +msgid "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." +msgstr "" + +#: modules/commands/cs_flags.cpp:435 +msgid "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access " +"list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. " +"You are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of " +"what your access is." +msgstr "" + +#: modules/commands/cs_seen.cpp:172 +msgid "" +"The STATS command prints out statistics about stored nicks and memory usage." +msgstr "" + +#: modules/commands/ns_register.cpp:291 +#, fuzzy +msgid "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." +msgstr "" +"Írd be: /msg %s SET EMAIL e-mail \n" +"Az email címed nem lesz kiadva harmadik személynek." + +#: modules/commands/cs_log.cpp:258 +#, c-format +msgid "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." +msgstr "" + +#: modules/commands/cs_ban.cpp:64 +#, fuzzy, c-format +msgid "The %s list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/os_sxline.cpp:220 +#, fuzzy, c-format +msgid "The %s list has been cleared." +msgstr "Az AKILL lista törölve." + +#: modules/commands/os_akill.cpp:377 +msgid "The AKILL list has been cleared." +msgstr "Az AKILL lista törölve." + +#: modules/commands/os_defcon.cpp:136 modules/commands/os_defcon.cpp:225 +#, fuzzy, c-format +msgid "The Defcon level is now at: %d" +msgstr "A Defcon szint most: %d" + +#: modules/commands/ns_info.cpp:171 +#, c-format +msgid "The E-mail address of %s will now be hidden from %s INFO displays." +msgstr "The E-mail address of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:172 +#, c-format +msgid "The E-mail address of %s will now be shown in %s INFO displays." +msgstr "The E-mail address of %s will now be shown in %s INFO displays." + +#: modules/commands/cs_flags.cpp:449 +msgid "The available flags are:" +msgstr "" + +#: modules/commands/os_defcon.cpp:240 +#, fuzzy +msgid "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." +msgstr "" +"Syntax: DEFCON [1|2|3|4|5]\n" +"A defcon rendszer képes használni előre beállított\n" +"korlátozást a szervíz használatban egy támadás alkalmával\n" +"a hálózaton." + +#: modules/ns_maxemail.cpp:51 +#, c-format +msgid "The email address %s has reached its usage limit of %d users." +msgstr "" + +#: modules/ns_maxemail.cpp:49 +#, c-format +msgid "The email address %s has reached its usage limit of 1 user." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:142 +#, fuzzy, c-format +msgid "The entry message list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/cs_access.cpp:796 +msgid "The following feature/function names are available:" +msgstr "" + +#: modules/commands/cs_access.cpp:584 +msgid "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." +msgstr "" + +#: modules/commands/os_session.cpp:240 +#, fuzzy, c-format +msgid "" +"The host %s currently has %d sessions with a limit of %d because it matches " +"entry: %s." +msgstr "A %s hoszt aktuálisan %d sessiont használ, a határértéke %d." + +#: modules/commands/ms_check.cpp:54 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has been read." +msgstr "Az utolsó memo, amit %s részére (%s időpontban) küldtél már olvasott." + +#: modules/commands/ms_check.cpp:52 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has not yet been read." +msgstr "" +"Az utolsó memo, amit %s részére (%s időpontban) küldtél még olvasatlan." + +#: modules/commands/ns_info.cpp:189 +#, c-format +msgid "The last quit message of %s will now be hidden from %s INFO displays." +msgstr "The last quit message of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:190 +#, c-format +msgid "The last quit message of %s will now be shown in %s INFO displays." +msgstr "The last quit message of %s will now be shown in %s INFO displays." + +#: modules/commands/ns_info.cpp:177 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." +msgstr "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:178 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." +msgstr "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." + +#: modules/commands/cs_enforce.cpp:190 +#, fuzzy, c-format +msgid "The limit on %s is not valid." +msgstr "Nem változtathatod meg %s üzeneteinek számát." + +#: modules/commands/os_forbid.cpp:193 +msgid "The mask must contain at least one non wildcard character." +msgstr "" + +#: modules/commands/ms_set.cpp:153 +#, c-format +msgid "The memo limit for %s may not be changed." +msgstr "Nem változtathatod meg %s üzeneteinek számát." + +#: modules/commands/cs_mode.cpp:347 +#, fuzzy, c-format +msgid "The mode lock list of %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/ns_set.cpp:355 +#, c-format +msgid "The new display MUST be a nickname of the nickname group %s." +msgstr "" + +#: include/language.h:98 +#, fuzzy, c-format +msgid "The new display is now %s." +msgstr "A Defcon szint most: %d" + +#: modules/commands/os_svs.cpp:57 +#, c-format +msgid "The nick %s is now being changed to %s." +msgstr "A nicked %s meg lett változtatva erre: %s." + +#: modules/commands/bs_bot.cpp:149 +msgid "The old information is the same as the new information specified." +msgstr "" + +#: modules/commands/os_info.cpp:157 +#, fuzzy, c-format +msgid "The oper info already exists on %s." +msgstr "%s nevű bot már létezik." + +#: modules/commands/os_info.cpp:147 +#, fuzzy, c-format +msgid "The oper info list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/ns_info.cpp:183 +#, c-format +msgid "" +"The services access status of %s will now be hidden from %s INFO displays." +msgstr "" +"The services access status of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:184 +#, c-format +msgid "The services access status of %s will now be shown in %s INFO displays." +msgstr "" +"The services access status of %s will now be shown in %s INFO displays." + +#: modules/commands/os_session.cpp:433 +#, fuzzy +msgid "The session exception list is empty." +msgstr " EXCEPTION Módosítja a session-korlát/kivétel listát" + +#: modules/commands/ns_recover.cpp:121 +msgid "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:195 +#, c-format +msgid "There are %d memos on channel %s." +msgstr "Összesen %d üzenet van a %s csatornán." + +#: modules/commands/bs_botlist.cpp:47 +msgid "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" +msgstr "" +"Nem áll rendelkezésre bot.\n" +"Kérj meg egy szervíz admint, hogy csináljon!" + +#: modules/commands/os_dns.cpp:213 +msgid "There are no configured servers." +msgstr "" + +#: modules/commands/os_forbid.cpp:392 +#, fuzzy, c-format +msgid "There are no forbids of type %s." +msgstr "Összesen %d üzenet van a %s csatornán." + +#: modules/commands/ns_group.cpp:162 +#, fuzzy +msgid "There are too many nicks in your group." +msgstr " DELALL Törli a vhosztot a nickekröl a csoportban" + +#: modules/commands/cs_log.cpp:123 +#, fuzzy, c-format +msgid "There currently are no logging configurations for %s." +msgstr " RELOAD Újratölti a szervíz Konfigurációs fájlját" + +#: modules/pseudoclients/memoserv.cpp:193 +#, c-format +msgid "There is %d memo on channel %s." +msgstr "%d üzenete van a %s szobának." + +#: include/language.h:110 +#, fuzzy, c-format +msgid "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." +msgstr "Használd a /msg %s READ %d parancsot." + +#: modules/commands/bs_assign.cpp:132 +#, c-format +msgid "There is no bot assigned to %s anymore." +msgstr "Nincsen bot kijelölve %s szobában többet." + +#: modules/commands/os_news.cpp:33 +msgid "There is no logon news." +msgstr "Nincs fellépő üzenet." + +#: modules/commands/os_news.cpp:43 +msgid "There is no oper news." +msgstr "Nincs oper news." + +#: modules/commands/os_news.cpp:53 +msgid "There is no random news." +msgstr "Nincs véletlenszerű hír." + +#: modules/commands/os_config.cpp:41 +#, fuzzy, c-format +msgid "There is no such configuration block %s." +msgstr " RELOAD Újratölti a szervíz Konfigurációs fájlját" + +#: modules/commands/cs_mode.cpp:706 +#, fuzzy, c-format +msgid "There is no such mode %s." +msgstr "Nincs oper news." + +#: modules/commands/ms_set.cpp:52 +msgid "There's no email address set for your nick." +msgstr "Nincs beállítva email cím a nevedhez." + +#: modules/commands/os_forbid.cpp:304 modules/commands/os_forbid.cpp:496 +#, fuzzy, c-format +msgid "This channel has been forbidden: %s" +msgstr "Ez a szoba a %s adatbázisában regisztrált." + +#: modules/commands/cs_suspend.cpp:121 +#, fuzzy +msgid "This channel has been suspended." +msgstr "Ez a csatorna nem használható." + +#: modules/commands/cs_suspend.cpp:232 +#, fuzzy +msgid "This channel is suspended." +msgstr "Ez a csatorna nem használható." + +#: modules/commands/cs_suspend.cpp:268 +msgid "This channel may not be used." +msgstr "Ez a csatorna nem használható." + +#: modules/commands/os_dns.cpp:702 +msgid "" +"This command allows managing DNS zones used for controlling what servers " +"users\n" +"are directed to when connecting. Omitting all parameters prints out the " +"status of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to " +"this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, " +"the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given " +"zones." +msgstr "" + +#: modules/commands/hs_group.cpp:72 +#, fuzzy +msgid "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." +msgstr "" +"Syntax: GROUP\n" +"\n" +"Ez a parancs lehetővé teszi, hogy a JELENLEGI nick\n" +"vhostját beállítsuk a csoport minden nickjére." + +#: modules/commands/ns_register.cpp:299 +msgid "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." +msgstr "" + +#: modules/m_rewrite.cpp:145 +#, c-format +msgid "This command is an alias to the command %s." +msgstr "" + +#: modules/commands/ns_register.cpp:95 +#, fuzzy +msgid "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." +msgstr "" +"Syntax: CONFIRM passcodE\n" +"\n" +"This is the second step of nickname registration process.\n" +"You must perform this command in order to get your nickname\n" +"registered with %s. The passcode (or called auth code also)\n" +"is sent to your e-mail address in the first step of the\n" +"registration process. For more information about the first\n" +"stage of the registration process, type: /msg %s HELP REGISTER\n" +"\n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." + +#: modules/commands/os_modinfo.cpp:70 +#, fuzzy +msgid "This command lists information about the specified loaded module." +msgstr "" +"Syntax: MODINFO Fájlnév\n" +"\n" +"A parancs részletes információt ad a betöltött modulokról." + +#: modules/commands/hs_list.cpp:136 +#, fuzzy +msgid "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." +msgstr "" +"Syntax: LIST [|<#X-Y>]\n" +"\n" +"Ez parancs listázza a regisztrált vhostokat az operátornak\n" +"Ha egy kulcs meg van határozva, akkor csak a feltételnek\n" +"megfelelő vhostokat adja ki melyekben vagy a nickben vagy\n" +"a hosztban szerepel a kulcs. Pl: Rob*\n" +"Ha az #x-y stílust használod, csak a megadott sorozatba\n" +"tartozó X és Y közötti vhostok fognak megjelenni. Például\n" +"az #1-3 csak az első 3 vhostot jeleníti meg.\n" +"A lista használja NSListMax értéket, mint tág határértéket\n" +"amikor megjeleníti a tartalmat az operátornak.\n" +"Korlátozva Szervíz operátorokra." + +#: modules/commands/os_module.cpp:45 +#, fuzzy +msgid "" +"This command loads the module named modname from the modules\n" +"directory." +msgstr "" +"Syntax: MODLOAD Fájlnév\n" +"\n" +"Ez a parancs betölti azt modult, a modules könyvtárból,\n" +"amelyiknek a fájlnevét megadtad." + +#: modules/commands/ns_group.cpp:201 +#, fuzzy +msgid "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." +msgstr "" +"Syntax: GROUP célnicknév jelszó\n" +"\n" +"A parancs belépteti a nickneved a célnicknév csoportjába.\n" +"A jelszó a célnicknév jelszavának kell lennie.\n" +"\n" +"A csoportba való belépés lehetővé teszi, hogy megoszd a\n" +"konfigurációt, memo üzeneteket, szoba hozzáféréseket\n" +"a nicknevekkel a csoportban, és sok más lehetőséget nyújt!\n" +" \n" +"A csoport addig létezik, amig használatban van.\n" +"Ez azt jelenti, ha egy nicknevet dropolnak a csoportból,\n" +"nem fogod elveszteni a megosztott dolgokat, egészen addig,\n" +"amig legalább egy nick van a csoportban.\n" +"\n" +"Akkor is használhatod a parancsot, ha még nem regisztrált\n" +"a nicked. Ha a nicked regisztrált, akkor előbb azonosítani\n" +"kell a jelszavaddal, mielőtt ezt a parancsot használod.\n" +"Írd be:/msg %s HELP IDENTIFY bővebb információért.\n" +"\n" +"Ajánlott, hogy inkább nem regisztrált névvel használd\n" +"ezt a parancsot, mert ezzel automatikusan regisztrálódik.\n" +"Ha regisztált nickről használod (hogy megváltoztasd a\n" +"csoportod) csak akkor működik, ha a network adminok ezt\n" +"engedélyezik.\n" +"\n" +"Egyszerre egy csoportban lehetsz. \n" +"\n" +"Megjegyzés: minden nicknévnek a csoportban ugyanaz\n" +"\t\t a jelszava." + +#: modules/commands/ns_ajoin.cpp:292 +msgid "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." +msgstr "" + +#: modules/commands/ns_set.cpp:345 modules/commands/ns_set.cpp:669 +msgid "" +"This command may not be used on this network because nickname ownership is " +"disabled." +msgstr "" + +#: modules/commands/os_module.cpp:118 +#, fuzzy +msgid "This command reloads the module named modname." +msgstr "" +"Syntax: MODLOAD Fájlnév\n" +"\n" +"Ez a parancs betölti azt modult, a modules könyvtárból,\n" +"amelyiknek a fájlnevét megadtad." + +#: modules/commands/hs_request.cpp:344 +msgid "This command retrieves the vhost requests." +msgstr "" + +#: modules/commands/os_logsearch.cpp:159 +msgid "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." +msgstr "" + +#: modules/commands/cs_status.cpp:106 +msgid "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." +msgstr "" + +#: modules/commands/ns_group.cpp:285 +#, fuzzy +msgid "" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." +msgstr "" +"Syntax: UNGROUP [nick]\n" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, url, and icq. Everything\n" +"else is reset. You may not ungroup yourself if there is only one\n" +"nick in your group." + +#: modules/commands/os_module.cpp:168 +#, fuzzy +msgid "This command unloads the module named modname." +msgstr "" +"Syntax: MODLOAD Fájlnév\n" +"\n" +"Ez a parancs betölti azt modult, a modules könyvtárból,\n" +"amelyiknek a fájlnevét megadtad." + +#: modules/commands/ns_register.cpp:353 +msgid "This command will resend you the registration confirmation email." +msgstr "" + +#: include/language.h:90 +#, c-format +msgid "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" +msgstr "" + +#: modules/commands/os_forbid.cpp:469 +#, fuzzy, c-format +msgid "This nickname has been forbidden: %s" +msgstr "This nickname is currently suspended, reason: %s" + +#: modules/commands/ns_recover.cpp:99 +#, fuzzy, c-format +msgid "This nickname has been recovered by %s." +msgstr "This nickname is currently suspended, reason: %s" + +#: modules/commands/ns_recover.cpp:77 +#, c-format +msgid "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." +msgstr "" + +#: include/language.h:95 +#, fuzzy +msgid "This nickname has been registered; you may not use it." +msgstr "Ez a szoba a %s adatbázisában regisztrált." + +#: modules/commands/ns_suspend.cpp:246 +#, fuzzy +msgid "This nickname is suspended." +msgstr "Ez a csatorna nem használható." + +#: include/language.h:92 +#, c-format +msgid "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." +msgstr "" + +#: modules/commands/ms_read.cpp:95 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %d" +msgstr "Üzenet szám: %d; feladó.: %s (%s). Törléshez: /msg %s DEL %s %d" + +#: modules/commands/ms_read.cpp:93 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %s %d" +msgstr "Üzenet szám: %d; feladó.: %s (%s). Törléshez: /msg %s DEL %s %d" + +#: modules/commands/bs_kick.cpp:791 +msgid "To protect ops against bot kicks" +msgstr "" + +#: modules/commands/bs_kick.cpp:856 +msgid "To protect voices against bot kicks" +msgstr "" + +#: modules/commands/cs_list.cpp:46 +msgid "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." +msgstr "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." + +#: modules/commands/os_logsearch.cpp:139 +#, fuzzy, c-format +msgid "Too many results for %s." +msgstr "%s hozzáférési listája:" + +#: modules/extra/stats/cs_fantasy_top.cpp:149 +#, c-format +msgid "Top %i of %s" +msgstr "" + +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Topic" +msgstr "Témaváltás lezárása" + +#: modules/commands/cs_topic.cpp:258 +#, fuzzy +msgid "Topic lock" +msgstr "Témaváltás lezárása" + +#: modules/commands/cs_topic.cpp:114 +#, fuzzy, c-format +msgid "Topic lock option for %s is now off." +msgstr "Topic lock option for %s is now ON." + +#: modules/commands/cs_topic.cpp:97 +#, fuzzy, c-format +msgid "Topic lock option for %s is now on." +msgstr "Topic lock option for %s is now ON." + +#: modules/commands/cs_topic.cpp:256 +#, fuzzy +msgid "Topic retention" +msgstr "Témamegőrzés" + +#: modules/commands/cs_topic.cpp:60 +#, fuzzy, c-format +msgid "Topic retention option for %s is now off." +msgstr "Topic retention option for %s is now ON." + +#: modules/commands/cs_topic.cpp:54 +#, fuzzy, c-format +msgid "Topic retention option for %s is now on." +msgstr "Topic retention option for %s is now ON." + +#: modules/commands/cs_topic.cpp:265 +msgid "Topic set by" +msgstr "" + +#: modules/commands/bs_kick.cpp:1323 +msgid "Turn caps lock OFF!" +msgstr "Kapcsold ki a caps lockod!" + +#: modules/extra/stats/m_chanstats.cpp:17 +#: modules/extra/stats/m_chanstats.cpp:71 +#, fuzzy +msgid "Turn chanstats statistics on or off" +msgstr " SECURE A nickneved védelmének be-,kikapcsolása" + +#: modules/commands/ns_set.cpp:1009 +#, fuzzy +msgid "Turn nickname security on or off" +msgstr " SECURE A nickneved védelmének be-,kikapcsolása" + +#: modules/commands/ns_set.cpp:655 +#, fuzzy +msgid "Turn protection on or off" +msgstr " KILL A kill védelem be-,kikapcsolása" + +#: modules/commands/ns_list.cpp:264 +#, fuzzy, c-format +msgid "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Syntax: SASET nickname PRIVATE {ON | OFF}\n" +"\n" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" + +#: modules/commands/ns_list.cpp:236 +#, fuzzy, c-format +msgid "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Syntax: SET PRIVATE {ON | OFF}\n" +"\n" +"Be/kikapcsolja a %s a privát opciót a nicknevedhez.\n" +"A PRIVATE beállítással, beállíthatod azt, hogy\n" +"a nickneved ne szerepeljen a nicknév listában ami \n" +"lekérhető a %s LIST paranccsal.\n" +"(Máskülönben, bárki kaphat információt a nicknevedről\n" +"használva az INFO parancsot.)" + +#: modules/commands/ns_set.cpp:1059 modules/commands/ns_set.cpp:1088 +#, fuzzy, c-format +msgid "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." +msgstr "" +"Syntax: SET SECURE {ON | OFF}\n" +"\n" +"Be/kikapcsolja a %s a biztonsági beállításokat a nickhez.\n" +"A SECURE beállítással, be kell írnod a jelszavadat\n" +"mielőtt a nicknév tulajdonsaként leszel tekintve,\n" +"kivéve, ha a hosztod szerepel az access listán.\n" +"Habár, ha az access listán szerepel a hosztod, akkor\n" +"nem fog automatikusan nevet váltóztatni a %s, hacsak\n" +"nincs bekapcsolva a KILL opció." + +#: modules/extra/stats/m_chanstats.cpp:142 +#, fuzzy +msgid "Turns chanstats channel statistics ON or OFF for this user." +msgstr " SECURE A nickneved védelmének be-,kikapcsolása" + +#: modules/extra/stats/m_chanstats.cpp:61 +#: modules/extra/stats/m_chanstats.cpp:119 +#, fuzzy +msgid "Turns chanstats statistics ON or OFF." +msgstr " SECURE A nickneved védelmének be-,kikapcsolása" + +#: modules/commands/ns_set.cpp:772 +#, fuzzy, c-format +msgid "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Syntax: SASET nickname KILL {ON | QUICK | IMMED | OFF}\n" +"\n" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +"\n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." + +#: modules/commands/ns_set.cpp:738 +#, fuzzy, c-format +msgid "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Syntax: SET KILL {ON | QUICK | IMMED | OFF}\n" +"\n" +"Be/kikapcsolja az automatikus kill védelmet a nickedhez.\n" +"A kill védelem bekapcsolásakor, ha más user megpróbálja\n" +"használni a nicked, kap egy percet mialatt meg kell\n" +"változtatnia a nickjét, ha letelt az idő akkor a %s \n" +"megváltóztatja a nickjét pl: Vendég-000001-re.\n" +"\n" +"Ha a QUICK -et választod, a user csak 20 másodpercet kap\n" +"a nickváltásra eltérően az általános 60 másodperctől.\n" +"Ha az IMMED-et választod akkor azonnal megváltóztatja.\n" +"Figyelmeztetés nélkül,nem kap esélyt a nickváltásra;\n" +"kérlek ne használd ezt az opciót csak ha nagyon indokolt.\n" +"A network adminisztrátorok letilthatják ezt." + +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_forbid.cpp:358 +msgid "Type" +msgstr "" + +#: modules/commands/ns_set.cpp:62 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Írd be: /msg %s HELP SET opció bővebb információért az\n" +"adott opcióról." + +#: modules/commands/bs_kick.cpp:151 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." +msgstr "" +"Type /msg %s HELP SASET option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname. " + +#: modules/commands/ns_set.cpp:107 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." +msgstr "" +"Type /msg %s HELP SASET option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname. " + +#: modules/commands/bs_set.cpp:62 modules/commands/cs_set.cpp:63 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." +msgstr "" +"Írd be: /msg %s HELP SET opció bővebb információért az\n" +"adott opcióról." + +#: modules/pseudoclients/nickserv.cpp:361 +#, fuzzy, c-format +msgid "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." +msgstr "" +"Írd be: /msg %s SET EMAIL e-mail \n" +"Az email címed nem lesz kiadva harmadik személynek." + +#: modules/commands/os_module.cpp:128 +#, fuzzy +msgid "Un-Load a module" +msgstr " MODUNLOAD Kitölti a modult" + +#: modules/commands/os_sxline.cpp:337 modules/commands/os_sxline.cpp:552 +#: modules/commands/os_akill.cpp:136 +#, fuzzy, c-format +msgid "Unable to find regex engine %s." +msgstr "Nem sikerült eltávolítani a %s modult" + +#: modules/commands/os_module.cpp:36 modules/commands/os_module.cpp:108 +#, fuzzy, c-format +msgid "Unable to load module %s." +msgstr "Nem sikerült a betölteni a %s modult" + +#: modules/commands/os_module.cpp:73 modules/commands/os_module.cpp:90 +#: modules/commands/os_module.cpp:145 modules/commands/os_module.cpp:159 +#, fuzzy, c-format +msgid "Unable to remove module %s." +msgstr "Nem sikerült eltávolítani a %s modult" + +#: modules/commands/bs_assign.cpp:90 +#, fuzzy +msgid "Unassigns a bot from a channel" +msgstr "UNASSIGN Unassigns a bot from a channel" + +#: modules/commands/bs_assign.cpp:139 +#, fuzzy +msgid "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." +msgstr "" +"Syntax: UNASSIGN #szoba\n" +"\n" +"Eltávolítja a botot a csatornáról. Ha használod ezt a\n" +"parancsot, akkor a botod nem fog többet belépni a\n" +"szobába. A bot konfigurációi megmaradnak.\n" +"Azaz nem kell újra bekonfigurálnod, ha később vissza\n" +"akarod hozni a szobádba." + +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1193 +#: modules/commands/bs_kick.cpp:1196 +#, fuzzy +msgid "Underlines kicker" +msgstr "\tAláhúzásért kirúgás: %s" + +#: modules/commands/os_dns.cpp:595 +#, fuzzy +msgid "Unknown SET option." +msgstr "Unknown SASET option %s." + +#: modules/commands/os_stats.cpp:229 +#, fuzzy, c-format +msgid "Unknown STATS option: %s" +msgstr "Ismeretlen STATS opció: %s." + +#: src/command.cpp:222 src/command.cpp:233 +#, fuzzy, c-format +msgid "Unknown command %s." +msgstr "Ismeretlen beállítás %s." + +#: src/command.cpp:220 src/command.cpp:231 +#, fuzzy, c-format +msgid "Unknown command %s. \"%s%s HELP\" for help." +msgstr "Ismeretlen parancs %s. Írd be: \"%s%s HELP\"." + +#: modules/commands/cs_mode.cpp:317 modules/commands/cs_mode.cpp:409 +#, fuzzy, c-format +msgid "Unknown mode character %c ignored." +msgstr "Ismeretlen mód karakter: %c figyelmen kívül hagyva." + +#: modules/commands/os_logsearch.cpp:78 +#, fuzzy, c-format +msgid "Unknown parameter: %s" +msgstr "SET opció beállítás" + +#: modules/commands/os_dns.cpp:241 +msgid "Unpooled" +msgstr "" + +#: modules/commands/cs_drop.cpp:77 +#, fuzzy +msgid "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." +msgstr "" +"Syntax: DROP #szoba\n" +"\n" +"Törli a megnevezett szoba regisztrációját.\n" +"Csak a szoba founder használhatja." + +#: modules/commands/cs_drop.cpp:74 +#, fuzzy +msgid "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." +msgstr "" +"Syntax: DROP #szoba\n" +"\n" +"Törli a regisztrációt a csatornáról.Csak Services Operators\n" +"droppolhat csatornát,úgy hogy nem használja a szoba\n" +"jelszavát." + +#: modules/commands/ns_suspend.cpp:160 +#, fuzzy +msgid "Unsuspend a given nick" +msgstr " UNSUSPEND Unsuspend a given nick" + +#: modules/commands/ns_suspend.cpp:199 +msgid "Unsuspends a nickname which allows it to be used again." +msgstr "" + +#: modules/commands/cs_updown.cpp:126 +msgid "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." +msgstr "" + +#: modules/commands/cs_updown.cpp:48 +#, fuzzy +msgid "Updates a selected nicks status on a channel" +msgstr " BAN Bans a selected nick on a channel" + +#: modules/commands/ns_update.cpp:19 +#, fuzzy +msgid "Updates your current status, i.e. it checks for new memos" +msgstr "" +" UPDATE Updates your current status, i.e. it checks for new memos" + +#: modules/commands/ns_update.cpp:43 +#, fuzzy +msgid "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." +msgstr "" +"Syntax: UPDATE\n" +"Frissíti a jelenlegi státuszod, vagyis ellenőrzi, hogy \n" +"jött-e új memo üzenet, beállítja a szükséges szoba \n" +"módokat, (ModeonID)és frissíti a vhostod, az userflagjeid\n" +"(utolsó fellépés, stb.)" + +#: modules/commands/os_update.cpp:25 +msgid "Updating databases." +msgstr "Adatbázis mentve." + +#: modules/commands/os_stats.cpp:154 +#, c-format +msgid "Uplink capab: %s" +msgstr "Uplink capab: %s" + +#: modules/commands/os_stats.cpp:153 +#, c-format +msgid "Uplink server: %s" +msgstr "Uplink server: %s" + +#: modules/commands/help.cpp:127 +#, c-format +msgid "Use the %s ALL command to list all commands and their descriptions." +msgstr "" + +#: modules/commands/bs_info.cpp:59 +msgid "Used on" +msgstr "" + +#: data/chanserv.example.conf:821 +#, fuzzy +msgid "Used to manage channels" +msgstr "%s váltóztatott a módodon." + +#: data/chanserv.example.conf:809 +#, fuzzy +msgid "Used to manage the list of privileged users" +msgstr " ACCESS A szoba hozzáférési listájának beállítása" + +#: data/chanserv.example.conf:815 +msgid "Used to modify the channel status of you or other users" +msgstr "" + +#: modules/commands/cs_akick.cpp:575 +#, fuzzy +msgid "User has been banned from the channel" +msgstr "%s csatornán a tiltást levetetted magadról." + +#: modules/commands/os_dns.cpp:587 +#, fuzzy, c-format +msgid "User limit for %s removed." +msgstr "%s vhosztja törölve lett." + +#: modules/commands/os_dns.cpp:585 +#, fuzzy, c-format +msgid "User limit for %s set to %d." +msgstr "%s maximálisan fogadható üzeneteinek száma: %d." + +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Users" +msgstr "Botok listája:" + +#: modules/commands/os_stats.cpp:172 +#, c-format +msgid "Users (nick): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:177 +#, c-format +msgid "Users (uid): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_list.cpp:184 +#, fuzzy +msgid "Users list:" +msgstr "Botok listája:" + +#: modules/commands/ns_info.cpp:105 modules/commands/ns_info.cpp:107 +msgid "VHost" +msgstr "" + +#: modules/commands/hs_set.cpp:92 +#, fuzzy, c-format +msgid "VHost for %s set to %s." +msgstr "%s vhostja erre változott: %s." + +#: modules/commands/hs_set.cpp:90 +#, fuzzy, c-format +msgid "VHost for %s set to %s@%s." +msgstr "%s vhostja erre változott: %s@%s." + +#: modules/commands/hs_set.cpp:199 +#, fuzzy, c-format +msgid "VHost for group %s set to %s." +msgstr "A %s csoport vhostja %s lett." + +#: modules/commands/hs_set.cpp:197 +#, fuzzy, c-format +msgid "VHost for group %s set to %s@%s." +msgstr "A %s csoport vhostja erre változott: %s@%s." + +#: modules/commands/os_session.cpp:247 +msgid "VIEW host" +msgstr "" + +#: modules/commands/os_sxline.cpp:428 modules/commands/os_sxline.cpp:662 +#: modules/commands/os_akill.cpp:389 +#, fuzzy +msgid "VIEW [mask | list | id]" +msgstr "LIST [#szoba] [list | NEW ]" + +#: modules/commands/os_session.cpp:526 +msgid "VIEW [mask | list]" +msgstr "" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +msgid "Value" +msgstr "" + +#: modules/commands/os_config.cpp:48 +#, fuzzy, c-format +msgid "Value of %s:%s changed to %s" +msgstr "A megadott csatorna (%s) új foundere: %s." + +#: modules/commands/hs_list.cpp:58 modules/commands/hs_request.cpp:305 +msgid "Vhost" +msgstr "" + +#: modules/commands/hs_del.cpp:38 +#, fuzzy, c-format +msgid "Vhost for %s removed." +msgstr "%s vhosztja törölve lett." + +#: modules/commands/os_oper.cpp:69 +#, fuzzy +msgid "View and change Services Operators" +msgstr "%s is a services operator of type %s." + +#: modules/commands/os_config.cpp:19 +msgid "View and change configuration file settings" +msgstr "" + +#: modules/commands/os_session.cpp:245 +#, fuzzy +msgid "View the list of host sessions" +msgstr " SESSION Olvassa a sessionok hoszt listáját" + +#: modules/commands/bs_kick.cpp:1221 +msgid "Voices protection" +msgstr "Voices védelme" + +#: modules/commands/bs_kick.cpp:1406 +msgid "Watch your language!" +msgstr "Figyelj a stílusra kiskomám!" + +#: modules/commands/cs_list.cpp:237 +#, c-format +msgid "" +"When private is set, the channel will not appear in\n" +"%s's %s command." +msgstr "" + +#: modules/commands/ms_info.cpp:204 +#, fuzzy +msgid "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." +msgstr "" +"Syntax: INFO [nick| #szoba]\n" +"\n" +"Paraméter nélkül kiirja az információt, hogy hány\n" +"üzeneted van, ebböl hány olvasatlan, és összesen\n" +"hány üzenetet fogadhatsz.\n" +"\n" +"A szoba paraméterrel, a csatornáról kapod meg \n" +"ezeket az információkat\t\n" +"A nicknév paraméterrel a megadott nicknévröl jeléeníti\n" +"meg ezeket az információkat.Enek használat korlátozva \n" +"Szervíz adminra." + +#: modules/commands/ns_logout.cpp:66 +#, fuzzy +msgid "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." +msgstr "" +"Syntax: LOGOUT [nicknév [REVALIDATE]]\n" +"\n" +"Kilépési paraméter, megfordítja az IDENTIFY parancs\n" +"hatását, azaz nem leszel beazonosítva a nickedre, mint a \n" +"valódi tulajdonosa a nickednek.\n" +"\n" +"A paraméter ugyanezt teszi a megadott nickkel.\n" +"Ha megadod a REVALIDATE opciót, akkor a nicktől\n" +"a szerviz újraazonosítást fog kérni. \n" +"\n" +"Használat korlátozva Szervíz adminoknak." + +#: modules/commands/os_stats.cpp:236 +#, fuzzy +msgid "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." +msgstr "" +"Syntax: STATS [AKILL | ALL | RESET]\n" +"\n" +"Ha választasz valamit, megmutatja az aktuális\n" +"felhasználók számát, a bejelentkezett IRCopokat (szervizek\n" +"nélkül), legmagasabb felhasználószámot a szervíz indulása\n" +"óta, és az időt amióta fut a szerver.\t\n" +"Az AKILL beállítással, kijelzi az aktuális maxot az\n" +"AKILL listán és az aktuális lejárati időt.\n" +"\n" +"Az ALL beállítást csak szervíz adminok használhatják és\n" +"kiírja a szervíz memória használatának információját. Ez a\n" +"beállítás lefagyaszthatja a szervízt egy rövid időre nagy\n" +"hálózat esetén, így nem lehet használni azt.\t\n" +"\n" +"A RESET beállítás nullázza az aktuális felhasználók max.\n" +"számát átírja a jelenlegi felhasználó számra\t" + +#: modules/commands/bs_badwords.cpp:194 +msgid "Word" +msgstr "" + +#: modules/commands/ns_group.cpp:158 +#, c-format +msgid "You are already a member of the group of %s." +msgstr "Már tagja vagy ennek a csoportnak: %s." + +#: modules/commands/os_login.cpp:34 modules/commands/ns_identify.cpp:87 +msgid "You are already identified." +msgstr "Már be vagy azonosítva. :-)" + +#: modules/commands/cs_invite.cpp:64 +#, fuzzy, c-format +msgid "You are already in %s!" +msgstr "You are already in %s! " + +#: modules/commands/os_set.cpp:91 +#, fuzzy +msgid "You are no longer a super admin." +msgstr "Te nem vagy már Szuper-Admin" + +#: modules/commands/os_login.cpp:81 +#, fuzzy +msgid "You are not identified." +msgstr "Már be vagy azonosítva. :-)" + +#: include/language.h:100 +#, fuzzy +msgid "You are not permitted to be on this channel." +msgstr "Nem változtathatod meg a max. fogadható üzenetek számát." + +#: modules/commands/ms_set.cpp:158 +msgid "You are not permitted to change your memo limit." +msgstr "Nem változtathatod meg a max. fogadható üzenetek számát." + +#: modules/commands/ns_cert.cpp:183 +#, fuzzy +msgid "You are not using a client certificate." +msgstr "Már be vagy azonosítva. :-)" + +#: modules/commands/os_set.cpp:85 +#, fuzzy +msgid "You are now a super admin." +msgstr "Most már Szuper-Admin vagy" + +#: modules/commands/os_oline.cpp:36 +msgid "You are now an IRC Operator." +msgstr "Most már IRC Operátor vagy!" + +#: modules/commands/ns_resetpass.cpp:108 +#, fuzzy +msgid "You are now identified for your nick. Change your password now." +msgstr "You are now identified for your nick. Change your password now." + +#: modules/commands/ns_group.cpp:64 +#, c-format +msgid "You are now in the group of %s." +msgstr "Mostantól tagja vagy a %scsoportnak." + +#: modules/pseudoclients/memoserv.cpp:147 +#, fuzzy, c-format +msgid "" +"You are over your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Figyelem: Fogadható üzenetek maximális számát (%d).\n" +"Nem fogadhatsz több üzenetet, amíg törölsz néhányat." + +#: modules/commands/os_noop.cpp:33 +msgid "You can not NOOP Services." +msgstr "" + +#: modules/commands/cs_access.cpp:672 +msgid "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." +msgstr "" + +#: modules/commands/os_jupe.cpp:34 +#, fuzzy +msgid "You can not jupe an already juped server." +msgstr "You can not jupe your services server or your uplink server." + +#: modules/commands/os_jupe.cpp:32 +#, fuzzy +msgid "You can not jupe your Services' pseudoserver or your uplink server." +msgstr "You can not jupe your services server or your uplink server." + +#: modules/commands/os_module.cpp:80 +#, c-format +msgid "You can not reload this module directly, instead reload %s." +msgstr "" + +#: modules/commands/ms_rsend.cpp:46 +msgid "You can not request a receipt when sending a memo to yourself." +msgstr "You can not request a receipt when sending a memo to yourself." + +#: modules/commands/ns_recover.cpp:163 +#, fuzzy, c-format +msgid "You can't %s yourself!" +msgstr "Nem ghostolhatod ki magad!" + +#: modules/commands/cs_access.cpp:154 modules/commands/cs_flags.cpp:109 +#: modules/commands/cs_xop.cpp:151 +#, fuzzy +msgid "You can't add a channel to its own access list." +msgstr "Nincs ilyen bejegyzés a (%s) csatorna hozzáférési listáján." + +#: modules/commands/ns_logout.cpp:37 +#, fuzzy, c-format +msgid "You can't logout %s, they are a Services Operator." +msgstr "%s nem tud kijelentkezni, mert ő egy Services Operator." + +#: modules/commands/ns_set.cpp:927 +#, fuzzy, c-format +msgid "You cannot %s on this network." +msgstr "Nem törölheted ezen a hálózaton az e-mail címed." + +#: modules/commands/cs_flags.cpp:231 +#, fuzzy, c-format +msgid "You cannot set the %c flag." +msgstr "You cannot use this command." + +#: modules/commands/ms_set.cpp:173 +#, c-format +msgid "You cannot set the memo limit for %s higher than %d." +msgstr "%s max. bejövő üzenetek száma nem lehet több, mint %d." + +#: modules/commands/ms_set.cpp:175 +#, c-format +msgid "You cannot set your memo limit higher than %d." +msgstr "A max. bejövő üzenetek száma nem lehet több, mint %d." + +#: modules/commands/bs_assign.cpp:124 +#, fuzzy +msgid "You cannot unassign bots while persist is set on the channel." +msgstr "You can not unassign bots while persist is set on the channel." + +#: modules/commands/ns_set.cpp:480 +msgid "You cannot unset the e-mail on this network." +msgstr "Nem törölheted ezen a hálózaton az e-mail címed." + +#: modules/commands/help.cpp:177 +msgid "You cannot use this command." +msgstr "You cannot use this command." + +#: modules/commands/ms_info.cpp:151 +#, c-format +msgid "You currently have %d memos, of which %d are unread." +msgstr "Van %d üzeneted, ebből %d olvasatlan." + +#: modules/commands/ms_info.cpp:149 +#, c-format +msgid "You currently have %d memos, of which 1 is unread." +msgstr "Van %d üzeneted, ebből 1 olvasatlan." + +#: modules/commands/ms_info.cpp:147 +#, c-format +msgid "You currently have %d memos." +msgstr "Van %d üzeneted." + +#: modules/commands/ms_info.cpp:145 +#, c-format +msgid "You currently have %d memos; all of them are unread." +msgstr "Van %d üzeneted; és mind olvasatlan." + +#: modules/commands/ms_info.cpp:134 +msgid "You currently have 1 memo, and it has not yet been read." +msgstr "Van 1 olvasatlan üzeneted." + +#: modules/commands/ms_info.cpp:136 +msgid "You currently have 1 memo." +msgstr "Van 1 üzeneted." + +#: modules/commands/ms_info.cpp:130 +msgid "You currently have no memos." +msgstr "Jelenleg nincs üzeneted." + +#: modules/commands/cs_mode.cpp:564 modules/commands/cs_mode.cpp:621 +#, c-format +msgid "You do not have access to set mode %c." +msgstr "" + +#: modules/commands/cs_mode.cpp:578 modules/commands/cs_mode.cpp:590 +#: modules/commands/cs_mode.cpp:631 +#, c-format +msgid "You do not have the access to change %s's modes." +msgstr "" + +#: modules/commands/cs_seen.cpp:198 +#, c-format +msgid "You found me, %s!" +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:143 +#, c-format +msgid "You have %d new memos." +msgstr "%d darab új üzeneted van." + +#: modules/pseudoclients/memoserv.cpp:143 +msgid "You have 1 new memo." +msgstr "Van egy új üzeneted." + +#: include/language.h:112 +#, fuzzy, c-format +msgid "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." +msgstr "Használd a /msg %s READ %d parancsot." + +#: modules/commands/cs_invite.cpp:76 +#, fuzzy, c-format +msgid "You have been invited to %s by %s." +msgstr "You have been invited to %s." + +#: modules/commands/cs_invite.cpp:81 +#, c-format +msgid "You have been invited to %s." +msgstr "You have been invited to %s." + +#: modules/protocol/ratbox.cpp:166 modules/commands/ns_recover.cpp:96 +#, fuzzy, c-format +msgid "You have been logged in as %s." +msgstr "A nicked sikeresen kijelentkezett." + +#: modules/commands/os_login.cpp:86 +#, fuzzy +msgid "You have been logged out." +msgstr "A nicked sikeresen kijelentkezett." + +#: modules/commands/cs_unban.cpp:94 +#, c-format +msgid "You have been unbanned from %s." +msgstr "%s csatornán a tiltást levetetted magadról." + +#: modules/commands/cs_unban.cpp:54 +#, fuzzy, c-format +msgid "You have been unbanned from %d channels." +msgstr "%s csatornán a tiltást levetetted magadról." + +#: modules/commands/ms_info.cpp:169 +msgid "You have no limit on the number of memos you may keep." +msgstr "Korlátlan számú üzenetet fogadhatsz." + +#: include/language.h:114 +#, fuzzy +msgid "You have no memos." +msgstr "%d darab új üzeneted van." + +#: include/language.h:117 +#, fuzzy +msgid "You have no new memos." +msgstr "%d darab új üzeneted van." + +#: modules/pseudoclients/memoserv.cpp:149 +#, fuzzy, c-format +msgid "" +"You have reached your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Figyelem: Fogadható üzenetek maximális száma (%d).\n" +"Nem fogadhatsz több üzenetet, amíg nem törölsz néhányat." + +#: modules/commands/ns_recover.cpp:117 +#, fuzzy, c-format +msgid "You have regained control of %s." +msgstr "You have been invited to %s." + +#: modules/commands/ns_drop.cpp:66 +#, fuzzy +msgid "You may drop any nick within your group." +msgstr " DELALL Törli a vhosztot a nickekröl a csoportban" + +#: modules/commands/cs_mode.cpp:322 modules/commands/cs_mode.cpp:414 +#, c-format +msgid "You may not (un)lock mode %c." +msgstr "" + +#: modules/commands/ns_set.cpp:485 +#, fuzzy +msgid "You may not change the e-mail of other Services Operators." +msgstr "Nem törölheted ezen a hálózaton az e-mail címed." + +#: modules/commands/ns_set.cpp:474 +#, fuzzy +msgid "You may not change the email of an unconfirmed account." +msgstr "Nem törölheted ezen a hálózaton az e-mail címed." + +#: modules/commands/ns_set.cpp:196 +#, fuzzy +msgid "You may not change the password of other Services Operators." +msgstr "%s nem tud kijelentkezni, mert ő egy Services Operator." + +#: modules/commands/ns_drop.cpp:45 +#, fuzzy +msgid "You may not drop other Services Operators' nicknames." +msgstr "%s is a services operator of type %s." + +#: modules/commands/ns_getpass.cpp:32 +#, fuzzy +msgid "You may not get the password of other Services Operators." +msgstr "%s nem tud kijelentkezni, mert ő egy Services Operator." + +#: modules/commands/ns_suspend.cpp:100 +#, fuzzy +msgid "You may not suspend other Services Operators' nicknames." +msgstr "%s nem tud kijelentkezni, mert ő egy Services Operator." + +#: modules/commands/ns_access.cpp:136 +#, fuzzy +msgid "" +"You may view but not modify the access list of other Services Operators." +msgstr "%s nem tud kijelentkezni, mert ő egy Services Operator." + +#: modules/commands/ns_cert.cpp:292 +#, fuzzy +msgid "" +"You may view but not modify the certificate list of other Services Operators." +msgstr "%s nem tud kijelentkezni, mert ő egy Services Operator." + +#: modules/commands/cs_seen.cpp:287 +#, c-format +msgid "You might see yourself in the mirror, %s." +msgstr "" + +#: include/language.h:120 +msgid "You must assign a bot to the channel before using this command." +msgstr "" + +#: modules/commands/cs_register.cpp:49 +msgid "You must be a channel operator to register the channel." +msgstr "A csatornán operátornak kell lenned, hogy regisztrálhasd." + +#: modules/commands/cs_updown.cpp:94 modules/commands/cs_updown.cpp:192 +#, fuzzy, c-format +msgid "You must be in %s to use this command." +msgstr "You need to be identified to use this command." + +#: modules/commands/cs_register.cpp:37 +#, fuzzy +msgid "You must confirm your account before you can register a channel." +msgstr "A csatornán operátornak kell lenned, hogy regisztrálhasd." + +#: modules/commands/hs_request.cpp:100 +#, fuzzy +msgid "You must confirm your account before you may request a vhost." +msgstr "A csatornán operátornak kell lenned, hogy regisztrálhasd." + +#: modules/commands/ms_send.cpp:44 +#, fuzzy +msgid "You must confirm your account before you may send a memo." +msgstr "A csatornán operátornak kell lenned, hogy regisztrálhasd." + +#: modules/commands/cs_drop.cpp:42 +#, c-format +msgid "" +"You must enter the channel name twice as a confirmation that you wish to drop" +" %s." +msgstr "" + +#: modules/commands/ns_register.cpp:153 +#, c-format +msgid "You must have been using this nick for at least %d seconds to register." +msgstr "" +"A nicked regisztrálásához %d másodpercnél régebben kell csatlakozva lenned." + +#: modules/commands/cs_mode.cpp:913 +#, fuzzy, c-format +msgid "You must have the %s(ME) privilege on the channel to use this command." +msgstr "You need to be identified to use this command." + +#: modules/pseudoclients/nickserv.cpp:358 +msgid "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." +msgstr "Be kell állítanod egy E-mail címet a nicknevedhez." + +#: modules/commands/help.cpp:172 +msgid "You need to be identified to use this command." +msgstr "You need to be identified to use this command." + +#: modules/commands/ms_info.cpp:182 +#, fuzzy +msgid "You will be notified by message and by mail when new memos arrive." +msgstr "Értesítést kapsz új üzenetek érkezésekor." + +#: modules/commands/ms_info.cpp:175 +#, fuzzy +msgid "" +"You will be notified of new memos at logon and when they arrive, and by mail " +"when they arrive." +msgstr "Értesítést kapsz új üzenetek érkezéséről csatlakozáskor." + +#: modules/commands/ms_info.cpp:177 +msgid "You will be notified of new memos at logon and when they arrive." +msgstr "Értesítést kapsz új üzenetek érkezéséről csatlakozáskor." + +#: modules/commands/ms_info.cpp:189 +#, fuzzy +msgid "" +"You will be notified of new memos at logon, and by mail when they arrive." +msgstr "Értesítést kapsz új üzenetek érkezéséről csatlakozáskor." + +#: modules/commands/ms_info.cpp:191 +msgid "You will be notified of new memos at logon." +msgstr "Értesítést kapsz az új üzeneteidről,ha fellépsz az IRC-re." + +#: modules/commands/ms_info.cpp:184 +msgid "You will be notified when new memos arrive." +msgstr "Értesítést kapsz új üzenetek érkezésekor." + +#: modules/commands/ms_set.cpp:190 +msgid "You will no longer be able to receive memos." +msgstr "Ezentúl nem tudsz üzeneteket fogadni." + +#: modules/commands/ms_set.cpp:57 +msgid "You will no longer be informed via email." +msgstr "Már nem kapsz értesítést emailben." + +#: modules/commands/ms_info.cpp:195 +msgid "You will not be notified of new memos." +msgstr "Nem kapsz értesítést az új üzeneteidről." + +#: modules/commands/ms_set.cpp:49 +msgid "You will now be informed about new memos via email." +msgstr "Az új memo üzeneteidről emailben kapsz értesítést." + +#: modules/commands/os_svs.cpp:86 +msgid "Your IRCd does not support SVSJOIN." +msgstr "" + +#: modules/commands/os_svs.cpp:31 +msgid "Your IRCd does not support SVSNICK." +msgstr "" + +#: modules/commands/os_svs.cpp:130 +msgid "Your IRCd does not support SVSPART." +msgstr "" + +#: include/language.h:127 +msgid "" +"Your IRCd does not support vIdent's, if this is incorrect, please report " +"this as a possible bug" +msgstr "" + +#: modules/extra/m_ldap_authentication.cpp:110 +#: modules/extra/m_sql_authentication.cpp:55 +#, fuzzy, c-format +msgid "Your account %s has been successfully created." +msgstr "A %s nevű bot törölve." + +#: modules/commands/ns_register.cpp:328 +#, fuzzy +msgid "Your account is already confirmed." +msgstr "Már be vagy azonosítva. :-)" + +#: modules/commands/ns_register.cpp:396 +#, fuzzy, c-format +msgid "Your account will expire, if not confirmed, in %s." +msgstr "Már be vagy azonosítva. :-)" + +#: modules/commands/ns_set.cpp:1274 +#, fuzzy, c-format +msgid "Your email address has been changed to %s." +msgstr "E-mail address for %s changed to %s." + +#: modules/commands/os_forbid.cpp:544 modules/commands/os_forbid.cpp:553 +#, fuzzy +msgid "Your email address is not allowed, choose a different one." +msgstr "Összes O:lines %s módosítva." + +#: modules/commands/ns_register.cpp:260 modules/commands/ns_register.cpp:391 +msgid "" +"Your email address is not confirmed. To confirm it, follow the instructions " +"that were emailed to you." +msgstr "" + +#: modules/commands/ns_register.cpp:67 +#, fuzzy, c-format +msgid "Your email address of %s has been confirmed." +msgstr "Összes O:lines %s módosítva." + +#: modules/extra/m_ldap_authentication.cpp:159 +#, fuzzy, c-format +msgid "Your email has been updated to %s" +msgstr "E-mail address for %s changed to %s." + +#: modules/extra/m_sql_authentication.cpp:62 +#, fuzzy, c-format +msgid "Your email has been updated to %s." +msgstr "E-mail address for %s changed to %s." + +#: modules/commands/ms_set.cpp:197 +msgid "Your memo limit has been disabled." +msgstr "Ezentúl korlátlan számú üzenetet fogadhatsz." + +#: modules/commands/ms_set.cpp:183 +#, c-format +msgid "Your memo limit has been set to %d." +msgstr "A max. bejövő üzenetek számanak új értéke: %d." + +#: modules/commands/ms_info.cpp:164 +#, c-format +msgid "Your memo limit is %d, and may not be changed." +msgstr "A max. bejövő üzentek száma: %d,ez fix érték." + +#: modules/commands/ms_info.cpp:166 +#, c-format +msgid "Your memo limit is %d." +msgstr "A maximálisan fogadható üzentek száma: %d." + +#: modules/commands/ms_info.cpp:159 +msgid "Your memo limit is 0; you will not receive any new memos." +msgstr "A max. bejövő üzentek száma: 0; és több nem jöhet." + +#: modules/commands/ms_info.cpp:157 +#, fuzzy +msgid "" +"Your memo limit is 0; you will not receive any new memos. You cannot change " +"this limit." +msgstr "" +"A max. bejövő üzentek száma: 0; és nem köhet több. \n" +"Ez nem változtatható meg." + +#: modules/commands/ns_logout.cpp:50 +msgid "Your nick has been logged out." +msgstr "A nicked sikeresen kijelentkezett." + +#: modules/commands/ns_group.cpp:156 +#, fuzzy +msgid "Your nick is already registered." +msgstr "A nicked már regisztrált; írd be /msg %s DROP először." + +#: modules/commands/ns_group.cpp:246 +msgid "Your nick is not grouped to anything, you can't ungroup it." +msgstr "Your nick is not grouped to anything, you can't ungroup it." + +#: include/language.h:77 +#, fuzzy +msgid "Your nick isn't registered." +msgstr "Nickname %s registered." + +#: modules/pseudoclients/nickserv.cpp:254 +#, c-format +msgid "Your nickname is now being changed to %s" +msgstr "A nickneved most meg lesz változtatva: %s." + +#: modules/commands/os_login.cpp:32 modules/commands/os_login.cpp:79 +msgid "Your oper block doesn't require logging in." +msgstr "" + +#: modules/commands/ns_register.cpp:336 +#, c-format +msgid "Your passcode has been re-sent to %s." +msgstr "A kód újra el lett küldve erre a címre: %s." + +#: modules/commands/ns_register.cpp:232 +#, c-format +msgid "Your password is %s - remember this for later use." +msgstr "Jelszavad: %s - jegyezd meg a későbbi használathoz!" + +#: include/language.h:76 +#, c-format +msgid "Your password is too long. It must not exceed %u characters." +msgstr "" + +#: modules/commands/ns_resetpass.cpp:96 +msgid "Your password reset request has expired." +msgstr "Your password request has expired." + +#: modules/commands/hs_request.cpp:170 +#, fuzzy +msgid "Your vHost has been requested." +msgstr "A %s nevű bot törölve." + +#: modules/pseudoclients/hostserv.cpp:64 +#: modules/pseudoclients/hostserv.cpp:103 modules/commands/hs_on.cpp:37 +#, c-format +msgid "Your vhost of %s is now activated." +msgstr "A %s virtuális hosztod aktiválva." + +#: modules/pseudoclients/hostserv.cpp:62 +#: modules/pseudoclients/hostserv.cpp:101 modules/commands/hs_on.cpp:35 +#, c-format +msgid "Your vhost of %s@%s is now activated." +msgstr "A %s@%s virtuális hosztod aktiválva." + +#: modules/commands/hs_off.cpp:39 +msgid "Your vhost was removed and the normal cloaking restored." +msgstr "Your vhost was removed and the normal cloaking restored." + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Zone" +msgstr "Nincs" + +#: modules/commands/os_dns.cpp:290 +#, fuzzy, c-format +msgid "Zone %s already exists." +msgstr "%s nevű bot már létezik." + +#: modules/commands/os_dns.cpp:310 modules/commands/os_dns.cpp:352 +#: modules/commands/os_dns.cpp:402 modules/commands/os_dns.cpp:438 +#, fuzzy, c-format +msgid "Zone %s does not exist." +msgstr "%s nevű bot már létezik." + +#: modules/commands/os_dns.cpp:332 +#, fuzzy, c-format +msgid "Zone %s removed." +msgstr "%s vhosztja törölve lett." + +#: modules/commands/os_defcon.cpp:177 +#, fuzzy +msgid "[1|2|3|4|5]" +msgstr "DEFCON [1|2|3|4|5]" + +#: modules/commands/os_news.cpp:400 +#, c-format +msgid "[Logon News - %s] %s" +msgstr "[Fellépési Hír] - %s %s" + +#: modules/commands/os_news.cpp:402 +#, c-format +msgid "[Oper News - %s] %s" +msgstr "[Oper Hír] - %s %s" + +#: modules/commands/os_news.cpp:404 +#, c-format +msgid "[Random News - %s] %s" +msgstr "[Véletlenszerű Hír] - %s %s" + +#: modules/commands/ns_identify.cpp:66 +#, fuzzy +msgid "[account] password" +msgstr "IDENTIFY jelszó" + +#: modules/commands/cs_updown.cpp:49 modules/commands/cs_updown.cpp:147 +#, fuzzy +msgid "[channel [nick]]" +msgstr "OP #channel [nick]" + +#: modules/commands/ms_ignore.cpp:20 +#, fuzzy +msgid "[channel] ADD entry" +msgstr "AOP #szoba { ADD | DEL | LIST | CLEAR } [ nick | sorszám ]" + +#: modules/commands/ms_ignore.cpp:21 +#, fuzzy +msgid "[channel] DEL entry" +msgstr "MODE szoba mód" + +#: modules/commands/ms_ignore.cpp:22 +#, fuzzy +msgid "[channel] LIST" +msgstr "DROP #szoba" + +#: modules/commands/ms_list.cpp:20 +#, fuzzy +msgid "[channel] [list | NEW]" +msgstr "LIST [#szoba] [list | NEW ]" + +#: modules/extra/stats/cs_fantasy_stats.cpp:40 +#, fuzzy +msgid "[channel] [nick]" +msgstr "OP #channel [nick]" + +#: modules/commands/ms_del.cpp:45 +#, fuzzy +msgid "[channel] {num | list | LAST | ALL}" +msgstr "DEL [#szoba] { szám | list | ALL}" + +#: modules/commands/ms_read.cpp:113 +#, fuzzy +msgid "[channel] {num | list | LAST | NEW | ALL}" +msgstr "DEL [#szoba] { szám | list | ALL}" + +#: modules/commands/hs_list.cpp:20 +msgid "[key|#X-Y]" +msgstr "" + +#: modules/commands/ms_info.cpp:20 +#, fuzzy +msgid "[nick | channel]" +msgstr "CANCEL {nick | #szoba}" + +#: modules/commands/ns_group.cpp:237 +#, fuzzy +msgid "[nick]" +msgstr "INFO nick" + +#: modules/commands/ns_logout.cpp:22 +msgid "[nickname [REVALIDATE]]" +msgstr "" + +#: modules/commands/ns_alist.cpp:25 modules/commands/ns_status.cpp:20 +#: modules/commands/ns_info.cpp:20 +#, fuzzy +msgid "[nickname]" +msgstr "CHECK nicknév " + +#: modules/commands/ns_set_misc.cpp:96 +msgid "[parameter]" +msgstr "" + +#: modules/commands/os_logsearch.cpp:33 +msgid "[+daysd] [+limitl] pattern" +msgstr "" + +#: modules/commands/os_chankill.cpp:22 +#, fuzzy +msgid "[+expiry] channel reason" +msgstr "CHANKILL [+lejárat] {#szoba} [indok]" + +#: modules/commands/ns_list.cpp:110 +msgid "[Hostname hidden]" +msgstr "" + +#: modules/commands/ns_list.cpp:112 modules/commands/cs_list.cpp:115 +msgid "[Suspended]" +msgstr "" + +#: modules/commands/ns_list.cpp:114 +msgid "[Unconfirmed]" +msgstr "" + +#: modules/commands/hs_request.cpp:213 +#, fuzzy +msgid "[auto memo] Your requested vHost has been approved." +msgstr "[auto-memo] A memo, amit %s számára küldtél meg lett tekintve." + +#: modules/commands/hs_request.cpp:267 +#, fuzzy +msgid "[auto memo] Your requested vHost has been rejected." +msgstr "[auto-memo] A memo, amit %s számára küldtél meg lett tekintve." + +#: modules/commands/hs_request.cpp:265 +#, c-format +msgid "[auto memo] Your requested vHost has been rejected. Reason: %s" +msgstr "" + +#: modules/commands/hs_request.cpp:388 +#, fuzzy, c-format +msgid "[auto memo] vHost %s has been requested by %s." +msgstr "%s részére küldött utolsó memo üzenet visszavonva." + +#: modules/commands/os_list.cpp:133 +msgid "[{pattern | channel} [INVISIBLE]]" +msgstr "" + +#: modules/commands/os_list.cpp:20 +msgid "[{pattern | nick} [SECRET]]" +msgstr "" + +#: src/misc.cpp:337 +msgid "day" +msgstr "" + +#: src/misc.cpp:337 +msgid "days" +msgstr "" + +#: include/language.h:88 +#, fuzzy +msgid "does not expire" +msgstr " %s (does not expire)" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d day" +msgstr "elévül %d nap múlva" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d days" +msgstr "elévül %d nap múlva" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minute" +msgstr "elévül %d óra, %d perc múlva" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minutes" +msgstr "elévül %d óra, %d perc múlva" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minute" +msgstr "elévül %d óra, %d perc múlva" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minutes" +msgstr "elévül %d óra, %d perc múlva" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minute" +msgstr "elévül %d perc múlva" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minutes" +msgstr "elévül %d perc múlva" + +#: src/misc.cpp:375 +#, fuzzy +msgid "expires momentarily" +msgstr "elévül %d nap múlva" + +#: src/misc.cpp:343 +msgid "hour" +msgstr "" + +#: src/misc.cpp:343 +msgid "hours" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:150 +#, c-format +msgid "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:349 +msgid "minute" +msgstr "" + +#: src/misc.cpp:349 +msgid "minutes" +msgstr "" + +#: modules/commands/bs_info.cpp:87 +msgid "not assigned yet" +msgstr "" + +#: src/misc.cpp:324 +msgid "second" +msgstr "" + +#: src/misc.cpp:324 +#, fuzzy +msgid "seconds" +msgstr "%s parancsok:" + +#: modules/commands/hs_request.cpp:215 +#, fuzzy, c-format +msgid "vHost for %s has been activated." +msgstr "A %s virtuális hosztod aktiválva." + +#: modules/commands/hs_request.cpp:272 +#, fuzzy, c-format +msgid "vHost for %s has been rejected." +msgstr "A %s nevű bot törölve." + +#: modules/commands/hs_request.cpp:79 +msgid "vhost" +msgstr "" + +#: modules/commands/hs_del.cpp:83 +#, c-format +msgid "vhosts for group %s have been removed." +msgstr "A %s csoport vhostja törölve." + +#: src/misc.cpp:331 +msgid "year" +msgstr "" + +#: src/misc.cpp:331 +msgid "years" +msgstr "" + +#: modules/commands/os_config.cpp:20 +msgid "{MODIFY|VIEW} [block name item name item value]" +msgstr "" + +#: modules/commands/bs_info.cpp:41 +#, fuzzy +msgid "{channel | nickname}" +msgstr "UNBAN #szoba [nick]" + +#: modules/commands/ms_cancel.cpp:20 +#, fuzzy +msgid "{nick | channel}" +msgstr "CANCEL {nick | #szoba}" + +#: modules/commands/ms_rsend.cpp:25 modules/commands/ms_send.cpp:25 +#, fuzzy +msgid "{nick | channel} memo-text" +msgstr "SEND {nick | #szoba} memo-szöveg" diff --git a/language/anope.it_IT.po b/language/anope.it_IT.po new file mode 100644 index 0000000..8253271 --- /dev/null +++ b/language/anope.it_IT.po @@ -0,0 +1,11224 @@ +# Anope IRC Services language file +# Copyright (C) 2011 +# This file is distributed under the same license as the Anope IRC Services package. +# Adam , 2011. +# +msgid "" +msgstr "" +"Project-Id-Version: Anope\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2020-01-06 18:19+0100\n" +"PO-Revision-Date: 2020-01-05 17:31+0100\n" +"Last-Translator: Dragone2 \n" +"Language-Team: Italian\n" +"Language: it_IT\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" + +#: modules/commands/os_forbid.cpp:324 +#, c-format +msgid "%d channel(s) cleared, and %d channel(s) dropped." +msgstr "%d canale(i) eliminato(i), e %d canale(i) deregistrato(i)." + +#: modules/commands/os_forbid.cpp:265 +#, c-format +msgid "%d nickname(s) dropped." +msgstr "%d nickname(s) deregistrato(i)." + +#: modules/commands/cs_xop.cpp:219 +#, c-format +msgid "%s added to %s %s list." +msgstr "%1$s aggiunto alla lista %3$s di %2$s." + +#: modules/commands/cs_access.cpp:225 +#, c-format +msgid "%s added to %s access list at level %d." +msgstr "%s aggiunto alla lista di accesso di %s con il livello %d." + +#: modules/commands/cs_access.cpp:223 +#, c-format +msgid "%s added to %s access list at privilege %s (level %d)" +msgstr "" +"%s aggiunto alla lista di accesso di %s con privilegio %s (livello %d)." + +#: modules/commands/cs_akick.cpp:190 +#, c-format +msgid "%s added to %s autokick list." +msgstr "%s aggiunto alla lista autokick di %s." + +#: modules/commands/bs_badwords.cpp:307 +#, c-format +msgid "%s added to %s bad words list." +msgstr "%s aggiunto alla lista delle parolacce di %s." + +#: modules/commands/ns_access.cpp:45 +#, c-format +msgid "%s added to %s's access list." +msgstr "%s aggiunto alla lista di accesso di %s." + +#: modules/commands/ns_cert.cpp:204 +#, c-format +msgid "%s added to %s's certificate list." +msgstr "%s aggiunto alla lista dei certificati di %s." + +#: modules/commands/ms_ignore.cpp:62 +#, c-format +msgid "%s added to ignore list." +msgstr "%s aggiunto alla tua lista ignore." + +#: modules/commands/os_sxline.cpp:415 modules/commands/os_sxline.cpp:649 +#, c-format +msgid "%s added to the %s list." +msgstr "%s aggiunto alla lista %s." + +#: modules/commands/os_akill.cpp:203 +#, c-format +msgid "%s added to the AKILL list." +msgstr "%s aggiunto alla lista AKILL." + +#: modules/pseudoclients/botserv.cpp:134 +#, c-format +msgid "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands " +"that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" +msgstr "" +"%s permette di eseguire comandi di \"fantasia\" in canale.\n" +"I comandi di fantasia sono comandi che possono essere eseguiti scrivendo " +"messaggi in\n" +"canale, e forniscono un modo più conveniente di eseguire comandi. I comandi " +"che\n" +"richiedono un canale come parametro saranno automaticamente completati con " +"il canale in cui è stato\n" +"eseguito il comando.\n" + +#: modules/pseudoclients/botserv.cpp:148 +#, c-format +msgid "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s ti permette di avere un bot nel tuo canale.\n" +"È un servizio pensato per gli utenti che non possono\n" +"mantenere un bot. I comandi disponibili sono i seguenti,\n" +"per usarli, digita %s%s comando.\n" +"Per maggiori informazioni sull'uso di un comando\n" +"specifico, digita %s%s %s comando.\n" + +#: modules/pseudoclients/nickserv.cpp:466 +#, c-format +msgid "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s ti permette di \"registrare\" un nick e di\n" +"evitare che gli altri lo usino. I seguenti\n" +"comandi permettono la registrazione e il mantenimento\n" +"dei nick, per usarli, digita %s%s comando.\n" +"Per maggiori informazioni su un comando specifico,\n" +"digita %s%s %s comando.\n" + +#: modules/pseudoclients/nickserv.cpp:473 +#, c-format +msgid "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s ti permette di registrare un account.\n" +"I seguenti comandi permettono la registrazione e il mantenimento degli\n" +"accounts, per usarli, digita %s%s comando.\n" +"Per maggiori informazioni su un comando specifico,\n" +"digita %s%s %s comando.\n" + +#: modules/pseudoclients/chanserv.cpp:255 +#, c-format +msgid "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" +msgstr "" +"%s permette di registrare i canali e di controllarne\n" +"vari aspetti. %s può spesso evitare che utenti non\n" +"autorizzati prendano il controllo dei canali (\"take over\")\n" +"limitandone l'accesso agli utenti. I comandi disponibili\n" +"sono indicati in basso, per usarli, puoi digitare\n" +"%s%s comando. Per avere maggiori informazioni su\n" +"un comando specifico, digita %s%s HELP comando.\n" + +#: modules/commands/bs_badwords.cpp:298 +#, c-format +msgid "%s already exists in %s bad words list." +msgstr "%s è già presente nella lista delle parolacce di %s." + +#: modules/commands/cs_akick.cpp:170 +#, c-format +msgid "%s already exists on %s autokick list." +msgstr "%s è già presente nella lista autokick di %s." + +#: modules/commands/os_session.cpp:361 +#, c-format +msgid "%s already exists on the EXCEPTION list." +msgstr "%s esiste già nella lista EXCEPTION." + +#: modules/commands/bs_kick.cpp:214 modules/commands/bs_kick.cpp:389 +#: modules/commands/bs_kick.cpp:520 modules/commands/bs_kick.cpp:651 +#, c-format +msgid "%s cannot be taken as times to ban." +msgstr "%s non può essere utilizzato come numero di volte al ban." + +#: modules/commands/os_mode.cpp:163 +#, c-format +msgid "%s changed your usermodes to %s." +msgstr "%s ha modificato i tuoi modi utente in %s." + +#: modules/commands/os_list.cpp:47 +#, c-format +msgid "%s channel list:" +msgstr "Lista canali di %s:" + +#: modules/commands/cs_xop.cpp:343 +#, c-format +msgid "%s deleted from %s %s list." +msgstr "%1$s eliminato dalla lista %3$s di %2$s." + +#: modules/commands/cs_access.cpp:326 +#, c-format +msgid "%s deleted from %s access list." +msgstr "%s eliminato dalla lista di accesso di %s." + +#: modules/commands/cs_akick.cpp:276 +#, c-format +msgid "%s deleted from %s autokick list." +msgstr "%s eliminato dalla lista autokick di %s." + +#: modules/commands/bs_badwords.cpp:348 +#, c-format +msgid "%s deleted from %s bad words list." +msgstr "%s eliminato dalla lista delle parolacce di %s." + +#: modules/commands/ns_access.cpp:72 +#, c-format +msgid "%s deleted from %s's access list." +msgstr "%s eliminato dalla lista di accesso di %s." + +#: modules/commands/ns_cert.cpp:233 +#, c-format +msgid "%s deleted from %s's certificate list." +msgstr "%s eliminato dalla tua lista dei certificati di %s." + +#: modules/commands/os_session.cpp:414 +#, c-format +msgid "%s deleted from session-limit exception list." +msgstr "%s eliminato dalla lista delle eccezioni." + +#: modules/commands/os_sxline.cpp:99 +#, c-format +msgid "%s deleted from the %s list." +msgstr "%s eliminato dalla lista %s." + +#: modules/commands/os_akill.cpp:246 +#, c-format +msgid "%s deleted from the AKILL list." +msgstr "%s eliminato dalla lista AKILL." + +#: modules/commands/cs_access.cpp:685 +#, c-format +msgid "%s disabled on channel %s." +msgstr "%s disabilitato sul canale %s." + +#: modules/commands/cs_invite.cpp:75 +#, c-format +msgid "%s has been invited to %s." +msgstr "%s è stato inviato in %s." + +#: modules/commands/os_svs.cpp:104 +#, c-format +msgid "%s has been joined to %s." +msgstr "%s è stato introdotto in %s." + +#: modules/commands/os_svs.cpp:152 +#, c-format +msgid "%s has been parted from %s." +msgstr "%s è stato rimosso da %s." + +#: modules/commands/cs_unban.cpp:96 +#, c-format +msgid "%s has been unbanned from %s." +msgstr "%s è stato riammesso su %s." + +#: modules/commands/ns_alist.cpp:110 +#, c-format +msgid "%s has no access in any channels." +msgstr "%s non è presente in alcuna lista di accesso." + +#: modules/commands/cs_status.cpp:55 +#, c-format +msgid "%s has no access on %s." +msgstr "%s non è presente nella lista di accesso di %s." + +#: modules/commands/cs_set.cpp:307 +#, c-format +msgid "%s has too many channels registered." +msgstr "%s ha troppi canali registrati." + +#: modules/commands/cs_status.cpp:51 +#, c-format +msgid "%s is a super administrator." +msgstr "%s è un Super Administrator." + +#: modules/pseudoclients/memoserv.cpp:214 +#, c-format +msgid "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" +msgstr "" +"%s è un servizio che permette agli utenti del network IRC di\n" +"scambiarsi brevi messaggi (memo), anche se i destinatari non\n" +"sono connessi, permette inoltre di inviare messaggi ai canali(*).\n" +"Il nick del mittente e quello del destinatario (o il canale\n" +"di destinazione) devono essere registrati.\n" +"\n" +"I comandi di %s sono:" + +#: modules/commands/cs_invite.cpp:66 +#, c-format +msgid "%s is already in %s!" +msgstr "%s è già presente in %s!" + +#: modules/commands/os_svs.cpp:99 +#, c-format +msgid "%s is already in %s." +msgstr "%s è già presente in %s." + +#: modules/commands/ms_ignore.cpp:65 +#, c-format +msgid "%s is already on the ignore list." +msgstr "%s è già presente nella lista ignore." + +#: modules/commands/cs_suspend.cpp:97 modules/commands/ns_suspend.cpp:106 +#, c-format +msgid "%s is already suspended." +msgstr "%s è già sospeso." + +#: modules/commands/ms_rsend.cpp:56 modules/commands/ms_send.cpp:55 +#, c-format +msgid "%s is not a registered unforbidden nick or channel." +msgstr "%s non è un nick o un canale registrato." + +#: modules/commands/cs_set.cpp:178 +#, c-format +msgid "%s is not a valid ban type." +msgstr "%s non è un tipo di ban valido." + +#: modules/commands/bs_info.cpp:101 +#, c-format +msgid "%s is not a valid bot or registered channel." +msgstr "%s non è un bot valido o un canale registrato." + +#: include/language.h:86 +#, c-format +msgid "%s is not a valid e-mail address." +msgstr "%s non è un indirizzo e-mail valido." + +#: include/language.h:80 +#, c-format +msgid "%s is not currently on channel %s." +msgstr "%s non è al momento nel canale %s." + +#: modules/commands/os_svs.cpp:144 +#, c-format +msgid "%s is not in %s." +msgstr "%s non è presente in %s." + +#: modules/commands/ms_ignore.cpp:77 +#, c-format +msgid "%s is not on the ignore list." +msgstr "%s non trovato nella lista ignore." + +#: modules/commands/cs_status.cpp:90 +#, c-format +msgid "%s is on the auto kick list of %s (%s)." +msgstr "%s è presente nella lista auto kick di %s (%s)." + +#: modules/commands/cs_status.cpp:53 +#, c-format +msgid "%s is the founder of %s." +msgstr "%s è il founder del canale %s." + +#: modules/commands/cs_status.cpp:78 +#, c-format +msgid "%s matches access entry %s (from entry %s), which has privilege %s." +msgstr "%s corrisponde al record %s (dalla voce %s), che ha livello %s." + +#: modules/commands/cs_status.cpp:71 +#, c-format +msgid "%s matches access entry %s, which has privilege %s." +msgstr "%s corrisponde al record %s, che ha privilegio %s." + +#: include/language.h:109 +#, c-format +msgid "" +"%s matches an except on %s and cannot be banned until the except has been " +"removed." +msgstr "" +"%s corrisponde a un'eccezione su %s e non può essere bannato fino a quando " +"non viene rimossa." + +#: modules/commands/cs_status.cpp:96 +#, c-format +msgid "%s matches auto kick entry %s on %s (%s)." +msgstr "" +"%s corrisponde al record %s presente nealla lista auto kick di %s (%s)." + +#: modules/commands/cs_xop.cpp:353 +#, c-format +msgid "%s not found on %s %s list." +msgstr "%1$s non trovato nella lista %3$s di %2$s." + +#: modules/commands/cs_access.cpp:338 modules/commands/cs_flags.cpp:255 +#, c-format +msgid "%s not found on %s access list." +msgstr "%s non trovato nella lista di accesso di %s." + +#: modules/commands/cs_akick.cpp:265 +#, c-format +msgid "%s not found on %s autokick list." +msgstr "%s non trovato nella lista autokick di %s." + +#: modules/commands/bs_badwords.cpp:341 +#, c-format +msgid "%s not found on %s bad words list." +msgstr "%s non trovato nella lista delle parolacce di %s." + +#: modules/commands/ns_access.cpp:66 +#, c-format +msgid "%s not found on %s's access list." +msgstr "%s non trovato nella lista di accesso di %s." + +#: modules/commands/ns_cert.cpp:226 +#, c-format +msgid "%s not found on %s's certificate list." +msgstr "%s non trovato nella lista dei certificati di %s." + +#: modules/commands/os_ignore.cpp:320 +#, c-format +msgid "%s not found on ignore list." +msgstr "%s non trovato nella lista ignore." + +#: modules/commands/os_session.cpp:238 +#, c-format +msgid "" +"%s not found on session list, but has a limit of %d because it matches entry:" +" %s." +msgstr "" +"%s non trovato nella lista sessioni, ma ha un limite di %d perché " +"corrisponde con: %s." + +#: modules/commands/os_session.cpp:418 +#, c-format +msgid "%s not found on session-limit exception list." +msgstr "Impossibile trovare %s nella lista delle eccezioni session-limit." + +#: modules/commands/os_sxline.cpp:92 +#, c-format +msgid "%s not found on the %s list." +msgstr "%s non trovato nella lista %s." + +#: modules/commands/os_akill.cpp:237 +#, c-format +msgid "%s not found on the AKILL list." +msgstr "%s non trovato nella lista AKILL." + +#: modules/commands/cs_flags.cpp:251 +#, c-format +msgid "%s removed from the %s access list." +msgstr "%s eliminato dalla lista di accesso di %s." + +#: modules/commands/ms_ignore.cpp:74 +#, c-format +msgid "%s removed from the ignore list." +msgstr "%s rimosso dalla lista ignore." + +#: modules/commands/os_list.cpp:157 +#, c-format +msgid "%s users list:" +msgstr "Lista utenti di %s:" + +#: modules/commands/os_ignore.cpp:316 +#, c-format +msgid "%s will no longer be ignored." +msgstr "%s non è più ignorato." + +#: modules/commands/os_ignore.cpp:238 +#, c-format +msgid "%s will now be ignored for %s." +msgstr "%s sarà ignorato per %s." + +#: modules/commands/os_ignore.cpp:233 +#, c-format +msgid "%s will now permanently be ignored." +msgstr "%s sarà ignorato permanentemente." + +#: include/language.h:66 +#, c-format +msgid "%s%s HELP %s for more information." +msgstr "%s%s HELP %s per ottenere maggiori." + +#: modules/commands/bs_bot.cpp:270 +msgid "ADD nick user host real" +msgstr "ADD nick user host real" + +#: modules/commands/bs_bot.cpp:271 +msgid "CHANGE oldnick newnick [user [host [real]]]" +msgstr "CHANGE vecchionick nuovonick [user [host [real]]]" + +#: modules/commands/bs_bot.cpp:272 +msgid "DEL nick" +msgstr "DEL nick" + +#: modules/commands/os_session.cpp:560 +msgid "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." +msgstr "" +"EXCEPTION ADD aggiunge la hostmask specificata alla lista delle\n" +"eccezioni. Bisogna tenere presente che le mask nick!user@host\n" +"e user@host non sono valide. Soltanto le vere mask di host,\n" +"come ad esempio box.host.dom e *.host.dom, sono permesse,\n" +"poiché la limitazione delle sessioni non tiene conto del nick e\n" +"degli username (ident). limite deve essere un numero maggiore o\n" +"uguale a zero. Questo valore indica quante sessioni contemporanee\n" +"sono permesse a quell'host. Se viene indicato il limite 0, l'host\n" +"non ha limite di sessioni. Guarda l'help del comando AKILL per\n" +"i dettagli sul formato del parametro opzionale durata.\n" +"EXCEPTION DEL rimuove la mask specificata dalla lista delle\n" +"eccezioni.\n" +"EXCEPTION MOVE sposta l'eccezione num alla posizione posizione.\n" +"Le eccezioni che si trovano in mezzo saranno spostate in alto o in\n" +"basso per riempire il vuoto.\n" +"EXCEPTION LIST e EXCEPTION VIEW mostrano tutte le eccezioni\n" +"attuali, se viene specificata la mask opzionale, la lista è limitata\n" +"alle eccezioni che corrispondono alla maschera. La differenza è\n" +"che EXCEPTION VIEW fornisce maggiori informazioni, visualizzando\n" +"il nome della persona che ha aggiunto l'eccezione, il suo limite di\n" +"sessioni, il motivo, la host mask e la data di scadenza.\n" +"\n" +"Si noti che un client che si connetterà \"userà\" la prima\n" +"eccezione corrispondente al suo host. Liste di eccezioni molto\n" +"grandi e mask generiche possono degradare le prestazioni dei\n" +"Services." + +#: modules/commands/os_noop.cpp:68 +msgid "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." +msgstr "" +"SET disconnette tutti gli operatori del server\n" +"specificato e gli impedisce di riottenere\n" +"gradi. REVOKE rimuove questa\n" +"restrizione." + +#: modules/commands/cs_access.cpp:611 +#, c-format +msgid "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." +msgstr "" +"Il livello di accesso degli utenti può essere visto usando il\n" +"comando %s. Digita %s%s HELP LEVELS per\n" +"informazioni." + +#: modules/commands/ms_read.cpp:35 +#, c-format +msgid "[auto-memo] The memo you sent to %s has been viewed." +msgstr "[auto-memo] Il memo che hai inviato a %s è stato letto." + +#: modules/commands/ns_group.cpp:92 +msgid "[target] [password]" +msgstr "[obiettivo] [password]" + +#: modules/commands/ns_set.cpp:453 +msgid "address" +msgstr "indirizzo" + +#: modules/commands/bs_set.cpp:162 +msgid "botname {ON|OFF}" +msgstr "nomebot {ON|OFF}" + +#: modules/extra/stats/cs_fantasy_top.cpp:39 +#: modules/extra/stats/cs_fantasy_top.cpp:51 +#: modules/commands/cs_suspend.cpp:152 modules/commands/cs_sync.cpp:20 +#: modules/commands/cs_log.cpp:106 modules/commands/bs_assign.cpp:91 +#: modules/commands/cs_info.cpp:20 modules/commands/cs_getkey.cpp:20 +msgid "channel" +msgstr "canale" + +#: modules/commands/cs_set.cpp:138 +msgid "channel bantype" +msgstr "canale tipo-di-ban" + +#: modules/commands/cs_drop.cpp:20 +msgid "channel channel" +msgstr "canale canale" + +#: modules/commands/cs_log.cpp:107 +msgid "channel command method [status]" +msgstr "canale comando metodo [status]" + +#: modules/commands/cs_kick.cpp:21 +msgid "channel mask [reason]" +msgstr "canale mask [motivo]" + +#: modules/commands/os_mode.cpp:20 +msgid "channel modes" +msgstr "canale modi" + +#: modules/commands/cs_set.cpp:267 modules/commands/bs_assign.cpp:20 +msgid "channel nick" +msgstr "canale nick" + +#: modules/commands/cs_kick.cpp:20 +msgid "channel nick [reason]" +msgstr "canale nick [motivo]" + +#: modules/commands/cs_clone.cpp:115 +msgid "channel target [what]" +msgstr "canale target [cosa]" + +#: modules/commands/bs_control.cpp:20 modules/commands/bs_control.cpp:80 +msgid "channel text" +msgstr "canale testo" + +#: modules/commands/bs_set.cpp:91 +msgid "channel time" +msgstr "canale tempo" + +#: modules/commands/os_kick.cpp:20 +msgid "channel user reason" +msgstr "canale utente motivo" + +#: modules/commands/cs_enforce.cpp:228 +msgid "channel what" +msgstr "canale cosa" + +#: modules/commands/cs_xop.cpp:481 +msgid "channel ADD mask" +msgstr "canale ADD mask" + +#: modules/commands/cs_access.cpp:499 +msgid "channel ADD mask level" +msgstr "canale ADD mask livello" + +#: modules/commands/cs_entrymsg.cpp:194 +msgid "channel ADD message" +msgstr "canale ADD messaggio" + +#: modules/commands/bs_badwords.cpp:371 +msgid "channel ADD word [SINGLE | START | END]" +msgstr "canale ADD parola [SINGLE | START | END]" + +#: modules/commands/cs_akick.cpp:435 +msgid "channel ADD {nick | mask} [reason]" +msgstr "canale ADD {nick | mask} [motivo]" + +#: modules/commands/cs_topic.cpp:151 +msgid "channel APPEND topic" +msgstr "canale APPEND topic" + +#: modules/commands/cs_access.cpp:503 modules/commands/cs_flags.cpp:376 +#: modules/commands/cs_xop.cpp:484 modules/commands/cs_entrymsg.cpp:197 +#: modules/commands/bs_badwords.cpp:374 modules/commands/cs_akick.cpp:440 +msgid "channel CLEAR" +msgstr "canale CLEAR" + +#: modules/commands/cs_mode.cpp:736 +msgid "channel CLEAR [what]" +msgstr "canale CLEAR [cosa]" + +#: modules/commands/os_mode.cpp:21 +msgid "channel CLEAR [ALL]" +msgstr "canale CLEAR [ALL]" + +#: modules/commands/cs_entrymsg.cpp:195 +msgid "channel DEL num" +msgstr "canale DEL num" + +#: modules/commands/cs_access.cpp:500 modules/commands/cs_xop.cpp:482 +msgid "channel DEL {mask | entry-num | list}" +msgstr "canale DEL {mask | num-voce | list}" + +#: modules/commands/cs_akick.cpp:436 +msgid "channel DEL {nick | mask | entry-num | list}" +msgstr "canale DEL {nick | mask | num-voce | list}" + +#: modules/commands/bs_badwords.cpp:372 +msgid "channel DEL {word | entry-num | list}" +msgstr "canale DEL {parola | num-voce | list}" + +#: modules/commands/cs_akick.cpp:439 +msgid "channel ENFORCE" +msgstr "canale ENFORCE" + +#: modules/commands/cs_access.cpp:744 modules/commands/cs_entrymsg.cpp:196 +msgid "channel LIST" +msgstr "canale LIST" + +#: modules/commands/cs_akick.cpp:437 +msgid "channel LIST [mask | entry-num | list]" +msgstr "canale LIST [mask | num-voce | list]" + +#: modules/commands/cs_access.cpp:501 modules/commands/cs_xop.cpp:483 +#: modules/commands/bs_badwords.cpp:373 +msgid "channel LIST [mask | list]" +msgstr "canale LIST [mask | list]" + +#: modules/commands/cs_flags.cpp:375 +msgid "channel LIST [mask | +flags]" +msgstr "canale LIST [mask | +flags]" + +#: modules/commands/cs_mode.cpp:734 +msgid "channel LOCK {ADD|DEL|SET|LIST} [what]" +msgstr "canale LOCK {ADD|DEL|SET|LIST} [cosa]" + +#: modules/commands/cs_access.cpp:745 +msgid "channel RESET" +msgstr "canale RESET" + +#: modules/commands/cs_mode.cpp:735 +msgid "channel SET modes" +msgstr "canale SET modi" + +#: modules/commands/cs_access.cpp:742 +msgid "channel SET type level" +msgstr "canale SET tipo livello" + +#: modules/commands/cs_akick.cpp:438 +msgid "channel VIEW [mask | entry-num | list]" +msgstr "canale VIEW [mask | num-voce | list]" + +#: modules/commands/cs_access.cpp:502 +msgid "channel VIEW [mask | list]" +msgstr "canale VIEW [mask | list]" + +#: modules/commands/cs_register.cpp:20 modules/commands/cs_set.cpp:205 +msgid "channel [description]" +msgstr "canale [descrizione]" + +#: modules/commands/cs_set.cpp:950 modules/commands/cs_invite.cpp:20 +#: modules/commands/cs_unban.cpp:20 +msgid "channel [nick]" +msgstr "canale [nick]" + +#: modules/commands/cs_set_misc.cpp:96 +msgid "channel [parameters]" +msgstr "canale [parametri]" + +#: modules/commands/cs_mode.cpp:807 modules/commands/cs_status.cpp:20 +msgid "channel [user]" +msgstr "canale [utente]" + +#: modules/commands/cs_suspend.cpp:59 +msgid "channel [+expiry] [reason]" +msgstr "canale [+scadenza] [motivo]" + +#: modules/commands/cs_ban.cpp:40 +msgid "channel [+expiry] {nick | mask} [reason]" +msgstr "canale [+scadenza] {nick | mask} [motivo]" + +#: modules/commands/cs_flags.cpp:374 +msgid "channel [MODIFY] mask changes" +msgstr "canale MODIFY mask modifiche" + +#: modules/commands/cs_topic.cpp:150 +msgid "channel [SET] [topic]" +msgstr "canale SET [topic]" + +#: modules/commands/cs_topic.cpp:152 +msgid "channel [UNLOCK|LOCK]" +msgstr "canale [UNLOCK|LOCK]" + +#: modules/fantasy.cpp:20 modules/commands/greet.cpp:20 +#: modules/commands/bs_assign.cpp:154 +msgid "channel {ON|OFF}" +msgstr "canale {ON|OFF}" + +#: modules/commands/bs_kick.cpp:491 +msgid "channel {ON|OFF} [ttb [ln [secs]]]" +msgstr "canale {ON|OFF} [ttb [ln [secs]]]" + +#: modules/commands/bs_kick.cpp:361 +msgid "channel {ON|OFF} [ttb [min [percent]]]" +msgstr "canale {ON|OFF} [ttb [min [percento]]]" + +#: modules/commands/bs_kick.cpp:623 +msgid "channel {ON|OFF} [ttb [num]]" +msgstr "canale {ON|OFF} [ttb [num]]" + +#: modules/commands/bs_kick.cpp:252 modules/commands/bs_kick.cpp:288 +#: modules/commands/bs_kick.cpp:327 modules/commands/bs_kick.cpp:457 +#: modules/commands/bs_kick.cpp:589 modules/commands/bs_kick.cpp:724 +#: modules/commands/bs_kick.cpp:758 +msgid "channel {ON|OFF} [ttb]" +msgstr "canale {ON|OFF} [ttb]" + +#: modules/commands/cs_access.cpp:743 +msgid "channel {DIS | DISABLE} type" +msgstr "canale {DIS | DISABLE} type" + +#: modules/commands/cs_set.cpp:873 +msgid "channel {ON | LEVEL | OFF}" +msgstr "canale {ON | LEVEL | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:18 modules/commands/cs_set.cpp:75 +#: modules/commands/cs_set.cpp:336 modules/commands/cs_set.cpp:401 +#: modules/commands/cs_set.cpp:473 modules/commands/cs_set.cpp:622 +#: modules/commands/cs_set.cpp:684 modules/commands/cs_set.cpp:747 +#: modules/commands/cs_set.cpp:811 modules/commands/cs_set.cpp:1044 +#: modules/commands/bs_kick.cpp:792 modules/commands/bs_kick.cpp:857 +#: modules/commands/cs_topic.cpp:21 modules/commands/cs_list.cpp:181 +msgid "channel {ON | OFF}" +msgstr "canale {ON | OFF}" + +#: modules/commands/ns_getemail.cpp:24 +msgid "email" +msgstr "email" + +#: modules/commands/ns_set.cpp:794 +msgid "language" +msgstr "lingua" + +#: modules/commands/ms_sendall.cpp:25 modules/commands/ms_staff.cpp:25 +msgid "memo-text" +msgstr "testo-memo" + +#: modules/commands/gl_global.cpp:22 modules/commands/greet.cpp:84 +msgid "message" +msgstr "messaggio" + +#: modules/commands/os_modinfo.cpp:20 modules/commands/os_module.cpp:20 +#: modules/commands/os_module.cpp:57 modules/commands/os_module.cpp:129 +msgid "modname" +msgstr "nomemod" + +#: modules/commands/ns_set.cpp:330 +msgid "new-display" +msgstr "nuovo-mostrato" + +#: modules/commands/ns_set.cpp:120 +msgid "new-password" +msgstr "nuova-password" + +#: modules/extra/stats/cs_fantasy_stats.cpp:52 modules/commands/hs_del.cpp:20 +#: modules/commands/hs_del.cpp:60 modules/commands/ms_check.cpp:20 +#: modules/commands/hs_request.cpp:192 modules/commands/cs_seen.cpp:262 +msgid "nick" +msgstr "nick" + +#: modules/commands/os_svs.cpp:79 +msgid "nick channel" +msgstr "nick canale" + +#: modules/commands/os_svs.cpp:123 +msgid "nick channel [reason]" +msgstr "nick canale [motivo]" + +#: modules/commands/os_oline.cpp:20 +msgid "nick flags" +msgstr "nick flags" + +#: modules/commands/hs_set.cpp:20 modules/commands/hs_set.cpp:126 +msgid "nick hostmask" +msgstr "nick hostmask" + +#: modules/commands/os_svs.cpp:20 +msgid "nick newnick" +msgstr "nick nuovonick" + +#: modules/commands/hs_request.cpp:241 +msgid "nick [reason]" +msgstr "nick [motivo]" + +#: modules/commands/ns_getpass.cpp:20 modules/commands/ns_drop.cpp:19 +#: modules/commands/ns_suspend.cpp:161 +msgid "nickname" +msgstr "nickname" + +#: modules/commands/ns_set.cpp:546 +msgid "nickname address" +msgstr "nickname indirizzo" + +#: modules/commands/ns_resetpass.cpp:22 +msgid "nickname email" +msgstr "nickname email" + +#: modules/commands/ns_set.cpp:872 +msgid "nickname language" +msgstr "nickname lingua" + +#: modules/commands/greet.cpp:145 +msgid "nickname message" +msgstr "nickname messaggio" + +#: modules/commands/ns_set.cpp:399 +msgid "nickname new-display" +msgstr "nickname nuovo-display" + +#: modules/commands/ns_set.cpp:173 +msgid "nickname new-password" +msgstr "nickname nuova-password" + +#: modules/commands/ns_set_misc.cpp:170 +msgid "nickname [parameter]" +msgstr "nickname [parametro]" + +#: modules/commands/ns_recover.cpp:150 +msgid "nickname [password]" +msgstr "nickname [password]" + +#: modules/commands/ns_suspend.cpp:61 +msgid "nickname [+expiry] [reason]" +msgstr "nickname [+scadenza] [motivo]" + +#: modules/commands/ns_info.cpp:239 +msgid "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +msgstr "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:130 modules/commands/ns_set.cpp:302 +#: modules/commands/ns_set.cpp:631 modules/commands/ns_set.cpp:985 +#: modules/commands/ns_set.cpp:1076 modules/commands/ns_set.cpp:1105 +#: modules/commands/ns_list.cpp:252 +msgid "nickname {ON | OFF}" +msgstr "nickname {ON | OFF}" + +#: modules/commands/ns_set.cpp:760 +msgid "nickname {ON | QUICK | IMMED | OFF}" +msgstr "nickname {ON | QUICK | IMMED | OFF}" + +#: modules/commands/bs_set.cpp:20 +msgid "option (channel | bot) settings" +msgstr "opzione (canale | bot) impostazioni" + +#: modules/commands/cs_set.cpp:21 +msgid "option channel parameters" +msgstr "opzione canale parametri" + +#: modules/commands/bs_kick.cpp:120 +msgid "option channel {ON|OFF} [settings]" +msgstr "opzione canale {ON|OFF} [impostazioni]" + +#: modules/commands/ns_set.cpp:75 +msgid "option nickname parameters" +msgstr "opzione nickname parametri" + +#: modules/commands/ms_set.cpp:207 modules/commands/ns_set.cpp:20 +msgid "option parameters" +msgstr "opzione parametri" + +#: modules/commands/os_set.cpp:170 +msgid "option setting" +msgstr "opzione setting" + +#: modules/commands/ns_register.cpp:22 +msgid "passcode" +msgstr "passcode" + +#: modules/commands/os_login.cpp:19 +msgid "password" +msgstr "password" + +#: modules/commands/ns_register.cpp:124 +msgid "password [email]" +msgstr "password [email]" + +#: modules/commands/ns_register.cpp:122 +msgid "password email" +msgstr "password email" + +#: modules/commands/cs_list.cpp:21 +msgid "pattern [SUSPENDED] [NOEXPIRE]" +msgstr "pattern [SUSPENDED] [NOEXPIRE]" + +#: modules/commands/ns_list.cpp:20 +msgid "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" +msgstr "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/os_jupe.cpp:20 +msgid "server [reason]" +msgstr "server [motivo]" + +#: modules/commands/os_mode.cpp:147 +msgid "user modes" +msgstr "utente modi" + +#: modules/commands/os_kill.cpp:20 +msgid "user [reason]" +msgstr "utente [motivo]" + +#: modules/commands/os_sxline.cpp:440 +msgid "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." +msgstr "" +" \n" +"SNLINE ADD aggiunge il realname specificato alla\n" +"lista SNLINE per il motivo dato (che deve essere indicato).\n" +"scadenza è specificato come un intero seguito da una lettera,\n" +"che può essere d (giorni), h (ore), o m (minuti). Le\n" +"combinazioni (ad esempio 1h30m) non sono permesse. Se non\n" +"viene specificata una unità, il valore viene inteso in giorni\n" +"(quindi +30 significa 30 giorni). Per aggiungere una SNLINE \n" +"senza scadenza, bisogna usare +0. Se il realname indicato\n" +"inizia con un +, la durata deve essere indicata esplicitamente,\n" +"anche se è la stessa di default. La durata di default per le\n" +"SNLINE può essere trovata con il comando STATS AKILL.\n" +" \n" +"Nota: visto che i realname possono contenere spazi, il\n" +"separatore tra il realname e il motivo sono i due punti." + +#: modules/commands/os_sxline.cpp:678 +msgid "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +" \n" +"SQLINE ADD aggiunge il nick specificato alla lista\n" +"SQLINE per il motivo dato (che deve essere indicato).\n" +"scadenza è specificato come un intero seguito da una lettera,\n" +"che può essere d (giorni), h (ore), o m (minuti). Le\n" +"combinazioni (ad esempio 1h30m) non sono permesse. Se non\n" +"viene specificata una unità, il valore viene inteso in giorni\n" +"(quindi +30 significa 30 giorni). Per aggiungere una SQLINE\n" +"senza scadenza, bisogna usare +0. Se il nick indicata\n" +"inizia con un +, la durata deve essere indicata esplicitamente,\n" +"anche se è la stessa di default. La durata di default per le\n" +"SQLINE può essere trovata con il comando STATS AKILL." + +#: modules/pseudoclients/nickserv.cpp:492 +#, c-format +msgid "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." +msgstr "" +" \n" +"I nick che non sono più usati sono soggetti a\n" +"cancellazione automatica, saranno quindi eliminati\n" +"dopo %d giorni di inutilizzo." + +#: modules/pseudoclients/botserv.cpp:143 +msgid "" +" \n" +"Available commands are:" +msgstr "" +" \n" +"I comandi disponibili sono:" + +#: modules/pseudoclients/botserv.cpp:167 +#, c-format +msgid "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." +msgstr "" +" \n" +"Il bot entrerà nel canale quando saranno presenti almeno\n" +"%d utente/i in esso." + +#: modules/fantasy.cpp:69 +#, c-format +msgid "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." +msgstr "" +" \n" +"Attiva o disattiva l'uso dei comandi di fantasia\n" +"nel canale. Quando è attivo, gli utenti potranno\n" +"digitare nel canale i comandi utilizzando il prefisso %s\n" +"\n" +"Gli utenti che vogliono usare i comandi di fantasia\n" +"DEVONO avere privilegi sufficienti sia per il livello\n" +"FANTASIA che per il livello del comando richiesto." + +#: modules/commands/greet.cpp:69 +msgid "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." +msgstr "" +" \n" +"Attiva o disattiva il saluto (greet) nel canale.\n" +"Quando è attivo, il bot mostrerà il messaggio di saluto\n" +"impostato degli utenti che accedono, se hanno privilegi\n" +"sufficienti nel canale." + +#: modules/commands/bs_kick.cpp:843 +msgid "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Attiva o disattiva la protezione degli op nel\n" +"canale. Quando è attiva, gli op non saranno\n" +"espulsi dal bot, anche se non hanno accesso al\n" +"livello NOKICK." + +#: modules/commands/bs_kick.cpp:908 +msgid "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Attiva o disattiva la protezione dei voice nel\n" +"canale. Quando è attiva, i voice non saranno\n" +"espulsi dal bot, anche se non hanno accesso al\n" +"livello NOKICK." + +#: modules/pseudoclients/botserv.cpp:141 +#, c-format +msgid "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" +msgstr "" +" \n" +"I comandi di fantasia possono essere inviati utilizzando uno dei seguenti " +"caratteri come prefisso: %s\n" + +#: modules/commands/cs_register.cpp:105 +msgid "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." +msgstr "" +" \n" +"NOTA: Per registrare un canale, è necessario aver prima\n" +"registrato il proprio nickname." + +#: modules/pseudoclients/chanserv.cpp:272 +#, c-format +msgid "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." +msgstr "" +" \n" +"Tieni conto che i canali che non vengono utilizzati per %d\n" +"giorni (cioè in quei canali in cui non entra nessun utente\n" +"che si trova nella relativa lista di accesso) saranno\n" +"automaticamente deregistrati." + +#: modules/commands/cs_register.cpp:101 +#, c-format +msgid "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +msgstr "" +" \n" +"Consulta il comando %s (%s%s HELP ACCESS) per\n" +"informazioni su come assegnare alcuni di questi privilegi ad\n" +"altri utenti del canale.\n" + +#: modules/pseudoclients/nickserv.cpp:486 +msgid "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." +msgstr "" +" \n" +"I Services Operator possono anche deregistrare qualsiasi nick\n" +"senza doversi identificare per quest'ultimo e possono visualizzare\n" +"le liste di accesso per qualunque nickname." + +#: modules/pseudoclients/chanserv.cpp:277 +msgid "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." +msgstr "" +" \n" +"I Services Operator possono anche (in base al loro livello) deregistrare\n" +"qualsiasi canale, vedere (e modificare) le liste ACCESS, AKICK, LEVELS\n" +"e le impostazioni per qualsiasi canale." + +#: modules/commands/bs_set.cpp:147 +msgid "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." +msgstr "" +" \n" +"Imposta il tempo entro cui i ban del bot scadranno. Se abilitato, tutti i " +"ban impostati dai\n" +"bots, come ad esempio kick per flood, kick per parolacce, ecc. saranno " +"automaticamente\n" +"rimossi dopo il tempo stabilito. Impostando il valore 0 si disabilita la " +"scadenza\n" +"automatica dei ban." + +#: modules/commands/cs_xop.cpp:542 +#, c-format +msgid "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." +msgstr "" +" \n" +"Il comando %s ADD aggiunge il nickname specificato alla\n" +"lista %s.\n" +" \n" +"Il comando %s DEL rimuove il nick specificato dalla\n" +"lista %s. Se viene specificata una lista, i record\n" +"corrispondenti vengono rimossi. (Guarda l'esempio per LIST sotto.)\n" +" \n" +"Il comando %s LIST mostra la lista %s. Se viene\n" +"utilizzata una wildcard per la mask, solo i record che\n" +"corrispondono alla mask vengono mostrati. Se viene\n" +"specificato un elenco, solo i record corrispondenti saranno mostrati.\n" +"Esempio:\n" +" %s #canale LIST 2-5,7-9\n" +" Mostra i record %s che vanno da 2 a 5\n" +" e da 7 a 9.\n" +" \n" +"Il comando %s CLEAR svuota la lista %s." + +#: modules/commands/cs_akick.cpp:508 +#, c-format +msgid "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." +msgstr "" +" \n" +"Il comando AKICK DEL rimuove il nick o la mask specificata\n" +"dalla lista AutoKick. Non rimuove, però, i ban piazzati da\n" +"un AutoKick, che devono quindi essere rimossi manualmente.\n" +" \n" +"Il comando AKICK LIST mostra la lista AutoKick, o, se\n" +"specificata, solo i record che corrispondono alla mask\n" +"indicata.\n" +" \n" +"Il comando AKICK VIEW mostra la lista Autokick, fornendo\n" +"più informazioni del comando AKICK LIST.\n" +" \n" +"Il comando AKICK ENFORCE fa sì che %s forzi la\n" +"lista AutoKick attuale, rimuovendo dal canale tutti gli\n" +"utenti che corrispondono alle varie mask presenti nella\n" +"lista.\n" +" \n" +"Il comando AKICK CLEAR svuota la lista AutoKick." + +#: modules/commands/os_akill.cpp:448 +msgid "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." +msgstr "" +" \n" +"Il comando AKILL DEL rimuove la mask specificata dalla lista\n" +"AKILL se presente. Se viene indicata una lista di numeri,\n" +"verrano rimossi i record corrispondenti (vedi l'esempio di\n" +"LIST.)\n" +" \n" +"Il comando AKILL LIST mostra la lista AKILL. Se viene usata\n" +"una wildcard nella mask, solo i record che corrispondono alla\n" +"mask vengono mostrati. Se viene indicata una lista di numeri,\n" +"soltanto quei record vengono mostrati, ad esempio:\n" +" AKILL LIST 2-5,7-9\n" +" Mostra i record della lista AKILL che hanno numeri da 2\n" +" a 5 e da 7 a 9.\n" +" \n" +"AKILL VIEW mostra più informazioni di AKILL LIST, e indica\n" +"chi ha aggiunto una AKILL, quando è stata aggiunta, e quando\n" +"scade, oltre alla mask user@host/ip mask e al motivo.\n" +" \n" +"AKILL CLEAR svuota la lista AKILL." + +#: modules/commands/os_sxline.cpp:462 +msgid "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." +msgstr "" +" \n" +"Il comando SNLINE DEL rimuove la mask specificata dalla lista\n" +"SNLINE se presente. Se viene indicata una lista di numeri,\n" +"verrano rimossi i record corrispondenti (vedi l'esempio di\n" +"LIST.)\n" +" \n" +"Il comando SNLINE LIST mostra la lista SNLINE. Se viene usata\n" +"una wildcard nella mask, solo i record che corrispondono alla\n" +"mask vengono mostrati. Se viene indicata una lista di numeri,\n" +"soltanto quei record vengono mostrati, ad esempio:\n" +" SNLINE LIST 2-5,7-9\n" +" Mostra i record della lista SNLINE che hanno numeri da 2\n" +" a 5 e da 7 a 9.\n" +" \n" +"SNLINE VIEW mostra più informazioni di SNLINE LIST, e indica\n" +"chi ha aggiunto una SNLINE, quando è stata aggiunta, e quando\n" +"scade, oltre alla mask di realname e il motivo.\n" +" \n" +"SNLINE CLEAR svuota la lista SNLINE." + +#: modules/commands/os_sxline.cpp:697 +msgid "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." +msgstr "" +" \n" +"Il comando SQLINE DEL rimuove la mask specificata dalla lista\n" +"SQLINE se presente. Se viene indicata una lista di numeri,\n" +"verrano rimossi i record corrispondenti (vedi l'esempio di\n" +"LIST.)\n" +" \n" +"The SQLINE LIST mostra la lista SQLINE. Se viene usata\n" +"una wildcard nella mask, solo i record che corrispondono alla\n" +"mask vengono mostrati. Se viene indicata una lista di numeri,\n" +"soltanto quei record vengono mostrati, ad esempio:\n" +" SQLINE LIST 2-5,7-9\n" +" Mostra i record della lista SNLINE che hanno numeri da 2\n" +" a 5 e da 7 a 9.\n" +" \n" +"SQLINE VIEW mostra più informazioni di SQLINE LIST, e indica\n" +"chi ha aggiunto una SQLINE, quando è stata aggiunta, e quando\n" +"scade, oltre alla mask e il motivo.\n" +" \n" +"SQLINE CLEAR svuota la lista SQLINE." + +#: modules/commands/bs_assign.cpp:197 +msgid "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." +msgstr "" +" \n" +"Questa opzione fa in modo che non sia possibile\n" +"assegnare alcun bot al canale specificato.\n" +"Se un bot è già assegnato, verrà rimosso\n" +"nel momento in cui viene attivata l'opzione." + +#: modules/commands/bs_set.cpp:199 +msgid "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." +msgstr "" +" \n" +"Questa opzione fa sì che il bot sia assegnabile\n" +"soltanto dagli IRCOp." + +#: modules/pseudoclients/memoserv.cpp:227 +#, c-format +msgid "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." +msgstr "" +" \n" +"Digita %s%s HELP comando per maggiori informazioni\n" +"sull'uso dei comandi sopraelencati." + +#: modules/commands/os_oper.cpp:167 +#, c-format +msgid " %s is online using this oper block." +msgstr " %s è online usando questo oper block." + +#: modules/commands/os_modinfo.cpp:55 +#, c-format +msgid " Command %s on %s is linked to %s" +msgstr " Il comando %s su %s è collegato a %s" + +#: modules/commands/os_modinfo.cpp:43 +#, c-format +msgid " Providing service: %s" +msgstr " Servizio fornito: %s" + +#: modules/commands/os_oper.cpp:163 +msgid " This oper is configured in the configuration file." +msgstr " Questo oper è configurato nel file di configurazione." + +#: modules/commands/os_modinfo.cpp:34 +#, c-format +msgid " Loaded at: %p" +msgstr " Caricato a: %p" + +#: modules/commands/cs_seen.cpp:303 +#, c-format +msgid " but %s mysteriously dematerialized." +msgstr " ma %s si è misteriosamente smaterializzato." + +#: src/messages.cpp:339 +#, c-format +msgid "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." +msgstr "\"/msg %s\" non è più supportato. Usa \"/msg %s@%s\" o \"/%s\"." + +#: modules/commands/os_jupe.cpp:19 +msgid "\"Jupiter\" a server" +msgstr "Disabilita (\"jupiter\") un server" + +#: modules/commands/os_oper.cpp:161 +#, c-format +msgid "%-8s %s" +msgstr "%-8s %s" + +#: modules/extra/stats/cs_fantasy_top.cpp:152 +#, c-format +msgid "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "%2lu %-16s lettere: %s, parole: %s, linee: %s, smileys: %s, azioni: %s" + +#: src/misc.cpp:359 +msgid "%b %d %H:%M:%S %Y %Z" +msgstr "%b %d %H:%M:%S %Y %Z" + +#: modules/commands/cs_log.cpp:205 +#, c-format +msgid "%c is an unknown status mode." +msgstr "%c è un modo sconosciuto." + +#: modules/commands/cs_mode.cpp:431 +#, c-format +msgid "%c%c is not locked on %s." +msgstr "%c%c non è bloccato su %s." + +#: modules/commands/cs_mode.cpp:427 +#, c-format +msgid "%c%c%s has been unlocked from %s." +msgstr "%c%c%s è stato sbloccato da %s." + +#: modules/commands/cs_clone.cpp:56 +#, c-format +msgid "%d access entries from %s have been cloned to %s." +msgstr "%d record della lista di %s sono stati clonati su %s." + +#: modules/commands/bs_botlist.cpp:56 +#, c-format +msgid "%d bots available." +msgstr "%d bot disponibili." + +#: modules/commands/os_modinfo.cpp:189 +#, c-format +msgid "%d modules loaded." +msgstr "%d moduli caricati." + +#: modules/commands/ns_group.cpp:357 +#, c-format +msgid "%d nickname(s) in the group." +msgstr "%d nickname nel gruppo." + +#: modules/commands/cs_seen.cpp:137 +#, c-format +msgid "%lu nicks are stored in the database, using %.2Lf kB of memory." +msgstr "%lu nicks sono memorizzati nel database, memoria in uso: %.2Lf kB." + +#: modules/commands/cs_xop.cpp:241 modules/commands/cs_xop.cpp:372 +#: modules/commands/cs_xop.cpp:450 +#, c-format +msgid "%s %s list is empty." +msgstr "La lista %2$s di %1$s è vuota." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1181 +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1201 +#: modules/commands/bs_kick.cpp:1211 +#, c-format +msgid "%s (%d kick(s) to ban)" +msgstr "%s (%d kick(s) al ban)" + +#: modules/commands/bs_kick.cpp:1161 +#, c-format +msgid "%s (%d kick(s) to ban; %d lines in %ds)" +msgstr "%s (%d kick(s) al ban; %d linee in %ds)" + +#: modules/commands/bs_kick.cpp:1171 +#, c-format +msgid "%s (%d kick(s) to ban; %d times)" +msgstr "%s (%d kick(s) al ban; %d volte)" + +#: modules/commands/bs_kick.cpp:1141 +#, c-format +msgid "%s (%d kick(s) to ban; minimum %d/%d%%)" +msgstr "%s (%d kick(s) al ban; minimo %d/%d%%)" + +#: modules/commands/bs_kick.cpp:1163 +#, c-format +msgid "%s (%d lines in %ds)" +msgstr "%s (%d linee in %ds)" + +#: modules/commands/bs_kick.cpp:1173 +#, c-format +msgid "%s (%d times)" +msgstr "%s (%d volte)" + +#: modules/commands/cs_seen.cpp:358 +#, c-format +msgid "%s (%s) was kicked from %s (\"%s\") %s ago%s" +msgstr "%s (%s) è stato allontanato da %s (\"%s\") %s fa%s" + +#: modules/commands/cs_seen.cpp:355 +#, c-format +msgid "%s (%s) was kicked from a secret channel %s ago%s" +msgstr "%s (%s) è stato allontanato da un canale segreto %s fa%s" + +#: modules/commands/cs_seen.cpp:326 +#, c-format +msgid "%s (%s) was last seen changing nick from %s to %s %s ago%s" +msgstr "%s (%s) è stato visto l'ultima volta cambiare nick da %s in %s %s fa%s" + +#: modules/commands/cs_seen.cpp:321 +#, c-format +msgid "%s (%s) was last seen changing nick to %s %s ago%s" +msgstr "%s (%s) è stato visto l'ultima volta cambiare nick in %s %s fa%s" + +#: modules/commands/cs_seen.cpp:310 +#, c-format +msgid "%s (%s) was last seen connecting %s ago (%s)%s" +msgstr "%s (%s) è stato visto l'ultima volta connesso %s fa (%s)%s" + +#: modules/commands/cs_seen.cpp:335 +#, c-format +msgid "%s (%s) was last seen joining %s %s ago%s" +msgstr "%s (%s) è stato visto l'ultima volta accedere a %s %s fa%s" + +#: modules/commands/cs_seen.cpp:332 +#, c-format +msgid "%s (%s) was last seen joining a secret channel %s ago%s" +msgstr "" +"%s (%s) è stato visto l'ultima volta accedere a un canale segreto %s fa%s" + +#: modules/commands/cs_seen.cpp:344 +#, c-format +msgid "%s (%s) was last seen parting %s %s ago%s" +msgstr "%s (%s) è stato visto l'ultima volta uscire da %s %s fa%s" + +#: modules/commands/cs_seen.cpp:341 +#, c-format +msgid "%s (%s) was last seen parting a secret channel %s ago%s" +msgstr "" +"%s (%s) è stato visto l'ultima volta uscire da un canale segreto %s fa%s" + +#: modules/commands/cs_seen.cpp:349 +#, c-format +msgid "%s (%s) was last seen quitting (%s) %s ago (%s)." +msgstr "%s (%s) è stato visto l'ultima volta uscire da IRC (%s) %s fa (%s)." + +#: modules/commands/bs_kick.cpp:1143 +#, c-format +msgid "%s (minimum %d/%d%%)" +msgstr "%s (minimo %d/%d%%)" + +#: modules/commands/cs_access.cpp:245 modules/commands/cs_access.cpp:349 +#: modules/commands/cs_access.cpp:454 modules/commands/cs_access.cpp:467 +#: modules/commands/cs_flags.cpp:295 +#, c-format +msgid "%s access list is empty." +msgstr "La lista di accesso di %s è vuota." + +#: modules/commands/ns_ajoin.cpp:184 +#, c-format +msgid "%s added to %s's auto join list." +msgstr "%s aggiunto alla lista auto join di %s." + +#: src/xline.cpp:389 +#, c-format +msgid "%s already exists." +msgstr "%s già esistente." + +#: modules/commands/cs_akick.cpp:202 modules/commands/cs_akick.cpp:387 +#: modules/commands/cs_akick.cpp:400 +#, c-format +msgid "%s autokick list is empty." +msgstr "La lista autokick di %s è vuota." + +#: modules/commands/bs_badwords.cpp:198 modules/commands/bs_badwords.cpp:316 +#, c-format +msgid "%s bad words list is empty." +msgstr "La lista delle parolacce di %s è vuota." + +#: modules/commands/cs_set.cpp:993 +#, c-format +msgid "%s cannot be the successor on channel %s as they are the founder." +msgstr "%s non può essere il successore del canale %s perché ne è il founder." + +#: modules/pseudoclients/global.cpp:90 modules/pseudoclients/hostserv.cpp:78 +#: modules/pseudoclients/operserv.cpp:287 +#, c-format +msgid "%s commands:" +msgstr "Comandi di %s:" + +#: include/language.h:69 +#, c-format +msgid "%s coverage is too wide; Please use a more specific mask." +msgstr "La copertura di %s è troppo ampia; usa una mask più specifica." + +#: modules/commands/ms_info.cpp:94 +#, c-format +msgid "%s currently has %d memos, of which %d are unread." +msgstr "%s ha %d memo, di cui %d non sono stati ancora letti." + +#: modules/commands/ms_info.cpp:92 +#, c-format +msgid "%s currently has %d memos, of which 1 is unread." +msgstr "%s ha %d memo, di cui 1 non è stato ancora letto." + +#: modules/commands/ms_info.cpp:90 +#, c-format +msgid "%s currently has %d memos." +msgstr "%s ha %d memo." + +#: modules/commands/ms_info.cpp:88 +#, c-format +msgid "%s currently has %d memos; all of them are unread." +msgstr "%s ha %d memo, nessuno dei quali è stato letto." + +#: modules/commands/ms_info.cpp:77 +#, c-format +msgid "%s currently has 1 memo, and it has not yet been read." +msgstr "%s ha 1 memo, e non è stato ancora letto." + +#: modules/commands/ms_info.cpp:79 +#, c-format +msgid "%s currently has 1 memo." +msgstr "%s ha 1 memo." + +#: modules/commands/ms_info.cpp:73 +#, c-format +msgid "%s currently has no memos." +msgstr "%s non ha alcun memo." + +#: modules/commands/os_forbid.cpp:344 +#, c-format +msgid "%s deleted from the %s forbid list." +msgstr "%s eliminato dalla lista dei %s non permessi." + +#: include/language.h:105 +#, c-format +msgid "%s for %s set to %s." +msgstr "%s per %s impostato a %s." + +#: include/language.h:106 +#, c-format +msgid "%s for %s unset." +msgstr "%s per %s rimosso." + +#: modules/commands/ns_ajoin.cpp:176 +#, c-format +msgid "%s had an invalid key specified, and was thus ignored." +msgstr "%s aveva una chiave specificata non valida ed è stata ignorata." + +#: modules/commands/ms_info.cpp:111 +#, c-format +msgid "%s has no memo limit." +msgstr "%s non ha alcun limite dei memo." + +#: include/language.h:115 +#, c-format +msgid "%s has no memos." +msgstr "%s non ha memo." + +#: include/language.h:118 +#, c-format +msgid "%s has no new memos." +msgstr "%s non ha nuovi memo." + +#: modules/commands/ns_info.cpp:53 +#, c-format +msgid "%s is %s" +msgstr "%s è %s" + +#: modules/commands/ns_info.cpp:59 +#, c-format +msgid "%s is a Services Operator of type %s." +msgstr "%s è un Services Operator di tipo %s." + +#: modules/commands/cs_seen.cpp:281 +#, c-format +msgid "%s is a client on services." +msgstr "%s è online in questo momento." + +#: modules/commands/cs_seen.cpp:200 +#, c-format +msgid "%s is a network service." +msgstr "%s è un network service." + +#: src/xline.cpp:407 +#, c-format +msgid "%s is already covered by %s." +msgstr "%s è già coperto da %s." + +#: modules/commands/ns_ajoin.cpp:170 +#, c-format +msgid "%s is already on %s's auto join list." +msgstr "%s è già presente nella lista auto join di %s." + +#: modules/commands/ns_info.cpp:56 +#, c-format +msgid "%s is an unconfirmed nickname." +msgstr "%s è un nickname non confermato." + +#: modules/commands/cs_flags.cpp:432 +#, c-format +msgid "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." +msgstr "" +"%s è un altro metodo di gestione della lista di accesso del canale, simile\n" +"ai metodi XOP e ACCESS." + +#: modules/commands/ns_info.cpp:74 +#, c-format +msgid "%s is currently online." +msgstr "%s è online in questo momento." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is disabled" +msgstr "%s è disattivato" + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is enabled" +msgstr "%s è attivato" + +#: modules/commands/os_dns.cpp:507 +#, c-format +msgid "%s is not a valid IP address." +msgstr "%s non è un indirizzo IP valido." + +#: modules/commands/cs_log.cpp:167 modules/commands/cs_log.cpp:192 +#, c-format +msgid "%s is not a valid command." +msgstr "%s non è un comando valido." + +#: modules/commands/cs_log.cpp:198 +#, c-format +msgid "%s is not a valid logging method." +msgstr "%s non è un metodo di logging valido." + +#: modules/commands/ms_info.cpp:124 +#, c-format +msgid "%s is not notified of new memos." +msgstr "%s non viene informato dei nuovi memo." + +#: modules/commands/ms_info.cpp:118 +#, c-format +msgid "%s is notified of new memos at logon and when they arrive." +msgstr "" +"%s viene informato dei nuovi memo quando si connette e quando li riceve." + +#: modules/commands/ms_info.cpp:122 +#, c-format +msgid "%s is notified of new memos at logon." +msgstr "%s viene informato dei nuovi memo quando si connette." + +#: modules/commands/ms_info.cpp:120 +#, c-format +msgid "%s is notified when new memos arrive." +msgstr "%s viene informato dei nuovi memo quando li riceve." + +#: modules/commands/cs_seen.cpp:232 +#, c-format +msgid "%s is on the channel right now (as %s)!" +msgstr "%s è nel canale adesso (%s)" + +#: modules/commands/cs_seen.cpp:221 +#, c-format +msgid "%s is on the channel right now!" +msgstr "%s è nel canale adesso!" + +#: modules/commands/cs_xop.cpp:434 +#, c-format +msgid "%s list for %s" +msgstr "%s lista per %s" + +#: modules/commands/os_sxline.cpp:69 modules/commands/os_sxline.cpp:113 +#, c-format +msgid "%s list is empty." +msgstr "La lista %s è vuota." + +#: modules/commands/cs_mode.cpp:376 +#, c-format +msgid "%s locked on %s." +msgstr "%s bloccato su %s." + +#: modules/extra/stats/cs_fantasy_stats.cpp:120 +#, c-format +msgid "%s not found." +msgstr "%s non trovato." + +#: modules/commands/os_config.cpp:79 +#, c-format +msgid "%s settings:" +msgstr "%s impostazioni:" + +#: modules/commands/cs_seen.cpp:255 +#, c-format +msgid "%s was last seen here %s ago." +msgstr "%s è stato visto l'ultima volta qui %s fa." + +#: modules/commands/ns_ajoin.cpp:213 +#, c-format +msgid "%s was not found on %s's auto join list." +msgstr "%s non trovato nella lista auto join di %s." + +#: modules/commands/ns_ajoin.cpp:221 +#, c-format +msgid "%s was removed from %s's auto join list." +msgstr "%s eliminato dalla lista auto join di %s." + +#: modules/commands/ms_set.cpp:64 +#, c-format +msgid "%s will not send you any notification of memos." +msgstr "%s non ti informerà dei nuovi memo." + +#: modules/commands/ms_set.cpp:42 +#, c-format +msgid "%s will now notify you of memos when they are sent to you." +msgstr "%s ti informerà dei nuovi memo quando li ricevi." + +#: modules/commands/ms_set.cpp:30 +#, c-format +msgid "" +"%s will now notify you of memos when you log on and when they are sent to " +"you." +msgstr "%s ti informerà dei nuovi memo quando ti connetti e quando li ricevi." + +#: modules/commands/ms_set.cpp:36 +#, c-format +msgid "%s will now notify you of memos when you log on or unset /AWAY." +msgstr "" +"%s ti informerà dei nuovi memo quando ti connetti e quando torni dall'/AWAY." + +#: modules/commands/bs_bot.cpp:89 +#, c-format +msgid "%s!%s@%s (%s) added to the bot list." +msgstr "%s!%s@%s (%s) aggiunto alla lista dei bot." + +#: modules/commands/ns_access.cpp:83 +#, c-format +msgid "%s's access list is empty." +msgstr "La lista di accesso di %s è vuota." + +#: modules/commands/ns_ajoin.cpp:96 +#, c-format +msgid "%s's auto join list is empty." +msgstr "La lista auto join di %s è vuota." + +#: modules/commands/ns_ajoin.cpp:111 +#, c-format +msgid "%s's auto join list:" +msgstr "Lista auto join di %s:" + +#: modules/commands/ns_cert.cpp:242 +#, c-format +msgid "%s's certificate list is empty." +msgstr "La tua lista dei certificati di %s è vuota." + +#: modules/commands/ms_info.cpp:99 modules/commands/ms_info.cpp:106 +#, c-format +msgid "%s's memo limit is %d, and may not be changed." +msgstr "Il limite dei memo di %s è %d, e non può essere modificato." + +#: modules/commands/ms_info.cpp:101 modules/commands/ms_info.cpp:108 +#, c-format +msgid "%s's memo limit is %d." +msgstr "Il limite dei memo di %s è %d." + +#: src/misc.cpp:363 +#, c-format +msgid "(%s ago)" +msgstr "(%s fa)" + +#: src/misc.cpp:365 +#, c-format +msgid "(%s from now)" +msgstr "(%s da adesso)" + +#: modules/commands/os_dns.cpp:244 +msgid "(Split)" +msgstr "(Separa)" + +#: modules/commands/os_info.cpp:268 +#, c-format +msgid "(by %s on %s) %s" +msgstr "(da %s su %s) %s" + +#: modules/commands/cs_access.cpp:710 +msgid "(disabled)" +msgstr "(disattivato)" + +#: modules/commands/cs_access.cpp:712 +msgid "(founder only)" +msgstr "(solo founder)" + +#: src/misc.cpp:367 +msgid "(now)" +msgstr "(ora)" + +#: modules/commands/os_defcon.cpp:168 +msgid "* AKILL any new clients connecting" +msgstr "* AKILL tutti i nuovi client che si collegano" + +#: modules/commands/os_defcon.cpp:158 +#, c-format +msgid "* Force channel modes (%s) to be set on all channels" +msgstr "* Forza l'impostazione dei modi canale (%s) su tutti i canali" + +#: modules/commands/os_defcon.cpp:164 +msgid "* Ignore non-opers with a message" +msgstr "* Ignora tutti i non-opers con un messaggio" + +#: modules/commands/os_defcon.cpp:162 +msgid "* Kill any new clients connecting" +msgstr "* Killa tutti i NUOVI client che si collegano" + +#: modules/commands/os_defcon.cpp:156 +msgid "* No mode lock changes" +msgstr "* Nessuna modifica ai modi bloccati" + +#: modules/commands/os_defcon.cpp:152 +msgid "* No new channel registrations" +msgstr "* Nessuna nuova registrazione di canali" + +#: modules/commands/os_defcon.cpp:170 +msgid "* No new memos sent" +msgstr "* Niente nuovi memo inviati" + +#: modules/commands/os_defcon.cpp:154 +msgid "* No new nick registrations" +msgstr "* Nessuna nuova registrazione di nick" + +#: modules/commands/os_defcon.cpp:166 +msgid "* Silently ignore non-opers" +msgstr "* Ignora silenziosamente i non-opers" + +#: modules/commands/os_defcon.cpp:160 +#, c-format +msgid "* Use the reduced session limit of %d" +msgstr "* Usa il limite di sessioni ridotto a %d" + +#: modules/commands/cs_seen.cpp:319 +#, c-format +msgid ", but %s mysteriously dematerialized." +msgstr ", ma %s si è misteriosamente smaterializzato." + +#: modules/commands/cs_seen.cpp:317 +#, c-format +msgid ". %s is still online." +msgstr ". %s è online in questo momento." + +#: include/language.h:87 +msgid "" +msgstr "" + +#: modules/commands/ns_set.cpp:504 +#, c-format +msgid "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." +msgstr "" +"È stata inviata una e-mail di conferma a %s. Segui le istruzioni contenute " +"nel messaggio per cambiare il tuo indirizzo e-mail." + +#: modules/commands/ms_sendall.cpp:45 +msgid "A massmemo has been sent to all registered users." +msgstr "Un memo di massa è stato inviato a tutti gli utenti registrati." + +#: modules/commands/hs_request.cpp:285 +msgid "" +"A memo informing the user will also be sent, which includes the reason for " +"the rejection if supplied." +msgstr "" +"Un memo che informa l'utente verrà inviato, con il relativo motivo del " +"rigetto se specificato." + +#: modules/commands/hs_request.cpp:229 +msgid "A memo informing the user will also be sent." +msgstr "Sarà anche inviato un memo che informerà l'utente." + +#: modules/commands/ms_read.cpp:42 +#, c-format +msgid "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." +msgstr "" +"Un memo di notifica è stato mandato a %s informandolo/a che hai\n" +"letto il suo memo." + +#: include/language.h:123 +msgid "A vHost ident must be in the format of a valid ident." +msgstr "L'ident di un vHost deve essere nel formato di una ident valida." + +#: include/language.h:122 +msgid "A vHost must be in the format of a valid hostname." +msgstr "Un vHost deve essere nel formato di un hostname valido." + +#: modules/commands/os_ignore.cpp:342 +msgid "ADD expiry {nick|mask} [reason]" +msgstr "ADD scadenza {nick|mask} [motivo]" + +#: modules/commands/os_oper.cpp:70 +msgid "ADD oper type" +msgstr "ADD oper tipo" + +#: modules/commands/os_info.cpp:102 +msgid "ADD target info" +msgstr "ADD target info" + +#: modules/commands/os_news.cpp:278 +msgid "ADD text" +msgstr "ADD testo" + +#: modules/commands/os_session.cpp:523 +msgid "ADD [+expiry] mask limit reason" +msgstr "ADD [+scadenza] mask limite motivo" + +#: modules/commands/ns_ajoin.cpp:231 +msgid "ADD [nickname] channel [key]" +msgstr "ADD [nickname] canale [chiave]" + +#: modules/commands/ns_access.cpp:102 +msgid "ADD [nickname] mask" +msgstr "ADD [nickname] mask" + +#: modules/commands/ns_cert.cpp:258 +msgid "ADD [nickname] [fingerprint]" +msgstr "ADD [nickname] [fingerprint]" + +#: modules/commands/os_sxline.cpp:659 modules/commands/os_akill.cpp:386 +msgid "ADD [+expiry] mask reason" +msgstr "ADD [+scadenza] mask motivo" + +#: modules/commands/os_sxline.cpp:425 +msgid "ADD [+expiry] mask:reason" +msgstr "ADD [+scadenza] mask:motivo" + +#: modules/commands/os_forbid.cpp:157 +msgid "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" +msgstr "ADD {NICK|CHAN|EMAIL|REGISTER} [+scadenza] voce motivo" + +#: modules/commands/os_dns.cpp:665 +msgid "ADDIP server.name ip" +msgstr "ADDIP server.nome ip" + +#: modules/commands/os_dns.cpp:663 +msgid "ADDSERVER server.name [zone.name]" +msgstr "ADDSERVER server.nome [zona.nome]" + +#: modules/commands/os_dns.cpp:661 +msgid "ADDZONE zone.name" +msgstr "ADDSERVER zona.nome" + +#: modules/commands/cs_akick.cpp:38 +#, c-format +msgid "AKICK ENFORCE for %s complete; %d users were affected." +msgstr "AKICK ENFORCE su %s completato, ne sono stati influenzati %d utenti." + +#: modules/commands/os_chankill.cpp:21 +msgid "AKILL all users on a specific channel" +msgstr "AKILL pert tutti gli utenti presenti in un canale specifico" + +#: modules/commands/os_akill.cpp:222 modules/commands/os_akill.cpp:339 +#: modules/commands/os_akill.cpp:353 +msgid "AKILL list is empty." +msgstr "La lista AKILL è vuota." + +#: modules/commands/bs_kick.cpp:1211 modules/commands/bs_kick.cpp:1213 +#: modules/commands/bs_kick.cpp:1216 +msgid "AMSG kicker" +msgstr "AMSG kicker" + +#: modules/commands/ns_alist.cpp:48 +msgid "Access" +msgstr "Accesso" + +#: include/language.h:72 +msgid "Access denied." +msgstr "Accesso non consentito." + +#: modules/commands/cs_status.cpp:58 +#, c-format +msgid "Access for %s on %s:" +msgstr "Accesso per %s su %s:" + +#: include/language.h:107 +#, c-format +msgid "Access level must be between %d and %d inclusive." +msgstr "Il livello di accesso deve essere compreso tra %d e %d (inclusi)." + +#: modules/commands/cs_access.cpp:108 +msgid "Access level must be non-zero." +msgstr "Il livello di accesso deve essere diverso da zero." + +#: modules/commands/cs_access.cpp:694 +#, c-format +msgid "Access level settings for channel %s:" +msgstr "Impostazioni dei livelli di accesso del canale %s:" + +#: modules/commands/cs_access.cpp:734 +#, c-format +msgid "Access levels for %s reset to defaults." +msgstr "" +"I livelli di accesso di %s sono stati ripristinati ai valori originali." + +#: modules/commands/cs_access.cpp:439 modules/commands/ns_access.cpp:87 +#, c-format +msgid "Access list for %s:" +msgstr "Lista di accesso di %s:" + +#: modules/commands/help.cpp:166 +#, c-format +msgid "" +"Access to this command requires the permission %s to be present in your " +"opertype." +msgstr "" +"L'accesso a questo comando richiede che i permessi %s siano presenti nel tuo " +"opertype." + +#: modules/commands/ns_cert.cpp:368 modules/commands/ns_cert.cpp:392 +#: modules/commands/ns_identify.cpp:94 +#, c-format +msgid "" +"Account %s has already reached the maximum number of simultaneous logins " +"(%u)." +msgstr "" +"L'account %s ha già raggiunto il numero massimo di login simultanei (%u)." + +#: modules/commands/cs_set.cpp:683 +msgid "Activate security features" +msgstr "Attiva le funzionalità di sicurezza" + +#: modules/commands/hs_request.cpp:227 +msgid "Activate the requested vHost for the given nick." +msgstr "Attiva il vHost richiesto per il nick specificato." + +#: modules/commands/hs_on.cpp:55 +msgid "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." +msgstr "" +"Attiva il vHost attualmente assegnato al nick in uso.\n" +"Quando usi questo comando, ogni utente che effettua un\n" +"/whois su di te vedrà il vHost invece del tuo vero indirizzo IP." + +#: modules/commands/hs_on.cpp:19 +msgid "Activates your assigned vhost" +msgstr "Attiva il tuo vHost" + +#: modules/commands/os_info.cpp:243 +msgid "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." +msgstr "" +"Aggiunge o rimuove le informazioni operatore per il nick\n" +"o il canale specificato. Queste informazioni saranno mostrate\n" +"agli operatori quando viene usato il comando INFO per un nick\n" +"o per un canale." + +#: modules/commands/os_dns.cpp:515 +#, c-format +msgid "Added IP %s to %s." +msgstr "Aggiunto IP %s a %s." + +#: modules/commands/os_forbid.cpp:239 +#, c-format +msgid "Added a forbid on %s of type %s to expire on %s." +msgstr "Aggiunto un divieto su %s di tipo %s con scadenza il %s." + +#: modules/commands/os_info.cpp:164 +#, c-format +msgid "Added info to %s." +msgstr "Informazioni aggiunte a %s." + +#: modules/commands/os_news.cpp:34 +msgid "Added new logon news item." +msgstr "Aggiunta una nuova Logon News." + +#: modules/commands/os_news.cpp:44 +msgid "Added new oper news item." +msgstr "Aggiunta una nuova Oper News." + +#: modules/commands/os_news.cpp:54 +msgid "Added new random news item." +msgstr "Aggiunta una nuova Random News." + +#: modules/commands/os_dns.cpp:395 +#, c-format +msgid "Added server %s." +msgstr "Aggiunto il server %s." + +#: modules/commands/os_dns.cpp:300 +#, c-format +msgid "Added zone %s." +msgstr "Aggiunta la zona %s." + +#: modules/commands/cs_entrymsg.cpp:257 +msgid "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." +msgstr "" +"Aggiungere, eliminare, o pulire i messaggi di ingresso richiede il\n" +"permesso di SET." + +#: modules/commands/ns_register.cpp:104 +msgid "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." +msgstr "" +"Inoltre i Services Operators con permessi nickserv/confirm possono\n" +"utilizzare il nick di un utente anziché il passcode per forzarne la " +"validazione." + +#: modules/pseudoclients/botserv.cpp:172 +#, c-format +msgid "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" +msgstr "" +"Inoltre, se fantasy è abilitato i comandi fantasia\n" +"possono essere eseguiti aggiungendo al nome del comando\n" +"uno dei seguenti caratteri come prefisso: %s" + +#: modules/commands/os_noop.cpp:58 +#, c-format +msgid "All O:lines of %s have been reset." +msgstr "Tutte le O:lines di %s sono state ripristinate." + +#: modules/commands/cs_clone.cpp:71 +#, c-format +msgid "All akick entries from %s have been cloned to %s." +msgstr "Tutte le voci akick impostate su %s sono state clonate su %s." + +#: modules/commands/help.cpp:57 +#, c-format +msgid "All available commands for %s:" +msgstr "Tutti i comandi disponibili per %s:" + +#: modules/commands/cs_clone.cpp:96 +#, c-format +msgid "All badword entries from %s have been cloned to %s." +msgstr "Tutte le parolacce impostate su %s sono state clonate su %s." + +#: modules/commands/cs_clone.cpp:108 +#, c-format +msgid "All level entries from %s have been cloned into %s." +msgstr "Tutte le voci akick impostate su %s sono state clonate su %s." + +#: modules/commands/os_news.cpp:38 +msgid "All logon news items deleted." +msgstr "Tutte le Logon News sono state eliminate." + +#: modules/commands/ms_del.cpp:115 +#, c-format +msgid "All memos for channel %s have been deleted." +msgstr "Tutti i memo per il canale %s sono stati cancellati." + +#: modules/commands/os_mode.cpp:61 +#, c-format +msgid "All modes cleared on %s." +msgstr "Tutti i modi sono stati rimossi su %s." + +#: modules/commands/ns_register.cpp:258 modules/commands/ns_register.cpp:389 +msgid "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." +msgstr "" +"Tutti i nuovi account devono essere validati da un amministratore. Per " +"favore attendi che la tua registrazione sia confermata." + +#: modules/commands/ms_del.cpp:119 +msgid "All of your memos have been deleted." +msgstr "Tutti i tuoi memo sono stati cancellati." + +#: modules/commands/os_news.cpp:48 +msgid "All oper news items deleted." +msgstr "Tutte le Oper News sono state eliminate." + +#: modules/commands/os_noop.cpp:41 +#, c-format +msgid "All operators from %s have been removed." +msgstr "Tutte le O:lines di %s sono state rimosse." + +#: modules/commands/os_news.cpp:58 +msgid "All random news items deleted." +msgstr "Tutte le Random News sono state eliminate." + +#: modules/commands/cs_clone.cpp:211 +#, c-format +msgid "All settings from %s have been cloned to %s." +msgstr "Tutte le impostazioni di %s sono state clonate su %s." + +#: modules/commands/cs_sync.cpp:41 +#, c-format +msgid "All user modes on %s have been synced." +msgstr "Tutti gli i modi utente su %s sono stati sincronizzati." + +#: modules/commands/hs_group.cpp:60 +#, c-format +msgid "All vhosts in the group %s have been set to %s." +msgstr "Tutti i vHost nel gruppo %s sono stati impostati a %s." + +#: modules/commands/hs_group.cpp:58 +#, c-format +msgid "All vhosts in the group %s have been set to %s@%s." +msgstr "Tutti i vHost nel gruppo %s sono stati impostati a %s@%s." + +#: src/access.cpp:40 +msgid "Allowed to (de)halfop him/herself" +msgstr "Autorizzato a dare o rimuovere lo stato di halfop a se stesso" + +#: src/access.cpp:39 +msgid "Allowed to (de)halfop users" +msgstr "Autorizzato a dare o rimuovere lo stato di halfop agli utenti" + +#: src/access.cpp:48 +msgid "Allowed to (de)op him/herself" +msgstr "Autorizzato a dare o rimuovere lo stato di op a se stesso" + +#: src/access.cpp:47 +msgid "Allowed to (de)op users" +msgstr "Autorizzato a dare o rimuovere lo stato di op agli utenti" + +#: src/access.cpp:50 +msgid "Allowed to (de)owner him/herself" +msgstr "Autorizzato a dare o rimuovere lo stato di owner a se stesso" + +#: src/access.cpp:49 +msgid "Allowed to (de)owner users" +msgstr "Autorizzato a dare o rimuovere lo stato di owner agli utenti" + +#: src/access.cpp:52 +msgid "Allowed to (de)protect him/herself" +msgstr "Autorizzato a dare o rimuovere lo stato di protect a se stesso" + +#: src/access.cpp:51 +msgid "Allowed to (de)protect users" +msgstr "Autorizzato a dare o rimuovere lo stato di protect agli utenti" + +#: src/access.cpp:59 +msgid "Allowed to (de)voice him/herself" +msgstr "Autorizzato a dare o rimuovere lo stato di voice a se stesso" + +#: src/access.cpp:58 +msgid "Allowed to (de)voice users" +msgstr "Autorizzato a dare o rimuovere lo stato di voice agli utenti" + +#: src/access.cpp:27 +msgid "Allowed to assign/unassign a bot" +msgstr "Autorizzato ad assegnare/rimuovere un bot" + +#: src/access.cpp:34 +msgid "Allowed to ban users" +msgstr "Autorizzato a impostare ban sugli utenti" + +#: src/access.cpp:56 +msgid "Allowed to change channel topics" +msgstr "Autorizzato al cambio del topic del canale" + +#: src/access.cpp:41 +msgid "Allowed to get full INFO output" +msgstr "Autorizzato a ottenere l'output completo del comando INFO" + +#: src/access.cpp:36 +msgid "Allowed to issue commands restricted to channel founders" +msgstr "" +"Autorizzato ad usare comandi normalmente limitati ai founders dei canali" + +#: src/access.cpp:33 +msgid "Allowed to modify channel badwords list" +msgstr "Autorizzato alla modifica della lista delle parolacce del canale" + +#: src/access.cpp:24 +msgid "Allowed to modify the access list" +msgstr "Autorizzato alla modifica della lista di accesso" + +#: src/access.cpp:44 +msgid "Allowed to read channel memos" +msgstr "Autorizzato alla lettura dei memo del canale" + +#: src/access.cpp:54 +msgid "Allowed to set channel settings" +msgstr "Autorizzato ad impostare i impostazioni del canale" + +#: src/access.cpp:57 +msgid "Allowed to unban users" +msgstr "Autorizzato a rimuovere i ban sugli utenti" + +#: src/access.cpp:37 +msgid "Allowed to use GETKEY command" +msgstr "Autorizzato ad usare il comando GETKEY" + +#: src/access.cpp:53 +msgid "Allowed to use SAY and ACT commands" +msgstr "Autorizzato ad usare i comandi SAY e ACT" + +#: src/access.cpp:35 +msgid "Allowed to use fantasy commands" +msgstr "Autorizzato ad usare i comandi fantasy" + +#: src/access.cpp:26 +msgid "Allowed to use the AKICK command" +msgstr "Autorizzato ad usare il comando AKICK" + +#: src/access.cpp:42 +msgid "Allowed to use the INVITE command" +msgstr "Autorizzato ad usare il comando INVITE" + +#: src/access.cpp:43 +msgid "Allowed to use the KICK command" +msgstr "Autorizzato ad usare il comando KICK" + +#: src/access.cpp:45 +msgid "Allowed to use the MODE command" +msgstr "Autorizzato ad usare il comando MODE" + +#: src/access.cpp:25 +msgid "Allowed to view the access list" +msgstr "Autorizzato alla visualizzazione della lista di accesso" + +#: modules/commands/gl_global.cpp:42 +#, c-format +msgid "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." +msgstr "" +"Permette agli Amministratori di inviare un messaggio a tutti\n" +"gli utenti della rete. Il messaggio sarà inviato dal nick %s." + +#: modules/commands/os_mode.cpp:133 +msgid "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." +msgstr "" +"Permette ai Services operator di impostare i modi per qualsiasi canale.\n" +"I parametri sono gli stessi utilizzati con il comando /MODE standard.\n" +"In alternativa, CLEAR può essere usato pre rimuovere tutti i modi nel " +"canale.\n" +"Se viene usato CLEAR ALL, tutti i modi, compresi lo stato degli utenti, " +"vengono rimossi." + +#: modules/commands/os_mode.cpp:173 +msgid "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." +msgstr "" +"Permette ai Services Operator di impostare modi per qualsiasi user.\n" +"I parametri sono gli stessi utilizzati con il comando /MODE standard." + +#: modules/commands/bs_bot.cpp:352 +msgid "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." +msgstr "" +"Permette ai Services Operator di creare, modificare\n" +"ed eliminare i bot che potranno essere usati\n" +"dagli utenti nei loro canali.\n" +" \n" +"Il comando BOT ADD aggiunge un bot con il nick, l'ident,\n" +"l'host e il realname specificati. Poiché non viene effettuato\n" +"nessun controllo sui valori indicati, è necessario inviare\n" +"il comando con attenzione.\n" +" \n" +"Il comando BOT CHANGE permette di cambiare il nick,\n" +"l'ident, l'host e il realname del bot specificato, senza\n" +"cancellarlo realmente (e senza perderne i dati associati).\n" +" \n" +"Il comando BOT DEL rimuove il bot indicato dalla lista dei\n" +"bot disponibili.\n" +" \n" +"Nota: se crei un bot con un nick che è già registrato,\n" +"il nick sarà deregistrato, inoltre, se un utente lo sta\n" +"usando, verrà killato." + +#: modules/commands/os_oline.cpp:56 +msgid "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." +msgstr "" +"Permette ai Services Operators di impostare le Operflag\n" +"per qualsiasi utente. Le flag devono essere introdotte\n" +"da \"+\" o \"-\". Per rimuovere tutte le flag, è sufficiente\n" +"usare \"-\" senza altri parametri." + +#: modules/commands/os_ignore.cpp:370 +msgid "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." +msgstr "" +"Permette ai Services Operators di fare ingorare ai Services un nick o una " +"mask\n" +"per un certo periodo di tempo fino al prossimo riavvio. Il formato\n" +"predefinito del tempo è in secondi. Puoi specificarlo usando le unità.\n" +"Le unità valide sono: s per i secondi, m per i minuti, \n" +"h per le ore e d per i giorni. \n" +"La combinazione di queste unità non è permessa. Per fare\n" +"ingorare ai Services un utento in modo permanente, usa 0 come tempo.\n" +"Quando viene aggiunta una mask, deve essere nel formato user@host\n" +"o nick!user@host, ogni altro formato sarà considerato un nick.\n" +"l'uso di Wildcards è permesso.\n" +"\n" +"Gli Ignore non saranno forzati sugli IRC Operators." + +#: modules/commands/os_akill.cpp:420 +msgid "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Permette ai Services operator di manipolare la lista AKILL.\n" +"Se un utente che si trova nella lista AKILL cerca di connettersi,\n" +"i Services invieranno un KILL per quell'utente e, se supportato,\n" +"indicheranno a tutti i server di aggiugnere una K:line per la\n" +"mask che corrispondeva all'utente.\n" +" \n" +"AKILL ADD aggiunge la mask user@host specificata alla lista\n" +"AKILL per il motivo specificato (che deve essere indicato).\n" +"durata è specificato come un intero seguito da una lettera,\n" +"che può essere d (giorni), h (ore), o m (minuti). Le\n" +"combinazioni (ad esempio 1h30m) non sono permesse. Se non\n" +"viene specificata una unità, il valore viene inteso in giorni\n" +"(quindi +30 significa 30 giorni). Per aggiungere una AKILL\n" +"senza scadenza, bisogna usare +0. Se la usermask indicata\n" +"inizia con un +, la durata deve essere indicata esplicitamente,\n" +"anche se è la stessa di default. La durata di default per le\n" +"AKILL può essere trovata con il comando STATS AKILL." + +#: modules/commands/os_sxline.cpp:436 +msgid "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." +msgstr "" +"Permette ai Services Operators di manipolare la lista delle SNLINE. Se\n" +"un utente con un realname corrispondente una mask in SNLINE prova a\n" +"connettersi, i Services non gli permetteranno di proseguire\n" +"la sua session IRC." + +#: modules/commands/os_sxline.cpp:670 +msgid "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." +msgstr "" +"Permette ai Services Operators di manipolare la lista delle SQLINE. Se\n" +"un utente con un nick corrispondente una mask in SQLINE prova a\n" +"connettersi, i Services non gli permetteranno di proseguire\n" +"la sua session IRC.\n" +"Se il primo carattere della mask è #, i services\n" +"impediranno l'uso dei canali corrispondenti." + +#: modules/commands/os_session.cpp:551 +msgid "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." +msgstr "" +"Permette ai Services Operators di manipolare la lista degli host\n" +"che hanno limiti di sessione specifici, in modo da permettere\n" +"ad alcune macchine, come ad esempio ai server di shell, di\n" +"avere un numero di client maggiore di quello di default.\n" +"Quando un host raggiunge il suo limite di sessioni, tutti i\n" +"client che cercano di connettersi da quell'host verranno\n" +"disconnessi (killati). Prima che gli utenti vengano killati,\n" +"ricevono notifica relativa al supporto e le informazioni relative\n" +"al limite delle sessioni. Il contenuto di questo notice è impostabile\n" +"nel file di configurazione dei services." + +#: modules/commands/os_session.cpp:270 +msgid "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." +msgstr "" +"Permette ai Services Operators di visualizzare la lista delle sessioni.\n" +" \n" +"SESSION LIST mostra gli host con almeno una soglia sessioni.\n" +"La soglia deve essere un numero maggiore di 1, in modo da evitare\n" +"la visualizzazione accidentale di un gran numero di host con una\n" +"sola sessione.\n" +" \n" +"SESSION VIEW mostra informazioni dettagliate su un host specifico,\n" +"incluso il conteggio attuale delle sessioni e del limite delle stesse.\n" +"Il valore host non può includere wildcards.\n" +" \n" +"Guarda l'help del comando EXCEPTION per maggiori informazioni\n" +"sulla limitazione delle sessioni e come configurare limiti specifici\n" +"per determinati host o gruppi di host." + +#: modules/commands/cs_topic.cpp:193 +msgid "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do " +"not have\n" +"the TOPIC privilege." +msgstr "" +"Permette la modifica del topic del canale specificato.\n" +"Il comando SET cambia il topic del canale al topic specificato\n" +"o rimuove il topic se nessun topic viene specificato. Il comando APPEND\n" +"accoda il topic specificato al topic esistente.\n" +" \n" +"LOCK e UNLOCK possono essere usati per abilitare e disabilitare il blocco " +"del topic.\n" +"Quando il blocco del topic è impostato, il topic del canale non è " +"modificabile se non tramite questo comando." + +#: modules/commands/os_kick.cpp:62 +#, c-format +msgid "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" +msgstr "" +"Permette agli IRCOp di kickare un utente da qualsiasi\n" +"canale. I parametri sono gli stessi del comando /KICK\n" +"standard. Il messaggio di kick conterrà all'inizio il\n" +"il nick dell'IRCOp che invia il comando, ad esempio:\n" +" \n" +"*** Spammer è stato cacciato dal canale #canale da %s (Nick-Operatore " +"(motivo))" + +#: modules/commands/cs_set.cpp:33 +msgid "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" +msgstr "" +"Permette al founder di un canale di impostare varie\n" +"opzioni e informazioni del canale stesso.\n" +" \n" +"Opzioni disponibili:" + +#: modules/commands/os_oper.cpp:250 +msgid "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." +msgstr "" +"Permette di cambiare e di vedere i Services Operators.\n" +"Nota che gli operatori rimossi utilizzando questo comando ma ancora " +"presenti\n" +"nel file di configurazione non sono rimossi in modo permanete da questa " +"azione." + +#: modules/commands/os_config.cpp:127 +msgid "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" +msgstr "" +"Permette di cambiare e vedere le impostazioni di configurazione.\n" +"Le impostazioni cambiate tramite questo comando sono temporanee e non hanno\n" +"effetto sul file di configurazione, saranno perdute se i Services vengono " +"arrestati,\n" +"riavviati, oppure viene usato il comando RELOAD.\n" +" \n" +"Esempio:\n" +" MODIFY nickserv forcemail no" + +#: modules/commands/ns_set.cpp:992 +msgid "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." +msgstr "" +"Permette di scegliere il modo in cui i Services comunicano\n" +"con il nick fornito. Se MSG è attivo, i Services usano i messaggi (query),\n" +"altrimenti usano i notices." + +#: modules/commands/ns_set.cpp:966 +#, c-format +msgid "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." +msgstr "" +"Ti permette di scegliere il modo in cui i Services comunicano\n" +"con te. Se %s è attivo, i Services usano i messaggi (query),\n" +"altrimenti usano i notices." + +#: modules/commands/ms_ignore.cpp:113 +msgid "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." +msgstr "" +"Ti permette di ignorare utenti per nick o host dalla ricezione di memo\n" +"a te stesso o ad un canale. Se qualcuno presente nella lista ignore dei memo " +"prova\n" +"ad inviati un memo o ad inviarlo al canale, non riceverà notifica\n" +"che lo hai ignorato." + +#: modules/commands/os_kill.cpp:48 +msgid "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." +msgstr "" +"Permette di killare un utente dal network.\n" +"I parametri sono gli stessi usati per il comando\n" +"standard /KILL." + +#: modules/commands/ns_info.cpp:252 +#, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Ti permette di nascondere alcune informazioni quando qualcuno\n" +"effettua un %s INFO sul nick. Puoi nascondere l'indirizzo\n" +"e-mail (EMAIL), l'ultima hostmask di accesso (USERMASK)\n" +"lo stato di accesso ai services (STATUS) e l'ultimo\n" +"messaggio di quit (QUIT). Il secondo parametro\n" +"specifica se l'informazione indicata debba essere\n" +"mostrata (OFF) o nascosta (ON)." + +#: modules/commands/ns_info.cpp:223 +#, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Ti permette di nascondere alcune informazioni quando qualcuno\n" +"effettua un %s INFO sul tuo nick. Puoi nascondere il tuo\n" +"indirizzo e-mail (EMAIL), l'ultima hostmask di accesso\n" +"(USERMASK) il tuo stato di accesso ai services (STATUS)\n" +"e l'ultimo messaggio di quit (QUIT). Il secondo\n" +"parametro specifica se l'informazione indicata debba essere\n" +"mostrata (OFF) o nascosta (ON)." + +#: modules/commands/bs_info.cpp:118 +#, c-format +msgid "Allows you to see %s information about a channel or a bot" +msgstr "Permette di vedere le informazioni di %s su un canale o su un bot" + +#: modules/commands/bs_info.cpp:108 +#, c-format +msgid "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." +msgstr "" +"Permette di vedere le informazioni di %s relative\n" +"a un canale o a un bot. Se il parametro è un canale,\n" +"mostrerà le informazioni sui kick attivi. Se il\n" +"parametro è il nick di un bot, mostrerà le informazioni\n" +"relative alla data di creazione e al numero di canali\n" +"a cui è assegnato." + +#: modules/commands/cs_xop.cpp:567 +msgid "" +"Alternative methods of modifying channel access lists are\n" +"available. " +msgstr "" +"Sono disponibili metodi alternativi per la modifica delle\n" +"liste di accesso dei canali. " + +#: modules/commands/hs_request.cpp:191 +msgid "Approve the requested vHost of a user" +msgstr "Approva il vHost richiesto di un utente" + +#: modules/commands/ns_drop.cpp:68 +msgid "As a Services Operator, you may drop any nick." +msgstr "La deregistrazione di qualsiasi nick è limitata ai Services Operator." + +#: modules/commands/bs_assign.cpp:19 +msgid "Assigns a bot to a channel" +msgstr "Assegna un bot a un canale" + +#: modules/commands/bs_assign.cpp:78 +msgid "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." +msgstr "" +"Assegna il bot con il nick specificato al canale\n" +"indicato. Dopo averlo assegnato, il bot può essere\n" +"configurato in base alle necessità." + +#: data/chanserv.example.conf:1197 +msgid "Associate a URL with the channel" +msgstr "Associa un URL al canale" + +#: data/nickserv.example.conf:594 +msgid "Associate a URL with this account" +msgstr "Associa un URL con questo account" + +#: data/nickserv.example.conf:593 +msgid "Associate a URL with your account" +msgstr "Associa un URL con il tuo account" + +#: modules/commands/greet.cpp:83 +msgid "Associate a greet message with your nickname" +msgstr "Associa un messaggio di saluto al tuo nickname" + +#: data/chanserv.example.conf:1198 +msgid "Associate an E-mail address with the channel" +msgstr "Associa un indirizzo e-mail al canale" + +#: modules/commands/ns_set.cpp:452 +msgid "Associate an E-mail address with your nickname" +msgstr "Associa un indirizzo e-mail al tuo nick" + +#: modules/commands/os_info.cpp:101 +msgid "Associate oper info with a nick or channel" +msgstr "Associa oper info a un nick o un canale" + +#: modules/commands/ns_set.cpp:558 +msgid "Associates the given E-mail address with the nickname." +msgstr "Associa un indirizzo e-mail al nickname." + +#: modules/commands/ns_set.cpp:533 +msgid "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." +msgstr "" +"Associa l'indirizzo e-mail specificato al proprio nick.\n" +"Questo indirizzo sarà mostrato quando qualcuno richiede\n" +"informazioni sul proprio nick con il comando INFO." + +#: modules/commands/ns_set.cpp:1315 +msgid "Auto-op" +msgstr "Auto-op" + +#: modules/commands/cs_akick.cpp:374 +#, c-format +msgid "Autokick list for %s:" +msgstr "Lista autokick di %s:" + +#: src/access.cpp:29 +msgid "Automatic channel operator status upon join" +msgstr "Stato di op automatico al momento del join" + +#: src/access.cpp:28 +msgid "Automatic halfop upon join" +msgstr "Stato di halfop automatico al momento del join" + +#: src/access.cpp:30 +msgid "Automatic owner upon join" +msgstr "Stato di owner automatico al momento del join" + +#: src/access.cpp:31 +msgid "Automatic protect upon join" +msgstr "Stato di protect automatico al momento del join" + +#: src/access.cpp:32 +msgid "Automatic voice on join" +msgstr "Stato di voice automatico al momento del join" + +#: modules/commands/os_oper.cpp:196 +#, c-format +msgid "Available commands for %s:" +msgstr "Comandi disponibili per %s:" + +#: modules/commands/os_oper.cpp:175 +msgid "Available opertypes:" +msgstr "Tipologie di oper disponibili:" + +#: modules/commands/os_oper.cpp:218 +#, c-format +msgid "Available privileges for %s:" +msgstr "Privilegi disponibili per %s:" + +#: modules/commands/cs_enforce.cpp:162 +msgid "BANS enforced by " +msgstr "BAN forzati da " + +#: modules/commands/bs_kick.cpp:1121 modules/commands/bs_kick.cpp:1123 +#: modules/commands/bs_kick.cpp:1126 +msgid "Bad words kicker" +msgstr "Kick in caso di parolacce" + +#: modules/commands/bs_badwords.cpp:252 +#, c-format +msgid "Bad words list for %s:" +msgstr "Lista parolacce per %s:" + +#: modules/commands/bs_badwords.cpp:364 +msgid "Bad words list is now empty." +msgstr "La lista delle parolacce è stata svuotata." + +#: modules/commands/bs_set.cpp:129 +msgid "Ban expiry may not be longer than 1 day." +msgstr "La scadenza dei ban non può essere superiore a 1 giorno." + +#: modules/commands/cs_ban.cpp:140 modules/commands/cs_ban.cpp:175 +#, c-format +msgid "Ban on %s expires in %s." +msgstr "Il ban su %s scadrà in %s." + +#: modules/commands/cs_info.cpp:60 +msgid "Ban type" +msgstr "Tipo di Ban" + +#: modules/commands/cs_set.cpp:174 +#, c-format +msgid "Ban type for channel %s is now #%d." +msgstr "Il tipo di ban del canale %s ora è #%d." + +#: modules/commands/cs_ban.cpp:39 +msgid "Bans a given nick or mask on a channel" +msgstr "Imposta un ban su un nick o una mask nel canale" + +#: modules/commands/cs_ban.cpp:227 +msgid "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." +msgstr "" +"Banna (non permette l'accesso) il nick specificato o la mask nel\n" +"canale. Opzionalmente può essere impostata una scadenza per\n" +"rimuovere il ban dopo il lasso di tempo impostato.\n" +" \n" +"Di default, il comando è limitato agli AOP o agli utenti con\n" +"livello di accesso 5 o superiori al canale. I founders dei canali\n" +"possono bannare le mask." + +#: modules/commands/cs_enforce.cpp:166 +#, c-format +msgid "Bans enforced on %s." +msgstr "Bans forzati su %s." + +#: modules/commands/bs_kick.cpp:1131 modules/commands/bs_kick.cpp:1133 +#: modules/commands/bs_kick.cpp:1136 +msgid "Bolds kicker" +msgstr "Kick in caso di grassetto" + +#: modules/commands/bs_bot.cpp:26 modules/commands/bs_bot.cpp:175 +#, c-format +msgid "Bot %s already exists." +msgstr "Il bot %s è già esistente." + +#: include/language.h:119 +#, c-format +msgid "Bot %s does not exist." +msgstr "Il bot %s non esiste." + +#: modules/commands/bs_assign.cpp:71 modules/commands/bs_assign.cpp:246 +#, c-format +msgid "Bot %s has been assigned to %s." +msgstr "Il bot %s è stato assegnato a %s." + +#: modules/commands/bs_bot.cpp:228 +#, c-format +msgid "Bot %s has been changed to %s!%s@%s (%s)." +msgstr "Il bot %s è stato modificato, ora si presenta come %s!%s@%s (%s)" + +#: modules/commands/bs_bot.cpp:262 +#, c-format +msgid "Bot %s has been deleted." +msgstr "Il bot %s è stato eliminato." + +#: modules/commands/bs_assign.cpp:63 modules/commands/bs_assign.cpp:241 +#, c-format +msgid "Bot %s is already assigned to channel %s." +msgstr "Il bot %s è già assegnato al canale %s." + +#: modules/commands/bs_kick.cpp:832 +#, c-format +msgid "Bot will kick ops on channel %s." +msgstr "Il bot kickerà anche gli operatori sul canale %s." + +#: modules/commands/bs_kick.cpp:897 +#, c-format +msgid "Bot will kick voices on channel %s." +msgstr "Il bot kickerà anche i voice sul canale %s." + +#: modules/commands/bs_kick.cpp:824 +#, c-format +msgid "Bot won't kick ops on channel %s." +msgstr "Il bot non kickerà gli operatori sul canale %s." + +#: modules/commands/bs_kick.cpp:889 +#, c-format +msgid "Bot won't kick voices on channel %s." +msgstr "Il bot non kickerà i voice sul canale %s." + +#: modules/commands/bs_bot.cpp:118 +#, c-format +msgid "Bot %s is not changeable." +msgstr "Il bot %s non è modificabile." + +#: modules/commands/bs_bot.cpp:254 +#, c-format +msgid "Bot %s is not deletable." +msgstr "Il bot %s non è eliminabile." + +#: modules/commands/bs_set.cpp:141 +#, c-format +msgid "Bot bans will automatically expire after %s." +msgstr "I ban del bot scadranno automaticamente dopo %s." + +#: modules/commands/bs_set.cpp:139 +msgid "Bot bans will no longer automatically expire." +msgstr "I ban del bot non scadranno automaticamente." + +#: modules/commands/bs_bot.cpp:46 modules/commands/bs_bot.cpp:138 +#, c-format +msgid "Bot hosts may only be %d characters long." +msgstr "Gli host dei Bot possono contenere solamente %d caratteri." + +#: modules/commands/bs_bot.cpp:64 modules/commands/bs_bot.cpp:167 +msgid "Bot hosts may only contain valid host characters." +msgstr "Gli host dei bot possono contenere unicamente caratteri validi." + +#: modules/commands/bs_bot.cpp:40 modules/commands/bs_bot.cpp:132 +#, c-format +msgid "Bot idents may only be %d characters long." +msgstr "Le ident dei Bot possono contenere solamente %d caratteri." + +#: modules/commands/bs_bot.cpp:58 modules/commands/bs_bot.cpp:161 +msgid "Bot idents may only contain valid ident characters." +msgstr "Le ident dei bot possono contenere unicamente caratteri validi." + +#: include/language.h:121 +#, c-format +msgid "Bot is not on channel %s." +msgstr "Il bot non è presente nel canale %s." + +#: modules/commands/bs_botlist.cpp:51 +msgid "Bot list:" +msgstr "Lista dei bot disponibili:" + +#: modules/commands/bs_info.cpp:87 +msgid "Bot nick" +msgstr "Bot nick" + +#: modules/commands/bs_bot.cpp:34 modules/commands/bs_bot.cpp:126 +#, c-format +msgid "Bot nicks may only be %d characters long." +msgstr "I nick dei Bot possono contenere solamente %d caratteri." + +#: modules/commands/bs_bot.cpp:52 modules/commands/bs_bot.cpp:155 +msgid "Bot nicks may only contain valid nick characters." +msgstr "I nick dei bot possono contenere unicamente caratteri validi." + +#: modules/commands/bs_kick.cpp:225 +#, c-format +msgid "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." +msgstr "" +"Il bot adesso kickerà per %s, e imposterà un ban\n" +"dopo %d kick nei confronti dello stesso utente.." + +#: modules/commands/bs_kick.cpp:228 +#, c-format +msgid "Bot will now kick for %s." +msgstr "Il bot ora kickerà per %s." + +#: modules/commands/bs_kick.cpp:416 +#, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." +msgstr "" +"Il bot ora kickerà chi usa le maiuscole (devono costituire almeno\n" +"%d caratteri e il %d%% dell'intero messaggio), e imposterà un ban\n" +"dopo %d kick nei confronti dello stesso utente." + +#: modules/commands/bs_kick.cpp:420 +#, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." +msgstr "" +"Il bot ora kickerà chi usa le maiuscole (devono costituire almeno\n" +"%d caratteri e il %d%% dell'intero messaggio)." + +#: modules/commands/bs_kick.cpp:551 +#, c-format +msgid "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." +msgstr "" +"Il bot ora kickerà chi flooda (%d linee in %d secondi), e\n" +"imposterà un ban dopo %d kick nei confronti dello stesso utente." + +#: modules/commands/bs_kick.cpp:554 +#, c-format +msgid "Bot will now kick for flood (%d lines in %d seconds)." +msgstr "Il bot ora kickerà chi flooda (%d linee in %d secondi)." + +#: modules/commands/bs_kick.cpp:677 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Il bot ora kickerà chi ripete (gli utenti che ripetono %d\n" +"volte la stessa cosa), e imposterà un ban dopo %d kick\n" +"nei confronti dello stesso utente." + +#: modules/commands/bs_kick.cpp:687 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." +msgstr "" +"Il bot ora kickerà chi ripete (gli utenti che ripetono %d\n" +"volte la stessa cosa)." + +#: modules/commands/bs_kick.cpp:673 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Il bot ora kickerà chi ripete (gli utenti che ripetono %d\n" +"volte la stessa cosa), e imposterà un ban dopo %d kick\n" +"nei confronti dello stesso utente." + +#: modules/commands/bs_kick.cpp:684 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." +msgstr "" +"Il bot ora kickerà chi ripete (gli utenti che ripetono %d\n" +"volte la stessa cosa)." + +#: modules/commands/bs_kick.cpp:239 +#, c-format +msgid "Bot won't kick for %s anymore." +msgstr "Il bot non kickerà più per %s." + +#: modules/commands/bs_kick.cpp:426 +msgid "Bot won't kick for caps anymore." +msgstr "Il bot non kickerà più chi usa le maiuscole." + +#: modules/commands/bs_kick.cpp:559 +msgid "Bot won't kick for flood anymore." +msgstr "Il bot non kickerà più chi flooda." + +#: modules/commands/bs_kick.cpp:694 +msgid "Bot won't kick for repeats anymore." +msgstr "Il bot non kickerà più chi ripete." + +#: modules/commands/cs_access.cpp:472 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_session.cpp:514 +msgid "By" +msgstr "Da" + +#: modules/commands/os_info.cpp:104 +msgid "CLEAR target" +msgstr "CLEAR target" + +#: modules/commands/cs_seen.cpp:119 +msgid "CLEAR time" +msgstr "CLEAR tempo" + +#: modules/commands/ms_cancel.cpp:19 +msgid "Cancel the last memo you sent" +msgstr "Annulla l'ultimo memo inviato" + +#: modules/commands/cs_drop.cpp:19 +msgid "Cancel the registration of a channel" +msgstr "Annulla la registrazione di un canale" + +#: modules/commands/ns_drop.cpp:20 +msgid "Cancel the registration of a nickname" +msgstr "Annulla la registrazione del nick" + +#: modules/commands/ms_cancel.cpp:84 +msgid "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." +msgstr "" +"Annulla l'ultimo memo inviato al nick o al canale specificato,\n" +"sempre che non sia già stato letto prima dell'uso di questo\n" +"comando." + +#: modules/commands/cs_clone.cpp:149 +#, c-format +msgid "Cannot clone channel %s to itself!" +msgstr "Non puoi clonare il canale %s su sé stesso!" + +#: modules/commands/ns_register.cpp:332 +msgid "Cannot send mail now; please retry a little later." +msgstr "Impossibile inviare e-mail adesso, riprova più tardi." + +#: modules/commands/bs_kick.cpp:1141 modules/commands/bs_kick.cpp:1143 +#: modules/commands/bs_kick.cpp:1146 +msgid "Caps kicker" +msgstr "Kick in caso di maiuscole" + +#: modules/commands/os_shutdown.cpp:34 +msgid "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." +msgstr "" +"Termina immediatamente i Services senza salvarne i\n" +"database. Questo comando non deve mai essere usato,\n" +"se non in caso di danni alla copia in memoria dei\n" +"database, per evitare che la copia danneggiata venga\n" +"salvata." + +#: modules/commands/os_reload.cpp:47 +msgid "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." +msgstr "" +"Rilegge il file di configurazione dei Services. Alcune\n" +"impostazioni contenute nel file richiedono il riavvio\n" +"effettivo dei Services per essere attivate (ad esempio\n" +"il cambio dei nick dei Services, l'attivazione della\n" +"limitazione delle sessioni, eccetera)." + +#: modules/commands/os_shutdown.cpp:62 +msgid "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." +msgstr "Salva i database su disco e riavvia i Services." + +#: modules/commands/os_shutdown.cpp:89 +msgid "Causes Services to save all databases and then shut down." +msgstr "Salva i database su disco e termina i Services." + +#: modules/commands/os_update.cpp:34 +msgid "" +"Causes Services to update all database files as soon as you\n" +"send the command." +msgstr "" +"Forza la scrittura su disco immediata dei database dei\n" +"Services nello stesso istante in cui il comando viene\n" +"inviato." + +#: modules/commands/ns_cert.cpp:246 +#, c-format +msgid "Certificate list for %s:" +msgstr "Lista dei certificati di %s:" + +#: modules/commands/cs_set.cpp:528 modules/commands/cs_set.cpp:570 +msgid "ChanServ is required to enable persist on this network." +msgstr "ChanServ è richiesto per abilitare la persistenza su questo network." + +#: modules/commands/os_mode.cpp:19 +msgid "Change channel modes" +msgstr "Cambia i modi del canale" + +#: modules/commands/ns_set.cpp:905 +msgid "Change the communication method of Services" +msgstr "Cambia il metodo di comunicazione usato dai Services" + +#: modules/commands/os_mode.cpp:146 +msgid "Change user modes" +msgstr "Cambia i modi utente" + +#: modules/commands/os_mode.cpp:161 +#, c-format +msgid "Changed usermodes of %s to %s." +msgstr "Modi utente di %s modificati in %s." + +#: modules/commands/ns_set.cpp:411 +msgid "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." +msgstr "" +"Imposta il nome con cui i Services fanno riferimento al tuo\n" +"gruppo. Il nuovo nome DEVE essere un nick del gruppo." + +#: modules/commands/ns_set.cpp:387 +msgid "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." +msgstr "" +"Imposta il nome con cui i Services si riferiscono al tuo\n" +"gruppo. Il nuovo nome DEVE essere un nick del gruppo." + +#: modules/commands/cs_set.cpp:324 +msgid "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." +msgstr "" +"Imposta il nuovo founder del canale. Il nick specificato\n" +"deve essere registrato." + +#: modules/commands/ns_set.cpp:884 +msgid "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Cambia la lingua utilizzata dai Services per inviarti\n" +"i messaggi, ad esempio per rispondere a un comando che\n" +"tu invii.\n" +"La lingua può essere scelta dalla seguente lista di\n" +"lingue supportate:" + +#: modules/commands/ns_set.cpp:848 +msgid "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Cambia la lingua utilizzata dai Services per inviarti\n" +"i messaggi, ad esempio per rispondere a un comando che\n" +"tu invii.\n" +"La lingua può essere scelta dalla seguente lista di\n" +"lingue supportate:" + +#: modules/commands/ns_set.cpp:227 +msgid "Changes the password used to identify as the nick's owner." +msgstr "" +"Cambia la password utilizzata per identificarti come\n" +"proprietario del nick." + +#: modules/commands/ns_set.cpp:161 +msgid "" +"Changes the password used to identify you as the nick's\n" +"owner." +msgstr "" +"Cambia la password utilizzata per identificarti come\n" +"proprietario del nick." + +#: modules/commands/cs_set.cpp:1017 +#, fuzzy +msgid "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." +msgstr "" +"Imposta il successore del founder del canale. Se il nick\n" +"del founder scade, o viene deregistrato mentre il canale\n" +"è ancora registrato, il successore diventerà il nuovo\n" +"founder del canale. Il nick specificato deve essere registrato." + +#: modules/commands/ns_alist.cpp:48 modules/commands/ns_ajoin.cpp:100 +msgid "Channel" +msgstr "Canale" + +#: include/language.h:84 +#, c-format +msgid "Channel %s doesn't exist." +msgstr "Il canale %s non esiste." + +#: modules/commands/cs_drop.cpp:63 +#, c-format +msgid "Channel %s has been dropped." +msgstr "Il canale %s è stato deregistrato." + +#: modules/commands/cs_getkey.cpp:43 +#, c-format +msgid "Channel %s has no key." +msgstr "Il canale %s non ha una chiave." + +#: modules/commands/cs_register.cpp:47 +#, c-format +msgid "Channel %s is already registered!" +msgstr "Il canale %s è già registrato!" + +#: modules/commands/os_forbid.cpp:524 +#, c-format +msgid "Channel %s is forbidden by %s: %s" +msgstr "Il canale %s è stato vietato da %s: %s" + +#: modules/commands/os_forbid.cpp:526 +#, c-format +msgid "Channel %s is forbidden." +msgstr "Il canale %s è vietato." + +#: modules/commands/cs_set.cpp:580 +#, c-format +msgid "Channel %s is no longer persistent." +msgstr "Il canale %s non è più persistente." + +#: modules/commands/cs_set.cpp:542 +#, c-format +msgid "Channel %s is now persistent." +msgstr "Il canale %s è adesso persistente." + +#: modules/commands/cs_suspend.cpp:180 +#, c-format +msgid "Channel %s is now released." +msgstr "Il canale %s ora è stato rilasciato." + +#: modules/commands/cs_suspend.cpp:125 +#, c-format +msgid "Channel %s is now suspended." +msgstr "Il canale %s è ora sospeso." + +#: include/language.h:83 +#, c-format +msgid "Channel %s isn't registered." +msgstr "Il canale %s non è registrato." + +#: modules/commands/cs_suspend.cpp:172 +#, c-format +msgid "Channel %s isn't suspended." +msgstr "Il canale %s non è sospeso." + +#: modules/commands/cs_register.cpp:68 +#, c-format +msgid "Channel %s registered under your account: %s" +msgstr "Il canale %s è stato registrato sotto il tuo account: %s" + +#: modules/commands/cs_set.cpp:1078 +#, c-format +msgid "Channel %s will expire." +msgstr "Il canale %s scadrà." + +#: modules/commands/cs_set.cpp:1072 +#, c-format +msgid "Channel %s will not expire." +msgstr "Il canale %s non scadrà." + +#: modules/commands/cs_xop.cpp:475 +#, c-format +msgid "Channel %s %s list has been cleared." +msgstr "La lista %2$s del canale %1$s è stata svuotata." + +#: modules/commands/cs_access.cpp:486 modules/commands/cs_flags.cpp:361 +#, c-format +msgid "Channel %s access list has been cleared." +msgstr "La lista di accesso del canale %s è stata svuotata." + +#: modules/commands/cs_akick.cpp:428 +#, c-format +msgid "Channel %s akick list has been cleared." +msgstr "La lista autokick del canale %s è stata svuotata." + +#: modules/commands/cs_mode.cpp:444 +#, c-format +msgid "Channel %s has no mode locks." +msgstr "Il canale %s non ha modi bloccati." + +#: include/language.h:82 +#, c-format +msgid "Channel %s is currently suspended." +msgstr "Il canale %s è attualmente sospeso." + +#: include/language.h:101 +#, c-format +msgid "Channel %s is not a valid channel." +msgstr "Il canale %s non è un canale valido." + +#: modules/commands/os_list.cpp:70 +msgid "Channel list:" +msgstr "Lista Canali:" + +#: modules/extra/stats/cs_fantasy_stats.cpp:148 +#, c-format +msgid "Channel stats for %s on %s:" +msgstr "Statistiche del canale per %s su %s:" + +#: modules/commands/cs_access.cpp:142 modules/commands/cs_flags.cpp:97 +#: modules/commands/cs_xop.cpp:139 +msgid "Channels may not be on access lists." +msgstr "I canali possono non essere nelle liste di accesso." + +#: modules/commands/ns_alist.cpp:114 +#, c-format +msgid "Channels that %s has access on:" +msgstr "Canali su cui %s ha accesso:" + +#: modules/commands/os_stats.cpp:181 +#, c-format +msgid "Channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "Canali: %lu voci, %lu buckets, longest chain is %d" + +#: modules/extra/stats/m_chanstats.cpp:517 +#: modules/extra/stats/m_chanstats.cpp:525 +msgid "Chanstats" +msgstr "Statistiche canale" + +#: modules/extra/stats/m_chanstats.cpp:102 +#, c-format +msgid "Chanstats statistics are now disabled for %s" +msgstr "Le statistiche di Chanstats sono ora disabilitate per %s" + +#: modules/extra/stats/m_chanstats.cpp:51 +msgid "Chanstats statistics are now disabled for this channel." +msgstr "Le statistiche di Chanstats sono state disabilitate per questo canale." + +#: modules/extra/stats/m_chanstats.cpp:104 +msgid "Chanstats statistics are now disabled for your nick." +msgstr "Le statistiche di Chanstats sono state disabilitate per il tuo nick." + +#: modules/extra/stats/m_chanstats.cpp:93 +#, c-format +msgid "Chanstats statistics are now enabled for %s" +msgstr "Le statistiche di Chanstats sono ora abilitate per %s" + +#: modules/extra/stats/m_chanstats.cpp:44 +msgid "Chanstats statistics are now enabled for this channel." +msgstr "Le statistiche di Chanstats sono state abilitate per questo canale." + +#: modules/extra/stats/m_chanstats.cpp:95 +msgid "Chanstats statistics are now enabled for your nick." +msgstr "Le statistiche di Chanstats sono state abilitate per il tuo nick." + +#: modules/commands/cs_seen.cpp:367 +msgid "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." +msgstr "" +"Controlla l'ultima volta che un nick è stato visto accedere, uscire,\n" +"o cambiare nick sul network e ti informa, in base alle impostazioni\n" +"del canale o dell'utente, dove si trovava." + +#: modules/commands/ms_check.cpp:19 +msgid "Checks if last memo to a nick was read" +msgstr "Controlla se l'ultimo memo inviato ad un nick è stato letto" + +#: modules/commands/ms_check.cpp:69 +msgid "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." +msgstr "" +"Controlla se l'_ultimo_ memo che hai inviato al nick è stato letto\n" +"oppure no. Nota che questo funziona unicamente coi nick, non coi canali." + +#: modules/commands/os_info.cpp:227 +#, c-format +msgid "Cleared info from %s." +msgstr "Info annullate da %s." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1153 +#: modules/commands/bs_kick.cpp:1156 +msgid "Colors kicker" +msgstr "Kick in caso di colori" + +#: modules/commands/cs_log.cpp:127 +msgid "Command" +msgstr "Comando" + +#: modules/commands/bs_kick.cpp:251 +msgid "Configures AMSG kicker" +msgstr "Configura i Kick in caso di AMSG" + +#: modules/commands/bs_kick.cpp:287 +msgid "Configures badwords kicker" +msgstr "Configura i Kick in caso di parolacce" + +#: modules/commands/bs_kick.cpp:326 +msgid "Configures bolds kicker" +msgstr "Configura i Kick in caso di grassetto" + +#: modules/commands/bs_kick.cpp:132 +msgid "Configures bot kickers. option can be one of:" +msgstr "Configura i kick del bot. L'opzione può essere una delle seguenti:" + +#: modules/commands/bs_set.cpp:19 +msgid "Configures bot options" +msgstr "Configura le opzioni del bot" + +#: modules/commands/bs_set.cpp:32 +msgid "" +"Configures bot options.\n" +" \n" +"Available options:" +msgstr "" +"Configura le opzioni del bot. \n" +"Opzioni disponibili:" + +#: modules/commands/bs_kick.cpp:360 +msgid "Configures caps kicker" +msgstr "Configura i kick in caso di caps" + +#: modules/commands/cs_log.cpp:105 +msgid "Configures channel logging settings" +msgstr "Configura le impostazioni di logging del canale" + +#: modules/commands/bs_kick.cpp:456 +msgid "Configures color kicker" +msgstr "Configura i kick in caso di colori" + +#: modules/commands/bs_kick.cpp:490 +msgid "Configures flood kicker" +msgstr "Configura i kick in caso di flood" + +#: modules/commands/bs_kick.cpp:588 +msgid "Configures italics kicker" +msgstr "Configura i kick in caso di italics" + +#: modules/commands/bs_kick.cpp:119 +msgid "Configures kickers" +msgstr "Configura i kick" + +#: modules/commands/bs_kick.cpp:622 +msgid "Configures repeat kicker" +msgstr "Configura i kick in caso di ripetizione" + +#: modules/commands/bs_kick.cpp:723 +msgid "Configures reverses kicker" +msgstr "Configura i kick in caso di reverse" + +#: modules/commands/bs_set.cpp:90 +msgid "Configures the time bot bans expire in" +msgstr "Imposta il tempo di scadenza dei ban impostati dal bot" + +#: modules/commands/bs_kick.cpp:757 +msgid "Configures underlines kicker" +msgstr "Configura i kick in caso di underline" + +#: modules/commands/ns_register.cpp:21 +msgid "Confirm a passcode" +msgstr "Conferma un codice di attivazione (passcode) di NickServ" + +#: modules/commands/cs_mode.cpp:733 +msgid "Control modes and mode locks on a channel" +msgstr "Controlla i modi e il blocco dei modi di un canale" + +#: modules/commands/cs_entrymsg.cpp:239 +msgid "" +"Controls what messages will be sent to users when they join the channel." +msgstr "" +"Controlla il messaggio che sarà inviato agli utenti quando accedono al " +"canale." + +#: modules/commands/cs_clone.cpp:242 +msgid "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." +msgstr "" +"Copia tutte le impostazioni, accessi, akick, etc da un canale\n" +"al canale di destinazione. Se specificato ACCESS, AKICK,\n" +"o BADWORDS solamente le rispettive impostazioni saranno clonate.\n" +"È necessario essere founder di entrambi i canali per usare\n" +"questo comando." + +#: modules/commands/cs_clone.cpp:114 +msgid "Copy all settings from one channel to another" +msgstr "Copia tutte le impostazioni da un canale ad un altro" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/bs_info.cpp:57 +#: modules/commands/os_akill.cpp:358 +msgid "Created" +msgstr "Creato" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_ignore.cpp:266 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_news.cpp:156 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_akill.cpp:358 +msgid "Creator" +msgstr "Autore" + +#: modules/commands/os_sxline.cpp:180 +#, c-format +msgid "Current %s list:" +msgstr "Lista %s attuale:" + +#: modules/commands/os_akill.cpp:323 +msgid "Current AKILL list:" +msgstr "Lista AKILL attuale:" + +#: modules/commands/os_session.cpp:493 +msgid "Current Session Limit Exception list:" +msgstr "Lista delle eccezioni attuale:" + +#: modules/commands/os_modinfo.cpp:116 +msgid "Current module list:" +msgstr "Lista moduli attuali:" + +#: modules/commands/os_stats.cpp:69 +#, c-format +msgid "Current number of AKILLs: %d" +msgstr "Numero attuale di AKILL: %d" + +#: modules/commands/os_stats.cpp:89 +#, c-format +msgid "Current number of SNLINEs: %d" +msgstr "Numero attuale di SNLINE: %d" + +#: modules/commands/os_stats.cpp:109 +#, c-format +msgid "Current number of SQLINEs: %d" +msgstr "Numero attuale di SQLINE: %d" + +#: modules/commands/os_stats.cpp:138 +#, c-format +msgid "Current users: %d (%d ops)" +msgstr "Utenti correnti: %d (%d operatori)" + +#: modules/commands/os_oper.cpp:71 +msgid "DEL oper" +msgstr "DEL oper" + +#: modules/commands/os_info.cpp:103 +msgid "DEL target info" +msgstr "DEL target info" + +#: modules/commands/ns_ajoin.cpp:232 +msgid "DEL [nickname] channel" +msgstr "DEL [nickname] canale" + +#: modules/commands/ns_cert.cpp:259 +msgid "DEL [nickname] fingerprint" +msgstr "DEL [nickname] fingerprint" + +#: modules/commands/ns_access.cpp:103 +msgid "DEL [nickname] mask" +msgstr "DEL [nickname] mask" + +#: modules/commands/os_sxline.cpp:426 modules/commands/os_sxline.cpp:660 +#: modules/commands/os_akill.cpp:387 +msgid "DEL {mask | entry-num | list | id}" +msgstr "DEL {mask | num-voce | list | id}" + +#: modules/commands/os_session.cpp:524 +msgid "DEL {mask | entry-num | list}" +msgstr "DEL {mask | num-voce | list}" + +#: modules/commands/os_ignore.cpp:343 +msgid "DEL {nick|mask}" +msgstr "DEL {nick|mask}" + +#: modules/commands/os_news.cpp:279 +msgid "DEL {num | ALL}" +msgstr "DEL {num | ALL}" + +#: modules/commands/os_forbid.cpp:158 +msgid "DEL {NICK|CHAN|EMAIL|REGISTER} entry" +msgstr "DEL {NICK|CHAN|EMAIL|REGISTER} voce" + +#: modules/commands/os_dns.cpp:666 +msgid "DELIP server.name ip" +msgstr "DELIP server.nome ip" + +#: modules/commands/os_dns.cpp:664 +msgid "DELSERVER server.name [zone.name]" +msgstr "DELSERVER server.nome [zona.nome]" + +#: modules/commands/os_dns.cpp:662 +msgid "DELZONE zone.name" +msgstr "DELZONE zona.nome" + +#: modules/commands/os_dns.cpp:669 +msgid "DEPOOL server.name" +msgstr "DEPOOL server.nome" + +#: modules/commands/cs_seen.cpp:162 +#, c-format +msgid "Database cleared, removed %lu nicks that were added after %s." +msgstr "Database pulito, rimossi %lu nicks che erano stati aggiunti dopo %s." + +#: modules/commands/ms_list.cpp:64 +msgid "Date/Time" +msgstr "Data/Ora" + +#: modules/commands/hs_off.cpp:49 +msgid "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." +msgstr "" +"Disattiva il vHost attualmente assegnato al nick in uso.\n" +"Quando usi questo comando, ogni utente che effettua un /whois\n" +"su di te vedrà il tuo vero indirizzo IP." + +#: modules/commands/hs_off.cpp:19 +msgid "Deactivates your assigned vhost" +msgstr "Disattiva il tuo vHost" + +#: modules/commands/os_stats.cpp:72 +#, c-format +msgid "Default AKILL expiry time: %d days" +msgstr "Durata di default delle AKILL: %d giorni" + +#: modules/commands/os_stats.cpp:76 +#, c-format +msgid "Default AKILL expiry time: %d hours" +msgstr "Durata di default delle AKILL: %d ore" + +#: modules/commands/os_stats.cpp:80 +#, c-format +msgid "Default AKILL expiry time: %d minutes" +msgstr "Durata di default delle AKILL: %d minuti" + +#: modules/commands/os_stats.cpp:74 +msgid "Default AKILL expiry time: 1 day" +msgstr "Durata di default delle AKILL: 1 giorno" + +#: modules/commands/os_stats.cpp:78 +msgid "Default AKILL expiry time: 1 hour" +msgstr "Durata di default delle AKILL: 1 ora" + +#: modules/commands/os_stats.cpp:82 +msgid "Default AKILL expiry time: 1 minute" +msgstr "Durata di default delle AKILL: 1 minuto" + +#: modules/commands/os_stats.cpp:84 +msgid "Default AKILL expiry time: No expiration" +msgstr "Durata di default delle AKILL: infinita" + +#: modules/commands/os_stats.cpp:92 +#, c-format +msgid "Default SNLINE expiry time: %d days" +msgstr "Durata di default delle SNLINE: %d giorni" + +#: modules/commands/os_stats.cpp:96 +#, c-format +msgid "Default SNLINE expiry time: %d hours" +msgstr "Durata di default delle SNLINE: %d ore" + +#: modules/commands/os_stats.cpp:100 +#, c-format +msgid "Default SNLINE expiry time: %d minutes" +msgstr "Durata di default delle SNLINE: %d minuti" + +#: modules/commands/os_stats.cpp:94 +msgid "Default SNLINE expiry time: 1 day" +msgstr "Durata di default delle SNLINE: 1 giorno" + +#: modules/commands/os_stats.cpp:98 +msgid "Default SNLINE expiry time: 1 hour" +msgstr "Durata di default delle SNLINE: 1 ora" + +#: modules/commands/os_stats.cpp:102 +msgid "Default SNLINE expiry time: 1 minute" +msgstr "Durata di default delle SNLINE: 1 minuto" + +#: modules/commands/os_stats.cpp:104 +msgid "Default SNLINE expiry time: No expiration" +msgstr "Durata di default delle SNLINE: infinita" + +#: modules/commands/os_stats.cpp:112 +#, c-format +msgid "Default SQLINE expiry time: %d days" +msgstr "Durata di default delle SQLINE: %d giorni" + +#: modules/commands/os_stats.cpp:116 +#, c-format +msgid "Default SQLINE expiry time: %d hours" +msgstr "Durata di default delle SQLINE: %d ore" + +#: modules/commands/os_stats.cpp:120 +#, c-format +msgid "Default SQLINE expiry time: %d minutes" +msgstr "Durata di default delle SQLINE: %d minuti" + +#: modules/commands/os_stats.cpp:114 +msgid "Default SQLINE expiry time: 1 day" +msgstr "Durata di default delle SQLINE: 1 giorno" + +#: modules/commands/os_stats.cpp:118 +msgid "Default SQLINE expiry time: 1 hour" +msgstr "Durata di default delle SQLINE: 1 ora" + +#: modules/commands/os_stats.cpp:122 +msgid "Default SQLINE expiry time: 1 minute" +msgstr "Durata di default delle SQLINE: 1 minuto" + +#: modules/commands/os_stats.cpp:124 +msgid "Default SQLINE expiry time: No expiration" +msgstr "Durata di default delle SQLINE: infinita" + +#: modules/commands/os_news.cpp:351 +msgid "Define messages to be randomly shown to users at logon" +msgstr "" +"Definisce i messaggi da mostrare in modo casuale agli utenti quando si " +"connettono" + +#: modules/commands/os_news.cpp:297 +msgid "Define messages to be shown to users at logon" +msgstr "Definisce i messaggi da mostrare agli utenti quando si connettono" + +#: modules/commands/os_news.cpp:324 +msgid "Define messages to be shown to users who oper" +msgstr "Definisce i messaggi da mostrare agli operatori" + +#: modules/commands/ms_del.cpp:44 +msgid "Delete a memo or memos" +msgstr "Cancella uno o più memo" + +#: modules/commands/hs_del.cpp:19 +msgid "Delete the vhost of another user" +msgstr "Rimuove il vHost di un altro utente" + +#: modules/commands/cs_xop.cpp:302 +#, c-format +msgid "Deleted %d entries from %s %s list." +msgstr "Eliminati %1$d record dalla lista %3$s di %2$s." + +#: modules/commands/cs_access.cpp:277 +#, c-format +msgid "Deleted %d entries from %s access list." +msgstr "Eliminati %d record dalla lista di accesso di %s." + +#: modules/commands/cs_akick.cpp:228 +#, c-format +msgid "Deleted %d entries from %s autokick list." +msgstr "Eliminati %d record dalla lista autokick di %s." + +#: modules/commands/bs_badwords.cpp:170 +#, c-format +msgid "Deleted %d entries from %s bad words list." +msgstr "Eliminati %d record dalla lista delle parolacce di %s." + +#: modules/commands/os_session.cpp:149 +#, c-format +msgid "Deleted %d entries from session-limit exception list." +msgstr "Eliminati %d record dalla lista delle eccezioni." + +#: modules/commands/os_sxline.cpp:32 +#, c-format +msgid "Deleted %d entries from the %s list." +msgstr "Eliminati %d record dalla lista %s." + +#: modules/commands/os_akill.cpp:33 +#, c-format +msgid "Deleted %d entries from the AKILL list." +msgstr "Eliminati %d record dalla lista AKILL." + +#: modules/commands/cs_access.cpp:275 +#, c-format +msgid "Deleted 1 entry from %s access list." +msgstr "Eliminato un record dalla lista di accesso di %s." + +#: modules/commands/cs_akick.cpp:226 +#, c-format +msgid "Deleted 1 entry from %s autokick list." +msgstr "Eliminato un record dalla lista autokick di %s." + +#: modules/commands/bs_badwords.cpp:168 +#, c-format +msgid "Deleted 1 entry from %s bad words list." +msgstr "Eliminato un record dalla lista delle parolacce di %s." + +#: modules/commands/os_session.cpp:147 +msgid "Deleted 1 entry from session-limit exception list." +msgstr "Eliminato 1 record dalla lista delle eccezioni." + +#: modules/commands/os_sxline.cpp:30 +#, c-format +msgid "Deleted 1 entry from the %s list." +msgstr "Eliminato 1 record dalla lista %s." + +#: modules/commands/os_akill.cpp:31 +msgid "Deleted 1 entry from the AKILL list." +msgstr "Eliminato 1 record dalla lista AKILL." + +#: modules/commands/os_info.cpp:208 +#, c-format +msgid "Deleted info from %s." +msgstr "Eliminata nformazione da %s." + +#: modules/commands/cs_xop.cpp:300 +#, c-format +msgid "Deleted one entry from %s %s list." +msgstr "Eliminato un record dalla lista %2$s di %1$s." + +#: modules/commands/ms_del.cpp:129 +msgid "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Elimina il memo o i memo specificati. Si possono indicare\n" +"numeri multipli di memo o intervalli di numeri invece di\n" +"un numero singolo, come nel secondo esempio.\n" +" \n" +"Se viene usato LAST elimina l'ultimo memo.\n" +"Se viene usato ALL elimina tutti i memo.\n" +" \n" +"Esempi:\n" +" \n" +" DEL 1\n" +" Elimina il primo memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Elimina i memo che hanno numero numeri tra 2 e 5 e\n" +" tra 7 e 9, conservando quindi il 6." + +#: modules/commands/hs_del.cpp:48 +msgid "" +"Deletes the vhost assigned to the given nick from the\n" +"database." +msgstr "Elimina dal database il vHost assegnato al nick specificato." + +#: modules/commands/hs_del.cpp:59 +msgid "Deletes the vhost for all nicks in a group" +msgstr "Rimuove il vHost da tutti i nick di un gruppo" + +#: modules/commands/hs_del.cpp:93 +msgid "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." +msgstr "" +"Rimuove il vHost da tutti i nick dello stesso gruppo del nick\n" +"specificato." + +#: modules/commands/os_dns.cpp:653 +#, c-format +msgid "Depooled %s." +msgstr "Rimosso dal pool %s." + +#: modules/commands/cs_access.cpp:799 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_list.cpp:75 modules/commands/cs_info.cpp:53 +msgid "Description" +msgstr "Descrizione" + +#: modules/commands/cs_set.cpp:239 +#, c-format +msgid "Description of %s changed to %s." +msgstr "La descrizione di %s è stata impostata a %s." + +#: modules/commands/cs_set.cpp:245 +#, c-format +msgid "Description of %s unset." +msgstr "La descrizione di %s è stata rimossa." + +#: modules/commands/bs_kick.cpp:1115 modules/commands/bs_info.cpp:90 +msgid "Disabled" +msgstr "Disattivato" + +#: modules/commands/cs_suspend.cpp:134 +msgid "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." +msgstr "" +"Impedisce chiunque di utilizzare il canale\n" +"specificato. Può essere annullato utilizzando il comando\n" +"UNSUSPEND preservando tutti i dati e le impostazioni precedenti.\n" +"Se specificata una scadenza, il canale tornerà utilizzabile\n" +"dopo quel periodo di tempo, altrimenti viene usata la\n" +"scadenza predefinita nella configurazione.\n" +" \n" +"Il motivo potrebbe essere richiesto su alcune reti." + +#: modules/commands/hs_request.cpp:337 +#, c-format +msgid "Displayed %d records (%d total)." +msgstr "Visualizzati %d records (totali: %d)" + +#: modules/commands/hs_list.cpp:122 +#, c-format +msgid "Displayed all records (count: %d)." +msgstr "Visualizzati tutti i records (Conteggio: %d)" + +#: modules/commands/hs_list.cpp:120 +#, c-format +msgid "Displayed records from %d to %d." +msgstr "Visualizzati records da %d a %d." + +#: modules/commands/hs_list.cpp:116 +#, c-format +msgid "Displayed records matching key %s (count: %d)." +msgstr "Visualizzati records corrispondenti alla chiave %s (Conteggio: %d)" + +#: modules/commands/ns_info.cpp:19 +msgid "Displays information about a given nickname" +msgstr "Mostra le informazioni su un nick" + +#: modules/commands/ns_info.cpp:125 +msgid "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." +msgstr "" +"Mostra informazioni sul nickname specificato, come ad\n" +"esempio il proprietario del nick, la data dell'ultimo\n" +"accesso, l'ultimo indirizzo utilizzato e le opzioni stesse\n" +"del nick. Se non viene specificato il nick, e sei identificato,\n" +"viene usato il tuo nome account, altrimenti sarà usato\n" +"il tuo nickname in uso." + +#: modules/commands/ms_info.cpp:19 +msgid "Displays information about your memos" +msgstr "Mostra informazioni sui tuoi memo" + +#: modules/commands/hs_list.cpp:19 +msgid "Displays one or more vhost entries" +msgstr "Mostra uno o più vHost nel database" + +#: modules/extra/stats/cs_fantasy_top.cpp:50 +msgid "Displays the top 10 users of a channel" +msgstr "Mostra i primi 10 utenti del canale" + +#: modules/extra/stats/cs_fantasy_top.cpp:73 +msgid "Displays the top 10 users of the network" +msgstr "Mostra i primi 10 utenti del network" + +#: modules/extra/stats/cs_fantasy_top.cpp:38 +msgid "Displays the top 3 users of a channel" +msgstr "Mostra i primi 3 utenti del canale" + +#: modules/extra/stats/cs_fantasy_top.cpp:62 +msgid "Displays the top 3 users of the network" +msgstr "Mostra i primi 3 utenti del network" + +#: modules/commands/help.cpp:33 +msgid "Displays this list and give information about commands" +msgstr "Mostra questa lista e dà informazioni sui comandi" + +#: modules/extra/stats/cs_fantasy_stats.cpp:39 +msgid "Displays your Channel Stats" +msgstr "Mostra le statistiche del tuo canale" + +#: modules/extra/stats/cs_fantasy_stats.cpp:51 +msgid "Displays your Global Stats" +msgstr "Mostra le tue statistiche globali" + +#: modules/commands/bs_kick.cpp:1463 +msgid "Don't use AMSGs!" +msgstr "Non usare gli AMSGs!" + +#: modules/commands/bs_kick.cpp:1266 +msgid "Don't use bolds on this channel!" +msgstr "Non usare il grassetto su questo canale!" + +#: modules/commands/bs_kick.cpp:1274 +msgid "Don't use colors on this channel!" +msgstr "Non usare i colori su questo canale!" + +#: modules/commands/bs_kick.cpp:1290 +msgid "Don't use italics on this channel!" +msgstr "Non usare il corsivo in questo canale!" + +#: modules/commands/bs_kick.cpp:1282 +msgid "Don't use reverses on this channel!" +msgstr "Non usare il reverse su questo canale!" + +#: modules/commands/bs_kick.cpp:1408 +#, c-format +msgid "Don't use the word \"%s\" on this channel!" +msgstr "Non usare la parola %s su questo canale!" + +#: modules/commands/bs_kick.cpp:1298 +msgid "Don't use underlines on this channel!" +msgstr "Non usare il sottolineato su questo canale!" + +#: modules/commands/ns_drop.cpp:61 +msgid "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." +msgstr "" +"Deregistra il nick specificato dal database. Una volta che il\n" +"tuo nickname è deregistrato potresti perdere tutti gli accessi e\n" +"i canali di cui sei founder. Qualsiasi altro utente avrà la\n" +"possibilità di avere il controllo di questo nick." + +#: modules/commands/ns_set.cpp:513 +#, c-format +msgid "E-mail address for %s changed to %s." +msgstr "Indirizzo e-mail per %s cambiato in %s." + +#: modules/commands/ns_set.cpp:519 +#, c-format +msgid "E-mail address for %s unset." +msgstr "Indirizzo e-mail per %s rimosso." + +#: src/mail.cpp:80 +#, c-format +msgid "E-mail for %s is invalid." +msgstr "L'e-mail per %s non è valida." + +#: modules/commands/os_news.cpp:309 +#, c-format +msgid "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Modifica o visualizza la lista dei messaggi di news all'accesso.\n" +"Quando gli utenti si connettono al network, riceveranno questi\n" +"messaggi. Comunque, non più di %d messaggi saranno\n" +"inviati per evitare di floodare l'utente. Se sono presenti\n" +"più messaggi di news, saranno inviati solo i più recenti." + +#: modules/commands/os_news.cpp:336 +#, c-format +msgid "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Modifica o visualizza la lista dei messaggi oper news.\n" +"Quando un utente si autentica come oper (con il comando /OPER), riceverà " +"questi\n" +"messaggi. Comunque, non più di %d messaggi saranno\n" +"inviati per evitare di floodare l'utente. Se sono presenti\n" +"più messaggi di news, saranno inviati solo i più recenti." + +#: modules/commands/os_news.cpp:363 +msgid "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." +msgstr "" +"Modifica o visualizza la lista dei messaggi news random.\n" +"Quando un utente si connette alla rete, una (e una soltanto)\n" +"delle random news sarà scelta casualmente e gli\n" +"sarà inviata." + +#: modules/commands/ns_info.cpp:98 +msgid "Email address" +msgstr "Indirizzo e-mail" + +#: modules/commands/ns_getemail.cpp:41 +#, c-format +msgid "Email matched: %s (%s) to %s." +msgstr "Email corrispondenti: %s ( %s ) a %s." + +#: modules/fantasy.cpp:19 +msgid "Enable fantaisist commands" +msgstr "Abilita i comandi Fantasy" + +#: modules/commands/greet.cpp:19 +msgid "Enable greet messages" +msgstr "Abilita il messaggio di saluto" + +#: modules/commands/ns_set.cpp:568 +msgid "Enable or disable keep modes" +msgstr "Abilita o disabilita il mantenimento degli user modo" + +#: modules/commands/bs_kick.cpp:1114 modules/commands/bs_info.cpp:89 +msgid "Enabled" +msgstr "Attivato" + +#: modules/commands/cs_set.cpp:124 +#, c-format +msgid "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." +msgstr "" +"Attiva o disattiva l'opzione %s autoop per il canale.\n" +"Quando l'opzione è disabilitata, gli utenti che accedono\n" +"al canale non otteranno automaticamente alcuno stato da %s." + +#: modules/commands/cs_set.cpp:388 +msgid "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." +msgstr "" +"Attiva o disattiva il mantenimento dei modi per il canale\n" +"specificato. Quando il mantenimento dei modi è attivo,\n" +"i services memorizzeranno i modi impostati nel canale\n" +"e provvederanno a reimpostatarli la prossima volta che il canale\n" +"sarà creato." + +#: modules/commands/ns_set.cpp:643 +msgid "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." +msgstr "" +"Abilita o disabilita il mantenimento dei modi per il nick specificato.\n" +"Se il mantenimento dei modi è abilitato, i services memorizzeranno gli\n" +"modi utente dell'utente, e provvederanno a reimpostarli la prossima\n" +"volta che si autenticherà." + +#: modules/commands/ns_set.cpp:618 +msgid "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." +msgstr "" +"Abilita o disabilita il mantenimento dei modi per il tuo nick.\n" +"Se il mantenimento dei modi è abilitato, i services memorizzeranno\n" +"i tuoi modi utente, e provvederanno a reimpostarli la prossima volta\n" +"che ti autenticherai." + +#: modules/commands/cs_set.cpp:733 +msgid "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." +msgstr "" +"Attiva o disattiva le funzionalità di sicurezza\n" +"per il canale. Quando SECURE è attivo,\n" +"solo gli utenti che hanno registrato il proprio nick\n" +"e che si sono identificati con la loro password\n" +"avranno l'accesso sul canale secondo le liste di accesso." + +#: modules/commands/cs_set.cpp:932 +msgid "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." +msgstr "" +"Attiva o disattiva i kick \"firmati\" per il canale. Quando\n" +"l'opzione è attiva, i kick effettuati con il comando KICK\n" +"indicheranno anche il nick della persona che ha\n" +"utilizzato il comando.\n" +"\n" +"Se usi LEVEL, il nick non sarà comunque mostrato se il\n" +"kick è effettuato da qualcuno il cui livello di accesso\n" +"è uguale o maggiore al livello SIGNKICK del canale." + +#: modules/commands/cs_set.cpp:452 +#, c-format +msgid "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." +msgstr "" +"Attiva o disattiva l'opzione \"pace\" per il canale.\n" +"Quando l'opzione è attiva, gli utenti non potranno\n" +"kickare, bannare o rimuovere uno stato di canale\n" +"(op, halfop, ecc.) di un utente con livello superiore,\n" +"tramite i comandi di %s." + +#: modules/commands/cs_list.cpp:232 +msgid "Enables or disables the private option for a channel." +msgstr "Abilita o disabilita l'opzione privato per un canale." + +#: modules/commands/cs_set.cpp:671 +msgid "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." +msgstr "" +"Abilita o disabilita l'opzione di accesso limitato per un\n" +"canale. Quando è impostato l'accesso limitato, gli utenti non\n" +"presenti in lista di accesso saranno espulsi e bannati dal canale." + +#: modules/commands/cs_set.cpp:796 +msgid "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." +msgstr "" +"Attiva o disattiva l'opzione secure founder per il\n" +"canale. Quando l'opzione è attiva, solo il vero founder\n" +"potrà deregistrare il canale (drop), cambiarne la password,\n" +"il founder e il successore, mentre non potranno gli utenti\n" +"gli utenti che hanno ottenuto il livello di founder tramite\n" +"il comando access/qop." + +#: modules/commands/cs_set.cpp:860 +msgid "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." +msgstr "" +"Attiva o disattiva l'opzione secure ops per il canale.\n" +"Quando l'opzione è attiva, gli utenti che non sono nella\n" +"lista di accesso non potranno avere lo stato di operatore\n" +"di canale." + +#: modules/commands/cs_topic.cpp:70 +#, c-format +msgid "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." +msgstr "" +"Attiva o disattiva il mantenimento del topic per\n" +"il canale. Quando %s è attivo il topic sarà memorizzato da %s\n" +"anche quando l'ultimo utente esce dal canale,\n" +"e sarà reimpostato la volta successiva che il canale\n" +"sarà creato." + +#: modules/commands/cs_set.cpp:592 +#, c-format +msgid "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." +msgstr "" +"Abilita o disabilita l'impostazione di canale persistente.\n" +"Quando l'opzione è attiva, il bot dei service continuerà a sostare\n" +"nel canale anche quando non vi sono presenti utenti.\n" +" \n" +"Se l'IRCd non supporta i canali permanenti (persistenti)\n" +"è necessaria la presenza di un bot dei services nel canale\n" +"per attivare l'opzione, il bot non può essere rimosso dal\n" +"canale fin quando l'opzione è attiva.\n" +" \n" +"Se il network non ha %s abilitato e non supporta\n" +"i canali permanenti, %s accederà al canale quando\n" +"l'opzione è attiva (e lascerà il canale quando\n" +"l'opzione è disattivata).\n" +" \n" +"Se l'IRCd supporta i canali permanenti (persistenti)\n" +"e sono abilitati o disabilitati (per qualsiasi motivo, incluso MLOCK),\n" +"l'opzione è automaticamente abilitata o disabilitata per il canale.\n" +"Inoltre, i services imposteranno o rimuoveranno il modo quando\n" +"persist viene abilitato o disabilitato." + +#: modules/commands/os_akill.cpp:331 +msgid "End of AKILL list." +msgstr "Fine della lista AKILL." + +#: modules/commands/cs_access.cpp:444 +msgid "End of access list" +msgstr "Fine della lista di accesso" + +#: modules/commands/cs_flags.cpp:347 +#, c-format +msgid "End of access list - %d/%d entries shown." +msgstr "Fine della lista di accesso - %d/%d risultati mostrati." + +#: modules/commands/cs_flags.cpp:345 +msgid "End of access list." +msgstr "Fine della lista di accesso." + +#: modules/commands/cs_akick.cpp:379 +msgid "End of autokick list" +msgstr "Fine della lista auto kick" + +#: modules/commands/bs_badwords.cpp:257 +msgid "End of bad words list." +msgstr "Fine della lista parolacce." + +#: modules/commands/os_list.cpp:100 +#, c-format +msgid "End of channel list. %u channels shown." +msgstr "Fine della lista canali. %u canali mostrati." + +#: modules/commands/os_config.cpp:117 +msgid "End of configuration." +msgstr "Fine della configurazione." + +#: modules/commands/cs_entrymsg.cpp:134 +msgid "End of entry message list." +msgstr "Fine della lista dei messaggi di ingresso." + +#: modules/commands/os_forbid.cpp:407 +#, c-format +msgid "End of forbid list - %d/%d entries shown." +msgstr "Fine della lista forbid - %d/%d risultati mostrati." + +#: modules/commands/os_forbid.cpp:405 +msgid "End of forbid list." +msgstr "Fine della lista forbid." + +#: modules/commands/ns_alist.cpp:119 +#, c-format +msgid "End of list - %d channels shown." +msgstr "Fine della lista - %d canali mostrati." + +#: modules/commands/ns_list.cpp:131 modules/commands/cs_list.cpp:130 +#, c-format +msgid "End of list - %d/%d matches shown." +msgstr "Fine della lista - %d/%d risultati mostrati." + +#: modules/commands/os_news.cpp:176 +msgid "End of news list." +msgstr "Fine della lista news." + +#: modules/commands/os_list.cpp:235 +#, c-format +msgid "End of users list. %u users shown." +msgstr "Fine della lista dei nick - %u utenti mostrati." + +#: modules/commands/cs_enforce.cpp:227 +msgid "Enforce various channel modes and set options" +msgstr "Forza l'impostazione di vari modi canale e opzioni" + +#: modules/commands/cs_enforce.cpp:263 +msgid "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." +msgstr "" +"Forza l'impostazione di vari modi canale e opzioni. La voce\n" +"\"canale\" indica su quale canale forzare i modi e le opzioni.\n" +"La voce \"cosa\" indica quali modi e opzioni forzare,\n" +"e possono essere SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, o LIMIT.\n" +" \n" +"Usa SECUREOPS per forzare l'opzione SECUREOPS, anche se questa non\n" +"è abilitata. Usa RESTRICTED per forzare l'opzione RESTRICTED, anche\n" +"se questa non è abilitata. Usa REGONLY per kickare tutti gli utenti non\n" +"registrati dal canale. Usa SSLONLY per kickare tutti gli utenti che non " +"usano\n" +"una connessione SSL dal canale. BANS forzerà i bans impostati nel canale\n" +"kickando gli utenti corrispondenti ad essi, LIMIT kickerà gli utenti fino\n" +"a quando il numero degli stessi non scende al di sotto del limite canale,\n" +"se un limite è impostato." + +#: src/language.cpp:43 modules/commands/ns_set.cpp:836 +#: modules/commands/ns_set.cpp:856 modules/commands/ns_set.cpp:891 +msgid "English" +msgstr "Italiano" + +#: modules/commands/cs_entrymsg.cpp:170 +#, c-format +msgid "Entry message %i for %s deleted." +msgstr "Il messaggio di ingresso %i per %s rimosso." + +#: modules/commands/cs_entrymsg.cpp:177 +#, c-format +msgid "Entry message %s not found on channel %s." +msgstr "Il messaggio di ingresso %s non è stato trovato nel canale %s." + +#: modules/commands/cs_entrymsg.cpp:147 +#, c-format +msgid "Entry message added to %s" +msgstr "Messaggio di ingresso aggiunto a %s" + +#: modules/commands/cs_entrymsg.cpp:109 modules/commands/cs_entrymsg.cpp:158 +#, c-format +msgid "Entry message list for %s is empty." +msgstr "La lista dei messaggi di ingresso di %s è vuota." + +#: modules/commands/cs_entrymsg.cpp:113 +#, c-format +msgid "Entry message list for %s:" +msgstr "Lista dei messaggi di ingresso di %s:" + +#: modules/commands/cs_entrymsg.cpp:187 +#, c-format +msgid "Entry messages for %s have been cleared." +msgstr "Tutti i messaggi di ingresso di %s sono stati cancellati." + +#: modules/commands/os_reload.cpp:39 +#, c-format +msgid "Error reloading configuration file: %s" +msgstr "Errore nel reload del file di configurazione: %s" + +#: include/language.h:125 +#, c-format +msgid "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." +msgstr "" +"Errore! L'ident del vHost è troppo lunga, usa una ident più corta di %d " +"caratteri." + +#: include/language.h:124 +#, c-format +msgid "" +"Error! The vHost is too long, please use a hostname shorter than %d " +"characters." +msgstr "" +"Errore! Il vHost è troppo lungo, usa un hostname più corto di %d caratteri." + +#: modules/commands/ns_cert.cpp:325 +msgid "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." +msgstr "" +"Esempi:\n" +" \n" +" CERT ADD \n" +" Aggiunge la firma digitale specificata alla lista\n" +" dei certificati e ti identifica automaticamente quando\n" +" ti connetti a IRC usando questo certificato.\n" +" \n" +" CERT DEL \n" +" Rimuove la firma digitale specificata dalla lista\n" +" dei certificati.\n" +" \n" +" CERT LIST\n" +" Visualizza la lista dei certificati attuale." + +#: modules/commands/os_session.cpp:358 +#, c-format +msgid "Exception for %s has been updated to %d." +msgstr "L'eccezione per %s è stata aggiornata in %d." + +#: modules/pseudoclients/chanserv.cpp:465 +#: modules/pseudoclients/nickserv.cpp:557 +#: modules/pseudoclients/nickserv.cpp:562 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_session.cpp:514 modules/commands/ns_group.cpp:327 +#: modules/commands/os_akill.cpp:358 +msgid "Expires" +msgstr "Scadenza" + +#: src/xline.cpp:397 +#, c-format +msgid "Expiry and reason updated for %s." +msgstr "Scadenza e motivo aggiornati per %s." + +#: src/xline.cpp:400 +#, c-format +msgid "Expiry for %s updated." +msgstr "Scadenza per %s modificata." + +#: modules/fantasy.cpp:214 +msgid "Fantasy" +msgstr "Fantasia" + +#: modules/fantasy.cpp:60 +#, c-format +msgid "Fantasy mode is now off on channel %s." +msgstr "La modalità fantasy ora è ATTIVA sul canale %s." + +#: modules/fantasy.cpp:52 +#, c-format +msgid "Fantasy mode is now on on channel %s." +msgstr "La modalità fantasy ora è ATTIVA sul canale %s." + +#: modules/commands/cs_status.cpp:19 +msgid "Find a user's status on a channel" +msgstr "Trova lo stato di un utente in un canale" + +#: modules/commands/ns_cert.cpp:192 +#, c-format +msgid "Fingerprint %s already present on %s's certificate list." +msgstr "La firma digitale %s è già presente nella lista dei certificati di %s." + +#: modules/commands/ns_cert.cpp:198 +#, c-format +msgid "Fingerprint %s is already in use." +msgstr "La firma digitale %s è già in uso." + +#: modules/commands/cs_flags.cpp:301 +msgid "Flags" +msgstr "Flags" + +#: modules/commands/cs_flags.cpp:286 +#, c-format +msgid "Flags for %s on %s set to +%s" +msgstr "Flags per %s su %s impostate a +%s" + +#: modules/commands/cs_flags.cpp:341 +#, c-format +msgid "Flags list for %s" +msgstr "Lista flags di %s" + +#: modules/commands/bs_kick.cpp:1161 modules/commands/bs_kick.cpp:1163 +#: modules/commands/bs_kick.cpp:1166 +msgid "Flood kicker" +msgstr "Kick in caso di flood" + +#: modules/commands/os_forbid.cpp:421 +msgid "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." +msgstr "" +"Forbid permette di vietare l'uso di certi nicknames, canali,\n" +"e indirizzi email. Le wildcards sono supportate per tutte le voci." + +#: modules/commands/os_forbid.cpp:354 +msgid "Forbid list is empty." +msgstr "La lista forbid è vuota." + +#: modules/commands/os_forbid.cpp:396 +msgid "Forbid list:" +msgstr "Lista forbid:" + +#: modules/commands/os_forbid.cpp:348 +#, c-format +msgid "Forbid on %s was not found." +msgstr "Il forbid su %s non è stato trovato." + +#: modules/commands/os_forbid.cpp:156 +msgid "Forbid usage of nicknames, channels, and emails" +msgstr "Vieta l'uso di nicknames, canali e indirizzi email" + +#: modules/commands/os_update.cpp:19 +msgid "Force the Services databases to be updated immediately" +msgstr "Forza l'aggiornamento immediato del database dei Services" + +#: modules/commands/os_svs.cpp:19 +msgid "Forcefully change a user's nickname" +msgstr "Forza il cambio del nickname di un utente" + +#: modules/commands/os_svs.cpp:68 +msgid "Forcefully changes a user's nickname from nick to newnick." +msgstr "Forza il cambio del nickname di un utente da nick a newnick." + +#: modules/commands/os_svs.cpp:78 +msgid "Forcefully join a user to a channel" +msgstr "Forza l'ingresso di un utente in un canale" + +#: modules/commands/os_svs.cpp:112 +msgid "Forcefully join a user to a channel." +msgstr "Forza l'ingresso di un utente in un canale." + +#: modules/commands/os_svs.cpp:122 +msgid "Forcefully part a user from a channel" +msgstr "Forza l'uscita di un utente da un canale" + +#: modules/commands/os_svs.cpp:160 +msgid "Forcefully part a user from a channel." +msgstr "Forza l'uscita di un utente da un canale." + +#: modules/commands/ns_alist.cpp:64 modules/commands/cs_info.cpp:47 +msgid "Founder" +msgstr "Founder" + +#: modules/commands/cs_set.cpp:315 +#, c-format +msgid "Founder of %s changed to %s." +msgstr "Il founder del canale %s adesso è %s." + +#: modules/commands/ns_getpass.cpp:41 +msgid "GETPASS command unavailable because encryption is in use." +msgstr "" +"Il comando GETPASS non è disponibile perché è in uso la criptazione dei dati." + +#: modules/commands/ns_recover.cpp:84 +msgid "Ghost with your nick has been killed." +msgstr "La connessione fantasma con il tuo nick è stata disconnessa." + +#: modules/commands/os_oline.cpp:19 +msgid "Give Operflags to a certain user" +msgstr "Imposta le operflag di un utente" + +#: modules/commands/cs_mode.cpp:905 +#, c-format +msgid "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." +msgstr "" +"Imposta lo stato di %s al nick specificato in un canale. Se il\n" +"nick non viene specificato, lo stato di %s viene impostato su te stesso." + +#: modules/commands/cs_mode.cpp:888 +#, c-format +msgid "Gives you or the specified nick %s status on a channel" +msgstr "" +"Imposta su te stesso o sul nick specificato lo stato di %s in un canale" + +#: modules/commands/greet.cpp:206 modules/commands/greet.cpp:212 +msgid "Greet" +msgstr "Saluto" + +#: src/access.cpp:38 +msgid "Greet message displayed on join" +msgstr "Messaggio di saluto mostrato all'accesso" + +#: modules/commands/greet.cpp:112 +#, c-format +msgid "Greet message for %s changed to %s." +msgstr "Messaggio di saluto per %s cambiato in %s." + +#: modules/commands/greet.cpp:118 +#, c-format +msgid "Greet message for %s unset." +msgstr "Messaggio di saluto per %s rimosso." + +#: modules/commands/greet.cpp:60 +#, c-format +msgid "Greet mode is now off on channel %s." +msgstr "La modalità greet ora è disabilitata nel canale %s." + +#: modules/commands/greet.cpp:52 +#, c-format +msgid "Greet mode is now on on channel %s." +msgstr "La modalità greet ora è attiva nel canale %s." + +#: modules/commands/ns_resetpass.cpp:21 +msgid "Helps you reset lost passwords" +msgstr "Avvia la procedura per reimpostare le passwords perdute" + +#: modules/commands/ns_info.cpp:141 +msgid "Hide certain pieces of nickname information" +msgstr "Nasconde alcune informazioni sul tuo nick" + +#: modules/commands/cs_list.cpp:180 +msgid "Hide channel from the LIST command" +msgstr "Nasconde il canale dall'output del comando LIST" + +#: modules/commands/os_session.cpp:192 +msgid "Host" +msgstr "Host" + +#: modules/commands/os_session.cpp:207 +#, c-format +msgid "Hosts with at least %d sessions:" +msgstr "Lista degli host con almeno %d sessioni:" + +#: modules/commands/cs_seen.cpp:207 +#, c-format +msgid "I don't know who %s is." +msgstr "Non conosco %s." + +#: modules/commands/cs_seen.cpp:253 +#, c-format +msgid "I've never seen %s on this channel." +msgstr "Non ho mai visto %s in questo canale." + +#: modules/commands/os_sxline.cpp:203 modules/commands/os_akill.cpp:360 +msgid "ID" +msgstr "ID" + +#: modules/commands/os_oper.cpp:72 +msgid "INFO [type]" +msgstr "INFO [tipo]" + +#: modules/commands/os_dns.cpp:218 +msgid "IP" +msgstr "IP" + +#: modules/commands/os_dns.cpp:500 +#, c-format +msgid "IP %s already exists for %s." +msgstr "L'IP %s esiste già per %s." + +#: modules/commands/os_dns.cpp:562 +#, c-format +msgid "IP %s does not exist for %s." +msgstr "L'IP %s non esiste per %s." + +#: modules/commands/ns_identify.cpp:65 +msgid "Identify yourself with your password" +msgstr "Ti identifica con la tua password" + +#: modules/pseudoclients/nickserv.cpp:205 +#: modules/pseudoclients/nickserv.cpp:211 +#, c-format +msgid "If you do not change within %s, I will change your nick." +msgstr "Se non cambi il tuo nick entro %s, verrà cambiato dal server." + +#: modules/commands/os_ignore.cpp:333 +msgid "Ignore list has been cleared." +msgstr "La lista ignore è stata cancellata." + +#: modules/commands/os_ignore.cpp:262 +msgid "Ignore list is empty." +msgstr "La lista ignore è vuota." + +#: modules/commands/ms_ignore.cpp:94 +msgid "Ignore list:" +msgstr "Lista ignore:" + +#: modules/commands/ns_set.cpp:1305 +msgid "Immediate protection" +msgstr "Protezione immediata" + +#: modules/commands/ns_resetpass.cpp:33 +msgid "Incorrect email address." +msgstr "Indirizzo e-mail non corretto." + +#: include/language.h:89 +msgid "Incorrect range specified. The correct syntax is #from-to." +msgstr "Range specificato errato. La sintassi corretta è #da-a." + +#: modules/commands/os_modinfo.cpp:19 +msgid "Info about a loaded module" +msgstr "Informazioni su un modulo caricato" + +#: modules/commands/bs_info.cpp:54 +#, c-format +msgid "Information for bot %s:" +msgstr "Informazioni sul bot %s:" + +#: include/language.h:108 +#, c-format +msgid "Information for channel %s:" +msgstr "Informazioni sul canale %s:" + +#: modules/commands/os_logsearch.cpp:57 +#, c-format +msgid "Invalid duration %s, using %d days." +msgstr "Durata non valida %s, usato %d giorni." + +#: include/language.h:68 +msgid "Invalid expiry time." +msgstr "Tempo di scadenza non valido." + +#: modules/commands/os_session.cpp:346 +msgid "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not " +"matched against nicks or usernames." +msgstr "" +"Hostmask non valida. Solo le hostmask reali sono valide, le eccezioni non " +"vengono confrontate con i nick o con gli username." + +#: modules/commands/os_logsearch.cpp:73 +#, c-format +msgid "Invalid limit %s, using %d." +msgstr "Limite non valido %s, usato %d." + +#: include/language.h:99 +msgid "" +"Invalid passcode has been entered, please check the e-mail again, and retry." +msgstr "" +"È stato inserito un codice di attivazione non valido, controlla di nuovo " +"l'email ricevuta e riprova." + +#: modules/commands/ns_register.cpp:83 modules/commands/ns_register.cpp:86 +msgid "Invalid passcode." +msgstr "Codice di attivazione non valido." + +#: modules/commands/os_session.cpp:339 +#, c-format +msgid "" +"Invalid session limit. It must be a valid integer greater than or equal to " +"zero and less than %d." +msgstr "" +"Limite delle sessioni non valido. Deve essere un numero intero maggiore o " +"uguale a zero e minore di %d." + +#: modules/commands/os_session.cpp:188 +msgid "Invalid threshold value. It must be a valid integer greater than 1." +msgstr "" +"Valore di soglia non valido. Deve essere un numero intero maggiore di 1." + +#: modules/commands/os_dns.cpp:591 +msgid "Invalid value for LIMIT. Must be numerical." +msgstr "Valore non valido per LIMIT. Deve essere numerico." + +#: modules/commands/cs_invite.cpp:19 +msgid "Invites you or an optionally specified nick into a channel" +msgstr "Invita te stesso oppure il nick specificato in un canale" + +#: modules/commands/bs_kick.cpp:1201 modules/commands/bs_kick.cpp:1203 +#: modules/commands/bs_kick.cpp:1206 +msgid "Italics kicker" +msgstr "Kick in caso di italics" + +#: modules/commands/ns_group.cpp:91 +msgid "Join a group" +msgstr "Entra in un gruppo" + +#: modules/commands/cs_set.cpp:1305 modules/commands/ns_set.cpp:1319 +msgid "Keep modes" +msgstr "Mantenimento modi" + +#: modules/commands/cs_set.cpp:377 modules/commands/ns_set.cpp:603 +#, c-format +msgid "Keep modes for %s is now off." +msgstr "Il mantenimento dei modi per %s è stato disattivato." + +#: modules/commands/cs_set.cpp:369 modules/commands/ns_set.cpp:597 +#, c-format +msgid "Keep modes for %s is now on." +msgstr "Il mantenimento dei modi per %s è stato attivato." + +#: modules/commands/ns_ajoin.cpp:100 +msgid "Key" +msgstr "Chiave" + +#: modules/commands/cs_getkey.cpp:50 +#, c-format +msgid "Key for channel %s is %s." +msgstr "La chiave per il canale %s è %s." + +#: modules/commands/os_kick.cpp:19 +msgid "Kick a user from a channel" +msgstr "Espelle un utente da un canale" + +#: modules/commands/cs_ban.cpp:217 modules/commands/cs_kick.cpp:116 +#, c-format +msgid "Kicked %d/%d users matching %s from %s." +msgstr "%d/%d utenti espulsi confrontando %s da %s." + +#: modules/commands/cs_kick.cpp:19 +msgid "Kicks a specified nick from a channel" +msgstr "Espelle il nick specificato da un canale" + +#: modules/commands/cs_kick.cpp:128 +msgid "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." +msgstr "" +"Espelle il nick specificato dal canale.\n" +" \n" +"Di default, il comando è limitato agli AOP o agli utenti con\n" +"livello di accesso 5 o superiori sul canale. I founder possono\n" +"usare anche una mask." + +#: modules/commands/os_kill.cpp:19 +msgid "Kill a user" +msgstr "Killa un utente" + +#: modules/commands/cs_enforce.cpp:217 +msgid "LIMIT enforced by " +msgstr "LIMIT forzato da " + +#: modules/commands/cs_enforce.cpp:221 +#, c-format +msgid "LIMIT enforced on %s, %d users removed." +msgstr "LIMIT forzato su %s, %d utenti rimossi." + +#: modules/commands/os_session.cpp:246 +msgid "LIST threshold" +msgstr "LIST soglia" + +#: modules/commands/os_sxline.cpp:427 modules/commands/os_sxline.cpp:661 +#: modules/commands/os_akill.cpp:388 +msgid "LIST [mask | list | id]" +msgstr "LIST [mask | list | id]" + +#: modules/commands/os_session.cpp:525 +msgid "LIST [mask | list]" +msgstr "LIST [mask | list]" + +#: modules/commands/ns_access.cpp:104 modules/commands/ns_cert.cpp:260 +#: modules/commands/ns_ajoin.cpp:233 +msgid "LIST [nickname]" +msgstr "LIST [nickname]" + +#: modules/commands/os_news.cpp:31 +msgid "LOGONNEWS {ADD|DEL|LIST} [text|num]" +msgstr "LOGONNEWS {ADD|DEL|LIST} [testo|numero]" + +#: modules/commands/ns_set.cpp:834 +msgid "Language changed to English." +msgstr "Lingua cambiata a Italiano." + +#: modules/commands/ns_set.cpp:836 +#, c-format +msgid "Language for %s changed to %s." +msgstr "Lingua per %s cambiata a %s." + +#: modules/commands/ms_cancel.cpp:72 +#, c-format +msgid "Last memo to %s has been cancelled." +msgstr "L'ultimo memo inviato a %s è stato annullato." + +#: modules/commands/ns_info.cpp:95 +msgid "Last quit message" +msgstr "Ultimo messaggio di quit" + +#: modules/commands/cs_access.cpp:472 modules/commands/ns_info.cpp:92 +msgid "Last seen" +msgstr "Ultimo accesso" + +#: modules/commands/ns_info.cpp:81 modules/commands/ns_info.cpp:86 +msgid "Last seen address" +msgstr "Ultimo indirizzo usato" + +#: modules/commands/cs_topic.cpp:264 +msgid "Last topic" +msgstr "Ultimo topic" + +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_info.cpp:56 +msgid "Last used" +msgstr "Ultimo usato" + +#: modules/commands/ns_list.cpp:75 +msgid "Last usermask" +msgstr "Ultima usermask" + +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +#: modules/commands/cs_access.cpp:697 +msgid "Level" +msgstr "Livello" + +#: modules/commands/cs_access.cpp:660 +#, c-format +msgid "Level for %s on channel %s changed to %d." +msgstr "Il livello di %s sul canale %s è stato modificato a %d." + +#: modules/commands/cs_access.cpp:658 +#, c-format +msgid "Level for %s on channel %s changed to founder only." +msgstr "Il livello di %s sul canale %s è stato modificato in solo fondatori." + +#: modules/commands/cs_access.cpp:643 +#, c-format +msgid "Level must be between %d and %d inclusive." +msgstr "Il livello deve essere compreso tra %d e %d (inclusi)." + +#: modules/commands/os_dns.cpp:218 modules/commands/os_session.cpp:506 +#: modules/commands/os_session.cpp:514 +msgid "Limit" +msgstr "Limite" + +#: modules/commands/ns_list.cpp:19 +msgid "List all registered nicknames that match a given pattern" +msgstr "" +"Mostra l'elenco dei nick registrati corrispondenti la chiave specificata" + +#: modules/commands/ns_alist.cpp:24 +msgid "List channels you have access on" +msgstr "Mostra i canali in cui si ha accesso" + +#: modules/commands/cs_mode.cpp:341 +#, c-format +msgid "List for mode %c is full." +msgstr "La lista per il modo %c è piena." + +#: modules/commands/os_modinfo.cpp:80 +msgid "List loaded modules" +msgstr "Elenca i moduli caricati" + +#: modules/commands/ns_list.cpp:123 modules/commands/cs_list.cpp:72 +#, c-format +msgid "List of entries matching %s:" +msgstr "Lista delle voci corrispondenti %s:" + +#: modules/commands/ns_group.cpp:350 +#, c-format +msgid "List of nicknames in the group of %s:" +msgstr "Lista dei nick nel gruppo di %s:" + +#: modules/commands/ns_group.cpp:350 +msgid "List of nicknames in your group:" +msgstr "Lista dei nick nel tuo gruppo:" + +#: modules/commands/ms_list.cpp:19 +msgid "List your memos" +msgstr "Mostra la lista dei propri memo" + +#: modules/commands/bs_botlist.cpp:64 +msgid "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." +msgstr "" +"Mostra la lista di tutti i bot disponibili.\n" +"I bot con prefisso * sono riservati per il Network." + +#: modules/commands/os_list.cpp:19 +msgid "Lists all channel records" +msgstr "Mostra tutti i canali" + +#: modules/commands/os_list.cpp:107 +msgid "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." +msgstr "" +"Mostra tutti i canali attivi sulla rete, che siano registrati\n" +"o meno.\n" +" \n" +"Se viene indicato un pattern mostra solo i canali corrispondenti.\n" +"Se viene indicato un nick, mostra solo i canali in cui si trova\n" +"l'utente specificato.\n" +"Se viene indicato SECRET, mostra solo i canali che corrisponodno a\n" +"pattern e che hanno il modo di canale +s o +p attivo." + +#: modules/commands/ns_alist.cpp:127 +msgid "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" +msgstr "" +"Mostra i canali in cui si ha accesso.\n" +" \n" +"I canali che hanno l'opzione NOEXPIRE impostata\n" +"avranno come prefisso un punto esclamativo. Il parametro nick\n" +"è limitato ai Services Operators" + +#: modules/commands/ns_group.cpp:299 +msgid "Lists all nicknames in your group" +msgstr "Mostra tutti i nickname nel tuo gruppo" + +#: modules/commands/cs_list.cpp:20 +msgid "Lists all registered channels matching the given pattern" +msgstr "" +"Mostra la lista dei canali registrati corrispondenti la chiave specificata" + +#: modules/commands/cs_list.cpp:137 +msgid "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." +msgstr "" +"Mostra la lista dei canali registrati corrispondenti\n" +"la chiave specificata. I canali con l'opzione PRIVATE\n" +"impostata saranno mostrati solo ai Services Operators.\n" +"I canali con l'opzione NOEXPIRE impostata avranno come prefisso\n" +"un ! (solo per i Services Operators). \n" +"Nota che l'uso del carattere '#' specifica un range,\n" +"i nomi dei canali devono essere scritti senza cancelletto.\n" +" \n" +"Se le opzioni SUSPENDED o NOEXPIRE sono specificate, solamente\n" +"i canali che sono rispettivamente SUSPENDED o hanno la flag NOEXPIRE\n" +"saranno mostrati. Se specificate opzioni multiple, tutti i canali\n" +"corrispondenti almeno un'opzione saranno mostrati.\n" +"Nota che queste opzioni sono limitate ai Services Operators.\n" +" \n" +"Esempi:\n" +" \n" +" LIST *anope*\n" +" Mostra tutti i canali registrati che contengono anope nei\n" +" loro nomi (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Mostra tutti i canali registrati che sono stati impostati NOEXPIRE.\n" +" \n" +" LIST #51-100\n" +" Mostra tutti i canali registrati compresi nel range specificato " +"(51-100)." + +#: modules/commands/ns_list.cpp:139 +msgid "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." +msgstr "" +"Mostra tutti i nick registrati che corrispondono al\n" +"pattern specificato, nel formato nick!user@host.\n" +"I nick con l'opzione PRIVATE attiva saranno mostrati\n" +"solo ai Services Operator. I nick con l'opzione NOEXPIRE\n" +"attiva avranno un ! prima del nick stesso (solo per i\n" +"Services Operator).\n" +" \n" +"Nota che l'uso del carattere '#' specifica un range.\n" +" \n" +"Se sono specificate le opzioni SUSPENDED, NOEXPIRE o UNCONFIRMED,\n" +"unicamente i nick che sono rispettivamente SUSPENDED, \n" +"UNCONFIRMED oppure hanno la flag NOEXPIRE impostata verranno\n" +"mostrati. Se tutte e tre le opzioni sono specificate, tutti\n" +"e tre i tipi di nick verranno mostrati. Queste opzioni sono\n" +"limitate ai Services Operator.\n" +" \n" +"Esempi:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Mostra tutti i nick che appartengono a joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Mostra tutti i nick registrati che contengono \n" +" Bot (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Mostra tutti i nick registrati che sono stati\n" +" impostati per non scadere. \n" +" LIST #51-100\n" +" Mostra tutti i canali registrati compresi nel range\n" +" specificato (51-100)." + +#: modules/commands/os_list.cpp:132 +msgid "Lists all user records" +msgstr "Mostra tutti gli utenti" + +#: modules/commands/os_list.cpp:243 +msgid "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only " +"users\n" +"with the +i flag will be listed." +msgstr "" +"Mostra tutti gli utenti connessi alla rete, che siano registrati\n" +"o meno.\n" +"\n" +"Se viene indicato un pattern mostra solo gli utenti corrispondenti\n" +"(il pattern deve essere nel formato nick!user@host).\n" +"Se viene indicato un canale, mostra solo gli utenti che si trovano\n" +"su quel canale.\n" +"Se viene indicato INVISIBLE, mostra solo gli utenti con il modo\n" +"utente +i attivo." + +#: modules/commands/ms_list.cpp:142 +msgid "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Mostra le proprie memo. Quando viene specificato NEW, mostra\n" +"soltanto i nuovi memo (non letti). I memo non letti sono segnati\n" +"con un \"*\" a sinistra del numero d'ordine. Si può anche indicare\n" +"una lista di numeri, come in quest'esempio:\n" +" LIST 2-5,7-9\n" +" Mostra i memo che hanno numeri tra 2 e 5 e tra 7 e 9,\n" +" escludendo quindi il 6." + +#: modules/commands/bs_botlist.cpp:19 +msgid "Lists available bots" +msgstr "Mostra la lista dei bot disponibili" + +#: modules/commands/os_modinfo.cpp:196 +msgid "Lists currently loaded modules." +msgstr "Elenca i moduli attualmente caricati." + +#: modules/commands/cs_info.cpp:19 +msgid "Lists information about the specified registered channel" +msgstr "Mostra le informazioni su un canale registrato" + +#: modules/commands/cs_info.cpp:76 +msgid "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." +msgstr "" +"Mostra varie informazioni a proposito del canale\n" +"specificato (a patto che sia registrato), tra cui il\n" +"founder, il giorno di registrazione, l'ultimo utilizzo,\n" +"la descrizione e il blocco dei modi, se presente. Se\n" +"l'utente che invia il comando ha l'accesso appropriato\n" +"al canale, visualizzerà anche la descrizione, il successore,\n" +"l'ultimo topic impostato, le impostazioni e la scandenza\n" +"del canale." + +#: modules/commands/os_module.cpp:19 +msgid "Load a module" +msgstr "Carica un modulo" + +#: modules/commands/cs_register.cpp:39 +msgid "Local channels cannot be registered." +msgstr "I canali locali non possono essere registrati." + +#: modules/commands/cs_log.cpp:142 +#, c-format +msgid "Log list for %s:" +msgstr "Lista log di %s:" + +#: modules/commands/cs_log.cpp:227 +#, c-format +msgid "Logging changed for command %s on %s, now using log method %s%s%s." +msgstr "" +"Logging cambiato per il comando %s su %s, metodo in uso adesso: %s%s%s." + +#: modules/commands/cs_log.cpp:220 +#, c-format +msgid "Logging for command %s on %s with log method %s%s%s has been removed." +msgstr "Logging per il comando %s su %s con metodo %s%s%s è stato rimosso." + +#: modules/commands/cs_log.cpp:248 +#, c-format +msgid "Logging is now active for command %s on %s, using log method %s%s%s." +msgstr "Logging attivato per il comando %s su %s, metodo in uso: %s%s%s." + +#: modules/commands/os_login.cpp:60 +#, c-format +msgid "Login to %s" +msgstr "Accedi a %s" + +#: modules/commands/os_news.cpp:36 +#, c-format +msgid "Logon news item #%d deleted." +msgstr "La Logon News numero %d è stata eliminata." + +#: modules/commands/os_news.cpp:35 +#, c-format +msgid "Logon news item #%s not found!" +msgstr "Impossibile trovare la Logon News numero #%s!" + +#: modules/commands/os_news.cpp:32 +msgid "Logon news items:" +msgstr "Lista delle Logon News:" + +#: modules/commands/os_login.cpp:102 +#, c-format +msgid "Logout from %s" +msgstr "Logout da %s" + +#: modules/commands/os_login.cpp:52 +#, c-format +msgid "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." +msgstr "" +"Dà accesso a %s permettendo di ottenere i privilegi di Services Operator.\n" +"Questo comando potrebbe non essere necessario se il tuo oper block\n" +"è configurato senza una password." + +#: modules/commands/os_login.cpp:94 +#, c-format +msgid "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." +msgstr "" +"Effettua il logout da %s in modo da perdere i privilegi di Services " +"Operator.\n" +"Questo comando è utile solamente se il tuo oper block\n" +"è configurato con una password." + +#: modules/commands/cs_seen.cpp:213 +#, c-format +msgid "Looking for yourself, eh %s?" +msgstr "Stai cercando te stesso, %s?" + +#: modules/commands/cs_mode.cpp:773 +#, c-format +msgid "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a " +"channel.\n" +"If a mode is locked on or off, services will not allow that mode to be " +"changed. The SET\n" +"command will clear all existing mode locks and set the new one given, while " +"ADD and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * " +"and ? may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may " +"be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, " +"halfops, and voices. If what\n" +"is not given then all basic modes are removed." +msgstr "" +"Controlla principalmente il blocco dei modi e l'accesso ai modi (che è una " +"cosa diversa dall'accesso al canale)\n" +"in un canale.\n" +" \n" +"Il comando %s LOCK permette di aggiungere, rimuovere, e vedere il blocco dei " +"modi in un canale.\n" +"Se un modo è bloccato o disattivato, i services non permetteranno a quel " +"modo di essere cambiato.\n" +"Il comando SET rimuovera tutti i modi bloccati e imposterà i nuovi modi " +"specificati, mentre ADD e DEL\n" +"apportano modifiche ai modi bloccati esistenti.\n" +"Esempi:\n" +" MODE #canale LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"Il comando %s SET permette di impostare i modi utilizzando i services. Le " +"wildcards * e ? possono\n" +"essere specificate come parametri per le liste e gli status modi.\n" +"Esempi:\n" +" MODE #canale SET +v *\n" +" Imposta lo stato di voice a tutti gli utenti presenti nel canale.\n" +" \n" +" MODE #canale SET -b c:*\n" +" Rimuove tutti i ban estesi che iniziano con c:\n" +" \n" +"Il comando %s CLEAR è un modo semplice per rimuovere tutti i modi in un " +"canale. \"cosa\" può essere\n" +"uno tra bans, exempts, inviteoverrides, ops, halfops, or voices. Se il " +"parametro \"cosa\" è omesso, allora\n" +"tutti i modi saranno rimossi dal canale." + +#: modules/commands/cs_akick.cpp:434 +msgid "Maintain the AutoKick list" +msgstr "Modifica la lista AutoKick" + +#: modules/commands/bs_bot.cpp:269 +msgid "Maintains network bot list" +msgstr "Gestisce la lista dei bot disponibili" + +#: modules/commands/cs_xop.cpp:522 +#, c-format +msgid "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " +msgstr "" +"Gestisce la lista %s di un canale. Gli utenti che vengono aggiunti\n" +"nella lista %s ricevono i seguenti privilegi:\n" +" " + +#: modules/commands/cs_akick.cpp:493 +#, c-format +msgid "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" +msgstr "" +"Gestice la lista AutoKick. Se un utente che si trova nella\n" +"cerca di entrare nel canale, %s imposterà un ban su di esso\n" +"e in seguito lo espellerà dal canale. \n" +"Il comando AKICK ADD aggiunge il nick o la mask specificata\n" +"alla lista AutoKick. Se viene specificato un motivo, sarà\n" +"utilizzato quando l'utente viene espulso, altrimenti\n" +"verrà utilizzata la frase standard \"Sei stato bannato\n" +"dal canale\".\n" +"Quando viene usato un AKICK su un nick registrato\n" +"l'AKICK sarà aggiunto sull'account %s anzichè sulla mask.\n" +"Tutti i nickname presenti nel gruppo dell'account saranno in AKICK.\n" + +#: modules/commands/cs_access.cpp:568 +#, c-format +msgid "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." +msgstr "" +"Gestisce la lista di accesso del canale. La lista\n" +"list di accesso specifica quali utenti hanno diritto\n" +"allo stato di operatore di canale e ai vari comandi di\n" +"di %s. Livelli utente diversi permettono l'accesso\n" +"a diversi sottoinsiemi di privilegi. Qualsiasi utente\n" +"registrato non presente nella lista di accesso del canale\n" +"ha livello utente 0, e qualsiasi utente non registrato\n" +"ha livello utente -1." + +#: modules/commands/bs_badwords.cpp:424 +#, c-format +msgid "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" +msgstr "" +"Gestisce la lista delle parolacce di un canale.\n" +"La lista delle parolacce indica quali parole devono\n" +"attivare un kick, quando il kick su parolacce\n" +"è attivo. Per maggiori informazioni, digita\n" +"%s%s HELP KICK %s.\n" +" \n" +"Il comando ADD aggiunge la parola specificata\n" +"alla lista parolacce. Se viene specificato SINGLE,\n" +"il kick sarà effettuato solo se un utente dice la parola\n" +"integralmente. Se viene specificato START, il kick sarà\n" +"effettuato se un utente dice una parola che inizia con\n" +"parola. Se viene specificato END, il kick sarà effettuato\n" +"se un utente dice una parola che termina con parola.\n" +"Se non viene specificata nessuna opzione, il kick sarà\n" +"effettuato ogni volta che un utente scriverà la parola.\n" +" \n" + +#: modules/commands/bs_badwords.cpp:370 +msgid "Maintains the bad words list" +msgstr "Gestisce la lista delle parolacce" + +#: modules/commands/bs_control.cpp:79 +msgid "Makes the bot do the equivalent of a \"/me\" command" +msgstr "Fa sì che il bot invii l'equivalente di un comando \"/me\"" + +#: modules/commands/bs_control.cpp:127 +msgid "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." +msgstr "" +"Fa sì che il bot invii l'equivalente di un comando \"/me\"\n" +"nel canale specificato utilizzando il testo specificato." + +#: modules/commands/bs_control.cpp:19 +msgid "Makes the bot say the specified text on the specified channel" +msgstr "Fa sì che il bot scriva il testo specificato nel canale specificato" + +#: modules/commands/bs_control.cpp:69 +msgid "Makes the bot say the specified text on the specified channel." +msgstr "Fa sì che il bot scriva il testo specificato nel canale specificato." + +#: modules/commands/greet.cpp:157 +msgid "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." +msgstr "" +"Imposta come saluto del nick il messaggio specificato.\n" +"Il saluto sarà mostrato quando si accede ad un canale che ha\n" +"l'opzione GREET attiva, se in possesso del livello di accesso\n" +"necessario." + +#: modules/commands/greet.cpp:131 +msgid "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." +msgstr "" +"Imposta come saluto del nick il messaggio specificato.\n" +"Il saluto sarà mostrato quando si accede ad un canale che ha\n" +"l'opzione GREET attiva, se in possesso del livello di accesso\n" +"necessario." + +#: modules/commands/os_dns.cpp:660 +msgid "Manage DNS zones for this network" +msgstr "Gestisce le zone DNS per questo network" + +#: modules/commands/cs_entrymsg.cpp:193 +msgid "Manage the channel's entry messages" +msgstr "Gestisce il messaggio di ingresso del canale" + +#: modules/commands/ms_ignore.cpp:19 +msgid "Manage the memo ignore list" +msgstr "Gestisce la lista ignore dei memo" + +#: modules/commands/ns_ajoin.cpp:230 +msgid "Manage your auto join list" +msgstr "Gestisce la tua lista auto join" + +#: modules/commands/os_sxline.cpp:233 +#, c-format +msgid "Manipulate the %s list" +msgstr "Gestisce la lista %s" + +#: modules/commands/os_akill.cpp:385 +msgid "Manipulate the AKILL list" +msgstr "Gestisce la lista AKILL" + +#: modules/commands/os_defcon.cpp:176 +msgid "Manipulate the DefCon system" +msgstr "Gestisce il sistema DefCon" + +#: modules/commands/cs_topic.cpp:149 +msgid "Manipulate the topic of the specified channel" +msgstr "Gestisce il topic del canale specificato" + +#: modules/commands/bs_botlist.cpp:27 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_forbid.cpp:358 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/ms_ignore.cpp:86 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_list.cpp:153 modules/commands/bs_info.cpp:55 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +msgid "Mask" +msgstr "Mask" + +#: modules/commands/ns_access.cpp:39 +#, c-format +msgid "Mask %s already present on %s's access list." +msgstr "La mask %s è già presente lista di accesso di %s." + +#: include/language.h:67 +msgid "Mask must be in the form user@host." +msgstr "La mask deve essere nel formato user@host." + +#: modules/commands/cs_access.cpp:166 modules/commands/cs_flags.cpp:120 +#: modules/commands/cs_xop.cpp:162 +msgid "Masks and unregistered users may not be on access lists." +msgstr "" +"Mask e utenti non registrati non possono essere aggiunti in una lista di " +"accesso." + +#: modules/commands/ns_getemail.cpp:23 +msgid "Matches and returns all users that registered using given email" +msgstr "" +"Mostra l'elenco degli utenti registratisi con l'indirizzo email specificato" + +#: modules/commands/os_logsearch.cpp:148 +#, c-format +msgid "Matches for %s:" +msgstr "Risultati per %s:" + +#: modules/commands/os_stats.cpp:139 +#, c-format +msgid "Maximum users: %d (%s)" +msgstr "Utenti massimi: %d (%s)" + +#: modules/commands/ms_read.cpp:84 modules/commands/ms_read.cpp:86 +#, c-format +msgid "Memo %d from %s (%s)." +msgstr "Memo %d da %s (%s)." + +#: modules/commands/ms_del.cpp:33 modules/commands/ms_del.cpp:101 +#, c-format +msgid "Memo %d has been deleted." +msgstr "Il memo %d è stato cancellato." + +#: modules/commands/ms_ignore.cpp:82 +msgid "Memo ignore list is empty." +msgstr "La lista ignore dei memo è vuota." + +#: modules/commands/ms_set.cpp:199 +#, c-format +msgid "Memo limit disabled for %s." +msgstr "Il limite dei memo di %s è stato disabilitato." + +#: modules/commands/ms_set.cpp:185 +#, c-format +msgid "Memo limit for %s set to %d." +msgstr "Il limite dei memo di %s è stato impostato a %d." + +#: modules/commands/ms_set.cpp:192 +#, c-format +msgid "Memo limit for %s set to 0." +msgstr "Il limite dei memo di %s è stato impostato a 0." + +#: modules/commands/ms_rsend.cpp:63 modules/commands/ms_send.cpp:51 +#, c-format +msgid "Memo sent to %s." +msgstr "Memo inviato a %s." + +#: modules/commands/ms_list.cpp:131 +#, c-format +msgid "Memos for %s:" +msgstr "Memo per %s:" + +#: modules/commands/cs_entrymsg.cpp:116 +msgid "Message" +msgstr "Messaggio" + +#: modules/commands/ns_set.cpp:1313 +msgid "Message mode" +msgstr "Modalità messaggio" + +#: modules/commands/cs_log.cpp:127 +msgid "Method" +msgstr "Metodo" + +#: modules/commands/cs_mode.cpp:329 modules/commands/cs_mode.cpp:420 +#, c-format +msgid "Missing parameter for mode %c." +msgstr "Parametro mancante per il modo %c." + +#: modules/commands/cs_mode.cpp:449 +msgid "Mode" +msgstr "Modo" + +#: modules/commands/cs_mode.cpp:718 +#, fuzzy, c-format +msgid "Mode %s is a virtual mode and can't be cleared." +msgstr "Il nick %s è un nickname non autorizzato e non può essere utilizzato." + +#: modules/commands/cs_mode.cpp:712 +#, c-format +msgid "Mode %s is not a status or list mode." +msgstr "Il modo %s non è modo di stato o di lista." + +#: modules/commands/cs_mode.cpp:1065 +msgid "Mode lock" +msgstr "Modi bloccati" + +#: modules/commands/cs_mode.cpp:466 +#, c-format +msgid "Mode locks for %s:" +msgstr "Modi bloccati per %s:" + +#: modules/commands/os_list.cpp:43 +msgid "Modes" +msgstr "Modi" + +#: modules/commands/os_mode.cpp:44 +#, c-format +msgid "Modes cleared on %s and the channel destroyed." +msgstr "Modi rimossi su %s e canale distrutto." + +#: modules/commands/ns_access.cpp:166 +#, c-format +msgid "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." +msgstr "" +"Visualizza o modifica la lista di accesso per il tuo nick.\n" +"Si tratta della lista degli indirizzi che saranno riconosciuti\n" +"automaticamente da %s e che ti permetteranno di utilizzare\n" +"il tuo nick. Se vuoi usare il nick da indirizzi diversi, dovrai\n" +"utilizzare il comando IDENTIFY per farti riconoscere da %s.\n" +"I Services Operators possono specificare un nick per modificare.\n" +"la lista di accesso degli altri utenti.\n" +"Esempi:\n" +"\n" +" ACCESS ADD pippo@*.disney.it\n" +" Permette l'accesso all'utente con ident pippo da\n" +" qualsiasi macchina all'interno del dominio disney.it.\n" +"\n" +" ACCESS DEL pippo@*.disney.it\n" +" Annulla l'effetto del comando precedente.\n" +"\n" +" ACCESS LIST\n" +" Visualizza la lista di accesso attuale." + +#: modules/commands/ns_cert.cpp:319 +msgid "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" +msgstr "" +"Visualizza o modifica la lista dei certificati per il tuo nick.\n" +"Se ti connetti a IRC e il tuo client fornisce un certificato con\n" +"una firma digitale corrispondente nella lista dei certificati, il\n" +"tuo nick sarà indentificato automaticamente con i services.\n" +"I Services Operators possono specificare un nick per modificare la\n" +"lista dei certificati degli altri utenti.\n" +" \n" + +#: modules/commands/os_ignore.cpp:341 +msgid "Modify the Services ignore list" +msgstr "Modifica la lista ignore dei Services" + +#: modules/commands/cs_xop.cpp:489 +#, c-format +msgid "Modify the list of %s users" +msgstr "Modifica la lista degli utenti %s" + +#: modules/commands/ns_access.cpp:101 +msgid "Modify the list of authorized addresses" +msgstr "Modifica la lista degli indirizzi autorizzati" + +#: modules/commands/cs_access.cpp:498 modules/commands/cs_flags.cpp:373 +msgid "Modify the list of privileged users" +msgstr "Modifica la lista degli utenti con privilegi" + +#: modules/commands/ns_cert.cpp:257 +msgid "Modify the nickname client certificate list" +msgstr "Modifica la lista dei certificati del client per il nickname" + +#: modules/commands/os_session.cpp:522 +msgid "Modify the session-limit exception list" +msgstr "Modifica la lista delle eccezioni del limite delle sessioni" + +#: modules/commands/os_module.cpp:34 +#, c-format +msgid "Module %s is already loaded." +msgstr "Il modulo %s è già caricato." + +#: modules/commands/os_module.cpp:67 modules/commands/os_module.cpp:139 +#, c-format +msgid "Module %s isn't loaded." +msgstr "Il modulo %s non è caricato." + +#: modules/commands/os_module.cpp:31 +#, c-format +msgid "Module %s loaded." +msgstr "Modulo %s caricato." + +#: modules/commands/os_module.cpp:98 +#, c-format +msgid "Module %s reloaded." +msgstr "Modulo %s ricaricato." + +#: modules/commands/os_module.cpp:156 +#, c-format +msgid "Module %s unloaded." +msgstr "Modulo %s rimosso." + +#: modules/commands/os_config.cpp:88 +msgid "Module Name" +msgstr "Nome Modulo" + +#: modules/commands/os_config.cpp:112 +msgid "Module settings:" +msgstr "Impostazioni Modulo:" + +#: modules/commands/os_modinfo.cpp:32 +#, c-format +msgid "Module: %s Version: %s Author: %s Loaded: %s" +msgstr "Modulo: %s Versione: %s Autore: %s caricato: %s" + +#: modules/commands/os_modinfo.cpp:183 +#, c-format +msgid "Module: %s [%s] [%s]" +msgstr "Modulo: %s [%s] [%s]" + +#: modules/commands/cs_access.cpp:697 modules/commands/cs_access.cpp:799 +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +#: modules/commands/cs_list.cpp:75 modules/commands/os_list.cpp:43 +#: modules/commands/os_list.cpp:153 +msgid "Name" +msgstr "Nome" + +#: modules/commands/os_oper.cpp:153 +msgid "Name Type" +msgstr "Nome Tipo" + +#: modules/extra/stats/cs_fantasy_stats.cpp:146 +#, c-format +msgid "Network stats for %s:" +msgstr "Statistiche network per %s:" + +#: modules/commands/os_forbid.cpp:384 +msgid "Never" +msgstr "Mai" + +#: modules/commands/hs_list.cpp:58 modules/commands/bs_botlist.cpp:27 +#: modules/commands/hs_request.cpp:305 modules/commands/ns_list.cpp:75 +#: modules/commands/ns_group.cpp:327 +msgid "Nick" +msgstr "Nick" + +#: modules/commands/ns_register.cpp:42 +#, c-format +msgid "Nick %s has been confirmed." +msgstr "Il nick %s è stato confermato." + +#: modules/commands/os_oper.cpp:95 +#, c-format +msgid "Nick %s is already an operator." +msgstr "Il nick %s è già un operatore." + +#: modules/commands/ns_register.cpp:36 +#, c-format +msgid "Nick %s is already confirmed." +msgstr "Il nick %s è già stato confermato." + +#: modules/commands/os_svs.cpp:46 +#, c-format +msgid "Nick %s is an illegal nickname and cannot be used." +msgstr "Il nick %s è un nickname non autorizzato e non può essere utilizzato." + +#: modules/commands/bs_bot.cpp:81 modules/commands/bs_bot.cpp:181 +#: modules/commands/os_svs.cpp:54 +#, c-format +msgid "Nick %s is currently in use." +msgstr "Il nick %s è attualmente in uso." + +#: modules/commands/os_forbid.cpp:512 +#, c-format +msgid "Nick %s is forbidden by %s: %s" +msgstr "Il nick %s è stato vietato da %s: %s" + +#: modules/commands/os_forbid.cpp:514 +#, c-format +msgid "Nick %s is forbidden." +msgstr "Il nick %s è vietato." + +#: modules/commands/os_oper.cpp:134 +#, c-format +msgid "Nick %s is not a Services Operator." +msgstr "%s non è un Services Operator." + +#: modules/commands/ns_info.cpp:34 +#, c-format +msgid "Nick %s is part of this Network's Services." +msgstr "Il nick %s fa parte dei servizi di questo network." + +#: include/language.h:79 +#, c-format +msgid "Nick %s isn't currently in use." +msgstr "Il nick %s non è attualmente in uso." + +#: include/language.h:78 +#, c-format +msgid "Nick %s isn't registered." +msgstr "Il nickname %s non è registrato." + +#: modules/commands/os_svs.cpp:39 +#, c-format +msgid "Nick %s was truncated to %d characters." +msgstr "Il nick %s è stato troncato a %d caratteri." + +#: modules/commands/ns_set.cpp:1135 +#, c-format +msgid "Nick %s will expire." +msgstr "Il nick %s scadrà." + +#: modules/commands/ns_set.cpp:1129 +#, c-format +msgid "Nick %s will not expire." +msgstr "Il nick %s non scadrà." + +#: modules/commands/ms_check.cpp:60 +#, c-format +msgid "Nick %s doesn't have a memo from you." +msgstr "Il nick %s non ha un tuo memo." + +#: modules/commands/ns_logout.cpp:48 +#, c-format +msgid "Nick %s has been logged out." +msgstr "Il nick %s è stato deidentificato." + +#: modules/commands/ns_group.cpp:272 +#, c-format +msgid "Nick %s has been ungrouped from %s." +msgstr "Il nick %s è stato rimosso dal gruppo da %s." + +#: include/language.h:81 +#, c-format +msgid "Nick %s is currently suspended." +msgstr "Il nick %s è attualmente sospeso." + +#: modules/commands/ns_group.cpp:250 +#, c-format +msgid "Nick %s is not in your group." +msgstr "Il nick %s non è nel tuo gruppo." + +#: modules/commands/ns_suspend.cpp:180 +#, c-format +msgid "Nick %s is not suspended." +msgstr "Il nick %s non è sospeso." + +#: modules/commands/ns_suspend.cpp:190 +#, c-format +msgid "Nick %s is now released." +msgstr "Il nick %s è ora rilasciato." + +#: modules/commands/ns_suspend.cpp:138 +#, c-format +msgid "Nick %s is now suspended." +msgstr "Il nick %s è ora sospeso." + +#: modules/commands/cs_seen.cpp:275 +#, c-format +msgid "Nick too long, max length is %u characters." +msgstr "Nick troppo lungo, lunghezza massima consentita %u caratteri." + +#: modules/commands/ns_drop.cpp:53 +#, c-format +msgid "Nickname %s has been dropped." +msgstr "Il nickname %s è stato deregistrato." + +#: include/language.h:97 +#, c-format +msgid "Nickname %s is already registered!" +msgstr "Il nickname %s è già registrato!" + +#: include/language.h:96 +#, c-format +msgid "Nickname %s may not be registered." +msgstr "Il nickname %s non può essere registrato." + +#: modules/commands/ns_register.cpp:226 +#, c-format +msgid "Nickname %s registered under your user@host-mask: %s" +msgstr "Il nick %s è stato registrato sotto la tua user@host-mask: %s" + +#: modules/commands/ns_register.cpp:228 +#, c-format +msgid "Nickname %s registered." +msgstr "Nickname %s registrato." + +#: modules/commands/cs_set.cpp:1307 +msgid "No auto-op" +msgstr "No auto-op" + +#: modules/commands/bs_assign.cpp:252 +msgid "No bot" +msgstr "Nessun bot" + +#: modules/commands/cs_set.cpp:1303 modules/commands/ns_set.cpp:1317 +msgid "No expire" +msgstr "Nessuna scadenza" + +#: modules/commands/help.cpp:184 +#, c-format +msgid "No help available for %s." +msgstr "Nessun aiuto disponibile per %s." + +#: modules/commands/os_modinfo.cpp:61 +#, c-format +msgid "No information about module %s is available." +msgstr "Nessun'informazione sul modulo %s è disponibile." + +#: modules/commands/cs_enforce.cpp:177 +#, c-format +msgid "No limit is set on %s." +msgstr "Nessun limite impostato su %s." + +#: modules/commands/os_news.cpp:37 +msgid "No logon news items to delete!" +msgstr "Nessuna Logon News da eliminare!" + +#: modules/commands/os_logsearch.cpp:133 +#, c-format +msgid "No matches for %s found." +msgstr "Nessuna corrispondenza trovata per %s." + +#: modules/commands/cs_xop.cpp:294 +#, c-format +msgid "No matching entries on %s %s list." +msgstr "Nessun record corrispondente nella lista %2$s di %1$s." + +#: modules/commands/cs_access.cpp:269 modules/commands/cs_access.cpp:433 +#: modules/commands/cs_flags.cpp:335 modules/commands/cs_xop.cpp:428 +#, c-format +msgid "No matching entries on %s access list." +msgstr "Nessun record corrispondente nella lista di accesso di %s." + +#: modules/commands/cs_akick.cpp:224 modules/commands/cs_akick.cpp:368 +#, c-format +msgid "No matching entries on %s autokick list." +msgstr "Nessun record corrispondente nella lista autokick di %s." + +#: modules/commands/bs_badwords.cpp:166 modules/commands/bs_badwords.cpp:246 +#, c-format +msgid "No matching entries on %s bad words list." +msgstr "Nessun record corrispondente nella lista delle parolacce di %s." + +#: modules/commands/os_session.cpp:145 modules/commands/os_session.cpp:490 +msgid "No matching entries on session-limit exception list." +msgstr "Nessun record corrispondente nella lista delle eccezioni." + +#: modules/commands/os_sxline.cpp:28 modules/commands/os_sxline.cpp:177 +#, c-format +msgid "No matching entries on the %s list." +msgstr "Nessun record corrispondente nella lista %s." + +#: modules/commands/os_akill.cpp:29 modules/commands/os_akill.cpp:320 +msgid "No matching entries on the AKILL list." +msgstr "Nessun record corrispondente nella lista AKILL." + +#: modules/commands/ms_cancel.cpp:77 +msgid "No memo was cancelable." +msgstr "Nessun memo è annullabile." + +#: modules/commands/ms_read.cpp:65 +msgid "No memos to display." +msgstr "Nessun memo da mostrare." + +#: modules/commands/os_modinfo.cpp:187 +msgid "No modules currently loaded matching that criteria." +msgstr "Nessn modulo attualmente caricato corrisponde quei criteri." + +#: modules/commands/ns_recover.cpp:55 +msgid "No one is using your nick, and services are not holding it." +msgstr "" +"Nessuno sta usando il tuo nick, e attualmente non è trattenuto dai service." + +#: modules/commands/os_login.cpp:30 modules/commands/os_login.cpp:77 +msgid "No oper block for your nick." +msgstr "Nessun oper block per il tuo nick." + +#: modules/commands/os_news.cpp:47 +msgid "No oper news items to delete!" +msgstr "Nessuna Oper News da eliminare!" + +#: modules/commands/os_news.cpp:57 +msgid "No random news items to delete!" +msgstr "Nessuna Random News da eliminare!" + +#: modules/commands/hs_list.cpp:111 +msgid "No records to display." +msgstr "Nessun risultato da mostrare." + +#: modules/commands/ns_getemail.cpp:47 +#, c-format +msgid "No registrations matching %s were found." +msgstr "Nessuna registrazione corrispondente %s è stata trovata." + +#: modules/commands/hs_request.cpp:220 modules/commands/hs_request.cpp:276 +#, c-format +msgid "No request for nick %s found." +msgstr "Nessuna richista trovata per il nick %s." + +#: src/access.cpp:55 +msgid "No signed kick when SIGNKICK LEVEL is used" +msgstr "No kick firmati quanto è usato SIGNKICK LEVEL" + +#: modules/extra/stats/cs_fantasy_top.cpp:159 +#: modules/extra/stats/cs_fantasy_stats.cpp:156 +#, c-format +msgid "No stats for %s." +msgstr "Non ci sono stats per %s." + +#: modules/commands/os_info.cpp:201 +#, c-format +msgid "No such info \"%s\" on %s." +msgstr "Nessuna informazione \"%s\" su %s." + +#: modules/commands/cs_ban.cpp:219 modules/commands/cs_kick.cpp:118 +#, c-format +msgid "No users on %s match %s." +msgstr "Nessun user su %s corrisponde a %s." + +#: modules/commands/bs_assign.cpp:188 +#, c-format +msgid "No-bot mode is now off on channel %s." +msgstr "La modalità No Bot ora è disattivata nel canale %s." + +#: modules/commands/bs_assign.cpp:181 +#, c-format +msgid "No-bot mode is now on on channel %s." +msgstr "La modalità No Bot ora è attiva nel canale %s." + +#: modules/commands/os_mode.cpp:64 +#, c-format +msgid "Non-status modes cleared on %s." +msgstr "Modi non di stato eliminati su %s." + +#: modules/commands/os_dns.cpp:226 modules/commands/bs_info.cpp:58 +msgid "None" +msgstr "Nessuna" + +#: modules/commands/cs_set.cpp:1029 +#, fuzzy, c-format +msgid "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." +msgstr "" +"Comunque, se il successore ha già troppi canali registrati (%d),\n" +"il canale sarà deregistrato, come se il successore non fosse \n" +"stato impostato." + +#: modules/commands/cs_mode.cpp:380 modules/commands/cs_mode.cpp:437 +msgid "Nothing to do." +msgstr "Niente da eseguire." + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:201 modules/commands/ms_list.cpp:64 +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_log.cpp:127 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +#: modules/commands/ns_ajoin.cpp:100 +msgid "Number" +msgstr "Numero" + +#: modules/commands/os_news.cpp:41 +msgid "OPERNEWS {ADD|DEL|LIST} [text|num]" +msgstr "OPERNEWS {ADD|DEL|LIST} [testo|numero]" + +#: modules/commands/ns_info.cpp:68 modules/commands/ns_info.cpp:72 +msgid "Online from" +msgstr "Connesso da" + +#: modules/commands/os_oper.cpp:138 +#, c-format +msgid "" +"Oper %s is configured in the configuration file(s) and can not be removed by " +"this command." +msgstr "" +"L'oper %s è configurato nel file di configurazione e non può essere rimosso " +"da questo comando." + +#: modules/commands/os_info.cpp:268 +msgid "Oper Info" +msgstr "Informazioni Operatore" + +#: modules/commands/os_info.cpp:182 modules/commands/os_info.cpp:221 +#, c-format +msgid "Oper info list for %s is empty." +msgstr "La lista oper info per %s è vuota." + +#: modules/commands/os_news.cpp:46 +#, c-format +msgid "Oper news item #%d deleted." +msgstr "La Oper News numero %d è stata eliminata." + +#: modules/commands/os_news.cpp:45 +#, c-format +msgid "Oper news item #%s not found!" +msgstr "Impossibile trovare la Oper News #%s!" + +#: modules/commands/os_news.cpp:42 +msgid "Oper news items:" +msgstr "Lista delle Oper News:" + +#: modules/commands/os_oper.cpp:148 +#, c-format +msgid "Oper privileges removed from %s (%s)." +msgstr "Privilegi di operatore rimossi da %s (%s)." + +#: modules/commands/os_oper.cpp:101 modules/commands/os_oper.cpp:189 +#, c-format +msgid "Oper type %s has not been configured." +msgstr "Il tipo di operatore %s non è stato configurato." + +#: modules/commands/os_oline.cpp:37 +#, c-format +msgid "Operflags %s have been added for %s." +msgstr "Le operflags %s sono state aggiunte a %s." + +#: modules/commands/os_oline.cpp:43 +#, c-format +msgid "Operflags %s have been removed from %s." +msgstr "Le operflags %s sono state rimosse a %s." + +#: modules/commands/os_oper.cpp:193 +#, c-format +msgid "Opertype %s has no allowed commands." +msgstr "Il tipo di oper %s non ha comandi permessi." + +#: modules/commands/os_oper.cpp:215 +#, c-format +msgid "Opertype %s has no allowed privileges." +msgstr "Il tipo di oper %s non ha privilegi permessi." + +#: modules/commands/os_oper.cpp:237 +#, c-format +msgid "Opertype %s receives modes %s once identified." +msgstr "Il tipo di oper %s riceve i modi %s quando si identifica." + +#: modules/commands/bs_kick.cpp:1219 +msgid "Ops protection" +msgstr "Protezione per gli op" + +#: src/misc.cpp:258 modules/commands/bs_info.cpp:58 +msgid "Options" +msgstr "Opzioni" + +#: modules/commands/os_dns.cpp:668 +msgid "POOL server.name" +msgstr "POOL server.nome" + +#: modules/commands/cs_mode.cpp:449 +msgid "Param" +msgstr "Parametro" + +#: modules/commands/ns_identify.cpp:38 +msgid "Password accepted - you are now recognized." +msgstr "Password accettata - adesso sei riconosciuto." + +#: modules/commands/os_login.cpp:44 +msgid "Password accepted." +msgstr "Password accettata." + +#: include/language.h:85 +msgid "Password authentication required for that command." +msgstr "Autenticazione con password richiesta per questo comando." + +#: modules/commands/ns_set.cpp:152 modules/commands/ns_set.cpp:218 +#, c-format +msgid "Password for %s changed to %s." +msgstr "La password di %s è stata cambiata in %s." + +#: modules/commands/ns_set.cpp:154 modules/commands/ns_set.cpp:220 +#, c-format +msgid "Password for %s changed." +msgstr "La password di %s è stata cambiata." + +#: modules/commands/ns_getpass.cpp:38 +#, c-format +msgid "Password for %s is %s." +msgstr "La password di %s è %s." + +#: include/language.h:71 +msgid "Password incorrect." +msgstr "Password errata." + +#: modules/commands/ns_resetpass.cpp:39 +#, c-format +msgid "Password reset email for %s has been sent." +msgstr "È stata inviata una email per il reset della password di %s." + +#: modules/commands/cs_set.cpp:1289 +msgid "Peace" +msgstr "Pace" + +#: modules/commands/cs_set.cpp:440 +#, c-format +msgid "Peace option for %s is now off." +msgstr "L'opzione pace per %s è ora disattivata." + +#: modules/commands/cs_set.cpp:434 +#, c-format +msgid "Peace option for %s is now on." +msgstr "L'opzione pace per %s è ora attiva." + +#: modules/commands/cs_set.cpp:1301 +msgid "Persistent" +msgstr "Persistenza" + +#: include/language.h:126 +msgid "Please contact an Operator to get a vHost assigned to this nick." +msgstr "" +"Per favore contatta un Operatore per avere un vHost assegnato a questo nick." + +#: include/language.h:73 +msgid "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." +msgstr "" +"Attenzione, prova di nuovo con una password più sicura. Le password devono " +"essere lunghe almeno\n" +"5 caratteri, non devono essere facilmente intuibili (ad es. il proprio nome " +"o nick)\n" +"e non possono contenere i caratteri di spazio e di tabulazione." + +#: modules/commands/os_jupe.cpp:30 +msgid "Please use a valid server name when juping." +msgstr "Utilizza un nome server valido per eseguire il jupe." + +#: include/language.h:104 +msgid "Please use the symbol of # when attempting to register." +msgstr "" +"Per favore usa il simbolo # davanti al nome del canale per poter procedere " +"con la registrazione." + +#: src/mail.cpp:78 +#, c-format +msgid "Please wait %d seconds and retry." +msgstr "Attendi %d secondi è riprova." + +#: modules/commands/hs_request.cpp:158 +#, c-format +msgid "Please wait %d seconds before requesting a new vHost." +msgstr "Attendi %d secondi prima di richiedere un nuovo vHost." + +#: modules/commands/ms_rsend.cpp:58 modules/commands/ms_send.cpp:57 +#, c-format +msgid "Please wait %d seconds before using the %s command again." +msgstr "Attendi %d secondi prima di usare di nuovo il comando %s." + +#: modules/commands/ns_group.cpp:149 +#, c-format +msgid "Please wait %d seconds before using the GROUP command again." +msgstr "" +"Per favore attendi %d secondi prima di usare di nuovo il comando GROUP." + +#: modules/commands/ns_register.cpp:198 +#, c-format +msgid "Please wait %d seconds before using the REGISTER command again." +msgstr "" +"Per favore attendi %d secondi prima di usare di nuovo il comando REGISTER." + +#: modules/commands/os_dns.cpp:628 +#, c-format +msgid "Pooled %s." +msgstr "Pooled %s." + +#: modules/commands/os_dns.cpp:237 +msgid "Pooled/Active" +msgstr "Pooled/Attivo" + +#: modules/commands/os_dns.cpp:239 +msgid "Pooled/Not Active" +msgstr "Pooled/Non Attivo" + +#: modules/commands/bs_set.cpp:161 +msgid "Prevent a bot from being assigned by non IRC operators" +msgstr "Impedisce che un bot venga assegnato da un non IRC operator" + +#: modules/commands/bs_assign.cpp:153 +msgid "Prevent a bot from being assigned to a channel" +msgstr "Impedisce che un bot venga assegnato ad un canale" + +#: modules/commands/cs_suspend.cpp:58 +msgid "Prevent a channel from being used preserving channel data and settings" +msgstr "Impedisce l'utilizzo di un canale mantenendone dati e impostazioni" + +#: modules/commands/cs_set.cpp:1043 +msgid "Prevent the channel from expiring" +msgstr "Impedisce ad un canale di scadere" + +#: modules/commands/ns_list.cpp:186 +msgid "Prevent the nickname from appearing in the LIST command" +msgstr "Nasconde il nickname dall'output del comando LIST" + +#: modules/commands/ns_set.cpp:1104 +msgid "Prevent the nickname from expiring" +msgstr "Impedisce ad un nickname di scadere" + +#: src/access.cpp:46 +msgid "Prevents users being kicked by Services" +msgstr "Impedisce agli utenti di essere espulsi dai Services" + +#: modules/commands/ns_list.cpp:297 modules/commands/cs_list.cpp:262 +#: modules/commands/bs_info.cpp:58 +msgid "Private" +msgstr "Privato" + +#: modules/commands/bs_set.cpp:190 +#, c-format +msgid "Private mode of bot %s is now off." +msgstr "La modalità Private del bot %s ora è disattivata." + +#: modules/commands/bs_set.cpp:185 +#, c-format +msgid "Private mode of bot %s is now on." +msgstr "La modalità private del bot %s ora è attiva." + +#: modules/commands/cs_list.cpp:220 +#, c-format +msgid "Private option for %s is now off." +msgstr "L'opzione private per %s è ora disattivata." + +#: modules/commands/cs_list.cpp:214 +#, c-format +msgid "Private option for %s is now on." +msgstr "L'opzione private per %s è ora attiva." + +#: modules/commands/ns_list.cpp:221 +#, c-format +msgid "Private option is now off for %s." +msgstr "L'opzione private è adesso disattivata per %s." + +#: modules/commands/ns_list.cpp:215 +#, c-format +msgid "Private option is now on for %s." +msgstr "L'opzione private è adesso attiva per %s." + +#: modules/commands/cs_flags.cpp:281 +#, c-format +msgid "Privilege %s added to %s on %s, new flags are +%s" +msgstr "Il privilegio %s è stato aggiunto a %s su %s, le nuove flags sono +%s" + +#: modules/commands/cs_flags.cpp:283 +#, c-format +msgid "Privilege %s removed from %s on %s, new flags are +%s" +msgstr "Il privilegio %s è stato rimosso a %s su %s, le nuove flags sono +%s" + +#: modules/commands/ns_set.cpp:1309 +msgid "Protection" +msgstr "Protezione" + +#: modules/commands/ns_set.cpp:721 +#, c-format +msgid "Protection is now off for %s." +msgstr "La protezione è adesso disattivata per %s." + +#: modules/commands/ns_set.cpp:700 +#, c-format +msgid "Protection is now on for %s, with a reduced delay." +msgstr "La protezione è adesso attiva per %s, con un ritardo ridotto." + +#: modules/commands/ns_set.cpp:710 +#, c-format +msgid "Protection is now on for %s, with no delay." +msgstr "La protezione è adesso attiva per %s, senza ritardo." + +#: modules/commands/ns_set.cpp:692 +#, c-format +msgid "Protection is now on for %s." +msgstr "La protezione è adesso attiva per %s." + +#: modules/commands/os_chankill.cpp:100 +msgid "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." +msgstr "" +"Imposta un AKILL per tutti i nick presenti nel canale specificato.\n" +"Utilizza la mask completa ident@host per ogni nick,\n" +"in seguito imposta l'AKILL." + +#: modules/commands/ns_set.cpp:1307 +msgid "Quick protection" +msgstr "Protezione rapida" + +#: modules/commands/os_news.cpp:51 +msgid "RANDOMNEWS {ADD|DEL|LIST} [text|num]" +msgstr "RANDOMNEWS {ADD|DEL|LIST} [text|num]" + +#: modules/commands/cs_enforce.cpp:99 +msgid "REGONLY enforced by " +msgstr "REGONLY forzato da " + +#: modules/commands/cs_enforce.cpp:68 +msgid "RESTRICTED enforced by " +msgstr "RESTRICTED forzato da " + +#: modules/commands/os_noop.cpp:21 +msgid "REVOKE server" +msgstr "REVOKE server" + +#: modules/commands/os_news.cpp:56 +#, c-format +msgid "Random news item #%d deleted." +msgstr "La Random News numero #%d è stata eliminata." + +#: modules/commands/os_news.cpp:55 +#, c-format +msgid "Random news item #%s not found!" +msgstr "Impossibile trovare la Random News numero #%s!" + +#: modules/commands/os_news.cpp:52 +msgid "Random news items:" +msgstr "Lista delle Random News:" + +#: modules/commands/ms_read.cpp:112 +msgid "Read a memo or memos" +msgstr "Legge uno o più memo" + +#: modules/commands/bs_info.cpp:56 +msgid "Real name" +msgstr "Real name" + +#: modules/commands/os_list.cpp:153 +msgid "Realname" +msgstr "Realname" + +#: modules/commands/os_ignore.cpp:266 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:204 modules/commands/os_forbid.cpp:358 +#: modules/commands/cs_akick.cpp:392 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:361 +msgid "Reason" +msgstr "Motivo" + +#: src/xline.cpp:386 +#, c-format +msgid "Reason for %s updated." +msgstr "Motivo per %s aggiornato." + +#: modules/commands/ns_recover.cpp:214 +msgid "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." +msgstr "" +"Recupera il tuo nick da un altro utente o dai services.\n" +"Se i services stanno attualmente trattenendo il tuo nick,\n" +"il nick sarà rilasciato. Se un altro utente sta usando il tuo\n" +"nick ed è identificato, l'utente sarà killato (simile al vecchio\n" +"comando GHOST). Se l'utente che sta usando il tuo nick non è\n" +"identificato sarà forzato a cambiarlo dai services." + +#: modules/commands/cs_access.cpp:741 +msgid "Redefine the meanings of access levels" +msgstr "Ridefinisce i privilegi dei livelli di accesso" + +#: modules/commands/ns_recover.cpp:149 +msgid "Regains control of your nick" +msgstr "Permette di riottenere il controllo del proprio nick" + +#: modules/commands/os_sxline.cpp:330 modules/commands/os_sxline.cpp:545 +#: modules/commands/os_akill.cpp:129 +msgid "Regex is disabled." +msgstr "Le espressioni regolari sono disabilitate." + +#: modules/commands/os_sxline.cpp:459 modules/commands/os_sxline.cpp:694 +#: modules/commands/os_akill.cpp:444 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." +msgstr "" +"È supportato l'uso di espressioni regolari utilizzando il motore %s.\n" +"Se vuoi puoi includere la mask tra //." + +#: modules/commands/os_ignore.cpp:386 modules/commands/os_forbid.cpp:428 +#: modules/commands/ns_list.cpp:172 modules/commands/cs_list.cpp:167 +#: modules/commands/os_list.cpp:119 modules/commands/os_list.cpp:255 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." +msgstr "" +"È supportato l'uso di espressioni regolari utilizzando il motore %s.\n" +"Se vuoi puoi includere la mask tra //." + +#: modules/commands/cs_register.cpp:19 +msgid "Register a channel" +msgstr "Registra un canale" + +#: modules/commands/ns_register.cpp:120 +msgid "Register a nickname" +msgstr "Registra un nickname" + +#: modules/commands/ns_info.cpp:89 modules/commands/cs_info.cpp:55 +msgid "Registered" +msgstr "Registrato" + +#: modules/commands/os_stats.cpp:184 +#, c-format +msgid "Registered channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "Canali registrati: %lu voci, %lu buckets, la catena più lunga è %d" + +#: modules/commands/os_stats.cpp:190 +#, c-format +msgid "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" +msgstr "" +"Gruppi di nick registrati: %lu entries, %lu buckets, longest chain is %d" + +#: modules/commands/os_stats.cpp:187 +#, c-format +msgid "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" +msgstr "Nickname registrati: %lu entries, %lu buckets, longest chain is %d" + +#: modules/commands/cs_enforce.cpp:105 +#, c-format +msgid "Registered only enforced on %s." +msgstr "Solo registrati forzato su %s." + +#: modules/commands/cs_register.cpp:86 +#, c-format +msgid "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." +msgstr "" +"Registra un canale nel database di %s. Per poter usare\n" +"questo commando, prima di tutto, devi essere operatore (op)\n" +"del canale che intendi registrare. La descrizione, che deve\n" +"essere specificata, è una descrizione generica dello scopo\n" +"del canale.\n" +" \n" +"Quando registri un canale, vieni registrato come \"founder\"\n" +"del canale. Il founder di un canale puo modificare tutte le'\n" +"impostazioni del canale e riceverà automaticamente da %s\n" +"i privilegi di operatore del canale quando vi accede." + +#: modules/commands/ns_register.cpp:269 +#, c-format +msgid "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." +msgstr "" +"Registra il tuo nick nel database di %s. Quando il\n" +"nick è registrato, puoi usare i comandi SET e ACCESS\n" +"per modificare a tuo piacimento le impostazioni del tuo\n" +"nick. Assicurati di non dimenticare la password che usi\n" +"per la registrazione - ne avrai bisogno per effettuare\n" +"modifiche sul tuo nick.\n" +"Tieni conto che le maiuscole e le minuscole sono\n" +"differenti! PIPPO, Pippo, pippo e PiPpO sono\n" +"tutte password diverse!\n" +"\n" +"Suggerimenti sulla scelta della password:\n" +"\n" +"Le password non devono essere facili da indovinare. Ad\n" +"esempio, usare il tuo vero nome come password è una\n" +"pessima idea. Utilizzare il tuo nick come password è un'idea \n" +"anche peggiore, infatti %s non ti permetterà di farlo.\n" +"Inoltre, le password brevi sono facili da indovinare con\n" +"meno tentativi, pertanto è necessario scegliere una password \n" +"di almeno 5 caratteri. Infine, gli spazi non possono essere \n" +"usati all'interno di una password." + +#: modules/commands/ns_register.cpp:145 +msgid "Registration is currently disabled." +msgstr "Spiacente, la registrazione è temporaneamente disabilitata." + +#: modules/commands/cs_set.cpp:400 +msgid "Regulate the use of critical commands" +msgstr "Regola l'uso dei comandi critici" + +#: modules/commands/hs_request.cpp:283 +msgid "Reject the requested vHost for the given nick." +msgstr "Rifiuta il vHost richisto per il nick specificato." + +#: modules/commands/hs_request.cpp:240 +msgid "Reject the requested vHost of a user" +msgstr "Rifiuta il vHost richisto di un utente" + +#: modules/commands/cs_suspend.cpp:151 +msgid "Releases a suspended channel" +msgstr "Rilascia un canale sospeso" + +#: modules/commands/cs_suspend.cpp:191 +msgid "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." +msgstr "" +"Rilascia un canale sospeso. Tutti le impostazioni e i dati\n" +"sono mantenuti da prima della sospensione." + +#: modules/commands/os_module.cpp:56 +msgid "Reload a module" +msgstr "Ricarica un modulo" + +#: modules/commands/os_reload.cpp:19 +msgid "Reload services' configuration file" +msgstr "Rilegge il file di configurazione dei Services" + +#: modules/commands/ns_group.cpp:236 +msgid "Remove a nick from a group" +msgstr "Rimuove un nick da un gruppo" + +#: modules/commands/cs_unban.cpp:19 +msgid "Remove all bans preventing a user from entering a channel" +msgstr "" +"Rimuove tutti i ban che impediscono a un utente di accedere a un canale" + +#: modules/commands/os_noop.cpp:19 +msgid "Remove all operators from a server remotely" +msgstr "Rimuove temporaneamente tutti gli operatori di un server" + +#: modules/commands/os_dns.cpp:543 +#, c-format +msgid "Removed IP %s from %s." +msgstr "IP %s rimosso da %s." + +#: modules/commands/os_dns.cpp:460 +#, c-format +msgid "Removed server %s from zone %s." +msgstr "Server %s rimosso dalla zona %s." + +#: modules/commands/os_dns.cpp:483 +#, c-format +msgid "Removed server %s." +msgstr "Server %s rimosso." + +#: modules/commands/cs_mode.cpp:909 +#, c-format +msgid "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." +msgstr "" +"Rimuove lo stato di %s al nick specificato in un canale. Se il nick\n" +"non viene specificato, lo stato di %s sarà rimosso a te stesso." + +#: modules/commands/cs_mode.cpp:890 +#, c-format +msgid "Removes %s status from you or the specified nick on a channel" +msgstr "Rimuove lo stato di %s al nick specificato o a te stesso in un canale" + +#: modules/commands/cs_updown.cpp:146 +msgid "Removes a selected nicks status from a channel" +msgstr "Rimuove lo stato di un nick specificato in un canale" + +#: modules/commands/cs_updown.cpp:223 +msgid "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." +msgstr "" +"Rimuove lo stato di un nick specificato in un canale. Se il nick\n" +"non viene specificato, lo stato viene rimosso a te stesso. Se il\n" +"canale non viene specificato, lo stato viene rimosso su tutti i canali\n" +"in cui ti trovi." + +#: src/xline.cpp:412 +#, c-format +msgid "Removing %s because %s covers it." +msgstr "%s rimosso perchè già coperto da %s." + +#: modules/commands/bs_kick.cpp:1171 modules/commands/bs_kick.cpp:1173 +#: modules/commands/bs_kick.cpp:1176 +msgid "Repeat kicker" +msgstr "Kick in caso di ripetizione" + +#: modules/commands/hs_request.cpp:78 +msgid "Request a vHost for your nick" +msgstr "Richiede un vHost per il tuo nick" + +#: modules/commands/hs_request.cpp:179 +msgid "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." +msgstr "" +"Richiede che il vHost specificato sia attivato per il tuo nick\n" +"da un amministratore della rete. Nel frattempo, rimani in attesa\n" +"che la tua richiesta sia presa in considerazione." + +#: modules/commands/ns_register.cpp:312 +msgid "Resend registration confirmation email" +msgstr "Reinvia l'email di conferma per la registrazione" + +#: modules/commands/cs_set.cpp:621 +msgid "Restrict access to the channel" +msgstr "Limita l'accesso al canale" + +#: modules/commands/cs_set.cpp:1291 +msgid "Restricted access" +msgstr "Accesso limitato" + +#: modules/commands/cs_set.cpp:661 +#, c-format +msgid "Restricted access option for %s is now off." +msgstr "L'opzione accesso ristretto per %s è ora disattivata." + +#: modules/commands/cs_set.cpp:655 +#, c-format +msgid "Restricted access option for %s is now on." +msgstr "L'opzione accesso ristretto per %s è ora attiva." + +#: modules/commands/cs_enforce.cpp:73 +#, c-format +msgid "Restricted enforced on %s." +msgstr "Ristretto forzato su %s." + +#: modules/commands/cs_set.cpp:335 +msgid "Retain modes when channel is not in use" +msgstr "Mantiene il modi quando il canale non è in uso" + +#: modules/commands/cs_topic.cpp:20 +msgid "Retain topic when channel is not in use" +msgstr "Mantiene il topic quando il canale non è in uso" + +#: modules/commands/ns_getpass.cpp:19 +msgid "Retrieve the password for a nickname" +msgstr "Recupera la password di un nickname" + +#: modules/commands/hs_request.cpp:296 +msgid "Retrieves the vhost requests" +msgstr "Recupera le richieste di vHost" + +#: modules/commands/cs_getkey.cpp:19 +msgid "Returns the key of the given channel" +msgstr "Recupera la password (+k) del canale specificato" + +#: modules/commands/cs_getkey.cpp:57 +msgid "Returns the key of the given channel." +msgstr "Recupera la password (+k) del canale specificato." + +#: modules/commands/ns_getemail.cpp:58 +msgid "Returns the matching accounts that used given email." +msgstr "Restituisce l'account corrispondente all'email specificata." + +#: modules/commands/ns_status.cpp:19 +msgid "Returns the owner status of the given nickname" +msgstr "Indica lo stato di proprietario del nickname specificato" + +#: modules/commands/ns_getpass.cpp:50 +msgid "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." +msgstr "" +"Restituisce la password del nick specificato.\n" +"Da notare che quando questo comando viene usato,\n" +"verrà inviato un WALLOPS o GLOBOPS ad indicare la\n" +"persona che l'ha utilizzato e su quale nick è stato\n" +"utilizzato." + +#: modules/commands/ns_status.cpp:55 +msgid "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." +msgstr "" +"Indica se l'utente che usa il nick specificato è riconosciuto\n" +"come proprietario del nick. La risposta ha questo formato:\n" +" \n" +" nick codice-di-stato account\n" +" \n" +"dove nick è il nickname specificato con il comando,\n" +"codice-di-stato è uno dei seguenti, e account\n" +"è l'account a cui il nick ha effettuato l'accesso.\n" +" \n" +" 0 - l'utente non è online oppure il nick non è registrato\n" +" 1 - l'utente non è riconosciuto come proprietario del nick\n" +" 2 - l'utente è riconosciuto come proprietario solo attraverso\n" +" la lista di accesso\n" +" 3 - l'utente è riconosciuto come proprietario attraverso\n" +" l'identificazione per mezzo della password\n" +"\n" +"Se nessun nickname è specificato sarà indicato lo stato del tuo nick." + +#: modules/commands/bs_kick.cpp:1181 modules/commands/bs_kick.cpp:1183 +#: modules/commands/bs_kick.cpp:1186 +msgid "Reverses kicker" +msgstr "Kick in caso di reverse" + +#: modules/commands/ns_logout.cpp:21 +msgid "Reverses the effect of the IDENTIFY command" +msgstr "Deidentifica dal proprio nick" + +#: modules/commands/os_noop.cpp:20 +msgid "SET server" +msgstr "SET server" + +#: modules/commands/os_dns.cpp:667 +msgid "SET server.name option value" +msgstr "SET server.nome opzione value" + +#: modules/commands/ns_cert.cpp:378 +#, c-format +msgid "SSL certificate fingerprint accepted, you are now identified to %s." +msgstr "" +"Firma digitale del certificato SSL accettata - adesso sei identificato come" +" %s." + +#: modules/commands/ns_cert.cpp:398 +msgid "SSL certificate fingerprint accepted, you are now identified." +msgstr "" +"Firma digitale del certificato SSL accettata - adesso sei riconosciuto." + +#: modules/commands/cs_enforce.cpp:137 +#, c-format +msgid "SSL only enforced on %s." +msgstr "SSL only forzato su %s." + +#: modules/commands/cs_enforce.cpp:131 +msgid "SSLONLY enforced by " +msgstr "SSLONLY forzato da " + +#: modules/commands/os_shutdown.cpp:47 +msgid "Save databases and restart Services" +msgstr "Salva i database e riavvia i Services" + +#: modules/commands/os_logsearch.cpp:32 +msgid "Searches logs for a matching pattern" +msgstr "Cerca nei log per la chiave specificata corrispondente" + +#: modules/commands/cs_set.cpp:1295 +msgid "Secure founder" +msgstr "Secure Founder" + +#: modules/commands/cs_set.cpp:786 +#, c-format +msgid "Secure founder option for %s is now off." +msgstr "L'opzione Secure founder per %s è ora disattivata." + +#: modules/commands/cs_set.cpp:780 +#, c-format +msgid "Secure founder option for %s is now on." +msgstr "L'opzione Secure founder per %s è ora attiva." + +#: modules/commands/cs_set.cpp:1297 +msgid "Secure ops" +msgstr "Secure ops" + +#: modules/commands/cs_set.cpp:850 +#, c-format +msgid "Secure ops option for %s is now off." +msgstr "L'opzione Secure ops per %s è ora disattivata." + +#: modules/commands/cs_set.cpp:844 +#, c-format +msgid "Secure ops option for %s is now on." +msgstr "L'opzione Secure ops per %s è ora attiva." + +#: modules/commands/cs_set.cpp:723 +#, c-format +msgid "Secure option for %s is now off." +msgstr "L'opzione Secure per %s è ora disattivata." + +#: modules/commands/cs_set.cpp:717 +#, c-format +msgid "Secure option for %s is now on." +msgstr "L'opzione Secure per %s è ora attiva." + +#: modules/commands/ns_set.cpp:1044 +#, c-format +msgid "Secure option is now off for %s." +msgstr "Opzione secure disattivata per %s." + +#: modules/commands/ns_set.cpp:1038 +#, c-format +msgid "Secure option is now on for %s." +msgstr "Opzione secure attiva per %s." + +#: modules/commands/cs_enforce.cpp:42 +#, c-format +msgid "Secureops enforced on %s." +msgstr "Secureops forzato su %s." + +#: modules/commands/cs_set.cpp:1293 modules/commands/ns_set.cpp:1311 +msgid "Security" +msgstr "Sicurezza" + +#: modules/commands/cs_xop.cpp:570 +#, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the access list." +msgstr "" +"Digita %s%s HELP %s per ottenere maggiori\n" +"informazioni sulla lista di accesso." + +#: modules/commands/cs_xop.cpp:573 +#, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the flags system." +msgstr "" +"Digita %s%s HELP %s per ottenere maggiori\n" +"informazioni sul sistema delle flags." + +#: modules/commands/ms_send.cpp:24 +msgid "Send a memo to a nick or channel" +msgstr "Invia un memo a un nick o a un canale" + +#: modules/commands/ms_staff.cpp:24 +msgid "Send a memo to all opers/admins" +msgstr "Invia un memo a tutti gli opers/admins" + +#: modules/commands/ms_sendall.cpp:24 +msgid "Send a memo to all registered users" +msgstr "Invia un memo a tutti gli utenti registrati" + +#: modules/commands/gl_global.cpp:21 +msgid "Send a message to all users" +msgstr "Invia un messaggio a tutti gli utenti" + +#: modules/commands/ms_list.cpp:64 +msgid "Sender" +msgstr "Mittente" + +#: modules/commands/ms_rsend.cpp:24 +msgid "Sends a memo and requests a read receipt" +msgstr "Invia un memo e richiede una notifica di lettura" + +#: modules/commands/ns_resetpass.cpp:50 +msgid "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." +msgstr "" +"Invia un messaggio contenente un codice di attivazione e le istruzioni\n" +"necessarie per procedere al reset della password per il nickname " +"specificato.\n" +"L'indirizzo email deve corrispondere all'indirizzo email associato\n" +"al nickname." + +#: modules/commands/ms_sendall.cpp:52 +msgid "Sends all registered users a memo containing memo-text." +msgstr "Invia un memo contenente testo-memo a tutti gli utenti registrati." + +#: modules/commands/ms_staff.cpp:48 +msgid "Sends all services staff a memo containing memo-text." +msgstr "Invia un memo contenente testo-memo a tutto lo staff dei services." + +#: modules/commands/ms_send.cpp:66 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." +msgstr "" +"Invia un memo che contiene il testo-memo al nick\n" +"o al canale specificato. Quando si invia un memo a un\n" +"nick, il destinatario riceverà un messaggio che lo notifica\n" +"che ha un nuovo memo. Il nick/canale di destinazione deve\n" +"esser registrato." + +#: modules/commands/ms_rsend.cpp:80 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." +msgstr "" +"Invia un memo contenente testo-memo al nick o canale\n" +"specificato. Se inviato ad un nickname, il destinatario riceverà\n" +"un notice che gli segnalerà il nuovo memo. Il nickname o canale\n" +"dev'essere registrato.\n" +"Una volta che il memo viene letto dal destinatario, verrà inviata\n" +"una notifica automatica al mittente, informandolo che il suo memo\n" +"è stato letto." + +#: modules/commands/ms_read.cpp:199 +msgid "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Mostra il testo dei propri memo specificati. Se viene indicato\n" +"LAST, mostra l'ultimo memo ricevuto. Se viene indicato NEW,\n" +"mostra tutti i nuovi memo. Altrimenti, mostra il memo che ha\n" +"numero numero. Si può anche specificare una lista di numeri,\n" +"come nell'esempio:\n" +"\n" +" READ 2-5,7-9\n" +" Mostra i memo che hanno numeri tra 2 e 5 e tra 7 e 9,\n" +" escludendo quindi il 6." + +#: modules/commands/os_dns.cpp:218 +msgid "Server" +msgstr "Server" + +#: modules/commands/os_dns.cpp:375 +#, c-format +msgid "Server %s added to zone %s." +msgstr "Il server %s è stato aggiunto alla zona %s." + +#: modules/commands/os_dns.cpp:345 +#, c-format +msgid "Server %s already exists." +msgstr "Il server %s è già esistente." + +#: modules/commands/os_noop.cpp:31 modules/commands/os_dns.cpp:430 +#: modules/commands/os_dns.cpp:493 modules/commands/os_dns.cpp:532 +#: modules/commands/os_dns.cpp:571 modules/commands/os_dns.cpp:604 +#: modules/commands/os_dns.cpp:639 +#, c-format +msgid "Server %s does not exist." +msgstr "Il server %s non esiste." + +#: modules/commands/os_dns.cpp:619 +#, c-format +msgid "Server %s has no configured IPs." +msgstr "Il server %s non ha IP configurati." + +#: modules/commands/os_dns.cpp:357 +#, c-format +msgid "Server %s is already in zone %s." +msgstr "Il server %s è già presente nella zona %s." + +#: modules/commands/os_dns.cpp:614 +#, c-format +msgid "Server %s is already pooled." +msgstr "Il server %s è già in pool." + +#: modules/commands/os_dns.cpp:609 +#, c-format +msgid "Server %s is not currently linked." +msgstr "Il server %s non è attualmente linkato." + +#: modules/commands/os_dns.cpp:443 +#, c-format +msgid "Server %s is not in zone %s." +msgstr "Il server %s non è presente nella zona %s." + +#: modules/commands/os_dns.cpp:384 +#, c-format +msgid "Server %s is not linked to the network." +msgstr "Il server %s non è linkato al network." + +#: modules/commands/os_dns.cpp:644 +#, c-format +msgid "Server %s is not pooled." +msgstr "Il server %s non è in pool." + +#: modules/commands/os_dns.cpp:465 +#, c-format +msgid "Server %s must be quit before it can be deleted." +msgstr "Il server %s deve essere scollegato prima di essere eliminato." + +#: modules/commands/os_dns.cpp:255 +msgid "Servers" +msgstr "Servers" + +#: modules/commands/os_stats.cpp:155 +#, c-format +msgid "Servers found: %d" +msgstr "Servers trovati: %d" + +#: modules/commands/cs_log.cpp:127 +msgid "Service" +msgstr "Servizio" + +#: modules/commands/ns_recover.cpp:51 +#, c-format +msgid "Service's hold on %s has been released." +msgstr "Il blocco dei servizi sul nick %s è stato rilasciato." + +#: data/nickserv.example.conf:236 data/chanserv.example.conf:827 +msgid "Services Operator commands" +msgstr "Comandi da Services Operator" + +#: modules/commands/os_defcon.cpp:443 modules/commands/os_defcon.cpp:454 +#: modules/commands/os_defcon.cpp:462 modules/commands/os_defcon.cpp:470 +#: modules/commands/os_defcon.cpp:478 +msgid "Services are in DefCon mode, please try again later." +msgstr "I Services sono in modalità Defcon, si prega di riprovare più tardi." + +#: include/language.h:70 +msgid "Services are in read-only mode!" +msgstr "I Services sono ora in modalità read-only!" + +#: modules/commands/os_defcon.cpp:186 modules/commands/os_defcon.cpp:213 +#, c-format +msgid "Services are now at DEFCON %d." +msgstr "I Services sono ora in DEFCON %d." + +#: modules/commands/os_set.cpp:128 +#, c-format +msgid "Services are now in debug mode (level %d)." +msgstr "I Services sono ora in modalità debug (livello %d)." + +#: modules/commands/os_set.cpp:114 +msgid "Services are now in debug mode." +msgstr "I Services sono ora in modalità debug." + +#: modules/commands/os_set.cpp:159 +msgid "Services are now in expire mode." +msgstr "I Services sono ora in modalità expire." + +#: modules/commands/os_set.cpp:153 +msgid "Services are now in no expire mode." +msgstr "I Services sono ora in modalità no expire." + +#: modules/commands/os_set.cpp:120 +msgid "Services are now in non-debug mode." +msgstr "I Services sono ora modalità no-debug." + +#: modules/commands/os_set.cpp:47 +msgid "Services are now in read-only mode." +msgstr "I Services sono ora in modalità read-only." + +#: modules/commands/os_set.cpp:53 +msgid "Services are now in read-write mode." +msgstr "I Services sono ora in modalità read-write." + +#: src/mail.cpp:76 +msgid "Services have been configured to not send mail." +msgstr "I Services sono stati configurati per non inviare e-mail." + +#: modules/commands/os_ignore.cpp:280 +msgid "Services ignore list:" +msgstr "Lista ignore dei Services:" + +#: modules/commands/os_mode.cpp:33 modules/commands/os_kick.cpp:39 +msgid "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" +msgstr "" +"I Services non riescono a cambiare i modi. Le U:lines dei server sono " +"configurate correttamente?" + +#: modules/commands/os_stats.cpp:140 +#, c-format +msgid "Services up %s." +msgstr "Services online da %s." + +#: modules/commands/ns_set.cpp:266 +#, c-format +msgid "Services will from now on set status modes on %s in channels." +msgstr "I servizi imposteranno lo stato di %s automaticamente nei canali." + +#: modules/commands/cs_set.cpp:114 +#, c-format +msgid "Services will no longer automatically give modes to users in %s." +msgstr "" +"I servizi non imposterannno più lo stato di %s automaticamente nei canali." + +#: modules/commands/ns_set.cpp:272 +#, c-format +msgid "Services will no longer set status modes on %s in channels." +msgstr "I servizi non imposterannno più lo stato di %s nei canali." + +#: modules/commands/cs_set.cpp:108 +#, c-format +msgid "Services will now automatically give modes to users in %s." +msgstr "I servizi imposteranno automaticamente lo stato degli utenti su %s." + +#: modules/commands/ns_set.cpp:940 +#, c-format +msgid "Services will now reply to %s with messages." +msgstr "I servizi risponderanno a %s usando i messaggi." + +#: modules/commands/ns_set.cpp:946 +#, c-format +msgid "Services will now reply to %s with notices." +msgstr "I servizi risponderanno a %s usando i notices." + +#: modules/commands/os_reload.cpp:34 +msgid "Services' configuration has been reloaded." +msgstr "Il file di configurazione dei Services è stato ricaricato in memoria." + +#: modules/commands/os_session.cpp:192 +msgid "Session" +msgstr "Sessione" + +#: modules/commands/os_session.cpp:382 +#, c-format +msgid "Session limit for %s set to %d." +msgstr "Il limite di sessioni per %s è stato impostato a %d." + +#: modules/commands/os_session.cpp:257 modules/commands/os_session.cpp:534 +msgid "Session limiting is disabled." +msgstr "Il limite delle sessioni è disabilitato." + +#: modules/commands/os_stats.cpp:195 +#, c-format +msgid "Sessions: %lu entries, %lu buckets, longest chain is %d" +msgstr "Sessioni: %lu entries, %lu buckets, longest chain is %d" + +#: modules/commands/ns_set.cpp:74 +msgid "Set SET-options on another nickname" +msgstr "Imposta le opzioni SET su un altro nickname" + +#: modules/commands/cs_set.cpp:20 +msgid "Set channel options and information" +msgstr "Imposta le opzioni e le informazioni di un canale" + +#: modules/commands/cs_set.cpp:137 +msgid "Set how Services make bans on the channel" +msgstr "Imposta il tipo di ban che sarà usato dai Services" + +#: modules/commands/ms_set.cpp:206 +msgid "Set options related to memos" +msgstr "Imposta le opzioni relative ai memo" + +#: modules/commands/ns_set.cpp:19 +msgid "Set options, including kill protection" +msgstr "Imposta le opzioni, inclusa la protezione del nick" + +#: modules/commands/cs_set.cpp:472 +msgid "Set the channel as permanent" +msgstr "Imposta il canale come permanente" + +#: modules/commands/cs_set.cpp:204 +msgid "Set the channel description" +msgstr "Imposta la descrizione del canale" + +#: modules/commands/ns_set.cpp:329 +msgid "Set the display of your group in Services" +msgstr "Imposta il nome del tuo gruppo" + +#: modules/commands/cs_set.cpp:266 +msgid "Set the founder of a channel" +msgstr "Imposta il founder del canale" + +#: modules/commands/ns_set.cpp:793 +msgid "Set the language Services will use when messaging you" +msgstr "Imposta la lingua utilizzata dai Services" + +#: modules/commands/ns_set.cpp:172 +msgid "Set the nickname password" +msgstr "Imposta la password del nick" + +#: modules/commands/cs_set.cpp:949 +msgid "Set the successor for a channel" +msgstr "Imposta il successore del founder del canale" + +#: modules/commands/hs_set.cpp:125 +msgid "Set the vhost for all nicks in a group" +msgstr "Imposta il vHost per tutti i nick di un gruppo" + +#: modules/commands/hs_set.cpp:19 +msgid "Set the vhost of another user" +msgstr "Imposta il vHost di un altro utente" + +#: modules/commands/os_set.cpp:169 +msgid "Set various global Services options" +msgstr "Imposta varie opzioni globali dei Services" + +#: modules/commands/ns_set.cpp:119 +msgid "Set your nickname password" +msgstr "Imposta la password del tuo nick" + +#: modules/commands/bs_kick.cpp:271 +#, c-format +msgid "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Imposta il kick degli AMSG attivo o non attivo. Quando attivo\n" +"Il bot kickerà gli utenti che inviano lo stesso messaggio su\n" +"canali multipli dove risiedono i bot di %s.\n" +" \n" +"ttb è il numero di volte che un utente può essere espulso\n" +"prima di ricevere un ban. Se il parametro non viene specificato,\n" +"l'utente non verrà bannato." + +#: modules/commands/bs_kick.cpp:307 +#, c-format +msgid "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Attiva o disattiva il kick su parolacce. Quando è attiva\n" +"questa opzione il bot kickerà gli utenti che scrivono\n" +"parole presenti nella lista delle parolacce dal canale.\n" +" \n" +"Le parolacce possono essere definite usando il comando\n" +"BADWORDS. Digita %s%s HELP BADWORDS per ottenere\n" +"maggiori informazioni.\n" +" \n" +"ttb è il numero di volte che un utente può essere espulso\n" +"prima di ricevere un ban. Se il parametro non viene specificato,\n" +"l'utente non verrà bannato." + +#: modules/commands/cs_set.cpp:186 +msgid "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" +msgstr "" +"Imposta il tipo di can che sarà usato dai Services in tutte\n" +"le occasioni in cui dovranno bannare un utente dal canale.\n" +" \n" +"Bantype è un numero tra 0 e 3 che indica:\n" +"\n" +"0: ban nella forma *!user@host\n" +"1: ban nella forma *!*user@host\n" +"2: ban nella forma *!*@host\n" +"3: ban nella forma *!*user@*.dominio" + +#: modules/commands/bs_kick.cpp:345 +msgid "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Attiva o disattiva il kick in caso di grassetto. Quando questa\n" +"opzione è attiva il bot kickarà tutti gli utenti che usano\n" +"il grassetto nel canale.\n" +" \n" +"ttb è il numero di volte che un utente può essere espulso\n" +"prima di ricevere un ban. Se il parametro non viene specificato,\n" +"l'utente non verrà bannato." + +#: modules/commands/bs_kick.cpp:436 +#, c-format +msgid "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Attiva o disattiva il kick in caso di maiuscole. Quando questa\n" +"opzione è attiva il bot kickarà tutti gli utenti che usano\n" +"le maiuscole nel canale.\n" +" \n" +"Il bot kicka soltanto se ci sono almeno minimo lettere\n" +"maiuscole e se costituiscono almeno il percento%% del testo\n" +"totale della linea. I valori di default per questi\n" +"parametri sono 10 caratteri e 25%%.\n" +" \n" +"ttb è il numero di volte che un utente può essere espulso\n" +"prima di ricevere un ban. Se il parametro non viene specificato,\n" +"l'utente non verrà bannato." + +#: modules/commands/bs_kick.cpp:475 +msgid "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Attiva o disattiva il kick in caso di colori. Quando questa\n" +"opzione è attiva il bot kickarà tutti gli utenti che usano\n" +"i colori nel canale.\n" +" \n" +"ttb è il numero di volte che un utente può essere espulso\n" +"prima di ricevere un ban. Se il parametro non viene specificato,\n" +"l'utente non verrà bannato." + +#: modules/commands/cs_set.cpp:255 +msgid "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." +msgstr "" +"Imposta la descrizione del canale, che viene mostrata usando\n" +"i comandi LIST e INFO." + +#: modules/commands/bs_kick.cpp:571 +msgid "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Attiva o disattiva il kick in caso di flood. Quando questa\n" +"opzione è attiva, il bot kickarà tutti gli utenti che floodano\n" +"il canale scrivendo almeno ln linee in secs secondi.\n" +"I valori di default per questi parametri sono 6 linee e 10 secondi.\n" +" \n" +"ttb è il numero di volte che un utente può essere espulso\n" +"prima di ricevere un ban. Se il parametro non viene specificato,\n" +"l'utente non verrà bannato." + +#: modules/commands/bs_kick.cpp:607 +msgid "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Attiva o disattiva il kick in caso di italics. Quando qesta\n" +"opzione è attiva, il bot kickerà tutti gli utenti che usano\n" +"il corsivo nel canale.\n" +" \n" +"ttb è il numero di volte che un utente può essere espulso\n" +"prima di ricevere un ban. Se il parametro non viene specificato,\n" +"l'utente non verrà bannato." + +#: modules/commands/bs_kick.cpp:706 +msgid "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Attiva o disattiva il kick in caso di ripetizione. Quando questa\n" +"opzione è attiva, il bot kickerà tutti gli utenti ripetono\n" +"la stessa cosa almeno num volte. Il valore di default per questo\n" +"parametro è 3.\n" +" \n" +"ttb è il numero di volte che un utente può essere espulso\n" +"prima di ricevere un ban. Se il parametro non viene specificato,\n" +"l'utente non verrà bannato." + +#: modules/commands/bs_kick.cpp:742 +msgid "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Attiva o disattiva il kick in caso di reverses. Quando questa\n" +"opzione è attiva, il bot kickerà tutti gli utenti che usano\n" +"il reverse nel canale.\n" +" \n" +"ttb è il numero di volte che un utente può essere espulso\n" +"prima di ricevere un ban. Se il parametro non viene specificato,\n" +"l'utente non verrà bannato." + +#: modules/commands/bs_kick.cpp:776 +msgid "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Attiva o disattiva il kick in caso di underlines. Quando questa\n" +"opzione è attiva, il bot kickerà tutti gli utenti che usano\n" +"il sottolineato nel canale.\n" +" \n" +"ttb è il numero di volte che un utente può essere espulso\n" +"prima di ricevere un ban. Se il parametro non viene specificato,\n" +"l'utente non verrà bannato." + +#: modules/commands/hs_set.cpp:206 +msgid "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." +msgstr "" +"Imposta il vHost per tutti i nick nel gruppo del nick indicato.\n" +"Se il tuo IRCD supporta i vIdent, la forma SETALL \n" +"@ permette di impostare l'ident, oltre che il\n" +"vHost.\n" +" \n" +"* NOTA - questo comando non aggiornerà i vHost dei nick\n" +"aggiunti successivamente al gruppo." + +#: modules/commands/hs_set.cpp:99 +msgid "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." +msgstr "" +"Imposta il vHost per il nick specificato a quello della hostmask\n" +"specificata. Se il tuo IRCD supporta i vIdent, la forma\n" +"SET  @ permette di impostare l'ident,\n" +"oltre che il vHost." + +#: modules/commands/os_set.cpp:199 +msgid "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" +msgstr "" +"Imposta varie opzioni globali dei Services. Le opzioni\n" +"configurabili sono:\n" +" READONLY Imposta la modalità read-only o read-write\n" +" DEBUG Attiva o disattiva la modalità di debug\n" +" NOEXPIRE Attiva o disattiva la modalità no expire\n" +" SUPERADMIN Attiva o disattiva la modalità Super Admin\n" +" LIST Elenca le opzioni" + +#: modules/commands/ms_set.cpp:235 +#, c-format +msgid "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Imposta varie opzioni dei memo. opzione può essere:\n" +"\n" +" NOTIFY Cambia il modo in cui si verrà notificati\n" +" alla ricezione di nuovi memo (solo\n" +" per i nick)\n" +" LIMIT Imposta il numero massimo di memo che si\n" +" possono ricevere\n" +" \n" +"Digita %s%s HELP %s opzione per ottenere\n" +"maggiori informazioni su un'opzione specifica." + +#: modules/commands/ns_set.cpp:33 modules/commands/ns_set.cpp:88 +msgid "Sets various nickname options. option can be one of:" +msgstr "Imposta varie opzioni del nick. opzione può essere una delle seguenti:" + +#: modules/commands/ns_set.cpp:237 +msgid "" +"Sets whether services should set channel status modes on you automatically." +msgstr "" +"Imposta se i Services modificheranno automaticamente il tuo stato nei canali." + +#: modules/commands/cs_set.cpp:1090 +msgid "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." +msgstr "" +"Imposta se il canale scadrà o meno in caso di inutilizzo. Se\n" +"l'opzione è impostata a ON, il canale non scadrà." + +#: modules/commands/ns_set.cpp:315 +#, c-format +msgid "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." +msgstr "" +"Imposta se i Services modificheranno automaticamente lo stato\n" +"del nickname specificato nei canali. Imposta su ON per permettere a %s\n" +"di impostare lo stato del nickname specificato automaticamente\n" +"quando accede al canale." + +#: modules/commands/ns_set.cpp:1145 +msgid "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." +msgstr "" +"Imposta se il nickname specificato scadrà. Impostandolo su\n" +"ON eviterà che il nickname scada." + +#: modules/commands/ns_set.cpp:288 +#, c-format +msgid "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." +msgstr "" +"Imposta se i Services modificheranno automaticamente il tuo stato nei " +"canali.\n" +"Impostalo su ON per permettere a %s di impostare automaticamente il tuo " +"stato\n" +"quando accedi ai canali. Nota che a seconda delle impostazioni del canale\n" +"alcuni modi potrebbero non essere attivati automaticamente." + +#: modules/commands/cs_access.cpp:648 modules/commands/cs_access.cpp:689 +#, c-format +msgid "" +"Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." +msgstr "" +"Impostazione %s sconosciuta. Digita %s%s HELP LEVELS per una lista delle " +"impostazioni valide." + +#: modules/commands/os_set.cpp:133 +msgid "Setting for DEBUG must be ON, OFF, or a positive number." +msgstr "" +"Il parametro dell'opzione DEBUG deve essere ON, OFF, o un numero positivo." + +#: modules/commands/os_set.cpp:162 +msgid "Setting for NOEXPIRE must be ON or OFF." +msgstr "Il parametro dell'opzione NOEXPIRE deve essere ON o OFF." + +#: modules/commands/os_set.cpp:56 +msgid "Setting for READONLY must be ON or OFF." +msgstr "Il parametro dell'opzione READONLY deve essere ON o OFF." + +#: modules/commands/os_set.cpp:95 +msgid "Setting for super admin must be ON or OFF." +msgstr "Il parametro dell'opzione super admin deve essere ON o OFF." + +#: modules/commands/cs_set.cpp:74 +msgid "Should services automatically give status to users" +msgstr "Abilita/disabilita l'impostazione automatica dello stato agli utenti" + +#: modules/commands/os_stats.cpp:203 +msgid "Show status of Services and network" +msgstr "Mostra lo stato dei Services e della rete" + +#: modules/commands/os_logsearch.cpp:152 +#, c-format +msgid "Showed %d/%d matches for %s." +msgstr "Mostrati %d/%d risultati per %s." + +#: modules/commands/cs_set.cpp:872 +msgid "Sign kicks that are done with the KICK command" +msgstr "Firma i kick effettuati con il comando KICK" + +#: modules/commands/cs_set.cpp:921 +#, c-format +msgid "Signed kick option for %s is now off." +msgstr "L'opzione Signed kick per %s è ora disattivata." + +#: modules/commands/cs_set.cpp:913 +#, c-format +msgid "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." +msgstr "" +"L'opzione Signed kick per %s è ora attiva, ma dipende dal\n" +"livello dell'utente che utilizza il comando." + +#: modules/commands/cs_set.cpp:906 +#, c-format +msgid "Signed kick option for %s is now on." +msgstr "L'opzione Signed kick per %s è ora attiva." + +#: modules/commands/cs_set.cpp:1299 +msgid "Signed kicks" +msgstr "Kicks firmati" + +#: modules/commands/ms_rsend.cpp:60 modules/commands/ms_send.cpp:59 +#, c-format +msgid "Sorry, %s currently has too many memos and cannot receive more." +msgstr "%s attualmente ha troppi memo e non può riceverne altri." + +#: modules/commands/cs_seen.cpp:294 +#, c-format +msgid "Sorry, I have not seen %s." +msgstr "Spiacente, non ho visto %s." + +#: modules/commands/bs_badwords.cpp:404 +msgid "Sorry, bad words list modification is temporarily disabled." +msgstr "" +"Spiacente, la modifica della lista parolacce è temporaneamente disabilitata." + +#: modules/commands/bs_assign.cpp:30 modules/commands/bs_assign.cpp:98 +msgid "Sorry, bot assignment is temporarily disabled." +msgstr "Spiacente, l'assegnazione dei bot è temporaneamente disabilitata." + +#: modules/commands/bs_bot.cpp:281 modules/commands/bs_assign.cpp:164 +msgid "Sorry, bot modification is temporarily disabled." +msgstr "Spiacente, la modifica dei bot è temporaneamente disabilitata." + +#: modules/fantasy.cpp:42 modules/commands/bs_kick.cpp:813 +#: modules/commands/bs_kick.cpp:878 +msgid "Sorry, bot option setting is temporarily disabled." +msgstr "" +"Spiacente, l'impostazione delle opzioni dei bot è temporaneamente " +"disabilitata." + +#: modules/commands/bs_set.cpp:115 +msgid "Sorry, changing bot options is temporarily disabled." +msgstr "" +"Spiacente, l'impostazione delle opzioni dei bot è temporaneamente " +"disabilitata." + +#: modules/commands/cs_xop.cpp:112 modules/commands/cs_xop.cpp:235 +#: modules/commands/cs_xop.cpp:444 +#, c-format +msgid "Sorry, channel %s list modification is temporarily disabled." +msgstr "Spiacente, la modifica della lista %s è temporaneamente disabilitata." + +#: modules/commands/cs_access.cpp:547 modules/commands/cs_flags.cpp:405 +msgid "Sorry, channel access list modification is temporarily disabled." +msgstr "" +"Spiacente, la modifica della lista di accesso dei canali è temporaneamente " +"disabilitata." + +#: modules/commands/cs_akick.cpp:469 +msgid "Sorry, channel autokick list modification is temporarily disabled." +msgstr "" +"Spiacente, la modifica della lista autokick è temporaneamente disabilitata." + +#: modules/commands/cs_drop.cpp:29 +msgid "Sorry, channel de-registration is temporarily disabled." +msgstr "" +"Spiacente, la deregistrazione dei canali è temporaneamente disabilitata." + +#: modules/commands/cs_register.cpp:35 +msgid "Sorry, channel registration is temporarily disabled." +msgstr "Spiacente, la registrazione dei canali è temporaneamente disabilitata." + +#: modules/commands/bs_kick.cpp:181 +msgid "Sorry, kicker configuration is temporarily disabled." +msgstr "Spiacente, la configurazione dei kick è temporaneamente disabilitata." + +#: modules/commands/ms_set.cpp:216 +msgid "Sorry, memo option setting is temporarily disabled." +msgstr "" +"Spiacente, l'impostazione delle opzioni dei memo è temporaneamente " +"disabilitata." + +#: include/language.h:116 +msgid "Sorry, memo sending is temporarily disabled." +msgstr "Spiacente, l'invio dei memo è temporaneamente disabilitato." + +#: modules/commands/ns_drop.cpp:29 +msgid "Sorry, nickname de-registration is temporarily disabled." +msgstr "Spiacente, la deregistrazione dei nick è temporaneamente disabilitata." + +#: modules/commands/ns_group.cpp:120 +msgid "Sorry, nickname grouping is temporarily disabled." +msgstr "Spiacente, il raggruppamento dei nick è temporaneamente disabilitato." + +#: modules/commands/ns_register.cpp:139 +msgid "Sorry, nickname registration is temporarily disabled." +msgstr "Spiacente, la registrazione dei nick è temporaneamente disabilitata." + +#: modules/commands/ns_access.cpp:33 +#, c-format +msgid "Sorry, the maximum of %d access entries has been reached." +msgstr "" +"Spiacente, il limite massimo di %d mask in lista di accesso è stato " +"raggiunto." + +#: modules/commands/ns_ajoin.cpp:141 +#, c-format +msgid "Sorry, the maximum of %d auto join entries has been reached." +msgstr "Spiacente, il limite massimo di %d auto join è stato raggiunto." + +#: modules/commands/ns_cert.cpp:173 +#, c-format +msgid "Sorry, the maximum of %d certificate entries has been reached." +msgstr "Spiacente, il limite massimo di %d certificati è stato raggiunto." + +#: modules/commands/ms_ignore.cpp:55 +#, c-format +msgid "Sorry, the memo ignore list for %s is full." +msgstr "La lista ignorati dei memo per %s è piena." + +#: modules/commands/cs_access.cpp:204 modules/commands/cs_flags.cpp:174 +#: modules/commands/cs_xop.cpp:201 +#, c-format +msgid "" +"Sorry, you can only have %d access entries on a channel, including access " +"entries from other channels." +msgstr "" +"Spiacente, puoi avere un massimo di %d voci nella lista di accesso di un " +"canale, incluse le voci da altri canali." + +#: modules/commands/cs_akick.cpp:177 +#, c-format +msgid "Sorry, you can only have %d autokick masks on a channel." +msgstr "Spiacente, puoi avere un massimo di %d mask in autokick." + +#: modules/commands/bs_badwords.cpp:286 +#, c-format +msgid "Sorry, you can only have %d bad words entries on a channel." +msgstr "" +"Spiacente, puoi avere un massimo di %d parolacce nella lista di un canale." + +#: include/language.h:103 +#, c-format +msgid "Sorry, you have already exceeded your limit of %d channels." +msgstr "Spiacente, hai già superato il tuo limite di %d canali." + +#: include/language.h:102 +#, c-format +msgid "Sorry, you have already reached your limit of %d channels." +msgstr "Spiacente, hai già raggiunto il tuo limite di %d canali." + +#: modules/commands/os_dns.cpp:218 +msgid "State" +msgstr "Stato" + +#: modules/commands/cs_seen.cpp:117 +msgid "Statistics and maintenance for seen data" +msgstr "Statistiche e manutenzione per i dati seen" + +#: modules/commands/os_stats.cpp:131 +msgid "Statistics reset." +msgstr "Reset delle statistiche." + +#: modules/commands/ns_update.cpp:36 +msgid "Status updated (memos, vhost, chmodes, flags)." +msgstr "Stato aggiornato (memos, vHost, chmodi, flags)." + +#: modules/commands/bs_kick.cpp:1432 +msgid "Stop flooding!" +msgstr "Non floodare!" + +#: modules/commands/bs_kick.cpp:1448 +msgid "Stop repeating yourself!" +msgstr "Smettila di ripetere!" + +#: modules/commands/cs_set.cpp:746 +msgid "Stricter control of channel founder status" +msgstr "Abilita un controllo più rigoroso dello stato di founder" + +#: modules/commands/cs_set.cpp:810 +msgid "Stricter control of chanop status" +msgstr "Abilita un controllo più rigoroso dello stato di operatore" + +#: modules/commands/ns_alist.cpp:75 modules/commands/cs_info.cpp:50 +msgid "Successor" +msgstr "Successore" + +#: modules/commands/cs_set.cpp:1006 +#, c-format +msgid "Successor for %s changed to %s." +msgstr "Il successore del canale %s ora è %s." + +#: modules/commands/cs_set.cpp:1008 +#, c-format +msgid "Successor for %s unset." +msgstr "Il successore del canale %s è stato rimosso." + +#: modules/commands/os_set.cpp:81 +msgid "" +"Super admin can not be set because it is not enabled in the configuration." +msgstr "" +"L'impostazione Super Admin non può essere attivata perché non è abilitata " +"nella configurazione." + +#: modules/commands/ns_suspend.cpp:60 +msgid "Suspend a given nick" +msgstr "Sospende il nick specificato" + +#: modules/commands/cs_suspend.cpp:236 modules/commands/ns_suspend.cpp:250 +msgid "Suspend reason" +msgstr "Motivo sospensione" + +#: modules/commands/cs_suspend.cpp:232 modules/commands/ns_suspend.cpp:246 +msgid "Suspended" +msgstr "Sospeso" + +#: modules/commands/cs_suspend.cpp:234 modules/commands/ns_suspend.cpp:248 +msgid "Suspended by" +msgstr "Sospeso da" + +#: modules/commands/cs_suspend.cpp:238 modules/commands/ns_suspend.cpp:252 +msgid "Suspended on" +msgstr "Sospeso il" + +#: modules/commands/ns_suspend.cpp:147 +msgid "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." +msgstr "" +"Sospende un nickname registrato. La sospensione del nick ne impedisce\n" +"l'uso mantenendone dati e impostazioni. Se viene specificata una\n" +"scandenza il nick sarà sospeso per quel determinato periodo di tempo, se " +"invece\n" +"non viene specificata nessuna scadenza, sarà usata la scadenza predefinita\n" +"specificata nel file di configurazione." + +#: modules/commands/cs_suspend.cpp:240 modules/commands/ns_suspend.cpp:254 +msgid "Suspension expires" +msgstr "Scadenza sospensione" + +#: modules/commands/cs_sync.cpp:19 +msgid "Sync users channel modes" +msgstr "Sincronizza i modi utente nel canale" + +#: modules/commands/cs_sync.cpp:49 +msgid "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." +msgstr "" +"Sincronizza tutti i modi impostati sugli utenti di un canale con\n" +"i modi che dovrebbero avere in base al loro accesso." + +#: modules/commands/hs_group.cpp:42 +msgid "Syncs the vhost for all nicks in a group" +msgstr "Sincronizza il vHost per tutti i nick nel gruppo" + +#: src/command.cpp:146 +msgid "Syntax" +msgstr "Sintassi" + +#: modules/commands/ns_group.cpp:373 +#, c-format +msgid "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." +msgstr "" +"Sintassi: %s\n" +" \n" +"Mostra tutti i nick del tuo gruppo." + +#: modules/commands/ns_group.cpp:363 +#, c-format +msgid "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." +msgstr "" +"Sintassi: %s [nickname]\n" +"\n" +"Senza parametro, mostra tutti i nick presenti nel\n" +"tuo gruppo.\n" +" \n" +"Con un parametro, mostra tutti i nick presenti nel gruppo\n" +"del nick specificato.\n" +"La specifica del nick è riservata ai Services Operator." + +#: modules/commands/os_set.cpp:227 +msgid "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." +msgstr "" +"Sintassi: DEBUG {ON | OFF}\n" +" \n" +"Attiva o disattiva la modalità di debug.\n" +" \n" +"Questa opzione è equivalente all'opzione da riga di comando\n" +"--debug." + +#: modules/commands/ms_set.cpp:287 +#, c-format +msgid "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." +msgstr "" +"Sintassi: LIMIT [canale] limit\n" +" \n" +"Imposta il numero massimo di memo che si possono tenere\n" +"in archivio (o che può tenere in archivio il canale indicato).\n" +"Se il limite è impostato a 0, nessuno potrà inviare memo.\n" +"In ogni caso, non è possibile impostare il limite a un valore\n" +" maggiore di %d." + +#: modules/commands/ms_set.cpp:267 +#, c-format +msgid "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." +msgstr "" +"Sintassi: SET LIMIT [user | canale] {limite | NONE} [HARD]\n" +" \n" +"Imposta il numero massimo di memo che un utente o un\n" +"canale può avere. Impostare il limite a 0 fa in modo che\n" +"l'utente (o il canale) non possa ricevere alcun memo,\n" +"impostarlo a NONE fa sì che l'utente (o il canale) possa\n" +"ricevere e conservare un numero indefinito di memo. Se non\n" +"viene specificato nessun nick o canale, viene impostato il\n" +"proprio limite.\n" +" \n" +"Aggiungere il parametro HARD fa in modo che l'utente non\n" +"possa cambiare il limite. Non aggiungerlo ha l'effetto\n" +"opposto, e permette all'utente di cambiarlo, anche se un\n" +"limite precedente era stato impostato con HARD.\n" +" \n" +"Questo uso di SET LIMIT è limitato ai Services Operator.\n" +"Gli altri utenti possono impostare il limite soltanto per\n" +"se stessi o per i canali sui quali hanno abbastanza\n" +"privilegi, e potrebbero non essere in grado di rimuovere\n" +"il limite o di impostarlo a un valore maggiore di %d." + +#: modules/commands/os_set.cpp:208 +#, c-format +msgid "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." +msgstr "" +"Sintassi: LIST\n" +" \n" +"Mostra le varie impostazioni di %s." + +#: modules/commands/os_set.cpp:234 +msgid "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." +msgstr "" +"Sintassi: NOEXPIRE {ON | OFF}\n" +" \n" +"Attiva o disattiva la modalità no expire. In modalità\n" +"no expire, i nick, i canali, le akill e le eccezioni\n" +"non scadranno fino a quando l'opzione non viene disattivata.\n" +" \n" +"Questa opzione è equivalente all'opzione di riga di comando\n" +"--noexpire." + +#: modules/commands/ms_set.cpp:246 +msgid "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." +msgstr "" +"Sintassi: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Cambia il modo in cui si verrà informati della ricezione\n" +"di nuovi memo:\n" +" \n" +" ON Si verrà informati dei nuovi memo quando ci si\n" +" connette, quando si torna dall'/AWAY, e quando\n" +" vengono inviati (se si è online).\n" +" LOGON Si verrà informati dei nuovi memo quando ci si\n" +" connette o quando si torna dall'/AWAY.\n" +" NEW Si verrà informati dei nuovi memo solo quando\n" +" vengono inviati (se si è online).\n" +" MAIL Si verrà informati dei nuovi memo via email,\n" +" oltre alle altre possibili impostazioni che hai.\n" +" NOMAIL Non riceverai notifiche via email.\n" +" OFF Non si verrà informati in nessun caso della\n" +" ricezione dei nuovi memo.\n" +" \n" +"ON è sostanzialmente la combinazione di LOGON e NEW." + +#: modules/commands/os_set.cpp:212 +msgid "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." +msgstr "" +"Sintassi: READONLY {ON | OFF}\n" +" \n" +"Attiva o disattiva la modalità read-only. In modalità\n" +"read-only, gli utenti normali non potranno modificare\n" +"nessuna informazione nei database dei Services, incluse\n" +"le liste di accesso dei nick e dei canali, eccetera.\n" +"Gli IRCOp con sufficienti privilegi sui Services potranno\n" +"modificare le liste AKILL, SQLINE, SNLINE, deregistrare o\n" +"bloccare nick e i canali, gestire news, oper info e DNS,\n" +"ma questi cambiamenti non saranno salvati nel databas, a meno\n" +"che la modalità read-only non sia disattivata prima che i\n" +"Services vengano terminati oppure riavviati.\n" +" \n" +"Questa opzione è equivalente all'opzione di riga di comando\n" +"--readonly." + +#: modules/commands/os_set.cpp:243 +msgid "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." +msgstr "" +"Sintassi: SUPERADMIN {ON | OFF}\n" +"Questa impostazione aumenterà i privilegi dell'admin che\n" +"la richiede, e permetterà ad esempio di essere founder\n" +"su tutti i canali, ecc.\n" +" \n" +"Questa opzione NON è persistente, e dovrebbe essere usata\n" +"solo quando necessario, e reimpostata a OFF al più presto." + +#: modules/commands/ns_identify.cpp:107 +#, c-format +msgid "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." +msgstr "" +"Indica a %s che sei il vero proprietario del nick.\n" +"Molti comandi richiedono che un utente sia autenticato\n" +"con questo comando prima di poter essere usati.\n" +"La password, se non è stata cambiata, è quella scelta\n" +"durante il processo di registrazione utilizzando il\n" +"comando REGISTER." + +#: modules/commands/cs_invite.cpp:91 +#, c-format +msgid "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Chiede a %s di invitarti, o di invitare il nick specificato\n" +"in un determinato canale.\n" +" \n" +"Di default, il comando è limitato agli AOP o agli utenti con\n" +"livello di accesso 5 o superiori al canale." + +#: modules/commands/cs_unban.cpp:103 +#, c-format +msgid "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Chiede a %s di rimuovere tutti i ban che non ti permettono,\n" +"o non permettono all'utente specificato di entrare in un\n" +"determinato canale. Se non viene specificato alcun canale,\n" +"tutti i ban presenti nei canali a cui hai accesso saranno\n" +"rimossi. \n" +"Di default, il comando è limitato agli AOP o agli utenti con\n" +"livello di accesso 5 o superiori sul canale." + +#: modules/commands/os_jupe.cpp:56 +msgid "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." +msgstr "" +"Fa sì che i Services blocchino un server, creando un server\n" +"\"fasullo\" connesso ai Services per evitare che il server reale\n" +"possa connettersi alla rete. Questo blocco può essere rimosso\n" +"utilizzando il comando standard SQUIT. Se viene indicato\n" +"un motivo, questo sarà utilizzato nel campo delle informazioni\n" +"del server, altrimenti, le informazioni conterranno il testo\n" +"\"Juped by \", indicando il nick della persona che ha\n" +"bloccato il server." + +#: modules/commands/cs_seen.cpp:261 +msgid "Tells you about the last time a user was seen" +msgstr "Ti informa sull'ultima volta che un utente è stato visto online" + +#: modules/commands/os_shutdown.cpp:19 +msgid "Terminate Services WITHOUT saving" +msgstr "Termina i Services senza salvare i database" + +#: modules/commands/os_shutdown.cpp:73 +msgid "Terminate services with save" +msgstr "Termina i Services salvando i database" + +#: modules/commands/os_news.cpp:156 +msgid "Text" +msgstr "Testo" + +#: modules/commands/cs_access.cpp:576 +msgid "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." +msgstr "" +"Il comando ACCESS ADD aggiunge il nick specificato alla\n" +"lista di accesso con il livello specificato, se il nick è\n" +"già presente nella lista, il suo livello viene modificato,\n" +"impostandolo a quello specificato nel comando. Il livello\n" +"specificato può essere un livello numerico o il nome di un\n" +"privilegio (es. AUTOOP)." + +#: modules/commands/cs_access.cpp:587 +msgid "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." +msgstr "" +"Il comando ACCESS DEL rimuove il nick specificato dalla\n" +"lista di accesso. Se viene specificata una lista di id numerici,\n" +"i record corrispondenti vengono rimossi. (Guarda l'esempio di\n" +"LIST). Se vuoi puoi rimuovere te stesso da una lista di accesso,\n" +"anche se non hai l'accesso necessario per modificarla." + +#: modules/commands/cs_access.cpp:593 +msgid "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." +msgstr "" +"Il comando ACCESS LIST mostra la lista di accesso. Se viene\n" +"utilizzata una wildcard per la mask, solo i record che\n" +"corrispondono alla mask vengono mostrati. Se viene specificata\n" +"una lista di id numerici, i record corrispondenti vengono mostrati.\n" +"Esempio:\n" +" ACCESS #canale LIST 2-5,7-9\n" +" Mostra i record della lista che hanno numero da 2\n" +" a 5 e da 7 a 9 (il 6 è quindi escluso).\n" +" \n" +"Il comando ACCESS VIEW mostra la lista di accesso in modo simile\n" +"a ACCESS LIST ma mostra chi ha inserito il record e l'ultimo accesso.\n" +" \n" +"Il comando ACCESS CLEAR svuota completamente la lista di\n" +"accesso." + +#: modules/commands/cs_flags.cpp:447 +msgid "" +"The CLEAR command clears the channel access list. This requires channel " +"founder access." +msgstr "" +"Il comando CLEAR svuota la lista di accesso del canale, richiede di essere " +"founder." + +#: modules/commands/cs_seen.cpp:173 +#, c-format +msgid "" +"The CLEAR command lets you clean the database by removing all entries from " +"the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." +msgstr "" +"Il comando CLEAR ti permette di pulire il database rimuovento tutti i dati\n" +"aggiunti nel lasso di tempo specificato dai dati presenti nel database.\n" +" \n" +"Esempio:\n" +" %s CLEAR 30m\n" +" Rimuoverà tutti i dati aggiunti negli ultimi 30 minuti." + +#: modules/commands/bs_badwords.cpp:438 +msgid "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." +msgstr "" +"Il comando DEL rimuove la parola specificata dalla lista\n" +"delle parolacce. Se viene indicata una lista di id numerici,\n" +"saranno rimossi solo i records corrispondenti. (Guarda \n" +"l'esempio di LIST.)\n" +" \n" +"Il comando LIST mostra la lista delle parolacce. Se viene\n" +"usata una wildcard, solo le parolacce che corrispondono\n" +"saranno mostrate. Se viene indicata una lista di id numerici,\n" +"saranno mostrati solo i records corrispondenti.\n" +"Esempio:\n" +" #canale LIST 2-5,7-9\n" +" Mostra le parolacce con id numerico da 2 a 5 e da\n" +" 7 a 9 (escludendo quindi il 6).\n" +" \n" +"Il comando CLEAR rimuove tutti i records dalla lista parolacce." + +#: modules/commands/cs_entrymsg.cpp:241 +msgid "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." +msgstr "" +"Il comando ENTRYMSG ADD aggiunge il messaggio specificato\n" +"alla lista dei messaggi da mostrare agli utenti al momento\n" +"dell'ingresso nel canale." + +#: modules/commands/cs_entrymsg.cpp:253 +msgid "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." +msgstr "" +"Il comando ENTRYMSG CLEAR rimuove tutti i records dalla\n" +"lista dei messaggi da mostrare agli utenti al momento\n" +"dell'ingresso nel canale, l'invio del messaggio di\n" +"di ingresso è di conseguenza disabilitato." + +#: modules/commands/cs_entrymsg.cpp:245 +msgid "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." +msgstr "" +"Il comando ENTRYMSG DEL rimuove il messaggio specificato dalla\n" +"lista dei messaggi da mostrare agli utenti al momento\n" +"dell'ingresso nel canale. Puoi rimuovere un messaggio specificando\n" +"il suo id numerico che puoi recuperare visualizzando la lista\n" +"dei messaggi come spiegato di seguito." + +#: modules/commands/cs_entrymsg.cpp:250 +msgid "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." +msgstr "" +"Il comando ENTRYMSG LIST mosta la lista dei messaggi da mostrare agli utenti " +"al momento dell'ingresso nel canale." + +#: modules/commands/ns_set.cpp:713 +msgid "The IMMED option is not available on this network." +msgstr "L'opzione IMMED non è disponibile su questa rete." + +#: modules/commands/cs_access.cpp:821 +#, c-format +msgid "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." +msgstr "" +"Il comando LEVELS permette un controllo preciso del\n" +"significato dei livelli di accesso numerici usati nei canali.\n" +"Con questo comando, è possibile definire il livello di accesso\n" +"necessario per la maggior parte delle funzioni di %s. (Il comando\n" +"SET FOUNDER, e questo comando sono sempre riservati al founder.)\n" +" \n" +"LEVELS SET permette di definire il livello di accesso per una funzione\n" +"o per un gruppo di funzioni. LEVELS DISABLE (o abbreviato DIS) disabilita\n" +"una funzione automatica o non permette più l'accesso a una funzione\n" +"a nessuno, founder incluso (il quale, può sempre e comunque riabilitarla).\n" +" \n" +"LEVELS LIST mostra i livelli di accesso attuali per ogni funzione\n" +"o gruppo di funzioni. LEVELS RESET reimposta i valori di default\n" +"di un canale appena creato (vedi HELP ACCESS LEVELS).\n" +" \n" +"Per una lista delle funzioni e delle caratteristiche i cui livelli\n" +"possono essere impostati, vedi HELP LEVELS DESC." + +#: modules/commands/cs_flags.cpp:442 +msgid "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." +msgstr "" +"Il comando LIST ti permette di mostrare la lista completa di tutti i " +"records\n" +"presenti nella lista di accesso del canale.\n" +"Se specifacata una mask, la mask viene confrontata con tutti i records " +"esistenti nella\n" +"lista di accesso, e solamente i records corrispondenti vengono mostrati.\n" +"Se specificato un set di flags, vengono mostrati solo quelli presenti nella " +"lista di accesso\n" +"con il flag specificato." + +#: modules/commands/cs_flags.cpp:435 +msgid "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access " +"list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. " +"You are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of " +"what your access is." +msgstr "" +"Il comando MODIFY permette di modificare la lista di accesso. Se la mask\n" +"non è già presente nella lista di accesso viene aggiunta, e quindi le " +"modifiche applicate.\n" +"Se una mask non ha più nessuna flag, la mask viene rimossa dalla lista di " +"accesso.\n" +"Inoltre, è possibile usare +* o -* per aggiungere o rimuovere " +"rispettivamente tutte le flags.\n" +"È possibile modificare la lista di accesso esclusivamente se in possesso " +"dei\n" +"privilegi necessari nel canale.\n" +"Non è possibile dare livello di accesso superiore di quello posseduto ad " +"altri utenti." + +#: modules/commands/cs_seen.cpp:172 +msgid "" +"The STATS command prints out statistics about stored nicks and memory usage." +msgstr "" +"Il comando STATS mostra le statistiche relative ai memorizzati e l'uso della " +"memoria." + +#: modules/commands/ns_register.cpp:291 +msgid "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." +msgstr "" +"Il parametro email è facoltativo e imposterà l'email\n" +"per il tuo nick immediatamente.\n" +"La tua privacy è rispettata, questa e-mail non sarà ceduta a terzi.\n" +"Puoi scegliere se mostrare o nascondere il tuo indirizzo email\n" +"dall'output del comando INFO utilizzando il comando SET HIDE.\n" +"Di default l'indirizzo email è nascosto." + +#: modules/commands/cs_log.cpp:258 +#, c-format +msgid "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." +msgstr "" +"Il comando %s permette agli utenti di configurare le impostazioni di\n" +"logging per i loro canali. Se non vengono specificati parametri, questo\n" +"comando mostra la lista dei metodi di logging attualmente attivi\n" +"sul canale.\n" +" \n" +"Altrimenti, comando deve essere il nome di un comando, e metodo\n" +"è uno dei seguenti metodi di logging:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Che sono rispettivamente usati per inviare un messaggio, un notice e un memo " +"al canale.\n" +"Con MESSAGE o NOTICE è necessario avere un bot dei services assegnato e " +"presente nel\n" +"canale. Status è lo stato degli utenti in un canale come @ o +.\n" +" \n" +"Per rimuovere un metodo di logging usa la stessa sintassi usata per " +"aggiungerlo.\n" +" \n" +"Esempio:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Invierà un messaggio a qualsiasi operatore del canale ogni volta che " +"qualcuno\n" +" userà il comando ACCESS su ChanServ nel canale." + +#: modules/commands/cs_ban.cpp:64 +#, c-format +msgid "The %s list for %s is full." +msgstr "La lista %s per %s è piena." + +#: modules/commands/os_sxline.cpp:220 +#, c-format +msgid "The %s list has been cleared." +msgstr "La lista %s è stata svuotata." + +#: modules/commands/os_akill.cpp:377 +msgid "The AKILL list has been cleared." +msgstr "La lista AKILL è stata svuotata." + +#: modules/commands/os_defcon.cpp:136 modules/commands/os_defcon.cpp:225 +#, c-format +msgid "The Defcon level is now at: %d" +msgstr "Il livello Defcon è ora: %d" + +#: modules/commands/ns_info.cpp:171 +#, c-format +msgid "The E-mail address of %s will now be hidden from %s INFO displays." +msgstr "L'indirizzo e-mail di %s verrà ora nascosto da %s INFO." + +#: modules/commands/ns_info.cpp:172 +#, c-format +msgid "The E-mail address of %s will now be shown in %s INFO displays." +msgstr "L'indirizzo e-mail di %s verrà ora mostrato in %s INFO." + +#: modules/commands/cs_flags.cpp:449 +msgid "The available flags are:" +msgstr "Le flags disponibili sono:" + +#: modules/commands/os_defcon.cpp:240 +msgid "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." +msgstr "" +"Il sistema defcon può essere utilizzato per implementare un insieme\n" +"di restrizioni dei servizi predefinite, utili durante un tentativo\n" +"d'attacco sul network." + +#: modules/ns_maxemail.cpp:51 +#, c-format +msgid "The email address %s has reached its usage limit of %d users." +msgstr "L'indirizzo email %s ha raggiunto il limite di %d utenti." + +#: modules/ns_maxemail.cpp:49 +#, c-format +msgid "The email address %s has reached its usage limit of 1 user." +msgstr "L'indirizzo email %s ha raggiunto il limite di 1 utente." + +#: modules/commands/cs_entrymsg.cpp:142 +#, c-format +msgid "The entry message list for %s is full." +msgstr "La lista dei messaggi di ingresso per %s è piena." + +#: modules/commands/cs_access.cpp:796 +msgid "The following feature/function names are available:" +msgstr "I seguenti nomi di caratteristiche/funzioni sono disponibili:" + +#: modules/commands/cs_access.cpp:584 +msgid "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." +msgstr "" +"La mask specificata può essere anche un canale, il quale userà\n" +"la lista di accesso dell'altro canale fino al livello specificato." + +#: modules/commands/os_session.cpp:240 +#, c-format +msgid "" +"The host %s currently has %d sessions with a limit of %d because it matches " +"entry: %s." +msgstr "" +"L'host %s ha %d sessioni, con un limite di %d perchè corrisponde il record:" +" %s." + +#: modules/commands/ms_check.cpp:54 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has been read." +msgstr "L'ultimo memo che hai inviato a %s (inviato il %s) è stato letto." + +#: modules/commands/ms_check.cpp:52 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has not yet been read." +msgstr "" +"L'ultimo memo che hai inviato a %s (inviato il %s) non è stato ancora letto." + +#: modules/commands/ns_info.cpp:189 +#, c-format +msgid "The last quit message of %s will now be hidden from %s INFO displays." +msgstr "L'ultimo messaggio di quit di %s verrà ora nascosto da %s INFO." + +#: modules/commands/ns_info.cpp:190 +#, c-format +msgid "The last quit message of %s will now be shown in %s INFO displays." +msgstr "L'ultimo messaggio di quit di %s verrà ora mostrato in %s INFO." + +#: modules/commands/ns_info.cpp:177 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." +msgstr "L'ultima mask user@host vista di %s verrà ora nascosta da %s INFO." + +#: modules/commands/ns_info.cpp:178 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." +msgstr "L'ultima mask user@host vista di %s verrà ora mostrata in %s INFO." + +#: modules/commands/cs_enforce.cpp:190 +#, c-format +msgid "The limit on %s is not valid." +msgstr "Il limite dei memo su %s non è valido." + +#: modules/commands/os_forbid.cpp:193 +msgid "The mask must contain at least one non wildcard character." +msgstr "La mask deve contenere almeno un carattere che non sia una wildcard." + +#: modules/commands/ms_set.cpp:153 +#, c-format +msgid "The memo limit for %s may not be changed." +msgstr "Il limite dei memo di %s non può essere modificato." + +#: modules/commands/cs_mode.cpp:347 +#, c-format +msgid "The mode lock list of %s is full." +msgstr "La lista dei modi bloccati di %s è piena." + +#: modules/commands/ns_set.cpp:355 +#, c-format +msgid "The new display MUST be a nickname of the nickname group %s." +msgstr "" +"Il nuovo nome del gruppo DEVE essere un nickname presente nel gruppo %s." + +#: include/language.h:98 +#, c-format +msgid "The new display is now %s." +msgstr "Il nuovo nome del gruppo adesso è: %s." + +#: modules/commands/os_svs.cpp:57 +#, c-format +msgid "The nick %s is now being changed to %s." +msgstr "Il nick %s viene ora cambiato in %s." + +#: modules/commands/bs_bot.cpp:149 +msgid "The old information is the same as the new information specified." +msgstr "La nuova informazione specificata è uguale alla vecchia." + +#: modules/commands/os_info.cpp:157 +#, c-format +msgid "The oper info already exists on %s." +msgstr "L'oper info è già esistente su %s." + +#: modules/commands/os_info.cpp:147 +#, c-format +msgid "The oper info list for %s is full." +msgstr "La lista oper info per %s è piena." + +#: modules/commands/ns_info.cpp:183 +#, c-format +msgid "" +"The services access status of %s will now be hidden from %s INFO displays." +msgstr "Lo stato di accesso ai servizi di %s verrà ora nascosto da %s INFO." + +#: modules/commands/ns_info.cpp:184 +#, c-format +msgid "The services access status of %s will now be shown in %s INFO displays." +msgstr "Lo stato di accesso ai servizi di %s verrà ora mostrato in %s INFO." + +#: modules/commands/os_session.cpp:433 +msgid "The session exception list is empty." +msgstr "La lista delle eccezioni sulle sessioni è vuota." + +#: modules/commands/ns_recover.cpp:121 +msgid "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." +msgstr "" +"L'utente con il tuo nick è stato rimosso. Usa questo comando di nuovo\n" +"per far rilasciare il blocco dei services sul tuo nick." + +#: modules/pseudoclients/memoserv.cpp:195 +#, c-format +msgid "There are %d memos on channel %s." +msgstr "Ci sono %d memo sul canale %s." + +#: modules/commands/bs_botlist.cpp:47 +msgid "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" +msgstr "" +"Non ci sono bot disponibili in questo momento.\n" +"Chiedi a un Services Operator di crearne uno!" + +#: modules/commands/os_dns.cpp:213 +msgid "There are no configured servers." +msgstr "Non ci sono servers configurati." + +#: modules/commands/os_forbid.cpp:392 +#, c-format +msgid "There are no forbids of type %s." +msgstr "Non sono presenti forbid di tipo %s." + +#: modules/commands/ns_group.cpp:162 +msgid "There are too many nicks in your group." +msgstr "Sono presenti troppo nick nel tuo gruppo." + +#: modules/commands/cs_log.cpp:123 +#, c-format +msgid "There currently are no logging configurations for %s." +msgstr "Attualmente non è presente alcuna configurazione per il logging su %s." + +#: modules/pseudoclients/memoserv.cpp:193 +#, c-format +msgid "There is %d memo on channel %s." +msgstr "C'è %d memo sul canale %s." + +#: include/language.h:110 +#, c-format +msgid "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." +msgstr "" +"C'è un nuovo memo sul canale %s.\n" +"Digita %s%s READ %s %d per leggerlo." + +#: modules/commands/bs_assign.cpp:132 +#, c-format +msgid "There is no bot assigned to %s anymore." +msgstr "Non c'è più nessun bot assegnato a %s." + +#: modules/commands/os_news.cpp:33 +msgid "There is no logon news." +msgstr "Non c'è nessuna Logon News." + +#: modules/commands/os_news.cpp:43 +msgid "There is no oper news." +msgstr "Non c'è nessuna Oper News." + +#: modules/commands/os_news.cpp:53 +msgid "There is no random news." +msgstr "Non c'è nessuna Random News." + +#: modules/commands/os_config.cpp:41 +#, c-format +msgid "There is no such configuration block %s." +msgstr "Non c'è nessun blocco di configurazione %s." + +#: modules/commands/cs_mode.cpp:706 +#, c-format +msgid "There is no such mode %s." +msgstr "Non esiste alcun modo %s." + +#: modules/commands/ms_set.cpp:52 +msgid "There's no email address set for your nick." +msgstr "Non c'è un indirizzo email impostato per il tuo nick." + +#: modules/commands/os_forbid.cpp:304 modules/commands/os_forbid.cpp:496 +#, c-format +msgid "This channel has been forbidden: %s" +msgstr "Questo canale è stato vietato: %s" + +#: modules/commands/cs_suspend.cpp:121 +msgid "This channel has been suspended." +msgstr "Questo canale è stato sospeso." + +#: modules/commands/cs_suspend.cpp:232 +msgid "This channel is suspended." +msgstr "Questo canale è sospeso." + +#: modules/commands/cs_suspend.cpp:268 +msgid "This channel may not be used." +msgstr "Questo canale non può essere usato." + +#: modules/commands/os_dns.cpp:702 +msgid "" +"This command allows managing DNS zones used for controlling what servers " +"users\n" +"are directed to when connecting. Omitting all parameters prints out the " +"status of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to " +"this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, " +"the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given " +"zones." +msgstr "" +"Questo comando permette di gestire le zone DNS usate per controllare su " +"quali server gli utenti\n" +"verranno indirizzati in fase di connessione. Omettere i parametri mostrerà " +"lo stato della\n" +"zona DNS.\n" +" \n" +"ADDZONE aggiunge una zona, es: us.yournetwork.tld. I servers possono essere " +"aggiunti a tale\n" +"zona con il comando ADDSERVER.\n" +" \n" +"Il comando ADDSERVER aggiungere un server alla zona. Quando una query viene " +"eseguita, la\n" +"zona in questione sarà servita se esiste, altrimenti tutti i server in tutte " +"le zone verranno serviti.\n" +"Un server potrebbe essere in più di una zona.\n" +" \n" +"Il comando ADDIP associa un IP con un server.\n" +" \n" +"I comandi POOL e DEPOOL aggiungono e rimuovono i server dalle loro " +"rispettive zone." + +#: modules/commands/hs_group.cpp:72 +msgid "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." +msgstr "" +"Questo comando permette agli utenti di impostare il vHost del\n" +"loro nick ATTUALE come vHost di tutti i nick nello stesso gruppo." + +#: modules/commands/ns_register.cpp:299 +msgid "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." +msgstr "" +"Questo comando crea anche un nuovo gruppo per il tuo nick,\n" +"che ti permetterà di registrare altri nick condividendo\n" +"la stessa configurazione, gli stessi memo e gli stessi\n" +"privilegi sui canali." + +#: modules/m_rewrite.cpp:145 +#, c-format +msgid "This command is an alias to the command %s." +msgstr "Questo comando è un alias del comando %s." + +#: modules/commands/ns_register.cpp:95 +msgid "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." +msgstr "" +"Questo comando è usato da alcuni comandi come modo per confermare\n" +"i cambiamenti fatti al tuo account.\n" +" \n" +"È comunemente usato per confermare il tuo indirizzo email\n" +"quando ti registri o quando lo cambi.\n" +" \n" +"È usato anche dopo il comando RESETPASS per forzare l'identificazione\n" +"del tuo nick e permetterti di reimpostare la password." + +#: modules/commands/os_modinfo.cpp:70 +msgid "This command lists information about the specified loaded module." +msgstr "Questo comando elenca informazioni sul modulo caricato specificato." + +#: modules/commands/hs_list.cpp:136 +msgid "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." +msgstr "" +"Questo comando elenca i vHost registrati all'operatore.\n" +"Se una chiave è specificata, verranno mostrati unicamente i\n" +"vHost corrispondenti a quanto immesso come chiave, ad\n" +"esempio Rob* per tutte le corrispondenze che iniziano con \"Rob\"\n" +"Se viene usata una lista in stile #X-Y, verranno mostrate unicamente\n" +"le corrispondenze tra X ed Y, ad es. #1-3 mostrerà unicamente le prime\n" +"3 corrispondenze nick/vHost." + +#: modules/commands/os_module.cpp:45 +msgid "" +"This command loads the module named modname from the modules\n" +"directory." +msgstr "" +"Questo comando carica il modulo chiamato nomemod dalla cartella\n" +"modules." + +#: modules/commands/ns_group.cpp:201 +msgid "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." +msgstr "" +"Questo comando fa sì che il tuo nick entri nel gruppo del\n" +"nick target, password è la password del nick target .\n" +" \n" +"Entrare in un gruppo ti permetterà di condividere la tua\n" +"configurazione, i tuoi memo e i privilegi sui canali con\n" +"tutti i nick nel tuo gruppo.\n" +" \n" +"Un gruppo esiste fino a quando è utile. Questo significa\n" +"che anche se uno dei nick del gruppo viene deregistrato,\n" +"non perderai le condivisioni descritte sopra, fino a quando\n" +"nel gruppo resta almeno un nick.\n" +" \n" +"Puoi usare questo comando anche se non hai ancora registrato\n" +"il tuo nick. Se il tuo nick è già registrato, dovrai\n" +"identificarti prima di usare questo comando.\n" +" \n" +"È consigliato l'uso di questo comando con un nick non\n" +"registrato, in quanto verrà registrato automaticamente\n" +"con l'uso stesso di questo comando.\n" +" \n" +"È possibile stare in un solo gruppo per volta. L'unione dei\n" +"gruppi non è possibile\n" +" \n" +"Nota: tutti i nick di un gruppo hanno la stessa password." + +#: modules/commands/ns_ajoin.cpp:292 +msgid "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." +msgstr "" +"Questo comando gestisce la tua lista auto join. Quando ti identifichi\n" +"effettuerai automaticamente l'accesso ai canali presenti nella lista auto " +"join.\n" +"I Services Operators possono specificare un nick per modificare la lista\n" +"auto join di altri utenti." + +#: modules/commands/ns_set.cpp:345 modules/commands/ns_set.cpp:669 +msgid "" +"This command may not be used on this network because nickname ownership is " +"disabled." +msgstr "" +"Questo comando non può essere usato su questo network perché l'ownership del " +"nickname è disabilitata." + +#: modules/commands/os_module.cpp:118 +msgid "This command reloads the module named modname." +msgstr "Questo comando ricarica il modulo chiamato modname." + +#: modules/commands/hs_request.cpp:344 +msgid "This command retrieves the vhost requests." +msgstr "Questo comando recupera le richieste di vHosts." + +#: modules/commands/os_logsearch.cpp:159 +msgid "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." +msgstr "" +"Questo comando effettua una ricerca nel file di log dei Services\n" +"utilizzando il pattern specificato. Gli argomenti day e limit possono essere " +"usati per specificare fino a quanti giorni\n" +"estendere la ricerca nei logs e il limite dei risultati da mostrare.\n" +"Come impostazione predefinita questo comando recupera una settimana di\n" +"logs e limita i risultati a 50.\n" +" \n" +"Per esempio:\n" +" LOGSEARCH +21d +500l Anope\n" +" Cerca i messaggi contenenti la parola Anope nei logs relativi\n" +" agli ultimi 21 giorni e ne mostra i 500 più recenti." + +#: modules/commands/cs_status.cpp:106 +msgid "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." +msgstr "" +"Questo comando mostra il livello di accesso degli utenti in un canale\n" +"e a quali voci in lista di accesso, se presenti, corrispondono. Inoltre, " +"informerà\n" +"della presenza di eventuali voci auto kick che affliggono l'utente\n" +"specificato. L'uso di questo comando è limitato agli utenti che hanno\n" +"accesso alla possibilità di modificare la lista di accesso del canale." + +#: modules/commands/ns_group.cpp:285 +msgid "" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." +msgstr "" +"Questo comando rimuove il tuo nick, o se specificato, il nick indicato,\n" +"dal gruppo in cui si trova. Il nick che è stato rimosso dal gruppo\n" +"mantiene data di registrazione, password, email, greet, lingua, url, e icq.\n" +"Tutto il resto viene rimosso. Non puoi rimuovere il tuo nick dal tuo gruppo\n" +"se nel tuo gruppo è presente un solo nick." + +#: modules/commands/os_module.cpp:168 +msgid "This command unloads the module named modname." +msgstr "Questo comando scarica il modulo chiamato nomemod." + +#: modules/commands/ns_register.cpp:353 +msgid "This command will resend you the registration confirmation email." +msgstr "" +"Questo comando permette di ottenere il reinvio della email di conferma per " +"la registrazione." + +#: include/language.h:90 +#, c-format +msgid "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" +msgstr "" +"Questo nick è di proprietà di qualcun altro. Scegli un altro nick.\n" +"(Se questo è il tuo nick, digita %s%s IDENTIFY password.)" + +#: modules/commands/os_forbid.cpp:469 +#, c-format +msgid "This nickname has been forbidden: %s" +msgstr "Questo nickname è stato vietato: %s" + +#: modules/commands/ns_recover.cpp:99 +#, c-format +msgid "This nickname has been recovered by %s." +msgstr "Questo nickname è stato recuperato da %s." + +#: modules/commands/ns_recover.cpp:77 +#, c-format +msgid "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." +msgstr "" +"Questo nickname è stato recuperato da %s. Se non sei stato tu\n" +"ad eseguire il recupero del nick, %s potrebbe avere la tua password,\n" +"in questo caso è necessario cambiare la propria password quanto prima." + +#: include/language.h:95 +msgid "This nickname has been registered; you may not use it." +msgstr "Questo nickname è stato registrato, non puoi usarlo." + +#: modules/commands/ns_suspend.cpp:246 +msgid "This nickname is suspended." +msgstr "Questo nickname è sospeso." + +#: include/language.h:92 +#, c-format +msgid "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." +msgstr "" +"Questo nick è registrato e protetto. Se questo è il tuo\n" +"nick, digita %s%s IDENTIFY password. Altrimenti,\n" +"scegli un nick diverso." + +#: modules/commands/ms_read.cpp:95 +#, c-format +msgid "To delete, type: %s%s %s %d" +msgstr "Per cancellare, digita: %s%s %s %d" + +#: modules/commands/ms_read.cpp:93 +#, c-format +msgid "To delete, type: %s%s %s %s %d" +msgstr "Per cancellare, digita: %s%s %s %s %d" + +#: modules/commands/bs_kick.cpp:791 +msgid "To protect ops against bot kicks" +msgstr "Per proteggere gli op dai kick del bot" + +#: modules/commands/bs_kick.cpp:856 +msgid "To protect voices against bot kicks" +msgstr "Per proteggere i voice dai kick del bot" + +#: modules/commands/cs_list.cpp:46 +msgid "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." +msgstr "" +"Per cercare canali che cominciano con #, cerca il nome del canale\n" +"senza il segno # (anope invece di #anope)." + +#: modules/commands/os_logsearch.cpp:139 +#, c-format +msgid "Too many results for %s." +msgstr "Troppi risultati per %s." + +#: modules/extra/stats/cs_fantasy_top.cpp:149 +#, c-format +msgid "Top %i of %s" +msgstr "Top %i di %s" + +#: modules/commands/os_list.cpp:43 +msgid "Topic" +msgstr "Topic" + +#: modules/commands/cs_topic.cpp:258 +msgid "Topic lock" +msgstr "Blocco del topic" + +#: modules/commands/cs_topic.cpp:114 +#, c-format +msgid "Topic lock option for %s is now off." +msgstr "Il blocco del topic per %s è ora disattivato." + +#: modules/commands/cs_topic.cpp:97 +#, c-format +msgid "Topic lock option for %s is now on." +msgstr "Il blocco del topic per %s è ora attivo." + +#: modules/commands/cs_topic.cpp:256 +msgid "Topic retention" +msgstr "Mantenimento del topic" + +#: modules/commands/cs_topic.cpp:60 +#, c-format +msgid "Topic retention option for %s is now off." +msgstr "Il mantenimento del topic per %s è ora disattivato." + +#: modules/commands/cs_topic.cpp:54 +#, c-format +msgid "Topic retention option for %s is now on." +msgstr "Il mantenimento del topic per %s è ora attivo." + +#: modules/commands/cs_topic.cpp:265 +msgid "Topic set by" +msgstr "Topic impostato da" + +#: modules/commands/bs_kick.cpp:1323 +msgid "Turn caps lock OFF!" +msgstr "Disattiva il caps lock!" + +#: modules/extra/stats/m_chanstats.cpp:17 +#: modules/extra/stats/m_chanstats.cpp:71 +msgid "Turn chanstats statistics on or off" +msgstr "Attiva o disattiva le statistiche chanstats" + +#: modules/commands/ns_set.cpp:1009 +msgid "Turn nickname security on or off" +msgstr "Attiva o disattiva le impostazioni di sicurezza" + +#: modules/commands/ns_set.cpp:655 +msgid "Turn protection on or off" +msgstr "Attiva o disattiva le impostazioni di protezione" + +#: modules/commands/ns_list.cpp:264 +#, c-format +msgid "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Attiva o disattiva l'opzione privacy di %s per il nick\n" +"specificato. Quando PRIVATE è attivo, il nick non comparirà nelle\n" +"liste dei nick generate con %s comando LIST. In ogni caso, però,\n" +"chiunque sappia il nick può leggerne le informazioni con il\n" +"comando INFO." + +#: modules/commands/ns_list.cpp:236 +#, c-format +msgid "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Attiva o disattiva l'opzione privacy di %s per il tuo\n" +"nick. Quando PRIVATE è attivo, il tuo nick non comparirà nelle\n" +"liste dei nick generate con %s comando LIST. In ogni caso, però,\n" +"chiunque sappia il tuo nick può leggerne le informazioni con il\n" +"comando INFO." + +#: modules/commands/ns_set.cpp:1059 modules/commands/ns_set.cpp:1088 +#, c-format +msgid "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." +msgstr "" +"Attiva o disattiva sul tuo nick le funzionalità di sicurezza\n" +"di %s. Quando SECURE è attivo, devi identificarti come\n" +"proprietario del nick, anche se il tuo indirizzo compare\n" +"nella lista di accesso. Comunque, se sei nella lista di\n" +"accesso, %s non cambierà il tuo nick, anche se l'opzione KILL\n" +"è attiva." + +#: modules/extra/stats/m_chanstats.cpp:142 +msgid "Turns chanstats channel statistics ON or OFF for this user." +msgstr "Attiva o disattiva le statistiche di chanstats per questo utente." + +#: modules/extra/stats/m_chanstats.cpp:61 +#: modules/extra/stats/m_chanstats.cpp:119 +msgid "Turns chanstats statistics ON or OFF." +msgstr "Attiva o disattiva le statistiche di Chanstats." + +#: modules/commands/ns_set.cpp:772 +#, c-format +msgid "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Attiva o disattiva l'opzione di protezione automatica per\n" +"il nick. Quando la protezione è attiva, se un altro\n" +"utente cerca di usare il nick, avrà un minuto per\n" +"cambiarlo, passato il quale %s forzerà il cambio\n" +"del.nick in un nickname casuale.\n" +" \n" +"Se scegli QUICK, l'utente avrà soltanto 20 secondi per\n" +"cambiare nick invece di 60. Se scegli IMMED, il nick\n" +"sarà cambiato immediatamente, senza nessun preavviso\n" +"ne la possibilità di cambiare nick, non usare questa\n" +"opzione se non è strettamente necessario.\n" +"L'opzione IMMED, inoltre, potrebbe non essere disponibile." + +#: modules/commands/ns_set.cpp:738 +#, c-format +msgid "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Attiva o disattiva l'opzione di protezione automatica per\n" +"il tuo nick. Quando la protezione è attiva, se un altro\n" +"utente cerca di usare il tuo nick, avrà un minuto per\n" +"cambiarlo, passato il quale %s forzerà il cambio\n" +"del nick in un nickname casuale.\n" +" \n" +"Se scegli QUICK, l'utente avrà soltanto 20 secondi per\n" +"cambiare nick invece di 60. Se scegli IMMED, il nick\n" +"sarà cambiato immediatamente, senza nessun preavviso\n" +"ne la possibilità di cambiare nick, non usare questa\n" +"opzione se non è strettamente necessario.\n" +"L'opzione IMMED, inoltre, potrebbe non essere disponibile." + +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_forbid.cpp:358 +msgid "Type" +msgstr "Tipo" + +#: modules/commands/ns_set.cpp:62 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Digita %s%s HELP %s opzione per ottenere maggiori\n" +"informazioni su un'opzione specifica." + +#: modules/commands/bs_kick.cpp:151 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." +msgstr "" +"Digita %s%s HELP %s opzione per ottenere maggiori\n" +"informazioni su un'opzione specifica.\n" +" \n" +"Nota: l'accesso a questo comando è controllato da\n" +"level SET." + +#: modules/commands/ns_set.cpp:107 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." +msgstr "" +"Digita %s%s HELP %s opzione per maggiori informazioni\n" +"su un'opzione specifica. Le opzioni verranno impostate sul\n" +"nickname specificato." + +#: modules/commands/bs_set.cpp:62 modules/commands/cs_set.cpp:63 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." +msgstr "" +"Digita %s%s HELP %s opzione per ottenere maggiori\n" +"informazioni su un'opzione specifica." + +#: modules/pseudoclients/nickserv.cpp:361 +#, c-format +msgid "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." +msgstr "" +"Digita %s%s SET EMAIL e-mail per impostare la tua e-mail.\n" +"La tua privacy è rispettata, questa e-mail non sarà ceduta\n" +"a terze parti." + +#: modules/commands/os_module.cpp:128 +msgid "Un-Load a module" +msgstr "Rimuove un modulo" + +#: modules/commands/os_sxline.cpp:337 modules/commands/os_sxline.cpp:552 +#: modules/commands/os_akill.cpp:136 +#, c-format +msgid "Unable to find regex engine %s." +msgstr "Impossibile trovare il motore di regex %s." + +#: modules/commands/os_module.cpp:36 modules/commands/os_module.cpp:108 +#, c-format +msgid "Unable to load module %s." +msgstr "Impossibile caricare il modulo %s." + +#: modules/commands/os_module.cpp:73 modules/commands/os_module.cpp:90 +#: modules/commands/os_module.cpp:145 modules/commands/os_module.cpp:159 +#, c-format +msgid "Unable to remove module %s." +msgstr "Impossibile rimuovere il modulo %s." + +#: modules/commands/bs_assign.cpp:90 +msgid "Unassigns a bot from a channel" +msgstr "Rimuove il bot da un canale" + +#: modules/commands/bs_assign.cpp:139 +msgid "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." +msgstr "" +"Rimuove il bot da un canale. Dopo aver usato questo\n" +"comando, il bot non entrerà più nel canale, ma la sua\n" +"configurazione resterà salvata, in questo modo, in futuro,\n" +"sarà possibile riassegnare un bot al canale senza la necessità\n" +"di doverlo riconfigurare interamente." + +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1193 +#: modules/commands/bs_kick.cpp:1196 +msgid "Underlines kicker" +msgstr "Kick in caso di sottolineato" + +#: modules/commands/os_dns.cpp:595 +msgid "Unknown SET option." +msgstr "Opzione SET sconosciuta." + +#: modules/commands/os_stats.cpp:229 +#, c-format +msgid "Unknown STATS option: %s" +msgstr "Opzione STATS sconosciuta: %s" + +#: src/command.cpp:222 src/command.cpp:233 +#, c-format +msgid "Unknown command %s." +msgstr "Comando %s sconosciuto." + +#: src/command.cpp:220 src/command.cpp:231 +#, c-format +msgid "Unknown command %s. \"%s%s HELP\" for help." +msgstr "Comando sconosciuto %s. \"%s%s HELP\" per l'aiuto." + +#: modules/commands/cs_mode.cpp:317 modules/commands/cs_mode.cpp:409 +#, c-format +msgid "Unknown mode character %c ignored." +msgstr "Modo sconosciuto carattere %c ignorato." + +#: modules/commands/os_logsearch.cpp:78 +#, c-format +msgid "Unknown parameter: %s" +msgstr "Parametro sconosciuto: %s" + +#: modules/commands/os_dns.cpp:241 +msgid "Unpooled" +msgstr "Unpooled" + +#: modules/commands/cs_drop.cpp:77 +msgid "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." +msgstr "" +"Deregistra il canale specificato. Può essere usato soltanto\n" +"dal founder del canale." + +#: modules/commands/cs_drop.cpp:74 +msgid "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." +msgstr "" +"Deregistra il canale specificato. Solo i Services Operator\n" +"possono deregistrare un canale del quale non sono founder." + +#: modules/commands/ns_suspend.cpp:160 +msgid "Unsuspend a given nick" +msgstr "Rilascia il nick specificato" + +#: modules/commands/ns_suspend.cpp:199 +msgid "Unsuspends a nickname which allows it to be used again." +msgstr "Rilascia un nickname permettendone nuovamente l'uso." + +#: modules/commands/cs_updown.cpp:126 +msgid "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." +msgstr "" +"Aggiorna lo stato del nick specificato in un canale. Se il nick\n" +"è omesso, viene aggiornato il tuo stato. Se il canale è omesso, il tuo\n" +"stato viene aggiornato in tutti i canali in cui sei presente." + +#: modules/commands/cs_updown.cpp:48 +msgid "Updates a selected nicks status on a channel" +msgstr "Aggiorna lo stato del nick specificato in un canale" + +#: modules/commands/ns_update.cpp:19 +msgid "Updates your current status, i.e. it checks for new memos" +msgstr "Aggiorna il tuo stato attuale, ovvero controlla eventuali nuovi memo" + +#: modules/commands/ns_update.cpp:43 +msgid "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." +msgstr "" +"Aggiorna il tuo stato attuale, ovvero controlla eventuali nuovi memo,\n" +"imposta i modi canale necessari e i tuoi userflags (lastseentime, etc)." + +#: modules/commands/os_update.cpp:25 +msgid "Updating databases." +msgstr "Aggiornamento dei database." + +#: modules/commands/os_stats.cpp:154 +#, c-format +msgid "Uplink capab: %s" +msgstr "Uplink capab: %s" + +#: modules/commands/os_stats.cpp:153 +#, c-format +msgid "Uplink server: %s" +msgstr "Uplink server: %s" + +#: modules/commands/help.cpp:127 +#, c-format +msgid "Use the %s ALL command to list all commands and their descriptions." +msgstr "" +"Usa il comando %s ALL per ottenere la lista completa dei comandi e la loro " +"descrizione." + +#: modules/commands/bs_info.cpp:59 +msgid "Used on" +msgstr "Usato su" + +#: data/chanserv.example.conf:821 +msgid "Used to manage channels" +msgstr "Usato per gestire i canali" + +#: data/chanserv.example.conf:809 +msgid "Used to manage the list of privileged users" +msgstr "Usato per gestire la lista degli utenti privilegiati" + +#: data/chanserv.example.conf:815 +msgid "Used to modify the channel status of you or other users" +msgstr "Usato per modificare lo status del canale per te o altri utenti" + +#: modules/commands/cs_akick.cpp:575 +msgid "User has been banned from the channel" +msgstr "L'utente è stato bannato dal canale" + +#: modules/commands/os_dns.cpp:587 +#, c-format +msgid "User limit for %s removed." +msgstr "Il limite di utenti per %s è stato rimosso." + +#: modules/commands/os_dns.cpp:585 +#, c-format +msgid "User limit for %s set to %d." +msgstr "Limite di utenti per %s impostato a %d." + +#: modules/commands/os_list.cpp:43 +msgid "Users" +msgstr "Utenti" + +#: modules/commands/os_stats.cpp:172 +#, c-format +msgid "Users (nick): %lu entries, %lu buckets, longest chain is %d" +msgstr "Utenti (nick): %lu voci, %lu buckets, longest chain is %d" + +#: modules/commands/os_stats.cpp:177 +#, c-format +msgid "Users (uid): %lu entries, %lu buckets, longest chain is %d" +msgstr "Utenti (uid): %lu voci, %lu buckets, longest chain is %d" + +#: modules/commands/os_list.cpp:184 +msgid "Users list:" +msgstr "Lista utenti:" + +#: modules/commands/ns_info.cpp:105 modules/commands/ns_info.cpp:107 +msgid "VHost" +msgstr "vHost" + +#: modules/commands/hs_set.cpp:92 +#, c-format +msgid "VHost for %s set to %s." +msgstr "Il vHost per %s è stato impostato a %s." + +#: modules/commands/hs_set.cpp:90 +#, c-format +msgid "VHost for %s set to %s@%s." +msgstr "Il vHost per %s è stato impostato a %s@%s." + +#: modules/commands/hs_set.cpp:199 +#, c-format +msgid "VHost for group %s set to %s." +msgstr "Il vHost per il gruppo %s è stato impostato a %s." + +#: modules/commands/hs_set.cpp:197 +#, c-format +msgid "VHost for group %s set to %s@%s." +msgstr "Il vHost per il gruppo %s è stato impostato a %s@%s." + +#: modules/commands/os_session.cpp:247 +msgid "VIEW host" +msgstr "VIEW host" + +#: modules/commands/os_sxline.cpp:428 modules/commands/os_sxline.cpp:662 +#: modules/commands/os_akill.cpp:389 +msgid "VIEW [mask | list | id]" +msgstr "VIEW [mask | list | id]" + +#: modules/commands/os_session.cpp:526 +msgid "VIEW [mask | list]" +msgstr "VIEW [mask | list]" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +msgid "Value" +msgstr "Valore" + +#: modules/commands/os_config.cpp:48 +#, c-format +msgid "Value of %s:%s changed to %s" +msgstr "Valore di %s:%s cambiato in %s " + +#: modules/commands/hs_list.cpp:58 modules/commands/hs_request.cpp:305 +msgid "Vhost" +msgstr "vHost" + +#: modules/commands/hs_del.cpp:38 +#, c-format +msgid "Vhost for %s removed." +msgstr "Il vHost di %s è stato rimosso." + +#: modules/commands/os_oper.cpp:69 +msgid "View and change Services Operators" +msgstr "Gestisce e mostra i Services Operators" + +#: modules/commands/os_config.cpp:19 +msgid "View and change configuration file settings" +msgstr "Gestisce e mostra le impostazioni del file di configurazione" + +#: modules/commands/os_session.cpp:245 +msgid "View the list of host sessions" +msgstr "Mostra la lista delle sessioni degli host" + +#: modules/commands/bs_kick.cpp:1221 +msgid "Voices protection" +msgstr "Protezione per i voice" + +#: modules/commands/bs_kick.cpp:1406 +msgid "Watch your language!" +msgstr "Occhio a come parli!" + +#: modules/commands/cs_list.cpp:237 +#, c-format +msgid "" +"When private is set, the channel will not appear in\n" +"%s's %s command." +msgstr "" +"Quando questa opzione è attiva, il canale non sarà\n" +"incluso nella lista restituita da %s's %s." + +#: modules/commands/ms_info.cpp:204 +msgid "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." +msgstr "" +"Senza parametro, mostra le informazioni sul numero di memo\n" +"che hai, quanti memo non sono ancora stati letti e quanti\n" +"memo puoi ricevere in totale.\n" +" \n" +"Se viene indicato un canale, mostra le stesse informazioni\n" +"ma relative al canale specificato.\n" +" \n" +"Se viene indicato un nick, mostra le stesse informazioni\n" +"ma relative al nick specificato. Questo modo d'uso\n" +"è limitato ai Services Operator." + +#: modules/commands/ns_logout.cpp:66 +msgid "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." +msgstr "" +"Senza nessun parametro, annulla l'effetto del comando IDENTIFY,\n" +"rendendoti non più identificato come proprietario del nick.\n" +"Da notare, comunque, che non ti sarà richiesto di identificarti\n" +"di nuovo.\n" +" \n" +"Con un parametro, il funzionamento è identico ma viene applicato\n" +"al nick specificato. Se si indica anche REVALIDATE, i Services\n" +"chiederanno al nick specificato di reidentificarsi.\n" +"Questo modo di utilizzo è limitato ai Services Operator." + +#: modules/commands/os_stats.cpp:236 +msgid "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." +msgstr "" +"Senza nessuna opzione, mostra il numero attuale di utenti\n" +"e di IRCOp online (Services esclusi), il numero massimo\n" +"di utenti online da quando i Services sono up, e il tempo\n" +"passato da quando i Services sono stati avviati.\n" +" \n" +"Con l'opzione AKILL, mostra la dimensione attuale della\n" +"lista AKILL e la durata di default delle nuove AKILL.\n" +" \n" +"L'opzione RESET imposta il numero massimo di utenti\n" +"registrato al numero degli utenti connessi attualmente\n" +"alla rete.\n" +" \n" +"L'opzione UPLINK , mostra informazioni relative al server\n" +"attualmente usato come uplink al network.\n" +" \n" +"L'opzione HASH , mostra informazioni relativa alla hash map. \n" +"L'opzione ALL, mostra tutte le statistiche descritte in precedenza." + +#: modules/commands/bs_badwords.cpp:194 +msgid "Word" +msgstr "Parola" + +#: modules/commands/ns_group.cpp:158 +#, c-format +msgid "You are already a member of the group of %s." +msgstr "Sei già un membro del gruppo %s." + +#: modules/commands/os_login.cpp:34 modules/commands/ns_identify.cpp:87 +msgid "You are already identified." +msgstr "Sei già identificato." + +#: modules/commands/cs_invite.cpp:64 +#, c-format +msgid "You are already in %s!" +msgstr "Sei già presente in %s!" + +#: modules/commands/os_set.cpp:91 +msgid "You are no longer a super admin." +msgstr "Non sei più un Super Admin." + +#: modules/commands/os_login.cpp:81 +msgid "You are not identified." +msgstr "Non sei identificato." + +#: include/language.h:100 +msgid "You are not permitted to be on this channel." +msgstr "Non ti è permesso accedere a questo canale." + +#: modules/commands/ms_set.cpp:158 +msgid "You are not permitted to change your memo limit." +msgstr "Non puoi modificare limite dei tuoi memo." + +#: modules/commands/ns_cert.cpp:183 +msgid "You are not using a client certificate." +msgstr "Non stai usando un certificato del client." + +#: modules/commands/os_set.cpp:85 +msgid "You are now a super admin." +msgstr "Ora sei un Super Admin." + +#: modules/commands/os_oline.cpp:36 +msgid "You are now an IRC Operator." +msgstr "Ora sei un IRC Operator." + +#: modules/commands/ns_resetpass.cpp:108 +msgid "You are now identified for your nick. Change your password now." +msgstr "" +"Adesso sei identificato per il tuo nick. Cambia la tua password adesso." + +#: modules/commands/ns_group.cpp:64 +#, c-format +msgid "You are now in the group of %s." +msgstr "Adesso sei nel gruppo %s." + +#: modules/pseudoclients/memoserv.cpp:147 +#, c-format +msgid "" +"You are over your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Attenzione: Hai superato il numero massimo di memo (%d). Non potrai ricevere " +"nuovi memo finché non ne eliminerai alcuni dal tuo archivio." + +#: modules/commands/os_noop.cpp:33 +msgid "You can not NOOP Services." +msgstr "Non puoi usare NOOP sui Services." + +#: modules/commands/cs_access.cpp:672 +msgid "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." +msgstr "" +"Non puoi disabilitare il privilegio di founder perché in seguito sarebbe " +"impossibile riabilitarlo." + +#: modules/commands/os_jupe.cpp:34 +msgid "You can not jupe an already juped server." +msgstr "Non puoi bloccare un server già bloccato." + +#: modules/commands/os_jupe.cpp:32 +msgid "You can not jupe your Services' pseudoserver or your uplink server." +msgstr "Non puoi bloccare lo pseudoserver dei Services o il tuo uplink." + +#: modules/commands/os_module.cpp:80 +#, c-format +msgid "You can not reload this module directly, instead reload %s." +msgstr "Non puoi ricaricare questo modulo direttamente, ricarica invece %s." + +#: modules/commands/ms_rsend.cpp:46 +msgid "You can not request a receipt when sending a memo to yourself." +msgstr "" +"Non puoi richiedere una conferma di lettura se invii un memo a te stesso." + +#: modules/commands/ns_recover.cpp:163 +#, c-format +msgid "You can't %s yourself!" +msgstr "Non puoi %s te stesso!" + +#: modules/commands/cs_access.cpp:154 modules/commands/cs_flags.cpp:109 +#: modules/commands/cs_xop.cpp:151 +msgid "You can't add a channel to its own access list." +msgstr "Non puoi aggiungere un canale alla sua stessa access list." + +#: modules/commands/ns_logout.cpp:37 +#, c-format +msgid "You can't logout %s, they are a Services Operator." +msgstr "Non puoi deidentificare %s, è un Services Operator." + +#: modules/commands/ns_set.cpp:927 +#, c-format +msgid "You cannot %s on this network." +msgstr "Non puoi usare %s su questo network." + +#: modules/commands/cs_flags.cpp:231 +#, c-format +msgid "You cannot set the %c flag." +msgstr "Non puoi impostare il flag %c." + +#: modules/commands/ms_set.cpp:173 +#, c-format +msgid "You cannot set the memo limit for %s higher than %d." +msgstr "" +"Non puoi impostare il limite dei memo di %s ad un valore superiore a %d." + +#: modules/commands/ms_set.cpp:175 +#, c-format +msgid "You cannot set your memo limit higher than %d." +msgstr "" +"Non puoi impostare il limite dei tuoi memo ad un valore superiore a %d." + +#: modules/commands/bs_assign.cpp:124 +msgid "You cannot unassign bots while persist is set on the channel." +msgstr "Non puoi rimuovere i bot quando la persistenza è impostata nel canale." + +#: modules/commands/ns_set.cpp:480 +msgid "You cannot unset the e-mail on this network." +msgstr "Non puoi annullare l'impostazione dell'e-mail." + +#: modules/commands/help.cpp:177 +msgid "You cannot use this command." +msgstr "Non puoi usare questo comando." + +#: modules/commands/ms_info.cpp:151 +#, c-format +msgid "You currently have %d memos, of which %d are unread." +msgstr "Hai %d memo, di cui %d non sono stati ancora letti." + +#: modules/commands/ms_info.cpp:149 +#, c-format +msgid "You currently have %d memos, of which 1 is unread." +msgstr "Hai %d memo, di cui 1 non è stato ancora letto." + +#: modules/commands/ms_info.cpp:147 +#, c-format +msgid "You currently have %d memos." +msgstr "Hai %d memo." + +#: modules/commands/ms_info.cpp:145 +#, c-format +msgid "You currently have %d memos; all of them are unread." +msgstr "Hai %d memo, nessuno di questi è stato letto." + +#: modules/commands/ms_info.cpp:134 +msgid "You currently have 1 memo, and it has not yet been read." +msgstr "Hai 1 memo, e non è stato ancora letto." + +#: modules/commands/ms_info.cpp:136 +msgid "You currently have 1 memo." +msgstr "Hai 1 memo." + +#: modules/commands/ms_info.cpp:130 +msgid "You currently have no memos." +msgstr "Non hai nessun memo." + +#: modules/commands/cs_mode.cpp:564 modules/commands/cs_mode.cpp:621 +#, c-format +msgid "You do not have access to set mode %c." +msgstr "Non hai accesso per impostare il modo %c." + +#: modules/commands/cs_mode.cpp:578 modules/commands/cs_mode.cpp:590 +#: modules/commands/cs_mode.cpp:631 +#, c-format +msgid "You do not have the access to change %s's modes." +msgstr "Non hai accesso per cambiare i modi di %s." + +#: modules/commands/cs_seen.cpp:198 +#, c-format +msgid "You found me, %s!" +msgstr "Mi hai trovato, %s!" + +#: modules/pseudoclients/memoserv.cpp:143 +#, c-format +msgid "You have %d new memos." +msgstr "Hai %d nuovi memo." + +#: modules/pseudoclients/memoserv.cpp:143 +msgid "You have 1 new memo." +msgstr "Hai un nuovo memo." + +#: include/language.h:112 +#, c-format +msgid "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." +msgstr "" +"Hai un nuovo memo da %s.\n" +"Digita %s%s READ %d per leggerlo." + +#: modules/commands/cs_invite.cpp:76 +#, c-format +msgid "You have been invited to %s by %s." +msgstr "Sei stato invitato in %s da %s." + +#: modules/commands/cs_invite.cpp:81 +#, c-format +msgid "You have been invited to %s." +msgstr "Sei stato invitato in %s." + +#: modules/protocol/ratbox.cpp:166 modules/commands/ns_recover.cpp:96 +#, c-format +msgid "You have been logged in as %s." +msgstr "Hai effettuato il login come %s." + +#: modules/commands/os_login.cpp:86 +msgid "You have been logged out." +msgstr "Non sei più identificato al tuo nick." + +#: modules/commands/cs_unban.cpp:94 +#, c-format +msgid "You have been unbanned from %s." +msgstr "I ban che ti riguardavano sono stati rimossi da %s." + +#: modules/commands/cs_unban.cpp:54 +#, c-format +msgid "You have been unbanned from %d channels." +msgstr "I ban che ti riguardavano sono stati rimossi da %d canali." + +#: modules/commands/ms_info.cpp:169 +msgid "You have no limit on the number of memos you may keep." +msgstr "Non c'è alcun limite al numero di memo che puoi conservare." + +#: include/language.h:114 +msgid "You have no memos." +msgstr "Non hai memo." + +#: include/language.h:117 +msgid "You have no new memos." +msgstr "Non hai nuovi memo." + +#: modules/pseudoclients/memoserv.cpp:149 +#, c-format +msgid "" +"You have reached your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Attenzione: Hai raggiunto il numero massimo di memo (%d). Non potrai " +"ricevere nuovi memo finché non ne elimini alcuni dal tuo archivio." + +#: modules/commands/ns_recover.cpp:117 +#, c-format +msgid "You have regained control of %s." +msgstr "Hai ripreso il controllo di %s." + +#: modules/commands/ns_drop.cpp:66 +msgid "You may drop any nick within your group." +msgstr "Puoi deregistrare qualsiasi nick del tuo gruppo." + +#: modules/commands/cs_mode.cpp:322 modules/commands/cs_mode.cpp:414 +#, c-format +msgid "You may not (un)lock mode %c." +msgstr "Non puoi sbloccare/bloccare il modo %c." + +#: modules/commands/ns_set.cpp:485 +msgid "You may not change the e-mail of other Services Operators." +msgstr "Non puoi cambiare l'e-mail di altri Services Operators." + +#: modules/commands/ns_set.cpp:474 +msgid "You may not change the email of an unconfirmed account." +msgstr "Non puoi cambiare l'e-mail di un account non confermato." + +#: modules/commands/ns_set.cpp:196 +msgid "You may not change the password of other Services Operators." +msgstr "Non puoi cambiare la password di altri Services Operators." + +#: modules/commands/ns_drop.cpp:45 +msgid "You may not drop other Services Operators' nicknames." +msgstr "Non puoi deregistrare il nickname di altri Services Operators." + +#: modules/commands/ns_getpass.cpp:32 +msgid "You may not get the password of other Services Operators." +msgstr "Non puoi richiedere la password di altri Services Operators." + +#: modules/commands/ns_suspend.cpp:100 +msgid "You may not suspend other Services Operators' nicknames." +msgstr "Non uoi sospendere il nickname di altri Services Operators." + +#: modules/commands/ns_access.cpp:136 +msgid "" +"You may view but not modify the access list of other Services Operators." +msgstr "" +"Puoi consultare la lista di accesso degli altri Services Operators, ma non " +"modificarla." + +#: modules/commands/ns_cert.cpp:292 +msgid "" +"You may view but not modify the certificate list of other Services Operators." +msgstr "" +"Puoi consultare la lista dei certificati degli altri Services Operators, ma " +"non modificarla." + +#: modules/commands/cs_seen.cpp:287 +#, c-format +msgid "You might see yourself in the mirror, %s." +msgstr "Potresti guardarti allo specchio, %s." + +#: include/language.h:120 +msgid "You must assign a bot to the channel before using this command." +msgstr "È necessario assegnare un bot al canale prima di usare questo comando." + +#: modules/commands/cs_register.cpp:49 +msgid "You must be a channel operator to register the channel." +msgstr "È necessario essere operatore del canale per poterlo registrare." + +#: modules/commands/cs_updown.cpp:94 modules/commands/cs_updown.cpp:192 +#, c-format +msgid "You must be in %s to use this command." +msgstr "Devi essere in %s per usare questo comando." + +#: modules/commands/cs_register.cpp:37 +msgid "You must confirm your account before you can register a channel." +msgstr "" +"È necessario confermare il tuo account prima di poter registrare un canale." + +#: modules/commands/hs_request.cpp:100 +msgid "You must confirm your account before you may request a vhost." +msgstr "" +"È necessario confermare il tuo account prima di poter richiedere un vHost." + +#: modules/commands/ms_send.cpp:44 +msgid "You must confirm your account before you may send a memo." +msgstr "È necessario confermare il tuo account prima di poter inviare un memo." + +#: modules/commands/cs_drop.cpp:42 +#, c-format +msgid "" +"You must enter the channel name twice as a confirmation that you wish to drop" +" %s." +msgstr "" +"È necessario specificare il nome del canale due volte come conferma che vuoi " +"deregistrare %s." + +#: modules/commands/ns_register.cpp:153 +#, c-format +msgid "You must have been using this nick for at least %d seconds to register." +msgstr "" +"È necessario aver usato questo nick per almeno %d secondi prima di poterlo " +"registrare." + +#: modules/commands/cs_mode.cpp:913 +#, c-format +msgid "You must have the %s(ME) privilege on the channel to use this command." +msgstr "" +"È necessario avere i privilegi %s(ME) nel canale per poter usare questo " +"comando." + +#: modules/pseudoclients/nickserv.cpp:358 +msgid "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." +msgstr "" +"Adesso devi impostare un indirizzo e-mail per il tuo nick.\n" +"Questa e-mail ti permetterà di recuperare la tua password\n" +"nel caso tu la dimentichi." + +#: modules/commands/help.cpp:172 +msgid "You need to be identified to use this command." +msgstr "È necessario essere identificati per usare questo comando." + +#: modules/commands/ms_info.cpp:182 +msgid "You will be notified by message and by mail when new memos arrive." +msgstr "" +"Sarai informato dei nuovi memo con un messaggio e con una email quando li " +"riceverai." + +#: modules/commands/ms_info.cpp:175 +msgid "" +"You will be notified of new memos at logon and when they arrive, and by mail " +"when they arrive." +msgstr "" +"Sarai informato dei nuovi memo quando ti connetterai e quando li riceverai, " +"anche via email." + +#: modules/commands/ms_info.cpp:177 +msgid "You will be notified of new memos at logon and when they arrive." +msgstr "" +"Sarai informato dei nuovi memo quando ti connetterai e quando li riceverai." + +#: modules/commands/ms_info.cpp:189 +msgid "" +"You will be notified of new memos at logon, and by mail when they arrive." +msgstr "" +"Sarai informato dei nuovi memo quando ti connetterai e via email quando li " +"riceverai." + +#: modules/commands/ms_info.cpp:191 +msgid "You will be notified of new memos at logon." +msgstr "Sarai informato dei nuovi memo quando ti connetterai." + +#: modules/commands/ms_info.cpp:184 +msgid "You will be notified when new memos arrive." +msgstr "Sarai informato dei nuovi memo quando li ricevi." + +#: modules/commands/ms_set.cpp:190 +msgid "You will no longer be able to receive memos." +msgstr "Non potrai più ricevere memo." + +#: modules/commands/ms_set.cpp:57 +msgid "You will no longer be informed via email." +msgstr "Non sarai più informato via email." + +#: modules/commands/ms_info.cpp:195 +msgid "You will not be notified of new memos." +msgstr "Non sarai informato dei nuovi memo." + +#: modules/commands/ms_set.cpp:49 +msgid "You will now be informed about new memos via email." +msgstr "Sarai informato dei nuovi memo via email." + +#: modules/commands/os_svs.cpp:86 +msgid "Your IRCd does not support SVSJOIN." +msgstr "Il tuo IRCd non supporta SVSJOIN." + +#: modules/commands/os_svs.cpp:31 +msgid "Your IRCd does not support SVSNICK." +msgstr "Il tuo IRCd non supporta SVSNICK." + +#: modules/commands/os_svs.cpp:130 +msgid "Your IRCd does not support SVSPART." +msgstr "Il tuo IRCd non supporta SVSPART." + +#: include/language.h:127 +msgid "" +"Your IRCd does not support vIdent's, if this is incorrect, please report " +"this as a possible bug" +msgstr "" +"Il tuo IRCd non supporta vIdent, se così non fosse, segnala il problema come " +"un possibile bug" + +#: modules/extra/m_ldap_authentication.cpp:110 +#: modules/extra/m_sql_authentication.cpp:55 +#, c-format +msgid "Your account %s has been successfully created." +msgstr "Il tuo account %s è stato creato con successo." + +#: modules/commands/ns_register.cpp:328 +msgid "Your account is already confirmed." +msgstr "Il tuo account è già stato confermato." + +#: modules/commands/ns_register.cpp:396 +#, c-format +msgid "Your account will expire, if not confirmed, in %s." +msgstr "Se non confermato, il tuo account scadrà in %s." + +#: modules/commands/ns_set.cpp:1274 +#, c-format +msgid "Your email address has been changed to %s." +msgstr "Il tuo indirizzo email è stato cambiato in %s." + +#: modules/commands/os_forbid.cpp:544 modules/commands/os_forbid.cpp:553 +msgid "Your email address is not allowed, choose a different one." +msgstr "Il tuo indirizzo email non è consentito, scegline uno diverso." + +#: modules/commands/ns_register.cpp:260 modules/commands/ns_register.cpp:391 +msgid "" +"Your email address is not confirmed. To confirm it, follow the instructions " +"that were emailed to you." +msgstr "" +"Il tuo indirizzo email non è stato confermato. Per confermarlo, segui le " +"istruzioni contenute nella email che hai ricevuto quando ti sei registrato." + +#: modules/commands/ns_register.cpp:67 +#, c-format +msgid "Your email address of %s has been confirmed." +msgstr "Il tuo indirizzo email per %s è stato confermato." + +#: modules/extra/m_ldap_authentication.cpp:159 +#, c-format +msgid "Your email has been updated to %s" +msgstr "Il tuo indirizzo email è stato modificato a %s" + +#: modules/extra/m_sql_authentication.cpp:62 +#, c-format +msgid "Your email has been updated to %s." +msgstr "Il tuo indirizzo email è stato modificato a %s." + +#: modules/commands/ms_set.cpp:197 +msgid "Your memo limit has been disabled." +msgstr "Il limite dei tuoi memo è stato disabilitato." + +#: modules/commands/ms_set.cpp:183 +#, c-format +msgid "Your memo limit has been set to %d." +msgstr "Il limite dei tuoi memo è stato impostato a %d." + +#: modules/commands/ms_info.cpp:164 +#, c-format +msgid "Your memo limit is %d, and may not be changed." +msgstr "Il limite dei tuoi memo è %d, e non può essere modificato." + +#: modules/commands/ms_info.cpp:166 +#, c-format +msgid "Your memo limit is %d." +msgstr "Il limite dei tuoi memo è %d." + +#: modules/commands/ms_info.cpp:159 +msgid "Your memo limit is 0; you will not receive any new memos." +msgstr "Il limite dei tuoi memo è 0, non riceverai alcun nuovo memo." + +#: modules/commands/ms_info.cpp:157 +msgid "" +"Your memo limit is 0; you will not receive any new memos. You cannot change " +"this limit." +msgstr "" +"Il limite dei tuoi memo è 0, non riceverai alcun nuovo memo. Non puoi " +"modificare questo limite." + +#: modules/commands/ns_logout.cpp:50 +msgid "Your nick has been logged out." +msgstr "Non sei più identificato al tuo nick." + +#: modules/commands/ns_group.cpp:156 +msgid "Your nick is already registered." +msgstr "Il tuo nick è già registrato." + +#: modules/commands/ns_group.cpp:246 +msgid "Your nick is not grouped to anything, you can't ungroup it." +msgstr "Il tuo nick non appartiene a un gruppo, non puoi usare UNGROUP." + +#: include/language.h:77 +msgid "Your nick isn't registered." +msgstr "Il tuo nickname non è registrato." + +#: modules/pseudoclients/nickserv.cpp:254 +#, c-format +msgid "Your nickname is now being changed to %s" +msgstr "Il tuo nick sarà cambiato in %s" + +#: modules/commands/os_login.cpp:32 modules/commands/os_login.cpp:79 +msgid "Your oper block doesn't require logging in." +msgstr "Il tuo blocco oper non richiede l'accesso." + +#: modules/commands/ns_register.cpp:336 +#, c-format +msgid "Your passcode has been re-sent to %s." +msgstr "Il codice di attivazione è stato reinviato a %s." + +#: modules/commands/ns_register.cpp:232 +#, c-format +msgid "Your password is %s - remember this for later use." +msgstr "La tua password è %s - non dimenticarla." + +#: include/language.h:76 +#, c-format +msgid "Your password is too long. It must not exceed %u characters." +msgstr "La password scelta è troppo lunga. Non deve superare %u caratteri." + +#: modules/commands/ns_resetpass.cpp:96 +msgid "Your password reset request has expired." +msgstr "La tua richiesta di reset della password è scaduta." + +#: modules/commands/hs_request.cpp:170 +msgid "Your vHost has been requested." +msgstr "Il tuo vHost è stato richisto." + +#: modules/pseudoclients/hostserv.cpp:64 +#: modules/pseudoclients/hostserv.cpp:103 modules/commands/hs_on.cpp:37 +#, c-format +msgid "Your vhost of %s is now activated." +msgstr "Il tuo vHost %s ora è attivato." + +#: modules/pseudoclients/hostserv.cpp:62 +#: modules/pseudoclients/hostserv.cpp:101 modules/commands/hs_on.cpp:35 +#, c-format +msgid "Your vhost of %s@%s is now activated." +msgstr "Il tuo vHost %s@%s è ora attivato." + +#: modules/commands/hs_off.cpp:39 +msgid "Your vhost was removed and the normal cloaking restored." +msgstr "" +"Il tuo vHost è stato rimosso e l'offuscamento IP/Host standard ripristinato." + +#: modules/commands/os_dns.cpp:255 +msgid "Zone" +msgstr "Zona" + +#: modules/commands/os_dns.cpp:290 +#, c-format +msgid "Zone %s already exists." +msgstr "La zona %s è già esistente." + +#: modules/commands/os_dns.cpp:310 modules/commands/os_dns.cpp:352 +#: modules/commands/os_dns.cpp:402 modules/commands/os_dns.cpp:438 +#, c-format +msgid "Zone %s does not exist." +msgstr "La zona %s non esiste." + +#: modules/commands/os_dns.cpp:332 +#, c-format +msgid "Zone %s removed." +msgstr "Zona %s rimossa." + +#: modules/commands/os_defcon.cpp:177 +msgid "[1|2|3|4|5]" +msgstr "[1|2|3|4|5]" + +#: modules/commands/os_news.cpp:400 +#, c-format +msgid "[Logon News - %s] %s" +msgstr "[Logon News - %s] %s" + +#: modules/commands/os_news.cpp:402 +#, c-format +msgid "[Oper News - %s] %s" +msgstr "[Oper News - %s] %s" + +#: modules/commands/os_news.cpp:404 +#, c-format +msgid "[Random News - %s] %s" +msgstr "[Random News - %s] %s" + +#: modules/commands/ns_identify.cpp:66 +msgid "[account] password" +msgstr "[account] password" + +#: modules/commands/cs_updown.cpp:49 modules/commands/cs_updown.cpp:147 +msgid "[channel [nick]]" +msgstr "[canale [nick]]" + +#: modules/commands/ms_ignore.cpp:20 +msgid "[channel] ADD entry" +msgstr "[canale] ADD voce" + +#: modules/commands/ms_ignore.cpp:21 +msgid "[channel] DEL entry" +msgstr "[canale] DEL voce" + +#: modules/commands/ms_ignore.cpp:22 +msgid "[channel] LIST" +msgstr "[canale] LIST" + +#: modules/commands/ms_list.cpp:20 +msgid "[channel] [list | NEW]" +msgstr "[canale] [list | NEW]" + +#: modules/extra/stats/cs_fantasy_stats.cpp:40 +msgid "[channel] [nick]" +msgstr "[canale] [nick]" + +#: modules/commands/ms_del.cpp:45 +msgid "[channel] {num | list | LAST | ALL}" +msgstr "[canale] {num | list | LAST | ALL}" + +#: modules/commands/ms_read.cpp:113 +msgid "[channel] {num | list | LAST | NEW | ALL}" +msgstr "[canale] {num | list | LAST | NEW | ALL}" + +#: modules/commands/hs_list.cpp:20 +msgid "[key|#X-Y]" +msgstr "[chiave|#X-Y]" + +#: modules/commands/ms_info.cpp:20 +msgid "[nick | channel]" +msgstr "[nick | canale]" + +#: modules/commands/ns_group.cpp:237 +msgid "[nick]" +msgstr "[nick]" + +#: modules/commands/ns_logout.cpp:22 +msgid "[nickname [REVALIDATE]]" +msgstr "[nickname [REVALIDATE]]" + +#: modules/commands/ns_alist.cpp:25 modules/commands/ns_status.cpp:20 +#: modules/commands/ns_info.cpp:20 +msgid "[nickname]" +msgstr "[nickname]" + +#: modules/commands/ns_set_misc.cpp:96 +msgid "[parameter]" +msgstr "[parametro]" + +#: modules/commands/os_logsearch.cpp:33 +msgid "[+daysd] [+limitl] pattern" +msgstr "[+giornid] [+limitel] pattern" + +#: modules/commands/os_chankill.cpp:22 +msgid "[+expiry] channel reason" +msgstr "[+scadenza] canale motivo" + +#: modules/commands/ns_list.cpp:110 +msgid "[Hostname hidden]" +msgstr "[Hostname nascosto]" + +#: modules/commands/ns_list.cpp:112 modules/commands/cs_list.cpp:115 +msgid "[Suspended]" +msgstr "[Sospeso]" + +#: modules/commands/ns_list.cpp:114 +msgid "[Unconfirmed]" +msgstr "[Non confermato]" + +#: modules/commands/hs_request.cpp:213 +msgid "[auto memo] Your requested vHost has been approved." +msgstr "[auto-memo] La tua richiesta per il vHost è stata approvata." + +#: modules/commands/hs_request.cpp:267 +msgid "[auto memo] Your requested vHost has been rejected." +msgstr "[auto-memo] La tua richiesta per il vHost è stata rifiutata." + +#: modules/commands/hs_request.cpp:265 +#, c-format +msgid "[auto memo] Your requested vHost has been rejected. Reason: %s" +msgstr "" +"[auto memo] La tua richiesta per il vHost è stata rifiutata. Motivo: %s" + +#: modules/commands/hs_request.cpp:388 +#, c-format +msgid "[auto memo] vHost %s has been requested by %s." +msgstr "[auto memo] il vHost %s è stato richiesto da %s." + +#: modules/commands/os_list.cpp:133 +msgid "[{pattern | channel} [INVISIBLE]]" +msgstr "[{pattern | canale} [INVISIBLE]]" + +#: modules/commands/os_list.cpp:20 +msgid "[{pattern | nick} [SECRET]]" +msgstr "[{pattern | nick} [SECRET]]" + +#: src/misc.cpp:337 +msgid "day" +msgstr "giorno" + +#: src/misc.cpp:337 +msgid "days" +msgstr "giorni" + +#: include/language.h:88 +msgid "does not expire" +msgstr "non scade" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d day" +msgstr "scade tra %d giorno" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d days" +msgstr "scade tra %d giorni" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minute" +msgstr "scade tra %d ora, %d minuto" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minutes" +msgstr "scade tra %d ora, %d minuti" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minute" +msgstr "scade tra %d ore, %d minuto" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minutes" +msgstr "scade tra %d ore, %d minuti" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minute" +msgstr "scade tra %d minuto" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minutes" +msgstr "scade tra %d minuti" + +#: src/misc.cpp:375 +msgid "expires momentarily" +msgstr "scade a momenti" + +#: src/misc.cpp:343 +msgid "hour" +msgstr "ora" + +#: src/misc.cpp:343 +msgid "hours" +msgstr "ore" + +#: modules/extra/stats/cs_fantasy_stats.cpp:150 +#, c-format +msgid "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "lettere: %s, parole: %s, linee: %s, smileys: %s, azioni: %s" + +#: src/misc.cpp:349 +msgid "minute" +msgstr "minuto" + +#: src/misc.cpp:349 +msgid "minutes" +msgstr "minuti" + +#: modules/commands/bs_info.cpp:87 +msgid "not assigned yet" +msgstr "non ancora assegnato" + +#: src/misc.cpp:324 +msgid "second" +msgstr "secondo" + +#: src/misc.cpp:324 +msgid "seconds" +msgstr "secondi" + +#: modules/commands/hs_request.cpp:215 +#, c-format +msgid "vHost for %s has been activated." +msgstr "Il vHost per %s è stato attivato." + +#: modules/commands/hs_request.cpp:272 +#, c-format +msgid "vHost for %s has been rejected." +msgstr "Il vHost per %s è stato rifiutato." + +#: modules/commands/hs_request.cpp:79 +msgid "vhost" +msgstr "vHost" + +#: modules/commands/hs_del.cpp:83 +#, c-format +msgid "vhosts for group %s have been removed." +msgstr "i vHost per il gruppo %s sono stati rimossi." + +#: src/misc.cpp:331 +msgid "year" +msgstr "anno" + +#: src/misc.cpp:331 +msgid "years" +msgstr "anni" + +#: modules/commands/os_config.cpp:20 +msgid "{MODIFY|VIEW} [block name item name item value]" +msgstr "{MODIFY|VIEW} [nome blocco nome elemento valore elemento]" + +#: modules/commands/bs_info.cpp:41 +msgid "{channel | nickname}" +msgstr "{canale | nickname}" + +#: modules/commands/ms_cancel.cpp:20 +msgid "{nick | channel}" +msgstr "{nick | canale}" + +#: modules/commands/ms_rsend.cpp:25 modules/commands/ms_send.cpp:25 +msgid "{nick | channel} memo-text" +msgstr "{nick | canale} testo-memo" diff --git a/language/anope.nl_NL.po b/language/anope.nl_NL.po new file mode 100644 index 0000000..1df906c --- /dev/null +++ b/language/anope.nl_NL.po @@ -0,0 +1,11212 @@ +# Anope IRC Services language file +# Copyright (C) 2013-2020 +# This file is distributed under the same license as the Anope IRC Services package. +# Robby , 2013-2020. +# +msgid "" +msgstr "" +"Project-Id-Version: Anope\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2020-01-06 18:19+0100\n" +"PO-Revision-Date: 2020-01-07 04:27+0100\n" +"Last-Translator: Robby \n" +"Language-Team: Dutch\n" +"Language: nl_NL\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" + +#: modules/commands/os_forbid.cpp:324 +#, c-format +msgid "%d channel(s) cleared, and %d channel(s) dropped." +msgstr "%d kana(a)l(en) opgekuist, en %d kanaalregistratie(s) verwijderd." + +#: modules/commands/os_forbid.cpp:265 +#, c-format +msgid "%d nickname(s) dropped." +msgstr "%d nickregistratie(s) verwijderd." + +#: modules/commands/cs_xop.cpp:219 +#, c-format +msgid "%s added to %s %s list." +msgstr "%s toegevoegd aan %s %s toegangslijst." + +#: modules/commands/cs_access.cpp:225 +#, c-format +msgid "%s added to %s access list at level %d." +msgstr "%s toegevoegd aan %s toegangslijst met niveau %d." + +#: modules/commands/cs_access.cpp:223 +#, c-format +msgid "%s added to %s access list at privilege %s (level %d)" +msgstr "%s toegevoegd aan %s toegangslijst met privilege %s (niveau %d)" + +#: modules/commands/cs_akick.cpp:190 +#, c-format +msgid "%s added to %s autokick list." +msgstr "%s toegevoegd aan %s autokicklijst." + +#: modules/commands/bs_badwords.cpp:307 +#, c-format +msgid "%s added to %s bad words list." +msgstr "%s toegevoegd aan %s slechtewoordenlijst." + +#: modules/commands/ns_access.cpp:45 +#, c-format +msgid "%s added to %s's access list." +msgstr "%s toegevoegd aan %s's toegangslijst." + +#: modules/commands/ns_cert.cpp:204 +#, c-format +msgid "%s added to %s's certificate list." +msgstr "%s toegevoegd aan %s's certificaatlijst." + +#: modules/commands/ms_ignore.cpp:62 +#, c-format +msgid "%s added to ignore list." +msgstr "%s toegevoegd aan negeerlijst." + +#: modules/commands/os_sxline.cpp:415 modules/commands/os_sxline.cpp:649 +#, c-format +msgid "%s added to the %s list." +msgstr "%s toegevoegd aan de %s lijst." + +#: modules/commands/os_akill.cpp:203 +#, c-format +msgid "%s added to the AKILL list." +msgstr "%s toegevoegd aan de AKILL lijst." + +#: modules/pseudoclients/botserv.cpp:134 +#, c-format +msgid "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands " +"that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" +msgstr "" +"%s laat je toe \"fantasie\" commando's uit te voeren in het kanaal.\n" +"Fantasie commando's zijn commando's die kunnen uitgevoerd worden door\n" +"een bericht naar het kanaal te sturen, en bieden een makkelijkere manier om\n" +"commando's uit te voeren. Commando's die een kanaal als parameter vereisen\n" +"zullen dit automatisch gegeven worden.\n" + +#: modules/pseudoclients/botserv.cpp:148 +#, c-format +msgid "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s stelt je in staat een bot op je eigen kanaal te hebben.\n" +"Het is gemaakt voor gebruikers die geen eigen bot kunnen\n" +"hosten of configureren, of voor gebruik op netwerken die\n" +"geen bots van gebruikers toestaan. Beschikbare commando's\n" +"worden hieronder weergegeven; om ze te gebruiken, typ\n" +"%s%s commando. Voor meer informatie over een\n" +"specifiek commando, typ %s%s %s commando.\n" + +#: modules/pseudoclients/nickserv.cpp:466 +#, c-format +msgid "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s stelt je in staat een nickname te registreren, en\n" +"te voorkomen dat anderen hem gebruiken. De volgende commando's\n" +"kunnen gebruikt worden voor registratie en onderhoud van\n" +"nicknames; om ze te gebruiken, typ %s%s commando.\n" +"Voor meer informatie over een specifiek commando, typ\n" +"%s%s %s commando.\n" + +#: modules/pseudoclients/nickserv.cpp:473 +#, c-format +msgid "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s stelt je in staat een account te registreren.\n" +"De volgende commando's kunnen gebruikt worden voor registratie en\n" +"onderhoud van logins; om ze te gebruiken, typ %s%s commando.\n" +"Voor meer informatie over een specifiek commando, typ\n" +"%s%s %s commando.\n" + +#: modules/pseudoclients/chanserv.cpp:255 +#, c-format +msgid "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" +msgstr "" +"%s stelt je in staat om kanalen te registreren en er\n" +"verschillende opties van in te stellen. %s kan vaak\n" +"voorkomen dat boosaardige gebruikers een kanaal \"overnemen\"\n" +"door te limiteren wie er op het kanaal operator mag zijn.\n" +"Beschikbare commando's staan hier beneden; om ze te gebruiken,\n" +"typ %s%s commando. Voor meer informatie over een\n" +"specifiek commando, typ %s%s HELP commando.\n" + +#: modules/commands/bs_badwords.cpp:298 +#, c-format +msgid "%s already exists in %s bad words list." +msgstr "%s bestaat al op %s slechtewoordenlijst." + +#: modules/commands/cs_akick.cpp:170 +#, c-format +msgid "%s already exists on %s autokick list." +msgstr "%s bestaat al op %s autokicklijst." + +#: modules/commands/os_session.cpp:361 +#, c-format +msgid "%s already exists on the EXCEPTION list." +msgstr "%s bestaat al op de uitzonderingenlijst." + +#: modules/commands/bs_kick.cpp:214 modules/commands/bs_kick.cpp:389 +#: modules/commands/bs_kick.cpp:520 modules/commands/bs_kick.cpp:651 +#, c-format +msgid "%s cannot be taken as times to ban." +msgstr "%s kan niet worden ingesteld als aantal keer om dan te bannen." + +#: modules/commands/os_mode.cpp:163 +#, c-format +msgid "%s changed your usermodes to %s." +msgstr "%s heeft je gebruikersmodes veranderd naar %s." + +#: modules/commands/os_list.cpp:47 +#, c-format +msgid "%s channel list:" +msgstr "%s kanalenlijst:" + +#: modules/commands/cs_xop.cpp:343 +#, c-format +msgid "%s deleted from %s %s list." +msgstr "%s verwijderd uit %s %s lijst." + +#: modules/commands/cs_access.cpp:326 +#, c-format +msgid "%s deleted from %s access list." +msgstr "%s verwijderd van %s toegangslijst." + +#: modules/commands/cs_akick.cpp:276 +#, c-format +msgid "%s deleted from %s autokick list." +msgstr "%s verwijderd van %s autokicklijst." + +#: modules/commands/bs_badwords.cpp:348 +#, c-format +msgid "%s deleted from %s bad words list." +msgstr "%s verwijderd van %s slechtewoordenlijst." + +#: modules/commands/ns_access.cpp:72 +#, c-format +msgid "%s deleted from %s's access list." +msgstr "%s verwijderd van %s's toegangslijst." + +#: modules/commands/ns_cert.cpp:233 +#, c-format +msgid "%s deleted from %s's certificate list." +msgstr "%s verwijderd van %s's certificaatlijst." + +#: modules/commands/os_session.cpp:414 +#, c-format +msgid "%s deleted from session-limit exception list." +msgstr "%s verwijderd van de uitzonderingenlijst voor sessielimieten." + +#: modules/commands/os_sxline.cpp:99 +#, c-format +msgid "%s deleted from the %s list." +msgstr "%s verwijderd uit de %s lijst." + +#: modules/commands/os_akill.cpp:246 +#, c-format +msgid "%s deleted from the AKILL list." +msgstr "%s verwijderd van de AKILL lijst." + +#: modules/commands/cs_access.cpp:685 +#, c-format +msgid "%s disabled on channel %s." +msgstr "%s uitgeschakeld op kanaal %s." + +#: modules/commands/cs_invite.cpp:75 +#, c-format +msgid "%s has been invited to %s." +msgstr "%s werd uitgenodigd naar %s." + +#: modules/commands/os_svs.cpp:104 +#, c-format +msgid "%s has been joined to %s." +msgstr "%s werd gejoined op %s." + +#: modules/commands/os_svs.cpp:152 +#, c-format +msgid "%s has been parted from %s." +msgstr "%s werd gepart van %s." + +#: modules/commands/cs_unban.cpp:96 +#, c-format +msgid "%s has been unbanned from %s." +msgstr "%s wordt niet meer verbannen op %s." + +#: modules/commands/ns_alist.cpp:110 +#, c-format +msgid "%s has no access in any channels." +msgstr "%s heeft op geen enkel kanaal toegang." + +#: modules/commands/cs_status.cpp:55 +#, c-format +msgid "%s has no access on %s." +msgstr "%s heeft geen toegang op %s." + +#: modules/commands/cs_set.cpp:307 +#, c-format +msgid "%s has too many channels registered." +msgstr "%s heeft te veel geregistreerde kanalen." + +#: modules/commands/cs_status.cpp:51 +#, c-format +msgid "%s is a super administrator." +msgstr "%s is een super administrator." + +#: modules/pseudoclients/memoserv.cpp:214 +#, c-format +msgid "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" +msgstr "" +"%s is een dienst die IRC gebruikers in staat stelt om\n" +"korte berichten te sturen naar andere IRC gebruikers, online\n" +"of offline, of naar kanalen(*). De verstuurder's nick en de\n" +"nick van de ontvanger, of het kanaal waar de memo naartoe gaat,\n" +"moeten geregistreerd zijn om de memo te versturen.\n" +"%s's commando's bevatten:" + +#: modules/commands/cs_invite.cpp:66 +#, c-format +msgid "%s is already in %s!" +msgstr "%s is al op %s!" + +#: modules/commands/os_svs.cpp:99 +#, c-format +msgid "%s is already in %s." +msgstr "%s is al op %s." + +#: modules/commands/ms_ignore.cpp:65 +#, c-format +msgid "%s is already on the ignore list." +msgstr "%s staat al op de negeerlijst." + +#: modules/commands/cs_suspend.cpp:97 modules/commands/ns_suspend.cpp:106 +#, c-format +msgid "%s is already suspended." +msgstr "%s is reeds geschorst." + +#: modules/commands/ms_rsend.cpp:56 modules/commands/ms_send.cpp:55 +#, c-format +msgid "%s is not a registered unforbidden nick or channel." +msgstr "%s is geen geregistreerde niet-verboden nick of kanaal." + +#: modules/commands/cs_set.cpp:178 +#, c-format +msgid "%s is not a valid ban type." +msgstr "%s is geen geldige ban type." + +#: modules/commands/bs_info.cpp:101 +#, c-format +msgid "%s is not a valid bot or registered channel." +msgstr "%s is geen geldige bot of geregistreerd kanaal." + +#: include/language.h:86 +#, c-format +msgid "%s is not a valid e-mail address." +msgstr "%s is geen geldig e-mailadres." + +#: include/language.h:80 +#, c-format +msgid "%s is not currently on channel %s." +msgstr "%s is niet aanwezig op kanaal %s." + +#: modules/commands/os_svs.cpp:144 +#, c-format +msgid "%s is not in %s." +msgstr "%s is niet op %s." + +#: modules/commands/ms_ignore.cpp:77 +#, c-format +msgid "%s is not on the ignore list." +msgstr "%s staat niet op de negeerlijst." + +#: modules/commands/cs_status.cpp:90 +#, c-format +msgid "%s is on the auto kick list of %s (%s)." +msgstr "%s staat op de autokicklijst van %s (%s)." + +#: modules/commands/cs_status.cpp:53 +#, c-format +msgid "%s is the founder of %s." +msgstr "%s is de stichter van %s." + +#: modules/commands/cs_status.cpp:78 +#, c-format +msgid "%s matches access entry %s (from entry %s), which has privilege %s." +msgstr "" +"%s stemt overeen met toegangsvermelding %s (van vermelding %s), die " +"privilege %s heeft." + +#: modules/commands/cs_status.cpp:71 +#, c-format +msgid "%s matches access entry %s, which has privilege %s." +msgstr "%s stemt overeen met toegangsvermelding %s, die privilege %s heeft." + +#: include/language.h:109 +#, c-format +msgid "" +"%s matches an except on %s and cannot be banned until the except has been " +"removed." +msgstr "" +"%s stemt overeen met een uitzondering op %s en kan niet verbannen worden tot " +"deze uitzondering verwijderd is." + +#: modules/commands/cs_status.cpp:96 +#, c-format +msgid "%s matches auto kick entry %s on %s (%s)." +msgstr "%s stemt overeen met autokick %s op %s (%s)." + +#: modules/commands/cs_xop.cpp:353 +#, c-format +msgid "%s not found on %s %s list." +msgstr "%s niet gevonden op %s %s lijst." + +#: modules/commands/cs_access.cpp:338 modules/commands/cs_flags.cpp:255 +#, c-format +msgid "%s not found on %s access list." +msgstr "%s niet gevonden op %s toegangslijst." + +#: modules/commands/cs_akick.cpp:265 +#, c-format +msgid "%s not found on %s autokick list." +msgstr "%s niet gevonden op %s autokicklijst." + +#: modules/commands/bs_badwords.cpp:341 +#, c-format +msgid "%s not found on %s bad words list." +msgstr "%s niet gevonden op %s slechtewoordenlijst." + +#: modules/commands/ns_access.cpp:66 +#, c-format +msgid "%s not found on %s's access list." +msgstr "%s niet gevonden op %s's toegangslijst." + +#: modules/commands/ns_cert.cpp:226 +#, c-format +msgid "%s not found on %s's certificate list." +msgstr "%s niet gevonden op %s's certificaatlijst." + +#: modules/commands/os_ignore.cpp:320 +#, c-format +msgid "%s not found on ignore list." +msgstr "%s niet gevonden op de negeerlijst." + +#: modules/commands/os_session.cpp:238 +#, c-format +msgid "" +"%s not found on session list, but has a limit of %d because it matches entry:" +" %s." +msgstr "" +"%s niet gevonden op sessielijst, maar heeft een limiet van %d omdat het " +"overeenstemt met: %s." + +#: modules/commands/os_session.cpp:418 +#, c-format +msgid "%s not found on session-limit exception list." +msgstr "%s niet gevonden op de uitzonderingenlijst voor sessielimieten." + +#: modules/commands/os_sxline.cpp:92 +#, c-format +msgid "%s not found on the %s list." +msgstr "%s niet gevonden op de %s lijst." + +#: modules/commands/os_akill.cpp:237 +#, c-format +msgid "%s not found on the AKILL list." +msgstr "%s niet gevonden op de AKILL lijst." + +#: modules/commands/cs_flags.cpp:251 +#, c-format +msgid "%s removed from the %s access list." +msgstr "%s verwijderd van %s toegangslijst." + +#: modules/commands/ms_ignore.cpp:74 +#, c-format +msgid "%s removed from the ignore list." +msgstr "%s verwijderd van de negeerlijst." + +#: modules/commands/os_list.cpp:157 +#, c-format +msgid "%s users list:" +msgstr "%s gebruikerslijst:" + +#: modules/commands/os_ignore.cpp:316 +#, c-format +msgid "%s will no longer be ignored." +msgstr "%s zal niet langer genegeerd worden." + +#: modules/commands/os_ignore.cpp:238 +#, c-format +msgid "%s will now be ignored for %s." +msgstr "%s zal nu genegeerd worden voor %s." + +#: modules/commands/os_ignore.cpp:233 +#, c-format +msgid "%s will now permanently be ignored." +msgstr "%s zal nu permanent genegeerd worden." + +#: include/language.h:66 +#, c-format +msgid "%s%s HELP %s for more information." +msgstr "%s%s HELP %s voor meer informatie." + +#: modules/commands/bs_bot.cpp:270 +msgid "ADD nick user host real" +msgstr "ADD nick ident host naam" + +#: modules/commands/bs_bot.cpp:271 +msgid "CHANGE oldnick newnick [user [host [real]]]" +msgstr "CHANGE oudenick nieuwenick [ident [host [naam]]]" + +#: modules/commands/bs_bot.cpp:272 +msgid "DEL nick" +msgstr "DEL nick" + +#: modules/commands/os_session.cpp:560 +msgid "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." +msgstr "" +"EXCEPTION ADD voegt de gegeven hostmasker toe aan de\n" +"uitzonderingenlijst. Let op: nick!ident@host en ident@host\n" +"maskers zijn ongeldig! Alleen echte host masks, zoals box.host.dom\n" +"en *.host.dom, zijn toegestaan omdat sessie limitering geen\n" +"rekening houdt met nicks of idents. limiet moet een nummer\n" +"groter dan of gelijk aan 0 zijn. Dit bepaalt hoe veel sessies\n" +"deze host tegelijkertijd mag hebben. Een waarde van 0 betekent\n" +"dat de host een ongelimiteerde sessielimiet heeft. Bekijk de\n" +"AKILL help voor details over het formaat van de optionele\n" +"verlooptijd parameter.\n" +" \n" +"EXCEPTION DEL verwijdert het gegeven masker van de\n" +"uitzonderingenlijst.\n" +" \n" +"EXCEPTION LIST en EXCEPTION VIEW geven alle huidige\n" +"uitzonderingen weer; als het optionele masker is gegeven wordt de\n" +"lijst gelimiteerd tot uitzonderingen overeenkomend met het\n" +"gegeven masker. Het verschil is dat EXCEPTION VIEW meer\n" +"informatie geeft: de naam van degene die de uitzondering\n" +"aangemaakt heeft, de bijbehorende sessielimiet, reden, hostmasker\n" +"en de verloop datum en tijd.\n" +" \n" +"Let op: een verbindende client zal de eerste uitzondering die\n" +"met zijn host overeenkomt \"gebruiken\"." + +#: modules/commands/os_noop.cpp:68 +msgid "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." +msgstr "" +"SET killt alle IRC operators van de opgegeven\n" +"server en voorkomt operators terug operator\n" +"te worden op die server. REVOKE verwijdert deze\n" +"beperking." + +#: modules/commands/cs_access.cpp:611 +#, c-format +msgid "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." +msgstr "" +"Gebruiker toegangsniveaus kunnen bekeken worden met het\n" +"%s commando; typ %s%s HELP LEVELS voor\n" +"informatie." + +#: modules/commands/ms_read.cpp:35 +#, c-format +msgid "[auto-memo] The memo you sent to %s has been viewed." +msgstr "[auto-memo] De memo die je naar %s gestuurd hebt is bekeken." + +#: modules/commands/ns_group.cpp:92 +msgid "[target] [password]" +msgstr "[doel] [wachtwoord]" + +#: modules/commands/ns_set.cpp:453 +msgid "address" +msgstr "adres" + +#: modules/commands/bs_set.cpp:162 +msgid "botname {ON|OFF}" +msgstr "botnick {ON|OFF}" + +#: modules/extra/stats/cs_fantasy_top.cpp:39 +#: modules/extra/stats/cs_fantasy_top.cpp:51 +#: modules/commands/cs_suspend.cpp:152 modules/commands/cs_sync.cpp:20 +#: modules/commands/cs_log.cpp:106 modules/commands/bs_assign.cpp:91 +#: modules/commands/cs_info.cpp:20 modules/commands/cs_getkey.cpp:20 +msgid "channel" +msgstr "kanaal" + +#: modules/commands/cs_set.cpp:138 +msgid "channel bantype" +msgstr "kanaal bantype" + +#: modules/commands/cs_drop.cpp:20 +msgid "channel channel" +msgstr "kanaal kanaal" + +#: modules/commands/cs_log.cpp:107 +msgid "channel command method [status]" +msgstr "kanaal commando methode [status]" + +#: modules/commands/cs_kick.cpp:21 +msgid "channel mask [reason]" +msgstr "kanaal masker [reden]" + +#: modules/commands/os_mode.cpp:20 +msgid "channel modes" +msgstr "kanaal modes" + +#: modules/commands/cs_set.cpp:267 modules/commands/bs_assign.cpp:20 +msgid "channel nick" +msgstr "kanaal nick" + +#: modules/commands/cs_kick.cpp:20 +msgid "channel nick [reason]" +msgstr "kanaal nick [reden]" + +#: modules/commands/cs_clone.cpp:115 +msgid "channel target [what]" +msgstr "kanaal doel [wat]" + +#: modules/commands/bs_control.cpp:20 modules/commands/bs_control.cpp:80 +msgid "channel text" +msgstr "kanaal tekst" + +#: modules/commands/bs_set.cpp:91 +msgid "channel time" +msgstr "kanaal tijd" + +#: modules/commands/os_kick.cpp:20 +msgid "channel user reason" +msgstr "kanaal nick reden" + +#: modules/commands/cs_enforce.cpp:228 +msgid "channel what" +msgstr "kanaal wat" + +#: modules/commands/cs_xop.cpp:481 +msgid "channel ADD mask" +msgstr "kanaal ADD masker" + +#: modules/commands/cs_access.cpp:499 +msgid "channel ADD mask level" +msgstr "kanaal ADD masker niveau" + +#: modules/commands/cs_entrymsg.cpp:194 +msgid "channel ADD message" +msgstr "kanaal ADD bericht" + +#: modules/commands/bs_badwords.cpp:371 +msgid "channel ADD word [SINGLE | START | END]" +msgstr "kanaal ADD woord [SINGLE | START | END]" + +#: modules/commands/cs_akick.cpp:435 +msgid "channel ADD {nick | mask} [reason]" +msgstr "kanaal ADD {nick | masker} [reden]" + +#: modules/commands/cs_topic.cpp:151 +msgid "channel APPEND topic" +msgstr "kanaal APPEND topic" + +#: modules/commands/cs_access.cpp:503 modules/commands/cs_flags.cpp:376 +#: modules/commands/cs_xop.cpp:484 modules/commands/cs_entrymsg.cpp:197 +#: modules/commands/bs_badwords.cpp:374 modules/commands/cs_akick.cpp:440 +msgid "channel CLEAR" +msgstr "kanaal CLEAR" + +#: modules/commands/cs_mode.cpp:736 +msgid "channel CLEAR [what]" +msgstr "kanaal CLEAR [wat]" + +#: modules/commands/os_mode.cpp:21 +msgid "channel CLEAR [ALL]" +msgstr "kanaal CLEAR [ALL]" + +#: modules/commands/cs_entrymsg.cpp:195 +msgid "channel DEL num" +msgstr "kanaal DEL nr" + +#: modules/commands/cs_access.cpp:500 modules/commands/cs_xop.cpp:482 +msgid "channel DEL {mask | entry-num | list}" +msgstr "kanaal DEL {masker | nr | lijst}" + +#: modules/commands/cs_akick.cpp:436 +msgid "channel DEL {nick | mask | entry-num | list}" +msgstr "kanaal DEL {nick | masker | nr | lijst}" + +#: modules/commands/bs_badwords.cpp:372 +msgid "channel DEL {word | entry-num | list}" +msgstr "kanaal DEL {woord | nr | lijst}" + +#: modules/commands/cs_akick.cpp:439 +msgid "channel ENFORCE" +msgstr "kanaal ENFORCE" + +#: modules/commands/cs_access.cpp:744 modules/commands/cs_entrymsg.cpp:196 +msgid "channel LIST" +msgstr "kanaal LIST" + +#: modules/commands/cs_akick.cpp:437 +msgid "channel LIST [mask | entry-num | list]" +msgstr "kanaal LIST [masker | nr | lijst]" + +#: modules/commands/cs_access.cpp:501 modules/commands/cs_xop.cpp:483 +#: modules/commands/bs_badwords.cpp:373 +msgid "channel LIST [mask | list]" +msgstr "kanaal LIST [masker | lijst]" + +#: modules/commands/cs_flags.cpp:375 +msgid "channel LIST [mask | +flags]" +msgstr "kanaal LIST [masker | +vlaggen]" + +#: modules/commands/cs_mode.cpp:734 +msgid "channel LOCK {ADD|DEL|SET|LIST} [what]" +msgstr "kanaal LOCK {ADD|DEL|SET|LIST} [wat]" + +#: modules/commands/cs_access.cpp:745 +msgid "channel RESET" +msgstr "kanaal RESET" + +#: modules/commands/cs_mode.cpp:735 +msgid "channel SET modes" +msgstr "kanaal SET modes" + +#: modules/commands/cs_access.cpp:742 +msgid "channel SET type level" +msgstr "kanaal SET type niveau" + +#: modules/commands/cs_akick.cpp:438 +msgid "channel VIEW [mask | entry-num | list]" +msgstr "kanaal VIEW [masker | nr | lijst]" + +#: modules/commands/cs_access.cpp:502 +msgid "channel VIEW [mask | list]" +msgstr "kanaal VIEW [masker | lijst]" + +#: modules/commands/cs_register.cpp:20 modules/commands/cs_set.cpp:205 +msgid "channel [description]" +msgstr "kanaal [beschrijving]" + +#: modules/commands/cs_set.cpp:950 modules/commands/cs_invite.cpp:20 +#: modules/commands/cs_unban.cpp:20 +msgid "channel [nick]" +msgstr "kanaal [nick]" + +#: modules/commands/cs_set_misc.cpp:96 +msgid "channel [parameters]" +msgstr "kanaal [parameters]" + +#: modules/commands/cs_mode.cpp:807 modules/commands/cs_status.cpp:20 +msgid "channel [user]" +msgstr "kanaal [nick]" + +#: modules/commands/cs_suspend.cpp:59 +msgid "channel [+expiry] [reason]" +msgstr "kanaal [+verlooptijd] [reden]" + +#: modules/commands/cs_ban.cpp:40 +msgid "channel [+expiry] {nick | mask} [reason]" +msgstr "kanaal [+verlooptijd] {nick | masker} [reden]" + +#: modules/commands/cs_flags.cpp:374 +msgid "channel [MODIFY] mask changes" +msgstr "kanaal [MODIFY] masker wijzigingen" + +#: modules/commands/cs_topic.cpp:150 +msgid "channel [SET] [topic]" +msgstr "kanaal [SET] [topic]" + +#: modules/commands/cs_topic.cpp:152 +msgid "channel [UNLOCK|LOCK]" +msgstr "kanaal [UNLOCK|LOCK]" + +#: modules/fantasy.cpp:20 modules/commands/greet.cpp:20 +#: modules/commands/bs_assign.cpp:154 +msgid "channel {ON|OFF}" +msgstr "kanaal {ON|OFF}" + +#: modules/commands/bs_kick.cpp:491 +msgid "channel {ON|OFF} [ttb [ln [secs]]]" +msgstr "kanaal {ON|OFF} [ttb [lijnen [seconden]]]" + +#: modules/commands/bs_kick.cpp:361 +msgid "channel {ON|OFF} [ttb [min [percent]]]" +msgstr "kanaal {ON|OFF} [ttb [minuten [percentage]]]" + +#: modules/commands/bs_kick.cpp:623 +msgid "channel {ON|OFF} [ttb [num]]" +msgstr "kanaal {ON|OFF} [ttb [aantal]]" + +#: modules/commands/bs_kick.cpp:252 modules/commands/bs_kick.cpp:288 +#: modules/commands/bs_kick.cpp:327 modules/commands/bs_kick.cpp:457 +#: modules/commands/bs_kick.cpp:589 modules/commands/bs_kick.cpp:724 +#: modules/commands/bs_kick.cpp:758 +msgid "channel {ON|OFF} [ttb]" +msgstr "kanaal {ON|OFF} [ttb]" + +#: modules/commands/cs_access.cpp:743 +msgid "channel {DIS | DISABLE} type" +msgstr "kanaal {DIS | DISABLE} type" + +#: modules/commands/cs_set.cpp:873 +msgid "channel {ON | LEVEL | OFF}" +msgstr "kanaal {ON | LEVEL | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:18 modules/commands/cs_set.cpp:75 +#: modules/commands/cs_set.cpp:336 modules/commands/cs_set.cpp:401 +#: modules/commands/cs_set.cpp:473 modules/commands/cs_set.cpp:622 +#: modules/commands/cs_set.cpp:684 modules/commands/cs_set.cpp:747 +#: modules/commands/cs_set.cpp:811 modules/commands/cs_set.cpp:1044 +#: modules/commands/bs_kick.cpp:792 modules/commands/bs_kick.cpp:857 +#: modules/commands/cs_topic.cpp:21 modules/commands/cs_list.cpp:181 +msgid "channel {ON | OFF}" +msgstr "kanaal {ON | OFF}" + +#: modules/commands/ns_getemail.cpp:24 +msgid "email" +msgstr "e-mail" + +#: modules/commands/ns_set.cpp:794 +msgid "language" +msgstr "taal" + +#: modules/commands/ms_sendall.cpp:25 modules/commands/ms_staff.cpp:25 +msgid "memo-text" +msgstr "memo-tekst" + +#: modules/commands/gl_global.cpp:22 modules/commands/greet.cpp:84 +msgid "message" +msgstr "bericht" + +#: modules/commands/os_modinfo.cpp:20 modules/commands/os_module.cpp:20 +#: modules/commands/os_module.cpp:57 modules/commands/os_module.cpp:129 +msgid "modname" +msgstr "modnaam" + +#: modules/commands/ns_set.cpp:330 +msgid "new-display" +msgstr "nieuwe-weergave" + +#: modules/commands/ns_set.cpp:120 +msgid "new-password" +msgstr "nieuw-wachtwoord" + +#: modules/extra/stats/cs_fantasy_stats.cpp:52 modules/commands/hs_del.cpp:20 +#: modules/commands/hs_del.cpp:60 modules/commands/ms_check.cpp:20 +#: modules/commands/hs_request.cpp:192 modules/commands/cs_seen.cpp:262 +msgid "nick" +msgstr "nick" + +#: modules/commands/os_svs.cpp:79 +msgid "nick channel" +msgstr "nick kanaal" + +#: modules/commands/os_svs.cpp:123 +msgid "nick channel [reason]" +msgstr "nick kanaal [reden]" + +#: modules/commands/os_oline.cpp:20 +msgid "nick flags" +msgstr "nick vlaggen" + +#: modules/commands/hs_set.cpp:20 modules/commands/hs_set.cpp:126 +msgid "nick hostmask" +msgstr "nick hostmasker" + +#: modules/commands/os_svs.cpp:20 +msgid "nick newnick" +msgstr "nick nieuwenick" + +#: modules/commands/hs_request.cpp:241 +msgid "nick [reason]" +msgstr "nick [reden]" + +#: modules/commands/ns_getpass.cpp:20 modules/commands/ns_drop.cpp:19 +#: modules/commands/ns_suspend.cpp:161 +msgid "nickname" +msgstr "nick" + +#: modules/commands/ns_set.cpp:546 +msgid "nickname address" +msgstr "nickname adres" + +#: modules/commands/ns_resetpass.cpp:22 +msgid "nickname email" +msgstr "nick e-mail" + +#: modules/commands/ns_set.cpp:872 +msgid "nickname language" +msgstr "nickname taal" + +#: modules/commands/greet.cpp:145 +msgid "nickname message" +msgstr "nickname bericht" + +#: modules/commands/ns_set.cpp:399 +msgid "nickname new-display" +msgstr "nickname nieuwe-weergave" + +#: modules/commands/ns_set.cpp:173 +msgid "nickname new-password" +msgstr "nickname nieuw-wachtwoord" + +#: modules/commands/ns_set_misc.cpp:170 +msgid "nickname [parameter]" +msgstr "nickname [parameter]" + +#: modules/commands/ns_recover.cpp:150 +msgid "nickname [password]" +msgstr "nick [wachtwoord]" + +#: modules/commands/ns_suspend.cpp:61 +msgid "nickname [+expiry] [reason]" +msgstr "nick [+verlooptijd] [reden]" + +#: modules/commands/ns_info.cpp:239 +msgid "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +msgstr "nick {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:130 modules/commands/ns_set.cpp:302 +#: modules/commands/ns_set.cpp:631 modules/commands/ns_set.cpp:985 +#: modules/commands/ns_set.cpp:1076 modules/commands/ns_set.cpp:1105 +#: modules/commands/ns_list.cpp:252 +msgid "nickname {ON | OFF}" +msgstr "nickname {ON | OFF}" + +#: modules/commands/ns_set.cpp:760 +msgid "nickname {ON | QUICK | IMMED | OFF}" +msgstr "nickname {ON | QUICK | IMMED | OFF}" + +#: modules/commands/bs_set.cpp:20 +msgid "option (channel | bot) settings" +msgstr "optie (kanaal | bot) instellingen" + +#: modules/commands/cs_set.cpp:21 +msgid "option channel parameters" +msgstr "optie kanaal parameters" + +#: modules/commands/bs_kick.cpp:120 +msgid "option channel {ON|OFF} [settings]" +msgstr "optie kanaal {ON|OFF} [instellingen]" + +#: modules/commands/ns_set.cpp:75 +msgid "option nickname parameters" +msgstr "optie nickname parameters" + +#: modules/commands/ms_set.cpp:207 modules/commands/ns_set.cpp:20 +msgid "option parameters" +msgstr "optie parameters" + +#: modules/commands/os_set.cpp:170 +msgid "option setting" +msgstr "optie instelling" + +#: modules/commands/ns_register.cpp:22 +msgid "passcode" +msgstr "bevestigingscode" + +#: modules/commands/os_login.cpp:19 +msgid "password" +msgstr "wachtwoord" + +#: modules/commands/ns_register.cpp:124 +msgid "password [email]" +msgstr "wachtwoord [e-mail]" + +#: modules/commands/ns_register.cpp:122 +msgid "password email" +msgstr "wachtwoord e-mail" + +#: modules/commands/cs_list.cpp:21 +msgid "pattern [SUSPENDED] [NOEXPIRE]" +msgstr "patroon [SUSPENDED] [NOEXPIRE]" + +#: modules/commands/ns_list.cpp:20 +msgid "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" +msgstr "patroon [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/os_jupe.cpp:20 +msgid "server [reason]" +msgstr "server [reden]" + +#: modules/commands/os_mode.cpp:147 +msgid "user modes" +msgstr "nick modes" + +#: modules/commands/os_kill.cpp:20 +msgid "user [reason]" +msgstr "nick [reden]" + +#: modules/commands/os_sxline.cpp:440 +msgid "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." +msgstr "" +" \n" +"SNLINE ADD voegt het opgegeven naam masker aan de SNLINE\n" +"lijst toe met de opgegeven reden (die moet gegeven worden).\n" +"verlooptijd wordt opgegeven als een getal gevolgd door een van\n" +"volgende tijdseenheden: d (dagen), h (uren), of m (minuten).\n" +"Combinaties (zoals 1h30m) zijn niet toegelaten. Indien geen eenheid werd\n" +"opgegeven, wordt het gezien als dagen (dus enkel +30 betekent 30\n" +"dagen). Om een SNLINE zonder verlooptijd toe te voegen, gebruik +0.\n" +"Als het naam masker begint met een +, dan moet de verlooptijd opgegeven\n" +"worden, ook al is deze hetzelfde als de standaardwaarde. De huidige SNLINE\n" +"standaard verlooptijd kan gevonden worden met het\n" +"STATS AKILL commando.\n" +" \n" +"Let op: omdat het naam masker spaties mag bevatten, is de scheiding\n" +"tussen het masker en de reden een dubbele punt (:)." + +#: modules/commands/os_sxline.cpp:678 +msgid "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +" \n" +"SQLINE ADD voegt het opgegeven (nick) masker aan de SQLINE\n" +"lijst toe met de opgegeven reden (die moet gegeven worden).\n" +"verlooptijd wordt opgegeven als een getal gevolgd door een van\n" +"volgende tijdseenheden: d (dagen), h (uren), of m (minuten).\n" +"Combinaties (zoals 1h30m) zijn niet toegelaten. Indien geen eenheid werd\n" +"opgegeven, wordt het gezien als dagen (dus enkel +30 betekent 30\n" +"dagen). Om een SQLINE zonder verlooptijd toe te voegen, gebruik +0.\n" +"Als het masker begint met een +, dan moet de verlooptijd opgegeven\n" +"worden, ook al is deze hetzelfde als de standaardwaarde. De huidige SQLINE\n" +"standaard verlooptijd kan gevonden worden met het\n" +"STATS AKILL commando." + +#: modules/pseudoclients/nickserv.cpp:492 +#, c-format +msgid "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." +msgstr "" +" \n" +"Nicknames die niet meer gebruikt worden zullen na een tijd\n" +"automatisch verlopen, oftewel: ze zullen verwijderd worden na\n" +"%d dagen van onbruik." + +#: modules/pseudoclients/botserv.cpp:143 +msgid "" +" \n" +"Available commands are:" +msgstr "" +" \n" +"Beschikbare commando's zijn:" + +#: modules/pseudoclients/botserv.cpp:167 +#, c-format +msgid "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." +msgstr "" +" \n" +"De bot zal een kanaal binnenkomen wanneer er tenminste\n" +"%d gebruiker(s) in aanwezig is/zijn." + +#: modules/fantasy.cpp:69 +#, c-format +msgid "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." +msgstr "" +" \n" +"Activeert of deactiveert fantasie-modus op een kanaal.\n" +"Wanneer het geactiveerd is zullen gebruikers fantasie commando's\n" +"op een kanaal kunnen gebruiken wanneer voorafgegaan door\n" +"één van de volgende karakters: %s\n" +" \n" +"Let op dat de gebruikers die de fantasie-commando's willen\n" +"gebruiken een hoog genoeg niveau MOETEN hebben voor zowel\n" +"het FANTASIA privilege als voor het uit te voeren commando." + +#: modules/commands/greet.cpp:69 +msgid "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." +msgstr "" +" \n" +"Activeert of deactiveert groet-modus op een kanaal.\n" +"Wanneer deze geactiveerd is zal de bot de groetberichten\n" +"van de gebruikers die het kanaal binnenkomen weergegeven,\n" +"mits ze hiertoe voldoende rechten hebben op het kanaal." + +#: modules/commands/bs_kick.cpp:843 +msgid "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Activeert of deactiveert operators bescherming-modus op een kanaal.\n" +"Wanneer deze geactiveerd is zullen operators niet door de bot\n" +"gekickt worden, zelfs wanneer deze niet overeen komen\n" +"met het NOKICK niveau." + +#: modules/commands/bs_kick.cpp:908 +msgid "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Activeert of deactiveert voices bescherming-modus op een kanaal.\n" +"Wanneer deze geactiveerd is zullen voices niet door de bot\n" +"gekickt worden, zelfs wanneer deze niet overeen komen\n" +"met het NOKICK niveau." + +#: modules/pseudoclients/botserv.cpp:141 +#, c-format +msgid "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" +msgstr "" +" \n" +"Fantasie commando's mogen voorafgegaan worden met één van de volgende " +"karakters: %s\n" + +#: modules/commands/cs_register.cpp:105 +msgid "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." +msgstr "" +" \n" +"OPGELET: Om een kanaal te kunnen registreren moet\n" +"eerst je nickname geregistreerd zijn." + +#: modules/pseudoclients/chanserv.cpp:272 +#, c-format +msgid "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." +msgstr "" +" \n" +"Onthoud dat elk kanaal dat %d dagen ongebruikt is (d.w.z. dat\n" +"er geen gebruiker die op de toegangslijst staat in die periode\n" +"het kanaal binnen is gekomen) automatisch zal worden verwijderd." + +#: modules/commands/cs_register.cpp:101 +#, c-format +msgid "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +msgstr "" +" \n" +"Zie het %s commando (%s%s HELP ACCESS) voor\n" +"informatie over het geven van privileges aan andere kanaal-\n" +"gebruikers.\n" + +#: modules/pseudoclients/nickserv.cpp:486 +msgid "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." +msgstr "" +" \n" +"Services Operators kunnen ook de registratie van elke nick\n" +"verwijderen zonder zich voor die nick te identificeren, en\n" +"mogen de toegangslijst voor elke nick bekijken." + +#: modules/pseudoclients/chanserv.cpp:277 +msgid "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." +msgstr "" +" \n" +"Services Operators kunnen ook, afhankelijk van hun eigen toegang,\n" +"kanaalregistraties verwijderen, bekijken (en aanpassen) van de toegangs-,\n" +"niveau-, privilege- en autokicklijsten, en de instellingen van elk kanaal." + +#: modules/commands/bs_set.cpp:147 +msgid "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." +msgstr "" +" \n" +"Stelt de tijd in wanneer bans via de bot verlopen. Indien geactiveerd,\n" +"zullen bans gezet door bots, zoals voor flood, slechte woorden, enz.\n" +"automatisch verlopen na de opgegeven tijd. Geef een tijd van 0 op om\n" +"het automatisch verlopen van bans uit te schakelen." + +#: modules/commands/cs_xop.cpp:542 +#, c-format +msgid "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." +msgstr "" +" \n" +"Het %s ADD commando voegt de gegeven nick toe aan de\n" +"%s lijst.\n" +" \n" +"Het %s DEL commando verwijdert de gegeven nick van de\n" +"%s lijst. Als een lijst van vermeldingsnummers is opgegeven\n" +"worden die verwijderd. (Zie het LIST-voorbeeld hieronder.)\n" +" \n" +"Het %s LIST commando geeft de %s lijst weer. Als er\n" +"een masker is gegeven worden alleen de overeenstemmende\n" +"resultaten weergegeven. Als een lijst van vermeldingsnummers\n" +"is opgegeven, worden alleen die weergegeven; bijvoorbeeld:\n" +" \n" +" %s #kanaal LIST 2-5,7-9\n" +" Geeft %s's 2 t/m 5 en 7 t/m 9 weer.\n" +" \n" +"Het %s CLEAR commando verwijdert alle vermeldingen van de\n" +"%s lijst." + +#: modules/commands/cs_akick.cpp:508 +#, c-format +msgid "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." +msgstr "" +" \n" +"Het AKICK DEL commando verwijdert het gegeven masker of de nick\n" +"van de AutoKicklijst. Het verwijdert weliswaar geen bans die geplaatst\n" +"zijn net omwille van de AutoKick; die moeten manueel verwijderd worden.\n" +" \n" +"Het AKICK LIST commando geeft de AutoKicklijst weer.\n" +"Als een masker word gegeven zullen alleen de AutoKickvermeldingen die\n" +"overeenkomen met het masker worden weergegeven.\n" +" \n" +"Het AKICK VIEW commando is een versie van AKICK LIST die meer\n" +"informatie geeft.\n" +" \n" +"Het AKICK ENFORCE commando zorgt ervoor dat %s gebruikers\n" +"verwijdert van het kanaal die overeenkomen met een vermelding in de\n" +"AutoKicklijst.\n" +" \n" +"Het AKICK CLEAR commando maakt de AutoKicklijst leeg." + +#: modules/commands/os_akill.cpp:448 +msgid "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." +msgstr "" +" \n" +"Het AKILL DEL commando verwijdert het gegeven masker van de AKILL\n" +"lijst als deze erop staat. Als er een lijst van vermeldingsnummers\n" +"is opgegeven zullen die verwijderd worden. (Zie het voorbeeld voor\n" +"LIST hier onder.)\n" +" \n" +"Het AKILL LIST commando geeft de AKILL lijst weer.\n" +"Als een masker met jokerteken is gegeven zullen alleen de AKILLs die\n" +"overeenkomen met het masker worden weergegeven. Als een lijst van\n" +"vermeldingsnummers is gegeven worden alleen die weergegeven.\n" +"Bijvoorbeeld:\n" +" AKILL LIST 2-5,7-9\n" +" Geeft AKILLs 2 t/m 5 en 7 t/m 9 weer.\n" +" \n" +"AKILL VIEW is een versie van AKILL LIST die meer informatie\n" +"geeft: de naam van degene die de AKILL toe heeft gevoegd, de datum\n" +"waarop dit gebeurde, waneer deze verloopt, en het ident@host/ip masker\n" +"en de reden.\n" +" \n" +"AKILL CLEAR maakt de AKILL lijst leeg." + +#: modules/commands/os_sxline.cpp:462 +msgid "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." +msgstr "" +" \n" +"Het SNLINE DEL commando verwijdert het gegeven masker\n" +"van de SNLINE lijst als die er op staat. Als een lijst van vermeldings-\n" +"nummers is gegeven, dan worden die verwijderd. (Zie het voorbeeld\n" +"voor LIST hieronder.)\n" +" \n" +"Het SNLINE LIST commando toont de SNLINE lijst.\n" +"Als een jokerteken is gegeven, dan zullen enkel de overeenkomende\n" +"vermeldingen getoont worden. Als een lijst van vermeldingsnummers\n" +"is gegeven, dan worden die getoont; bijvoorbeeld:\n" +" SNLINE LIST 2-5,7-9\n" +" Toont SNLINE vermeldingen genummerd van 2 t/m 5 en 7 t/m 9.\n" +" \n" +"SNLINE VIEW geeft gedetailleerdere informatie dan SNLINE LIST,\n" +"en toont wie een SNLINE heeft toegevoegd, de datum waarop, wanneer\n" +"deze verloopt, alsook het naammasker en de reden.\n" +" \n" +"SNLINE CLEAR verwijdert alle vermeldingen van de SNLINE lijst." + +#: modules/commands/os_sxline.cpp:697 +msgid "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." +msgstr "" +" \n" +"Het SQLINE DEL commando verwijdert het gegeven masker\n" +"van de SQLINE lijst als die er op staat. Als een lijst van vermeldings-\n" +"nummers is gegeven, dan worden die verwijderd. (Zie het voorbeeld\n" +"voor LIST hieronder.)\n" +" \n" +"Het SQLINE LIST commando toont de SQLINE lijst.\n" +"Als een jokerteken is gegeven, dan zullen enkel de overeenkomende\n" +"vermeldingen getoont worden. Als een lijst van vermeldingsnummers\n" +"is gegeven, dan worden die getoont; bijvoorbeeld:\n" +" SQLINE LIST 2-5,7-9\n" +" Toont SQLINE vermeldingen genummerd van 2 t/m 5 en 7 t/m 9.\n" +" \n" +"SQLINE VIEW geeft gedetailleerdere informatie dan SQLINE LIST,\n" +"en toont wie een SQLINE heeft toegevoegd, de datum waarop, wanneer\n" +"deze verloopt, alsook het masker en de reden.\n" +" \n" +"SQLINE CLEAR verwijdert alle vermeldingen van de SQLINE lijst." + +#: modules/commands/bs_assign.cpp:197 +msgid "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." +msgstr "" +" \n" +"Deze optie zorgt ervoor dat een kanaal geen bot kan hebben.\n" +"Als er al een bot aan het kanaal is toegewezen wordt deze\n" +"automatisch van het kanaal gehaald wanneer je deze optie\n" +"aan zet." + +#: modules/commands/bs_set.cpp:199 +msgid "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." +msgstr "" +" \n" +"Deze optie zorgt ervoor dat een bot niet kan worden\n" +"toegewezen aan een kanaal door gebruikers die geen\n" +"IRC operator zijn." + +#: modules/pseudoclients/memoserv.cpp:227 +#, c-format +msgid "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." +msgstr "" +" \n" +"Typ %s%s HELP commando voor help over een van\n" +"de bovenstaande commando's." + +#: modules/commands/os_oper.cpp:167 +#, c-format +msgid " %s is online using this oper block." +msgstr " %s is online met dit oper blok." + +#: modules/commands/os_modinfo.cpp:55 +#, c-format +msgid " Command %s on %s is linked to %s" +msgstr " Commando %s op %s is gelinkt aan %s" + +#: modules/commands/os_modinfo.cpp:43 +#, c-format +msgid " Providing service: %s" +msgstr " Stelt ter beschikking: %s" + +#: modules/commands/os_oper.cpp:163 +msgid " This oper is configured in the configuration file." +msgstr " Deze oper is ingesteld in het configuratiebestand." + +#: modules/commands/os_modinfo.cpp:34 +#, c-format +msgid " Loaded at: %p" +msgstr " Geladen op: %p" + +#: modules/commands/cs_seen.cpp:303 +#, c-format +msgid " but %s mysteriously dematerialized." +msgstr " maar %s is in rook opgegaan." + +#: src/messages.cpp:339 +#, c-format +msgid "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." +msgstr "" +"\"/msg %s\" wordt niet meer ondersteund. Gebruik \"/msg %s@%s\" of \"/%s\"." + +#: modules/commands/os_jupe.cpp:19 +msgid "\"Jupiter\" a server" +msgstr "Blokkeer een server" + +#: modules/commands/os_oper.cpp:161 +#, c-format +msgid "%-8s %s" +msgstr "%-8s %s" + +#: modules/extra/stats/cs_fantasy_top.cpp:152 +#, c-format +msgid "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" +"%2lu %-16s letters: %s, woorden: %s, lijnen: %s, smileys: %s, acties: %s" + +#: src/misc.cpp:359 +msgid "%b %d %H:%M:%S %Y %Z" +msgstr "%b %d %H:%M:%S %Y %Z" + +#: modules/commands/cs_log.cpp:205 +#, c-format +msgid "%c is an unknown status mode." +msgstr "%c is een onbekende status mode." + +#: modules/commands/cs_mode.cpp:431 +#, c-format +msgid "%c%c is not locked on %s." +msgstr "%c%c is niet vergrendeld op %s." + +#: modules/commands/cs_mode.cpp:427 +#, c-format +msgid "%c%c%s has been unlocked from %s." +msgstr "%c%c%s werd ontgrendeld op %s." + +#: modules/commands/cs_clone.cpp:56 +#, c-format +msgid "%d access entries from %s have been cloned to %s." +msgstr "%d toegangsvermeldingen van %s zijn gekopiëerd naar %s." + +#: modules/commands/bs_botlist.cpp:56 +#, c-format +msgid "%d bots available." +msgstr "%d bots beschikbaar." + +#: modules/commands/os_modinfo.cpp:189 +#, c-format +msgid "%d modules loaded." +msgstr "%d modules geladen." + +#: modules/commands/ns_group.cpp:357 +#, c-format +msgid "%d nickname(s) in the group." +msgstr "%d nick(s) in de groep." + +#: modules/commands/cs_seen.cpp:137 +#, c-format +msgid "%lu nicks are stored in the database, using %.2Lf kB of memory." +msgstr "" +"%lu nicks zijn opgeslagen in de database, geheugenverbruik is %.2Lf kB." + +#: modules/commands/cs_xop.cpp:241 modules/commands/cs_xop.cpp:372 +#: modules/commands/cs_xop.cpp:450 +#, c-format +msgid "%s %s list is empty." +msgstr "%s %s lijst is leeg." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1181 +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1201 +#: modules/commands/bs_kick.cpp:1211 +#, c-format +msgid "%s (%d kick(s) to ban)" +msgstr "%s (%d kick(s) tot ban)" + +#: modules/commands/bs_kick.cpp:1161 +#, c-format +msgid "%s (%d kick(s) to ban; %d lines in %ds)" +msgstr "%s (%d kick(s) tot ban; %d lijnen in %ds)" + +#: modules/commands/bs_kick.cpp:1171 +#, c-format +msgid "%s (%d kick(s) to ban; %d times)" +msgstr "%s (%d kick(s) tot ban; %d maal)" + +#: modules/commands/bs_kick.cpp:1141 +#, c-format +msgid "%s (%d kick(s) to ban; minimum %d/%d%%)" +msgstr "%s (%d kick(s) tot ban; minimaal %d/%d%%)" + +#: modules/commands/bs_kick.cpp:1163 +#, c-format +msgid "%s (%d lines in %ds)" +msgstr "%s (%d lijnen in %ds)" + +#: modules/commands/bs_kick.cpp:1173 +#, c-format +msgid "%s (%d times)" +msgstr "%s (%d keer)" + +#: modules/commands/cs_seen.cpp:358 +#, c-format +msgid "%s (%s) was kicked from %s (\"%s\") %s ago%s" +msgstr "%s (%s) werd gekickt van %s (\"%s\") %s geleden%s" + +#: modules/commands/cs_seen.cpp:355 +#, c-format +msgid "%s (%s) was kicked from a secret channel %s ago%s" +msgstr "%s (%s) werd gekickt van een geheim kanaal %s geleden%s" + +#: modules/commands/cs_seen.cpp:326 +#, c-format +msgid "%s (%s) was last seen changing nick from %s to %s %s ago%s" +msgstr "" +"%s (%s) werd het laatst gezien bij het van nick veranderen van %s naar %s %s " +"geleden%s" + +#: modules/commands/cs_seen.cpp:321 +#, c-format +msgid "%s (%s) was last seen changing nick to %s %s ago%s" +msgstr "" +"%s (%s) werd het laatst gezien bij het van nick veranderen naar %s %s geleden" +"%s" + +#: modules/commands/cs_seen.cpp:310 +#, c-format +msgid "%s (%s) was last seen connecting %s ago (%s)%s" +msgstr "%s (%s) werd het laatst gezien bij het verbinden %s geleden (%s)%s" + +#: modules/commands/cs_seen.cpp:335 +#, c-format +msgid "%s (%s) was last seen joining %s %s ago%s" +msgstr "%s (%s) werd het laatst gezien bij het binnenkomen op %s %s geleden%s" + +#: modules/commands/cs_seen.cpp:332 +#, c-format +msgid "%s (%s) was last seen joining a secret channel %s ago%s" +msgstr "" +"%s (%s) werd het laatst gezien bij het binnenkomen van een geheim kanaal %s " +"geleden%s" + +#: modules/commands/cs_seen.cpp:344 +#, c-format +msgid "%s (%s) was last seen parting %s %s ago%s" +msgstr "%s (%s) werd het laatst gezien bij het verlaten van %s %s geleden%s" + +#: modules/commands/cs_seen.cpp:341 +#, c-format +msgid "%s (%s) was last seen parting a secret channel %s ago%s" +msgstr "" +"%s (%s) werd het laatst gezien bij het verlaten van een geheim kanaal %s " +"geleden%s" + +#: modules/commands/cs_seen.cpp:349 +#, c-format +msgid "%s (%s) was last seen quitting (%s) %s ago (%s)." +msgstr "%s (%s) werd het laatst gezien bij het quitten (%s) %s geleden (%s)." + +#: modules/commands/bs_kick.cpp:1143 +#, c-format +msgid "%s (minimum %d/%d%%)" +msgstr "%s (minimaal %d/%d%%)" + +#: modules/commands/cs_access.cpp:245 modules/commands/cs_access.cpp:349 +#: modules/commands/cs_access.cpp:454 modules/commands/cs_access.cpp:467 +#: modules/commands/cs_flags.cpp:295 +#, c-format +msgid "%s access list is empty." +msgstr "%s toegangslijst is leeg." + +#: modules/commands/ns_ajoin.cpp:184 +#, c-format +msgid "%s added to %s's auto join list." +msgstr "%s toegevoegd aan %s's autojoinlijst." + +#: src/xline.cpp:389 +#, c-format +msgid "%s already exists." +msgstr "%s bestaat al." + +#: modules/commands/cs_akick.cpp:202 modules/commands/cs_akick.cpp:387 +#: modules/commands/cs_akick.cpp:400 +#, c-format +msgid "%s autokick list is empty." +msgstr "%s autokicklijst is leeg." + +#: modules/commands/bs_badwords.cpp:198 modules/commands/bs_badwords.cpp:316 +#, c-format +msgid "%s bad words list is empty." +msgstr "%s slechtewoordenlijst is leeg." + +#: modules/commands/cs_set.cpp:993 +#, c-format +msgid "%s cannot be the successor on channel %s as they are the founder." +msgstr "" +"%s kan de opvolger niet zijn op kanaal %s omdat hij/zij de stichter is." + +#: modules/pseudoclients/global.cpp:90 modules/pseudoclients/hostserv.cpp:78 +#: modules/pseudoclients/operserv.cpp:287 +#, c-format +msgid "%s commands:" +msgstr "%s commando's:" + +#: include/language.h:69 +#, c-format +msgid "%s coverage is too wide; Please use a more specific mask." +msgstr "%s is te breed; gelieve een meer specifiek masker te gebruiken." + +#: modules/commands/ms_info.cpp:94 +#, c-format +msgid "%s currently has %d memos, of which %d are unread." +msgstr "%s heeft momenteel %d memo's, waarvan er %d ongelezen zijn." + +#: modules/commands/ms_info.cpp:92 +#, c-format +msgid "%s currently has %d memos, of which 1 is unread." +msgstr "%s heeft momenteel %d memo's, waarvan er 1 ongelezen is." + +#: modules/commands/ms_info.cpp:90 +#, c-format +msgid "%s currently has %d memos." +msgstr "%s heeft momenteel %d memo's." + +#: modules/commands/ms_info.cpp:88 +#, c-format +msgid "%s currently has %d memos; all of them are unread." +msgstr "%s heeft momenteel %d memo's; allemaal zijn ze ongelezen." + +#: modules/commands/ms_info.cpp:77 +#, c-format +msgid "%s currently has 1 memo, and it has not yet been read." +msgstr "%s heeft momenteel 1 memo, en deze is nog ongelezen." + +#: modules/commands/ms_info.cpp:79 +#, c-format +msgid "%s currently has 1 memo." +msgstr "%s heeft momenteel 1 memo." + +#: modules/commands/ms_info.cpp:73 +#, c-format +msgid "%s currently has no memos." +msgstr "%s heeft momenteel geen memo's." + +#: modules/commands/os_forbid.cpp:344 +#, c-format +msgid "%s deleted from the %s forbid list." +msgstr "%s verwijderd van de verboden %s lijst." + +#: include/language.h:105 +#, c-format +msgid "%s for %s set to %s." +msgstr "%s voor %s gewijzigd naar %s." + +#: include/language.h:106 +#, c-format +msgid "%s for %s unset." +msgstr "%s voor %s verwijderd." + +#: modules/commands/ns_ajoin.cpp:176 +#, c-format +msgid "%s had an invalid key specified, and was thus ignored." +msgstr "%s had een ongeldige opgegeven sleutel, en werd dus genegeerd." + +#: modules/commands/ms_info.cpp:111 +#, c-format +msgid "%s has no memo limit." +msgstr "%s heeft geen memolimiet." + +#: include/language.h:115 +#, c-format +msgid "%s has no memos." +msgstr "%s heeft geen memo's." + +#: include/language.h:118 +#, c-format +msgid "%s has no new memos." +msgstr "%s heeft geen nieuwe memo's." + +#: modules/commands/ns_info.cpp:53 +#, c-format +msgid "%s is %s" +msgstr "%s is %s" + +#: modules/commands/ns_info.cpp:59 +#, c-format +msgid "%s is a Services Operator of type %s." +msgstr "%s is een Services Operator van het type %s." + +#: modules/commands/cs_seen.cpp:281 +#, c-format +msgid "%s is a client on services." +msgstr "%s is een bot van Services." + +#: modules/commands/cs_seen.cpp:200 +#, c-format +msgid "%s is a network service." +msgstr "%s is een netwerkdienst." + +#: src/xline.cpp:407 +#, c-format +msgid "%s is already covered by %s." +msgstr "%s is al gedekt door %s." + +#: modules/commands/ns_ajoin.cpp:170 +#, c-format +msgid "%s is already on %s's auto join list." +msgstr "%s staat al op %s's autojoinlijst." + +#: modules/commands/ns_info.cpp:56 +#, c-format +msgid "%s is an unconfirmed nickname." +msgstr "%s is een onbevestigde nickname." + +#: modules/commands/cs_flags.cpp:432 +#, c-format +msgid "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." +msgstr "" +"%s is een andere manier om de kanaal toegangslijst aan te passen,\n" +"vergelijkbaar met de xOP en ACCESS methodes." + +#: modules/commands/ns_info.cpp:74 +#, c-format +msgid "%s is currently online." +msgstr "%s is momenteel online." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is disabled" +msgstr "%s is uitgeschakeld" + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is enabled" +msgstr "%s is ingeschakeld" + +#: modules/commands/os_dns.cpp:507 +#, c-format +msgid "%s is not a valid IP address." +msgstr "%s is geen geldig IP-adres." + +#: modules/commands/cs_log.cpp:167 modules/commands/cs_log.cpp:192 +#, c-format +msgid "%s is not a valid command." +msgstr "%s is geen geldig commando." + +#: modules/commands/cs_log.cpp:198 +#, c-format +msgid "%s is not a valid logging method." +msgstr "%s is geen geldige log methode." + +#: modules/commands/ms_info.cpp:124 +#, c-format +msgid "%s is not notified of new memos." +msgstr "%s wordt niet geïnformeerd over nieuwe memo's." + +#: modules/commands/ms_info.cpp:118 +#, c-format +msgid "%s is notified of new memos at logon and when they arrive." +msgstr "" +"%s wordt geïnformeerd over nieuwe memo's wanneer hij/zij inlogt en wanneer " +"deze toekomen." + +#: modules/commands/ms_info.cpp:122 +#, c-format +msgid "%s is notified of new memos at logon." +msgstr "%s wordt geïnformeerd over nieuwe memo's wanneer hij/zij inlogt." + +#: modules/commands/ms_info.cpp:120 +#, c-format +msgid "%s is notified when new memos arrive." +msgstr "%s wordt geinformeerd over nieuwe memo's wanneer deze arriveren." + +#: modules/commands/cs_seen.cpp:232 +#, c-format +msgid "%s is on the channel right now (as %s)!" +msgstr "%s is nu op het kanaal (als %s)!" + +#: modules/commands/cs_seen.cpp:221 +#, c-format +msgid "%s is on the channel right now!" +msgstr "%s is nu op het kanaal!" + +#: modules/commands/cs_xop.cpp:434 +#, c-format +msgid "%s list for %s" +msgstr "%s lijst voor %s" + +#: modules/commands/os_sxline.cpp:69 modules/commands/os_sxline.cpp:113 +#, c-format +msgid "%s list is empty." +msgstr "%s lijst is leeg." + +#: modules/commands/cs_mode.cpp:376 +#, c-format +msgid "%s locked on %s." +msgstr "%s vergrendeld op %s." + +#: modules/extra/stats/cs_fantasy_stats.cpp:120 +#, c-format +msgid "%s not found." +msgstr "%s niet gevonden." + +#: modules/commands/os_config.cpp:79 +#, c-format +msgid "%s settings:" +msgstr "%s instellingen:" + +#: modules/commands/cs_seen.cpp:255 +#, c-format +msgid "%s was last seen here %s ago." +msgstr "%s werd hier het laatst %s geleden gezien." + +#: modules/commands/ns_ajoin.cpp:213 +#, c-format +msgid "%s was not found on %s's auto join list." +msgstr "%s werd niet gevonden op %s's autojoinlijst." + +#: modules/commands/ns_ajoin.cpp:221 +#, c-format +msgid "%s was removed from %s's auto join list." +msgstr "%s werd verwijderd van %s's autojoinlijst." + +#: modules/commands/ms_set.cpp:64 +#, c-format +msgid "%s will not send you any notification of memos." +msgstr "%s zal je niet over memo's informeren." + +#: modules/commands/ms_set.cpp:42 +#, c-format +msgid "%s will now notify you of memos when they are sent to you." +msgstr "" +"%s zal je nu informeren over memo's wanneer deze naar jou worden verzonden." + +#: modules/commands/ms_set.cpp:30 +#, c-format +msgid "" +"%s will now notify you of memos when you log on and when they are sent to " +"you." +msgstr "" +"%s zal je nu informeren over memo's zodra je inlogt en wanneer deze naar je " +"toegezonden worden." + +#: modules/commands/ms_set.cpp:36 +#, c-format +msgid "%s will now notify you of memos when you log on or unset /AWAY." +msgstr "" +"%s zal je nu informeren over memo's wanneer je inlogt of /AWAY uitschakelt." + +#: modules/commands/bs_bot.cpp:89 +#, c-format +msgid "%s!%s@%s (%s) added to the bot list." +msgstr "%s!%s@%s (%s) toegevoegd aan de botlijst." + +#: modules/commands/ns_access.cpp:83 +#, c-format +msgid "%s's access list is empty." +msgstr "%s's toegangslijst is leeg." + +#: modules/commands/ns_ajoin.cpp:96 +#, c-format +msgid "%s's auto join list is empty." +msgstr "%s's autojoinlijst is leeg." + +#: modules/commands/ns_ajoin.cpp:111 +#, c-format +msgid "%s's auto join list:" +msgstr "%s's autojoinlijst:" + +#: modules/commands/ns_cert.cpp:242 +#, c-format +msgid "%s's certificate list is empty." +msgstr "%s's certificaatlijst is leeg." + +#: modules/commands/ms_info.cpp:99 modules/commands/ms_info.cpp:106 +#, c-format +msgid "%s's memo limit is %d, and may not be changed." +msgstr "%s's memolimiet is %d, en mag niet worden veranderd." + +#: modules/commands/ms_info.cpp:101 modules/commands/ms_info.cpp:108 +#, c-format +msgid "%s's memo limit is %d." +msgstr "%s's memolimiet is %d." + +#: src/misc.cpp:363 +#, c-format +msgid "(%s ago)" +msgstr "(%s geleden)" + +#: src/misc.cpp:365 +#, c-format +msgid "(%s from now)" +msgstr "(%s vanaf nu)" + +#: modules/commands/os_dns.cpp:244 +msgid "(Split)" +msgstr "(Gesplit)" + +#: modules/commands/os_info.cpp:268 +#, c-format +msgid "(by %s on %s) %s" +msgstr "(door %s op %s) %s" + +#: modules/commands/cs_access.cpp:710 +msgid "(disabled)" +msgstr "(uitgeschakeld)" + +#: modules/commands/cs_access.cpp:712 +msgid "(founder only)" +msgstr "(enkel stichter)" + +#: src/misc.cpp:367 +msgid "(now)" +msgstr "(nu)" + +#: modules/commands/os_defcon.cpp:168 +msgid "* AKILL any new clients connecting" +msgstr "* AKILL elke nieuwe gebruiker die verbindt" + +#: modules/commands/os_defcon.cpp:158 +#, c-format +msgid "* Force channel modes (%s) to be set on all channels" +msgstr "* Forceer kanaalmodes (%s) op alle kanalen" + +#: modules/commands/os_defcon.cpp:164 +msgid "* Ignore non-opers with a message" +msgstr "* Negeer niet-operators (met een boodschap)" + +#: modules/commands/os_defcon.cpp:162 +msgid "* Kill any new clients connecting" +msgstr "* Kill elke nieuwe gebruiker die verbindt" + +#: modules/commands/os_defcon.cpp:156 +msgid "* No mode lock changes" +msgstr "* Geen mode lock veranderingen" + +#: modules/commands/os_defcon.cpp:152 +msgid "* No new channel registrations" +msgstr "* Geen nieuwe kanaalregistraties" + +#: modules/commands/os_defcon.cpp:170 +msgid "* No new memos sent" +msgstr "* Geen nieuwe memo's verzenden" + +#: modules/commands/os_defcon.cpp:154 +msgid "* No new nick registrations" +msgstr "* Geen nieuwe nickregistraties" + +#: modules/commands/os_defcon.cpp:166 +msgid "* Silently ignore non-opers" +msgstr "* Negeer niet-operators (geen boodschap)" + +#: modules/commands/os_defcon.cpp:160 +#, c-format +msgid "* Use the reduced session limit of %d" +msgstr "* Gebruik de beperkte sessielimiet van %d" + +#: modules/commands/cs_seen.cpp:319 +#, c-format +msgid ", but %s mysteriously dematerialized." +msgstr ", maar %s is in rook opgegaan." + +#: modules/commands/cs_seen.cpp:317 +#, c-format +msgid ". %s is still online." +msgstr "%s is nog steeds online." + +#: include/language.h:87 +msgid "" +msgstr "" + +#: modules/commands/ns_set.cpp:504 +#, c-format +msgid "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." +msgstr "" +"Een bevestigings-e-mail werd verstuurd naar %s. Volg de instructies om je e-" +"mail adres te wijzigen." + +#: modules/commands/ms_sendall.cpp:45 +msgid "A massmemo has been sent to all registered users." +msgstr "Een memo werd gestuurd naar alle geregistreerde gebruikers." + +#: modules/commands/hs_request.cpp:285 +msgid "" +"A memo informing the user will also be sent, which includes the reason for " +"the rejection if supplied." +msgstr "" +"Een informerende memo zal ook gestuurd worden naar de gebruiker, met de " +"reden indien opgegeven." + +#: modules/commands/hs_request.cpp:229 +msgid "A memo informing the user will also be sent." +msgstr "Een informerende memo zal ook gestuurd worden naar de gebruiker." + +#: modules/commands/ms_read.cpp:42 +#, c-format +msgid "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." +msgstr "" +"Een notificatie-memo is naar %s verstuurd om hem/haar te\n" +"informeren dat je zijn/haar memo gelezen hebt." + +#: include/language.h:123 +msgid "A vHost ident must be in the format of a valid ident." +msgstr "Een vHost ident moet in het formaat van een geldige ident zijn." + +#: include/language.h:122 +msgid "A vHost must be in the format of a valid hostname." +msgstr "Een vHost moet in het formaat van een geldige host zijn." + +#: modules/commands/os_ignore.cpp:342 +msgid "ADD expiry {nick|mask} [reason]" +msgstr "ADD verlooptijd {nick|masker} [reden]" + +#: modules/commands/os_oper.cpp:70 +msgid "ADD oper type" +msgstr "ADD operator type" + +#: modules/commands/os_info.cpp:102 +msgid "ADD target info" +msgstr "ADD doel info" + +#: modules/commands/os_news.cpp:278 +msgid "ADD text" +msgstr "ADD tekst" + +#: modules/commands/os_session.cpp:523 +msgid "ADD [+expiry] mask limit reason" +msgstr "ADD [+verlooptijd] masker limiet reden" + +#: modules/commands/ns_ajoin.cpp:231 +msgid "ADD [nickname] channel [key]" +msgstr "ADD [nick] kanaal [sleutel]" + +#: modules/commands/ns_access.cpp:102 +msgid "ADD [nickname] mask" +msgstr "ADD [nick] masker" + +#: modules/commands/ns_cert.cpp:258 +msgid "ADD [nickname] [fingerprint]" +msgstr "ADD [nick] [vingerafdruk]" + +#: modules/commands/os_sxline.cpp:659 modules/commands/os_akill.cpp:386 +msgid "ADD [+expiry] mask reason" +msgstr "ADD [+verlooptijd] masker reden" + +#: modules/commands/os_sxline.cpp:425 +msgid "ADD [+expiry] mask:reason" +msgstr "ADD [+verlooptijd] masker:reden" + +#: modules/commands/os_forbid.cpp:157 +msgid "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" +msgstr "ADD {NICK|CHAN|EMAIL|REGISTER} [+verlooptijd] vermelding reden" + +#: modules/commands/os_dns.cpp:665 +msgid "ADDIP server.name ip" +msgstr "ADDIP server.naam ip" + +#: modules/commands/os_dns.cpp:663 +msgid "ADDSERVER server.name [zone.name]" +msgstr "ADDSERVER server.naam [domein.naam]" + +#: modules/commands/os_dns.cpp:661 +msgid "ADDZONE zone.name" +msgstr "ADDZONE domein.naam" + +#: modules/commands/cs_akick.cpp:38 +#, c-format +msgid "AKICK ENFORCE for %s complete; %d users were affected." +msgstr "AKICK ENFORCE voor %s klaar; %d gebruiker(s) zijn/is getroffen." + +#: modules/commands/os_chankill.cpp:21 +msgid "AKILL all users on a specific channel" +msgstr "AKILL alle gebruikers op een specifiek kanaal" + +#: modules/commands/os_akill.cpp:222 modules/commands/os_akill.cpp:339 +#: modules/commands/os_akill.cpp:353 +msgid "AKILL list is empty." +msgstr "AKILL lijst is leeg." + +#: modules/commands/bs_kick.cpp:1211 modules/commands/bs_kick.cpp:1213 +#: modules/commands/bs_kick.cpp:1216 +msgid "AMSG kicker" +msgstr "AMSG-kicker" + +#: modules/commands/ns_alist.cpp:48 +msgid "Access" +msgstr "Toegang" + +#: include/language.h:72 +msgid "Access denied." +msgstr "Toegang geweigerd." + +#: modules/commands/cs_status.cpp:58 +#, c-format +msgid "Access for %s on %s:" +msgstr "Toegang voor %s op %s:" + +#: include/language.h:107 +#, c-format +msgid "Access level must be between %d and %d inclusive." +msgstr "Toegangsniveau moet tussen de %d en %d zijn." + +#: modules/commands/cs_access.cpp:108 +msgid "Access level must be non-zero." +msgstr "Toegangsniveau mag geen nul zijn." + +#: modules/commands/cs_access.cpp:694 +#, c-format +msgid "Access level settings for channel %s:" +msgstr "Toegangsniveau instellingen voor kanaal %s:" + +#: modules/commands/cs_access.cpp:734 +#, c-format +msgid "Access levels for %s reset to defaults." +msgstr "Toegangsniveaus voor %s teruggezet naar standaardwaarden." + +#: modules/commands/cs_access.cpp:439 modules/commands/ns_access.cpp:87 +#, c-format +msgid "Access list for %s:" +msgstr "Toegangslijst voor %s:" + +#: modules/commands/help.cpp:166 +#, c-format +msgid "" +"Access to this command requires the permission %s to be present in your " +"opertype." +msgstr "" +"Toegang tot dit commando vereist dat het %s recht in jouw opertype aanwezig " +"is." + +#: modules/commands/ns_cert.cpp:368 modules/commands/ns_cert.cpp:392 +#: modules/commands/ns_identify.cpp:94 +#, c-format +msgid "" +"Account %s has already reached the maximum number of simultaneous logins " +"(%u)." +msgstr "" +"Account %s heeft reeds het maximum aantal gelijktijdige logins bereikt (%u)." + +#: modules/commands/cs_set.cpp:683 +msgid "Activate security features" +msgstr "Activeer veiligheidsopties" + +#: modules/commands/hs_request.cpp:227 +msgid "Activate the requested vHost for the given nick." +msgstr "Activeer de aangevraagde vHost voor de opgegeven nick." + +#: modules/commands/hs_on.cpp:55 +msgid "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." +msgstr "" +"Activeert de vHost die momenteel toegewezen is aan de nick\n" +"die je gebruikt. Als je dit commando uitvoert zal elke\n" +"gebruiker die een /whois op je doet de vHost zien in plaats\n" +"van je echte host/IP-adres." + +#: modules/commands/hs_on.cpp:19 +msgid "Activates your assigned vhost" +msgstr "Activeert je toegewezen vHost" + +#: modules/commands/os_info.cpp:243 +msgid "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." +msgstr "" +"Voeg oper informatie toe of verwijder deze voor de opgegeven nick of " +"kanaal.\n" +"Dit zal getoond worden aan operators in het respectievelijke INFO commando " +"voor\n" +"de nick of het kanaal." + +#: modules/commands/os_dns.cpp:515 +#, c-format +msgid "Added IP %s to %s." +msgstr "IP-adres %s toegevoegd aan %s." + +#: modules/commands/os_forbid.cpp:239 +#, c-format +msgid "Added a forbid on %s of type %s to expire on %s." +msgstr "Verbod toegevoegd op %s van het type %s dat verloopt op %s." + +#: modules/commands/os_info.cpp:164 +#, c-format +msgid "Added info to %s." +msgstr "Info toegevoegd aan %s." + +#: modules/commands/os_news.cpp:34 +msgid "Added new logon news item." +msgstr "Nieuw login nieuwsbericht toegevoegd." + +#: modules/commands/os_news.cpp:44 +msgid "Added new oper news item." +msgstr "Nieuw operator nieuwsbericht toegevoegd." + +#: modules/commands/os_news.cpp:54 +msgid "Added new random news item." +msgstr "Nieuw willekeurig nieuwsbericht toegevoegd." + +#: modules/commands/os_dns.cpp:395 +#, c-format +msgid "Added server %s." +msgstr "Server %s toegevoegd." + +#: modules/commands/os_dns.cpp:300 +#, c-format +msgid "Added zone %s." +msgstr "Domein %s toegevoegd." + +#: modules/commands/cs_entrymsg.cpp:257 +msgid "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." +msgstr "" +"Toevoegen, verwijderen, of leegmaken van de welkomstberichtenlijst vereist " +"het\n" +"SET recht." + +#: modules/commands/ns_register.cpp:104 +msgid "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." +msgstr "" +"Bovendien kunnen Services Operators met het nickserv/confirm recht\n" +"een nick opgeven in de plaats van bevestigingscode om hen te valideren." + +#: modules/pseudoclients/botserv.cpp:172 +#, c-format +msgid "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" +msgstr "" +"Bovendien, als fantasie geactiveerd is, kunnen fantasie\n" +"commando's uitgevoerd worden door de commandonaam\n" +"vooraf te gaan met één van de volgende karakters: %s" + +#: modules/commands/os_noop.cpp:58 +#, c-format +msgid "All O:lines of %s have been reset." +msgstr "Alle O:lines van %s zijn hersteld." + +#: modules/commands/cs_clone.cpp:71 +#, c-format +msgid "All akick entries from %s have been cloned to %s." +msgstr "Alle autokicks van %s zijn gekopiëerd naar %s." + +#: modules/commands/help.cpp:57 +#, c-format +msgid "All available commands for %s:" +msgstr "Alle beschikbare commando's voor %s:" + +#: modules/commands/cs_clone.cpp:96 +#, c-format +msgid "All badword entries from %s have been cloned to %s." +msgstr "Alle slechte woorden van %s zijn gekopiëerd naar %s." + +#: modules/commands/cs_clone.cpp:108 +#, c-format +msgid "All level entries from %s have been cloned into %s." +msgstr "Alle toegangsniveaus van %s zijn gekopiëerd naar %s." + +#: modules/commands/os_news.cpp:38 +msgid "All logon news items deleted." +msgstr "Alle login nieuwsberichten zijn verwijderd." + +#: modules/commands/ms_del.cpp:115 +#, c-format +msgid "All memos for channel %s have been deleted." +msgstr "Alle memo's voor kanaal %s zijn verwijderd." + +#: modules/commands/os_mode.cpp:61 +#, c-format +msgid "All modes cleared on %s." +msgstr "Alle modes verwijderd op %s." + +#: modules/commands/ns_register.cpp:258 modules/commands/ns_register.cpp:389 +msgid "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." +msgstr "" +"Alle nieuwe accounts moeten gevalideerd worden door een beheerder. Gelieve " +"te wachten op bevestiging." + +#: modules/commands/ms_del.cpp:119 +msgid "All of your memos have been deleted." +msgstr "Al je memo's zijn verwijderd." + +#: modules/commands/os_news.cpp:48 +msgid "All oper news items deleted." +msgstr "Alle operator nieuwsberichten zijn verwijderd." + +#: modules/commands/os_noop.cpp:41 +#, c-format +msgid "All operators from %s have been removed." +msgstr "Alle operators van %s zijn verwijderd." + +#: modules/commands/os_news.cpp:58 +msgid "All random news items deleted." +msgstr "Alle willekeurige nieuwsberichten zijn verwijderd." + +#: modules/commands/cs_clone.cpp:211 +#, c-format +msgid "All settings from %s have been cloned to %s." +msgstr "Alle instellingen van %s zijn gekopiëerd naar %s." + +#: modules/commands/cs_sync.cpp:41 +#, c-format +msgid "All user modes on %s have been synced." +msgstr "Alle gebruikermodes op %s zijn gesynchroniseerd." + +#: modules/commands/hs_group.cpp:60 +#, c-format +msgid "All vhosts in the group %s have been set to %s." +msgstr "Alle vHosts in de groep %s zijn gewijzigd naar %s." + +#: modules/commands/hs_group.cpp:58 +#, c-format +msgid "All vhosts in the group %s have been set to %s@%s." +msgstr "Alle vHosts in de groep %s zijn gewijzigd naar %s@%s." + +#: src/access.cpp:40 +msgid "Allowed to (de)halfop him/herself" +msgstr "Kan zich/haarzelf (de)halfop'en" + +#: src/access.cpp:39 +msgid "Allowed to (de)halfop users" +msgstr "Kan gebruikers (de)halfop'en" + +#: src/access.cpp:48 +msgid "Allowed to (de)op him/herself" +msgstr "Kan zich/haarzelf (de)op'en" + +#: src/access.cpp:47 +msgid "Allowed to (de)op users" +msgstr "Kan gebruikers (de)op'en" + +#: src/access.cpp:50 +msgid "Allowed to (de)owner him/herself" +msgstr "Kan zich/haarzelf (de)owner'en" + +#: src/access.cpp:49 +msgid "Allowed to (de)owner users" +msgstr "Kan gebruikers (de)owner'en" + +#: src/access.cpp:52 +msgid "Allowed to (de)protect him/herself" +msgstr "Kan zich/haarzelf (de)protect'en" + +#: src/access.cpp:51 +msgid "Allowed to (de)protect users" +msgstr "Kan gebruikers (de)protect'en" + +#: src/access.cpp:59 +msgid "Allowed to (de)voice him/herself" +msgstr "Kan zich/haarzelf (de)voice'en" + +#: src/access.cpp:58 +msgid "Allowed to (de)voice users" +msgstr "Kan gebruikers (de)voice'en" + +#: src/access.cpp:27 +msgid "Allowed to assign/unassign a bot" +msgstr "Kan bots toewijzen/verwijderen" + +#: src/access.cpp:34 +msgid "Allowed to ban users" +msgstr "Kan gebruikers bannen" + +#: src/access.cpp:56 +msgid "Allowed to change channel topics" +msgstr "Kan de topic wijzigen" + +#: src/access.cpp:41 +msgid "Allowed to get full INFO output" +msgstr "Kan de volledige INFO zien" + +#: src/access.cpp:36 +msgid "Allowed to issue commands restricted to channel founders" +msgstr "Kan commando's voorbehouden aan stichters uitvoeren" + +#: src/access.cpp:33 +msgid "Allowed to modify channel badwords list" +msgstr "Kan de slechtewoordenlijst aanpassen" + +#: src/access.cpp:24 +msgid "Allowed to modify the access list" +msgstr "Kan de toegangslijst aanpassen" + +#: src/access.cpp:44 +msgid "Allowed to read channel memos" +msgstr "Kan kanaalmemo's lezen" + +#: src/access.cpp:54 +msgid "Allowed to set channel settings" +msgstr "Kan kanaalinstellingen wijzigen" + +#: src/access.cpp:57 +msgid "Allowed to unban users" +msgstr "Kan bans op gebruikers verwijderen" + +#: src/access.cpp:37 +msgid "Allowed to use GETKEY command" +msgstr "Kan het GETKEY commando gebruiken" + +#: src/access.cpp:53 +msgid "Allowed to use SAY and ACT commands" +msgstr "Kan de SAY en ACT commando's gebruiken" + +#: src/access.cpp:35 +msgid "Allowed to use fantasy commands" +msgstr "Kan fantasie commando's gebruiken" + +#: src/access.cpp:26 +msgid "Allowed to use the AKICK command" +msgstr "Kan het AKICK commando gebruiken" + +#: src/access.cpp:42 +msgid "Allowed to use the INVITE command" +msgstr "Kan het INVITE commando gebruiken" + +#: src/access.cpp:43 +msgid "Allowed to use the KICK command" +msgstr "Kan het KICK commando gebruiken" + +#: src/access.cpp:45 +msgid "Allowed to use the MODE command" +msgstr "Kan het MODE commando gebruiken" + +#: src/access.cpp:25 +msgid "Allowed to view the access list" +msgstr "Kan de toegangslijst bekijken" + +#: modules/commands/gl_global.cpp:42 +#, c-format +msgid "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." +msgstr "" +"Stelt Administrators in staat om berichten te versturen\n" +"naar alle gebruikers op het netwerk. Berichten zullen\n" +"verstuurd worden vanaf de nick %s." + +#: modules/commands/os_mode.cpp:133 +msgid "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." +msgstr "" +"Stelt Services Operators in staat om de modes van elk willekeurig\n" +"kanaal te wijzigen. De parameters zijn dezelfde als bij een\n" +"standaard /MODE commando. Anderzijds, CLEAR mag opgegeven\n" +"worden om alle modes weg te halen. Indien CLEAR ALL is opgegeven,\n" +"dan zullen alle modes, inclusief gebruikersstatus modes, weggehaald\n" +"worden." + +#: modules/commands/os_mode.cpp:173 +msgid "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." +msgstr "" +"Stelt Services Operators in staat om de gebruikersmodes van\n" +"iemand aan te passen. De parameters zijn dezelfde als bij\n" +"het standaard /MODE commando." + +#: modules/commands/bs_bot.cpp:352 +msgid "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." +msgstr "" +"Stelt Services Operators in staat om bots te maken, te\n" +"wijzigen en te verwijderen, die gebruikers op hun eigen kanaal\n" +"kunnen gebruiken.\n" +" \n" +"BOT ADD voegt een bot toe met de gegeven nickname,\n" +"ident, host en echte naam. De parameters worden\n" +"niet nagekeken of ze correct zijn, dus pas op.\n" +" \n" +"BOT CHANGE kan de nick, ident, host of echte\n" +"naam van een bot veranderen zonder deze (en de data die\n" +"met de bot geassocieerd is) te moeten verwijderen.\n" +" \n" +"BOT DEL verwijdert de gegeven bot van de botlijst.\n" +" \n" +"Let op: Je kan geen bot maken met een nick die\n" +"geregistreerd is. Als een ongeregistreerde gebruiker\n" +"de nick momenteel in gebruik heeft zal de betreffende\n" +"gebruiker worden gekillt." + +#: modules/commands/os_oline.cpp:56 +msgid "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." +msgstr "" +"Stelt Services Operators in staat om Opervlaggen te geven\n" +"aan een gebruiker. Vlaggen moeten worden vooraf\n" +"gegaan door een \"+\" of een \"-\". Om alle vlaggen te verwijderen\n" +"kun je simpelweg een \"-\" typen in de plaats van de vlaggen." + +#: modules/commands/os_ignore.cpp:370 +msgid "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." +msgstr "" +"Stelt Services Operators in staat de Services een nick\n" +"of masker voor een bepaalde tijd of tot de volgende herstart te\n" +"laten negeren. Standaard wordt de tijd gegeven in seconden.\n" +"Je kan de tijd opgegeven met behulp van eenheden. Geldige eenheden\n" +"zijn: s voor seconden, m voor minuten, h voor uren\n" +"en d voor dagen. Combinaties hiervan zijn niet toegestaan.\n" +"Om Services iemand permanent te laten negeren kun je 0 opgeven als tijd.\n" +"Als je een masker toevoegt moet deze in volgend formaat zijn:\n" +"nick!user@host, iets anders wordt als een nick beschouwd.\n" +"Jokertekens zijn toegestaan.\n" +" \n" +"IRC operators zullen niet genegeerd worden, zelfs al komen\n" +"ze overeen met een masker uit de lijst." + +#: modules/commands/os_akill.cpp:420 +msgid "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Stelt Services Operators in staat de AKILL lijst te beheren.\n" +"Als een gebruiker die overeenkomt met een AKILL mask probeert\n" +"te verbinden zullen Services een KILL voor die gebruiker door-\n" +"voeren en, als het netwerk dit ondersteund, zullen alle servers\n" +"geïnstrueerd worden een ban voor het betreffende masker\n" +"toe te voegen.\n" +" \n" +"AKILL ADD voegt het gegeven masker toe aan de AKILL\n" +"lijst met de gegeven reden, die moet worden gegeven.\n" +"Masker kan in de volle nick!ident@host#realname formaat zijn,\n" +"maar ident@host word ook aanvaard. Als een realname word\n" +"word opgegeven moet de reden voorafgegaan worden door\n" +"een dubbele punt (:).\n" +"verlooptijd word gespecificeerd als een getal waarachter d\n" +"(dagen), h (uur), of m (minuten) geplaatst word. Combinaties\n" +"(zoals 1h30m) zijn niet toegestaan. Als er geen d, h of m word\n" +"meegegeven, is het standaard dagen (dus +30 zelfstandig betekent\n" +"30 dagen). Om een AKILL die niet verloopt toe te voegen, gebruik je\n" +"+0. Als het masker die toegevoegd moet worden met een + begint,\n" +"is een verlooptijd verplicht, zelfs als die overeenkomt met de\n" +"standaard verlooptijd. De huidige standaard verlooptijd voor een\n" +"AKILL kan gevonden worden met het STATS AKILL commando." + +#: modules/commands/os_sxline.cpp:436 +msgid "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." +msgstr "" +"Stelt Services Operators in staat de SNLINE lijst te beheren.\n" +"Als een gebruiker probeert te verbinden met een realname die\n" +"overeenkomt met een vermelding op de lijst, dan zal Services\n" +"die gebruiker verwijderen." + +#: modules/commands/os_sxline.cpp:670 +msgid "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." +msgstr "" +"Stelt Services Operators in staat de SQLINE lijst te beheren.\n" +"Als een gebruiker probeert te verbinden met een nick die\n" +"overeenkomt met een vermelding op de lijst, dan zal Services\n" +"die gebruiker verwijderen.\n" +"Indien de eerste karakter van een masker begint met een #,\n" +"dan zal Services het gebruik van overeenkomende kanalen\n" +"verbieden. Als het masker een reguliere expressie is, dan zal\n" +"deze expressie ook op kanalen van toepassing zijn." + +#: modules/commands/os_session.cpp:551 +msgid "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." +msgstr "" +"Stelt Services Operators in staat de uitzonderingenlijst voor sessie-\n" +"limieten te beheren. Door deze lijst kunnen specifieke computersystemen,\n" +"zoals shellservers, toegestaan worden een hoger aantal simultane\n" +"verbindingen te hebben dan normaal mag. Zodra een host zijn sessie-\n" +"limiet bereikt heeft, worden alle gebruikers ervan gekilld. Voor ze gekilld\n" +"worden, worden ze op de hoogte gebracht van de sessielimietering via\n" +"een notice die kan geconfigureerd worden." + +#: modules/commands/os_session.cpp:270 +msgid "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." +msgstr "" +"Laat Services Operators toe de sessielijst te bekijken.\n" +" \n" +"SESSION LIST geeft hosts weer met tenminste drempel\n" +"sessies weer. Deze drempel moet een nummer groter dan 1 zijn.\n" +"Dit is om te voorkomen dat je per ongeluk het grote aantal\n" +"hosts met maar 1 sessie weergeeft.\n" +" \n" +"SESSION VIEW geeft gedetailleerde informatie weer over een\n" +"specifieke host, inclusief het huidige aantal sessies en de\n" +"sessielimiet. De host waarde mag geen jokertekens bevatten.\n" +" \n" +"Bekijk de EXCEPTION help voor meer informatie over sessie-\n" +"limiteringen en hoe sessielimieten in te stellen voor\n" +"specifieke hosts en groepen daarvan." + +#: modules/commands/cs_topic.cpp:193 +msgid "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do " +"not have\n" +"the TOPIC privilege." +msgstr "" +"Maakt het mogelijk de topic van een kanaal aan te passen en te beheren.\n" +"Het SET commando verandert de topic van het kanaal naar het opgegeven\n" +"topic, of verwijdert deze indien geen topic is opgegeven.\n" +"Het APPEND commando voegt de gegeven topic toe aan de reeds bestaande\n" +"topic.\n" +" \n" +"LOCK en UNLOCK kunnen gebruikt worden om de topic te vergrendelen\n" +"of ontgrendelen. Wanneer de topic vergrendeld is kan de topic niet " +"gewijzigd\n" +"worden door gebruikers die niet beschikken over het TOPIC privilege." + +#: modules/commands/os_kick.cpp:62 +#, c-format +msgid "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" +msgstr "" +"Stelt medewerkers in staat om een gebruiker van elk\n" +"kanaal te kicken. De parameters zijn dezelfde als die van\n" +"het standaard /KICK commando. Het kick-bericht zal de nick\n" +"van de IRCop die het KICK commando uitvoert vooraan bevatten.\n" +"Bijvoorbeeld:\n" +" \n" +"*** SpamMan werd gekickt uit kanaal #mijn_kanaal door %s (Alcan (Flood))" + +#: modules/commands/cs_set.cpp:33 +msgid "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" +msgstr "" +"Stelt de kanaalstichter in staat om verschillende kanaal-\n" +"opties en andere informatie in te stellen.\n" +" \n" +"Beschikbare opties:" + +#: modules/commands/os_oper.cpp:250 +msgid "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." +msgstr "" +"Laat je toe Services Operators te wijzigen en bekijken.\n" +"Let op dat operators verwijderd via dit commando en\n" +"die nog steeds in het configuratiebestand staan, niet\n" +"permanent verwijderd zijn." + +#: modules/commands/os_config.cpp:127 +msgid "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" +msgstr "" +"Laat je toe configuratie-instellingen te wijzigen en bekijken.\n" +"Instellingen gewijzigd via dit commando zijn tijdelijk en\n" +"worden niet bewaard in het configuratiebestand, en zullen\n" +"verloren gaan wanneer Services afgesloten worden, herstart,\n" +"of de configuratie herladen wordt.\n" +" \n" +"Voorbeeld:\n" +" MODIFY nickserv forcemail no" + +#: modules/commands/ns_set.cpp:992 +msgid "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." +msgstr "" +"Laat je toe te bepalen hoe Services berichten naar de gegeven\n" +"gebruiker stuurt. Als MSG ingesteld is zal Services privé-\n" +"berichten gebruiken, anders zullen ze notice's gebruiken." + +#: modules/commands/ns_set.cpp:966 +#, c-format +msgid "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." +msgstr "" +"Laat je toe te bepalen hoe Services berichten naar jou\n" +"stuurt. Als %s ingesteld is, dan zal Services privé-\n" +"berichten gebruiken, anders zullen ze notice's gebruiken." + +#: modules/commands/ms_ignore.cpp:113 +msgid "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." +msgstr "" +"Laat je toe om gebruikers via hun nick of masker te negeren,\n" +"zodat ze geen memo naar jou of een kanaal kunnen sturen.\n" +"Als iemand op deze memo-negeerlijst jou of een kanaal een\n" +"memo probeert te sturen zal hen niet verteld worden dat je\n" +"hen negeert." + +#: modules/commands/os_kill.cpp:48 +msgid "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." +msgstr "" +"Laat je toe een gebruiker te killen van het netwerk.\n" +"Parameters zijn dezelfde als voor een standaard /KILL\n" +"commando." + +#: modules/commands/ns_info.cpp:252 +#, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Stelt je in staat te voorkomen dat bepaalde informatie getoont wordt\n" +"wanneer iemand een %s INFO doet op de nick. Je kan\n" +"het e-mailadres (EMAIL), laatst geziene ident@host (USERMASK),\n" +"de Services toegangsniveau (STATUS) en het laatste quit\n" +"bericht (QUIT) verbergen. De tweede parameter geeft aan of\n" +"de informatie moet getoont (OFF) of verborgen (ON) worden." + +#: modules/commands/ns_info.cpp:223 +#, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Stelt je in staat te voorkomen dat bepaalde informatie getoont wordt\n" +"wanneer iemand een %s INFO doet op je nick. Je kan\n" +"het e-mailadres (EMAIL), laatst geziene ident@host (USERMASK),\n" +"je Services toegangsniveau (STATUS) en het laatste quit\n" +"bericht (QUIT) verbergen. De tweede parameter geeft aan of\n" +"de informatie moet getoont (OFF) of verborgen (ON) worden." + +#: modules/commands/bs_info.cpp:118 +#, c-format +msgid "Allows you to see %s information about a channel or a bot" +msgstr "Stelt je in staat %s informatie te zien over een kanaal of bot" + +#: modules/commands/bs_info.cpp:108 +#, c-format +msgid "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." +msgstr "" +"Stelt je in staat %s informatie te zien over een kanaal of\n" +"een bot. Als het parameter een kanaal is krijg je bijvoorbeeld\n" +"informatie over geactiveerde kickers. Als het parameter een\n" +"nick is krijg je informatie over een bot, zoals de tijd waarop\n" +"deze gemaakt is of op hoeveel kanalen deze staat." + +#: modules/commands/cs_xop.cpp:567 +msgid "" +"Alternative methods of modifying channel access lists are\n" +"available. " +msgstr "" +"Alternatieve methodes voor het beheren en aanpassen\n" +"van de kanaaltoegangslijsten zijn beschikbaar." + +#: modules/commands/hs_request.cpp:191 +msgid "Approve the requested vHost of a user" +msgstr "Keur de aangevraagde vHost van een gebruiker goed" + +#: modules/commands/ns_drop.cpp:68 +msgid "As a Services Operator, you may drop any nick." +msgstr "Als Services Operator kan je elke nickregistratie verwijderen." + +#: modules/commands/bs_assign.cpp:19 +msgid "Assigns a bot to a channel" +msgstr "Wijs een bot toe aan een kanaal" + +#: modules/commands/bs_assign.cpp:78 +msgid "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." +msgstr "" +"Wijst een opgegeven bot toe aan een kanaal.\n" +"Hierna kun je de bot voor het kanaal instellen zoals je\n" +"wil." + +#: data/chanserv.example.conf:1197 +msgid "Associate a URL with the channel" +msgstr "Koppel een URL aan het kanaal" + +#: data/nickserv.example.conf:594 +msgid "Associate a URL with this account" +msgstr "Koppel een URL aan dit account" + +#: data/nickserv.example.conf:593 +msgid "Associate a URL with your account" +msgstr "Koppel een URL aan jouw account" + +#: modules/commands/greet.cpp:83 +msgid "Associate a greet message with your nickname" +msgstr "Koppel een begroeting aan je nick" + +#: data/chanserv.example.conf:1198 +msgid "Associate an E-mail address with the channel" +msgstr "Koppel een e-mailadres aan het kanaal" + +#: modules/commands/ns_set.cpp:452 +msgid "Associate an E-mail address with your nickname" +msgstr "Koppel een e-mailadres aan jouw nick" + +#: modules/commands/os_info.cpp:101 +msgid "Associate oper info with a nick or channel" +msgstr "Koppel oper informatie aan een nick of kanaal" + +#: modules/commands/ns_set.cpp:558 +msgid "Associates the given E-mail address with the nickname." +msgstr "Koppel het opgegeven e-mailadres aan de nick" + +#: modules/commands/ns_set.cpp:533 +msgid "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." +msgstr "" +"Koppel het opgegeven e-mailadres aan jouw nick. Dit adres\n" +"zal worden weergegeven wanneer iemand informatie over je\n" +"nick opvraagt met het INFO commando." + +#: modules/commands/ns_set.cpp:1315 +msgid "Auto-op" +msgstr "Auto-op" + +#: modules/commands/cs_akick.cpp:374 +#, c-format +msgid "Autokick list for %s:" +msgstr "Autokicklijst voor %s:" + +#: src/access.cpp:29 +msgid "Automatic channel operator status upon join" +msgstr "Automatische kanaaloperator status bij het betreden" + +#: src/access.cpp:28 +msgid "Automatic halfop upon join" +msgstr "Automatische halfoperator status bij het betreden" + +#: src/access.cpp:30 +msgid "Automatic owner upon join" +msgstr "Automatische eigenaar status bij het betreden" + +#: src/access.cpp:31 +msgid "Automatic protect upon join" +msgstr "Automatische bescherming status bij het betreden" + +#: src/access.cpp:32 +msgid "Automatic voice on join" +msgstr "Automatische voice status bij het betreden" + +#: modules/commands/os_oper.cpp:196 +#, c-format +msgid "Available commands for %s:" +msgstr "Beschikbare commando's voor %s:" + +#: modules/commands/os_oper.cpp:175 +msgid "Available opertypes:" +msgstr "Beschikbare opertypes:" + +#: modules/commands/os_oper.cpp:218 +#, c-format +msgid "Available privileges for %s:" +msgstr "Beschikbare privileges voor %s:" + +#: modules/commands/cs_enforce.cpp:162 +msgid "BANS enforced by " +msgstr "BANS afgedwongen door " + +#: modules/commands/bs_kick.cpp:1121 modules/commands/bs_kick.cpp:1123 +#: modules/commands/bs_kick.cpp:1126 +msgid "Bad words kicker" +msgstr "Slechtewoordenkicker" + +#: modules/commands/bs_badwords.cpp:252 +#, c-format +msgid "Bad words list for %s:" +msgstr "Slechtewoordenlijst voor %s:" + +#: modules/commands/bs_badwords.cpp:364 +msgid "Bad words list is now empty." +msgstr "Slechtewoordenlijst is nu leeg." + +#: modules/commands/bs_set.cpp:129 +msgid "Ban expiry may not be longer than 1 day." +msgstr "Ban verlooptijd mag niet langer dan 1 dag zijn." + +#: modules/commands/cs_ban.cpp:140 modules/commands/cs_ban.cpp:175 +#, c-format +msgid "Ban on %s expires in %s." +msgstr "Ban op %s verloopt over %s." + +#: modules/commands/cs_info.cpp:60 +msgid "Ban type" +msgstr "Bantype" + +#: modules/commands/cs_set.cpp:174 +#, c-format +msgid "Ban type for channel %s is now #%d." +msgstr "Ban type voor kanaal %s is nu #%d." + +#: modules/commands/cs_ban.cpp:39 +msgid "Bans a given nick or mask on a channel" +msgstr "Ban een opgegeven nick of masker op een kanaal" + +#: modules/commands/cs_ban.cpp:227 +msgid "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." +msgstr "" +"Bant de gegeven nick of masker op een kanaal. Een optionele\n" +"verlooptijd mag opgegeven worden zodat de ban automatisch\n" +"verwijderd wordt wanneer de tijd verstreken is.\n" +" \n" +"Standaard is dit gelimiteerd tot AOP's of diegenen met\n" +"niveau 5 of hoger op het kanaal. Kanaalstichters mogen\n" +"maskers opgeven." + +#: modules/commands/cs_enforce.cpp:166 +#, c-format +msgid "Bans enforced on %s." +msgstr "Bans afgedwongen op %s." + +#: modules/commands/bs_kick.cpp:1131 modules/commands/bs_kick.cpp:1133 +#: modules/commands/bs_kick.cpp:1136 +msgid "Bolds kicker" +msgstr "Vetkicker" + +#: modules/commands/bs_bot.cpp:26 modules/commands/bs_bot.cpp:175 +#, c-format +msgid "Bot %s already exists." +msgstr "Bot %s bestaat al." + +#: include/language.h:119 +#, c-format +msgid "Bot %s does not exist." +msgstr "Bot %s bestaat niet." + +#: modules/commands/bs_assign.cpp:71 modules/commands/bs_assign.cpp:246 +#, c-format +msgid "Bot %s has been assigned to %s." +msgstr "Bot %s toegewezen aan %s." + +#: modules/commands/bs_bot.cpp:228 +#, c-format +msgid "Bot %s has been changed to %s!%s@%s (%s)." +msgstr "Bot %s is veranderd in %s!%s@%s (%s)." + +#: modules/commands/bs_bot.cpp:262 +#, c-format +msgid "Bot %s has been deleted." +msgstr "Bot %s is verwijderd." + +#: modules/commands/bs_assign.cpp:63 modules/commands/bs_assign.cpp:241 +#, c-format +msgid "Bot %s is already assigned to channel %s." +msgstr "Bot %s is al toegewezen aan kanaal %s." + +#: modules/commands/bs_kick.cpp:832 +#, c-format +msgid "Bot will kick ops on channel %s." +msgstr "Bot zal ops kicken op kanaal %s." + +#: modules/commands/bs_kick.cpp:897 +#, c-format +msgid "Bot will kick voices on channel %s." +msgstr "Bot zal voices kicken op kanaal %s." + +#: modules/commands/bs_kick.cpp:824 +#, c-format +msgid "Bot won't kick ops on channel %s." +msgstr "Bot zal geen ops kicken op kanaal %s." + +#: modules/commands/bs_kick.cpp:889 +#, c-format +msgid "Bot won't kick voices on channel %s." +msgstr "Bot zal geen voices kicken op kanaal %s." + +#: modules/commands/bs_bot.cpp:118 +#, c-format +msgid "Bot %s is not changeable." +msgstr "Bot %s is niet te wijzigen." + +#: modules/commands/bs_bot.cpp:254 +#, c-format +msgid "Bot %s is not deletable." +msgstr "Bot %s is niet te verwijderen." + +#: modules/commands/bs_set.cpp:141 +#, c-format +msgid "Bot bans will automatically expire after %s." +msgstr "Bot bans verlopen automatisch na %s." + +#: modules/commands/bs_set.cpp:139 +msgid "Bot bans will no longer automatically expire." +msgstr "Bot bans zullen niet langer automatisch verlopen." + +#: modules/commands/bs_bot.cpp:46 modules/commands/bs_bot.cpp:138 +#, c-format +msgid "Bot hosts may only be %d characters long." +msgstr "Bot hosts mogen maximaal %d karakters bevatten." + +#: modules/commands/bs_bot.cpp:64 modules/commands/bs_bot.cpp:167 +msgid "Bot hosts may only contain valid host characters." +msgstr "Bot hosts mogen alleen geldige host-karakters bevatten." + +#: modules/commands/bs_bot.cpp:40 modules/commands/bs_bot.cpp:132 +#, c-format +msgid "Bot idents may only be %d characters long." +msgstr "Bot idents mogen maximaal %d karakters bevatten." + +#: modules/commands/bs_bot.cpp:58 modules/commands/bs_bot.cpp:161 +msgid "Bot idents may only contain valid ident characters." +msgstr "Bot idents mogen alleen geldige ident-karakters bevatten." + +#: include/language.h:121 +#, c-format +msgid "Bot is not on channel %s." +msgstr "Bot is niet op kanaal %s." + +#: modules/commands/bs_botlist.cpp:51 +msgid "Bot list:" +msgstr "Botlijst:" + +#: modules/commands/bs_info.cpp:87 +msgid "Bot nick" +msgstr "Bot nick" + +#: modules/commands/bs_bot.cpp:34 modules/commands/bs_bot.cpp:126 +#, c-format +msgid "Bot nicks may only be %d characters long." +msgstr "Bot nicks mogen maximaal %d karakters bevatten." + +#: modules/commands/bs_bot.cpp:52 modules/commands/bs_bot.cpp:155 +msgid "Bot nicks may only contain valid nick characters." +msgstr "Bot nicks mogen alleen geldige nick-karakters bevatten." + +#: modules/commands/bs_kick.cpp:225 +#, c-format +msgid "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." +msgstr "" +"Bot zal nu kicken voor %s, en zal een ban plaatsen\n" +"na %d kicks op dezelfde gebruiker." + +#: modules/commands/bs_kick.cpp:228 +#, c-format +msgid "Bot will now kick for %s." +msgstr "Bot zal nu kicken voor %s." + +#: modules/commands/bs_kick.cpp:416 +#, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." +msgstr "" +"Bot zal nu kicken voor hoofdletters (bij minstens\n" +"%d karakters en %d%% van het gehele bericht), en zal\n" +"een ban plaatsen na %d kicks op dezelfde gebruiker." + +#: modules/commands/bs_kick.cpp:420 +#, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." +msgstr "" +"Bot zal nu kicken voor hoofdletters (bij minstens\n" +"%d karakters en %d%% van het gehele bericht)." + +#: modules/commands/bs_kick.cpp:551 +#, c-format +msgid "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." +msgstr "" +"Bot zal nu kicken voor flood (%d regels in %d seconden),\n" +"en zal een ban plaatsen na %d kicks op dezelfde gebruiker." + +#: modules/commands/bs_kick.cpp:554 +#, c-format +msgid "Bot will now kick for flood (%d lines in %d seconds)." +msgstr "Bot zal nu kicken voor flood (%d regels in %d seconden)." + +#: modules/commands/bs_kick.cpp:677 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Bot zal nu kicken voor herhalingen (gebruikers die %d maal\n" +"hetzelfde herhalen), en zal een ban plaatsen na %d\n" +"kicks op dezelfde gebruiker." + +#: modules/commands/bs_kick.cpp:687 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." +msgstr "" +"Bot zal nu kicken voor herhalingen (gebruikers die %d maal\n" +"hetzelfde herhalen)." + +#: modules/commands/bs_kick.cpp:673 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Bot zal nu kicken voor herhalingen (gebruikers die %d maal\n" +"hetzelfde herhalen), en zal een ban plaatsen na %d\n" +"kicks op dezelfde gebruiker." + +#: modules/commands/bs_kick.cpp:684 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." +msgstr "" +"Bot zal nu kicken voor herhalingen (gebruikers die %d maal\n" +"hetzelfde herhalen)." + +#: modules/commands/bs_kick.cpp:239 +#, c-format +msgid "Bot won't kick for %s anymore." +msgstr "Bot zal niet meer kicken voor %s." + +#: modules/commands/bs_kick.cpp:426 +msgid "Bot won't kick for caps anymore." +msgstr "Bot zal niet meer kicken voor hoofdletters." + +#: modules/commands/bs_kick.cpp:559 +msgid "Bot won't kick for flood anymore." +msgstr "Bot zal niet meer kicken voor flood." + +#: modules/commands/bs_kick.cpp:694 +msgid "Bot won't kick for repeats anymore." +msgstr "Bot zal niet meer kicken voor herhalingen." + +#: modules/commands/cs_access.cpp:472 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_session.cpp:514 +msgid "By" +msgstr "Door" + +#: modules/commands/os_info.cpp:104 +msgid "CLEAR target" +msgstr "CLEAR doel" + +#: modules/commands/cs_seen.cpp:119 +msgid "CLEAR time" +msgstr "CLEAR tijd" + +#: modules/commands/ms_cancel.cpp:19 +msgid "Cancel the last memo you sent" +msgstr "Annuleer je laatst verzonden memo" + +#: modules/commands/cs_drop.cpp:19 +msgid "Cancel the registration of a channel" +msgstr "Annuleer een kanaalregistratie" + +#: modules/commands/ns_drop.cpp:20 +msgid "Cancel the registration of a nickname" +msgstr "Annuleer een nickregistratie" + +#: modules/commands/ms_cancel.cpp:84 +msgid "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." +msgstr "" +"Annuleert de laatste memo die je gestuurd hebt aan de gegeven\n" +"nick of kanaal, indien deze nog niet gelezen is op het moment\n" +"dat je dit commando gebruikt." + +#: modules/commands/cs_clone.cpp:149 +#, c-format +msgid "Cannot clone channel %s to itself!" +msgstr "Kan kanaal %s niet naar zichzelf clonen!" + +#: modules/commands/ns_register.cpp:332 +msgid "Cannot send mail now; please retry a little later." +msgstr "Onmogelijk e-mail te sturen; probeer later opnieuw." + +#: modules/commands/bs_kick.cpp:1141 modules/commands/bs_kick.cpp:1143 +#: modules/commands/bs_kick.cpp:1146 +msgid "Caps kicker" +msgstr "Hoofdletterskicker" + +#: modules/commands/os_shutdown.cpp:34 +msgid "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." +msgstr "" +"Zorgt ervoor dat Services meteen afsluiten: databases worden\n" +"niet opgeslagen. Dit commando moet niet gebruikt worden\n" +"tenzij schade aan de kopies van de databases in het geheugen\n" +"wordt gevreesd en ze niet moeten worden opgeslagen." + +#: modules/commands/os_reload.cpp:47 +msgid "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." +msgstr "" +"Zorgt ervoor dat Services het configuratiebestand opnieuw\n" +"inladen. Let er wel op dat sommige instellingen nog steeds\n" +"vereisen dat de Services opnieuw gestart worden (bijvoorbeeld\n" +"Services' nicknames, activatie van de sessielimiet, etc.)." + +#: modules/commands/os_shutdown.cpp:62 +msgid "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." +msgstr "" +"Zorgt ervoor dat Services alle databases opslaat en dan\n" +"zichzelf opnieuw opstart." + +#: modules/commands/os_shutdown.cpp:89 +msgid "Causes Services to save all databases and then shut down." +msgstr "Zorgt ervoor dat Services alle databases opslaat en dan afsluit." + +#: modules/commands/os_update.cpp:34 +msgid "" +"Causes Services to update all database files as soon as you\n" +"send the command." +msgstr "" +"Zorgt ervoor dat Services de databases bijwerken zodra je\n" +"dit commando verstuurt." + +#: modules/commands/ns_cert.cpp:246 +#, c-format +msgid "Certificate list for %s:" +msgstr "Certificaatlijst voor %s:" + +#: modules/commands/cs_set.cpp:528 modules/commands/cs_set.cpp:570 +msgid "ChanServ is required to enable persist on this network." +msgstr "ChanServ is vereist om PERSIST te activeren op dit netwerk." + +#: modules/commands/os_mode.cpp:19 +msgid "Change channel modes" +msgstr "Wijzig kanaalmodes" + +#: modules/commands/ns_set.cpp:905 +msgid "Change the communication method of Services" +msgstr "Verander de communicatiemethode van Services" + +#: modules/commands/os_mode.cpp:146 +msgid "Change user modes" +msgstr "Wijzig gebruikersmodes" + +#: modules/commands/os_mode.cpp:161 +#, c-format +msgid "Changed usermodes of %s to %s." +msgstr "Gebruikersmodes van %s veranderd naar %s." + +#: modules/commands/ns_set.cpp:411 +msgid "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." +msgstr "" +"Verandert de weergegeven nick van de nick-groep in Services.\n" +"De nieuwe weergave MOET een nick in de groep zijn." + +#: modules/commands/ns_set.cpp:387 +msgid "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." +msgstr "" +"Verandert de weergegeven nick van je nick-groep in Services.\n" +"De nieuwe weergave MOET een nick in je groep zijn." + +#: modules/commands/cs_set.cpp:324 +msgid "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." +msgstr "" +"Verandert de stichter van een kanaal. De nieuwe nick moet\n" +"een geregistreerde nick zijn." + +#: modules/commands/ns_set.cpp:884 +msgid "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Verandert de taal die Services gebruikt wanneer deze een\n" +"bericht naar de gebruiker stuurt (bijvoorbeeld wanneer deze antwoord\n" +"op een commando dat werd verzonden). taal moet gekozen\n" +"worden uit de volgende lijst van ondersteunde talen:" + +#: modules/commands/ns_set.cpp:848 +msgid "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Verandert de taal die Services gebruikt wanneer deze een\n" +"bericht naar jou stuurt (bijvoorbeeld wanneer deze antwoord\n" +"op een commando dat je hebt verzonden). taal moet gekozen\n" +"worden uit de volgende lijst van ondersteunde talen:" + +#: modules/commands/ns_set.cpp:227 +msgid "Changes the password used to identify as the nick's owner." +msgstr "" +"Verandert het wachtwoord dat gebruikt wordt om te identificeren\n" +"als de eigenaar van de nick." + +#: modules/commands/ns_set.cpp:161 +msgid "" +"Changes the password used to identify you as the nick's\n" +"owner." +msgstr "" +"Verandert het wachtwoord dat je gebruikt om je te identificeren\n" +"als de eigenaar van de nick." + +#: modules/commands/cs_set.cpp:1017 +msgid "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." +msgstr "" +"Verandert de opvolger van een kanaal. Als de nick van de\n" +"stichter verloopt of de registratie ervan wordt geannuleerd\n" +"terwijl het kanaal nog geregistreerd is, dan wordt de opvolger\n" +"de nieuwe stichter van het kanaal. De opvolgers nick moet een\n" +"geregistreerde nick zijn. Als er geen opvolger ingesteld staat,\n" +"dan zal de eerste nick op de toegangslijst (met de hoogste\n" +"toegangsrechten, indien van toepassing) de nieuwe stichter\n" +"worden, maar als de toegangslijst leeg is, dan zal het kanaal\n" +"verlopen." + +#: modules/commands/ns_alist.cpp:48 modules/commands/ns_ajoin.cpp:100 +msgid "Channel" +msgstr "Kanaal" + +#: include/language.h:84 +#, c-format +msgid "Channel %s doesn't exist." +msgstr "Kanaal %s bestaat niet." + +#: modules/commands/cs_drop.cpp:63 +#, c-format +msgid "Channel %s has been dropped." +msgstr "Kanaalregistratie voor %s werd verwijderd." + +#: modules/commands/cs_getkey.cpp:43 +#, c-format +msgid "Channel %s has no key." +msgstr "Kanaal %s heeft geen sleutel." + +#: modules/commands/cs_register.cpp:47 +#, c-format +msgid "Channel %s is already registered!" +msgstr "Kanaal %s is al geregistreerd!" + +#: modules/commands/os_forbid.cpp:524 +#, c-format +msgid "Channel %s is forbidden by %s: %s" +msgstr "Kanaal %s is verboden door %s: %s" + +#: modules/commands/os_forbid.cpp:526 +#, c-format +msgid "Channel %s is forbidden." +msgstr "Kanaal %s is verboden." + +#: modules/commands/cs_set.cpp:580 +#, c-format +msgid "Channel %s is no longer persistent." +msgstr "Kanaal %s is niet langer permanent." + +#: modules/commands/cs_set.cpp:542 +#, c-format +msgid "Channel %s is now persistent." +msgstr "Kanaal %s is nu permanent." + +#: modules/commands/cs_suspend.cpp:180 +#, c-format +msgid "Channel %s is now released." +msgstr "Kanaal %s is weer vrijgegeven." + +#: modules/commands/cs_suspend.cpp:125 +#, c-format +msgid "Channel %s is now suspended." +msgstr "Kanaal %s is nu geschorst." + +#: include/language.h:83 +#, c-format +msgid "Channel %s isn't registered." +msgstr "Kanaal %s is niet geregistreerd." + +#: modules/commands/cs_suspend.cpp:172 +#, c-format +msgid "Channel %s isn't suspended." +msgstr "Kanaal %s is niet geschorst." + +#: modules/commands/cs_register.cpp:68 +#, c-format +msgid "Channel %s registered under your account: %s" +msgstr "Kanaal %s is nu geregistreerd op jouw account: %s" + +#: modules/commands/cs_set.cpp:1078 +#, c-format +msgid "Channel %s will expire." +msgstr "Kanaal %s zal verlopen." + +#: modules/commands/cs_set.cpp:1072 +#, c-format +msgid "Channel %s will not expire." +msgstr "Kanaal %s zal niet verlopen." + +#: modules/commands/cs_xop.cpp:475 +#, c-format +msgid "Channel %s %s list has been cleared." +msgstr "Kanaal %s %s lijst is leeggemaakt." + +#: modules/commands/cs_access.cpp:486 modules/commands/cs_flags.cpp:361 +#, c-format +msgid "Channel %s access list has been cleared." +msgstr "Kanaal %s toegangslijst is leeggemaakt." + +#: modules/commands/cs_akick.cpp:428 +#, c-format +msgid "Channel %s akick list has been cleared." +msgstr "Kanaal %s autokicklijst is leeggemaakt." + +#: modules/commands/cs_mode.cpp:444 +#, c-format +msgid "Channel %s has no mode locks." +msgstr "Kanaal %s heeft geen vergrendelde modes." + +#: include/language.h:82 +#, c-format +msgid "Channel %s is currently suspended." +msgstr "Kanaal %s is momenteel geschorst." + +#: include/language.h:101 +#, c-format +msgid "Channel %s is not a valid channel." +msgstr "Kanaal %s is geen geldig kanaal." + +#: modules/commands/os_list.cpp:70 +msgid "Channel list:" +msgstr "Kanalenlijst:" + +#: modules/extra/stats/cs_fantasy_stats.cpp:148 +#, c-format +msgid "Channel stats for %s on %s:" +msgstr "Kanaalstatistieken voor %s op %s:" + +#: modules/commands/cs_access.cpp:142 modules/commands/cs_flags.cpp:97 +#: modules/commands/cs_xop.cpp:139 +msgid "Channels may not be on access lists." +msgstr "Kanalen mogen niet op de toegangslijst staan." + +#: modules/commands/ns_alist.cpp:114 +#, c-format +msgid "Channels that %s has access on:" +msgstr "Kanalen waar %s toegang op heeft:" + +#: modules/commands/os_stats.cpp:181 +#, c-format +msgid "Channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "Kanalen: %lu vermeldingen, %lu emmers, langste ketting is %d" + +#: modules/extra/stats/m_chanstats.cpp:517 +#: modules/extra/stats/m_chanstats.cpp:525 +msgid "Chanstats" +msgstr "Kanaalstatistieken" + +#: modules/extra/stats/m_chanstats.cpp:102 +#, c-format +msgid "Chanstats statistics are now disabled for %s" +msgstr "Chanstats statistieken zijn nu uitgeschakeld voor %s" + +#: modules/extra/stats/m_chanstats.cpp:51 +msgid "Chanstats statistics are now disabled for this channel." +msgstr "Chanstats statistieken zijn nu uitgeschakeld voor dit kanaal." + +#: modules/extra/stats/m_chanstats.cpp:104 +msgid "Chanstats statistics are now disabled for your nick." +msgstr "Chanstats statistieken zijn nu uitgeschakeld voor jouw nick." + +#: modules/extra/stats/m_chanstats.cpp:93 +#, c-format +msgid "Chanstats statistics are now enabled for %s" +msgstr "Chanstats statistieken zijn nu ingeschakeld voor %s" + +#: modules/extra/stats/m_chanstats.cpp:44 +msgid "Chanstats statistics are now enabled for this channel." +msgstr "Chanstats statistieken zijn nu ingeschakeld voor dit kanaal." + +#: modules/extra/stats/m_chanstats.cpp:95 +msgid "Chanstats statistics are now enabled for your nick." +msgstr "Chanstats statistieken zijn nu ingeschakeld voor jouw nick." + +#: modules/commands/cs_seen.cpp:367 +msgid "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." +msgstr "" +"Kijkt naar de laatste keer dat nick werd gezien bij het,\n" +"binnenkomen, verlaten of van nick veranderen, en vertelt je\n" +"wanneer en, afhankelijk van de kanaal of gebruikersinstellingen,\n" +"waar het was." + +#: modules/commands/ms_check.cpp:19 +msgid "Checks if last memo to a nick was read" +msgstr "Kijk of je laatste memo naar iemand al is gelezen" + +#: modules/commands/ms_check.cpp:69 +msgid "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." +msgstr "" +"Controleert of de _laatste_ memo die je naar nick gestuurd\n" +"hebt is gelezen of niet. Let wel op: dit werkt alleen met nicks,\n" +"niet met kanalen." + +#: modules/commands/os_info.cpp:227 +#, c-format +msgid "Cleared info from %s." +msgstr "Informatie verwijderd van %s." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1153 +#: modules/commands/bs_kick.cpp:1156 +msgid "Colors kicker" +msgstr "Kleurenkicker" + +#: modules/commands/cs_log.cpp:127 +msgid "Command" +msgstr "Commando" + +#: modules/commands/bs_kick.cpp:251 +msgid "Configures AMSG kicker" +msgstr "Configureert AMSG-kicker" + +#: modules/commands/bs_kick.cpp:287 +msgid "Configures badwords kicker" +msgstr "Configureert slechtewoordenkicker" + +#: modules/commands/bs_kick.cpp:326 +msgid "Configures bolds kicker" +msgstr "Configureert vetkicker" + +#: modules/commands/bs_kick.cpp:132 +msgid "Configures bot kickers. option can be one of:" +msgstr "Configureert bot kickers. optie kan zijn:" + +#: modules/commands/bs_set.cpp:19 +msgid "Configures bot options" +msgstr "Configureert bot opties" + +#: modules/commands/bs_set.cpp:32 +msgid "" +"Configures bot options.\n" +" \n" +"Available options:" +msgstr "" +"Configureert bot opties.\n" +" \n" +"Beschikbare opties:" + +#: modules/commands/bs_kick.cpp:360 +msgid "Configures caps kicker" +msgstr "Configureert hoofdletterskicker" + +#: modules/commands/cs_log.cpp:105 +msgid "Configures channel logging settings" +msgstr "Configureert kanaal log instellingen" + +#: modules/commands/bs_kick.cpp:456 +msgid "Configures color kicker" +msgstr "Configureert kleurenkicker" + +#: modules/commands/bs_kick.cpp:490 +msgid "Configures flood kicker" +msgstr "Configureert floodkicker" + +#: modules/commands/bs_kick.cpp:588 +msgid "Configures italics kicker" +msgstr "Configureert cursiefkicker" + +#: modules/commands/bs_kick.cpp:119 +msgid "Configures kickers" +msgstr "Configureert kickers" + +#: modules/commands/bs_kick.cpp:622 +msgid "Configures repeat kicker" +msgstr "Configureert herhalingskicker" + +#: modules/commands/bs_kick.cpp:723 +msgid "Configures reverses kicker" +msgstr "Configureert inverteringskicker" + +#: modules/commands/bs_set.cpp:90 +msgid "Configures the time bot bans expire in" +msgstr "Configureert wanneer bot bans verlopen" + +#: modules/commands/bs_kick.cpp:757 +msgid "Configures underlines kicker" +msgstr "Configureert onderlijningskicker" + +#: modules/commands/ns_register.cpp:21 +msgid "Confirm a passcode" +msgstr "Gebruik een bevestigingscode" + +#: modules/commands/cs_mode.cpp:733 +msgid "Control modes and mode locks on a channel" +msgstr "Beheer modes en vergrendelde modes op een kanaal" + +#: modules/commands/cs_entrymsg.cpp:239 +msgid "" +"Controls what messages will be sent to users when they join the channel." +msgstr "" +"Beheer welke berichten verstuurd worden naar gebruikers wanneer ze het " +"kanaal betreden." + +#: modules/commands/cs_clone.cpp:242 +msgid "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." +msgstr "" +"Kopiëert alle instellingen, toegangen, autokicks, enz. van kanaal naar het\n" +"doel kanaal. Als wat één van ACCESS, AKICK, BADWORDS of\n" +"LEVELS is, dan worden enkel de respectievelijke instellingen gekopiëerd.\n" +"Je moet de stichter zijn van zowel kanaal als doel." + +#: modules/commands/cs_clone.cpp:114 +msgid "Copy all settings from one channel to another" +msgstr "Kopiëer alle instellingen van het ene kanaal naar het andere" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/bs_info.cpp:57 +#: modules/commands/os_akill.cpp:358 +msgid "Created" +msgstr "Gemaakt" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_ignore.cpp:266 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_news.cpp:156 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_akill.cpp:358 +msgid "Creator" +msgstr "Door" + +#: modules/commands/os_sxline.cpp:180 +#, c-format +msgid "Current %s list:" +msgstr "Huidige %s lijst:" + +#: modules/commands/os_akill.cpp:323 +msgid "Current AKILL list:" +msgstr "Huidige AKILL lijst:" + +#: modules/commands/os_session.cpp:493 +msgid "Current Session Limit Exception list:" +msgstr "Huidige uitzonderingenlijst voor sessielimieten:" + +#: modules/commands/os_modinfo.cpp:116 +msgid "Current module list:" +msgstr "Huidige modulelijst:" + +#: modules/commands/os_stats.cpp:69 +#, c-format +msgid "Current number of AKILLs: %d" +msgstr "Huidig aantal AKILLs: %d" + +#: modules/commands/os_stats.cpp:89 +#, c-format +msgid "Current number of SNLINEs: %d" +msgstr "Huidig aantal SNLINEs: %d" + +#: modules/commands/os_stats.cpp:109 +#, c-format +msgid "Current number of SQLINEs: %d" +msgstr "Huidig aantal SQLINEs: %d" + +#: modules/commands/os_stats.cpp:138 +#, c-format +msgid "Current users: %d (%d ops)" +msgstr "Huidig aantal gebruikers: %d (%d ops)" + +#: modules/commands/os_oper.cpp:71 +msgid "DEL oper" +msgstr "DEL oper" + +#: modules/commands/os_info.cpp:103 +msgid "DEL target info" +msgstr "DEL doel info" + +#: modules/commands/ns_ajoin.cpp:232 +msgid "DEL [nickname] channel" +msgstr "DEL [nick] kanaal" + +#: modules/commands/ns_cert.cpp:259 +msgid "DEL [nickname] fingerprint" +msgstr "DEL [nick] vingerafdruk" + +#: modules/commands/ns_access.cpp:103 +msgid "DEL [nickname] mask" +msgstr "DEL [nick] masker" + +#: modules/commands/os_sxline.cpp:426 modules/commands/os_sxline.cpp:660 +#: modules/commands/os_akill.cpp:387 +msgid "DEL {mask | entry-num | list | id}" +msgstr "DEL {masker | nr | lijst | id}" + +#: modules/commands/os_session.cpp:524 +msgid "DEL {mask | entry-num | list}" +msgstr "DEL {masker | nr | lijst}" + +#: modules/commands/os_ignore.cpp:343 +msgid "DEL {nick|mask}" +msgstr "DEL {nickname|masker}" + +#: modules/commands/os_news.cpp:279 +msgid "DEL {num | ALL}" +msgstr "DEL {nr | ALL}" + +#: modules/commands/os_forbid.cpp:158 +msgid "DEL {NICK|CHAN|EMAIL|REGISTER} entry" +msgstr "DEL {NICK|CHAN|EMAIL|REGISTER} vermelding" + +#: modules/commands/os_dns.cpp:666 +msgid "DELIP server.name ip" +msgstr "DELIP server.naam ip" + +#: modules/commands/os_dns.cpp:664 +msgid "DELSERVER server.name [zone.name]" +msgstr "DELSERVER server.naam [domein.naam]" + +#: modules/commands/os_dns.cpp:662 +msgid "DELZONE zone.name" +msgstr "DELZONE domein.naam" + +#: modules/commands/os_dns.cpp:669 +msgid "DEPOOL server.name" +msgstr "DEPOOL server.naam" + +#: modules/commands/cs_seen.cpp:162 +#, c-format +msgid "Database cleared, removed %lu nicks that were added after %s." +msgstr "Database opgekuist, %lu nicks verwijderd die werden toegevoegd na %s." + +#: modules/commands/ms_list.cpp:64 +msgid "Date/Time" +msgstr "Datum/Tijd" + +#: modules/commands/hs_off.cpp:49 +msgid "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." +msgstr "" +"Deactiveert de vHost die moementeel toegewezen is aan de nick\n" +"die in gebruik is. Als je dit commando uitvoert zal elke gebruiker\n" +"die een /whois op je doet je echte hostname zien in plaats van\n" +"je vHost." + +#: modules/commands/hs_off.cpp:19 +msgid "Deactivates your assigned vhost" +msgstr "Deactiveert je toegewezen vHost" + +#: modules/commands/os_stats.cpp:72 +#, c-format +msgid "Default AKILL expiry time: %d days" +msgstr "Standaard AKILL verlooptijd: %d dagen" + +#: modules/commands/os_stats.cpp:76 +#, c-format +msgid "Default AKILL expiry time: %d hours" +msgstr "Standaard AKILL verlooptijd: %d uur" + +#: modules/commands/os_stats.cpp:80 +#, c-format +msgid "Default AKILL expiry time: %d minutes" +msgstr "Standaard AKILL verlooptijd: %d minuten" + +#: modules/commands/os_stats.cpp:74 +msgid "Default AKILL expiry time: 1 day" +msgstr "Standaard AKILL verlooptijd: 1 dag" + +#: modules/commands/os_stats.cpp:78 +msgid "Default AKILL expiry time: 1 hour" +msgstr "Standaard AKILL verlooptijd: 1 uur" + +#: modules/commands/os_stats.cpp:82 +msgid "Default AKILL expiry time: 1 minute" +msgstr "Standaard AKILL verlooptijd: 1 minuut" + +#: modules/commands/os_stats.cpp:84 +msgid "Default AKILL expiry time: No expiration" +msgstr "Standaard AKILL verlooptijd: Verloopt niet" + +#: modules/commands/os_stats.cpp:92 +#, c-format +msgid "Default SNLINE expiry time: %d days" +msgstr "Standaard SNLINE verlooptijd: %d dagen" + +#: modules/commands/os_stats.cpp:96 +#, c-format +msgid "Default SNLINE expiry time: %d hours" +msgstr "Standaard SNLINE verlooptijd: %d uur" + +#: modules/commands/os_stats.cpp:100 +#, c-format +msgid "Default SNLINE expiry time: %d minutes" +msgstr "Standaard SNLINE verlooptijd: %d minuten" + +#: modules/commands/os_stats.cpp:94 +msgid "Default SNLINE expiry time: 1 day" +msgstr "Standaard SNLINE verlooptijd: 1 dag" + +#: modules/commands/os_stats.cpp:98 +msgid "Default SNLINE expiry time: 1 hour" +msgstr "Standaard SNLINE verlooptijd: 1 uur" + +#: modules/commands/os_stats.cpp:102 +msgid "Default SNLINE expiry time: 1 minute" +msgstr "Standaard SNLINE verlooptijd: 1 minuut" + +#: modules/commands/os_stats.cpp:104 +msgid "Default SNLINE expiry time: No expiration" +msgstr "Standaard SNLINE verlooptijd: Verloopt niet" + +#: modules/commands/os_stats.cpp:112 +#, c-format +msgid "Default SQLINE expiry time: %d days" +msgstr "Standaard SQLINE verlooptijd: %d dagen" + +#: modules/commands/os_stats.cpp:116 +#, c-format +msgid "Default SQLINE expiry time: %d hours" +msgstr "Standaard SQLINE verlooptijd: %d uur" + +#: modules/commands/os_stats.cpp:120 +#, c-format +msgid "Default SQLINE expiry time: %d minutes" +msgstr "Standaard SQLINE verlooptijd: %d minuten" + +#: modules/commands/os_stats.cpp:114 +msgid "Default SQLINE expiry time: 1 day" +msgstr "Standaard SQLINE verlooptijd: 1 dag" + +#: modules/commands/os_stats.cpp:118 +msgid "Default SQLINE expiry time: 1 hour" +msgstr "Standaard SQLINE verlooptijd: 1 uur" + +#: modules/commands/os_stats.cpp:122 +msgid "Default SQLINE expiry time: 1 minute" +msgstr "Standaard SQLINE verlooptijd: 1 minuut" + +#: modules/commands/os_stats.cpp:124 +msgid "Default SQLINE expiry time: No expiration" +msgstr "Standaard SQLINE verlooptijd: Verloopt niet" + +#: modules/commands/os_news.cpp:351 +msgid "Define messages to be randomly shown to users at logon" +msgstr "" +"Stel de berichten in die gebruikers willekeurig krijgen als ze verbinden" + +#: modules/commands/os_news.cpp:297 +msgid "Define messages to be shown to users at logon" +msgstr "Stel de berichten in die gebruikers krijgen als ze verbinden" + +#: modules/commands/os_news.cpp:324 +msgid "Define messages to be shown to users who oper" +msgstr "" +"Stel de berichten in die gebruikers te zien krijgen wanneer ze OPER worden" + +#: modules/commands/ms_del.cpp:44 +msgid "Delete a memo or memos" +msgstr "Verwijder een of meerdere memo's" + +#: modules/commands/hs_del.cpp:19 +msgid "Delete the vhost of another user" +msgstr "Verwijder de vHost van een andere gebruiker" + +#: modules/commands/cs_xop.cpp:302 +#, c-format +msgid "Deleted %d entries from %s %s list." +msgstr "%d vermeldingen verwijderd van %s %s lijst." + +#: modules/commands/cs_access.cpp:277 +#, c-format +msgid "Deleted %d entries from %s access list." +msgstr "%d vermeldingen verwijderd van %s toegangslijst." + +#: modules/commands/cs_akick.cpp:228 +#, c-format +msgid "Deleted %d entries from %s autokick list." +msgstr "%d vermeldingen verwijderd van %s autokicklijst." + +#: modules/commands/bs_badwords.cpp:170 +#, c-format +msgid "Deleted %d entries from %s bad words list." +msgstr "%d vermeldingen verwijderd van %s slechtewoordenlijst." + +#: modules/commands/os_session.cpp:149 +#, c-format +msgid "Deleted %d entries from session-limit exception list." +msgstr "" +"%d vermeldingen verwijderd van de uitzonderingenlijst voor sessielimieten." + +#: modules/commands/os_sxline.cpp:32 +#, c-format +msgid "Deleted %d entries from the %s list." +msgstr "%d vermeldingen verwijderd van de %s lijst." + +#: modules/commands/os_akill.cpp:33 +#, c-format +msgid "Deleted %d entries from the AKILL list." +msgstr "%d vermeldingen verwijderd van de AKILL lijst." + +#: modules/commands/cs_access.cpp:275 +#, c-format +msgid "Deleted 1 entry from %s access list." +msgstr "1 vermelding verwijderd van %s toegangslijst." + +#: modules/commands/cs_akick.cpp:226 +#, c-format +msgid "Deleted 1 entry from %s autokick list." +msgstr "1 vermelding verwijderd van %s autokicklijst." + +#: modules/commands/bs_badwords.cpp:168 +#, c-format +msgid "Deleted 1 entry from %s bad words list." +msgstr "1 vermelding verwijderd van %s slechtewoordenlijst." + +#: modules/commands/os_session.cpp:147 +msgid "Deleted 1 entry from session-limit exception list." +msgstr "" +"1 vermelding verwijderd van de uitzonderingenlijst voor sessielimieten." + +#: modules/commands/os_sxline.cpp:30 +#, c-format +msgid "Deleted 1 entry from the %s list." +msgstr "1 vermelding verwijderd van de %s lijst." + +#: modules/commands/os_akill.cpp:31 +msgid "Deleted 1 entry from the AKILL list." +msgstr "1 vermelding verwijderd van de AKILL lijst." + +#: modules/commands/os_info.cpp:208 +#, c-format +msgid "Deleted info from %s." +msgstr "Info verwijderd van %s." + +#: modules/commands/cs_xop.cpp:300 +#, c-format +msgid "Deleted one entry from %s %s list." +msgstr "1 vermelding verwijderd van %s %s lijst." + +#: modules/commands/ms_del.cpp:129 +msgid "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Verwijdert de opgegeven memo('s). Je kan meerdere\n" +"memo-nummers opgeven of lijsten van nummers ipv een\n" +"enkel nummer, zoals in het 2e voorbeeld hieronder.\n" +" \n" +"Als LAST is gegeven, wordt de laatste memo verwijderd.\n" +"Als ALL is gegeven, worden al je memo's verwijderd.\n" +" \n" +"Voorbeelden:\n" +" \n" +" DEL 1\n" +" Verwijdert je eerste memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Verwijdert de memo's genummerd 2 t/m 5 en 7 t/m 9." + +#: modules/commands/hs_del.cpp:48 +msgid "" +"Deletes the vhost assigned to the given nick from the\n" +"database." +msgstr "" +"Verwijdert de vHost die toegewezen is aan de gegeven nick\n" +"uit de database." + +#: modules/commands/hs_del.cpp:59 +msgid "Deletes the vhost for all nicks in a group" +msgstr "Verwijdert de vHost voor alle nicks in een groep" + +#: modules/commands/hs_del.cpp:93 +msgid "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." +msgstr "" +"Verwijdert de vHost voor alle nicks in dezelfde groep\n" +"als de opgegeven nick." + +#: modules/commands/os_dns.cpp:653 +#, c-format +msgid "Depooled %s." +msgstr "Depooled %s." + +#: modules/commands/cs_access.cpp:799 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_list.cpp:75 modules/commands/cs_info.cpp:53 +msgid "Description" +msgstr "Beschrijving" + +#: modules/commands/cs_set.cpp:239 +#, c-format +msgid "Description of %s changed to %s." +msgstr "Beschrijving van %s veranderd naar %s." + +#: modules/commands/cs_set.cpp:245 +#, c-format +msgid "Description of %s unset." +msgstr "Beschrijving van %s verwijderd." + +#: modules/commands/bs_kick.cpp:1115 modules/commands/bs_info.cpp:90 +msgid "Disabled" +msgstr "Uitgeschakeld" + +#: modules/commands/cs_suspend.cpp:134 +msgid "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." +msgstr "" +"Verbied iedereen het gebruik van het opgegeven\n" +"kanaal. Kan ongedaan gemaakt worden door middel van\n" +"het UNSUSPEND commando om alle vorige kanaal\n" +"data en instellingen te behouden. Als een verlooptijd is\n" +"opgegeven zal de schorsing na die tijd opgeheven worden,\n" +"zoniet word de standaard tijd uit de configuratie gebruikt.\n" +" \n" +"Op sommige netwerken is een reden verplicht." + +#: modules/commands/hs_request.cpp:337 +#, c-format +msgid "Displayed %d records (%d total)." +msgstr "%d resultaten getoond (%d in totaal)." + +#: modules/commands/hs_list.cpp:122 +#, c-format +msgid "Displayed all records (count: %d)." +msgstr "Alle resultaten getoond (aantal: %d)." + +#: modules/commands/hs_list.cpp:120 +#, c-format +msgid "Displayed records from %d to %d." +msgstr "Resultaten van %d tot %d getoond." + +#: modules/commands/hs_list.cpp:116 +#, c-format +msgid "Displayed records matching key %s (count: %d)." +msgstr "Alle resultaten met overeenkomend patroon %s getoond (aantal: %d)." + +#: modules/commands/ns_info.cpp:19 +msgid "Displays information about a given nickname" +msgstr "Toont informatie over de gegeven nick" + +#: modules/commands/ns_info.cpp:125 +msgid "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." +msgstr "" +"Geeft informatie weer over de gegeven nick, zoals eigenaar\n" +"van de nick, het laatst bekende adres, wanneer deze\n" +"voor het laatst gezien is, en de ingestelde opties. Indien geen\n" +"nick opgegeven is en je bent geïdentificeerd, dan word\n" +"jouw accountnaam gebruikt, en anders je huidige nick." + +#: modules/commands/ms_info.cpp:19 +msgid "Displays information about your memos" +msgstr "Toont informatie over jouw memo's" + +#: modules/commands/hs_list.cpp:19 +msgid "Displays one or more vhost entries" +msgstr "Geeft een of meer vHosts weer" + +#: modules/extra/stats/cs_fantasy_top.cpp:50 +msgid "Displays the top 10 users of a channel" +msgstr "Toont de top 10 gebruikers van een kanaal" + +#: modules/extra/stats/cs_fantasy_top.cpp:73 +msgid "Displays the top 10 users of the network" +msgstr "Toont de top 10 gebruikers van het netwerk" + +#: modules/extra/stats/cs_fantasy_top.cpp:38 +msgid "Displays the top 3 users of a channel" +msgstr "Toont de top 3 gebruikers van een kanaal" + +#: modules/extra/stats/cs_fantasy_top.cpp:62 +msgid "Displays the top 3 users of the network" +msgstr "Toont de top 3 gebruikers van het netwerk" + +#: modules/commands/help.cpp:33 +msgid "Displays this list and give information about commands" +msgstr "Toont deze lijst en geeft informatie over commando's" + +#: modules/extra/stats/cs_fantasy_stats.cpp:39 +msgid "Displays your Channel Stats" +msgstr "Toont jouw kanaalstatistieken" + +#: modules/extra/stats/cs_fantasy_stats.cpp:51 +msgid "Displays your Global Stats" +msgstr "Toont jouw globale statistieken" + +#: modules/commands/bs_kick.cpp:1463 +msgid "Don't use AMSGs!" +msgstr "Geen AMSG gebruiken!" + +#: modules/commands/bs_kick.cpp:1266 +msgid "Don't use bolds on this channel!" +msgstr "Gebruik geen vette karakters in dit kanaal!" + +#: modules/commands/bs_kick.cpp:1274 +msgid "Don't use colors on this channel!" +msgstr "Gebruik geen kleuren in dit kanaal!" + +#: modules/commands/bs_kick.cpp:1290 +msgid "Don't use italics on this channel!" +msgstr "Gebruik geen cursief in dit kanaal!" + +#: modules/commands/bs_kick.cpp:1282 +msgid "Don't use reverses on this channel!" +msgstr "Gebruik geen inverteringen in dit kanaal!" + +#: modules/commands/bs_kick.cpp:1408 +#, c-format +msgid "Don't use the word \"%s\" on this channel!" +msgstr "Het woord \"%s\" niet in dit kanaal gebruiken!" + +#: modules/commands/bs_kick.cpp:1298 +msgid "Don't use underlines on this channel!" +msgstr "Gebruik geen onderlijningen in dit kanaal!" + +#: modules/commands/ns_drop.cpp:61 +msgid "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." +msgstr "" +"Verwijdert de gegeven nick uit de database. Eens dit gedaan\n" +"is kan je al je toegangen en kanalen verliezen dat u bezit.\n" +"Iedereen kan dan deze nick opnieuw registreren." + +#: modules/commands/ns_set.cpp:513 +#, c-format +msgid "E-mail address for %s changed to %s." +msgstr "E-mailadres voor %s gewijzigd naar %s." + +#: modules/commands/ns_set.cpp:519 +#, c-format +msgid "E-mail address for %s unset." +msgstr "E-mailadres voor %s verwijderd." + +#: src/mail.cpp:80 +#, c-format +msgid "E-mail for %s is invalid." +msgstr "E-mail voor %s is ongeldig." + +#: modules/commands/os_news.cpp:309 +#, c-format +msgid "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Wijzigt de lijst met login nieuwsberichten of geeft deze weer.\n" +"Wanneer een gebruiker met het netwerk verbindt, worden deze\n" +"berichten naar hem/haar verzonden. Echter, er zullen nooit\n" +"meer dan %d berichten worden verstuurd om het flooden van de\n" +"gebruiker te voorkomen. Als er meer nieuwsberichten\n" +"zijn worden alleen de meest recente vestuurd." + +#: modules/commands/os_news.cpp:336 +#, c-format +msgid "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Wijzigt de lijst met operator nieuwsberichten of geeft deze weer.\n" +"Wanneer een gebruiker opert (d.m.v. het /OPER commando), worden\n" +"deze berichten naar hem/haar verzonden. Echter, er zullen\n" +"nooit meer dan %d berichten worden verstuurd om het flooden\n" +"van de gebruiker te voorkomen. Als er meer nieuwsberichten\n" +"zijn worden alleen de meest recente vestuurd." + +#: modules/commands/os_news.cpp:363 +msgid "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." +msgstr "" +"Wijzigt de lijst mer willekeurige nieuwsberichten of geeft\n" +"deze weer. Wanneer een gebruiker met het netwerk verbind,\n" +"word er één (en niet meer dan één) van deze willekeurige\n" +"nieuwsberichten willekeurig uitgekozen en naar hem/haar\n" +"verstuurd." + +#: modules/commands/ns_info.cpp:98 +msgid "Email address" +msgstr "E-mailadres" + +#: modules/commands/ns_getemail.cpp:41 +#, c-format +msgid "Email matched: %s (%s) to %s." +msgstr "E-mail overeenkomst: %s (%s) met %s." + +#: modules/fantasy.cpp:19 +msgid "Enable fantaisist commands" +msgstr "Activeer fantasie commando's" + +#: modules/commands/greet.cpp:19 +msgid "Enable greet messages" +msgstr "Activeer begroetingen" + +#: modules/commands/ns_set.cpp:568 +msgid "Enable or disable keep modes" +msgstr "Activeer of deactiveer KEEPMODES" + +#: modules/commands/bs_kick.cpp:1114 modules/commands/bs_info.cpp:89 +msgid "Enabled" +msgstr "Ingeschakeld" + +#: modules/commands/cs_set.cpp:124 +#, c-format +msgid "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." +msgstr "" +"Activeert of deactiveert %s's AUTOOP optie voor een\n" +"kanaal. Wanneer inactief, zullen gebruikers hun status-\n" +"modes niet automatisch krijgen van %s." + +#: modules/commands/cs_set.cpp:388 +msgid "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." +msgstr "" +"Activeert of deactiveert KEEPMODES voor het gegeven kanaal.\n" +"Indien geactiveerd, dan zullen Services de kanaalmodes\n" +"onthouden en pogen deze terug te zetten wanneer het kanaal\n" +"de volgende keer weer aangemaakt wordt." + +#: modules/commands/ns_set.cpp:643 +msgid "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." +msgstr "" +"Activeert of deactiveert KEEPMODES voor de gegeven nick.\n" +"Indien geactiveerd, dan zullen Services de gebruikersmodes\n" +"onthouden en pogen deze terug te zetten wanneer ze de\n" +"volgende keer identificeren." + +#: modules/commands/ns_set.cpp:618 +msgid "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." +msgstr "" +"Activeert of deactiveert KEEPMODES voor je nick.\n" +"Indien geactiveerd, dan zullen Services je gebruikersmodes\n" +"onthouden en pogen deze terug te zetten wanneer je de\n" +"volgende keer identificeert." + +#: modules/commands/cs_set.cpp:733 +msgid "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." +msgstr "" +"Zet veiligheidsfuncties aan of uit voor een kanaal.\n" +"Wanneer SECURE aan staat zullen alleen gebruikers die\n" +"geïdentificeerd zijn, en niet enkel herkend, toegang\n" +"krijgen tot kanalen vanaf account-gebaseerde\n" +"toegangsvermeldingen." + +#: modules/commands/cs_set.cpp:932 +msgid "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." +msgstr "" +"Zet ondertekende kicks aan of uit voor een kanaal.\n" +"Wanneer SIGNKICK aan staat zullen kicks die uitgevoerd\n" +"worden met het KICK commando de nick van diegene die\n" +"het commando uitgevoerd heeft in de reden hebben.\n" +" \n" +"Als je LEVEL gebruikt zullen diegenen die een niveau hebben\n" +"gelijk aan of hoger dan het SIGNKICK niveau op het kanaal\n" +"hun nick niet toegevoegd hebben aan de kickredenen." + +#: modules/commands/cs_set.cpp:452 +#, c-format +msgid "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." +msgstr "" +"Zet de vrede optie aan of uit voor een kanaal. Wanneer\n" +"vrede aanstaat kan een gebruiker niemand kicken, bannen,\n" +"of iemand's kanaal status wijzigen/verwijderen van een\n" +"gebruiker met een gelijkwaardig of hoger level dan die\n" +"van zichzelf via de %s commando's." + +#: modules/commands/cs_list.cpp:232 +msgid "Enables or disables the private option for a channel." +msgstr "Activeert of deactiveert de privé optie voor een kanaal." + +#: modules/commands/cs_set.cpp:671 +msgid "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." +msgstr "" +"Activeert of deactiveert de beperkte toegang optie voor een\n" +"kanaal. Wanneer beperkte toegang aan staat zullen gebruikers\n" +"die niet op de toegangslijst staan gekickt en gebant worden van het\n" +"kanaal." + +#: modules/commands/cs_set.cpp:796 +msgid "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." +msgstr "" +"Zet de veilige stichter optie aan of uit voor een kanaal.\n" +"Wanneer veilige stichter aan staat zal alleen de echte\n" +"stichter een kanaal kunnen annuleren, en de stichter en de\n" +"opvolger veranderen, en niet diegenen die stichter-toegang\n" +"hebben." + +#: modules/commands/cs_set.cpp:860 +msgid "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." +msgstr "" +"Zet de veilige ops optie aan of uit voor een kanaal.\n" +"Wanneer veilige ops aan staat mogen gebruikers die niet\n" +"op de toegangslijst staan geen kanaaloperator status krijgen." + +#: modules/commands/cs_topic.cpp:70 +#, c-format +msgid "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." +msgstr "" +"Zet de topicbehoud optie aan of uit voor een kanaal.\n" +"Wanneer %s aan staat zal de topic van het\n" +"kanaal onthouden worden door %s, zelfs nadat de laatste\n" +"gebruiker het kanaal heeft verlaten. De topic zal wanneer\n" +"een gebruiker het kanaal een volgende keer binnenkomt\n" +"worden teruggezet." + +#: modules/commands/cs_set.cpp:592 +#, c-format +msgid "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." +msgstr "" +"Activeert of deactiveert de PERSIST kanaalinstelling.\n" +"Wanneer dit actief is zal de Services Bot op het kanaal\n" +"blijven zitten, zelfs als er niemand anders aanwezig is.\n" +" \n" +"Als jouw IRCd geen ondersteuning heeft voor permanente\n" +"kanalen, dan moet je een Services Bot in je kanaal\n" +"hebben om PERSIST aan te kunnen zetten, en deze kan\n" +"verwijderd worden zolang PERSIST aan staat.\n" +" \n" +"Als dit netwerk geen %s en geen permanent kanalen\n" +"ondersteunt, dan zal %s je kanaal joinen wanneer\n" +"je deze instelling activeert (en weg gaan wanneer je\n" +"deze weer deactiveert).\n" +" \n" +"Indien jouw IRCd wel permanente kanalen ondersteunt\n" +"en de bijhorende kanaalmode wordt ingesteld of\n" +"verwijderd (voor welke reden dan ook, inclusief MODE LOCK),\n" +"dan wordt PERSIST geactiveerd of gedeactiveerd.\n" +"Bovendien zullen Services deze kanaalmode instellen of\n" +"verwijderen wanneer je PERSIST aan of uit zet." + +#: modules/commands/os_akill.cpp:331 +msgid "End of AKILL list." +msgstr "Einde van AKILL lijst." + +#: modules/commands/cs_access.cpp:444 +msgid "End of access list" +msgstr "Einde van de toegangslijst." + +#: modules/commands/cs_flags.cpp:347 +#, c-format +msgid "End of access list - %d/%d entries shown." +msgstr "Einde van de toegangslijst - %d/%d resultaten weergegeven." + +#: modules/commands/cs_flags.cpp:345 +msgid "End of access list." +msgstr "Einde van de toegangslijst." + +#: modules/commands/cs_akick.cpp:379 +msgid "End of autokick list" +msgstr "Einde van de autokicklijst." + +#: modules/commands/bs_badwords.cpp:257 +msgid "End of bad words list." +msgstr "Einde van de slechtewoordenlijst." + +#: modules/commands/os_list.cpp:100 +#, c-format +msgid "End of channel list. %u channels shown." +msgstr "Einde van kanalenlijst. %u kanalen weergegeven." + +#: modules/commands/os_config.cpp:117 +msgid "End of configuration." +msgstr "Einde van configuratie." + +#: modules/commands/cs_entrymsg.cpp:134 +msgid "End of entry message list." +msgstr "Einde van berichtenlijst." + +#: modules/commands/os_forbid.cpp:407 +#, c-format +msgid "End of forbid list - %d/%d entries shown." +msgstr "Einde van verbodslijst - %d/%d resultaten weergegeven." + +#: modules/commands/os_forbid.cpp:405 +msgid "End of forbid list." +msgstr "Einde van verbodslijst." + +#: modules/commands/ns_alist.cpp:119 +#, c-format +msgid "End of list - %d channels shown." +msgstr "Einde van lijst - %d kanalen weergegeven." + +#: modules/commands/ns_list.cpp:131 modules/commands/cs_list.cpp:130 +#, c-format +msgid "End of list - %d/%d matches shown." +msgstr "Einde van lijst - %d/%d overeenkomsten weergegeven." + +#: modules/commands/os_news.cpp:176 +msgid "End of news list." +msgstr "Einde van nieuwslijst." + +#: modules/commands/os_list.cpp:235 +#, c-format +msgid "End of users list. %u users shown." +msgstr "Einde van gebruikerslijst. %u gebruikers weergegeven." + +#: modules/commands/cs_enforce.cpp:227 +msgid "Enforce various channel modes and set options" +msgstr "Dwing verschillende kanaalmodes af en stel opties in" + +#: modules/commands/cs_enforce.cpp:263 +msgid "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." +msgstr "" +"Dwingt verschillende kanaalmodes en SET opties af. Het kanaal\n" +"parameter geeft aan op welk kanaal dit moet gebeuren. De wat\n" +"optie geeft aan wat er moet afgedwongen worden, en kan één van\n" +"de volgende zijn: SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, of LIMIT.\n" +" \n" +"Gebruik SECUREOPS om de SECUREOPS optie af te dwingen, zelfs\n" +"als deze niet geactiveerd is. Gebruik RESTRICTED om de RESTRICTED\n" +"optie af te dwingen, ook wanneer deze niet geactiveerd is. Gebruik REGONLY\n" +"om alle ongeregistreerde gebruikers te kicken van het kanaal. Gebruik " +"SSLONLY\n" +"om alle gebruikers die geen veilige/versleutelde verbinding gebruiken te " +"kicken\n" +"van het kanaal. BANS zal actieve bans afdwingen door gebruikers te kicken\n" +"die ermee overeenstemmen, en LIMIT zal gebruikers kicken tot het\n" +"gebruikersaantal onder de kanaallimiet zakt, indien ingesteld." + +#: src/language.cpp:43 modules/commands/ns_set.cpp:836 +#: modules/commands/ns_set.cpp:856 modules/commands/ns_set.cpp:891 +msgid "English" +msgstr "Nederlands" + +#: modules/commands/cs_entrymsg.cpp:170 +#, c-format +msgid "Entry message %i for %s deleted." +msgstr "Welkomstbericht %i voor %s verwijderd." + +#: modules/commands/cs_entrymsg.cpp:177 +#, c-format +msgid "Entry message %s not found on channel %s." +msgstr "Welkomstbericht %s niet gevonden op kanaal %s." + +#: modules/commands/cs_entrymsg.cpp:147 +#, c-format +msgid "Entry message added to %s" +msgstr "Welkomstbericht toegevoegd op %s" + +#: modules/commands/cs_entrymsg.cpp:109 modules/commands/cs_entrymsg.cpp:158 +#, c-format +msgid "Entry message list for %s is empty." +msgstr "Welkomstberichtenlijst voor %s is leeg." + +#: modules/commands/cs_entrymsg.cpp:113 +#, c-format +msgid "Entry message list for %s:" +msgstr "Welkomstberichtenlijst voor %s:" + +#: modules/commands/cs_entrymsg.cpp:187 +#, c-format +msgid "Entry messages for %s have been cleared." +msgstr "Alle welkomstberichten voor %s zijn verwijderd." + +#: modules/commands/os_reload.cpp:39 +#, c-format +msgid "Error reloading configuration file: %s" +msgstr "Fout bij laden configuratiebestand: %s" + +#: include/language.h:125 +#, c-format +msgid "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." +msgstr "" +"Fout! De vHost ident is te lang, gelieve een ident korter dan %d karakters " +"op te geven." + +#: include/language.h:124 +#, c-format +msgid "" +"Error! The vHost is too long, please use a hostname shorter than %d " +"characters." +msgstr "" +"Fout! De vHost is te lang, gelieve een host korter dan %d karakters op te " +"geven." + +#: modules/commands/ns_cert.cpp:325 +msgid "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." +msgstr "" +"Voorbeelden:\n" +" \n" +" CERT ADD\n" +" Voegt je huidige vingerafdruk toe aan de certificaatlijst, en\n" +" identificeert je automatisch wanneer je verbinding maakt\n" +" met deze certificaat.\n" +" \n" +" CERT DEL \n" +" Verwijdert de gegeven vingerafdruk van je certificaatlijst.\n" +" \n" +" CERT LIST\n" +" Toont de huidige certificaatlijst." + +#: modules/commands/os_session.cpp:358 +#, c-format +msgid "Exception for %s has been updated to %d." +msgstr "Uitzondering voor %s is geüpdatet naar %d." + +#: modules/pseudoclients/chanserv.cpp:465 +#: modules/pseudoclients/nickserv.cpp:557 +#: modules/pseudoclients/nickserv.cpp:562 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_session.cpp:514 modules/commands/ns_group.cpp:327 +#: modules/commands/os_akill.cpp:358 +msgid "Expires" +msgstr "Verloopt" + +#: src/xline.cpp:397 +#, c-format +msgid "Expiry and reason updated for %s." +msgstr "Verlooptijd en reden voor %s geüpdatet." + +#: src/xline.cpp:400 +#, c-format +msgid "Expiry for %s updated." +msgstr "Verlooptijd voor %s geüpdatet." + +#: modules/fantasy.cpp:214 +msgid "Fantasy" +msgstr "Fantasie" + +#: modules/fantasy.cpp:60 +#, c-format +msgid "Fantasy mode is now off on channel %s." +msgstr "Fantasie modus staat nu uit op kanaal %s." + +#: modules/fantasy.cpp:52 +#, c-format +msgid "Fantasy mode is now on on channel %s." +msgstr "Fantasie modus staat nu aan op kanaal %s." + +#: modules/commands/cs_status.cpp:19 +msgid "Find a user's status on a channel" +msgstr "Vind een gebruiker's status op een kanaal" + +#: modules/commands/ns_cert.cpp:192 +#, c-format +msgid "Fingerprint %s already present on %s's certificate list." +msgstr "Vingerafdruk %s is al aanwezig op %s's certificaatlist." + +#: modules/commands/ns_cert.cpp:198 +#, c-format +msgid "Fingerprint %s is already in use." +msgstr "Vingerafdruk %s is al in gebruik." + +#: modules/commands/cs_flags.cpp:301 +msgid "Flags" +msgstr "Vlaggen" + +#: modules/commands/cs_flags.cpp:286 +#, c-format +msgid "Flags for %s on %s set to +%s" +msgstr "Vlaggen voor %s op %s gewijzigd naar +%s" + +#: modules/commands/cs_flags.cpp:341 +#, c-format +msgid "Flags list for %s" +msgstr "Vlaggenlijst voor %s" + +#: modules/commands/bs_kick.cpp:1161 modules/commands/bs_kick.cpp:1163 +#: modules/commands/bs_kick.cpp:1166 +msgid "Flood kicker" +msgstr "Floodkicker" + +#: modules/commands/os_forbid.cpp:421 +msgid "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." +msgstr "" +"Stelt je in staat bepaalde nicks, kanalen of e-mailadressen te\n" +"verbieden. Jokertekens worden aanvaard voor alle vermeldingen." + +#: modules/commands/os_forbid.cpp:354 +msgid "Forbid list is empty." +msgstr "Verbodslijst is leeg." + +#: modules/commands/os_forbid.cpp:396 +msgid "Forbid list:" +msgstr "Verbodsijst:" + +#: modules/commands/os_forbid.cpp:348 +#, c-format +msgid "Forbid on %s was not found." +msgstr "Verbod op %s werd niet gevonden." + +#: modules/commands/os_forbid.cpp:156 +msgid "Forbid usage of nicknames, channels, and emails" +msgstr "Verbied gebruik van nicks, kanalen en e-mails" + +#: modules/commands/os_update.cpp:19 +msgid "Force the Services databases to be updated immediately" +msgstr "Forceer dat de Services database onmiddellijk word geüpdatet" + +#: modules/commands/os_svs.cpp:19 +msgid "Forcefully change a user's nickname" +msgstr "Forceer een nickwijziging" + +#: modules/commands/os_svs.cpp:68 +msgid "Forcefully changes a user's nickname from nick to newnick." +msgstr "Verandert een gebruiker's nick van nick naar nieuwenick." + +#: modules/commands/os_svs.cpp:78 +msgid "Forcefully join a user to a channel" +msgstr "Dwing een gebruiker een kanaal te betreden" + +#: modules/commands/os_svs.cpp:112 +msgid "Forcefully join a user to a channel." +msgstr "Dwing een gebruiker een kanaal te betreden." + +#: modules/commands/os_svs.cpp:122 +msgid "Forcefully part a user from a channel" +msgstr "Dwing een gebruiker een kanaal te verlaten" + +#: modules/commands/os_svs.cpp:160 +msgid "Forcefully part a user from a channel." +msgstr "Dwing een gebruiker een kanaal te verlaten." + +#: modules/commands/ns_alist.cpp:64 modules/commands/cs_info.cpp:47 +msgid "Founder" +msgstr "Stichter" + +#: modules/commands/cs_set.cpp:315 +#, c-format +msgid "Founder of %s changed to %s." +msgstr "Stichter van %s veranderd naar %s." + +#: modules/commands/ns_getpass.cpp:41 +msgid "GETPASS command unavailable because encryption is in use." +msgstr "GETPASS commando is onbeschikbaar omdat encryptie aanstaat." + +#: modules/commands/ns_recover.cpp:84 +msgid "Ghost with your nick has been killed." +msgstr "Ghost met jouw nick is gekilld." + +#: modules/commands/os_oline.cpp:19 +msgid "Give Operflags to a certain user" +msgstr "Geef Operflags aan een bepaalde gebruiker" + +#: modules/commands/cs_mode.cpp:905 +#, c-format +msgid "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." +msgstr "" +"Geeft %s status aan de gegeven nick op een kanaal. Als nick\n" +"niet gegeven, zal het jou %s status geven of afnemen." + +#: modules/commands/cs_mode.cpp:888 +#, c-format +msgid "Gives you or the specified nick %s status on a channel" +msgstr "Geeft jou of een gegeven nick %s status op een kanaal" + +#: modules/commands/greet.cpp:206 modules/commands/greet.cpp:212 +msgid "Greet" +msgstr "Begroeting" + +#: src/access.cpp:38 +msgid "Greet message displayed on join" +msgstr "Begroetingsbericht getoond bij betreden" + +#: modules/commands/greet.cpp:112 +#, c-format +msgid "Greet message for %s changed to %s." +msgstr "Begroetingsbericht voor %s gewijzigd naar %s." + +#: modules/commands/greet.cpp:118 +#, c-format +msgid "Greet message for %s unset." +msgstr "Begroetingsbericht voor %s verwijderd." + +#: modules/commands/greet.cpp:60 +#, c-format +msgid "Greet mode is now off on channel %s." +msgstr "Begroetingsmodus staat nu uit op kanaal %s." + +#: modules/commands/greet.cpp:52 +#, c-format +msgid "Greet mode is now on on channel %s." +msgstr "Begroetingsmodus staat nu aan op kanaal %s." + +#: modules/commands/ns_resetpass.cpp:21 +msgid "Helps you reset lost passwords" +msgstr "Helpt je verloren wachtwoorden te resetten" + +#: modules/commands/ns_info.cpp:141 +msgid "Hide certain pieces of nickname information" +msgstr "Verberg specifieke delen van nick informatie" + +#: modules/commands/cs_list.cpp:180 +msgid "Hide channel from the LIST command" +msgstr "Verberg een kanaal van het LIST commando" + +#: modules/commands/os_session.cpp:192 +msgid "Host" +msgstr "Host" + +#: modules/commands/os_session.cpp:207 +#, c-format +msgid "Hosts with at least %d sessions:" +msgstr "Hosts met tenminste %d sessies:" + +#: modules/commands/cs_seen.cpp:207 +#, c-format +msgid "I don't know who %s is." +msgstr "Ik weet niet wie %s is." + +#: modules/commands/cs_seen.cpp:253 +#, c-format +msgid "I've never seen %s on this channel." +msgstr "Ik heb %s nooit gezien op dit kanaal." + +#: modules/commands/os_sxline.cpp:203 modules/commands/os_akill.cpp:360 +msgid "ID" +msgstr "ID" + +#: modules/commands/os_oper.cpp:72 +msgid "INFO [type]" +msgstr "INFO [type]" + +#: modules/commands/os_dns.cpp:218 +msgid "IP" +msgstr "IP" + +#: modules/commands/os_dns.cpp:500 +#, c-format +msgid "IP %s already exists for %s." +msgstr "IP %s bestaat al voor %s." + +#: modules/commands/os_dns.cpp:562 +#, c-format +msgid "IP %s does not exist for %s." +msgstr "IP %s bestaat niet voor %s." + +#: modules/commands/ns_identify.cpp:65 +msgid "Identify yourself with your password" +msgstr "Identificeer jezelf met je wachtwoord" + +#: modules/pseudoclients/nickserv.cpp:205 +#: modules/pseudoclients/nickserv.cpp:211 +#, c-format +msgid "If you do not change within %s, I will change your nick." +msgstr "Als je niet binnen %s je nick verandert, verander ik je nick." + +#: modules/commands/os_ignore.cpp:333 +msgid "Ignore list has been cleared." +msgstr "Negeerlijst is leeggemaakt." + +#: modules/commands/os_ignore.cpp:262 +msgid "Ignore list is empty." +msgstr "Negeerlijst is leeg." + +#: modules/commands/ms_ignore.cpp:94 +msgid "Ignore list:" +msgstr "Negeerlijst:" + +#: modules/commands/ns_set.cpp:1305 +msgid "Immediate protection" +msgstr "Onmiddellijke berscherming" + +#: modules/commands/ns_resetpass.cpp:33 +msgid "Incorrect email address." +msgstr "Onjuist e-mailadres." + +#: include/language.h:89 +msgid "Incorrect range specified. The correct syntax is #from-to." +msgstr "Ongeldig bereik. De correcte syntax is #van-naar." + +#: modules/commands/os_modinfo.cpp:19 +msgid "Info about a loaded module" +msgstr "Info over een geladen module" + +#: modules/commands/bs_info.cpp:54 +#, c-format +msgid "Information for bot %s:" +msgstr "Informatie voor bot %s:" + +#: include/language.h:108 +#, c-format +msgid "Information for channel %s:" +msgstr "Informatie voor kanaal %s:" + +#: modules/commands/os_logsearch.cpp:57 +#, c-format +msgid "Invalid duration %s, using %d days." +msgstr "Ongeldige duratie %s, teruggevallen op %d dagen." + +#: include/language.h:68 +msgid "Invalid expiry time." +msgstr "Ongeldige verlooptijd." + +#: modules/commands/os_session.cpp:346 +msgid "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not " +"matched against nicks or usernames." +msgstr "" +"Ongeldig hostmasker. Alleen echte hostmaskers zijn geldig als uitzondering " +"omdat deze niet worden vergeleken met nicks of idents." + +#: modules/commands/os_logsearch.cpp:73 +#, c-format +msgid "Invalid limit %s, using %d." +msgstr "Ongeldig limiet %s, teruggevallen op %d." + +#: include/language.h:99 +msgid "" +"Invalid passcode has been entered, please check the e-mail again, and retry." +msgstr "" +"Ongeldige bevestigingscode, gelieve de e-mail opnieuw te controleren en nog " +"eens te proberen." + +#: modules/commands/ns_register.cpp:83 modules/commands/ns_register.cpp:86 +msgid "Invalid passcode." +msgstr "Ongeldige bevestigingscode." + +#: modules/commands/os_session.cpp:339 +#, c-format +msgid "" +"Invalid session limit. It must be a valid integer greater than or equal to " +"zero and less than %d." +msgstr "" +"Ongeldige sessielimiet. Het moet een geldig getal groter dan, of gelijk aan " +"nul, en kleiner dan %d zijn." + +#: modules/commands/os_session.cpp:188 +msgid "Invalid threshold value. It must be a valid integer greater than 1." +msgstr "Ongeldige drempel waarde. Het moet een geldig getal groter dan 1 zijn." + +#: modules/commands/os_dns.cpp:591 +msgid "Invalid value for LIMIT. Must be numerical." +msgstr "Ongeldige waarde voor LIMIT. Moet numeriek zijn." + +#: modules/commands/cs_invite.cpp:19 +msgid "Invites you or an optionally specified nick into a channel" +msgstr "Nodigt jou of een optionele nick naar een kanaal uit" + +#: modules/commands/bs_kick.cpp:1201 modules/commands/bs_kick.cpp:1203 +#: modules/commands/bs_kick.cpp:1206 +msgid "Italics kicker" +msgstr "Cursiefkicker" + +#: modules/commands/ns_group.cpp:91 +msgid "Join a group" +msgstr "Bij een groep aanmelden" + +#: modules/commands/cs_set.cpp:1305 modules/commands/ns_set.cpp:1319 +msgid "Keep modes" +msgstr "Behoud modes" + +#: modules/commands/cs_set.cpp:377 modules/commands/ns_set.cpp:603 +#, c-format +msgid "Keep modes for %s is now off." +msgstr "Modes behouden voor %s is nu uit." + +#: modules/commands/cs_set.cpp:369 modules/commands/ns_set.cpp:597 +#, c-format +msgid "Keep modes for %s is now on." +msgstr "Modes behouden voor %s is nu aan." + +#: modules/commands/ns_ajoin.cpp:100 +msgid "Key" +msgstr "Sleutel" + +#: modules/commands/cs_getkey.cpp:50 +#, c-format +msgid "Key for channel %s is %s." +msgstr "Sleutel voor kanaal %s is %s." + +#: modules/commands/os_kick.cpp:19 +msgid "Kick a user from a channel" +msgstr "Kick een gebruiker uit een kanaal" + +#: modules/commands/cs_ban.cpp:217 modules/commands/cs_kick.cpp:116 +#, c-format +msgid "Kicked %d/%d users matching %s from %s." +msgstr "%d/%d gebruikers gekickd die overeenstemden met %s uit %s." + +#: modules/commands/cs_kick.cpp:19 +msgid "Kicks a specified nick from a channel" +msgstr "Kick een gegeven nick uit een kanaal" + +#: modules/commands/cs_kick.cpp:128 +msgid "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." +msgstr "" +"Kick een gegeven nick uit een kanaal.\n" +" \n" +"Standaard is dit gelimiteerd tot AOPs of diegenen met\n" +"niveau 5 of hoger op het kanaal. Kanaalstichters mogen\n" +"ook maskers opgeven." + +#: modules/commands/os_kill.cpp:19 +msgid "Kill a user" +msgstr "Kill een gebruiker" + +#: modules/commands/cs_enforce.cpp:217 +msgid "LIMIT enforced by " +msgstr "LIMIT afgedwongen door " + +#: modules/commands/cs_enforce.cpp:221 +#, c-format +msgid "LIMIT enforced on %s, %d users removed." +msgstr "LIMIT afgedwongen op %s, %d gebruikers werden verwijderd." + +#: modules/commands/os_session.cpp:246 +msgid "LIST threshold" +msgstr "LIST aantal" + +#: modules/commands/os_sxline.cpp:427 modules/commands/os_sxline.cpp:661 +#: modules/commands/os_akill.cpp:388 +msgid "LIST [mask | list | id]" +msgstr "LIST [masker | lijst | id]" + +#: modules/commands/os_session.cpp:525 +msgid "LIST [mask | list]" +msgstr "LIST [masker | lijst]" + +#: modules/commands/ns_access.cpp:104 modules/commands/ns_cert.cpp:260 +#: modules/commands/ns_ajoin.cpp:233 +msgid "LIST [nickname]" +msgstr "LIST [nick]" + +#: modules/commands/os_news.cpp:31 +msgid "LOGONNEWS {ADD|DEL|LIST} [text|num]" +msgstr "LOGONNEWS {ADD|DEL|LIST} [text|nr]" + +#: modules/commands/ns_set.cpp:834 +msgid "Language changed to English." +msgstr "Taal gewijzigd naar Nederlands." + +#: modules/commands/ns_set.cpp:836 +#, c-format +msgid "Language for %s changed to %s." +msgstr "Taal voor %s gewijzigd naar %s." + +#: modules/commands/ms_cancel.cpp:72 +#, c-format +msgid "Last memo to %s has been cancelled." +msgstr "Laatste memo naar %s is geannuleerd." + +#: modules/commands/ns_info.cpp:95 +msgid "Last quit message" +msgstr "Laatste quit-bericht" + +#: modules/commands/cs_access.cpp:472 modules/commands/ns_info.cpp:92 +msgid "Last seen" +msgstr "Laatst gezien" + +#: modules/commands/ns_info.cpp:81 modules/commands/ns_info.cpp:86 +msgid "Last seen address" +msgstr "Laatst bekende adres" + +#: modules/commands/cs_topic.cpp:264 +msgid "Last topic" +msgstr "Laatste topic" + +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_info.cpp:56 +msgid "Last used" +msgstr "Laatst gebruikt" + +#: modules/commands/ns_list.cpp:75 +msgid "Last usermask" +msgstr "Laatste ident@host" + +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +#: modules/commands/cs_access.cpp:697 +msgid "Level" +msgstr "Niveau" + +#: modules/commands/cs_access.cpp:660 +#, c-format +msgid "Level for %s on channel %s changed to %d." +msgstr "Niveau voor %s op kanaal %s veranderd naar %d." + +#: modules/commands/cs_access.cpp:658 +#, c-format +msgid "Level for %s on channel %s changed to founder only." +msgstr "Niveau voor %s op kanaal %s gewijzigd naar enkel-stichter." + +#: modules/commands/cs_access.cpp:643 +#, c-format +msgid "Level must be between %d and %d inclusive." +msgstr "Niveau moet tussen de %d en %d inclusief zijn." + +#: modules/commands/os_dns.cpp:218 modules/commands/os_session.cpp:506 +#: modules/commands/os_session.cpp:514 +msgid "Limit" +msgstr "Limiet" + +#: modules/commands/ns_list.cpp:19 +msgid "List all registered nicknames that match a given pattern" +msgstr "" +"Toon alle geregistreerde nicks die met het gegeven patroon overeenstemmen" + +#: modules/commands/ns_alist.cpp:24 +msgid "List channels you have access on" +msgstr "Toon kanalen waar je toegang in hebt" + +#: modules/commands/cs_mode.cpp:341 +#, c-format +msgid "List for mode %c is full." +msgstr "Lijst voor mode %c is vol." + +#: modules/commands/os_modinfo.cpp:80 +msgid "List loaded modules" +msgstr "Geef geladen modules weer" + +#: modules/commands/ns_list.cpp:123 modules/commands/cs_list.cpp:72 +#, c-format +msgid "List of entries matching %s:" +msgstr "Lijst van vermeldingen overeenstemmend met %s:" + +#: modules/commands/ns_group.cpp:350 +#, c-format +msgid "List of nicknames in the group of %s:" +msgstr "Lijst van nicks in de groep van %s:" + +#: modules/commands/ns_group.cpp:350 +msgid "List of nicknames in your group:" +msgstr "Lijst van nicks in je groep:" + +#: modules/commands/ms_list.cpp:19 +msgid "List your memos" +msgstr "Geef je memo's weer" + +#: modules/commands/bs_botlist.cpp:64 +msgid "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." +msgstr "" +"Geeft alle beschikbare bots op dit netwerk weer.\n" +"Bots voorafgegaan met een * zijn gereserveerd\n" +"voor IRC operators." + +#: modules/commands/os_list.cpp:19 +msgid "Lists all channel records" +msgstr "Geef alle kanalen weer" + +#: modules/commands/os_list.cpp:107 +msgid "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." +msgstr "" +"Geeft alle kanalen weer die momenteel in gebruik zijn op het\n" +"IRC netwerk, geregistreerd of niet.\n" +" \n" +"Als patroon is gegeven, worden alleen overeenkomende\n" +"kanalen weergegeven. Als een nick is gegeven worden\n" +"alleen de kanalen waar de betreffende gebruiker aanwezig is\n" +"weergegeven. Als SECRET is gegeven worden alleen kanalen\n" +"weergegeven die met patroon overeenkomen en de +s\n" +"of +p kanaalmodus actief hebben." + +#: modules/commands/ns_alist.cpp:127 +msgid "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" +msgstr "" +"Geeft alle kanalen weer waar je toegangsrechten hebt.\n" +" \n" +"Kanalen die de NOEXPIRE optie hebben aan staan\n" +"zullen vooraan een uitroepteken hebben staan. Een nick\n" +"opgeven is voorbehouden aan Services Operators." + +#: modules/commands/ns_group.cpp:299 +msgid "Lists all nicknames in your group" +msgstr "Toon alle nicks in je groep" + +#: modules/commands/cs_list.cpp:20 +msgid "Lists all registered channels matching the given pattern" +msgstr "" +"Toon alle geregistreerde kanalen overeenstemmend met het gegeven patroon" + +#: modules/commands/cs_list.cpp:137 +msgid "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." +msgstr "" +"Geeft alle geregistreerde kanalen weer die overeenkomen\n" +"met het gegeven patroon. Kanalen met de PRIVATE optie\n" +"aan zullen enkel getoont worden aan Services Operators die er\n" +"de toegang voor hebben. Kanalen met de NOEXPIRE optie\n" +"aan zullen een ! voor de kanaalnaam hebben zodat\n" +"een Services Operator het ziet.\n" +" \n" +"Let op dat een '#' opgeven een bereik betekent, kanaalnamen\n" +"moeten zonder '#' opgegeven worden.\n" +" \n" +"Als de SUSPENDED of NOEXPIRE opties gegeven zijn, dan zullen\n" +"enkel de kanalen die respectievelijk de SUSPENDED of de NOEXPIRE status\n" +"hebben, getoont worden. Als meerdere opties gegeven zijn zullen\n" +"alle kanalen die met tenminste één optie overeenkomen getoont worden.\n" +"Let op dat deze opties beperkt zijn tot Services Operators.\n" +" \n" +"Voorbeelden:\n" +" \n" +" LIST *anope*\n" +" Toont alle geregistreerde kanalen waar anope in\n" +" voorkomt (hoofdletterongevoelig).\n" +" \n" +" LIST * NOEXPIRE\n" +" Toont alle geregistreerde kanalen die niet zullen verlopen.\n" +" \n" +" LIST #51-100\n" +" Toont alle geregistreerde kanalen binnen het\n" +" opgegeven bereik (51-100)." + +#: modules/commands/ns_list.cpp:139 +msgid "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." +msgstr "" +"Geeft alle geregistreerde nicks weer die overeenkomen\n" +"met het gegeven patroon, in nick!ident@host formaat.\n" +"Nicks met de PRIVATE optie aan worden alleen weergegeven\n" +"aan Services Operators die er de toegang voor hebben. Nicks met\n" +"de NOEXPIRE optie aan zullen een ! voor de nick hebben\n" +"zodat een Services Operator het ziet.\n" +" \n" +"Let op dat een '#' opgeven een bereik betekent.\n" +" \n" +"Als de SUSPENDED, UNCONFIRMED of NOEXPIRE opties gegeven zijn,\n" +"dan zullen enkel de nicks die respectievelijk de SUSPENDED, UNCONFIRMED\n" +"of de NOEXPIRE status hebben, getoont worden. Als meerdere opties\n" +"gegeven zijn zullen alle nicks die met tenminste één optie overeenkomen\n" +"getoont worden. Let op dat deze opties beperkt zijn tot Services Operators.\n" +" \n" +"Voorbeelden:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Toont alle geregistreerde nicks waar\n" +" joeuser@foo.com de eigenaar van is.\n" +" \n" +" LIST *Bot*!*@*\n" +" Toont alle geregistreerde nicks waar Bot in\n" +" voorkomt (hoofdletterongevoelig).\n" +" \n" +" LIST * NOEXPIRE\n" +" Toont alle geregistreerde nicks die niet zullen verlopen.\n" +" \n" +" LIST #51-100\n" +" Toont alle geregistreerde nicks binnen het\n" +" opgegeven bereik (51-100)." + +#: modules/commands/os_list.cpp:132 +msgid "Lists all user records" +msgstr "Geef alle gebruikers weer" + +#: modules/commands/os_list.cpp:243 +msgid "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only " +"users\n" +"with the +i flag will be listed." +msgstr "" +"Geeft alle gebruikers weer die momenteel online zijn op het\n" +"IRC netwerk, geregistreerd of niet.\n" +" \n" +"Als een patroon is gegeven worden alleen overeenkomende\n" +"gebruikers weergegeven (het moet in het nick!ident@host[#realname]\n" +"formaat gegeven worden). Als een kanaal is opgegeven worden\n" +"alleen gebruikers die op het betreffende kanaal zijn\n" +"weergegeven. Als INVISIBLE is gegeven worden alleen\n" +"gebruikers met gebruikersmodus +i weergegeven." + +#: modules/commands/ms_list.cpp:142 +msgid "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Geeft alle memo's die je hebt weer. Als je NEW opgeeft worden\n" +"alleen nieuwe (ongelezen) memo's weergegeven. Ongelezen memo's\n" +"worden gemarkeert met een \"*\" links van het memo nummer. Je kan\n" +"ook een lijst van nummers opgeven, zoals in het onderstaand voorbeeld:\n" +" LIST 2-5,7-9\n" +" Geeft de memo's genummerd 2 t/m 5 en 7 t/m 9 weer." + +#: modules/commands/bs_botlist.cpp:19 +msgid "Lists available bots" +msgstr "Geef beschikbare bots weer" + +#: modules/commands/os_modinfo.cpp:196 +msgid "Lists currently loaded modules." +msgstr "Geef geladen modules weer" + +#: modules/commands/cs_info.cpp:19 +msgid "Lists information about the specified registered channel" +msgstr "Toont informatie over het opgegeven geregistreerde kanaal" + +#: modules/commands/cs_info.cpp:76 +msgid "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." +msgstr "" +"Geeft informatie weer over het gegeven geregistreerde\n" +"kanaal, inclusief de stichter, registratietijd, tijd van\n" +"laatste gebruik, en beschrijving. Als de gebruiker die het\n" +"commando uitvoert de benodigde toegang er voor heeft,\n" +"dan zal de opvolger, de laatst ingestelde topic, de\n" +"instellingen, en de verlooptijd ook getoond worden\n" +"indien van toepassing." + +#: modules/commands/os_module.cpp:19 +msgid "Load a module" +msgstr "Laad een module" + +#: modules/commands/cs_register.cpp:39 +msgid "Local channels cannot be registered." +msgstr "Lokale kanalen kunnen niet geregistreerd worden." + +#: modules/commands/cs_log.cpp:142 +#, c-format +msgid "Log list for %s:" +msgstr "Loglijst voor %s:" + +#: modules/commands/cs_log.cpp:227 +#, c-format +msgid "Logging changed for command %s on %s, now using log method %s%s%s." +msgstr "" +"Logging gewijzigd voor commando %s op %s, maakt nu gebruik van logmethode %s" +"%s%s." + +#: modules/commands/cs_log.cpp:220 +#, c-format +msgid "Logging for command %s on %s with log method %s%s%s has been removed." +msgstr "Logging voor commando %s op %s met logmethode %s%s%s werd verwijderd." + +#: modules/commands/cs_log.cpp:248 +#, c-format +msgid "Logging is now active for command %s on %s, using log method %s%s%s." +msgstr "" +"Logging is nu actief voor commando %s op %s, gebruikmakend van logmethode %s" +"%s%s." + +#: modules/commands/os_login.cpp:60 +#, c-format +msgid "Login to %s" +msgstr "Meld aan bij %s" + +#: modules/commands/os_news.cpp:36 +#, c-format +msgid "Logon news item #%d deleted." +msgstr "Login nieuwsbericht #%d verwijderd." + +#: modules/commands/os_news.cpp:35 +#, c-format +msgid "Logon news item #%s not found!" +msgstr "Login nieuwsbericht #%s niet gevonden!" + +#: modules/commands/os_news.cpp:32 +msgid "Logon news items:" +msgstr "Login nieuwsberichten:" + +#: modules/commands/os_login.cpp:102 +#, c-format +msgid "Logout from %s" +msgstr "Meld af bij %s" + +#: modules/commands/os_login.cpp:52 +#, c-format +msgid "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." +msgstr "" +"Meld je aan bij %s zodat je je Services Operator privileges\n" +"krijgt. Dit commando kan overbodig zijn indien jouw operblok\n" +"zonder wachtwoord ingesteld is." + +#: modules/commands/os_login.cpp:94 +#, c-format +msgid "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." +msgstr "" +"Meld je af bij %s zodat je Services Operator privileges ontnomen\n" +"worden. Dit commando is enkel nuttig indien je operblok ingesteld\n" +"is met een wachtwoord." + +#: modules/commands/cs_seen.cpp:213 +#, c-format +msgid "Looking for yourself, eh %s?" +msgstr "Zoek je jezelf, %s?" + +#: modules/commands/cs_mode.cpp:773 +#, c-format +msgid "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a " +"channel.\n" +"If a mode is locked on or off, services will not allow that mode to be " +"changed. The SET\n" +"command will clear all existing mode locks and set the new one given, while " +"ADD and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * " +"and ? may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may " +"be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, " +"halfops, and voices. If what\n" +"is not given then all basic modes are removed." +msgstr "" +"Controleert voornamelijk de mode-vergrendelingen en mode-toegang (welke " +"verschillend\n" +"is van kanaaltoegang) op een kanaal.\n" +" \n" +"Het %s LOCK commando laat je toe mode-vergrendelingen toe te voegen, te\n" +"verwijderen, en te bekijken op een kanaal. Als een mode vergrendeld is dan " +"zal Services\n" +"wijzigingen van die mode niet toelaten. Het SET commando verwijdert alle " +"bestaande\n" +"mode-vergrendelingen, en stelt de gegeven modes in als de nieuwe " +"vergrendeling,\n" +"en ADD en DEL passen de bestaande vergrendelingen aan.\n" +"Voorbeeld:\n" +" MODE #kanaal LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"Het %s SET commando laat je toe modes te zetten via Services.\n" +"Jokertekens * en ? mogen gegeven worden als parameters voor lijst- en " +"statusmodes.\n" +"Voorbeeld:\n" +" MODE #kanaal SET +v *\n" +" Geeft voice status aan alle gebruikers op het kanaal.\n" +" \n" +" MODE #kanaal SET -b ~c:*\n" +" Verwijdert alle extended bans die beginnen met ~c:\n" +" \n" +"Het %s CLEAR commando is een gemakkelijke manier om modes te verwijderen op\n" +"een kanaal. wat kan eender welke mode-naam zijn. Voorbeelden zijn: bans,\n" +"excepts, inviteoverrides, ops, halfops, en voices. Als wat niet is gegeven, " +"dan\n" +"worden alle basismodes verwijderd." + +#: modules/commands/cs_akick.cpp:434 +msgid "Maintain the AutoKick list" +msgstr "Beheer de AutoKicklijst" + +#: modules/commands/bs_bot.cpp:269 +msgid "Maintains network bot list" +msgstr "Beheer de lijst met bots op het netwerk" + +#: modules/commands/cs_xop.cpp:522 +#, c-format +msgid "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " +msgstr "" +"Beheert de %s lijst voor een kanaal. Gebruikers die op\n" +"de %s lijst staan krijgen volgende privileges:\n" +" " + +#: modules/commands/cs_akick.cpp:493 +#, c-format +msgid "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" +msgstr "" +"Beheert de AutoKicklijst voor een kanaal. Als een gebruiker\n" +"op de lijst probeert binnen te komen, dan zal %s die gebruiker\n" +"bannen en vervolgens van het kanaal kicken.\n" +" \n" +"Het AKICK ADD commando voegt het gegeven nick of masker\n" +"toe aan de AutoKicklijst. Als reden is gegeven, dan zal die\n" +"gebruikt worden bij het kicken van de gebruiker; indien niet gegeven\n" +"zal de standaard reden gebruikt worden: \"Gebruiker werd verbannen\n" +"van het kanaal\".\n" +"Wanneer een geregistreerde nick is opgegeven dan zal het\n" +"%s account op de lijst worden gezet in plaats van het masker.\n" +"Alle gebruikers in die nickgroep zullen dan worden verbannen.\n" + +#: modules/commands/cs_access.cpp:568 +#, c-format +msgid "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." +msgstr "" +"Beheert de toegangslijst voor een kanaal. De toegangs-\n" +"lijst bepaalt welke gebruikers er kanaaloperator status mogen\n" +"hebben of toegang hebben tot bepaalde %s commando's op\n" +"het kanaal. Verschillende gebruikersniveaus bieden toegang\n" +"tot verschillende subsets van privileges. Elke geregistreerde\n" +"die niet op de toegangslijst staat heeft een niveau van 0, en\n" +"elke ongeregistreerde gebruiker heeft een niveau van -1." + +#: modules/commands/bs_badwords.cpp:424 +#, c-format +msgid "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" +msgstr "" +"Beheert de slechtewoordenlijst voor een kanaal. De\n" +"slechtewoordenlijst bepaalt voor welke woorden wordt\n" +"gekickt als de slechtewoordenkicker aan staat. Voor\n" +"meer informatie, typ %s%s HELP KICK %s.\n" +" \n" +"Het ADD commando voegt het gegeven woord toe aan\n" +"de slechtewoordenlijst. Als SINGLE is opgegeven zal\n" +"alleen worden gekickt als de gebruiker het gehele woord zegt.\n" +"Als START is opgegeven zal er gekickt worden als de gebruiker\n" +"een woord zegt dat begint met woord. Als END is\n" +"opgegeven zal er alleen gekickt worden als de gebruiker\n" +"een woord zegt dat eindigt op woord. Als er niets\n" +"opgegeven is zal er elke keer dat woord gezegd wordt\n" +"door een gebruiker, gekickt worden.\n" +" \n" + +#: modules/commands/bs_badwords.cpp:370 +msgid "Maintains the bad words list" +msgstr "Beheer de slechtewoordenlijst" + +#: modules/commands/bs_control.cpp:79 +msgid "Makes the bot do the equivalent of a \"/me\" command" +msgstr "Laat de bot het equivalent van het \"/me\" commando doen" + +#: modules/commands/bs_control.cpp:127 +msgid "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." +msgstr "" +"Laat de bot het equivalent van het \"/me\" commando doen\n" +"op het gegeven kanaal met de gegeven tekst." + +#: modules/commands/bs_control.cpp:19 +msgid "Makes the bot say the specified text on the specified channel" +msgstr "Laat de bot een gegeven bericht zeggen op het gegeven kanaal" + +#: modules/commands/bs_control.cpp:69 +msgid "Makes the bot say the specified text on the specified channel." +msgstr "Laat de bot een gegeven bericht zeggen op het gegeven kanaal." + +#: modules/commands/greet.cpp:157 +msgid "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." +msgstr "" +"Maakt van het gegeven bericht de begroeting van de nick,\n" +"die zal getoond worden bij het betreden van een kanaal\n" +"waar de GREET optie aan staat, en als de gebruiker daarop\n" +"voldoende toegang toe heeft." + +#: modules/commands/greet.cpp:131 +msgid "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." +msgstr "" +"Maakt van het gegeven bericht de begroeting van jouw nick,\n" +"die zal getoond worden bij het betreden van een kanaal\n" +"waar de GREET optie aan staat, en als je daarop voldoende\n" +"toegang tot hebt." + +#: modules/commands/os_dns.cpp:660 +msgid "Manage DNS zones for this network" +msgstr "Beheer DNS domeinnamen voor dit netwerk" + +#: modules/commands/cs_entrymsg.cpp:193 +msgid "Manage the channel's entry messages" +msgstr "Beheer de welkomstberichten van het kanaal" + +#: modules/commands/ms_ignore.cpp:19 +msgid "Manage the memo ignore list" +msgstr "Beheer de memo-negeerlijst" + +#: modules/commands/ns_ajoin.cpp:230 +msgid "Manage your auto join list" +msgstr "Beheer je autojoinlijst" + +#: modules/commands/os_sxline.cpp:233 +#, c-format +msgid "Manipulate the %s list" +msgstr "Beheer de %s lijst" + +#: modules/commands/os_akill.cpp:385 +msgid "Manipulate the AKILL list" +msgstr "Beheer de AKILL lijst" + +#: modules/commands/os_defcon.cpp:176 +msgid "Manipulate the DefCon system" +msgstr "Beheer het DefCon systeem" + +#: modules/commands/cs_topic.cpp:149 +msgid "Manipulate the topic of the specified channel" +msgstr "Pas de topic van het gegeven kanaal aan" + +#: modules/commands/bs_botlist.cpp:27 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_forbid.cpp:358 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/ms_ignore.cpp:86 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_list.cpp:153 modules/commands/bs_info.cpp:55 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +msgid "Mask" +msgstr "Masker" + +#: modules/commands/ns_access.cpp:39 +#, c-format +msgid "Mask %s already present on %s's access list." +msgstr "Masker %s bestaat al op %s's toegangslijst." + +#: include/language.h:67 +msgid "Mask must be in the form user@host." +msgstr "Masker moet in het ident@host formaat zijn." + +#: modules/commands/cs_access.cpp:166 modules/commands/cs_flags.cpp:120 +#: modules/commands/cs_xop.cpp:162 +msgid "Masks and unregistered users may not be on access lists." +msgstr "" +"Maskers en ongeregistreerde gebruikers mogen niet op toegangslijsten staan." + +#: modules/commands/ns_getemail.cpp:23 +msgid "Matches and returns all users that registered using given email" +msgstr "Geeft alle met het gegeven e-mail geregistreerde gebruikers weer" + +#: modules/commands/os_logsearch.cpp:148 +#, c-format +msgid "Matches for %s:" +msgstr "Overeenkomsten voor %s:" + +#: modules/commands/os_stats.cpp:139 +#, c-format +msgid "Maximum users: %d (%s)" +msgstr "Maximum gebruikers: %d (%s)" + +#: modules/commands/ms_read.cpp:84 modules/commands/ms_read.cpp:86 +#, c-format +msgid "Memo %d from %s (%s)." +msgstr "Memo %d van %s (%s)." + +#: modules/commands/ms_del.cpp:33 modules/commands/ms_del.cpp:101 +#, c-format +msgid "Memo %d has been deleted." +msgstr "Memo %d werd verwijderd." + +#: modules/commands/ms_ignore.cpp:82 +msgid "Memo ignore list is empty." +msgstr "Memo-negeerlijst is leeg." + +#: modules/commands/ms_set.cpp:199 +#, c-format +msgid "Memo limit disabled for %s." +msgstr "Memolimiet voor %s uitgeschakeld." + +#: modules/commands/ms_set.cpp:185 +#, c-format +msgid "Memo limit for %s set to %d." +msgstr "Memolimiet voor %s veranderd naar %d." + +#: modules/commands/ms_set.cpp:192 +#, c-format +msgid "Memo limit for %s set to 0." +msgstr "Memolimiet voor %s veranderd naar 0." + +#: modules/commands/ms_rsend.cpp:63 modules/commands/ms_send.cpp:51 +#, c-format +msgid "Memo sent to %s." +msgstr "Memo verstuurd naar %s." + +#: modules/commands/ms_list.cpp:131 +#, c-format +msgid "Memos for %s:" +msgstr "Memo's voor %s:" + +#: modules/commands/cs_entrymsg.cpp:116 +msgid "Message" +msgstr "Bericht" + +#: modules/commands/ns_set.cpp:1313 +msgid "Message mode" +msgstr "Berichtenmodus" + +#: modules/commands/cs_log.cpp:127 +msgid "Method" +msgstr "Methode" + +#: modules/commands/cs_mode.cpp:329 modules/commands/cs_mode.cpp:420 +#, c-format +msgid "Missing parameter for mode %c." +msgstr "Ontbrekende parameter voor mode %c." + +#: modules/commands/cs_mode.cpp:449 +msgid "Mode" +msgstr "Mode" + +#: modules/commands/cs_mode.cpp:718 +#, c-format +msgid "Mode %s is a virtual mode and can't be cleared." +msgstr "Modus %s is een virtuele modus en kan niet verwijderd worden." + +#: modules/commands/cs_mode.cpp:712 +#, c-format +msgid "Mode %s is not a status or list mode." +msgstr "Mode %s is geen status- of lijst-mode." + +#: modules/commands/cs_mode.cpp:1065 +msgid "Mode lock" +msgstr "Mode-vergrendeling" + +#: modules/commands/cs_mode.cpp:466 +#, c-format +msgid "Mode locks for %s:" +msgstr "Mode-vergrendelingen voor %s:" + +#: modules/commands/os_list.cpp:43 +msgid "Modes" +msgstr "Modes" + +#: modules/commands/os_mode.cpp:44 +#, c-format +msgid "Modes cleared on %s and the channel destroyed." +msgstr "Modes verwijderd op %s en het kanaal vernietigd." + +#: modules/commands/ns_access.cpp:166 +#, c-format +msgid "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." +msgstr "" +"Verandert of geeft de toegangslijst weer van je nick. Dit is\n" +"de lijst met adressen vanaf waar je automatisch toegestaan\n" +"wordt door %s om de nick te gebruiken. Als je je nick vanaf\n" +"een ander adres wilt gebruiken moet je een IDENTIFY commando\n" +"sturen om %s je te laten herkennen. Services Operators kunnen\n" +"ook een nick opgeven om anderen hun toegangslijst aan te passen.\n" +" \n" +"Voorbeelden:\n" +" \n" +" ACCESS ADD iemand@*.bepeg.com\n" +" Staat toegang toe voor gebruiker iemand vanaf elke machine\n" +" in het bepeg.com domein.\n" +" \n" +" ACCESS DEL iemand@*.bepeg.com\n" +" Maakt het vorige commando ongedaan.\n" +" \n" +" ACCESS LIST\n" +" Geeft de huidige toegangslijst weer." + +#: modules/commands/ns_cert.cpp:319 +msgid "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" +msgstr "" +"Wijzigt of toont de lijst met certificaten voor jouw nick.\n" +"Als u verbinding maakt met een certificaat waarvan de\n" +"vingerafdruk overeenstemt met een vermelding op de\n" +"lijst, dan zal je automatisch geïdentificeert worden.\n" +"Services Operators kunnen ook een nick opgeven om\n" +"anderen hun certificaatlijst aan te passen.\n" +" \n" + +#: modules/commands/os_ignore.cpp:341 +msgid "Modify the Services ignore list" +msgstr "Wijzig de Services negeerlijst" + +#: modules/commands/cs_xop.cpp:489 +#, c-format +msgid "Modify the list of %s users" +msgstr "Wijzig de lijst van %s's" + +#: modules/commands/ns_access.cpp:101 +msgid "Modify the list of authorized addresses" +msgstr "Wijzig de lijst met toegestane adressen" + +#: modules/commands/cs_access.cpp:498 modules/commands/cs_flags.cpp:373 +msgid "Modify the list of privileged users" +msgstr "Wijzig de lijst van gebruikers met privileges" + +#: modules/commands/ns_cert.cpp:257 +msgid "Modify the nickname client certificate list" +msgstr "Wijzig de certificaatlijst" + +#: modules/commands/os_session.cpp:522 +msgid "Modify the session-limit exception list" +msgstr "Wijzig de uitzonderingenlijst voor sessielimieten" + +#: modules/commands/os_module.cpp:34 +#, c-format +msgid "Module %s is already loaded." +msgstr "Module %s is reeds geladen." + +#: modules/commands/os_module.cpp:67 modules/commands/os_module.cpp:139 +#, c-format +msgid "Module %s isn't loaded." +msgstr "Module %s is niet geladen." + +#: modules/commands/os_module.cpp:31 +#, c-format +msgid "Module %s loaded." +msgstr "Module %s geladen." + +#: modules/commands/os_module.cpp:98 +#, c-format +msgid "Module %s reloaded." +msgstr "Module %s herladen." + +#: modules/commands/os_module.cpp:156 +#, c-format +msgid "Module %s unloaded." +msgstr "Module %s ontladen." + +#: modules/commands/os_config.cpp:88 +msgid "Module Name" +msgstr "Modulenaam" + +#: modules/commands/os_config.cpp:112 +msgid "Module settings:" +msgstr "Module-instellingen:" + +#: modules/commands/os_modinfo.cpp:32 +#, c-format +msgid "Module: %s Version: %s Author: %s Loaded: %s" +msgstr "Module: %s Versie: %s Auteur: %s Geladen: %s" + +#: modules/commands/os_modinfo.cpp:183 +#, c-format +msgid "Module: %s [%s] [%s]" +msgstr "Module: %s [%s] [%s]" + +#: modules/commands/cs_access.cpp:697 modules/commands/cs_access.cpp:799 +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +#: modules/commands/cs_list.cpp:75 modules/commands/os_list.cpp:43 +#: modules/commands/os_list.cpp:153 +msgid "Name" +msgstr "Naam" + +#: modules/commands/os_oper.cpp:153 +msgid "Name Type" +msgstr "Naam Type" + +#: modules/extra/stats/cs_fantasy_stats.cpp:146 +#, c-format +msgid "Network stats for %s:" +msgstr "Netwerkstatistieken voor %s:" + +#: modules/commands/os_forbid.cpp:384 +msgid "Never" +msgstr "Nooit" + +#: modules/commands/hs_list.cpp:58 modules/commands/bs_botlist.cpp:27 +#: modules/commands/hs_request.cpp:305 modules/commands/ns_list.cpp:75 +#: modules/commands/ns_group.cpp:327 +msgid "Nick" +msgstr "Nick" + +#: modules/commands/ns_register.cpp:42 +#, c-format +msgid "Nick %s has been confirmed." +msgstr "Nick %s werd bevestigd." + +#: modules/commands/os_oper.cpp:95 +#, c-format +msgid "Nick %s is already an operator." +msgstr "Nick %s is reeds een operator." + +#: modules/commands/ns_register.cpp:36 +#, c-format +msgid "Nick %s is already confirmed." +msgstr "Nick %s is reeds bevestigd." + +#: modules/commands/os_svs.cpp:46 +#, c-format +msgid "Nick %s is an illegal nickname and cannot be used." +msgstr "Nick %s is een illegale nick en mag niet worden gebruikt." + +#: modules/commands/bs_bot.cpp:81 modules/commands/bs_bot.cpp:181 +#: modules/commands/os_svs.cpp:54 +#, c-format +msgid "Nick %s is currently in use." +msgstr "Nick %s is momenteel in gebruik." + +#: modules/commands/os_forbid.cpp:512 +#, c-format +msgid "Nick %s is forbidden by %s: %s" +msgstr "Nick %s is verboden door %s: %s" + +#: modules/commands/os_forbid.cpp:514 +#, c-format +msgid "Nick %s is forbidden." +msgstr "Nick %s is verboden." + +#: modules/commands/os_oper.cpp:134 +#, c-format +msgid "Nick %s is not a Services Operator." +msgstr "Nick %s is geen Services Operator." + +#: modules/commands/ns_info.cpp:34 +#, c-format +msgid "Nick %s is part of this Network's Services." +msgstr "Nick %s is deel van de Services van dit netwerk." + +#: include/language.h:79 +#, c-format +msgid "Nick %s isn't currently in use." +msgstr "Nick %s is momenteel niet in gebruik." + +#: include/language.h:78 +#, c-format +msgid "Nick %s isn't registered." +msgstr "Nick %s is niet geregistreerd." + +#: modules/commands/os_svs.cpp:39 +#, c-format +msgid "Nick %s was truncated to %d characters." +msgstr "Nick %s werd verkort naar %d tekens." + +#: modules/commands/ns_set.cpp:1135 +#, c-format +msgid "Nick %s will expire." +msgstr "Nick %s zal verlopen." + +#: modules/commands/ns_set.cpp:1129 +#, c-format +msgid "Nick %s will not expire." +msgstr "Nick %s zal niet verlopen." + +#: modules/commands/ms_check.cpp:60 +#, c-format +msgid "Nick %s doesn't have a memo from you." +msgstr "Nick %s heeft geen memo van jou." + +#: modules/commands/ns_logout.cpp:48 +#, c-format +msgid "Nick %s has been logged out." +msgstr "Nick %s werd uitgelogd." + +#: modules/commands/ns_group.cpp:272 +#, c-format +msgid "Nick %s has been ungrouped from %s." +msgstr "Nick %s werd uit groep %s gehaald." + +#: include/language.h:81 +#, c-format +msgid "Nick %s is currently suspended." +msgstr "Nick %s is momenteel geschorst." + +#: modules/commands/ns_group.cpp:250 +#, c-format +msgid "Nick %s is not in your group." +msgstr "Nick %s is niet in je groep." + +#: modules/commands/ns_suspend.cpp:180 +#, c-format +msgid "Nick %s is not suspended." +msgstr "Nick %s is niet geschorst." + +#: modules/commands/ns_suspend.cpp:190 +#, c-format +msgid "Nick %s is now released." +msgstr "Nick %s is nu vrijgegeven." + +#: modules/commands/ns_suspend.cpp:138 +#, c-format +msgid "Nick %s is now suspended." +msgstr "Nick %s is nu geschorst." + +#: modules/commands/cs_seen.cpp:275 +#, c-format +msgid "Nick too long, max length is %u characters." +msgstr "Nick te lang, maximum lengte is %u karakters." + +#: modules/commands/ns_drop.cpp:53 +#, c-format +msgid "Nickname %s has been dropped." +msgstr "Nickregistratie voor %s werd verwijderd." + +#: include/language.h:97 +#, c-format +msgid "Nickname %s is already registered!" +msgstr "Nick %s is al geregistreerd!" + +#: include/language.h:96 +#, c-format +msgid "Nickname %s may not be registered." +msgstr "Nick %s mag niet geregistreerd worden." + +#: modules/commands/ns_register.cpp:226 +#, c-format +msgid "Nickname %s registered under your user@host-mask: %s" +msgstr "Nick %s is geregistreerd onder jouw gebruikersmasker: %s" + +#: modules/commands/ns_register.cpp:228 +#, c-format +msgid "Nickname %s registered." +msgstr "Nick %s is geregistreerd." + +#: modules/commands/cs_set.cpp:1307 +msgid "No auto-op" +msgstr "Geen auto-op" + +#: modules/commands/bs_assign.cpp:252 +msgid "No bot" +msgstr "Geen bot" + +#: modules/commands/cs_set.cpp:1303 modules/commands/ns_set.cpp:1317 +msgid "No expire" +msgstr "Verloopt niet" + +#: modules/commands/help.cpp:184 +#, c-format +msgid "No help available for %s." +msgstr "Geen help beschikbaar voor %s." + +#: modules/commands/os_modinfo.cpp:61 +#, c-format +msgid "No information about module %s is available." +msgstr "Er is geen informatie aanwezig over module %s." + +#: modules/commands/cs_enforce.cpp:177 +#, c-format +msgid "No limit is set on %s." +msgstr "Er is geen limiet ingesteld op %s." + +#: modules/commands/os_news.cpp:37 +msgid "No logon news items to delete!" +msgstr "Geen login nieuwsberichten om te verwijderen!" + +#: modules/commands/os_logsearch.cpp:133 +#, c-format +msgid "No matches for %s found." +msgstr "Geen overeenkomsten voor %s gevonden." + +#: modules/commands/cs_xop.cpp:294 +#, c-format +msgid "No matching entries on %s %s list." +msgstr "Geen overeenkomsten op %s %s lijst." + +#: modules/commands/cs_access.cpp:269 modules/commands/cs_access.cpp:433 +#: modules/commands/cs_flags.cpp:335 modules/commands/cs_xop.cpp:428 +#, c-format +msgid "No matching entries on %s access list." +msgstr "Geen overeenkomsten op %s toegangslijst." + +#: modules/commands/cs_akick.cpp:224 modules/commands/cs_akick.cpp:368 +#, c-format +msgid "No matching entries on %s autokick list." +msgstr "Geen overeenkomsten op %s autokicklijst." + +#: modules/commands/bs_badwords.cpp:166 modules/commands/bs_badwords.cpp:246 +#, c-format +msgid "No matching entries on %s bad words list." +msgstr "Geen overeenkomsten op %s slechtewoordenlijst." + +#: modules/commands/os_session.cpp:145 modules/commands/os_session.cpp:490 +msgid "No matching entries on session-limit exception list." +msgstr "Geen overeenkomsten op de uitzonderingenlijst voor sessielimieten." + +#: modules/commands/os_sxline.cpp:28 modules/commands/os_sxline.cpp:177 +#, c-format +msgid "No matching entries on the %s list." +msgstr "Geen overeenkomsten op de %s lijst." + +#: modules/commands/os_akill.cpp:29 modules/commands/os_akill.cpp:320 +msgid "No matching entries on the AKILL list." +msgstr "Geen overeenkomsten op de AKILL lijst." + +#: modules/commands/ms_cancel.cpp:77 +msgid "No memo was cancelable." +msgstr "Geen annuleerbare memo's gevonden." + +#: modules/commands/ms_read.cpp:65 +msgid "No memos to display." +msgstr "Geen memo's om weer te geven." + +#: modules/commands/os_modinfo.cpp:187 +msgid "No modules currently loaded matching that criteria." +msgstr "Geen modules geladen die overeenkomen met die criteria." + +#: modules/commands/ns_recover.cpp:55 +msgid "No one is using your nick, and services are not holding it." +msgstr "" +"Er is niemand die je nick gebruikt, en Services blokkeert het ook niet." + +#: modules/commands/os_login.cpp:30 modules/commands/os_login.cpp:77 +msgid "No oper block for your nick." +msgstr "Geen operblok voor jouw nick." + +#: modules/commands/os_news.cpp:47 +msgid "No oper news items to delete!" +msgstr "Geen operator nieuwsberichten om te verwijderen!" + +#: modules/commands/os_news.cpp:57 +msgid "No random news items to delete!" +msgstr "Geen willekeurige nieuwsberichten om te verwijderen!" + +#: modules/commands/hs_list.cpp:111 +msgid "No records to display." +msgstr "Geen resultaten om weer te geven." + +#: modules/commands/ns_getemail.cpp:47 +#, c-format +msgid "No registrations matching %s were found." +msgstr "Geen nicknameregistraties overeenkomend met %s gevonden." + +#: modules/commands/hs_request.cpp:220 modules/commands/hs_request.cpp:276 +#, c-format +msgid "No request for nick %s found." +msgstr "Geen aanvraag voor nick %s gevonden." + +#: src/access.cpp:55 +msgid "No signed kick when SIGNKICK LEVEL is used" +msgstr "Geen ondertekende kicks wanneer SIGNKICK LEVEL gebruikt word" + +#: modules/extra/stats/cs_fantasy_top.cpp:159 +#: modules/extra/stats/cs_fantasy_stats.cpp:156 +#, c-format +msgid "No stats for %s." +msgstr "Geen statistieken voor %s." + +#: modules/commands/os_info.cpp:201 +#, c-format +msgid "No such info \"%s\" on %s." +msgstr "Geen zulke info \"%s\" over %s." + +#: modules/commands/cs_ban.cpp:219 modules/commands/cs_kick.cpp:118 +#, c-format +msgid "No users on %s match %s." +msgstr "Geen gebruikers op %s die overeenkomen met %s." + +#: modules/commands/bs_assign.cpp:188 +#, c-format +msgid "No-bot mode is now off on channel %s." +msgstr "Geen-botmodus staat nu uit op kanaal %s." + +#: modules/commands/bs_assign.cpp:181 +#, c-format +msgid "No-bot mode is now on on channel %s." +msgstr "Geen-botmodus staat nu aan op kanaal %s." + +#: modules/commands/os_mode.cpp:64 +#, c-format +msgid "Non-status modes cleared on %s." +msgstr "Niet-statusmodes weggehaald op %s." + +#: modules/commands/os_dns.cpp:226 modules/commands/bs_info.cpp:58 +msgid "None" +msgstr "Geen" + +#: modules/commands/cs_set.cpp:1029 +#, c-format +msgid "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." +msgstr "" +"Merk op dat als de opvolger al teveel geregistreerde\n" +"kanalen heeft (%d), dat die niet de nieuwe opvolger\n" +"zal kunnen worden en het dan zal zijn net alsof het\n" +"kanaal geen opvolger ingesteld heeft staan." + +#: modules/commands/cs_mode.cpp:380 modules/commands/cs_mode.cpp:437 +msgid "Nothing to do." +msgstr "Niets te doen." + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:201 modules/commands/ms_list.cpp:64 +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_log.cpp:127 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +#: modules/commands/ns_ajoin.cpp:100 +msgid "Number" +msgstr "Nummer" + +#: modules/commands/os_news.cpp:41 +msgid "OPERNEWS {ADD|DEL|LIST} [text|num]" +msgstr "OPERNEWS {ADD|DEL|LIST} [text|nr]" + +#: modules/commands/ns_info.cpp:68 modules/commands/ns_info.cpp:72 +msgid "Online from" +msgstr "Is online vanaf" + +#: modules/commands/os_oper.cpp:138 +#, c-format +msgid "" +"Oper %s is configured in the configuration file(s) and can not be removed by " +"this command." +msgstr "" +"Oper %s is ingesteld in de configuratiebestanden en kan niet worden " +"verwijderd met dit commando." + +#: modules/commands/os_info.cpp:268 +msgid "Oper Info" +msgstr "Oper info" + +#: modules/commands/os_info.cpp:182 modules/commands/os_info.cpp:221 +#, c-format +msgid "Oper info list for %s is empty." +msgstr "Operator infolijst voor %s is leeg." + +#: modules/commands/os_news.cpp:46 +#, c-format +msgid "Oper news item #%d deleted." +msgstr "Operator nieuwsbericht #%d verwijderd." + +#: modules/commands/os_news.cpp:45 +#, c-format +msgid "Oper news item #%s not found!" +msgstr "Operator nieuwsbericht #%s niet gevonden!" + +#: modules/commands/os_news.cpp:42 +msgid "Oper news items:" +msgstr "Operator nieuwsberichten:" + +#: modules/commands/os_oper.cpp:148 +#, c-format +msgid "Oper privileges removed from %s (%s)." +msgstr "Operator privileges ontnomen van %s (%s)." + +#: modules/commands/os_oper.cpp:101 modules/commands/os_oper.cpp:189 +#, c-format +msgid "Oper type %s has not been configured." +msgstr "Opertype %s werd niet ingesteld." + +#: modules/commands/os_oline.cpp:37 +#, c-format +msgid "Operflags %s have been added for %s." +msgstr "Opervlaggen %s zijn toegevoegd voor %s." + +#: modules/commands/os_oline.cpp:43 +#, c-format +msgid "Operflags %s have been removed from %s." +msgstr "Opervlaggen %s zijn verwijderd van %s." + +#: modules/commands/os_oper.cpp:193 +#, c-format +msgid "Opertype %s has no allowed commands." +msgstr "Opertype %s heeft geen toegestane commando's." + +#: modules/commands/os_oper.cpp:215 +#, c-format +msgid "Opertype %s has no allowed privileges." +msgstr "Opertype %s heeft geen toegestane privileges." + +#: modules/commands/os_oper.cpp:237 +#, c-format +msgid "Opertype %s receives modes %s once identified." +msgstr "Opertype %s ontvangt modes %s eens geïdentificeerd." + +#: modules/commands/bs_kick.cpp:1219 +msgid "Ops protection" +msgstr "Ops bescherming" + +#: src/misc.cpp:258 modules/commands/bs_info.cpp:58 +msgid "Options" +msgstr "Opties" + +#: modules/commands/os_dns.cpp:668 +msgid "POOL server.name" +msgstr "POOL server.naam" + +#: modules/commands/cs_mode.cpp:449 +msgid "Param" +msgstr "Param" + +#: modules/commands/ns_identify.cpp:38 +msgid "Password accepted - you are now recognized." +msgstr "Wachtwoord aanvaard - je wordt nu herkend." + +#: modules/commands/os_login.cpp:44 +msgid "Password accepted." +msgstr "Wachtwoord aanvaard." + +#: include/language.h:85 +msgid "Password authentication required for that command." +msgstr "Wachtwoord authenticatie vereist voor dat commando." + +#: modules/commands/ns_set.cpp:152 modules/commands/ns_set.cpp:218 +#, c-format +msgid "Password for %s changed to %s." +msgstr "Wachtwoord voor %s gewijzigd naar %s." + +#: modules/commands/ns_set.cpp:154 modules/commands/ns_set.cpp:220 +#, c-format +msgid "Password for %s changed." +msgstr "Wachtwoord voor %s gewijzigd." + +#: modules/commands/ns_getpass.cpp:38 +#, c-format +msgid "Password for %s is %s." +msgstr "Wachtwoord voor %s is %s." + +#: include/language.h:71 +msgid "Password incorrect." +msgstr "Fout wachtwoord." + +#: modules/commands/ns_resetpass.cpp:39 +#, c-format +msgid "Password reset email for %s has been sent." +msgstr "Wachtwoord reset e-mail voor %s werd verstuurd." + +#: modules/commands/cs_set.cpp:1289 +msgid "Peace" +msgstr "Vrede" + +#: modules/commands/cs_set.cpp:440 +#, c-format +msgid "Peace option for %s is now off." +msgstr "Vrede-optie voor %s is nu uit." + +#: modules/commands/cs_set.cpp:434 +#, c-format +msgid "Peace option for %s is now on." +msgstr "Vrede-optie voor %s is nu aan." + +#: modules/commands/cs_set.cpp:1301 +msgid "Persistent" +msgstr "Permanent" + +#: include/language.h:126 +msgid "Please contact an Operator to get a vHost assigned to this nick." +msgstr "" +"Gelieve een Operator te contacteren om een vHost aan je nick toegewezen te " +"krijgen." + +#: include/language.h:73 +msgid "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." +msgstr "" +"Gelieve opnieuw te proberen met een moeilijker wachtwoord. Wachtwoorden\n" +"moeten tenminste 5 karakters lang zijn, iets dat niet makkelijk geraden kan\n" +"worden (zoals bijvoorbeeld je echte naam of nick), en kan geen spaties of " +"tab-\n" +"karakters bevatten." + +#: modules/commands/os_jupe.cpp:30 +msgid "Please use a valid server name when juping." +msgstr "Gelieve een geldige servernaam te gebruiken bij het blokkeren." + +#: include/language.h:104 +msgid "Please use the symbol of # when attempting to register." +msgstr "Gelieve het #-symbool te gebruiken bij het registreren." + +#: src/mail.cpp:78 +#, c-format +msgid "Please wait %d seconds and retry." +msgstr "Gelieve %d seconden te wachten en opnieuw te proberen." + +#: modules/commands/hs_request.cpp:158 +#, c-format +msgid "Please wait %d seconds before requesting a new vHost." +msgstr "" +"Gelieve %d seconden te wachten alvorens een nieuwe vHost aan te vragen." + +#: modules/commands/ms_rsend.cpp:58 modules/commands/ms_send.cpp:57 +#, c-format +msgid "Please wait %d seconds before using the %s command again." +msgstr "" +"Gelieve %d seconden te wachten alvorens het %s commando opnieuw te gebruiken." + +#: modules/commands/ns_group.cpp:149 +#, c-format +msgid "Please wait %d seconds before using the GROUP command again." +msgstr "" +"Gelieve %d seconden te wachten alvorens het GROUP commando opnieuw te " +"gebruiken." + +#: modules/commands/ns_register.cpp:198 +#, c-format +msgid "Please wait %d seconds before using the REGISTER command again." +msgstr "" +"Gelieve %d seconden te wachten alvorens het REGISTER commando opnieuw te " +"gebruiken." + +#: modules/commands/os_dns.cpp:628 +#, c-format +msgid "Pooled %s." +msgstr "Pooled %s." + +#: modules/commands/os_dns.cpp:237 +msgid "Pooled/Active" +msgstr "Pooled/Actief" + +#: modules/commands/os_dns.cpp:239 +msgid "Pooled/Not Active" +msgstr "Pooled/Niet actief" + +#: modules/commands/bs_set.cpp:161 +msgid "Prevent a bot from being assigned by non IRC operators" +msgstr "Voorkom dat een bot toegewezen word door niet-IRC operators" + +#: modules/commands/bs_assign.cpp:153 +msgid "Prevent a bot from being assigned to a channel" +msgstr "Voorkom dat een bot toegewezen word aan een kanaal" + +#: modules/commands/cs_suspend.cpp:58 +msgid "Prevent a channel from being used preserving channel data and settings" +msgstr "" +"Voorkom gebruik van een kanaal terwijl de data en instellingen ervan toch " +"behouden blijven" + +#: modules/commands/cs_set.cpp:1043 +msgid "Prevent the channel from expiring" +msgstr "Voorkom dat het kanaal verloopt" + +#: modules/commands/ns_list.cpp:186 +msgid "Prevent the nickname from appearing in the LIST command" +msgstr "Voorkom dat de nick in het LIST commando verschijnt" + +#: modules/commands/ns_set.cpp:1104 +msgid "Prevent the nickname from expiring" +msgstr "Voorkom dat de nick verloopt" + +#: src/access.cpp:46 +msgid "Prevents users being kicked by Services" +msgstr "Voorkomt dat gebruikers gekickt worden door Services" + +#: modules/commands/ns_list.cpp:297 modules/commands/cs_list.cpp:262 +#: modules/commands/bs_info.cpp:58 +msgid "Private" +msgstr "Privé" + +#: modules/commands/bs_set.cpp:190 +#, c-format +msgid "Private mode of bot %s is now off." +msgstr "Privémodus van bot %s staat nu uit." + +#: modules/commands/bs_set.cpp:185 +#, c-format +msgid "Private mode of bot %s is now on." +msgstr "Privémodus van bot %s staat nu aan." + +#: modules/commands/cs_list.cpp:220 +#, c-format +msgid "Private option for %s is now off." +msgstr "Privé-optie voor %s staat nu uit." + +#: modules/commands/cs_list.cpp:214 +#, c-format +msgid "Private option for %s is now on." +msgstr "Privé-optie voor %s staat nu aan." + +#: modules/commands/ns_list.cpp:221 +#, c-format +msgid "Private option is now off for %s." +msgstr "Privé-optie voor %s staat nu uit." + +#: modules/commands/ns_list.cpp:215 +#, c-format +msgid "Private option is now on for %s." +msgstr "Privé-optie voor %s staat nu aan." + +#: modules/commands/cs_flags.cpp:281 +#, c-format +msgid "Privilege %s added to %s on %s, new flags are +%s" +msgstr "Privilege %s toegevoegd bij %s op %s, nieuwe vlaggen zijn +%s" + +#: modules/commands/cs_flags.cpp:283 +#, c-format +msgid "Privilege %s removed from %s on %s, new flags are +%s" +msgstr "Privilege %s verwijderd van %s op %s, nieuwe vlaggen zijn +%s" + +#: modules/commands/ns_set.cpp:1309 +msgid "Protection" +msgstr "Bescherming" + +#: modules/commands/ns_set.cpp:721 +#, c-format +msgid "Protection is now off for %s." +msgstr "Bescherming is nu uit voor %s." + +#: modules/commands/ns_set.cpp:700 +#, c-format +msgid "Protection is now on for %s, with a reduced delay." +msgstr "Bescherming is nu aan voor %s, met een kortere vertraging." + +#: modules/commands/ns_set.cpp:710 +#, c-format +msgid "Protection is now on for %s, with no delay." +msgstr "Bescherming is nu aan voor %s, zonder vertraging." + +#: modules/commands/ns_set.cpp:692 +#, c-format +msgid "Protection is now on for %s." +msgstr "Bescherming is nu aan voor %s." + +#: modules/commands/os_chankill.cpp:100 +msgid "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." +msgstr "" +"Plaatst een AKILL voor elke nick op het gegeven kanaal. Het\n" +"gebruikt de volledige echte ident@host voor elke nick,\n" +"en dwingt dan de AKILL af." + +#: modules/commands/ns_set.cpp:1307 +msgid "Quick protection" +msgstr "Snelle bescherming" + +#: modules/commands/os_news.cpp:51 +msgid "RANDOMNEWS {ADD|DEL|LIST} [text|num]" +msgstr "RANDOMNEWS {ADD|DEL|LIST} [tekst|nr]" + +#: modules/commands/cs_enforce.cpp:99 +msgid "REGONLY enforced by " +msgstr "REGONLY afgedwongen door " + +#: modules/commands/cs_enforce.cpp:68 +msgid "RESTRICTED enforced by " +msgstr "RESTRICTED afgedwongen door " + +#: modules/commands/os_noop.cpp:21 +msgid "REVOKE server" +msgstr "REVOKE server" + +#: modules/commands/os_news.cpp:56 +#, c-format +msgid "Random news item #%d deleted." +msgstr "Willekeurig nieuwsbericht #%d verwijderd." + +#: modules/commands/os_news.cpp:55 +#, c-format +msgid "Random news item #%s not found!" +msgstr "Willekeurig nieuwsbericht #%s niet gevonden!" + +#: modules/commands/os_news.cpp:52 +msgid "Random news items:" +msgstr "Willekeurige nieuwsberichten:" + +#: modules/commands/ms_read.cpp:112 +msgid "Read a memo or memos" +msgstr "Lees een of meerdere memo's" + +#: modules/commands/bs_info.cpp:56 +msgid "Real name" +msgstr "Echte naam" + +#: modules/commands/os_list.cpp:153 +msgid "Realname" +msgstr "Echte naam" + +#: modules/commands/os_ignore.cpp:266 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:204 modules/commands/os_forbid.cpp:358 +#: modules/commands/cs_akick.cpp:392 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:361 +msgid "Reason" +msgstr "Reden" + +#: src/xline.cpp:386 +#, c-format +msgid "Reason for %s updated." +msgstr "Reden voor %s geüpdatet." + +#: modules/commands/ns_recover.cpp:214 +msgid "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." +msgstr "" +"Eist je nick op van een andere gebruiker, of van Services.\n" +"Indien Services je nick blokkeren, dan zal deze worden\n" +"vrijgegeven. Als een andere gebruiker je nick momenteel gebruikt\n" +"en geïdentificeert is, dan zal die gekillt worden (vergelijkbaar met\n" +"het oude GHOST commando). Als die echter niet geïdentificeert is,\n" +"dan zal de nick worden gewijzigd." + +#: modules/commands/cs_access.cpp:741 +msgid "Redefine the meanings of access levels" +msgstr "Verander de betekenissen van toegangsniveaus" + +#: modules/commands/ns_recover.cpp:149 +msgid "Regains control of your nick" +msgstr "Neemt de controle van je nick weer over" + +#: modules/commands/os_sxline.cpp:330 modules/commands/os_sxline.cpp:545 +#: modules/commands/os_akill.cpp:129 +msgid "Regex is disabled." +msgstr "Regex is uitgeschakeld." + +#: modules/commands/os_sxline.cpp:459 modules/commands/os_sxline.cpp:694 +#: modules/commands/os_akill.cpp:444 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." +msgstr "" +"Regex overeenkomsten worden ook ondersteund via de %s engine.\n" +"Omsluit het masker met // indien dit gewenst is." + +#: modules/commands/os_ignore.cpp:386 modules/commands/os_forbid.cpp:428 +#: modules/commands/ns_list.cpp:172 modules/commands/cs_list.cpp:167 +#: modules/commands/os_list.cpp:119 modules/commands/os_list.cpp:255 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." +msgstr "" +"Regex overeenkomsten worden ook ondersteund via de %s engine.\n" +"Omsluit het patroon met // indien dit gewenst is." + +#: modules/commands/cs_register.cpp:19 +msgid "Register a channel" +msgstr "Registreer een kanaal" + +#: modules/commands/ns_register.cpp:120 +msgid "Register a nickname" +msgstr "Registreer een nickname" + +#: modules/commands/ns_info.cpp:89 modules/commands/cs_info.cpp:55 +msgid "Registered" +msgstr "Geregistreerd" + +#: modules/commands/os_stats.cpp:184 +#, c-format +msgid "Registered channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" +"Geregistreerde kanalen: %lu vermeldingen, %lu emmers, langste ketting is %d" + +#: modules/commands/os_stats.cpp:190 +#, c-format +msgid "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" +msgstr "" +"Geregistreerde nickgroepen: %lu vermeldingen, %lu emmers, langste ketting is " +"%d" + +#: modules/commands/os_stats.cpp:187 +#, c-format +msgid "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" +msgstr "" +"Geregistreerde nicks: %lu vermeldingen, %lu emmers, langste ketting is %d" + +#: modules/commands/cs_enforce.cpp:105 +#, c-format +msgid "Registered only enforced on %s." +msgstr "REGONLY afgedwongen op %s." + +#: modules/commands/cs_register.cpp:86 +#, c-format +msgid "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." +msgstr "" +"Registreert een kanaal in de %s database. Om dit\n" +"commando te kunnen gebruiken moet je eerst een\n" +"kanaaloperator zijn op het kanaal dat je wilt\n" +"registreren. De beschrijving, die optioneel is, is een\n" +"algemene beschrijving van het doel van het kanaal.\n" +" \n" +"Wanneer je een kanaal registreert word jij als de\n" +"\"stichter\" van het kanaal aanzien. De kanaal-\n" +"stichter kan alle instellingen van het kanaal wijzigen;\n" +"%s zal ook automatisch de stichter kanaaloperator\n" +"status geven wanneer deze het kanaal binnenkomt." + +#: modules/commands/ns_register.cpp:269 +#, c-format +msgid "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." +msgstr "" +"Registreert je nick in de %s database. Wanneer je nick\n" +"geregistreerd is kan je de SET en ACCESS commando's\n" +"gebruiken om je nick instellingen te veranderen.\n" +"Onthoud het wachtwoord dat je gebruikt bij het registreren,\n" +"je hebt het nodig als je je nick instellingen later wilt\n" +"veranderen. (Let erop dat hoofdletters belangrijk zijn!\n" +"ANOPE, Anope, en anope zijn allemaal verschillende\n" +"wachtwoorden!)\n" +" \n" +"Wachtwoordrichtlijnen:\n" +" \n" +"Wachtwoorden mogen niet makkelijk te raden zijn. Bijvoorbeeld,\n" +"je echte naam als wachtwoord gebruiken is een slecht idee. Je\n" +"nick als een wachtwoord gebruiken is een veel slechter idee ;)\n" +"en in feite, %s staat het niet toe. Bovendien zijn korte wachtwoorden\n" +"kwetsbaar voor zoekacties, dus kies je best een wachtwoord\n" +"dat minstens 5 karakters lang is. Als laatste, de spatie kan niet\n" +"gebruikt worden in wachtwoorden." + +#: modules/commands/ns_register.cpp:145 +msgid "Registration is currently disabled." +msgstr "Registratie is momenteel uitgeschakeld." + +#: modules/commands/cs_set.cpp:400 +msgid "Regulate the use of critical commands" +msgstr "Reguleer het gebruik van kritieke commando's" + +#: modules/commands/hs_request.cpp:283 +msgid "Reject the requested vHost for the given nick." +msgstr "Wijs de aangevraagde vHost van de opgegeven nick af." + +#: modules/commands/hs_request.cpp:240 +msgid "Reject the requested vHost of a user" +msgstr "Wijs de aangevraagde vHost van een gebruiker af" + +#: modules/commands/cs_suspend.cpp:151 +msgid "Releases a suspended channel" +msgstr "Geeft een kanaal weer vrij" + +#: modules/commands/cs_suspend.cpp:191 +msgid "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." +msgstr "" +"Geeft een kanaal weer vrij. Alle data en instellingen\n" +"van voor de schorsing zijn behouden." + +#: modules/commands/os_module.cpp:56 +msgid "Reload a module" +msgstr "Herlaad een module" + +#: modules/commands/os_reload.cpp:19 +msgid "Reload services' configuration file" +msgstr "Herlaad Services' configuratiebestand" + +#: modules/commands/ns_group.cpp:236 +msgid "Remove a nick from a group" +msgstr "Haal een nick uit een groep" + +#: modules/commands/cs_unban.cpp:19 +msgid "Remove all bans preventing a user from entering a channel" +msgstr "Haal alle bans weg die een gebruiker voorkomen een kanaal te betreden" + +#: modules/commands/os_noop.cpp:19 +msgid "Remove all operators from a server remotely" +msgstr "Verwijder op afstand alle operators van een server" + +#: modules/commands/os_dns.cpp:543 +#, c-format +msgid "Removed IP %s from %s." +msgstr "IP %s verwijderd van %s." + +#: modules/commands/os_dns.cpp:460 +#, c-format +msgid "Removed server %s from zone %s." +msgstr "Server %s verwijderd van domein %s." + +#: modules/commands/os_dns.cpp:483 +#, c-format +msgid "Removed server %s." +msgstr "Server %s verwijderd." + +#: modules/commands/cs_mode.cpp:909 +#, c-format +msgid "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." +msgstr "" +"Verwijdert %s status van de gegeven nick op een channel. Als nick\n" +"niet gegeven is, dan zal het bij jou de %s status weghalen." + +#: modules/commands/cs_mode.cpp:890 +#, c-format +msgid "Removes %s status from you or the specified nick on a channel" +msgstr "Verwijdert %s status van jou of de gegeven nick op een kanaal" + +#: modules/commands/cs_updown.cpp:146 +msgid "Removes a selected nicks status from a channel" +msgstr "Verwijder een opgegeven nick's status van een kanaal" + +#: modules/commands/cs_updown.cpp:223 +msgid "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." +msgstr "" +"Verwijder een opgegeven nick's status modes in een kanaal.\n" +"Als nick niet is opgegeven, dan worden jouw status modes\n" +"verwijderd. Indien kanaal niet is opgegeven, dan word je\n" +"status op elk kanaal waar je aanwezig bent verwijderd." + +#: src/xline.cpp:412 +#, c-format +msgid "Removing %s because %s covers it." +msgstr "%s verwijderd want %s dekt dit al." + +#: modules/commands/bs_kick.cpp:1171 modules/commands/bs_kick.cpp:1173 +#: modules/commands/bs_kick.cpp:1176 +msgid "Repeat kicker" +msgstr "Herhalingskicker" + +#: modules/commands/hs_request.cpp:78 +msgid "Request a vHost for your nick" +msgstr "Vraag een vHost voor je nick aan" + +#: modules/commands/hs_request.cpp:179 +msgid "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." +msgstr "" +"Vraag de opgegeven vHost aan voor activatie voor jouw nick\n" +"door de netwerkbeheerders. Gelieve geduldig te wachten\n" +"terwijl uw aanvraag lopende is." + +#: modules/commands/ns_register.cpp:312 +msgid "Resend registration confirmation email" +msgstr "Registratiebevestigings-e-mail opnieuw verzenden" + +#: modules/commands/cs_set.cpp:621 +msgid "Restrict access to the channel" +msgstr "Beperk de toegang tot het kanaal" + +#: modules/commands/cs_set.cpp:1291 +msgid "Restricted access" +msgstr "Beperkte toegang" + +#: modules/commands/cs_set.cpp:661 +#, c-format +msgid "Restricted access option for %s is now off." +msgstr "Beperkte toegangsoptie voor %s is nu uit." + +#: modules/commands/cs_set.cpp:655 +#, c-format +msgid "Restricted access option for %s is now on." +msgstr "Beperkte toegangsoptie voor %s is nu aan." + +#: modules/commands/cs_enforce.cpp:73 +#, c-format +msgid "Restricted enforced on %s." +msgstr "RESTRICTED afgedwongen op %s." + +#: modules/commands/cs_set.cpp:335 +msgid "Retain modes when channel is not in use" +msgstr "Onthoud modes wanneer het kanaal niet in gebruik is" + +#: modules/commands/cs_topic.cpp:20 +msgid "Retain topic when channel is not in use" +msgstr "Onthoud het topic wanneer het kanaal niet in gebruik is" + +#: modules/commands/ns_getpass.cpp:19 +msgid "Retrieve the password for a nickname" +msgstr "Vraag het wachtwoord van een nick op" + +#: modules/commands/hs_request.cpp:296 +msgid "Retrieves the vhost requests" +msgstr "Vraag de vHost-aanvraaglijst op" + +#: modules/commands/cs_getkey.cpp:19 +msgid "Returns the key of the given channel" +msgstr "Toont de sleutel voor het gegeven kanaal" + +#: modules/commands/cs_getkey.cpp:57 +msgid "Returns the key of the given channel." +msgstr "Toont de sleutel voor het gegeven kanaal." + +#: modules/commands/ns_getemail.cpp:58 +msgid "Returns the matching accounts that used given email." +msgstr "" +"Geeft geregistreerde gebruikers weer die het gegeven e-mailadres gebruikt " +"hebben." + +#: modules/commands/ns_status.cpp:19 +msgid "Returns the owner status of the given nickname" +msgstr "Geeft de eigenaarsstatus van de gegeven nick weer" + +#: modules/commands/ns_getpass.cpp:50 +msgid "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." +msgstr "" +"Geeft het wachtwoord van de opgegeven nick weer. Merk op\n" +"dat wanneer je dit commando gebruikt er een bericht met de\n" +"persoon die het commando heeft uitgevoerd en de nick waarop\n" +"het is gebruikt zal worden gelogd en verstuurd zal worden\n" +"als WALLOPS/GLOBOPS." + +#: modules/commands/ns_status.cpp:55 +msgid "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." +msgstr "" +"Geeft weer of de gebruiker van de gegeven nick wordt herkend\n" +"als de eigenaar van die nick. Het antwoord is in dit formaat:\n" +" \n" +" nick status-code account\n" +" \n" +"waar nick de nick is die gegeven werd in het commando,\n" +"status-code is één van volgende, en account is\n" +"het account waarmee ze ingelogt zijn.\n" +" \n" +" 0 - gebruiker niet online of nick niet geregistreerd\n" +" 1 - gebruiker wordt niet herkend als de eigenaar van de nick\n" +" 2 - gebruiker wordt alleen via de toegangslijst herkend als eigenaar\n" +" 3 - gebruiker wordt door wachtwoordidentificatie herkend als eigenaar\n" +" \n" +"Indien geen nick is gegeven, wordt je eigen status weergegeven." + +#: modules/commands/bs_kick.cpp:1181 modules/commands/bs_kick.cpp:1183 +#: modules/commands/bs_kick.cpp:1186 +msgid "Reverses kicker" +msgstr "Inverteringskicker" + +#: modules/commands/ns_logout.cpp:21 +msgid "Reverses the effect of the IDENTIFY command" +msgstr "Doet het omgekeerde van het IDENTIFY commando" + +#: modules/commands/os_noop.cpp:20 +msgid "SET server" +msgstr "SET server" + +#: modules/commands/os_dns.cpp:667 +msgid "SET server.name option value" +msgstr "SET server.naam optie waarde" + +#: modules/commands/ns_cert.cpp:378 +#, c-format +msgid "SSL certificate fingerprint accepted, you are now identified to %s." +msgstr "" +"SSL certificaatvingerafdruk aanvaard, je bent nu geïdentificeerd voor %s." + +#: modules/commands/ns_cert.cpp:398 +msgid "SSL certificate fingerprint accepted, you are now identified." +msgstr "SSL certificaatvingerafdruk aanvaard, je bent nu geïdentificeerd." + +#: modules/commands/cs_enforce.cpp:137 +#, c-format +msgid "SSL only enforced on %s." +msgstr "SSLONLY afgedwongen op %s." + +#: modules/commands/cs_enforce.cpp:131 +msgid "SSLONLY enforced by " +msgstr "SSLONLY afgedwongen door " + +#: modules/commands/os_shutdown.cpp:47 +msgid "Save databases and restart Services" +msgstr "Sla de database op en herstart Services" + +#: modules/commands/os_logsearch.cpp:32 +msgid "Searches logs for a matching pattern" +msgstr "Doorzoekt logs voor een overeenstemmend patroon" + +#: modules/commands/cs_set.cpp:1295 +msgid "Secure founder" +msgstr "Strikte stichter controle" + +#: modules/commands/cs_set.cpp:786 +#, c-format +msgid "Secure founder option for %s is now off." +msgstr "Strikte stichter controle-optie voor %s is nu uit." + +#: modules/commands/cs_set.cpp:780 +#, c-format +msgid "Secure founder option for %s is now on." +msgstr "Strikte stichter controle-optie voor %s is nu aan." + +#: modules/commands/cs_set.cpp:1297 +msgid "Secure ops" +msgstr "Strikte operator controle" + +#: modules/commands/cs_set.cpp:850 +#, c-format +msgid "Secure ops option for %s is now off." +msgstr "Strikte operator controle-optie voor %s is nu uit." + +#: modules/commands/cs_set.cpp:844 +#, c-format +msgid "Secure ops option for %s is now on." +msgstr "Strikte operator controle-optie voor %s is nu aan." + +#: modules/commands/cs_set.cpp:723 +#, c-format +msgid "Secure option for %s is now off." +msgstr "Veiligheidsoptie voor %s is nu uit." + +#: modules/commands/cs_set.cpp:717 +#, c-format +msgid "Secure option for %s is now on." +msgstr "Veiligheidsoptie voor %s is nu aan." + +#: modules/commands/ns_set.cpp:1044 +#, c-format +msgid "Secure option is now off for %s." +msgstr "Veiligheidsoptie is nu uit voor %s." + +#: modules/commands/ns_set.cpp:1038 +#, c-format +msgid "Secure option is now on for %s." +msgstr "Veiligheidsoptie is nu aan voor %s." + +#: modules/commands/cs_enforce.cpp:42 +#, c-format +msgid "Secureops enforced on %s." +msgstr "SECUREOPS afgedwongen op %s." + +#: modules/commands/cs_set.cpp:1293 modules/commands/ns_set.cpp:1311 +msgid "Security" +msgstr "Veiligheid" + +#: modules/commands/cs_xop.cpp:570 +#, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the access list." +msgstr "" +"Typ %s%s HELP %s voor meer informatie\n" +"over de toegangslijst." + +#: modules/commands/cs_xop.cpp:573 +#, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the flags system." +msgstr "" +"Typ %s%s HELP %s voor meer informatie\n" +"over het vlaggen systeem." + +#: modules/commands/ms_send.cpp:24 +msgid "Send a memo to a nick or channel" +msgstr "Stuur een memo naar een nick of kanaal" + +#: modules/commands/ms_staff.cpp:24 +msgid "Send a memo to all opers/admins" +msgstr "Stuur een memo naar alle opers/admins" + +#: modules/commands/ms_sendall.cpp:24 +msgid "Send a memo to all registered users" +msgstr "Stuur een memo naar alle geregistreerde gebruikers " + +#: modules/commands/gl_global.cpp:21 +msgid "Send a message to all users" +msgstr "Stuur een bericht naar alle gebruikers" + +#: modules/commands/ms_list.cpp:64 +msgid "Sender" +msgstr "Afzender" + +#: modules/commands/ms_rsend.cpp:24 +msgid "Sends a memo and requests a read receipt" +msgstr "Stuur een memo en een verzoek voor ontvangstbevestiging" + +#: modules/commands/ns_resetpass.cpp:50 +msgid "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." +msgstr "" +"Stuurt een bevestigingscode naar de nick met instructies om hun\n" +"wachtwoord te resetten. E-mail moet het e-mailadres zijn die bij\n" +"deze nick hoort." + +#: modules/commands/ms_sendall.cpp:52 +msgid "Sends all registered users a memo containing memo-text." +msgstr "Stuurt alle geregistreerde gebruikers een memo die memo-tekst bevat." + +#: modules/commands/ms_staff.cpp:48 +msgid "Sends all services staff a memo containing memo-text." +msgstr "Stuurt alle Services medewerkers een memo die memo-tekst bevat." + +#: modules/commands/ms_send.cpp:66 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." +msgstr "" +"Stuurt de gegeven nick of kanaal een memo met memo-tekst.\n" +"Wanneer je een memo naar een nick stuurt zal de ontvanger een\n" +"notificatie krijgen dat hij/zij een nieuwe memo heeft.\n" +"Het doel nick of kanaal moet geregistreerd zijn." + +#: modules/commands/ms_rsend.cpp:80 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." +msgstr "" +"Stuurt de gegeven nick of kanaal een memo met memo-tekst.\n" +"Wanneer je een memo naar een nick stuurt zal de ontvanger een\n" +"notificatie krijgen dat hij/zij een nieuwe memo heeft.\n" +"Het doel nick of kanaal moet geregistreerd zijn.\n" +"Zodra de memo is gelezen door de ontvanger zal er automatisch\n" +"een memo teruggestuurd worden naar degene die de memo verstuurd\n" +"heeft om hem/haar te informeren dat de memo gelezen is." + +#: modules/commands/ms_read.cpp:199 +msgid "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Verstuurt de tekst van de opgegeven memo's. Als LAST is\n" +"gegeven wordt de laatst ontvangen memo verstuurd. Als NEW is\n" +"gegeven worden alle nieuwe memo's verstuurd. Als ALL wordt\n" +"opgegeven worden alle memo's verstuurd. Anders wordt\n" +"memo nummer nr getoond. Je kan ook een lijst van nummers\n" +"opgeven, zoals in onderstaand voorbeeld:\n" +" \n" +" READ 2-5,7-9\n" +" Geeft de memo's genummerd 2 t/m 5 en 7 t/m 9 weer." + +#: modules/commands/os_dns.cpp:218 +msgid "Server" +msgstr "Server" + +#: modules/commands/os_dns.cpp:375 +#, c-format +msgid "Server %s added to zone %s." +msgstr "Server %s toegevoegd aan domein %s." + +#: modules/commands/os_dns.cpp:345 +#, c-format +msgid "Server %s already exists." +msgstr "Server %s bestaat reeds." + +#: modules/commands/os_noop.cpp:31 modules/commands/os_dns.cpp:430 +#: modules/commands/os_dns.cpp:493 modules/commands/os_dns.cpp:532 +#: modules/commands/os_dns.cpp:571 modules/commands/os_dns.cpp:604 +#: modules/commands/os_dns.cpp:639 +#, c-format +msgid "Server %s does not exist." +msgstr "Server %s bestaat niet." + +#: modules/commands/os_dns.cpp:619 +#, c-format +msgid "Server %s has no configured IPs." +msgstr "Server %s heeft geen geconfigureerde IP-adressen." + +#: modules/commands/os_dns.cpp:357 +#, c-format +msgid "Server %s is already in zone %s." +msgstr "Server %s is reeds in domein %s." + +#: modules/commands/os_dns.cpp:614 +#, c-format +msgid "Server %s is already pooled." +msgstr "Server %s is reeds pooled." + +#: modules/commands/os_dns.cpp:609 +#, c-format +msgid "Server %s is not currently linked." +msgstr "Server %s is momenteel niet gelinkt." + +#: modules/commands/os_dns.cpp:443 +#, c-format +msgid "Server %s is not in zone %s." +msgstr "Server %s is niet in domein %s." + +#: modules/commands/os_dns.cpp:384 +#, c-format +msgid "Server %s is not linked to the network." +msgstr "Server %s is niet gelinkt aan het netwerk." + +#: modules/commands/os_dns.cpp:644 +#, c-format +msgid "Server %s is not pooled." +msgstr "Server %s is niet pooled." + +#: modules/commands/os_dns.cpp:465 +#, c-format +msgid "Server %s must be quit before it can be deleted." +msgstr "Server %s moet gequit zijn alvorens het verwijderd kan worden." + +#: modules/commands/os_dns.cpp:255 +msgid "Servers" +msgstr "Servers" + +#: modules/commands/os_stats.cpp:155 +#, c-format +msgid "Servers found: %d" +msgstr "Servers gevonden: %d" + +#: modules/commands/cs_log.cpp:127 +msgid "Service" +msgstr "Service" + +#: modules/commands/ns_recover.cpp:51 +#, c-format +msgid "Service's hold on %s has been released." +msgstr "Nick %s werd vrijgegeven." + +#: data/nickserv.example.conf:236 data/chanserv.example.conf:827 +msgid "Services Operator commands" +msgstr "Services Operator commando's" + +#: modules/commands/os_defcon.cpp:443 modules/commands/os_defcon.cpp:454 +#: modules/commands/os_defcon.cpp:462 modules/commands/os_defcon.cpp:470 +#: modules/commands/os_defcon.cpp:478 +msgid "Services are in DefCon mode, please try again later." +msgstr "Services zijn in DefCon modus, probeer later opnieuw." + +#: include/language.h:70 +msgid "Services are in read-only mode!" +msgstr "Services zijn in alleen-lezen modus!" + +#: modules/commands/os_defcon.cpp:186 modules/commands/os_defcon.cpp:213 +#, c-format +msgid "Services are now at DEFCON %d." +msgstr "Services zijn nu in DEFCON %d." + +#: modules/commands/os_set.cpp:128 +#, c-format +msgid "Services are now in debug mode (level %d)." +msgstr "Services zijn nu in debug modus (niveau %d)." + +#: modules/commands/os_set.cpp:114 +msgid "Services are now in debug mode." +msgstr "Services zijn nu in debug modus." + +#: modules/commands/os_set.cpp:159 +msgid "Services are now in expire mode." +msgstr "Services zijn nu in verloop modus." + +#: modules/commands/os_set.cpp:153 +msgid "Services are now in no expire mode." +msgstr "Services zijn nu in geen-verloop modus." + +#: modules/commands/os_set.cpp:120 +msgid "Services are now in non-debug mode." +msgstr "Services zijn nu in niet-debug modus." + +#: modules/commands/os_set.cpp:47 +msgid "Services are now in read-only mode." +msgstr "Services zijn nu in alleen-lezen modus." + +#: modules/commands/os_set.cpp:53 +msgid "Services are now in read-write mode." +msgstr "Services zijn nu in lezen-schrijven modus." + +#: src/mail.cpp:76 +msgid "Services have been configured to not send mail." +msgstr "Services zijn geconfigureerd om geen e-mails te versturen." + +#: modules/commands/os_ignore.cpp:280 +msgid "Services ignore list:" +msgstr "Services negeerlijst:" + +#: modules/commands/os_mode.cpp:33 modules/commands/os_kick.cpp:39 +msgid "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" +msgstr "" +"Services kan geen modes veranderen. Zijn de U:lines van je servers goed " +"geconfigureerd?" + +#: modules/commands/os_stats.cpp:140 +#, c-format +msgid "Services up %s." +msgstr "Services draaien reeds %s." + +#: modules/commands/ns_set.cpp:266 +#, c-format +msgid "Services will from now on set status modes on %s in channels." +msgstr "Services zal vanaf nu status modes geven aan %s in kanalen." + +#: modules/commands/cs_set.cpp:114 +#, c-format +msgid "Services will no longer automatically give modes to users in %s." +msgstr "" +"Services zal nu niet langer automatisch modes geven aan gebruikers in %s." + +#: modules/commands/ns_set.cpp:272 +#, c-format +msgid "Services will no longer set status modes on %s in channels." +msgstr "Services zal niet langer status modes geven aan %s in kanalen." + +#: modules/commands/cs_set.cpp:108 +#, c-format +msgid "Services will now automatically give modes to users in %s." +msgstr "Services zal nu automatisch modes geven aan gebruikers in %s." + +#: modules/commands/ns_set.cpp:940 +#, c-format +msgid "Services will now reply to %s with messages." +msgstr "Services zal nu antwoorden sturen naar %s via privé berichten." + +#: modules/commands/ns_set.cpp:946 +#, c-format +msgid "Services will now reply to %s with notices." +msgstr "Services zal nu antwoorden sturen naar %s via notice." + +#: modules/commands/os_reload.cpp:34 +msgid "Services' configuration has been reloaded." +msgstr "Services' configuratiebestand is opnieuw geladen." + +#: modules/commands/os_session.cpp:192 +msgid "Session" +msgstr "Sessie" + +#: modules/commands/os_session.cpp:382 +#, c-format +msgid "Session limit for %s set to %d." +msgstr "Sessielimiet voor %s veranderd naar %d." + +#: modules/commands/os_session.cpp:257 modules/commands/os_session.cpp:534 +msgid "Session limiting is disabled." +msgstr "Sessielimitering is uitgeschakeld." + +#: modules/commands/os_stats.cpp:195 +#, c-format +msgid "Sessions: %lu entries, %lu buckets, longest chain is %d" +msgstr "Sessies: %lu vermeldingen, %lu emmers, langste ketting is %d" + +#: modules/commands/ns_set.cpp:74 +msgid "Set SET-options on another nickname" +msgstr "Stel SET-opties in op een andere nick" + +#: modules/commands/cs_set.cpp:20 +msgid "Set channel options and information" +msgstr "Stel kanaalopties en informatie in" + +#: modules/commands/cs_set.cpp:137 +msgid "Set how Services make bans on the channel" +msgstr "Stelt in hoe Services bans op het kanaal maken" + +#: modules/commands/ms_set.cpp:206 +msgid "Set options related to memos" +msgstr "Stel opties gerelateerd aan memo's in" + +#: modules/commands/ns_set.cpp:19 +msgid "Set options, including kill protection" +msgstr "Opties instellen, inclusief kill bescherming" + +#: modules/commands/cs_set.cpp:472 +msgid "Set the channel as permanent" +msgstr "Stel het kanaal als permanent in" + +#: modules/commands/cs_set.cpp:204 +msgid "Set the channel description" +msgstr "Stelt de kanaalbeschrijving in" + +#: modules/commands/ns_set.cpp:329 +msgid "Set the display of your group in Services" +msgstr "Stel de weergave van je groep in Services in" + +#: modules/commands/cs_set.cpp:266 +msgid "Set the founder of a channel" +msgstr "Stelt de stichter van een kanaal in" + +#: modules/commands/ns_set.cpp:793 +msgid "Set the language Services will use when messaging you" +msgstr "" +"Selecteer de taal die Services zal gebruiken voor het versturen van " +"berichten naar jou" + +#: modules/commands/ns_set.cpp:172 +msgid "Set the nickname password" +msgstr "Verander het wachtwoord van de nick" + +#: modules/commands/cs_set.cpp:949 +msgid "Set the successor for a channel" +msgstr "Stelt de opvolger voor het kanaal in" + +#: modules/commands/hs_set.cpp:125 +msgid "Set the vhost for all nicks in a group" +msgstr "Stel de vHost voor alle nicks in een groep in" + +#: modules/commands/hs_set.cpp:19 +msgid "Set the vhost of another user" +msgstr "Stel de vHost van een andere gebruiker in" + +#: modules/commands/os_set.cpp:169 +msgid "Set various global Services options" +msgstr "Stel verscheidene globale Services opties in" + +#: modules/commands/ns_set.cpp:119 +msgid "Set your nickname password" +msgstr "Verander het wachtwoord van je nick" + +#: modules/commands/bs_kick.cpp:271 +#, c-format +msgid "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Zet de AMSG-kicker aan of uit. Wanneer deze aan staat\n" +"zal de bot gebruikers kicken die hetzelfde bericht\n" +"tegelijkertijd sturen naar meerdere kanalen waar %s bots staan.\n" +" \n" +"ttb is het aantal keren dat een gebruiker gekickt kan\n" +"worden voordat deze geband wordt. Geef geen ttb op om het\n" +"bansysteem uit te schakelen als deze kicker geactiveerd is." + +#: modules/commands/bs_kick.cpp:307 +#, c-format +msgid "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Zet de slechtewoordenkicker aan of uit. Wanneer deze aan\n" +"staat zal de bot gebruikers kicken die bepaald slechte\n" +"woorden op het kanaal zeggen.\n" +"Je kan de slechte woorden voor je kanaal instellen met het\n" +"BADWORDS commando. Typ %s%s HELP BADWORDS voor\n" +"meer informatie.\n" +" \n" +"ttb is het aantal keren dat een gebruiker gekickt kan\n" +"worden voordat deze geband wordt. Geef geen ttb op om het\n" +"bansysteem uit te schakelen als deze kicker geactiveerd is." + +#: modules/commands/cs_set.cpp:186 +msgid "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" +msgstr "" +"Stelt het bantype in dat gebruikt zal worden door Services\n" +"wanneer ze een ban moeten zetten op je kanaal.\n" +" \n" +"Bantype is een nummer tussen 0 en 3 dat betekent:\n" +" \n" +"0: ban in het formaat *!ident@host\n" +"1: ban in het formaat *!*ident@host\n" +"2: ban in het formaat *!*@host\n" +"3: ban in het formaat *!*ident@*.domein" + +#: modules/commands/bs_kick.cpp:345 +msgid "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Zet de vetkicker aan of uit. Wanneer deze aan staat zal\n" +"de bot gebruikers kicken die vet gebruiken.\n" +" \n" +"ttb is het aantal keren dat een gebruiker gekickt kan\n" +"worden voordat deze geband wordt. Geef geen ttb op om het\n" +"bansysteem uit te schakelen als deze kicker geactiveerd is." + +#: modules/commands/bs_kick.cpp:436 +#, c-format +msgid "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Zet de hoofdletterskicker aan of uit. Wanneer deze aan staat\n" +"zal de bot gebruikers kicken die HOOFDLETTERS gebruiken.\n" +"De bot kickt alleen als er minstens min hoofdletters in\n" +"de zin staan en deze minstens procent%% van de totale\n" +"regel bevatten (indien niet gegeven, staat dit standaard op\n" +"10 karakters en 25%%).\n" +" \n" +"ttb is het aantal keren dat een gebruiker gekickt kan\n" +"worden voordat deze geband wordt. Geef geen ttb op om het\n" +"bansysteem uit te schakelen als deze kicker geactiveerd is." + +#: modules/commands/bs_kick.cpp:475 +msgid "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Zet de kleurenkicker aan of uit. Wanneer deze aan staat\n" +"zal de bot gebruikers kicken die kleuren gebruiken.\n" +" \n" +"ttb is het aantal keren dat een gebruiker gekickt kan\n" +"worden voordat deze geband wordt. Geef geen ttb op om het\n" +"bansysteem uit te schakelen als deze kicker geactiveerd is." + +#: modules/commands/cs_set.cpp:255 +msgid "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." +msgstr "" +"Stelt de beschrijving van het kanaal in, die weergegeven\n" +"wordt door de LIST en INFO commando's." + +#: modules/commands/bs_kick.cpp:571 +msgid "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Zet de floodkicker aan of uit. Wanneer deze aan staat zal\n" +"de bot gebruikers kicken die het kanaal flooden met minstens\n" +"regels regels in seconden seconden (indien niet\n" +"gegeven, staat dit standaard op 6 regels in 10 seconden).\n" +" \n" +"ttb is het aantal keren dat een gebruiker gekickt kan\n" +"worden voordat deze geband wordt. Geef geen ttb op om het\n" +"bansysteem uit te schakelen als deze kicker geactiveerd is." + +#: modules/commands/bs_kick.cpp:607 +msgid "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Zet de cursiefkicker aan of uit. Wanneer deze aan staat zal\n" +"de bot gebruikers kicken die cursief gebruiken.\n" +" \n" +"ttb is het aantal keren dat een gebruiker gekickt kan\n" +"worden voordat deze geband wordt. Geef geen ttb op om het\n" +"bansysteem uit te schakelen als deze kicker geactiveerd is." + +#: modules/commands/bs_kick.cpp:706 +msgid "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Zet de herhalingskicker aan of uit. Wanneer deze aan staat\n" +"zal de bot gebruikers kicken die zichzelf nr keer herhalen\n" +"(als nr niet is gegeven staat die standaard op 3).\n" +" \n" +"ttb is het aantal keren dat een gebruiker gekickt kan\n" +"worden voordat deze geband wordt. Geef geen ttb op om het\n" +"bansysteem uit te schakelen als deze kicker geactiveerd is." + +#: modules/commands/bs_kick.cpp:742 +msgid "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Zet de inverteringskicker aan of uit. Wanneer deze aan\n" +"staat zal de bot gebruikers kicken die inverteringen\n" +"gebruiken.\n" +" \n" +"ttb is het aantal keren dat een gebruiker gekickt kan\n" +"worden voordat deze geband wordt. Geef geen ttb op om het\n" +"bansysteem uit te schakelen als deze kicker geactiveerd is." + +#: modules/commands/bs_kick.cpp:776 +msgid "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Zet de onderlijningskicker aan of uit. Wanneer deze aan\n" +"staat zal de bot gebruikers kicken die onderlijningen\n" +"gebruiken.\n" +" \n" +"ttb is het aantal keren dat een gebruiker\n" +"gekickt kan worden voordat deze geband wordt.\n" +"Geef geen ttb op om het bansysteem uit te schakelen\n" +"als deze kicker geactiveerd is." + +#: modules/commands/hs_set.cpp:206 +msgid "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." +msgstr "" +"Stelt de vHost voor alle nicks in dezelfde groep in als die\n" +"van de gegeven nick. Als de IRCd vIdent's ondersteunt\n" +"kun je ook SETALL @ gebruiken\n" +"om de ident voor gebruikers aan te passen tegelijk met\n" +"de host.\n" +"* LET OP, dit wijzigt de vHost niet voor nicks die lid\n" +"worden van de groep nadat dit commando is gebruikt." + +#: modules/commands/hs_set.cpp:99 +msgid "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." +msgstr "" +"Stelt de vHost voor de gegeven nick in op de host die je\n" +"opgegeven hebt. Als de IRCd vIdents ondersteund kun je\n" +"ook SET @ gebruiken om de ident\n" +"voor een gebruiker aan te passen tegelijk met de host." + +#: modules/commands/os_set.cpp:199 +msgid "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" +msgstr "" +"Stelt verschillende globale Services opties in. Momenteel\n" +"zijn de volgende opties beschikbaar:\n" +" READONLY Stel alleen-lezen of lezen-schrijven modus in\n" +" DEBUG (De)activeer debug modus\n" +" NOEXPIRE (De)activeer de geen-verlooptijd modus\n" +" SUPERADMIN (De)activeer Super Administrator modus\n" +" LIST Toon de opties" + +#: modules/commands/ms_set.cpp:235 +#, c-format +msgid "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Stelt verschillende memo opties in. optie kan zijn:\n" +" \n" +" NOTIFY Verandert wanneer je geïnformeerd wordt over\n" +" nieuwe memo's (alleen voor nicks)\n" +" LIMIT Stelt het maximum aantal memo's dat je kan\n" +" ontvangen in\n" +" \n" +"Typ %s%s HELP %s optie voor meer informatie over\n" +"een specifieke optie." + +#: modules/commands/ns_set.cpp:33 modules/commands/ns_set.cpp:88 +msgid "Sets various nickname options. option can be one of:" +msgstr "Stelt verscheidene nick opties in. optie kan een van de volgende zijn:" + +#: modules/commands/ns_set.cpp:237 +msgid "" +"Sets whether services should set channel status modes on you automatically." +msgstr "" +"Stelt in of Services je automatisch je status modes geeft op het kanaal." + +#: modules/commands/cs_set.cpp:1090 +msgid "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." +msgstr "" +"Stelt in of het gegeven kanaal zal verlopen. Door deze optie\n" +"AAN te zetten kun je verhinderen dat het kanaal verloopt." + +#: modules/commands/ns_set.cpp:315 +#, c-format +msgid "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." +msgstr "" +"Stelt in of de gegeven nick kanaalstatus modes automatisch krijgt of niet.\n" +"Zet dit op ON om %s toe te staan de statusmodes automatisch\n" +"te zetten wanneer de nick kanalen betreed. Let op dat afhankelijk van de\n" +"kanaalinstellingen sommige modes niet automatisch gezet kunnen worden." + +#: modules/commands/ns_set.cpp:1145 +msgid "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." +msgstr "" +"Stelt in of de gegeven nick zal verlopen of niet.\n" +"Dit aan zetten voorkomt dat de nick zal verlopen." + +#: modules/commands/ns_set.cpp:288 +#, c-format +msgid "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." +msgstr "" +"Stelt in of je jouw kanaalstatus modes automatisch krijgt of niet.\n" +"Zet dit op ON om %s toe te staan je statusmodes automatisch\n" +"te zetten wanneer je kanalen betreed. Let op dat afhankelijk van de\n" +"kanaalinstellingen sommige modes niet automatisch gezet kunnen worden." + +#: modules/commands/cs_access.cpp:648 modules/commands/cs_access.cpp:689 +#, c-format +msgid "" +"Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." +msgstr "" +"Instelling %s onbekend. Typ %s%s HELP LEVELS voor een lijst van geldige " +"instellingen." + +#: modules/commands/os_set.cpp:133 +msgid "Setting for DEBUG must be ON, OFF, or a positive number." +msgstr "Instelling voor DEBUG moet ON, OFF, of een positief nummer zijn." + +#: modules/commands/os_set.cpp:162 +msgid "Setting for NOEXPIRE must be ON or OFF." +msgstr "Instelling voor NOEXPIRE moet ON of OFF zijn." + +#: modules/commands/os_set.cpp:56 +msgid "Setting for READONLY must be ON or OFF." +msgstr "Instelling voor READONLY moet ON of OFF zijn." + +#: modules/commands/os_set.cpp:95 +msgid "Setting for super admin must be ON or OFF." +msgstr "Instelling voor super administrator moet ON of OFF zijn." + +#: modules/commands/cs_set.cpp:74 +msgid "Should services automatically give status to users" +msgstr "Moet Services automatisch status modes geven aan gebruikers" + +#: modules/commands/os_stats.cpp:203 +msgid "Show status of Services and network" +msgstr "Geef de status van Services en het netwerk weer" + +#: modules/commands/os_logsearch.cpp:152 +#, c-format +msgid "Showed %d/%d matches for %s." +msgstr "%d/%d overeenkomsten getoond voor %s." + +#: modules/commands/cs_set.cpp:872 +msgid "Sign kicks that are done with the KICK command" +msgstr "Onderteken kicks die worden uitgevoerd met het KICK commando" + +#: modules/commands/cs_set.cpp:921 +#, c-format +msgid "Signed kick option for %s is now off." +msgstr "Ondertekende kicks-optie voor %s is nu uit." + +#: modules/commands/cs_set.cpp:913 +#, c-format +msgid "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." +msgstr "" +"Ondertekende kicks-optie voor %s is nu aan, maar hangt af\n" +"van het niveau van de gebruiker die het commando uitvoert." + +#: modules/commands/cs_set.cpp:906 +#, c-format +msgid "Signed kick option for %s is now on." +msgstr "Ondertekende kicks-optie voor %s is nu aan." + +#: modules/commands/cs_set.cpp:1299 +msgid "Signed kicks" +msgstr "Ondertekende kicks" + +#: modules/commands/ms_rsend.cpp:60 modules/commands/ms_send.cpp:59 +#, c-format +msgid "Sorry, %s currently has too many memos and cannot receive more." +msgstr "" +"Sorry, %s heeft momenteel te veel memo's en kan er geen meer ontvangen." + +#: modules/commands/cs_seen.cpp:294 +#, c-format +msgid "Sorry, I have not seen %s." +msgstr "Sorry, ik heb %s niet gezien." + +#: modules/commands/bs_badwords.cpp:404 +msgid "Sorry, bad words list modification is temporarily disabled." +msgstr "" +"Sorry, het wijzigen van de slechtewoordenlijst is tijdelijk uitgeschakeld." + +#: modules/commands/bs_assign.cpp:30 modules/commands/bs_assign.cpp:98 +msgid "Sorry, bot assignment is temporarily disabled." +msgstr "Sorry, bot toewijzing is tijdelijk uitgeschakeld." + +#: modules/commands/bs_bot.cpp:281 modules/commands/bs_assign.cpp:164 +msgid "Sorry, bot modification is temporarily disabled." +msgstr "Sorry, bot wijzigingen zijn tijdelijk uitgeschakeld." + +#: modules/fantasy.cpp:42 modules/commands/bs_kick.cpp:813 +#: modules/commands/bs_kick.cpp:878 +msgid "Sorry, bot option setting is temporarily disabled." +msgstr "Sorry, bot opties instellen is tijdelijk uitgeschakeld." + +#: modules/commands/bs_set.cpp:115 +msgid "Sorry, changing bot options is temporarily disabled." +msgstr "Sorry, het wijzigen van bot opties is tijdelijk uitgeschakeld." + +#: modules/commands/cs_xop.cpp:112 modules/commands/cs_xop.cpp:235 +#: modules/commands/cs_xop.cpp:444 +#, c-format +msgid "Sorry, channel %s list modification is temporarily disabled." +msgstr "Sorry, kanaal %s lijst wijzigingen zijn tijdelijk uitgeschakeld." + +#: modules/commands/cs_access.cpp:547 modules/commands/cs_flags.cpp:405 +msgid "Sorry, channel access list modification is temporarily disabled." +msgstr "Sorry, kanaal toegangslijst wijzigingen zijn tijdelijk uitgeschakeld." + +#: modules/commands/cs_akick.cpp:469 +msgid "Sorry, channel autokick list modification is temporarily disabled." +msgstr "Sorry, kanaal autokicklijst wijzigingen zijn tijdelijk uitgeschakeld." + +#: modules/commands/cs_drop.cpp:29 +msgid "Sorry, channel de-registration is temporarily disabled." +msgstr "Sorry, kanalen kunnen tijdelijk niet verwijderd worden." + +#: modules/commands/cs_register.cpp:35 +msgid "Sorry, channel registration is temporarily disabled." +msgstr "Sorry, kanaal registratie is tijdelijk uitgeschakeld." + +#: modules/commands/bs_kick.cpp:181 +msgid "Sorry, kicker configuration is temporarily disabled." +msgstr "Sorry, kicker configuratie is tijdelijk uitgeschakeld." + +#: modules/commands/ms_set.cpp:216 +msgid "Sorry, memo option setting is temporarily disabled." +msgstr "Sorry, memo opties instellen is tijdelijk uitgeschakeld." + +#: include/language.h:116 +msgid "Sorry, memo sending is temporarily disabled." +msgstr "Sorry, het versturen van memo's is tijdelijk uitgeschakeld." + +#: modules/commands/ns_drop.cpp:29 +msgid "Sorry, nickname de-registration is temporarily disabled." +msgstr "Sorry, nicknames kunnen tijdelijk niet verwijderd worden." + +#: modules/commands/ns_group.cpp:120 +msgid "Sorry, nickname grouping is temporarily disabled." +msgstr "Sorry, nickname groeperingen zijn tijdelijk uitgeschakeld." + +#: modules/commands/ns_register.cpp:139 +msgid "Sorry, nickname registration is temporarily disabled." +msgstr "Sorry, nickname registratie is tijdelijk uitgeschakeld." + +#: modules/commands/ns_access.cpp:33 +#, c-format +msgid "Sorry, the maximum of %d access entries has been reached." +msgstr "Sorry, de maximum van %d toegangsvermeldingen is bereikt." + +#: modules/commands/ns_ajoin.cpp:141 +#, c-format +msgid "Sorry, the maximum of %d auto join entries has been reached." +msgstr "Sorry, de maximum van %d autojoinvermeldingen is bereikt." + +#: modules/commands/ns_cert.cpp:173 +#, c-format +msgid "Sorry, the maximum of %d certificate entries has been reached." +msgstr "Sorry, de maximum van %d certificaten is bereikt." + +#: modules/commands/ms_ignore.cpp:55 +#, c-format +msgid "Sorry, the memo ignore list for %s is full." +msgstr "Sorry, de memo negeerlijst voor %s is vol." + +#: modules/commands/cs_access.cpp:204 modules/commands/cs_flags.cpp:174 +#: modules/commands/cs_xop.cpp:201 +#, c-format +msgid "" +"Sorry, you can only have %d access entries on a channel, including access " +"entries from other channels." +msgstr "" +"Sorry, je kan maar %d toegangsvermeldingen hebben op een kanaal, inclusief " +"toegangsvermeldingen van andere kanalen." + +#: modules/commands/cs_akick.cpp:177 +#, c-format +msgid "Sorry, you can only have %d autokick masks on a channel." +msgstr "Sorry, je kan maar %d autokick maskers op een kanaal hebben." + +#: modules/commands/bs_badwords.cpp:286 +#, c-format +msgid "Sorry, you can only have %d bad words entries on a channel." +msgstr "Sorry, je kan maar %d slechte woorden per kanaal instellen." + +#: include/language.h:103 +#, c-format +msgid "Sorry, you have already exceeded your limit of %d channels." +msgstr "Sorry, je hebt het maximum aantal kanalen van %d al overschreden." + +#: include/language.h:102 +#, c-format +msgid "Sorry, you have already reached your limit of %d channels." +msgstr "Sorry, je hebt het maximum aantal kanalen van %d al bereikt." + +#: modules/commands/os_dns.cpp:218 +msgid "State" +msgstr "Staat" + +#: modules/commands/cs_seen.cpp:117 +msgid "Statistics and maintenance for seen data" +msgstr "Statistieken en onderhoud van seen gegevens" + +#: modules/commands/os_stats.cpp:131 +msgid "Statistics reset." +msgstr "Statistieken gereset." + +#: modules/commands/ns_update.cpp:36 +msgid "Status updated (memos, vhost, chmodes, flags)." +msgstr "Status geüpdatet (memo's, vHost, kanaalmodes, vlaggen)." + +#: modules/commands/bs_kick.cpp:1432 +msgid "Stop flooding!" +msgstr "Stop met flooden!" + +#: modules/commands/bs_kick.cpp:1448 +msgid "Stop repeating yourself!" +msgstr "Stop met jezelf te herhalen!" + +#: modules/commands/cs_set.cpp:746 +msgid "Stricter control of channel founder status" +msgstr "Striktere controle van de kanaalstichter status" + +#: modules/commands/cs_set.cpp:810 +msgid "Stricter control of chanop status" +msgstr "Striktere controle van de kanaaloperator status" + +#: modules/commands/ns_alist.cpp:75 modules/commands/cs_info.cpp:50 +msgid "Successor" +msgstr "Opvolger" + +#: modules/commands/cs_set.cpp:1006 +#, c-format +msgid "Successor for %s changed to %s." +msgstr "Opvolger voor %s veranderd naar %s." + +#: modules/commands/cs_set.cpp:1008 +#, c-format +msgid "Successor for %s unset." +msgstr "Opvolger voor %s verwijderd." + +#: modules/commands/os_set.cpp:81 +msgid "" +"Super admin can not be set because it is not enabled in the configuration." +msgstr "" +"Super Administrator kan niet ingesteld worden want het is niet ingeschakeld " +"in het configuratiebestand." + +#: modules/commands/ns_suspend.cpp:60 +msgid "Suspend a given nick" +msgstr "Schors een opgegeven nick" + +#: modules/commands/cs_suspend.cpp:236 modules/commands/ns_suspend.cpp:250 +msgid "Suspend reason" +msgstr "Schorsingsreden" + +#: modules/commands/cs_suspend.cpp:232 modules/commands/ns_suspend.cpp:246 +msgid "Suspended" +msgstr "Geschorst" + +#: modules/commands/cs_suspend.cpp:234 modules/commands/ns_suspend.cpp:248 +msgid "Suspended by" +msgstr "Geschorst door" + +#: modules/commands/cs_suspend.cpp:238 modules/commands/ns_suspend.cpp:252 +msgid "Suspended on" +msgstr "Geschorst op" + +#: modules/commands/ns_suspend.cpp:147 +msgid "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." +msgstr "" +"Schors een geregistreerde nickname, dit voorkomt dat deze kan gebruikt\n" +"worden, terwijl alle data voor die nick toch behouden blijft. Als een\n" +"verlooptijd is opgegeven, dan zal de schorsing na die periode weer\n" +"vervallen, anders zal de standaard verlooptijd gebruikt worden." + +#: modules/commands/cs_suspend.cpp:240 modules/commands/ns_suspend.cpp:254 +msgid "Suspension expires" +msgstr "Schorsing verloopt" + +#: modules/commands/cs_sync.cpp:19 +msgid "Sync users channel modes" +msgstr "Synchroniseer gebruikers kanaalstatusmodes" + +#: modules/commands/cs_sync.cpp:49 +msgid "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." +msgstr "" +"Synchroniseer alle gebruikersmodes op het kanaal met de\n" +"modes die ze zouden moeten hebben gebaseerd op hun toegang." + +#: modules/commands/hs_group.cpp:42 +msgid "Syncs the vhost for all nicks in a group" +msgstr "Stelt de vHost voor alle nicks in een groep gelijk" + +#: src/command.cpp:146 +msgid "Syntax" +msgstr "Gebruik" + +#: modules/commands/ns_group.cpp:373 +#, c-format +msgid "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." +msgstr "" +"Gebruik: %s\n" +" \n" +"Geeft alle nicks in je groep weer." + +#: modules/commands/ns_group.cpp:363 +#, c-format +msgid "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." +msgstr "" +"Gebruik: %s [nickname]\n" +" \n" +"Zonder een parameter worden alle nicks weergegeven die\n" +"zich in jouw groep bevinden.\n" +" \n" +"Indien een parameter gegeven is worden alle nicks\n" +"weergegeven die zich in de groep van de gegeven nick\n" +"bevinden.\n" +"Nicks opgeven is beperkt tot Services Operators." + +#: modules/commands/os_set.cpp:227 +msgid "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." +msgstr "" +"Gebruik: DEBUG {ON | OFF}\n" +" \n" +"Zet de debugmodus aan of uit.\n" +" \n" +"Deze optie komt overeen met de commandline-optie --debug." + +#: modules/commands/ms_set.cpp:287 +#, c-format +msgid "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." +msgstr "" +"Gebruik: LIMIT [kanaal] limiet\n" +" \n" +"Stelt het maximum aantal memo's in dat jij (of het gegeven\n" +"kanaal) kan hebben. Als je dit op 0 zet zal niemand memo's\n" +"naar je kunnen sturen. Je kan dit echter niet hoger dan %d\n" +"zetten." + +#: modules/commands/ms_set.cpp:267 +#, c-format +msgid "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." +msgstr "" +"Gebruik: LIMIT [nick | kanaal] {limiet | NONE} [HARD]\n" +" \n" +"Stelt het maximum aantal memo's in dat een gebruiker of\n" +"kanaal mag hebben. Als deze limiet op 0 word gezet kan de\n" +"gebruiker geen memo's ontvangen; zet dit op NONE om\n" +"toe te staan dat de gebruiker zoveel memo's mag hebben\n" +"als hij/zij wil. Als je geen nick of kanaal opgeeft, word\n" +"je eigen limiet ingesteld.\n" +" \n" +"Als je HARD toevoegt kan de gebruiker de limiet niet\n" +"veranderen. HARD weglaten heeft het tegenovergestelde\n" +"effect: de gebruiker in staat stellen de limiet te veranderen\n" +"(zelfs als een vorige limiet was ingesteld met HARD).\n" +" \n" +"Het gebruiken van het SET LIMIT commando is gelimiteerd tot\n" +"Services Operators. Andere gebruikers mogen alleen een limiet\n" +"voor zichzelf instellen, of voor een kanaal waar ze voldoende rechten\n" +"toe hebben, mogen hun eigen limiet niet verwijderen, mogen geen\n" +"limiet instellen boven %d, en mogen geen harde limiet instellen." + +#: modules/commands/os_set.cpp:208 +#, c-format +msgid "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." +msgstr "" +"Gebruik: LIST\n" +" \n" +"Geef de verschillende %s instellingen weer." + +#: modules/commands/os_set.cpp:234 +msgid "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." +msgstr "" +"Gebruik: NOEXPIRE {ON | OFF}\n" +" \n" +"Zet de geen-verloop modus aan of uit. In de geen-verloop modus\n" +"zullen nicks, kanalen, AKILLs en uitzonderingen niet verlopen,\n" +"totdat de geen-verloop modus weer wordt uitgezet.\n" +" \n" +"Deze optie komt overeen met de commandline-optie --noexpire." + +#: modules/commands/ms_set.cpp:246 +msgid "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." +msgstr "" +"Gebruik: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Verandert wanneer je geïnformeerd zal worden over nieuwe memo's:\n" +" \n" +" ON Je wordt geïnformeerd over memo's wanneer je inlogt,\n" +" terugkomt van /AWAY, en wanneer ze naar je\n" +" gestuurd worden.\n" +" LOGON Je wordt geïnformeerd over memo's wanneer je inlogt,\n" +" of wanneer je terugkomt van /AWAY.\n" +" NEW Je wordt alleen geïnformeerd over memo's wanneer ze\n" +" naar je worden verstuurd.\n" +" MAIL Je wordt geïnformeerd over memo's via zowel e-mail\n" +" als enige andere instellingen die je hebt.\n" +" NOMAIL Je wordt niet geïnformeerd over memo's via e-mail.\n" +" OFF Je zal geen notificaties over memo's ontvangen.\n" +" \n" +"ON is effectief LOGON en NEW gecombineerd." + +#: modules/commands/os_set.cpp:212 +msgid "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." +msgstr "" +"Gebruik: READONLY {ON | OFF}\n" +" \n" +"Zet de alleen-lezen modus aan of uit. In alleen-lezen modus\n" +"zullen normale gebruikers niet in staat zijn data van de\n" +"Services te wijzigen, inclusief kanaal en nick toegangslijsten, etc.\n" +"IRC operators met voldoende Services rechten kunnen de AKILL,\n" +"SQLINE, SNLINE en negeerlijsten wijzigen, en nicknames en kanalen\n" +"verwijderen, verbieden en schorsen, en het nieuws, oper info en de\n" +"DNS beheren, maar deze veranderingen zullen niet worden opgeslagen\n" +"behalve als de alleen-lezen modus wordt uitgeschakeld voordat de\n" +"Services afgesloten of opnieuw gestart worden.\n" +" \n" +"Deze optie komt overeen met de commandline-optie --readonly." + +#: modules/commands/os_set.cpp:243 +msgid "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." +msgstr "" +"Gebruik: SUPERADMIN {ON | OFF}\n" +" \n" +"Als je dit aan zet krijg je extra privileges, zo ben je dan\n" +"bijvoorbeeld \"stichter\" op alle kanalen, enz...\n" +" \n" +"Deze optie is niet permanent, en moet alleen gebruikt worden\n" +"wanneer het echt nodig is, en terug op OFF gezet worden als het\n" +"niet meer nodig is." + +#: modules/commands/ns_identify.cpp:107 +#, c-format +msgid "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." +msgstr "" +"Vertelt %s dat je echt de eigenaar van deze nick bent. Veel\n" +"commando's vereisen dat je jezelf identificeert met dit commando\n" +"voordat je ze gebruikt. Het wachtwoord moet hetzelfde zijn als\n" +"die je gestuurd hebt met het REGISTER commando." + +#: modules/commands/cs_invite.cpp:91 +#, c-format +msgid "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Laat %s jou of een optioneel gegeven nick uitnodigen\n" +"naar een gegeven kanaal.\n" +" \n" +"Standaard is dit gelimiteerd tot AOP's of diegenen met\n" +"niveau 5 of hoger op het kanaal." + +#: modules/commands/cs_unban.cpp:103 +#, c-format +msgid "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Zegt %s alle bans weg te halen die jou of een gegeven\n" +"gebruiker blokkeren het gegeven kanaal te betreden.\n" +"Indien geen kanaal opgegeven is, zullen alle bans die jou\n" +"treffen op kanalen waar je privileges hebt verwijderd worden.\n" +" \n" +"Standaard is dit gelimiteerd tot AOP's of diegenen met\n" +"niveau 5 of hoger op het kanaal." + +#: modules/commands/os_jupe.cpp:56 +msgid "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." +msgstr "" +"Zorgt ervoor dat Services de opgegeven server \"blokkeren\".\n" +"Dit betekent dat er een nep-\"server\", die verbonden is aan\n" +"Services, gemaakt wordt die voorkomt dat de echte server met\n" +"die naam verbindt. De JUPE kan worden verwijderd met een\n" +"standaard SQUIT commando. Als een reden is gegeven, wordt\n" +"deze in het server informatie veld geplaatst, anders zal het\n" +"informatie veld de text \"Juped by \" bevatten, waar\n" +" vervangen wordt door de nick die de server blokkeerde." + +#: modules/commands/cs_seen.cpp:261 +msgid "Tells you about the last time a user was seen" +msgstr "Vertelt je wanneer iemand het laatst gezien is" + +#: modules/commands/os_shutdown.cpp:19 +msgid "Terminate Services WITHOUT saving" +msgstr "Sluit Services af zonder de database te bewaren" + +#: modules/commands/os_shutdown.cpp:73 +msgid "Terminate services with save" +msgstr "Sla de database op en sluit Services af" + +#: modules/commands/os_news.cpp:156 +msgid "Text" +msgstr "Tekst" + +#: modules/commands/cs_access.cpp:576 +msgid "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." +msgstr "" +"Het ACCESS ADD commando voegt het gegeven masker toe\n" +"aan de toegangslijst met het gegeven gebruikersniveau; als het\n" +"masker al op de lijst staat, dan wordt het niveau gewijzigd naar\n" +"het niveau opgegeven in het commando. Het opgegeven niveau\n" +"mag een numerieke niveau zijn, of de naam van een\n" +"privilege (bijvoorbeeld AUTOOP).\n" +"Wanneer een gebruiker het kanaal betreed zal de toegang die\n" +"het krijgt van de hoogste niveau-vermelding zijn in de toegangslijst." + +#: modules/commands/cs_access.cpp:587 +msgid "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." +msgstr "" +"Het ACCESS DEL commando verwijdert de gegeven nick\n" +"van de toegangslijst. Als een lijst van vermeldingsnummers is\n" +"gegeven, dan zullen die vermeldingen worden verwijderd. (Zie\n" +"het voorbeeld voor LIST hieronder.)\n" +"Je kan jezelf van een toegangslijst verwijderen, ook als je\n" +"eigenlijk geen toegang hebt om die lijst te wijzigen." + +#: modules/commands/cs_access.cpp:593 +msgid "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." +msgstr "" +"Het ACCESS LIST commando toont de toegangslijst. Als\n" +"een masker word gegeven, worden enkel de overeenkomende\n" +"vermeldingen getoont. Als een lijst van vermeldingsnummers\n" +"is opgegeven dan worden enkel die getoont; bijvoorbeeld:\n" +" ACCESS #kanaal LIST 2-5,7-9\n" +" Toont toegangsvermeldingen 2 t/m 5 en 7 t/m 9.\n" +" \n" +"Het ACCESS VIEW commando geeft meer details dan\n" +"ACCESS LIST en toont wie de vermelding heeft\n" +"toegevoegd, en wanneer het laatst gebruikt is.\n" +" \n" +"Het ACCESS CLEAR commando maakt de toegangslijst\n" +"leeg." + +#: modules/commands/cs_flags.cpp:447 +msgid "" +"The CLEAR command clears the channel access list. This requires channel " +"founder access." +msgstr "" +"Het CLEAR commando maakt de toegangslijst leeg, dit vereist stichter rechten." + +#: modules/commands/cs_seen.cpp:173 +#, c-format +msgid "" +"The CLEAR command lets you clean the database by removing all entries from " +"the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." +msgstr "" +"Het CLEAR commando laat je de database opkuisen door het verwijderen van " +"alle\n" +"vermeldingen die binnen tijd zijn toegevoegd.\n" +" \n" +"Voorbeeld:\n" +" %s CLEAR 30m\n" +" Verwijdert alle vermeldingen toegevoegd in de laatste 30 minuten." + +#: modules/commands/bs_badwords.cpp:438 +msgid "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." +msgstr "" +"Het DEL commando verwijdert het gegeven woord\n" +"van de slechtewoordenlijst. Als vermeldingsnummers\n" +"worden gegeven, dan zullen die verwijderd worden. (Zie\n" +"het voorbeeld voor LIST hieronder.)\n" +" \n" +"Het LIST commando toont de slechtewoordenlijst.\n" +"Als jokertekens worden gegeven, dan worden enkel\n" +"overeenkomende woorden getoont. Als een lijst van\n" +"vermeldingsnummers is gegeven, dan worden enkel\n" +"die woorden getoont; bijvoorbeeld:\n" +" #kanaal LIST 2-5,7-9\n" +" Toont slechte woorden genummerd van 2 t/m 5 en\n" +" 7 t/m 9.\n" +" \n" +"Het CLEAR commando verwijdert alle woorden\n" +"van de slechtewoordenlijst." + +#: modules/commands/cs_entrymsg.cpp:241 +msgid "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." +msgstr "" +"Het ENTRYMSG ADD commando voegt het gegeven bericht\n" +"toe aan de lijst van berichten die getoont moeten worden bij het\n" +"betreden van het kanaal." + +#: modules/commands/cs_entrymsg.cpp:253 +msgid "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." +msgstr "" +"Het ENTRYMSG CLEAR commando verwijdert alle berichten\n" +"die getoont worden bij het betreden van het kanaal, dit schakelt\n" +"in weze de berichten bij het betreden uit." + +#: modules/commands/cs_entrymsg.cpp:245 +msgid "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." +msgstr "" +"Het ENTRYMSG DEL commando verwijdert het gegeven bericht\n" +"uit de lijst van berichten die getoont worden bij het betreden van het\n" +"kanaal. Je kan het bericht verwijderen door het opgeven van het\n" +"bijbehorende nummer die je kan verkrijgen door de lijst op te vragen\n" +"zoals hieronder uitgelegd." + +#: modules/commands/cs_entrymsg.cpp:250 +msgid "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." +msgstr "" +"Het ENTRYMSG LIST commando toont een lijst van berichten\n" +"die naar gebruikers gestuurd worden wanneer ze het kanaal betreden." + +#: modules/commands/ns_set.cpp:713 +msgid "The IMMED option is not available on this network." +msgstr "De IMMED optie is niet beschikbaar op dit netwerk." + +#: modules/commands/cs_access.cpp:821 +#, c-format +msgid "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." +msgstr "" +"Het LEVELS commando laat toe de betekenissen van numerieke\n" +"toegangsniveaus op kanalen aan te passen. Met dit commando\n" +"kan je de toegangsniveaus instellen die vereist zijn voor de meeste\n" +"functies van %s. (SET FOUNDER en dit commando zijn altijd\n" +"voorbehouden aan de kanaalstichter.)\n" +" \n" +"LEVELS SET laat toe het toegangsniveau voor een functie, of groep\n" +"van functies te wijzigen. LEVELS DISABLE (of kortweg DIS)\n" +"schakelt een automatische optie uit, of verbied toegang tot een functie\n" +"voor iedereen, INCLUSIEF de stichter (al kan de stichter deze altijd\n" +"weer inschakelen). Gebruik LEVELS SET founder om een niveau\n" +"enkel aan stichters voor te behouden.\n" +" \n" +"LEVELS LIST toont de huidige niveaus voor elke functie of groep\n" +"van functies. LEVELS RESET stelt de niveaus weer in naar\n" +"de standaardwaarden van een nieuw-geregistreerd kanaal.\n" +" \n" +"Voor een lijst van de opties en functies waar de niveaus van\n" +"ingesteld kunnen worden, zie HELP LEVELS DESC." + +#: modules/commands/cs_flags.cpp:442 +msgid "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." +msgstr "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." + +#: modules/commands/cs_flags.cpp:435 +msgid "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access " +"list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. " +"You are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of " +"what your access is." +msgstr "" +"Het MODIFY commando laat je toe de toegangslijst aan te passen.\n" +"Als het masker nog niet op de lijst staat, dan wordt deze toegevoegd en\n" +"de wijzigingen doorgevoerd. Als het masker geen vlaggen meer heeft,\n" +"dan wordt het masker verwijderd van de lijst. Je kan ook +* of -*\n" +"gebruiken om respectievelijk alle vlaggen toe te voegen of te verwijderen.\n" +"Je kan de toegangslijst enkel aanpassen wanneer je de nodige rechten\n" +"hiertoe hebt op het kanaal, en dan nog kan je enkel maar anderen\n" +"toevoegen tot maximum het toegangsniveau dat je zelf hebt." + +#: modules/commands/cs_seen.cpp:172 +msgid "" +"The STATS command prints out statistics about stored nicks and memory usage." +msgstr "" +"Het STATS commando toont statistieken over opgeslagen nicks en " +"geheugenverbruik." + +#: modules/commands/ns_register.cpp:291 +msgid "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." +msgstr "" +"Het email parameter is optioneel en stelt onmiddellijk het e-mail\n" +"adres voor je nick in.\n" +"Je privacy wordt gerespecteerd; dit e-mailadres wordt niet aan\n" +"een derde partij doorgegeven. Je zal mogelijks ook SET HIDE\n" +"willen doen na het registreren, als het al niet de standaard instelling is." + +#: modules/commands/cs_log.cpp:258 +#, c-format +msgid "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." +msgstr "" +"Het %s commando laat gebruikers toe om logs in te stellen\n" +"voor hun kanaal. Indien geen parameters worden gegeven\n" +"zal het de huidige log instellingen weergeven.\n" +" \n" +"Anderzijds, commando moet een commando naam zijn,\n" +"en methode één van de volgende log methodes:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Welke gebruikt worden om respectievelijk berichtjes, notices\n" +"of memo's te sturen naar het kanaal. Met MESSAGE en NOTICE\n" +"moet je een service bot toegewezen en aanwezig hebben op\n" +"je kanaal. Status mag een kanaal status zijn, zoals @ of +.\n" +" \n" +"Om een log methode weg te halen gebruik je dezelfde syntax\n" +"dat je zou gebruiken om het toe te voegen.\n" +" \n" +"Voorbeeld:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Dit zou een bericht sturen naar alle kanaal operators wanneer\n" +" iemand het ACCESS commando in ChanServ gebruikt op het kanaal." + +#: modules/commands/cs_ban.cpp:64 +#, c-format +msgid "The %s list for %s is full." +msgstr "De %s-lijst voor %s is vol." + +#: modules/commands/os_sxline.cpp:220 +#, c-format +msgid "The %s list has been cleared." +msgstr "De %s lijst is leeggemaakt." + +#: modules/commands/os_akill.cpp:377 +msgid "The AKILL list has been cleared." +msgstr "De AKILL lijst is leeggemaakt." + +#: modules/commands/os_defcon.cpp:136 modules/commands/os_defcon.cpp:225 +#, c-format +msgid "The Defcon level is now at: %d" +msgstr "Het Defcon niveau staat nu op: %d" + +#: modules/commands/ns_info.cpp:171 +#, c-format +msgid "The E-mail address of %s will now be hidden from %s INFO displays." +msgstr "" +"Het e-mailadres van %s zal vanaf nu verborgen worden in %s INFO opvragingen." + +#: modules/commands/ns_info.cpp:172 +#, c-format +msgid "The E-mail address of %s will now be shown in %s INFO displays." +msgstr "" +"Het e-mailadres van %s zal vanaf nu getoond worden in %s INFO opvragingen." + +#: modules/commands/cs_flags.cpp:449 +msgid "The available flags are:" +msgstr "De beschikbare vlaggen zijn:" + +#: modules/commands/os_defcon.cpp:240 +msgid "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." +msgstr "" +"Het defcon systeem kan gebruikt worden om een vooraf bepaalde\n" +"set van restricties op de services toe te passen tijdens een\n" +"aanval op het netwerk." + +#: modules/ns_maxemail.cpp:51 +#, c-format +msgid "The email address %s has reached its usage limit of %d users." +msgstr "Het e-mailadres %s heeft de limiet bereikt van %d gebruikers." + +#: modules/ns_maxemail.cpp:49 +#, c-format +msgid "The email address %s has reached its usage limit of 1 user." +msgstr "Het e-mailadres %s heeft de limiet bereikt van 1 gebruiker." + +#: modules/commands/cs_entrymsg.cpp:142 +#, c-format +msgid "The entry message list for %s is full." +msgstr "De welkomstberichtenlijst voor %s is vol." + +#: modules/commands/cs_access.cpp:796 +msgid "The following feature/function names are available:" +msgstr "De volgende privilege/functie namen zijn beschikbaar:" + +#: modules/commands/cs_access.cpp:584 +msgid "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." +msgstr "" +"Het opgegeven masker mag ook een kanaal zijn, welke de toegangslijst\n" +"van dat kanaal zal gebruiken, tot aan het opgegeven niveau." + +#: modules/commands/os_session.cpp:240 +#, c-format +msgid "" +"The host %s currently has %d sessions with a limit of %d because it matches " +"entry: %s." +msgstr "" +"Host %s heeft momenteel %d sessies met een limiet van %d omdat het " +"overeenstemt met: %s." + +#: modules/commands/ms_check.cpp:54 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has been read." +msgstr "De laatste memo die je naar %s gestuurd hebt (op %s) is gelezen." + +#: modules/commands/ms_check.cpp:52 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has not yet been read." +msgstr "" +"De laatste memo die je naar %s gestuurd hebt (op %s) is nog niet gelezen." + +#: modules/commands/ns_info.cpp:189 +#, c-format +msgid "The last quit message of %s will now be hidden from %s INFO displays." +msgstr "" +"De laatste quit reden van %s zal vanaf nu verborgen worden in %s INFO " +"opvragingen." + +#: modules/commands/ns_info.cpp:190 +#, c-format +msgid "The last quit message of %s will now be shown in %s INFO displays." +msgstr "" +"De laatste quit reden van %s zal vanaf nu getoond worden in %s INFO " +"opvragingen." + +#: modules/commands/ns_info.cpp:177 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." +msgstr "" +"Het laatst geziene ident@host masker van %s zal vanaf nu verborgen worden in " +"%s INFO opvragingen." + +#: modules/commands/ns_info.cpp:178 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." +msgstr "" +"Het laatst geziene ident@host masker van %s zal vanaf nu getoond worden in " +"%s INFO opvragingen." + +#: modules/commands/cs_enforce.cpp:190 +#, c-format +msgid "The limit on %s is not valid." +msgstr "De limiet op %s is ongeldig." + +#: modules/commands/os_forbid.cpp:193 +msgid "The mask must contain at least one non wildcard character." +msgstr "Het masker moet tenminste één niet-jokerteken bevatten." + +#: modules/commands/ms_set.cpp:153 +#, c-format +msgid "The memo limit for %s may not be changed." +msgstr "De memolimiet voor %s mag niet worden veranderd." + +#: modules/commands/cs_mode.cpp:347 +#, c-format +msgid "The mode lock list of %s is full." +msgstr "De mode blokkeerlijst van %s is vol." + +#: modules/commands/ns_set.cpp:355 +#, c-format +msgid "The new display MUST be a nickname of the nickname group %s." +msgstr "De nieuwe weergave MOET een nick zijn van de nick-groep %s." + +#: include/language.h:98 +#, c-format +msgid "The new display is now %s." +msgstr "De nieuwe weergave is nu %s." + +#: modules/commands/os_svs.cpp:57 +#, c-format +msgid "The nick %s is now being changed to %s." +msgstr "De nick %s wordt nu veranderd naar %s." + +#: modules/commands/bs_bot.cpp:149 +msgid "The old information is the same as the new information specified." +msgstr "De oude informatie is dezelfde als de nieuw opgegeven informatie." + +#: modules/commands/os_info.cpp:157 +#, c-format +msgid "The oper info already exists on %s." +msgstr "Die oper info bestaat reeds al op %s." + +#: modules/commands/os_info.cpp:147 +#, c-format +msgid "The oper info list for %s is full." +msgstr "De oper infolijst voor %s is vol." + +#: modules/commands/ns_info.cpp:183 +#, c-format +msgid "" +"The services access status of %s will now be hidden from %s INFO displays." +msgstr "" +"Het services toegangsniveau van %s zal vanaf nu verborgen worden in %s INFO " +"opvragingen." + +#: modules/commands/ns_info.cpp:184 +#, c-format +msgid "The services access status of %s will now be shown in %s INFO displays." +msgstr "" +"Het services toegangsniveau van %s zal vanaf nu getoond worden in %s INFO " +"opvragingen." + +#: modules/commands/os_session.cpp:433 +msgid "The session exception list is empty." +msgstr "De uitzonderingenlijst voor sessielimieten is leeg." + +#: modules/commands/ns_recover.cpp:121 +msgid "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." +msgstr "" +"De gebruiker met jouw nick werd verwijderd. Gebruik dit commando\n" +"opnieuw om Services' blokkade op jouw nick op te heffen." + +#: modules/pseudoclients/memoserv.cpp:195 +#, c-format +msgid "There are %d memos on channel %s." +msgstr "Er zijn %d memo's op kanaal %s." + +#: modules/commands/bs_botlist.cpp:47 +msgid "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" +msgstr "" +"Er zijn momenteel geen bots beschikbaar.\n" +"Vraag een Services Operator om er een te maken!" + +#: modules/commands/os_dns.cpp:213 +msgid "There are no configured servers." +msgstr "Er zijn geen servers ingesteld." + +#: modules/commands/os_forbid.cpp:392 +#, c-format +msgid "There are no forbids of type %s." +msgstr "Er is geen verbod van het type %s." + +#: modules/commands/ns_group.cpp:162 +msgid "There are too many nicks in your group." +msgstr "Er zijn teveel nicks in je groep." + +#: modules/commands/cs_log.cpp:123 +#, c-format +msgid "There currently are no logging configurations for %s." +msgstr "Er zijn momenteel geen log instellingen voor %s." + +#: modules/pseudoclients/memoserv.cpp:193 +#, c-format +msgid "There is %d memo on channel %s." +msgstr "Er is %d memo op kanaal %s." + +#: include/language.h:110 +#, c-format +msgid "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." +msgstr "" +"Er is een nieuwe memo op kanaal %s.\n" +"Typ %s%s READ %s %d om het te lezen." + +#: modules/commands/bs_assign.cpp:132 +#, c-format +msgid "There is no bot assigned to %s anymore." +msgstr "Er is geen bot meer toegewezen aan %s." + +#: modules/commands/os_news.cpp:33 +msgid "There is no logon news." +msgstr "Er is geen login nieuws." + +#: modules/commands/os_news.cpp:43 +msgid "There is no oper news." +msgstr "Er is geen operator nieuws." + +#: modules/commands/os_news.cpp:53 +msgid "There is no random news." +msgstr "Er is geen willekeurig nieuws." + +#: modules/commands/os_config.cpp:41 +#, c-format +msgid "There is no such configuration block %s." +msgstr "Onbestaand configuratie blok %s." + +#: modules/commands/cs_mode.cpp:706 +#, c-format +msgid "There is no such mode %s." +msgstr "Mode %s bestaat niet." + +#: modules/commands/ms_set.cpp:52 +msgid "There's no email address set for your nick." +msgstr "Er is geen e-mailadres ingesteld voor jouw nick." + +#: modules/commands/os_forbid.cpp:304 modules/commands/os_forbid.cpp:496 +#, c-format +msgid "This channel has been forbidden: %s" +msgstr "Dit kanaal is verboden: %s" + +#: modules/commands/cs_suspend.cpp:121 +msgid "This channel has been suspended." +msgstr "Dit kanaal is geschorst." + +#: modules/commands/cs_suspend.cpp:232 +msgid "This channel is suspended." +msgstr "Dit kanaal is geschorst." + +#: modules/commands/cs_suspend.cpp:268 +msgid "This channel may not be used." +msgstr "Dit kanaal mag niet gebruikt worden." + +#: modules/commands/os_dns.cpp:702 +msgid "" +"This command allows managing DNS zones used for controlling what servers " +"users\n" +"are directed to when connecting. Omitting all parameters prints out the " +"status of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to " +"this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, " +"the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given " +"zones." +msgstr "" +"Dit commando laat toe om domeinnamen te beheren voor het beheren van\n" +"naar welke servers gebruikers worden doorverwezen wanneer ze verbinden.\n" +"Het weglaten van alle parameters toont de status van het domeinnaam.\n" +" \n" +"ADDZONE voegt een domeinnaam toe, bijvoorbeeld us.jouwnetwerk.tld.\n" +"Servers kunnen dan toegevoegd worden met het ADDSERVER commando.\n" +" \n" +"Het ADDSERVER commando voegt servers toe aan het gegeven domein.\n" +"Bij een DNS-verzoek wordt deze zone uitgegeven indien deze bestaat,\n" +"anders worden alle servers in alle domeinen uitgegeven.\n" +" \n" +"Het ADDIP commando koppelt een IP aan een server.\n" +" \n" +"De POOL and DEPOOL commando's voegen servers toe en verwijderen\n" +"servers van de gegeven domeinen." + +#: modules/commands/hs_group.cpp:72 +msgid "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." +msgstr "" +"Dit commando stelt gebruikers in staat de vHost van hun\n" +"HUIDIGE nick de vHost van alle nicks in dezelfde groep te\n" +"laten zijn." + +#: modules/commands/ns_register.cpp:299 +msgid "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." +msgstr "" +"Dit commando maakt ook een nieuwe groep aan voor je nick,\n" +"dit zal je toelaten andere nicks te registreren die dan je instellingen,\n" +"memo's en kanaalrechten delen." + +#: modules/m_rewrite.cpp:145 +#, c-format +msgid "This command is an alias to the command %s." +msgstr "Dit commando is een alias voor het commando %s." + +#: modules/commands/ns_register.cpp:95 +msgid "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." +msgstr "" +"Dit commando wordt gebruikt door een aantal commando's als een\n" +"manier om wijzigingen aan je nick/login te bevestigen.\n" +" \n" +"Dit commando wordt het vaakst gebruikt om je e-mailadres te\n" +"bevestigen als je je registreert, of als je deze wijzigt.\n" +" \n" +"Dit wordt ook gebruikt nadat het RESETPASS commando gebruikt is\n" +"om je te kunnen identificeren zodat je je wachtwoord kan wijzigen." + +#: modules/commands/os_modinfo.cpp:70 +msgid "This command lists information about the specified loaded module." +msgstr "Dit commando geeft informatie weer over de opgegeven geladen module." + +#: modules/commands/hs_list.cpp:136 +msgid "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." +msgstr "" +"Dit commando toont alle geregistreerde vHosts aan de operator.\n" +"Indien patroon opgegeven is, worden enkel nicks en vHosts\n" +"getoont die overeenstemmen met patroon, bijvoorbeeld Rob*\n" +"voor alle vermeldingen die beginnen met \"Rob\".\n" +"Als de #X-Y stijl gebruikt wordt, dan zal enkel de reeks tussen X\n" +"en Y getoont worden. Bijvoorbeeld #1-3 zal de eerste 3\n" +"nick/vHost vermeldingen tonen." + +#: modules/commands/os_module.cpp:45 +msgid "" +"This command loads the module named modname from the modules\n" +"directory." +msgstr "Dit commando laadt de module genaamd modnaam uit de modules map." + +#: modules/commands/ns_group.cpp:201 +msgid "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." +msgstr "" +"Dit commando zorgt ervoor dat je huidige nickname zich bij de\n" +"groep van doel's nick aanmeldt. wachtwoord is het\n" +"wachtwoord van het doel.\n" +" \n" +"Bij een groep aanmelden stelt je in staat om je configuratie,\n" +"memos en kanaalrechten met alle nicknames in je groep te delen,\n" +"en veel meer!\n" +" \n" +"Een groep bestaat zolang als deze nuttig is. Dit betekent dat\n" +"zelfs als een nick in de groep niet meer geregistreerd is, je niet\n" +"de gedeelde dingen die hierboven beschreven zijn verliest,\n" +"zolang dat er minstens één nick overblijft in de groep.\n" +" \n" +"Je kan dit commando mogelijks zelfs gebruiken als je je nog niet\n" +"geregistreerd hebt. Als je nick al geregistreerd is moet je je\n" +"eerst identificeren voordat je dit commando kan gebruiken\n" +" \n" +"Het is aanbevolen om dit commando te gebruiken met een niet-\n" +"geregistreerde nick omdat het automatisch geregistreerd wordt\n" +"als je dit commando gebruikt. Je mag het mogelijks alleen met een\n" +"geregistreerde nick gebruiken (om je groep te veranderen) als de\n" +"netwerkbeheerders het toestaan.\n" +" \n" +"Je kan maar in één groep tegelijk zijn. Groepen samenvoegen is\n" +"niet mogelijk.\n" +" \n" +"Let op: alle nicknames in een groep hebben hetzelfde wachtwoord." + +#: modules/commands/ns_ajoin.cpp:292 +msgid "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." +msgstr "" +"Dit commando beheert je autojoinlijst. Wanneer je jezelf\n" +"identificeert zal je automatisch de kanalen in deze lijst joinen.\n" +"Services Operators kunnen een nick opgeven om anderen hun\n" +"autojoinlijsten aan te passen." + +#: modules/commands/ns_set.cpp:345 modules/commands/ns_set.cpp:669 +msgid "" +"This command may not be used on this network because nickname ownership is " +"disabled." +msgstr "" +"Dit commando mag niet gebruikt worden op dit netwerk om dat eigenaarschap " +"over nicknames uitgeschakeld is." + +#: modules/commands/os_module.cpp:118 +msgid "This command reloads the module named modname." +msgstr "Dit commando herlaad de module genaamd modnaam." + +#: modules/commands/hs_request.cpp:344 +msgid "This command retrieves the vhost requests." +msgstr "Dit commando toont de aangevraagde vHosts." + +#: modules/commands/os_logsearch.cpp:159 +msgid "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." +msgstr "" +"Dit commando doorzoekt Services' logbestanden voor berichten\n" +"die overeenkomen met het opgegeven patroon. De dag en limiet\n" +"parameters kunnen gebruikt worden om aan te geven hoeveel\n" +"dagen aan logs te doorzoeken en het aantal resultaten te beperken.\n" +"Standaard doorzoekt dit commando 1 week aan logs, en beperkt\n" +"de resultaten tot 50. \n" +"Bijvoorbeeld:\n" +" LOGSEARCH +21d +500l Anope\n" +" Doorzoekt de laatste 21 dagen aan log voor berichten\n" +" die Anope bevatten en toont de 500 recentste resultaten." + +#: modules/commands/cs_status.cpp:106 +msgid "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." +msgstr "" +"Dit commando toont je welke toegang iemand heeft op een\n" +"kanaal, en met welke toegangsvermeldingen deze overeenkomt.\n" +"Bovendien zal het ook overeenkomsten met autokick vermeldingen\n" +"tonen. Gebruik van dit commando is beperkt tot gebruikers die\n" +"toegang hebben om de toegangslijst van het kanaal aan te passen." + +#: modules/commands/ns_group.cpp:285 +msgid "" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." +msgstr "" +"Dit commando haalt je nick uit een groep, of, de opgegeven nick\n" +"uit een groep. De ongegroepeerde nick behoud zijn registratietijd,\n" +"wachtwoord, e-mail, groet, taal en URL. Al de rest wordt gereset.\n" +"Je kan jezelf niet uit een groep halen als je nick de enige in de groep is." + +#: modules/commands/os_module.cpp:168 +msgid "This command unloads the module named modname." +msgstr "Dit commando ontlaadt de module genaamd modnaam." + +#: modules/commands/ns_register.cpp:353 +msgid "This command will resend you the registration confirmation email." +msgstr "" +"Dit commando zal je de registratiebevestigings-e-mail opnieuw toezenden." + +#: include/language.h:90 +#, c-format +msgid "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" +msgstr "" +"Deze nick is eigendom van iemand anders. Gelieve een andere te kiezen.\n" +"(Indien dit uw nick is, typ %s%s IDENTIFY wachtwoord.)" + +#: modules/commands/os_forbid.cpp:469 +#, c-format +msgid "This nickname has been forbidden: %s" +msgstr "Deze nickname is verboden: %s" + +#: modules/commands/ns_recover.cpp:99 +#, c-format +msgid "This nickname has been recovered by %s." +msgstr "Deze nickname werd opgeëist door %s." + +#: modules/commands/ns_recover.cpp:77 +#, c-format +msgid "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." +msgstr "" +"Deze nickname werd opgeëist door %s. Indien jij dit niet deed,\n" +"dan kan het zijn dat %s je wachtwoord heeft, en wijzig je deze best." + +#: include/language.h:95 +msgid "This nickname has been registered; you may not use it." +msgstr "Deze nickname is geregistreerd; je mag het niet gebruiken." + +#: modules/commands/ns_suspend.cpp:246 +msgid "This nickname is suspended." +msgstr "Deze nick is geschorst." + +#: include/language.h:92 +#, c-format +msgid "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." +msgstr "" +"Deze nickname is geregistreerd en beschermd. Als het\n" +"jouw nickname is, typ %s%s IDENTIFY wachtwoord.\n" +"Gelieve anders een andere nickname te kiezen." + +#: modules/commands/ms_read.cpp:95 +#, c-format +msgid "To delete, type: %s%s %s %d" +msgstr "Om te verwijderen, typ: %s%s %s %d" + +#: modules/commands/ms_read.cpp:93 +#, c-format +msgid "To delete, type: %s%s %s %s %d" +msgstr "Om te verwijderen, typ: %s%s %s %s %d" + +#: modules/commands/bs_kick.cpp:791 +msgid "To protect ops against bot kicks" +msgstr "Om operators te beschermen tegen bot kicks" + +#: modules/commands/bs_kick.cpp:856 +msgid "To protect voices against bot kicks" +msgstr "Om voices te beschermen tegen bot kicks" + +#: modules/commands/cs_list.cpp:46 +msgid "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." +msgstr "" +"Om te zoeken naar kanalen die met een # beginnen moet gezocht\n" +"worden naar de kanaalnaam zonder het #-teken ervoor (anope\n" +"in plaats van #anope)." + +#: modules/commands/os_logsearch.cpp:139 +#, c-format +msgid "Too many results for %s." +msgstr "Teveel resultaten voor %s." + +#: modules/extra/stats/cs_fantasy_top.cpp:149 +#, c-format +msgid "Top %i of %s" +msgstr "Top %i van %s" + +#: modules/commands/os_list.cpp:43 +msgid "Topic" +msgstr "Topic" + +#: modules/commands/cs_topic.cpp:258 +msgid "Topic lock" +msgstr "Topicvergrendeling" + +#: modules/commands/cs_topic.cpp:114 +#, c-format +msgid "Topic lock option for %s is now off." +msgstr "Topicvergrendeling-optie voor %s is nu gedeactiveerd." + +#: modules/commands/cs_topic.cpp:97 +#, c-format +msgid "Topic lock option for %s is now on." +msgstr "Topicvergrendeling-optie voor %s is nu geactiveerd." + +#: modules/commands/cs_topic.cpp:256 +msgid "Topic retention" +msgstr "Topicbehoud" + +#: modules/commands/cs_topic.cpp:60 +#, c-format +msgid "Topic retention option for %s is now off." +msgstr "Topicbehoud-optie voor %s is nu gedeactiveerd." + +#: modules/commands/cs_topic.cpp:54 +#, c-format +msgid "Topic retention option for %s is now on." +msgstr "Topicbehoud-optie voor %s is nu geactiveerd." + +#: modules/commands/cs_topic.cpp:265 +msgid "Topic set by" +msgstr "Topic gezet door" + +#: modules/commands/bs_kick.cpp:1323 +msgid "Turn caps lock OFF!" +msgstr "Zet hoofdletters UIT!" + +#: modules/extra/stats/m_chanstats.cpp:17 +#: modules/extra/stats/m_chanstats.cpp:71 +msgid "Turn chanstats statistics on or off" +msgstr "Zet chanstats statistieken aan of uit" + +#: modules/commands/ns_set.cpp:1009 +msgid "Turn nickname security on or off" +msgstr "Zet nickname beveiliging aan of uit" + +#: modules/commands/ns_set.cpp:655 +msgid "Turn protection on or off" +msgstr "Zet bescherming aan of uit" + +#: modules/commands/ns_list.cpp:264 +#, c-format +msgid "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Zet de privé optie van %s aan of uit voor de nick.\n" +"Met PRIVATE aan zal de nick niet verschijnen in nicklijsten\n" +"gegenereerd met %s's LIST commando. (Echter,\n" +"iedereen die de nick weet kan nog steeds informatie krijgen\n" +"via het INFO commando." + +#: modules/commands/ns_list.cpp:236 +#, c-format +msgid "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Zet de privé optie van %s aan of uit voor jouw nick.\n" +"Met PRIVATE aan zal je nick niet verschijnen in nicklijsten\n" +"gegenereerd met %s's LIST commando. (Echter,\n" +"iedereen die je nick weet kan nog steeds informatie krijgen\n" +"via het INFO commando." + +#: modules/commands/ns_set.cpp:1059 modules/commands/ns_set.cpp:1088 +#, c-format +msgid "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." +msgstr "" +"Zet %s's veiligheidsopties aan of uit voor jouw nick.\n" +"Met SECURE aan moet je altijd een wachtwoord geven\n" +"voordat je wordt herkend als de eigenaar van de nick,\n" +"ook als je adres op de toegangslijst voor deze nick\n" +"staat. Echter, als je op de toegangslijst staat zal\n" +"%s je niet automatisch killen, hoe de KILL optie ook\n" +"ingesteld staat." + +#: modules/extra/stats/m_chanstats.cpp:142 +msgid "Turns chanstats channel statistics ON or OFF for this user." +msgstr "Zet chanstats kanaal statistieken aan of uit voor deze gebruiker." + +#: modules/extra/stats/m_chanstats.cpp:61 +#: modules/extra/stats/m_chanstats.cpp:119 +msgid "Turns chanstats statistics ON or OFF." +msgstr "Zet chanstats statistieken aan of uit." + +#: modules/commands/ns_set.cpp:772 +#, c-format +msgid "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Zet de automatiche beschermingsoptie voor de nick aan of uit.\n" +"Met bescherming aan, krijgt elke gebruiker met de nick een\n" +"minuut om zich te identificeren of om zijn/haar nick te\n" +"veranderen. Is geen van beiden gebeurd in die minuut, dan zal\n" +"%s een nick-verandering forceren.\n" +" \n" +"Als je QUICK kiest, zal de gebruiker maar 20 seconden hebben\n" +"om zijn/haar nick te veranderen in plaats van de gebruikelijke\n" +"60. Als je IMMED kiest, zal de nick meteen worden aangepast\n" +"zonder enige waarschuwing vooraf of kans om zijn/haar nick\n" +"te wijzigen; gebruik deze optie alleen wanneer noodzakelijk.\n" +"Deze optie kan ook uitgeschakeld zijn door de netwerk\n" +"administrators." + +#: modules/commands/ns_set.cpp:738 +#, c-format +msgid "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Zet de automatiche beschermingsoptie voor je nick aan of uit.\n" +"Met bescherming aan, krijgt elke gebruiker met jouw nick een\n" +"minuut om zich te identificeren of om zijn/haar nick te\n" +"veranderen. Is geen van beiden gebeurd in die minuut, dan zal\n" +"%s een nick-verandering forceren.\n" +" \n" +"Als je QUICK kiest, zal de gebruiker maar 20 seconden hebben\n" +"om zijn/haar nick te veranderen in plaats van de gebruikelijke\n" +"60. Als je IMMED kiest, zal de nick meteen worden aangepast\n" +"zonder enige waarschuwing vooraf of kans om zijn/haar nick\n" +"te wijzigen; gebruik deze optie alleen wanneer noodzakelijk.\n" +"Deze optie kan ook uitgeschakeld zijn door de netwerk\n" +"beheerders." + +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_forbid.cpp:358 +msgid "Type" +msgstr "Type" + +#: modules/commands/ns_set.cpp:62 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Typ %s%s HELP %s optie voor meer informatie\n" +"over een specifieke optie." + +#: modules/commands/bs_kick.cpp:151 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." +msgstr "" +"Typ %s%s HELP %s optie voor meer informatie\n" +"over een specifieke optie.\n" +" \n" +"Let op: toegang tot dit commando wordt gereguleerd door\n" +"het SET niveau." + +#: modules/commands/ns_set.cpp:107 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." +msgstr "" +"Typ %s%s HELP %s optie voor meer informatie\n" +"over een specifieke optie. Deze opties zullen ingesteld worden\n" +"op de gegeven nickname. " + +#: modules/commands/bs_set.cpp:62 modules/commands/cs_set.cpp:63 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." +msgstr "" +"Typ %s%s HELP %s optie voor meer informatie over een\n" +"specifieke optie." + +#: modules/pseudoclients/nickserv.cpp:361 +#, c-format +msgid "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." +msgstr "" +"Typ %s%s SET EMAIL e-mail om je e-mail in te stellen.\n" +"Je privacy wordt gerespecteerd; deze e-mail wordt niet aan\n" +"een derde partij doorgegeven." + +#: modules/commands/os_module.cpp:128 +msgid "Un-Load a module" +msgstr "Ontlaad een module" + +#: modules/commands/os_sxline.cpp:337 modules/commands/os_sxline.cpp:552 +#: modules/commands/os_akill.cpp:136 +#, c-format +msgid "Unable to find regex engine %s." +msgstr "Kan regex engine %s niet vinden." + +#: modules/commands/os_module.cpp:36 modules/commands/os_module.cpp:108 +#, c-format +msgid "Unable to load module %s." +msgstr "Laden van module %s is mislukt." + +#: modules/commands/os_module.cpp:73 modules/commands/os_module.cpp:90 +#: modules/commands/os_module.cpp:145 modules/commands/os_module.cpp:159 +#, c-format +msgid "Unable to remove module %s." +msgstr "Verwijderen van module %s is mislukt." + +#: modules/commands/bs_assign.cpp:90 +msgid "Unassigns a bot from a channel" +msgstr "Toewijzing van een bot ongedaan maken op een kanaal" + +#: modules/commands/bs_assign.cpp:139 +msgid "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." +msgstr "" +"Verwijdert een bot van een kanaal. Wanneer je dit commando\n" +"gebruikt zal de bot niet meer in het kanaal komen. De configuratie\n" +"van de bot voor het kanaal wordt echter wel behouden,\n" +"zodat je later de bot altijd opnieuw aan het kanaal kan\n" +"toewijzen zonder dat je deze opnieuw hoeft te configureren." + +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1193 +#: modules/commands/bs_kick.cpp:1196 +msgid "Underlines kicker" +msgstr "Onderlijningskicker" + +#: modules/commands/os_dns.cpp:595 +msgid "Unknown SET option." +msgstr "Onbekende SET optie." + +#: modules/commands/os_stats.cpp:229 +#, c-format +msgid "Unknown STATS option: %s" +msgstr "Onbekende STATS optie %s" + +#: src/command.cpp:222 src/command.cpp:233 +#, c-format +msgid "Unknown command %s." +msgstr "Onbekend commando %s." + +#: src/command.cpp:220 src/command.cpp:231 +#, c-format +msgid "Unknown command %s. \"%s%s HELP\" for help." +msgstr "Onbekend commando %s. \"%s%s HELP\" voor hulp." + +#: modules/commands/cs_mode.cpp:317 modules/commands/cs_mode.cpp:409 +#, c-format +msgid "Unknown mode character %c ignored." +msgstr "Onbekende mode karakter %c genegeerd." + +#: modules/commands/os_logsearch.cpp:78 +#, c-format +msgid "Unknown parameter: %s" +msgstr "Onbekend parameter: %s" + +#: modules/commands/os_dns.cpp:241 +msgid "Unpooled" +msgstr "Niet pooled" + +#: modules/commands/cs_drop.cpp:77 +msgid "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." +msgstr "" +"Zegt de registratie van het gegeven kanaal op. Kan alleen\n" +"gebruikt worden door de kanaalstichter." + +#: modules/commands/cs_drop.cpp:74 +msgid "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." +msgstr "" +"Zegt de registratie van het gegeven kanaal op. Enkel\n" +"Services Operators kunnen dit voor elk kanaal doen,\n" +"ook al zijn ze de stichter niet." + +#: modules/commands/ns_suspend.cpp:160 +msgid "Unsuspend a given nick" +msgstr "Schorsing op gegeven nick opheffen" + +#: modules/commands/ns_suspend.cpp:199 +msgid "Unsuspends a nickname which allows it to be used again." +msgstr "Heft de schorsing op een nick op zodat deze weer kan gebruikt worden." + +#: modules/commands/cs_updown.cpp:126 +msgid "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." +msgstr "" +"Werkt de gegeven nick's status modes bij op een kanaal.\n" +"Als nick niet opgegeven is, dan wordt jouw status bijgewerkt.\n" +"Indien kanaal niet wordt opgegeven, dan wordt je status op\n" +"ieder kanaal waar je zit bijgewerkt." + +#: modules/commands/cs_updown.cpp:48 +msgid "Updates a selected nicks status on a channel" +msgstr "Werkt de gegeven nick's status bij op een kanaal" + +#: modules/commands/ns_update.cpp:19 +msgid "Updates your current status, i.e. it checks for new memos" +msgstr "" +"Werkt je huidige status bij, het controleert bijvoorbeeld op nieuwe memo's" + +#: modules/commands/ns_update.cpp:43 +msgid "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." +msgstr "" +"Werkt je huidige status bij, het controleert bijvoorbeeld op nieuwe\n" +"memo's, stelt de benodigde kanaalmodes in, en werkt je vHost en\n" +"gebruikersvlaggen bij (laatst gezien, enz)." + +#: modules/commands/os_update.cpp:25 +msgid "Updating databases." +msgstr "Bijwerken databases." + +#: modules/commands/os_stats.cpp:154 +#, c-format +msgid "Uplink capab: %s" +msgstr "Uplink capab: %s" + +#: modules/commands/os_stats.cpp:153 +#, c-format +msgid "Uplink server: %s" +msgstr "Uplink server: %s" + +#: modules/commands/help.cpp:127 +#, c-format +msgid "Use the %s ALL command to list all commands and their descriptions." +msgstr "" +"Gebruik het %s ALL commando om alle commando's en hun omschrijving te tonen." + +#: modules/commands/bs_info.cpp:59 +msgid "Used on" +msgstr "Gebruikt op" + +#: data/chanserv.example.conf:821 +msgid "Used to manage channels" +msgstr "Dient om kanalen te beheren" + +#: data/chanserv.example.conf:809 +msgid "Used to manage the list of privileged users" +msgstr "Dient om de lijst van gebruikers met privileges te beheren" + +#: data/chanserv.example.conf:815 +msgid "Used to modify the channel status of you or other users" +msgstr "Dient om de kanaalstatus van jezelf of anderen aan te passen" + +#: modules/commands/cs_akick.cpp:575 +msgid "User has been banned from the channel" +msgstr "Gebruiker werd verbannen van het kanaal" + +#: modules/commands/os_dns.cpp:587 +#, c-format +msgid "User limit for %s removed." +msgstr "Gebruikerslimiet voor %s verwijderd." + +#: modules/commands/os_dns.cpp:585 +#, c-format +msgid "User limit for %s set to %d." +msgstr "Gebruikerslimiet voor %s gewijzigd naar %d." + +#: modules/commands/os_list.cpp:43 +msgid "Users" +msgstr "Gebruikers" + +#: modules/commands/os_stats.cpp:172 +#, c-format +msgid "Users (nick): %lu entries, %lu buckets, longest chain is %d" +msgstr "Gebruikers (nick): %lu vermeldingen, %lu emmers, langste ketting is %d" + +#: modules/commands/os_stats.cpp:177 +#, c-format +msgid "Users (uid): %lu entries, %lu buckets, longest chain is %d" +msgstr "Gebruikers (uid): %lu vermeldingen, %lu emmers, langste ketting is %d" + +#: modules/commands/os_list.cpp:184 +msgid "Users list:" +msgstr "Gebruikerslijst:" + +#: modules/commands/ns_info.cpp:105 modules/commands/ns_info.cpp:107 +msgid "VHost" +msgstr "vHost" + +#: modules/commands/hs_set.cpp:92 +#, c-format +msgid "VHost for %s set to %s." +msgstr "vHost voor %s gewijzigd naar %s." + +#: modules/commands/hs_set.cpp:90 +#, c-format +msgid "VHost for %s set to %s@%s." +msgstr "vHost voor %s gewijzigd naar %s@%s." + +#: modules/commands/hs_set.cpp:199 +#, c-format +msgid "VHost for group %s set to %s." +msgstr "vHost voor groep %s gewijzigd naar %s." + +#: modules/commands/hs_set.cpp:197 +#, c-format +msgid "VHost for group %s set to %s@%s." +msgstr "vHost voor groep %s gewijzigd naar %s@%s." + +#: modules/commands/os_session.cpp:247 +msgid "VIEW host" +msgstr "VIEW host" + +#: modules/commands/os_sxline.cpp:428 modules/commands/os_sxline.cpp:662 +#: modules/commands/os_akill.cpp:389 +msgid "VIEW [mask | list | id]" +msgstr "VIEW [masker | lijst | id]" + +#: modules/commands/os_session.cpp:526 +msgid "VIEW [mask | list]" +msgstr "VIEW [masker | lijst]" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +msgid "Value" +msgstr "Waarde" + +#: modules/commands/os_config.cpp:48 +#, c-format +msgid "Value of %s:%s changed to %s" +msgstr "Waarde van %s:%s gewijzigd naar %s" + +#: modules/commands/hs_list.cpp:58 modules/commands/hs_request.cpp:305 +msgid "Vhost" +msgstr "vHost" + +#: modules/commands/hs_del.cpp:38 +#, c-format +msgid "Vhost for %s removed." +msgstr "vHost voor %s verwijderd." + +#: modules/commands/os_oper.cpp:69 +msgid "View and change Services Operators" +msgstr "Bekijk en wijzig Services Operators" + +#: modules/commands/os_config.cpp:19 +msgid "View and change configuration file settings" +msgstr "Bekijk en wijzig configuratiebestand's instellingen" + +#: modules/commands/os_session.cpp:245 +msgid "View the list of host sessions" +msgstr "Bekijk de host sessielijst" + +#: modules/commands/bs_kick.cpp:1221 +msgid "Voices protection" +msgstr "Voices bescherming" + +#: modules/commands/bs_kick.cpp:1406 +msgid "Watch your language!" +msgstr "Let op je taal!" + +#: modules/commands/cs_list.cpp:237 +#, c-format +msgid "" +"When private is set, the channel will not appear in\n" +"%s's %s command." +msgstr "" +"Wanneer private geactiveerd is, zal het kanaal niet verschijnen in\n" +"%s's %s commando." + +#: modules/commands/ms_info.cpp:204 +msgid "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." +msgstr "" +"Zonder een parameter geeft dit informatie weer over het aantal\n" +"memo's dat je hebt, hoeveel daarvan er ongelezen zijn, en\n" +"hoeveel memo's je in totaal kan ontvangen.\n" +" \n" +"Met een kanaal parameter wordt dezelfde informatie voor\n" +"het gegeven kanaal weergegeven.\n" +" \n" +"Met een nick parameter wordt dezelfde informatie voor de\n" +"gegeven nick weergegeven. Dit gebruik is gelimiteerd tot\n" +"Services Operators." + +#: modules/commands/ns_logout.cpp:66 +msgid "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." +msgstr "" +"Zonder een parameter keert dit command het effect van het\n" +"IDENTIFY commando om; je wordt dus niet meer herkend als\n" +"de echte eigenaar van je huidige nick. Merk echter op dat\n" +"je niet wordt gevraagd jezelf opnieuw te identificeren.\n" +" \n" +"Met een parameter doet dit commando hetzelfde voor de\n" +"gegeven nick. Als je ook REVALIDATE meegeeft, zullen\n" +"Services de gegeven nick vragen opnieuw te identificeren.\n" +"Het gebruik hiervan is gelimiteerd tot Services Operators." + +#: modules/commands/os_stats.cpp:236 +msgid "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." +msgstr "" +"Zonder een optie wordt het huidig aantal gebruikers online,\n" +"en het hoogste aantal gebruikers online sinds Services gestart zijn,\n" +"en hoe lang Services al online zijn, weegegeven.\n" +" \n" +"Met de AKILL optie worden de huidige grootte van de AKILL\n" +"lijst en de huidige standaard verloop-tijd weergegeven.\n" +" \n" +"De RESET optie reset het maximum gebruikers aantal\n" +"naar het aantal momenteel aanwezig op het netwerk.\n" +" \n" +"De UPLINK optie toont informatie over de huidige server\n" +"dat Services gebruiken als uplink naar het netwerk.\n" +" \n" +"De HASH optie toont informatie over de hash mappen.\n" +" \n" +"De ALL optie toont alle bovenstaande statistieken." + +#: modules/commands/bs_badwords.cpp:194 +msgid "Word" +msgstr "Woord" + +#: modules/commands/ns_group.cpp:158 +#, c-format +msgid "You are already a member of the group of %s." +msgstr "Je bent al lid van de groep van %s." + +#: modules/commands/os_login.cpp:34 modules/commands/ns_identify.cpp:87 +msgid "You are already identified." +msgstr "Je bent al geïdentificeerd." + +#: modules/commands/cs_invite.cpp:64 +#, c-format +msgid "You are already in %s!" +msgstr "Je bent al op %s!" + +#: modules/commands/os_set.cpp:91 +msgid "You are no longer a super admin." +msgstr "Je bent geen super administrator meer." + +#: modules/commands/os_login.cpp:81 +msgid "You are not identified." +msgstr "Je bent niet geïdentificeerd." + +#: include/language.h:100 +msgid "You are not permitted to be on this channel." +msgstr "Je hebt geen toestemming om op dit kanaal aanwezig te zijn." + +#: modules/commands/ms_set.cpp:158 +msgid "You are not permitted to change your memo limit." +msgstr "Je hebt geen toegang om je memolimiet te veranderen." + +#: modules/commands/ns_cert.cpp:183 +msgid "You are not using a client certificate." +msgstr "Je gebruikt geen certificaat." + +#: modules/commands/os_set.cpp:85 +msgid "You are now a super admin." +msgstr "Je bent nu een super administrator." + +#: modules/commands/os_oline.cpp:36 +msgid "You are now an IRC Operator." +msgstr "Je bent nu een IRC Operator." + +#: modules/commands/ns_resetpass.cpp:108 +msgid "You are now identified for your nick. Change your password now." +msgstr "Je bent nu geïdentificeerd voor je nick. Wijzig nu je wachtwoord." + +#: modules/commands/ns_group.cpp:64 +#, c-format +msgid "You are now in the group of %s." +msgstr "Je zit nu in de groep van %s." + +#: modules/pseudoclients/memoserv.cpp:147 +#, c-format +msgid "" +"You are over your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Je hebt je maximum aantal memo's overschreden (%d). Je kan geen nieuwe " +"memo's ontvangen totdat je enkele van je huidige memo's verwijdert." + +#: modules/commands/os_noop.cpp:33 +msgid "You can not NOOP Services." +msgstr "Je kan geen NOOP doen op Services." + +#: modules/commands/cs_access.cpp:672 +msgid "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." +msgstr "" +"Je kan de stichter privilege niet uitschakelen, want het zou onmogelijk zijn " +"dit later weer in te schakelen." + +#: modules/commands/os_jupe.cpp:34 +msgid "You can not jupe an already juped server." +msgstr "Je kan geen reeds geblokkeerde server blokkeren." + +#: modules/commands/os_jupe.cpp:32 +msgid "You can not jupe your Services' pseudoserver or your uplink server." +msgstr "Je kan services' pseudoserver of je uplink server niet blokkeren." + +#: modules/commands/os_module.cpp:80 +#, c-format +msgid "You can not reload this module directly, instead reload %s." +msgstr "" +"Je kan deze module niet rechtstreeks herladen, in plaats daarvan, herlaad %s." + +#: modules/commands/ms_rsend.cpp:46 +msgid "You can not request a receipt when sending a memo to yourself." +msgstr "" +"Je kan geen ontvangstbevestiging aanvragen voor een memo die je naar jezelf " +"stuurt." + +#: modules/commands/ns_recover.cpp:163 +#, c-format +msgid "You can't %s yourself!" +msgstr "Je kan geen %s doen op jezelf!" + +#: modules/commands/cs_access.cpp:154 modules/commands/cs_flags.cpp:109 +#: modules/commands/cs_xop.cpp:151 +msgid "You can't add a channel to its own access list." +msgstr "Je kan geen kanaal toevoegen op zijn eigen toegangslijst." + +#: modules/commands/ns_logout.cpp:37 +#, c-format +msgid "You can't logout %s, they are a Services Operator." +msgstr "Je kan %s niet uitloggen omdat hij een Services Operator is." + +#: modules/commands/ns_set.cpp:927 +#, c-format +msgid "You cannot %s on this network." +msgstr "Je kan geen %s doen op dit netwerk." + +#: modules/commands/cs_flags.cpp:231 +#, c-format +msgid "You cannot set the %c flag." +msgstr "Je kan de %c vlag niet zetten." + +#: modules/commands/ms_set.cpp:173 +#, c-format +msgid "You cannot set the memo limit for %s higher than %d." +msgstr "Je kan de memolimiet voor %s niet hoger dan %d zetten." + +#: modules/commands/ms_set.cpp:175 +#, c-format +msgid "You cannot set your memo limit higher than %d." +msgstr "Je kan je memolimiet niet hoger dan %d zetten." + +#: modules/commands/bs_assign.cpp:124 +msgid "You cannot unassign bots while persist is set on the channel." +msgstr "" +"Je kan geen bottoewijzingen ongedaan maken zolang persist geactiveerd is op " +"het kanaal." + +#: modules/commands/ns_set.cpp:480 +msgid "You cannot unset the e-mail on this network." +msgstr "Je kan het e-mailadres niet verwijderen op dit netwerk." + +#: modules/commands/help.cpp:177 +msgid "You cannot use this command." +msgstr "Je kan dit commando niet gebruiken." + +#: modules/commands/ms_info.cpp:151 +#, c-format +msgid "You currently have %d memos, of which %d are unread." +msgstr "Je hebt momenteel %d memo's, waarvan er %d ongelezen zijn." + +#: modules/commands/ms_info.cpp:149 +#, c-format +msgid "You currently have %d memos, of which 1 is unread." +msgstr "Je hebt momenteel %d memo's, waarvan er 1 ongelezen is." + +#: modules/commands/ms_info.cpp:147 +#, c-format +msgid "You currently have %d memos." +msgstr "Je hebt momenteel %d memo's." + +#: modules/commands/ms_info.cpp:145 +#, c-format +msgid "You currently have %d memos; all of them are unread." +msgstr "Je hebt momenteel %d memo's; allemaal zijn ze ongelezen." + +#: modules/commands/ms_info.cpp:134 +msgid "You currently have 1 memo, and it has not yet been read." +msgstr "Je hebt momenteel 1 memo, en deze is nog niet gelezen." + +#: modules/commands/ms_info.cpp:136 +msgid "You currently have 1 memo." +msgstr "Je hebt momenteel 1 memo." + +#: modules/commands/ms_info.cpp:130 +msgid "You currently have no memos." +msgstr "Je hebt momenteel geen memo's." + +#: modules/commands/cs_mode.cpp:564 modules/commands/cs_mode.cpp:621 +#, c-format +msgid "You do not have access to set mode %c." +msgstr "Je hebt geen toegang om mode %c te zetten." + +#: modules/commands/cs_mode.cpp:578 modules/commands/cs_mode.cpp:590 +#: modules/commands/cs_mode.cpp:631 +#, c-format +msgid "You do not have the access to change %s's modes." +msgstr "Je hebt geen toegang om %s's modes te veranderen." + +#: modules/commands/cs_seen.cpp:198 +#, c-format +msgid "You found me, %s!" +msgstr "Je hebt me gevonden, %s!" + +#: modules/pseudoclients/memoserv.cpp:143 +#, c-format +msgid "You have %d new memos." +msgstr "Je hebt %d nieuwe memo's." + +#: modules/pseudoclients/memoserv.cpp:143 +msgid "You have 1 new memo." +msgstr "Je hebt 1 nieuwe memo." + +#: include/language.h:112 +#, c-format +msgid "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." +msgstr "" +"Je hebt een nieuwe memo van %s.\n" +"Typ %s%s READ %d om deze te lezen." + +#: modules/commands/cs_invite.cpp:76 +#, c-format +msgid "You have been invited to %s by %s." +msgstr "Je bent uitgenodigd naar %s door %s." + +#: modules/commands/cs_invite.cpp:81 +#, c-format +msgid "You have been invited to %s." +msgstr "Je bent uitgenodigd naar %s." + +#: modules/protocol/ratbox.cpp:166 modules/commands/ns_recover.cpp:96 +#, c-format +msgid "You have been logged in as %s." +msgstr "Je bent ingelogd als %s." + +#: modules/commands/os_login.cpp:86 +msgid "You have been logged out." +msgstr "Je bent uitgelogd." + +#: modules/commands/cs_unban.cpp:94 +#, c-format +msgid "You have been unbanned from %s." +msgstr "Je ban op %s werd opgeheven." + +#: modules/commands/cs_unban.cpp:54 +#, c-format +msgid "You have been unbanned from %d channels." +msgstr "Je ban werd op %d kana(a)l(en) opgeheven." + +#: modules/commands/ms_info.cpp:169 +msgid "You have no limit on the number of memos you may keep." +msgstr "Je hebt geen limiet op het aantal memo's dat je mag hebben." + +#: include/language.h:114 +msgid "You have no memos." +msgstr "Je hebt geen memo's." + +#: include/language.h:117 +msgid "You have no new memos." +msgstr "Je hebt geen nieuwe memo's." + +#: modules/pseudoclients/memoserv.cpp:149 +#, c-format +msgid "" +"You have reached your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Je hebt je maximum aantal memo's bereikt (%d). Je kan geen nieuwe memo's " +"ontvangen totdat je enkele van je huidige memo's verwijdert." + +#: modules/commands/ns_recover.cpp:117 +#, c-format +msgid "You have regained control of %s." +msgstr "Je hebt weer de controle over %s." + +#: modules/commands/ns_drop.cpp:66 +msgid "You may drop any nick within your group." +msgstr "Je kan de registraties van nicks in je groep verwijderen." + +#: modules/commands/cs_mode.cpp:322 modules/commands/cs_mode.cpp:414 +#, c-format +msgid "You may not (un)lock mode %c." +msgstr "Je mag mode %c niet (de)blokkeren." + +#: modules/commands/ns_set.cpp:485 +msgid "You may not change the e-mail of other Services Operators." +msgstr "Je mag het e-mailadres van andere Services Operators niet wijzigen." + +#: modules/commands/ns_set.cpp:474 +msgid "You may not change the email of an unconfirmed account." +msgstr "Je mag het e-mailadres van een onbevestigde account niet wijzigen." + +#: modules/commands/ns_set.cpp:196 +msgid "You may not change the password of other Services Operators." +msgstr "Je mag het wachtwoord van andere Services Operators niet wijzigen." + +#: modules/commands/ns_drop.cpp:45 +msgid "You may not drop other Services Operators' nicknames." +msgstr "" +"Je mag de nickregistraties van andere Services Operators niet verwijderen." + +#: modules/commands/ns_getpass.cpp:32 +msgid "You may not get the password of other Services Operators." +msgstr "Je mag het wachtwoord van andere Services Operators niet opvragen." + +#: modules/commands/ns_suspend.cpp:100 +msgid "You may not suspend other Services Operators' nicknames." +msgstr "Je kan de nicks van andere Services Operators niet schorsen." + +#: modules/commands/ns_access.cpp:136 +msgid "" +"You may view but not modify the access list of other Services Operators." +msgstr "" +"Je kan de toegangslijst van andere Services Operators bekijken, maar niet " +"aanpassen." + +#: modules/commands/ns_cert.cpp:292 +msgid "" +"You may view but not modify the certificate list of other Services Operators." +msgstr "" +"Je kan de certificaatlijst van andere Services Operators bekijken, maar niet " +"aanpassen." + +#: modules/commands/cs_seen.cpp:287 +#, c-format +msgid "You might see yourself in the mirror, %s." +msgstr "Je kan jezelf misschien zien in de spiegel, %s." + +#: include/language.h:120 +msgid "You must assign a bot to the channel before using this command." +msgstr "" +"Je moet een bot toewijzen aan het kanaal alvorens dit commando te gebruiken." + +#: modules/commands/cs_register.cpp:49 +msgid "You must be a channel operator to register the channel." +msgstr "Je moet een operator zijn op het kanaal om deze te registreren." + +#: modules/commands/cs_updown.cpp:94 modules/commands/cs_updown.cpp:192 +#, c-format +msgid "You must be in %s to use this command." +msgstr "Je moet in %s zijn om dit commando te gebruiken." + +#: modules/commands/cs_register.cpp:37 +msgid "You must confirm your account before you can register a channel." +msgstr "Je moet je nick bevestigen voor je een kanaal kan registreren." + +#: modules/commands/hs_request.cpp:100 +msgid "You must confirm your account before you may request a vhost." +msgstr "Je moet je nick bevestigen voor je een vhost kan aanvragen." + +#: modules/commands/ms_send.cpp:44 +msgid "You must confirm your account before you may send a memo." +msgstr "Je moet je nick bevestigen voor je een memo kan versturen." + +#: modules/commands/cs_drop.cpp:42 +#, c-format +msgid "" +"You must enter the channel name twice as a confirmation that you wish to drop" +" %s." +msgstr "" +"Je moet de kanaalnaam twee keer opgeven als bevestiging dat je de " +"registratie van %s wenst ongedaan te maken." + +#: modules/commands/ns_register.cpp:153 +#, c-format +msgid "You must have been using this nick for at least %d seconds to register." +msgstr "Je moet deze nick tenminste %d seconden gebruiken om te registreren." + +#: modules/commands/cs_mode.cpp:913 +#, c-format +msgid "You must have the %s(ME) privilege on the channel to use this command." +msgstr "" +"Je moet het %s(ME) privilege hebben op het kanaal om dit commando te " +"gebruiken." + +#: modules/pseudoclients/nickserv.cpp:358 +msgid "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." +msgstr "" +"Je moet nu een e-mailadres opgeven voor je nick.\n" +"Dit stelt je in staat je wachtwoord terug te halen in\n" +"het geval dat je het vergeet." + +#: modules/commands/help.cpp:172 +msgid "You need to be identified to use this command." +msgstr "Je moet geïdentificeerd zijn om dit commando te gebruiken." + +#: modules/commands/ms_info.cpp:182 +msgid "You will be notified by message and by mail when new memos arrive." +msgstr "" +"Je wordt geïnformeerd over nieuwe memo's via berichten en e-mail wanneer " +"deze aankomen." + +#: modules/commands/ms_info.cpp:175 +msgid "" +"You will be notified of new memos at logon and when they arrive, and by mail " +"when they arrive." +msgstr "" +"Je wordt geïnformeerd over nieuwe memo's wanneer je inlogt en wanneer deze " +"aankomen, en via e-mail wanneer deze aankomen." + +#: modules/commands/ms_info.cpp:177 +msgid "You will be notified of new memos at logon and when they arrive." +msgstr "" +"Je wordt geïnformeerd over nieuwe memo's wanneer je inlogt en wanneer deze " +"aankomen." + +#: modules/commands/ms_info.cpp:189 +msgid "" +"You will be notified of new memos at logon, and by mail when they arrive." +msgstr "" +"Je wordt geïnformeerd over nieuwe memo's wanneer je inlogt, en via e-mail " +"wanneer deze aankomen." + +#: modules/commands/ms_info.cpp:191 +msgid "You will be notified of new memos at logon." +msgstr "Je wordt geïnformeerd over nieuwe memo's wanneer je inlogt." + +#: modules/commands/ms_info.cpp:184 +msgid "You will be notified when new memos arrive." +msgstr "Je wordt geïnformeerd over nieuwe memo's wanneer deze aankomen." + +#: modules/commands/ms_set.cpp:190 +msgid "You will no longer be able to receive memos." +msgstr "Je zal niet langer memo's ontvangen." + +#: modules/commands/ms_set.cpp:57 +msgid "You will no longer be informed via email." +msgstr "Je wordt niet langer geïnformeerd via e-mail." + +#: modules/commands/ms_info.cpp:195 +msgid "You will not be notified of new memos." +msgstr "Je wordt niet op de hoogte gehouden over nieuwe memo's." + +#: modules/commands/ms_set.cpp:49 +msgid "You will now be informed about new memos via email." +msgstr "" +"Je zal zal nu op de hoogte worden gehouden van nieuwe memo's via e-mail." + +#: modules/commands/os_svs.cpp:86 +msgid "Your IRCd does not support SVSJOIN." +msgstr "Je IRCd ondersteunt geen SVSJOIN." + +#: modules/commands/os_svs.cpp:31 +msgid "Your IRCd does not support SVSNICK." +msgstr "Je IRCd ondersteunt geen SVSNICK." + +#: modules/commands/os_svs.cpp:130 +msgid "Your IRCd does not support SVSPART." +msgstr "Je IRCd ondersteunt geen SVSPART." + +#: include/language.h:127 +msgid "" +"Your IRCd does not support vIdent's, if this is incorrect, please report " +"this as a possible bug" +msgstr "" +"Je IRCd ondersteunt geen vIdent's, indien dit niet klopt, gelieve dit dan te " +"melden als een mogelijke fout" + +#: modules/extra/m_ldap_authentication.cpp:110 +#: modules/extra/m_sql_authentication.cpp:55 +#, c-format +msgid "Your account %s has been successfully created." +msgstr "Je account %s is succesvol aangemaakt." + +#: modules/commands/ns_register.cpp:328 +msgid "Your account is already confirmed." +msgstr "Je account is reeds bevestigd." + +#: modules/commands/ns_register.cpp:396 +#, c-format +msgid "Your account will expire, if not confirmed, in %s." +msgstr "Je account verloopt, indien niet bevestigd, over %s." + +#: modules/commands/ns_set.cpp:1274 +#, c-format +msgid "Your email address has been changed to %s." +msgstr "Je e-mailadres werd gewijzigd naar %s." + +#: modules/commands/os_forbid.cpp:544 modules/commands/os_forbid.cpp:553 +msgid "Your email address is not allowed, choose a different one." +msgstr "Je e-mailadres is niet toegelaten, kies een andere." + +#: modules/commands/ns_register.cpp:260 modules/commands/ns_register.cpp:391 +msgid "" +"Your email address is not confirmed. To confirm it, follow the instructions " +"that were emailed to you." +msgstr "" +"Je e-mailadres is niet bevestigd. Om deze te bevestigen dien je de " +"instructies te volgen in de toegezonden e-mail." + +#: modules/commands/ns_register.cpp:67 +#, c-format +msgid "Your email address of %s has been confirmed." +msgstr "Je e-mailadres %s werd bevestigd." + +#: modules/extra/m_ldap_authentication.cpp:159 +#, c-format +msgid "Your email has been updated to %s" +msgstr "Je e-mail werd geüpdatet naar %s." + +#: modules/extra/m_sql_authentication.cpp:62 +#, c-format +msgid "Your email has been updated to %s." +msgstr "Je e-mail werd geüpdatet naar %s." + +#: modules/commands/ms_set.cpp:197 +msgid "Your memo limit has been disabled." +msgstr "Je memolimiet is uitgeschakeld." + +#: modules/commands/ms_set.cpp:183 +#, c-format +msgid "Your memo limit has been set to %d." +msgstr "Je memolimiet is veranderd naar %d." + +#: modules/commands/ms_info.cpp:164 +#, c-format +msgid "Your memo limit is %d, and may not be changed." +msgstr "Je memolimiet is %d, en mag niet worden veranderd." + +#: modules/commands/ms_info.cpp:166 +#, c-format +msgid "Your memo limit is %d." +msgstr "Je memolimiet is %d." + +#: modules/commands/ms_info.cpp:159 +msgid "Your memo limit is 0; you will not receive any new memos." +msgstr "Je memolimiet is 0; je zal geen nieuwe memo's ontvangen." + +#: modules/commands/ms_info.cpp:157 +msgid "" +"Your memo limit is 0; you will not receive any new memos. You cannot change " +"this limit." +msgstr "" +"Je memolimiet is 0; je zal geen nieuwe memo's ontvangen. Je kan deze limiet " +"niet veranderen." + +#: modules/commands/ns_logout.cpp:50 +msgid "Your nick has been logged out." +msgstr "Je nick is uitgelogd." + +#: modules/commands/ns_group.cpp:156 +msgid "Your nick is already registered." +msgstr "Je nick is al geregistreerd." + +#: modules/commands/ns_group.cpp:246 +msgid "Your nick is not grouped to anything, you can't ungroup it." +msgstr "Je nick behoort tot geen enkele groep, je kan dit dus niet uitvoeren." + +#: include/language.h:77 +msgid "Your nick isn't registered." +msgstr "Je nickname is niet geregistreerd." + +#: modules/pseudoclients/nickserv.cpp:254 +#, c-format +msgid "Your nickname is now being changed to %s" +msgstr "Je nickname wordt nu veranderd in %s" + +#: modules/commands/os_login.cpp:32 modules/commands/os_login.cpp:79 +msgid "Your oper block doesn't require logging in." +msgstr "Je oper blok vereist geen aanmelding." + +#: modules/commands/ns_register.cpp:336 +#, c-format +msgid "Your passcode has been re-sent to %s." +msgstr "Je bevestingscode is opnieuw gestuurd naar %s." + +#: modules/commands/ns_register.cpp:232 +#, c-format +msgid "Your password is %s - remember this for later use." +msgstr "Je wachtwoord is %s - onthoudt dit voor later gebruik." + +#: include/language.h:76 +#, c-format +msgid "Your password is too long. It must not exceed %u characters." +msgstr "Je wachtwoord is te lang. Het mag niet langer zijn dan %u karakters." + +#: modules/commands/ns_resetpass.cpp:96 +msgid "Your password reset request has expired." +msgstr "Je wachtwoord-reset aanvraag is verlopen." + +#: modules/commands/hs_request.cpp:170 +msgid "Your vHost has been requested." +msgstr "Je vHost werd aangevraagd." + +#: modules/pseudoclients/hostserv.cpp:64 +#: modules/pseudoclients/hostserv.cpp:103 modules/commands/hs_on.cpp:37 +#, c-format +msgid "Your vhost of %s is now activated." +msgstr "Je vHost %s is nu geactiveerd." + +#: modules/pseudoclients/hostserv.cpp:62 +#: modules/pseudoclients/hostserv.cpp:101 modules/commands/hs_on.cpp:35 +#, c-format +msgid "Your vhost of %s@%s is now activated." +msgstr "Je vHost %s@%s is nu geactiveerd." + +#: modules/commands/hs_off.cpp:39 +msgid "Your vhost was removed and the normal cloaking restored." +msgstr "Je vHost werd verwijderd en de normale cloaking hersteld." + +#: modules/commands/os_dns.cpp:255 +msgid "Zone" +msgstr "Domein" + +#: modules/commands/os_dns.cpp:290 +#, c-format +msgid "Zone %s already exists." +msgstr "Domein %s bestaat al." + +#: modules/commands/os_dns.cpp:310 modules/commands/os_dns.cpp:352 +#: modules/commands/os_dns.cpp:402 modules/commands/os_dns.cpp:438 +#, c-format +msgid "Zone %s does not exist." +msgstr "Domein %s bestaat niet." + +#: modules/commands/os_dns.cpp:332 +#, c-format +msgid "Zone %s removed." +msgstr "Domein %s verwijderd." + +#: modules/commands/os_defcon.cpp:177 +msgid "[1|2|3|4|5]" +msgstr "[1|2|3|4|5]" + +#: modules/commands/os_news.cpp:400 +#, c-format +msgid "[Logon News - %s] %s" +msgstr "[Login Nieuws - %s] %s" + +#: modules/commands/os_news.cpp:402 +#, c-format +msgid "[Oper News - %s] %s" +msgstr "[Operator Nieuws - %s] %s" + +#: modules/commands/os_news.cpp:404 +#, c-format +msgid "[Random News - %s] %s" +msgstr "[Willekeurig Nieuws - %s] %s" + +#: modules/commands/ns_identify.cpp:66 +msgid "[account] password" +msgstr "[nick] wachtwoord" + +#: modules/commands/cs_updown.cpp:49 modules/commands/cs_updown.cpp:147 +msgid "[channel [nick]]" +msgstr "[kanaal [nick]]" + +#: modules/commands/ms_ignore.cpp:20 +msgid "[channel] ADD entry" +msgstr "[kanaal] ADD vermelding" + +#: modules/commands/ms_ignore.cpp:21 +msgid "[channel] DEL entry" +msgstr "[kanaal] DEL vermelding" + +#: modules/commands/ms_ignore.cpp:22 +msgid "[channel] LIST" +msgstr "[kanaal] LIST" + +#: modules/commands/ms_list.cpp:20 +msgid "[channel] [list | NEW]" +msgstr "[kanaal] [lijst | NEW]" + +#: modules/extra/stats/cs_fantasy_stats.cpp:40 +msgid "[channel] [nick]" +msgstr "[kanaal] [nick]" + +#: modules/commands/ms_del.cpp:45 +msgid "[channel] {num | list | LAST | ALL}" +msgstr "[kanaal] {nr | lijst | LAST | ALL}" + +#: modules/commands/ms_read.cpp:113 +msgid "[channel] {num | list | LAST | NEW | ALL}" +msgstr "[kanaal] {nr | lijst | LAST | NEW | ALL}" + +#: modules/commands/hs_list.cpp:20 +msgid "[key|#X-Y]" +msgstr "[patroon|#X-Y]" + +#: modules/commands/ms_info.cpp:20 +msgid "[nick | channel]" +msgstr "[nick | kanaal]" + +#: modules/commands/ns_group.cpp:237 +msgid "[nick]" +msgstr "[nick]" + +#: modules/commands/ns_logout.cpp:22 +msgid "[nickname [REVALIDATE]]" +msgstr "[nickname [REVALIDATE]]" + +#: modules/commands/ns_alist.cpp:25 modules/commands/ns_status.cpp:20 +#: modules/commands/ns_info.cpp:20 +msgid "[nickname]" +msgstr "[nick]" + +#: modules/commands/ns_set_misc.cpp:96 +msgid "[parameter]" +msgstr "[parameter]" + +#: modules/commands/os_logsearch.cpp:33 +msgid "[+daysd] [+limitl] pattern" +msgstr "[+dagend] [+limietl] patroon" + +#: modules/commands/os_chankill.cpp:22 +msgid "[+expiry] channel reason" +msgstr "[+verlooptijd] kanaal reden" + +#: modules/commands/ns_list.cpp:110 +msgid "[Hostname hidden]" +msgstr "[host verborgen]" + +#: modules/commands/ns_list.cpp:112 modules/commands/cs_list.cpp:115 +msgid "[Suspended]" +msgstr "[geschorst]" + +#: modules/commands/ns_list.cpp:114 +msgid "[Unconfirmed]" +msgstr "[onbevestigd]" + +#: modules/commands/hs_request.cpp:213 +msgid "[auto memo] Your requested vHost has been approved." +msgstr "[auto memo] Uw aanvraag voor de vHost werd goedgekeurd." + +#: modules/commands/hs_request.cpp:267 +msgid "[auto memo] Your requested vHost has been rejected." +msgstr "[auto memo] Uw aanvraag voor de vHost werd geweigerd." + +#: modules/commands/hs_request.cpp:265 +#, c-format +msgid "[auto memo] Your requested vHost has been rejected. Reason: %s" +msgstr "[auto memo] Uw aanvraag voor de vHost werd geweigerd. Reden: %s" + +#: modules/commands/hs_request.cpp:388 +#, c-format +msgid "[auto memo] vHost %s has been requested by %s." +msgstr "[auto memo] vHost %s aangevraagd door %s." + +#: modules/commands/os_list.cpp:133 +msgid "[{pattern | channel} [INVISIBLE]]" +msgstr "[{patroon | kanaal} [INVISIBLE]]" + +#: modules/commands/os_list.cpp:20 +msgid "[{pattern | nick} [SECRET]]" +msgstr "[{patroon | nick} [SECRET]]" + +#: src/misc.cpp:337 +msgid "day" +msgstr "dag" + +#: src/misc.cpp:337 +msgid "days" +msgstr "dagen" + +#: include/language.h:88 +msgid "does not expire" +msgstr "verloopt niet" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d day" +msgstr "verloopt over %d dag" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d days" +msgstr "verloopt over %d dagen" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minute" +msgstr "verloopt over %d uur, %d minuut" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minutes" +msgstr "verloopt over %d uur, %d minuten" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minute" +msgstr "verloopt over %d uur, %d minuut" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minutes" +msgstr "verloopt over %d uur, %d minuten" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minute" +msgstr "verloopt over %d minuut" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minutes" +msgstr "verloopt over %d minuten" + +#: src/misc.cpp:375 +msgid "expires momentarily" +msgstr "verloopt elk moment" + +#: src/misc.cpp:343 +msgid "hour" +msgstr "uur" + +#: src/misc.cpp:343 +msgid "hours" +msgstr "uur" + +#: modules/extra/stats/cs_fantasy_stats.cpp:150 +#, c-format +msgid "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "letters: %s, woorden: %s, lijnen: %s, smileys: %s, acties: %s" + +#: src/misc.cpp:349 +msgid "minute" +msgstr "minuut" + +#: src/misc.cpp:349 +msgid "minutes" +msgstr "minuten" + +#: modules/commands/bs_info.cpp:87 +msgid "not assigned yet" +msgstr "nog niet toegewezen" + +#: src/misc.cpp:324 +msgid "second" +msgstr "seconde" + +#: src/misc.cpp:324 +msgid "seconds" +msgstr "seconden" + +#: modules/commands/hs_request.cpp:215 +#, c-format +msgid "vHost for %s has been activated." +msgstr "vHost voor %s is geactiveerd." + +#: modules/commands/hs_request.cpp:272 +#, c-format +msgid "vHost for %s has been rejected." +msgstr "vHost voor %s is geweigerd." + +#: modules/commands/hs_request.cpp:79 +msgid "vhost" +msgstr "vHost" + +#: modules/commands/hs_del.cpp:83 +#, c-format +msgid "vhosts for group %s have been removed." +msgstr "vHosts voor groep %s zijn verwijderd." + +#: src/misc.cpp:331 +msgid "year" +msgstr "jaar" + +#: src/misc.cpp:331 +msgid "years" +msgstr "jaar" + +#: modules/commands/os_config.cpp:20 +msgid "{MODIFY|VIEW} [block name item name item value]" +msgstr "{MODIFY|VIEW} [blok naam item naam item waarde]" + +#: modules/commands/bs_info.cpp:41 +msgid "{channel | nickname}" +msgstr "{kanaal | nick}" + +#: modules/commands/ms_cancel.cpp:20 +msgid "{nick | channel}" +msgstr "{nick | kanaal}" + +#: modules/commands/ms_rsend.cpp:25 modules/commands/ms_send.cpp:25 +msgid "{nick | channel} memo-text" +msgstr "{nick | kanaal} memo-tekst" diff --git a/language/anope.pl_PL.po b/language/anope.pl_PL.po new file mode 100644 index 0000000..611bd4f --- /dev/null +++ b/language/anope.pl_PL.po @@ -0,0 +1,11060 @@ +# Anope IRC Services language file +# Copyright (C) 2011 +# This file is distributed under the same license as the Anope IRC Services package. +# Adam , 2011. +# +msgid "" +msgstr "" +"Project-Id-Version: Anope\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2022-01-03 18:52+0100\n" +"PO-Revision-Date: 2022-01-03 19:01+0100\n" +"Last-Translator: Adam \n" +"Language-Team: Polish\n" +"Language: pl_PL\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=3; plural=(n==1 ? 0 : n%10>=2 && n%10<=4 && (n%100<10 || n" +"%100>=20) ? 1 : 2);\n" +"X-Generator: Poedit 2.2.4\n" + +#: modules/commands/os_forbid.cpp:324 +#, c-format +msgid "%d channel(s) cleared, and %d channel(s) dropped." +msgstr "Oczyszczono %d kanałów, a %d usunięto." + +#: modules/commands/os_forbid.cpp:265 +#, c-format +msgid "%d nickname(s) dropped." +msgstr "Odrejestrowano %d nicków." + +#: modules/commands/cs_xop.cpp:219 +#, c-format +msgid "%s added to %s %s list." +msgstr "%s dodano do listy %s %s." + +#: modules/commands/cs_access.cpp:225 +#, c-format +msgid "%s added to %s access list at level %d." +msgstr "" +"%s dodano do listy dostępu kanału %s z\n" +"poziomem %d." + +#: modules/commands/cs_access.cpp:223 +#, c-format +msgid "%s added to %s access list at privilege %s (level %d)" +msgstr "" +"%s dodano do listy dostępu kanału %s z\n" +"uprawnieniami %s (poziom %d)." + +#: modules/commands/cs_akick.cpp:190 +#, c-format +msgid "%s added to %s autokick list." +msgstr "%s dodano do listy AKICK kanału %s." + +#: modules/commands/bs_badwords.cpp:307 +#, c-format +msgid "%s added to %s bad words list." +msgstr "%s dodano do listy zakazanych słów kanału %s." + +#: modules/commands/ns_access.cpp:45 +#, c-format +msgid "%s added to %s's access list." +msgstr "%s dodano do listy dostępu %s." + +#: modules/commands/ns_cert.cpp:204 +#, c-format +msgid "%s added to %s's certificate list." +msgstr "%s dodano do listy certyfikatów %s." + +#: modules/commands/ms_ignore.cpp:62 +#, c-format +msgid "%s added to ignore list." +msgstr "%s dodano do Twojej listy dostępu." + +#: modules/commands/os_sxline.cpp:415 modules/commands/os_sxline.cpp:649 +#, c-format +msgid "%s added to the %s list." +msgstr "%s dodano do listy %s." + +#: modules/commands/os_akill.cpp:203 +#, c-format +msgid "%s added to the AKILL list." +msgstr "%s dodano do listy AKILL." + +#: modules/pseudoclients/botserv.cpp:134 +#, c-format +msgid "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" +msgstr "" +"%s pozwala na wykonywanie komend \"fanstasy\" na kanale.\n" +"Komendy te są aktywowane poprzez wysłanie wiadomości na kanał,\n" +"i umożliwiają wygodniejsze wykonywanie pewnych zadań.\n" +"Polecenia, które wymagają podania kanału jako parametru,\n" +"będą miały ten parametr ustawiony automatycznie.\n" + +#: modules/pseudoclients/botserv.cpp:148 +#, c-format +msgid "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s pozwala umieścić bota na własnym kanale.\n" +"Został stworzony dla użytkowników, którzy nie mogą\n" +"hostować własnego bota oraz dla tych sieci które\n" +"nie pozwalają na ich używanie. Poniższe komendy\n" +"umożliwiają zarządzanie botem, aby ich użyć wpisz:\n" +"%s%s komenda\n" +"Aby uzyskać szczegółowy opis polecenia wpisz:\n" +"%s%s %s komenda\n" + +#: modules/pseudoclients/nickserv.cpp:466 +#, c-format +msgid "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s umożliwia rejestrację nicka i zapewnia\n" +"wyłączność na jego używanie. Poniższe komendy\n" +"umożliwiają zarządzanie nickiem, aby ich użyć wpisz:\n" +"%s%s komenda\n" +"Aby uzyskać szczegółowy opis polecenia wpisz:\n" +"%s%s %s komenda\n" + +#: modules/pseudoclients/nickserv.cpp:473 +#, c-format +msgid "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s umożliwia rejestrację konta.\n" +"Poniższe komendy pozwalają na rejestrację i zarządzanie\n" +"kontami; aby ich użyć, wpisz %s%s komenda.\n" +"Aby uzyskać szczegółowy opis polecenia wpisz:\n" +"%s%s %s komenda\n" + +#: modules/pseudoclients/chanserv.cpp:255 +#, c-format +msgid "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" +msgstr "" +"%s umożliwia rejestrację kanału, zmianę\n" +"jego ustawień. %s zapobiega przed odebraniem\n" +"kontroli nad kanałem, uniemożliwiając nieuprawnionym\n" +"uzyskanie statusu operatora. Poniższe komendy\n" +"pozwalają na zarządzanie kanałem, aby ich użyć wpisz:\n" +"%s%s komenda\n" +"Aby uzyskać szczegółowy opis polecenia wpisz:\n" +"%s%s HELP komenda\n" + +#: modules/commands/bs_badwords.cpp:298 +#, c-format +msgid "%s already exists in %s bad words list." +msgstr "%s już istnieje na liście zakazanych słów kanału %s." + +#: modules/commands/cs_akick.cpp:170 +#, c-format +msgid "%s already exists on %s autokick list." +msgstr "%s już istnieje w liście AKICK kanału %s." + +#: modules/commands/os_session.cpp:361 +#, c-format +msgid "%s already exists on the EXCEPTION list." +msgstr "%s już istnieje na liście wyjątków." + +#: modules/commands/bs_kick.cpp:214 modules/commands/bs_kick.cpp:389 +#: modules/commands/bs_kick.cpp:520 modules/commands/bs_kick.cpp:651 +#, c-format +msgid "%s cannot be taken as times to ban." +msgstr "%s nie może być wzięty jako ilość wykroczeń do założenia bana." + +#: modules/commands/os_mode.cpp:163 +#, c-format +msgid "%s changed your usermodes to %s." +msgstr "%s zmienił Twoje flagi użytkownika na %s." + +#: modules/commands/os_list.cpp:47 +#, c-format +msgid "%s channel list:" +msgstr "Lista kanałów %s:" + +#: modules/commands/cs_xop.cpp:343 +#, c-format +msgid "%s deleted from %s %s list." +msgstr "%s usunięto z listy %s kanału %s." + +#: modules/commands/cs_access.cpp:326 +#, c-format +msgid "%s deleted from %s access list." +msgstr "%s usunięto z listy dostępu kanału %s." + +#: modules/commands/cs_akick.cpp:276 +#, c-format +msgid "%s deleted from %s autokick list." +msgstr "%s usunięto z listy AKICK %s." + +#: modules/commands/bs_badwords.cpp:348 +#, c-format +msgid "%s deleted from %s bad words list." +msgstr "%s usunięto z listy zakazanych słów kanału %s." + +#: modules/commands/ns_access.cpp:72 +#, c-format +msgid "%s deleted from %s's access list." +msgstr "%s usunięto z listy dostępu kanału %s." + +#: modules/commands/ns_cert.cpp:233 +#, c-format +msgid "%s deleted from %s's certificate list." +msgstr "%s usunięto z listy certyfikatów %s." + +#: modules/commands/os_session.cpp:414 +#, c-format +msgid "%s deleted from session-limit exception list." +msgstr "%s usunięto z listy wyjątków limitów sesji." + +#: modules/commands/os_sxline.cpp:99 +#, c-format +msgid "%s deleted from the %s list." +msgstr "%s usunięto z listy %s." + +#: modules/commands/os_akill.cpp:246 +#, c-format +msgid "%s deleted from the AKILL list." +msgstr "%s usunięto z listy AKILL." + +#: modules/commands/cs_access.cpp:685 +#, c-format +msgid "%s disabled on channel %s." +msgstr "%s wyłączono na kanale %s." + +#: modules/commands/cs_invite.cpp:75 +#, c-format +msgid "%s has been invited to %s." +msgstr "%s został zaproszony na %s." + +#: modules/commands/os_svs.cpp:104 +#, c-format +msgid "%s has been joined to %s." +msgstr "%s został dołączony do %s." + +#: modules/commands/os_svs.cpp:152 +#, c-format +msgid "%s has been parted from %s." +msgstr "%s został odłączony od %s." + +#: modules/commands/cs_unban.cpp:100 +#, c-format +msgid "%s has been unbanned from %s." +msgstr "%s has been unbanned from %s." + +#: modules/commands/ns_alist.cpp:110 +#, c-format +msgid "%s has no access in any channels." +msgstr "%s nie jest na liście dostępu żadnego kanału." + +#: modules/commands/cs_status.cpp:55 +#, c-format +msgid "%s has no access on %s." +msgstr "%s nie ma uprawnień na %s." + +#: modules/commands/cs_set.cpp:307 +#, c-format +msgid "%s has too many channels registered." +msgstr "%s posiada za dużo zarejestrowanych kanałów." + +#: modules/commands/cs_status.cpp:51 +#, c-format +msgid "%s is a super administrator." +msgstr "%s jest super-administratorem." + +#: modules/pseudoclients/memoserv.cpp:214 +#, c-format +msgid "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" +msgstr "" +"%s umożliwia wysyłanie krótkich wiadomości\n" +"do innych użytkowników (niezależnie od tego czy\n" +"są oni w danej chwili na IRCu) lub do kanałów(*).\n" +"Aby móc używać tego serwisu nadawca i odbiorca\n" +"(kanał lub nick) muszą być zarejestrowani.\n" +"Poniższe komendy pozwalają na wysyłanie i\n" +"odbieranie wiadomości.\n" +"Polecenia %s są następujące:" + +#: modules/commands/cs_invite.cpp:66 +#, c-format +msgid "%s is already in %s!" +msgstr "%s już przebywa na %s!" + +#: modules/commands/os_svs.cpp:99 +#, c-format +msgid "%s is already in %s." +msgstr "%s już przebywa na %s." + +#: modules/commands/ms_ignore.cpp:65 +#, c-format +msgid "%s is already on the ignore list." +msgstr "%s już jest na liście ignorowanych." + +#: modules/commands/cs_suspend.cpp:97 modules/commands/ns_suspend.cpp:106 +#, c-format +msgid "%s is already suspended." +msgstr "%s już jest zawieszony." + +#: modules/commands/ms_send.cpp:55 modules/commands/ms_rsend.cpp:56 +#, c-format +msgid "%s is not a registered unforbidden nick or channel." +msgstr "%s nie jest prawidłowym i dozwolonym nickiem lub nazwą kanału." + +#: modules/commands/cs_set.cpp:178 +#, c-format +msgid "%s is not a valid ban type." +msgstr "%s nie jest prawidłowym rodzajem bana." + +#: modules/commands/bs_info.cpp:101 +#, c-format +msgid "%s is not a valid bot or registered channel." +msgstr "%s nie jest prawidłową nazwą bota lub kanału." + +#: include/language.h:86 +#, c-format +msgid "%s is not a valid e-mail address." +msgstr "%s nie jest prawidłowym adresem e-mail." + +#: include/language.h:80 +#, c-format +msgid "%s is not currently on channel %s." +msgstr "%s nie znajduje się teraz na kanale %s." + +#: modules/commands/os_svs.cpp:144 +#, c-format +msgid "%s is not in %s." +msgstr "%s nie znajduje się na %s." + +#: modules/commands/ms_ignore.cpp:77 +#, c-format +msgid "%s is not on the ignore list." +msgstr "%s nie znaleziono na liście ignorowanych." + +#: modules/commands/cs_status.cpp:90 +#, c-format +msgid "%s is on the auto kick list of %s (%s)." +msgstr "%s jest na liście AKICK kanału %s (%s)." + +#: modules/commands/cs_status.cpp:53 +#, c-format +msgid "%s is the founder of %s." +msgstr "%s jest założycielem %s." + +#: modules/commands/cs_status.cpp:78 +#, c-format +msgid "%s matches access entry %s (from entry %s), which has privilege %s." +msgstr "" +"%s pasuje do wpisu %s (na podstawie %s) na liście dostępu, posiadającego " +"uprawnienia %s." + +#: modules/commands/cs_status.cpp:71 +#, c-format +msgid "%s matches access entry %s, which has privilege %s." +msgstr "%s pasuje do wpisu %s na liście dostępu, posiadającego uprawnienia %s." + +#: include/language.h:109 +#, c-format +msgid "" +"%s matches an except on %s and cannot be banned until the except has been removed." +msgstr "" +"%s pasuje do wyjątku na %s i nie może być zbanowany, dopóki ten wyjątek nie " +"zostanie usunięty." + +#: modules/commands/cs_status.cpp:96 +#, c-format +msgid "%s matches auto kick entry %s on %s (%s)." +msgstr "%s pasuje do wpisu %s listy AKICK na %s (%s)." + +#: modules/commands/cs_xop.cpp:353 +#, c-format +msgid "%s not found on %s %s list." +msgstr "Nie znaleziono %1$s na liście %3$s kanału %2$s." + +#: modules/commands/cs_flags.cpp:255 modules/commands/cs_access.cpp:338 +#, c-format +msgid "%s not found on %s access list." +msgstr "%s nie znaleziono na liście dostępu kanału %s." + +#: modules/commands/cs_akick.cpp:265 +#, c-format +msgid "%s not found on %s autokick list." +msgstr "%s nie znaleziono na liście AKICK kanału %s." + +#: modules/commands/bs_badwords.cpp:341 +#, c-format +msgid "%s not found on %s bad words list." +msgstr "%s nie znaleziono na liście zakazanych słów kanału %s." + +#: modules/commands/ns_access.cpp:66 +#, c-format +msgid "%s not found on %s's access list." +msgstr "%s nie znaleziono na liście dostępu kanału %s." + +#: modules/commands/ns_cert.cpp:226 +#, c-format +msgid "%s not found on %s's certificate list." +msgstr "%s nie znaleziono na liście certyfikatów %s." + +#: modules/commands/os_ignore.cpp:320 +#, c-format +msgid "%s not found on ignore list." +msgstr "%s nie znaleziono na liście ignorowanych." + +#: modules/commands/os_session.cpp:238 +#, c-format +msgid "" +"%s not found on session list, but has a limit of %d because it matches entry: %s." +msgstr "" +"%s nie został znaleziony na liście sesji, ale jego limit to %d z uwagi na to, że " +"pasuje do wpisu: %s." + +#: modules/commands/os_session.cpp:418 +#, c-format +msgid "%s not found on session-limit exception list." +msgstr "%s nie znaleziono na liście wyjątków limitów sesji." + +#: modules/commands/os_sxline.cpp:92 +#, c-format +msgid "%s not found on the %s list." +msgstr "%s nie znaleziono na liście %s." + +#: modules/commands/os_akill.cpp:237 +#, c-format +msgid "%s not found on the AKILL list." +msgstr "%s nie znaleziono na liście AKILL." + +#: modules/commands/cs_flags.cpp:251 +#, c-format +msgid "%s removed from the %s access list." +msgstr "%s usunięto z listy dostępu kanału %s." + +#: modules/commands/ms_ignore.cpp:74 +#, c-format +msgid "%s removed from the ignore list." +msgstr "%s usunięto z Twojej listy dostępu." + +#: modules/commands/os_list.cpp:157 +#, c-format +msgid "%s users list:" +msgstr "Lista użytkowników %s:" + +#: modules/commands/os_ignore.cpp:316 +#, c-format +msgid "%s will no longer be ignored." +msgstr "Nick %s nie będzie ignorowany." + +#: modules/commands/os_ignore.cpp:238 +#, c-format +msgid "%s will now be ignored for %s." +msgstr "Nick %s będzie ignorowany przez %s." + +#: modules/commands/os_ignore.cpp:233 +#, c-format +msgid "%s will now permanently be ignored." +msgstr "Nick %s będzie stale ignorowany." + +#: include/language.h:66 +#, c-format +msgid "%s%s HELP %s for more information." +msgstr "" +"Aby uzyskać więcej informacji, wpisz:\n" +"%s%s HELP %s" + +#: modules/commands/bs_bot.cpp:270 +msgid "ADD nick user host real" +msgstr "ADD nick user host realname" + +#: modules/commands/bs_bot.cpp:271 +msgid "CHANGE oldnick newnick [user [host [real]]]" +msgstr "CHANGE stary-nick nowy-nick [user [host [realname]]]" + +#: modules/commands/bs_bot.cpp:272 +msgid "DEL nick" +msgstr "DEL nick" + +#: modules/commands/os_session.cpp:560 +msgid "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." +msgstr "" +"EXCEPTION ADD dodaje wskazaną maskę na listę wyjątków.\n" +"Maski nick!user@host oraz user@host są nieprawidłowe,\n" +"ponieważ zawierają nick lub ident użytkownika. Dopuszczalne\n" +"maski to np. box.host.dom lub *.host.dom. Limit musi\n" +"być liczbą nieujemną. Podanie zera oznacza wyłączenie limitu.\n" +"Format czasu jest opisany w pomocy polecenia AKILL.\n" +"\n" +"EXCEPTION DEL usuwa wskazane wpisy z listy wyjątków.\n" +"\n" +"EXCEPTION LIST oraz EXCEPTION VIEW listują wyjątki.\n" +"Podanie maski powoduje ograniczenie wyświetlanych wpisów.\n" +"EXCEPTION VIEW zwraca dodatkowo informacje o zakładającym,\n" +"limicie, powodzie, masce oraz czasie.\n" +"\n" +"Należy pamiętać, że podłączający się klient będzie używał\n" +"pierwszego wyjątku o pasującej masce. Duża lista wyjątków i\n" +"zbyt ogólne maski powodują pogorszenie wydajności serwisów." + +#: modules/commands/os_noop.cpp:68 +msgid "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." +msgstr "" +"SET rozłącza wszystkich operatorów na podanym\n" +"serwerze i nie pozwala na uzyskanie tam statusu operatora.\n" +"REVOKE usuwa to ograniczenie." + +#: modules/commands/cs_access.cpp:611 +#, c-format +msgid "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." +msgstr "" +"Poziomy dostępu użytkowników można podejrzeć, używając\n" +"polecenia %s; wpisz %s%s HELP LEVELS aby uzyskać pomoc." + +#: modules/commands/ms_read.cpp:35 +#, c-format +msgid "[auto-memo] The memo you sent to %s has been viewed." +msgstr "[auto-memo] Wysłana przez Ciebie wiadomość do %s została przeczytana." + +#: modules/commands/ns_group.cpp:92 +msgid "[target] [password]" +msgstr "[grupa-docelowa] [hasło]" + +#: modules/commands/ns_set.cpp:453 +msgid "address" +msgstr "adres" + +#: modules/commands/bs_set.cpp:162 +msgid "botname {ON|OFF}" +msgstr "nazwa-bota {ON|OFF}" + +#: modules/commands/cs_sync.cpp:20 modules/commands/cs_log.cpp:106 +#: modules/commands/cs_suspend.cpp:152 modules/commands/bs_assign.cpp:91 +#: modules/commands/cs_info.cpp:20 modules/commands/cs_getkey.cpp:20 +#: modules/extra/stats/cs_fantasy_top.cpp:39 +#: modules/extra/stats/cs_fantasy_top.cpp:51 +msgid "channel" +msgstr "kanał" + +#: modules/commands/cs_set.cpp:138 +msgid "channel bantype" +msgstr "kanał typ-bana" + +#: modules/commands/cs_drop.cpp:20 +msgid "channel channel" +msgstr "kanał kanał" + +#: modules/commands/cs_log.cpp:107 +msgid "channel command method [status]" +msgstr "kanał komenda metoda [status]" + +#: modules/commands/cs_kick.cpp:21 +msgid "channel mask [reason]" +msgstr "#kanał maska [powód]" + +#: modules/commands/os_mode.cpp:20 +msgid "channel modes" +msgstr "kanał flagi" + +#: modules/commands/bs_assign.cpp:20 modules/commands/cs_set.cpp:267 +msgid "channel nick" +msgstr "kanał nick" + +#: modules/commands/cs_kick.cpp:20 +msgid "channel nick [reason]" +msgstr "#kanał nick [powód]" + +#: modules/commands/cs_clone.cpp:115 +msgid "channel target [what]" +msgstr "kanał cel [co]" + +#: modules/commands/bs_control.cpp:20 modules/commands/bs_control.cpp:80 +msgid "channel text" +msgstr "kanał tekst" + +#: modules/commands/bs_set.cpp:91 +msgid "channel time" +msgstr "kanał czas" + +#: modules/commands/os_kick.cpp:20 +msgid "channel user reason" +msgstr "kanał nick powód" + +#: modules/commands/cs_enforce.cpp:228 +msgid "channel what" +msgstr "kanał co" + +#: modules/commands/cs_xop.cpp:481 +msgid "channel ADD mask" +msgstr "kanał ADD maska" + +#: modules/commands/cs_access.cpp:499 +msgid "channel ADD mask level" +msgstr "kanał ADD maska poziom" + +#: modules/commands/cs_entrymsg.cpp:194 +msgid "channel ADD message" +msgstr "kanał ADD wiadomość" + +#: modules/commands/bs_badwords.cpp:371 +msgid "channel ADD word [SINGLE | START | END]" +msgstr "kanał ADD słowo [SINGLE | START | END]" + +#: modules/commands/cs_akick.cpp:435 +msgid "channel ADD {nick | mask} [reason]" +msgstr "kanał ADD {nick | maska} [powód]" + +#: modules/commands/cs_topic.cpp:151 +msgid "channel APPEND topic" +msgstr "kanał APPEND temat" + +#: modules/commands/cs_entrymsg.cpp:197 modules/commands/cs_akick.cpp:440 +#: modules/commands/bs_badwords.cpp:374 modules/commands/cs_xop.cpp:484 +#: modules/commands/cs_flags.cpp:376 modules/commands/cs_access.cpp:503 +msgid "channel CLEAR" +msgstr "kanał CLEAR" + +#: modules/commands/cs_mode.cpp:736 +msgid "channel CLEAR [what]" +msgstr "kanał CLEAR [co]" + +#: modules/commands/os_mode.cpp:21 +msgid "channel CLEAR [ALL]" +msgstr "kanał CLEAR [ALL]" + +#: modules/commands/cs_entrymsg.cpp:195 +msgid "channel DEL num" +msgstr "kanał DEL numer" + +#: modules/commands/cs_xop.cpp:482 modules/commands/cs_access.cpp:500 +msgid "channel DEL {mask | entry-num | list}" +msgstr "kanał DEL {maska | numer-wpisu | lista}" + +#: modules/commands/cs_akick.cpp:436 +msgid "channel DEL {nick | mask | entry-num | list}" +msgstr "kanał DEL {nick | maska | numer-wpisu | lista}" + +#: modules/commands/bs_badwords.cpp:372 +msgid "channel DEL {word | entry-num | list}" +msgstr "kanał DEL {słowo | numer-wpisu | lista}" + +#: modules/commands/cs_akick.cpp:439 +msgid "channel ENFORCE" +msgstr "kanał ENFORCE" + +#: modules/commands/cs_entrymsg.cpp:196 modules/commands/cs_access.cpp:744 +msgid "channel LIST" +msgstr "kanał LIST" + +#: modules/commands/cs_akick.cpp:437 +msgid "channel LIST [mask | entry-num | list]" +msgstr "kanał LIST [maska | numer-wpisu | lista]" + +#: modules/commands/bs_badwords.cpp:373 modules/commands/cs_xop.cpp:483 +#: modules/commands/cs_access.cpp:501 +msgid "channel LIST [mask | list]" +msgstr "kanał LIST [maska | lista]" + +#: modules/commands/cs_flags.cpp:375 +msgid "channel LIST [mask | +flags]" +msgstr "kanał LIST [maska | +flagi]" + +#: modules/commands/cs_mode.cpp:734 +msgid "channel LOCK {ADD|DEL|SET|LIST} [what]" +msgstr "kanał LOCK {ADD|DEL|SET|LIST} [co]" + +#: modules/commands/cs_access.cpp:745 +msgid "channel RESET" +msgstr "kanał RESET" + +#: modules/commands/cs_mode.cpp:735 +msgid "channel SET modes" +msgstr "kanał SET flagi" + +#: modules/commands/cs_access.cpp:742 +msgid "channel SET type level" +msgstr "kanał SET typ poziom" + +#: modules/commands/cs_akick.cpp:438 +msgid "channel VIEW [mask | entry-num | list]" +msgstr "kanał VIEW [maska | numer-wpisu | lista]" + +#: modules/commands/cs_access.cpp:502 +msgid "channel VIEW [mask | list]" +msgstr "kanał VIEW [maska | lista]" + +#: modules/commands/cs_set.cpp:205 modules/commands/cs_register.cpp:20 +msgid "channel [description]" +msgstr "kanał [opis]" + +#: modules/commands/cs_invite.cpp:20 modules/commands/cs_unban.cpp:20 +#: modules/commands/cs_set.cpp:950 +msgid "channel [nick]" +msgstr "kanał [nick]" + +#: modules/commands/cs_set_misc.cpp:96 +msgid "channel [parameters]" +msgstr "kanał [parametry]" + +#: modules/commands/cs_status.cpp:20 modules/commands/cs_mode.cpp:807 +msgid "channel [user]" +msgstr "kanał [nick]" + +#: modules/commands/cs_suspend.cpp:59 +msgid "channel [+expiry] [reason]" +msgstr "kanał [+czas] [powód]" + +#: modules/commands/cs_ban.cpp:40 +msgid "channel [+expiry] {nick | mask} [reason]" +msgstr "kanał [+czas] {nick | maska} [powód]" + +#: modules/commands/cs_flags.cpp:374 +msgid "channel [MODIFY] mask changes" +msgstr "kanał [MODIFY] maska zmiany" + +#: modules/commands/cs_topic.cpp:150 +msgid "channel [SET] [topic]" +msgstr "kanał [SET] [temat]" + +#: modules/commands/cs_topic.cpp:152 +msgid "channel [UNLOCK|LOCK]" +msgstr "kanał [UNLOCK|LOCK]" + +#: modules/commands/bs_assign.cpp:154 modules/commands/greet.cpp:20 +#: modules/fantasy.cpp:20 +msgid "channel {ON|OFF}" +msgstr "kanał {ON|OFF}" + +#: modules/commands/bs_kick.cpp:491 +msgid "channel {ON|OFF} [ttb [ln [secs]]]" +msgstr "kanał {ON|OFF} [ttb [linie [sekundy]]]" + +#: modules/commands/bs_kick.cpp:361 +msgid "channel {ON|OFF} [ttb [min [percent]]]" +msgstr "kanał {ON|OFF} [ttb [min [procent]]]" + +#: modules/commands/bs_kick.cpp:623 +msgid "channel {ON|OFF} [ttb [num]]" +msgstr "kanał {ON|OFF} [ttb [numer]]" + +#: modules/commands/bs_kick.cpp:252 modules/commands/bs_kick.cpp:288 +#: modules/commands/bs_kick.cpp:327 modules/commands/bs_kick.cpp:457 +#: modules/commands/bs_kick.cpp:589 modules/commands/bs_kick.cpp:724 +#: modules/commands/bs_kick.cpp:758 +msgid "channel {ON|OFF} [ttb]" +msgstr "kanał {ON|OFF} [ttb]" + +#: modules/commands/cs_access.cpp:743 +msgid "channel {DIS | DISABLE} type" +msgstr "kanał {DIS | DISABLE} typ" + +#: modules/commands/cs_set.cpp:873 +msgid "channel {ON | LEVEL | OFF}" +msgstr "kanał {ON | LEVEL | OFF}" + +#: modules/commands/bs_kick.cpp:792 modules/commands/bs_kick.cpp:857 +#: modules/commands/cs_topic.cpp:21 modules/commands/cs_set.cpp:75 +#: modules/commands/cs_set.cpp:336 modules/commands/cs_set.cpp:401 +#: modules/commands/cs_set.cpp:473 modules/commands/cs_set.cpp:622 +#: modules/commands/cs_set.cpp:684 modules/commands/cs_set.cpp:747 +#: modules/commands/cs_set.cpp:811 modules/commands/cs_set.cpp:1044 +#: modules/commands/cs_list.cpp:181 modules/extra/stats/m_chanstats.cpp:18 +msgid "channel {ON | OFF}" +msgstr "kanał {ON | OFF}" + +#: modules/commands/ns_getemail.cpp:24 +msgid "email" +msgstr "email" + +#: modules/commands/ns_set.cpp:794 +msgid "language" +msgstr "język" + +#: modules/commands/ms_sendall.cpp:25 modules/commands/ms_staff.cpp:25 +msgid "memo-text" +msgstr "treść wiadomości" + +#: modules/commands/gl_global.cpp:22 modules/commands/greet.cpp:84 +msgid "message" +msgstr "treść wiadomości" + +#: modules/commands/os_modinfo.cpp:20 modules/commands/os_module.cpp:20 +#: modules/commands/os_module.cpp:57 modules/commands/os_module.cpp:129 +msgid "modname" +msgstr "modname" + +#: modules/commands/ns_set.cpp:330 +msgid "new-display" +msgstr "nowa-nazwa" + +#: modules/commands/ns_set.cpp:120 +msgid "new-password" +msgstr "nowe-hasło" + +#: modules/commands/hs_del.cpp:20 modules/commands/hs_del.cpp:60 +#: modules/commands/cs_seen.cpp:262 modules/commands/hs_request.cpp:192 +#: modules/commands/ms_check.cpp:20 modules/extra/stats/cs_fantasy_stats.cpp:52 +msgid "nick" +msgstr "nick" + +#: modules/commands/os_svs.cpp:79 +msgid "nick channel" +msgstr "nick kanał" + +#: modules/commands/os_svs.cpp:123 +msgid "nick channel [reason]" +msgstr "nick kanał [powód]" + +#: modules/commands/os_oline.cpp:20 +msgid "nick flags" +msgstr "nick flagi" + +#: modules/commands/hs_set.cpp:20 modules/commands/hs_set.cpp:126 +msgid "nick hostmask" +msgstr "nick maska-hosta" + +#: modules/commands/os_svs.cpp:20 +msgid "nick newnick" +msgstr "nick nowy-nick" + +#: modules/commands/hs_request.cpp:241 +msgid "nick [reason]" +msgstr "nick [powód]" + +#: modules/commands/ns_suspend.cpp:161 modules/commands/ns_getpass.cpp:20 +#: modules/commands/ns_drop.cpp:19 +msgid "nickname" +msgstr "nick" + +#: modules/commands/ns_set.cpp:546 +msgid "nickname address" +msgstr "nick adres" + +#: modules/commands/ns_resetpass.cpp:22 +msgid "nickname email" +msgstr "nick e-mail" + +#: modules/commands/ns_set.cpp:872 +msgid "nickname language" +msgstr "nick język" + +#: modules/commands/greet.cpp:145 +msgid "nickname message" +msgstr "nick wiadomość" + +#: modules/commands/ns_set.cpp:399 +msgid "nickname new-display" +msgstr "nick nowa-wyświetlana-nazwa" + +#: modules/commands/ns_set.cpp:173 +msgid "nickname new-password" +msgstr "nick nowe-hasło" + +#: modules/commands/ns_set_misc.cpp:170 +msgid "nickname [parameter]" +msgstr "nick [parametr]" + +#: modules/commands/ns_recover.cpp:150 +msgid "nickname [password]" +msgstr "nick [hasło]" + +#: modules/commands/ns_suspend.cpp:61 +msgid "nickname [+expiry] [reason]" +msgstr "nick [+czas] [powód]" + +#: modules/commands/ns_info.cpp:240 +msgid "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +msgstr "nick {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" + +#: modules/commands/ns_list.cpp:252 modules/commands/ns_set.cpp:302 +#: modules/commands/ns_set.cpp:631 modules/commands/ns_set.cpp:985 +#: modules/commands/ns_set.cpp:1076 modules/commands/ns_set.cpp:1105 +#: modules/extra/stats/m_chanstats.cpp:130 +msgid "nickname {ON | OFF}" +msgstr "nick {ON | OFF}" + +#: modules/commands/ns_set.cpp:760 +msgid "nickname {ON | QUICK | IMMED | OFF}" +msgstr "nick {ON | QUICK | IMMED | OFF}" + +#: modules/commands/bs_set.cpp:20 +msgid "option (channel | bot) settings" +msgstr "opcja (kanał | bot) ustawienia" + +#: modules/commands/cs_set.cpp:21 +msgid "option channel parameters" +msgstr "opcja kanał parametry" + +#: modules/commands/bs_kick.cpp:120 +msgid "option channel {ON|OFF} [settings]" +msgstr "opcja kanał {ON|OFF} [ustawienia]" + +#: modules/commands/ns_set.cpp:75 +msgid "option nickname parameters" +msgstr "opcja nick parametry" + +#: modules/commands/ns_set.cpp:20 modules/commands/ms_set.cpp:207 +msgid "option parameters" +msgstr "opcja parametry" + +#: modules/commands/os_set.cpp:170 +msgid "option setting" +msgstr "opcja ustawienie" + +#: modules/commands/ns_register.cpp:22 +msgid "passcode" +msgstr "kod-aktywacyjny" + +#: modules/commands/os_login.cpp:19 +msgid "password" +msgstr "hasło" + +#: modules/commands/ns_register.cpp:124 +msgid "password [email]" +msgstr "hasło [email]" + +#: modules/commands/ns_register.cpp:122 +msgid "password email" +msgstr "hasło email" + +#: modules/commands/cs_list.cpp:21 +msgid "pattern [SUSPENDED] [NOEXPIRE]" +msgstr "wzorzec [SUSPENDED] [NOEXPIRE]" + +#: modules/commands/ns_list.cpp:20 +msgid "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" +msgstr "wzorzec [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/os_jupe.cpp:20 +msgid "server [reason]" +msgstr "serwer [powód]" + +#: modules/commands/os_mode.cpp:147 +msgid "user modes" +msgstr "użytkownik flagi" + +#: modules/commands/os_kill.cpp:20 +msgid "user [reason]" +msgstr "użytkownik [powód]" + +#: modules/commands/os_sxline.cpp:440 +msgid "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." +msgstr "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." + +#: modules/commands/os_sxline.cpp:678 +msgid "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." + +#: modules/pseudoclients/nickserv.cpp:492 +#, c-format +msgid "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." +msgstr "" +" \n" +"Konta nieużywane przez dłuższy czas są automatycznie\n" +"usuwane po %d dniach od ostatniej identyfikacji.\n" +"Wszelkie ustawienia oraz uprawnienia zostają usunięte." + +#: modules/pseudoclients/botserv.cpp:143 +msgid "" +" \n" +"Available commands are:" +msgstr "" +" \n" +"Dostępne polecenia to:" + +#: modules/pseudoclients/botserv.cpp:167 +#, c-format +msgid "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." +msgstr "" +" \n" +"Bot dołączy do kanału, gdy będzie na nim co najmniej %d użytkowników." + +#: modules/fantasy.cpp:69 +#, c-format +msgid "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." +msgstr "" +" \n" +"Włącza lub wyłącza dostęp do publicznych poleceń\n" +"\"fantasy\" na kanale. Komendy muszą być poprzedzone\n" +"jednym z następujących znaków: %s\n" +"\n" +"Użytkownicy dopuszczeni do używania komend\n" +"publicznych muszą mieć odpowiedni poziom dostępu\n" +"do wydania danego polecenia (np. aby używac !deop\n" +"trzeba posiadać poziom dostępu OPDEOP), oraz\n" +"jednocześnie uprawnienie FANTASIA." + +#: modules/commands/greet.cpp:69 +msgid "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." +msgstr "" +" \n" +"Włącza lub wyłącza witanie podczas wejścia użytkowników\n" +"ich własną wiadomością powitalną. Użytkownik zostanie\n" +"powitany, jeśli będzie miał odpowiedni poziom dostępu." + +#: modules/commands/bs_kick.cpp:843 +msgid "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Włącza lub wyłącza opcję kopania użytkowników\n" +"posiadających status operatora nawet jeśli nie\n" +"przysługuje im poziom dostępu NOKICK." + +#: modules/commands/bs_kick.cpp:908 +msgid "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +" \n" +"Włącza lub wyłącza opcję kopania użytkowników\n" +"posiadających prawo głosu nawet jeśli nie\n" +"przysługuje im poziom dostępu NOKICK." + +#: modules/pseudoclients/botserv.cpp:141 +#, c-format +msgid "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" +msgstr "" +" \n" +"Komendy \"fantasy\" mogą być poprzedzone jednym z następujących znaków: %s\n" + +#: modules/commands/cs_register.cpp:105 +msgid "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." +msgstr "" +" \n" +"UWAGA: aby zarejestrować kanał, musisz najpierw\n" +"zarejestrować swojego nicka." + +#: modules/pseudoclients/chanserv.cpp:272 +#, c-format +msgid "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." +msgstr "" +" \n" +"Uwaga! Kanał który nie był używany przez %d dni\n" +"(np. nie odwiedził go żaden użytkownik umieszczony\n" +"na liście dostępu kanału w tym czasie) zostanie\n" +"automatycznie odrejestrowany." + +#: modules/commands/cs_register.cpp:101 +#, c-format +msgid "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +msgstr "" +" \n" +"Zapoznaj się z poleceniem %s (%s%s HELP ACCESS), aby uzyskać\n" +"informacje na temat przyznawania części z tych uprawnień\n" +"innym użytkownikom na kanale.\n" + +#: modules/pseudoclients/nickserv.cpp:486 +msgid "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." +msgstr "" +" \n" +"Administratorzy serwisów mogą usunąć każdy nick\n" +"bez potrzeby identyfikacji jako jego właściciele\n" +"oraz przeglądać listę dostępu do każdego nicka." + +#: modules/pseudoclients/chanserv.cpp:277 +msgid "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." +msgstr "" +" \n" +"Operatorzy serwisów mogą usunąć każdy kanał\n" +"bez potrzeby identyfikacji jako jego właściciele.\n" +"Mogą przeglądać (i zmieniać) listę dostępu każdego\n" +"kanału, listę AKICK, ustawienia poziomów dostępu itd." + +#: modules/commands/bs_set.cpp:147 +msgid "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." +msgstr "" +" \n" +"Ustawia czas, po którym bany ustawione przez bota przedawnią się.\n" +"Jeśli ustawienie jest włączone, wszystkie bany ustawione przez bota,\n" +"na przykład za flood, zabronione słowa itp. zostaną automatycznie usunięte\n" +"po upływie zadanego czasu. Ustaw 0, aby bany nie przedawniały się." + +#: modules/commands/cs_xop.cpp:542 +#, c-format +msgid "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." +msgstr "" +" \n" +"Komenda %s ADD dodaje podany nick do listy %s.\n" +" \n" +"Komenda %s DEL usuwa wskazane wpisy z listy %s.\n" +"Jako argument przyjmuje nick, numer wpisu lub\n" +"listę (przykład poniżej dla polecenia LIST).\n" +" \n" +"Komenda %s LIST wyświetla zawartość listy %s.\n" +"Parametr maska pozwala filtrować wyświetlane wpisy\n" +"(symbol * zastępuje dowolny ciąg znaków w nicku).\n" +"Jako parametr można też podać numery wpisów na liście:\n" +"\n" +" %s #kanał LIST 2-5,7-9\n" +" Wyświetli wpisy na liście %s od numeru 2 do 5 oraz\n" +" od 7 do 9.\n" +"\n" +"Komenda %s CLEAR usuwa wszystkie wpisy z listy %s." + +#: modules/commands/cs_akick.cpp:508 +#, c-format +msgid "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." +msgstr "" +" \n" +"Polecenie AKICK DEL usuwa podany nick lub maskę\n" +"z listy AutoKick. Użycie tego polecenia nie powoduje automatycznego\n" +"usunięcia żadnych banów ustawionych przez AutoKick;\n" +"bany te muszą zostać usunięte ręcznie.\n" +" \n" +"Polecenie AKICK LIST wyświetla listę AutoKick, lub, opcjonalnie,\n" +"tylko te wpisy na liście, które pasują do zadanej maski.\n" +" \n" +"Polecenie AKICK VIEW działa podobnie do AKICK LIST,\n" +"ale podaje więcej informacji.\n" +" \n" +"Polecenie AKICK ENFORCE powoduje, że %s usuwa wszystkich\n" +"użytkowników pasujących do aktualnej maski AKICK.\n" +" \n" +"Polecenie AKICK CLEAR usuwa wszystkie wpisy z listy AKICK." + +#: modules/commands/os_akill.cpp:448 +msgid "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." +msgstr "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." + +#: modules/commands/os_sxline.cpp:462 +msgid "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." +msgstr "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." + +#: modules/commands/os_sxline.cpp:697 +msgid "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." +msgstr "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." + +#: modules/commands/bs_assign.cpp:197 +msgid "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." +msgstr "" +" \n" +"Polecenie to pozwala określić kanał, dla którego\n" +"nie wolno przypisywać botów. Jeśli w danej chwili\n" +"bot jest przypisany do kanału, zostanie usunięty." + +#: modules/commands/bs_set.cpp:199 +msgid "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." +msgstr "" +" \n" +"Ta opcja pozwala na przypisanie bota do kanału tylko\n" +"przez IRCoperatorów." + +#: modules/pseudoclients/memoserv.cpp:227 +#, c-format +msgid "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." +msgstr "" +" \n" +"Użyj polecenia %s%s HELP polecenie, aby uzyskać pomoc dotyczącą\n" +"dowolnego z powyższych poleceń." + +#: modules/commands/os_oper.cpp:167 +#, c-format +msgid " %s is online using this oper block." +msgstr " %s jest online używając tego bloku oper." + +#: modules/commands/os_modinfo.cpp:55 +#, c-format +msgid " Command %s on %s is linked to %s" +msgstr " Polecenie %s na %s jest połączone z %s" + +#: modules/commands/os_modinfo.cpp:43 +#, c-format +msgid " Providing service: %s" +msgstr " Dodane komendy: %s" + +#: modules/commands/os_oper.cpp:163 +msgid " This oper is configured in the configuration file." +msgstr " Ten oper jest ustawiony w pliku konfiguracyjnym." + +#: modules/commands/os_modinfo.cpp:34 +#, c-format +msgid " Loaded at: %p" +msgstr " Załadowano na: %p" + +#: modules/commands/cs_seen.cpp:303 +#, c-format +msgid " but %s mysteriously dematerialized." +msgstr " ale %s w magiczny sposób przestał istnieć." + +#: src/messages.cpp:339 +#, c-format +msgid "\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." +msgstr "\"/msg %s\" nie jest już obsługiwane. Użyj \"/msg %s@%s\" lub \"/%s\"." + +#: modules/commands/os_jupe.cpp:19 +msgid "\"Jupiter\" a server" +msgstr "Blokuje podłączanie podanego serwera" + +#: modules/commands/os_oper.cpp:161 +#, c-format +msgid "%-8s %s" +msgstr "%-8s %s" + +#: modules/extra/stats/cs_fantasy_top.cpp:152 +#, c-format +msgid "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "%2lu %-16s liter: %s, słów: %s, linii: %s, emotikon: %s, akcji: %s" + +#: src/misc.cpp:359 +msgid "%b %d %H:%M:%S %Y %Z" +msgstr "%b %d %H:%M:%S %Y %Z" + +#: modules/commands/cs_log.cpp:205 +#, c-format +msgid "%c is an unknown status mode." +msgstr "%c nie jest znanym trybem statusu." + +#: modules/commands/cs_mode.cpp:431 +#, c-format +msgid "%c%c is not locked on %s." +msgstr "%c%c nie jest zablokowany na %s." + +#: modules/commands/cs_mode.cpp:427 +#, c-format +msgid "%c%c%s has been unlocked from %s." +msgstr "%c%c%s został odblokowany z %s." + +#: modules/commands/cs_clone.cpp:56 +#, c-format +msgid "%d access entries from %s have been cloned to %s." +msgstr "%d wpisów listy dostępu z %s zostało skopiowanych do %s." + +#: modules/commands/bs_botlist.cpp:56 +#, c-format +msgid "%d bots available." +msgstr "%d boty(ów) dostępnych." + +#: modules/commands/os_modinfo.cpp:189 +#, c-format +msgid "%d modules loaded." +msgstr "Załadowanych modułów: %d." + +#: modules/commands/ns_group.cpp:357 +#, c-format +msgid "%d nickname(s) in the group." +msgstr "%d nicków w grupie." + +#: modules/commands/cs_seen.cpp:137 +#, c-format +msgid "%lu nicks are stored in the database, using %.2Lf kB of memory." +msgstr "" +"%lu nicków jest zapisanych w bazie danych, zajmując przy tym %.2Lf kB pamięci." + +#: modules/commands/cs_xop.cpp:241 modules/commands/cs_xop.cpp:372 +#: modules/commands/cs_xop.cpp:450 +#, c-format +msgid "%s %s list is empty." +msgstr "Lista %s kanału %s jest pusta." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1181 +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1201 +#: modules/commands/bs_kick.cpp:1211 +#, c-format +msgid "%s (%d kick(s) to ban)" +msgstr "%s (%d kop(y) do bana)" + +#: modules/commands/bs_kick.cpp:1161 +#, c-format +msgid "%s (%d kick(s) to ban; %d lines in %ds)" +msgstr "%s (%d kop(y) do bana; %d linii w %ds)" + +#: modules/commands/bs_kick.cpp:1171 +#, c-format +msgid "%s (%d kick(s) to ban; %d times)" +msgstr "%s (%d kop(y) do bana; %d razy)" + +#: modules/commands/bs_kick.cpp:1141 +#, c-format +msgid "%s (%d kick(s) to ban; minimum %d/%d%%)" +msgstr "%s (%d kop(y) do bana; minimum %d/%d%%)" + +#: modules/commands/bs_kick.cpp:1163 +#, c-format +msgid "%s (%d lines in %ds)" +msgstr "%s (%d linii przez %ds)" + +#: modules/commands/bs_kick.cpp:1173 +#, c-format +msgid "%s (%d times)" +msgstr "%s (%d razy)" + +#: modules/commands/cs_seen.cpp:358 +#, c-format +msgid "%s (%s) was kicked from %s (\"%s\") %s ago%s" +msgstr "%s (%s) został wyrzucony z %s (\"%s\") %s temu%s" + +#: modules/commands/cs_seen.cpp:355 +#, c-format +msgid "%s (%s) was kicked from a secret channel %s ago%s" +msgstr "%s (%s) został wyrzucony z ukrytego kanału %s temu%s" + +#: modules/commands/cs_seen.cpp:326 +#, c-format +msgid "%s (%s) was last seen changing nick from %s to %s %s ago%s" +msgstr "%s (%s) ostatnio widziano, gdy zmieniał(a) nick z %s na %s %s temu%s" + +#: modules/commands/cs_seen.cpp:321 +#, c-format +msgid "%s (%s) was last seen changing nick to %s %s ago%s" +msgstr "%s (%s) ostatnio widziano, gdy zmieniał(a) nick na %s %s temu%s" + +#: modules/commands/cs_seen.cpp:310 +#, c-format +msgid "%s (%s) was last seen connecting %s ago (%s)%s" +msgstr "%s (%s) ostatnio widziano, gdy łączył(a) się %s temu (%s)%s" + +#: modules/commands/cs_seen.cpp:335 +#, c-format +msgid "%s (%s) was last seen joining %s %s ago%s" +msgstr "%s (%s) ostatnio widziano, gdy dołączał(a) do %s %s temu%s" + +#: modules/commands/cs_seen.cpp:332 +#, c-format +msgid "%s (%s) was last seen joining a secret channel %s ago%s" +msgstr "%s (%s) ostatnio widziano, gdy dołączał(a) do ukrytego kanału %s temu%s" + +#: modules/commands/cs_seen.cpp:344 +#, c-format +msgid "%s (%s) was last seen parting %s %s ago%s" +msgstr "%s (%s) ostatnio widziano, gdy opuszczał(a) %s %s temu%s" + +#: modules/commands/cs_seen.cpp:341 +#, c-format +msgid "%s (%s) was last seen parting a secret channel %s ago%s" +msgstr "%s (%s) ostatnio widziano, gdy opuszczał(a) ukryty kanał %s temu%s" + +#: modules/commands/cs_seen.cpp:349 +#, c-format +msgid "%s (%s) was last seen quitting (%s) %s ago (%s)." +msgstr "%s (%s) ostatnio widziano, gdy rozłączał(a) się (%s) %s temu (%s)." + +#: modules/commands/bs_kick.cpp:1143 +#, c-format +msgid "%s (minimum %d/%d%%)" +msgstr "%s (minimum %d/%d%%)" + +#: modules/commands/cs_flags.cpp:295 modules/commands/cs_access.cpp:245 +#: modules/commands/cs_access.cpp:349 modules/commands/cs_access.cpp:454 +#: modules/commands/cs_access.cpp:467 +#, c-format +msgid "%s access list is empty." +msgstr "Lista dostępu kanału %s jest pusta." + +#: modules/commands/ns_ajoin.cpp:184 +#, c-format +msgid "%s added to %s's auto join list." +msgstr "%s dodano do listy automatycznego dołączania do %s." + +#: src/xline.cpp:389 +#, c-format +msgid "%s already exists." +msgstr "%s już istnieje." + +#: modules/commands/cs_akick.cpp:202 modules/commands/cs_akick.cpp:387 +#: modules/commands/cs_akick.cpp:400 +#, c-format +msgid "%s autokick list is empty." +msgstr "Lista AKICK kanału %s jest pusta." + +#: modules/commands/bs_badwords.cpp:198 modules/commands/bs_badwords.cpp:316 +#, c-format +msgid "%s bad words list is empty." +msgstr "Lista zakazanych słów dla kanału %s jest pusta." + +#: modules/commands/cs_set.cpp:993 +#, c-format +msgid "%s cannot be the successor on channel %s as they are the founder." +msgstr "%s nie może być zastępcą na kanale %s, ponieważ jest jego właścicielem." + +#: modules/pseudoclients/operserv.cpp:287 modules/pseudoclients/hostserv.cpp:87 +#: modules/pseudoclients/global.cpp:95 +#, c-format +msgid "%s commands:" +msgstr "Komendy %s:" + +#: include/language.h:69 +#, c-format +msgid "%s coverage is too wide; Please use a more specific mask." +msgstr "Zakres %s jest zbyt szeroki; proszę użyć dokładniejszej maski." + +#: modules/commands/ms_info.cpp:94 +#, c-format +msgid "%s currently has %d memos, of which %d are unread." +msgstr "%s ma aktualnie %d wiadomości, z czego %d jest nieprzeczytanych." + +#: modules/commands/ms_info.cpp:92 +#, c-format +msgid "%s currently has %d memos, of which 1 is unread." +msgstr "%s ma aktualnie %d wiadomości, w tym jedną nieprzeczytaną." + +#: modules/commands/ms_info.cpp:90 +#, c-format +msgid "%s currently has %d memos." +msgstr "%s ma aktualnie %d wiadomości." + +#: modules/commands/ms_info.cpp:88 +#, c-format +msgid "%s currently has %d memos; all of them are unread." +msgstr "%s ma aktualnie %d nieprzeczytanych wiadomości." + +#: modules/commands/ms_info.cpp:77 +#, c-format +msgid "%s currently has 1 memo, and it has not yet been read." +msgstr "%s ma aktualnie jedną wiadomość, która jest nieprzeczytana." + +#: modules/commands/ms_info.cpp:79 +#, c-format +msgid "%s currently has 1 memo." +msgstr "%s aktualnie ma jedną wiadomość." + +#: modules/commands/ms_info.cpp:73 +#, c-format +msgid "%s currently has no memos." +msgstr "%s aktualnie nie ma wiadomości." + +#: modules/commands/os_forbid.cpp:344 +#, c-format +msgid "%s deleted from the %s forbid list." +msgstr "%s usunięto z listy zakazanych słów kanału %s." + +#: include/language.h:105 +#, c-format +msgid "%s for %s set to %s." +msgstr "%s dla %s został zmieniony na %s." + +#: include/language.h:106 +#, c-format +msgid "%s for %s unset." +msgstr "%s dla %s usunięto." + +#: modules/commands/ns_ajoin.cpp:176 +#, c-format +msgid "%s had an invalid key specified, and was thus ignored." +msgstr "%s posiadał podany błędny klucz, więc został zignorowany." + +#: modules/commands/ms_info.cpp:111 +#, c-format +msgid "%s has no memo limit." +msgstr "%s nie ma limitu wiadomości." + +#: include/language.h:115 +#, c-format +msgid "%s has no memos." +msgstr "%s nie ma wiadomości." + +#: include/language.h:118 +#, c-format +msgid "%s has no new memos." +msgstr "%s nie ma nowych wiadomości." + +#: modules/commands/ns_info.cpp:53 +#, c-format +msgid "%s is %s" +msgstr "%s to %s" + +#: modules/commands/ns_info.cpp:59 +#, c-format +msgid "%s is a Services Operator of type %s." +msgstr "%s jest operatorem serwisów typu %s." + +#: modules/commands/cs_seen.cpp:281 +#, c-format +msgid "%s is a client on services." +msgstr "%s jest usługą sieciową." + +#: modules/commands/cs_seen.cpp:200 +#, c-format +msgid "%s is a network service." +msgstr "%s jest usługą sieciową." + +#: src/xline.cpp:407 +#, c-format +msgid "%s is already covered by %s." +msgstr "%s już jest obejmowane przez %s." + +#: modules/commands/ns_ajoin.cpp:170 +#, c-format +msgid "%s is already on %s's auto join list." +msgstr "%s jest już na liście automatycznego dołączania %s." + +#: modules/commands/ns_info.cpp:56 +#, c-format +msgid "%s is an unconfirmed nickname." +msgstr "%s jest niepotwierdzonym nickiem." + +#: modules/commands/cs_flags.cpp:432 +#, c-format +msgid "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." +msgstr "" +"%s jest kolejnym sposobem na modyfikację listy dostępu kanału, podobnie do\n" +"XOP i ACCESS." + +#: modules/commands/ns_info.cpp:75 +#, c-format +msgid "%s is currently online." +msgstr "%s jest teraz online." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is disabled" +msgstr "%s jest wyłączone" + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is enabled" +msgstr "%s jest włączone" + +#: modules/commands/os_dns.cpp:507 +#, c-format +msgid "%s is not a valid IP address." +msgstr "%s nie jest poprawnym adresem IP." + +#: modules/commands/cs_log.cpp:167 modules/commands/cs_log.cpp:192 +#, c-format +msgid "%s is not a valid command." +msgstr "%s nie jest poprawnym poleceniem." + +#: modules/commands/cs_log.cpp:198 +#, c-format +msgid "%s is not a valid logging method." +msgstr "%s nie jest poprawną metodą logowania." + +#: modules/commands/ms_info.cpp:124 +#, c-format +msgid "%s is not notified of new memos." +msgstr "%s nie otrzymuje powiadomień o nowych wiadomościach." + +#: modules/commands/ms_info.cpp:118 +#, c-format +msgid "%s is notified of new memos at logon and when they arrive." +msgstr "" +"%s otrzymuje powiadomienia o nowych wiadomościach\n" +"podczas logowania i w momencie ich nadejścia." + +#: modules/commands/ms_info.cpp:122 +#, c-format +msgid "%s is notified of new memos at logon." +msgstr "%s otrzymuje powiadomienia o nowych wiadomościach podczas logowania." + +#: modules/commands/ms_info.cpp:120 +#, c-format +msgid "%s is notified when new memos arrive." +msgstr "%s otrzymuje powiadomienia o nowych wiadomościach w momencie ich nadejścia." + +#: modules/commands/cs_seen.cpp:232 +#, c-format +msgid "%s is on the channel right now (as %s)!" +msgstr "%s jest teraz na kanale (jako %s)!" + +#: modules/commands/cs_seen.cpp:221 +#, c-format +msgid "%s is on the channel right now!" +msgstr "%s jest teraz na kanale!" + +#: modules/commands/cs_xop.cpp:434 +#, c-format +msgid "%s list for %s" +msgstr "Lista %s dla %s" + +#: modules/commands/os_sxline.cpp:69 modules/commands/os_sxline.cpp:113 +#, c-format +msgid "%s list is empty." +msgstr "Lista %s jest pusta." + +#: modules/commands/cs_mode.cpp:376 +#, c-format +msgid "%s locked on %s." +msgstr "%s zablokowany na %s." + +#: modules/extra/stats/cs_fantasy_stats.cpp:120 +#, c-format +msgid "%s not found." +msgstr "%s nie znaleziono." + +#: modules/commands/os_config.cpp:79 +#, c-format +msgid "%s settings:" +msgstr "Ustawienia %s:" + +#: modules/commands/cs_seen.cpp:255 +#, c-format +msgid "%s was last seen here %s ago." +msgstr "%s widziano tutaj ostatnio %s temu." + +#: modules/commands/ns_ajoin.cpp:213 +#, c-format +msgid "%s was not found on %s's auto join list." +msgstr "%s nie znaleziono na liście automatycznego dołączania %s." + +#: modules/commands/ns_ajoin.cpp:221 +#, c-format +msgid "%s was removed from %s's auto join list." +msgstr "%s usunięto z listy automatycznego dołączania %s." + +#: modules/commands/ms_set.cpp:64 +#, c-format +msgid "%s will not send you any notification of memos." +msgstr "%s nie będzie powiadamiał Cię o nowych wiadomościach." + +#: modules/commands/ms_set.cpp:42 +#, c-format +msgid "%s will now notify you of memos when they are sent to you." +msgstr "%s będzie powiadamiał Cię o nowych wiadomościach w momencie ich nadejścia." + +#: modules/commands/ms_set.cpp:30 +#, c-format +msgid "" +"%s will now notify you of memos when you log on and when they are sent to you." +msgstr "" +"%s powiadomi Cię o wiadomościach podczas logowania i w momencie ich nadejścia." + +#: modules/commands/ms_set.cpp:36 +#, c-format +msgid "%s will now notify you of memos when you log on or unset /AWAY." +msgstr "" +"%s powiadomi Cię o wiadomościach podczas logowania oraz po wyłączeniu /away." + +#: modules/commands/bs_bot.cpp:89 +#, c-format +msgid "%s!%s@%s (%s) added to the bot list." +msgstr "%s!%s@%s (%s) dodano do listy botów." + +#: modules/commands/ns_access.cpp:83 +#, c-format +msgid "%s's access list is empty." +msgstr "Lista dostępu kanału %s jest pusta." + +#: modules/commands/ns_ajoin.cpp:96 +#, c-format +msgid "%s's auto join list is empty." +msgstr "Lista automatycznego dołączania do kanału %s jest pusta." + +#: modules/commands/ns_ajoin.cpp:111 +#, c-format +msgid "%s's auto join list:" +msgstr "Lista automatycznego dołączania do kanału %s:" + +#: modules/commands/ns_cert.cpp:242 +#, c-format +msgid "%s's certificate list is empty." +msgstr "Lista certyfikatów %s jest pusta." + +#: modules/commands/ms_info.cpp:99 modules/commands/ms_info.cpp:106 +#, c-format +msgid "%s's memo limit is %d, and may not be changed." +msgstr "%s ma limit wiadomości %d i nie może być zmieniony." + +#: modules/commands/ms_info.cpp:101 modules/commands/ms_info.cpp:108 +#, c-format +msgid "%s's memo limit is %d." +msgstr "%s ma limit wiadomości %d." + +#: src/misc.cpp:363 +#, c-format +msgid "(%s ago)" +msgstr "(%s temu)" + +#: src/misc.cpp:365 +#, c-format +msgid "(%s from now)" +msgstr "(%s od tego momentu)" + +#: modules/commands/os_dns.cpp:244 +msgid "(Split)" +msgstr "(Split)" + +#: modules/commands/os_info.cpp:268 +#, c-format +msgid "(by %s on %s) %s" +msgstr "(przez %s jako %s) %s" + +#: modules/commands/cs_access.cpp:710 +msgid "(disabled)" +msgstr "(wyłączone)" + +#: modules/commands/cs_access.cpp:712 +msgid "(founder only)" +msgstr "(tylko założyciel)" + +#: src/misc.cpp:367 +msgid "(now)" +msgstr "(teraz)" + +#: modules/commands/os_defcon.cpp:168 +msgid "* AKILL any new clients connecting" +msgstr "* AKILLuje wszystkich nowych klientów" + +#: modules/commands/os_defcon.cpp:158 +#, c-format +msgid "* Force channel modes (%s) to be set on all channels" +msgstr "* Wymusza ustawienie flag (%s) na wszystkich kanałach" + +#: modules/commands/os_defcon.cpp:164 +msgid "* Ignore non-opers with a message" +msgstr "* Ignoruje zwykłych użytkowników (informuje ich o tym)" + +#: modules/commands/os_defcon.cpp:162 +msgid "* Kill any new clients connecting" +msgstr "* Killuje wszystkich nowych klientów" + +#: modules/commands/os_defcon.cpp:156 +msgid "* No mode lock changes" +msgstr "* Flagi kanałów nie będą wymuszane (MLOCK)" + +#: modules/commands/os_defcon.cpp:152 +msgid "* No new channel registrations" +msgstr "* Wyłącza rejestrowanie kanałów" + +#: modules/commands/os_defcon.cpp:170 +msgid "* No new memos sent" +msgstr "* Nowe wiadomości nie będą wysyłane" + +#: modules/commands/os_defcon.cpp:154 +msgid "* No new nick registrations" +msgstr "* Wyłącza rejestrowanie nicków" + +#: modules/commands/os_defcon.cpp:166 +msgid "* Silently ignore non-opers" +msgstr "* Cicho ignoruje zwykłych użytkowników" + +#: modules/commands/os_defcon.cpp:160 +#, c-format +msgid "* Use the reduced session limit of %d" +msgstr "* Używa zredukowanego limitu sesji: %d" + +#: modules/commands/cs_seen.cpp:319 +#, c-format +msgid ", but %s mysteriously dematerialized." +msgstr ", ale %s w tajemniczy sposób zniknął." + +#: modules/commands/cs_seen.cpp:317 +#, c-format +msgid ". %s is still online." +msgstr ". %s jest nadal online." + +#: include/language.h:87 +msgid "" +msgstr "" + +#: modules/commands/ns_set.cpp:504 +#, c-format +msgid "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." +msgstr "" +"Wiadomość potwierdzająca została wysłana na e-mail %s.\n" +"Postępuj według instrukcji w niej, aby dokończyć procedurę rejestracji." + +#: modules/commands/ms_sendall.cpp:45 +msgid "A massmemo has been sent to all registered users." +msgstr "Wiadomość została wysłana do wszystkich zarejestrowanych użytkowników." + +#: modules/commands/hs_request.cpp:285 +msgid "" +"A memo informing the user will also be sent, which includes the reason for the " +"rejection if supplied." +msgstr "" +"Wysłana zostanie także wiadomość informująca użytkownika. Jeśli podano przyczynę " +"odrzucenia, informacja ta zostanie dołączona." + +#: modules/commands/hs_request.cpp:229 +msgid "A memo informing the user will also be sent." +msgstr "Wysłana zostanie także wiadomość informująca użytkownika." + +#: modules/commands/ms_read.cpp:42 +#, c-format +msgid "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." +msgstr "Powiadomienie o przeczytaniu wiadomości zostało wysłane do %s." + +#: include/language.h:123 +msgid "A vHost ident must be in the format of a valid ident." +msgstr "Ident vHost musi być w formacie właściwego dla nazwy użytkownika." + +#: include/language.h:122 +msgid "A vHost must be in the format of a valid hostname." +msgstr "" +"VHost musi mieć format prawidłowej nazwy hosta\n" +"(m. in. nie może zawierać spacji, a musi co najmniej jedną kropkę)." + +#: modules/commands/os_ignore.cpp:342 +msgid "ADD expiry {nick|mask} [reason]" +msgstr "ADD czas {nick|maska} [powód]" + +#: modules/commands/os_oper.cpp:70 +msgid "ADD oper type" +msgstr "ADD oper typ" + +#: modules/commands/os_info.cpp:102 +msgid "ADD target info" +msgstr "ADD cel informacja" + +#: modules/commands/os_news.cpp:278 +msgid "ADD text" +msgstr "ADD tekst" + +#: modules/commands/os_session.cpp:523 +msgid "ADD [+expiry] mask limit reason" +msgstr "ADD [+czas] maska limit powód" + +#: modules/commands/ns_ajoin.cpp:231 +msgid "ADD [nickname] channel [key]" +msgstr "ADD [nick] kanał [klucz]" + +#: modules/commands/ns_access.cpp:102 +msgid "ADD [nickname] mask" +msgstr "ADD [nick] maska" + +#: modules/commands/ns_cert.cpp:258 +msgid "ADD [nickname] [fingerprint]" +msgstr "ADD [nick] [odcisk-palca]" + +#: modules/commands/os_sxline.cpp:659 modules/commands/os_akill.cpp:386 +msgid "ADD [+expiry] mask reason" +msgstr "ADD [+czas] maska powód" + +#: modules/commands/os_sxline.cpp:425 +msgid "ADD [+expiry] mask:reason" +msgstr "ADD [+czas] maska:powód" + +#: modules/commands/os_forbid.cpp:157 +msgid "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" +msgstr "ADD {NICK|CHAN|EMAIL|REGISTER} [+czas] wpis powód" + +#: modules/commands/os_dns.cpp:665 +msgid "ADDIP server.name ip" +msgstr "ADDIP nazwa.serwera ip" + +#: modules/commands/os_dns.cpp:663 +msgid "ADDSERVER server.name [zone.name]" +msgstr "ADDSERVER nazwa.serwera [nazwa.strefy]" + +#: modules/commands/os_dns.cpp:661 +msgid "ADDZONE zone.name" +msgstr "ADDZONE nazwa.strefy" + +#: modules/commands/cs_akick.cpp:38 +#, c-format +msgid "AKICK ENFORCE for %s complete; %d users were affected." +msgstr "" +"Egzekucja listy AKICK kanału %s zakończona.\n" +"Dotyczyła %d użytkowników." + +#: modules/commands/os_chankill.cpp:21 +msgid "AKILL all users on a specific channel" +msgstr "AKILL wszystkich użytkowników na kanale" + +#: modules/commands/os_akill.cpp:222 modules/commands/os_akill.cpp:339 +#: modules/commands/os_akill.cpp:353 +msgid "AKILL list is empty." +msgstr "Lista AKILL jest pusta." + +#: modules/commands/bs_kick.cpp:1211 modules/commands/bs_kick.cpp:1213 +#: modules/commands/bs_kick.cpp:1216 +msgid "AMSG kicker" +msgstr "Kopanie za AMSG" + +#: modules/commands/ns_alist.cpp:48 +msgid "Access" +msgstr "Dostęp" + +#: include/language.h:72 +msgid "Access denied." +msgstr "Odmowa dostępu." + +#: modules/commands/cs_status.cpp:58 +#, c-format +msgid "Access for %s on %s:" +msgstr "Dostęp dla %s na %s:" + +#: include/language.h:107 +#, c-format +msgid "Access level must be between %d and %d inclusive." +msgstr "Poziom musi być pomiędzy %d a %d włącznie." + +#: modules/commands/cs_access.cpp:108 +msgid "Access level must be non-zero." +msgstr "Poziom dostępu nie może być zerem." + +#: modules/commands/cs_access.cpp:694 +#, c-format +msgid "Access level settings for channel %s:" +msgstr "Ustawienia poziomów dostępu kanału %s:" + +#: modules/commands/cs_access.cpp:734 +#, c-format +msgid "Access levels for %s reset to defaults." +msgstr "Poziomy dostępu kanału %s zostały zresetowane do domyślnych." + +#: modules/commands/ns_access.cpp:87 modules/commands/cs_access.cpp:439 +#, c-format +msgid "Access list for %s:" +msgstr "Lista dostępu dla %s:" + +#: modules/commands/help.cpp:166 +#, c-format +msgid "" +"Access to this command requires the permission %s to be present in your opertype." +msgstr "" +"Dostęp do tego polecenia wymaga ustawienia uprawnienia %s w twoim bloku operatora." + +#: modules/commands/ns_info.cpp:63 +msgid "Account" +msgstr "Konto" + +#: modules/commands/ns_identify.cpp:94 modules/commands/ns_cert.cpp:368 +#: modules/commands/ns_cert.cpp:392 +#, c-format +msgid "" +"Account %s has already reached the maximum number of simultaneous logins (%u)." +msgstr "Konto %s już osiągnęło maksymalną ilość równoczesnych logowań (%u)." + +#: modules/commands/cs_set.cpp:683 +msgid "Activate security features" +msgstr "Włącza funkcje bezpieczeństwa" + +#: modules/commands/hs_request.cpp:227 +msgid "Activate the requested vHost for the given nick." +msgstr "Aktywuje vHosta dla podanego nicka." + +#: modules/commands/hs_on.cpp:55 +msgid "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." +msgstr "" +"Aktywuje vhosta aktualnie przypisanego do używanego nicka.\n" +"Po użyciu tego polecenia Twój prawdziwy adres zostanie \n" +"zastąpiony vhostem." + +#: modules/commands/hs_on.cpp:19 +msgid "Activates your assigned vhost" +msgstr "Aktywuje przypisanego vhosta" + +#: modules/commands/os_info.cpp:243 +msgid "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." +msgstr "" +"Dodaje lub usuwa informacje operatorów dla podanego\n" +"nicka lub kanału. Informacje te będą widoczne dla operatorów\n" +"po użyciu odpowiadających temu nickowi lub kanałowi poleceń info." + +#: modules/commands/os_dns.cpp:515 +#, c-format +msgid "Added IP %s to %s." +msgstr "Dodano IP %s do %s." + +#: modules/commands/os_forbid.cpp:239 +#, c-format +msgid "Added a forbid on %s of type %s to expire on %s." +msgstr "Dodano zakaz na %s typu %s, ważny do %s." + +#: modules/commands/os_info.cpp:164 +#, c-format +msgid "Added info to %s." +msgstr "Dodano informacje dla %s." + +#: modules/commands/os_news.cpp:34 +msgid "Added new logon news item." +msgstr "Dodano nową wiadomość powitalną." + +#: modules/commands/os_news.cpp:44 +msgid "Added new oper news item." +msgstr "Dodano nową wiadomość dla operatorów." + +#: modules/commands/os_news.cpp:54 +msgid "Added new random news item." +msgstr "Dodano nową losową wiadomość." + +#: modules/commands/os_dns.cpp:395 +#, c-format +msgid "Added server %s." +msgstr "Dodano serwer %s." + +#: modules/commands/os_dns.cpp:300 +#, c-format +msgid "Added zone %s." +msgstr "Dodano strefę %s." + +#: modules/commands/cs_entrymsg.cpp:257 +msgid "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." +msgstr "" +"Dodawanie, usuwanie lub czyszczenie wiadomości wejściowych\n" +"wymaga uprawnienia SET." + +#: modules/commands/ns_register.cpp:104 +msgid "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." +msgstr "" +"Dodatkowo, operatorzy serwisów posiadający uprawnienie nickserv/confirm\n" +"mają możliwość wpisania w miejscu kodu nick użytkownika, aby wymusić\n" +"jego potwierdzenie rejestracji." + +#: modules/pseudoclients/botserv.cpp:172 +#, c-format +msgid "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" +msgstr "" +"Dodatkowo, gdy włączone są polecenia \"fantasy\", polecenia\n" +"te mogą być wykonywane po poprzedzeniu polecenia przez jeden\n" +"z następujących znaków: %s" + +#: modules/commands/os_noop.cpp:58 +#, c-format +msgid "All O:lines of %s have been reset." +msgstr "Wszystkie O:linie %s zostały zresetowane." + +#: modules/commands/cs_clone.cpp:71 +#, c-format +msgid "All akick entries from %s have been cloned to %s." +msgstr "Wszystkie wpisy AKICK z %s zostały skopiowane do %s." + +#: modules/commands/help.cpp:57 +#, c-format +msgid "All available commands for %s:" +msgstr "Wszystkie dostępne polecenia dla %s:" + +#: modules/commands/cs_clone.cpp:96 +#, c-format +msgid "All badword entries from %s have been cloned to %s." +msgstr "Wszystkie zabronione słowa z %s zostały skopiowane do %s." + +#: modules/commands/cs_clone.cpp:108 +#, c-format +msgid "All level entries from %s have been cloned into %s." +msgstr "Wszystkie ustawienia poziomów z %s zostały skopiowane do %s." + +#: modules/commands/os_news.cpp:38 +msgid "All logon news items deleted." +msgstr "Wszystkie wiadomości powitalne został skasowane." + +#: modules/commands/ms_del.cpp:115 +#, c-format +msgid "All memos for channel %s have been deleted." +msgstr "Wszystkie wiadomości kanału %s zostały usunięte." + +#: modules/commands/os_mode.cpp:61 +#, c-format +msgid "All modes cleared on %s." +msgstr "Skasowano wszystkie tryby na %s." + +#: modules/commands/ns_register.cpp:260 modules/commands/ns_register.cpp:391 +msgid "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." +msgstr "" +"Wszystkie nowe konta muszą zostać zweryfikowane przez administratora. Poczekaj " +"proszę na potwierdzenie Twojej rejestracji." + +#: modules/commands/ms_del.cpp:119 +msgid "All of your memos have been deleted." +msgstr "Wszystkie Twoje wiadomości zostały usunięte." + +#: modules/commands/os_news.cpp:48 +msgid "All oper news items deleted." +msgstr "Wszystkie wiadomości dla operatorów zostały skasowane." + +#: modules/commands/os_noop.cpp:41 +#, c-format +msgid "All operators from %s have been removed." +msgstr "Wszystkie O:linie %s zostały usunięte." + +#: modules/commands/os_news.cpp:58 +msgid "All random news items deleted." +msgstr "Wszystkie losowe wiadomości zostały skasowane." + +#: modules/commands/cs_clone.cpp:211 +#, c-format +msgid "All settings from %s have been cloned to %s." +msgstr "Wszystkie ustawienia z %s zostały skopiowane do %s." + +#: modules/commands/cs_sync.cpp:41 +#, c-format +msgid "All user modes on %s have been synced." +msgstr "Wszystkie tryby na %s zostały zsynchronizowane." + +#: modules/commands/hs_group.cpp:60 +#, c-format +msgid "All vhosts in the group %s have been set to %s." +msgstr "Wszystkie vhosty w grupie %s zostały zmienione na %s." + +#: modules/commands/hs_group.cpp:58 +#, c-format +msgid "All vhosts in the group %s have been set to %s@%s." +msgstr "Wszystkie vhosty w grupie %s zostały zmienione na %s@%s." + +#: src/access.cpp:40 +msgid "Allowed to (de)halfop him/herself" +msgstr "Uprawniony do ustawiania/kasowania własnego statusu półoperatora (halfop)" + +#: src/access.cpp:39 +msgid "Allowed to (de)halfop users" +msgstr "" +"Uprawniony do ustawiania/kasowania statusu półoperatora (halfop) użytkowników" + +#: src/access.cpp:48 +msgid "Allowed to (de)op him/herself" +msgstr "Uprawniony do ustawiania/kasowania własnego statusu operatora (op)" + +#: src/access.cpp:47 +msgid "Allowed to (de)op users" +msgstr "Uprawniony do ustawiania/kasowania statusu operatora (op) użytkowników" + +#: src/access.cpp:50 +msgid "Allowed to (de)owner him/herself" +msgstr "Uprawniony do ustawiania/kasowania własnego statusu właściciela (owner)" + +#: src/access.cpp:49 +msgid "Allowed to (de)owner users" +msgstr "Uprawniony do ustawiania/kasowania statusu właściciela (owner) użytkowników" + +#: src/access.cpp:52 +msgid "Allowed to (de)protect him/herself" +msgstr "" +"Uprawniony do ustawiania/kasowania własnego statusu administratora/chronionego " +"(protect)" + +#: src/access.cpp:51 +msgid "Allowed to (de)protect users" +msgstr "" +"Uprawniony do ustawiania/kasowania statusu administratora/chronionego (protect) " +"użytkowników" + +#: src/access.cpp:59 +msgid "Allowed to (de)voice him/herself" +msgstr "Uprawniony do ustawiania/kasowania własnego prawa głosu (voice)" + +#: src/access.cpp:58 +msgid "Allowed to (de)voice users" +msgstr "Uprawniony do ustawiania/kasowania prawa głosu (voice) użytkowników" + +#: src/access.cpp:27 +msgid "Allowed to assign/unassign a bot" +msgstr "Uprawniony do przydzielania i zwalniania bota" + +#: src/access.cpp:34 +msgid "Allowed to ban users" +msgstr "Uprawniony do banowania" + +#: src/access.cpp:56 +msgid "Allowed to change channel topics" +msgstr "Uprawniony do zmiany tematu kanału" + +#: src/access.cpp:41 +msgid "Allowed to get full INFO output" +msgstr "Uprawniony do uzyskiwania wszystkich informacji poleceniem INFO" + +#: src/access.cpp:36 +msgid "Allowed to issue commands restricted to channel founders" +msgstr "Uprawniony do używania poleceń dozwolonych tylko dla założycieli" + +#: src/access.cpp:33 +msgid "Allowed to modify channel badwords list" +msgstr "Uprawniony do edycji listy zabronionych słów" + +#: src/access.cpp:24 +msgid "Allowed to modify the access list" +msgstr "Uprawniony do zmieniania listy dostępu" + +#: src/access.cpp:44 +msgid "Allowed to read channel memos" +msgstr "Uprawniony do czytania wiadomości MEMO dla kanału" + +#: src/access.cpp:54 +msgid "Allowed to set channel settings" +msgstr "Uprawniony do zmiany ustawień kanału" + +#: src/access.cpp:57 +msgid "Allowed to unban users" +msgstr "Uprawniony do usuwania banów" + +#: src/access.cpp:37 +msgid "Allowed to use GETKEY command" +msgstr "Uprawniony do użycia GETKEY" + +#: src/access.cpp:53 +msgid "Allowed to use SAY and ACT commands" +msgstr "Uprawniony do użycia SAY i ACT" + +#: src/access.cpp:35 +msgid "Allowed to use fantasy commands" +msgstr "Uprawniony do używania poleceń \"fantasy\"" + +#: src/access.cpp:26 +msgid "Allowed to use the AKICK command" +msgstr "Uprawniony do użycia AKICK" + +#: src/access.cpp:42 +msgid "Allowed to use the INVITE command" +msgstr "Uprawniony do użycia polecenia INVITE" + +#: src/access.cpp:43 +msgid "Allowed to use the KICK command" +msgstr "Uprawniony do użycia KICK" + +#: src/access.cpp:45 +msgid "Allowed to use the MODE command" +msgstr "Uprawniony do użycia MODE" + +#: src/access.cpp:25 +msgid "Allowed to view the access list" +msgstr "Uprawniony do podglądania listy dostępowej" + +#: modules/commands/gl_global.cpp:48 +#, c-format +msgid "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." +msgstr "" +"Pozwala administratorom wysyłać wiadomości do wszystkich\n" +"użytkowników. Wiadomość zostanie wysłana z nicka %s." + +#: modules/commands/os_mode.cpp:133 +msgid "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." +msgstr "" +"Pozwala operatorom serwisów na zmianę flag dla wskazanego\n" +"kanału. Parametry są identyczne jak dla komendy /MODE.\n" +"Alternatywnie, można użyć CLEAR, aby usunąć wszystkie tryby\n" +"kanału. Gdy użyte zostanie CLEAR ALL, usunięte zostaną wszystkie\n" +"tryby, jak również uprawnienia użytkowników." + +#: modules/commands/os_mode.cpp:173 +msgid "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." +msgstr "" +"Pozwala operatorom serwisów na zmianę flag dla wskazanego\n" +"kanału. Parametry są identyczne jak dla komendy /MODE." + +#: modules/commands/bs_bot.cpp:352 +msgid "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." +msgstr "" +"Polecenie pozwala administratorom serwisów na\n" +"tworzenie, modyfikowanie oraz kasowanie botów\n" +"używanych przez użytkowników sieci na kanałach.\n" +"\n" +"BOT ADD dodaje bota o podanym nicku, idencie,\n" +"hoście oraz realname. Bądź ostrożny - poprawność\n" +"parametrów nie jest sprawdzana.\n" +"BOT CHANGE pozwala na zmianę nicka, identa,\n" +"hosta lub realname bota bez jego kasowania.\n" +"BOT DEL usuwa wskazanego bota.\n" +"\n" +"UWAGA: Jeśli stworzony zostanie bot o nicku,\n" +"który jest już zarejestrowany, nick zostanie\n" +"odrejestrowany. Podobnie jeśli nick stworzonego\n" +"bota będzie używany przez innego użytkownika,\n" +"zostanie on wtedy skillowany." + +#: modules/commands/os_oline.cpp:56 +msgid "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." +msgstr "" +"Pozwala Services Operators na nadanie wskazanemu\n" +"użytkownikowi uprawnień irc operatora z określonymi\n" +"flagami. Flagi powinny być poprzedzone znakami \"+\" lub \"-\". \n" +"Aby usunąć wszystkie flagi wystarczy podać \"-\"." + +#: modules/commands/os_ignore.cpp:370 +msgid "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." +msgstr "" +"Pozwala operatorom serwisów na spowodowanie, aby serwisy\n" +"ignorowały wskazany nick lub maskę przez określony czas lub\n" +"do kolejnego restartu. Domyślny format czasu to sekundy. Możesz\n" +"określić inny, podając jednostki: s - sekundy, m - minuty,\n" +"h - godziny, d - dni. Nie jest dopuszczalne łączenie jednostek.\n" +"Aby ustawić trwałe ignorowanie, podaj 0 jako czas.\n" +"Dodawana maska musi być w formacie nick!user@host,\n" +"a wszystko inne zostanie potraktowane jako nick. Znaki * i ? są\n" +"dozwolone.\n" +" \n" +"To ograniczenie nie wpływa na IRC Operatorów." + +#: modules/commands/os_akill.cpp:420 +msgid "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Pozwala operatorom serwisów na zarządzanie listą AKILL.\n" +"Jeśli użytkownik pasujący do maski na liście podłączy się\n" +"do sieci serwisy natychmiast go rozłączą oraz założą K-line\n" +"na jego host.\n" +"\n" +"AKILL ADD dodaje maskę (w formacie user@host lub ip)\n" +"oraz powód (który musi zostać podany) na listę AKILL.\n" +"Podając czas można stosować jednostki: s dla sekund,\n" +"m dla minut, h dla godzin oraz d dla dni.\n" +"Kombinacja tych jednostek nie jest możliwa. Domyślną\n" +"jednostką są dni (+30 oznacza 30 dni). Podanie +0\n" +"oznacza, że wpis nie wygaśnie. Jeśli maska zaczyna się\n" +"znakiem + to podanie czasu jest obowiązkowe (nawet jeśli\n" +"jest identyczny z domyślnym). Domyślny czas wygasania\n" +"można sprawdzić przy pomocy polecenia STATS AKILL." + +#: modules/commands/os_sxline.cpp:436 +msgid "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." +msgstr "" +"Pozwala Operatorom Serwisów manipulować listą SNLINE.\n" +"Jeżeli użytkownik, którego realname pasuje do maski SNLINE\n" +"próbuje się połączyć, serwisy nie pozwolą na stworzenie tej sesji IRC." + +#: modules/commands/os_sxline.cpp:670 +msgid "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." +msgstr "" +"Pozwala Operatorom Serwisów na manipulowanie listą SQLINE.\n" +"Jeżeli użytkownik, którego nick pasuje do maski SQLINE próbuje\n" +"się połączyć, serwisy nie pozwolą na stworzenie tej sesji IRC.\n" +"Jeśli pierwszy znak maski to #, serwisy zabronią używania pasujących\n" +"kanałów. Jeśli maska jest wyrażeniem regularnym, wyrażenie to będzie\n" +"dopasowywane także do kanałów." + +#: modules/commands/os_session.cpp:551 +msgid "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." +msgstr "" +"Pozwala operatorom serwisów na manipulowanie listą hostów,\n" +"które posiadają właściwe dla siebie limity sesji - pozwalając konkretnym\n" +"hostom, takim jak serwery shell, na posiadanie większej niż standardowa\n" +"ilości połączeń z IRC. Gdy host osiągnie swój limit sesji, wszystkie klienty\n" +"próbujące się z niego łączyć zostaną skillowane. Zanim użytkownik\n" +"zostanie rozłączony, otrzyma informację dotyczącą limitu sesji. Treść\n" +"tej informacji jest ustawiana w konfiguracji." + +#: modules/commands/os_session.cpp:270 +msgid "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." +msgstr "" +"Pozwala administratorom serwisów na listowanie sesji.\n" +"\n" +"SESSION LIST listuje hosty z przynajmniej minimum sesjami.\n" +"Minimum musi być większe od 1, aby zapobiec przypadkowemu\n" +"listowaniu dużej liczby pojedynczych hostów.\n" +"SESSION VIEW wyświetla szczegółowe informacje na temat \n" +"podanego hosta - podając aktualny limit oraz ilość sesji.\n" +"Parametr host może zawierać symboli wieloznacznych.\n" +"\n" +"Więcej informacji na temat ograniczania liczby sesji\n" +"znajduje się w pomocy polecenia EXCEPTION." + +#: modules/commands/cs_topic.cpp:193 +msgid "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do not " +"have\n" +"the TOPIC privilege." +msgstr "" +"Pozwala na manipulowanie tematem określonego kanału.\n" +"Polecenie SET zmienia temat kanału na podany,\n" +"lub czyści go gdy nie podano żadnego. Komenda APPEND\n" +"dopisuje podany tekst do istniejącego tematu.\n" +" \n" +"LOCK i UNLOCK służą do włączania i wyłączania\n" +"blokady zmian tematu. Gdy blokada jest włączona, użytkownicy,\n" +"którzy nie posiadają uprawnienia TOPIC, nie będą mogli\n" +"zmienić tematu kanału." + +#: modules/commands/os_kick.cpp:62 +#, c-format +msgid "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" +msgstr "" +"Pozwala administratorom wyrzucić użytkownika z\n" +"dowolnego kanału. Parametry są identyczne jak\n" +"dla komendy /KICK. Do powodu zostaje dołączony\n" +"nick operatora, który wydaje polecenie.\n" +"\n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" + +#: modules/commands/cs_set.cpp:33 +msgid "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" +msgstr "" +"Pozwala właścicielowi kanału na zmianę rożnych\n" +"opcji oraz informacji dotyczących kanału.\n" +"\n" +"Dostępne opcje:" + +#: modules/commands/os_oper.cpp:250 +msgid "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." +msgstr "" +"Pozwala na zmianę i podgląd Operatorów Serwisów.\n" +"Uwaga: operatorzy usunięci tym poleceniem, ale nadal\n" +"znajdujący się w pliku konfiguracyjnym, nie zostaną trwale\n" +"pozbawieni uprawnień." + +#: modules/commands/os_config.cpp:127 +msgid "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" +msgstr "" +"Pozwala na zmianę i sprawdzenie ustawień konfiguracji.\n" +"Ustawienia zmienione tym poleceniem są tymczasowe,\n" +"i nie zostaną zapisane w pliku konfiguracyjnym. Wszelkie\n" +"zmiany zostają utracone przy zamknięciu lub restarcie Anope,\n" +"oraz podczas przeładowania konfiguracji.\n" +"\n" +"Przykład:\n" +" MODIFY nickserv forcemail no" + +#: modules/commands/ns_set.cpp:992 +msgid "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." +msgstr "" +"Pozwala wybrać sposób, w jaki serwisy będą pisać do\n" +"Ciebie. Kiedy opcja MSG jest włączona, serwisy będą\n" +"wysyłać wiadomości prywatne (query), w przeciwnym\n" +"wypadku będą wysyłać powiadomienia (notice)." + +#: modules/commands/ns_set.cpp:966 +#, c-format +msgid "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." +msgstr "" +"Pozwala wybrać sposób, w jaki serwisy będą pisać do\n" +"Ciebie. Kiedy opcja %s jest włączona, serwisy będą\n" +"wysyłać wiadomości prywatne (query), w przeciwnym\n" +"wypadku będą wysyłać powiadomienia (notice)." + +#: modules/commands/ms_ignore.cpp:113 +msgid "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." +msgstr "" +"Użycie polecenia powoduje dopisanie na liście ignorowania Memo, czyli\n" +"uniemożliwienie użytkownikom pasującym do podanej maski lub nicka\n" +"wysyłanie Tobie lub do kanału wiadomości z użyciem serwisu Memo.\n" +"Gdy ktoś obecny na liście ignorowania spróbuje wysłać do Ciebie lub\n" +"na kanał, nie otrzyma informacji, że ignorujesz wiadomości od niego." + +#: modules/commands/os_kill.cpp:48 +msgid "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." +msgstr "" +"Pozwala na skillowanie użytkownika, czyli rozłączenie go z siecią.\n" +"Parametry są takie same, jak przy standardowej komendzie /KILL." + +#: modules/commands/ns_info.cpp:253 +#, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"To polecenie pozwala na ukrycie części informacji, które\n" +"są wyświetlane przez polecenie INFO serwisu %s.\n" +"Pierwszy argument określa ukrywaną informację:\n" +"EMAIL - adres e-mail, USERMASK - ostatnio używany host,\n" +"QUIT - ostatnia wiadomość pożegnalna, STATUS - status\n" +"dostępu do serwisów. Drugi argument określa, czy dana \n" +"informacja będzie pokazywana (OFF), czy ukrywana (ON)." + +#: modules/commands/ns_info.cpp:224 +#, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"To polecenie pozwala na ukrycie części informacji, które\n" +"są wyświetlane przez polecenie INFO serwisu %s.\n" +"Pierwszy argument określa ukrywaną informację:\n" +"EMAIL - adres e-mail, USERMASK - ostatnio używany host,\n" +"QUIT - ostatnia wiadomość pożegnalna, STATUS - status\n" +"dostępu do serwisów. Drugi argument określa, czy dana \n" +"informacja będzie pokazywana (OFF), czy ukrywana (ON)." + +#: modules/commands/bs_info.cpp:118 +#, c-format +msgid "Allows you to see %s information about a channel or a bot" +msgstr "Pokazuje informacje i ustawienia %s dotyczące bota lub kanału" + +#: modules/commands/bs_info.cpp:108 +#, c-format +msgid "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." +msgstr "" +"Wyświetla informacje serwisu %s o wskazanym kanale\n" +"lub bocie. Jeśli parametrem jest nazwa kanału to\n" +"zostaną pokazane informacje dotyczące kanału.\n" +"Jeśli parametrem będzie nick bota to zostaną\n" +"pokazane informacje takie jak: data utworzenia,\n" +"ilość obsługiwanych kanałów itp." + +#: modules/commands/cs_xop.cpp:567 +msgid "" +"Alternative methods of modifying channel access lists are\n" +"available. " +msgstr "" +"Alternatywne sposoby na modyfikację kanałowych list dostępu\n" +"są dostępne. " + +#: modules/commands/hs_request.cpp:191 +msgid "Approve the requested vHost of a user" +msgstr "Akceptuje prośbę o vhost wskazanego użytkownika" + +#: modules/commands/ns_drop.cpp:68 +msgid "As a Services Operator, you may drop any nick." +msgstr "Jako Operator Serwisów, możesz skasować dowolny nick." + +#: modules/commands/bs_assign.cpp:19 +msgid "Assigns a bot to a channel" +msgstr "Przydziela bota na kanał" + +#: modules/commands/bs_assign.cpp:78 +msgid "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." +msgstr "" +"Przydziela bota o wskazanym nicku na kanał.\n" +"W następnej kolejności możesz skonfigurować\n" +"przydzielonego bota według własnych potrzeb." + +#: data/chanserv.example.conf:1197 +msgid "Associate a URL with the channel" +msgstr "Przypisuje URL do kanału" + +#: data/nickserv.example.conf:596 +msgid "Associate a URL with this account" +msgstr "Przypisz URL do tego konta" + +#: data/nickserv.example.conf:595 +msgid "Associate a URL with your account" +msgstr "Przypisuje URL do Twojego konta" + +#: modules/commands/greet.cpp:83 +msgid "Associate a greet message with your nickname" +msgstr "Przypisuje komunikat powitalny do nicka" + +#: data/chanserv.example.conf:1198 +msgid "Associate an E-mail address with the channel" +msgstr "Przypisuje adres e-mail do kanału" + +#: modules/commands/ns_set.cpp:452 +msgid "Associate an E-mail address with your nickname" +msgstr "Przypisuje adres e-mail do nicka" + +#: modules/commands/os_info.cpp:101 +msgid "Associate oper info with a nick or channel" +msgstr "Przypisuje informacje operatora do nicka lub kanału" + +#: modules/commands/ns_set.cpp:558 +msgid "Associates the given E-mail address with the nickname." +msgstr "Przypisuje adres e-mail do nicka." + +#: modules/commands/ns_set.cpp:533 +msgid "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." +msgstr "" +"Przypisuje adres e-mail Twojemu nickowi. Adres\n" +"będzie wyświetlany przy opisie Twojego nicka\n" +"dostępnym przy użyciu komendy INFO\n" +"(można to ukryć)." + +#: modules/commands/ns_set.cpp:1315 +msgid "Auto-op" +msgstr "AUTOOP" + +#: modules/commands/cs_akick.cpp:374 +#, c-format +msgid "Autokick list for %s:" +msgstr "Lista AKICK dla kanału %s:" + +#: src/access.cpp:29 +msgid "Automatic channel operator status upon join" +msgstr "Automatyczne przydzielanie statusu operatora przy wejściu" + +#: src/access.cpp:28 +msgid "Automatic halfop upon join" +msgstr "Automatyczne przydzielanie statusu półoperatora (halfop) przy wejściu" + +#: src/access.cpp:30 +msgid "Automatic owner upon join" +msgstr "Automatyczne przydzielanie statusu właściciela (owner) przy wejściu" + +#: src/access.cpp:31 +msgid "Automatic protect upon join" +msgstr "Automatyczne przydzielanie statusu administratora (protect) przy wejściu" + +#: src/access.cpp:32 +msgid "Automatic voice on join" +msgstr "Automatyczne przydzielanie głosu (voice) przy wejściu" + +#: modules/commands/os_oper.cpp:196 +#, c-format +msgid "Available commands for %s:" +msgstr "Dostępne polecenia dla %s:" + +#: modules/commands/os_oper.cpp:175 +msgid "Available opertypes:" +msgstr "Dostępne typy operatorów:" + +#: modules/commands/os_oper.cpp:218 +#, c-format +msgid "Available privileges for %s:" +msgstr "Uprawnienia dostępne dla %s:" + +#: modules/commands/cs_enforce.cpp:162 +msgid "BANS enforced by " +msgstr "BANY wymuszone przez " + +#: modules/commands/bs_kick.cpp:1121 modules/commands/bs_kick.cpp:1123 +#: modules/commands/bs_kick.cpp:1126 +msgid "Bad words kicker" +msgstr "Kopanie za słowa" + +#: modules/commands/bs_badwords.cpp:252 +#, c-format +msgid "Bad words list for %s:" +msgstr "Lista zabronionych słów dla %s:" + +#: modules/commands/bs_badwords.cpp:364 +msgid "Bad words list is now empty." +msgstr "Lista zakazanych słów została wyczyszczona." + +#: modules/commands/bs_set.cpp:129 +msgid "Ban expiry may not be longer than 1 day." +msgstr "Bany nie mogą przedawnić się później niż po 1 dniu." + +#: modules/commands/cs_ban.cpp:143 modules/commands/cs_ban.cpp:178 +#, c-format +msgid "Ban on %s expires in %s." +msgstr "Ban dla %s przedawni się %s." + +#: modules/commands/cs_info.cpp:60 +msgid "Ban type" +msgstr "Typ bana" + +#: modules/commands/cs_set.cpp:174 +#, c-format +msgid "Ban type for channel %s is now #%d." +msgstr "Rodzajem bana dla kanału %s jest teraz #%d." + +#: modules/commands/cs_ban.cpp:39 +msgid "Bans a given nick or mask on a channel" +msgstr "Banuje wskazaną osobę na kanale" + +#: modules/commands/cs_ban.cpp:230 +msgid "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." +msgstr "" +"Banuje wskazanego użytkownika (nick lub maskę) na kanale.\n" +"Opcjonalnie można podać czas przedawnienia - spowoduje\n" +"to automatyczne usunięcie bana po podanym czasie.\n" +"\n" +"Standardowo ta komenda jest dostępna dla użytkowników\n" +"wpisanych na listę AOP lub posiadających poziom dostępu 5\n" +"lub wyższy. Właściciele kanału mogą podać także maskę." + +#: modules/commands/cs_enforce.cpp:166 +#, c-format +msgid "Bans enforced on %s." +msgstr "Wymuszono bany na %s." + +#: modules/commands/bs_kick.cpp:1131 modules/commands/bs_kick.cpp:1133 +#: modules/commands/bs_kick.cpp:1136 +msgid "Bolds kicker" +msgstr "Kopanie za pogrubienia" + +#: modules/commands/bs_bot.cpp:26 modules/commands/bs_bot.cpp:175 +#, c-format +msgid "Bot %s already exists." +msgstr "Bot %s już istnieje." + +#: include/language.h:119 +#, c-format +msgid "Bot %s does not exist." +msgstr "Bot %s nie istnieje." + +#: modules/commands/bs_assign.cpp:71 modules/commands/bs_assign.cpp:246 +#, c-format +msgid "Bot %s has been assigned to %s." +msgstr "Bot %s został przypisany do %s." + +#: modules/commands/bs_bot.cpp:228 +#, c-format +msgid "Bot %s has been changed to %s!%s@%s (%s)." +msgstr "Bot %s został zmieniony na %s!%s@%s (%s)" + +#: modules/commands/bs_bot.cpp:262 +#, c-format +msgid "Bot %s has been deleted." +msgstr "Bot %s został usunięty." + +#: modules/commands/bs_assign.cpp:63 modules/commands/bs_assign.cpp:241 +#, c-format +msgid "Bot %s is already assigned to channel %s." +msgstr "Bot %s jest już postawiony na %s." + +#: modules/commands/bs_kick.cpp:832 +#, c-format +msgid "Bot will kick ops on channel %s." +msgstr "Bot będzie teraz kopał operatorów na kanale %s." + +#: modules/commands/bs_kick.cpp:897 +#, c-format +msgid "Bot will kick voices on channel %s." +msgstr "Bot będzie kopał voiców na kanale %s." + +#: modules/commands/bs_kick.cpp:824 +#, c-format +msgid "Bot won't kick ops on channel %s." +msgstr "Bot nie będzie kopał operatorów na kanale %s." + +#: modules/commands/bs_kick.cpp:889 +#, c-format +msgid "Bot won't kick voices on channel %s." +msgstr "Bot nie będzie kopał voiców na kanale %s." + +#: modules/commands/bs_bot.cpp:118 +#, c-format +msgid "Bot %s is not changeable." +msgstr "Nie ma możliwości zmiany bota %s." + +#: modules/commands/bs_bot.cpp:254 +#, c-format +msgid "Bot %s is not deletable." +msgstr "Nie ma możliwości usunięcia bota %s." + +#: modules/commands/bs_set.cpp:141 +#, c-format +msgid "Bot bans will automatically expire after %s." +msgstr "Bany ustawione przez bota zostaną usunięte automatycznie po %s." + +#: modules/commands/bs_set.cpp:139 +msgid "Bot bans will no longer automatically expire." +msgstr "Bany zakładane przez bota nie będą już się przedawniały." + +#: modules/commands/bs_bot.cpp:46 modules/commands/bs_bot.cpp:138 +#, c-format +msgid "Bot hosts may only be %d characters long." +msgstr "Host bota może się składać maksymalnie z %d znaków." + +#: modules/commands/bs_bot.cpp:64 modules/commands/bs_bot.cpp:167 +msgid "Bot hosts may only contain valid host characters." +msgstr "Host bota może zawierać tylko prawidłowe znaki." + +#: modules/commands/bs_bot.cpp:40 modules/commands/bs_bot.cpp:132 +#, c-format +msgid "Bot idents may only be %d characters long." +msgstr "Ident bota może się składać maksymalnie z %d znaków." + +#: modules/commands/bs_bot.cpp:58 modules/commands/bs_bot.cpp:161 +msgid "Bot idents may only contain valid ident characters." +msgstr "Ident bota może zawierać tylko prawidłowe znaki." + +#: include/language.h:121 +#, c-format +msgid "Bot is not on channel %s." +msgstr "Bot nie jest obecny na kanale %s." + +#: modules/commands/bs_botlist.cpp:51 +msgid "Bot list:" +msgstr "Lista botów:" + +#: modules/commands/bs_info.cpp:87 +msgid "Bot nick" +msgstr "Nick bota" + +#: modules/commands/bs_bot.cpp:34 modules/commands/bs_bot.cpp:126 +#, c-format +msgid "Bot nicks may only be %d characters long." +msgstr "Nick bota może się składać maksymalnie z %d znaków." + +#: modules/commands/bs_bot.cpp:52 modules/commands/bs_bot.cpp:155 +msgid "Bot nicks may only contain valid nick characters." +msgstr "Nick bota może zawierać tylko prawidłowe znaki." + +#: modules/commands/bs_kick.cpp:225 +#, c-format +msgid "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." +msgstr "" +"Bot będzie teraz kopał za %s, a bana ustawi\n" +"po %d kopnięciach tego samego użytkownika." + +#: modules/commands/bs_kick.cpp:228 +#, c-format +msgid "Bot will now kick for %s." +msgstr "Bot będzie kopał za %s." + +#: modules/commands/bs_kick.cpp:416 +#, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." +msgstr "" +"Bot będzie kopał za CAPSa (duże litery\n" +"muszą stanowić %d znaków %d%% całej wiadomości).\n" +"po %d kopach dla tego samego użytkownika założy bana." + +#: modules/commands/bs_kick.cpp:420 +#, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." +msgstr "" +"Bot będzie kopał za CAPSa (duże litery\n" +"muszą stanowić %d znaków %d%% całej wiadomości)." + +#: modules/commands/bs_kick.cpp:551 +#, c-format +msgid "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." +msgstr "" +"Bot będzie kopał za flood (%d linii w %d sekund),\n" +"po %d kopach dla tego samego użytkownika założy bana." + +#: modules/commands/bs_kick.cpp:554 +#, c-format +msgid "Bot will now kick for flood (%d lines in %d seconds)." +msgstr "" +"Bot będzie kopał za flood\n" +"(%d linii w %d sekund)." + +#: modules/commands/bs_kick.cpp:677 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Bot będzie kopał za powtórzenia\n" +"(użytkowników, którzy napiszą %d raz to samo),\n" +"po %d kopach dla tego samego użytkownika założy bana." + +#: modules/commands/bs_kick.cpp:687 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." +msgstr "" +"Bot będzie kopał za powtórzenia\n" +"(użytkowników, którzy napiszą %d raz to samo)." + +#: modules/commands/bs_kick.cpp:673 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Bot będzie kopał za powtórzenia\n" +"(użytkowników, którzy napiszą %d razy to samo),\n" +"po %d kopach dla tego samego użytkownika założy bana." + +#: modules/commands/bs_kick.cpp:684 +#, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." +msgstr "" +"Bot będzie kopał za powtórzenia\n" +"(użytkowników, którzy napiszą %d razy to samo)." + +#: modules/commands/bs_kick.cpp:239 +#, c-format +msgid "Bot won't kick for %s anymore." +msgstr "Bot nie będzie kopał za %s." + +#: modules/commands/bs_kick.cpp:426 +msgid "Bot won't kick for caps anymore." +msgstr "Bot nie będzie kopał za CAPSa." + +#: modules/commands/bs_kick.cpp:559 +msgid "Bot won't kick for flood anymore." +msgstr "Bot nie będzie kopał za flood." + +#: modules/commands/bs_kick.cpp:694 +msgid "Bot won't kick for repeats anymore." +msgstr "Bot nie będzie kopał za powtórzenia." + +#: modules/commands/os_sxline.cpp:201 modules/commands/os_session.cpp:514 +#: modules/commands/cs_access.cpp:472 +msgid "By" +msgstr "Przez" + +#: modules/commands/os_info.cpp:104 +msgid "CLEAR target" +msgstr "CLEAR cel" + +#: modules/commands/cs_seen.cpp:119 +msgid "CLEAR time" +msgstr "CLEAR czas" + +#: modules/commands/ms_cancel.cpp:19 +msgid "Cancel the last memo you sent" +msgstr "Wycofuje ostatnią wysłaną wiadomość" + +#: modules/commands/cs_drop.cpp:19 +msgid "Cancel the registration of a channel" +msgstr "Usuwa kanał" + +#: modules/commands/ns_drop.cpp:20 +msgid "Cancel the registration of a nickname" +msgstr "Usuwa nicka" + +#: modules/commands/ms_cancel.cpp:84 +msgid "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." +msgstr "" +"Wycofuje ostatnią wysłaną wiadomość,\n" +"o ile nie została przeczytana." + +#: modules/commands/cs_clone.cpp:149 +#, c-format +msgid "Cannot clone channel %s to itself!" +msgstr "Nie można skopiować kanału %s na siebie samego!" + +#: modules/commands/ns_register.cpp:334 +msgid "Cannot send mail now; please retry a little later." +msgstr "Nie mogę wysłać teraz maila. Spróbuj za chwilę." + +#: modules/commands/bs_kick.cpp:1141 modules/commands/bs_kick.cpp:1143 +#: modules/commands/bs_kick.cpp:1146 +msgid "Caps kicker" +msgstr "Kopanie za capsa" + +#: modules/commands/os_shutdown.cpp:34 +msgid "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." +msgstr "" +"Wymusza na serwisach natychmiastowe zakończenie pracy bez\n" +"zapisywania baz. To polecenie powinno być użyte jedynie,\n" +"gdy zachodzi podejrzenie uszkodzenia baz, które serwisy\n" +"przechowują w pamięci. Do normalnego zakończenia pracy\n" +"serwisów należy użyć polecenia SHUTDOWN." + +#: modules/commands/os_reload.cpp:47 +msgid "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." +msgstr "" +"Wymusza ponowne załadowanie pliku konfiguracyjnego.\n" +"Niektóre opcje wciąż wymagają restartu serwisów\n" +"(zmiana nicków serwisów, aktywacja limitów sesji itd.)." + +#: modules/commands/os_shutdown.cpp:62 +msgid "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." +msgstr "Wymusza zapisanie baz, a następnie restartuje serwisy." + +#: modules/commands/os_shutdown.cpp:89 +msgid "Causes Services to save all databases and then shut down." +msgstr "Wymusza zapisanie baz danych, a następnie wyłącza serwisy." + +#: modules/commands/os_update.cpp:34 +msgid "" +"Causes Services to update all database files as soon as you\n" +"send the command." +msgstr "Wymusza natychmiastowy zapis baz danych na dysku." + +#: modules/commands/ns_cert.cpp:246 +#, c-format +msgid "Certificate list for %s:" +msgstr "Lista certyfikatów dla %s:" + +#: modules/commands/cs_set.cpp:528 modules/commands/cs_set.cpp:570 +msgid "ChanServ is required to enable persist on this network." +msgstr "ChanServ jest wymagany, aby włączyć nieusuwalność w tej sieci." + +#: modules/commands/os_mode.cpp:19 +msgid "Change channel modes" +msgstr "Zmienia flagi kanału" + +#: modules/commands/ns_set.cpp:905 +msgid "Change the communication method of Services" +msgstr "Zmienia sposób komunikacji serwisów" + +#: modules/commands/os_mode.cpp:146 +msgid "Change user modes" +msgstr "Zmienia flagi użytkownika" + +#: modules/commands/os_mode.cpp:161 +#, c-format +msgid "Changed usermodes of %s to %s." +msgstr "Zmieniono flagi użytkownika dla %s na %s." + +#: modules/commands/ns_set.cpp:411 +msgid "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." +msgstr "" +"Zmienia nazwę reprezentującą grupę nicków w\n" +"serwisach na nową. Nazwa MUSI być jednym z nicków\n" +"należących do Twojej grupy." + +#: modules/commands/ns_set.cpp:387 +msgid "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." +msgstr "" +"Zmienia nazwę reprezentującą Twoją grupę nicków w\n" +"serwisach na nową. Nazwa MUSI być jednym z nicków\n" +"należących do Twojej grupy." + +#: modules/commands/cs_set.cpp:324 +msgid "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." +msgstr "" +"Zmienia właściciela kanału.\n" +"Nowy nick musi być zarejestrowany." + +#: modules/commands/ns_set.cpp:884 +msgid "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Zmienia język jakiego używają serwisy odpowiadając \n" +"użytkownikowi (czyli przykładowo kiedy odpowiadają na \n" +"wysłaną przez niego komendę). Język może być \n" +"wybrany z poniższej listy obsługiwanych języków:" + +#: modules/commands/ns_set.cpp:848 +msgid "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Zmienia język jakiego używają serwisy odpowiadając \n" +"Tobie (czyli przykładowo kiedy odpowiadają na \n" +"wysłaną przez Ciebie komendę). Język może być \n" +"wybrany z poniższej listy obsługiwanych języków:" + +#: modules/commands/ns_set.cpp:227 +msgid "Changes the password used to identify as the nick's owner." +msgstr "Zmienia hasło do nicka." + +#: modules/commands/ns_set.cpp:161 +msgid "" +"Changes the password used to identify you as the nick's\n" +"owner." +msgstr "Zmienia Twoje hasło do nicka." + +#: modules/commands/cs_set.cpp:1017 +msgid "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." +msgstr "" +"Ustawia spadkobiercę (następcę właściciela) kanału.\n" +"W sytuacji, gdy nick właściciela wygaśnie lub zostanie\n" +"usunięty, a kanał nadal jest zarejestrowany, własność\n" +"tego kanału zostaje przekazana spadkobiercy, czyniąc\n" +"go tym samym nowym właścicielem.\n" +"Podany nick spadkobiercy musi być zarejestrowany.\n" +"Jeśli spadkobierca nie jest ustawiony, pierwszy użytkownik\n" +"z listy dostępu (ten o najwyższych prawach, jeśli taki występuje\n" +"zostanie spadkobiercą z domysłu. Jeżeli zaś w takim\n" +"przypadku lista dostępowa okaże się być pusta, to kanał\n" +"zostanie odrejestrowany." + +#: modules/commands/ns_ajoin.cpp:100 modules/commands/ns_alist.cpp:48 +msgid "Channel" +msgstr "Kanał" + +#: include/language.h:84 +#, c-format +msgid "Channel %s doesn't exist." +msgstr "Kanał %s nie istnieje." + +#: modules/commands/cs_drop.cpp:63 +#, c-format +msgid "Channel %s has been dropped." +msgstr "Kanał %s został odrejestrowany." + +#: modules/commands/cs_getkey.cpp:43 +#, c-format +msgid "Channel %s has no key." +msgstr "Kanał %s nie posiada klucza." + +#: modules/commands/cs_register.cpp:47 +#, c-format +msgid "Channel %s is already registered!" +msgstr "Kanał %s jest już zarejestrowany!" + +#: modules/commands/os_forbid.cpp:524 +#, c-format +msgid "Channel %s is forbidden by %s: %s" +msgstr "Kanał %s został zabroniony przez %s: %s" + +#: modules/commands/os_forbid.cpp:526 +#, c-format +msgid "Channel %s is forbidden." +msgstr "Kanał %s jest zabroniony." + +#: modules/commands/cs_set.cpp:580 +#, c-format +msgid "Channel %s is no longer persistent." +msgstr "Kanał %s nie jest już trwały." + +#: modules/commands/cs_set.cpp:542 +#, c-format +msgid "Channel %s is now persistent." +msgstr "Kanał %s jest teraz trwały." + +#: modules/commands/cs_suspend.cpp:180 +#, c-format +msgid "Channel %s is now released." +msgstr "Kanał %s został uwolniony." + +#: modules/commands/cs_suspend.cpp:125 +#, c-format +msgid "Channel %s is now suspended." +msgstr "Kanał %s został zawieszony." + +#: include/language.h:83 +#, c-format +msgid "Channel %s isn't registered." +msgstr "Kanał %s nie jest zarejestrowany." + +#: modules/commands/cs_suspend.cpp:172 +#, c-format +msgid "Channel %s isn't suspended." +msgstr "Kanał %s nie jest zawieszony." + +#: modules/commands/cs_register.cpp:68 +#, c-format +msgid "Channel %s registered under your account: %s" +msgstr "Kanał %s został zarejestrowany dla Twojego konta: %s" + +#: modules/commands/cs_set.cpp:1078 +#, c-format +msgid "Channel %s will expire." +msgstr "Kanał %s od teraz podlega prawu wygasania." + +#: modules/commands/cs_set.cpp:1072 +#, c-format +msgid "Channel %s will not expire." +msgstr "Kanał %s nie wygaśnie." + +#: modules/commands/cs_xop.cpp:475 +#, c-format +msgid "Channel %s %s list has been cleared." +msgstr "Lista %s kanału %s została wyczyszczona." + +#: modules/commands/cs_flags.cpp:361 modules/commands/cs_access.cpp:486 +#, c-format +msgid "Channel %s access list has been cleared." +msgstr "Lista dostępu kanału %s została wyczyszczona." + +#: modules/commands/cs_akick.cpp:428 +#, c-format +msgid "Channel %s akick list has been cleared." +msgstr "Lista AKICK kanału %s została wyczyszczona." + +#: modules/commands/cs_mode.cpp:444 +#, c-format +msgid "Channel %s has no mode locks." +msgstr "Kanał %s nie posiada blokad trybów." + +#: include/language.h:82 +#, c-format +msgid "Channel %s is currently suspended." +msgstr "Kanał %s został zawieszony." + +#: include/language.h:101 +#, c-format +msgid "Channel %s is not a valid channel." +msgstr "%s nie jest prawidłowym kanałem." + +#: modules/commands/os_list.cpp:70 +msgid "Channel list:" +msgstr "Lista kanałów:" + +#: modules/extra/stats/cs_fantasy_stats.cpp:148 +#, c-format +msgid "Channel stats for %s on %s:" +msgstr "Statystyki kanałowe dla %s na %s:" + +#: modules/commands/cs_xop.cpp:139 modules/commands/cs_flags.cpp:97 +#: modules/commands/cs_access.cpp:142 +msgid "Channels may not be on access lists." +msgstr "Kanały nie mogą znajdować się na listach dostępowych." + +#: modules/commands/ns_alist.cpp:114 +#, c-format +msgid "Channels that %s has access on:" +msgstr "Kanały, na których %s jest na liście dostępu:" + +#: modules/commands/os_stats.cpp:181 +#, c-format +msgid "Channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "Kanały: %lu wpisów, %lu pakietów, najdłuższy łańcuch to %d" + +#: modules/extra/stats/m_chanstats.cpp:517 modules/extra/stats/m_chanstats.cpp:525 +msgid "Chanstats" +msgstr "Statystyki kanałów" + +#: modules/extra/stats/m_chanstats.cpp:102 +#, c-format +msgid "Chanstats statistics are now disabled for %s" +msgstr "Statystyki kanałowe są teraz wyłączone dla %s" + +#: modules/extra/stats/m_chanstats.cpp:51 +msgid "Chanstats statistics are now disabled for this channel." +msgstr "Statystyki tego kanału są teraz wyłączone." + +#: modules/extra/stats/m_chanstats.cpp:104 +msgid "Chanstats statistics are now disabled for your nick." +msgstr "Statystyki kanałowe dla Twojego nicka są teraz wyłączone." + +#: modules/extra/stats/m_chanstats.cpp:93 +#, c-format +msgid "Chanstats statistics are now enabled for %s" +msgstr "Statystyki kanałowe dla %s są teraz włączone" + +#: modules/extra/stats/m_chanstats.cpp:44 +msgid "Chanstats statistics are now enabled for this channel." +msgstr "Statystyki tego kanału są teraz włączone." + +#: modules/extra/stats/m_chanstats.cpp:95 +msgid "Chanstats statistics are now enabled for your nick." +msgstr "Statystyki kanałowe dla Twojego nicka są teraz włączone." + +#: modules/commands/cs_seen.cpp:367 +msgid "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." +msgstr "" +"Sprawdza, kiedy ostatnio nick był widziany, gdy opuszczał kanał,\n" +"dołączał do niego, lub zmieniał nick w sieci, i informuje, kiedy, i (zależnie\n" +"od ustawień kanału i użytkownika), gdzie on był." + +#: modules/commands/ms_check.cpp:19 +msgid "Checks if last memo to a nick was read" +msgstr "Sprawdza, czy ostatnia wiadomość została przeczytana" + +#: modules/commands/ms_check.cpp:69 +msgid "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." +msgstr "" +"Sprawdza, czy ostatnia wiadomość wysłana do nick\n" +"została przeczytana. Ta komenda nie działa dla kanałów." + +#: modules/commands/os_info.cpp:227 +#, c-format +msgid "Cleared info from %s." +msgstr "Usunięto info od %s." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1153 +#: modules/commands/bs_kick.cpp:1156 +msgid "Colors kicker" +msgstr "Kopanie za kolory" + +#: modules/commands/cs_log.cpp:127 +msgid "Command" +msgstr "Polecenie" + +#: modules/commands/bs_kick.cpp:251 +msgid "Configures AMSG kicker" +msgstr "Konfiguruje kopanie za AMSG" + +#: modules/commands/bs_kick.cpp:287 +msgid "Configures badwords kicker" +msgstr "Konfiguruje kopanie za słowa" + +#: modules/commands/bs_kick.cpp:326 +msgid "Configures bolds kicker" +msgstr "Konfiguruje kopanie za pogrubienia" + +#: modules/commands/bs_kick.cpp:132 +msgid "Configures bot kickers. option can be one of:" +msgstr "Konfiguruje kopanie przez bota. opcja może być jedną z następujących:" + +#: modules/commands/bs_set.cpp:19 +msgid "Configures bot options" +msgstr "Konfiguruje bota" + +#: modules/commands/bs_set.cpp:32 +msgid "" +"Configures bot options.\n" +" \n" +"Available options:" +msgstr "" +"Konfiguruje bota.\n" +"Dostępne opcje:" + +#: modules/commands/bs_kick.cpp:360 +msgid "Configures caps kicker" +msgstr "Konfiguruje kopanie za CAPSa" + +#: modules/commands/cs_log.cpp:105 +msgid "Configures channel logging settings" +msgstr "Konfiguruje ustawienia logowania kanałów" + +#: modules/commands/bs_kick.cpp:456 +msgid "Configures color kicker" +msgstr "Konfiguruje kopanie za kolory" + +#: modules/commands/bs_kick.cpp:490 +msgid "Configures flood kicker" +msgstr "Konfiguruje kopanie za flood" + +#: modules/commands/bs_kick.cpp:588 +msgid "Configures italics kicker" +msgstr "Konfiguruje kopanie za tekst pochylony" + +#: modules/commands/bs_kick.cpp:119 +msgid "Configures kickers" +msgstr "Konfiguruje opcje kopania" + +#: modules/commands/bs_kick.cpp:622 +msgid "Configures repeat kicker" +msgstr "Konfiguruje kopanie za powtórzenia" + +#: modules/commands/bs_kick.cpp:723 +msgid "Configures reverses kicker" +msgstr "Konfiguruje kopanie za odwrócenie kolorów" + +#: modules/commands/bs_set.cpp:90 +msgid "Configures the time bot bans expire in" +msgstr "Konfiguruje czas, po którym bany ustawione przez bota przedawnią się" + +#: modules/commands/bs_kick.cpp:757 +msgid "Configures underlines kicker" +msgstr "Konfiguruje kopanie za podkreślenia" + +#: modules/commands/ns_register.cpp:21 +msgid "Confirm a passcode" +msgstr "Potwierdza rejestrację nicka" + +#: modules/commands/cs_mode.cpp:733 +msgid "Control modes and mode locks on a channel" +msgstr "Kontroluje tryby i blokady trybów na kanale" + +#: modules/commands/cs_entrymsg.cpp:239 +msgid "Controls what messages will be sent to users when they join the channel." +msgstr "" +"Kontroluje, jakie wiadomości będą wysyłane do użytkowników\n" +"podczas ich dołączania do kanału." + +#: modules/commands/cs_clone.cpp:242 +msgid "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." +msgstr "" +"Kopiuje wszystkie ustawienia, listy dostępu, AKICK itp z kanału na\n" +"kanał docelowy. Jeśli jako \"co\" podano ACCESS, AKICK, BADWORDS,\n" +"lub LEVELS, wtedy tylko żądana nastawa zostanie skopiowana.\n" +"Musisz posiadać status właściciela kanału i celu." + +#: modules/commands/cs_clone.cpp:114 +msgid "Copy all settings from one channel to another" +msgstr "Kopiuje wszystkie ustawienia z jednego kanału na inny" + +#: modules/commands/os_sxline.cpp:201 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_news.cpp:156 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:358 modules/commands/hs_request.cpp:305 +#: modules/commands/hs_list.cpp:58 modules/commands/cs_akick.cpp:405 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_flags.cpp:301 +#: modules/commands/bs_info.cpp:57 +msgid "Created" +msgstr "Utworzony" + +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/os_news.cpp:156 +#: modules/commands/os_akill.cpp:358 modules/commands/os_forbid.cpp:358 +#: modules/commands/hs_list.cpp:58 modules/commands/os_ignore.cpp:266 +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_mode.cpp:449 +#: modules/commands/cs_flags.cpp:301 +msgid "Creator" +msgstr "Utworzony przez" + +#: modules/commands/os_sxline.cpp:180 +#, c-format +msgid "Current %s list:" +msgstr "Aktualna lista %s:" + +#: modules/commands/os_akill.cpp:323 +msgid "Current AKILL list:" +msgstr "Aktualna lista AKILL:" + +#: modules/commands/os_session.cpp:493 +msgid "Current Session Limit Exception list:" +msgstr "Aktualna lista wyjątków limitów sesji:" + +#: modules/commands/os_modinfo.cpp:116 +msgid "Current module list:" +msgstr "Aktualna lista modułów:" + +#: modules/commands/os_stats.cpp:69 +#, c-format +msgid "Current number of AKILLs: %d" +msgstr "Aktualna ilość wpisów AKILL: %d" + +#: modules/commands/os_stats.cpp:89 +#, c-format +msgid "Current number of SNLINEs: %d" +msgstr "Aktualna ilość wpisów SNLINE: %d" + +#: modules/commands/os_stats.cpp:109 +#, c-format +msgid "Current number of SQLINEs: %d" +msgstr "Aktualna ilość wpisów SQLINE: %d" + +#: modules/commands/os_stats.cpp:138 +#, c-format +msgid "Current users: %d (%d ops)" +msgstr "Użytkowników : %d (%d operatorów)" + +#: modules/commands/os_oper.cpp:71 +msgid "DEL oper" +msgstr "DEL oper" + +#: modules/commands/os_info.cpp:103 +msgid "DEL target info" +msgstr "DEL cel info" + +#: modules/commands/ns_ajoin.cpp:232 +msgid "DEL [nickname] channel" +msgstr "DEL [nick] kanał" + +#: modules/commands/ns_cert.cpp:259 +msgid "DEL [nickname] fingerprint" +msgstr "DEL [nick] odcisk-palca" + +#: modules/commands/ns_access.cpp:103 +msgid "DEL [nickname] mask" +msgstr "DEL [nick] maska" + +#: modules/commands/os_sxline.cpp:426 modules/commands/os_sxline.cpp:660 +#: modules/commands/os_akill.cpp:387 +msgid "DEL {mask | entry-num | list | id}" +msgstr "DEL {maska | numer-wpisu | lista | id}" + +#: modules/commands/os_session.cpp:524 +msgid "DEL {mask | entry-num | list}" +msgstr "DEL {maska | numer-wpisu | lista}" + +#: modules/commands/os_ignore.cpp:343 +msgid "DEL {nick|mask}" +msgstr "DEL {nick|maska}" + +#: modules/commands/os_news.cpp:279 +msgid "DEL {num | ALL}" +msgstr "DEL {numer | ALL}" + +#: modules/commands/os_forbid.cpp:158 +msgid "DEL {NICK|CHAN|EMAIL|REGISTER} entry" +msgstr "DEL {NICK|CHAN|EMAIL|REGISTER} wpis" + +#: modules/commands/os_dns.cpp:666 +msgid "DELIP server.name ip" +msgstr "DELIP nazwa.serwera ip" + +#: modules/commands/os_dns.cpp:664 +msgid "DELSERVER server.name [zone.name]" +msgstr "DELSERVER nazwa.serwera [nazwa.strefy]" + +#: modules/commands/os_dns.cpp:662 +msgid "DELZONE zone.name" +msgstr "DELZONE nazwa.strefy" + +#: modules/commands/os_dns.cpp:669 +msgid "DEPOOL server.name" +msgstr "DEPOOL nazwa.serwera" + +#: modules/commands/cs_seen.cpp:162 +#, c-format +msgid "Database cleared, removed %lu nicks that were added after %s." +msgstr "Baza danych wyczyszczona. Usunięto %lu nicków dodanych po %s." + +#: modules/commands/ms_list.cpp:64 +msgid "Date/Time" +msgstr "Data/Czas" + +#: modules/commands/hs_off.cpp:49 +msgid "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." +msgstr "" +"Deaktywuje vhosta aktualnie przypisanego do używanego nicka.\n" +"Po użyciu tego polecenia każdy będzie mógł sprawdzić Twój\n" +"prawdziwy adres używając polecenia /WHOIS." + +#: modules/commands/hs_off.cpp:19 +msgid "Deactivates your assigned vhost" +msgstr "Deaktywuje przypisanego vhosta" + +#: modules/commands/os_stats.cpp:72 +#, c-format +msgid "Default AKILL expiry time: %d days" +msgstr "Domyślny czas wygasania AKILL: %d dni" + +#: modules/commands/os_stats.cpp:76 +#, c-format +msgid "Default AKILL expiry time: %d hours" +msgstr "Domyślny czas wygasania AKILL: %d godzin(y)" + +#: modules/commands/os_stats.cpp:80 +#, c-format +msgid "Default AKILL expiry time: %d minutes" +msgstr "Domyślny czas wygasania AKILL: %d minut(y)" + +#: modules/commands/os_stats.cpp:74 +msgid "Default AKILL expiry time: 1 day" +msgstr "Domyślny czas wygasania AKILL: 1 dzień" + +#: modules/commands/os_stats.cpp:78 +msgid "Default AKILL expiry time: 1 hour" +msgstr "Domyślny czas wygasania AKILL: 1 godzina" + +#: modules/commands/os_stats.cpp:82 +msgid "Default AKILL expiry time: 1 minute" +msgstr "Domyślny czas wygasania AKILL: 1 minuta" + +#: modules/commands/os_stats.cpp:84 +msgid "Default AKILL expiry time: No expiration" +msgstr "Domyślny czas wygasania AKILL: nie wygasa" + +#: modules/commands/os_stats.cpp:92 +#, c-format +msgid "Default SNLINE expiry time: %d days" +msgstr "Domyślny czas wygasania SNLINE: %d dni" + +#: modules/commands/os_stats.cpp:96 +#, c-format +msgid "Default SNLINE expiry time: %d hours" +msgstr "Domyślny czas wygasania SNLINE: %d godzin(y)" + +#: modules/commands/os_stats.cpp:100 +#, c-format +msgid "Default SNLINE expiry time: %d minutes" +msgstr "Domyślny czas wygasania SNLINE: %d minut(y)" + +#: modules/commands/os_stats.cpp:94 +msgid "Default SNLINE expiry time: 1 day" +msgstr "Domyślny czas wygasania SNLINE: 1 dzień" + +#: modules/commands/os_stats.cpp:98 +msgid "Default SNLINE expiry time: 1 hour" +msgstr "Domyślny czas wygasania SNLINE: 1 godzina" + +#: modules/commands/os_stats.cpp:102 +msgid "Default SNLINE expiry time: 1 minute" +msgstr "Domyślny czas wygasania SNLINE: 1 minuta" + +#: modules/commands/os_stats.cpp:104 +msgid "Default SNLINE expiry time: No expiration" +msgstr "Domyślny czas wygasania SNLINE: nie wygasa" + +#: modules/commands/os_stats.cpp:112 +#, c-format +msgid "Default SQLINE expiry time: %d days" +msgstr "Domyślny czas wygasania SQLINE: %d dni" + +#: modules/commands/os_stats.cpp:116 +#, c-format +msgid "Default SQLINE expiry time: %d hours" +msgstr "Domyślny czas wygasania SQLINE: %d godzin(y)" + +#: modules/commands/os_stats.cpp:120 +#, c-format +msgid "Default SQLINE expiry time: %d minutes" +msgstr "Domyślny czas wygasania SQLINE: %d minut(y)" + +#: modules/commands/os_stats.cpp:114 +msgid "Default SQLINE expiry time: 1 day" +msgstr "Domyślny czas wygasania SQLINE: 1 dzień" + +#: modules/commands/os_stats.cpp:118 +msgid "Default SQLINE expiry time: 1 hour" +msgstr "Domyślny czas wygasania SQLINE: 1 godzina" + +#: modules/commands/os_stats.cpp:122 +msgid "Default SQLINE expiry time: 1 minute" +msgstr "Domyślny czas wygasania SQLINE: 1 minuta" + +#: modules/commands/os_stats.cpp:124 +msgid "Default SQLINE expiry time: No expiration" +msgstr "Domyślny czas wygasania SQLINE: nie wygasa" + +#: modules/commands/os_news.cpp:351 +msgid "Define messages to be randomly shown to users at logon" +msgstr "Zarządza losowymi wiadomościami powitalnymi" + +#: modules/commands/os_news.cpp:297 +msgid "Define messages to be shown to users at logon" +msgstr "Zarządza wiadomościami powitalnymi" + +#: modules/commands/os_news.cpp:324 +msgid "Define messages to be shown to users who oper" +msgstr "Zarządza wiadomościami dla operatorów" + +#: modules/commands/ms_del.cpp:44 +msgid "Delete a memo or memos" +msgstr "Kasuje jedną lub więcej wiadomości" + +#: modules/commands/hs_del.cpp:19 +msgid "Delete the vhost of another user" +msgstr "Usuwa vhost wskazanego użytkownika" + +#: modules/commands/cs_xop.cpp:302 +#, c-format +msgid "Deleted %d entries from %s %s list." +msgstr "Usunięto %d wpisów(y) z listy %s kanału %s." + +#: modules/commands/cs_access.cpp:277 +#, c-format +msgid "Deleted %d entries from %s access list." +msgstr "Usunięto %d wpisów(y) z listy dostępu kanału %s." + +#: modules/commands/cs_akick.cpp:228 +#, c-format +msgid "Deleted %d entries from %s autokick list." +msgstr "Usunięto %d wpisów z listy AKICK kanału %s." + +#: modules/commands/bs_badwords.cpp:170 +#, c-format +msgid "Deleted %d entries from %s bad words list." +msgstr "" +"Usunięto %d wpisów z listy zakazanych słów\n" +"kanału %s." + +#: modules/commands/os_session.cpp:149 +#, c-format +msgid "Deleted %d entries from session-limit exception list." +msgstr "Usunięto %d wpisy(ów) z listy wyjątków limitów sesji." + +#: modules/commands/os_sxline.cpp:32 +#, c-format +msgid "Deleted %d entries from the %s list." +msgstr "Usunięto %d wpisów(y) z listy %s." + +#: modules/commands/os_akill.cpp:33 +#, c-format +msgid "Deleted %d entries from the AKILL list." +msgstr "Usunięto %d wpisy(ów) z listy AKILL." + +#: modules/commands/cs_access.cpp:275 +#, c-format +msgid "Deleted 1 entry from %s access list." +msgstr "Usunięto 1 wpis z listy dostępu kanału %s." + +#: modules/commands/cs_akick.cpp:226 +#, c-format +msgid "Deleted 1 entry from %s autokick list." +msgstr "Usunięto 1 wpis z listy AKICK kanału %s." + +#: modules/commands/bs_badwords.cpp:168 +#, c-format +msgid "Deleted 1 entry from %s bad words list." +msgstr "Usunięto 1 wpis z listy zakazanych słów kanału %s." + +#: modules/commands/os_session.cpp:147 +msgid "Deleted 1 entry from session-limit exception list." +msgstr "Usunięto 1 wpis z listy wyjątków limitów sesji." + +#: modules/commands/os_sxline.cpp:30 +#, c-format +msgid "Deleted 1 entry from the %s list." +msgstr "Usunięto 1 wpis z listy %s." + +#: modules/commands/os_akill.cpp:31 +msgid "Deleted 1 entry from the AKILL list." +msgstr "Usunięto 1 wpis z listy AKILL." + +#: modules/commands/os_info.cpp:208 +#, c-format +msgid "Deleted info from %s." +msgstr "Usunięto informacje dla %s." + +#: modules/commands/cs_xop.cpp:300 +#, c-format +msgid "Deleted one entry from %s %s list." +msgstr "Usunięto 1 wpis z listy %s kanału %s." + +#: modules/commands/ms_del.cpp:129 +msgid "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Kasuje jedną lub więcej wiadomości. Dopuszczalne \n" +"jest podanie numeru wiadomości lub listy wiadomości, \n" +"przykład poniżej.\n" +"\n" +"Parametr LAST oznacza skasowanie ostatniej wiadomości.\n" +"Parametr ALL oznacza skasowanie wszystkich wiadomości.\n" +"\n" +"Przykłady:\n" +"\n" +" DEL 1\n" +" Usuwa pierwszą wiadomość.\n" +"\n" +" DEL 2-5,7-9\n" +" Kasuje wiadomości od numeru 2 do 5 oraz od 7 do 9." + +#: modules/commands/hs_del.cpp:48 +msgid "" +"Deletes the vhost assigned to the given nick from the\n" +"database." +msgstr "Usuwa vhosta przypisanego do wskazanego nicka." + +#: modules/commands/hs_del.cpp:59 +msgid "Deletes the vhost for all nicks in a group" +msgstr "Usuwa vhosty wszystkich nicków w grupie" + +#: modules/commands/hs_del.cpp:93 +msgid "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." +msgstr "Usuwa wszystkie vhosty grupy, do której należy wskazany nick." + +#: modules/commands/os_dns.cpp:653 +#, c-format +msgid "Depooled %s." +msgstr "%s usunięty z puli." + +#: modules/commands/ns_alist.cpp:48 modules/commands/cs_access.cpp:799 +#: modules/commands/cs_list.cpp:75 modules/commands/cs_info.cpp:53 +msgid "Description" +msgstr "Opis" + +#: modules/commands/cs_set.cpp:239 +#, c-format +msgid "Description of %s changed to %s." +msgstr "Opis kanału %s został zmieniony na %s." + +#: modules/commands/cs_set.cpp:245 +#, c-format +msgid "Description of %s unset." +msgstr "Opis %s został skasowany." + +#: modules/commands/bs_kick.cpp:1115 modules/commands/bs_info.cpp:90 +msgid "Disabled" +msgstr "Wyłączone" + +#: modules/commands/cs_suspend.cpp:134 +msgid "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." +msgstr "" +"Zawiesza działanie wskazanego kanału.\n" +"Blokada może zostać zdjęta z zachowaniem\n" +"wszelkich ustawień komendą UNSUSPEND.\n" +"Jeśli podano czas przedawnienia, kanał zostanie\n" +"odblokowany po upływie podanego czasu, w przeciwnym\n" +"razie użyty zostanie czas podany w pliku konfiguracyjnym.\n" +"\n" +"W niektórych sieciach wymagane jest podanie powodu." + +#: modules/commands/hs_request.cpp:337 +#, c-format +msgid "Displayed %d records (%d total)." +msgstr "Wyświetlono %d wpisów (razem %d)" + +#: modules/commands/hs_list.cpp:122 +#, c-format +msgid "Displayed all records (count: %d)." +msgstr "Wyświetlono wszystkie wpisy (Liczba: %d)" + +#: modules/commands/hs_list.cpp:120 +#, c-format +msgid "Displayed records from %d to %d." +msgstr "Wyświetlono wpisy od %d do %d." + +#: modules/commands/hs_list.cpp:116 +#, c-format +msgid "Displayed records matching key %s (count: %d)." +msgstr "Wyświetlono pasujące wpisy %s (Liczba: %d)" + +#: modules/commands/ns_info.cpp:19 +msgid "Displays information about a given nickname" +msgstr "Pokazuje informacje o zarejestrowanym nicku" + +#: modules/commands/ns_info.cpp:126 +msgid "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." +msgstr "" +"Wyświetla informacje na temat wybranego nicka:\n" +"właściciel, kiedy ostatnio widziano, z jakiego \n" +"hosta oraz opcje nicka. Jeśli zidentyfikowany \n" +"użytkownik użyje tej komendy na sobie, otrzyma\n" +"wszystkie możliwe informacje - nawet jeśli zostały one ukryte." + +#: modules/commands/ms_info.cpp:19 +msgid "Displays information about your memos" +msgstr "Wyświetla informacje o wiadomościach" + +#: modules/commands/hs_list.cpp:19 +msgid "Displays one or more vhost entries" +msgstr "Listuje vhosty" + +#: modules/extra/stats/cs_fantasy_top.cpp:50 +msgid "Displays the top 10 users of a channel" +msgstr "Wyświetla Top10 użytkowników na kanale" + +#: modules/extra/stats/cs_fantasy_top.cpp:73 +msgid "Displays the top 10 users of the network" +msgstr "Wyświetla Top10 użytkowników sieci" + +#: modules/extra/stats/cs_fantasy_top.cpp:38 +msgid "Displays the top 3 users of a channel" +msgstr "Wyświetla trzech użytkowników, którzy są najwyżej w rankingu kanału" + +#: modules/extra/stats/cs_fantasy_top.cpp:62 +msgid "Displays the top 3 users of the network" +msgstr "Wyświetla trzech najwyżej notowanych użytkowników sieci" + +#: modules/commands/help.cpp:33 +msgid "Displays this list and give information about commands" +msgstr "Wyświetla tę listę i podaje informacje o poleceniach" + +#: modules/extra/stats/cs_fantasy_stats.cpp:39 +msgid "Displays your Channel Stats" +msgstr "Wyświetla twoje statystyki kanałowe" + +#: modules/extra/stats/cs_fantasy_stats.cpp:51 +msgid "Displays your Global Stats" +msgstr "Wyświetla twoje statystyki globalne" + +#: modules/commands/bs_kick.cpp:1463 +msgid "Don't use AMSGs!" +msgstr "Nie używaj AMSG!" + +#: modules/commands/bs_kick.cpp:1266 +msgid "Don't use bolds on this channel!" +msgstr "Nie pogrubiaj tekstu na tym kanale!" + +#: modules/commands/bs_kick.cpp:1274 +msgid "Don't use colors on this channel!" +msgstr "Nie używaj kolorów na tym kanale!" + +#: modules/commands/bs_kick.cpp:1290 +msgid "Don't use italics on this channel!" +msgstr "Nie używaj pochylonego tekstu na tym kanale!" + +#: modules/commands/bs_kick.cpp:1282 +msgid "Don't use reverses on this channel!" +msgstr "Nie używaj odwracania kolorów!" + +#: modules/commands/bs_kick.cpp:1408 +#, c-format +msgid "Don't use the word \"%s\" on this channel!" +msgstr "Nie używaj słowa \"%s\" na tym kanale!" + +#: modules/commands/bs_kick.cpp:1298 +msgid "Don't use underlines on this channel!" +msgstr "Nie używaj podkreśleń na tym kanale!" + +#: modules/commands/ns_drop.cpp:61 +msgid "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." +msgstr "" +"Usuwa podany nick z bazy danych. Po usunięciu Twojego nicka\n" +"stracisz dostęp na wszystkich kanałach, łącznie z tymi, których\n" +"jesteś właścicielem. Dowolny inny użytkownik będzie mógł uzyskać\n" +"dostęp do tego nicka." + +#: modules/commands/ns_set.cpp:513 +#, c-format +msgid "E-mail address for %s changed to %s." +msgstr "Adres e-mail osoby %s został zmieniony na %s." + +#: modules/commands/ns_set.cpp:519 +#, c-format +msgid "E-mail address for %s unset." +msgstr "Adres e-mail osoby %s został usunięty." + +#: src/mail.cpp:80 +#, c-format +msgid "E-mail for %s is invalid." +msgstr "Adres e-mail dla %s nie jest prawidłowy." + +#: modules/commands/os_news.cpp:309 +#, c-format +msgid "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Edytuje lub wyświetla listę wiadomości wysyłanych po\n" +"przyłączeniu użytkownika do sieci. Jeśli zdefniowanych\n" +"wiadomości jest więcej tylko najnowsze %d zostanie\n" +"wysłanych (aby zapobiec floodowaniu)." + +#: modules/commands/os_news.cpp:336 +#, c-format +msgid "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Edytuje lub wyświetla listę wiadomości wysyłanych po\n" +"wykonaniu polecenia /OPER. Jeśli zdefiniowanych\n" +"wiadomości jest więcej tylko najnowsze %d zostanie\n" +"wysłanych (aby zapobiec floodowaniu)." + +#: modules/commands/os_news.cpp:363 +msgid "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." +msgstr "" +"Edytuje lub wyświetla listę losowych newsów.\n" +"Po połączeniu z siecią użytkownik otrzyma dokładnie\n" +"jedną wylosowaną z tej listy wiadomość." + +#: modules/commands/ns_info.cpp:99 +msgid "Email address" +msgstr "Adres e-mail" + +#: modules/commands/ns_getemail.cpp:41 +#, c-format +msgid "Email matched: %s (%s) to %s." +msgstr "Adresy e-mail: %s (%s) pasują do %s." + +#: modules/fantasy.cpp:19 +msgid "Enable fantaisist commands" +msgstr "Włącz polecenia kanałowe" + +#: modules/commands/greet.cpp:19 +msgid "Enable greet messages" +msgstr "Włącz wiadomości powitalne" + +#: modules/commands/ns_set.cpp:568 +msgid "Enable or disable keep modes" +msgstr "Włącza lub wyłącza przywracanie flag" + +#: modules/commands/bs_kick.cpp:1114 modules/commands/bs_info.cpp:89 +msgid "Enabled" +msgstr "Włączone" + +#: modules/commands/cs_set.cpp:124 +#, c-format +msgid "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." +msgstr "" +"Włącza lub wyłącza opcję kanału autoop w %s dla kanału.\n" +"Kiedy ta opcja jest włączona, użytkownicy wchodzący na kanał\n" +"nie dostaną automatycznie żadnych uprawnień od %s." + +#: modules/commands/cs_set.cpp:388 +msgid "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." +msgstr "" +"Włącza lub wyłącza opcję zapamiętywania flag.\n" +"Kiedy ta opcja jest włączona, serwisy zapiszą tryby ustawione\n" +"na kanale, i spróbują ustawić je ponownie przy jego ponownym\n" +"stworzeniu." + +#: modules/commands/ns_set.cpp:643 +msgid "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." +msgstr "" +"Włącza lub wyłącza zapamiętywanie trybów dla podanego nicka.\n" +"Gdy zapamiętywanie jest włączone, serwisy zapiszą flagi użytkownika,\n" +"i podejmą próbę ich przywrócenia przy ponownym zalogowaniu." + +#: modules/commands/ns_set.cpp:618 +msgid "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." +msgstr "" +"Włącza lub wyłącza zapamiętywanie trybów dla Twojego nicka.\n" +"Gdy zapamiętywanie jest włączone, serwisy zapiszą flagi użytkownika,\n" +"i podejmą próbę ich przywrócenia przy ponownym zalogowaniu." + +#: modules/commands/cs_set.cpp:733 +msgid "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." +msgstr "" +"Włącza lub wyłącza opcje bezpieczeństwa kanału.\n" +"Po włączeniu opcji SECURE tylko zarejestrowani\n" +"użytkownicy, którzy się zidentyfikowali, będą\n" +"otrzymywać od serwisu uprawnienia wynikające\n" +"z wpisów na liście dostępu." + +#: modules/commands/cs_set.cpp:932 +msgid "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." +msgstr "" +"Włącza lub wyłącza podpisywanie komend kick.\n" +"Włączenie tej opcji powoduje dodawanie nicka osoby \n" +"wydającej polecenie do uzasadnienia kicka.\n" +"\n" +"Jeśli poziomy dostępu były konfigurowane z użyciem LEVEL\n" +"osoby mające poziom większy lub równy SIGNKICK nie będą\n" +"podpisywane." + +#: modules/commands/cs_set.cpp:452 +#, c-format +msgid "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." +msgstr "" +"Włącza lub wyłącza opcję PEACE dla kanału.\n" +"Włączenie tej opcji uniemożliwia wykopanie,\n" +"banowanie lub odebranie uprawnień użytkownikowi,\n" +"który ma poziom uprawnień wyższy lub równy,\n" +"korzystając z poleceń serwisu %s." + +#: modules/commands/cs_list.cpp:232 +msgid "Enables or disables the private option for a channel." +msgstr "Włącza lub wyłącza tryb prywatny kanału." + +#: modules/commands/cs_set.cpp:671 +msgid "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." +msgstr "" +"Włącza lub wyłącza opcję ograniczonego dostępu do kanału.\n" +"Po włączeniu tej opcji tylko osoby znajdujące się na\n" +"liście dostępu będą mogły przebywać na kanale. Pozostali\n" +"użytkownicy będą banowani, a następnie usuwani z kanału." + +#: modules/commands/cs_set.cpp:796 +msgid "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." +msgstr "" +"Włącza lub wyłącza opcję bezpiecznego właściciela.\n" +"Ustawienie tej opcji powoduje ograniczenie uprawnień\n" +"właściciela do osoby, która jest wpisana jako właściciel,\n" +"uniemożliwiając to tym umieszczonym na liście dostępowej\n" +"czy QOP.\n" +"Operacje takie jak usunięcie kanału, zmiana hasła,\n" +"właściciela oraz zastępcy będą dostępne tylko\n" +"dla jednego użytkownika." + +#: modules/commands/cs_set.cpp:860 +msgid "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." +msgstr "" +"Włącza lub wyłącza opcję SECUREOPS dla kanału.\n" +"Kiedy ta opcja jest włączona użytkownicy bez wpisu\n" +"na liście dostępu kanału (ACCESS LIST) nie będą\n" +"mogli posiadać statusu operatora." + +#: modules/commands/cs_topic.cpp:70 +#, c-format +msgid "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." +msgstr "" +"Włącza lub wyłącza opcję zapamiętywania tematu.\n" +"Kiedy opcja %s jest włączona, %s ustawi ostatni\n" +"temat za każdym razem, gdy na kanał będzie wchodzić\n" +"pierwsza osoba." + +#: modules/commands/cs_set.cpp:592 +#, c-format +msgid "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." +msgstr "" +"Włącza lub wyłącza tryb \"wiecznych\" kanałów.\n" +"Gdy włączony, bot serwisowy pozostanie na kanale\n" +"gdy nie będzie na nim żadnych użytkowników.\n" +" \n" +"Jeżeli twój IRCd nie posiada trybu kanału wiecznego,\n" +"podany kanał musi mieć przypisanego bota przed\n" +"włączeniem PERSIST, i nie można usunąć tego\n" +"przypisania, dopóki PERSIST jest włączony.\n" +" \n" +"Jeśli ta sieć nie ma włączonego %s, i nie posiada\n" +"trybu wiecznych kanałów, %s wejdzie na Twój kanał\n" +"gdy włączysz PERSIST (i wyjdzie po wyłączeniu tej opcji).\n" +" \n" +"Gdy Twój IRCd posiada tryb wiecznego kanału, i zostanie\n" +"on ustawiony lub zdjęty (z dowolnego powodu, wliczając\n" +"MLOCK), opcja PERSIST będzie jednocześnie automatycznie\n" +"włączana i wyłączana. Dodatkowo, serwisy zmienią ten tryb\n" +"gdy opcja zostanie przełączona ręcznie." + +#: modules/commands/os_akill.cpp:331 +msgid "End of AKILL list." +msgstr "Koniec listy AKILL." + +#: modules/commands/cs_access.cpp:444 +msgid "End of access list" +msgstr "Koniec listy dostępu" + +#: modules/commands/cs_flags.cpp:347 +#, c-format +msgid "End of access list - %d/%d entries shown." +msgstr "Koniec listy - %d/%d wpisów wyświetlono." + +#: modules/commands/cs_flags.cpp:345 +msgid "End of access list." +msgstr "Koniec listy dostępu." + +#: modules/commands/cs_akick.cpp:379 +msgid "End of autokick list" +msgstr "Koniec listy AutoKick" + +#: modules/commands/bs_badwords.cpp:257 +msgid "End of bad words list." +msgstr "Koniec listy zabronionych słów." + +#: modules/commands/os_list.cpp:100 +#, c-format +msgid "End of channel list. %u channels shown." +msgstr "Koniec listy - %u kanałów wyświetlono." + +#: modules/commands/os_config.cpp:117 +msgid "End of configuration." +msgstr "Koniec konfiguracji." + +#: modules/commands/cs_entrymsg.cpp:134 +msgid "End of entry message list." +msgstr "Koniec listy wiadomości powitalnych." + +#: modules/commands/os_forbid.cpp:407 +#, c-format +msgid "End of forbid list - %d/%d entries shown." +msgstr "Koniec listy zakazów - %d/%d wpisów wyświetlono." + +#: modules/commands/os_forbid.cpp:405 +msgid "End of forbid list." +msgstr "Koniec listy zakazów." + +#: modules/commands/ns_alist.cpp:119 +#, c-format +msgid "End of list - %d channels shown." +msgstr "Koniec listy - %d kanałów wyświetlono." + +#: modules/commands/ns_list.cpp:131 modules/commands/cs_list.cpp:130 +#, c-format +msgid "End of list - %d/%d matches shown." +msgstr "Koniec listy - %d/%d wpisów wyświetlono." + +#: modules/commands/os_news.cpp:176 +msgid "End of news list." +msgstr "Koniec listy wiadomości." + +#: modules/commands/os_list.cpp:235 +#, c-format +msgid "End of users list. %u users shown." +msgstr "Koniec listy użytkowników. Wyświetlono %u pozycji." + +#: modules/commands/cs_enforce.cpp:227 +msgid "Enforce various channel modes and set options" +msgstr "Wymuszanie różnych flag kanału i opcji" + +#: modules/commands/cs_enforce.cpp:263 +msgid "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." +msgstr "" +"Wymuszanie różnych flag kanału i opcji. Ustawienie kanał\n" +"wskazuje, dla którego kanału tryby i opcje mają być wymuszane.\n" +"Opcja co wskazuje, jakie tryby i opcje mają zostać wymuszone.\n" +"Może to być jedna z następujących: SECUREOPS, RESTRICTED,\n" +"REGONLY, SSLONLY, BANS, lub LIMIT.\n" +" \n" +"Użyj SECUREOPS, aby wymusić opcję SECUREOPS nawet, gdy nie jest\n" +"włączona. Użyj RESTRICTED dla opcji RESTRICTED, także gdy nie jest\n" +"włączona. Użyj REGONLY, aby wyrzucić z kanału wszystkich niezarejestrowanych\n" +"użytkowników. Użyj SSLONLY, aby wyrzucić wszystkich nie korzystających\n" +"z połączenia bezpiecznego. BANS spowoduje wymuszenie banów poprzez\n" +"wyrzucenie pasujących do nich użytkowników, natomiast LIMIT będzie\n" +"wyrzucać użytkowników, dopóki ich ilość spadnie poniżej limitu kanałowego,\n" +"o ile taki jest ustawiony." + +#: src/language.cpp:43 modules/commands/ns_set.cpp:836 +#: modules/commands/ns_set.cpp:856 modules/commands/ns_set.cpp:891 +msgid "English" +msgstr "Polski" + +#: modules/commands/cs_entrymsg.cpp:170 +#, c-format +msgid "Entry message %i for %s deleted." +msgstr "Wiadomość powitalna %i osoby %s została usunięta." + +#: modules/commands/cs_entrymsg.cpp:177 +#, c-format +msgid "Entry message %s not found on channel %s." +msgstr "Wiadomość powitalna %s nie została znaleziona na kanale %s." + +#: modules/commands/cs_entrymsg.cpp:147 +#, c-format +msgid "Entry message added to %s" +msgstr "Wiadomość powitalna dodana do %s" + +#: modules/commands/cs_entrymsg.cpp:109 modules/commands/cs_entrymsg.cpp:158 +#, c-format +msgid "Entry message list for %s is empty." +msgstr "Lista wiadomości powitalnych dla %s jest pusta." + +#: modules/commands/cs_entrymsg.cpp:113 +#, c-format +msgid "Entry message list for %s:" +msgstr "Lista wiadomości powitalnych dla %s:" + +#: modules/commands/cs_entrymsg.cpp:187 +#, c-format +msgid "Entry messages for %s have been cleared." +msgstr "Wszystkie wiadomości kanału %s zostały usunięte." + +#: modules/commands/os_reload.cpp:39 +#, c-format +msgid "Error reloading configuration file: %s" +msgstr "Błąd przeładowywania pliku konfiguracyjnego: %s" + +#: include/language.h:125 +#, c-format +msgid "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." +msgstr "" +"Błąd: podany wirtualny ident jest zbyt długi. Proszę użyć nazwy krótszej niż %d " +"znaków." + +#: include/language.h:124 +#, c-format +msgid "" +"Error! The vHost is too long, please use a hostname shorter than %d characters." +msgstr "" +"Błąd: podany vHost jest zbyt długi. Proszę użyć nazwy krótszej niż %d znaków." + +#: modules/commands/ns_cert.cpp:325 +msgid "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." +msgstr "" +"Przykłady:\n" +" \n" +" CERT ADD\n" +" Dodaje twój aktualny \"odcisk palca\" do listy certyfikatów,\n" +" i automatycznie identyfikuje Ciebie gdy połączysz się z IRC\n" +" z jego użyciem.\n" +" \n" +" CERT DEL \n" +" Usuwa \"\" z Twojej listy certyfikatów.\n" +" \n" +" CERT LIST\n" +" Wyświetla bieżącą listę certyfikatów." + +#: modules/commands/os_session.cpp:358 +#, c-format +msgid "Exception for %s has been updated to %d." +msgstr "Wyjątek dla %s został zaktualizowany do %d." + +#: modules/commands/os_sxline.cpp:201 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:358 modules/commands/os_forbid.cpp:358 +#: modules/commands/ns_group.cpp:327 modules/commands/os_ignore.cpp:266 +#: modules/pseudoclients/nickserv.cpp:557 modules/pseudoclients/nickserv.cpp:562 +#: modules/pseudoclients/chanserv.cpp:465 +msgid "Expires" +msgstr "Wygasa" + +#: src/xline.cpp:397 +#, c-format +msgid "Expiry and reason updated for %s." +msgstr "Zaktualizowano wygasanie i powód dla %s." + +#: src/xline.cpp:400 +#, c-format +msgid "Expiry for %s updated." +msgstr "Zmieniono czas wygasania %s." + +#: modules/fantasy.cpp:214 +msgid "Fantasy" +msgstr "FANTASY" + +#: modules/fantasy.cpp:60 +#, c-format +msgid "Fantasy mode is now off on channel %s." +msgstr "Komendy fantasy na kanale %s zostały wyłączone." + +#: modules/fantasy.cpp:52 +#, c-format +msgid "Fantasy mode is now on on channel %s." +msgstr "Komendy fantasy na kanale %s zostały włączone." + +#: modules/commands/cs_status.cpp:19 +msgid "Find a user's status on a channel" +msgstr "Sprawdź status użytkownika na kanale" + +#: modules/commands/ns_cert.cpp:192 +#, c-format +msgid "Fingerprint %s already present on %s's certificate list." +msgstr "\"Odcisk palca\" %s jest już na liście certyfikatów %s." + +#: modules/commands/ns_cert.cpp:198 +#, c-format +msgid "Fingerprint %s is already in use." +msgstr "\"Odcisk palca %s jest już używany." + +#: modules/commands/cs_flags.cpp:301 +msgid "Flags" +msgstr "Flagi" + +#: modules/commands/cs_flags.cpp:286 +#, c-format +msgid "Flags for %s on %s set to +%s" +msgstr "Flagi dla %s na kanale %s zmieniono na +%s" + +#: modules/commands/cs_flags.cpp:341 +#, c-format +msgid "Flags list for %s" +msgstr "Lista flag dla %s" + +#: modules/commands/bs_kick.cpp:1161 modules/commands/bs_kick.cpp:1163 +#: modules/commands/bs_kick.cpp:1166 +msgid "Flood kicker" +msgstr "Kopanie za flood" + +#: modules/commands/os_forbid.cpp:421 +msgid "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." +msgstr "" +"\"Forbid\" pozwala zabronić używania pewnych nicków, kanałów,\n" +"i adresów e-mail. Symbole wieloznaczne są akceptowane dla\n" +"wszystkich wpisów." + +#: modules/commands/os_forbid.cpp:354 +msgid "Forbid list is empty." +msgstr "Lista zakazów jest pusta." + +#: modules/commands/os_forbid.cpp:396 +msgid "Forbid list:" +msgstr "Lista zakazów:" + +#: modules/commands/os_forbid.cpp:348 +#, c-format +msgid "Forbid on %s was not found." +msgstr "Zakaz %s nie znaleziony." + +#: modules/commands/os_forbid.cpp:156 +msgid "Forbid usage of nicknames, channels, and emails" +msgstr "Zakaz użycia nicków, kanałów i adresów e-mail" + +#: modules/commands/os_update.cpp:19 +msgid "Force the Services databases to be updated immediately" +msgstr "Wymusza natychmiastowy zapis baz na dysku" + +#: modules/commands/os_svs.cpp:19 +msgid "Forcefully change a user's nickname" +msgstr "Wymusza zmianę nicka danego użytkownika" + +#: modules/commands/os_svs.cpp:68 +msgid "Forcefully changes a user's nickname from nick to newnick." +msgstr "Zmienia nick wskazanemu użytkownikowi." + +#: modules/commands/os_svs.cpp:78 +msgid "Forcefully join a user to a channel" +msgstr "Wymusza wejście użytkownika na kanał" + +#: modules/commands/os_svs.cpp:112 +msgid "Forcefully join a user to a channel." +msgstr "Wymusza wejście użytkownika na kanał." + +#: modules/commands/os_svs.cpp:122 +msgid "Forcefully part a user from a channel" +msgstr "Wymusza wyjście użytkownika z kanału" + +#: modules/commands/os_svs.cpp:160 +msgid "Forcefully part a user from a channel." +msgstr "Wymusza wyjście użytkownika z kanału." + +#: modules/commands/ns_alist.cpp:64 modules/commands/cs_info.cpp:47 +msgid "Founder" +msgstr "Właściciel" + +#: modules/commands/cs_set.cpp:315 +#, c-format +msgid "Founder of %s changed to %s." +msgstr "Właścicielem kanału %s jest teraz %s." + +#: modules/commands/ns_getpass.cpp:41 +msgid "GETPASS command unavailable because encryption is in use." +msgstr "Komenda GETPASS nie działa, bo hasła są szyfrowane." + +#: modules/commands/ns_recover.cpp:84 +msgid "Ghost with your nick has been killed." +msgstr "Nick został usunięty z sieci." + +#: modules/commands/os_oline.cpp:19 +msgid "Give Operflags to a certain user" +msgstr "Daje flagi operatora wybranemu użytkownikowi" + +#: modules/commands/cs_mode.cpp:905 +#, c-format +msgid "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." +msgstr "" +"Daje status %s podanemu nickowi na kanale. Jeżeli nick\n" +"nie był podany, zastosuje %s dla Ciebie." + +#: modules/commands/cs_mode.cpp:888 +#, c-format +msgid "Gives you or the specified nick %s status on a channel" +msgstr "Nadaje Tobie lub podanemu nickowi status %s na kanale" + +#: modules/commands/greet.cpp:206 modules/commands/greet.cpp:212 +msgid "Greet" +msgstr "GREET" + +#: src/access.cpp:38 +msgid "Greet message displayed on join" +msgstr "Wiadomość powitalna wyświetlana przy wejściu" + +#: modules/commands/greet.cpp:112 +#, c-format +msgid "Greet message for %s changed to %s." +msgstr "Wiadomość powitalna osoby %s została zmieniona na %s." + +#: modules/commands/greet.cpp:118 +#, c-format +msgid "Greet message for %s unset." +msgstr "Wiadomość powitalna osoby %s została usunięta." + +#: modules/commands/greet.cpp:60 +#, c-format +msgid "Greet mode is now off on channel %s." +msgstr "Witanie użytkowników na kanale %s zostało wyłączone." + +#: modules/commands/greet.cpp:52 +#, c-format +msgid "Greet mode is now on on channel %s." +msgstr "Witanie użytkowników na kanale %s zostało włączone." + +#: modules/commands/ns_resetpass.cpp:21 +msgid "Helps you reset lost passwords" +msgstr "Umożliwia resetowanie zapomnianych haseł" + +#: modules/commands/ns_info.cpp:142 +msgid "Hide certain pieces of nickname information" +msgstr "Ukrywa poszczególne informacje o nicku" + +#: modules/commands/cs_list.cpp:180 +msgid "Hide channel from the LIST command" +msgstr "Zapobiega wyświetlaniu kanału po wydaniu polecenia LIST" + +#: modules/commands/os_session.cpp:192 +msgid "Host" +msgstr "Host" + +#: modules/commands/os_session.cpp:207 +#, c-format +msgid "Hosts with at least %d sessions:" +msgstr "Hosty z przynajmniej %d sesjami:" + +#: modules/commands/cs_seen.cpp:207 +#, c-format +msgid "I don't know who %s is." +msgstr "Nie wiem, kim jest %s." + +#: modules/commands/cs_seen.cpp:253 +#, c-format +msgid "I've never seen %s on this channel." +msgstr "Nigdy nie widziałem %s na tym kanale." + +#: modules/commands/os_sxline.cpp:203 modules/commands/os_akill.cpp:360 +msgid "ID" +msgstr "ID" + +#: modules/commands/os_oper.cpp:72 +msgid "INFO [type]" +msgstr "INFO [typ]" + +#: modules/commands/os_dns.cpp:218 +msgid "IP" +msgstr "IP" + +#: modules/commands/os_dns.cpp:500 +#, c-format +msgid "IP %s already exists for %s." +msgstr "IP %s już istnieje dla %s." + +#: modules/commands/os_dns.cpp:562 +#, c-format +msgid "IP %s does not exist for %s." +msgstr "IP %s nie istnieje dla %s." + +#: modules/commands/ns_identify.cpp:65 +msgid "Identify yourself with your password" +msgstr "Identyfikuje (loguje) właściciela nicka" + +#: modules/pseudoclients/nickserv.cpp:205 modules/pseudoclients/nickserv.cpp:211 +#, c-format +msgid "If you do not change within %s, I will change your nick." +msgstr "Jeśli go nie zmienisz w ciągu %s, zostanie zmieniony siłą." + +#: modules/commands/os_ignore.cpp:333 +msgid "Ignore list has been cleared." +msgstr "Lista ignorowanych została wyczyszczona." + +#: modules/commands/os_ignore.cpp:262 +msgid "Ignore list is empty." +msgstr "Lista ignorowanych jest pusta." + +#: modules/commands/ms_ignore.cpp:94 +msgid "Ignore list:" +msgstr "Lista ignorowania:" + +#: modules/commands/ns_set.cpp:1305 +msgid "Immediate protection" +msgstr "Bezpośrednia ochrona" + +#: modules/commands/ns_resetpass.cpp:33 +msgid "Incorrect email address." +msgstr "Błędny adres e-mail." + +#: include/language.h:89 +msgid "Incorrect range specified. The correct syntax is #from-to." +msgstr "Podano błędny zakres. Poprawna składnia to #od-do." + +#: modules/commands/os_modinfo.cpp:19 +msgid "Info about a loaded module" +msgstr "Wyświetla informacja o podanym module" + +#: modules/commands/bs_info.cpp:54 +#, c-format +msgid "Information for bot %s:" +msgstr "Informacje o bocie %s:" + +#: include/language.h:108 +#, c-format +msgid "Information for channel %s:" +msgstr "Informacje o kanale %s:" + +#: modules/commands/os_logsearch.cpp:57 +#, c-format +msgid "Invalid duration %s, using %d days." +msgstr "Niewłaściwy czas trwania %s, używam %d dni." + +#: include/language.h:68 +msgid "Invalid expiry time." +msgstr "Błędny czas przedawnienia." + +#: modules/commands/os_session.cpp:346 +msgid "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not matched " +"against nicks or usernames." +msgstr "Nieprawidłowa maska. Tylko rzeczywiste maski są prawidłowe jako wyjątki." + +#: modules/commands/os_logsearch.cpp:73 +#, c-format +msgid "Invalid limit %s, using %d." +msgstr "Błędny limit %s, stosuję %d." + +#: include/language.h:99 +msgid "Invalid passcode has been entered, please check the e-mail again, and retry." +msgstr "" +"Wpisano niewłaściwy kod. Proszę o ponowne sprawdzenie e-mail i ponowną próbę." + +#: modules/commands/ns_register.cpp:83 modules/commands/ns_register.cpp:86 +msgid "Invalid passcode." +msgstr "Niewłaściwy kod." + +#: modules/commands/os_session.cpp:339 +#, c-format +msgid "" +"Invalid session limit. It must be a valid integer greater than or equal to zero " +"and less than %d." +msgstr "Nieprawidłowy limit sesji. Musi być liczbą nieujemną i mniejszą niż %d." + +#: modules/commands/os_session.cpp:188 +msgid "Invalid threshold value. It must be a valid integer greater than 1." +msgstr "Nieprawidłowa wartość progu. Musi być liczbą całkowitą większą niż 1." + +#: modules/commands/os_dns.cpp:591 +msgid "Invalid value for LIMIT. Must be numerical." +msgstr "Niewłaściwa wartość LIMIT - wymagana liczba." + +#: modules/commands/cs_invite.cpp:19 +msgid "Invites you or an optionally specified nick into a channel" +msgstr "Zaprasza Ciebie lub podanego użytkownika na kanał" + +#: modules/commands/bs_kick.cpp:1201 modules/commands/bs_kick.cpp:1203 +#: modules/commands/bs_kick.cpp:1206 +msgid "Italics kicker" +msgstr "Kopanie za pochyły tekst" + +#: modules/commands/ns_group.cpp:91 +msgid "Join a group" +msgstr "Dołącza nick do wskazanej grupy" + +#: modules/commands/ns_set.cpp:1319 modules/commands/cs_set.cpp:1305 +msgid "Keep modes" +msgstr "Utrzymywanie trybów" + +#: modules/commands/ns_set.cpp:603 modules/commands/cs_set.cpp:377 +#, c-format +msgid "Keep modes for %s is now off." +msgstr "Opcja zapamiętywania flag dla %s została wyłączona." + +#: modules/commands/ns_set.cpp:597 modules/commands/cs_set.cpp:369 +#, c-format +msgid "Keep modes for %s is now on." +msgstr "Opcja zapamiętywania flag dla %s została włączona." + +#: modules/commands/ns_ajoin.cpp:100 +msgid "Key" +msgstr "Klucz" + +#: modules/commands/cs_getkey.cpp:50 +#, c-format +msgid "Key for channel %s is %s." +msgstr "Kluczem do kanału %s jest %s." + +#: modules/commands/os_kick.cpp:19 +msgid "Kick a user from a channel" +msgstr "Wyrzuca użytkownika z kanału" + +#: modules/commands/cs_ban.cpp:220 modules/commands/cs_kick.cpp:116 +#, c-format +msgid "Kicked %d/%d users matching %s from %s." +msgstr "Wyrzucono %d/%d użytkowników pasujących do %s z %s." + +#: modules/commands/cs_kick.cpp:19 +msgid "Kicks a specified nick from a channel" +msgstr "Wyrzuca wskazany nick z kanału" + +#: modules/commands/cs_kick.cpp:128 +msgid "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." +msgstr "" +"Wykopuje wskazanego użytkownika z kanału.\n" +"\n" +"Standardowo ta komenda jest dostępna dla użytkowników\n" +"wpisanych na listę AOP lub posiadających poziom\n" +"dostępu 5 lub wyższy. Właściciele kanału mogą podawać maski." + +#: modules/commands/os_kill.cpp:19 +msgid "Kill a user" +msgstr "Skilluj (rozłącz) użytkownika" + +#: modules/commands/cs_enforce.cpp:217 +msgid "LIMIT enforced by " +msgstr "LIMIT wymuszony przez " + +#: modules/commands/cs_enforce.cpp:221 +#, c-format +msgid "LIMIT enforced on %s, %d users removed." +msgstr "LIMIT wymuszony na %s, wyrzucono %d użytkowników." + +#: modules/commands/os_session.cpp:246 +msgid "LIST threshold" +msgstr "LIST wartość-progowa" + +#: modules/commands/os_sxline.cpp:427 modules/commands/os_sxline.cpp:661 +#: modules/commands/os_akill.cpp:388 +msgid "LIST [mask | list | id]" +msgstr "LIST [maska | lista | id]" + +#: modules/commands/os_session.cpp:525 +msgid "LIST [mask | list]" +msgstr "LIST [maska | lista]" + +#: modules/commands/ns_access.cpp:104 modules/commands/ns_ajoin.cpp:233 +#: modules/commands/ns_cert.cpp:260 +msgid "LIST [nickname]" +msgstr "LIST [nick]" + +#: modules/commands/os_news.cpp:31 +msgid "LOGONNEWS {ADD|DEL|LIST} [text|num]" +msgstr "" +"LOGONNEWS {ADD|DEL|LIST} [tekst|numer]\n" +"LOGONNEWS {ADD|DEL|LIST} [tekst|numer]" + +#: modules/commands/ns_set.cpp:834 +msgid "Language changed to English." +msgstr "Język został zmieniony na Polski." + +#: modules/commands/ns_set.cpp:836 +#, c-format +msgid "Language for %s changed to %s." +msgstr "Język dla %s zmieniono na %s." + +#: modules/commands/ms_cancel.cpp:72 +#, c-format +msgid "Last memo to %s has been cancelled." +msgstr "Ostatnia wiadomość do %s została odwołana." + +#: modules/commands/ns_info.cpp:96 +msgid "Last quit message" +msgstr "Ostatni QUIT" + +#: modules/commands/ns_info.cpp:93 modules/commands/cs_access.cpp:472 +msgid "Last seen" +msgstr "Widziano" + +#: modules/commands/ns_info.cpp:82 modules/commands/ns_info.cpp:87 +msgid "Last seen address" +msgstr "Ostatni host" + +#: modules/commands/cs_topic.cpp:264 +msgid "Last topic" +msgstr "Ostatni temat" + +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_info.cpp:56 +msgid "Last used" +msgstr "Widziano" + +#: modules/commands/ns_list.cpp:75 +msgid "Last usermask" +msgstr "Ostatnia maska" + +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +#: modules/commands/cs_access.cpp:697 +msgid "Level" +msgstr "Poziom" + +#: modules/commands/cs_access.cpp:660 +#, c-format +msgid "Level for %s on channel %s changed to %d." +msgstr "" +"Wymagany poziom dla %s\n" +"na kanale %s zmieniono teraz na %d." + +#: modules/commands/cs_access.cpp:658 +#, c-format +msgid "Level for %s on channel %s changed to founder only." +msgstr "Level for %s on channel %s changed to founder only." + +#: modules/commands/cs_access.cpp:643 +#, c-format +msgid "Level must be between %d and %d inclusive." +msgstr "Poziom musi być pomiędzy %d a %d włącznie." + +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_dns.cpp:218 +msgid "Limit" +msgstr "Limit" + +#: modules/commands/ns_list.cpp:19 +msgid "List all registered nicknames that match a given pattern" +msgstr "Listuje zarejestrowane nicki pasujące do wzorca" + +#: modules/commands/ns_alist.cpp:24 +msgid "List channels you have access on" +msgstr "Listuje kanały na których masz uprawnienia" + +#: modules/commands/cs_mode.cpp:341 +#, c-format +msgid "List for mode %c is full." +msgstr "Lista dla trybu %c jest pełna." + +#: modules/commands/os_modinfo.cpp:80 +msgid "List loaded modules" +msgstr "Listuje załadowane moduły" + +#: modules/commands/ns_list.cpp:123 modules/commands/cs_list.cpp:72 +#, c-format +msgid "List of entries matching %s:" +msgstr "Listuje wpisy pasujące do %s:" + +#: modules/commands/ns_group.cpp:350 +#, c-format +msgid "List of nicknames in the group of %s:" +msgstr "Lista nicków grupy %s:" + +#: modules/commands/ns_group.cpp:350 +msgid "List of nicknames in your group:" +msgstr "Lista nicków w grupie:" + +#: modules/commands/ms_list.cpp:19 +msgid "List your memos" +msgstr "Wyświetla wszystkie wiadomości" + +#: modules/commands/bs_botlist.cpp:64 +msgid "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." +msgstr "" +"Listuje dostępne w sieci boty. Te, które zaczynają się od\n" +"*, są zarezerwowane dla IRC Operatorów." + +#: modules/commands/os_list.cpp:19 +msgid "Lists all channel records" +msgstr "Listuje wszystkie kanały" + +#: modules/commands/os_list.cpp:107 +msgid "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." +msgstr "" +"Listuje wszystkie istniejące kanały w sieci, niezależnie od\n" +"tego czy są zarejestrowane.\n" +"\n" +"Podanie wzorca ogranicza listę pokazywanych kanałów.\n" +"Podanie nicka wyświetla kanały, na których przebywa\n" +"wskazany użytkownik. Dodanie parametru SECRET ogranicza\n" +"listę do kanałów z flagą +s lub +p." + +#: modules/commands/ns_alist.cpp:127 +msgid "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" +msgstr "" +"Wyświetla wszystkie kanały, na których posiadasz uprawnienia.\n" +"\n" +"Kanały z włączoną opcją NOEXPIRE będą poprzedzone\n" +"wykrzyknikiem. Parametr \"nick\" jest dostępny tylko dla operatorów\n" +"serwisów" + +#: modules/commands/ns_group.cpp:299 +msgid "Lists all nicknames in your group" +msgstr "Listuje nicki w grupie" + +#: modules/commands/cs_list.cpp:20 +msgid "Lists all registered channels matching the given pattern" +msgstr "Listuje zarejestrowane kanały pasujące do wzorca" + +#: modules/commands/cs_list.cpp:137 +msgid "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." +msgstr "" +"Listuje wszystkie zarejestrowane kanały pasujące do podanego\n" +"wzorca. Kanały z ustawioną opcją PRIVATE będą widziane\n" +"tylko przez operatorów serwisów posiadających odpowiednie\n" +"uprawnienia. Kanały z opcją NOEXPIRE będą poprzedzone\n" +"znakiem ! widocznym dla operatorów serwisów. \n" +"Uwaga: poprzedzający '#' oznacza zakres; nazwy kanałów\n" +"powinny być wpisywane bez '#'.\n" +" \n" +"Jeżeli podano opcję SUSPENDED lub NOEXPIRE, tylko kanały,\n" +"które, odpowiednio, są zawieszone bądź mają ustawione NOEXPIRE,\n" +"będą wyświetlane. Gdy podano wiele opcji, wyświetlane będą\n" +"wszystkie kanały pasujące do chociaż jednej z nich. Wspomniane\n" +"opcje są dostępne tylko dla Operatorów Serwisów.\n" +" \n" +"Przykłady:\n" +" \n" +" LIST *anope*\n" +" Wyświetla wszystkie zarejestrowane kanały zawierające\n" +" anope w swojej nazwie (wielkość liter bez znaczenia).\n" +" \n" +" LIST * NOEXPIRE\n" +" Pokazuje wszystkie kanały, które nie wygasają.\n" +" \n" +" LIST #51-100\n" +" Pokazuje wszystkie zarejestrowane kanały z podanego\n" +" zakresu (51-100)." + +#: modules/commands/ns_list.cpp:139 +msgid "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." +msgstr "" +"Listuje wszystkie zarejestrowane nicki pasujące\n" +"do podanego wzorca w postaci nick!ident@host.\n" +"Administratorzy serwisów mogą zobaczyć nicki z\n" +"ustawioną opcją PRIVATE, a przy nickach z opcją\n" +"NOEXPIRE zobaczą dodany do nich wykrzyknik.\n" +" \n" +"Uwaga: poprzedzający '#' oznacza zakres.\n" +" \n" +"Administratorzy serwisów mogą także podać parametry:\n" +"FORBIDDEN, SUSPENDED, NOEXPIRE i UNCONFIRMED, które\n" +"ograniczą listę wyświetlanych nicków do tych, które\n" +"spełniają podane warunki. Jeśli zostanie podanych\n" +"więcej warunków, wszystkie nicki spełniające choć\n" +"jeden z nich zostaną pokazane.\n" +"\n" +"Przykłady:\n" +"\n" +" LIST *!adirm@mafia.ru\n" +" Lista wszystkich nicków pasujących do\n" +" *!adirm@mafia.ru.\n" +"\n" +" LIST *Bot*!*@*\n" +" Lista wszystkich nicków z Bot w nazwie\n" +" (wielkość liter nie ma znaczenia).\n" +"\n" +" LIST *!*@*.tpnet.pl\n" +" Lista wszystkich nicków z maską domeny\n" +" tpnet.pl \n" +" LIST * NOEXPIRE\n" +" Lista wszystkich nicków, które nie wygasną.\n" +" \n" +" LIST #51-100\n" +" Lista wszystkich nicków z podanego zakresu (51-100)." + +#: modules/commands/os_list.cpp:132 +msgid "Lists all user records" +msgstr "Listuje wszystkich użytkowników" + +#: modules/commands/os_list.cpp:243 +msgid "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only users\n" +"with the +i flag will be listed." +msgstr "" +"Listuje wszystkich użytkowników w sieci, niezależnie od\n" +"tego czy mają zarejestrowanego nicka.\n" +"\n" +"Podanie wzorca ogranicza listę pokazywanych użytkowników.\n" +"(musi być w formacie nick!ident@host[#realname]). Podanie kanału\n" +"listuje użytkowników przebywających na wskazanym kanale.\n" +"Dodanie parametru INVISIBLE listuje tylko użytkowników z flagą +i." + +#: modules/commands/ms_list.cpp:142 +msgid "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Wyświetla wszystkie odebrane wiadomości. Parametr \n" +"NEW ogranicza listę do nowych wiadomości, które\n" +"oznaczane są symbolem \"*\" po lewej stronie numeru.\n" +"Można także sprecyzować listę wyświetlanych \n" +"wiadomości podając ich numery, np:\n" +" LIST 2-5,7-9\n" +" Wyświetli wiadomości od numeru 2 do 5 oraz od 7 do 9." + +#: modules/commands/bs_botlist.cpp:19 +msgid "Lists available bots" +msgstr "Listuje dostępne boty" + +#: modules/commands/os_modinfo.cpp:196 +msgid "Lists currently loaded modules." +msgstr "Listuje załadowane moduły." + +#: modules/commands/cs_info.cpp:19 +msgid "Lists information about the specified registered channel" +msgstr "Pokazuje informacje o zarejestrowanym kanale" + +#: modules/commands/cs_info.cpp:76 +msgid "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." +msgstr "" +"Wyświetla informacje o zarejestrowanym kanale:\n" +"właściciel, data założenia, opis, czas ostatniego użycia.\n" +"Jeśli użytkownik wydający polecenie posiada odpowiednie\n" +"uprawnienia, to otrzyma także informacje o spadkobiercy,\n" +"ostatnim temacie, ustawieniach i przeterminowaniu,\n" +"gdy dostępne." + +#: modules/commands/os_module.cpp:19 +msgid "Load a module" +msgstr "Ładuje moduł" + +#: modules/commands/cs_register.cpp:39 +msgid "Local channels cannot be registered." +msgstr "Lokalne kanały nie mogą być rejestrowane." + +#: modules/commands/cs_log.cpp:142 +#, c-format +msgid "Log list for %s:" +msgstr "Lista logowania dla %s:" + +#: modules/commands/cs_log.cpp:227 +#, c-format +msgid "Logging changed for command %s on %s, now using log method %s%s%s." +msgstr "Logowanie dla polecenia %s na %s zmienione. Aktualnie używam metody %s%s%s." + +#: modules/commands/cs_log.cpp:220 +#, c-format +msgid "Logging for command %s on %s with log method %s%s%s has been removed." +msgstr "Logowanie dla polecenia %s na %s metodą %s%s%s zostało usunięte." + +#: modules/commands/cs_log.cpp:248 +#, c-format +msgid "Logging is now active for command %s on %s, using log method %s%s%s." +msgstr "" +"Logowanie jest teraz aktywne dla polecenia %s na %s, przy użyciu metody %s%s%s." + +#: modules/commands/os_login.cpp:60 +#, c-format +msgid "Login to %s" +msgstr "Logowanie do %s" + +#: modules/commands/os_news.cpp:36 +#, c-format +msgid "Logon news item #%d deleted." +msgstr "Wiadomość powitalna #%d została skasowana." + +#: modules/commands/os_news.cpp:35 +#, c-format +msgid "Logon news item #%s not found!" +msgstr "Wiadomość powitalna #%s nie została znaleziona!" + +#: modules/commands/os_news.cpp:32 +msgid "Logon news items:" +msgstr "Wiadomości powitalne:" + +#: modules/commands/os_login.cpp:102 +#, c-format +msgid "Logout from %s" +msgstr "Wylogowanie z %s" + +#: modules/commands/os_login.cpp:52 +#, c-format +msgid "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." +msgstr "" +"Pozwala Ci zalogować się do %s, dzięki czemu uzyskasz uprawnienia\n" +"operatora. To polecenie może nie być konieczne, jeśli masz blok\n" +"oper skonfigurowany bez hasła." + +#: modules/commands/os_login.cpp:94 +#, c-format +msgid "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." +msgstr "" +"Wylogowuje Ciebie z %s, przez co tracisz uprawnienia operatora.\n" +"To polecenie przydaje się tylko, gdy twój blok oper został skonfigurowany\n" +"z wykorzystaniem hasła." + +#: modules/commands/cs_seen.cpp:213 +#, c-format +msgid "Looking for yourself, eh %s?" +msgstr "Ej, szukasz siebie, %s?" + +#: modules/commands/cs_mode.cpp:773 +#, c-format +msgid "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a channel.\n" +"If a mode is locked on or off, services will not allow that mode to be changed. " +"The SET\n" +"command will clear all existing mode locks and set the new one given, while ADD " +"and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * and ? " +"may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, halfops, and " +"voices. If what\n" +"is not given then all basic modes are removed." +msgstr "" +"Kontroluje przede wszystkim blokady trybów i uprawnienia do trybów (które różnią " +"się od uprawnień\n" +"do kanałów).\n" +" \n" +"Polecenie %s LOCK pozwala na dodawanie, usuwanie i podglądanie blokad trybów na " +"kanale.\n" +"Gdy flaga jest zablokowana jako włączona lub wyłączona, serwisy uniemożliwią jej " +"zmianę.\n" +"Polecenie SET usunie wszystkie aktualne blokady trybów, i ustawi tylko podane, " +"natomiast\n" +"komendy ADD i DEL zmodyfikują istniejącą blokadę.\n" +"Przykład:\n" +" MODE #kanał LOCK ADD +bmnt *!*@*neostrada*\n" +" \n" +"Komenda %s SET pozwala na ustawianie trybów za pomocą serwisów. Znaki * oraz ? " +"mogą\n" +"być podawane jako parametry dla list i trybów użytkowników.\n" +"Przykład:\n" +" MODE #kanał SET +v *\n" +" Daje prawo głosu wszystkim użytkownikom na kanale.\n" +" \n" +" MODE #kanał SET -b ~c:*\n" +" Kasuje wszystkie bany rozszerzone, zaczynające się od ~c:\n" +" \n" +"Komenda %s CLEAR jest łatwą metodą na usunięcie trybów kanałowych. Opcją co może " +"być\n" +"dowolna flaga. Do przykładów można zaliczyć bany, wyjątki banów, wyjątki " +"zaproszeń, statusy opa, halfopa,\n" +"Jeśli nie podano co, zostaną wyczyszczone wszystkie podstawowe tryby." + +#: modules/commands/cs_akick.cpp:434 +msgid "Maintain the AutoKick list" +msgstr "Zarządza listą AKICK" + +#: modules/commands/bs_bot.cpp:269 +msgid "Maintains network bot list" +msgstr "Zarządza sieciową listą botów" + +#: modules/commands/cs_xop.cpp:522 +#, c-format +msgid "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " +msgstr "" +"Zarządza listą %s dla kanału. Użytkownicy pasujący do wpisu na liście\n" +"dostępowej %s otrzymują następujące uprawnienia:\n" +" " + +#: modules/commands/cs_akick.cpp:493 +#, c-format +msgid "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" +msgstr "" +"Zarządza listą AutoKick dla kanału. Gdy użytkownik\n" +"obecny na liście AutoKick spróbuje dołączyć do kanału, %s\n" +"zbanuje go, a następnie wyrzuci.\n" +"\n" +"Polecenie AKICK ADD dodaje podanego nicka lub maskę\n" +"do listy AutoKick. Jeśli podano powód, zostanie on podany\n" +"przy wyrzucaniu użytkownika z kanału. Jeśli nie, pojawi się\n" +"domyślny komunikat \"Użytkownik został zbanowany.\"\n" +"Dodanie do AutoKick zarejestrowanego nicka spowoduje\n" +"dodanie jego konta %s zamiast maski. Wszystkie nicki\n" +"znajdujące się w grupie będą wówczas wyrzucane.\n" + +#: modules/commands/cs_access.cpp:568 +#, c-format +msgid "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." +msgstr "" +"Zarządza kanałową listą dostępu. Lista ta wyznacza,\n" +"którzy użytkownicy będą otrzymywali status operatora, lub też\n" +"dostęp do poleceń %s na kanale. Różne poziomy dostępowe\n" +"pozwalają na przydzielenie użytkowników do wielu grup uprawnień.\n" +"Każdy zarejestrowany użytkownik, który nie znajduje się na liście\n" +"dostępowej, posiada poziom 0, natomiast każdy niezarejestrowany\n" +"jest identyfikowany z poziomem -1." + +#: modules/commands/bs_badwords.cpp:424 +#, c-format +msgid "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" +msgstr "" +"Polecenie umożliwia zarządzanie listą niedozwolonych\n" +"słów. Lista definiuje za jakie słowa użytkownicy mogą\n" +"zostać wyrzuceni z kanału. Aby uzyskać więcej informacji\n" +"napisz: %s%s HELP KICK %s\n" +"\n" +"ADD dodaje wskazane słowo do listy.\n" +"Parametr SINGLE powoduje, że użytkownicy będą kopani za\n" +"używanie wskazanego słowa w całości.\n" +"Parametr START powoduje, że użytkownicy będą kopani za\n" +"używanie wskazanego słowa na początku innych wyrazów.\n" +"Parametr END powoduje, że użytkownicy będą kopani za\n" +"używanie wskazanego słowa na końcu innych wyrazów.\n" +"Pominięcie parametru powoduje, że użytkownicy będą\n" +"kopani w każdym z przypadków, kiedy zostanie użyte \n" +"wskazane słowo.\n" +" \n" + +#: modules/commands/bs_badwords.cpp:370 +msgid "Maintains the bad words list" +msgstr "Zarządza listą zakazanych słów" + +#: modules/commands/bs_control.cpp:79 +msgid "Makes the bot do the equivalent of a \"/me\" command" +msgstr "Wyraża przez bota akcję (komenda /me)" + +#: modules/commands/bs_control.cpp:127 +msgid "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." +msgstr "" +"Sprawia, że bot użyje komendy akcji (/me) przy\n" +"wypowiadaniu podanego tekstu na kanale." + +#: modules/commands/bs_control.cpp:19 +msgid "Makes the bot say the specified text on the specified channel" +msgstr "Wypowiada przez bota tekst na kanale" + +#: modules/commands/bs_control.cpp:69 +msgid "Makes the bot say the specified text on the specified channel." +msgstr "Wypowiada przez bota tekst na kanale." + +#: modules/commands/greet.cpp:157 +msgid "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." +msgstr "" +"Ustawia wiadomość powitalną dla wskazanego użytkownika.\n" +"Jeśli kanał ma włączone witanie (GREET), oraz użytkownik posiada\n" +"odpowiedni poziom dostępu, wiadomość będzie wysyłana na kanał\n" +"przez bota." + +#: modules/commands/greet.cpp:131 +msgid "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." +msgstr "" +"Ustawia wiadomość powitalną dla Ciebie.\n" +"Jeśli kanał ma włączone witanie (GREET), oraz posiadasz\n" +"odpowiedni poziom dostępu, wiadomość będzie wysyłana na\n" +"kanał przez bota." + +#: modules/commands/os_dns.cpp:660 +msgid "Manage DNS zones for this network" +msgstr "Zarządza strefami DNS sieci" + +#: modules/commands/cs_entrymsg.cpp:193 +msgid "Manage the channel's entry messages" +msgstr "Zarządza wiadomościami powitalnymi kanału" + +#: modules/commands/ms_ignore.cpp:19 +msgid "Manage the memo ignore list" +msgstr "Zarządza listą ignorowanych Memo" + +#: modules/commands/ns_ajoin.cpp:230 +msgid "Manage your auto join list" +msgstr "Zarządza Twoją listą automatycznego dołączania do kanalów" + +#: modules/commands/os_sxline.cpp:233 +#, c-format +msgid "Manipulate the %s list" +msgstr "Zarządza listą %s" + +#: modules/commands/os_akill.cpp:385 +msgid "Manipulate the AKILL list" +msgstr "Zarządza listą AKILL" + +#: modules/commands/os_defcon.cpp:176 +msgid "Manipulate the DefCon system" +msgstr "Modyfikuje poziom systemu DefCon" + +#: modules/commands/cs_topic.cpp:149 +msgid "Manipulate the topic of the specified channel" +msgstr "Zmienia temat podanego kanału" + +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +#: modules/commands/ms_ignore.cpp:86 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_ignore.cpp:266 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/os_list.cpp:153 +#: modules/commands/cs_xop.cpp:377 modules/commands/cs_flags.cpp:301 +#: modules/commands/bs_info.cpp:55 modules/commands/bs_botlist.cpp:27 +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +msgid "Mask" +msgstr "Maska" + +#: modules/commands/ns_access.cpp:39 +#, c-format +msgid "Mask %s already present on %s's access list." +msgstr "Maska %s jest już w liście dostępu %s." + +#: include/language.h:67 +msgid "Mask must be in the form user@host." +msgstr "Maska musi mieć postać user@host." + +#: modules/commands/cs_xop.cpp:162 modules/commands/cs_flags.cpp:120 +#: modules/commands/cs_access.cpp:166 +msgid "Masks and unregistered users may not be on access lists." +msgstr "" +"Maski ani niezarejestrowane nicki nie mogą znajdować się na listach dostępowych." + +#: modules/commands/ns_getemail.cpp:23 +msgid "Matches and returns all users that registered using given email" +msgstr "Wyświetla użytkowników zarejestrowanych z podanym adresem e-mail" + +#: modules/commands/os_logsearch.cpp:148 +#, c-format +msgid "Matches for %s:" +msgstr "Pasujący do %s:" + +#: modules/commands/os_stats.cpp:139 +#, c-format +msgid "Maximum users: %d (%s)" +msgstr "Rekord użytk. : %d (%s)" + +#: modules/commands/ms_read.cpp:84 modules/commands/ms_read.cpp:86 +#, c-format +msgid "Memo %d from %s (%s)." +msgstr "Wiadomość %d od %s (%s)." + +#: modules/commands/ms_del.cpp:33 modules/commands/ms_del.cpp:101 +#, c-format +msgid "Memo %d has been deleted." +msgstr "Wiadomość %d została usunięta." + +#: modules/commands/ms_ignore.cpp:82 +msgid "Memo ignore list is empty." +msgstr "Lista ignorowanych jest pusta." + +#: modules/commands/ms_set.cpp:199 +#, c-format +msgid "Memo limit disabled for %s." +msgstr "Limit wiadomości dla %s jest wyłączony." + +#: modules/commands/ms_set.cpp:185 +#, c-format +msgid "Memo limit for %s set to %d." +msgstr "Limit wiadomości dla %s zmieniono na %d." + +#: modules/commands/ms_set.cpp:192 +#, c-format +msgid "Memo limit for %s set to 0." +msgstr "Limit wiadomości dla %s ustawiono na 0." + +#: modules/commands/ms_send.cpp:51 modules/commands/ms_rsend.cpp:63 +#, c-format +msgid "Memo sent to %s." +msgstr "Wiadomość została wysłana do %s." + +#: modules/commands/ms_list.cpp:131 +#, c-format +msgid "Memos for %s:" +msgstr "Wiadomości dla %s:" + +#: modules/commands/cs_entrymsg.cpp:116 +msgid "Message" +msgstr "Wiadomość" + +#: modules/commands/ns_set.cpp:1313 +msgid "Message mode" +msgstr "MSG" + +#: modules/commands/cs_log.cpp:127 +msgid "Method" +msgstr "Metoda" + +#: modules/commands/cs_mode.cpp:329 modules/commands/cs_mode.cpp:420 +#, c-format +msgid "Missing parameter for mode %c." +msgstr "Brakuje parametru dla trybu %c." + +#: modules/commands/cs_mode.cpp:449 +msgid "Mode" +msgstr "Tryb" + +#: modules/commands/cs_mode.cpp:718 +#, c-format +msgid "Mode %s is a virtual mode and can't be cleared." +msgstr "Tryb %s jest wirtualny, więc nie można go usunąć." + +#: modules/commands/cs_mode.cpp:712 +#, c-format +msgid "Mode %s is not a status or list mode." +msgstr "%s nie jest trybem dotyczącym uprawnienia ani listy." + +#: modules/commands/cs_mode.cpp:1065 +msgid "Mode lock" +msgstr "Blokowane tryby" + +#: modules/commands/cs_mode.cpp:466 +#, c-format +msgid "Mode locks for %s:" +msgstr "Blokowane tryby dla %s:" + +#: modules/commands/os_list.cpp:43 +msgid "Modes" +msgstr "Tryby" + +#: modules/commands/os_mode.cpp:44 +#, c-format +msgid "Modes cleared on %s and the channel destroyed." +msgstr "Wyczyszczono tryby i zniszczono kanał %s." + +#: modules/commands/ns_access.cpp:166 +#, c-format +msgid "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." +msgstr "" +"Modyfikuje lub wyświetla listę dostępu dla nicka.\n" +"Lista dostępu określa hosty użytkowników rozpoznawanych\n" +"przez %s, mogących używać Twojego nicka. Jeśli chcesz\n" +"używać nicka z innego hosta, musisz się najpierw\n" +"zidentyfikować w serwisie %s komendą IDENTIFY.\n" +"Operator Serwisów może podać nicka, aby\n" +"modyfikować jego listę zamiast swojej.\n" +"\n" +"Przykłady:\n" +"\n" +" ACCESS ADD *@example.pl\n" +" Zezwala na dostęp do nicka każdemu \n" +" łączącemu się z domeny example.pl.\n" +"\n" +" ACCESS DEL *@example.pl\n" +" Odwraca efekt poprzedniej komendy.\n" +"\n" +" ACCESS LIST\n" +" Wyświetla aktualną listę dostępu." + +#: modules/commands/ns_cert.cpp:319 +msgid "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" +msgstr "" +"Modyfikuje lub wyświetla listę certyfikatów dla Twojego nicka.\n" +"Gdy połączysz się z IRC, i prześlesz certyfikat klienta z \"odciskiem palca\"\n" +"znajdującym się na liście certyfikatów, zostaniesz automatycznie\n" +"zalogowany. Operatorzy serwisów mogą podać nick, aby modyfikować\n" +"listy certyfikatów innych użytkowników. \n" + +#: modules/commands/os_ignore.cpp:341 +msgid "Modify the Services ignore list" +msgstr "Zarządza listą ignorowanych przez serwisy" + +#: modules/commands/cs_xop.cpp:489 +#, c-format +msgid "Modify the list of %s users" +msgstr "Zarządza listą %s" + +#: modules/commands/ns_access.cpp:101 +msgid "Modify the list of authorized addresses" +msgstr "Zarządza listą dostępu" + +#: modules/commands/cs_flags.cpp:373 modules/commands/cs_access.cpp:498 +msgid "Modify the list of privileged users" +msgstr "Zarządza listą uprawnionych użytkowników" + +#: modules/commands/ns_cert.cpp:257 +msgid "Modify the nickname client certificate list" +msgstr "Modyfikuje listę certyfikatów klienta dla nicka" + +#: modules/commands/os_session.cpp:522 +msgid "Modify the session-limit exception list" +msgstr "Zarządza listą wyjątków dla limitów sesji" + +#: modules/commands/os_module.cpp:34 +#, c-format +msgid "Module %s is already loaded." +msgstr "Moduł %s już jest załadowany." + +#: modules/commands/os_module.cpp:67 modules/commands/os_module.cpp:139 +#, c-format +msgid "Module %s isn't loaded." +msgstr "Moduł %s nie jest załadowany." + +#: modules/commands/os_module.cpp:31 +#, c-format +msgid "Module %s loaded." +msgstr "Moduł %s został załadowany." + +#: modules/commands/os_module.cpp:98 +#, c-format +msgid "Module %s reloaded." +msgstr "Moduł %s został przeładowany." + +#: modules/commands/os_module.cpp:156 +#, c-format +msgid "Module %s unloaded." +msgstr "Moduł %s został wyładowany." + +#: modules/commands/os_config.cpp:88 +msgid "Module Name" +msgstr "Nazwa modułu" + +#: modules/commands/os_config.cpp:112 +msgid "Module settings:" +msgstr "Ustawienia modułu:" + +#: modules/commands/os_modinfo.cpp:32 +#, c-format +msgid "Module: %s Version: %s Author: %s Loaded: %s" +msgstr "Moduł: %s Wersja: %s Autor: %s Załadowano: %s" + +#: modules/commands/os_modinfo.cpp:183 +#, c-format +msgid "Module: %s [%s] [%s]" +msgstr "Moduł: %s [%s] [%s]" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +#: modules/commands/os_list.cpp:43 modules/commands/os_list.cpp:153 +#: modules/commands/cs_access.cpp:697 modules/commands/cs_access.cpp:799 +#: modules/commands/cs_list.cpp:75 +msgid "Name" +msgstr "Nazwa" + +#: modules/commands/os_oper.cpp:153 +msgid "Name Type" +msgstr "Nazwa Typ" + +#: modules/extra/stats/cs_fantasy_stats.cpp:146 +#, c-format +msgid "Network stats for %s:" +msgstr "Statystyki sieciowe dla %s:" + +#: modules/commands/os_forbid.cpp:384 +msgid "Never" +msgstr "Nigdy" + +#: modules/commands/hs_request.cpp:305 modules/commands/hs_list.cpp:58 +#: modules/commands/ns_group.cpp:327 modules/commands/ns_list.cpp:75 +#: modules/commands/bs_botlist.cpp:27 +msgid "Nick" +msgstr "Nick" + +#: modules/commands/ns_register.cpp:42 +#, c-format +msgid "Nick %s has been confirmed." +msgstr "Nick %s został potwierdzony." + +#: modules/commands/os_oper.cpp:95 +#, c-format +msgid "Nick %s is already an operator." +msgstr "Nick %s jest już operatorem." + +#: modules/commands/ns_register.cpp:36 +#, c-format +msgid "Nick %s is already confirmed." +msgstr "Nick %s jest już potwierdzony." + +#: modules/commands/os_svs.cpp:46 +#, c-format +msgid "Nick %s is an illegal nickname and cannot be used." +msgstr "Nick %s jest nieprawidłowy i nie może być używany." + +#: modules/commands/os_svs.cpp:54 modules/commands/bs_bot.cpp:81 +#: modules/commands/bs_bot.cpp:181 +#, c-format +msgid "Nick %s is currently in use." +msgstr "Nick %s jest aktualnie w użyciu." + +#: modules/commands/os_forbid.cpp:512 +#, c-format +msgid "Nick %s is forbidden by %s: %s" +msgstr "Nick %s jest zabroniony przez %s: %s" + +#: modules/commands/os_forbid.cpp:514 +#, c-format +msgid "Nick %s is forbidden." +msgstr "Nick %s jest zabroniony." + +#: modules/commands/os_oper.cpp:134 +#, c-format +msgid "Nick %s is not a Services Operator." +msgstr "Nick %s nie jest operatorem serwisów." + +#: modules/commands/ns_info.cpp:34 +#, c-format +msgid "Nick %s is part of this Network's Services." +msgstr "Nick %s jest serwisem!" + +#: include/language.h:79 +#, c-format +msgid "Nick %s isn't currently in use." +msgstr "Nick %s nie jest aktualnie w użyciu." + +#: include/language.h:78 +#, c-format +msgid "Nick %s isn't registered." +msgstr "Nick %s nie jest zarejestrowany." + +#: modules/commands/os_svs.cpp:39 +#, c-format +msgid "Nick %s was truncated to %d characters." +msgstr "Nick %s został skrócony do %d znaków." + +#: modules/commands/ns_set.cpp:1135 +#, c-format +msgid "Nick %s will expire." +msgstr "Nick %s od teraz podlega zasadom wygasania." + +#: modules/commands/ns_set.cpp:1129 +#, c-format +msgid "Nick %s will not expire." +msgstr "Nick %s nie wygaśnie." + +#: modules/commands/ms_check.cpp:60 +#, c-format +msgid "Nick %s doesn't have a memo from you." +msgstr "%s nie posiada wiadomości od Ciebie." + +#: modules/commands/ns_logout.cpp:48 +#, c-format +msgid "Nick %s has been logged out." +msgstr "Nick %s został wylogowany." + +#: modules/commands/ns_group.cpp:272 +#, c-format +msgid "Nick %s has been ungrouped from %s." +msgstr "Nick %s has been ungrouped from %s." + +#: include/language.h:81 +#, c-format +msgid "Nick %s is currently suspended." +msgstr "Nick %s jest zawieszony." + +#: modules/commands/ns_group.cpp:250 +#, c-format +msgid "Nick %s is not in your group." +msgstr "Nicka %s nie ma w Twojej grupie." + +#: modules/commands/ns_suspend.cpp:180 +#, c-format +msgid "Nick %s is not suspended." +msgstr "Nick %s nie jest zawieszony." + +#: modules/commands/ns_suspend.cpp:190 +#, c-format +msgid "Nick %s is now released." +msgstr "Nick %s został uwolniony." + +#: modules/commands/ns_suspend.cpp:138 +#, c-format +msgid "Nick %s is now suspended." +msgstr "Nick %s został zawieszony." + +#: modules/commands/cs_seen.cpp:275 +#, c-format +msgid "Nick too long, max length is %u characters." +msgstr "Zbyt długi nick. Maksymalna długość to %u znaków." + +#: modules/commands/ns_drop.cpp:53 +#, c-format +msgid "Nickname %s has been dropped." +msgstr "Nick %s został odrejestrowany." + +#: include/language.h:97 +#, c-format +msgid "Nickname %s is already registered!" +msgstr "Nick %s jest już zarejestrowany!" + +#: include/language.h:96 +#, c-format +msgid "Nickname %s may not be registered." +msgstr "Nick %s nie może zostać zarejestrowany." + +#: modules/commands/ns_register.cpp:228 +#, c-format +msgid "Nickname %s registered under your user@host-mask: %s" +msgstr "Nick %s został zarejestrowany z maską: %s" + +#: modules/commands/ns_register.cpp:230 +#, c-format +msgid "Nickname %s registered." +msgstr "Nick %s został zarejestrowany." + +#: modules/commands/cs_set.cpp:1307 +msgid "No auto-op" +msgstr "Brak AUTOOP" + +#: modules/commands/bs_assign.cpp:252 +msgid "No bot" +msgstr "NOBOT" + +#: modules/commands/ns_set.cpp:1317 modules/commands/cs_set.cpp:1303 +msgid "No expire" +msgstr "Nie wygasa" + +#: modules/commands/help.cpp:184 +#, c-format +msgid "No help available for %s." +msgstr "Brak dostępnej pomocy dla %s." + +#: modules/commands/os_modinfo.cpp:61 +#, c-format +msgid "No information about module %s is available." +msgstr "Informacje o module %s nie są dostępne." + +#: modules/commands/cs_enforce.cpp:177 +#, c-format +msgid "No limit is set on %s." +msgstr "Brak ustawionego limitu dla %s." + +#: modules/commands/os_news.cpp:37 +msgid "No logon news items to delete!" +msgstr "Nie ma wiadomości powitalnych do skasowania!" + +#: modules/commands/os_logsearch.cpp:133 +#, c-format +msgid "No matches for %s found." +msgstr "Nie znaleziono dopasowań do %s." + +#: modules/commands/cs_xop.cpp:294 +#, c-format +msgid "No matching entries on %s %s list." +msgstr "Nie znaleziono wpisów w liście %s kanału %s." + +#: modules/commands/cs_xop.cpp:428 modules/commands/cs_flags.cpp:335 +#: modules/commands/cs_access.cpp:269 modules/commands/cs_access.cpp:433 +#, c-format +msgid "No matching entries on %s access list." +msgstr "Nie znaleziono wpisów na liście dostępu kanału %s." + +#: modules/commands/cs_akick.cpp:224 modules/commands/cs_akick.cpp:368 +#, c-format +msgid "No matching entries on %s autokick list." +msgstr "Nie znaleziono wpisów na liście AKICK kanału %s." + +#: modules/commands/bs_badwords.cpp:166 modules/commands/bs_badwords.cpp:246 +#, c-format +msgid "No matching entries on %s bad words list." +msgstr "Nie znaleziono pasujących wpisów na liście zakazanych słów kanału %s." + +#: modules/commands/os_session.cpp:145 modules/commands/os_session.cpp:490 +msgid "No matching entries on session-limit exception list." +msgstr "Nie znaleziono wpisów na liście wyjątków limitów sesji." + +#: modules/commands/os_sxline.cpp:28 modules/commands/os_sxline.cpp:177 +#, c-format +msgid "No matching entries on the %s list." +msgstr "Nie znaleziono wpisów w liście %s." + +#: modules/commands/os_akill.cpp:29 modules/commands/os_akill.cpp:320 +msgid "No matching entries on the AKILL list." +msgstr "Nie znaleziono pasujących wpisów na liście AKILL." + +#: modules/commands/ms_cancel.cpp:77 +msgid "No memo was cancelable." +msgstr "Brak wiadomości do odwołania." + +#: modules/commands/ms_read.cpp:65 +msgid "No memos to display." +msgstr "Brak wpisów do wyświetlenia." + +#: modules/commands/os_modinfo.cpp:187 +msgid "No modules currently loaded matching that criteria." +msgstr "Aktualnie nie ma załadowanych modułów spełniających kryteria." + +#: modules/commands/ns_recover.cpp:55 +msgid "No one is using your nick, and services are not holding it." +msgstr "Twój nick nie jest używany przez nikogo, ani blokowany przez serwisy." + +#: modules/commands/os_login.cpp:30 modules/commands/os_login.cpp:77 +msgid "No oper block for your nick." +msgstr "Brak bloku oper dla Twojego nicka." + +#: modules/commands/os_news.cpp:47 +msgid "No oper news items to delete!" +msgstr "Nie ma wiadomości dla operatorów do skasowania!" + +#: modules/commands/os_news.cpp:57 +msgid "No random news items to delete!" +msgstr "Nie ma losowych wiadomości do skasowania!" + +#: modules/commands/hs_list.cpp:111 +msgid "No records to display." +msgstr "Brak wpisów do wyświetlenia." + +#: modules/commands/ns_getemail.cpp:47 +#, c-format +msgid "No registrations matching %s were found." +msgstr "Brak wpisów pasujących do %s." + +#: modules/commands/hs_request.cpp:220 modules/commands/hs_request.cpp:276 +#, c-format +msgid "No request for nick %s found." +msgstr "Nie znaleziono próśb od nicka %s." + +#: src/access.cpp:55 +msgid "No signed kick when SIGNKICK LEVEL is used" +msgstr "Brak podpisanych kopnięć gdy użyto poziomu SIGNKICK" + +#: modules/extra/stats/cs_fantasy_stats.cpp:156 +#: modules/extra/stats/cs_fantasy_top.cpp:159 +#, c-format +msgid "No stats for %s." +msgstr "Brak statystyk dla %s." + +#: modules/commands/os_info.cpp:201 +#, c-format +msgid "No such info \"%s\" on %s." +msgstr "Nie ma informacji \"%s\" dla %s." + +#: modules/commands/cs_ban.cpp:222 modules/commands/cs_kick.cpp:118 +#, c-format +msgid "No users on %s match %s." +msgstr "Żaden użytkownik na %s nie pasuje do %s." + +#: modules/commands/bs_assign.cpp:188 +#, c-format +msgid "No-bot mode is now off on channel %s." +msgstr "Opcja NOBOT została wyłączona na kanale %s." + +#: modules/commands/bs_assign.cpp:181 +#, c-format +msgid "No-bot mode is now on on channel %s." +msgstr "Opcja NOBOT została włączona na kanale %s." + +#: modules/commands/os_mode.cpp:64 +#, c-format +msgid "Non-status modes cleared on %s." +msgstr "Usunięto wszystkie tryby nie dotyczące uprawnień użytkowników na kanale %s." + +#: modules/commands/os_dns.cpp:226 modules/commands/bs_info.cpp:58 +msgid "None" +msgstr "Brak" + +#: modules/commands/cs_set.cpp:1029 +#, c-format +msgid "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." +msgstr "" +"W przypadku, gdy następca już posiada zbyt wiele (%d)\n" +"zarejestrowanych kanałów, nie będzie on mógł zostać\n" +"nowym właścicielem. W takiej sytuacji przekazanie własności\n" +"zadziała tak, jak gdyby żaden spadkobierca nie był ustawiony." + +#: modules/commands/cs_mode.cpp:380 modules/commands/cs_mode.cpp:437 +msgid "Nothing to do." +msgstr "Brak działań do wykonania." + +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/ns_ajoin.cpp:100 +#: modules/commands/os_news.cpp:156 modules/commands/os_session.cpp:506 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:358 modules/commands/hs_request.cpp:305 +#: modules/commands/cs_log.cpp:127 modules/commands/hs_list.cpp:58 +#: modules/commands/ns_alist.cpp:48 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/ms_list.cpp:64 +#: modules/commands/bs_badwords.cpp:194 modules/commands/cs_xop.cpp:377 +#: modules/commands/cs_flags.cpp:301 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 +msgid "Number" +msgstr "Liczba" + +#: modules/commands/os_news.cpp:41 +msgid "OPERNEWS {ADD|DEL|LIST} [text|num]" +msgstr "OPERNEWS {ADD|DEL|LIST} [tekst|numer]" + +#: modules/commands/ns_info.cpp:69 modules/commands/ns_info.cpp:73 +msgid "Online from" +msgstr "Jest online z" + +#: modules/commands/os_oper.cpp:138 +#, c-format +msgid "" +"Oper %s is configured in the configuration file(s) and can not be removed by this " +"command." +msgstr "" +"Operator %s jest dodany w pliku konfiguracyjnym, więc nie można usunąć go tym " +"poleceniem." + +#: modules/commands/os_info.cpp:268 +msgid "Oper Info" +msgstr "Informacje Oper" + +#: modules/commands/os_info.cpp:182 modules/commands/os_info.cpp:221 +#, c-format +msgid "Oper info list for %s is empty." +msgstr "Lista dostępu operatorów dla %s jest pusta." + +#: modules/commands/os_news.cpp:46 +#, c-format +msgid "Oper news item #%d deleted." +msgstr "Wiadomość dla operatorów #%d została skasowana." + +#: modules/commands/os_news.cpp:45 +#, c-format +msgid "Oper news item #%s not found!" +msgstr "Wiadomość dla operatorów #%s nie została znaleziona!" + +#: modules/commands/os_news.cpp:42 +msgid "Oper news items:" +msgstr "Wiadomości dla operatorów:" + +#: modules/commands/os_oper.cpp:148 +#, c-format +msgid "Oper privileges removed from %s (%s)." +msgstr "Uprawnienia operatora zostały odebrane użytkownikowi %s (%s)." + +#: modules/commands/os_oper.cpp:101 modules/commands/os_oper.cpp:189 +#, c-format +msgid "Oper type %s has not been configured." +msgstr "Typ operatora %s nie jest skonfigurowany." + +#: modules/commands/os_oline.cpp:37 +#, c-format +msgid "Operflags %s have been added for %s." +msgstr "Flagi operatora %s zostały przyznane dla %s." + +#: modules/commands/os_oline.cpp:43 +#, c-format +msgid "Operflags %s have been removed from %s." +msgstr "Flagi operatora %s zostały zabrane %s." + +#: modules/commands/os_oper.cpp:193 +#, c-format +msgid "Opertype %s has no allowed commands." +msgstr "Typ operatora %s nie posiada żadnych dozwolonych komend." + +#: modules/commands/os_oper.cpp:215 +#, c-format +msgid "Opertype %s has no allowed privileges." +msgstr "Typ operatora %s nie posiada żadnych uprawnień." + +#: modules/commands/os_oper.cpp:237 +#, c-format +msgid "Opertype %s receives modes %s once identified." +msgstr "Typ operatora %s otrzymuje tryby %s po zalogowaniu." + +#: modules/commands/bs_kick.cpp:1219 +msgid "Ops protection" +msgstr "DONTKICKOPS" + +#: src/misc.cpp:258 modules/commands/bs_info.cpp:58 +msgid "Options" +msgstr "Opcje" + +#: modules/commands/os_dns.cpp:668 +msgid "POOL server.name" +msgstr "POOL nazwa.serwera" + +#: modules/commands/cs_mode.cpp:449 +msgid "Param" +msgstr "Parametr" + +#: modules/commands/ns_identify.cpp:38 +msgid "Password accepted - you are now recognized." +msgstr "Hasło przyjęte - jesteś zidentyfikowany(a)." + +#: modules/commands/os_login.cpp:44 +msgid "Password accepted." +msgstr "Hasło przyjęte." + +#: modules/commands/ns_set.cpp:152 modules/commands/ns_set.cpp:218 +#, c-format +msgid "Password for %s changed to %s." +msgstr "Hasło dla %s zmieniono na %s" + +#: modules/commands/ns_set.cpp:154 modules/commands/ns_set.cpp:220 +#, c-format +msgid "Password for %s changed." +msgstr "Hasło dla %s zmienione." + +#: modules/commands/ns_getpass.cpp:38 +#, c-format +msgid "Password for %s is %s." +msgstr "Hasło dla %s to %s." + +#: include/language.h:71 +msgid "Password incorrect." +msgstr "Nieprawidłowe hasło." + +#: modules/commands/ns_resetpass.cpp:39 +#, c-format +msgid "Password reset email for %s has been sent." +msgstr "Wysłano wiadomość e-mail służącą resetowaniu hasła dla %s." + +#: modules/commands/cs_set.cpp:1289 +msgid "Peace" +msgstr "PEACE" + +#: modules/commands/cs_set.cpp:440 +#, c-format +msgid "Peace option for %s is now off." +msgstr "Opcja PEACE dla kanału %s została wyłączona." + +#: modules/commands/cs_set.cpp:434 +#, c-format +msgid "Peace option for %s is now on." +msgstr "Opcja PEACE dla kanału %s została włączona." + +#: modules/commands/cs_set.cpp:1301 +msgid "Persistent" +msgstr "Trwały" + +#: include/language.h:126 +msgid "Please contact an Operator to get a vHost assigned to this nick." +msgstr "Proszę o kontakt z operatorem, aby uzyskać vHosta dla tego nicka." + +#: include/language.h:73 +msgid "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." +msgstr "" +"Proszę spróbować ponownie, używając trudniejszego hasła. Hasło powinno\n" +"składać się co najmniej z 5 znaków, nie powinno być łatwe do odgadnięcia\n" +"(na przykład Twoje imię bądź nick), i nie może zawierać spacji albo znaków Tab." + +#: modules/commands/os_jupe.cpp:30 +msgid "Please use a valid server name when juping." +msgstr "Proszę użyć prawidłowej nazwy serwera." + +#: include/language.h:104 +msgid "Please use the symbol of # when attempting to register." +msgstr "Proszę używać symbolu # przy próbie rejestracji." + +#: src/mail.cpp:78 +#, c-format +msgid "Please wait %d seconds and retry." +msgstr "Proszę odczekać %d sekund(y) i ponowić próbę." + +#: modules/commands/hs_request.cpp:158 +#, c-format +msgid "Please wait %d seconds before requesting a new vHost." +msgstr "Odczekaj %d sekund(y) przed ponowną prośbą o vHosta." + +#: modules/commands/ms_send.cpp:57 modules/commands/ms_rsend.cpp:58 +#, c-format +msgid "Please wait %d seconds before using the %s command again." +msgstr "Odczekaj %d sekund(y) przed ponownym użyciem komendy %s." + +#: modules/commands/ns_group.cpp:149 +#, c-format +msgid "Please wait %d seconds before using the GROUP command again." +msgstr "Odczekaj %d sekund przed ponownym użyciem komendy GROUP." + +#: modules/commands/ns_register.cpp:200 +#, c-format +msgid "Please wait %d seconds before using the REGISTER command again." +msgstr "Odczekaj %d sekund przed ponownym użyciem komendy REGISTER." + +#: modules/commands/os_dns.cpp:628 +#, c-format +msgid "Pooled %s." +msgstr "%s dodany do puli." + +#: modules/commands/os_dns.cpp:237 +msgid "Pooled/Active" +msgstr "Dodany do puli - aktywny" + +#: modules/commands/os_dns.cpp:239 +msgid "Pooled/Not Active" +msgstr "Nieobecny w puli - nieaktywny" + +#: modules/commands/bs_set.cpp:161 +msgid "Prevent a bot from being assigned by non IRC operators" +msgstr "Zezwalaj na przydzielenie bota tylko przez IRCoperatorów" + +#: modules/commands/bs_assign.cpp:153 +msgid "Prevent a bot from being assigned to a channel" +msgstr "Uniemożliwia przypisanie bota do kanału" + +#: modules/commands/cs_suspend.cpp:58 +msgid "Prevent a channel from being used preserving channel data and settings" +msgstr "Blokuje podany kanał z zachowaniem wszelkich jego danych i ustawień" + +#: modules/commands/cs_set.cpp:1043 +msgid "Prevent the channel from expiring" +msgstr "Uniemożliwia wygaśnięcie kanału" + +#: modules/commands/ns_list.cpp:186 +msgid "Prevent the nickname from appearing in the LIST command" +msgstr "Zapobiega wyświetlaniu nicka po wydaniu polecenia LIST" + +#: modules/commands/ns_set.cpp:1104 +msgid "Prevent the nickname from expiring" +msgstr "Zapobiega wygaśnięciu nicka" + +#: src/access.cpp:46 +msgid "Prevents users being kicked by Services" +msgstr "Zabrania kopania użytkowników przez serwisy" + +#: modules/commands/ns_list.cpp:297 modules/commands/bs_info.cpp:58 +#: modules/commands/cs_list.cpp:262 +msgid "Private" +msgstr "PRIVATE" + +#: modules/commands/bs_set.cpp:190 +#, c-format +msgid "Private mode of bot %s is now off." +msgstr "Opcja PRIVATE bota %s została wyłączona." + +#: modules/commands/bs_set.cpp:185 +#, c-format +msgid "Private mode of bot %s is now on." +msgstr "Opcja PRIVATE bota %s została włączona." + +#: modules/commands/cs_list.cpp:220 +#, c-format +msgid "Private option for %s is now off." +msgstr "Opcja PRIVATE dla kanału %s została wyłączona." + +#: modules/commands/cs_list.cpp:214 +#, c-format +msgid "Private option for %s is now on." +msgstr "Opcja PRIVATE dla kanału %s została włączona." + +#: modules/commands/ns_list.cpp:221 +#, c-format +msgid "Private option is now off for %s." +msgstr "Opcja prywatności dla %s została wyłączona." + +#: modules/commands/ns_list.cpp:215 +#, c-format +msgid "Private option is now on for %s." +msgstr "Opcja prywatności dla %s została włączona." + +#: modules/commands/cs_flags.cpp:281 +#, c-format +msgid "Privilege %s added to %s on %s, new flags are +%s" +msgstr "Uprawnienie %s dodane do %s na %s. Nowe flagi: +%s" + +#: modules/commands/cs_flags.cpp:283 +#, c-format +msgid "Privilege %s removed from %s on %s, new flags are +%s" +msgstr "Uprawnienie %s usunięte z %s na %s. Nowe flagi: +%s" + +#: modules/commands/ns_set.cpp:1309 +msgid "Protection" +msgstr "KILL" + +#: modules/commands/ns_set.cpp:721 +#, c-format +msgid "Protection is now off for %s." +msgstr "Ochrona dla %s jest teraz wyłączona." + +#: modules/commands/ns_set.cpp:700 +#, c-format +msgid "Protection is now on for %s, with a reduced delay." +msgstr "Ochrona dla %s ze zredukowanym opóźnieniem jest teraz włączona." + +#: modules/commands/ns_set.cpp:710 +#, c-format +msgid "Protection is now on for %s, with no delay." +msgstr "Natychmiastowa ochrona dla %s jest teraz włączona." + +#: modules/commands/ns_set.cpp:692 +#, c-format +msgid "Protection is now on for %s." +msgstr "Ochrona dla %s jest teraz włączona." + +#: modules/commands/os_chankill.cpp:100 +msgid "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." +msgstr "" +"Zakłada AKILLa na każdy nick na wskazanym kanale.\n" +"Na listę zostają dodane prawdziwe adresy (ident@host),\n" +"po czym AKILL zostaje wykonany." + +#: modules/commands/ns_set.cpp:1307 +msgid "Quick protection" +msgstr "Szybka ochrona" + +#: modules/commands/os_news.cpp:51 +msgid "RANDOMNEWS {ADD|DEL|LIST} [text|num]" +msgstr "RANDOMNEWS {ADD|DEL|LIST} [tekst|numer]" + +#: modules/commands/cs_enforce.cpp:99 +msgid "REGONLY enforced by " +msgstr "REGONLY wymuszony przez " + +#: modules/commands/cs_enforce.cpp:68 +msgid "RESTRICTED enforced by " +msgstr "RESTRICTED wymuszony przez " + +#: modules/commands/os_noop.cpp:21 +msgid "REVOKE server" +msgstr "REVOKE serwer" + +#: modules/commands/os_news.cpp:56 +#, c-format +msgid "Random news item #%d deleted." +msgstr "Losowa wiadomość #%d została skasowana." + +#: modules/commands/os_news.cpp:55 +#, c-format +msgid "Random news item #%s not found!" +msgstr "Losowa wiadomość #%s nie została znaleziona!" + +#: modules/commands/os_news.cpp:52 +msgid "Random news items:" +msgstr "Losowe wiadomości:" + +#: modules/commands/ms_read.cpp:112 +msgid "Read a memo or memos" +msgstr "Wyświetla jedną lub więcej wiadomości" + +#: modules/commands/bs_info.cpp:56 +msgid "Real name" +msgstr "Nazwa" + +#: modules/commands/os_list.cpp:153 +msgid "Realname" +msgstr "Nazwa" + +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:204 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:361 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_ignore.cpp:266 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 +msgid "Reason" +msgstr "Powód" + +#: src/xline.cpp:386 +#, c-format +msgid "Reason for %s updated." +msgstr "Zaktualizowano powód dla %s." + +#: modules/commands/ns_recover.cpp:214 +msgid "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." +msgstr "" +"Odzyskuje Twój nick od innego użytkownika lub od serwisów.\n" +"Jeżeli serwisy akurat blokują Twojego nicka, blokada zostanie\n" +"zwolniona. Jeśli inny użytkownik korzysta z Twojego nicka\n" +"i jest zalogowany, zostanie rozłączony (podobnie do starego\n" +"polecenia GHOST). Jeżeli jednak nie był zalogowany, wtedy\n" +"zostanie zmuszony do zmiany nicka." + +#: modules/commands/cs_access.cpp:741 +msgid "Redefine the meanings of access levels" +msgstr "Zarządza poziomami dostępu" + +#: modules/commands/ns_recover.cpp:149 +msgid "Regains control of your nick" +msgstr "Odzyskuje dostęp do Twojego nicka" + +#: modules/commands/os_sxline.cpp:330 modules/commands/os_sxline.cpp:545 +#: modules/commands/os_akill.cpp:129 +msgid "Regex is disabled." +msgstr "Regex wyłączony." + +#: modules/commands/os_sxline.cpp:459 modules/commands/os_sxline.cpp:694 +#: modules/commands/os_akill.cpp:444 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." +msgstr "" +"Wyrażenia regularne są obsługiwane także za pomocą silnika %s.\n" +"Umieść swoją maskę wewnątrz znaków // " + +#: modules/commands/os_forbid.cpp:428 modules/commands/os_ignore.cpp:386 +#: modules/commands/os_list.cpp:119 modules/commands/os_list.cpp:255 +#: modules/commands/ns_list.cpp:172 modules/commands/cs_list.cpp:167 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." +msgstr "" +"Wyrażenia regularne są obsługiwane także za pomocą silnika %s.\n" +"Aby z tego skorzystać, umieść swoje wyrażenie wewnątrz znaków //" + +#: modules/commands/cs_register.cpp:19 +msgid "Register a channel" +msgstr "Rejestruje kanał" + +#: modules/commands/ns_register.cpp:120 +msgid "Register a nickname" +msgstr "Rejestruje nicka" + +#: modules/commands/ns_info.cpp:90 modules/commands/cs_info.cpp:55 +msgid "Registered" +msgstr "Zarejestrowano" + +#: modules/commands/os_stats.cpp:184 +#, c-format +msgid "Registered channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "Zarejestrowane kanały: %lu wpisów, %lu pakietów, najdłuższy łańcuch to %d" + +#: modules/commands/os_stats.cpp:190 +#, c-format +msgid "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" +msgstr "" +"Zarejestrowane grupy nicków: %lu wpisów, %lu pakietów, najdłuższy łańcuch to %d" + +#: modules/commands/os_stats.cpp:187 +#, c-format +msgid "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" +msgstr "Zarejestrowane nicki: %lu wpisów, %lu pakietów, najdłuższy łańcuch to %d" + +#: modules/commands/cs_enforce.cpp:105 +#, c-format +msgid "Registered only enforced on %s." +msgstr "Wymuszono dostęp tylko dla zarejestrowanych na %s." + +#: modules/commands/cs_register.cpp:86 +#, c-format +msgid "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." +msgstr "" +"Rejestruje kanał w bazie %s. Aby użyć tego polecenia,\n" +"musisz być operatorem na kanale, który chcesz zarejestrować.\n" +"Opis (opcjonalny) to ogólna informacja o przeznaczeniu kanału.\n" +" \n" +"Gdy zarejestrujesz kanał, zostaniesz zapisany jako jego\n" +"\"założyciel\". Założyciel kanału może zmieniać wszystkie jego\n" +"ustawienia; otrzyma także od %s uprawnienia właściciela\n" +"i operatora za każdym razem, gdy dołączy do kanału." + +#: modules/commands/ns_register.cpp:271 +#, c-format +msgid "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." +msgstr "" +"Rejestruje aktualnie używany nick w bazie %s.\n" +"Po rejestracji możesz użyć komend SET i ACCESS\n" +"do konfiguracji niektórych opcji nicka wedle upodobań.\n" +"Upewnij się, że pamiętasz hasło rejestracyjne, bo \n" +"będzie ono potrzebne w przyszłości do zmiany\n" +"ustawień i identyfikacji. Wielkość liter w haśle \n" +"ma znaczenie!!!.\n" +"\n" +"Jak wybrać hasło?\n" +"\n" +"Hasło musi być trudne do odgadnięcia. Używanie imion\n" +"jako haseł jest niewskazane. Nie wolno użyć hasła takiego\n" +"samego, jak nick (a %s na to nie pozwoli). Bardzo krótkie\n" +"hasło może zostać odgadnięte metodą prób i błędów.\n" +"Twoje hasło musi mieć długość co najmniej 5 znaków.\n" +"Znak spacji nie może być użyty w haśle." + +#: modules/commands/ns_register.cpp:145 +msgid "Registration is currently disabled." +msgstr "Rejestracja jest tymczasowo wyłączona." + +#: modules/commands/cs_set.cpp:400 +msgid "Regulate the use of critical commands" +msgstr "Reguluje użycie krytycznych komend" + +#: modules/commands/hs_request.cpp:283 +msgid "Reject the requested vHost for the given nick." +msgstr "Odrzuca prośbę o vHosta dla podanego nicka." + +#: modules/commands/hs_request.cpp:240 +msgid "Reject the requested vHost of a user" +msgstr "Odrzuca prośbę o vHosta użytkownika" + +#: modules/commands/cs_suspend.cpp:151 +msgid "Releases a suspended channel" +msgstr "Uwalnia zawieszony kanał" + +#: modules/commands/cs_suspend.cpp:191 +msgid "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." +msgstr "" +"Uwalnia zawieszony kanał. Wszystkie dane i ustawienia\n" +"są odtworzone sprzed zawieszenia." + +#: modules/commands/os_module.cpp:56 +msgid "Reload a module" +msgstr "Przeładowuje moduł" + +#: modules/commands/os_reload.cpp:19 +msgid "Reload services' configuration file" +msgstr "Ładuje na nowo plik konfiguracyjny" + +#: modules/commands/ns_group.cpp:236 +msgid "Remove a nick from a group" +msgstr "Usuwa nick z grupy" + +#: modules/commands/cs_unban.cpp:19 +msgid "Remove all bans preventing a user from entering a channel" +msgstr "Usuwa wszystkie bany uniemożliwiające użytkownikowi wejście na kanał" + +#: modules/commands/os_noop.cpp:19 +msgid "Remove all operators from a server remotely" +msgstr "Zdalnie usuwa wszystkich operatorów z serwera" + +#: modules/commands/os_dns.cpp:543 +#, c-format +msgid "Removed IP %s from %s." +msgstr "Usunięto IP %s z %s." + +#: modules/commands/os_dns.cpp:460 +#, c-format +msgid "Removed server %s from zone %s." +msgstr "Usunięto serwer %s ze strefy %s." + +#: modules/commands/os_dns.cpp:483 +#, c-format +msgid "Removed server %s." +msgstr "Usunięto serwer %s." + +#: modules/commands/cs_mode.cpp:909 +#, c-format +msgid "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." +msgstr "" +"Odbiera status %s podanemu nickowi na kanale. Jeśli nick\n" +"nie będzie podany, %s zostanie odebrany Tobie." + +#: modules/commands/cs_mode.cpp:890 +#, c-format +msgid "Removes %s status from you or the specified nick on a channel" +msgstr "Usuwa status %s dla Twojego lub podanego nicka na kanale" + +#: modules/commands/cs_updown.cpp:146 +msgid "Removes a selected nicks status from a channel" +msgstr "Odbiera podanym nickom uprawnienia na kanale" + +#: modules/commands/cs_updown.cpp:223 +msgid "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." +msgstr "" +"Odbiera podanym nickom uprawnienia na kanale. Gdy nick\n" +"nie zostanie podany, wtedy odebrane zostaną Twoje uprawnienia.\n" +"Gdy pominięty zostanie kanał, wtedy odebrane zostaną Twoje\n" +"uprawnienia na wszystkich kanałach, na których się znajdujesz." + +#: src/xline.cpp:412 +#, c-format +msgid "Removing %s because %s covers it." +msgstr "Usuwam %s, ponieważ jest objęty przez %s." + +#: modules/commands/bs_kick.cpp:1171 modules/commands/bs_kick.cpp:1173 +#: modules/commands/bs_kick.cpp:1176 +msgid "Repeat kicker" +msgstr "Kopanie za powtarzanie" + +#: modules/commands/hs_request.cpp:78 +msgid "Request a vHost for your nick" +msgstr "Prośba o vHosta dla Twojego nicka" + +#: modules/commands/hs_request.cpp:179 +msgid "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." +msgstr "" +"Poproś o przydzielenie vHosta dla twojego nicka przez\n" +"administratorów sieci. Proszę o cierpliwość, gdy Twoja prośba\n" +"czeka na rozpatrzenie." + +#: modules/commands/ns_register.cpp:314 +msgid "Resend registration confirmation email" +msgstr "Ponownie wysyła e-maila potwierdzającego rejestrację" + +#: modules/commands/cs_set.cpp:621 +msgid "Restrict access to the channel" +msgstr "Ogranicza dostęp do kanału" + +#: modules/commands/cs_set.cpp:1291 +msgid "Restricted access" +msgstr "RESTRICTED" + +#: modules/commands/cs_set.cpp:661 +#, c-format +msgid "Restricted access option for %s is now off." +msgstr "Dostęp do kanału %s nie jest teraz ograniczony." + +#: modules/commands/cs_set.cpp:655 +#, c-format +msgid "Restricted access option for %s is now on." +msgstr "Dostęp do kanału %s jest teraz ograniczony." + +#: modules/commands/cs_enforce.cpp:73 +#, c-format +msgid "Restricted enforced on %s." +msgstr "Wymuszono RESTRICTED na %s." + +#: modules/commands/cs_set.cpp:335 +msgid "Retain modes when channel is not in use" +msgstr "Zapamiętuje flagi kiedy kanał jest pusty" + +#: modules/commands/cs_topic.cpp:20 +msgid "Retain topic when channel is not in use" +msgstr "Zapamiętuje temat kiedy kanał jest pusty" + +#: modules/commands/ns_getpass.cpp:19 +msgid "Retrieve the password for a nickname" +msgstr "Podaje hasło do wskazanego nicka" + +#: modules/commands/hs_request.cpp:296 +msgid "Retrieves the vhost requests" +msgstr "Wyświetla prośby o vHosta" + +#: modules/commands/cs_getkey.cpp:19 +msgid "Returns the key of the given channel" +msgstr "Podaje klucz do wskazanego kanału" + +#: modules/commands/cs_getkey.cpp:57 +msgid "Returns the key of the given channel." +msgstr "Podaje klucz do wskazanego kanału." + +#: modules/commands/ns_getemail.cpp:58 +msgid "Returns the matching accounts that used given email." +msgstr "Podaje konta, które używają wskazanego e-maila." + +#: modules/commands/ns_status.cpp:19 +msgid "Returns the owner status of the given nickname" +msgstr "Podaje status właściciela podanego nicka" + +#: modules/commands/ns_getpass.cpp:50 +msgid "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." +msgstr "" +"Zwraca hasło dla wskazanego nicka.\n" +"UWAGA: użycie tej komendy powoduje wysłanie\n" +"informacji o jej użyciu przy pomocy WALLOP/GLOBOP." + +#: modules/commands/ns_status.cpp:55 +msgid "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." +msgstr "" +"Zwraca status wskazanych użytkowników (czy są\n" +"rozpoznawani jako właściciele nicka).\n" +"Odpowiedź ma następujący format:\n" +"\n" +" nick kod konto\n" +"\n" +"gdzie nick jest żądanym nickiem,\n" +"kod jest jednym z poniższych, a konto\n" +"to nazwa konta, na którym jest zalogowany.\n" +"\n" +"0 - użytkownik jest offline lub nick niezarejestrowany\n" +"1 - użytkownik nie zidentyfikował się jako właściciel nicka\n" +"2 - użytkownik rozpoznany na podstawie listy dostępu\n" +"3 - użytkownik rozpoznany na podstawie hasła\n" +"\n" +"Maksymalnie można podać 16 nicków w jednym poleceniu.\n" +"Reszta będzie ignorowana. Jeśli nie zostanie podany\n" +"żaden nick, zostanie zwrócony Twój status." + +#: modules/commands/bs_kick.cpp:1181 modules/commands/bs_kick.cpp:1183 +#: modules/commands/bs_kick.cpp:1186 +msgid "Reverses kicker" +msgstr "Kopanie za odw kolorów" + +#: modules/commands/ns_logout.cpp:21 +msgid "Reverses the effect of the IDENTIFY command" +msgstr "Odwraca działanie komendy IDENTIFY" + +#: modules/commands/os_noop.cpp:20 +msgid "SET server" +msgstr "SET serwer" + +#: modules/commands/os_dns.cpp:667 +msgid "SET server.name option value" +msgstr "SET nazwa.serwera opcje wartość" + +#: modules/commands/ns_cert.cpp:378 +#, c-format +msgid "SSL certificate fingerprint accepted, you are now identified to %s." +msgstr "Certyfikat SSL przyjęty - jesteś zidentyfikowany(a) jako %s." + +#: modules/commands/ns_cert.cpp:398 +msgid "SSL certificate fingerprint accepted, you are now identified." +msgstr "Certyfikat przyjęty - jesteś zidentyfikowany(a)." + +#: modules/commands/cs_enforce.cpp:137 +#, c-format +msgid "SSL only enforced on %s." +msgstr "Wymuszono SSL na %s." + +#: modules/commands/cs_enforce.cpp:131 +msgid "SSLONLY enforced by " +msgstr "SSLONLY wymuszony przez " + +#: modules/commands/os_shutdown.cpp:47 +msgid "Save databases and restart Services" +msgstr "Zapisuje bazy i restartuje serwisy" + +#: modules/commands/os_logsearch.cpp:32 +msgid "Searches logs for a matching pattern" +msgstr "Przeszukuje logi pod kątem wyrażenia" + +#: modules/commands/cs_set.cpp:1295 +msgid "Secure founder" +msgstr "SECUREFOUNDER" + +#: modules/commands/cs_set.cpp:786 +#, c-format +msgid "Secure founder option for %s is now off." +msgstr "Status właściciela kanału %s nie będzie teraz chroniony." + +#: modules/commands/cs_set.cpp:780 +#, c-format +msgid "Secure founder option for %s is now on." +msgstr "Status właściciela kanału %s będzie teraz chroniony." + +#: modules/commands/cs_set.cpp:1297 +msgid "Secure ops" +msgstr "SECUREOPS" + +#: modules/commands/cs_set.cpp:850 +#, c-format +msgid "Secure ops option for %s is now off." +msgstr "Status operatora kanału %s nie będzie teraz chroniony." + +#: modules/commands/cs_set.cpp:844 +#, c-format +msgid "Secure ops option for %s is now on." +msgstr "Status operatora kanału %s będzie teraz chroniony." + +#: modules/commands/cs_set.cpp:723 +#, c-format +msgid "Secure option for %s is now off." +msgstr "Opcja bezpieczeństwa dla kanału %s została wyłączona." + +#: modules/commands/cs_set.cpp:717 +#, c-format +msgid "Secure option for %s is now on." +msgstr "Opcja bezpieczeństwa dla kanału %s została włączona." + +#: modules/commands/ns_set.cpp:1044 +#, c-format +msgid "Secure option is now off for %s." +msgstr "Opcja bezpieczeństwa dla %s została wyłączona." + +#: modules/commands/ns_set.cpp:1038 +#, c-format +msgid "Secure option is now on for %s." +msgstr "Opcja bezpieczeństwa dla %s została włączona." + +#: modules/commands/cs_enforce.cpp:42 +#, c-format +msgid "Secureops enforced on %s." +msgstr "Opcja bezpieczeństwa dla %s została wymuszona." + +#: modules/commands/ns_set.cpp:1311 modules/commands/cs_set.cpp:1293 +msgid "Security" +msgstr "SECURE" + +#: modules/commands/cs_xop.cpp:570 +#, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the access list." +msgstr "" +"Aby uzyskać więcej informacji o liście dostępowej wpisz:\n" +"%s%s HELP %s" + +#: modules/commands/cs_xop.cpp:573 +#, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the flags system." +msgstr "" +"Aby uzyskać więcej informacji o systemie flag, wpisz:\n" +"%s%s HELP S%s" + +#: modules/commands/ms_send.cpp:24 +msgid "Send a memo to a nick or channel" +msgstr "Wysyła wiadomość do użytkownika/kanału" + +#: modules/commands/ms_staff.cpp:24 +msgid "Send a memo to all opers/admins" +msgstr "Wysyła wiadomość do wszystkich operatorów/administratorów" + +#: modules/commands/ms_sendall.cpp:24 +msgid "Send a memo to all registered users" +msgstr "Wysyła wiadomość do wszystkich zarejestrowanych użytkowników" + +#: modules/commands/gl_global.cpp:21 +msgid "Send a message to all users" +msgstr "Wysyła wiadomość do wszystkich użytkowników" + +#: modules/commands/ms_list.cpp:64 +msgid "Sender" +msgstr "Wysyłający" + +#: modules/commands/ms_rsend.cpp:24 +msgid "Sends a memo and requests a read receipt" +msgstr "Wysyła wiadomość z żądaniem potwierdzenia odbioru" + +#: modules/commands/ns_resetpass.cpp:50 +msgid "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." +msgstr "" +"Wysyła kod potwierdzający dla tego nicka, z instrukcją,\n" +"w jaki sposób można zresetować hasło. Adres e-mail\n" +"musi być zgodny z przypisanym do nicka." + +#: modules/commands/ms_sendall.cpp:52 +msgid "Sends all registered users a memo containing memo-text." +msgstr "Wysyła wiadomość do wszystkich zarejestrowanych użytkowników." + +#: modules/commands/ms_staff.cpp:48 +msgid "Sends all services staff a memo containing memo-text." +msgstr "" +"Wysyła wiadomość o podanej treści do wszystkich\n" +"operatorów i administratorów serwisów." + +#: modules/commands/ms_send.cpp:66 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." +msgstr "" +"Wysyła wiadomość wskazanej osobie lub na podany kanał.\n" +"Po wysłaniu odbiorca otrzyma powiadomienie o nowej\n" +"wiadomości (o ile ma włączone powiadomienia).\n" +"Adresatem musi być zarejestrowany nick lub kanał." + +#: modules/commands/ms_rsend.cpp:80 +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." +msgstr "" +"Wysyła wiadomość wskazanej osobie lub na podany kanał.\n" +"Po wysłaniu odbiorca otrzyma powiadomienie o nowej\n" +"wiadomości (o ile ma włączone powiadomienia).\n" +"Adresatem musi być zarejestrowany nick lub kanał.\n" +"Kiedy wiadomość zostanie przeczytana przez odbiorcę\n" +"automatyczne potwierdzenie odbioru zostanie wysłane\n" +"do nadawcy." + +#: modules/commands/ms_read.cpp:199 +msgid "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Wyświetla tekst wskazanej wiadomości. Parametr LAST\n" +"oznacza ostatnią z wiadomości, NEW wyświetla wszystkie\n" +"nieprzeczytane wiadomości, natomiast ALL wyświetla wszystkie.\n" +"Gdy podany zostanie numer, wyświetlona będzie wiadomość\n" +"o podanym numerze. Można także podawać listę wiadomości np.:\n" +"\n" +" READ 2-5,7-9\n" +" Wyświetli wiadomości od numeru 2 do 5 oraz od 7 do 9." + +#: modules/commands/os_dns.cpp:218 +msgid "Server" +msgstr "Serwer" + +#: modules/commands/os_dns.cpp:375 +#, c-format +msgid "Server %s added to zone %s." +msgstr "Serwer %s dodany do strefy %s." + +#: modules/commands/os_dns.cpp:345 +#, c-format +msgid "Server %s already exists." +msgstr "Serwer %s już istnieje." + +#: modules/commands/os_dns.cpp:430 modules/commands/os_dns.cpp:493 +#: modules/commands/os_dns.cpp:532 modules/commands/os_dns.cpp:571 +#: modules/commands/os_dns.cpp:604 modules/commands/os_dns.cpp:639 +#: modules/commands/os_noop.cpp:31 +#, c-format +msgid "Server %s does not exist." +msgstr "Serwer %s nie istnieje." + +#: modules/commands/os_dns.cpp:619 +#, c-format +msgid "Server %s has no configured IPs." +msgstr "Serwer %s nie ma ustawionych adresów IP." + +#: modules/commands/os_dns.cpp:357 +#, c-format +msgid "Server %s is already in zone %s." +msgstr "Serwer %s jest już w strefie %s." + +#: modules/commands/os_dns.cpp:614 +#, c-format +msgid "Server %s is already pooled." +msgstr "Serwer %s jest już w puli roboczej." + +#: modules/commands/os_dns.cpp:609 +#, c-format +msgid "Server %s is not currently linked." +msgstr "Serwer %s nie jest aktualnie podłączony." + +#: modules/commands/os_dns.cpp:443 +#, c-format +msgid "Server %s is not in zone %s." +msgstr "Serwera %s nie ma w strefie %s." + +#: modules/commands/os_dns.cpp:384 +#, c-format +msgid "Server %s is not linked to the network." +msgstr "Serwer %s nie jest połączony z siecią." + +#: modules/commands/os_dns.cpp:644 +#, c-format +msgid "Server %s is not pooled." +msgstr "Serwer %s nie znajduje się w puli roboczej." + +#: modules/commands/os_dns.cpp:465 +#, c-format +msgid "Server %s must be quit before it can be deleted." +msgstr "Serwer %s musi zostać odłączony przed jego usunięciem." + +#: modules/commands/os_dns.cpp:255 +msgid "Servers" +msgstr "Serwery" + +#: modules/commands/os_stats.cpp:155 +#, c-format +msgid "Servers found: %d" +msgstr "Serwerów: %d" + +#: modules/commands/cs_log.cpp:127 +msgid "Service" +msgstr "Usługa" + +#: modules/commands/ns_recover.cpp:51 +#, c-format +msgid "Service's hold on %s has been released." +msgstr "Serwisy właśnie zwolniły nicka %s." + +#: data/nickserv.example.conf:238 data/chanserv.example.conf:827 +msgid "Services Operator commands" +msgstr "Komendy dla operatorów serwisów" + +#: modules/commands/os_defcon.cpp:443 modules/commands/os_defcon.cpp:454 +#: modules/commands/os_defcon.cpp:462 modules/commands/os_defcon.cpp:470 +#: modules/commands/os_defcon.cpp:478 +msgid "Services are in DefCon mode, please try again later." +msgstr "Serwisy są w trybie defcon, spróbuj ponownie później." + +#: include/language.h:70 +msgid "Services are in read-only mode!" +msgstr "Serwisy są teraz w trybie tylko-do-odczytu!" + +#: modules/commands/os_defcon.cpp:186 modules/commands/os_defcon.cpp:213 +#, c-format +msgid "Services are now at DEFCON %d." +msgstr "Serwisy są teraz w trybie DEFCON %d," + +#: modules/commands/os_set.cpp:128 +#, c-format +msgid "Services are now in debug mode (level %d)." +msgstr "Serwisy są teraz w trybie debugowania (poziom %d)." + +#: modules/commands/os_set.cpp:114 +msgid "Services are now in debug mode." +msgstr "Serwisy są teraz w trybie debugowania." + +#: modules/commands/os_set.cpp:159 +msgid "Services are now in expire mode." +msgstr "Serwisy są teraz w trybie wygasania." + +#: modules/commands/os_set.cpp:153 +msgid "Services are now in no expire mode." +msgstr "Serwisy nie są już w trybie wygasania." + +#: modules/commands/os_set.cpp:120 +msgid "Services are now in non-debug mode." +msgstr "Serwisy nie są już w trybie debugowania." + +#: modules/commands/os_set.cpp:47 +msgid "Services are now in read-only mode." +msgstr "Serwisy są teraz w trybie tylko-do-odczytu." + +#: modules/commands/os_set.cpp:53 +msgid "Services are now in read-write mode." +msgstr "Serwisy są teraz w trybie odczyt-zapis." + +#: src/mail.cpp:76 +msgid "Services have been configured to not send mail." +msgstr "Serwisy zostały skonfigurowane tak, aby nie wysyłać poczty." + +#: modules/commands/os_ignore.cpp:280 +msgid "Services ignore list:" +msgstr "Lista ignorowanych przez serwisy:" + +#: modules/commands/os_kick.cpp:39 modules/commands/os_mode.cpp:33 +msgid "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" +msgstr "" +"Serwisy nie mogą zmieniać trybów. Czy U-linie serwerów są dobrze skonfigurowane?" + +#: modules/commands/os_stats.cpp:140 +#, c-format +msgid "Services up %s." +msgstr "Serwisy uruchomione: %s." + +#: modules/commands/ns_set.cpp:266 +#, c-format +msgid "Services will from now on set status modes on %s in channels." +msgstr "" +"Serwisy będą teraz automatycznie nadawały uprawnienia na kanałach dla użytkownika " +"%s." + +#: modules/commands/cs_set.cpp:114 +#, c-format +msgid "Services will no longer automatically give modes to users in %s." +msgstr "" +"Serwisy nie będą już automatycznie nadawały uprawnień dla użytkowników na %s." + +#: modules/commands/ns_set.cpp:272 +#, c-format +msgid "Services will no longer set status modes on %s in channels." +msgstr "Serwisy nie będą już automatycznie nadawały uprawnień dla użytkownika %s." + +#: modules/commands/cs_set.cpp:108 +#, c-format +msgid "Services will now automatically give modes to users in %s." +msgstr "Serwisy będą automatycznie nadawały uprawnienia dla użytkowników na %s." + +#: modules/commands/ns_set.cpp:940 +#, c-format +msgid "Services will now reply to %s with messages." +msgstr "Serwisy będą teraz wysyłać do %s wiadomości." + +#: modules/commands/ns_set.cpp:946 +#, c-format +msgid "Services will now reply to %s with notices." +msgstr "Serwisy będą teraz wysyłać do %s powiadomienia." + +#: modules/commands/os_reload.cpp:34 +msgid "Services' configuration has been reloaded." +msgstr "Plik konfiguracyjny serwisów został przeładowany." + +#: modules/commands/os_session.cpp:192 +msgid "Session" +msgstr "Sesja" + +#: modules/commands/os_session.cpp:382 +#, c-format +msgid "Session limit for %s set to %d." +msgstr "Limit sesji dla %s zmieniono na %d." + +#: modules/commands/os_session.cpp:257 modules/commands/os_session.cpp:534 +msgid "Session limiting is disabled." +msgstr "Limitowanie sesji jest wyłączone." + +#: modules/commands/os_stats.cpp:195 +#, c-format +msgid "Sessions: %lu entries, %lu buckets, longest chain is %d" +msgstr "Sesje: %lu wpisów, %lu pakietów, najdłuższy łańcuch to %d" + +#: modules/commands/ns_set.cpp:74 +msgid "Set SET-options on another nickname" +msgstr "Ustawia opcje wskazanemu nickowi" + +#: modules/commands/cs_set.cpp:20 +msgid "Set channel options and information" +msgstr "Modyfikuje ustawienia kanału" + +#: modules/commands/cs_set.cpp:137 +msgid "Set how Services make bans on the channel" +msgstr "Ustawia sposób banowania przez serwisy" + +#: modules/commands/ms_set.cpp:206 +msgid "Set options related to memos" +msgstr "Ustawia opcje związane z wiadomościami" + +#: modules/commands/ns_set.cpp:19 +msgid "Set options, including kill protection" +msgstr "Modyfikuje ustawienia nicka" + +#: modules/commands/cs_set.cpp:472 +msgid "Set the channel as permanent" +msgstr "Ustawia kanał jako \"wieczny\"" + +#: modules/commands/cs_set.cpp:204 +msgid "Set the channel description" +msgstr "Ustawia opis kanału" + +#: modules/commands/ns_set.cpp:329 +msgid "Set the display of your group in Services" +msgstr "Ustawia nick reprezentujący grupę nicków" + +#: modules/commands/cs_set.cpp:266 +msgid "Set the founder of a channel" +msgstr "Ustawia nick właściciela kanału" + +#: modules/commands/ns_set.cpp:793 +msgid "Set the language Services will use when messaging you" +msgstr "Ustawia język, w którym serwisy będą wysyłały komunikaty" + +#: modules/commands/ns_set.cpp:172 +msgid "Set the nickname password" +msgstr "Ustawia hasło do nicka" + +#: modules/commands/cs_set.cpp:949 +msgid "Set the successor for a channel" +msgstr "Ustawia nick spadkobiercy kanału" + +#: modules/commands/hs_set.cpp:125 +msgid "Set the vhost for all nicks in a group" +msgstr "Zmienia vhosty wszystkich nicków w grupie" + +#: modules/commands/hs_set.cpp:19 +msgid "Set the vhost of another user" +msgstr "Zmienia vhost wskazanemu użytkownikowi" + +#: modules/commands/os_set.cpp:169 +msgid "Set various global Services options" +msgstr "Ustawia różne globalne opcje serwisów" + +#: modules/commands/ns_set.cpp:119 +msgid "Set your nickname password" +msgstr "Ustawia hasło do nicka" + +#: modules/commands/bs_kick.cpp:271 +#, c-format +msgid "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Włącza lub wyłącza kopanie za AMSG. Gdy włączone, bot będzie\n" +"wyrzucał użytkowników, którzy wysyłają te same wiadomości na\n" +"wiele kanałów, na których są boty %s.\n" +" \n" +"ttb oznacza, ile razy użytkownik może zostać wyrzucony,\n" +"zanim dostanie on bana. Nie podawaj ttb, aby wyłączyć\n" +"banowanie, gdy jest ono włączone." + +#: modules/commands/bs_kick.cpp:307 +#, c-format +msgid "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Ustawia kopanie za używanie zakazanych słów.\n" +"\n" +"Aby ustalić listę zakazanych użyj polecenia BADWORDS.\n" +"Aby uzyskać więcej informacji wpisz:\n" +"%s%s HELP BADWORDS\n" +"\n" +"ttb to liczba określająca ile razy użytkownik\n" +"zostanie wykopany zanim bot założy bana.\n" +"Pominięcie parametru ttb wyłącza banowanie." + +#: modules/commands/cs_set.cpp:186 +msgid "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" +msgstr "" +"Ustala typ banów zakładanych przez serwisy.\n" +"\n" +"Typ banów oznaczany jest numerami od 0 do 3,\n" +"poszczególne numery oznaczają:\n" +"\n" +"0: ban w postaci *!ident@host\n" +"1: ban w postaci *!*ident@host\n" +"2: ban w postaci *!*@host\n" +"3: ban w postaci *!*ident@*.domena" + +#: modules/commands/bs_kick.cpp:345 +msgid "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Ustawia kopanie za pogrubianie tekstu.\n" +"\n" +"ttb to liczba określająca ile razy użytkownik\n" +"zostanie wykopany zanim bot założy bana.\n" +"Pominięcie parametru ttb wyłącza banowanie." + +#: modules/commands/bs_kick.cpp:436 +#, c-format +msgid "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Ustawia kopanie za używanie WIELKICH LITER.\n" +"\n" +"Bot kopie jeśli tekst zawiera przynajmniej min\n" +"wielkich liter i stanowi przynajmniej procent\n" +"całego tekstu w linii (w przypadku nie podania tych\n" +"wartości przyjmowane są domyślne: 10 znaków i 25%%).\n" +"\n" +"ttb to liczba określająca ile razy użytkownik\n" +"zostanie wykopany zanim bot założy bana.\n" +"Pominięcie parametru ttb wyłącza banowanie." + +#: modules/commands/bs_kick.cpp:475 +msgid "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Ustawia kopanie za używanie kolorowego tekstu.\n" +"\n" +"ttb to liczba określająca ile razy użytkownik\n" +"zostanie wykopany zanim bot założy bana.\n" +"Pominięcie parametru ttb wyłącza banowanie." + +#: modules/commands/cs_set.cpp:255 +msgid "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." +msgstr "Ustawia opis kanału widoczny po wydaniu polecenia LIST oraz INFO." + +#: modules/commands/bs_kick.cpp:571 +msgid "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Ustawia kopanie za flood. Włączenie tej opcji\n" +"powoduje wykopywanie użytkowników wysyłających na\n" +"kanał przynajmniej ln linii tekstu w ciągu sek\n" +"sekund (w przypadku nie podania tych wartości przyjmowane\n" +"są domyślne: 6 linii w ciągu 10 sekund).\n" +"\n" +"ttb to liczba określająca ile razy użytkownik\n" +"zostanie wykopany zanim bot założy bana.\n" +"Pominięcie parametru ttb wyłącza banowanie." + +#: modules/commands/bs_kick.cpp:607 +msgid "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Ustawia kopanie za używanie pochylonego tekstu.\n" +"\n" +"ttb to liczba określająca ile razy użytkownik\n" +"zostanie wykopany zanim bot założy bana.\n" +"Pominięcie parametru ttb wyłącza banowanie." + +#: modules/commands/bs_kick.cpp:706 +msgid "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Ustawia kopanie za powtarzanie tekstu. Włączenie tej\n" +"opcji powoduje wykopywanie użytkowników wysyłających\n" +"na kanał przynajmniej liczba razy ten sam tekst\n" +"(w przypadku nie podania tego parametru jego wartość\n" +"ustalana jest domyślnie na 3).\n" +"\n" +"ttb to liczba określająca ile razy użytkownik\n" +"zostanie wykopany zanim bot założy bana.\n" +"Pominięcie parametru ttb wyłącza banowanie." + +#: modules/commands/bs_kick.cpp:742 +msgid "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Ustawia kopanie za odwracanie kolorów tekstu (ctrl+r).\n" +"\n" +"ttb to liczba określająca ile razy użytkownik\n" +"zostanie wykopany zanim bot założy bana.\n" +"Pominięcie parametru ttb wyłącza banowanie." + +#: modules/commands/bs_kick.cpp:776 +msgid "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Ustawia kopanie za podkreślanie tekstu.\n" +"\n" +"ttb to liczba określająca ile razy użytkownik\n" +"zostanie wykopany zanim bot założy bana.\n" +"Pominięcie parametru ttb wyłącza banowanie." + +#: modules/commands/hs_set.cpp:206 +msgid "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." +msgstr "" +"Ustawia vhosta dla wszystkich nicków w obrębie grupy.\n" +"Jeśli IRCD obsługuje vIdenty, wydanie polecenia\n" +"SETALL @ spowoduje ustawienie\n" +"także identów.\n" +"\n" +"UWAGA: to polecenie nie spowoduje zmiany vhosta\n" +"dla nicka, który później zostanie dodany do grupy." + +#: modules/commands/hs_set.cpp:99 +msgid "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." +msgstr "" +"Ustawia wskazanemu użytkownikowi vhosta.\n" +"Jeśli Twoje IRCD obsługuje videnty, to używając\n" +"polecenia SET @\n" +"można zmieniać także ident." + +#: modules/commands/os_set.cpp:199 +msgid "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" +msgstr "" +"Zmienia różnorodne globalne ustawienia serwisów.\n" +"Obecnie zdefiniowane są następujące ustawienia:\n" +" READONLY Włącza tryb tylko-do-odczytu lub odczyt-zapis\n" +" DEBUG Włącza lub wyłącza tryb debugowania\n" +" NOEXPIRE Włącza lub wyłącza tryb noexpire\n" +" SUPERADMIN Włącza lub wyłącza tryb super administratora\n" +" LIST Listuje aktualne ustawienia" + +#: modules/commands/ms_set.cpp:235 +#, c-format +msgid "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Ustawia różne opcje wiadomości. Dostępne opcje:\n" +"\n" +" NOTIFY Ustawia kiedy otrzymasz informację\n" +" o nowej wiadomości\n" +" LIMIT Ustawia maksymalną liczbę wiadomości\n" +" jakie możesz odebrać\n" +"\n" +"Aby uzyskać więcej informacji o danej opcji wpisz:\n" +"%s%s HELP %s opcja" + +#: modules/commands/ns_set.cpp:33 modules/commands/ns_set.cpp:88 +msgid "Sets various nickname options. option can be one of:" +msgstr "" +"Ustawia różne opcje nicka. Dostępne opcje to (jeśli nie widzisz żadnych, zaloguj " +"się):" + +#: modules/commands/ns_set.cpp:237 +msgid "Sets whether services should set channel status modes on you automatically." +msgstr "" +"Pozwala na wybór, czy serwisy będą ustawiały automatycznie Twoje uprawnienia na " +"kanale." + +#: modules/commands/cs_set.cpp:1090 +msgid "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." +msgstr "" +"Włącza lub wyłącza automatyczne usunięcie kanału,\n" +"jeśli nie będzie on używany." + +#: modules/commands/ns_set.cpp:315 +#, c-format +msgid "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." +msgstr "" +"Włącza lub wyłącza automatyczne nadawanie uprawnień\n" +"wskazanemu użytkownikowi przez %s przy wchodzeniu\n" +"na kanał. Uwaga: zależnie od ustawień kanału, niektóre\n" +"tryby mogą nie być ustawiane samoczynnie." + +#: modules/commands/ns_set.cpp:1145 +msgid "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." +msgstr "" +"Włącza lub wyłącza automatyczne usunięcie nicka,\n" +"jeśli nie będzie on używany." + +#: modules/commands/ns_set.cpp:288 +#, c-format +msgid "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." +msgstr "" +"Włącza lub wyłącza automatyczne nadawanie uprawnień\n" +"Tobie przez %s przy wchodzeniu na kanał.\n" +"Uwaga: zależnie od ustawień kanału, niektóre\n" +"tryby mogą nie być ustawiane samoczynnie." + +#: modules/commands/cs_access.cpp:648 modules/commands/cs_access.cpp:689 +#, c-format +msgid "Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." +msgstr "" +"Nieznane ustawienie %s.\n" +"Napisz %s%s HELP LEVELS, aby uzyskać listę dostępnych możliwości." + +#: modules/commands/os_set.cpp:133 +msgid "Setting for DEBUG must be ON, OFF, or a positive number." +msgstr "Parametrem opcji DEBUG musi być ON, OFF albo liczba dodatnia." + +#: modules/commands/os_set.cpp:162 +msgid "Setting for NOEXPIRE must be ON or OFF." +msgstr "Parametrem opcji NOEXPIRE musi być ON albo OFF." + +#: modules/commands/os_set.cpp:56 +msgid "Setting for READONLY must be ON or OFF." +msgstr "Parametrem opcji READONLY musi być ON albo OFF." + +#: modules/commands/os_set.cpp:95 +msgid "Setting for super admin must be ON or OFF." +msgstr "Parametrem opcji SUPERADMIN musi być ON albo OFF." + +#: modules/commands/cs_set.cpp:74 +msgid "Should services automatically give status to users" +msgstr "Włącza lub wyłącza automatyczne opowanie" + +#: modules/commands/os_stats.cpp:203 +msgid "Show status of Services and network" +msgstr "Pokazuje informacje o serwisach i sieci" + +#: modules/commands/os_logsearch.cpp:152 +#, c-format +msgid "Showed %d/%d matches for %s." +msgstr "Wyświetlono %d/%d dopasowań dla %s." + +#: modules/commands/cs_set.cpp:872 +msgid "Sign kicks that are done with the KICK command" +msgstr "Podpisuje kicki kiedy użyto komendy KICK" + +#: modules/commands/cs_set.cpp:921 +#, c-format +msgid "Signed kick option for %s is now off." +msgstr "Podpisywanie komendy KICK na kanale %s zostało wyłączone." + +#: modules/commands/cs_set.cpp:913 +#, c-format +msgid "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." +msgstr "" +"Podpisywanie komendy KICK na kanale %s zostało włączone, ale\n" +"będzie zależało od poziomu dostępu jaki posiada użytkownik." + +#: modules/commands/cs_set.cpp:906 +#, c-format +msgid "Signed kick option for %s is now on." +msgstr "Podpisywanie komendy KICK na kanale %s zostało włączone." + +#: modules/commands/cs_set.cpp:1299 +msgid "Signed kicks" +msgstr "SIGNKICK" + +#: modules/commands/ms_send.cpp:59 modules/commands/ms_rsend.cpp:60 +#, c-format +msgid "Sorry, %s currently has too many memos and cannot receive more." +msgstr "%s ma zbyt dużo wiadomości i nie może otrzymywać nowych." + +#: modules/commands/cs_seen.cpp:294 +#, c-format +msgid "Sorry, I have not seen %s." +msgstr "Przepraszam, ale nie widziałem %s." + +#: modules/commands/bs_badwords.cpp:404 +msgid "Sorry, bad words list modification is temporarily disabled." +msgstr "Modyfikacja listy zakazanych słów jest tymczasowo wyłączona." + +#: modules/commands/bs_assign.cpp:30 modules/commands/bs_assign.cpp:98 +msgid "Sorry, bot assignment is temporarily disabled." +msgstr "Konfigurowanie bota jest tymczasowo wyłączone." + +#: modules/commands/bs_bot.cpp:281 modules/commands/bs_assign.cpp:164 +msgid "Sorry, bot modification is temporarily disabled." +msgstr "Modyfikacja botów jest tymczasowo wyłączona." + +#: modules/commands/bs_kick.cpp:813 modules/commands/bs_kick.cpp:878 +#: modules/fantasy.cpp:42 +msgid "Sorry, bot option setting is temporarily disabled." +msgstr "Konfigurowanie bota jest tymczasowo wyłączone." + +#: modules/commands/bs_set.cpp:115 +msgid "Sorry, changing bot options is temporarily disabled." +msgstr "Konfigurowanie bota jest tymczasowo wyłączone." + +#: modules/commands/cs_xop.cpp:112 modules/commands/cs_xop.cpp:235 +#: modules/commands/cs_xop.cpp:444 +#, c-format +msgid "Sorry, channel %s list modification is temporarily disabled." +msgstr "Modyfikacja listy %s jest tymczasowo wyłączona." + +#: modules/commands/cs_flags.cpp:405 modules/commands/cs_access.cpp:547 +msgid "Sorry, channel access list modification is temporarily disabled." +msgstr "Modyfikacja listy dostępu jest tymczasowo wyłączona." + +#: modules/commands/cs_akick.cpp:469 +msgid "Sorry, channel autokick list modification is temporarily disabled." +msgstr "Modyfikacja listy AKICK jest tymczasowo wyłączona." + +#: modules/commands/cs_drop.cpp:29 +msgid "Sorry, channel de-registration is temporarily disabled." +msgstr "Usuwanie kanałów jest tymczasowo wyłączone." + +#: modules/commands/cs_register.cpp:35 +msgid "Sorry, channel registration is temporarily disabled." +msgstr "Rejestracja kanałów jest tymczasowo wyłączona." + +#: modules/commands/bs_kick.cpp:181 +msgid "Sorry, kicker configuration is temporarily disabled." +msgstr "Konfigurowanie kopów jest tymczasowo wyłączone." + +#: modules/commands/ms_set.cpp:216 +msgid "Sorry, memo option setting is temporarily disabled." +msgstr "Ustawianie opcji wiadomości jest tymczasowo wyłączone." + +#: include/language.h:116 +msgid "Sorry, memo sending is temporarily disabled." +msgstr "Wysyłanie wiadomości jest tymczasowo wyłączone." + +#: modules/commands/ns_drop.cpp:29 +msgid "Sorry, nickname de-registration is temporarily disabled." +msgstr "Usuwanie nicków jest tymczasowo wyłączone." + +#: modules/commands/ns_group.cpp:120 +msgid "Sorry, nickname grouping is temporarily disabled." +msgstr "Grupowanie nicków jest tymczasowo wyłączone." + +#: modules/commands/ns_register.cpp:139 +msgid "Sorry, nickname registration is temporarily disabled." +msgstr "Rejestracja nicków jest tymczasowo wyłączona." + +#: modules/commands/ns_access.cpp:33 +#, c-format +msgid "Sorry, the maximum of %d access entries has been reached." +msgstr "Możesz mieć tylko %d wpisów na kanałowej liście dostępu." + +#: modules/commands/ns_ajoin.cpp:141 +#, c-format +msgid "Sorry, the maximum of %d auto join entries has been reached." +msgstr "" +"Przepraszamy, maksymalna liczba %d wpisów automatycznego dołączania została " +"osiągnięta." + +#: modules/commands/ns_cert.cpp:173 +#, c-format +msgid "Sorry, the maximum of %d certificate entries has been reached." +msgstr "Możesz mieć tylko %d wpisy(ów) na liście certyfikatów." + +#: modules/commands/ms_ignore.cpp:55 +#, c-format +msgid "Sorry, the memo ignore list for %s is full." +msgstr "Lista ignorowania dla %s jest już pełna." + +#: modules/commands/cs_xop.cpp:201 modules/commands/cs_flags.cpp:174 +#: modules/commands/cs_access.cpp:204 +#, c-format +msgid "" +"Sorry, you can only have %d access entries on a channel, including access entries " +"from other channels." +msgstr "" +"Możesz mieć tylko %d wpisów na kanałowej liście dostępu, wliczając inne kanały." + +#: modules/commands/cs_akick.cpp:177 +#, c-format +msgid "Sorry, you can only have %d autokick masks on a channel." +msgstr "Możesz mieć jedynie %d wpisów w liście AKICK." + +#: modules/commands/bs_badwords.cpp:286 +#, c-format +msgid "Sorry, you can only have %d bad words entries on a channel." +msgstr "Błąd, możesz mieć tylko %d wpisów na liście zakazanych słów." + +#: include/language.h:103 +#, c-format +msgid "Sorry, you have already exceeded your limit of %d channels." +msgstr "Błąd, możesz mieć ustawione tylko %d kanały(ów)." + +#: include/language.h:102 +#, c-format +msgid "Sorry, you have already reached your limit of %d channels." +msgstr "Błąd, możesz mieć ustawione tylko %d kanały(ów)." + +#: modules/commands/os_dns.cpp:218 +msgid "State" +msgstr "Stan" + +#: modules/commands/cs_seen.cpp:117 +msgid "Statistics and maintenance for seen data" +msgstr "Statystyki i zarządzanie danymi SEEN" + +#: modules/commands/os_stats.cpp:131 +msgid "Statistics reset." +msgstr "Statystyki zostały zresetowane." + +#: modules/commands/ns_update.cpp:36 +msgid "Status updated (memos, vhost, chmodes, flags)." +msgstr "Status zaktualizowany (wiadomości, vhosty, flagi)." + +#: modules/commands/bs_kick.cpp:1432 +msgid "Stop flooding!" +msgstr "Przestań floodować!" + +#: modules/commands/bs_kick.cpp:1448 +msgid "Stop repeating yourself!" +msgstr "Nie powtarzaj się!" + +#: modules/commands/cs_set.cpp:746 +msgid "Stricter control of channel founder status" +msgstr "Ściśle kontroluje status właściciela" + +#: modules/commands/cs_set.cpp:810 +msgid "Stricter control of chanop status" +msgstr "Ściśle kontroluje status operatorów" + +#: modules/commands/ns_alist.cpp:75 modules/commands/cs_info.cpp:50 +msgid "Successor" +msgstr "Następca" + +#: modules/commands/cs_set.cpp:1006 +#, c-format +msgid "Successor for %s changed to %s." +msgstr "Zastępcę dla kanału %s zmieniono na %s." + +#: modules/commands/cs_set.cpp:1008 +#, c-format +msgid "Successor for %s unset." +msgstr "Zastępcę dla kanału %s usunięto." + +#: modules/commands/os_set.cpp:81 +msgid "Super admin can not be set because it is not enabled in the configuration." +msgstr "Opcja SuperAdmin nie jest włączona w pliku konfiguracyjnym." + +#: modules/commands/ns_suspend.cpp:60 +msgid "Suspend a given nick" +msgstr "Blokuje podany nick z zachowaniem wszelkich jego danych i ustawień" + +#: modules/commands/cs_suspend.cpp:236 modules/commands/ns_suspend.cpp:250 +msgid "Suspend reason" +msgstr "Powód zawieszenia" + +#: modules/commands/cs_suspend.cpp:232 modules/commands/ns_suspend.cpp:246 +msgid "Suspended" +msgstr "Zawieszony" + +#: modules/commands/cs_suspend.cpp:234 modules/commands/ns_suspend.cpp:248 +msgid "Suspended by" +msgstr "Zawieszony przez" + +#: modules/commands/cs_suspend.cpp:238 modules/commands/ns_suspend.cpp:252 +msgid "Suspended on" +msgstr "Zawieszony" + +#: modules/commands/ns_suspend.cpp:147 +msgid "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." +msgstr "" +"Zawiesza działanie wskazanego nicka, co uniemożliwia\n" +"korzystanie z niego. Podanie czasu powoduje automatyczne\n" +"przywrócenie nicka po podanym czasie - w przeciwnym razie\n" +"użyta zostanie wartość z konfiguracji." + +#: modules/commands/cs_suspend.cpp:240 modules/commands/ns_suspend.cpp:254 +msgid "Suspension expires" +msgstr "Zawieszenie wygasa" + +#: modules/commands/cs_sync.cpp:19 +msgid "Sync users channel modes" +msgstr "Synchronizuj flagi użytkownika na kanale" + +#: modules/commands/cs_sync.cpp:49 +msgid "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." +msgstr "" +"Dostosowuje flagi użytkowników na kanale do trybów,\n" +"które powinni mieć według listy dostępowej." + +#: modules/commands/hs_group.cpp:42 +msgid "Syncs the vhost for all nicks in a group" +msgstr "Synchronizuje vhosty wszystkich nicków w grupie" + +#: src/command.cpp:146 +msgid "Syntax" +msgstr "Składnia" + +#: modules/commands/ns_group.cpp:373 +#, c-format +msgid "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." +msgstr "" +"Składnia: %s\n" +"\n" +"Listuje wszystkie nicki z Twojej grupy." + +#: modules/commands/ns_group.cpp:363 +#, c-format +msgid "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." +msgstr "" +"Składnia: %s [nick]\n" +"\n" +"Polecenie wywołane bez parametrów listuje wszystkie\n" +"nicki należące do grupy wydającego polecenie.\n" +"\n" +"Administratorzy serwisów mogą jako parametr podać\n" +"nick osoby, której nicki chcą sprawdzić." + +#: modules/commands/os_set.cpp:227 +msgid "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." +msgstr "" +"Składnia: DEBUG {ON | OFF}\n" +" \n" +"Włącza lub wyłącza tryb debugowania.\n" +" \n" +"Ta opcja jest odpowiednikiem użycia --debug w linii poleceń." + +#: modules/commands/ms_set.cpp:287 +#, c-format +msgid "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." +msgstr "" +"Składnia: LIMIT [channel] limit\n" +"\n" +"Ustala Twoją (lub kanału) maksymalną liczbę \n" +"wiadomości. Jeśli ustalona zostanie ona na 0, \n" +"przyjmowanie wiadomości zostanie wyłączone. Limit \n" +"nie może być większy niż %d." + +#: modules/commands/ms_set.cpp:267 +#, c-format +msgid "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." +msgstr "" +"Składnia: LIMIT [użytkownik | kanał] {limit | NONE} [HARD]\n" +"\n" +"Ustala maksymalną ilość wiadomości jaką może \n" +"posiadać użytkownik lub kanał. Ustalenie limitu \n" +"na 0, wyłączy przyjmowanie wiadomości. Parametr \n" +"NONE pozwoli na nielimitowaną ilość wiadomości. \n" +"Jeśli nie podany zostanie nick lub kanał zmieniony \n" +"zostanie limit wydającego polecenie.\n" +"\n" +"Dodanie parametru HARD uniemożliwia zmianę \n" +"limitu przez użytkownika.\n" +"To użycie polecenia SET LIMIT jest dostępne dla \n" +"administratorów serwisów. Pozostali użytkownicy \n" +"mogą jedynie modyfikować własny limit lub kanału na\n" +"którym mają do tego uprawnienia. Nie mogą wyłączyć \n" +"limitu, a także ustalić jego wartości powyżej %d \n" +"oraz użyć parametru HARD." + +#: modules/commands/os_set.cpp:208 +#, c-format +msgid "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." +msgstr "" +"Składnia: LIST\n" +"\n" +"Listuje aktualne ustawienia serwisu %s." + +#: modules/commands/os_set.cpp:234 +msgid "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." +msgstr "" +"Składnia: NOEXPIRE {ON | OFF}\n" +"\n" +"Włącza lub wyłącza tryb wygasania. Jeśli ta opcja\n" +"została włączona nicki, kanały, wpisy na listach\n" +"AKILL oraz wyjątków nie będą automatycznie wygasały.\n" +"\n" +"Ta opcja ma taki sam efekt jak argument linii poleceń -noexpire." + +#: modules/commands/ms_set.cpp:246 +msgid "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." +msgstr "" +"Składnia: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +"\n" +"Ustala sposób wysłania powiadomień o nowych wiadomościach:\n" +"\n" +" ON Powiadomienie zostanie wysłane po \n" +" zalogowaniu się, kiedy nie będzie \n" +" ustawiony tryb /AWAY oraz w momencie\n" +" otrzymania wiadomości.\n" +" LOGON Powiadomienie zostanie wysłane jedynie \n" +" po zalogowaniu się lub po wyłączeniu \n" +" trybu /AWAY.\n" +" NEW Powiadomienie będzie wysyłane jedynie w \n" +" momencie otrzymania wiadomości.\n" +" MAIL Powiadomienia będą wysyłane e-mailem oraz\n" +" wedle pozostałych ustawień.\n" +" NOMAIL Powiadomienia nie będą wysyłane e-mailem.\n" +" OFF Powiadomienia nie będą wysyłane.\n" +"\n" +"Opcja ON jest kombinacją opcji LOGON oraz NEW." + +#: modules/commands/os_set.cpp:212 +msgid "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." +msgstr "" +"Składnia: READONLY {ON | OFF}\n" +"\n" +"Włącza lub wyłącza tryb tylko-do-odczytu. Włączenie tej\n" +"opcji powoduje zablokowanie wykonywania zmian w ustawieniach\n" +"serwisów, dotyczy to list dostępu kanału oraz nicka itd.\n" +"Operatorzy serwisów z odpowiednimi uprawnieniami będą\n" +"mogli modyfikować listę AKILL, usuwać lub blokować nicki\n" +"oraz kanały, ale żadne z tych zmian nie zostaną zapisane\n" +"dopóki tryb tylko-do-odczytu nie zostanie wyłączony przed\n" +"restartem lub wyłączeniem serwisów.\n" +"\n" +"Ta opcja ma taki sam efekt jak argument linii poleceń -readonly." + +#: modules/commands/os_set.cpp:243 +msgid "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." +msgstr "" +"Składnia: SUPERADMIN {ON | OFF}\n" +"\n" +"Ustawienie tej opcji nadaje wydającemu polecenie\n" +"dodatkowe uprawnienia (np. jest właścicielem \n" +"wszystkich kanałów w sieci).\n" +"\n" +"Ta opcja powinna być używana tylko wtedy, kiedy\n" +"jest taka potrzeba. Należy ją później wyłączyć." + +#: modules/commands/ns_identify.cpp:107 +#, c-format +msgid "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." +msgstr "" +"Informuje %s, że nick którego właśnie używasz \n" +"należy do Ciebie. Wiele komend wymaga identyfikacji \n" +"przed ich użyciem. Hasłem jest to samo hasło, \n" +"którego użyto przy komendzie REGISTER." + +#: modules/commands/cs_invite.cpp:91 +#, c-format +msgid "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"%s wysyła użytkownikowi zaproszenie do kanału.\n" +"\n" +"Standardowo ta komenda jest dostępna dla użytkowników\n" +"wpisanych na listę AOP lub posiadających poziom\n" +"dostępu 5 lub wyższy." + +#: modules/commands/cs_unban.cpp:107 +#, c-format +msgid "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Powoduje usunięcie przez %s wszystkich banów, które\n" +"uniemożliwiają Tobie lub podanemu użytkownikowi wejście\n" +"na podany kanał. Gdy nie podano kanału, bany dotyczące\n" +"Ciebie na wszystkich kanałach, na których masz uprawnienia,\n" +"zostaną usunięte.\n" +" \n" +"Standardowo, polecenie jest dostępne dla posiadających\n" +"uprawnienie AOP, lub tych o poziomie dostępu 5 lub wyższym." + +#: modules/commands/os_jupe.cpp:56 +msgid "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." +msgstr "" +"To polecenie powoduje wprowadzenie przez serwisy do sieci\n" +"sztucznego serwera, co zapobiega podłączaniu prawdziwego\n" +"serwera o tej samej nazwie. Blokadę można zdjąć używając\n" +"standardowego polecenia SQUIT. Jeśli zostanie podany\n" +"powód będzie on wyświetlany w polu informacyjnym serwera,\n" +"w przeciwnym wypadku wyświetlane będzie \"Juped by \"." + +#: modules/commands/cs_seen.cpp:261 +msgid "Tells you about the last time a user was seen" +msgstr "Informuje, kiedy ostatnio widziano użytkownika" + +#: modules/commands/os_shutdown.cpp:19 +msgid "Terminate Services WITHOUT saving" +msgstr "Wyłącza serwisy NIE zapisując baz" + +#: modules/commands/os_shutdown.cpp:73 +msgid "Terminate services with save" +msgstr "Wyłącza serwisy z zapisaniem baz" + +#: modules/commands/os_news.cpp:156 +msgid "Text" +msgstr "Tekst" + +#: modules/commands/cs_access.cpp:576 +msgid "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." +msgstr "" +"Polecenie ACCESS ADD dodaje podaną maskę do\n" +"listy dostępowej z podanym poziomem dostępu; jeżeli\n" +"maska już znajduje się na liście, jej poziom zostaje zmieniony\n" +"na podany. Wskazany poziom może być liczbą, lub też\n" +"nazwą uprawnienia (na przykład AUTOOP). Gdy użytkownik\n" +"dołącza do kanału, uprawnienie, które otrzyma, zależy od\n" +"najwyższego wpisu na liście dostępowej." + +#: modules/commands/cs_access.cpp:587 +msgid "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." +msgstr "" +"Polecenie ACCESS DEL usuwa podany nick z listy dostępowej.\n" +"Gdy podana zostanie lista numerów wpisów, wpisy te zostaną skasowane.\n" +"(Przykład LISTy poniżej.)\n" +"Możesz usunąć sam siebie z listy, nawet, gdy nie posiadasz uprawnień\n" +"do jej modyfikowania w innym przypadku." + +#: modules/commands/cs_access.cpp:593 +msgid "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." +msgstr "" +"Polecenie ACCESS LIST pozwala na podgląd listy dostępowej.\n" +"Jeżeli podana zostanie maska wieloznaczna, tylko wpisy do niej pasujące\n" +"będą wyświetlone. Gdy parametrem będzie lista numerów wpisów, tylko\n" +"te wpisy zostaną pokazane, na przykład:\n" +" ACCESS #kanał LIST 2-5,7-9\n" +" Pokaż wpisy dostępu o numerach od 2 do 5 oraz od 7 do 9.\n" +" \n" +"Polecenie ACCESS VIEW działa podobnie do ACCESS LIST,\n" +"ale pokazuje osobę dodającą oraz czas ostatniego użycia.\n" +" \n" +"Polecenie ACCESS CLEAR usuwa wszystkie wpisy z listy dostępowej." + +#: modules/commands/cs_flags.cpp:447 +msgid "" +"The CLEAR command clears the channel access list. This requires channel founder " +"access." +msgstr "" +"Polecenie CLEAR usuwa wszystkie wpisy z listy dostępów kanału. Wymaga to " +"uprawnień założyciela." + +#: modules/commands/cs_seen.cpp:173 +#, c-format +msgid "" +"The CLEAR command lets you clean the database by removing all entries from the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." +msgstr "" +"Polecenie CLEAR pozwala Ci oczyścić bazę danych poprzez usunięcie\n" +"wszystkich wpisów, które zostały dodane przez ostatni czas.\n" +" \n" +"Przykład:\n" +" %s CLEAR 30m\n" +" Usunie wszystkie wpisy z ostatnich 30 minut." + +#: modules/commands/bs_badwords.cpp:438 +msgid "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." +msgstr "" +"Polecenie DEL usuwa podane słowo z listy słów\n" +"zabronionych. Gdy podana zostanie lista numerów wpisów,\n" +"wpisy te zostaną skasowane. (Zobacz przykład dla LIST poniżej.)\n" +" \n" +"Komenda LIST wyświetla listę zabronionych słów.\n" +"Jeżeli podana będzie wieloznaczna maska, wyświetlone zostaną\n" +"tylko wpisy pasujące do tej maski. Gdy podana zostanie lista\n" +"numerów wpisów, pokazane zostaną wpisy o tych numerach,\n" +"na przykład: #kanał LIST 2-5,7-9\n" +" Wyświetla wpisy listy zabronionych słów o numerach od 2\n" +" do 5 oraz od 7 do 9.\n" +" \n" +"Polecenie CLEAR usuwa wszystkie wpisy z listy." + +#: modules/commands/cs_entrymsg.cpp:241 +msgid "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." +msgstr "" +"Polecenie ENTRYMSG ADD dodaje podaną wiadomość do\n" +"listy wiadomości pokazywanych użytkownikom gdy dołączają do kanału." + +#: modules/commands/cs_entrymsg.cpp:253 +msgid "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." +msgstr "" +"Polecenie ENTRYMSG CLEAR usuwa wszystkie wpisy\n" +"z listy wiadomości pokazywanych użytkownikom, gdy dołączają\n" +"do kanału, w efekcie wyłączając wiadomości powitalne." + +#: modules/commands/cs_entrymsg.cpp:245 +msgid "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." +msgstr "" +"Polecenie ENTRYMSG DEL usuwa wskazaną wiadomość\n" +"z listy wiadomości wysyłanych użytkownikom, gdy dołączają\n" +"do kanału. Możesz usunąć wiadomość podając jej numer,\n" +"który uzyskasz wyświetlając wszystkie wiadomości w sposób\n" +"podany niżej." + +#: modules/commands/cs_entrymsg.cpp:250 +msgid "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." +msgstr "" +"Polecenie ENTRYMSG LIST wyświetla listę wiadomości\n" +"wysyłanych użytkownikom, gdy dołączają oni do kanału." + +#: modules/commands/ns_set.cpp:713 +msgid "The IMMED option is not available on this network." +msgstr "Opcja IMMED nie jest jest dostępna w tej sieci." + +#: modules/commands/cs_access.cpp:821 +#, c-format +msgid "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." +msgstr "" +"Komenda LEVELS pozwala na zmianę znaczenia numerów\n" +"poziomów dostępów, co umożliwia szczegółowe dostosowanie\n" +"uprawnień na kanałach. Używając tego polecenia można\n" +"zdefiniować poziomy dostępu wymagane dla większości funkcji\n" +"%s. (Polecenie SET FOUNDER i bieżąca komenda są\n" +"zawsze dostępne tylko dla właściciela kanału.)\n" +" \n" +"LEVELS SET umożliwia zmianę poziomu dostępu dla funkcji\n" +"lub grupy funkcji. LEVELS DISABLE (lub, krócej, DIS)\n" +"wyłącza automatyczne działanie, lub też blokuje dostęp do funkcji\n" +"dla wszystkich, wraz Z WŁAŚCICIELEM (ale właściciel może ją włączyć\n" +"ponownie). Użyj komendy LEVELS SET founder aby przydzielić\n" +"podane uprawnienie tylko właścicielowi. \n" +"LEVELS LIST wyświetla bieżącą listę poziomów dla każdej funkcji\n" +"lub grupy funkcji. LEVELS RESET przywraca ustawienia poziomów\n" +"do domyślnych, takich, jakie są one na świeżo stworzonych kanałach.\n" +" \n" +"Aby zobaczyć, jaka funkcjonalność może mieć ustawione poziomy, użyj\n" +"HELP LEVELS DESC." + +#: modules/commands/cs_flags.cpp:442 +msgid "" +"The LIST command allows you to list existing entries on the channel access list.\n" +"If a mask is given, the mask is wildcard matched against all existing entries on " +"the\n" +"access list, and only those entries are returned. If a set of flags is given, " +"only those\n" +"on the access list with the specified flags are returned." +msgstr "" +"Polecenie LIST pozwala na przeglądanie zawartości kanałowej listy dostępu.\n" +"Jeśli podano maskę, zwrócone zostaną tylko pasujące do niej wpisy. Gdy podano\n" +"listę flag, wyświetlone zostaną tylko pozycje z listy posiadające te flagi." + +#: modules/commands/cs_flags.cpp:435 +msgid "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. You " +"are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of what " +"your access is." +msgstr "" +"Polecenie MODIFY pozwala na zmianę kanałowej listy dostępu.\n" +"Gdy podana maska nie znajduje się już na liście dostępowej, zostanie ona\n" +"dodana. Gdy po wykonaniu zmiany maska nie będzie miała żadnych flag,\n" +"zostanie usunięta. Dodatkowo, możesz używać +* lub -* w celu odpowiednio\n" +"dodania bądź usunięcia wszystkich flag. Możesz modyfikować listę dostępu\n" +"tylko wtedy, gdy posiadasz odpowiednie uprawnienia na kanale.\n" +"Nawet w takim przypadku nie możesz wpływać na uprawnienia innych\n" +"użytkowników na poziomie wyższym niż Twoje." + +#: modules/commands/cs_seen.cpp:172 +msgid "The STATS command prints out statistics about stored nicks and memory usage." +msgstr "" +"Komenda STATS wyświetla statystyki dotyczące zapisanych nicków i wykorzystania " +"pamięci." + +#: modules/commands/ns_register.cpp:293 +msgid "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." +msgstr "" +"Parametr email jest opcjonalny (choć w pewnych sieciach\n" +"może być wymagany) i natychmiast zmieni adres przypisany\n" +"Twojemu nickowi.\n" +"Szanujemy Twoją prywatność: adres nie będzie udostępniany\n" +"osobom trzecim. Możesz także ustawić SET HIDE aby\n" +"ukryć adres po rejestracji (o ile nie jest to już ustawione domyślnie)." + +#: modules/commands/cs_log.cpp:258 +#, c-format +msgid "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." +msgstr "" +"Polecenie %s pozwala użytkownikom na konfigurowanie logowania\n" +"ich kanałów. Gdy nie zostanie podany żaden parametr, polecenie\n" +"wylistuje aktualne metody logowania włączone na tym kanale.\n" +" \n" +"W przeciwnym wypadku, polecenie musi być nazwą polecenia,\n" +"a metoda jest jednym z poniższych sposobów logowania:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Służą one, odpowiednio, do wysyłania normalnych wiadomości,\n" +"wiadomości NOTICE, lub wiadomości Memo. Aby użyć MESSAGE\n" +"lub NOTICE, musisz posiadać bota przypisanego do kanału\n" +"i znajdującego się tam. Status może być uprawnieniem kanałowym\n" +"jak @ czy +.\n" +" \n" +"Aby usunąć metodę logowania, użyj tej samej składni jak przy jej\n" +"dodawaniu.\n" +" \n" +"Przykład:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Poinformuje wszystkich operatorów kanału, gdy ktoś użyje\n" +" komendy ACCESS w usłudze ChanServ na kanale." + +#: modules/commands/cs_ban.cpp:67 +#, c-format +msgid "The %s list for %s is full." +msgstr "Lista %s dla %s jest pełna." + +#: modules/commands/os_sxline.cpp:220 +#, c-format +msgid "The %s list has been cleared." +msgstr "Lista %s została wyczyszczona." + +#: modules/commands/os_akill.cpp:377 +msgid "The AKILL list has been cleared." +msgstr "Lista AKILL została wyczyszczona." + +#: modules/commands/os_defcon.cpp:136 modules/commands/os_defcon.cpp:225 +#, c-format +msgid "The Defcon level is now at: %d" +msgstr "Defcon jest teraz na poziomie: %d" + +#: modules/commands/ns_info.cpp:172 +#, c-format +msgid "The E-mail address of %s will now be hidden from %s INFO displays." +msgstr "Adres e-mail osoby %s będzie ukrywany w informacjach %s." + +#: modules/commands/ns_info.cpp:173 +#, c-format +msgid "The E-mail address of %s will now be shown in %s INFO displays." +msgstr "Adres e-mail osoby %s będzie pokazywany w informacjach %s." + +#: modules/commands/cs_flags.cpp:449 +msgid "The available flags are:" +msgstr "Dostępne flagi to:" + +#: modules/commands/os_defcon.cpp:240 +msgid "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." +msgstr "" +"System defcon umożliwia wprowadzanie wcześniej\n" +"zdefiniowanych ograniczeń dla serwisów podczas\n" +"próby ataku na sieć." + +#: modules/ns_maxemail.cpp:51 +#, c-format +msgid "The email address %s has reached its usage limit of %d users." +msgstr "Adres e-mail %s osiągnął limit %d używających go użytkowników." + +#: modules/ns_maxemail.cpp:49 +#, c-format +msgid "The email address %s has reached its usage limit of 1 user." +msgstr "Adres e-mail %s jest już używany." + +#: modules/commands/cs_entrymsg.cpp:142 +#, c-format +msgid "The entry message list for %s is full." +msgstr "Lista wiadomości powitalnych dla %s jest pełna." + +#: modules/commands/cs_access.cpp:796 +msgid "The following feature/function names are available:" +msgstr "Następujące nazwy funkcjonalności są dostępne:" + +#: modules/commands/cs_access.cpp:584 +msgid "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." +msgstr "" +"Podana maska może również być kanałem - spowoduje\n" +"to użycie listy dostępowej z podanego kanału do podanego\n" +"poziomu włącznie." + +#: modules/commands/os_session.cpp:240 +#, c-format +msgid "" +"The host %s currently has %d sessions with a limit of %d because it matches entry:" +" %s." +msgstr "" +"Host %s aktualnie posiada %d sesji z limitem %d, ponieważ pasuje do wpisu: %s." + +#: modules/commands/ms_check.cpp:54 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has been read." +msgstr "Ostatnia wiadomość wysłana do %s (w %s) została przeczytana." + +#: modules/commands/ms_check.cpp:52 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has not yet been read." +msgstr "" +"Ostatnia wysłana przez Ciebie wiadomość\n" +"do %s (w %s) jest wciąż nieprzeczytana." + +#: modules/commands/ns_info.cpp:190 +#, c-format +msgid "The last quit message of %s will now be hidden from %s INFO displays." +msgstr "Ostatnia wiadomość QUIT osoby %s będzie ukrywana w informacjach %s." + +#: modules/commands/ns_info.cpp:191 +#, c-format +msgid "The last quit message of %s will now be shown in %s INFO displays." +msgstr "Ostatnia wiadomość QUIT osoby %s będzie pokazywana w informacjach %s." + +#: modules/commands/ns_info.cpp:178 +#, c-format +msgid "The last seen user@host mask of %s will now be hidden from %s INFO displays." +msgstr "Ostatnia maska ident@host osoby %s będzie ukrywana w informacjach %s." + +#: modules/commands/ns_info.cpp:179 +#, c-format +msgid "The last seen user@host mask of %s will now be shown in %s INFO displays." +msgstr "Ostatnia maska ident@host osoby %s będzie pokazywana w informacjach %s." + +#: modules/commands/cs_enforce.cpp:190 +#, c-format +msgid "The limit on %s is not valid." +msgstr "Limit dla %s nie jest poprawny." + +#: modules/commands/os_forbid.cpp:193 +msgid "The mask must contain at least one non wildcard character." +msgstr "Maska musi zawierać co najmniej jeden rzeczywisty znak." + +#: modules/commands/ms_set.cpp:153 +#, c-format +msgid "The memo limit for %s may not be changed." +msgstr "Limit wiadomości dla %s nie może być zmieniany." + +#: modules/commands/cs_mode.cpp:347 +#, c-format +msgid "The mode lock list of %s is full." +msgstr "Lista blokad flag dla %s jest pełna." + +#: modules/commands/ns_set.cpp:355 +#, c-format +msgid "The new display MUST be a nickname of the nickname group %s." +msgstr "Nowy nick reprezentujący grupę %s musi być jej członkiem." + +#: include/language.h:98 +#, c-format +msgid "The new display is now %s." +msgstr "%s jest teraz głównym nickiem." + +#: modules/commands/os_svs.cpp:57 +#, c-format +msgid "The nick %s is now being changed to %s." +msgstr "Nick %s zostaje zmieniony na %s." + +#: modules/commands/bs_bot.cpp:149 +msgid "The old information is the same as the new information specified." +msgstr "Stara dana jest taka sama jak nowa." + +#: modules/commands/os_info.cpp:157 +#, c-format +msgid "The oper info already exists on %s." +msgstr "Informacja operatora dla %s już istnieje." + +#: modules/commands/os_info.cpp:147 +#, c-format +msgid "The oper info list for %s is full." +msgstr "Lista informacji operatora dla %s jest pełna." + +#: modules/commands/ns_info.cpp:184 +#, c-format +msgid "The services access status of %s will now be hidden from %s INFO displays." +msgstr "Status dostępu do serwisów osoby %s będzie ukrywany w informacjach %s." + +#: modules/commands/ns_info.cpp:185 +#, c-format +msgid "The services access status of %s will now be shown in %s INFO displays." +msgstr "Status dostępu do serwisów osoby %s będzie pokazywany w informacjach %s." + +#: modules/commands/os_session.cpp:433 +msgid "The session exception list is empty." +msgstr "Lista wyjątków sesji jest pusta." + +#: modules/commands/ns_recover.cpp:121 +msgid "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." +msgstr "" +"Użytkownik wykorzystujący Twojego nicka został usunięty.\n" +"Użyj tego polecenia ponownie, aby zdjąć blokadę założoną\n" +"przez serwisy." + +#: modules/pseudoclients/memoserv.cpp:195 +#, c-format +msgid "There are %d memos on channel %s." +msgstr "Jest %d wiadomości dla kanału %s." + +#: modules/commands/bs_botlist.cpp:47 +msgid "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" +msgstr "" +"Obecnie nie są dostępne żadne boty.\n" +"Poproś administratora serwisów o dodanie!" + +#: modules/commands/os_dns.cpp:213 +msgid "There are no configured servers." +msgstr "Brak skonfigurowanych serwerów." + +#: modules/commands/os_forbid.cpp:392 +#, c-format +msgid "There are no forbids of type %s." +msgstr "Nie ma zakazów typu %s." + +#: modules/commands/ns_group.cpp:162 +msgid "There are too many nicks in your group." +msgstr "W Twojej grupie jest zbyt wiele nicków." + +#: modules/commands/cs_log.cpp:123 +#, c-format +msgid "There currently are no logging configurations for %s." +msgstr "Aktualnie nie ma logowania skonfigurowanego dla %s." + +#: modules/pseudoclients/memoserv.cpp:193 +#, c-format +msgid "There is %d memo on channel %s." +msgstr "Jest %d wiadomość dla kanału %s." + +#: include/language.h:110 +#, c-format +msgid "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." +msgstr "" +"Jest nowa wiadomość dla kanału %s.\n" +"Napisz %s%s READ %s %d aby przeczytać." + +#: modules/commands/bs_assign.cpp:132 +#, c-format +msgid "There is no bot assigned to %s anymore." +msgstr "Nie ma żadnych botów przydzielonych do %s." + +#: modules/commands/os_news.cpp:33 +msgid "There is no logon news." +msgstr "Nie ma wiadomości powitalnych." + +#: modules/commands/os_news.cpp:43 +msgid "There is no oper news." +msgstr "Nie ma wiadomości dla operatorów." + +#: modules/commands/os_news.cpp:53 +msgid "There is no random news." +msgstr "Nie ma losowych wiadomości." + +#: modules/commands/os_config.cpp:41 +#, c-format +msgid "There is no such configuration block %s." +msgstr "Nie ma bloku konfiguracyjnego %s." + +#: modules/commands/cs_mode.cpp:706 +#, c-format +msgid "There is no such mode %s." +msgstr "Nie ma takiego trybu: %s." + +#: modules/commands/ms_set.cpp:52 +msgid "There's no email address set for your nick." +msgstr "Twój nick nie ma ustawionego adresu e-mail." + +#: modules/commands/os_forbid.cpp:304 modules/commands/os_forbid.cpp:496 +#, c-format +msgid "This channel has been forbidden: %s" +msgstr "Ten kanał został zablokowany: %s" + +#: modules/commands/cs_suspend.cpp:121 +msgid "This channel has been suspended." +msgstr "Ten kanał został zawieszony." + +#: modules/commands/cs_suspend.cpp:232 +msgid "This channel is suspended." +msgstr "Ten kanał jest zawieszony." + +#: modules/commands/cs_suspend.cpp:268 +msgid "This channel may not be used." +msgstr "Ten kanał nie może być używany." + +#: modules/commands/os_dns.cpp:702 +msgid "" +"This command allows managing DNS zones used for controlling what servers users\n" +"are directed to when connecting. Omitting all parameters prints out the status " +"of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given zones." +msgstr "" +"To polecenie pozwala na zarządzanie strefami DNS, używanych do sprawdzania,\n" +"na które serwery trafiają łączący się użytkownicy. Pominięcie wszystkich " +"parametrów\n" +"wyświetli status strefy DNS.\n" +"\n" +"ADDZONE dodaje strefę, np. pl.twojasiec.net. Następnie do stworzonej strefy " +"można\n" +"dodawać serwery używając komendy ADDSERVER.\n" +" \n" +"Komenda ADDSERVER dodaje serwer do podanej strefy. Gdy otrzymane zostanie " +"zapytanie,\n" +"to gdy strefa istnieje, zostanie ona wykorzystana, a w przeciwnym przypadku " +"przesłane zostaną\n" +"wszystkie serwery ze wszystkich stref.\n" +" Serwer może znajdować się we więcej niż jednej strefie.\n" +" \n" +"Komenda ADDIP przypisuje adres IP do serwera.\n" +" \n" +"Komendy POOL i DEPOOL aktywują i dezaktywują serwery w swoich podanych strefach." + +#: modules/commands/hs_group.cpp:72 +msgid "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." +msgstr "" +"To polecenie pozwala ustawić vhost bieżącego nicka\n" +"dla wszystkich nicków w grupie." + +#: modules/commands/ns_register.cpp:301 +msgid "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." +msgstr "" +"To polecenie tworzy także nową grupę dla Twojego nicka.\n" +"Pozwala ona na późniejsze rejestrowanie innych nicków,\n" +"posiadających wspólną konfigurację, wiadomości i uprawnienia\n" +"kanałowe." + +#: modules/m_rewrite.cpp:145 +#, c-format +msgid "This command is an alias to the command %s." +msgstr "To polecenie jest aliasem dla %s." + +#: modules/commands/ns_register.cpp:95 +msgid "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." +msgstr "" +"To polecenie umożliwia zakończenie procesu rejestracji\n" +"lub zmian wprowadzonych dla konta. Najczęściej jest używane\n" +"dla potwierdzenia adresu e-mail po rejestracji lub jego zmianie.\n" +" \n" +"Używane jest także po wykorzystaniu polecenia RESETPASS dla\n" +"umożliwienia identyfikacji celem zmiany hasła." + +#: modules/commands/os_modinfo.cpp:70 +msgid "This command lists information about the specified loaded module." +msgstr "To polecenie wyświetla informacje na temat załadowanego modułu." + +#: modules/commands/hs_list.cpp:136 +msgid "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." +msgstr "" +"To polecenie listuje zarejestrowane vhosty operatorowi.\n" +"Jeśli podano wzorzec tylko wpisy o pasujących nickach\n" +"lub vhostach zostaną pokazane. Podanie np. Rob*\n" +"spowoduje wyświetlenie wszystkich wpisów zaczynających\n" +"się od Rob.\n" +"\n" +"Jeśli zostanie użyty format #X-Y to tylko wpisy należące\n" +"do przedziału od X do Y będą pokazane. Podanie #1-3\n" +"spowoduje wyświetlenie pierwszych 3 wpisów wpisów." + +#: modules/commands/os_module.cpp:45 +msgid "" +"This command loads the module named modname from the modules\n" +"directory." +msgstr "To polecenie ładuje wskazany moduł z katalogu modułów." + +#: modules/commands/ns_group.cpp:201 +msgid "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." +msgstr "" +"Ta komenda powoduje dodanie Twojego nicka do grupy\n" +"reprezentowanej przez nick grupa-docelowa o haśle hasło.\n" +"\n" +"Grupowanie nicków pozwala na dzielenie się ustawieniami,\n" +"wiadomościami oraz uprawnieniami z innymi nickami z grupy.\n" +"\n" +"Jeśli jakiś nick z grupy zostanie usunięty, nie tracisz\n" +"żadnych ustawień czy uprawnień, jednak grupa istnieje\n" +"dopóki jest w niej przynajmniej jeden nick.\n" +"\n" +"Komenda może być użyta nawet wtedy kiedy bieżący nick\n" +"nie jest zarejestrowany, w przeciwnym wypadku musisz\n" +"się zidentyfikować.\n" +"\n" +"Możliwe i zalecane jest używanie tej komendy na nickach,\n" +"które nie są zarejestrowane, zostaną one wtedy automatycznie\n" +"dodane do bazy.\n" +"\n" +"UWAGA: Komendę można użyć także na zarejestrowanym nicku,\n" +"należy jednak wziąć pod uwagę to, że jeśli bieżący nick jest\n" +"ostatni ze swojej grupy, to wszystkie jego ustawienia oraz\n" +"uprawnienia zostaną usunięte! Z tego powodu najlepiej grupować\n" +"nowy nick ze starym, a nie na odwrót. Zmiana grupy może być\n" +"wyłączona przez administratora w niektórych sieciach.\n" +"\n" +"Można być tylko w jednej grupie w danej chwili,\n" +"łączenie grup nie jest możliwe.\n" +"\n" +"Uwaga: wszystkie nicki w grupie mają to samo hasło." + +#: modules/commands/ns_ajoin.cpp:292 +msgid "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." +msgstr "" +"To polecenie pozwala na zarządzanie Twoją listą automatycznego\n" +"dołączania. Gdy zalogujesz się, dołączysz automatycznie do kanałów\n" +"wpisanych na tę listę.\n" +"Operatorzy serwisów mogą podać nicka, aby modyfikować listy\n" +"innych użytkowników." + +#: modules/commands/ns_set.cpp:345 modules/commands/ns_set.cpp:669 +msgid "" +"This command may not be used on this network because nickname ownership is " +"disabled." +msgstr "" +"Tego polecenia nie można użyć w tej sieci, gdyż rejestracja nicków nie jest " +"dostępna." + +#: modules/commands/os_module.cpp:118 +msgid "This command reloads the module named modname." +msgstr "To polecenie ponownie ładuje wskazany moduł z katalogu modułów." + +#: modules/commands/hs_request.cpp:344 +msgid "This command retrieves the vhost requests." +msgstr "Ta komenda powoduje wyświetlenie próśb o vHosta." + +#: modules/commands/os_logsearch.cpp:159 +msgid "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." +msgstr "" +"To polecenie przeszukuje pliki logów serwisów pod kątem\n" +"wpisów pasujących do wzorca. Argument dni i limitu może zostać\n" +"użyty w celu sprecyzowania, ile dni logów przeszukiwać, i ile\n" +"wpisów maksymalnie wyświetlić. Domyślnie przeszukiwany jest\n" +"jeden tydzień i wyświetlane 50 wpisów.\n" +" \n" +"Na przykład:\n" +" LOGSEARCH +21d +500l Anope\n" +" Przeszukuje logi z ostatnich 21 dni pod kątem wpisów\n" +" zawierających Anope, a następnie wyświetla 500 najnowszych." + +#: modules/commands/cs_status.cpp:106 +msgid "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." +msgstr "" +"To polecenie informuje, jaki poziom dostępu na kanale ma\n" +"użytkownik, oraz do jakich wpisów (jeśli w ogóle) pasuje.\n" +"Dodatkowo, podana zostanie informacja dotycząca wpisów\n" +"AutoKick, do których pasuje podany użytkownik. Dostęp\n" +"do tego polecenia jest ograniczony tylko do użytkowników,\n" +"którzy mają uprawnienia do modyfikowania listy dostępowej." + +#: modules/commands/ns_group.cpp:285 +msgid "" +"This command ungroups your nick, or if given, the specified nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." +msgstr "" +"To polecenie usuwa Twój lub podany nick z grupy, w której\n" +"się znajduje. Usunięty nick zachowuje swój czas rejestracji,\n" +"hasło, e-mail, powitania, języki i url. Wszystko inne zostaje\n" +"skasowane. Nie możesz użyć tego polecenia, gdy w Twojej\n" +"grupie jest tylko jeden nick." + +#: modules/commands/os_module.cpp:168 +msgid "This command unloads the module named modname." +msgstr "To polecenie wyładowuje wskazany moduł." + +#: modules/commands/ns_register.cpp:355 +msgid "This command will resend you the registration confirmation email." +msgstr "" +"To polecenie spowoduje ponowne wysłanie e-maila potwierdzającego rejestrację." + +#: include/language.h:90 +#, c-format +msgid "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" +msgstr "" +"Ten nick jest zarejestrowany. Proszę, wybierz inny.\n" +"(Jeśli to Twój nick, wpisz %s%s IDENTIFY hasło.)" + +#: modules/commands/os_forbid.cpp:469 +#, c-format +msgid "This nickname has been forbidden: %s" +msgstr "Ten nick jest zabroniony, powód: %s" + +#: modules/commands/ns_recover.cpp:99 +#, c-format +msgid "This nickname has been recovered by %s." +msgstr "Ten nick został odzyskany przez %s." + +#: modules/commands/ns_recover.cpp:77 +#, c-format +msgid "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." +msgstr "" +"Ten nick został odzyskany przez %s. Jeśli to nie Ty zrobiłeś,\n" +"istnieje możliwość, że %s posiada Twoje hasło - powinieneś\n" +"je zatem zmienić." + +#: include/language.h:95 +msgid "This nickname has been registered; you may not use it." +msgstr "Ten nick jest zarejestrowany: nie możesz go użyć." + +#: modules/commands/ns_suspend.cpp:246 +msgid "This nickname is suspended." +msgstr "Ten nick jest zawieszony." + +#: include/language.h:92 +#, c-format +msgid "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." +msgstr "" +"Ten nick jest zarejestrowany i chroniony. Jeśli należy do Ciebie,\n" +"wpisz %s%s IDENTIFY hasło. W przeciwnym wypadku\n" +"wybierz proszę inny nick." + +#: modules/commands/ms_read.cpp:95 +#, c-format +msgid "To delete, type: %s%s %s %d" +msgstr "Aby usunąć, napisz: %s%s %s %d" + +#: modules/commands/ms_read.cpp:93 +#, c-format +msgid "To delete, type: %s%s %s %s %d" +msgstr "Aby usunąć, napisz: %s%s %s %s %d" + +#: modules/commands/bs_kick.cpp:791 +msgid "To protect ops against bot kicks" +msgstr "Ochrona opów przed kopaniem przez bota" + +#: modules/commands/bs_kick.cpp:856 +msgid "To protect voices against bot kicks" +msgstr "Ochrona posiadających prawo głosu przed kopaniem przez bota" + +#: modules/commands/cs_list.cpp:46 +msgid "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." +msgstr "" +"Aby wyszukać kanały o nazwach zaczynających się znakiem #\n" +"należy ten znak pominąć (anope zamiast #anope)." + +#: modules/commands/os_logsearch.cpp:139 +#, c-format +msgid "Too many results for %s." +msgstr "Za dużo wyników dla %s." + +#: modules/extra/stats/cs_fantasy_top.cpp:149 +#, c-format +msgid "Top %i of %s" +msgstr "Najlepsi %i wśród %s" + +#: modules/commands/os_list.cpp:43 +msgid "Topic" +msgstr "Temat" + +#: modules/commands/cs_topic.cpp:258 +msgid "Topic lock" +msgstr "TOPICLOCK" + +#: modules/commands/cs_topic.cpp:114 +#, c-format +msgid "Topic lock option for %s is now off." +msgstr "Blokada tematu na kanale %s została wyłączona." + +#: modules/commands/cs_topic.cpp:97 +#, c-format +msgid "Topic lock option for %s is now on." +msgstr "Blokada tematu na kanale %s została włączona." + +#: modules/commands/cs_topic.cpp:256 +msgid "Topic retention" +msgstr "KEEPTOPIC" + +#: modules/commands/cs_topic.cpp:60 +#, c-format +msgid "Topic retention option for %s is now off." +msgstr "Temat kanału %s nie będzie teraz utrzymywany." + +#: modules/commands/cs_topic.cpp:54 +#, c-format +msgid "Topic retention option for %s is now on." +msgstr "Temat kanału %s będzie teraz utrzymywany." + +#: modules/commands/cs_topic.cpp:265 +msgid "Topic set by" +msgstr "Temat ustawiony przez" + +#: modules/commands/bs_kick.cpp:1323 +msgid "Turn caps lock OFF!" +msgstr "Wyłącz CAPS LOCKa!" + +#: modules/extra/stats/m_chanstats.cpp:17 modules/extra/stats/m_chanstats.cpp:71 +msgid "Turn chanstats statistics on or off" +msgstr "Włącza lub wyłącza statystyki kanałowe" + +#: modules/commands/ns_set.cpp:1009 +msgid "Turn nickname security on or off" +msgstr "Włącza lub wyłącza bezpieczeństwo nicka" + +#: modules/commands/ns_set.cpp:655 +msgid "Turn protection on or off" +msgstr "Włącza lub wyłącza ochronę nicka" + +#: modules/commands/ns_list.cpp:264 +#, c-format +msgid "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Włącza lub wyłącza opcję PRIVATE dla nickaw %s.\n" +"Kiedy ta opcja jest włączona nick nie będzie\n" +"umieszczany na listach wyświetlanych komendą\n" +"LIST w %s. Jednak każdy, kto zna nick może uzyskać\n" +"o nim informacje używając polecenia INFO." + +#: modules/commands/ns_list.cpp:236 +#, c-format +msgid "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Włącza lub wyłącza opcję PRIVATE dla nickaw %s.\n" +"Kiedy ta opcja jest włączona nick nie będzie\n" +"umieszczany na listach wyświetlanych komendą:\n" +"/msg %s LIST\n" +"Jednak każdy, kto zna nick może uzyskać o nim\n" +"informacje używając polecenia INFO." + +#: modules/commands/ns_set.cpp:1059 modules/commands/ns_set.cpp:1088 +#, c-format +msgid "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." +msgstr "" +"Włącza lub wyłącza opcję bezpieczeństwa dla nicka.\n" +"Włączenie SECURE wymusza na użytkowniku podanie\n" +"hasła zanim ten zostanie rozpoznany jako właściciel\n" +"nicka. %s nie bierze pod uwagę w tym wypadku\n" +"występowania adresu liście dostępu. Jeśli adres \n" +"znajduje się na liście %s nie skilluje\n" +"użytkownika niezależnie od ustawienia opcji KILL." + +#: modules/extra/stats/m_chanstats.cpp:142 +msgid "Turns chanstats channel statistics ON or OFF for this user." +msgstr "Włącza lub wyłącza statystyki kanałowe dla podanego użytkownika." + +#: modules/extra/stats/m_chanstats.cpp:61 modules/extra/stats/m_chanstats.cpp:119 +msgid "Turns chanstats statistics ON or OFF." +msgstr "Włącza lub wyłącza statystyki kanałowe." + +#: modules/commands/ns_set.cpp:772 +#, c-format +msgid "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Włącza lub wyłącza automatyczną ochronę dla nicka.\n" +"Użytkownicy wchodzący na chroniony nick otrzymują\n" +"informacje od %s, że nick jest zarejestrowany i\n" +"jeśli się nie zidentyfikują lub go nie zmienią\n" +"w określonym czasie to ich nick zostanie zmieniony\n" +"siłą lub zostaną odłączeni od sieci.\n" +"\n" +"Opcja QUICK skraca czas oczekiwania na zmianę\n" +"z 60 sekund do 20. W przypadku opcji IMMED\n" +"nick zostanie zmieniony natychmiast bez możliwości\n" +"identyfikacji (wstępna identyfikacja następuje\n" +"na podstawie listy dostępu, dlatego tę opcję\n" +"należy stosować z rozwagą). Administrator sieci \n" +"może wyłączyć korzystanie z IMMED." + +#: modules/commands/ns_set.cpp:738 +#, c-format +msgid "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Włącza lub wyłącza automatyczną ochronę dla Twojego\n" +"nicka. Użytkownicy wchodzący na chroniony nick otrzymują\n" +"informacje od %s, że nick jest zarejestrowany i\n" +"jeśli się nie zidentyfikują lub go nie zmienią\n" +"w określonym czasie to ich nick zostanie zmieniony\n" +"siłą lub zostaną odłączeni od sieci.\n" +"\n" +"Opcja QUICK skraca czas oczekiwania na zmianę\n" +"z 60 sekund do 20. W przypadku opcji IMMED\n" +"nick zostanie zmieniony natychmiast bez możliwości\n" +"identyfikacji (wstępna identyfikacja następuje\n" +"na podstawie listy dostępu, dlatego tą opcję\n" +"należy stosować z rozwagą). Administrator sieci \n" +"może wyłączyć korzystanie z IMMED." + +#: modules/commands/os_forbid.cpp:358 modules/commands/bs_badwords.cpp:194 +msgid "Type" +msgstr "Typ" + +#: modules/commands/ns_set.cpp:62 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Aby uzyskać więcej informacji o danej opcji wpisz:\n" +"%s%s HELP %s opcja" + +#: modules/commands/bs_kick.cpp:151 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." +msgstr "" +"Aby uzyskać więcej informacji o danej opcji wpisz:\n" +"%s%s HELP %s opcja\n" +" \n" +"Uwaga: dostęp do tej opcji jest kontrolowany\n" +"poprzez poziom SET." + +#: modules/commands/ns_set.cpp:107 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." +msgstr "" +"Aby uzyskać więcej informacji o danej opcji wpisz:\n" +"%s%s HELP %s opcja\n" +"Ta opcja zostanie ustawiona dla podanego nicka." + +#: modules/commands/bs_set.cpp:62 modules/commands/cs_set.cpp:63 +#, c-format +msgid "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." +msgstr "" +"Aby uzyskać więcej informacji o danej opcji wpisz:\n" +"%s%s HELP %s opcja" + +#: modules/pseudoclients/nickserv.cpp:361 +#, c-format +msgid "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." +msgstr "" +"Napisz %s%s SET EMAIL e-mail, aby ustawić adres e-mail.\n" +"Twoja prywatność będzie uszanowana - nie będzie podawany osobom trzecim." + +#: modules/commands/os_module.cpp:128 +msgid "Un-Load a module" +msgstr "Wyładowuje moduł" + +#: modules/commands/os_sxline.cpp:337 modules/commands/os_sxline.cpp:552 +#: modules/commands/os_akill.cpp:136 +#, c-format +msgid "Unable to find regex engine %s." +msgstr "Nie można odnaleźć silnika regex %s" + +#: modules/commands/os_module.cpp:36 modules/commands/os_module.cpp:108 +#, c-format +msgid "Unable to load module %s." +msgstr "Nie można załadować modułu %s" + +#: modules/commands/os_module.cpp:73 modules/commands/os_module.cpp:90 +#: modules/commands/os_module.cpp:145 modules/commands/os_module.cpp:159 +#, c-format +msgid "Unable to remove module %s." +msgstr "Nie można wyładować modułu %s" + +#: modules/commands/bs_assign.cpp:90 +msgid "Unassigns a bot from a channel" +msgstr "Usuwa bota z kanału" + +#: modules/commands/bs_assign.cpp:139 +msgid "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." +msgstr "" +"Użycie tej komendy usuwa bota z kanału.\n" +"Będzie można go ponownie przydzielić w każdej\n" +"chwili, bez potrzeby ponownego konfigurowania." + +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1193 +#: modules/commands/bs_kick.cpp:1196 +msgid "Underlines kicker" +msgstr "Kopanie za podkreślenia" + +#: modules/commands/os_dns.cpp:595 +msgid "Unknown SET option." +msgstr "Nieznana opcja komendy SET." + +#: modules/commands/os_stats.cpp:229 +#, c-format +msgid "Unknown STATS option: %s" +msgstr "Nieznana opcja STATS %s" + +#: src/command.cpp:222 src/command.cpp:233 +#, c-format +msgid "Unknown command %s." +msgstr "Nieznana opcja %s." + +#: src/command.cpp:220 src/command.cpp:231 +#, c-format +msgid "Unknown command %s. \"%s%s HELP\" for help." +msgstr "Nieznana komenda %s. Napisz \"%s%s HELP\" aby uzyskać pomoc." + +#: modules/commands/cs_mode.cpp:317 modules/commands/cs_mode.cpp:409 +#, c-format +msgid "Unknown mode character %c ignored." +msgstr "Nieznana flaga %c zostaje zignorowana." + +#: modules/commands/os_logsearch.cpp:78 +#, c-format +msgid "Unknown parameter: %s" +msgstr "Nieznany parametr: %s" + +#: modules/commands/os_dns.cpp:241 +msgid "Unpooled" +msgstr "Usunięto z puli" + +#: modules/commands/cs_drop.cpp:77 +msgid "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." +msgstr "" +"Usuwa podany kanał. Komenda może zostać użyta\n" +"jedynie przez właściciela kanału." + +#: modules/commands/cs_drop.cpp:74 +msgid "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." +msgstr "" +"Usuwa wskazany kanał. Tylko administratorzy serwisów\n" +"mogą usunąć kanał, którego nie są właścicielami." + +#: modules/commands/ns_suspend.cpp:160 +msgid "Unsuspend a given nick" +msgstr "Uwalnia zawieszonego nicka" + +#: modules/commands/ns_suspend.cpp:199 +msgid "Unsuspends a nickname which allows it to be used again." +msgstr "\"Odwiesza\" nicka, dzięki czemu może on zostać użyty ponownie." + +#: modules/commands/cs_updown.cpp:126 +msgid "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." +msgstr "" +"Aktualizuje uprawnienia podanego nicka na kanale. Jeśli\n" +"nie podasz nicka, zaktualizowane zostaną Twoje\n" +"uprawnienia. Gdy pominiesz kanał, wówczas Twój\n" +"status zostanie zaktualizowany na wszystkich kanałach,\n" +"na których jesteś." + +#: modules/commands/cs_updown.cpp:48 +msgid "Updates a selected nicks status on a channel" +msgstr "Aktualizuje uprawnienia podanego nicka na kanale" + +#: modules/commands/ns_update.cpp:19 +msgid "Updates your current status, i.e. it checks for new memos" +msgstr "Aktualizuje twój obecny status np. sprawdza nowe wiadomości" + +#: modules/commands/ns_update.cpp:43 +msgid "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." +msgstr "" +"Aktualizuje twój obecny status, np. sprawdza czy są nowe\n" +"wiadomości, ustawia odpowiednie uprawnienia na kanałach,\n" +"aktualizuje vhosta oraz flagi użytkownika." + +#: modules/commands/os_update.cpp:25 +msgid "Updating databases." +msgstr "Aktualizacja baz danych." + +#: modules/commands/os_stats.cpp:154 +#, c-format +msgid "Uplink capab: %s" +msgstr "Uplink capab: %s" + +#: modules/commands/os_stats.cpp:153 +#, c-format +msgid "Uplink server: %s" +msgstr "Podłączony do: %s" + +#: modules/commands/help.cpp:127 +#, c-format +msgid "Use the %s ALL command to list all commands and their descriptions." +msgstr "Użyj polecenia %s ALL w celu wyświetlenia wszystkich poleceń i ich opisów." + +#: modules/commands/bs_info.cpp:59 +msgid "Used on" +msgstr "Używany" + +#: data/chanserv.example.conf:821 +msgid "Used to manage channels" +msgstr "Zarządza kanałami" + +#: data/chanserv.example.conf:809 +msgid "Used to manage the list of privileged users" +msgstr "Zarządza listą dostępu" + +#: data/chanserv.example.conf:815 +msgid "Used to modify the channel status of you or other users" +msgstr "Modyfikuje uprawnienia na kanale dotyczące Ciebie lub innych" + +#: modules/commands/cs_akick.cpp:575 +msgid "User has been banned from the channel" +msgstr "Użytkownik został zbanowany" + +#: modules/commands/os_dns.cpp:587 +#, c-format +msgid "User limit for %s removed." +msgstr "Usunięto limit użytkowników dla %s." + +#: modules/commands/os_dns.cpp:585 +#, c-format +msgid "User limit for %s set to %d." +msgstr "Limit użytkowników dla %s zmieniono na %d." + +#: modules/commands/os_list.cpp:43 +msgid "Users" +msgstr "Użytkownicy" + +#: modules/commands/os_stats.cpp:172 +#, c-format +msgid "Users (nick): %lu entries, %lu buckets, longest chain is %d" +msgstr "Użytkownicy (nicki): %lu wpisów, %lu pakietów, najdłuższy łańcuch to %d" + +#: modules/commands/os_stats.cpp:177 +#, c-format +msgid "Users (uid): %lu entries, %lu buckets, longest chain is %d" +msgstr "Użytkownicy (uid): %lu wpisów, %lu pakietów, najdłuższy łańcuch to %d" + +#: modules/commands/os_list.cpp:184 +msgid "Users list:" +msgstr "Lista użytkowników:" + +#: modules/commands/ns_info.cpp:106 modules/commands/ns_info.cpp:108 +msgid "VHost" +msgstr "VHost" + +#: modules/commands/hs_set.cpp:92 +#, c-format +msgid "VHost for %s set to %s." +msgstr "Vhost dla %s został zmieniony na %s." + +#: modules/commands/hs_set.cpp:90 +#, c-format +msgid "VHost for %s set to %s@%s." +msgstr "Vhost dla %s został zmieniony na %s@%s." + +#: modules/commands/hs_set.cpp:199 +#, c-format +msgid "VHost for group %s set to %s." +msgstr "Vhosty dla grupy %s zostały zmienione na %s." + +#: modules/commands/hs_set.cpp:197 +#, c-format +msgid "VHost for group %s set to %s@%s." +msgstr "Vhosty dla grupy %s zostały zmienione na %s@%s." + +#: modules/commands/os_session.cpp:247 +msgid "VIEW host" +msgstr "VIEW host" + +#: modules/commands/os_sxline.cpp:428 modules/commands/os_sxline.cpp:662 +#: modules/commands/os_akill.cpp:389 +msgid "VIEW [mask | list | id]" +msgstr "VIEW [maska | lista | id]" + +#: modules/commands/os_session.cpp:526 +msgid "VIEW [mask | list]" +msgstr "VIEW [maska | lista]" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +msgid "Value" +msgstr "Wartość" + +#: modules/commands/os_config.cpp:48 +#, c-format +msgid "Value of %s:%s changed to %s" +msgstr "Wartość %s:%s zmieniona na %s" + +#: modules/commands/hs_request.cpp:305 modules/commands/hs_list.cpp:58 +msgid "Vhost" +msgstr "Vhost" + +#: modules/commands/hs_del.cpp:38 +#, c-format +msgid "Vhost for %s removed." +msgstr "Vhost dla %s został usunięty." + +#: modules/commands/os_oper.cpp:69 +msgid "View and change Services Operators" +msgstr "Podgląd i modyfikacja operatorów serwisów" + +#: modules/commands/os_config.cpp:19 +msgid "View and change configuration file settings" +msgstr "Podejrzyj i zmodyfikuj ustawienia w pliku konfiguracyjnym" + +#: modules/commands/os_session.cpp:245 +msgid "View the list of host sessions" +msgstr "Wyświetla listę sesji" + +#: modules/commands/bs_kick.cpp:1221 +msgid "Voices protection" +msgstr "DONTKICKVOICES" + +#: modules/commands/bs_kick.cpp:1406 +msgid "Watch your language!" +msgstr "Uważaj co piszesz!" + +#: modules/commands/cs_list.cpp:237 +#, c-format +msgid "" +"When private is set, the channel will not appear in\n" +"%s's %s command." +msgstr "" +"Gdy ustawiono tryb prywatny, kanał nie zostanie podany przez %s\n" +"w poleceniu %s." + +#: modules/commands/ms_info.cpp:204 +msgid "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." +msgstr "" +"Polecenie wydane bez parametru wyświetla informacje o\n" +"liczbie odebranych wiadomości, liczbie nowych wiadomości\n" +"oraz limicie wiadomości.\n" +"\n" +"Jeśli zostanie wskazany kanał, pokazane zostaną te \n" +"same informacje w odniesieniu do tego kanału.\n" +"\n" +"Administratorzy serwisów mogą obejrzeć informacje \n" +"dot. dowolnych użytkowników podając parametr nick." + +#: modules/commands/ns_logout.cpp:66 +msgid "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." +msgstr "" +"Polecenie wydane bez parametrów odwraca działanie\n" +"komendy IDENTIFY - nie będziesz rozpoznawany jako\n" +"właściciel nicka.\n" +"\n" +"Administrator serwisów może podać jako parametr nick\n" +"użytkownika, który ma zostać wylogowany. Parametr\n" +"REVALIDATE powoduje informowanie przez serwisy\n" +"użytkownika o potrzebie ponownej identyfikacji." + +#: modules/commands/os_stats.cpp:236 +msgid "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." +msgstr "" +"Polecenie bez parametrów wyświetla bieżącą liczbę \n" +"użytkowników oraz operatorów podłączonych do sieci (nie\n" +"licząc serwisów), największą liczbę użytkowników licząc od \n" +"startu serwisów oraz czas pracy serwisów.\n" +"\n" +"Parametr AKILL wyświetla informacje o rozmiarze listy\n" +"AKILL oraz domyślnym czasie wygasania wpisów.\n" +"\n" +"Parametr RESET resetuje maksymalną liczbę użytkowników\n" +"podłączonych do sieci.\n" +"\n" +"Parametr UPLINK wyświetla informacje o serwerze, do \n" +"którego serwisy są bezpośrednio podłączone.\n" +" \n" +"ParametrHASH wyświetla informacje o mapie hashy.\n" +"\n" +"Parametr ALL wyświetla wszystkie dostępne informacje." + +#: modules/commands/bs_badwords.cpp:194 +msgid "Word" +msgstr "Słowo" + +#: modules/commands/ns_group.cpp:158 +#, c-format +msgid "You are already a member of the group of %s." +msgstr "Należysz już do grupy %s." + +#: modules/commands/os_login.cpp:34 modules/commands/ns_identify.cpp:87 +msgid "You are already identified." +msgstr "Jesteś już zidentyfikowany(a)." + +#: modules/commands/cs_invite.cpp:64 +#, c-format +msgid "You are already in %s!" +msgstr "Przebywasz już na kanale %s!" + +#: modules/commands/os_set.cpp:91 +msgid "You are no longer a super admin." +msgstr "Nie jesteś już dłużej super-administratorem." + +#: modules/commands/os_login.cpp:81 +msgid "You are not identified." +msgstr "Nie jesteś zidentyfikowany(a)." + +#: include/language.h:100 +msgid "You are not permitted to be on this channel." +msgstr "Nie możesz znajdować się na tym kanale." + +#: modules/commands/ms_set.cpp:158 +msgid "You are not permitted to change your memo limit." +msgstr "Nie możesz zmieniać swojego limitu wiadomości." + +#: modules/commands/ns_cert.cpp:183 +msgid "You are not using a client certificate." +msgstr "Nie korzystasz z certyfikatu klienta." + +#: modules/commands/os_set.cpp:85 +msgid "You are now a super admin." +msgstr "Jesteś teraz super-administratorem." + +#: modules/commands/os_oline.cpp:36 +msgid "You are now an IRC Operator." +msgstr "Jesteś teraz IRC operatorem." + +#: modules/commands/ns_resetpass.cpp:108 +msgid "You are now identified for your nick. Change your password now." +msgstr "Jesteś zidentyfikowany. Zmień teraz swoje hasło." + +#: modules/commands/ns_group.cpp:64 +#, c-format +msgid "You are now in the group of %s." +msgstr "Należysz teraz do grupy %s." + +#: modules/pseudoclients/memoserv.cpp:147 +#, c-format +msgid "" +"You are over your maximum number of memos (%d). You will be unable to receive any " +"new memos until you delete some of your current ones." +msgstr "" +"Uwaga: Maksymalny limit wiadomości (%d) został osiągnięty.\n" +"Nie będziesz otrzymywać nowych wiadomości jeśli kilku nie usuniesz." + +#: modules/commands/os_noop.cpp:33 +msgid "You can not NOOP Services." +msgstr "Nie możesz użyć NOOP na serwisach." + +#: modules/commands/cs_access.cpp:672 +msgid "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." +msgstr "" +"Nie możesz wyłączyć uprawnienia właściciela, gdyż nie dałoby się wtedy ustawić go " +"ponownie w przyszłości." + +#: modules/commands/os_jupe.cpp:34 +msgid "You can not jupe an already juped server." +msgstr "Nie można wykluczyć serwera, ponieważ już to zrobiono." + +#: modules/commands/os_jupe.cpp:32 +msgid "You can not jupe your Services' pseudoserver or your uplink server." +msgstr "Nie można wykluczyć samych serwisów lub uplinka serwisów." + +#: modules/commands/os_module.cpp:80 +#, c-format +msgid "You can not reload this module directly, instead reload %s." +msgstr "" +"Nie możesz bezpośrednio przeładować podanego modułu. Zamiast tego przeładuj %s." + +#: modules/commands/ms_rsend.cpp:46 +msgid "You can not request a receipt when sending a memo to yourself." +msgstr "Nie możesz wysyłać wiadomości z potwierdzeniem odbioru do siebie!" + +#: modules/commands/ns_recover.cpp:163 +#, c-format +msgid "You can't %s yourself!" +msgstr "Nie możesz usunąć samego siebie za pomocą %s!" + +#: modules/commands/cs_xop.cpp:151 modules/commands/cs_flags.cpp:109 +#: modules/commands/cs_access.cpp:154 +msgid "You can't add a channel to its own access list." +msgstr "Nie możesz dodać kanału do swojej własnej listy dostępowej %s." + +#: modules/commands/ns_logout.cpp:37 +#, c-format +msgid "You can't logout %s, they are a Services Operator." +msgstr "Nie mogę wylogować %s, bo to administrator serwisów." + +#: modules/commands/ns_set.cpp:927 +#, c-format +msgid "You cannot %s on this network." +msgstr "Nie możesz %s w tej sieci." + +#: modules/commands/cs_flags.cpp:231 +#, c-format +msgid "You cannot set the %c flag." +msgstr "Nie możesz ustawić flagi %c." + +#: modules/commands/ms_set.cpp:173 +#, c-format +msgid "You cannot set the memo limit for %s higher than %d." +msgstr "Nie możesz ustawić limitu wiadomości dla %s większego niż %d." + +#: modules/commands/ms_set.cpp:175 +#, c-format +msgid "You cannot set your memo limit higher than %d." +msgstr "Nie możesz ustawić swojego limitu wiadomości większego niż %d." + +#: modules/commands/bs_assign.cpp:124 +msgid "You cannot unassign bots while persist is set on the channel." +msgstr "Nie możesz usunąć przypisania bota, dopóki kanał ma ustawiony PERSIST." + +#: modules/commands/ns_set.cpp:480 +msgid "You cannot unset the e-mail on this network." +msgstr "Nie możesz usuwać adresu e-mail w tej sieci." + +#: modules/commands/help.cpp:177 +msgid "You cannot use this command." +msgstr "Nie możesz użyć tego polecenia." + +#: modules/commands/ms_info.cpp:151 +#, c-format +msgid "You currently have %d memos, of which %d are unread." +msgstr "Aktualnie masz %d wiadomości, z czego %d jest nieprzeczytanych." + +#: modules/commands/ms_info.cpp:149 +#, c-format +msgid "You currently have %d memos, of which 1 is unread." +msgstr "Aktualnie masz %d wiadomości, w tym jedną nieprzeczytaną." + +#: modules/commands/ms_info.cpp:147 +#, c-format +msgid "You currently have %d memos." +msgstr "Aktualnie masz %d wiadomości." + +#: modules/commands/ms_info.cpp:145 +#, c-format +msgid "You currently have %d memos; all of them are unread." +msgstr "Aktualnie masz %d nieprzeczytanych wiadomości." + +#: modules/commands/ms_info.cpp:134 +msgid "You currently have 1 memo, and it has not yet been read." +msgstr "Aktualnie masz jedną wiadomość i jest ona nieprzeczytana." + +#: modules/commands/ms_info.cpp:136 +msgid "You currently have 1 memo." +msgstr "Aktualnie masz jedną wiadomość." + +#: modules/commands/ms_info.cpp:130 +msgid "You currently have no memos." +msgstr "Aktualnie nie masz wiadomości." + +#: modules/commands/cs_mode.cpp:564 modules/commands/cs_mode.cpp:621 +#, c-format +msgid "You do not have access to set mode %c." +msgstr "Nie masz uprawnień dla ustawienia flagi %c." + +#: modules/commands/cs_mode.cpp:578 modules/commands/cs_mode.cpp:590 +#: modules/commands/cs_mode.cpp:631 +#, c-format +msgid "You do not have the access to change %s's modes." +msgstr "Nie masz uprawnień do zmiany trybów na %s." + +#: modules/commands/cs_seen.cpp:198 +#, c-format +msgid "You found me, %s!" +msgstr "Ha, odnalazłeś mnie, %s!" + +#: modules/pseudoclients/memoserv.cpp:143 +#, c-format +msgid "You have %d new memos." +msgstr "Masz %d nowe(ych) wiadomości." + +#: modules/pseudoclients/memoserv.cpp:143 +msgid "You have 1 new memo." +msgstr "Masz jedną nową wiadomość." + +#: include/language.h:112 +#, c-format +msgid "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." +msgstr "" +"Masz nową wiadomość od %s.\n" +"Napisz %s%s READ %d aby przeczytać." + +#: modules/commands/cs_invite.cpp:76 +#, c-format +msgid "You have been invited to %s by %s." +msgstr "Zostałeś zaproszony do %s przez %s." + +#: modules/commands/cs_invite.cpp:81 +#, c-format +msgid "You have been invited to %s." +msgstr "Zostałeś zaproszony do %s." + +#: modules/commands/ns_recover.cpp:96 modules/protocol/ratbox.cpp:166 +#, c-format +msgid "You have been logged in as %s." +msgstr "Zalogowałeś się jako %s." + +#: modules/commands/os_login.cpp:86 +msgid "You have been logged out." +msgstr "Twój nick został pomyślnie wylogowany." + +#: modules/commands/cs_unban.cpp:98 +#, c-format +msgid "You have been unbanned from %s." +msgstr "Ban na kanale %s został zdjęty." + +#: modules/commands/cs_unban.cpp:56 +#, c-format +msgid "You have been unbanned from %d channels." +msgstr "Bany na %d kanałach zostały zdjęte." + +#: modules/commands/ms_info.cpp:169 +msgid "You have no limit on the number of memos you may keep." +msgstr "Nie masz limitu wiadomości, które możesz trzymać." + +#: include/language.h:114 +msgid "You have no memos." +msgstr "Nie masz wiadomości." + +#: include/language.h:117 +msgid "You have no new memos." +msgstr "Nie masz nowych wiadomości." + +#: modules/pseudoclients/memoserv.cpp:149 +#, c-format +msgid "" +"You have reached your maximum number of memos (%d). You will be unable to receive " +"any new memos until you delete some of your current ones." +msgstr "" +"Uwaga: Osiągnięto już limit wiadomości (%d).\n" +"Nie będziesz otrzymywać nowych wiadomości dopóki\n" +"nie usuniesz kilku starych." + +#: modules/commands/ns_recover.cpp:117 +#, c-format +msgid "You have regained control of %s." +msgstr "Odzyskałeś kontrolę nad %s." + +#: modules/commands/ns_drop.cpp:66 +msgid "You may drop any nick within your group." +msgstr "Możesz usunąć dowolny nick ze swojej grupy." + +#: modules/commands/cs_mode.cpp:322 modules/commands/cs_mode.cpp:414 +#, c-format +msgid "You may not (un)lock mode %c." +msgstr "Nie możesz (od)blokować flagi %c." + +#: modules/commands/ns_set.cpp:485 +msgid "You may not change the e-mail of other Services Operators." +msgstr "Nie możesz zmieniać adresu e-mail innych operatorów serwisów." + +#: modules/commands/ns_set.cpp:474 +msgid "You may not change the email of an unconfirmed account." +msgstr "Nie możesz zmienić adresu e-mail dla niepotwierdzonego konta." + +#: modules/commands/ns_set.cpp:196 +msgid "You may not change the password of other Services Operators." +msgstr "Nie możesz zmienić hasła innych operatorów serwisów." + +#: modules/commands/ns_drop.cpp:45 +msgid "You may not drop other Services Operators' nicknames." +msgstr "Nie możesz skasować nicków innych operatorów serwisów." + +#: modules/commands/ns_getpass.cpp:32 +msgid "You may not get the password of other Services Operators." +msgstr "Nie możesz odczytać hasła innych operatorów serwisów." + +#: modules/commands/ns_suspend.cpp:100 +msgid "You may not suspend other Services Operators' nicknames." +msgstr "Nie możesz zawiesić nicków innych operatorów serwisów." + +#: modules/commands/ns_access.cpp:136 +msgid "You may view but not modify the access list of other Services Operators." +msgstr "" +"Możesz podglądać, ale nie modyfikować list dostępowych innych operatorów serwisów." + +#: modules/commands/ns_cert.cpp:292 +msgid "" +"You may view but not modify the certificate list of other Services Operators." +msgstr "" +"Możesz podglądać, ale nie modyfikować list certyfikatów innych operatorów " +"serwisów." + +#: modules/commands/cs_seen.cpp:287 +#, c-format +msgid "You might see yourself in the mirror, %s." +msgstr "Spojrzyj w lustro, %s." + +#: include/language.h:120 +msgid "You must assign a bot to the channel before using this command." +msgstr "Musisz przypisać bota do kanału, zanim użyjesz tej komendy." + +#: modules/commands/cs_register.cpp:49 +msgid "You must be a channel operator to register the channel." +msgstr "Aby zarejestrować kanał musisz być jego operatorem." + +#: modules/commands/cs_updown.cpp:94 modules/commands/cs_updown.cpp:192 +#, c-format +msgid "You must be in %s to use this command." +msgstr "Musisz być w %s aby użyć tego polecenia." + +#: include/language.h:85 +msgid "You must be logged into an account to use that command." +msgstr "Musisz być zalogowany do swojego konta, aby użyć tego polecenia." + +#: modules/commands/cs_register.cpp:37 +msgid "You must confirm your account before you can register a channel." +msgstr "Aby zarejestrować kanał, musisz potwierdzić najpierw swoje konto." + +#: modules/commands/hs_request.cpp:100 +msgid "You must confirm your account before you may request a vhost." +msgstr "Musisz potwierdzić swoje konto przed wysłaniem prośby o vhost." + +#: modules/commands/ms_send.cpp:44 +msgid "You must confirm your account before you may send a memo." +msgstr "Musisz potwierdzić swoje konto przed wysłaniem wiadomości." + +#: modules/commands/cs_drop.cpp:42 +#, c-format +msgid "" +"You must enter the channel name twice as a confirmation that you wish to drop %s." +msgstr "" +"Musisz dwukrotnie podać nazwę kanału, aby potwierdzić, że na pewno chcesz " +"odrejestrować %s." + +#: modules/commands/ns_register.cpp:153 +#, c-format +msgid "You must have been using this nick for at least %d seconds to register." +msgstr "" +"Musisz być połączony(a) dłużej niż %d sekund(y), aby móc zarejestrować nick." + +#: modules/commands/cs_mode.cpp:913 +#, c-format +msgid "You must have the %s(ME) privilege on the channel to use this command." +msgstr "Musisz mieć uprawnienie %s(ME) aby użyć tego polecenia." + +#: modules/pseudoclients/nickserv.cpp:358 +msgid "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." +msgstr "" +"Teraz ustaw adres e-mail dla Twojego nicka.\n" +"Gdy zapomnisz hasła, zostanie ono wysłane na e-mail." + +#: modules/commands/help.cpp:172 +msgid "You need to be identified to use this command." +msgstr "Musisz być zalogowany, aby móc używać tego polecenia." + +#: modules/commands/ms_info.cpp:182 +msgid "You will be notified by message and by mail when new memos arrive." +msgstr "" +"Będziesz otrzymywać powiadomienie o nowych wiadomościach\n" +"na IRC i przez e-mail." + +#: modules/commands/ms_info.cpp:175 +msgid "" +"You will be notified of new memos at logon and when they arrive, and by mail when " +"they arrive." +msgstr "" +"Będziesz powiadomienie informacje o nowych wiadomościach\n" +"podczas logowania i w momencie ich nadejścia (bezpośrednio\n" +"i przez e-mail)." + +#: modules/commands/ms_info.cpp:177 +msgid "You will be notified of new memos at logon and when they arrive." +msgstr "" +"Będziesz powiadomienie informacje o nowych wiadomościach\n" +"podczas logowania i w momencie ich nadejścia." + +#: modules/commands/ms_info.cpp:189 +msgid "You will be notified of new memos at logon, and by mail when they arrive." +msgstr "" +"Będziesz powiadomienie informacje o nowych wiadomościach\n" +"podczas logowania i w momencie ich nadejścia (przez e-mail)." + +#: modules/commands/ms_info.cpp:191 +msgid "You will be notified of new memos at logon." +msgstr "Będziesz otrzymywać powiadomienie o nowych wiadomościach podczas logowania." + +#: modules/commands/ms_info.cpp:184 +msgid "You will be notified when new memos arrive." +msgstr "Będziesz otrzymywać powiadomienie o nowych wiadomościach." + +#: modules/commands/ms_set.cpp:190 +msgid "You will no longer be able to receive memos." +msgstr "Nie będziesz już dłużej odbierać wiadomości." + +#: modules/commands/ms_set.cpp:57 +msgid "You will no longer be informed via email." +msgstr "Powiadomienie o nowych wiadomościach nie będą wysyłane na adres e-mail." + +#: modules/commands/ms_info.cpp:195 +msgid "You will not be notified of new memos." +msgstr "Nie będziesz otrzymywać informacji o nowych wiadomościach." + +#: modules/commands/ms_set.cpp:49 +msgid "You will now be informed about new memos via email." +msgstr "Powiadomienie o nowych wiadomościach będą wysyłane na adres e-mail." + +#: modules/commands/os_svs.cpp:86 +msgid "Your IRCd does not support SVSJOIN." +msgstr "Ten IRCd nie obsługuje SVSJOIN." + +#: modules/commands/os_svs.cpp:31 +msgid "Your IRCd does not support SVSNICK." +msgstr "Ten IRCd nie obsługuje SVSNICK." + +#: modules/commands/os_svs.cpp:130 +msgid "Your IRCd does not support SVSPART." +msgstr "Ten IRCd nie obsługuje SVSPART." + +#: include/language.h:127 +msgid "" +"Your IRCd does not support vIdent's, if this is incorrect, please report this as " +"a possible bug" +msgstr "" +"Ten IRCd nie obsługuje vIdentów. Jeżeli to nieprawda, wyślij zgłoszenie o błędzie." + +#: modules/extra/m_ldap_authentication.cpp:110 +#: modules/extra/m_sql_authentication.cpp:55 +#, c-format +msgid "Your account %s has been successfully created." +msgstr "Stworzono konto %s." + +#: modules/commands/ns_register.cpp:330 +msgid "Your account is already confirmed." +msgstr "Konto jest już potwierdzone." + +#: modules/commands/ns_register.cpp:398 +#, c-format +msgid "Your account will expire, if not confirmed, in %s." +msgstr "Jeżeli nie zostanie potwierdzone, Twoje konto wygaśnie za %s." + +#: modules/commands/ns_set.cpp:1274 +#, c-format +msgid "Your email address has been changed to %s." +msgstr "Twój adres e-mail został zmieniony na %s." + +#: modules/commands/os_forbid.cpp:544 modules/commands/os_forbid.cpp:553 +msgid "Your email address is not allowed, choose a different one." +msgstr "Twój e-mail nie jest dozwolony. Użyj innego." + +#: modules/commands/ns_register.cpp:262 modules/commands/ns_register.cpp:393 +msgid "" +"Your email address is not confirmed. To confirm it, follow the instructions that " +"were emailed to you." +msgstr "" +"Twój adres e-mail nie jest potwierdzony. Aby to zrobić, postępuj według wysłanych " +"Tobie instrukcji." + +#: modules/commands/ns_register.cpp:67 +#, c-format +msgid "Your email address of %s has been confirmed." +msgstr "Twój e-mail %s został potwierdzony." + +#: modules/extra/m_ldap_authentication.cpp:159 +#, c-format +msgid "Your email has been updated to %s" +msgstr "Twój e-mail został zmieniony na %s" + +#: modules/extra/m_sql_authentication.cpp:62 +#, c-format +msgid "Your email has been updated to %s." +msgstr "Twój adres e-mail został zmieniony na %s." + +#: modules/commands/ms_set.cpp:197 +msgid "Your memo limit has been disabled." +msgstr "Twój limit wiadomości został wyłączony." + +#: modules/commands/ms_set.cpp:183 +#, c-format +msgid "Your memo limit has been set to %d." +msgstr "Twój limit wiadomości został zmieniony na %d." + +#: modules/commands/ms_info.cpp:164 +#, c-format +msgid "Your memo limit is %d, and may not be changed." +msgstr "Twój limit wiadomości wynosi %d i nie może być zmieniony." + +#: modules/commands/ms_info.cpp:166 +#, c-format +msgid "Your memo limit is %d." +msgstr "Twój limit wiadomości wynosi %d." + +#: modules/commands/ms_info.cpp:159 +msgid "Your memo limit is 0; you will not receive any new memos." +msgstr "Twój limit wiadomości wynosi 0, nie będziesz otrzymywać nowych." + +#: modules/commands/ms_info.cpp:157 +msgid "" +"Your memo limit is 0; you will not receive any new memos. You cannot change this " +"limit." +msgstr "" +"Twój limit wiadomości wynosi 0, nie będziesz odbierać nowych i nie możesz zmienić " +"tego limitu." + +#: modules/commands/ns_logout.cpp:50 +msgid "Your nick has been logged out." +msgstr "Twój nick został pomyślnie wylogowany." + +#: modules/commands/ns_group.cpp:156 +msgid "Your nick is already registered." +msgstr "Twój nick jest już zarejestrowany." + +#: modules/commands/ns_group.cpp:246 +msgid "Your nick is not grouped to anything, you can't ungroup it." +msgstr "" +"Nie możesz usunąć swojego nicka z grupy, ponieważ w żadnej się nie znajduje." + +#: include/language.h:77 +msgid "Your nick isn't registered." +msgstr "Twój nick nie jest zarejestrowany." + +#: modules/pseudoclients/nickserv.cpp:254 +#, c-format +msgid "Your nickname is now being changed to %s" +msgstr "Twój nick został zmieniony na %s" + +#: modules/commands/os_login.cpp:32 modules/commands/os_login.cpp:79 +msgid "Your oper block doesn't require logging in." +msgstr "Twoje ustawienia operatora nie wymagają logowania się." + +#: modules/commands/ns_register.cpp:338 +#, c-format +msgid "Your passcode has been re-sent to %s." +msgstr "Twój kod rejestracyjny został ponownie wysłany na %s." + +#: modules/commands/ns_register.cpp:234 +#, c-format +msgid "Your password is %s - remember this for later use." +msgstr "Twoje hasło do nicka to %s" + +#: include/language.h:76 +#, c-format +msgid "Your password is too long. It must not exceed %u characters." +msgstr "Twoje hasło jest zbyt długie (max %u znaków)." + +#: modules/commands/ns_resetpass.cpp:96 +msgid "Your password reset request has expired." +msgstr "Twoja prośba o reset hasła jest nieaktualna." + +#: modules/commands/hs_request.cpp:170 +msgid "Your vHost has been requested." +msgstr "Wysłałeś prośbę o vHosta." + +#: modules/commands/hs_on.cpp:37 modules/pseudoclients/hostserv.cpp:64 +#: modules/pseudoclients/hostserv.cpp:112 +#, c-format +msgid "Your vhost of %s is now activated." +msgstr "Twój vhost %s jest teraz aktywny." + +#: modules/commands/hs_on.cpp:35 modules/pseudoclients/hostserv.cpp:62 +#: modules/pseudoclients/hostserv.cpp:110 +#, c-format +msgid "Your vhost of %s@%s is now activated." +msgstr "Twój vhost %s@%s jest teraz aktywny." + +#: modules/commands/hs_off.cpp:39 +msgid "Your vhost was removed and the normal cloaking restored." +msgstr "Twój vhost został usunięty i zostało włączone normalne ukrywanie hosta." + +#: modules/commands/os_dns.cpp:255 +msgid "Zone" +msgstr "Strefa" + +#: modules/commands/os_dns.cpp:290 +#, c-format +msgid "Zone %s already exists." +msgstr "Strefa %s już istnieje." + +#: modules/commands/os_dns.cpp:310 modules/commands/os_dns.cpp:352 +#: modules/commands/os_dns.cpp:402 modules/commands/os_dns.cpp:438 +#, c-format +msgid "Zone %s does not exist." +msgstr "Strefa %s nie istnieje." + +#: modules/commands/os_dns.cpp:332 +#, c-format +msgid "Zone %s removed." +msgstr "Strefa %s usunięta." + +#: modules/commands/os_defcon.cpp:177 +msgid "[1|2|3|4|5]" +msgstr "[1|2|3|4|5]" + +#: modules/commands/os_news.cpp:400 +#, c-format +msgid "[Logon News - %s] %s" +msgstr "[Wiadomość powitalna - %s] %s" + +#: modules/commands/os_news.cpp:402 +#, c-format +msgid "[Oper News - %s] %s" +msgstr "[Wiadomość dla operatorów - %s] %s" + +#: modules/commands/os_news.cpp:404 +#, c-format +msgid "[Random News - %s] %s" +msgstr "[Losowa wiadomość - %s] %s" + +#: modules/commands/ns_identify.cpp:66 +msgid "[account] password" +msgstr "[konto] hasło" + +#: modules/commands/cs_updown.cpp:49 modules/commands/cs_updown.cpp:147 +msgid "[channel [nick]]" +msgstr "[kanał [nick]]" + +#: modules/commands/ms_ignore.cpp:20 +msgid "[channel] ADD entry" +msgstr "[kanał] ADD wpis" + +#: modules/commands/ms_ignore.cpp:21 +msgid "[channel] DEL entry" +msgstr "[kanał] DEL wpis" + +#: modules/commands/ms_ignore.cpp:22 +msgid "[channel] LIST" +msgstr "[kanał] LIST" + +#: modules/commands/ms_list.cpp:20 +msgid "[channel] [list | NEW]" +msgstr "[kanał] [lista | NEW]" + +#: modules/extra/stats/cs_fantasy_stats.cpp:40 +msgid "[channel] [nick]" +msgstr "[kanał] [nick]" + +#: modules/commands/ms_del.cpp:45 +msgid "[channel] {num | list | LAST | ALL}" +msgstr "[kanał] {num | lista | LAST | ALL}" + +#: modules/commands/ms_read.cpp:113 +msgid "[channel] {num | list | LAST | NEW | ALL}" +msgstr "[kanał] {num | lista | LAST | NEW | ALL}" + +#: modules/commands/hs_list.cpp:20 +msgid "[key|#X-Y]" +msgstr "[klucz|#X-Y]" + +#: modules/commands/ms_info.cpp:20 +msgid "[nick | channel]" +msgstr "[nick | kanał]" + +#: modules/commands/ns_group.cpp:237 +msgid "[nick]" +msgstr "[nick]" + +#: modules/commands/ns_logout.cpp:22 +msgid "[nickname [REVALIDATE]]" +msgstr "[nick [REVALIDATE]]" + +#: modules/commands/ns_info.cpp:20 modules/commands/ns_alist.cpp:25 +#: modules/commands/ns_status.cpp:20 +msgid "[nickname]" +msgstr "[nick]" + +#: modules/commands/ns_set_misc.cpp:96 +msgid "[parameter]" +msgstr "[parametr]" + +#: modules/commands/os_logsearch.cpp:33 +msgid "[+daysd] [+limitl] pattern" +msgstr "[+dnid] [+limitl] wzorzec" + +#: modules/commands/os_chankill.cpp:22 +msgid "[+expiry] channel reason" +msgstr "[+czas] kanał powód" + +#: modules/commands/ns_list.cpp:110 +msgid "[Hostname hidden]" +msgstr "[Host ukryty]" + +#: modules/commands/ns_list.cpp:112 modules/commands/cs_list.cpp:115 +msgid "[Suspended]" +msgstr "[Zawieszony]" + +#: modules/commands/ns_list.cpp:114 +msgid "[Unconfirmed]" +msgstr "[Niepotwierdzony]" + +#: modules/commands/hs_request.cpp:213 +msgid "[auto memo] Your requested vHost has been approved." +msgstr "[wiadomość automatyczna] Twój vHost został zaakceptowany." + +#: modules/commands/hs_request.cpp:267 +msgid "[auto memo] Your requested vHost has been rejected." +msgstr "[wiadomość automatyczna] Twój vHost został odrzucony." + +#: modules/commands/hs_request.cpp:265 +#, c-format +msgid "[auto memo] Your requested vHost has been rejected. Reason: %s" +msgstr "" +"[wiadomość automatyczna] Twoja prośba o vHosta została odrzucona. Podany powód: %s" + +#: modules/commands/hs_request.cpp:388 +#, c-format +msgid "[auto memo] vHost %s has been requested by %s." +msgstr "[wiadomość automatyczna] Prośba o vHost %s została wysłana przez %s." + +#: modules/commands/os_list.cpp:133 +msgid "[{pattern | channel} [INVISIBLE]]" +msgstr "[{wzór | kanał} [INVISIBLE]]" + +#: modules/commands/os_list.cpp:20 +msgid "[{pattern | nick} [SECRET]]" +msgstr "[{wzór | nick} [SECRET]]" + +#: src/misc.cpp:337 +msgid "day" +msgstr "dzień" + +#: src/misc.cpp:337 +msgid "days" +msgstr "dni" + +#: include/language.h:88 +msgid "does not expire" +msgstr "nie wygasa" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d day" +msgstr "wygasa za %d dzień" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d days" +msgstr "wygasa za %d dni" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minute" +msgstr "wygasa za %d godzinę i %d minutę" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minutes" +msgstr "wygasa za %d godzinę i %d minut(y)" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minute" +msgstr "wygasa za %d godzinę i %d minut(y)" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minutes" +msgstr "wygasa za %d godzin(y) i %d minut(y)" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minute" +msgstr "wygasa za %d minutę" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minutes" +msgstr "wygasa za %d minut(y)" + +#: src/misc.cpp:375 +msgid "expires momentarily" +msgstr "za chwilę wygasa" + +#: src/misc.cpp:343 +msgid "hour" +msgstr "godzina" + +#: src/misc.cpp:343 +msgid "hours" +msgstr "godzin(y)" + +#: modules/extra/stats/cs_fantasy_stats.cpp:150 +#, c-format +msgid "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "litery: %s, słowa: %s, linie: %s, emotikony: %s, akcje: %s" + +#: src/misc.cpp:349 +msgid "minute" +msgstr "minuta(y)" + +#: src/misc.cpp:349 +msgid "minutes" +msgstr "minut(y)" + +#: modules/commands/bs_info.cpp:87 +msgid "not assigned yet" +msgstr "jeszcze nie przypisano" + +#: src/misc.cpp:324 +msgid "second" +msgstr "sekunda" + +#: src/misc.cpp:324 +msgid "seconds" +msgstr "sekund(y)" + +#: modules/commands/hs_request.cpp:215 +#, c-format +msgid "vHost for %s has been activated." +msgstr "vHost dla %s został aktywowany." + +#: modules/commands/hs_request.cpp:272 +#, c-format +msgid "vHost for %s has been rejected." +msgstr "vHost dla %s został odrzucony." + +#: modules/commands/hs_request.cpp:79 +msgid "vhost" +msgstr "vhost" + +#: modules/commands/hs_del.cpp:83 +#, c-format +msgid "vhosts for group %s have been removed." +msgstr "Vhosty dla grupy %s zostały usunięte." + +#: src/misc.cpp:331 +msgid "year" +msgstr "rok" + +#: src/misc.cpp:331 +msgid "years" +msgstr "lat(a)" + +#: modules/commands/os_config.cpp:20 +msgid "{MODIFY|VIEW} [block name item name item value]" +msgstr "{MODIFY|VIEW} [nazwa-bloku nazwa-obiektu wartość-obiektu]" + +#: modules/commands/bs_info.cpp:41 +msgid "{channel | nickname}" +msgstr "{kanał | nick}" + +#: modules/commands/ms_cancel.cpp:20 +msgid "{nick | channel}" +msgstr "{nick | kanał}" + +#: modules/commands/ms_send.cpp:25 modules/commands/ms_rsend.cpp:25 +msgid "{nick | channel} memo-text" +msgstr "{nick | kanał} treść" + +#~ msgid "Password authentication required for that command." +#~ msgstr "Ta komenda wymaga zalogowania do zarejestrowanego nicka." diff --git a/language/anope.pt_PT.po b/language/anope.pt_PT.po new file mode 100644 index 0000000..589f3dc --- /dev/null +++ b/language/anope.pt_PT.po @@ -0,0 +1,11801 @@ +# Anope IRC Services language file +# Copyright (C) 2011 +# This file is distributed under the same license as the Anope IRC Services package. +# Adam , 2011. +# +msgid "" +msgstr "" +"Project-Id-Version: Anope\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2020-01-06 18:19+0100\n" +"PO-Revision-Date: 2010-09-19 21:02-0400\n" +"Last-Translator: Adam \n" +"Language-Team: Portuguese\n" +"Language: pt_PT\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=2; plural=(n != 1);\n" + +#: modules/commands/os_forbid.cpp:324 +#, c-format +msgid "%d channel(s) cleared, and %d channel(s) dropped." +msgstr "" + +#: modules/commands/os_forbid.cpp:265 +#, fuzzy, c-format +msgid "%d nickname(s) dropped." +msgstr "O registro do seu nick foi cancelado." + +#: modules/commands/cs_xop.cpp:219 +#, fuzzy, c-format +msgid "%s added to %s %s list." +msgstr "%s adicionado à lista de AKILL." + +#: modules/commands/cs_access.cpp:225 +#, c-format +msgid "%s added to %s access list at level %d." +msgstr "%s adicionado à lista de acesso do %s com o nível %d." + +#: modules/commands/cs_access.cpp:223 +#, fuzzy, c-format +msgid "%s added to %s access list at privilege %s (level %d)" +msgstr "%s adicionado à lista de acesso do %s com o nível %d." + +#: modules/commands/cs_akick.cpp:190 +#, c-format +msgid "%s added to %s autokick list." +msgstr "%s adicionado à lista de akick do %s." + +#: modules/commands/bs_badwords.cpp:307 +#, c-format +msgid "%s added to %s bad words list." +msgstr "%s adicionado na lista de palavrões do %s." + +#: modules/commands/ns_access.cpp:45 +#, fuzzy, c-format +msgid "%s added to %s's access list." +msgstr "%s adicionado em sua lista de acesso." + +#: modules/commands/ns_cert.cpp:204 +#, fuzzy, c-format +msgid "%s added to %s's certificate list." +msgstr "%s adicionado em sua lista de acesso." + +#: modules/commands/ms_ignore.cpp:62 +#, fuzzy, c-format +msgid "%s added to ignore list." +msgstr "%s adicionado em sua lista de acesso." + +#: modules/commands/os_sxline.cpp:415 modules/commands/os_sxline.cpp:649 +#, fuzzy, c-format +msgid "%s added to the %s list." +msgstr "%s adicionado à lista de AKILL." + +#: modules/commands/os_akill.cpp:203 +#, c-format +msgid "%s added to the AKILL list." +msgstr "%s adicionado à lista de AKILL." + +#: modules/pseudoclients/botserv.cpp:134 +#, c-format +msgid "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands " +"that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" +msgstr "" + +#: modules/pseudoclients/botserv.cpp:148 +#, fuzzy, c-format +msgid "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s permite que você tenha um bot no seu canal.\n" +"Foi criado para usuários que não tem como hospedar\n" +"ou configurar um bot, ou para Redes que não permitem\n" +"aos usuários terem um bot. Os comandos disponíveis \n" +"estão listados abaixo; para usá-los, digite\n" +"/msg %s comando. Para informações mais específicas\n" +"sobre um comando, digite /msg %s HELP comando." + +#: modules/pseudoclients/nickserv.cpp:466 +#, fuzzy, c-format +msgid "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s permite que você \"registre\" um nick e evita que outras\n" +"pessoas o utilizem. Os seguintes comandos permitem o\n" +"registro e a manutenção dos nicks; para utilizá-los, digite\n" +"/msg %s comando. Para mais informações sobre um\n" +"comando específico, digite /msg %s HELP comando." + +#: modules/pseudoclients/nickserv.cpp:473 +#, fuzzy, c-format +msgid "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s permite que você \"registre\" um nick e evita que outras\n" +"pessoas o utilizem. Os seguintes comandos permitem o\n" +"registro e a manutenção dos nicks; para utilizá-los, digite\n" +"/msg %s comando. Para mais informações sobre um\n" +"comando específico, digite /msg %s HELP comando." + +#: modules/pseudoclients/chanserv.cpp:255 +#, fuzzy, c-format +msgid "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" +msgstr "" +"%s permite que você registre e controle vários\n" +"aspectos do canal. %s pode prevenir o \"take over\"\n" +"do canal por usuários maliciosos, limitando quem possui\n" +"o privilégio de OP do canal. Os comandos disponíveis\n" +"estão listados abaixo; para usá-los, digite\n" +"/msg %s comando. Para mais informações sobre\n" +"um comando específico, digite /msg %s HELP comando." + +#: modules/commands/bs_badwords.cpp:298 +#, c-format +msgid "%s already exists in %s bad words list." +msgstr "%s já existe na lista de palavrões do %s." + +#: modules/commands/cs_akick.cpp:170 +#, c-format +msgid "%s already exists on %s autokick list." +msgstr "%s já existe na lista de akick do %s." + +#: modules/commands/os_session.cpp:361 +#, c-format +msgid "%s already exists on the EXCEPTION list." +msgstr "%s já existe na lista de EXCEPTION." + +#: modules/commands/bs_kick.cpp:214 modules/commands/bs_kick.cpp:389 +#: modules/commands/bs_kick.cpp:520 modules/commands/bs_kick.cpp:651 +#, c-format +msgid "%s cannot be taken as times to ban." +msgstr "%s não pode ser colocado como tempo para ban." + +#: modules/commands/os_mode.cpp:163 +#, fuzzy, c-format +msgid "%s changed your usermodes to %s." +msgstr "%s alterou seus modos de usuário." + +#: modules/commands/os_list.cpp:47 +#, fuzzy, c-format +msgid "%s channel list:" +msgstr "Fim da listagem." + +#: modules/commands/cs_xop.cpp:343 +#, fuzzy, c-format +msgid "%s deleted from %s %s list." +msgstr "%s deletado da lista de AOP do %s." + +#: modules/commands/cs_access.cpp:326 +#, c-format +msgid "%s deleted from %s access list." +msgstr "%s removido da lista de acesso do %s." + +#: modules/commands/cs_akick.cpp:276 +#, c-format +msgid "%s deleted from %s autokick list." +msgstr "%s removido da lista de akick do %s." + +#: modules/commands/bs_badwords.cpp:348 +#, c-format +msgid "%s deleted from %s bad words list." +msgstr "%s removido da lista de palavrões do %s." + +#: modules/commands/ns_access.cpp:72 +#, fuzzy, c-format +msgid "%s deleted from %s's access list." +msgstr "%s removido da lista de acesso do %s." + +#: modules/commands/ns_cert.cpp:233 +#, fuzzy, c-format +msgid "%s deleted from %s's certificate list." +msgstr "%s removido da sua lista de acesso." + +#: modules/commands/os_session.cpp:414 +#, c-format +msgid "%s deleted from session-limit exception list." +msgstr "%s removido da lista de limite de sessões." + +#: modules/commands/os_sxline.cpp:99 +#, fuzzy, c-format +msgid "%s deleted from the %s list." +msgstr "%s deletado da lista de AOP do %s." + +#: modules/commands/os_akill.cpp:246 +#, c-format +msgid "%s deleted from the AKILL list." +msgstr "%s removido da lista de AKILL." + +#: modules/commands/cs_access.cpp:685 +#, c-format +msgid "%s disabled on channel %s." +msgstr "%s desabilitado no canal %s." + +#: modules/commands/cs_invite.cpp:75 +#, c-format +msgid "%s has been invited to %s." +msgstr "%s has been invited to %s." + +#: modules/commands/os_svs.cpp:104 +#, fuzzy, c-format +msgid "%s has been joined to %s." +msgstr "%s has been invited to %s." + +#: modules/commands/os_svs.cpp:152 +#, fuzzy, c-format +msgid "%s has been parted from %s." +msgstr "%s has been unbanned from %s." + +#: modules/commands/cs_unban.cpp:96 +#, c-format +msgid "%s has been unbanned from %s." +msgstr "%s has been unbanned from %s." + +#: modules/commands/ns_alist.cpp:110 +#, fuzzy, c-format +msgid "%s has no access in any channels." +msgstr "%s desabilitado no canal %s." + +#: modules/commands/cs_status.cpp:55 +#, fuzzy, c-format +msgid "%s has no access on %s." +msgstr "%s has been invited to %s." + +#: modules/commands/cs_set.cpp:307 +#, c-format +msgid "%s has too many channels registered." +msgstr "%s possui muitos canais registrados." + +#: modules/commands/cs_status.cpp:51 +#, fuzzy, c-format +msgid "%s is a super administrator." +msgstr "%s is a services operator of type %s." + +#: modules/pseudoclients/memoserv.cpp:214 +#, fuzzy, c-format +msgid "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" +msgstr "" +"%s é um serviço que permite aos usuários de IRC\n" +"enviar curtas mensagens a outros usuários, mesmo\n" +"que eles estejam conectados no momento ou não; ou\n" +"a canais(*). Ambos, destinatários e remetentes,\n" +"devem possuir seus nicks (ou canais) registrados para\n" +"que possam enviar uma mensagem (memo).\n" +"Os comandos do %s são:" + +#: modules/commands/cs_invite.cpp:66 +#, fuzzy, c-format +msgid "%s is already in %s!" +msgstr "You are already in %s! " + +#: modules/commands/os_svs.cpp:99 +#, fuzzy, c-format +msgid "%s is already in %s." +msgstr "You are already in %s! " + +#: modules/commands/ms_ignore.cpp:65 +#, fuzzy, c-format +msgid "%s is already on the ignore list." +msgstr "%s adicionado em sua lista de acesso." + +#: modules/commands/cs_suspend.cpp:97 modules/commands/ns_suspend.cpp:106 +#, fuzzy, c-format +msgid "%s is already suspended." +msgstr "You are already in %s! " + +#: modules/commands/ms_rsend.cpp:56 modules/commands/ms_send.cpp:55 +#, fuzzy, c-format +msgid "%s is not a registered unforbidden nick or channel." +msgstr "%s não é um bot válido ou um canal registrado." + +#: modules/commands/cs_set.cpp:178 +#, c-format +msgid "%s is not a valid ban type." +msgstr "%s não é um ban válido." + +#: modules/commands/bs_info.cpp:101 +#, c-format +msgid "%s is not a valid bot or registered channel." +msgstr "%s não é um bot válido ou um canal registrado." + +#: include/language.h:86 +#, fuzzy, c-format +msgid "%s is not a valid e-mail address." +msgstr "%s não é um ban válido." + +#: include/language.h:80 +#, fuzzy, c-format +msgid "%s is not currently on channel %s." +msgstr "%s desabilitado no canal %s." + +#: modules/commands/os_svs.cpp:144 +#, fuzzy, c-format +msgid "%s is not in %s." +msgstr "You are already in %s! " + +#: modules/commands/ms_ignore.cpp:77 +#, fuzzy, c-format +msgid "%s is not on the ignore list." +msgstr "%s não encontrado na lista de Ignore." + +#: modules/commands/cs_status.cpp:90 +#, fuzzy, c-format +msgid "%s is on the auto kick list of %s (%s)." +msgstr "%s adicionado à lista de akick do %s." + +#: modules/commands/cs_status.cpp:53 +#, fuzzy, c-format +msgid "%s is the founder of %s." +msgstr "%s desabilitado no canal %s." + +#: modules/commands/cs_status.cpp:78 +#, c-format +msgid "%s matches access entry %s (from entry %s), which has privilege %s." +msgstr "" + +#: modules/commands/cs_status.cpp:71 +#, c-format +msgid "%s matches access entry %s, which has privilege %s." +msgstr "" + +#: include/language.h:109 +#, c-format +msgid "" +"%s matches an except on %s and cannot be banned until the except has been " +"removed." +msgstr "" + +#: modules/commands/cs_status.cpp:96 +#, fuzzy, c-format +msgid "%s matches auto kick entry %s on %s (%s)." +msgstr "%s adicionado à lista de akick do %s." + +#: modules/commands/cs_xop.cpp:353 +#, fuzzy, c-format +msgid "%s not found on %s %s list." +msgstr "Nick %s não encontrado na lista de AOP do %s." + +#: modules/commands/cs_access.cpp:338 modules/commands/cs_flags.cpp:255 +#, c-format +msgid "%s not found on %s access list." +msgstr "%s não foi encontrado na lista de acesso do %s." + +#: modules/commands/cs_akick.cpp:265 +#, c-format +msgid "%s not found on %s autokick list." +msgstr "%s não encontrado na lista de akick do %s." + +#: modules/commands/bs_badwords.cpp:341 +#, c-format +msgid "%s not found on %s bad words list." +msgstr "%s não foi encontrado na lista de palavrões do %s." + +#: modules/commands/ns_access.cpp:66 +#, fuzzy, c-format +msgid "%s not found on %s's access list." +msgstr "%s não foi encontrado na lista de acesso do %s." + +#: modules/commands/ns_cert.cpp:226 +#, fuzzy, c-format +msgid "%s not found on %s's certificate list." +msgstr "%s não foi encontrado em sua lista de acesso." + +#: modules/commands/os_ignore.cpp:320 +#, fuzzy, c-format +msgid "%s not found on ignore list." +msgstr "%s não encontrado na lista de Ignore." + +#: modules/commands/os_session.cpp:238 +#, c-format +msgid "" +"%s not found on session list, but has a limit of %d because it matches entry:" +" %s." +msgstr "" + +#: modules/commands/os_session.cpp:418 +#, c-format +msgid "%s not found on session-limit exception list." +msgstr "%s não encontrado na lista de limite de sessões." + +#: modules/commands/os_sxline.cpp:92 +#, fuzzy, c-format +msgid "%s not found on the %s list." +msgstr "Nick %s não encontrado na lista de AOP do %s." + +#: modules/commands/os_akill.cpp:237 +#, c-format +msgid "%s not found on the AKILL list." +msgstr "%s não encontrado na lista de AKILL." + +#: modules/commands/cs_flags.cpp:251 +#, fuzzy, c-format +msgid "%s removed from the %s access list." +msgstr "%s removido da lista de acesso do %s." + +#: modules/commands/ms_ignore.cpp:74 +#, fuzzy, c-format +msgid "%s removed from the ignore list." +msgstr "%s removido da sua lista de acesso." + +#: modules/commands/os_list.cpp:157 +#, fuzzy, c-format +msgid "%s users list:" +msgstr "Fim da listagem." + +#: modules/commands/os_ignore.cpp:316 +#, c-format +msgid "%s will no longer be ignored." +msgstr "%s não será mais ignorado." + +#: modules/commands/os_ignore.cpp:238 +#, c-format +msgid "%s will now be ignored for %s." +msgstr "%s agora será ignorado por %s." + +#: modules/commands/os_ignore.cpp:233 +#, c-format +msgid "%s will now permanently be ignored." +msgstr "%s agora será permanentemente ignorado." + +#: include/language.h:66 +#, fuzzy, c-format +msgid "%s%s HELP %s for more information." +msgstr "" +"Digite /msg %s HELP SET opção para maiores informações\n" +"sobre uma opção em particular." + +#: modules/commands/bs_bot.cpp:270 +msgid "ADD nick user host real" +msgstr "" + +#: modules/commands/bs_bot.cpp:271 +#, fuzzy +msgid "CHANGE oldnick newnick [user [host [real]]]" +msgstr "" +"BOT ADD nick user host real\n" +"BOT CHANGE nickantigo nicknovo [user [host [real]]]\n" +"BOT DEL nick" + +#: modules/commands/bs_bot.cpp:272 +#, fuzzy +msgid "DEL nick" +msgstr "DEL ." + +#: modules/commands/os_session.cpp:560 +#, fuzzy +msgid "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." +msgstr "" +"Sintaxe: EXCEPTION ADD [+tempo] máscara limite motivo\n" +" EXCEPTION DEL {máscara | lista}\n" +" EXCEPTION MOVE núm posição\n" +" EXCEPTION LIST [máscara | lista]\n" +" EXCEPTION VIEW [máscara | lista]\n" +"\n" +"Permite que os Administradores dos Services manipulem a lista\n" +"de hosts que tenham limite de conexões especificados - deixando \n" +"certos hosts, como shell de servidores, conectar mais que o\n" +"número padrão de conexões simultâneas. Uma vez um host atingindo\n" +"um limite de conexão, todos os clientes que tentem conectar \n" +"daquele host serão expulsos (\"killados\").\n" +"Antes do usuário ser expulso (\"killado\"), ele será notificado\n" +"via /NOTICE do %s com um tópico de ajuda sobre limitação\n" +"de conexões.\n" +"\n" +"EXCEPTION ADD adiciona a máscara fornecida à lista de exceções.\n" +"Note que as máscaras nick!user@host e user@host são\n" +"inválidas. Só nomes reais de hosts, como mail.dominio.com e \n" +"*.dominio.com, são permitidos porque a limitação de\n" +"conexão não utiliza o nick ou ident para bloquear o acesso. \n" +"\n" +"EXCEPTION DEL remove a máscara especificada da Lista de\n" +"exceções.\n" +"EXCEPTION MOVE move uma exceção de número núm para uma\n" +"posição dada. As exceções que estavam na faixa onde houve\n" +"alteração serão todas movidas para cima ou para baixo conforme\n" +"for o deslocamento necessário.\n" +"EXCEPTION LIST ou EXCEPTION VIEW mostram todas as \n" +"exceções atuais válidas; se uma máscara é dada como parâmetro\n" +"opcional, a lista é limitada as exceções que são compatíveis\n" +"com a máscara dada. A diferenca é que EXCEPTION VIEW \n" +"é mais detalhado, mostrando o nome da pessoa que adicionou \n" +"a exceção, o seu limite de conexões, o motivo, a máscara do\n" +"host, a data e o tempo de validade.\n" +"\n" +"Note que um cliente que conecte vai usar a primeira exceção\n" +"que for compatível com o seu host. Listas de exceções muito\n" +"grandes e máscaras de hosts muito abrangentes certamente\n" +"irão degradar a eficácia de funcionamento (\"performance\")\n" +"dos services." + +#: modules/commands/os_noop.cpp:68 +msgid "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." +msgstr "" + +#: modules/commands/cs_access.cpp:611 +#, c-format +msgid "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." +msgstr "" + +#: modules/commands/ms_read.cpp:35 +#, c-format +msgid "[auto-memo] The memo you sent to %s has been viewed." +msgstr "[Auto-Memo] O memo que você enviou para %s foi lido." + +#: modules/commands/ns_group.cpp:92 +#, fuzzy +msgid "[target] [password]" +msgstr "GROUP alvo senha" + +#: modules/commands/ns_set.cpp:453 +msgid "address" +msgstr "" + +#: modules/commands/bs_set.cpp:162 +#, fuzzy +msgid "botname {ON|OFF}" +msgstr "SASET nickname AUTOOP {ON | OFF}" + +#: modules/extra/stats/cs_fantasy_top.cpp:39 +#: modules/extra/stats/cs_fantasy_top.cpp:51 +#: modules/commands/cs_suspend.cpp:152 modules/commands/cs_sync.cpp:20 +#: modules/commands/cs_log.cpp:106 modules/commands/bs_assign.cpp:91 +#: modules/commands/cs_info.cpp:20 modules/commands/cs_getkey.cpp:20 +#, fuzzy +msgid "channel" +msgstr "DROP canal" + +#: modules/commands/cs_set.cpp:138 +#, fuzzy +msgid "channel bantype" +msgstr "ACT canal texto" + +#: modules/commands/cs_drop.cpp:20 +#, fuzzy +msgid "channel channel" +msgstr "TOPIC canal [tópico]" + +#: modules/commands/cs_log.cpp:107 +#, fuzzy +msgid "channel command method [status]" +msgstr "KICK canal opções {ON|OFF} [configurações]" + +#: modules/commands/cs_kick.cpp:21 +#, fuzzy +msgid "channel mask [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_mode.cpp:20 +#, fuzzy +msgid "channel modes" +msgstr "MODE canal modos" + +#: modules/commands/cs_set.cpp:267 modules/commands/bs_assign.cpp:20 +#, fuzzy +msgid "channel nick" +msgstr "UNBAN canal [nick]" + +#: modules/commands/cs_kick.cpp:20 +#, fuzzy +msgid "channel nick [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_clone.cpp:115 +#, fuzzy +msgid "channel target [what]" +msgstr "CLEAR canal opção" + +#: modules/commands/bs_control.cpp:20 modules/commands/bs_control.cpp:80 +#, fuzzy +msgid "channel text" +msgstr "ACT canal texto" + +#: modules/commands/bs_set.cpp:91 +#, fuzzy +msgid "channel time" +msgstr "ACT canal texto" + +#: modules/commands/os_kick.cpp:20 +#, fuzzy +msgid "channel user reason" +msgstr "KICK canal usuário motivo" + +#: modules/commands/cs_enforce.cpp:228 +#, fuzzy +msgid "channel what" +msgstr "TOPIC canal [tópico]" + +#: modules/commands/cs_xop.cpp:481 +#, fuzzy +msgid "channel ADD mask" +msgstr "MODE canal modos" + +#: modules/commands/cs_access.cpp:499 +msgid "channel ADD mask level" +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:194 +#, fuzzy +msgid "channel ADD message" +msgstr "MODE canal modos" + +#: modules/commands/bs_badwords.cpp:371 +msgid "channel ADD word [SINGLE | START | END]" +msgstr "" + +#: modules/commands/cs_akick.cpp:435 +#, fuzzy +msgid "channel ADD {nick | mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_topic.cpp:151 +#, fuzzy +msgid "channel APPEND topic" +msgstr "TOPIC canal [tópico]" + +#: modules/commands/cs_access.cpp:503 modules/commands/cs_flags.cpp:376 +#: modules/commands/cs_xop.cpp:484 modules/commands/cs_entrymsg.cpp:197 +#: modules/commands/bs_badwords.cpp:374 modules/commands/cs_akick.cpp:440 +#, fuzzy +msgid "channel CLEAR" +msgstr "DROP canal" + +#: modules/commands/cs_mode.cpp:736 +#, fuzzy +msgid "channel CLEAR [what]" +msgstr "TOPIC canal [tópico]" + +#: modules/commands/os_mode.cpp:21 +#, fuzzy +msgid "channel CLEAR [ALL]" +msgstr "DROP canal" + +#: modules/commands/cs_entrymsg.cpp:195 +#, fuzzy +msgid "channel DEL num" +msgstr "MODE canal modos" + +#: modules/commands/cs_access.cpp:500 modules/commands/cs_xop.cpp:482 +#, fuzzy +msgid "channel DEL {mask | entry-num | list}" +msgstr "DEL [canal] {núm | list | ALL}" + +#: modules/commands/cs_akick.cpp:436 +#, fuzzy +msgid "channel DEL {nick | mask | entry-num | list}" +msgstr "AOP canal {ADD|DEL|LIST|CLEAR} [nick | entrada]" + +#: modules/commands/bs_badwords.cpp:372 +#, fuzzy +msgid "channel DEL {word | entry-num | list}" +msgstr "DEL [canal] {núm | list | ALL}" + +#: modules/commands/cs_akick.cpp:439 +msgid "channel ENFORCE" +msgstr "" + +#: modules/commands/cs_access.cpp:744 modules/commands/cs_entrymsg.cpp:196 +#, fuzzy +msgid "channel LIST" +msgstr "DROP canal" + +#: modules/commands/cs_akick.cpp:437 +#, fuzzy +msgid "channel LIST [mask | entry-num | list]" +msgstr "AOP canal {ADD|DEL|LIST|CLEAR} [nick | entrada]" + +#: modules/commands/cs_access.cpp:501 modules/commands/cs_xop.cpp:483 +#: modules/commands/bs_badwords.cpp:373 +#, fuzzy +msgid "channel LIST [mask | list]" +msgstr "AOP canal {ADD|DEL|LIST|CLEAR} [nick | entrada]" + +#: modules/commands/cs_flags.cpp:375 +msgid "channel LIST [mask | +flags]" +msgstr "" + +#: modules/commands/cs_mode.cpp:734 +#, fuzzy +msgid "channel LOCK {ADD|DEL|SET|LIST} [what]" +msgstr "AOP canal {ADD|DEL|LIST|CLEAR} [nick | entrada]" + +#: modules/commands/cs_access.cpp:745 +#, fuzzy +msgid "channel RESET" +msgstr "SET canal GREET {ON|OFF}" + +#: modules/commands/cs_mode.cpp:735 +#, fuzzy +msgid "channel SET modes" +msgstr "MODE canal modos" + +#: modules/commands/cs_access.cpp:742 +msgid "channel SET type level" +msgstr "" + +#: modules/commands/cs_akick.cpp:438 +#, fuzzy +msgid "channel VIEW [mask | entry-num | list]" +msgstr "AOP canal {ADD|DEL|LIST|CLEAR} [nick | entrada]" + +#: modules/commands/cs_access.cpp:502 +#, fuzzy +msgid "channel VIEW [mask | list]" +msgstr "DEL [canal] {núm | list | ALL}" + +#: modules/commands/cs_register.cpp:20 modules/commands/cs_set.cpp:205 +#, fuzzy +msgid "channel [description]" +msgstr "REGISTER canal descrição" + +#: modules/commands/cs_set.cpp:950 modules/commands/cs_invite.cpp:20 +#: modules/commands/cs_unban.cpp:20 +#, fuzzy +msgid "channel [nick]" +msgstr "UNBAN canal [nick]" + +#: modules/commands/cs_set_misc.cpp:96 +#, fuzzy +msgid "channel [parameters]" +msgstr "CLEAR canal opção" + +#: modules/commands/cs_mode.cpp:807 modules/commands/cs_status.cpp:20 +#, fuzzy +msgid "channel [user]" +msgstr "UNBAN canal [nick]" + +#: modules/commands/cs_suspend.cpp:59 +#, fuzzy +msgid "channel [+expiry] [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_ban.cpp:40 +#, fuzzy +msgid "channel [+expiry] {nick | mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_flags.cpp:374 +#, fuzzy +msgid "channel [MODIFY] mask changes" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_topic.cpp:150 +#, fuzzy +msgid "channel [SET] [topic]" +msgstr "TOPIC canal [tópico]" + +#: modules/commands/cs_topic.cpp:152 +#, fuzzy +msgid "channel [UNLOCK|LOCK]" +msgstr "DROP canal" + +#: modules/fantasy.cpp:20 modules/commands/greet.cpp:20 +#: modules/commands/bs_assign.cpp:154 +#, fuzzy +msgid "channel {ON|OFF}" +msgstr "SET canal XOP {ON | OFF}" + +#: modules/commands/bs_kick.cpp:491 +#, fuzzy +msgid "channel {ON|OFF} [ttb [ln [secs]]]" +msgstr "KICK canal opções {ON|OFF} [configurações]" + +#: modules/commands/bs_kick.cpp:361 +#, fuzzy +msgid "channel {ON|OFF} [ttb [min [percent]]]" +msgstr "KICK canal opções {ON|OFF} [configurações]" + +#: modules/commands/bs_kick.cpp:623 +#, fuzzy +msgid "channel {ON|OFF} [ttb [num]]" +msgstr "KICK canal opções {ON|OFF} [configurações]" + +#: modules/commands/bs_kick.cpp:252 modules/commands/bs_kick.cpp:288 +#: modules/commands/bs_kick.cpp:327 modules/commands/bs_kick.cpp:457 +#: modules/commands/bs_kick.cpp:589 modules/commands/bs_kick.cpp:724 +#: modules/commands/bs_kick.cpp:758 +#, fuzzy +msgid "channel {ON|OFF} [ttb]" +msgstr "SET canal XOP {ON | OFF}" + +#: modules/commands/cs_access.cpp:743 +msgid "channel {DIS | DISABLE} type" +msgstr "" + +#: modules/commands/cs_set.cpp:873 +#, fuzzy +msgid "channel {ON | LEVEL | OFF}" +msgstr "SET canal SIGNKICK {ON | LEVEL | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:18 modules/commands/cs_set.cpp:75 +#: modules/commands/cs_set.cpp:336 modules/commands/cs_set.cpp:401 +#: modules/commands/cs_set.cpp:473 modules/commands/cs_set.cpp:622 +#: modules/commands/cs_set.cpp:684 modules/commands/cs_set.cpp:747 +#: modules/commands/cs_set.cpp:811 modules/commands/cs_set.cpp:1044 +#: modules/commands/bs_kick.cpp:792 modules/commands/bs_kick.cpp:857 +#: modules/commands/cs_topic.cpp:21 modules/commands/cs_list.cpp:181 +#, fuzzy +msgid "channel {ON | OFF}" +msgstr "SET canal XOP {ON | OFF}" + +#: modules/commands/ns_getemail.cpp:24 +msgid "email" +msgstr "" + +#: modules/commands/ns_set.cpp:794 +#, fuzzy +msgid "language" +msgstr "SET LANGUAGE número" + +#: modules/commands/ms_sendall.cpp:25 modules/commands/ms_staff.cpp:25 +#, fuzzy +msgid "memo-text" +msgstr "STAFF memo-text" + +#: modules/commands/gl_global.cpp:22 modules/commands/greet.cpp:84 +#, fuzzy +msgid "message" +msgstr "GLOBAL mensagem" + +#: modules/commands/os_modinfo.cpp:20 modules/commands/os_module.cpp:20 +#: modules/commands/os_module.cpp:57 modules/commands/os_module.cpp:129 +msgid "modname" +msgstr "" + +#: modules/commands/ns_set.cpp:330 +msgid "new-display" +msgstr "" + +#: modules/commands/ns_set.cpp:120 +#, fuzzy +msgid "new-password" +msgstr "GROUP alvo senha" + +#: modules/extra/stats/cs_fantasy_stats.cpp:52 modules/commands/hs_del.cpp:20 +#: modules/commands/hs_del.cpp:60 modules/commands/ms_check.cpp:20 +#: modules/commands/hs_request.cpp:192 modules/commands/cs_seen.cpp:262 +#, fuzzy +msgid "nick" +msgstr "INFO nick" + +#: modules/commands/os_svs.cpp:79 +#, fuzzy +msgid "nick channel" +msgstr "CANCEL {nick | canal}" + +#: modules/commands/os_svs.cpp:123 +#, fuzzy +msgid "nick channel [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_oline.cpp:20 +#, fuzzy +msgid "nick flags" +msgstr "OLINE nick flags" + +#: modules/commands/hs_set.cpp:20 modules/commands/hs_set.cpp:126 +#, fuzzy +msgid "nick hostmask" +msgstr "SET  ." + +#: modules/commands/os_svs.cpp:20 +#, fuzzy +msgid "nick newnick" +msgstr "SVSNICK nick novonick " + +#: modules/commands/hs_request.cpp:241 +#, fuzzy +msgid "nick [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/ns_getpass.cpp:20 modules/commands/ns_drop.cpp:19 +#: modules/commands/ns_suspend.cpp:161 +#, fuzzy +msgid "nickname" +msgstr "CHECK nick" + +#: modules/commands/ns_set.cpp:546 +#, fuzzy +msgid "nickname address" +msgstr "FORBID nick motivo" + +#: modules/commands/ns_resetpass.cpp:22 +#, fuzzy +msgid "nickname email" +msgstr "FORBID nick motivo" + +#: modules/commands/ns_set.cpp:872 +#, fuzzy +msgid "nickname language" +msgstr "FORBID nick motivo" + +#: modules/commands/greet.cpp:145 +#, fuzzy +msgid "nickname message" +msgstr "FORBID nick motivo" + +#: modules/commands/ns_set.cpp:399 +#, fuzzy +msgid "nickname new-display" +msgstr "FORBID nick motivo" + +#: modules/commands/ns_set.cpp:173 +#, fuzzy +msgid "nickname new-password" +msgstr "GHOST nick [senha]" + +#: modules/commands/ns_set_misc.cpp:170 +#, fuzzy +msgid "nickname [parameter]" +msgstr "GHOST nick [senha]" + +#: modules/commands/ns_recover.cpp:150 +#, fuzzy +msgid "nickname [password]" +msgstr "GHOST nick [senha]" + +#: modules/commands/ns_suspend.cpp:61 +#, fuzzy +msgid "nickname [+expiry] [reason]" +msgstr "FORBID nick motivo" + +#: modules/commands/ns_info.cpp:239 +#, fuzzy +msgid "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +msgstr "SET HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:130 modules/commands/ns_set.cpp:302 +#: modules/commands/ns_set.cpp:631 modules/commands/ns_set.cpp:985 +#: modules/commands/ns_set.cpp:1076 modules/commands/ns_set.cpp:1105 +#: modules/commands/ns_list.cpp:252 +#, fuzzy +msgid "nickname {ON | OFF}" +msgstr "SASET nickname AUTOOP {ON | OFF}" + +#: modules/commands/ns_set.cpp:760 +#, fuzzy +msgid "nickname {ON | QUICK | IMMED | OFF}" +msgstr "SASET nickname KILL {ON | QUICK | IMMED | OFF}" + +#: modules/commands/bs_set.cpp:20 +#, fuzzy +msgid "option (channel | bot) settings" +msgstr "SET canal opções configurações" + +#: modules/commands/cs_set.cpp:21 +#, fuzzy +msgid "option channel parameters" +msgstr "SEND {nick | canal} texto" + +#: modules/commands/bs_kick.cpp:120 +#, fuzzy +msgid "option channel {ON|OFF} [settings]" +msgstr "KICK canal opções {ON|OFF} [configurações]" + +#: modules/commands/ns_set.cpp:75 +msgid "option nickname parameters" +msgstr "" + +#: modules/commands/ms_set.cpp:207 modules/commands/ns_set.cpp:20 +#, fuzzy +msgid "option parameters" +msgstr "SET opção configuração" + +#: modules/commands/os_set.cpp:170 +#, fuzzy +msgid "option setting" +msgstr "SET opção configuração" + +#: modules/commands/ns_register.cpp:22 +#, fuzzy +msgid "passcode" +msgstr "REGISTER senha email" + +#: modules/commands/os_login.cpp:19 +#, fuzzy +msgid "password" +msgstr "GROUP alvo senha" + +#: modules/commands/ns_register.cpp:124 +#, fuzzy +msgid "password [email]" +msgstr "REGISTER senha email" + +#: modules/commands/ns_register.cpp:122 +#, fuzzy +msgid "password email" +msgstr "REGISTER senha email" + +#: modules/commands/cs_list.cpp:21 +#, fuzzy +msgid "pattern [SUSPENDED] [NOEXPIRE]" +msgstr "LIST opções [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/ns_list.cpp:20 +#, fuzzy +msgid "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" +msgstr "LIST opções [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/os_jupe.cpp:20 +#, fuzzy +msgid "server [reason]" +msgstr "JUPE servidor [motivo]" + +#: modules/commands/os_mode.cpp:147 +#, fuzzy +msgid "user modes" +msgstr "MODE canal modos" + +#: modules/commands/os_kill.cpp:20 +#, fuzzy +msgid "user [reason]" +msgstr "JUPE servidor [motivo]" + +#: modules/commands/os_sxline.cpp:440 +#, fuzzy +msgid "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." +msgstr "" +"Sintaxe: AKILL ADD [+tempo] máscara motivo\n" +" AKILL DEL {máscara | entrada | lista-entradas}\n" +" AKILL LIST [máscara | lista-entradas]\n" +" AKILL VIEW [máscara | lista-entradas]\n" +" AKILL CLEAR\n" +"\n" +"Permite que Operadores dos Services manipulem a lista de\n" +"AKILL. Se um usuário que tenta conectar possui uma máscara\n" +"prevista na lista de AKILL, os Services emitem um KILL para\n" +"aquele usuário, em servidores que suportam, e instrui todos\n" +"os servidores da rede a adicionar um ban (K-line) para a\n" +"máscara do usuário encontrado.\n" +"\n" +"AKILL ADD adiciona uma máscara ident@host na lista de AKILL\n" +"para um dado motivo (deve ser fornecido).\n" +"Opcionalmente, um tempo para o akill expirar pode ser\n" +"fornecido. O tempo precede a máscara ident@host, e é\n" +"especificado como um número inteiro seguido por uma das\n" +"seguintes unidades: d (dias), h (horas) ou m (minutos).\n" +"Combinações (como 1h30m) não são permitidas. Se uma unidade\n" +"específica não é incluída, o padrão é em dias (assim, +30\n" +"significa 30 dias). Para adicionar um AKILL que não expira,\n" +"use +0. Se a máscara a ser adicionada começar com um +,\n" +"o tempo do AKILL deve ser fornecido, mesmo se esse tempo for igual\n" +"ao padrão. O tempo atual de expiração de AKILLs pode ser encontrado\n" +"com o comando STATS AKILL.\n" +"\n" +"AKILL DEL remove uma dada máscara da lista de AKILL, se ela\n" +"estiver presente. Se uma lista de números de entrada for fornecida,\n" +"essas entradas serão apagadas. (Veja o exemplo para LIST abaixo.)\n" +"\n" +"AKILL LIST mostra a lista de AKILL atual.\n" +"Se uma máscara for fornecida, apenas as entradas que combinarem\n" +"com a máscara serão exibidas. Se uma lista de números de entrada\n" +"for fornecida, apenas essas entradas serão exibidas; por exemplo:\n" +"\n" +" AKILL LIST 2-5,7-9\n" +" Lista as entradas de AKILL numeradas de 2 a 5 e de 7 a 9.\n" +"\n" +"AKILL VIEW é uma versão mais detalhada do AKILL LIST,\n" +"e mostrará quem adicionou o AKILL, a data em que foi adicionado,\n" +"e quando irá expirar, como também a máscara (ident@host) e o motivo.\n" +"\n" +"AKILL CLEAR apaga todas as entradas da lista de AKILL." + +#: modules/commands/os_sxline.cpp:678 +#, fuzzy +msgid "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Sintaxe: AKILL ADD [+tempo] máscara motivo\n" +" AKILL DEL {máscara | entrada | lista-entradas}\n" +" AKILL LIST [máscara | lista-entradas]\n" +" AKILL VIEW [máscara | lista-entradas]\n" +" AKILL CLEAR\n" +"\n" +"Permite que Operadores dos Services manipulem a lista de\n" +"AKILL. Se um usuário que tenta conectar possui uma máscara\n" +"prevista na lista de AKILL, os Services emitem um KILL para\n" +"aquele usuário, em servidores que suportam, e instrui todos\n" +"os servidores da rede a adicionar um ban (K-line) para a\n" +"máscara do usuário encontrado.\n" +"\n" +"AKILL ADD adiciona uma máscara ident@host na lista de AKILL\n" +"para um dado motivo (deve ser fornecido).\n" +"Opcionalmente, um tempo para o akill expirar pode ser\n" +"fornecido. O tempo precede a máscara ident@host, e é\n" +"especificado como um número inteiro seguido por uma das\n" +"seguintes unidades: d (dias), h (horas) ou m (minutos).\n" +"Combinações (como 1h30m) não são permitidas. Se uma unidade\n" +"específica não é incluída, o padrão é em dias (assim, +30\n" +"significa 30 dias). Para adicionar um AKILL que não expira,\n" +"use +0. Se a máscara a ser adicionada começar com um +,\n" +"o tempo do AKILL deve ser fornecido, mesmo se esse tempo for igual\n" +"ao padrão. O tempo atual de expiração de AKILLs pode ser encontrado\n" +"com o comando STATS AKILL.\n" +"\n" +"AKILL DEL remove uma dada máscara da lista de AKILL, se ela\n" +"estiver presente. Se uma lista de números de entrada for fornecida,\n" +"essas entradas serão apagadas. (Veja o exemplo para LIST abaixo.)\n" +"\n" +"AKILL LIST mostra a lista de AKILL atual.\n" +"Se uma máscara for fornecida, apenas as entradas que combinarem\n" +"com a máscara serão exibidas. Se uma lista de números de entrada\n" +"for fornecida, apenas essas entradas serão exibidas; por exemplo:\n" +"\n" +" AKILL LIST 2-5,7-9\n" +" Lista as entradas de AKILL numeradas de 2 a 5 e de 7 a 9.\n" +"\n" +"AKILL VIEW é uma versão mais detalhada do AKILL LIST,\n" +"e mostrará quem adicionou o AKILL, a data em que foi adicionado,\n" +"e quando irá expirar, como também a máscara (ident@host) e o motivo.\n" +"\n" +"AKILL CLEAR apaga todas as entradas da lista de AKILL." + +#: modules/pseudoclients/nickserv.cpp:492 +#, fuzzy, c-format +msgid "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." +msgstr "" +"Nicks que não estejam mais sendo usados estão sujeitos \n" +"a expirarem automaticamente, ou seja, eles serão apagados\n" +"após %d dias sem serem usados." + +#: modules/pseudoclients/botserv.cpp:143 +#, fuzzy +msgid "" +" \n" +"Available commands are:" +msgstr "Nenhuma ajuda disponível para %s." + +#: modules/pseudoclients/botserv.cpp:167 +#, c-format +msgid "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." +msgstr "" + +#: modules/fantasy.cpp:69 +#, fuzzy, c-format +msgid "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." +msgstr "" +"Sintaxe: SET canal FANTASY {ON|OFF}\n" +"\n" +"Ativa ou desativa o modo fantasia em um canal.\n" +"Quando estiver ativado, os usuários poderão usar\n" +"comandos como !op, !deop, !voice, !devoice,\n" +"!kick, !kb, !unban, !seen em um canal. Em algumas\n" +"redes, mais comandos podem estar disponíveis, tais\n" +"como: !owner, !deowner, !protect, !deprotect,\n" +"!halfop, !dehalfop.\n" +"\n" +"Note que os usuários que quiserem usar esses \n" +"comandos DEVEM ter um nível suficiente tanto para\n" +"o nível FANTASIA quanto para outro, dependendo\n" +"do comando usado (por exemplo, para usar !op, o \n" +"usuário deve ter acesso aos comandos OP e DEOP)." + +#: modules/commands/greet.cpp:69 +#, fuzzy +msgid "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." +msgstr "" +"Sintaxe: SET canal GREET {ON|OFF}\n" +"\n" +"Ativa ou desativa o modo greet em um canal.\n" +"Quando ativado, o bot irá mostrar mensagens de\n" +"entrada dos usuários quando eles entrarem no\n" +"canal, caso tenham nível de acesso suficiente." + +#: modules/commands/bs_kick.cpp:843 +#, fuzzy +msgid "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +"Sintaxe: SET canal DONTKICKOPS {ON|OFF}\n" +"\n" +"Ativa ou desativa o modo de proteção de OPs em um canal.\n" +"Quando estiver ativado, os OPs não serão kickados pelo bot,\n" +"mesmo se eles não se enquadram no nível de NOKICK." + +#: modules/commands/bs_kick.cpp:908 +#, fuzzy +msgid "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +"Sintaxe: SET canal DONTKICKVOICES {ON|OFF}\n" +"\n" +"Ativa ou desativa o modo de proteção de voices em um canal.\n" +"Quando estiver ativado, os voices não serão kickados pelo bot,\n" +"mesmo se eles não se enquadram no nível de NOKICK." + +#: modules/pseudoclients/botserv.cpp:141 +#, c-format +msgid "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" +msgstr "" + +#: modules/commands/cs_register.cpp:105 +msgid "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." +msgstr "" + +#: modules/pseudoclients/chanserv.cpp:272 +#, fuzzy, c-format +msgid "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." +msgstr "" +"Note que qualquer canal não utilizado por %d dias\n" +"(entenda como se nenhum usuário da lista de acesso\n" +"desse canal entrar neste período de tempo) terá\n" +"automaticamente cancelado o seu registro." + +#: modules/commands/cs_register.cpp:101 +#, c-format +msgid "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +msgstr "" + +#: modules/pseudoclients/nickserv.cpp:486 +#, fuzzy +msgid "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." +msgstr "" +"Os Administradores dos Services podem ainda usar o DROP em qualquer nick\n" +"sem ser necessário se identificar como dono dele, e podem ver a lista de\n" +"acesso de qualquer nick (/msg %s ACCESS LIST nick)." + +#: modules/pseudoclients/chanserv.cpp:277 +#, fuzzy +msgid "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." +msgstr "" +" \n" +"Os Administradores dos Services podem também usar o comando\n" +"DROP mesmo sem se identificarem como donos do canal, e podem\n" +"também ver as listas de acesso, AKICK, e níveis de qualquer\n" +"canal." + +#: modules/commands/bs_set.cpp:147 +msgid "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." +msgstr "" + +#: modules/commands/cs_xop.cpp:542 +#, fuzzy, c-format +msgid "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." +msgstr "" +"Sintaxe: HOP canal ADD nick\n" +" HOP canal DEL {nick | entrada | lista-entradas}\n" +" HOP canal LIST [máscara | lista-entradas]\n" +" HOP canal CLEAR\n" +"\n" +"Mantém a lista de HOP (HalfOP) para um canal. A lista\n" +"de HOP dá a um usuário o direito de receber HalfOP\n" +"automaticamente ao entrar no canal.\n" +"\n" +"O comando HOP ADD adiciona o nick fornecido à lista de HOP.\n" +"\n" +"O comando HOP DEL remove o nick fornecido da lista de HOP.\n" +"Se uma lista de números de entrada é fornecida, essas entradas\n" +"são deletadas. (Veja o exemplo para LIST abaixo.)\n" +"\n" +"O comando HOP LIST exibe a lista de HOP. Se uma máscara\n" +"é fornecida, apenas as entradas que combinarem com ela serão\n" +"mostradas. Se uma lista de números de entrada é fornecida,\n" +"apenas essas entradas são mostradas; por exemplo:\n" +"\n" +" HOP #canal LIST 2-5,7-9\n" +" Lista as entradas de HOP numeradas de 2 a 5 e de\n" +" 7 a 9.\n" +"\n" +"O comando HOP CLEAR remove todas as entradas da lista de HOP.\n" +"\n" +"Os comandos HOP ADD, HOP DEL e HOP LIST são limitados\n" +"aos AOPs ou acima, enquanto o comando HOP CLEAR pode ser usado\n" +"apenas pelo Fundador do canal.\n" +"\n" +"Este comando pode ter sido desabilitado para seu canal\n" +"e, nesse caso, você precisa usar a lista de acesso. Veja\n" +"/msg %s HELP ACCESS para informações sobre a lista\n" +"de acesso, e /msg %s HELP SET XOP para saber como\n" +"escolher entre a lista de acesso e o sistema de listas xOP." + +#: modules/commands/cs_akick.cpp:508 +#, c-format +msgid "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." +msgstr "" + +#: modules/commands/os_akill.cpp:448 +#, fuzzy +msgid "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." +msgstr "" +"Sintaxe: HOP canal ADD nick\n" +" HOP canal DEL {nick | entrada | lista-entradas}\n" +" HOP canal LIST [máscara | lista-entradas]\n" +" HOP canal CLEAR\n" +"\n" +"Mantém a lista de HOP (HalfOP) para um canal. A lista\n" +"de HOP dá a um usuário o direito de receber HalfOP\n" +"automaticamente ao entrar no canal.\n" +"\n" +"O comando HOP ADD adiciona o nick fornecido à lista de HOP.\n" +"\n" +"O comando HOP DEL remove o nick fornecido da lista de HOP.\n" +"Se uma lista de números de entrada é fornecida, essas entradas\n" +"são deletadas. (Veja o exemplo para LIST abaixo.)\n" +"\n" +"O comando HOP LIST exibe a lista de HOP. Se uma máscara\n" +"é fornecida, apenas as entradas que combinarem com ela serão\n" +"mostradas. Se uma lista de números de entrada é fornecida,\n" +"apenas essas entradas são mostradas; por exemplo:\n" +"\n" +" HOP #canal LIST 2-5,7-9\n" +" Lista as entradas de HOP numeradas de 2 a 5 e de\n" +" 7 a 9.\n" +"\n" +"O comando HOP CLEAR remove todas as entradas da lista de HOP.\n" +"\n" +"Os comandos HOP ADD, HOP DEL e HOP LIST são limitados\n" +"aos AOPs ou acima, enquanto o comando HOP CLEAR pode ser usado\n" +"apenas pelo Fundador do canal.\n" +"\n" +"Este comando pode ter sido desabilitado para seu canal\n" +"e, nesse caso, você precisa usar a lista de acesso. Veja\n" +"/msg %s HELP ACCESS para informações sobre a lista\n" +"de acesso, e /msg %s HELP SET XOP para saber como\n" +"escolher entre a lista de acesso e o sistema de listas xOP." + +#: modules/commands/os_sxline.cpp:462 +#, fuzzy +msgid "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." +msgstr "" +"Sintaxe: HOP canal ADD nick\n" +" HOP canal DEL {nick | entrada | lista-entradas}\n" +" HOP canal LIST [máscara | lista-entradas]\n" +" HOP canal CLEAR\n" +"\n" +"Mantém a lista de HOP (HalfOP) para um canal. A lista\n" +"de HOP dá a um usuário o direito de receber HalfOP\n" +"automaticamente ao entrar no canal.\n" +"\n" +"O comando HOP ADD adiciona o nick fornecido à lista de HOP.\n" +"\n" +"O comando HOP DEL remove o nick fornecido da lista de HOP.\n" +"Se uma lista de números de entrada é fornecida, essas entradas\n" +"são deletadas. (Veja o exemplo para LIST abaixo.)\n" +"\n" +"O comando HOP LIST exibe a lista de HOP. Se uma máscara\n" +"é fornecida, apenas as entradas que combinarem com ela serão\n" +"mostradas. Se uma lista de números de entrada é fornecida,\n" +"apenas essas entradas são mostradas; por exemplo:\n" +"\n" +" HOP #canal LIST 2-5,7-9\n" +" Lista as entradas de HOP numeradas de 2 a 5 e de\n" +" 7 a 9.\n" +"\n" +"O comando HOP CLEAR remove todas as entradas da lista de HOP.\n" +"\n" +"Os comandos HOP ADD, HOP DEL e HOP LIST são limitados\n" +"aos AOPs ou acima, enquanto o comando HOP CLEAR pode ser usado\n" +"apenas pelo Fundador do canal.\n" +"\n" +"Este comando pode ter sido desabilitado para seu canal\n" +"e, nesse caso, você precisa usar a lista de acesso. Veja\n" +"/msg %s HELP ACCESS para informações sobre a lista\n" +"de acesso, e /msg %s HELP SET XOP para saber como\n" +"escolher entre a lista de acesso e o sistema de listas xOP." + +#: modules/commands/os_sxline.cpp:697 +#, fuzzy +msgid "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." +msgstr "" +"Sintaxe: HOP canal ADD nick\n" +" HOP canal DEL {nick | entrada | lista-entradas}\n" +" HOP canal LIST [máscara | lista-entradas]\n" +" HOP canal CLEAR\n" +"\n" +"Mantém a lista de HOP (HalfOP) para um canal. A lista\n" +"de HOP dá a um usuário o direito de receber HalfOP\n" +"automaticamente ao entrar no canal.\n" +"\n" +"O comando HOP ADD adiciona o nick fornecido à lista de HOP.\n" +"\n" +"O comando HOP DEL remove o nick fornecido da lista de HOP.\n" +"Se uma lista de números de entrada é fornecida, essas entradas\n" +"são deletadas. (Veja o exemplo para LIST abaixo.)\n" +"\n" +"O comando HOP LIST exibe a lista de HOP. Se uma máscara\n" +"é fornecida, apenas as entradas que combinarem com ela serão\n" +"mostradas. Se uma lista de números de entrada é fornecida,\n" +"apenas essas entradas são mostradas; por exemplo:\n" +"\n" +" HOP #canal LIST 2-5,7-9\n" +" Lista as entradas de HOP numeradas de 2 a 5 e de\n" +" 7 a 9.\n" +"\n" +"O comando HOP CLEAR remove todas as entradas da lista de HOP.\n" +"\n" +"Os comandos HOP ADD, HOP DEL e HOP LIST são limitados\n" +"aos AOPs ou acima, enquanto o comando HOP CLEAR pode ser usado\n" +"apenas pelo Fundador do canal.\n" +"\n" +"Este comando pode ter sido desabilitado para seu canal\n" +"e, nesse caso, você precisa usar a lista de acesso. Veja\n" +"/msg %s HELP ACCESS para informações sobre a lista\n" +"de acesso, e /msg %s HELP SET XOP para saber como\n" +"escolher entre a lista de acesso e o sistema de listas xOP." + +#: modules/commands/bs_assign.cpp:197 +#, fuzzy +msgid "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." +msgstr "" +"Sintaxe: SET canal NOBOT {ON|OFF}\n" +"\n" +"Este comando faz com que um determinado bot não possa ser\n" +"associado a um canal. Se já houver um bot associado a este\n" +"canal, este será automaticamente desassociado quando você\n" +"ativar essa opção." + +#: modules/commands/bs_set.cpp:199 +#, fuzzy +msgid "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." +msgstr "" +"Sintaxe: SET nick PRIVATE {ON|OFF}\n" +"\n" +"Esta opção previne um bot de ser associado a um canal\n" +"por usuários que não sejam Operadores de IRC." + +#: modules/pseudoclients/memoserv.cpp:227 +#, c-format +msgid "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." +msgstr "" + +#: modules/commands/os_oper.cpp:167 +#, c-format +msgid " %s is online using this oper block." +msgstr "" + +#: modules/commands/os_modinfo.cpp:55 +#, c-format +msgid " Command %s on %s is linked to %s" +msgstr "" + +#: modules/commands/os_modinfo.cpp:43 +#, fuzzy, c-format +msgid " Providing service: %s" +msgstr "Comando fornecido: //msg %s %s" + +#: modules/commands/os_oper.cpp:163 +msgid " This oper is configured in the configuration file." +msgstr "" + +#: modules/commands/os_modinfo.cpp:34 +#, c-format +msgid " Loaded at: %p" +msgstr "" + +#: modules/commands/cs_seen.cpp:303 +#, c-format +msgid " but %s mysteriously dematerialized." +msgstr "" + +#: src/messages.cpp:339 +#, c-format +msgid "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." +msgstr "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." + +#: modules/commands/os_jupe.cpp:19 +#, fuzzy +msgid "\"Jupiter\" a server" +msgstr " JUPE Jupa um servidor" + +#: modules/commands/os_oper.cpp:161 +#, fuzzy, c-format +msgid "%-8s %s" +msgstr "%-20s %s@%s" + +#: modules/extra/stats/cs_fantasy_top.cpp:152 +#, c-format +msgid "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:359 +msgid "%b %d %H:%M:%S %Y %Z" +msgstr "" + +#: modules/commands/cs_log.cpp:205 +#, c-format +msgid "%c is an unknown status mode." +msgstr "" + +#: modules/commands/cs_mode.cpp:431 +#, fuzzy, c-format +msgid "%c%c is not locked on %s." +msgstr "%s não é notificado de novos memos." + +#: modules/commands/cs_mode.cpp:427 +#, fuzzy, c-format +msgid "%c%c%s has been unlocked from %s." +msgstr "Nick %s has been ungrouped from %s." + +#: modules/commands/cs_clone.cpp:56 +#, fuzzy, c-format +msgid "%d access entries from %s have been cloned to %s." +msgstr "Todos os vhost's no grupo %s foram ajustados para %s" + +#: modules/commands/bs_botlist.cpp:56 +#, c-format +msgid "%d bots available." +msgstr "%d bots disponíveis." + +#: modules/commands/os_modinfo.cpp:189 +#, fuzzy, c-format +msgid "%d modules loaded." +msgstr "%d módulos carregados." + +#: modules/commands/ns_group.cpp:357 +#, fuzzy, c-format +msgid "%d nickname(s) in the group." +msgstr "%d nicks no grupo." + +#: modules/commands/cs_seen.cpp:137 +#, c-format +msgid "%lu nicks are stored in the database, using %.2Lf kB of memory." +msgstr "" + +#: modules/commands/cs_xop.cpp:241 modules/commands/cs_xop.cpp:372 +#: modules/commands/cs_xop.cpp:450 +#, fuzzy, c-format +msgid "%s %s list is empty." +msgstr "Lista de AOP do canal %s está vazia." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1181 +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1201 +#: modules/commands/bs_kick.cpp:1211 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban)" +msgstr " Kick por negrito: %s (%d kick(s) para banir)" + +#: modules/commands/bs_kick.cpp:1161 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; %d lines in %ds)" +msgstr " Kick por flood: %s (%d kick(s) para banir; %d linhas em %ds)" + +#: modules/commands/bs_kick.cpp:1171 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; %d times)" +msgstr " Kick por repetição: %s (%d kick(s) para banir; %d vezes)" + +#: modules/commands/bs_kick.cpp:1141 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; minimum %d/%d%%)" +msgstr " Kick por Caps: %s (%d kick(s) para banir; mínimo %d/%d%%)" + +#: modules/commands/bs_kick.cpp:1163 +#, fuzzy, c-format +msgid "%s (%d lines in %ds)" +msgstr " %s (expira em %s)" + +#: modules/commands/bs_kick.cpp:1173 +#, c-format +msgid "%s (%d times)" +msgstr "" + +#: modules/commands/cs_seen.cpp:358 +#, c-format +msgid "%s (%s) was kicked from %s (\"%s\") %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:355 +#, c-format +msgid "%s (%s) was kicked from a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:326 +#, c-format +msgid "%s (%s) was last seen changing nick from %s to %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:321 +#, c-format +msgid "%s (%s) was last seen changing nick to %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:310 +#, c-format +msgid "%s (%s) was last seen connecting %s ago (%s)%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:335 +#, c-format +msgid "%s (%s) was last seen joining %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:332 +#, c-format +msgid "%s (%s) was last seen joining a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:344 +#, c-format +msgid "%s (%s) was last seen parting %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:341 +#, c-format +msgid "%s (%s) was last seen parting a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:349 +#, c-format +msgid "%s (%s) was last seen quitting (%s) %s ago (%s)." +msgstr "" + +#: modules/commands/bs_kick.cpp:1143 +#, fuzzy, c-format +msgid "%s (minimum %d/%d%%)" +msgstr " Kick por Caps: %s (mínimo %d/%d%%)" + +#: modules/commands/cs_access.cpp:245 modules/commands/cs_access.cpp:349 +#: modules/commands/cs_access.cpp:454 modules/commands/cs_access.cpp:467 +#: modules/commands/cs_flags.cpp:295 +#, c-format +msgid "%s access list is empty." +msgstr "Lista de acesso do canal %s está vazia." + +#: modules/commands/ns_ajoin.cpp:184 +#, fuzzy, c-format +msgid "%s added to %s's auto join list." +msgstr "%s adicionado à lista de akick do %s." + +#: src/xline.cpp:389 +#, fuzzy, c-format +msgid "%s already exists." +msgstr "Bot %s já existe." + +#: modules/commands/cs_akick.cpp:202 modules/commands/cs_akick.cpp:387 +#: modules/commands/cs_akick.cpp:400 +#, c-format +msgid "%s autokick list is empty." +msgstr "Lista de akick do %s vazia." + +#: modules/commands/bs_badwords.cpp:198 modules/commands/bs_badwords.cpp:316 +#, c-format +msgid "%s bad words list is empty." +msgstr "Lista de palvrões do %s está vazia." + +#: modules/commands/cs_set.cpp:993 +#, fuzzy, c-format +msgid "%s cannot be the successor on channel %s as they are the founder." +msgstr "%s não pode ser o successor do canal %s porque ele é o founder." + +#: modules/pseudoclients/global.cpp:90 modules/pseudoclients/hostserv.cpp:78 +#: modules/pseudoclients/operserv.cpp:287 +#, c-format +msgid "%s commands:" +msgstr "Comandos do %s:" + +#: include/language.h:69 +#, c-format +msgid "%s coverage is too wide; Please use a more specific mask." +msgstr "" + +#: modules/commands/ms_info.cpp:94 +#, c-format +msgid "%s currently has %d memos, of which %d are unread." +msgstr "%s possui atualmente %d memos, dos quais %d não foram lidos." + +#: modules/commands/ms_info.cpp:92 +#, c-format +msgid "%s currently has %d memos, of which 1 is unread." +msgstr "%s possui atualmente %d memos, dos quais 1 não foi lido." + +#: modules/commands/ms_info.cpp:90 +#, c-format +msgid "%s currently has %d memos." +msgstr "%s possui atualmente %d memos." + +#: modules/commands/ms_info.cpp:88 +#, c-format +msgid "%s currently has %d memos; all of them are unread." +msgstr "%s possui atualmente %d memos; dos quais nenhum foi lido." + +#: modules/commands/ms_info.cpp:77 +#, c-format +msgid "%s currently has 1 memo, and it has not yet been read." +msgstr "%s possui atualmente 1 memo, e ainda não foi lido." + +#: modules/commands/ms_info.cpp:79 +#, c-format +msgid "%s currently has 1 memo." +msgstr "%s possui atualmente 1 memo." + +#: modules/commands/ms_info.cpp:73 +#, c-format +msgid "%s currently has no memos." +msgstr "%s não possui nenhum memo atualmente." + +#: modules/commands/os_forbid.cpp:344 +#, fuzzy, c-format +msgid "%s deleted from the %s forbid list." +msgstr "%s removido da lista de palavrões do %s." + +#: include/language.h:105 +#, fuzzy, c-format +msgid "%s for %s set to %s." +msgstr "vhost de %s ajustado para %s." + +#: include/language.h:106 +#, fuzzy, c-format +msgid "%s for %s unset." +msgstr "Successor do canal %s removido." + +#: modules/commands/ns_ajoin.cpp:176 +#, c-format +msgid "%s had an invalid key specified, and was thus ignored." +msgstr "" + +#: modules/commands/ms_info.cpp:111 +#, c-format +msgid "%s has no memo limit." +msgstr "%s não possui limite de memos." + +#: include/language.h:115 +#, fuzzy, c-format +msgid "%s has no memos." +msgstr "%s não possui limite de memos." + +#: include/language.h:118 +#, fuzzy, c-format +msgid "%s has no new memos." +msgstr "%s não possui limite de memos." + +#: modules/commands/ns_info.cpp:53 +#, c-format +msgid "%s is %s" +msgstr "%s é %s" + +#: modules/commands/ns_info.cpp:59 +#, fuzzy, c-format +msgid "%s is a Services Operator of type %s." +msgstr "%s is a services operator of type %s." + +#: modules/commands/cs_seen.cpp:281 +#, fuzzy, c-format +msgid "%s is a client on services." +msgstr "%s está online neste momento." + +#: modules/commands/cs_seen.cpp:200 +#, fuzzy, c-format +msgid "%s is a network service." +msgstr "%s está online neste momento." + +#: src/xline.cpp:407 +#, fuzzy, c-format +msgid "%s is already covered by %s." +msgstr "%s já está coberto pelo AKILL %s." + +#: modules/commands/ns_ajoin.cpp:170 +#, fuzzy, c-format +msgid "%s is already on %s's auto join list." +msgstr "%s adicionado em sua lista de acesso." + +#: modules/commands/ns_info.cpp:56 +#, fuzzy, c-format +msgid "%s is an unconfirmed nickname." +msgstr "Este nick não irá expirar." + +#: modules/commands/cs_flags.cpp:432 +#, c-format +msgid "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." +msgstr "" + +#: modules/commands/ns_info.cpp:74 +#, c-format +msgid "%s is currently online." +msgstr "%s está online neste momento." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is disabled" +msgstr "%s está desativada" + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is enabled" +msgstr "%s está ativada" + +#: modules/commands/os_dns.cpp:507 +#, fuzzy, c-format +msgid "%s is not a valid IP address." +msgstr "%s não é um ban válido." + +#: modules/commands/cs_log.cpp:167 modules/commands/cs_log.cpp:192 +#, fuzzy, c-format +msgid "%s is not a valid command." +msgstr "%s não é um ban válido." + +#: modules/commands/cs_log.cpp:198 +#, fuzzy, c-format +msgid "%s is not a valid logging method." +msgstr "%s não é um ban válido." + +#: modules/commands/ms_info.cpp:124 +#, c-format +msgid "%s is not notified of new memos." +msgstr "%s não é notificado de novos memos." + +#: modules/commands/ms_info.cpp:118 +#, c-format +msgid "%s is notified of new memos at logon and when they arrive." +msgstr "" +"%s é notificado de novos memos quando conecta e quando eles são enviados." + +#: modules/commands/ms_info.cpp:122 +#, c-format +msgid "%s is notified of new memos at logon." +msgstr "%s é notificado de novos memos quando conecta." + +#: modules/commands/ms_info.cpp:120 +#, c-format +msgid "%s is notified when new memos arrive." +msgstr "%s é notificado de novos memos quando eles são enviados." + +#: modules/commands/cs_seen.cpp:232 +#, c-format +msgid "%s is on the channel right now (as %s)!" +msgstr "" + +#: modules/commands/cs_seen.cpp:221 +#, fuzzy, c-format +msgid "%s is on the channel right now!" +msgstr "%s desabilitado no canal %s." + +#: modules/commands/cs_xop.cpp:434 +#, fuzzy, c-format +msgid "%s list for %s" +msgstr "Lista de acesso para %s:" + +#: modules/commands/os_sxline.cpp:69 modules/commands/os_sxline.cpp:113 +#, fuzzy, c-format +msgid "%s list is empty." +msgstr "Lista de AOP do canal %s está vazia." + +#: modules/commands/cs_mode.cpp:376 +#, fuzzy, c-format +msgid "%s locked on %s." +msgstr "%s não é notificado de novos memos." + +#: modules/extra/stats/cs_fantasy_stats.cpp:120 +#, fuzzy, c-format +msgid "%s not found." +msgstr "Nick %s não encontrado na lista de AOP do %s." + +#: modules/commands/os_config.cpp:79 +#, c-format +msgid "%s settings:" +msgstr "" + +#: modules/commands/cs_seen.cpp:255 +#, c-format +msgid "%s was last seen here %s ago." +msgstr "" + +#: modules/commands/ns_ajoin.cpp:213 +#, fuzzy, c-format +msgid "%s was not found on %s's auto join list." +msgstr "%s não encontrado na lista de akick do %s." + +#: modules/commands/ns_ajoin.cpp:221 +#, fuzzy, c-format +msgid "%s was removed from %s's auto join list." +msgstr "%s removido da lista de akick do %s." + +#: modules/commands/ms_set.cpp:64 +#, c-format +msgid "%s will not send you any notification of memos." +msgstr "%s não irá mais notificá-lo de novos memos." + +#: modules/commands/ms_set.cpp:42 +#, c-format +msgid "%s will now notify you of memos when they are sent to you." +msgstr "" +"%s irá agora notificá-lo de novos memos quando eles lhe forem enviados." + +#: modules/commands/ms_set.cpp:30 +#, c-format +msgid "" +"%s will now notify you of memos when you log on and when they are sent to " +"you." +msgstr "" +"%s irá agora notificá-lo de novos memos quando você conectar, quando eles " +"lhe forem enviados ou quando desativar o /AWAY." + +#: modules/commands/ms_set.cpp:36 +#, c-format +msgid "%s will now notify you of memos when you log on or unset /AWAY." +msgstr "" +"%s irá agora notificá-lo de novos memos quando você conectar ou quando " +"desativar o /AWAY." + +#: modules/commands/bs_bot.cpp:89 +#, c-format +msgid "%s!%s@%s (%s) added to the bot list." +msgstr "%s!%s@%s (%s) adicionado à lista de bots." + +#: modules/commands/ns_access.cpp:83 +#, fuzzy, c-format +msgid "%s's access list is empty." +msgstr "Lista de acesso do canal %s está vazia." + +#: modules/commands/ns_ajoin.cpp:96 +#, fuzzy, c-format +msgid "%s's auto join list is empty." +msgstr "Lista de akick do %s vazia." + +#: modules/commands/ns_ajoin.cpp:111 +#, fuzzy, c-format +msgid "%s's auto join list:" +msgstr " AKICK Faz a manutenção da Lista de Autokick" + +#: modules/commands/ns_cert.cpp:242 +#, fuzzy, c-format +msgid "%s's certificate list is empty." +msgstr "Sua lista de acesso está vazia." + +#: modules/commands/ms_info.cpp:99 modules/commands/ms_info.cpp:106 +#, c-format +msgid "%s's memo limit is %d, and may not be changed." +msgstr "Limite de memos para %s é de %d, e não pode ser alterado." + +#: modules/commands/ms_info.cpp:101 modules/commands/ms_info.cpp:108 +#, c-format +msgid "%s's memo limit is %d." +msgstr "Limite de memos para %s é de %d." + +#: src/misc.cpp:363 +#, c-format +msgid "(%s ago)" +msgstr "" + +#: src/misc.cpp:365 +#, c-format +msgid "(%s from now)" +msgstr "" + +#: modules/commands/os_dns.cpp:244 +msgid "(Split)" +msgstr "" + +#: modules/commands/os_info.cpp:268 +#, c-format +msgid "(by %s on %s) %s" +msgstr "" + +#: modules/commands/cs_access.cpp:710 +#, fuzzy +msgid "(disabled)" +msgstr "%s está ativada" + +#: modules/commands/cs_access.cpp:712 +msgid "(founder only)" +msgstr "" + +#: src/misc.cpp:367 +msgid "(now)" +msgstr "" + +#: modules/commands/os_defcon.cpp:168 +msgid "* AKILL any new clients connecting" +msgstr "* AKILLA quaisquer novos clientes conectando" + +#: modules/commands/os_defcon.cpp:158 +#, fuzzy, c-format +msgid "* Force channel modes (%s) to be set on all channels" +msgstr "* Força os Modos de Canal (%s) a serem setados em todos os canais" + +#: modules/commands/os_defcon.cpp:164 +#, fuzzy +msgid "* Ignore non-opers with a message" +msgstr "* Ignora quaisquer não-opers com mensagem" + +#: modules/commands/os_defcon.cpp:162 +#, fuzzy +msgid "* Kill any new clients connecting" +msgstr "* Killa quaisquer NOVOS clientes conectando" + +#: modules/commands/os_defcon.cpp:156 +#, fuzzy +msgid "* No mode lock changes" +msgstr "* Impedida a mudança de MLOCK" + +#: modules/commands/os_defcon.cpp:152 +msgid "* No new channel registrations" +msgstr "* Impedido o registro de novos canais" + +#: modules/commands/os_defcon.cpp:170 +msgid "* No new memos sent" +msgstr "* Impede o envio de novos memos" + +#: modules/commands/os_defcon.cpp:154 +msgid "* No new nick registrations" +msgstr "* Impedido o registro de novos nicks" + +#: modules/commands/os_defcon.cpp:166 +msgid "* Silently ignore non-opers" +msgstr "* Silenciosamente ignora não-opers" + +#: modules/commands/os_defcon.cpp:160 +#, c-format +msgid "* Use the reduced session limit of %d" +msgstr "* Usa o limite de sessões reduzido de %d" + +#: modules/commands/cs_seen.cpp:319 +#, c-format +msgid ", but %s mysteriously dematerialized." +msgstr "" + +#: modules/commands/cs_seen.cpp:317 +#, fuzzy, c-format +msgid ". %s is still online." +msgstr "%s está online neste momento." + +#: include/language.h:87 +msgid "" +msgstr "" + +#: modules/commands/ns_set.cpp:504 +#, fuzzy, c-format +msgid "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." +msgstr "" +"O passcode foi enviado para %s, por favor digite /msg %s confirm  " +"para completar o registro." + +#: modules/commands/ms_sendall.cpp:45 +msgid "A massmemo has been sent to all registered users." +msgstr "Uma mensagem global foi enviada a todos os usuários registrados." + +#: modules/commands/hs_request.cpp:285 +msgid "" +"A memo informing the user will also be sent, which includes the reason for " +"the rejection if supplied." +msgstr "" + +#: modules/commands/hs_request.cpp:229 +msgid "A memo informing the user will also be sent." +msgstr "" + +#: modules/commands/ms_read.cpp:42 +#, c-format +msgid "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." +msgstr "" +"Um memo de notificação foi enviado para %s informando que você leu seu memo." + +#: include/language.h:123 +msgid "A vHost ident must be in the format of a valid ident." +msgstr "" + +#: include/language.h:122 +msgid "A vHost must be in the format of a valid hostname." +msgstr "" + +#: modules/commands/os_ignore.cpp:342 +#, fuzzy +msgid "ADD expiry {nick|mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_oper.cpp:70 +msgid "ADD oper type" +msgstr "" + +#: modules/commands/os_info.cpp:102 +#, fuzzy +msgid "ADD target info" +msgstr "GROUP alvo senha" + +#: modules/commands/os_news.cpp:278 +msgid "ADD text" +msgstr "" + +#: modules/commands/os_session.cpp:523 +#, fuzzy +msgid "ADD [+expiry] mask limit reason" +msgstr "CHANKILL [+tempo] {#canal} [motivo]" + +#: modules/commands/ns_ajoin.cpp:231 +#, fuzzy +msgid "ADD [nickname] channel [key]" +msgstr "CHANKILL [+tempo] {#canal} [motivo]" + +#: modules/commands/ns_access.cpp:102 +#, fuzzy +msgid "ADD [nickname] mask" +msgstr "CHANKILL [+tempo] {#canal} [motivo]" + +#: modules/commands/ns_cert.cpp:258 +#, fuzzy +msgid "ADD [nickname] [fingerprint]" +msgstr "FORBID nick motivo" + +#: modules/commands/os_sxline.cpp:659 modules/commands/os_akill.cpp:386 +#, fuzzy +msgid "ADD [+expiry] mask reason" +msgstr "CHANKILL [+tempo] {#canal} [motivo]" + +#: modules/commands/os_sxline.cpp:425 +#, fuzzy +msgid "ADD [+expiry] mask:reason" +msgstr "CHANKILL [+tempo] {#canal} [motivo]" + +#: modules/commands/os_forbid.cpp:157 +#, fuzzy +msgid "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" +msgstr "CHANKILL [+tempo] {#canal} [motivo]" + +#: modules/commands/os_dns.cpp:665 +msgid "ADDIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:663 +msgid "ADDSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:661 +msgid "ADDZONE zone.name" +msgstr "" + +#: modules/commands/cs_akick.cpp:38 +#, c-format +msgid "AKICK ENFORCE for %s complete; %d users were affected." +msgstr "AKICK ENFORCE para %s terminado; %d usuários afetados." + +#: modules/commands/os_chankill.cpp:21 +#, fuzzy +msgid "AKILL all users on a specific channel" +msgstr " CHANKILL AKILL todos os usuários de um canal específico" + +#: modules/commands/os_akill.cpp:222 modules/commands/os_akill.cpp:339 +#: modules/commands/os_akill.cpp:353 +msgid "AKILL list is empty." +msgstr "A lista de AKILL está vazia." + +#: modules/commands/bs_kick.cpp:1211 modules/commands/bs_kick.cpp:1213 +#: modules/commands/bs_kick.cpp:1216 +#, fuzzy +msgid "AMSG kicker" +msgstr " Kick por Caps: %s" + +#: modules/commands/ns_alist.cpp:48 +#, fuzzy +msgid "Access" +msgstr "Lista de acesso:" + +#: include/language.h:72 +#, fuzzy +msgid "Access denied." +msgstr "Lista de acesso:" + +#: modules/commands/cs_status.cpp:58 +#, fuzzy, c-format +msgid "Access for %s on %s:" +msgstr "Nível de acesso para %s no %s alterado para %d." + +#: include/language.h:107 +#, fuzzy, c-format +msgid "Access level must be between %d and %d inclusive." +msgstr "O nível deve ser entre %d e %d inclusive." + +#: modules/commands/cs_access.cpp:108 +msgid "Access level must be non-zero." +msgstr "O nível de acesso deve ser diferente de zero." + +#: modules/commands/cs_access.cpp:694 +#, c-format +msgid "Access level settings for channel %s:" +msgstr "Opções de nível de acesso para o canal %s:" + +#: modules/commands/cs_access.cpp:734 +#, c-format +msgid "Access levels for %s reset to defaults." +msgstr "Níveis de acesso para o %s redefinidos para o padrão." + +#: modules/commands/cs_access.cpp:439 modules/commands/ns_access.cpp:87 +#, fuzzy, c-format +msgid "Access list for %s:" +msgstr "Lista de acesso para %s:" + +#: modules/commands/help.cpp:166 +#, c-format +msgid "" +"Access to this command requires the permission %s to be present in your " +"opertype." +msgstr "" +"Access to this command requires the permission %s to be present in your " +"opertype." + +#: modules/commands/ns_cert.cpp:368 modules/commands/ns_cert.cpp:392 +#: modules/commands/ns_identify.cpp:94 +#, c-format +msgid "" +"Account %s has already reached the maximum number of simultaneous logins " +"(%u)." +msgstr "" + +#: modules/commands/cs_set.cpp:683 +#, fuzzy +msgid "Activate security features" +msgstr " SECURE Ativa os recursos de segurança do %s" + +#: modules/commands/hs_request.cpp:227 +msgid "Activate the requested vHost for the given nick." +msgstr "" + +#: modules/commands/hs_on.cpp:55 +#, fuzzy +msgid "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." +msgstr "" +"Sintaxe: ON\n" +"Ativa o vhost atualmente associado ao nick em uso.\n" +"Quando você usa este comando, qualquer usuário que faça um /whois\n" +"em você irá ver o vhost em vez do seu endereço IP real/encriptado." + +#: modules/commands/hs_on.cpp:19 +#, fuzzy +msgid "Activates your assigned vhost" +msgstr " ON Ativa seu vHost associado" + +#: modules/commands/os_info.cpp:243 +msgid "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." +msgstr "" + +#: modules/commands/os_dns.cpp:515 +#, c-format +msgid "Added IP %s to %s." +msgstr "" + +#: modules/commands/os_forbid.cpp:239 +#, c-format +msgid "Added a forbid on %s of type %s to expire on %s." +msgstr "" + +#: modules/commands/os_info.cpp:164 +#, fuzzy, c-format +msgid "Added info to %s." +msgstr "Memo enviado para %s." + +#: modules/commands/os_news.cpp:34 +#, fuzzy +msgid "Added new logon news item." +msgstr "Adicionado novo logon news (#%d)." + +#: modules/commands/os_news.cpp:44 +#, fuzzy +msgid "Added new oper news item." +msgstr "Adicionado novo OperNews (#%d)." + +#: modules/commands/os_news.cpp:54 +#, fuzzy +msgid "Added new random news item." +msgstr "Adicionada novo item RandomNews (#%d)." + +#: modules/commands/os_dns.cpp:395 +#, fuzzy, c-format +msgid "Added server %s." +msgstr "Uplink server: %s" + +#: modules/commands/os_dns.cpp:300 +#, c-format +msgid "Added zone %s." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:257 +msgid "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." +msgstr "" + +#: modules/commands/ns_register.cpp:104 +msgid "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." +msgstr "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." + +#: modules/pseudoclients/botserv.cpp:172 +#, c-format +msgid "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" +msgstr "" + +#: modules/commands/os_noop.cpp:58 +#, c-format +msgid "All O:lines of %s have been reset." +msgstr "Todas as O:lines do servidor %s foram resetadas." + +#: modules/commands/cs_clone.cpp:71 +#, fuzzy, c-format +msgid "All akick entries from %s have been cloned to %s." +msgstr "Todos os vhost's no grupo %s foram ajustados para %s" + +#: modules/commands/help.cpp:57 +#, fuzzy, c-format +msgid "All available commands for %s:" +msgstr "Nenhuma ajuda disponível para %s." + +#: modules/commands/cs_clone.cpp:96 +#, fuzzy, c-format +msgid "All badword entries from %s have been cloned to %s." +msgstr "Todos os vhost's no grupo %s foram ajustados para %s" + +#: modules/commands/cs_clone.cpp:108 +#, fuzzy, c-format +msgid "All level entries from %s have been cloned into %s." +msgstr "Todos os vhost's no grupo %s foram ajustados para %s" + +#: modules/commands/os_news.cpp:38 +msgid "All logon news items deleted." +msgstr "Todos os logon news foram removidos." + +#: modules/commands/ms_del.cpp:115 +#, c-format +msgid "All memos for channel %s have been deleted." +msgstr "Todos os memos para o canal %s foram apagados." + +#: modules/commands/os_mode.cpp:61 +#, c-format +msgid "All modes cleared on %s." +msgstr "" + +#: modules/commands/ns_register.cpp:258 modules/commands/ns_register.cpp:389 +msgid "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." +msgstr "" + +#: modules/commands/ms_del.cpp:119 +msgid "All of your memos have been deleted." +msgstr "Todos os seus memos foram apagados." + +#: modules/commands/os_news.cpp:48 +msgid "All oper news items deleted." +msgstr "Todos os OperNews foram removidos." + +#: modules/commands/os_noop.cpp:41 +#, fuzzy, c-format +msgid "All operators from %s have been removed." +msgstr "Todas as O:lines do servidor %s foram removidas." + +#: modules/commands/os_news.cpp:58 +msgid "All random news items deleted." +msgstr "Todos os itens RandomNews deletados." + +#: modules/commands/cs_clone.cpp:211 +#, fuzzy, c-format +msgid "All settings from %s have been cloned to %s." +msgstr "Todos os vhost's no grupo %s foram ajustados para %s" + +#: modules/commands/cs_sync.cpp:41 +#, fuzzy, c-format +msgid "All user modes on %s have been synced." +msgstr "Todas as O:lines do servidor %s foram resetadas." + +#: modules/commands/hs_group.cpp:60 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s." +msgstr "Todos os vhost's no grupo %s foram ajustados para %s" + +#: modules/commands/hs_group.cpp:58 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s@%s." +msgstr "Todos os vhost's no grupo %s foram ajustados para %s@%s" + +#: src/access.cpp:40 +msgid "Allowed to (de)halfop him/herself" +msgstr "" + +#: src/access.cpp:39 +msgid "Allowed to (de)halfop users" +msgstr "" + +#: src/access.cpp:48 +msgid "Allowed to (de)op him/herself" +msgstr "" + +#: src/access.cpp:47 +msgid "Allowed to (de)op users" +msgstr "" + +#: src/access.cpp:50 +msgid "Allowed to (de)owner him/herself" +msgstr "" + +#: src/access.cpp:49 +msgid "Allowed to (de)owner users" +msgstr "" + +#: src/access.cpp:52 +msgid "Allowed to (de)protect him/herself" +msgstr "" + +#: src/access.cpp:51 +msgid "Allowed to (de)protect users" +msgstr "" + +#: src/access.cpp:59 +msgid "Allowed to (de)voice him/herself" +msgstr "" + +#: src/access.cpp:58 +msgid "Allowed to (de)voice users" +msgstr "" + +#: src/access.cpp:27 +msgid "Allowed to assign/unassign a bot" +msgstr "" + +#: src/access.cpp:34 +msgid "Allowed to ban users" +msgstr "" + +#: src/access.cpp:56 +#, fuzzy +msgid "Allowed to change channel topics" +msgstr "%s alterou seus modos de usuário." + +#: src/access.cpp:41 +msgid "Allowed to get full INFO output" +msgstr "" + +#: src/access.cpp:36 +msgid "Allowed to issue commands restricted to channel founders" +msgstr "" + +#: src/access.cpp:33 +msgid "Allowed to modify channel badwords list" +msgstr "" + +#: src/access.cpp:24 +#, fuzzy +msgid "Allowed to modify the access list" +msgstr "%s removido da lista de acesso do %s." + +#: src/access.cpp:44 +msgid "Allowed to read channel memos" +msgstr "" + +#: src/access.cpp:54 +#, fuzzy +msgid "Allowed to set channel settings" +msgstr "* Impedido o registro de novos canais" + +#: src/access.cpp:57 +msgid "Allowed to unban users" +msgstr "" + +#: src/access.cpp:37 +msgid "Allowed to use GETKEY command" +msgstr "" + +#: src/access.cpp:53 +msgid "Allowed to use SAY and ACT commands" +msgstr "" + +#: src/access.cpp:35 +#, fuzzy +msgid "Allowed to use fantasy commands" +msgstr " PEACE Regula o uso de comandos críticos" + +#: src/access.cpp:26 +#, fuzzy +msgid "Allowed to use the AKICK command" +msgstr "You cannot use this command." + +#: src/access.cpp:42 +msgid "Allowed to use the INVITE command" +msgstr "" + +#: src/access.cpp:43 +#, fuzzy +msgid "Allowed to use the KICK command" +msgstr "You cannot use this command." + +#: src/access.cpp:45 +#, fuzzy +msgid "Allowed to use the MODE command" +msgstr "You cannot use this command." + +#: src/access.cpp:25 +#, fuzzy +msgid "Allowed to view the access list" +msgstr "%s removido da lista de acesso do %s." + +#: modules/commands/gl_global.cpp:42 +#, fuzzy, c-format +msgid "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." +msgstr "" +"Sintaxe: GLOBAL mensagens\n" +"\n" +"Permite que os IRCops enviem mensagens para todos os usuários\n" +"da Rede. A mensagem será enviada pelo nick %s." + +#: modules/commands/os_mode.cpp:133 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." +msgstr "" +"Sintaxe: MODE canal modos\n" +"\n" +"Permite que os Operadores dos Services ajustem os modos de\n" +"qualquer canal. Os parâmetros são os mesmos do comando\n" +"/MODE padrão." + +#: modules/commands/os_mode.cpp:173 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." +msgstr "" +"Sintaxe: MODE canal modos\n" +"\n" +"Permite que os Operadores dos Services ajustem os modos de\n" +"qualquer canal. Os parâmetros são os mesmos do comando\n" +"/MODE padrão." + +#: modules/commands/bs_bot.cpp:352 +#, fuzzy +msgid "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." +msgstr "" +"Sintaxe: BOT ADD nick user host real\n" +" BOT CHANGE NickAntigo NickNovo [user [host [real]]]\n" +" BOT DEL nick\n" +"\n" +"Permite que os Administradores dos Services criem,\n" +"modifiquem, e apaguem bots que os usuários poderão usar\n" +"em seus próprios canais.\n" +"\n" +"BOT ADD adiciona um bot com um determinado nick, username,\n" +"hostname e realname. \n" +"BOT CHANGE permite alterar o nick, username, hostname\n" +"ou realname de um bot sem que seja necessário apagá-lo (e\n" +"todas as informações nele contidas).\n" +"BOT DEL remove um bot da lista de bots. \n" +"\n" +"Nota: você não pode criar um bot que use um nick que já\n" +"seja registrado. Se um usuário não registrado está atualmente\n" +"usando o nick, ele será killado." + +#: modules/commands/os_oline.cpp:56 +#, fuzzy +msgid "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." +msgstr "" +"Sintaxe: OLINE usuário flags\n" +"\n" +"Permite aos Services Operators dar flags de Oper\n" +"a qualquer usuário. Flags devem ser prefixadas com \"+\" ou\n" +"\"-\". Para remover todas as flags apenas digite um \"-\" em\n" +"vez de usar alguma flag." + +#: modules/commands/os_ignore.cpp:370 +#, fuzzy +msgid "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." +msgstr "" +"Syntax: IGNORE {ADD|DEL|LIST|CLEAR} [time] [nick | mask]\n" +"\n" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes, \n" +"h for hours and d for days. \n" +"Combinations of these units are not permitted. To make\n" +"Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format user@host\n" +"or nick!user@host, everything else will be considered a nick.\n" +"Wildcards are permitted.\n" +"\n" +"Ignores will not be enforced on IRC Operators." + +#: modules/commands/os_akill.cpp:420 +#, fuzzy +msgid "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Sintaxe: AKILL ADD [+tempo] máscara motivo\n" +" AKILL DEL {máscara | entrada | lista-entradas}\n" +" AKILL LIST [máscara | lista-entradas]\n" +" AKILL VIEW [máscara | lista-entradas]\n" +" AKILL CLEAR\n" +"\n" +"Permite que Operadores dos Services manipulem a lista de\n" +"AKILL. Se um usuário que tenta conectar possui uma máscara\n" +"prevista na lista de AKILL, os Services emitem um KILL para\n" +"aquele usuário, em servidores que suportam, e instrui todos\n" +"os servidores da rede a adicionar um ban (K-line) para a\n" +"máscara do usuário encontrado.\n" +"\n" +"AKILL ADD adiciona uma máscara ident@host na lista de AKILL\n" +"para um dado motivo (deve ser fornecido).\n" +"Opcionalmente, um tempo para o akill expirar pode ser\n" +"fornecido. O tempo precede a máscara ident@host, e é\n" +"especificado como um número inteiro seguido por uma das\n" +"seguintes unidades: d (dias), h (horas) ou m (minutos).\n" +"Combinações (como 1h30m) não são permitidas. Se uma unidade\n" +"específica não é incluída, o padrão é em dias (assim, +30\n" +"significa 30 dias). Para adicionar um AKILL que não expira,\n" +"use +0. Se a máscara a ser adicionada começar com um +,\n" +"o tempo do AKILL deve ser fornecido, mesmo se esse tempo for igual\n" +"ao padrão. O tempo atual de expiração de AKILLs pode ser encontrado\n" +"com o comando STATS AKILL.\n" +"\n" +"AKILL DEL remove uma dada máscara da lista de AKILL, se ela\n" +"estiver presente. Se uma lista de números de entrada for fornecida,\n" +"essas entradas serão apagadas. (Veja o exemplo para LIST abaixo.)\n" +"\n" +"AKILL LIST mostra a lista de AKILL atual.\n" +"Se uma máscara for fornecida, apenas as entradas que combinarem\n" +"com a máscara serão exibidas. Se uma lista de números de entrada\n" +"for fornecida, apenas essas entradas serão exibidas; por exemplo:\n" +"\n" +" AKILL LIST 2-5,7-9\n" +" Lista as entradas de AKILL numeradas de 2 a 5 e de 7 a 9.\n" +"\n" +"AKILL VIEW é uma versão mais detalhada do AKILL LIST,\n" +"e mostrará quem adicionou o AKILL, a data em que foi adicionado,\n" +"e quando irá expirar, como também a máscara (ident@host) e o motivo.\n" +"\n" +"AKILL CLEAR apaga todas as entradas da lista de AKILL." + +#: modules/commands/os_sxline.cpp:436 +msgid "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." +msgstr "" + +#: modules/commands/os_sxline.cpp:670 +msgid "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." +msgstr "" + +#: modules/commands/os_session.cpp:551 +msgid "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." +msgstr "" + +#: modules/commands/os_session.cpp:270 +#, fuzzy +msgid "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." +msgstr "" +"Sintaxe: SESSION LIST número\n" +" SESSION VIEW host\n" +"\n" +"Permite que os Administradores dos Services vejam a lista de\n" +"conexões.\n" +"\n" +"SESSION LIST lista máscaras de hosts com pelo menos \n" +"número conexões permitidas.\n" +"O limite deve ser um número maior que 1. Isto deve prevenir \n" +"a listagem de muitos hosts com um limite de conexões \n" +"limitado a 1.\n" +"SESSION VIEW mostra informações detalhadas sobre um host\n" +"específico, incluindo o número de conexões atual e o limite\n" +"A máscara dada em host não deve incluir wildcards.\n" +"\n" +"Veja a ajuda sobre EXCEPTION para mais informações sobre\n" +"o limite de conexões e como especificar limites de conexões\n" +"para certos hosts e grupos de hosts." + +#: modules/commands/cs_topic.cpp:193 +msgid "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do " +"not have\n" +"the TOPIC privilege." +msgstr "" + +#: modules/commands/os_kick.cpp:62 +#, fuzzy, c-format +msgid "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" +msgstr "" +"Sintaxe: KICK canal usuário motivo\n" +"\n" +"Permite IRCops kickar um usuário de um canal.\n" +"Os parâmetros são os mesmos do comando /KICK padrão.\n" +"A mensagem do kick tem o nick do IRCop que enviou o\n" +"comando KICK, por exemplo:\n" +"\n" +"*** Spam foi kickado do canal #canal pelo %s (Operador (Flood))" + +#: modules/commands/cs_set.cpp:33 +#, fuzzy +msgid "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" +msgstr "" +"Sintaxe: SET canal opção parâmetros\n" +"\n" +"Permite ao fundador do canal ajustar as várias opções do\n" +"canal e outras informações.\n" +"\n" +"Opções disponíveis:" + +#: modules/commands/os_oper.cpp:250 +msgid "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." +msgstr "" + +#: modules/commands/os_config.cpp:127 +msgid "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" +msgstr "" + +#: modules/commands/ns_set.cpp:992 +#, fuzzy +msgid "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." +msgstr "" +"Syntax: SASET nickname MSG {ON | OFF}\n" +"\n" +"Allows you to choose the way Services are communicating with \n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." + +#: modules/commands/ns_set.cpp:966 +#, fuzzy, c-format +msgid "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." +msgstr "" +"Sintaxe: SET MSG {ON | OFF}\n" +"\n" +"Permite que você escolha a forma que os Services devem se \n" +"comunicar com você. Com MSG acionado, os Services irão usar\n" +"mensagems, caso contrário, usarão notices. " + +#: modules/commands/ms_ignore.cpp:113 +msgid "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." +msgstr "" + +#: modules/commands/os_kill.cpp:48 +msgid "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." +msgstr "" + +#: modules/commands/ns_info.cpp:252 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Syntax: SASET nickname HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}\n" +"\n" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." + +#: modules/commands/ns_info.cpp:223 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Sintaxe: SET HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}\n" +"\n" +"Permite que você previna que certas informações sejam\n" +"mostradas quando alguém usa %s INFO no seu nick. Você pode\n" +"esconder seu endereço de e-mail (EMAIL), última máscara vista\n" +"user@host (USERMASK), seu status de acesso aos Services\n" +"(STATUS) e sua última mensagem de saída (QUIT).\n" +"O segundo parâmetro especifica quando a informação deve ser\n" +"mostrada (OFF) ou escondida (ON)." + +#: modules/commands/bs_info.cpp:118 +#, fuzzy, c-format +msgid "Allows you to see %s information about a channel or a bot" +msgstr "" +" INFO Permite que você veja informações do BotServ sobre um " +"canal ou bot" + +#: modules/commands/bs_info.cpp:108 +#, fuzzy, c-format +msgid "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." +msgstr "" +"Sintaxe: INFO {canal | nick}\n" +"\n" +"Permite que você veja informações do %s sobre um\n" +"canal ou bot. Se a opção for um canal, então você terá\n" +"informações tais como kickers ativos. Se tiver sido um nick,\n" +"você terá informações sobre o bot, como o horário de criação\n" +"ou número de canais onde ele está." + +#: modules/commands/cs_xop.cpp:567 +msgid "" +"Alternative methods of modifying channel access lists are\n" +"available. " +msgstr "" + +#: modules/commands/hs_request.cpp:191 +#, fuzzy +msgid "Approve the requested vHost of a user" +msgstr " DEL Deleta o vHost de outro usuário" + +#: modules/commands/ns_drop.cpp:68 +#, fuzzy +msgid "As a Services Operator, you may drop any nick." +msgstr "%s is a services operator of type %s." + +#: modules/commands/bs_assign.cpp:19 +#, fuzzy +msgid "Assigns a bot to a channel" +msgstr " ASSIGN Associa um bot ao canal" + +#: modules/commands/bs_assign.cpp:78 +#, fuzzy +msgid "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." +msgstr "" +"Sintaxe: ASSIGN canal nick\n" +"\n" +"Associa um bot escolhido pelo nick a um canal.\n" +"Você poderá então configurar o bot para o canal de acordo\n" +"com as suas necessidades." + +#: data/chanserv.example.conf:1197 +#, fuzzy +msgid "Associate a URL with the channel" +msgstr " ASSIGN Associa um bot ao canal" + +#: data/nickserv.example.conf:594 +msgid "Associate a URL with this account" +msgstr "" + +#: data/nickserv.example.conf:593 +#, fuzzy +msgid "Associate a URL with your account" +msgstr " GREET Associa uma mensgem de entrada ao seu nick" + +#: modules/commands/greet.cpp:83 +#, fuzzy +msgid "Associate a greet message with your nickname" +msgstr " GREET Associa uma mensgem de entrada ao seu nick" + +#: data/chanserv.example.conf:1198 +#, fuzzy +msgid "Associate an E-mail address with the channel" +msgstr " EMAIL Associa um endereço de e-mail ao seu nick" + +#: modules/commands/ns_set.cpp:452 +#, fuzzy +msgid "Associate an E-mail address with your nickname" +msgstr " EMAIL Associa um endereço de e-mail ao seu nick" + +#: modules/commands/os_info.cpp:101 +#, fuzzy +msgid "Associate oper info with a nick or channel" +msgstr " ASSIGN Associa um bot ao canal" + +#: modules/commands/ns_set.cpp:558 +#, fuzzy +msgid "Associates the given E-mail address with the nickname." +msgstr " EMAIL Associa um endereço de e-mail ao seu nick" + +#: modules/commands/ns_set.cpp:533 +#, fuzzy +msgid "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." +msgstr "" +"Sintaxe: SET EMAIL endereço\n" +"\n" +"Associa um endereço de email designado ao seu nick. Este\n" +"endereço será sempre mostrado quando alguém solicitar\n" +"informação sobre seu nick atraves do comando INFO.\n" +"O email especificado também é usado para enviar sua senha\n" +"caso seja perdida. Caso não tenha nenhum endereço para seu\n" +"nick ou o mesmo seje inválido, não será possível recuperar\n" +"a senha perdida." + +#: modules/commands/ns_set.cpp:1315 +msgid "Auto-op" +msgstr "Auto-op" + +#: modules/commands/cs_akick.cpp:374 +#, c-format +msgid "Autokick list for %s:" +msgstr "Lista de akick para %s:" + +#: src/access.cpp:29 +msgid "Automatic channel operator status upon join" +msgstr "" + +#: src/access.cpp:28 +msgid "Automatic halfop upon join" +msgstr "" + +#: src/access.cpp:30 +msgid "Automatic owner upon join" +msgstr "" + +#: src/access.cpp:31 +msgid "Automatic protect upon join" +msgstr "" + +#: src/access.cpp:32 +msgid "Automatic voice on join" +msgstr "" + +#: modules/commands/os_oper.cpp:196 +#, fuzzy, c-format +msgid "Available commands for %s:" +msgstr "Nenhuma ajuda disponível para %s." + +#: modules/commands/os_oper.cpp:175 +#, fuzzy +msgid "Available opertypes:" +msgstr "Nenhuma ajuda disponível para %s." + +#: modules/commands/os_oper.cpp:218 +#, c-format +msgid "Available privileges for %s:" +msgstr "" + +#: modules/commands/cs_enforce.cpp:162 +msgid "BANS enforced by " +msgstr "" + +#: modules/commands/bs_kick.cpp:1121 modules/commands/bs_kick.cpp:1123 +#: modules/commands/bs_kick.cpp:1126 +#, fuzzy +msgid "Bad words kicker" +msgstr " Kick por palavrão: %s" + +#: modules/commands/bs_badwords.cpp:252 +#, fuzzy, c-format +msgid "Bad words list for %s:" +msgstr "Lista de acesso para %s:" + +#: modules/commands/bs_badwords.cpp:364 +msgid "Bad words list is now empty." +msgstr "Lista de palavrões está agora vazia." + +#: modules/commands/bs_set.cpp:129 +msgid "Ban expiry may not be longer than 1 day." +msgstr "" + +#: modules/commands/cs_ban.cpp:140 modules/commands/cs_ban.cpp:175 +#, fuzzy, c-format +msgid "Ban on %s expires in %s." +msgstr "Bot %s já existe." + +#: modules/commands/cs_info.cpp:60 +msgid "Ban type" +msgstr "" + +#: modules/commands/cs_set.cpp:174 +#, c-format +msgid "Ban type for channel %s is now #%d." +msgstr "Tipo de ban para o canal %s é agora #%d." + +#: modules/commands/cs_ban.cpp:39 +#, fuzzy +msgid "Bans a given nick or mask on a channel" +msgstr " BAN Bane o nick selecionado em um canal" + +#: modules/commands/cs_ban.cpp:227 +#, fuzzy +msgid "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." +msgstr "" +"Sintaxe: BAN #canal nick [motivo]\n" +"\n" +"Bane o nick selecionado em um canal.\n" +"\n" +"Por padrão, limitado a AOPs ou àqueles com nível de acesso 5 ou\n" +"superior no canal." + +#: modules/commands/cs_enforce.cpp:166 +#, fuzzy, c-format +msgid "Bans enforced on %s." +msgstr "%s não é notificado de novos memos." + +#: modules/commands/bs_kick.cpp:1131 modules/commands/bs_kick.cpp:1133 +#: modules/commands/bs_kick.cpp:1136 +#, fuzzy +msgid "Bolds kicker" +msgstr " Kick por negrito: %s" + +#: modules/commands/bs_bot.cpp:26 modules/commands/bs_bot.cpp:175 +#, c-format +msgid "Bot %s already exists." +msgstr "Bot %s já existe." + +#: include/language.h:119 +#, fuzzy, c-format +msgid "Bot %s does not exist." +msgstr "Bot %s já existe." + +#: modules/commands/bs_assign.cpp:71 modules/commands/bs_assign.cpp:246 +#, c-format +msgid "Bot %s has been assigned to %s." +msgstr "Bot %s foi associado ao canal %s." + +#: modules/commands/bs_bot.cpp:228 +#, fuzzy, c-format +msgid "Bot %s has been changed to %s!%s@%s (%s)." +msgstr "Bot %s foi alterado para %s!%s@%s (%s)" + +#: modules/commands/bs_bot.cpp:262 +#, c-format +msgid "Bot %s has been deleted." +msgstr "Bot %s foi removido." + +#: modules/commands/bs_assign.cpp:63 modules/commands/bs_assign.cpp:241 +#, c-format +msgid "Bot %s is already assigned to channel %s." +msgstr "Bot %s já está associado ao canal %s." + +#: modules/commands/bs_kick.cpp:832 +#, c-format +msgid "Bot will kick ops on channel %s." +msgstr "Bot irá kickar OPs no canal %s." + +#: modules/commands/bs_kick.cpp:897 +#, c-format +msgid "Bot will kick voices on channel %s." +msgstr "Bot irá kickar voices no canal %s." + +#: modules/commands/bs_kick.cpp:824 +#, c-format +msgid "Bot won't kick ops on channel %s." +msgstr "Bot não irá kickar OPs no canal %s." + +#: modules/commands/bs_kick.cpp:889 +#, c-format +msgid "Bot won't kick voices on channel %s." +msgstr "Bot não irá kickar voices no canal %s." + +#: modules/commands/bs_bot.cpp:118 +#, fuzzy, c-format +msgid "Bot %s is not changeable." +msgstr "Modo NOBOT está agora ATIVADO no canal %s." + +#: modules/commands/bs_bot.cpp:254 +#, fuzzy, c-format +msgid "Bot %s is not deletable." +msgstr "Bot %s foi removido." + +#: modules/commands/bs_set.cpp:141 +#, c-format +msgid "Bot bans will automatically expire after %s." +msgstr "" + +#: modules/commands/bs_set.cpp:139 +#, fuzzy +msgid "Bot bans will no longer automatically expire." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/bs_bot.cpp:46 modules/commands/bs_bot.cpp:138 +#, fuzzy, c-format +msgid "Bot hosts may only be %d characters long." +msgstr "Bot Hosts may only contain %d characters." + +#: modules/commands/bs_bot.cpp:64 modules/commands/bs_bot.cpp:167 +#, fuzzy +msgid "Bot hosts may only contain valid host characters." +msgstr "O Host do bot deve conter apenas caracteres válidos a Hosts." + +#: modules/commands/bs_bot.cpp:40 modules/commands/bs_bot.cpp:132 +#, fuzzy, c-format +msgid "Bot idents may only be %d characters long." +msgstr "Bot Idents may only contain %d characters." + +#: modules/commands/bs_bot.cpp:58 modules/commands/bs_bot.cpp:161 +#, fuzzy +msgid "Bot idents may only contain valid ident characters." +msgstr "A Identd do bot deve conter apenas caracteres válidos." + +#: include/language.h:121 +#, fuzzy, c-format +msgid "Bot is not on channel %s." +msgstr "Bot irá kickar OPs no canal %s." + +#: modules/commands/bs_botlist.cpp:51 +msgid "Bot list:" +msgstr "Lista de bots:" + +#: modules/commands/bs_info.cpp:87 +msgid "Bot nick" +msgstr "" + +#: modules/commands/bs_bot.cpp:34 modules/commands/bs_bot.cpp:126 +#, fuzzy, c-format +msgid "Bot nicks may only be %d characters long." +msgstr "Bot Idents may only contain %d characters." + +#: modules/commands/bs_bot.cpp:52 modules/commands/bs_bot.cpp:155 +#, fuzzy +msgid "Bot nicks may only contain valid nick characters." +msgstr "O Nick do bot deve conter apenas caracteres válidos a Nicks." + +#: modules/commands/bs_kick.cpp:225 +#, fuzzy, c-format +msgid "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." +msgstr "" +"Bot will now kick italics, and will place a ban after %d\n" +"kicks for the same user." + +#: modules/commands/bs_kick.cpp:228 +#, fuzzy, c-format +msgid "Bot will now kick for %s." +msgstr "O bot irá agora kickar por negritos." + +#: modules/commands/bs_kick.cpp:416 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." +msgstr "" +"O bot irá agora kickar por caps (deve ter no mínimo\n" +"%d caracteres e %d%% na mensagem inteira), e irá setar\n" +"um ban após %d kicks no mesmo usuário." + +#: modules/commands/bs_kick.cpp:420 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." +msgstr "" +"O bot irá agora kickar por caps (deve ter no mínimo\n" +"%d caracteres e %d%% na mensagem inteira)." + +#: modules/commands/bs_kick.cpp:551 +#, fuzzy, c-format +msgid "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." +msgstr "" +"O bot irá agora kickar por flood (%d linhas em %d segundos), e \n" +"setar um ban após %d kicks no mesmo usuário." + +#: modules/commands/bs_kick.cpp:554 +#, fuzzy, c-format +msgid "Bot will now kick for flood (%d lines in %d seconds)." +msgstr "O bot irá agora kickar por flood (%d linhas em %d segundos)." + +#: modules/commands/bs_kick.cpp:677 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"O bot irá agora kickar por repetição (usuários que escreverem\n" +"%d vezes a mesma coisa), e irá setar um ban após %d \n" +"kicks no mesmo usuário." + +#: modules/commands/bs_kick.cpp:687 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." +msgstr "" +"O bot irá agora kickar por repetição (usuários que escreverem\n" +"%d vezes a mesma coisa)." + +#: modules/commands/bs_kick.cpp:673 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"O bot irá agora kickar por repetição (usuários que escreverem\n" +"%d vezes a mesma coisa), e irá setar um ban após %d \n" +"kicks no mesmo usuário." + +#: modules/commands/bs_kick.cpp:684 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." +msgstr "" +"O bot irá agora kickar por repetição (usuários que escreverem\n" +"%d vezes a mesma coisa)." + +#: modules/commands/bs_kick.cpp:239 +#, fuzzy, c-format +msgid "Bot won't kick for %s anymore." +msgstr "O bot não irá mais kickar por caps." + +#: modules/commands/bs_kick.cpp:426 +#, fuzzy +msgid "Bot won't kick for caps anymore." +msgstr "O bot não irá mais kickar por caps." + +#: modules/commands/bs_kick.cpp:559 +#, fuzzy +msgid "Bot won't kick for flood anymore." +msgstr "O bot não irá mais kickar por flood." + +#: modules/commands/bs_kick.cpp:694 +#, fuzzy +msgid "Bot won't kick for repeats anymore." +msgstr "O bot não irá mais kickar por repetição." + +#: modules/commands/cs_access.cpp:472 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_session.cpp:514 +msgid "By" +msgstr "" + +#: modules/commands/os_info.cpp:104 +msgid "CLEAR target" +msgstr "" + +#: modules/commands/cs_seen.cpp:119 +msgid "CLEAR time" +msgstr "" + +#: modules/commands/ms_cancel.cpp:19 +#, fuzzy +msgid "Cancel the last memo you sent" +msgstr " CANCEL Cancela o último memo enviado por você" + +#: modules/commands/cs_drop.cpp:19 +#, fuzzy +msgid "Cancel the registration of a channel" +msgstr " DROP Cancela o registro de um canal" + +#: modules/commands/ns_drop.cpp:20 +#, fuzzy +msgid "Cancel the registration of a nickname" +msgstr " DROP Cancela o registro de um nick" + +#: modules/commands/ms_cancel.cpp:84 +#, fuzzy +msgid "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." +msgstr "" +"Sintaxe: CANCEL {nick | canal}\n" +"\n" +"Cancela a última mensagem enviada para um determinado nick ou\n" +"canal, caso ela ainda não tenha sido lida no momento em que este\n" +"comando for usado." + +#: modules/commands/cs_clone.cpp:149 +#, fuzzy, c-format +msgid "Cannot clone channel %s to itself!" +msgstr "Bot irá kickar OPs no canal %s." + +#: modules/commands/ns_register.cpp:332 +msgid "Cannot send mail now; please retry a little later." +msgstr "Não foi possível enviar e-mail agora; tente novamente mais tarde." + +#: modules/commands/bs_kick.cpp:1141 modules/commands/bs_kick.cpp:1143 +#: modules/commands/bs_kick.cpp:1146 +#, fuzzy +msgid "Caps kicker" +msgstr " Kick por Caps: %s" + +#: modules/commands/os_shutdown.cpp:34 +#, fuzzy +msgid "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." +msgstr "" +"Sintaxe: QUIT\n" +"\n" +"Faz com que desligue os Services imediatamente; o banco de\n" +"dados não é salvo. Este comando não deve ser usado a menos\n" +"que haja um dano da cópia do banco de dados na memória e por\n" +"isso eles não devam ser salvos. Para desligar normalmente,\n" +"use o comando SHUTDOWN." + +#: modules/commands/os_reload.cpp:47 +#, fuzzy +msgid "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." +msgstr "" +"Sintaxe: RELOAD\n" +"\n" +"Faz com que os Services recarreguem seu arquivo de configuração. \n" +"Repare que, para algumas mudanças terem efeito, será necessário\n" +"que os Services sejam reiniciados." + +#: modules/commands/os_shutdown.cpp:62 +#, fuzzy +msgid "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." +msgstr "" +"Sintaxe: RESTART\n" +"\n" +"Salva o banco de dados dos Services e os reinicia.\n" +"(sai e roda imediatamente o executável)." + +#: modules/commands/os_shutdown.cpp:89 +#, fuzzy +msgid "Causes Services to save all databases and then shut down." +msgstr "" +"Sintaxe: SHUTDOWN\n" +"\n" +"Salva o banco de dados dos Services e os desliga." + +#: modules/commands/os_update.cpp:34 +#, fuzzy +msgid "" +"Causes Services to update all database files as soon as you\n" +"send the command." +msgstr "" +"Sintaxe: UPDATE\n" +"\n" +"Faz com que os Services atualizem o banco de dados logo que\n" +"você envia este comando." + +#: modules/commands/ns_cert.cpp:246 +#, fuzzy, c-format +msgid "Certificate list for %s:" +msgstr "Lista de acesso para %s:" + +#: modules/commands/cs_set.cpp:528 modules/commands/cs_set.cpp:570 +msgid "ChanServ is required to enable persist on this network." +msgstr "" + +#: modules/commands/os_mode.cpp:19 +#, fuzzy +msgid "Change channel modes" +msgstr "%s alterou seus modos de usuário." + +#: modules/commands/ns_set.cpp:905 +#, fuzzy +msgid "Change the communication method of Services" +msgstr " MSG Altera o método de comunicação dos Services" + +#: modules/commands/os_mode.cpp:146 +#, fuzzy +msgid "Change user modes" +msgstr "%s alterou seus modos de usuário." + +#: modules/commands/os_mode.cpp:161 +#, fuzzy, c-format +msgid "Changed usermodes of %s to %s." +msgstr "Modos do usuário %s alterados." + +#: modules/commands/ns_set.cpp:411 +#, fuzzy +msgid "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." +msgstr "" +"Sintaxe: SET DISPLAY novo-display\n" +"\n" +"Altera o display usado como referência ao nome do seu grupo \n" +"nos Services. O novo display DEVE ser um nick do seu grupo." + +#: modules/commands/ns_set.cpp:387 +#, fuzzy +msgid "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." +msgstr "" +"Sintaxe: SET DISPLAY novo-display\n" +"\n" +"Altera o display usado como referência ao nome do seu grupo \n" +"nos Services. O novo display DEVE ser um nick do seu grupo." + +#: modules/commands/cs_set.cpp:324 +#, fuzzy +msgid "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." +msgstr "" +"Sintaxe: %s canal FOUNDER nick\n" +"\n" +"Muda o fundador do canal. O novo nick deve estar\n" +"registrado." + +#: modules/commands/ns_set.cpp:884 +#, fuzzy +msgid "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Sintaxe: SET LANGUAGE número\n" +"\n" +"Muda a linguagem que os Services usam ao enviar mensagens\n" +"para você (por exemplo, quando responde um comando que você\n" +"emite). A linguagem Português, assim como outras, pode\n" +"apresentar algumas diferenças da linguagem Inglês (English),\n" +"já que Inglês é a linguagem oficial destes Services.\n" +"O número deve ser escolhido da seguinte lista de línguas:" + +#: modules/commands/ns_set.cpp:848 +#, fuzzy +msgid "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Sintaxe: SET LANGUAGE número\n" +"\n" +"Muda a linguagem que os Services usam ao enviar mensagens\n" +"para você (por exemplo, quando responde um comando que você\n" +"emite). A linguagem Português, assim como outras, pode\n" +"apresentar algumas diferenças da linguagem Inglês (English),\n" +"já que Inglês é a linguagem oficial destes Services.\n" +"O número deve ser escolhido da seguinte lista de línguas:" + +#: modules/commands/ns_set.cpp:227 +#, fuzzy +msgid "Changes the password used to identify as the nick's owner." +msgstr "" +"Sintaxe: SET PASSWORD nova-senha\n" +"\n" +"Muda a senha de seu nick." + +#: modules/commands/ns_set.cpp:161 +#, fuzzy +msgid "" +"Changes the password used to identify you as the nick's\n" +"owner." +msgstr "" +"Sintaxe: SET PASSWORD nova-senha\n" +"\n" +"Muda a senha de seu nick." + +#: modules/commands/cs_set.cpp:1017 +#, fuzzy +msgid "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." +msgstr "" +"Sintaxe: %s canal SUCCESSOR nick\n" +"\n" +"Altera o sucessor de um canal. Se o nick do founder expirar\n" +"ou for dropado enquanto o canal ainda estiver registrado,\n" +"o sucessor se tornará o novo founder do canal.\n" +"No entanto, se o sucessor possuir muitos canais registrados\n" +"(%d), o canal será dropado, como se nenhum sucessor tivesse\n" +"sido ajustado. O novo nick deverá estar registrado." + +#: modules/commands/ns_alist.cpp:48 modules/commands/ns_ajoin.cpp:100 +#, fuzzy +msgid "Channel" +msgstr "DROP canal" + +#: include/language.h:84 +#, fuzzy, c-format +msgid "Channel %s doesn't exist." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_drop.cpp:63 +#, c-format +msgid "Channel %s has been dropped." +msgstr "O canal %s foi desregistrado." + +#: modules/commands/cs_getkey.cpp:43 +#, fuzzy, c-format +msgid "Channel %s has no key." +msgstr "O canal %s não tem key." + +#: modules/commands/cs_register.cpp:47 +#, c-format +msgid "Channel %s is already registered!" +msgstr "O canal %s já está registrado!" + +#: modules/commands/os_forbid.cpp:524 +#, fuzzy, c-format +msgid "Channel %s is forbidden by %s: %s" +msgstr "Este canal foi registrado com o %s." + +#: modules/commands/os_forbid.cpp:526 +#, fuzzy, c-format +msgid "Channel %s is forbidden." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_set.cpp:580 +#, fuzzy, c-format +msgid "Channel %s is no longer persistent." +msgstr "Channel %s is no longer persistant." + +#: modules/commands/cs_set.cpp:542 +#, fuzzy, c-format +msgid "Channel %s is now persistent." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_suspend.cpp:180 +#, c-format +msgid "Channel %s is now released." +msgstr "Canal %s está agora liberado." + +#: modules/commands/cs_suspend.cpp:125 +#, c-format +msgid "Channel %s is now suspended." +msgstr "Canal %s está agora suspenso." + +#: include/language.h:83 +#, fuzzy, c-format +msgid "Channel %s isn't registered." +msgstr "O canal %s não pode ser registrado." + +#: modules/commands/cs_suspend.cpp:172 +#, fuzzy, c-format +msgid "Channel %s isn't suspended." +msgstr "Canal %s está agora suspenso." + +#: modules/commands/cs_register.cpp:68 +#, fuzzy, c-format +msgid "Channel %s registered under your account: %s" +msgstr "O nick %s foi registrado em sua conta: %s" + +#: modules/commands/cs_set.cpp:1078 +#, c-format +msgid "Channel %s will expire." +msgstr "O canal %s irá expirar." + +#: modules/commands/cs_set.cpp:1072 +#, c-format +msgid "Channel %s will not expire." +msgstr "O canal %s não irá expirar." + +#: modules/commands/cs_xop.cpp:475 +#, fuzzy, c-format +msgid "Channel %s %s list has been cleared." +msgstr "Lista de AOP do canal %s foi limpa." + +#: modules/commands/cs_access.cpp:486 modules/commands/cs_flags.cpp:361 +#, c-format +msgid "Channel %s access list has been cleared." +msgstr "Lista de acesso do canal %s apagada." + +#: modules/commands/cs_akick.cpp:428 +#, c-format +msgid "Channel %s akick list has been cleared." +msgstr "Lista de akick do canal %s foi limpa." + +#: modules/commands/cs_mode.cpp:444 +#, fuzzy, c-format +msgid "Channel %s has no mode locks." +msgstr "Canal %s está agora liberado." + +#: include/language.h:82 +#, fuzzy, c-format +msgid "Channel %s is currently suspended." +msgstr "Canal %s está agora suspenso." + +#: include/language.h:101 +#, fuzzy, c-format +msgid "Channel %s is not a valid channel." +msgstr "%s não é um ban válido." + +#: modules/commands/os_list.cpp:70 +#, fuzzy +msgid "Channel list:" +msgstr "Lista de bots:" + +#: modules/extra/stats/cs_fantasy_stats.cpp:148 +#, fuzzy, c-format +msgid "Channel stats for %s on %s:" +msgstr "" +"Canais nos quais %s tem acesso:\n" +" Núm Canal Nível Descrição " + +#: modules/commands/cs_access.cpp:142 modules/commands/cs_flags.cpp:97 +#: modules/commands/cs_xop.cpp:139 +#, fuzzy +msgid "Channels may not be on access lists." +msgstr "%s não foi encontrado na lista de acesso do %s." + +#: modules/commands/ns_alist.cpp:114 +#, fuzzy, c-format +msgid "Channels that %s has access on:" +msgstr "" +"Canais nos quais %s tem acesso:\n" +" Núm Canal Nível Descrição " + +#: modules/commands/os_stats.cpp:181 +#, c-format +msgid "Channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:517 +#: modules/extra/stats/m_chanstats.cpp:525 +msgid "Chanstats" +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:102 +#, fuzzy, c-format +msgid "Chanstats statistics are now disabled for %s" +msgstr " SECURE Ativa/Desativa os recursos de segurança para o seu nick" + +#: modules/extra/stats/m_chanstats.cpp:51 +msgid "Chanstats statistics are now disabled for this channel." +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:104 +#, fuzzy +msgid "Chanstats statistics are now disabled for your nick." +msgstr " SECURE Ativa/Desativa os recursos de segurança para o seu nick" + +#: modules/extra/stats/m_chanstats.cpp:93 +#, fuzzy, c-format +msgid "Chanstats statistics are now enabled for %s" +msgstr " SECURE Ativa/Desativa os recursos de segurança para o seu nick" + +#: modules/extra/stats/m_chanstats.cpp:44 +msgid "Chanstats statistics are now enabled for this channel." +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:95 +#, fuzzy +msgid "Chanstats statistics are now enabled for your nick." +msgstr " SECURE Ativa/Desativa os recursos de segurança para o seu nick" + +#: modules/commands/cs_seen.cpp:367 +msgid "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." +msgstr "" + +#: modules/commands/ms_check.cpp:19 +#, fuzzy +msgid "Checks if last memo to a nick was read" +msgstr " CHECK Verifica se o último memo enviado para um nick foi lido" + +#: modules/commands/ms_check.cpp:69 +#, fuzzy +msgid "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." +msgstr "" +"Sintaxe: CHECK nick\n" +"\n" +"Verifica se o último memo que você enviou para nick\n" +"foi lido ou não. Observe que isso só funciona com nicks,\n" +"nunca com canais." + +#: modules/commands/os_info.cpp:227 +#, c-format +msgid "Cleared info from %s." +msgstr "" + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1153 +#: modules/commands/bs_kick.cpp:1156 +#, fuzzy +msgid "Colors kicker" +msgstr " KICK Configura os kickers" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Command" +msgstr "Comandos do %s:" + +#: modules/commands/bs_kick.cpp:251 +#, fuzzy +msgid "Configures AMSG kicker" +msgstr " KICK Configura os kickers" + +#: modules/commands/bs_kick.cpp:287 +#, fuzzy +msgid "Configures badwords kicker" +msgstr " KICK Configura os kickers" + +#: modules/commands/bs_kick.cpp:326 +#, fuzzy +msgid "Configures bolds kicker" +msgstr " KICK Configura os kickers" + +#: modules/commands/bs_kick.cpp:132 +#, fuzzy +msgid "Configures bot kickers. option can be one of:" +msgstr "" +"Sintaxe: SET opção parâmetros\n" +"\n" +"Ajusta várias opções de nick. A opção pode ser:" + +#: modules/commands/bs_set.cpp:19 +#, fuzzy +msgid "Configures bot options" +msgstr " SET Configura as opções do bot" + +#: modules/commands/bs_set.cpp:32 +#, fuzzy +msgid "" +"Configures bot options.\n" +" \n" +"Available options:" +msgstr " SET Configura as opções do bot" + +#: modules/commands/bs_kick.cpp:360 +#, fuzzy +msgid "Configures caps kicker" +msgstr " KICK Configura os kickers" + +#: modules/commands/cs_log.cpp:105 +#, fuzzy +msgid "Configures channel logging settings" +msgstr "* Impedido o registro de novos canais" + +#: modules/commands/bs_kick.cpp:456 +#, fuzzy +msgid "Configures color kicker" +msgstr " KICK Configura os kickers" + +#: modules/commands/bs_kick.cpp:490 +#, fuzzy +msgid "Configures flood kicker" +msgstr " KICK Configura os kickers" + +#: modules/commands/bs_kick.cpp:588 +#, fuzzy +msgid "Configures italics kicker" +msgstr " KICK Configura os kickers" + +#: modules/commands/bs_kick.cpp:119 +#, fuzzy +msgid "Configures kickers" +msgstr " KICK Configura os kickers" + +#: modules/commands/bs_kick.cpp:622 +#, fuzzy +msgid "Configures repeat kicker" +msgstr " KICK Configura os kickers" + +#: modules/commands/bs_kick.cpp:723 +#, fuzzy +msgid "Configures reverses kicker" +msgstr " KICK Configura os kickers" + +#: modules/commands/bs_set.cpp:90 +#, fuzzy +msgid "Configures the time bot bans expire in" +msgstr " SET Configura as opções do bot" + +#: modules/commands/bs_kick.cpp:757 +#, fuzzy +msgid "Configures underlines kicker" +msgstr " KICK Configura os kickers" + +#: modules/commands/ns_register.cpp:21 +#, fuzzy +msgid "Confirm a passcode" +msgstr " CONFIRM Confirma um código de autorização do NickServ" + +#: modules/commands/cs_mode.cpp:733 +#, fuzzy +msgid "Control modes and mode locks on a channel" +msgstr " CLEARMODES Limpa os modos de um canal" + +#: modules/commands/cs_entrymsg.cpp:239 +msgid "" +"Controls what messages will be sent to users when they join the channel." +msgstr "" + +#: modules/commands/cs_clone.cpp:242 +msgid "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." +msgstr "" + +#: modules/commands/cs_clone.cpp:114 +#, fuzzy +msgid "Copy all settings from one channel to another" +msgstr "" +" UNBAN Remove all bans preventing a user from entering a channel" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/bs_info.cpp:57 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Created" +msgstr " Criado: %s" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_ignore.cpp:266 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_news.cpp:156 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Creator" +msgstr " Criado: %s" + +#: modules/commands/os_sxline.cpp:180 +#, fuzzy, c-format +msgid "Current %s list:" +msgstr "Lista de AKILL atual:" + +#: modules/commands/os_akill.cpp:323 +#, fuzzy +msgid "Current AKILL list:" +msgstr "Lista de AKILL atual:" + +#: modules/commands/os_session.cpp:493 +msgid "Current Session Limit Exception list:" +msgstr "Atual lista de Limite de sessões:" + +#: modules/commands/os_modinfo.cpp:116 +#, fuzzy +msgid "Current module list:" +msgstr "Lista de Módulos atual:" + +#: modules/commands/os_stats.cpp:69 +#, c-format +msgid "Current number of AKILLs: %d" +msgstr "Número atual de AKILLs: %d" + +#: modules/commands/os_stats.cpp:89 +#, c-format +msgid "Current number of SNLINEs: %d" +msgstr "Número atual de SNLINEs: %d" + +#: modules/commands/os_stats.cpp:109 +#, c-format +msgid "Current number of SQLINEs: %d" +msgstr "Número atual de SQLINEs: %d" + +#: modules/commands/os_stats.cpp:138 +#, c-format +msgid "Current users: %d (%d ops)" +msgstr "Usuários atuais: %d (%d ops)" + +#: modules/commands/os_oper.cpp:71 +#, fuzzy +msgid "DEL oper" +msgstr "DEL ." + +#: modules/commands/os_info.cpp:103 +#, fuzzy +msgid "DEL target info" +msgstr "GROUP alvo senha" + +#: modules/commands/ns_ajoin.cpp:232 +#, fuzzy +msgid "DEL [nickname] channel" +msgstr "MODE canal modos" + +#: modules/commands/ns_cert.cpp:259 +#, fuzzy +msgid "DEL [nickname] fingerprint" +msgstr "FORBID nick motivo" + +#: modules/commands/ns_access.cpp:103 +#, fuzzy +msgid "DEL [nickname] mask" +msgstr "MODE canal modos" + +#: modules/commands/os_sxline.cpp:426 modules/commands/os_sxline.cpp:660 +#: modules/commands/os_akill.cpp:387 +#, fuzzy +msgid "DEL {mask | entry-num | list | id}" +msgstr "DEL [canal] {núm | list | ALL}" + +#: modules/commands/os_session.cpp:524 +#, fuzzy +msgid "DEL {mask | entry-num | list}" +msgstr "DEL [canal] {núm | list | ALL}" + +#: modules/commands/os_ignore.cpp:343 +#, fuzzy +msgid "DEL {nick|mask}" +msgstr "DEL ." + +#: modules/commands/os_news.cpp:279 +#, fuzzy +msgid "DEL {num | ALL}" +msgstr "OPERNEWS DEL {núm | ALL}" + +#: modules/commands/os_forbid.cpp:158 +msgid "DEL {NICK|CHAN|EMAIL|REGISTER} entry" +msgstr "" + +#: modules/commands/os_dns.cpp:666 +msgid "DELIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:664 +msgid "DELSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:662 +msgid "DELZONE zone.name" +msgstr "" + +#: modules/commands/os_dns.cpp:669 +#, fuzzy +msgid "DEPOOL server.name" +msgstr "NOOP {SET|REVOKE} servidor" + +#: modules/commands/cs_seen.cpp:162 +#, c-format +msgid "Database cleared, removed %lu nicks that were added after %s." +msgstr "" + +#: modules/commands/ms_list.cpp:64 +msgid "Date/Time" +msgstr "" + +#: modules/commands/hs_off.cpp:49 +#, fuzzy +msgid "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." +msgstr "" +"Sintaxe: OFF\n" +"Desativa o vhost atualmente associado ao nick em uso.\n" +"Quando você usa este comando, qualquer usuário que faça um /whois\n" +"em você irá ver seu endereço IP real/encriptado." + +#: modules/commands/hs_off.cpp:19 +#, fuzzy +msgid "Deactivates your assigned vhost" +msgstr " OFF Desativa seu vHost associado" + +#: modules/commands/os_stats.cpp:72 +#, c-format +msgid "Default AKILL expiry time: %d days" +msgstr "Tempo atual de expiração de akill: %d dias" + +#: modules/commands/os_stats.cpp:76 +#, c-format +msgid "Default AKILL expiry time: %d hours" +msgstr "Tempo atual de expiração de akill: %d horas" + +#: modules/commands/os_stats.cpp:80 +#, c-format +msgid "Default AKILL expiry time: %d minutes" +msgstr "Tempo atual de expiração de akill: %d minutos" + +#: modules/commands/os_stats.cpp:74 +msgid "Default AKILL expiry time: 1 day" +msgstr "Tempo atual de expiração de akill: 1 dia" + +#: modules/commands/os_stats.cpp:78 +msgid "Default AKILL expiry time: 1 hour" +msgstr "Tempo atual de expiração de akill: 1 hora" + +#: modules/commands/os_stats.cpp:82 +msgid "Default AKILL expiry time: 1 minute" +msgstr "Tempo atual de expiração de akill: 1 minuto" + +#: modules/commands/os_stats.cpp:84 +msgid "Default AKILL expiry time: No expiration" +msgstr "Tempo atual de expiração de akill: Não expira" + +#: modules/commands/os_stats.cpp:92 +#, c-format +msgid "Default SNLINE expiry time: %d days" +msgstr "Tempo atual de expiração de SNLINE: %d dias" + +#: modules/commands/os_stats.cpp:96 +#, c-format +msgid "Default SNLINE expiry time: %d hours" +msgstr "Tempo atual de expiração de SNLINE: %d horas" + +#: modules/commands/os_stats.cpp:100 +#, c-format +msgid "Default SNLINE expiry time: %d minutes" +msgstr "Tempo atual de expiração de SNLINE: %d minutos" + +#: modules/commands/os_stats.cpp:94 +msgid "Default SNLINE expiry time: 1 day" +msgstr "Tempo atual de expiração de SNLINE: 1 dia" + +#: modules/commands/os_stats.cpp:98 +msgid "Default SNLINE expiry time: 1 hour" +msgstr "Tempo atual de expiração de SNLINE: 1 hora" + +#: modules/commands/os_stats.cpp:102 +msgid "Default SNLINE expiry time: 1 minute" +msgstr "Tempo atual de expiração de SNLINE: 1 minuto" + +#: modules/commands/os_stats.cpp:104 +msgid "Default SNLINE expiry time: No expiration" +msgstr "Tempo atual de expiração de SNLINE: Não expira" + +#: modules/commands/os_stats.cpp:112 +#, c-format +msgid "Default SQLINE expiry time: %d days" +msgstr "Tempo atual de expiração de SQLINE: %d dias" + +#: modules/commands/os_stats.cpp:116 +#, c-format +msgid "Default SQLINE expiry time: %d hours" +msgstr "Tempo atual de expiração de SQLINE: %d horas" + +#: modules/commands/os_stats.cpp:120 +#, c-format +msgid "Default SQLINE expiry time: %d minutes" +msgstr "Tempo atual de expiração de SQLINE: %d minutos" + +#: modules/commands/os_stats.cpp:114 +msgid "Default SQLINE expiry time: 1 day" +msgstr "Tempo atual de expiração de SQLINE: 1 dia" + +#: modules/commands/os_stats.cpp:118 +msgid "Default SQLINE expiry time: 1 hour" +msgstr "Tempo atual de expiração de SQLINE: 1 hora" + +#: modules/commands/os_stats.cpp:122 +msgid "Default SQLINE expiry time: 1 minute" +msgstr "Tempo atual de expiração de SQLINE: 1 minuto" + +#: modules/commands/os_stats.cpp:124 +msgid "Default SQLINE expiry time: No expiration" +msgstr "Tempo atual de expiração de SQLINE: Não expira" + +#: modules/commands/os_news.cpp:351 +#, fuzzy +msgid "Define messages to be randomly shown to users at logon" +msgstr " LOGONNEWS Define mensagens a serem mostradas na conexão" + +#: modules/commands/os_news.cpp:297 +#, fuzzy +msgid "Define messages to be shown to users at logon" +msgstr " LOGONNEWS Define mensagens a serem mostradas na conexão" + +#: modules/commands/os_news.cpp:324 +#, fuzzy +msgid "Define messages to be shown to users who oper" +msgstr " OPERNEWS Define mensagens a serem mostradas a quem pega Oper" + +#: modules/commands/ms_del.cpp:44 +#, fuzzy +msgid "Delete a memo or memos" +msgstr " DEL Apaga a(s) mensagem(ns)" + +#: modules/commands/hs_del.cpp:19 +#, fuzzy +msgid "Delete the vhost of another user" +msgstr " DEL Deleta o vHost de outro usuário" + +#: modules/commands/cs_xop.cpp:302 +#, fuzzy, c-format +msgid "Deleted %d entries from %s %s list." +msgstr "Deletadas %d entradas da lista de AOP do %s." + +#: modules/commands/cs_access.cpp:277 +#, c-format +msgid "Deleted %d entries from %s access list." +msgstr "Removidas %d entradas da lista de acesso do %s." + +#: modules/commands/cs_akick.cpp:228 +#, c-format +msgid "Deleted %d entries from %s autokick list." +msgstr "Removidas %d entradas da lista de akick do %s." + +#: modules/commands/bs_badwords.cpp:170 +#, c-format +msgid "Deleted %d entries from %s bad words list." +msgstr "Removidas %d entradas da lista de palavrões do %s." + +#: modules/commands/os_session.cpp:149 +#, c-format +msgid "Deleted %d entries from session-limit exception list." +msgstr "Removidas %d entradas da lista de limite de sessões." + +#: modules/commands/os_sxline.cpp:32 +#, fuzzy, c-format +msgid "Deleted %d entries from the %s list." +msgstr "Deletadas %d entradas da lista de AOP do %s." + +#: modules/commands/os_akill.cpp:33 +#, c-format +msgid "Deleted %d entries from the AKILL list." +msgstr "Removidas %d entradas da lista de AKILL." + +#: modules/commands/cs_access.cpp:275 +#, c-format +msgid "Deleted 1 entry from %s access list." +msgstr "Removida 1 entrada da lista de acesso do %s." + +#: modules/commands/cs_akick.cpp:226 +#, c-format +msgid "Deleted 1 entry from %s autokick list." +msgstr "Removida 1 entrada da lista de akick do %s." + +#: modules/commands/bs_badwords.cpp:168 +#, c-format +msgid "Deleted 1 entry from %s bad words list." +msgstr "Removida 1 entrada da lista de palavrões do %s." + +#: modules/commands/os_session.cpp:147 +msgid "Deleted 1 entry from session-limit exception list." +msgstr "Removida 1 entrada da lista de limite de sessões." + +#: modules/commands/os_sxline.cpp:30 +#, fuzzy, c-format +msgid "Deleted 1 entry from the %s list." +msgstr "Removida 1 entrada da lista de AKILL." + +#: modules/commands/os_akill.cpp:31 +msgid "Deleted 1 entry from the AKILL list." +msgstr "Removida 1 entrada da lista de AKILL." + +#: modules/commands/os_info.cpp:208 +#, fuzzy, c-format +msgid "Deleted info from %s." +msgstr "Removida 1 entrada da lista de AKILL." + +#: modules/commands/cs_xop.cpp:300 +#, fuzzy, c-format +msgid "Deleted one entry from %s %s list." +msgstr "Deletada 1 entrada da lista de AOP do %s." + +#: modules/commands/ms_del.cpp:129 +#, fuzzy +msgid "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Sintaxe: DEL [canal] {num | list | LAST | ALL}\n" +"\n" +"Apaga a(s) mensagem(ns) especificada(s). Você pode fornecer\n" +"vários números de mensagens ou seqüências de números ao invés\n" +"de um único número, como no segundo exemplo abaixo.\n" +"Se LAST é fornecido, a última mensagem será apagada.\n" +"Se ALL é fornecido, todas as suas mensagens serão apagadas.\n" +"\n" +"Exemplos:\n" +"\n" +" DEL 1\n" +" Apaga sua primeira mensagem.\n" +"\n" +" DEL 2-5,7-9\n" +" Apaga mensagens numeradas de 2 a 5 e de 7 a 9." + +#: modules/commands/hs_del.cpp:48 +#, fuzzy +msgid "" +"Deletes the vhost assigned to the given nick from the\n" +"database." +msgstr "" +"Sintaxe: DEL \n" +"Deleta o vhost associado ao nick dado." + +#: modules/commands/hs_del.cpp:59 +#, fuzzy +msgid "Deletes the vhost for all nicks in a group" +msgstr " DELALL Deleta o vHost de todos os nicks de um grupo" + +#: modules/commands/hs_del.cpp:93 +#, fuzzy +msgid "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." +msgstr "" +"Sintaxe: DELALL .\n" +"Deleta o vhost para todos os nicks no mesmo grupo do\n" +"nick fornecido." + +#: modules/commands/os_dns.cpp:653 +#, c-format +msgid "Depooled %s." +msgstr "" + +#: modules/commands/cs_access.cpp:799 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_list.cpp:75 modules/commands/cs_info.cpp:53 +#, fuzzy +msgid "Description" +msgstr "Descrição do canal %s alterada para %s." + +#: modules/commands/cs_set.cpp:239 +#, c-format +msgid "Description of %s changed to %s." +msgstr "Descrição do canal %s alterada para %s." + +#: modules/commands/cs_set.cpp:245 +#, fuzzy, c-format +msgid "Description of %s unset." +msgstr "Descrição do canal %s alterada para %s." + +#: modules/commands/bs_kick.cpp:1115 modules/commands/bs_info.cpp:90 +#, fuzzy +msgid "Disabled" +msgstr "%s está ativada" + +#: modules/commands/cs_suspend.cpp:134 +#, fuzzy +msgid "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." +msgstr "" +"Sintaxe: SUSPEND canal [motivo]\n" +"\n" +"Proibe qualquer um de registrar ou usar o canal dado.\n" +"Pode ser cancelado usando o comando UNSUSPEND para\n" +"preservar todos os dados/configurações anteriores do canal.\n" +"\n" +"Um motivo pode ser necessário em algumas redes." + +#: modules/commands/hs_request.cpp:337 +#, fuzzy, c-format +msgid "Displayed %d records (%d total)." +msgstr "Exibidos todos os registros (Contador: %d)" + +#: modules/commands/hs_list.cpp:122 +#, fuzzy, c-format +msgid "Displayed all records (count: %d)." +msgstr "Exibidos todos os registros (Contador: %d)" + +#: modules/commands/hs_list.cpp:120 +#, fuzzy, c-format +msgid "Displayed records from %d to %d." +msgstr "Exibidos registros de %d até %d" + +#: modules/commands/hs_list.cpp:116 +#, fuzzy, c-format +msgid "Displayed records matching key %s (count: %d)." +msgstr "Exibidos registros coincidindo com a chave %s (Contador: %d)" + +#: modules/commands/ns_info.cpp:19 +#, fuzzy +msgid "Displays information about a given nickname" +msgstr " INFO Mostra informações sobre algum nick registrado" + +#: modules/commands/ns_info.cpp:125 +#, fuzzy +msgid "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." +msgstr "" +"Sintaxe: INFO nick\n" +"\n" +"Mostra a informação sobre o nick dado, como o dono do nick,\n" +"último endereço utilizado e horário, e opções. Se você está\n" +"identificado para o nick que você está obtendo informações\n" +"e a opção ALL é especificada, será mostrado a você toda\n" +"informação possível; independente de haver opções para esconder." + +#: modules/commands/ms_info.cpp:19 +#, fuzzy +msgid "Displays information about your memos" +msgstr " INFO Exibe informações sobre suas mensagens" + +#: modules/commands/hs_list.cpp:19 +#, fuzzy +msgid "Displays one or more vhost entries" +msgstr " LIST Exibe uma ou mais entradas de vHost" + +#: modules/extra/stats/cs_fantasy_top.cpp:50 +#, fuzzy +msgid "Displays the top 10 users of a channel" +msgstr " FOUNDER Ajusta o fundador do canal" + +#: modules/extra/stats/cs_fantasy_top.cpp:73 +msgid "Displays the top 10 users of the network" +msgstr "" + +#: modules/extra/stats/cs_fantasy_top.cpp:38 +#, fuzzy +msgid "Displays the top 3 users of a channel" +msgstr " FOUNDER Ajusta o fundador do canal" + +#: modules/extra/stats/cs_fantasy_top.cpp:62 +msgid "Displays the top 3 users of the network" +msgstr "" + +#: modules/commands/help.cpp:33 +#, fuzzy +msgid "Displays this list and give information about commands" +msgstr " INFO Exibe informações sobre suas mensagens" + +#: modules/extra/stats/cs_fantasy_stats.cpp:39 +msgid "Displays your Channel Stats" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:51 +msgid "Displays your Global Stats" +msgstr "" + +#: modules/commands/bs_kick.cpp:1463 +msgid "Don't use AMSGs!" +msgstr "" + +#: modules/commands/bs_kick.cpp:1266 +msgid "Don't use bolds on this channel!" +msgstr "Não use negritos neste canal!" + +#: modules/commands/bs_kick.cpp:1274 +msgid "Don't use colors on this channel!" +msgstr "Não use cores neste canal!" + +#: modules/commands/bs_kick.cpp:1290 +msgid "Don't use italics on this channel!" +msgstr "Don't use italics on this channel!" + +#: modules/commands/bs_kick.cpp:1282 +msgid "Don't use reverses on this channel!" +msgstr "Por favor não use reversos no canal!" + +#: modules/commands/bs_kick.cpp:1408 +#, c-format +msgid "Don't use the word \"%s\" on this channel!" +msgstr "Não use a palavra %s neste canal!" + +#: modules/commands/bs_kick.cpp:1298 +msgid "Don't use underlines on this channel!" +msgstr "Não use sublinhados neste canal!" + +#: modules/commands/ns_drop.cpp:61 +msgid "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." +msgstr "" + +#: modules/commands/ns_set.cpp:513 +#, c-format +msgid "E-mail address for %s changed to %s." +msgstr "E-mail address for %s changed to %s." + +#: modules/commands/ns_set.cpp:519 +#, c-format +msgid "E-mail address for %s unset." +msgstr "E-mail address for %s unset." + +#: src/mail.cpp:80 +#, c-format +msgid "E-mail for %s is invalid." +msgstr "E-mail para %s é inválido." + +#: modules/commands/os_news.cpp:309 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Syntax: LOGONNEWS ADD text\n" +" LOGONNEWS DEL {num | ALL}\n" +" LOGONNEWS LIST\n" +"\n" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. (However, no more than %s messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent.)\n" +"NewsCount can be configured in services.conf.\n" +"\n" +"LOGONNEWS may only be used by Services Operators." + +#: modules/commands/os_news.cpp:336 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Syntax: OPERNEWS ADD text\n" +" OPERNEWS DEL {num | ALL}\n" +" OPERNEWS LIST\n" +"\n" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. (However, no more than %s messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent.)\n" +"NewsCount can be configured in services.conf.\n" +"\n" +"OPERNEWS may only be used by Services Operators." + +#: modules/commands/os_news.cpp:363 +#, fuzzy +msgid "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." +msgstr "" +"Sintaxe: RANDOMNEWS ADD texto\n" +" RANDOMNEWS DEL {núm | ALL}\n" +" RANDOMNEWS LIST\n" +"\n" +"Edita ou mostra a lista de random news. Quando um usuário\n" +"se conecta à rede, uma (apenas uma) das random news será\n" +"aleatóriamente escolhida e enviada a ele.\n" +"\n" +"RANDOMNEWS may only be used by Services Operators." + +#: modules/commands/ns_info.cpp:98 +#, fuzzy +msgid "Email address" +msgstr " E-mail: %s" + +#: modules/commands/ns_getemail.cpp:41 +#, fuzzy, c-format +msgid "Email matched: %s (%s) to %s." +msgstr "O nick %s usa o E-mail %s." + +#: modules/fantasy.cpp:19 +msgid "Enable fantaisist commands" +msgstr "" + +#: modules/commands/greet.cpp:19 +msgid "Enable greet messages" +msgstr "" + +#: modules/commands/ns_set.cpp:568 +msgid "Enable or disable keep modes" +msgstr "" + +#: modules/commands/bs_kick.cpp:1114 modules/commands/bs_info.cpp:89 +#, fuzzy +msgid "Enabled" +msgstr "%s está ativada" + +#: modules/commands/cs_set.cpp:124 +#, fuzzy, c-format +msgid "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." +msgstr "" +"Sintaxe: %s canal SECUREOPS {ON|OFF}\n" +"\n" +"Ativa ou desativa a opção de segurança de ops para um canal.\n" +"Quando secure ops estiver ativada, os usuários que não\n" +"estiverem na lista de acesso não poderão ter o status de OP." + +#: modules/commands/cs_set.cpp:388 +#, fuzzy +msgid "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." +msgstr "" +"Sintaxe: %s canal KEEPTOPIC {ON|OFF}\n" +"\n" +"Ativa ou desativa a opção de retenção de tópico para\n" +"um canal. Quando a retenção de tópico está acionada,\n" +"o tópico para o canal será lembrado pelo %s\n" +"mesmo depois que os usuários deixarem o canal, e será\n" +"restaurado na próxima vez que o canal for reutilizado." + +#: modules/commands/ns_set.cpp:643 +msgid "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." +msgstr "" + +#: modules/commands/ns_set.cpp:618 +msgid "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." +msgstr "" + +#: modules/commands/cs_set.cpp:733 +#, fuzzy +msgid "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." +msgstr "" +"Sintaxe: %s canal SECURE {ON|OFF}\n" +"\n" +"Ativa ou desativa os recursos de segurança do %s\n" +"para um canal. Quando o SECURE estiver ativo, somente\n" +"usuários que possuirem seus nicks registrados no %s\n" +"e identificados com sua senha poderão entrar no canal\n" +"controlado pela lista de acesso." + +#: modules/commands/cs_set.cpp:932 +#, fuzzy +msgid "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." +msgstr "" +"Sintaxe: %s canal SIGNKICK {ON | LEVEL | OFF}\n" +"\n" +"Habilita ou desabilita a assinatura nos kicks para um\n" +"canal. Quando o SIGNKICK está habilitado, kicks através\n" +"do comando %s KICK terão o nick de quem usou o comando\n" +"no motivo do kick.\n" +"\n" +"Se você usar LEVEL, aqueles que tiverem um nível igual ou \n" +"superior ao nível do SIGNKICK não terão o nick aparecendo no \n" +"motivo. Veja /msg %s HELP LEVELS para maiores informações. " + +#: modules/commands/cs_set.cpp:452 +#, fuzzy, c-format +msgid "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." +msgstr "" +"Sintaxe: %s canal PEACE {ON | OFF}\n" +"\n" +"Ativa ou destiva a opção peace para um canal.\n" +"Quando peace está ativada, um usuário não poderá kickar,\n" +"banir ou remover os modos no canal de um usuário que tenha\n" +"nível superior ou igual ao seu via comandos do %s." + +#: modules/commands/cs_list.cpp:232 +msgid "Enables or disables the private option for a channel." +msgstr "" + +#: modules/commands/cs_set.cpp:671 +#, fuzzy +msgid "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." +msgstr "" +"Sintaxe: %s canal RESTRICTED {ON|OFF}\n" +"\n" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." + +#: modules/commands/cs_set.cpp:796 +#, fuzzy +msgid "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." +msgstr "" +"Sintaxe: %s canal SECUREFOUNDER {ON | OFF}\n" +"\n" +"Ativa ou desativa a opção secure founder para um canal.\n" +"Quando o secure founder está ligado, apenas o verdadeiro founder\n" +"poderá dar DROP no canal, mudar sua senha, seu founder e seu\n" +"successor, e não aqueles que estiverem identificados no %s." + +#: modules/commands/cs_set.cpp:860 +#, fuzzy +msgid "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." +msgstr "" +"Sintaxe: %s canal SECUREOPS {ON|OFF}\n" +"\n" +"Ativa ou desativa a opção de segurança de ops para um canal.\n" +"Quando secure ops estiver ativada, os usuários que não\n" +"estiverem na lista de acesso não poderão ter o status de OP." + +#: modules/commands/cs_topic.cpp:70 +#, fuzzy, c-format +msgid "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." +msgstr "" +"Sintaxe: %s canal KEEPTOPIC {ON|OFF}\n" +"\n" +"Ativa ou desativa a opção de retenção de tópico para\n" +"um canal. Quando a retenção de tópico está acionada,\n" +"o tópico para o canal será lembrado pelo %s\n" +"mesmo depois que os usuários deixarem o canal, e será\n" +"restaurado na próxima vez que o canal for reutilizado." + +#: modules/commands/cs_set.cpp:592 +#, fuzzy, c-format +msgid "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." +msgstr "" +"Syntax: %s channel PERSIST {ON | OFF}\n" +"Enables or disables the persistant channel setting.\n" +"When persistant is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +"\n" +"If your IRCd does not a permanent (persistant) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +"\n" +"If this network does not have BotServ enabled and does\n" +"not have a permanent channel mode, ChanServ will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +"\n" +"If your IRCd has a permanent (persistant) channel mode\n" +"and is is set or unset (for any reason, including MLOCK),\n" +"persist is automatically set and unset for the channel aswell.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." + +#: modules/commands/os_akill.cpp:331 +#, fuzzy +msgid "End of AKILL list." +msgstr "Fim da listagem." + +#: modules/commands/cs_access.cpp:444 +#, fuzzy +msgid "End of access list" +msgstr "Fim da lista de acesso." + +#: modules/commands/cs_flags.cpp:347 +#, fuzzy, c-format +msgid "End of access list - %d/%d entries shown." +msgstr "Fim da listagem - %d/%d resultados mostrados." + +#: modules/commands/cs_flags.cpp:345 +msgid "End of access list." +msgstr "Fim da lista de acesso." + +#: modules/commands/cs_akick.cpp:379 +#, fuzzy +msgid "End of autokick list" +msgstr "Fim da lista de acesso." + +#: modules/commands/bs_badwords.cpp:257 +#, fuzzy +msgid "End of bad words list." +msgstr "Fim da listagem." + +#: modules/commands/os_list.cpp:100 +#, fuzzy, c-format +msgid "End of channel list. %u channels shown." +msgstr "Fim da listagem - %d/%d resultados mostrados." + +#: modules/commands/os_config.cpp:117 +msgid "End of configuration." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:134 +#, fuzzy +msgid "End of entry message list." +msgstr "Fim da listagem." + +#: modules/commands/os_forbid.cpp:407 +#, fuzzy, c-format +msgid "End of forbid list - %d/%d entries shown." +msgstr "Fim da listagem - %d/%d resultados mostrados." + +#: modules/commands/os_forbid.cpp:405 +#, fuzzy +msgid "End of forbid list." +msgstr "Fim da listagem." + +#: modules/commands/ns_alist.cpp:119 +#, fuzzy, c-format +msgid "End of list - %d channels shown." +msgstr "Fim da listagem - %d/%d resultados mostrados." + +#: modules/commands/ns_list.cpp:131 modules/commands/cs_list.cpp:130 +#, c-format +msgid "End of list - %d/%d matches shown." +msgstr "Fim da listagem - %d/%d resultados mostrados." + +#: modules/commands/os_news.cpp:176 +#, fuzzy +msgid "End of news list." +msgstr "Fim da listagem." + +#: modules/commands/os_list.cpp:235 +#, fuzzy, c-format +msgid "End of users list. %u users shown." +msgstr "Fim da listagem - %d/%d resultados mostrados." + +#: modules/commands/cs_enforce.cpp:227 +msgid "Enforce various channel modes and set options" +msgstr "" + +#: modules/commands/cs_enforce.cpp:263 +msgid "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." +msgstr "" + +#: src/language.cpp:43 modules/commands/ns_set.cpp:836 +#: modules/commands/ns_set.cpp:856 modules/commands/ns_set.cpp:891 +msgid "English" +msgstr "Português" + +#: modules/commands/cs_entrymsg.cpp:170 +#, fuzzy, c-format +msgid "Entry message %i for %s deleted." +msgstr "Greet message for %s unset." + +#: modules/commands/cs_entrymsg.cpp:177 +#, fuzzy, c-format +msgid "Entry message %s not found on channel %s." +msgstr "Modo Fantasia está agora ATIVADO no canal %s." + +#: modules/commands/cs_entrymsg.cpp:147 +#, fuzzy, c-format +msgid "Entry message added to %s" +msgstr "Greet message for %s changed to %s." + +#: modules/commands/cs_entrymsg.cpp:109 modules/commands/cs_entrymsg.cpp:158 +#, fuzzy, c-format +msgid "Entry message list for %s is empty." +msgstr "Lista de acesso para %s está vazia." + +#: modules/commands/cs_entrymsg.cpp:113 +#, fuzzy, c-format +msgid "Entry message list for %s:" +msgstr "Lista de acesso para %s:" + +#: modules/commands/cs_entrymsg.cpp:187 +#, fuzzy, c-format +msgid "Entry messages for %s have been cleared." +msgstr "Todos os memos para o canal %s foram apagados." + +#: modules/commands/os_reload.cpp:39 +#, fuzzy, c-format +msgid "Error reloading configuration file: %s" +msgstr " RELOAD Recarrega o arquivo de configuração dos Services" + +#: include/language.h:125 +#, c-format +msgid "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." +msgstr "" + +#: include/language.h:124 +#, c-format +msgid "" +"Error! The vHost is too long, please use a hostname shorter than %d " +"characters." +msgstr "" + +#: modules/commands/ns_cert.cpp:325 +msgid "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." +msgstr "" + +#: modules/commands/os_session.cpp:358 +#, c-format +msgid "Exception for %s has been updated to %d." +msgstr "Exceção para %s foi atualizada para %d." + +#: modules/pseudoclients/chanserv.cpp:465 +#: modules/pseudoclients/nickserv.cpp:557 +#: modules/pseudoclients/nickserv.cpp:562 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_session.cpp:514 modules/commands/ns_group.cpp:327 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Expires" +msgstr " Expira em: %s" + +#: src/xline.cpp:397 +#, fuzzy, c-format +msgid "Expiry and reason updated for %s." +msgstr "Exceção para %s foi atualizada para %d." + +#: src/xline.cpp:400 +#, fuzzy, c-format +msgid "Expiry for %s updated." +msgstr "Tempo de expiração para %s alterado." + +#: modules/fantasy.cpp:214 +msgid "Fantasy" +msgstr "Fantasia" + +#: modules/fantasy.cpp:60 +#, fuzzy, c-format +msgid "Fantasy mode is now off on channel %s." +msgstr "Modo Fantasia está agora ATIVADO no canal %s." + +#: modules/fantasy.cpp:52 +#, fuzzy, c-format +msgid "Fantasy mode is now on on channel %s." +msgstr "Modo Fantasia está agora ATIVADO no canal %s." + +#: modules/commands/cs_status.cpp:19 +#, fuzzy +msgid "Find a user's status on a channel" +msgstr " DEOWNER Retira seu status de Owner no canal" + +#: modules/commands/ns_cert.cpp:192 +#, fuzzy, c-format +msgid "Fingerprint %s already present on %s's certificate list." +msgstr "A máscara %s já se encontra em sua lista de acesso." + +#: modules/commands/ns_cert.cpp:198 +#, fuzzy, c-format +msgid "Fingerprint %s is already in use." +msgstr "You are already in %s! " + +#: modules/commands/cs_flags.cpp:301 +msgid "Flags" +msgstr "" + +#: modules/commands/cs_flags.cpp:286 +#, fuzzy, c-format +msgid "Flags for %s on %s set to +%s" +msgstr "Nível de acesso para %s no %s alterado para %d." + +#: modules/commands/cs_flags.cpp:341 +#, fuzzy, c-format +msgid "Flags list for %s" +msgstr "Lista de acesso para %s:" + +#: modules/commands/bs_kick.cpp:1161 modules/commands/bs_kick.cpp:1163 +#: modules/commands/bs_kick.cpp:1166 +#, fuzzy +msgid "Flood kicker" +msgstr " Kick por flood: %s" + +#: modules/commands/os_forbid.cpp:421 +msgid "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." +msgstr "" + +#: modules/commands/os_forbid.cpp:354 +#, fuzzy +msgid "Forbid list is empty." +msgstr "Lista de Ignore dos Services vazia." + +#: modules/commands/os_forbid.cpp:396 +#, fuzzy +msgid "Forbid list:" +msgstr "Lista de bots:" + +#: modules/commands/os_forbid.cpp:348 +#, c-format +msgid "Forbid on %s was not found." +msgstr "" + +#: modules/commands/os_forbid.cpp:156 +msgid "Forbid usage of nicknames, channels, and emails" +msgstr "" + +#: modules/commands/os_update.cpp:19 +#, fuzzy +msgid "Force the Services databases to be updated immediately" +msgstr " UPDATE Salva os dados atuais dos Services" + +#: modules/commands/os_svs.cpp:19 +#, fuzzy +msgid "Forcefully change a user's nickname" +msgstr " SVSNICK Força a mudança do nick de um usuário" + +#: modules/commands/os_svs.cpp:68 +#, fuzzy +msgid "Forcefully changes a user's nickname from nick to newnick." +msgstr "" +"Sintaxe: SVSNICK nick novo-nick\n" +"\n" +"Força a mudança do nick de um usuário, de nick a novo-nick." + +#: modules/commands/os_svs.cpp:78 +#, fuzzy +msgid "Forcefully join a user to a channel" +msgstr " SVSNICK Força a mudança do nick de um usuário" + +#: modules/commands/os_svs.cpp:112 +#, fuzzy +msgid "Forcefully join a user to a channel." +msgstr " SVSNICK Força a mudança do nick de um usuário" + +#: modules/commands/os_svs.cpp:122 +#, fuzzy +msgid "Forcefully part a user from a channel" +msgstr " KICK Kicka um usuário de um canal" + +#: modules/commands/os_svs.cpp:160 +#, fuzzy +msgid "Forcefully part a user from a channel." +msgstr " KICK Kicka um usuário de um canal" + +#: modules/commands/ns_alist.cpp:64 modules/commands/cs_info.cpp:47 +#, fuzzy +msgid "Founder" +msgstr "Founder Seguro" + +#: modules/commands/cs_set.cpp:315 +#, fuzzy, c-format +msgid "Founder of %s changed to %s." +msgstr "Founder do canal %s alterado para %s." + +#: modules/commands/ns_getpass.cpp:41 +msgid "GETPASS command unavailable because encryption is in use." +msgstr "Comando GETPASS não disponível: modo de encriptação ativado." + +#: modules/commands/ns_recover.cpp:84 +msgid "Ghost with your nick has been killed." +msgstr "Seu nick foi derrubado e pode ser usado." + +#: modules/commands/os_oline.cpp:19 +#, fuzzy +msgid "Give Operflags to a certain user" +msgstr " OLINE Dá flags de Operador a um determinado usuário" + +#: modules/commands/cs_mode.cpp:905 +#, c-format +msgid "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." +msgstr "" + +#: modules/commands/cs_mode.cpp:888 +#, fuzzy, c-format +msgid "Gives you or the specified nick %s status on a channel" +msgstr " OWNER Concede-lhe status de Owner no canal" + +#: modules/commands/greet.cpp:206 modules/commands/greet.cpp:212 +msgid "Greet" +msgstr "Mensagem de entrada" + +#: src/access.cpp:38 +#, fuzzy +msgid "Greet message displayed on join" +msgstr "Greet message for %s changed to %s." + +#: modules/commands/greet.cpp:112 +#, c-format +msgid "Greet message for %s changed to %s." +msgstr "Greet message for %s changed to %s." + +#: modules/commands/greet.cpp:118 +#, c-format +msgid "Greet message for %s unset." +msgstr "Greet message for %s unset." + +#: modules/commands/greet.cpp:60 +#, fuzzy, c-format +msgid "Greet mode is now off on channel %s." +msgstr "Modo mensagem de entrada está agora ATIVADO no canal %s." + +#: modules/commands/greet.cpp:52 +#, fuzzy, c-format +msgid "Greet mode is now on on channel %s." +msgstr "Modo mensagem de entrada está agora ATIVADO no canal %s." + +#: modules/commands/ns_resetpass.cpp:21 +#, fuzzy +msgid "Helps you reset lost passwords" +msgstr " RESETPASS Helps you reset lost passwords" + +#: modules/commands/ns_info.cpp:141 +#, fuzzy +msgid "Hide certain pieces of nickname information" +msgstr " HIDE Esconde certas informações sobre seu nick" + +#: modules/commands/cs_list.cpp:180 +#, fuzzy +msgid "Hide channel from the LIST command" +msgstr " PRIVATE Esconde o canal do comando LIST" + +#: modules/commands/os_session.cpp:192 +msgid "Host" +msgstr "" + +#: modules/commands/os_session.cpp:207 +#, c-format +msgid "Hosts with at least %d sessions:" +msgstr "Hosts com pelo menos %d sessões:" + +#: modules/commands/cs_seen.cpp:207 +#, c-format +msgid "I don't know who %s is." +msgstr "" + +#: modules/commands/cs_seen.cpp:253 +#, fuzzy, c-format +msgid "I've never seen %s on this channel." +msgstr "Por favor não use reversos no canal!" + +#: modules/commands/os_sxline.cpp:203 modules/commands/os_akill.cpp:360 +msgid "ID" +msgstr "" + +#: modules/commands/os_oper.cpp:72 +msgid "INFO [type]" +msgstr "" + +#: modules/commands/os_dns.cpp:218 +msgid "IP" +msgstr "" + +#: modules/commands/os_dns.cpp:500 +#, fuzzy, c-format +msgid "IP %s already exists for %s." +msgstr "Bot %s já existe." + +#: modules/commands/os_dns.cpp:562 +#, fuzzy, c-format +msgid "IP %s does not exist for %s." +msgstr "Bot %s já existe." + +#: modules/commands/ns_identify.cpp:65 +#, fuzzy +msgid "Identify yourself with your password" +msgstr " IDENTIFY Identifica seu nick com sua senha" + +#: modules/pseudoclients/nickserv.cpp:205 +#: modules/pseudoclients/nickserv.cpp:211 +#, fuzzy, c-format +msgid "If you do not change within %s, I will change your nick." +msgstr "Se você não mudar seu nick em 20 segundos, eu irei mudá-lo." + +#: modules/commands/os_ignore.cpp:333 +msgid "Ignore list has been cleared." +msgstr "Lista de Ignore foi apagada." + +#: modules/commands/os_ignore.cpp:262 +msgid "Ignore list is empty." +msgstr "Lista de Ignore dos Services vazia." + +#: modules/commands/ms_ignore.cpp:94 +#, fuzzy +msgid "Ignore list:" +msgstr "Lista de bots:" + +#: modules/commands/ns_set.cpp:1305 +#, fuzzy +msgid "Immediate protection" +msgstr "Proteção de Voices" + +#: modules/commands/ns_resetpass.cpp:33 +#, fuzzy +msgid "Incorrect email address." +msgstr " E-mail: %s" + +#: include/language.h:89 +msgid "Incorrect range specified. The correct syntax is #from-to." +msgstr "" + +#: modules/commands/os_modinfo.cpp:19 +#, fuzzy +msgid "Info about a loaded module" +msgstr " MODINFO Informação sobre um módulo carregado" + +#: modules/commands/bs_info.cpp:54 +#, c-format +msgid "Information for bot %s:" +msgstr "Informações do bot %s:" + +#: include/language.h:108 +#, fuzzy, c-format +msgid "Information for channel %s:" +msgstr "Informações do bot %s:" + +#: modules/commands/os_logsearch.cpp:57 +#, c-format +msgid "Invalid duration %s, using %d days." +msgstr "" + +#: include/language.h:68 +msgid "Invalid expiry time." +msgstr "" + +#: modules/commands/os_session.cpp:346 +#, fuzzy +msgid "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not " +"matched against nicks or usernames." +msgstr "" +"Máscara inválida. Apenas máscaras (hosts) são válidas como exceções aos " +"limites de sessões. Nick ou username não são válidos." + +#: modules/commands/os_logsearch.cpp:73 +#, c-format +msgid "Invalid limit %s, using %d." +msgstr "" + +#: include/language.h:99 +msgid "" +"Invalid passcode has been entered, please check the e-mail again, and retry." +msgstr "" + +#: modules/commands/ns_register.cpp:83 modules/commands/ns_register.cpp:86 +msgid "Invalid passcode." +msgstr "" + +#: modules/commands/os_session.cpp:339 +#, c-format +msgid "" +"Invalid session limit. It must be a valid integer greater than or equal to " +"zero and less than %d." +msgstr "" +"Limite de sessão inválida. O limite deve ser um número inteiro maior ou " +"igual a zero e menor que %d." + +#: modules/commands/os_session.cpp:188 +msgid "Invalid threshold value. It must be a valid integer greater than 1." +msgstr "Número inválido. Deve ser um número inteiro maior que 1." + +#: modules/commands/os_dns.cpp:591 +msgid "Invalid value for LIMIT. Must be numerical." +msgstr "" + +#: modules/commands/cs_invite.cpp:19 +#, fuzzy +msgid "Invites you or an optionally specified nick into a channel" +msgstr " OP Atribui status de OP a um nick no canal" + +#: modules/commands/bs_kick.cpp:1201 modules/commands/bs_kick.cpp:1203 +#: modules/commands/bs_kick.cpp:1206 +#, fuzzy +msgid "Italics kicker" +msgstr " Italics kicker : %s" + +#: modules/commands/ns_group.cpp:91 +#, fuzzy +msgid "Join a group" +msgstr " GROUP Se junta a um grupo" + +#: modules/commands/cs_set.cpp:1305 modules/commands/ns_set.cpp:1319 +#, fuzzy +msgid "Keep modes" +msgstr "Modo mensagem" + +#: modules/commands/cs_set.cpp:377 modules/commands/ns_set.cpp:603 +#, fuzzy, c-format +msgid "Keep modes for %s is now off." +msgstr "Opção Peace para %s está agora ATIVADA." + +#: modules/commands/cs_set.cpp:369 modules/commands/ns_set.cpp:597 +#, fuzzy, c-format +msgid "Keep modes for %s is now on." +msgstr "Opção Peace para %s está agora ATIVADA." + +#: modules/commands/ns_ajoin.cpp:100 +msgid "Key" +msgstr "" + +#: modules/commands/cs_getkey.cpp:50 +#, c-format +msgid "Key for channel %s is %s." +msgstr "Key for channel %s is %s." + +#: modules/commands/os_kick.cpp:19 +#, fuzzy +msgid "Kick a user from a channel" +msgstr " KICK Kicka um usuário de um canal" + +#: modules/commands/cs_ban.cpp:217 modules/commands/cs_kick.cpp:116 +#, c-format +msgid "Kicked %d/%d users matching %s from %s." +msgstr "" + +#: modules/commands/cs_kick.cpp:19 +#, fuzzy +msgid "Kicks a specified nick from a channel" +msgstr " KICK Kicka (expulsa) um nick de um canal" + +#: modules/commands/cs_kick.cpp:128 +#, fuzzy +msgid "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." +msgstr "" +"Sintaxe: KICK #canal nick [motivo]\n" +"\n" +"Kicka (expulsa) um nick dado em um determinado canal.\n" +"Por padrão, é limitado aos AOPs ou àqueles que possuem\n" +"nível de acesso 5 ou superior no canal." + +#: modules/commands/os_kill.cpp:19 +msgid "Kill a user" +msgstr "" + +#: modules/commands/cs_enforce.cpp:217 +msgid "LIMIT enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:221 +#, c-format +msgid "LIMIT enforced on %s, %d users removed." +msgstr "" + +#: modules/commands/os_session.cpp:246 +msgid "LIST threshold" +msgstr "" + +#: modules/commands/os_sxline.cpp:427 modules/commands/os_sxline.cpp:661 +#: modules/commands/os_akill.cpp:388 +#, fuzzy +msgid "LIST [mask | list | id]" +msgstr "LIST [canal] [list | NEW]" + +#: modules/commands/os_session.cpp:525 +#, fuzzy +msgid "LIST [mask | list]" +msgstr "LIST [canal] [list | NEW]" + +#: modules/commands/ns_access.cpp:104 modules/commands/ns_cert.cpp:260 +#: modules/commands/ns_ajoin.cpp:233 +#, fuzzy +msgid "LIST [nickname]" +msgstr "CHECK nick" + +#: modules/commands/os_news.cpp:31 +msgid "LOGONNEWS {ADD|DEL|LIST} [text|num]" +msgstr "LOGONNEWS {ADD|DEL|LIST} [texto|núm]" + +#: modules/commands/ns_set.cpp:834 +msgid "Language changed to English." +msgstr "Linguagem alterada para Português." + +#: modules/commands/ns_set.cpp:836 +#, fuzzy, c-format +msgid "Language for %s changed to %s." +msgstr "Successor do canal %s alterado para %s." + +#: modules/commands/ms_cancel.cpp:72 +#, c-format +msgid "Last memo to %s has been cancelled." +msgstr "Último memo enviado para %s foi cancelado." + +#: modules/commands/ns_info.cpp:95 +#, fuzzy +msgid "Last quit message" +msgstr "Última mensagem de saída: %s" + +#: modules/commands/cs_access.cpp:472 modules/commands/ns_info.cpp:92 +#, fuzzy +msgid "Last seen" +msgstr " Último horário visto: %s" + +#: modules/commands/ns_info.cpp:81 modules/commands/ns_info.cpp:86 +#, fuzzy +msgid "Last seen address" +msgstr " Último endereço visto: %s" + +#: modules/commands/cs_topic.cpp:264 +msgid "Last topic" +msgstr "" + +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_info.cpp:56 +#, fuzzy +msgid "Last used" +msgstr " Último horário visto: %s" + +#: modules/commands/ns_list.cpp:75 +#, fuzzy +msgid "Last usermask" +msgstr " Último horário visto: %s" + +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +#: modules/commands/cs_access.cpp:697 +msgid "Level" +msgstr "" + +#: modules/commands/cs_access.cpp:660 +#, c-format +msgid "Level for %s on channel %s changed to %d." +msgstr "Nível para %s no canal %s alterado para %d." + +#: modules/commands/cs_access.cpp:658 +#, c-format +msgid "Level for %s on channel %s changed to founder only." +msgstr "Level for %s on channel %s changed to founder only." + +#: modules/commands/cs_access.cpp:643 +#, c-format +msgid "Level must be between %d and %d inclusive." +msgstr "O nível deve ser entre %d e %d inclusive." + +#: modules/commands/os_dns.cpp:218 modules/commands/os_session.cpp:506 +#: modules/commands/os_session.cpp:514 +msgid "Limit" +msgstr "" + +#: modules/commands/ns_list.cpp:19 +#, fuzzy +msgid "List all registered nicknames that match a given pattern" +msgstr "" +" LIST Lista todos os nicks registrados que combinam com o padrão " +"fornecido" + +#: modules/commands/ns_alist.cpp:24 +#, fuzzy +msgid "List channels you have access on" +msgstr " ALIST Lista todos os canais nos quais você tem acesso" + +#: modules/commands/cs_mode.cpp:341 +#, c-format +msgid "List for mode %c is full." +msgstr "" + +#: modules/commands/os_modinfo.cpp:80 +#, fuzzy +msgid "List loaded modules" +msgstr " MODLIST Lista os módulos carregados" + +#: modules/commands/ns_list.cpp:123 modules/commands/cs_list.cpp:72 +#, fuzzy, c-format +msgid "List of entries matching %s:" +msgstr "Lista de nicks no grupo %s:" + +#: modules/commands/ns_group.cpp:350 +#, c-format +msgid "List of nicknames in the group of %s:" +msgstr "Lista de nicks no grupo %s:" + +#: modules/commands/ns_group.cpp:350 +msgid "List of nicknames in your group:" +msgstr "Lista de nicks no grupo:" + +#: modules/commands/ms_list.cpp:19 +#, fuzzy +msgid "List your memos" +msgstr " LIST Lista suas mensagens" + +#: modules/commands/bs_botlist.cpp:64 +#, fuzzy +msgid "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." +msgstr "" +"Sintaxe: BOTLIST\n" +"\n" +"Lista todos os bots disponíveis nesta Rede." + +#: modules/commands/os_list.cpp:19 +#, fuzzy +msgid "Lists all channel records" +msgstr " CHANLIST Lista todos os canais em uso na Rede" + +#: modules/commands/os_list.cpp:107 +#, fuzzy +msgid "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." +msgstr "" +"Sintaxe: CHANLIST [{padrão | nick} [SECRET]]\n" +"\n" +"Lista todos os canais em uso na Rede, sejam eles registrados ou não.\n" +"\n" +"Se um padrão é fornecido, listará apenas canais que combinem com\n" +"ele. Se um nick é fornecido, listará apenas canais que o usuário\n" +"estiver usando. Se SECRET é especificado, listará apenas canais\n" +"combinando com o padrão e que tenham modo +s ou +p." + +#: modules/commands/ns_alist.cpp:127 +msgid "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" +msgstr "" + +#: modules/commands/ns_group.cpp:299 +#, fuzzy +msgid "Lists all nicknames in your group" +msgstr "Lista de nicks no grupo:" + +#: modules/commands/cs_list.cpp:20 +#, fuzzy +msgid "Lists all registered channels matching the given pattern" +msgstr "" +" LIST Lista todos os canais registrados que combinam com o padrão " +"fornecido" + +#: modules/commands/cs_list.cpp:137 +#, fuzzy +msgid "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." +msgstr "" +"Sintaxe: LIST padrão [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]\n" +"\n" +"Lista todos os nicks registrados que combinem com o padrão\n" +"fornecido (formato nick!ident@host). Nicks com opção PRIVATE\n" +"serão somente exibidos para os Administradores dos Services.\n" +"Nicks com opção NOEXPIRE ajustada terão um ! preposto ao nick\n" +"na lista quando for a pedido de Administrador dos Services.\n" +"\n" +"Se as opções FORBIDDEN, SUSPENDED, NOEXPIRE ou UNCONFIRMED são fornecidas, " +"apenas\n" +"nicks que são, respectivamente, FORBIDDEN, SUSPENDED, UNCONFIRMED ou têm a " +"opção\n" +"NOEXPIRE ativa, serão exibidos. Se todas as três opções forem fornecidas,\n" +"todos os três tipos de nicks serão exibidos. Estas opções são limitas aos\n" +"Administradores dos Services.\n" +"\n" +"Exemplos:\n" +"\n" +" LIST *!ident@servidor.com.br\n" +" Lista todos os nicks de *!ident@servidor.com.br.\n" +"\n" +" LIST *Bot*!*@*\n" +" Lista todos os nicks registrados com Bot em seus nomes.\n" +"\n" +" LIST * NOEXPIRE\n" +" Lista todos os nicks registrados cujos registros foram\n" +" ajustados para não expirar." + +#: modules/commands/ns_list.cpp:139 +#, fuzzy +msgid "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." +msgstr "" +"Sintaxe: LIST padrão [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]\n" +"\n" +"Lista todos os nicks registrados que combinem com o padrão\n" +"fornecido (formato nick!ident@host). Nicks com opção PRIVATE\n" +"serão somente exibidos para os Administradores dos Services.\n" +"Nicks com opção NOEXPIRE ajustada terão um ! preposto ao nick\n" +"na lista quando for a pedido de Administrador dos Services.\n" +"\n" +"Se as opções FORBIDDEN, SUSPENDED, NOEXPIRE ou UNCONFIRMED são fornecidas, " +"apenas\n" +"nicks que são, respectivamente, FORBIDDEN, SUSPENDED, UNCONFIRMED ou têm a " +"opção\n" +"NOEXPIRE ativa, serão exibidos. Se todas as três opções forem fornecidas,\n" +"todos os três tipos de nicks serão exibidos. Estas opções são limitas aos\n" +"Administradores dos Services.\n" +"\n" +"Exemplos:\n" +"\n" +" LIST *!ident@servidor.com.br\n" +" Lista todos os nicks de *!ident@servidor.com.br.\n" +"\n" +" LIST *Bot*!*@*\n" +" Lista todos os nicks registrados com Bot em seus nomes.\n" +"\n" +" LIST * NOEXPIRE\n" +" Lista todos os nicks registrados cujos registros foram\n" +" ajustados para não expirar." + +#: modules/commands/os_list.cpp:132 +#, fuzzy +msgid "Lists all user records" +msgstr " USERLIST Lista todos os usuários online na Rede" + +#: modules/commands/os_list.cpp:243 +#, fuzzy +msgid "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only " +"users\n" +"with the +i flag will be listed." +msgstr "" +"Sintaxe: USERLIST [{padrão | canal} [INVISIBLE]]\n" +"\n" +"Lista todos os usuários online na Rede, tenham eles nicks\n" +"registrados ou não.\n" +"\n" +"Se um padrão é fornecido, listará apenas usuários que combinem\n" +"com ele (deve estar no formato nick!ident@host). Se um canal é\n" +"fornecido, listará apenas usuários que estão no canal dado.\n" +"estiver usando. Se INVISIBLE é especificado, listará apenas usuários\n" +"que tenham o modo +i." + +#: modules/commands/ms_list.cpp:142 +#, fuzzy +msgid "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Sintaxe: LIST [canal] [list | NEW]\n" +"\n" +"Lista quaisquer mensagens que você tiver. Com NEW, lista apenas\n" +"as novas mensagens (não lidas). Mensagens não lidas são marcadas\n" +"com \"*\" à esquerda do número. Você também pode especificar uma\n" +"lista de números, como no exemplo abaixo:\n" +"\n" +"LIST 2-5,7-9\n" +" Lista mensagens numeradas de 2 a 5 e de 7 a 9." + +#: modules/commands/bs_botlist.cpp:19 +#, fuzzy +msgid "Lists available bots" +msgstr " BOTLIST Lista os bots disponíveis" + +#: modules/commands/os_modinfo.cpp:196 +#, fuzzy +msgid "Lists currently loaded modules." +msgstr " MODLIST Lista os módulos carregados" + +#: modules/commands/cs_info.cpp:19 +#, fuzzy +msgid "Lists information about the specified registered channel" +msgstr " INFO Mostra informações sobre algum canal registrado" + +#: modules/commands/cs_info.cpp:76 +#, fuzzy +msgid "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." +msgstr "" +"Sintaxe: INFO canal\n" +"\n" +"Lista as informações referentes ao canal registrado dado,\n" +"incluindo seu fundador, data do registro, última vez que\n" +"foi usado, descrição, e trava dos modos (se existirem).\n" +"\n" +"Se você está identificado como fundador do canal que está\n" +"solicitando informações e a opção ALL é especificada,\n" +"informações sobre a mensagem de entrada e sobre o sucessor\n" +"do canal também serão mostradas." + +#: modules/commands/os_module.cpp:19 +#, fuzzy +msgid "Load a module" +msgstr " MODLOAD Carrega um módulo" + +#: modules/commands/cs_register.cpp:39 +msgid "Local channels cannot be registered." +msgstr "Canais locais não podem ser registrados." + +#: modules/commands/cs_log.cpp:142 +#, fuzzy, c-format +msgid "Log list for %s:" +msgstr "Lista de acesso para %s:" + +#: modules/commands/cs_log.cpp:227 +#, c-format +msgid "Logging changed for command %s on %s, now using log method %s%s%s." +msgstr "" + +#: modules/commands/cs_log.cpp:220 +#, c-format +msgid "Logging for command %s on %s with log method %s%s%s has been removed." +msgstr "" + +#: modules/commands/cs_log.cpp:248 +#, c-format +msgid "Logging is now active for command %s on %s, using log method %s%s%s." +msgstr "" + +#: modules/commands/os_login.cpp:60 +#, c-format +msgid "Login to %s" +msgstr "" + +#: modules/commands/os_news.cpp:36 +#, c-format +msgid "Logon news item #%d deleted." +msgstr "Logon news removido #%d." + +#: modules/commands/os_news.cpp:35 +#, fuzzy, c-format +msgid "Logon news item #%s not found!" +msgstr "Logon news não encontrado #%d!" + +#: modules/commands/os_news.cpp:32 +msgid "Logon news items:" +msgstr "Logon News itens:" + +#: modules/commands/os_login.cpp:102 +#, fuzzy, c-format +msgid "Logout from %s" +msgstr "Lista de acesso para %s:" + +#: modules/commands/os_login.cpp:52 +#, c-format +msgid "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." +msgstr "" + +#: modules/commands/os_login.cpp:94 +#, c-format +msgid "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." +msgstr "" + +#: modules/commands/cs_seen.cpp:213 +#, c-format +msgid "Looking for yourself, eh %s?" +msgstr "" + +#: modules/commands/cs_mode.cpp:773 +#, c-format +msgid "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a " +"channel.\n" +"If a mode is locked on or off, services will not allow that mode to be " +"changed. The SET\n" +"command will clear all existing mode locks and set the new one given, while " +"ADD and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * " +"and ? may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may " +"be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, " +"halfops, and voices. If what\n" +"is not given then all basic modes are removed." +msgstr "" + +#: modules/commands/cs_akick.cpp:434 +#, fuzzy +msgid "Maintain the AutoKick list" +msgstr " AKICK Faz a manutenção da Lista de Autokick" + +#: modules/commands/bs_bot.cpp:269 +#, fuzzy +msgid "Maintains network bot list" +msgstr " BOT Mantém a lista de bots da Rede" + +#: modules/commands/cs_xop.cpp:522 +#, c-format +msgid "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " +msgstr "" + +#: modules/commands/cs_akick.cpp:493 +#, c-format +msgid "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" +msgstr "" + +#: modules/commands/cs_access.cpp:568 +#, c-format +msgid "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." +msgstr "" + +#: modules/commands/bs_badwords.cpp:424 +#, fuzzy, c-format +msgid "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" +msgstr "" +"Sintaxe: BADWORDS canal ADD palavra [SINGLE | START | END]\n" +" BADWORDS canal DEL {palavra | núm-entrada | lista}\n" +" BADWORDS canal LIST [máscara | lista]\n" +" BADWORDS canal CLEAR\n" +"\n" +"Faz a manutenção da lista de palavrões em um canal.\n" +"Essa lista determina quais são as palavras que deverão\n" +"ser motivo de kick em um canal quando a opção BADWORDS\n" +"estiver ativada. Para maiores informações, digite\n" +"/msg %s HELP KICK BADWORDS.\n" +"\n" +"O comando BADWORDS ADD adiciona a palavra na lista\n" +"de palavrões. A opção SINGLE, quando especificada, só\n" +"kicka o usuário se ele escrever a palavra inteira.\n" +"A opção START, quando especificada, irá kickar o usuário\n" +"que escrever uma palavra que comece com a palavra.\n" +"A opção END se tiver sido especificada só kicka o usuário\n" +"que escrever uma palavra que termine com a palavra.\n" +"Se você não especificar nada, o bot irá kickar sempre\n" +"que a palavra for escrita pelo usuário.\n" +"\n" +"O comando BADWORDS DEL remove uma palavra da lista de\n" +"palavrões de um determinado canal. Se uma lista de números\n" +"de entrada for fornecida, essas entradas serão apagadas\n" +"(veja o exemplo para LIST abaixo).\n" +"\n" +"O comando BADWORDS LIST mostra a lista de palavrões.\n" +"Se forem usados coringas, apenas aquelas entradas com\n" +"as determinadas máscaras serão mostradas. Se uma lista\n" +"de números de entrada for dada, apenas aquelas entradas\n" +"serão mostradas; por exemplo:\n" +"\n" +" BADWORDS #canal LIST 2-5,7-9\n" +" Lista as entradas dos palavrões numeradas de 2 a 5\n" +" e de 7 a 9.\n" +"\n" +"O comando BADWORDS CLEAR limpa todas entradas da lista." + +#: modules/commands/bs_badwords.cpp:370 +#, fuzzy +msgid "Maintains the bad words list" +msgstr " BADWORDS Configura os palavrões" + +#: modules/commands/bs_control.cpp:79 +#, fuzzy +msgid "Makes the bot do the equivalent of a \"/me\" command" +msgstr "" +" ACT Faz com que o bot faça o mesmo que o comando \"/me\"" + +#: modules/commands/bs_control.cpp:127 +#, fuzzy +msgid "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." +msgstr "" +"Sintaxe: ACT canal texto\n" +"\n" +"Faz com que o bot faça o mesmo que o comando \"/me\"\n" +"em um determinado canal com o determinado texto." + +#: modules/commands/bs_control.cpp:19 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel" +msgstr "" +" SAY Faz com que o bot diga determinado texto no canal dado" + +#: modules/commands/bs_control.cpp:69 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel." +msgstr "" +" SAY Faz com que o bot diga determinado texto no canal dado" + +#: modules/commands/greet.cpp:157 +#, fuzzy +msgid "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." +msgstr "" +"Syntax: SASET nickname GREET message\n" +"\n" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary \n" +"access on it." + +#: modules/commands/greet.cpp:131 +#, fuzzy +msgid "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." +msgstr "" +"Sintaxe: SET GREET mensagem\n" +"\n" +"Faz com que a mensagen escolhida se torne a sua mensagem\n" +"de entrada que aparecerá sempre quando você entrar em um canal\n" +"que tenha a opção GREET habilitada, e também tenha acesso a isto." + +#: modules/commands/os_dns.cpp:660 +#, fuzzy +msgid "Manage DNS zones for this network" +msgstr "Você não pode remover o e-mail nesta Rede." + +#: modules/commands/cs_entrymsg.cpp:193 +#, fuzzy +msgid "Manage the channel's entry messages" +msgstr " PERSIST Set the channel as permanent" + +#: modules/commands/ms_ignore.cpp:19 +#, fuzzy +msgid "Manage the memo ignore list" +msgstr " IGNORE Modifica a lista de ignorados dos Services" + +#: modules/commands/ns_ajoin.cpp:230 +#, fuzzy +msgid "Manage your auto join list" +msgstr " AKICK Faz a manutenção da Lista de Autokick" + +#: modules/commands/os_sxline.cpp:233 +#, fuzzy, c-format +msgid "Manipulate the %s list" +msgstr " AKILL Manipula a lista de AKILL" + +#: modules/commands/os_akill.cpp:385 +#, fuzzy +msgid "Manipulate the AKILL list" +msgstr " AKILL Manipula a lista de AKILL" + +#: modules/commands/os_defcon.cpp:176 +#, fuzzy +msgid "Manipulate the DefCon system" +msgstr " DEFCON Manipula o sistema DefCon" + +#: modules/commands/cs_topic.cpp:149 +#, fuzzy +msgid "Manipulate the topic of the specified channel" +msgstr " TOPIC Modifica o tópico de um canal" + +#: modules/commands/bs_botlist.cpp:27 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_forbid.cpp:358 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/ms_ignore.cpp:86 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_list.cpp:153 modules/commands/bs_info.cpp:55 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +msgid "Mask" +msgstr "" + +#: modules/commands/ns_access.cpp:39 +#, fuzzy, c-format +msgid "Mask %s already present on %s's access list." +msgstr "A máscara %s já se encontra em sua lista de acesso." + +#: include/language.h:67 +msgid "Mask must be in the form user@host." +msgstr "" + +#: modules/commands/cs_access.cpp:166 modules/commands/cs_flags.cpp:120 +#: modules/commands/cs_xop.cpp:162 +#, fuzzy +msgid "Masks and unregistered users may not be on access lists." +msgstr "A máscara %s já se encontra em sua lista de acesso." + +#: modules/commands/ns_getemail.cpp:23 +#, fuzzy +msgid "Matches and returns all users that registered using given email" +msgstr "" +" GETEMAIL Encontra e retorna todos os usuários que se\n" +" registraram usando o email fornecido" + +#: modules/commands/os_logsearch.cpp:148 +#, fuzzy, c-format +msgid "Matches for %s:" +msgstr " Trava de modo: %s" + +#: modules/commands/os_stats.cpp:139 +#, c-format +msgid "Maximum users: %d (%s)" +msgstr "Máximo atingido: %d (%s)" + +#: modules/commands/ms_read.cpp:84 modules/commands/ms_read.cpp:86 +#, fuzzy, c-format +msgid "Memo %d from %s (%s)." +msgstr " Trava de modo: %s" + +#: modules/commands/ms_del.cpp:33 modules/commands/ms_del.cpp:101 +#, c-format +msgid "Memo %d has been deleted." +msgstr "Memo %d foi apagado." + +#: modules/commands/ms_ignore.cpp:82 +#, fuzzy +msgid "Memo ignore list is empty." +msgstr "Lista de Ignore dos Services vazia." + +#: modules/commands/ms_set.cpp:199 +#, c-format +msgid "Memo limit disabled for %s." +msgstr "Limite de memos desativado para %s." + +#: modules/commands/ms_set.cpp:185 +#, c-format +msgid "Memo limit for %s set to %d." +msgstr "Limite de memos para %s é agora de %d." + +#: modules/commands/ms_set.cpp:192 +#, c-format +msgid "Memo limit for %s set to 0." +msgstr "Limite de memos para %s é agora de 0." + +#: modules/commands/ms_rsend.cpp:63 modules/commands/ms_send.cpp:51 +#, c-format +msgid "Memo sent to %s." +msgstr "Memo enviado para %s." + +#: modules/commands/ms_list.cpp:131 +#, fuzzy, c-format +msgid "Memos for %s:" +msgstr " Trava de modo: %s" + +#: modules/commands/cs_entrymsg.cpp:116 +#, fuzzy +msgid "Message" +msgstr "GLOBAL mensagem" + +#: modules/commands/ns_set.cpp:1313 +msgid "Message mode" +msgstr "Modo mensagem" + +#: modules/commands/cs_log.cpp:127 +msgid "Method" +msgstr "" + +#: modules/commands/cs_mode.cpp:329 modules/commands/cs_mode.cpp:420 +#, c-format +msgid "Missing parameter for mode %c." +msgstr "" + +#: modules/commands/cs_mode.cpp:449 +msgid "Mode" +msgstr "" + +#: modules/commands/cs_mode.cpp:718 +#, fuzzy, c-format +msgid "Mode %s is a virtual mode and can't be cleared." +msgstr "Nick %s é um nick ilegal e não pode ser usado." + +#: modules/commands/cs_mode.cpp:712 +#, fuzzy, c-format +msgid "Mode %s is not a status or list mode." +msgstr "%s não encontrado na lista de Ignore." + +#: modules/commands/cs_mode.cpp:1065 +#, fuzzy +msgid "Mode lock" +msgstr " Trava de modo: %s" + +#: modules/commands/cs_mode.cpp:466 +#, fuzzy, c-format +msgid "Mode locks for %s:" +msgstr " Trava de modo: %s" + +#: modules/commands/os_list.cpp:43 +msgid "Modes" +msgstr "" + +#: modules/commands/os_mode.cpp:44 +#, c-format +msgid "Modes cleared on %s and the channel destroyed." +msgstr "" + +#: modules/commands/ns_access.cpp:166 +#, fuzzy, c-format +msgid "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." +msgstr "" +"Sintaxe: ACCESS ADD máscara\n" +" ACCESS DEL máscara\n" +" ACCESS LIST\n" +"\n" +"Modifica ou mostra a lista de acesso do seu nick. Esta é\n" +"a lista de endereços a qual será automaticamente reconhecida\n" +"pelo %s como as permitidas a usarem seu nick. Se você\n" +"quer usar um nick de um endereço diferente, você deve usar o\n" +"comando IDENTIFY para identificar-se ao %s\n" +"\n" +"Exemplos:\n" +"\n" +" ACCESS ADD nick@*.provedor.com.br\n" +" Permite o acesso do usuário nick de qualquer\n" +" máquina com o domínio provedor.com.br.\n" +"\n" +" ACCESS DEL nick@*.provedor.com.br\n" +" Reverte o comando anterior\n" +"\n" +" ACCESS LIST\n" +" Mostra a lista de acesso atual." + +#: modules/commands/ns_cert.cpp:319 +msgid "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" +msgstr "" + +#: modules/commands/os_ignore.cpp:341 +#, fuzzy +msgid "Modify the Services ignore list" +msgstr " IGNORE Modifica a lista de ignorados dos Services" + +#: modules/commands/cs_xop.cpp:489 +#, fuzzy, c-format +msgid "Modify the list of %s users" +msgstr " AOP Modifica a lista de AOP (AutoOP) de um canal" + +#: modules/commands/ns_access.cpp:101 +#, fuzzy +msgid "Modify the list of authorized addresses" +msgstr " ACCESS Modifica a lista de endereços autorizados" + +#: modules/commands/cs_access.cpp:498 modules/commands/cs_flags.cpp:373 +#, fuzzy +msgid "Modify the list of privileged users" +msgstr " ACCESS Modifica a lista de usuários privilegiados" + +#: modules/commands/ns_cert.cpp:257 +#, fuzzy +msgid "Modify the nickname client certificate list" +msgstr " IGNORE Modifica a lista de ignorados dos Services" + +#: modules/commands/os_session.cpp:522 +#, fuzzy +msgid "Modify the session-limit exception list" +msgstr " EXCEPTION Modifica a lista de limite de sessões" + +#: modules/commands/os_module.cpp:34 +#, c-format +msgid "Module %s is already loaded." +msgstr "Module %s is already loaded." + +#: modules/commands/os_module.cpp:67 modules/commands/os_module.cpp:139 +#, c-format +msgid "Module %s isn't loaded." +msgstr "Module %s isn't loaded." + +#: modules/commands/os_module.cpp:31 +#, fuzzy, c-format +msgid "Module %s loaded." +msgstr "Módulo %s carregado" + +#: modules/commands/os_module.cpp:98 +#, fuzzy, c-format +msgid "Module %s reloaded." +msgstr "Módulo %s carregado" + +#: modules/commands/os_module.cpp:156 +#, fuzzy, c-format +msgid "Module %s unloaded." +msgstr "Módulo %s descarregado" + +#: modules/commands/os_config.cpp:88 +#, fuzzy +msgid "Module Name" +msgstr "Módulo %s carregado" + +#: modules/commands/os_config.cpp:112 +msgid "Module settings:" +msgstr "" + +#: modules/commands/os_modinfo.cpp:32 +#, fuzzy, c-format +msgid "Module: %s Version: %s Author: %s Loaded: %s" +msgstr "Módulo: %s Versão: %s Autor: %s Carregado: %s" + +#: modules/commands/os_modinfo.cpp:183 +#, c-format +msgid "Module: %s [%s] [%s]" +msgstr "Módulo: %s [%s] [%s]" + +#: modules/commands/cs_access.cpp:697 modules/commands/cs_access.cpp:799 +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +#: modules/commands/cs_list.cpp:75 modules/commands/os_list.cpp:43 +#: modules/commands/os_list.cpp:153 +msgid "Name" +msgstr "" + +#: modules/commands/os_oper.cpp:153 +msgid "Name Type" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:146 +#, fuzzy, c-format +msgid "Network stats for %s:" +msgstr "Lista de acesso para %s:" + +#: modules/commands/os_forbid.cpp:384 +msgid "Never" +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/bs_botlist.cpp:27 +#: modules/commands/hs_request.cpp:305 modules/commands/ns_list.cpp:75 +#: modules/commands/ns_group.cpp:327 +#, fuzzy +msgid "Nick" +msgstr "INFO nick" + +#: modules/commands/ns_register.cpp:42 +#, fuzzy, c-format +msgid "Nick %s has been confirmed." +msgstr "O nick %s foi desregistrado." + +#: modules/commands/os_oper.cpp:95 +#, fuzzy, c-format +msgid "Nick %s is already an operator." +msgstr "O nick %s já está registrado!" + +#: modules/commands/ns_register.cpp:36 +#, fuzzy, c-format +msgid "Nick %s is already confirmed." +msgstr "O nick %s já está registrado!" + +#: modules/commands/os_svs.cpp:46 +#, c-format +msgid "Nick %s is an illegal nickname and cannot be used." +msgstr "Nick %s é um nick ilegal e não pode ser usado." + +#: modules/commands/bs_bot.cpp:81 modules/commands/bs_bot.cpp:181 +#: modules/commands/os_svs.cpp:54 +#, c-format +msgid "Nick %s is currently in use." +msgstr "Nick %s está atualmente em uso." + +#: modules/commands/os_forbid.cpp:512 +#, fuzzy, c-format +msgid "Nick %s is forbidden by %s: %s" +msgstr "Nick %s está atualmente em uso." + +#: modules/commands/os_forbid.cpp:514 +#, fuzzy, c-format +msgid "Nick %s is forbidden." +msgstr "Nick %s não está em uso no momento." + +#: modules/commands/os_oper.cpp:134 +#, fuzzy, c-format +msgid "Nick %s is not a Services Operator." +msgstr "%s is a services operator of type %s." + +#: modules/commands/ns_info.cpp:34 +#, c-format +msgid "Nick %s is part of this Network's Services." +msgstr "Nick %s é parte dos Services desta Rede." + +#: include/language.h:79 +#, fuzzy, c-format +msgid "Nick %s isn't currently in use." +msgstr "Nick %s está atualmente em uso." + +#: include/language.h:78 +#, fuzzy, c-format +msgid "Nick %s isn't registered." +msgstr "Nick %s registrado." + +#: modules/commands/os_svs.cpp:39 +#, c-format +msgid "Nick %s was truncated to %d characters." +msgstr "Nick %s foi truncado para %d caracteres." + +#: modules/commands/ns_set.cpp:1135 +#, c-format +msgid "Nick %s will expire." +msgstr "Nick %s will expire." + +#: modules/commands/ns_set.cpp:1129 +#, c-format +msgid "Nick %s will not expire." +msgstr "Nick %s will not expire." + +#: modules/commands/ms_check.cpp:60 +#, c-format +msgid "Nick %s doesn't have a memo from you." +msgstr "O nick %s não possui nenhum memo seu." + +#: modules/commands/ns_logout.cpp:48 +#, c-format +msgid "Nick %s has been logged out." +msgstr "O nick %s foi desconectado." + +#: modules/commands/ns_group.cpp:272 +#, c-format +msgid "Nick %s has been ungrouped from %s." +msgstr "Nick %s has been ungrouped from %s." + +#: include/language.h:81 +#, fuzzy, c-format +msgid "Nick %s is currently suspended." +msgstr "Nick %s foi suspendido." + +#: modules/commands/ns_group.cpp:250 +#, fuzzy, c-format +msgid "Nick %s is not in your group." +msgstr "The nick %s is not in your group." + +#: modules/commands/ns_suspend.cpp:180 +#, fuzzy, c-format +msgid "Nick %s is not suspended." +msgstr "Nick %s foi suspendido." + +#: modules/commands/ns_suspend.cpp:190 +#, c-format +msgid "Nick %s is now released." +msgstr "Nick %s foi liberado." + +#: modules/commands/ns_suspend.cpp:138 +#, c-format +msgid "Nick %s is now suspended." +msgstr "Nick %s foi suspendido." + +#: modules/commands/cs_seen.cpp:275 +#, c-format +msgid "Nick too long, max length is %u characters." +msgstr "" + +#: modules/commands/ns_drop.cpp:53 +#, c-format +msgid "Nickname %s has been dropped." +msgstr "O nick %s foi desregistrado." + +#: include/language.h:97 +#, fuzzy, c-format +msgid "Nickname %s is already registered!" +msgstr "O canal %s já está registrado!" + +#: include/language.h:96 +#, fuzzy, c-format +msgid "Nickname %s may not be registered." +msgstr "O canal %s não pode ser registrado." + +#: modules/commands/ns_register.cpp:226 +#, fuzzy, c-format +msgid "Nickname %s registered under your user@host-mask: %s" +msgstr "O nick %s foi registrado em sua conta: %s" + +#: modules/commands/ns_register.cpp:228 +#, fuzzy, c-format +msgid "Nickname %s registered." +msgstr "Nick %s registrado." + +#: modules/commands/cs_set.cpp:1307 +#, fuzzy +msgid "No auto-op" +msgstr "Auto-op" + +#: modules/commands/bs_assign.cpp:252 +msgid "No bot" +msgstr "Sem bot" + +#: modules/commands/cs_set.cpp:1303 modules/commands/ns_set.cpp:1317 +#, fuzzy +msgid "No expire" +msgstr "não expira" + +#: modules/commands/help.cpp:184 +#, c-format +msgid "No help available for %s." +msgstr "Nenhuma ajuda disponível para %s." + +#: modules/commands/os_modinfo.cpp:61 +#, fuzzy, c-format +msgid "No information about module %s is available." +msgstr "Nenhuma informação sobre o módulo %s está disponível." + +#: modules/commands/cs_enforce.cpp:177 +#, fuzzy, c-format +msgid "No limit is set on %s." +msgstr "Limite de memos para %s é agora de %d." + +#: modules/commands/os_news.cpp:37 +msgid "No logon news items to delete!" +msgstr "Nenhum logon news para remover!" + +#: modules/commands/os_logsearch.cpp:133 +#, fuzzy, c-format +msgid "No matches for %s found." +msgstr "Nenhum email listado para %s." + +#: modules/commands/cs_xop.cpp:294 +#, fuzzy, c-format +msgid "No matching entries on %s %s list." +msgstr "Resultado não encontrado na lista de AOP do %s." + +#: modules/commands/cs_access.cpp:269 modules/commands/cs_access.cpp:433 +#: modules/commands/cs_flags.cpp:335 modules/commands/cs_xop.cpp:428 +#, c-format +msgid "No matching entries on %s access list." +msgstr "Resultado não encontrado na lista de acesso do %s." + +#: modules/commands/cs_akick.cpp:224 modules/commands/cs_akick.cpp:368 +#, c-format +msgid "No matching entries on %s autokick list." +msgstr "Nenhum resultado encontrado na lista de akick do %s." + +#: modules/commands/bs_badwords.cpp:166 modules/commands/bs_badwords.cpp:246 +#, c-format +msgid "No matching entries on %s bad words list." +msgstr "Nenhum resultado correspondente encontrado na lista do %s." + +#: modules/commands/os_session.cpp:145 modules/commands/os_session.cpp:490 +msgid "No matching entries on session-limit exception list." +msgstr "Nenhum resultado encontrado na lista de limite de sessões." + +#: modules/commands/os_sxline.cpp:28 modules/commands/os_sxline.cpp:177 +#, fuzzy, c-format +msgid "No matching entries on the %s list." +msgstr "Resultado não encontrado na lista de AOP do %s." + +#: modules/commands/os_akill.cpp:29 modules/commands/os_akill.cpp:320 +msgid "No matching entries on the AKILL list." +msgstr "Nenhum resultado equivalente na lista de AKILL." + +#: modules/commands/ms_cancel.cpp:77 +msgid "No memo was cancelable." +msgstr "Nenhum memo foi cancelado." + +#: modules/commands/ms_read.cpp:65 +msgid "No memos to display." +msgstr "" + +#: modules/commands/os_modinfo.cpp:187 +#, fuzzy +msgid "No modules currently loaded matching that criteria." +msgstr "Nenhum módulo carregado atualmente." + +#: modules/commands/ns_recover.cpp:55 +msgid "No one is using your nick, and services are not holding it." +msgstr "" + +#: modules/commands/os_login.cpp:30 modules/commands/os_login.cpp:77 +msgid "No oper block for your nick." +msgstr "" + +#: modules/commands/os_news.cpp:47 +msgid "No oper news items to delete!" +msgstr "Nenhum OperNews para remover!" + +#: modules/commands/os_news.cpp:57 +msgid "No random news items to delete!" +msgstr "Nenhum item RandomNews para deletar!" + +#: modules/commands/hs_list.cpp:111 +msgid "No records to display." +msgstr "" + +#: modules/commands/ns_getemail.cpp:47 +#, fuzzy, c-format +msgid "No registrations matching %s were found." +msgstr "* Impedido o registro de novos nicks" + +#: modules/commands/hs_request.cpp:220 modules/commands/hs_request.cpp:276 +#, c-format +msgid "No request for nick %s found." +msgstr "" + +#: src/access.cpp:55 +msgid "No signed kick when SIGNKICK LEVEL is used" +msgstr "" + +#: modules/extra/stats/cs_fantasy_top.cpp:159 +#: modules/extra/stats/cs_fantasy_stats.cpp:156 +#, fuzzy, c-format +msgid "No stats for %s." +msgstr "Lista de acesso para %s:" + +#: modules/commands/os_info.cpp:201 +#, fuzzy, c-format +msgid "No such info \"%s\" on %s." +msgstr "%s has been invited to %s." + +#: modules/commands/cs_ban.cpp:219 modules/commands/cs_kick.cpp:118 +#, fuzzy, c-format +msgid "No users on %s match %s." +msgstr "Modos do usuário %s alterados." + +#: modules/commands/bs_assign.cpp:188 +#, fuzzy, c-format +msgid "No-bot mode is now off on channel %s." +msgstr "Modo NOBOT está agora ATIVADO no canal %s." + +#: modules/commands/bs_assign.cpp:181 +#, fuzzy, c-format +msgid "No-bot mode is now on on channel %s." +msgstr "Modo NOBOT está agora ATIVADO no canal %s." + +#: modules/commands/os_mode.cpp:64 +#, c-format +msgid "Non-status modes cleared on %s." +msgstr "" + +#: modules/commands/os_dns.cpp:226 modules/commands/bs_info.cpp:58 +msgid "None" +msgstr "Nenhuma" + +#: modules/commands/cs_set.cpp:1029 +#, c-format +msgid "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." +msgstr "" + +#: modules/commands/cs_mode.cpp:380 modules/commands/cs_mode.cpp:437 +msgid "Nothing to do." +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:201 modules/commands/ms_list.cpp:64 +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_log.cpp:127 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +#: modules/commands/ns_ajoin.cpp:100 +msgid "Number" +msgstr "" + +#: modules/commands/os_news.cpp:41 +msgid "OPERNEWS {ADD|DEL|LIST} [text|num]" +msgstr "OPERNEWS {ADD|DEL|LIST} [texto|núm]" + +#: modules/commands/ns_info.cpp:68 modules/commands/ns_info.cpp:72 +#, fuzzy +msgid "Online from" +msgstr " Está online em: %s" + +#: modules/commands/os_oper.cpp:138 +#, c-format +msgid "" +"Oper %s is configured in the configuration file(s) and can not be removed by " +"this command." +msgstr "" + +#: modules/commands/os_info.cpp:268 +msgid "Oper Info" +msgstr "" + +#: modules/commands/os_info.cpp:182 modules/commands/os_info.cpp:221 +#, fuzzy, c-format +msgid "Oper info list for %s is empty." +msgstr "Lista de acesso para %s está vazia." + +#: modules/commands/os_news.cpp:46 +#, c-format +msgid "Oper news item #%d deleted." +msgstr "OperNews removido #%d." + +#: modules/commands/os_news.cpp:45 +#, fuzzy, c-format +msgid "Oper news item #%s not found!" +msgstr "OperNews não encontrado #%d!" + +#: modules/commands/os_news.cpp:42 +msgid "Oper news items:" +msgstr "Oper News itens:" + +#: modules/commands/os_oper.cpp:148 +#, c-format +msgid "Oper privileges removed from %s (%s)." +msgstr "" + +#: modules/commands/os_oper.cpp:101 modules/commands/os_oper.cpp:189 +#, fuzzy, c-format +msgid "Oper type %s has not been configured." +msgstr "O nick %s foi desregistrado." + +#: modules/commands/os_oline.cpp:37 +#, c-format +msgid "Operflags %s have been added for %s." +msgstr "As Operflags %s foram adicionadas para %s." + +#: modules/commands/os_oline.cpp:43 +#, fuzzy, c-format +msgid "Operflags %s have been removed from %s." +msgstr "As Operflags %s foram adicionadas para %s." + +#: modules/commands/os_oper.cpp:193 +#, c-format +msgid "Opertype %s has no allowed commands." +msgstr "" + +#: modules/commands/os_oper.cpp:215 +#, c-format +msgid "Opertype %s has no allowed privileges." +msgstr "" + +#: modules/commands/os_oper.cpp:237 +#, c-format +msgid "Opertype %s receives modes %s once identified." +msgstr "" + +#: modules/commands/bs_kick.cpp:1219 +msgid "Ops protection" +msgstr "Proteção de OPs" + +#: src/misc.cpp:258 modules/commands/bs_info.cpp:58 +#, fuzzy +msgid "Options" +msgstr " Opções: %s" + +#: modules/commands/os_dns.cpp:668 +#, fuzzy +msgid "POOL server.name" +msgstr "NOOP {SET|REVOKE} servidor" + +#: modules/commands/cs_mode.cpp:449 +msgid "Param" +msgstr "" + +#: modules/commands/ns_identify.cpp:38 +msgid "Password accepted - you are now recognized." +msgstr "Senha aceita - você está agora reconhecido." + +#: modules/commands/os_login.cpp:44 +#, fuzzy +msgid "Password accepted." +msgstr "Senha incorreta." + +#: include/language.h:85 +msgid "Password authentication required for that command." +msgstr "" + +#: modules/commands/ns_set.cpp:152 modules/commands/ns_set.cpp:218 +#, fuzzy, c-format +msgid "Password for %s changed to %s." +msgstr "Successor do canal %s alterado para %s." + +#: modules/commands/ns_set.cpp:154 modules/commands/ns_set.cpp:220 +#, fuzzy, c-format +msgid "Password for %s changed." +msgstr "Senha para %s foi enviada." + +#: modules/commands/ns_getpass.cpp:38 +#, c-format +msgid "Password for %s is %s." +msgstr "Senha para %s é %s." + +#: include/language.h:71 +#, fuzzy +msgid "Password incorrect." +msgstr "Senha incorreta." + +#: modules/commands/ns_resetpass.cpp:39 +#, c-format +msgid "Password reset email for %s has been sent." +msgstr "Password reset email for %s has been sent." + +#: modules/commands/cs_set.cpp:1289 +msgid "Peace" +msgstr "Paz" + +#: modules/commands/cs_set.cpp:440 +#, fuzzy, c-format +msgid "Peace option for %s is now off." +msgstr "Opção Peace para %s está agora ATIVADA." + +#: modules/commands/cs_set.cpp:434 +#, fuzzy, c-format +msgid "Peace option for %s is now on." +msgstr "Opção Peace para %s está agora ATIVADA." + +#: modules/commands/cs_set.cpp:1301 +#, fuzzy +msgid "Persistent" +msgstr "Persistant" + +#: include/language.h:126 +msgid "Please contact an Operator to get a vHost assigned to this nick." +msgstr "" + +#: include/language.h:73 +msgid "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." +msgstr "" + +#: modules/commands/os_jupe.cpp:30 +#, fuzzy +msgid "Please use a valid server name when juping." +msgstr "Por favor, use um nome de servidor válido quando estiver \"jupando\"." + +#: include/language.h:104 +msgid "Please use the symbol of # when attempting to register." +msgstr "" + +#: src/mail.cpp:78 +#, c-format +msgid "Please wait %d seconds and retry." +msgstr "Por favor aguarde %d segundos e tente novamente." + +#: modules/commands/hs_request.cpp:158 +#, fuzzy, c-format +msgid "Please wait %d seconds before requesting a new vHost." +msgstr "Por favor aguarde %d segundos antes de usar o comando SEND novamente." + +#: modules/commands/ms_rsend.cpp:58 modules/commands/ms_send.cpp:57 +#, fuzzy, c-format +msgid "Please wait %d seconds before using the %s command again." +msgstr "Por favor aguarde %d segundos antes de usar o comando SEND novamente." + +#: modules/commands/ns_group.cpp:149 +#, c-format +msgid "Please wait %d seconds before using the GROUP command again." +msgstr "Por favor espere %d segundos antes de usar o comando GROUP novamente." + +#: modules/commands/ns_register.cpp:198 +#, c-format +msgid "Please wait %d seconds before using the REGISTER command again." +msgstr "" +"Por favor espere %d segundos antes de usar o comando REGISTER novamente." + +#: modules/commands/os_dns.cpp:628 +#, c-format +msgid "Pooled %s." +msgstr "" + +#: modules/commands/os_dns.cpp:237 +msgid "Pooled/Active" +msgstr "" + +#: modules/commands/os_dns.cpp:239 +msgid "Pooled/Not Active" +msgstr "" + +#: modules/commands/bs_set.cpp:161 +msgid "Prevent a bot from being assigned by non IRC operators" +msgstr "" + +#: modules/commands/bs_assign.cpp:153 +#, fuzzy +msgid "Prevent a bot from being assigned to a channel" +msgstr "" +" SUSPEND Previne um canal de ser registrado/usado,\n" +" preservando os dados do canal e suas configurações" + +#: modules/commands/cs_suspend.cpp:58 +#, fuzzy +msgid "Prevent a channel from being used preserving channel data and settings" +msgstr "" +" SUSPEND Previne um canal de ser registrado/usado,\n" +" preservando os dados do canal e suas configurações" + +#: modules/commands/cs_set.cpp:1043 +#, fuzzy +msgid "Prevent the channel from expiring" +msgstr " NOEXPIRE Prevent the channel from expiring" + +#: modules/commands/ns_list.cpp:186 +#, fuzzy +msgid "Prevent the nickname from appearing in the LIST command" +msgstr "" +" PRIVATE Prevent the nickname from appearing in a\n" +" /msg %s LIST" + +#: modules/commands/ns_set.cpp:1104 +#, fuzzy +msgid "Prevent the nickname from expiring" +msgstr " NOEXPIRE Prevent the nickname from expiring" + +#: src/access.cpp:46 +msgid "Prevents users being kicked by Services" +msgstr "" + +#: modules/commands/ns_list.cpp:297 modules/commands/cs_list.cpp:262 +#: modules/commands/bs_info.cpp:58 +msgid "Private" +msgstr "Privado" + +#: modules/commands/bs_set.cpp:190 +#, fuzzy, c-format +msgid "Private mode of bot %s is now off." +msgstr "Modo Privado do bot %s está agora ATIVADO." + +#: modules/commands/bs_set.cpp:185 +#, fuzzy, c-format +msgid "Private mode of bot %s is now on." +msgstr "Modo Privado do bot %s está agora ATIVADO." + +#: modules/commands/cs_list.cpp:220 +#, fuzzy, c-format +msgid "Private option for %s is now off." +msgstr "Opção Private para %s está agora ATIVADA." + +#: modules/commands/cs_list.cpp:214 +#, fuzzy, c-format +msgid "Private option for %s is now on." +msgstr "Opção Private para %s está agora ATIVADA." + +#: modules/commands/ns_list.cpp:221 +#, fuzzy, c-format +msgid "Private option is now off for %s." +msgstr "Private option is now ON for %s." + +#: modules/commands/ns_list.cpp:215 +#, fuzzy, c-format +msgid "Private option is now on for %s." +msgstr "Private option is now ON for %s." + +#: modules/commands/cs_flags.cpp:281 +#, c-format +msgid "Privilege %s added to %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/cs_flags.cpp:283 +#, c-format +msgid "Privilege %s removed from %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/ns_set.cpp:1309 +msgid "Protection" +msgstr "Proteção" + +#: modules/commands/ns_set.cpp:721 +#, fuzzy, c-format +msgid "Protection is now off for %s." +msgstr "Protection is now ON for %s." + +#: modules/commands/ns_set.cpp:700 +#, fuzzy, c-format +msgid "Protection is now on for %s, with a reduced delay." +msgstr "Protection is now ON for %s, with a reduced delay." + +#: modules/commands/ns_set.cpp:710 +#, fuzzy, c-format +msgid "Protection is now on for %s, with no delay." +msgstr "Protection is now ON for %s, with no delay." + +#: modules/commands/ns_set.cpp:692 +#, fuzzy, c-format +msgid "Protection is now on for %s." +msgstr "Protection is now ON for %s." + +#: modules/commands/os_chankill.cpp:100 +#, fuzzy +msgid "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." +msgstr "" +"Sintaxe: CHANKILL [+tempo] canal motivo\n" +"Adiciona um AKILL para cada nick no canal especificado. Isso\n" +"usa por completo todo o host real ident@host para cada nick;\n" +"em seguida, força o AKILL." + +#: modules/commands/ns_set.cpp:1307 +#, fuzzy +msgid "Quick protection" +msgstr "Proteção de Voices" + +#: modules/commands/os_news.cpp:51 +msgid "RANDOMNEWS {ADD|DEL|LIST} [text|num]" +msgstr "RANDOMNEWS {ADD|DEL|LIST} [texto|núm]" + +#: modules/commands/cs_enforce.cpp:99 +msgid "REGONLY enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:68 +msgid "RESTRICTED enforced by " +msgstr "" + +#: modules/commands/os_noop.cpp:21 +#, fuzzy +msgid "REVOKE server" +msgstr "NOOP {SET|REVOKE} servidor" + +#: modules/commands/os_news.cpp:56 +#, c-format +msgid "Random news item #%d deleted." +msgstr "RandomNews item #%d deletado." + +#: modules/commands/os_news.cpp:55 +#, fuzzy, c-format +msgid "Random news item #%s not found!" +msgstr "RandomNews item #%d não encontrado!" + +#: modules/commands/os_news.cpp:52 +msgid "Random news items:" +msgstr "Random News itens:" + +#: modules/commands/ms_read.cpp:112 +#, fuzzy +msgid "Read a memo or memos" +msgstr " READ Lê a(s) mensagem(ns)" + +#: modules/commands/bs_info.cpp:56 +#, fuzzy +msgid "Real name" +msgstr " RealName: %s" + +#: modules/commands/os_list.cpp:153 +#, fuzzy +msgid "Realname" +msgstr " RealName: %s" + +#: modules/commands/os_ignore.cpp:266 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:204 modules/commands/os_forbid.cpp:358 +#: modules/commands/cs_akick.cpp:392 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:361 +msgid "Reason" +msgstr "" + +#: src/xline.cpp:386 +#, fuzzy, c-format +msgid "Reason for %s updated." +msgstr "Successor do canal %s removido." + +#: modules/commands/ns_recover.cpp:214 +msgid "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." +msgstr "" + +#: modules/commands/cs_access.cpp:741 +#, fuzzy +msgid "Redefine the meanings of access levels" +msgstr " LEVELS Redefine os níveis de acesso" + +#: modules/commands/ns_recover.cpp:149 +#, fuzzy +msgid "Regains control of your nick" +msgstr " RELEASE Retoma a custódia do seu nick após um RECOVER" + +#: modules/commands/os_sxline.cpp:330 modules/commands/os_sxline.cpp:545 +#: modules/commands/os_akill.cpp:129 +#, fuzzy +msgid "Regex is disabled." +msgstr "%s está ativada" + +#: modules/commands/os_sxline.cpp:459 modules/commands/os_sxline.cpp:694 +#: modules/commands/os_akill.cpp:444 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." +msgstr "" + +#: modules/commands/os_ignore.cpp:386 modules/commands/os_forbid.cpp:428 +#: modules/commands/ns_list.cpp:172 modules/commands/cs_list.cpp:167 +#: modules/commands/os_list.cpp:119 modules/commands/os_list.cpp:255 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." +msgstr "" + +#: modules/commands/cs_register.cpp:19 +#, fuzzy +msgid "Register a channel" +msgstr " REGISTER Registra um nick" + +#: modules/commands/ns_register.cpp:120 +#, fuzzy +msgid "Register a nickname" +msgstr " REGISTER Registra um nick" + +#: modules/commands/ns_info.cpp:89 modules/commands/cs_info.cpp:55 +#, fuzzy +msgid "Registered" +msgstr " Hora de registro: %s" + +#: modules/commands/os_stats.cpp:184 +#, c-format +msgid "Registered channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:190 +#, c-format +msgid "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:187 +#, c-format +msgid "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/cs_enforce.cpp:105 +#, c-format +msgid "Registered only enforced on %s." +msgstr "" + +#: modules/commands/cs_register.cpp:86 +#, fuzzy, c-format +msgid "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." +msgstr "" +"Sintaxe: REGISTER canal descrição\n" +"\n" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which must be included, is a\n" +"general description of the channel's purpose.\n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel.\n" +"See the ACCESS command (/msg %s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname. If you haven't,\n" +"/msg %s HELP for information on how to do so." + +#: modules/commands/ns_register.cpp:269 +#, fuzzy, c-format +msgid "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." +msgstr "" +"Sintaxe: REGISTER senha [email]\n" +"\n" +"Registra seu nick no banco de dados do %s. Uma vez\n" +"que seu nick está registrado, você pode usar os comandos\n" +"SET e ACCESS para configurar as opções do seu nick como\n" +"você preferir depois. Certifique-se de lembrar sua senha\n" +"durante o registro, você precisará dela para fazer alterações\n" +"no seu nick futuramente.\n" +"(Lembre-se que maiúsculas diferem, como: ANOPE, Anope e \n" +"anope são senhas diferentes!)\n" +"\n" +"Sugestões ao escolher sua senha:\n" +"\n" +"As senhas não devem ser de fácil adivinhação. Por exemplo,\n" +"usar seu nome como senha é uma péssima idéia. Utilizar seu\n" +"nick como senha é uma idéia muito pior e, de fato, o %s\n" +"não permitirá isso. Da mesma maneira, senhas curtas são\n" +"vulneráveis a testes de erro-e-acerto, então você deve\n" +"escolher uma senha com pelo menos 5 caracteres. Finalmente,\n" +"o caractere \"ESPAÇO\" não pode ser usado em senhas.\n" +"\n" +"O parâmetro email é opcional e servirá para setar um\n" +"email para seu nick. Entretanto, o email pode ser obrigatório\n" +"em algumas Redes de IRC.\n" +"Sua privacidade é respeitada; este e-mail nunca será dado\n" +"para terceiros.\n" +"\n" +"Este comando servirá também para criar um GRUPO para o seu\n" +"nick, e irá permitir que você registre outros nicks e divida\n" +"as mesmas configurações, os mesmos memos e os mesmos \n" +"privilégios em canais. Para maiores informações neste recurso,\n" +"digite /msg %s HELP GROUP." + +#: modules/commands/ns_register.cpp:145 +#, fuzzy +msgid "Registration is currently disabled." +msgstr "Desculpe, o registro de canais está temporariamente desativado." + +#: modules/commands/cs_set.cpp:400 +#, fuzzy +msgid "Regulate the use of critical commands" +msgstr " PEACE Regula o uso de comandos críticos" + +#: modules/commands/hs_request.cpp:283 +#, fuzzy +msgid "Reject the requested vHost for the given nick." +msgstr " STATUS Retorna o status do owner de um determinado nick" + +#: modules/commands/hs_request.cpp:240 +#, fuzzy +msgid "Reject the requested vHost of a user" +msgstr " DEL Deleta o vHost de outro usuário" + +#: modules/commands/cs_suspend.cpp:151 +#, fuzzy +msgid "Releases a suspended channel" +msgstr " UNSUSPEND Libera um canal suspenso" + +#: modules/commands/cs_suspend.cpp:191 +#, fuzzy +msgid "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." +msgstr "" +"Sintaxe: UNSUSPEND canal\n" +"\n" +"Libera um canal suspenso. Todos os dados e configurações\n" +"são preservados de antes da suspensão." + +#: modules/commands/os_module.cpp:56 +#, fuzzy +msgid "Reload a module" +msgstr " MODLOAD Carrega um módulo" + +#: modules/commands/os_reload.cpp:19 +#, fuzzy +msgid "Reload services' configuration file" +msgstr " RELOAD Recarrega o arquivo de configuração dos Services" + +#: modules/commands/ns_group.cpp:236 +#, fuzzy +msgid "Remove a nick from a group" +msgstr " UNGROUP Remove a nick from a group" + +#: modules/commands/cs_unban.cpp:19 +#, fuzzy +msgid "Remove all bans preventing a user from entering a channel" +msgstr "" +" UNBAN Remove all bans preventing a user from entering a channel" + +#: modules/commands/os_noop.cpp:19 +#, fuzzy +msgid "Remove all operators from a server remotely" +msgstr "" +" NOOP Remove temporariamente todas as O:lines de um \n" +" servidor remotamente" + +#: modules/commands/os_dns.cpp:543 +#, fuzzy, c-format +msgid "Removed IP %s from %s." +msgstr " Trava de modo: %s" + +#: modules/commands/os_dns.cpp:460 +#, c-format +msgid "Removed server %s from zone %s." +msgstr "" + +#: modules/commands/os_dns.cpp:483 +#, c-format +msgid "Removed server %s." +msgstr "" + +#: modules/commands/cs_mode.cpp:909 +#, c-format +msgid "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." +msgstr "" + +#: modules/commands/cs_mode.cpp:890 +#, fuzzy, c-format +msgid "Removes %s status from you or the specified nick on a channel" +msgstr " OP Atribui status de OP a um nick no canal" + +#: modules/commands/cs_updown.cpp:146 +#, fuzzy +msgid "Removes a selected nicks status from a channel" +msgstr " KICK Kicka (expulsa) um nick de um canal" + +#: modules/commands/cs_updown.cpp:223 +msgid "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." +msgstr "" + +#: src/xline.cpp:412 +#, c-format +msgid "Removing %s because %s covers it." +msgstr "" + +#: modules/commands/bs_kick.cpp:1171 modules/commands/bs_kick.cpp:1173 +#: modules/commands/bs_kick.cpp:1176 +#, fuzzy +msgid "Repeat kicker" +msgstr " Kick por repetição: %s" + +#: modules/commands/hs_request.cpp:78 +#, fuzzy +msgid "Request a vHost for your nick" +msgstr "Não há endereço de email ajustado para o seu nick." + +#: modules/commands/hs_request.cpp:179 +msgid "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." +msgstr "" + +#: modules/commands/ns_register.cpp:312 +#, fuzzy +msgid "Resend registration confirmation email" +msgstr " RELOAD Recarrega o arquivo de configuração dos Services" + +#: modules/commands/cs_set.cpp:621 +#, fuzzy +msgid "Restrict access to the channel" +msgstr " RESTRICTED Acesso restrito ao canal" + +#: modules/commands/cs_set.cpp:1291 +#, fuzzy +msgid "Restricted access" +msgstr "Acesso restrito" + +#: modules/commands/cs_set.cpp:661 +#, fuzzy, c-format +msgid "Restricted access option for %s is now off." +msgstr "Opção de acesso restrito para %s está agora ATIVADA." + +#: modules/commands/cs_set.cpp:655 +#, fuzzy, c-format +msgid "Restricted access option for %s is now on." +msgstr "Opção de acesso restrito para %s está agora ATIVADA." + +#: modules/commands/cs_enforce.cpp:73 +#, fuzzy, c-format +msgid "Restricted enforced on %s." +msgstr "Acesso restrito" + +#: modules/commands/cs_set.cpp:335 +#, fuzzy +msgid "Retain modes when channel is not in use" +msgstr " KEEPTOPIC Mantem o tópico quando o canal não está em uso" + +#: modules/commands/cs_topic.cpp:20 +#, fuzzy +msgid "Retain topic when channel is not in use" +msgstr " KEEPTOPIC Mantem o tópico quando o canal não está em uso" + +#: modules/commands/ns_getpass.cpp:19 +#, fuzzy +msgid "Retrieve the password for a nickname" +msgstr " GETPASS Recupera a senha de um determinado nick" + +#: modules/commands/hs_request.cpp:296 +msgid "Retrieves the vhost requests" +msgstr "" + +#: modules/commands/cs_getkey.cpp:19 +#, fuzzy +msgid "Returns the key of the given channel" +msgstr " GETKEY Retorna a key (do modo +k) do canal fornecido" + +#: modules/commands/cs_getkey.cpp:57 +#, fuzzy +msgid "Returns the key of the given channel." +msgstr " GETKEY Retorna a key (do modo +k) do canal fornecido" + +#: modules/commands/ns_getemail.cpp:58 +#, fuzzy +msgid "Returns the matching accounts that used given email." +msgstr " GETKEY Retorna a key (do modo +k) do canal fornecido" + +#: modules/commands/ns_status.cpp:19 +#, fuzzy +msgid "Returns the owner status of the given nickname" +msgstr " STATUS Retorna o status do owner de um determinado nick" + +#: modules/commands/ns_getpass.cpp:50 +#, fuzzy +msgid "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." +msgstr "" +"Sintaxe: GETPASS nick\n" +"\n" +"Mostra a senha de um nick especificado.\n" +"Note que sempre que este comando for usado, uma mensagem\n" +"incluindo o nick da pessoa que emitiu o comando e o nick\n" +"no qual foi usado serão gravados e enviados para WALLOPS/GLOBOPS.\n" +"\n" +"Este comando não fica disponível quando a encriptação está habilitada." + +#: modules/commands/ns_status.cpp:55 +#, fuzzy +msgid "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." +msgstr "" +"Sintaxe: STATUS nick...\n" +"\n" +"Retorna se o usuário que está usando um determinado nick\n" +"é reconhecio como dono do nick. \n" +"A resposta tem este formato:\n" +"\n" +" nick código-de-status account\n" +"\n" +"where nick is the nickname sent with the command,\n" +"código-de-status is one of the following, and account\n" +"is the account they are logged in as.\n" +"\n" +" 0 - usuário não está conectado ou o nick não está registrado\n" +" 1 - usuário não reconhecido como dono do nick\n" +" 2 - usuário reconhecido como dono só pela lista de acesso\n" +" 3 - usuário reconhecido como dono via identificação por senha\n" +"\n" +"Até 16 nicks podem ser enviados com cada comando; o resto será\n" +"ignorado. Se nenhum nick for fornecido, seu status será exibido." + +#: modules/commands/bs_kick.cpp:1181 modules/commands/bs_kick.cpp:1183 +#: modules/commands/bs_kick.cpp:1186 +#, fuzzy +msgid "Reverses kicker" +msgstr " Kick por reversos: %s" + +#: modules/commands/ns_logout.cpp:21 +#, fuzzy +msgid "Reverses the effect of the IDENTIFY command" +msgstr " LOGOUT Reverte o efeito do comando IDENTIFY" + +#: modules/commands/os_noop.cpp:20 +#, fuzzy +msgid "SET server" +msgstr "NOOP {SET|REVOKE} servidor" + +#: modules/commands/os_dns.cpp:667 +msgid "SET server.name option value" +msgstr "" + +#: modules/commands/ns_cert.cpp:378 +#, fuzzy, c-format +msgid "SSL certificate fingerprint accepted, you are now identified to %s." +msgstr "Senha aceita - você está agora reconhecido." + +#: modules/commands/ns_cert.cpp:398 +#, fuzzy +msgid "SSL certificate fingerprint accepted, you are now identified." +msgstr "Senha aceita - você está agora reconhecido." + +#: modules/commands/cs_enforce.cpp:137 +#, c-format +msgid "SSL only enforced on %s." +msgstr "" + +#: modules/commands/cs_enforce.cpp:131 +msgid "SSLONLY enforced by " +msgstr "" + +#: modules/commands/os_shutdown.cpp:47 +#, fuzzy +msgid "Save databases and restart Services" +msgstr " RESTART Salva os dados e reinicia os Services" + +#: modules/commands/os_logsearch.cpp:32 +msgid "Searches logs for a matching pattern" +msgstr "" + +#: modules/commands/cs_set.cpp:1295 +#, fuzzy +msgid "Secure founder" +msgstr "Founder Seguro" + +#: modules/commands/cs_set.cpp:786 +#, fuzzy, c-format +msgid "Secure founder option for %s is now off." +msgstr "Opção Secure Founder para %s está agora ATIVADA." + +#: modules/commands/cs_set.cpp:780 +#, fuzzy, c-format +msgid "Secure founder option for %s is now on." +msgstr "Opção Secure Founder para %s está agora ATIVADA." + +#: modules/commands/cs_set.cpp:1297 +#, fuzzy +msgid "Secure ops" +msgstr "OPs Seguros" + +#: modules/commands/cs_set.cpp:850 +#, fuzzy, c-format +msgid "Secure ops option for %s is now off." +msgstr "Opção Secure OPs para %s está agora ATIVADA." + +#: modules/commands/cs_set.cpp:844 +#, fuzzy, c-format +msgid "Secure ops option for %s is now on." +msgstr "Opção Secure OPs para %s está agora ATIVADA." + +#: modules/commands/cs_set.cpp:723 +#, fuzzy, c-format +msgid "Secure option for %s is now off." +msgstr "Opção Secure para %s está agora ATIVADA." + +#: modules/commands/cs_set.cpp:717 +#, fuzzy, c-format +msgid "Secure option for %s is now on." +msgstr "Opção Secure para %s está agora ATIVADA." + +#: modules/commands/ns_set.cpp:1044 +#, fuzzy, c-format +msgid "Secure option is now off for %s." +msgstr "Secure option is now ON for %s." + +#: modules/commands/ns_set.cpp:1038 +#, fuzzy, c-format +msgid "Secure option is now on for %s." +msgstr "Secure option is now ON for %s." + +#: modules/commands/cs_enforce.cpp:42 +#, fuzzy, c-format +msgid "Secureops enforced on %s." +msgstr "Secure option is now ON for %s." + +#: modules/commands/cs_set.cpp:1293 modules/commands/ns_set.cpp:1311 +msgid "Security" +msgstr "Segurança" + +#: modules/commands/cs_xop.cpp:570 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the access list." +msgstr "" +"Digite /msg %s HELP SET opção para maiores informações\n" +"sobre uma opção em particular." + +#: modules/commands/cs_xop.cpp:573 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the flags system." +msgstr "" +"Digite /msg %s HELP SET opção para maiores informações\n" +"sobre uma opção em particular." + +#: modules/commands/ms_send.cpp:24 +#, fuzzy +msgid "Send a memo to a nick or channel" +msgstr " SEND Envia uma mensagem para um nick ou para um canal" + +#: modules/commands/ms_staff.cpp:24 +#, fuzzy +msgid "Send a memo to all opers/admins" +msgstr " STAFF Envia um memo para todos os opers/admins" + +#: modules/commands/ms_sendall.cpp:24 +#, fuzzy +msgid "Send a memo to all registered users" +msgstr " SENDALL Envia um memo para todos os usuários registrados" + +#: modules/commands/gl_global.cpp:21 +#, fuzzy +msgid "Send a message to all users" +msgstr " GLOBAL Envia uma mensagem para todos usuários" + +#: modules/commands/ms_list.cpp:64 +#, fuzzy +msgid "Sender" +msgstr "Founder Seguro" + +#: modules/commands/ms_rsend.cpp:24 +#, fuzzy +msgid "Sends a memo and requests a read receipt" +msgstr " RSEND Envia um memo e pede uma confirmação de leitura" + +#: modules/commands/ns_resetpass.cpp:50 +#, fuzzy +msgid "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." +msgstr "" +"Syntax: RESETPASS nickname\n" +"\n" +"Sends a codekey to the nickname with the instructions on how to\n" +"reset their psasword." + +#: modules/commands/ms_sendall.cpp:52 +#, fuzzy +msgid "Sends all registered users a memo containing memo-text." +msgstr "" +"Sintaxe: SENDALL mensagem\n" +"\n" +"Envia um memo para todos os usuários registrados\n" +"contendo uma mensagem." + +#: modules/commands/ms_staff.cpp:48 +#, fuzzy +msgid "Sends all services staff a memo containing memo-text." +msgstr "" +"Sintaxe: STAFF mensagem\n" +"\n" +"Envia um memo a todos os membros da Staff dos Services\n" +"contendo uma mensagem." + +#: modules/commands/ms_send.cpp:66 +#, fuzzy +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." +msgstr "" +"Sintaxe: SEND {nick | canal} mensagem\n" +"\n" +"Envia um memo ao nick ou ao canal determinado contendo\n" +"a mensagem. Quando enviada para o destinatário, este\n" +"receberá um aviso que possui uma nova mensagem. O nick/canal\n" +"de destino deverá estar registrado." + +#: modules/commands/ms_rsend.cpp:80 +#, fuzzy +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." +msgstr "" +"Sintaxe: RSEND {nick | canal} mensagem\n" +"\n" +"Envia para um nick ou canal um memo contendo uma\n" +"mensagem. Quando enviar a um nick, o destinatário receberá\n" +"um aviso de que ele tem um novo memo. O destino (nick/canal)\n" +"deve ser registrado.\n" +"Uma vez que o memo for lido pelo destinatário, uma notificação\n" +"automática será enviada ao remetente informando-o que o memo\n" +"foi lido." + +#: modules/commands/ms_read.cpp:199 +#, fuzzy +msgid "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Sintaxe: READ [canal] {núm | list | LAST | NEW}\n" +"\n" +"Mostra as mensagens especificadas. Se LAST é fornecido, envia\n" +"a você a mensagem recebida mais recentemente. Se NEW é fornecido,\n" +"envia a você todas as suas novas mensagens. Caso contrário, envia\n" +"a você a mensagem de número núm. Você também pode fornecer uma\n" +"lista de números, como neste exemplo:\n" +"\n" +"READ 2-5,7-9\n" +" Mostra as mensagens numeradas de 2 a 5 e de 7 a 9." + +#: modules/commands/os_dns.cpp:218 +#, fuzzy +msgid "Server" +msgstr "NOOP {SET|REVOKE} servidor" + +#: modules/commands/os_dns.cpp:375 +#, fuzzy, c-format +msgid "Server %s added to zone %s." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:345 +#, fuzzy, c-format +msgid "Server %s already exists." +msgstr "Bot %s já existe." + +#: modules/commands/os_noop.cpp:31 modules/commands/os_dns.cpp:430 +#: modules/commands/os_dns.cpp:493 modules/commands/os_dns.cpp:532 +#: modules/commands/os_dns.cpp:571 modules/commands/os_dns.cpp:604 +#: modules/commands/os_dns.cpp:639 +#, fuzzy, c-format +msgid "Server %s does not exist." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:619 +#, fuzzy, c-format +msgid "Server %s has no configured IPs." +msgstr "O nick %s foi desregistrado." + +#: modules/commands/os_dns.cpp:357 +#, fuzzy, c-format +msgid "Server %s is already in zone %s." +msgstr "You are already in %s! " + +#: modules/commands/os_dns.cpp:614 +#, fuzzy, c-format +msgid "Server %s is already pooled." +msgstr "Module %s is already loaded." + +#: modules/commands/os_dns.cpp:609 +#, fuzzy, c-format +msgid "Server %s is not currently linked." +msgstr "%s está online neste momento." + +#: modules/commands/os_dns.cpp:443 +#, fuzzy, c-format +msgid "Server %s is not in zone %s." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:384 +#, fuzzy, c-format +msgid "Server %s is not linked to the network." +msgstr "Não possui mais nenhum bot associado ao canal %s." + +#: modules/commands/os_dns.cpp:644 +#, fuzzy, c-format +msgid "Server %s is not pooled." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:465 +#, c-format +msgid "Server %s must be quit before it can be deleted." +msgstr "" + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Servers" +msgstr "NOOP {SET|REVOKE} servidor" + +#: modules/commands/os_stats.cpp:155 +#, c-format +msgid "Servers found: %d" +msgstr "Servers found: %d" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Service" +msgstr "Servers found: %d" + +#: modules/commands/ns_recover.cpp:51 +#, fuzzy, c-format +msgid "Service's hold on %s has been released." +msgstr "Seu nick foi derrubado e pode ser usado." + +#: data/nickserv.example.conf:236 data/chanserv.example.conf:827 +#, fuzzy +msgid "Services Operator commands" +msgstr "%s is a services operator of type %s." + +#: modules/commands/os_defcon.cpp:443 modules/commands/os_defcon.cpp:454 +#: modules/commands/os_defcon.cpp:462 modules/commands/os_defcon.cpp:470 +#: modules/commands/os_defcon.cpp:478 +#, fuzzy +msgid "Services are in DefCon mode, please try again later." +msgstr "" +"Este serviço está temporariamente desabilitado, por favor tente novamente " +"mais tarde" + +#: include/language.h:70 +#, fuzzy +msgid "Services are in read-only mode!" +msgstr "Services estão agora no modo somente leitura." + +#: modules/commands/os_defcon.cpp:186 modules/commands/os_defcon.cpp:213 +#, fuzzy, c-format +msgid "Services are now at DEFCON %d." +msgstr "Services estão agora em DEFCON %d" + +#: modules/commands/os_set.cpp:128 +#, fuzzy, c-format +msgid "Services are now in debug mode (level %d)." +msgstr "Services estão agora no modo debug (nível %d)." + +#: modules/commands/os_set.cpp:114 +#, fuzzy +msgid "Services are now in debug mode." +msgstr "Services estão agora no modo debug." + +#: modules/commands/os_set.cpp:159 +msgid "Services are now in expire mode." +msgstr "Services estão agora no modo expira." + +#: modules/commands/os_set.cpp:153 +msgid "Services are now in no expire mode." +msgstr "Services estão agora no modo não expira." + +#: modules/commands/os_set.cpp:120 +#, fuzzy +msgid "Services are now in non-debug mode." +msgstr "Services não estão mais no modo debug." + +#: modules/commands/os_set.cpp:47 +msgid "Services are now in read-only mode." +msgstr "Services estão agora no modo somente leitura." + +#: modules/commands/os_set.cpp:53 +msgid "Services are now in read-write mode." +msgstr "Services estão agora no modo leitura e gravação." + +#: src/mail.cpp:76 +msgid "Services have been configured to not send mail." +msgstr "Os services foram configurados para não enviar e-mail." + +#: modules/commands/os_ignore.cpp:280 +#, fuzzy +msgid "Services ignore list:" +msgstr " IGNORE Modifica a lista de ignorados dos Services" + +#: modules/commands/os_mode.cpp:33 modules/commands/os_kick.cpp:39 +#, fuzzy +msgid "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" +msgstr "" +"Os Services não conseguiram alterar os modos. As U:lines dos seus servidores " +"estão configuradas corretamente?" + +#: modules/commands/os_stats.cpp:140 +#, fuzzy, c-format +msgid "Services up %s." +msgstr "Servers found: %d" + +#: modules/commands/ns_set.cpp:266 +#, fuzzy, c-format +msgid "Services will from now on set status modes on %s in channels." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/cs_set.cpp:114 +#, fuzzy, c-format +msgid "Services will no longer automatically give modes to users in %s." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/ns_set.cpp:272 +#, fuzzy, c-format +msgid "Services will no longer set status modes on %s in channels." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/cs_set.cpp:108 +#, fuzzy, c-format +msgid "Services will now automatically give modes to users in %s." +msgstr "Services will now autoop %s in channels." + +#: modules/commands/ns_set.cpp:940 +#, c-format +msgid "Services will now reply to %s with messages." +msgstr "Services will now reply to %s with messages." + +#: modules/commands/ns_set.cpp:946 +#, c-format +msgid "Services will now reply to %s with notices." +msgstr "Services will now reply to %s with notices." + +#: modules/commands/os_reload.cpp:34 +#, fuzzy +msgid "Services' configuration has been reloaded." +msgstr "Arquivos de configuração dos Services foram recarregados." + +#: modules/commands/os_session.cpp:192 +msgid "Session" +msgstr "" + +#: modules/commands/os_session.cpp:382 +#, c-format +msgid "Session limit for %s set to %d." +msgstr "Limite de sessões para %s é agora de %d." + +#: modules/commands/os_session.cpp:257 modules/commands/os_session.cpp:534 +msgid "Session limiting is disabled." +msgstr "Opção de limite de sessões desabilitada." + +#: modules/commands/os_stats.cpp:195 +#, c-format +msgid "Sessions: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/ns_set.cpp:74 +#, fuzzy +msgid "Set SET-options on another nickname" +msgstr " SASET Set SET-options on another nickname" + +#: modules/commands/cs_set.cpp:20 +#, fuzzy +msgid "Set channel options and information" +msgstr " SET Ajusta as opções e informações do canal" + +#: modules/commands/cs_set.cpp:137 +#, fuzzy +msgid "Set how Services make bans on the channel" +msgstr " BANTYPE Ajusta como os Services devem fazer o ban" + +#: modules/commands/ms_set.cpp:206 +#, fuzzy +msgid "Set options related to memos" +msgstr " SET Ajusta opções relacionadas às mensagens" + +#: modules/commands/ns_set.cpp:19 +#, fuzzy +msgid "Set options, including kill protection" +msgstr " SET Ajusta opções, incluindo proteção de kill" + +#: modules/commands/cs_set.cpp:472 +#, fuzzy +msgid "Set the channel as permanent" +msgstr " PERSIST Set the channel as permanent" + +#: modules/commands/cs_set.cpp:204 +#, fuzzy +msgid "Set the channel description" +msgstr " DESC Ajusta a descrição do canal" + +#: modules/commands/ns_set.cpp:329 +#, fuzzy +msgid "Set the display of your group in Services" +msgstr " DISPLAY Mostra o seu grupo nos Services" + +#: modules/commands/cs_set.cpp:266 +#, fuzzy +msgid "Set the founder of a channel" +msgstr " FOUNDER Ajusta o fundador do canal" + +#: modules/commands/ns_set.cpp:793 +#, fuzzy +msgid "Set the language Services will use when messaging you" +msgstr "" +" LANGUAGE Ajusta a linguagem dos Services quando\n" +" mensagens são enviadas à você" + +#: modules/commands/ns_set.cpp:172 +#, fuzzy +msgid "Set the nickname password" +msgstr " PASSWORD Set the nickname password" + +#: modules/commands/cs_set.cpp:949 +#, fuzzy +msgid "Set the successor for a channel" +msgstr " SUCCESSOR Ajusta o sucessor do canal" + +#: modules/commands/hs_set.cpp:125 +#, fuzzy +msgid "Set the vhost for all nicks in a group" +msgstr " SETALL Ajusta o vHost de todos os nicks de um grupo" + +#: modules/commands/hs_set.cpp:19 +#, fuzzy +msgid "Set the vhost of another user" +msgstr " SET Ajusta o vHost de outro usuário" + +#: modules/commands/os_set.cpp:169 +#, fuzzy +msgid "Set various global Services options" +msgstr " SET Configura várias opções globais dos Services" + +#: modules/commands/ns_set.cpp:119 +#, fuzzy +msgid "Set your nickname password" +msgstr " PASSWORD Ajusta a senha do seu nick" + +#: modules/commands/bs_kick.cpp:271 +#, fuzzy, c-format +msgid "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK channel ITALICS {ON|OFF} [ttb]\n" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +"ttb is the number of times a user can be kicked\n" +"before it get banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:307 +#, fuzzy, c-format +msgid "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintaxe: KICK canal BADWORDS {ON|OFF} [ttb]\n" +"\n" +"Ativa ou desativa o kick por palavrões. Quando ativado\n" +"o bot irá kickar usuários que disserem determinadas\n" +"palavras no canal.\n" +"\n" +"Você pode definir os palavrões para um canal usando o\n" +"comando BADWORDS. Digite /msg %s HELP BADWORDS para\n" +"maiores informações.\n" +"\n" +"ttb é o número de vezes que o usuário será kickado\n" +"antes de ser banido. Não forneça ttb para desabilitar\n" +"o sistema de ban que foi uma vez ativado." + +#: modules/commands/cs_set.cpp:186 +#, fuzzy +msgid "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" +msgstr "" +"Sintaxe: %s canal BANTYPE tipo-de-ban\n" +"\n" +"Seleciona o tipo de ban que será usado sempre que os Services\n" +"precisarem banir alguém do seu canal.\n" +"\n" +"O tipo-de-ban é um número entre 0 e 3 que significa:\n" +"\n" +"0: ban na forma *!user@host\n" +"1: ban na forma *!*user@host\n" +"2: ban na forma *!*@host\n" +"3: ban na forma *!*user@*.domain" + +#: modules/commands/bs_kick.cpp:345 +#, fuzzy +msgid "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintaxe: KICK canal BOLDS {ON|OFF} [ttb]\n" +"\n" +"Ativa ou desativa o kick por negrito. Quando ativado\n" +"o bot irá kickar os usuários que usarem negrito.\n" +"\n" +"ttb é o número de vezes que o usuário será kickado\n" +"antes de ser banido. Não forneça ttb para desabilitar\n" +"o sistema de ban que foi uma vez ativado." + +#: modules/commands/bs_kick.cpp:436 +#, fuzzy, c-format +msgid "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintaxe: KICK canal CAPS {ON|OFF} [ttb [mínimo [porcentagem]]]\n" +"\n" +"Ativa ou desativa o kick por caps. Quando ativado\n" +"o bot irá kickar os usuários que usarem CAPS (maiúsculas).\n" +"\n" +"O bot irá kickar apenas se usarem pelo menos um mínimo de\n" +"caps e eles constituírem pelo menos porcentagem%% do total \n" +"do texto (se não for especificado, o padrão é 10 caracteres\n" +"e 25%%).\n" +"\n" +"ttb é o número de vezes que o usuário será kickado\n" +"antes de ser banido. Não forneça ttb para desabilitar\n" +"o sistema de ban que foi uma vez ativado." + +#: modules/commands/bs_kick.cpp:475 +#, fuzzy +msgid "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintaxe: KICK canal COLORS {ON|OFF} [ttb]\n" +"\n" +"Ativa ou desativa o kick por cores. Quando ativado\n" +"o bot irá kickar os usuários que usarem cores.\n" +"\n" +"ttb é o número de vezes que o usuário será kickado\n" +"antes de ser banido. Não forneça ttb para desabilitar\n" +"o sistema de ban que foi uma vez ativado." + +#: modules/commands/cs_set.cpp:255 +#, fuzzy +msgid "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." +msgstr "" +"Sintaxe: %s canal DESC descrição\n" +"\n" +"Ajusta a descrição para o canal, que são mostradas com\n" +"os comandos LIST e INFO." + +#: modules/commands/bs_kick.cpp:571 +#, fuzzy +msgid "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintaxe: KICK canal FLOOD {ON|OFF} [ttb [linhas [segs]]]\n" +"\n" +"Ativa ou desativa o kick por flood. Quando ativado o\n" +"o bot irá kickar por flood no canal desde que sejam\n" +"pelo menos linhas linhas em segs segundos.\n" +"(se não for especificado, o padrão é 6 linhas em\n" +"10 segundos).\n" +"\n" +"ttb é o número de vezes que o usuário será kickado\n" +"antes de ser banido. Não forneça ttb para desabilitar\n" +"o sistema de ban que foi uma vez ativado." + +#: modules/commands/bs_kick.cpp:607 +#, fuzzy +msgid "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK channel ITALICS {ON|OFF} [ttb]\n" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +"ttb is the number of times a user can be kicked\n" +"before it get banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:706 +#, fuzzy +msgid "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintaxe: KICK canal REPEAT {ON|OFF} [ttb [núm]]\n" +"\n" +"Ativa ou desativa o kick por repetição. Quando ativado\n" +"o bot irá kickar os usuários que fizerem repetições (onde\n" +"núm é o número de repetições para kick; se não for fornecido,\n" +"o padrão é 3).\n" +"\n" +"ttb é o número de vezes que o usuário será kickado\n" +"antes de ser banido. Não forneça ttb para desabilitar\n" +"o sistema de ban que foi uma vez ativado." + +#: modules/commands/bs_kick.cpp:742 +#, fuzzy +msgid "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintaxe: KICK canal REVERSES {ON|OFF} [ttb]\n" +"\n" +"Ativa ou desativa o kick por reverso. Quando ativado\n" +"o bot irá kickar os usuários que usarem reverso.\n" +"\n" +"ttb é o número de vezes que o usuário será kickado\n" +"antes de ser banido. Não forneça ttb para desabilitar\n" +"o sistema de ban que foi uma vez ativado." + +#: modules/commands/bs_kick.cpp:776 +#, fuzzy +msgid "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Sintaxe: KICK canal UNDERLINES {ON|OFF} [ttb]\n" +"\n" +"Ativa ou desativa o kick por sublinhado. Quando ativado\n" +"o bot irá kickar os usuários que usarem sublinhado.\n" +"\n" +"ttb é o número de vezes que o usuário será kickado\n" +"antes de ser banido. Não forneça ttb para desabilitar\n" +"o sistema de ban que foi uma vez ativado." + +#: modules/commands/hs_set.cpp:206 +#, fuzzy +msgid "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." +msgstr "" +"Sintaxe: SETALL  .\n" +"Ajusta o vhost para todos os nicks no mesmo grupo do\n" +"nick fornecido. Caso seu IRCd suporte vIdents, então\n" +"usando SETALL @ ajustará idents\n" +"para usuários, assim como vhosts.\n" +"* NOTA: isto não irá atualizar o vhost de nenhum nick\n" +"adicionado ao grupo depois que o comando foi usado." + +#: modules/commands/hs_set.cpp:99 +#, fuzzy +msgid "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." +msgstr "" +"Sintaxe: SET  .\n" +"Ajusta o vhost para o nick dado com a hostmask fornecida.\n" +"Caso seu IRCd suporte vIdents, então usando\n" +"SET @ ajustará idents para\n" +"usuários, assim como vhosts." + +#: modules/commands/os_set.cpp:199 +#, fuzzy +msgid "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" +msgstr "" +"Sintaxe: SET opção seleção\n" +"\n" +"Ajusta várias opções globais dos Services. Os nomes de opção\n" +"atualmente definidas são:\n" +" READONLY Ativa o modo read-only ou read-write\n" +" LOGCHAN Ativa ou desativa envio de log a um canal\n" +" DEBUG Ativa ou desativa o modo de depuração (debug)\n" +" NOEXPIRE Ativa ou desativa o modo não-expira\n" +" SUPERADMIN Ativa ou desativa o modo Super-Admin\n" +" IGNORE Ativa ou desativa o modo Ignore\n" +" LIST Lista as opções atuais" + +#: modules/commands/ms_set.cpp:235 +#, fuzzy, c-format +msgid "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Sintaxe: SET opção parâmetros\n" +"\n" +"Ajusta várias opções de mensagens. A opção pode ser uma dessas:\n" +"\n" +" NOTIFY Altera quando você será notificado sobre novas\n" +" mensagens (só para nicks)\n" +" LIMIT Ajusta o número máximo de mensagens que você\n" +" pode receber.\n" +"\n" +"Digite /msg %s HELP SET opção, para mais informações sobre\n" +"uma opção específica." + +#: modules/commands/ns_set.cpp:33 modules/commands/ns_set.cpp:88 +#, fuzzy +msgid "Sets various nickname options. option can be one of:" +msgstr "" +"Sintaxe: SET opção parâmetros\n" +"\n" +"Ajusta várias opções de nick. A opção pode ser:" + +#: modules/commands/ns_set.cpp:237 +msgid "" +"Sets whether services should set channel status modes on you automatically." +msgstr "" + +#: modules/commands/cs_set.cpp:1090 +#, fuzzy +msgid "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." +msgstr "" +"Sintaxe: SET canal NOEXPIRE {ON | OFF}\n" +"\n" +"Determina se o canal poderá ter seu registro expirado.\n" +"Ajustando para ON, evita que o canal seja desregistrado\n" +"por passar do tempo de expiração." + +#: modules/commands/ns_set.cpp:315 +#, fuzzy, c-format +msgid "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." +msgstr "" +"Syntax: SASET nickname AUTOOP {ON | OFF}\n" +"\n" +"Sets whether the given nickname will be opped automatically.\n" +"Set to ON to allow ChanServ to op the given nickname \n" +"automatically when joining channels." + +#: modules/commands/ns_set.cpp:1145 +#, fuzzy +msgid "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." +msgstr "" +"Syntax: SASET nickname NOEXPIRE {ON | OFF}\n" +"\n" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." + +#: modules/commands/ns_set.cpp:288 +#, fuzzy, c-format +msgid "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." +msgstr "" +"Syntax: SET AUTOOP {ON | OFF}\n" +"\n" +"Sets whether you will be opped automatically. Set to ON to \n" +"allow ChanServ to op you automatically when entering channels." + +#: modules/commands/cs_access.cpp:648 modules/commands/cs_access.cpp:689 +#, fuzzy, c-format +msgid "" +"Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." +msgstr "" +"Level %s desconhecido. Digite /msg %s HELP LEVELS DESC para uma lista de " +"Levels válidos." + +#: modules/commands/os_set.cpp:133 +#, fuzzy +msgid "Setting for DEBUG must be ON, OFF, or a positive number." +msgstr "Configuração do DEBUG deve ser ON, OFF, ou um número positivo." + +#: modules/commands/os_set.cpp:162 +#, fuzzy +msgid "Setting for NOEXPIRE must be ON or OFF." +msgstr "Opção NOEXPIRE deve ser ON ou OFF." + +#: modules/commands/os_set.cpp:56 +#, fuzzy +msgid "Setting for READONLY must be ON or OFF." +msgstr "Configuração do READONLY deve ser ON ou OFF." + +#: modules/commands/os_set.cpp:95 +#, fuzzy +msgid "Setting for super admin must be ON or OFF." +msgstr "Configuração do READONLY deve ser ON ou OFF." + +#: modules/commands/cs_set.cpp:74 +#, fuzzy +msgid "Should services automatically give status to users" +msgstr " AUTOOP Should services op you automatically. " + +#: modules/commands/os_stats.cpp:203 +#, fuzzy +msgid "Show status of Services and network" +msgstr " STATS Mostra estatísticas dos Services e da Rede" + +#: modules/commands/os_logsearch.cpp:152 +#, c-format +msgid "Showed %d/%d matches for %s." +msgstr "" + +#: modules/commands/cs_set.cpp:872 +#, fuzzy +msgid "Sign kicks that are done with the KICK command" +msgstr " SIGNKICK Assinatura dos kicks feitos pelo comando KICK" + +#: modules/commands/cs_set.cpp:921 +#, fuzzy, c-format +msgid "Signed kick option for %s is now off." +msgstr "Opção Signed Kicks para %s está agora ATIVADA." + +#: modules/commands/cs_set.cpp:913 +#, fuzzy, c-format +msgid "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." +msgstr "" +"Opção Signed Kicks para %s está agora ATIVADA, mas depende\n" +"do nível de acesso do usuário que está usando o comando." + +#: modules/commands/cs_set.cpp:906 +#, fuzzy, c-format +msgid "Signed kick option for %s is now on." +msgstr "Opção Signed Kicks para %s está agora ATIVADA." + +#: modules/commands/cs_set.cpp:1299 +msgid "Signed kicks" +msgstr "Kicks assinados" + +#: modules/commands/ms_rsend.cpp:60 modules/commands/ms_send.cpp:59 +#, fuzzy, c-format +msgid "Sorry, %s currently has too many memos and cannot receive more." +msgstr "%s possui muitos memos atualmente e não pode receber mais nenhum." + +#: modules/commands/cs_seen.cpp:294 +#, c-format +msgid "Sorry, I have not seen %s." +msgstr "" + +#: modules/commands/bs_badwords.cpp:404 +#, fuzzy +msgid "Sorry, bad words list modification is temporarily disabled." +msgstr "Desculpe, o comando BADWORDS está temporariamente desatvado." + +#: modules/commands/bs_assign.cpp:30 modules/commands/bs_assign.cpp:98 +#, fuzzy +msgid "Sorry, bot assignment is temporarily disabled." +msgstr "Desculpe, o comando SET está temporariamente desativado." + +#: modules/commands/bs_bot.cpp:281 modules/commands/bs_assign.cpp:164 +msgid "Sorry, bot modification is temporarily disabled." +msgstr "Desculpe, comando CHANGE temporariamente desativado." + +#: modules/fantasy.cpp:42 modules/commands/bs_kick.cpp:813 +#: modules/commands/bs_kick.cpp:878 +msgid "Sorry, bot option setting is temporarily disabled." +msgstr "Desculpe, o comando SET está temporariamente desativado." + +#: modules/commands/bs_set.cpp:115 +#, fuzzy +msgid "Sorry, changing bot options is temporarily disabled." +msgstr "Desculpe, o comando SET está temporariamente desativado." + +#: modules/commands/cs_xop.cpp:112 modules/commands/cs_xop.cpp:235 +#: modules/commands/cs_xop.cpp:444 +#, fuzzy, c-format +msgid "Sorry, channel %s list modification is temporarily disabled." +msgstr "" +"Desculpe, a modificação da lista de AOP está temporariamente desabilitada." + +#: modules/commands/cs_access.cpp:547 modules/commands/cs_flags.cpp:405 +msgid "Sorry, channel access list modification is temporarily disabled." +msgstr "Desculpe, o registro de canais está temporariamente desativado." + +#: modules/commands/cs_akick.cpp:469 +msgid "Sorry, channel autokick list modification is temporarily disabled." +msgstr "Desculpe, o comando AKICK está temporariamente desativado." + +#: modules/commands/cs_drop.cpp:29 +msgid "Sorry, channel de-registration is temporarily disabled." +msgstr "Desculpe, o comando DROP está temporariamente desativado." + +#: modules/commands/cs_register.cpp:35 +msgid "Sorry, channel registration is temporarily disabled." +msgstr "Desculpe, o registro de canais está temporariamente desativado." + +#: modules/commands/bs_kick.cpp:181 +msgid "Sorry, kicker configuration is temporarily disabled." +msgstr "" +"Desculpe, as configurações do kicker estão temporariamente desativadas." + +#: modules/commands/ms_set.cpp:216 +msgid "Sorry, memo option setting is temporarily disabled." +msgstr "Desculpe, a opção SET está temporariamente desativada." + +#: include/language.h:116 +#, fuzzy +msgid "Sorry, memo sending is temporarily disabled." +msgstr "Desculpe, a opção SET está temporariamente desativada." + +#: modules/commands/ns_drop.cpp:29 +msgid "Sorry, nickname de-registration is temporarily disabled." +msgstr "Desculpe, o comando DROP está temporariamente desativado." + +#: modules/commands/ns_group.cpp:120 +msgid "Sorry, nickname grouping is temporarily disabled." +msgstr "Desculpe, o comando GROUP está temporariamente desativado." + +#: modules/commands/ns_register.cpp:139 +msgid "Sorry, nickname registration is temporarily disabled." +msgstr "Desculpe, registros de nick estão temporariamente desativados." + +#: modules/commands/ns_access.cpp:33 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d access entries has been reached." +msgstr "" +"Desculpe, você pode ter apenas %d entradas na lista de acesso do canal." + +#: modules/commands/ns_ajoin.cpp:141 +#, c-format +msgid "Sorry, the maximum of %d auto join entries has been reached." +msgstr "" + +#: modules/commands/ns_cert.cpp:173 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d certificate entries has been reached." +msgstr "Desculpe, você pode ter somente %d entradas em sua lista de acesso." + +#: modules/commands/ms_ignore.cpp:55 +#, fuzzy, c-format +msgid "Sorry, the memo ignore list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/cs_access.cpp:204 modules/commands/cs_flags.cpp:174 +#: modules/commands/cs_xop.cpp:201 +#, fuzzy, c-format +msgid "" +"Sorry, you can only have %d access entries on a channel, including access " +"entries from other channels." +msgstr "" +"Desculpe, você pode ter apenas %d entradas na lista de acesso do canal." + +#: modules/commands/cs_akick.cpp:177 +#, c-format +msgid "Sorry, you can only have %d autokick masks on a channel." +msgstr "Desculpe, você pode ter apenas %d akicks na lista do canal." + +#: modules/commands/bs_badwords.cpp:286 +#, c-format +msgid "Sorry, you can only have %d bad words entries on a channel." +msgstr "Desculpe, você pode ter apenas %d palavrões em sua lista." + +#: include/language.h:103 +#, fuzzy, c-format +msgid "Sorry, you have already exceeded your limit of %d channels." +msgstr "Desculpe, você pode ter apenas %d palavrões em sua lista." + +#: include/language.h:102 +#, fuzzy, c-format +msgid "Sorry, you have already reached your limit of %d channels." +msgstr "Desculpe, você pode ter apenas %d palavrões em sua lista." + +#: modules/commands/os_dns.cpp:218 +msgid "State" +msgstr "" + +#: modules/commands/cs_seen.cpp:117 +msgid "Statistics and maintenance for seen data" +msgstr "" + +#: modules/commands/os_stats.cpp:131 +msgid "Statistics reset." +msgstr "Resetar estatísticas." + +#: modules/commands/ns_update.cpp:36 +msgid "Status updated (memos, vhost, chmodes, flags)." +msgstr "Status atualizado (memos, vhost, chmodes, flags)." + +#: modules/commands/bs_kick.cpp:1432 +msgid "Stop flooding!" +msgstr "Pare de floodar!" + +#: modules/commands/bs_kick.cpp:1448 +msgid "Stop repeating yourself!" +msgstr "Pare de ficar repetindo!" + +#: modules/commands/cs_set.cpp:746 +#, fuzzy +msgid "Stricter control of channel founder status" +msgstr " SECUREFOUNDER Controle rigoroso do status de Fundador do Canal" + +#: modules/commands/cs_set.cpp:810 +#, fuzzy +msgid "Stricter control of chanop status" +msgstr " SECUREOPS Controle rigoroso do status de OP" + +#: modules/commands/ns_alist.cpp:75 modules/commands/cs_info.cpp:50 +msgid "Successor" +msgstr "" + +#: modules/commands/cs_set.cpp:1006 +#, fuzzy, c-format +msgid "Successor for %s changed to %s." +msgstr "Successor do canal %s alterado para %s." + +#: modules/commands/cs_set.cpp:1008 +#, c-format +msgid "Successor for %s unset." +msgstr "Successor do canal %s removido." + +#: modules/commands/os_set.cpp:81 +#, fuzzy +msgid "" +"Super admin can not be set because it is not enabled in the configuration." +msgstr "Opção SuperAdmin não habilitada no arquivo services.conf" + +#: modules/commands/ns_suspend.cpp:60 +#, fuzzy +msgid "Suspend a given nick" +msgstr " SUSPEND Suspende o nick fornecido" + +#: modules/commands/cs_suspend.cpp:236 modules/commands/ns_suspend.cpp:250 +#, fuzzy +msgid "Suspend reason" +msgstr "JUPE servidor [motivo]" + +#: modules/commands/cs_suspend.cpp:232 modules/commands/ns_suspend.cpp:246 +msgid "Suspended" +msgstr "" + +#: modules/commands/cs_suspend.cpp:234 modules/commands/ns_suspend.cpp:248 +msgid "Suspended by" +msgstr "" + +#: modules/commands/cs_suspend.cpp:238 modules/commands/ns_suspend.cpp:252 +#, fuzzy +msgid "Suspended on" +msgstr " SUSPEND Suspende o nick fornecido" + +#: modules/commands/ns_suspend.cpp:147 +#, fuzzy +msgid "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." +msgstr "" +"Sintaxe: SUSPEND canal [motivo]\n" +"\n" +"Proibe qualquer um de registrar ou usar o canal dado.\n" +"Pode ser cancelado usando o comando UNSUSPEND para\n" +"preservar todos os dados/configurações anteriores do canal.\n" +"\n" +"Um motivo pode ser necessário em algumas redes." + +#: modules/commands/cs_suspend.cpp:240 modules/commands/ns_suspend.cpp:254 +#, fuzzy +msgid "Suspension expires" +msgstr " %s (does not expire)" + +#: modules/commands/cs_sync.cpp:19 +#, fuzzy +msgid "Sync users channel modes" +msgstr "%s alterou seus modos de usuário." + +#: modules/commands/cs_sync.cpp:49 +msgid "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." +msgstr "" + +#: modules/commands/hs_group.cpp:42 +#, fuzzy +msgid "Syncs the vhost for all nicks in a group" +msgstr "" +" GROUP Sincroniza um mesmo vHost para todos os nicks de um grupo" + +#: src/command.cpp:146 +msgid "Syntax" +msgstr "" + +#: modules/commands/ns_group.cpp:373 +#, fuzzy, c-format +msgid "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." +msgstr "" +"Sintaxe: GLIST\n" +"\n" +"Lista todos os nicks do grupo." + +#: modules/commands/ns_group.cpp:363 +#, fuzzy, c-format +msgid "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." +msgstr "" +"Sintaxe: GLIST [nick]\n" +"\n" +"Sem nenhum parâmetro, lista todos os nicks no seu grupo.\n" +"Com um parâmetro, lista todos os nicks no grupo determinado.\n" +"\n" +"Este comando é limitado aos Administradores dos Services." + +#: modules/commands/os_set.cpp:227 +#, fuzzy +msgid "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." +msgstr "" +"Sintaxe: SET NOEXPIRE {ON | OFF}\n" +"\n" +"Ativa ou desativa o modo NOEXPIRE. Se estiver ativado, os\n" +"nicks, canais, akills e exceções não irão expirar enquanto a \n" +"opção não for desativada.\n" +"\n" +"Esta opção é equivalente à opção da linha de comando\n" +"-noexpire." + +#: modules/commands/ms_set.cpp:287 +#, fuzzy, c-format +msgid "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." +msgstr "" +"Sintaxe: SET LIMIT [canal] limite\n" +"\n" +"Ajusta o número máximo de mensagens que você (ou o canal fornecido)\n" +"podem ter. Se você ajustar para 0, ninguém será capaz de enviar\n" +"mensagens para você. Entretanto, você não pode ajustar este\n" +"limite para mais que %d." + +#: modules/commands/ms_set.cpp:267 +#, fuzzy, c-format +msgid "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." +msgstr "" +"Sintaxe: SET LIMIT [usuário | canal] {limite | NONE} [HARD]\n" +"\n" +"Ajusta o número máximo de mensagens que um usuário ou canal podem\n" +"ter. Ajustando o limite para 0, previne o usuário de receber\n" +"qualquer mensagem; ajustando o limite em NONE permite que o\n" +"usuário receba e mantenha quantas mensagens quiser. Se você\n" +"não fornecer o nick ou canal, seu próprio limite será ajustado.\n" +"\n" +"Adicionando HARD previne que o usuário mude o limite.\n" +"Não adicionando HARD tem o efeito contrário, permitindo\n" +"que o usuário mude o limite (mesmo se um limite anterior\n" +"foi ajustado com HARD).\n" +"\n" +"Este uso do comando SET LIMIT é limitado aos Administradores\n" +"dos Services. Outros usuários somente ajustarão seus\n" +"próprios limites ou de um canal onde tenham privilégios\n" +"para isso, não podem remover seu próprio limite, não\n" +"podem ajustar o limite acima de %d, e não podem ajustar\n" +"um limite máximo (HARD)." + +#: modules/commands/os_set.cpp:208 +#, fuzzy, c-format +msgid "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." +msgstr "" +"Sintaxe: SET LIST\n" +"\n" +"Exibe as várias configurações do %s." + +#: modules/commands/os_set.cpp:234 +#, fuzzy +msgid "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." +msgstr "" +"Sintaxe: SET NOEXPIRE {ON | OFF}\n" +"\n" +"Ativa ou desativa o modo NOEXPIRE. Se estiver ativado, os\n" +"nicks, canais, akills e exceções não irão expirar enquanto a \n" +"opção não for desativada.\n" +"\n" +"Esta opção é equivalente à opção da linha de comando\n" +"-noexpire." + +#: modules/commands/ms_set.cpp:246 +#, fuzzy +msgid "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." +msgstr "" +"Sintaxe: SET NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +"\n" +"Altera quando você será notificado sobre novas mensagens:\n" +"\n" +" ON Você será notificado sobre mensagens quando você\n" +" conectar, quando voltar de um /AWAY e quando\n" +" são enviadas a você.\n" +" LOGON Você só será notificado sobre mensagens quando você\n" +" conectar ou quando voltar de um /AWAY.\n" +" NEW Você só será notificado sobre mensagens quando elas\n" +" forem enviadas a você.\n" +" MAIL You will be notified of memos by email aswell as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF Você não receberá nenhuma notificação sobre mensagens.\n" +"\n" +"ON é essencialmente a combinação de LOGON e NEW." + +#: modules/commands/os_set.cpp:212 +#, fuzzy +msgid "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." +msgstr "" +"Sintaxe: SET READONLY {ON | OFF}\n" +"\n" +"Ativa ou desativa o modo read-only (somente leitura).\n" +"No modo read-only, usuários normais não serão capazes de\n" +"modificar nenhum dado nos Services, incluindo lista de acesso\n" +"de canais e nicks etc. IRCops com privilégios suficientes\n" +"nos Services serão capazes de modificar a lista de AKILL\n" +"e de proibir ou cancelar o registro de canais ou nicks,\n" +"embora quaisquer mudanças não serão salvas no banco de\n" +"dados a menos que o modo read-only seja desativado antes\n" +"dos Services serem terminados ou reiniciados.\n" +"\n" +"Esta opção é equivalente à opção da linha de comando\n" +"-readonly." + +#: modules/commands/os_set.cpp:243 +#, fuzzy +msgid "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." +msgstr "" +"Sintaxe: SET SUPERADMIN {ON | OFF}\n" +"\n" +"Ativando esta opção, lhe serão concedidos privilégios extras como a\n" +"habilidade de ser \"founder\" em todos os canais etc.\n" +"Esta opção não é permanente, e deve ser usada somente quando\n" +"necessária, e desativada quando não for mais necessária." + +#: modules/commands/ns_identify.cpp:107 +#, fuzzy, c-format +msgid "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." +msgstr "" +"Sintaxe: IDENTIFY [account] senha\n" +"\n" +"Identifica você ao %s como sendo dono do nick.\n" +"Muitos comandos exigem que você se identifique com este\n" +"comando antes de você usá-los. A senha deve ser a mesma que\n" +"você enviou com o comando REGISTER." + +#: modules/commands/cs_invite.cpp:91 +#, fuzzy, c-format +msgid "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Sintaxe: INVITE #canal\n" +"\n" +"Manda o %s dar um invite em você para o canal dado.\n" +"Por padrão, é limitado aos AOPs ou àqueles que possuem\n" +"nível de acesso 5 ou superior no canal." + +#: modules/commands/cs_unban.cpp:103 +#, fuzzy, c-format +msgid "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Sintaxe: UNBAN #canal [nick]\n" +"\n" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel.\n" +"\n" +"Por padrão, é limitado aos AOPs ou àqueles que possuem\n" +"nível de acesso 5 ou superior no canal." + +#: modules/commands/os_jupe.cpp:56 +#, fuzzy +msgid "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." +msgstr "" +"Sintaxe: JUPE servidor [motivo]\n" +"\n" +"Diz aos Services para \"jupar\" um servidor -- isto é, criar\n" +"um falso servidor conectado aos Services que previne que o\n" +"servidor real com aquele nome se conecte na rede. O jupe\n" +"pode ser removido usando um SQUIT padrão. Se um motivo\n" +"é dado, ele é colocado no campo de informação do servidor;\n" +"caso contrário, o campo de informação do servidor irá conter\n" +"o texto \"Jupado por \", mostrando o nick de quem mascarou\n" +"o servidor." + +#: modules/commands/cs_seen.cpp:261 +msgid "Tells you about the last time a user was seen" +msgstr "" + +#: modules/commands/os_shutdown.cpp:19 +#, fuzzy +msgid "Terminate Services WITHOUT saving" +msgstr " SHUTDOWN Termina os Services salvando os dados" + +#: modules/commands/os_shutdown.cpp:73 +#, fuzzy +msgid "Terminate services with save" +msgstr " SHUTDOWN Termina os Services salvando os dados" + +#: modules/commands/os_news.cpp:156 +msgid "Text" +msgstr "" + +#: modules/commands/cs_access.cpp:576 +msgid "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." +msgstr "" + +#: modules/commands/cs_access.cpp:587 +msgid "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." +msgstr "" + +#: modules/commands/cs_access.cpp:593 +msgid "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." +msgstr "" + +#: modules/commands/cs_flags.cpp:447 +msgid "" +"The CLEAR command clears the channel access list. This requires channel " +"founder access." +msgstr "" + +#: modules/commands/cs_seen.cpp:173 +#, c-format +msgid "" +"The CLEAR command lets you clean the database by removing all entries from " +"the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." +msgstr "" + +#: modules/commands/bs_badwords.cpp:438 +#, fuzzy +msgid "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." +msgstr "" +"Sintaxe: HOP canal ADD nick\n" +" HOP canal DEL {nick | entrada | lista-entradas}\n" +" HOP canal LIST [máscara | lista-entradas]\n" +" HOP canal CLEAR\n" +"\n" +"Mantém a lista de HOP (HalfOP) para um canal. A lista\n" +"de HOP dá a um usuário o direito de receber HalfOP\n" +"automaticamente ao entrar no canal.\n" +"\n" +"O comando HOP ADD adiciona o nick fornecido à lista de HOP.\n" +"\n" +"O comando HOP DEL remove o nick fornecido da lista de HOP.\n" +"Se uma lista de números de entrada é fornecida, essas entradas\n" +"são deletadas. (Veja o exemplo para LIST abaixo.)\n" +"\n" +"O comando HOP LIST exibe a lista de HOP. Se uma máscara\n" +"é fornecida, apenas as entradas que combinarem com ela serão\n" +"mostradas. Se uma lista de números de entrada é fornecida,\n" +"apenas essas entradas são mostradas; por exemplo:\n" +"\n" +" HOP #canal LIST 2-5,7-9\n" +" Lista as entradas de HOP numeradas de 2 a 5 e de\n" +" 7 a 9.\n" +"\n" +"O comando HOP CLEAR remove todas as entradas da lista de HOP.\n" +"\n" +"Os comandos HOP ADD, HOP DEL e HOP LIST são limitados\n" +"aos AOPs ou acima, enquanto o comando HOP CLEAR pode ser usado\n" +"apenas pelo Fundador do canal.\n" +"\n" +"Este comando pode ter sido desabilitado para seu canal\n" +"e, nesse caso, você precisa usar a lista de acesso. Veja\n" +"/msg %s HELP ACCESS para informações sobre a lista\n" +"de acesso, e /msg %s HELP SET XOP para saber como\n" +"escolher entre a lista de acesso e o sistema de listas xOP." + +#: modules/commands/cs_entrymsg.cpp:241 +msgid "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:253 +msgid "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:245 +msgid "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:250 +msgid "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." +msgstr "" + +#: modules/commands/ns_set.cpp:713 +msgid "The IMMED option is not available on this network." +msgstr "O comando IMMED não está disponível nesta Rede." + +#: modules/commands/cs_access.cpp:821 +#, fuzzy, c-format +msgid "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." +msgstr "" +"Sintaxe: LEVELS canal SET tipo [nível|FOUNDER]\n" +" LEVELS canal {DIS | DISABLE} tipo\n" +" LEVELS canal LIST\n" +" LEVELS canal RESET\n" +"\n" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +"\n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it).\n" +"\n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel (see\n" +"HELP ACCESS LEVELS).\n" +"\n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." + +#: modules/commands/cs_flags.cpp:442 +msgid "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." +msgstr "" + +#: modules/commands/cs_flags.cpp:435 +msgid "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access " +"list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. " +"You are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of " +"what your access is." +msgstr "" + +#: modules/commands/cs_seen.cpp:172 +msgid "" +"The STATS command prints out statistics about stored nicks and memory usage." +msgstr "" + +#: modules/commands/ns_register.cpp:291 +#, fuzzy +msgid "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." +msgstr "" +"Digite /msg %s SET EMAIL e-mail para setar seu e-mail.\n" +"Sua privacidade é respeitada; seu e-mail não será dado\n" +"para terceiros." + +#: modules/commands/cs_log.cpp:258 +#, c-format +msgid "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." +msgstr "" + +#: modules/commands/cs_ban.cpp:64 +#, fuzzy, c-format +msgid "The %s list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/os_sxline.cpp:220 +#, fuzzy, c-format +msgid "The %s list has been cleared." +msgstr "Lista de AKILL apagada." + +#: modules/commands/os_akill.cpp:377 +msgid "The AKILL list has been cleared." +msgstr "Lista de AKILL apagada." + +#: modules/commands/os_defcon.cpp:136 modules/commands/os_defcon.cpp:225 +#, fuzzy, c-format +msgid "The Defcon level is now at: %d" +msgstr "O Nível do Defcon está agora no Nível: %d" + +#: modules/commands/ns_info.cpp:171 +#, c-format +msgid "The E-mail address of %s will now be hidden from %s INFO displays." +msgstr "The E-mail address of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:172 +#, c-format +msgid "The E-mail address of %s will now be shown in %s INFO displays." +msgstr "The E-mail address of %s will now be shown in %s INFO displays." + +#: modules/commands/cs_flags.cpp:449 +msgid "The available flags are:" +msgstr "" + +#: modules/commands/os_defcon.cpp:240 +#, fuzzy +msgid "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." +msgstr "" +"Sintaxe: DEFCON [1|2|3|4|5]\n" +"O sistema Defcon pode ser usado para implementar um conjunto\n" +"pré-definido de restrições aos Services, útil durante uma\n" +"tentativa de ataque à Rede." + +#: modules/ns_maxemail.cpp:51 +#, c-format +msgid "The email address %s has reached its usage limit of %d users." +msgstr "" + +#: modules/ns_maxemail.cpp:49 +#, c-format +msgid "The email address %s has reached its usage limit of 1 user." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:142 +#, fuzzy, c-format +msgid "The entry message list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/cs_access.cpp:796 +msgid "The following feature/function names are available:" +msgstr "" + +#: modules/commands/cs_access.cpp:584 +msgid "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." +msgstr "" + +#: modules/commands/os_session.cpp:240 +#, fuzzy, c-format +msgid "" +"The host %s currently has %d sessions with a limit of %d because it matches " +"entry: %s." +msgstr "O host %s possui atualmente %d sessões com um limite de %d." + +#: modules/commands/ms_check.cpp:54 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has been read." +msgstr "O último memo que você enviou para %s (enviado em %s) foi lido." + +#: modules/commands/ms_check.cpp:52 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has not yet been read." +msgstr "" +"O último memo que você enviou para %s (enviado em %s) ainda não foi lido." + +#: modules/commands/ns_info.cpp:189 +#, c-format +msgid "The last quit message of %s will now be hidden from %s INFO displays." +msgstr "The last quit message of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:190 +#, c-format +msgid "The last quit message of %s will now be shown in %s INFO displays." +msgstr "The last quit message of %s will now be shown in %s INFO displays." + +#: modules/commands/ns_info.cpp:177 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." +msgstr "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:178 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." +msgstr "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." + +#: modules/commands/cs_enforce.cpp:190 +#, fuzzy, c-format +msgid "The limit on %s is not valid." +msgstr "O limite de memos para %s não pode ser mudado." + +#: modules/commands/os_forbid.cpp:193 +msgid "The mask must contain at least one non wildcard character." +msgstr "" + +#: modules/commands/ms_set.cpp:153 +#, c-format +msgid "The memo limit for %s may not be changed." +msgstr "O limite de memos para %s não pode ser mudado." + +#: modules/commands/cs_mode.cpp:347 +#, fuzzy, c-format +msgid "The mode lock list of %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/ns_set.cpp:355 +#, c-format +msgid "The new display MUST be a nickname of the nickname group %s." +msgstr "" + +#: include/language.h:98 +#, fuzzy, c-format +msgid "The new display is now %s." +msgstr "O Nível do Defcon está agora no Nível: %d" + +#: modules/commands/os_svs.cpp:57 +#, c-format +msgid "The nick %s is now being changed to %s." +msgstr "O nick %s está sendo alterado para %s." + +#: modules/commands/bs_bot.cpp:149 +msgid "The old information is the same as the new information specified." +msgstr "" + +#: modules/commands/os_info.cpp:157 +#, fuzzy, c-format +msgid "The oper info already exists on %s." +msgstr "Bot %s já existe." + +#: modules/commands/os_info.cpp:147 +#, fuzzy, c-format +msgid "The oper info list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/ns_info.cpp:183 +#, c-format +msgid "" +"The services access status of %s will now be hidden from %s INFO displays." +msgstr "" +"The services access status of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:184 +#, c-format +msgid "The services access status of %s will now be shown in %s INFO displays." +msgstr "" +"The services access status of %s will now be shown in %s INFO displays." + +#: modules/commands/os_session.cpp:433 +#, fuzzy +msgid "The session exception list is empty." +msgstr " EXCEPTION Modifica a lista de limite de sessões" + +#: modules/commands/ns_recover.cpp:121 +msgid "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:195 +#, c-format +msgid "There are %d memos on channel %s." +msgstr "Existem %d memos para o canal %s." + +#: modules/commands/bs_botlist.cpp:47 +msgid "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" +msgstr "" +"Não existem bots disponíveis no momento.\n" +"Peça a um Administrador dos Services para criar mais bots!" + +#: modules/commands/os_dns.cpp:213 +msgid "There are no configured servers." +msgstr "" + +#: modules/commands/os_forbid.cpp:392 +#, fuzzy, c-format +msgid "There are no forbids of type %s." +msgstr "Existem %d memos para o canal %s." + +#: modules/commands/ns_group.cpp:162 +#, fuzzy +msgid "There are too many nicks in your group." +msgstr " DELALL Deleta o vHost de todos os nicks de um grupo" + +#: modules/commands/cs_log.cpp:123 +#, fuzzy, c-format +msgid "There currently are no logging configurations for %s." +msgstr " RELOAD Recarrega o arquivo de configuração dos Services" + +#: modules/pseudoclients/memoserv.cpp:193 +#, c-format +msgid "There is %d memo on channel %s." +msgstr "Existe %d memo para o canal %s." + +#: include/language.h:110 +#, fuzzy, c-format +msgid "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." +msgstr "Digite /msg %s READ %d para ler." + +#: modules/commands/bs_assign.cpp:132 +#, c-format +msgid "There is no bot assigned to %s anymore." +msgstr "Não possui mais nenhum bot associado ao canal %s." + +#: modules/commands/os_news.cpp:33 +msgid "There is no logon news." +msgstr "Não existem logon news." + +#: modules/commands/os_news.cpp:43 +msgid "There is no oper news." +msgstr "Não existe nenhum oper news." + +#: modules/commands/os_news.cpp:53 +msgid "There is no random news." +msgstr "Não há RandomNews." + +#: modules/commands/os_config.cpp:41 +#, fuzzy, c-format +msgid "There is no such configuration block %s." +msgstr " RELOAD Recarrega o arquivo de configuração dos Services" + +#: modules/commands/cs_mode.cpp:706 +#, fuzzy, c-format +msgid "There is no such mode %s." +msgstr "Não existe nenhum oper news." + +#: modules/commands/ms_set.cpp:52 +msgid "There's no email address set for your nick." +msgstr "Não há endereço de email ajustado para o seu nick." + +#: modules/commands/os_forbid.cpp:304 modules/commands/os_forbid.cpp:496 +#, fuzzy, c-format +msgid "This channel has been forbidden: %s" +msgstr "Este canal foi registrado com o %s." + +#: modules/commands/cs_suspend.cpp:121 +#, fuzzy +msgid "This channel has been suspended." +msgstr "Este canal não pode ser usado." + +#: modules/commands/cs_suspend.cpp:232 +#, fuzzy +msgid "This channel is suspended." +msgstr "Este canal não pode ser usado." + +#: modules/commands/cs_suspend.cpp:268 +msgid "This channel may not be used." +msgstr "Este canal não pode ser usado." + +#: modules/commands/os_dns.cpp:702 +msgid "" +"This command allows managing DNS zones used for controlling what servers " +"users\n" +"are directed to when connecting. Omitting all parameters prints out the " +"status of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to " +"this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, " +"the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given " +"zones." +msgstr "" + +#: modules/commands/hs_group.cpp:72 +#, fuzzy +msgid "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." +msgstr "" +"Sintaxe: GROUP\n" +"\n" +"Este comando permite aos usuários ajustar o vhost do seu\n" +"nick ATUAL para ser o vhost de todos os nicks no mesmo grupo." + +#: modules/commands/ns_register.cpp:299 +msgid "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." +msgstr "" + +#: modules/m_rewrite.cpp:145 +#, c-format +msgid "This command is an alias to the command %s." +msgstr "" + +#: modules/commands/ns_register.cpp:95 +#, fuzzy +msgid "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." +msgstr "" +"Syntax: CONFIRM passcode\n" +"\n" +"This is the second step of nickname registration process.\n" +"You must perform this command in order to get your nickname\n" +"registered with %s. The passcode (or called auth code also)\n" +"is sent to your e-mail address in the first step of the\n" +"registration process. For more information about the first\n" +"stage of the registration process, type: /msg %s HELP REGISTER\n" +"\n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." + +#: modules/commands/os_modinfo.cpp:70 +#, fuzzy +msgid "This command lists information about the specified loaded module." +msgstr "" +"Sintaxe: MODINFO NomeDoArquivo\n" +"\n" +"Este comando lista informações sobre um módulo carregado." + +#: modules/commands/hs_list.cpp:136 +#, fuzzy +msgid "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." +msgstr "" +"Sintaxe: LIST [|<#X-Y>]\n" +"Este comando lista ao Operador os vhosts registrados.\n" +"Se uma Key é especificada, apenas entradas cujo nick ou vhost\n" +"combinem com o padrão fornecido em serão exibidas.\n" +"Ex.: Rob* mostra todas as entradas começando com \"Rob\"\n" +"Se o estilo #X-Y for usado, apenas entradas entre o alvo X\n" +"e Y serão exibidas. Ex.: #1-3 irá mostrar as 3 primeiras\n" +"entradas de nick/vhost.\n" +"A lista usa o valor de NSListMax como limite do número de\n" +"itens para exibir a um Operator de uma vez só." + +#: modules/commands/os_module.cpp:45 +#, fuzzy +msgid "" +"This command loads the module named modname from the modules\n" +"directory." +msgstr "" +"Sintaxe: MODLOAD NomeDoArquivo\n" +"\n" +"Este comando carrega o módulo chamado NomeDoArquivo\n" +"do diretório de módulos." + +#: modules/commands/ns_group.cpp:201 +#, fuzzy +msgid "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." +msgstr "" +"Sintaxe: GROUP alvo senha\n" +"\n" +"Este comando faz seu nick entrar no grupo de um nick alvo.\n" +"A senha é a senha do nick alvo.\n" +"\n" +"Entrando em um grupo permitirá a você compartilhar suas\n" +"configurações, memos e privilégios em canais com todos os\n" +"nicks do grupo.\n" +"\n" +"Um grupo existe por quanto tempo for necessário. Isso\n" +"significa que mesmo se um nick do grupo for desregistrado,\n" +"você não perderá os recursos compartilhados citados acima,\n" +"durante o tempo em que houver pelo menos um nick restando\n" +"no grupo.\n" +"\n" +"Você pode usar este comando mesmo se não ainda não tiver\n" +"registrado seu nick. Se seu nick já estiver registrado,\n" +"você precisará identificá-lo antes de usar este comando.\n" +"Digite /msg %s HELP IDENTIFY para mais informação; talvez\n" +"isso não seja possível em algumas redes.\n" +"\n" +"É recomendável usar este comando com nicks não-registrados,\n" +"pois eles serão automaticamente registrados ao usar o comando.\n" +"Você pode usar isto com um nick registrado (para alterar seu\n" +"grupo) apenas se for permitido na rede.\n" +"\n" +"Você só pode estar em um grupo por vez. Mesclar grupos não é\n" +"possível.\n" +"\n" +"Atenção: todos os nicks do grupo terão a mesma senha." + +#: modules/commands/ns_ajoin.cpp:292 +msgid "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." +msgstr "" + +#: modules/commands/ns_set.cpp:345 modules/commands/ns_set.cpp:669 +msgid "" +"This command may not be used on this network because nickname ownership is " +"disabled." +msgstr "" + +#: modules/commands/os_module.cpp:118 +#, fuzzy +msgid "This command reloads the module named modname." +msgstr "" +"Sintaxe: MODLOAD NomeDoArquivo\n" +"\n" +"Este comando carrega o módulo chamado NomeDoArquivo\n" +"do diretório de módulos." + +#: modules/commands/hs_request.cpp:344 +msgid "This command retrieves the vhost requests." +msgstr "" + +#: modules/commands/os_logsearch.cpp:159 +msgid "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." +msgstr "" + +#: modules/commands/cs_status.cpp:106 +msgid "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." +msgstr "" + +#: modules/commands/ns_group.cpp:285 +#, fuzzy +msgid "" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." +msgstr "" +"Syntax: UNGROUP [nick]\n" +"\n" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, url, and icq. Everything\n" +"else is reset. You may not ungroup yourself if there is only one\n" +"nick in your group." + +#: modules/commands/os_module.cpp:168 +#, fuzzy +msgid "This command unloads the module named modname." +msgstr "" +"Sintaxe: MODLOAD NomeDoArquivo\n" +"\n" +"Este comando carrega o módulo chamado NomeDoArquivo\n" +"do diretório de módulos." + +#: modules/commands/ns_register.cpp:353 +msgid "This command will resend you the registration confirmation email." +msgstr "" + +#: include/language.h:90 +#, c-format +msgid "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" +msgstr "" + +#: modules/commands/os_forbid.cpp:469 +#, fuzzy, c-format +msgid "This nickname has been forbidden: %s" +msgstr "Este nick está atualmente suspenso, motivo: %s" + +#: modules/commands/ns_recover.cpp:99 +#, fuzzy, c-format +msgid "This nickname has been recovered by %s." +msgstr "Este nick está atualmente suspenso, motivo: %s" + +#: modules/commands/ns_recover.cpp:77 +#, c-format +msgid "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." +msgstr "" + +#: include/language.h:95 +#, fuzzy +msgid "This nickname has been registered; you may not use it." +msgstr "Este canal foi registrado com o %s." + +#: modules/commands/ns_suspend.cpp:246 +#, fuzzy +msgid "This nickname is suspended." +msgstr "Este canal não pode ser usado." + +#: include/language.h:92 +#, c-format +msgid "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." +msgstr "" + +#: modules/commands/ms_read.cpp:95 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %d" +msgstr "Memo %d de %s (%s). Para apagar, digite: /msg %s DEL %s %d" + +#: modules/commands/ms_read.cpp:93 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %s %d" +msgstr "Memo %d de %s (%s). Para apagar, digite: /msg %s DEL %s %d" + +#: modules/commands/bs_kick.cpp:791 +msgid "To protect ops against bot kicks" +msgstr "" + +#: modules/commands/bs_kick.cpp:856 +msgid "To protect voices against bot kicks" +msgstr "" + +#: modules/commands/cs_list.cpp:46 +msgid "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." +msgstr "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." + +#: modules/commands/os_logsearch.cpp:139 +#, fuzzy, c-format +msgid "Too many results for %s." +msgstr "Lista de acesso para %s:" + +#: modules/extra/stats/cs_fantasy_top.cpp:149 +#, c-format +msgid "Top %i of %s" +msgstr "" + +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Topic" +msgstr "Trava de tópico" + +#: modules/commands/cs_topic.cpp:258 +#, fuzzy +msgid "Topic lock" +msgstr "Trava de tópico" + +#: modules/commands/cs_topic.cpp:114 +#, fuzzy, c-format +msgid "Topic lock option for %s is now off." +msgstr "Trava de tópico para %s está agora ATIVADA." + +#: modules/commands/cs_topic.cpp:97 +#, fuzzy, c-format +msgid "Topic lock option for %s is now on." +msgstr "Trava de tópico para %s está agora ATIVADA." + +#: modules/commands/cs_topic.cpp:256 +#, fuzzy +msgid "Topic retention" +msgstr "Retenção de tópico" + +#: modules/commands/cs_topic.cpp:60 +#, fuzzy, c-format +msgid "Topic retention option for %s is now off." +msgstr "Retenção de tópico para %s está agora ATIVADA." + +#: modules/commands/cs_topic.cpp:54 +#, fuzzy, c-format +msgid "Topic retention option for %s is now on." +msgstr "Retenção de tópico para %s está agora ATIVADA." + +#: modules/commands/cs_topic.cpp:265 +msgid "Topic set by" +msgstr "" + +#: modules/commands/bs_kick.cpp:1323 +msgid "Turn caps lock OFF!" +msgstr "Desligue o CAPS LOCK!" + +#: modules/extra/stats/m_chanstats.cpp:17 +#: modules/extra/stats/m_chanstats.cpp:71 +#, fuzzy +msgid "Turn chanstats statistics on or off" +msgstr " SECURE Ativa/Desativa os recursos de segurança para o seu nick" + +#: modules/commands/ns_set.cpp:1009 +#, fuzzy +msgid "Turn nickname security on or off" +msgstr " SECURE Ativa/Desativa os recursos de segurança para o seu nick" + +#: modules/commands/ns_set.cpp:655 +#, fuzzy +msgid "Turn protection on or off" +msgstr " KILL Ativa/Desativa a proteção de kill para o seu nick" + +#: modules/commands/ns_list.cpp:264 +#, fuzzy, c-format +msgid "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Syntax: SASET nickname PRIVATE {ON | OFF}\n" +"\n" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" + +#: modules/commands/ns_list.cpp:236 +#, fuzzy, c-format +msgid "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Sintaxe: SET PRIVATE {ON | OFF}\n" +"\n" +"Torna a opção de privacidade do %s sobre o seu nick\n" +"em ativada (ON) ou desativada (OFF). Com o PRIVATE ativado,\n" +"seu nick não aparecerá nas listagens de nicks geradas com\n" +"o comando %s's LIST. (Entretando, alguém que sabe do seu\n" +"nick ainda pode obter informações usando o comando INFO)." + +#: modules/commands/ns_set.cpp:1059 modules/commands/ns_set.cpp:1088 +#, fuzzy, c-format +msgid "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." +msgstr "" +"Sintaxe: SET SECURE {ON | OFF}\n" +"\n" +"Torna os recursos de segurança do %s ativados (ON) ou\n" +"desativados (OFF) sobre o seu nick. Com o SECURE acionado\n" +"você deve entrar com sua senha antes de ser reconhecido como\n" +"usuário do nick, independentemente do fato do seu endereço\n" +"constar na lista de acesso. Entretanto, se você está na\n" +"lista de acesso, o %s não irá dar auto-kill em você de\n" +"acordo com os ajustes da opção KILL." + +#: modules/extra/stats/m_chanstats.cpp:142 +#, fuzzy +msgid "Turns chanstats channel statistics ON or OFF for this user." +msgstr " SECURE Ativa/Desativa os recursos de segurança para o seu nick" + +#: modules/extra/stats/m_chanstats.cpp:61 +#: modules/extra/stats/m_chanstats.cpp:119 +#, fuzzy +msgid "Turns chanstats statistics ON or OFF." +msgstr " SECURE Ativa/Desativa os recursos de segurança para o seu nick" + +#: modules/commands/ns_set.cpp:772 +#, fuzzy, c-format +msgid "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Syntax: SASET nickname KILL {ON | QUICK | IMMED | OFF}\n" +"\n" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +"\n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." + +#: modules/commands/ns_set.cpp:738 +#, fuzzy, c-format +msgid "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Sintaxe: SET KILL {ON | QUICK | IMMED | OFF}\n" +"\n" +"Possibilita a proteção de KILL do seu nick. Com a proteção\n" +"de KILL acionada, se outro usuário tentar tomar seu nick,\n" +"será dado 1 minuto para este mudar de nick; após isso, será\n" +"forçado pelo %s a trocar de nick, ou será desconectado da\n" +"rede (esse último não acontece em todas elas).\n" +"\n" +"Se você selecionar QUICK, será dado ao usuário somente 20\n" +"segundos para mudar de nick ao invés do usual (60 segundos).\n" +"Se você selecionar a opção IMMED, o nick será mudado\n" +"imediatamente sem mesmo ser avisado antes; é recomendado\n" +"não usar essa opção, a não ser que seja necessário. Pode\n" +"acontecer do Administrador da Rede desabilitar essa opção." + +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_forbid.cpp:358 +msgid "Type" +msgstr "" + +#: modules/commands/ns_set.cpp:62 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Digite /msg %s HELP SET opção para maiores informações\n" +"sobre uma opção em particular." + +#: modules/commands/bs_kick.cpp:151 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." +msgstr "" +"Type /msg %s HELP SASET option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname. " + +#: modules/commands/ns_set.cpp:107 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." +msgstr "" +"Type /msg %s HELP SASET option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname. " + +#: modules/commands/bs_set.cpp:62 modules/commands/cs_set.cpp:63 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." +msgstr "" +"Digite /msg %s HELP SET opção para maiores informações\n" +"sobre uma opção em particular." + +#: modules/pseudoclients/nickserv.cpp:361 +#, fuzzy, c-format +msgid "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." +msgstr "" +"Digite /msg %s SET EMAIL e-mail para setar seu e-mail.\n" +"Sua privacidade é respeitada; seu e-mail não será dado\n" +"para terceiros." + +#: modules/commands/os_module.cpp:128 +#, fuzzy +msgid "Un-Load a module" +msgstr " MODUNLOAD Descarrega um módulo" + +#: modules/commands/os_sxline.cpp:337 modules/commands/os_sxline.cpp:552 +#: modules/commands/os_akill.cpp:136 +#, fuzzy, c-format +msgid "Unable to find regex engine %s." +msgstr "Impossível remover o módulo %s" + +#: modules/commands/os_module.cpp:36 modules/commands/os_module.cpp:108 +#, fuzzy, c-format +msgid "Unable to load module %s." +msgstr "Impossível carregar o módulo %s" + +#: modules/commands/os_module.cpp:73 modules/commands/os_module.cpp:90 +#: modules/commands/os_module.cpp:145 modules/commands/os_module.cpp:159 +#, fuzzy, c-format +msgid "Unable to remove module %s." +msgstr "Impossível remover o módulo %s" + +#: modules/commands/bs_assign.cpp:90 +#, fuzzy +msgid "Unassigns a bot from a channel" +msgstr " UNASSIGN Desassocia um bot de um canal" + +#: modules/commands/bs_assign.cpp:139 +#, fuzzy +msgid "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." +msgstr "" +"Sintaxe: UNASSIGN canal\n" +"\n" +"Desassocia um bot de um canal. Quando você usa este comando,\n" +"o bot não irá entrar mais no canal. Entretando, será mantida\n" +"a configuração do bot para aquele canal, para que você possa\n" +"sempre poder associá-lo àquele canal mais tarde sem ter que\n" +"configurar tudo novamente." + +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1193 +#: modules/commands/bs_kick.cpp:1196 +#, fuzzy +msgid "Underlines kicker" +msgstr " Kick por sublinhado: %s" + +#: modules/commands/os_dns.cpp:595 +#, fuzzy +msgid "Unknown SET option." +msgstr "Unknown SASET option %s." + +#: modules/commands/os_stats.cpp:229 +#, fuzzy, c-format +msgid "Unknown STATS option: %s" +msgstr "Opção STATS desconhecida: %s." + +#: src/command.cpp:222 src/command.cpp:233 +#, fuzzy, c-format +msgid "Unknown command %s." +msgstr "Opção desconhecida: %s." + +#: src/command.cpp:220 src/command.cpp:231 +#, fuzzy, c-format +msgid "Unknown command %s. \"%s%s HELP\" for help." +msgstr "Comando desconhecido %s. Digite %s%s HELP para ajuda." + +#: modules/commands/cs_mode.cpp:317 modules/commands/cs_mode.cpp:409 +#, fuzzy, c-format +msgid "Unknown mode character %c ignored." +msgstr "Modo %c desconhecido e ignorado." + +#: modules/commands/os_logsearch.cpp:78 +#, fuzzy, c-format +msgid "Unknown parameter: %s" +msgstr "SET opção configuração" + +#: modules/commands/os_dns.cpp:241 +msgid "Unpooled" +msgstr "" + +#: modules/commands/cs_drop.cpp:77 +#, fuzzy +msgid "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." +msgstr "" +"Sintaxe: DROP canal\n" +"\n" +"Cancela o registro do canal. So poderá ser usado pelo\n" +"fundador do canal." + +#: modules/commands/cs_drop.cpp:74 +#, fuzzy +msgid "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." +msgstr "" +"Sintaxe: DROP canal\n" +"\n" +"Cancela o registro de um canal. Somente Administradores dos\n" +"Services podem cancelar canais que pertencem a outros usuários." + +#: modules/commands/ns_suspend.cpp:160 +#, fuzzy +msgid "Unsuspend a given nick" +msgstr " UNSUSPEND Libera o nick fornecido" + +#: modules/commands/ns_suspend.cpp:199 +msgid "Unsuspends a nickname which allows it to be used again." +msgstr "" + +#: modules/commands/cs_updown.cpp:126 +msgid "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." +msgstr "" + +#: modules/commands/cs_updown.cpp:48 +#, fuzzy +msgid "Updates a selected nicks status on a channel" +msgstr " BAN Bane o nick selecionado em um canal" + +#: modules/commands/ns_update.cpp:19 +#, fuzzy +msgid "Updates your current status, i.e. it checks for new memos" +msgstr "" +" UPDATE Atualiza seu status atual, ou seja, verifica novos memos" + +#: modules/commands/ns_update.cpp:43 +#, fuzzy +msgid "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." +msgstr "" +"Sintaxe: UPDATE\n" +"Atualiza seu status atual, ou seja, checa por novos memos,\n" +"seta modos de canal necessários (ModeonID) e atualiza seu\n" +"vHost e suas flags de usuário (Último horário visto etc)." + +#: modules/commands/os_update.cpp:25 +msgid "Updating databases." +msgstr "Atualizando banco de dados." + +#: modules/commands/os_stats.cpp:154 +#, c-format +msgid "Uplink capab: %s" +msgstr "Uplink capab: %s" + +#: modules/commands/os_stats.cpp:153 +#, c-format +msgid "Uplink server: %s" +msgstr "Uplink server: %s" + +#: modules/commands/help.cpp:127 +#, c-format +msgid "Use the %s ALL command to list all commands and their descriptions." +msgstr "" + +#: modules/commands/bs_info.cpp:59 +msgid "Used on" +msgstr "" + +#: data/chanserv.example.conf:821 +#, fuzzy +msgid "Used to manage channels" +msgstr "%s alterou seus modos de usuário." + +#: data/chanserv.example.conf:809 +#, fuzzy +msgid "Used to manage the list of privileged users" +msgstr " ACCESS Modifica a lista de usuários privilegiados" + +#: data/chanserv.example.conf:815 +msgid "Used to modify the channel status of you or other users" +msgstr "" + +#: modules/commands/cs_akick.cpp:575 +#, fuzzy +msgid "User has been banned from the channel" +msgstr "Você não está mais banido do %s." + +#: modules/commands/os_dns.cpp:587 +#, fuzzy, c-format +msgid "User limit for %s removed." +msgstr "vhost para %s removido." + +#: modules/commands/os_dns.cpp:585 +#, fuzzy, c-format +msgid "User limit for %s set to %d." +msgstr "Limite de memos para %s é agora de %d." + +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Users" +msgstr "Lista de bots:" + +#: modules/commands/os_stats.cpp:172 +#, c-format +msgid "Users (nick): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:177 +#, c-format +msgid "Users (uid): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_list.cpp:184 +#, fuzzy +msgid "Users list:" +msgstr "Lista de bots:" + +#: modules/commands/ns_info.cpp:105 modules/commands/ns_info.cpp:107 +msgid "VHost" +msgstr "" + +#: modules/commands/hs_set.cpp:92 +#, fuzzy, c-format +msgid "VHost for %s set to %s." +msgstr "vhost de %s ajustado para %s." + +#: modules/commands/hs_set.cpp:90 +#, fuzzy, c-format +msgid "VHost for %s set to %s@%s." +msgstr "vhost de %s ajustado para %s@%s." + +#: modules/commands/hs_set.cpp:199 +#, fuzzy, c-format +msgid "VHost for group %s set to %s." +msgstr "vhost do grupo %s ajustado para %s." + +#: modules/commands/hs_set.cpp:197 +#, fuzzy, c-format +msgid "VHost for group %s set to %s@%s." +msgstr "vhost do grupo %s ajustado para %s@%s." + +#: modules/commands/os_session.cpp:247 +msgid "VIEW host" +msgstr "" + +#: modules/commands/os_sxline.cpp:428 modules/commands/os_sxline.cpp:662 +#: modules/commands/os_akill.cpp:389 +#, fuzzy +msgid "VIEW [mask | list | id]" +msgstr "LIST [canal] [list | NEW]" + +#: modules/commands/os_session.cpp:526 +msgid "VIEW [mask | list]" +msgstr "" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +msgid "Value" +msgstr "" + +#: modules/commands/os_config.cpp:48 +#, fuzzy, c-format +msgid "Value of %s:%s changed to %s" +msgstr "Founder do canal %s alterado para %s." + +#: modules/commands/hs_list.cpp:58 modules/commands/hs_request.cpp:305 +msgid "Vhost" +msgstr "" + +#: modules/commands/hs_del.cpp:38 +#, fuzzy, c-format +msgid "Vhost for %s removed." +msgstr "vhost para %s removido." + +#: modules/commands/os_oper.cpp:69 +#, fuzzy +msgid "View and change Services Operators" +msgstr "%s is a services operator of type %s." + +#: modules/commands/os_config.cpp:19 +msgid "View and change configuration file settings" +msgstr "" + +#: modules/commands/os_session.cpp:245 +#, fuzzy +msgid "View the list of host sessions" +msgstr " SESSION Mostra a lista de sessões de host" + +#: modules/commands/bs_kick.cpp:1221 +msgid "Voices protection" +msgstr "Proteção de Voices" + +#: modules/commands/bs_kick.cpp:1406 +msgid "Watch your language!" +msgstr "Cuidado com suas palavras!" + +#: modules/commands/cs_list.cpp:237 +#, c-format +msgid "" +"When private is set, the channel will not appear in\n" +"%s's %s command." +msgstr "" + +#: modules/commands/ms_info.cpp:204 +#, fuzzy +msgid "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." +msgstr "" +"Sintaxe: INFO [nick | canal]\n" +"\n" +"Sem um parâmetro, informa o número de mensagens que você\n" +"tem, quantas mensagens ainda não foram lidas, e quantas\n" +"mensagens no total você pode receber.\n" +"\n" +"Com o parâmetro do canal, mostra a mesma informação para\n" +"o canal fornecido.\n" +"\n" +"Com o parâmetro de nick, mostra a mesma informação para\n" +"o nick fornecido. Esta derivação do comando é limitada aos\n" +"Administradores dos Services." + +#: modules/commands/ns_logout.cpp:66 +#, fuzzy +msgid "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." +msgstr "" +"Sintaxe: LOGOUT [nick [REVALIDATE]]\n" +"\n" +"Sem nenhum parâmetro, reverte o efeito do comando IDENTIFY,\n" +"ou seja, faz com que você não seja mais reconhecido como o\n" +"verdadeiro dono do nick. Note, entretanto, que ele não pedirá\n" +"que você se identifique novamente.\n" +"\n" +"Com um parâmetro, fará o mesmo para o nick determinado. Se você\n" +"especificar REVALIDATE também, os Services irão pedir que o nick\n" +"em questão se identifique novamente. \n" +"\n" +"Comando limitado aos Administradores dos Services." + +#: modules/commands/os_stats.cpp:236 +#, fuzzy +msgid "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." +msgstr "" +"Sintaxe: STATS [AKILL | ALL | RESET]\n" +"\n" +"Sem nenhuma opção, mostra o número atual de usuários e\n" +"IRCops online (excluindo Services), o número máximo de\n" +"usuários online conectados simultaneamente desde que os\n" +"Services foram iniciados na rede, e o tempo pelo qual os\n" +"Services estão rodando sem interrupções.\n" +"\n" +"Com a opção AKILL, será mostrado o tamanho atual da\n" +"listas de AKILL e SQLINE e o tempo padrão para um AKILL\n" +"ou SQLINE expirar.\n" +"\n" +"A opção ALL está disponível apenas para os Administradores\n" +"dos Services, e mostra informações sobre o consumo de memória\n" +"dos Services. O uso deste comando pode congelar os Services\n" +"por um curto período de tempo em redes grandes, então não\n" +"abuse deste comando!\n" +"\n" +"A opção RESET reinicia a contagem do máximo de usuários\n" +"para o número de usuários atualmente conectados na rede." + +#: modules/commands/bs_badwords.cpp:194 +msgid "Word" +msgstr "" + +#: modules/commands/ns_group.cpp:158 +#, c-format +msgid "You are already a member of the group of %s." +msgstr "Você já é um membro do grupo %s." + +#: modules/commands/os_login.cpp:34 modules/commands/ns_identify.cpp:87 +msgid "You are already identified." +msgstr "Você já está identificado." + +#: modules/commands/cs_invite.cpp:64 +#, fuzzy, c-format +msgid "You are already in %s!" +msgstr "You are already in %s! " + +#: modules/commands/os_set.cpp:91 +#, fuzzy +msgid "You are no longer a super admin." +msgstr "Você não é mais um Super-Admin" + +#: modules/commands/os_login.cpp:81 +#, fuzzy +msgid "You are not identified." +msgstr "Você já está identificado." + +#: include/language.h:100 +#, fuzzy +msgid "You are not permitted to be on this channel." +msgstr "Você não tem permissão para mudar seu limite de memos." + +#: modules/commands/ms_set.cpp:158 +msgid "You are not permitted to change your memo limit." +msgstr "Você não tem permissão para mudar seu limite de memos." + +#: modules/commands/ns_cert.cpp:183 +#, fuzzy +msgid "You are not using a client certificate." +msgstr "Você já está identificado." + +#: modules/commands/os_set.cpp:85 +#, fuzzy +msgid "You are now a super admin." +msgstr "Você é agora um Super-Admin" + +#: modules/commands/os_oline.cpp:36 +msgid "You are now an IRC Operator." +msgstr "Você agora é um Operador de IRC." + +#: modules/commands/ns_resetpass.cpp:108 +#, fuzzy +msgid "You are now identified for your nick. Change your password now." +msgstr "You are now identified for your nick. Change your password now." + +#: modules/commands/ns_group.cpp:64 +#, c-format +msgid "You are now in the group of %s." +msgstr "Você é agora um membro do grupo %s." + +#: modules/pseudoclients/memoserv.cpp:147 +#, fuzzy, c-format +msgid "" +"You are over your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Atenção: Você ultrapassou seu número máximo de memos (%d). Não será possível " +"receber novos memos enquanto você não apagar alguns." + +#: modules/commands/os_noop.cpp:33 +msgid "You can not NOOP Services." +msgstr "" + +#: modules/commands/cs_access.cpp:672 +msgid "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." +msgstr "" + +#: modules/commands/os_jupe.cpp:34 +#, fuzzy +msgid "You can not jupe an already juped server." +msgstr "You can not jupe your services server or your uplink server." + +#: modules/commands/os_jupe.cpp:32 +#, fuzzy +msgid "You can not jupe your Services' pseudoserver or your uplink server." +msgstr "You can not jupe your services server or your uplink server." + +#: modules/commands/os_module.cpp:80 +#, c-format +msgid "You can not reload this module directly, instead reload %s." +msgstr "" + +#: modules/commands/ms_rsend.cpp:46 +msgid "You can not request a receipt when sending a memo to yourself." +msgstr "" +"Você não pode pedir uma notificação ao enviar uma mensagem a si próprio." + +#: modules/commands/ns_recover.cpp:163 +#, fuzzy, c-format +msgid "You can't %s yourself!" +msgstr "Você não pode usar o comando GHOST em si mesmo!" + +#: modules/commands/cs_access.cpp:154 modules/commands/cs_flags.cpp:109 +#: modules/commands/cs_xop.cpp:151 +#, fuzzy +msgid "You can't add a channel to its own access list." +msgstr "Resultado não encontrado na lista de acesso do %s." + +#: modules/commands/ns_logout.cpp:37 +#, fuzzy, c-format +msgid "You can't logout %s, they are a Services Operator." +msgstr "" +"Impossível fazer logout em %s porque ele é um Administrador dos Services." + +#: modules/commands/ns_set.cpp:927 +#, fuzzy, c-format +msgid "You cannot %s on this network." +msgstr "Você não pode remover o e-mail nesta Rede." + +#: modules/commands/cs_flags.cpp:231 +#, fuzzy, c-format +msgid "You cannot set the %c flag." +msgstr "You cannot use this command." + +#: modules/commands/ms_set.cpp:173 +#, c-format +msgid "You cannot set the memo limit for %s higher than %d." +msgstr "Você não pode colocar o limite de memos para %s maior que %d." + +#: modules/commands/ms_set.cpp:175 +#, c-format +msgid "You cannot set your memo limit higher than %d." +msgstr "Você não pode colocar seu limite de memos maior que %d." + +#: modules/commands/bs_assign.cpp:124 +#, fuzzy +msgid "You cannot unassign bots while persist is set on the channel." +msgstr "You can not unassign bots while persist is set on the channel." + +#: modules/commands/ns_set.cpp:480 +msgid "You cannot unset the e-mail on this network." +msgstr "Você não pode remover o e-mail nesta Rede." + +#: modules/commands/help.cpp:177 +msgid "You cannot use this command." +msgstr "You cannot use this command." + +#: modules/commands/ms_info.cpp:151 +#, c-format +msgid "You currently have %d memos, of which %d are unread." +msgstr "Você possui atualmente %d memos, dos quais %d não foram lidos." + +#: modules/commands/ms_info.cpp:149 +#, c-format +msgid "You currently have %d memos, of which 1 is unread." +msgstr "Você possui atualmente %d memos, dos quais 1 não foi lido." + +#: modules/commands/ms_info.cpp:147 +#, c-format +msgid "You currently have %d memos." +msgstr "Você possui atualmente %d memos." + +#: modules/commands/ms_info.cpp:145 +#, c-format +msgid "You currently have %d memos; all of them are unread." +msgstr "Você possui atualmente %d memos; dos quais nenhum foi lido." + +#: modules/commands/ms_info.cpp:134 +msgid "You currently have 1 memo, and it has not yet been read." +msgstr "Você possui atualmente 1 memo, e este ainda não foi lido." + +#: modules/commands/ms_info.cpp:136 +msgid "You currently have 1 memo." +msgstr "Você possui atualmente 1 memo." + +#: modules/commands/ms_info.cpp:130 +msgid "You currently have no memos." +msgstr "Você não possui nenhum memo atualmente." + +#: modules/commands/cs_mode.cpp:564 modules/commands/cs_mode.cpp:621 +#, c-format +msgid "You do not have access to set mode %c." +msgstr "" + +#: modules/commands/cs_mode.cpp:578 modules/commands/cs_mode.cpp:590 +#: modules/commands/cs_mode.cpp:631 +#, c-format +msgid "You do not have the access to change %s's modes." +msgstr "" + +#: modules/commands/cs_seen.cpp:198 +#, c-format +msgid "You found me, %s!" +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:143 +#, c-format +msgid "You have %d new memos." +msgstr "Você tem %d novos memos." + +#: modules/pseudoclients/memoserv.cpp:143 +msgid "You have 1 new memo." +msgstr "Você tem 1 novo memo." + +#: include/language.h:112 +#, fuzzy, c-format +msgid "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." +msgstr "Digite /msg %s READ %d para ler." + +#: modules/commands/cs_invite.cpp:76 +#, fuzzy, c-format +msgid "You have been invited to %s by %s." +msgstr "You have been invited to %s." + +#: modules/commands/cs_invite.cpp:81 +#, c-format +msgid "You have been invited to %s." +msgstr "You have been invited to %s." + +#: modules/protocol/ratbox.cpp:166 modules/commands/ns_recover.cpp:96 +#, fuzzy, c-format +msgid "You have been logged in as %s." +msgstr "Seu nick foi desconectado." + +#: modules/commands/os_login.cpp:86 +#, fuzzy +msgid "You have been logged out." +msgstr "Seu nick foi desconectado." + +#: modules/commands/cs_unban.cpp:94 +#, c-format +msgid "You have been unbanned from %s." +msgstr "Você não está mais banido do %s." + +#: modules/commands/cs_unban.cpp:54 +#, fuzzy, c-format +msgid "You have been unbanned from %d channels." +msgstr "Você não está mais banido do %s." + +#: modules/commands/ms_info.cpp:169 +msgid "You have no limit on the number of memos you may keep." +msgstr "Você não possui limite de memos que pode guardar." + +#: include/language.h:114 +#, fuzzy +msgid "You have no memos." +msgstr "Você tem %d novos memos." + +#: include/language.h:117 +#, fuzzy +msgid "You have no new memos." +msgstr "Você tem %d novos memos." + +#: modules/pseudoclients/memoserv.cpp:149 +#, fuzzy, c-format +msgid "" +"You have reached your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Atenção: Você atingiu seu número máximo de memos (%d). Não será possível " +"receber novos memos enquanto você não apagar alguns." + +#: modules/commands/ns_recover.cpp:117 +#, fuzzy, c-format +msgid "You have regained control of %s." +msgstr "You have been invited to %s." + +#: modules/commands/ns_drop.cpp:66 +#, fuzzy +msgid "You may drop any nick within your group." +msgstr " DELALL Deleta o vHost de todos os nicks de um grupo" + +#: modules/commands/cs_mode.cpp:322 modules/commands/cs_mode.cpp:414 +#, c-format +msgid "You may not (un)lock mode %c." +msgstr "" + +#: modules/commands/ns_set.cpp:485 +#, fuzzy +msgid "You may not change the e-mail of other Services Operators." +msgstr "Você não pode remover o e-mail nesta Rede." + +#: modules/commands/ns_set.cpp:474 +#, fuzzy +msgid "You may not change the email of an unconfirmed account." +msgstr "Você não pode remover o e-mail nesta Rede." + +#: modules/commands/ns_set.cpp:196 +#, fuzzy +msgid "You may not change the password of other Services Operators." +msgstr "" +"Impossível fazer logout em %s porque ele é um Administrador dos Services." + +#: modules/commands/ns_drop.cpp:45 +#, fuzzy +msgid "You may not drop other Services Operators' nicknames." +msgstr "%s is a services operator of type %s." + +#: modules/commands/ns_getpass.cpp:32 +#, fuzzy +msgid "You may not get the password of other Services Operators." +msgstr "" +"Impossível fazer logout em %s porque ele é um Administrador dos Services." + +#: modules/commands/ns_suspend.cpp:100 +#, fuzzy +msgid "You may not suspend other Services Operators' nicknames." +msgstr "" +"Impossível fazer logout em %s porque ele é um Administrador dos Services." + +#: modules/commands/ns_access.cpp:136 +#, fuzzy +msgid "" +"You may view but not modify the access list of other Services Operators." +msgstr "" +"Impossível fazer logout em %s porque ele é um Administrador dos Services." + +#: modules/commands/ns_cert.cpp:292 +#, fuzzy +msgid "" +"You may view but not modify the certificate list of other Services Operators." +msgstr "" +"Impossível fazer logout em %s porque ele é um Administrador dos Services." + +#: modules/commands/cs_seen.cpp:287 +#, c-format +msgid "You might see yourself in the mirror, %s." +msgstr "" + +#: include/language.h:120 +msgid "You must assign a bot to the channel before using this command." +msgstr "" + +#: modules/commands/cs_register.cpp:49 +msgid "You must be a channel operator to register the channel." +msgstr "Você deve ser no mínimo um operador para registrar o canal." + +#: modules/commands/cs_updown.cpp:94 modules/commands/cs_updown.cpp:192 +#, fuzzy, c-format +msgid "You must be in %s to use this command." +msgstr "You need to be identified to use this command." + +#: modules/commands/cs_register.cpp:37 +#, fuzzy +msgid "You must confirm your account before you can register a channel." +msgstr "Você deve ser no mínimo um operador para registrar o canal." + +#: modules/commands/hs_request.cpp:100 +#, fuzzy +msgid "You must confirm your account before you may request a vhost." +msgstr "Você deve ser no mínimo um operador para registrar o canal." + +#: modules/commands/ms_send.cpp:44 +#, fuzzy +msgid "You must confirm your account before you may send a memo." +msgstr "Você deve ser no mínimo um operador para registrar o canal." + +#: modules/commands/cs_drop.cpp:42 +#, c-format +msgid "" +"You must enter the channel name twice as a confirmation that you wish to drop" +" %s." +msgstr "" + +#: modules/commands/ns_register.cpp:153 +#, c-format +msgid "You must have been using this nick for at least %d seconds to register." +msgstr "" +"Você deve estar conectado há mais de %d segundos para registrar seu nick." + +#: modules/commands/cs_mode.cpp:913 +#, fuzzy, c-format +msgid "You must have the %s(ME) privilege on the channel to use this command." +msgstr "You need to be identified to use this command." + +#: modules/pseudoclients/nickserv.cpp:358 +msgid "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." +msgstr "" +"Você deve agora setar um e-mail para seu nick.\n" +"Este e-mail permitirá que você receba sua senha por ele\n" +"caso você se esqueça dela." + +#: modules/commands/help.cpp:172 +msgid "You need to be identified to use this command." +msgstr "You need to be identified to use this command." + +#: modules/commands/ms_info.cpp:182 +#, fuzzy +msgid "You will be notified by message and by mail when new memos arrive." +msgstr "Você será notificado de novos memos quando eles forem enviados." + +#: modules/commands/ms_info.cpp:175 +#, fuzzy +msgid "" +"You will be notified of new memos at logon and when they arrive, and by mail " +"when they arrive." +msgstr "" +"Você será notificado de novos memos quando conectar e quando eles forem " +"enviados." + +#: modules/commands/ms_info.cpp:177 +msgid "You will be notified of new memos at logon and when they arrive." +msgstr "" +"Você será notificado de novos memos quando conectar e quando eles forem " +"enviados." + +#: modules/commands/ms_info.cpp:189 +#, fuzzy +msgid "" +"You will be notified of new memos at logon, and by mail when they arrive." +msgstr "" +"Você será notificado de novos memos quando conectar e quando eles forem " +"enviados." + +#: modules/commands/ms_info.cpp:191 +msgid "You will be notified of new memos at logon." +msgstr "Você será notificado de novos memos quando conectar." + +#: modules/commands/ms_info.cpp:184 +msgid "You will be notified when new memos arrive." +msgstr "Você será notificado de novos memos quando eles forem enviados." + +#: modules/commands/ms_set.cpp:190 +msgid "You will no longer be able to receive memos." +msgstr "Você não poderá mais receber memos." + +#: modules/commands/ms_set.cpp:57 +msgid "You will no longer be informed via email." +msgstr "Você não será mais notificado por email." + +#: modules/commands/ms_info.cpp:195 +msgid "You will not be notified of new memos." +msgstr "Você será notificado de novos memos." + +#: modules/commands/ms_set.cpp:49 +msgid "You will now be informed about new memos via email." +msgstr "Você será notificado sobre novos memos por email." + +#: modules/commands/os_svs.cpp:86 +msgid "Your IRCd does not support SVSJOIN." +msgstr "" + +#: modules/commands/os_svs.cpp:31 +msgid "Your IRCd does not support SVSNICK." +msgstr "" + +#: modules/commands/os_svs.cpp:130 +msgid "Your IRCd does not support SVSPART." +msgstr "" + +#: include/language.h:127 +msgid "" +"Your IRCd does not support vIdent's, if this is incorrect, please report " +"this as a possible bug" +msgstr "" + +#: modules/extra/m_ldap_authentication.cpp:110 +#: modules/extra/m_sql_authentication.cpp:55 +#, fuzzy, c-format +msgid "Your account %s has been successfully created." +msgstr "Bot %s foi removido." + +#: modules/commands/ns_register.cpp:328 +#, fuzzy +msgid "Your account is already confirmed." +msgstr "Você já está identificado." + +#: modules/commands/ns_register.cpp:396 +#, fuzzy, c-format +msgid "Your account will expire, if not confirmed, in %s." +msgstr "Você já está identificado." + +#: modules/commands/ns_set.cpp:1274 +#, fuzzy, c-format +msgid "Your email address has been changed to %s." +msgstr "E-mail address for %s changed to %s." + +#: modules/commands/os_forbid.cpp:544 modules/commands/os_forbid.cpp:553 +#, fuzzy +msgid "Your email address is not allowed, choose a different one." +msgstr "Todas as O:lines do servidor %s foram removidas." + +#: modules/commands/ns_register.cpp:260 modules/commands/ns_register.cpp:391 +msgid "" +"Your email address is not confirmed. To confirm it, follow the instructions " +"that were emailed to you." +msgstr "" + +#: modules/commands/ns_register.cpp:67 +#, fuzzy, c-format +msgid "Your email address of %s has been confirmed." +msgstr "Todas as O:lines do servidor %s foram removidas." + +#: modules/extra/m_ldap_authentication.cpp:159 +#, fuzzy, c-format +msgid "Your email has been updated to %s" +msgstr "E-mail address for %s changed to %s." + +#: modules/extra/m_sql_authentication.cpp:62 +#, fuzzy, c-format +msgid "Your email has been updated to %s." +msgstr "E-mail address for %s changed to %s." + +#: modules/commands/ms_set.cpp:197 +msgid "Your memo limit has been disabled." +msgstr "Seu limite de memos foi desativado." + +#: modules/commands/ms_set.cpp:183 +#, c-format +msgid "Your memo limit has been set to %d." +msgstr "Seu limite de memo é agora de %d." + +#: modules/commands/ms_info.cpp:164 +#, c-format +msgid "Your memo limit is %d, and may not be changed." +msgstr "Seu limite de memos é de %d, e não pode ser alterado." + +#: modules/commands/ms_info.cpp:166 +#, c-format +msgid "Your memo limit is %d." +msgstr "Seu limite de memos é de %d." + +#: modules/commands/ms_info.cpp:159 +msgid "Your memo limit is 0; you will not receive any new memos." +msgstr "Seu limite de memos é de 0; você não pode receber novos memos." + +#: modules/commands/ms_info.cpp:157 +#, fuzzy +msgid "" +"Your memo limit is 0; you will not receive any new memos. You cannot change " +"this limit." +msgstr "" +"Seu limite de memos é de 0; você não pode receber novos memos. Você não pode " +"alterar esse limite." + +#: modules/commands/ns_logout.cpp:50 +msgid "Your nick has been logged out." +msgstr "Seu nick foi desconectado." + +#: modules/commands/ns_group.cpp:156 +#, fuzzy +msgid "Your nick is already registered." +msgstr "Seu nick já está registrado; digite /msg %s DROP primeiro." + +#: modules/commands/ns_group.cpp:246 +msgid "Your nick is not grouped to anything, you can't ungroup it." +msgstr "Your nick is not grouped to anything, you can't ungroup it." + +#: include/language.h:77 +#, fuzzy +msgid "Your nick isn't registered." +msgstr "Nick %s registrado." + +#: modules/pseudoclients/nickserv.cpp:254 +#, c-format +msgid "Your nickname is now being changed to %s" +msgstr "Seu nick está sendo mudado para %s." + +#: modules/commands/os_login.cpp:32 modules/commands/os_login.cpp:79 +msgid "Your oper block doesn't require logging in." +msgstr "" + +#: modules/commands/ns_register.cpp:336 +#, c-format +msgid "Your passcode has been re-sent to %s." +msgstr "Seu passcode foi re-enviado para %s." + +#: modules/commands/ns_register.cpp:232 +#, c-format +msgid "Your password is %s - remember this for later use." +msgstr "Sua senha é %s - guarde ela para uso posterior." + +#: include/language.h:76 +#, c-format +msgid "Your password is too long. It must not exceed %u characters." +msgstr "" + +#: modules/commands/ns_resetpass.cpp:96 +msgid "Your password reset request has expired." +msgstr "Your password reset request has expired." + +#: modules/commands/hs_request.cpp:170 +#, fuzzy +msgid "Your vHost has been requested." +msgstr "Bot %s foi removido." + +#: modules/pseudoclients/hostserv.cpp:64 +#: modules/pseudoclients/hostserv.cpp:103 modules/commands/hs_on.cpp:37 +#, c-format +msgid "Your vhost of %s is now activated." +msgstr "Seu vhost %s está agora ativado." + +#: modules/pseudoclients/hostserv.cpp:62 +#: modules/pseudoclients/hostserv.cpp:101 modules/commands/hs_on.cpp:35 +#, c-format +msgid "Your vhost of %s@%s is now activated." +msgstr "Seu vhost %s@%s está agora ativado." + +#: modules/commands/hs_off.cpp:39 +msgid "Your vhost was removed and the normal cloaking restored." +msgstr "Your vhost was removed and the normal cloaking restored." + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Zone" +msgstr "Nenhuma" + +#: modules/commands/os_dns.cpp:290 +#, fuzzy, c-format +msgid "Zone %s already exists." +msgstr "Bot %s já existe." + +#: modules/commands/os_dns.cpp:310 modules/commands/os_dns.cpp:352 +#: modules/commands/os_dns.cpp:402 modules/commands/os_dns.cpp:438 +#, fuzzy, c-format +msgid "Zone %s does not exist." +msgstr "Bot %s já existe." + +#: modules/commands/os_dns.cpp:332 +#, fuzzy, c-format +msgid "Zone %s removed." +msgstr "vhost para %s removido." + +#: modules/commands/os_defcon.cpp:177 +#, fuzzy +msgid "[1|2|3|4|5]" +msgstr "DEFCON [1|2|3|4|5]" + +#: modules/commands/os_news.cpp:400 +#, c-format +msgid "[Logon News - %s] %s" +msgstr "[Logon News - %s] %s" + +#: modules/commands/os_news.cpp:402 +#, c-format +msgid "[Oper News - %s] %s" +msgstr "[Oper News - %s] %s" + +#: modules/commands/os_news.cpp:404 +#, c-format +msgid "[Random News - %s] %s" +msgstr "[Random News - %s] %s" + +#: modules/commands/ns_identify.cpp:66 +#, fuzzy +msgid "[account] password" +msgstr "IDENTIFY senha" + +#: modules/commands/cs_updown.cpp:49 modules/commands/cs_updown.cpp:147 +#, fuzzy +msgid "[channel [nick]]" +msgstr "OP #channel [nick]" + +#: modules/commands/ms_ignore.cpp:20 +#, fuzzy +msgid "[channel] ADD entry" +msgstr "AOP canal {ADD|DEL|LIST|CLEAR} [nick | entrada]" + +#: modules/commands/ms_ignore.cpp:21 +#, fuzzy +msgid "[channel] DEL entry" +msgstr "MODE canal modos" + +#: modules/commands/ms_ignore.cpp:22 +#, fuzzy +msgid "[channel] LIST" +msgstr "DROP canal" + +#: modules/commands/ms_list.cpp:20 +#, fuzzy +msgid "[channel] [list | NEW]" +msgstr "LIST [canal] [list | NEW]" + +#: modules/extra/stats/cs_fantasy_stats.cpp:40 +#, fuzzy +msgid "[channel] [nick]" +msgstr "OP #channel [nick]" + +#: modules/commands/ms_del.cpp:45 +#, fuzzy +msgid "[channel] {num | list | LAST | ALL}" +msgstr "DEL [canal] {núm | list | ALL}" + +#: modules/commands/ms_read.cpp:113 +#, fuzzy +msgid "[channel] {num | list | LAST | NEW | ALL}" +msgstr "DEL [canal] {núm | list | ALL}" + +#: modules/commands/hs_list.cpp:20 +msgid "[key|#X-Y]" +msgstr "" + +#: modules/commands/ms_info.cpp:20 +#, fuzzy +msgid "[nick | channel]" +msgstr "CANCEL {nick | canal}" + +#: modules/commands/ns_group.cpp:237 +#, fuzzy +msgid "[nick]" +msgstr "INFO nick" + +#: modules/commands/ns_logout.cpp:22 +msgid "[nickname [REVALIDATE]]" +msgstr "" + +#: modules/commands/ns_alist.cpp:25 modules/commands/ns_status.cpp:20 +#: modules/commands/ns_info.cpp:20 +#, fuzzy +msgid "[nickname]" +msgstr "CHECK nick" + +#: modules/commands/ns_set_misc.cpp:96 +msgid "[parameter]" +msgstr "" + +#: modules/commands/os_logsearch.cpp:33 +msgid "[+daysd] [+limitl] pattern" +msgstr "" + +#: modules/commands/os_chankill.cpp:22 +#, fuzzy +msgid "[+expiry] channel reason" +msgstr "CHANKILL [+tempo] {#canal} [motivo]" + +#: modules/commands/ns_list.cpp:110 +msgid "[Hostname hidden]" +msgstr "" + +#: modules/commands/ns_list.cpp:112 modules/commands/cs_list.cpp:115 +msgid "[Suspended]" +msgstr "" + +#: modules/commands/ns_list.cpp:114 +msgid "[Unconfirmed]" +msgstr "" + +#: modules/commands/hs_request.cpp:213 +#, fuzzy +msgid "[auto memo] Your requested vHost has been approved." +msgstr "[Auto-Memo] O memo que você enviou para %s foi lido." + +#: modules/commands/hs_request.cpp:267 +#, fuzzy +msgid "[auto memo] Your requested vHost has been rejected." +msgstr "[Auto-Memo] O memo que você enviou para %s foi lido." + +#: modules/commands/hs_request.cpp:265 +#, c-format +msgid "[auto memo] Your requested vHost has been rejected. Reason: %s" +msgstr "" + +#: modules/commands/hs_request.cpp:388 +#, fuzzy, c-format +msgid "[auto memo] vHost %s has been requested by %s." +msgstr "Último memo enviado para %s foi cancelado." + +#: modules/commands/os_list.cpp:133 +msgid "[{pattern | channel} [INVISIBLE]]" +msgstr "" + +#: modules/commands/os_list.cpp:20 +msgid "[{pattern | nick} [SECRET]]" +msgstr "" + +#: src/misc.cpp:337 +msgid "day" +msgstr "" + +#: src/misc.cpp:337 +msgid "days" +msgstr "" + +#: include/language.h:88 +#, fuzzy +msgid "does not expire" +msgstr " %s (does not expire)" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d day" +msgstr "expira em %d dia" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d days" +msgstr "expira em %d dias" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minute" +msgstr "expira em %d hora, %d minuto" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minutes" +msgstr "expira em %d hora, %d minutos" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minute" +msgstr "expira em %d horas, %d minuto" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minutes" +msgstr "expira em %d horas, %d minutos" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minute" +msgstr "expira em %d minuto" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minutes" +msgstr "expira em %d minutos" + +#: src/misc.cpp:375 +#, fuzzy +msgid "expires momentarily" +msgstr "expira em %d dia" + +#: src/misc.cpp:343 +msgid "hour" +msgstr "" + +#: src/misc.cpp:343 +msgid "hours" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:150 +#, c-format +msgid "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:349 +msgid "minute" +msgstr "" + +#: src/misc.cpp:349 +msgid "minutes" +msgstr "" + +#: modules/commands/bs_info.cpp:87 +msgid "not assigned yet" +msgstr "" + +#: src/misc.cpp:324 +msgid "second" +msgstr "" + +#: src/misc.cpp:324 +#, fuzzy +msgid "seconds" +msgstr "Comandos do %s:" + +#: modules/commands/hs_request.cpp:215 +#, fuzzy, c-format +msgid "vHost for %s has been activated." +msgstr "Seu vhost %s está agora ativado." + +#: modules/commands/hs_request.cpp:272 +#, fuzzy, c-format +msgid "vHost for %s has been rejected." +msgstr "Bot %s foi removido." + +#: modules/commands/hs_request.cpp:79 +msgid "vhost" +msgstr "" + +#: modules/commands/hs_del.cpp:83 +#, c-format +msgid "vhosts for group %s have been removed." +msgstr "vhosts do grupo %s foi removido." + +#: src/misc.cpp:331 +msgid "year" +msgstr "" + +#: src/misc.cpp:331 +msgid "years" +msgstr "" + +#: modules/commands/os_config.cpp:20 +msgid "{MODIFY|VIEW} [block name item name item value]" +msgstr "" + +#: modules/commands/bs_info.cpp:41 +#, fuzzy +msgid "{channel | nickname}" +msgstr "UNBAN canal [nick]" + +#: modules/commands/ms_cancel.cpp:20 +#, fuzzy +msgid "{nick | channel}" +msgstr "CANCEL {nick | canal}" + +#: modules/commands/ms_rsend.cpp:25 modules/commands/ms_send.cpp:25 +#, fuzzy +msgid "{nick | channel} memo-text" +msgstr "SEND {nick | canal} texto" diff --git a/language/anope.ru_RU.po b/language/anope.ru_RU.po new file mode 100644 index 0000000..bf6db2d --- /dev/null +++ b/language/anope.ru_RU.po @@ -0,0 +1,12087 @@ +# Anope IRC Services language file +# Copyright (C) 2011 +# This file is distributed under the same license as the Anope IRC Services package. +# Adam , 2011. +# +msgid "" +msgstr "" +"Project-Id-Version: Anope\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2020-01-06 18:19+0100\n" +"PO-Revision-Date: 2010-09-19 21:10-0400\n" +"Last-Translator: Adam \n" +"Language-Team: Russian\n" +"Language: ru_RU\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && n" +"%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2);\n" + +#: modules/commands/os_forbid.cpp:324 +#, c-format +msgid "%d channel(s) cleared, and %d channel(s) dropped." +msgstr "" + +#: modules/commands/os_forbid.cpp:265 +#, fuzzy, c-format +msgid "%d nickname(s) dropped." +msgstr "Ваш ник успешно удален из базы данных сервисов." + +#: modules/commands/cs_xop.cpp:219 +#, fuzzy, c-format +msgid "%s added to %s %s list." +msgstr "Запись вида %s успешно добавлена в список AKILL'ов." + +#: modules/commands/cs_access.cpp:225 +#, c-format +msgid "%s added to %s access list at level %d." +msgstr "%s добавлен в список доступа канала %s с уровнем доступа %d." + +#: modules/commands/cs_access.cpp:223 +#, fuzzy, c-format +msgid "%s added to %s access list at privilege %s (level %d)" +msgstr "%s добавлен в список доступа канала %s с уровнем доступа %d." + +#: modules/commands/cs_akick.cpp:190 +#, c-format +msgid "%s added to %s autokick list." +msgstr "Запись вида %s успешно добавлена в список автокиков канала %s." + +#: modules/commands/bs_badwords.cpp:307 +#, c-format +msgid "%s added to %s bad words list." +msgstr "Запись вида %s успешно добавлена в список плохих слов канала %s." + +#: modules/commands/ns_access.cpp:45 +#, fuzzy, c-format +msgid "%s added to %s's access list." +msgstr "Маска вида %s успешно добавлена в ваш список доступа." + +#: modules/commands/ns_cert.cpp:204 +#, fuzzy, c-format +msgid "%s added to %s's certificate list." +msgstr "Маска вида %s успешно добавлена в ваш список доступа." + +#: modules/commands/ms_ignore.cpp:62 +#, fuzzy, c-format +msgid "%s added to ignore list." +msgstr "Маска вида %s успешно добавлена в ваш список доступа." + +#: modules/commands/os_sxline.cpp:415 modules/commands/os_sxline.cpp:649 +#, fuzzy, c-format +msgid "%s added to the %s list." +msgstr "Запись вида %s успешно добавлена в список AKILL'ов." + +#: modules/commands/os_akill.cpp:203 +#, c-format +msgid "%s added to the AKILL list." +msgstr "Запись вида %s успешно добавлена в список AKILL'ов." + +#: modules/pseudoclients/botserv.cpp:134 +#, c-format +msgid "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands " +"that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" +msgstr "" + +#: modules/pseudoclients/botserv.cpp:148 +#, fuzzy, c-format +msgid "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s позволяет Вам установить бота на свой канал.\n" +"Даный сервис сделан для тех пользователей, которые\n" +"не могут иначе установить или настроить бота, или же,\n" +"использование ботов запрещено в IRC сети. Доступные\n" +"команды перечислены ниже, чтобы использовать их, напишите\n" +"/msg %s команда. Для получения более подробной\n" +"информации по конкретной команде, напишите\n" +"/msg %s HELP команда." + +#: modules/pseudoclients/nickserv.cpp:466 +#, fuzzy, c-format +msgid "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s - это сервис, предназначенный для \"регистрации\" вашего\n" +"ника и защиты его от использования еще кем-либо кроме вас. Ниже\n" +"представлен список команд, позволяющих осуществлять регистрацию и\n" +"настройку ников. Чтобы использовать команду, пошлите запрос вида\n" +"/msg %s команда.\n" +"Для более подробной информации по какой-либо команде используйте:\n" +"/msg %s HELP команда." + +#: modules/pseudoclients/nickserv.cpp:473 +#, fuzzy, c-format +msgid "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s - это сервис, предназначенный для \"регистрации\" вашего\n" +"ника и защиты его от использования еще кем-либо кроме вас. Ниже\n" +"представлен список команд, позволяющих осуществлять регистрацию и\n" +"настройку ников. Чтобы использовать команду, пошлите запрос вида\n" +"/msg %s команда.\n" +"Для более подробной информации по какой-либо команде используйте:\n" +"/msg %s HELP команда." + +#: modules/pseudoclients/chanserv.cpp:255 +#, fuzzy, c-format +msgid "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" +msgstr "" +"%s позволяет вам регистрировать канал и управлять его различными\n" +"настройками. Также, %s поможет вам обезопасить ваш канал от\n" +"злонамеренных пользователей, желающих его \"захватить\", используя\n" +"ограничение возможности получения статуса опа на канале и другие\n" +"настройки безопасности. Список доступных команд представлен ниже,\n" +"чтобы использовать их, пошлите запрос вида\n" +"/msg %s команда\n" +"Для более подробной информации о конкретной команде, воспользуйтесь:\n" +"/msg %s HELP команда\n" +" " + +#: modules/commands/bs_badwords.cpp:298 +#, c-format +msgid "%s already exists in %s bad words list." +msgstr "Запись вида %s уже содержится в списке плохих слов канала %s." + +#: modules/commands/cs_akick.cpp:170 +#, c-format +msgid "%s already exists on %s autokick list." +msgstr "Запись вида %s уже присутствует в списке автокиков канала %s." + +#: modules/commands/os_session.cpp:361 +#, c-format +msgid "%s already exists on the EXCEPTION list." +msgstr "Запись вида %s уже присутствует в списке исключений из лимита сессий." + +#: modules/commands/bs_kick.cpp:214 modules/commands/bs_kick.cpp:389 +#: modules/commands/bs_kick.cpp:520 modules/commands/bs_kick.cpp:651 +#, c-format +msgid "%s cannot be taken as times to ban." +msgstr "Значение вида %s не может быть использовано как кол-во киков до бана." + +#: modules/commands/os_mode.cpp:163 +#, fuzzy, c-format +msgid "%s changed your usermodes to %s." +msgstr "%s принудительно изменил ваши пользовательские режимы." + +#: modules/commands/os_list.cpp:47 +#, fuzzy, c-format +msgid "%s channel list:" +msgstr "Конец списка каналов." + +#: modules/commands/cs_xop.cpp:343 +#, fuzzy, c-format +msgid "%s deleted from %s %s list." +msgstr "%s успешно удален из AOP'ов канала %s." + +#: modules/commands/cs_access.cpp:326 +#, c-format +msgid "%s deleted from %s access list." +msgstr "Ник %s успешно удален из списка доступа канала %s." + +#: modules/commands/cs_akick.cpp:276 +#, c-format +msgid "%s deleted from %s autokick list." +msgstr "Запись вида %s удалена из списка автокиков канала %s." + +#: modules/commands/bs_badwords.cpp:348 +#, c-format +msgid "%s deleted from %s bad words list." +msgstr "Запись вида %s успешно удалена из списка плохих слов канала %s." + +#: modules/commands/ns_access.cpp:72 +#, fuzzy, c-format +msgid "%s deleted from %s's access list." +msgstr "Ник %s успешно удален из списка доступа канала %s." + +#: modules/commands/ns_cert.cpp:233 +#, fuzzy, c-format +msgid "%s deleted from %s's certificate list." +msgstr "Маска вида %s успешно удалена из вашего списка доступа." + +#: modules/commands/os_session.cpp:414 +#, c-format +msgid "%s deleted from session-limit exception list." +msgstr "Запись вида %s успешно удалена из списка исключений лимита сессий." + +#: modules/commands/os_sxline.cpp:99 +#, fuzzy, c-format +msgid "%s deleted from the %s list." +msgstr "%s успешно удален из AOP'ов канала %s." + +#: modules/commands/os_akill.cpp:246 +#, c-format +msgid "%s deleted from the AKILL list." +msgstr "Запись вида %s успешно удалена из списка AKILL'ов." + +#: modules/commands/cs_access.cpp:685 +#, c-format +msgid "%s disabled on channel %s." +msgstr "Уровень доступа к %s на канале %s отключен." + +#: modules/commands/cs_invite.cpp:75 +#, c-format +msgid "%s has been invited to %s." +msgstr "%s has been invited to %s." + +#: modules/commands/os_svs.cpp:104 +#, fuzzy, c-format +msgid "%s has been joined to %s." +msgstr "%s has been invited to %s." + +#: modules/commands/os_svs.cpp:152 +#, fuzzy, c-format +msgid "%s has been parted from %s." +msgstr "%s has been unbanned from %s." + +#: modules/commands/cs_unban.cpp:96 +#, c-format +msgid "%s has been unbanned from %s." +msgstr "%s has been unbanned from %s." + +#: modules/commands/ns_alist.cpp:110 +#, fuzzy, c-format +msgid "%s has no access in any channels." +msgstr "Уровень доступа к %s на канале %s отключен." + +#: modules/commands/cs_status.cpp:55 +#, fuzzy, c-format +msgid "%s has no access on %s." +msgstr "%s has been invited to %s." + +#: modules/commands/cs_set.cpp:307 +#, c-format +msgid "%s has too many channels registered." +msgstr "%s имеет слишком много зарегистрированных каналов." + +#: modules/commands/cs_status.cpp:51 +#, fuzzy, c-format +msgid "%s is a super administrator." +msgstr "%s is a services operator of type %s." + +#: modules/pseudoclients/memoserv.cpp:214 +#, fuzzy, c-format +msgid "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" +msgstr "" +"Основное предназначение %s - это дать зарегистрированным\n" +"пользователям возможность посылать друг-другу короткие \"записки\",\n" +"называемые так же мемо-сообщениями. Данный сервис особенно удобен,\n" +"когда вам необходимо что-то сообщить интересующему вас человеку, а\n" +"он на данный момент вне сети (offline).\n" +"В качестве отправителя вы можете указать как ник, так и имя канала*.\n" +"Помните, что отправка сообщения возможна лишь зарегистрированному\n" +"на сервисах адресату!\n" +"\n" +"Список команд %s:" + +#: modules/commands/cs_invite.cpp:66 +#, fuzzy, c-format +msgid "%s is already in %s!" +msgstr "You are already in %s! " + +#: modules/commands/os_svs.cpp:99 +#, fuzzy, c-format +msgid "%s is already in %s." +msgstr "You are already in %s! " + +#: modules/commands/ms_ignore.cpp:65 +#, fuzzy, c-format +msgid "%s is already on the ignore list." +msgstr "Маска вида %s успешно добавлена в ваш список доступа." + +#: modules/commands/cs_suspend.cpp:97 modules/commands/ns_suspend.cpp:106 +#, fuzzy, c-format +msgid "%s is already suspended." +msgstr "You are already in %s! " + +#: modules/commands/ms_rsend.cpp:56 modules/commands/ms_send.cpp:55 +#, fuzzy, c-format +msgid "%s is not a registered unforbidden nick or channel." +msgstr "" +"Указанный параметр %s не является ником бота или зарегистрированным каналом." + +#: modules/commands/cs_set.cpp:178 +#, c-format +msgid "%s is not a valid ban type." +msgstr "Число %s не является валидным номером шаблона банмаски." + +#: modules/commands/bs_info.cpp:101 +#, c-format +msgid "%s is not a valid bot or registered channel." +msgstr "" +"Указанный параметр %s не является ником бота или зарегистрированным каналом." + +#: include/language.h:86 +#, fuzzy, c-format +msgid "%s is not a valid e-mail address." +msgstr "Число %s не является валидным номером шаблона банмаски." + +#: include/language.h:80 +#, fuzzy, c-format +msgid "%s is not currently on channel %s." +msgstr "Уровень доступа к %s на канале %s отключен." + +#: modules/commands/os_svs.cpp:144 +#, fuzzy, c-format +msgid "%s is not in %s." +msgstr "You are already in %s! " + +#: modules/commands/ms_ignore.cpp:77 +#, fuzzy, c-format +msgid "%s is not on the ignore list." +msgstr "Ник %s в списке игнорируемых не обнаружен." + +#: modules/commands/cs_status.cpp:90 +#, fuzzy, c-format +msgid "%s is on the auto kick list of %s (%s)." +msgstr "Запись вида %s успешно добавлена в список автокиков канала %s." + +#: modules/commands/cs_status.cpp:53 +#, fuzzy, c-format +msgid "%s is the founder of %s." +msgstr "Уровень доступа к %s на канале %s отключен." + +#: modules/commands/cs_status.cpp:78 +#, c-format +msgid "%s matches access entry %s (from entry %s), which has privilege %s." +msgstr "" + +#: modules/commands/cs_status.cpp:71 +#, c-format +msgid "%s matches access entry %s, which has privilege %s." +msgstr "" + +#: include/language.h:109 +#, c-format +msgid "" +"%s matches an except on %s and cannot be banned until the except has been " +"removed." +msgstr "" + +#: modules/commands/cs_status.cpp:96 +#, fuzzy, c-format +msgid "%s matches auto kick entry %s on %s (%s)." +msgstr "Запись вида %s успешно добавлена в список автокиков канала %s." + +#: modules/commands/cs_xop.cpp:353 +#, fuzzy, c-format +msgid "%s not found on %s %s list." +msgstr "Ник %s в списке AOP'ов канала %s не обнаружен." + +#: modules/commands/cs_access.cpp:338 modules/commands/cs_flags.cpp:255 +#, c-format +msgid "%s not found on %s access list." +msgstr "Ник %s в списке доступа канала %s не обнаружен." + +#: modules/commands/cs_akick.cpp:265 +#, c-format +msgid "%s not found on %s autokick list." +msgstr "Запись вида %s в списке автокиков канала %s не обнаружена." + +#: modules/commands/bs_badwords.cpp:341 +#, c-format +msgid "%s not found on %s bad words list." +msgstr "Запись вида %s в списке плохих слов канала %s не обнаружена." + +#: modules/commands/ns_access.cpp:66 +#, fuzzy, c-format +msgid "%s not found on %s's access list." +msgstr "Ник %s в списке доступа канала %s не обнаружен." + +#: modules/commands/ns_cert.cpp:226 +#, fuzzy, c-format +msgid "%s not found on %s's certificate list." +msgstr "Маска вида %s не найдена в вашем списке доступа." + +#: modules/commands/os_ignore.cpp:320 +#, fuzzy, c-format +msgid "%s not found on ignore list." +msgstr "Ник %s в списке игнорируемых не обнаружен." + +#: modules/commands/os_session.cpp:238 +#, c-format +msgid "" +"%s not found on session list, but has a limit of %d because it matches entry:" +" %s." +msgstr "" + +#: modules/commands/os_session.cpp:418 +#, c-format +msgid "%s not found on session-limit exception list." +msgstr "Запись вида %s в списке исключений из лимита сессий не обнаружена." + +#: modules/commands/os_sxline.cpp:92 +#, fuzzy, c-format +msgid "%s not found on the %s list." +msgstr "Ник %s в списке AOP'ов канала %s не обнаружен." + +#: modules/commands/os_akill.cpp:237 +#, c-format +msgid "%s not found on the AKILL list." +msgstr "Запись вида %s в списке AKILL'ов не обнаружена." + +#: modules/commands/cs_flags.cpp:251 +#, fuzzy, c-format +msgid "%s removed from the %s access list." +msgstr "Ник %s успешно удален из списка доступа канала %s." + +#: modules/commands/ms_ignore.cpp:74 +#, fuzzy, c-format +msgid "%s removed from the ignore list." +msgstr "Маска вида %s успешно удалена из вашего списка доступа." + +#: modules/commands/os_list.cpp:157 +#, fuzzy, c-format +msgid "%s users list:" +msgstr "Конец списка пользователей." + +#: modules/commands/os_ignore.cpp:316 +#, c-format +msgid "%s will no longer be ignored." +msgstr "Ник %s успешно удален из списка игнорирования." + +#: modules/commands/os_ignore.cpp:238 +#, c-format +msgid "%s will now be ignored for %s." +msgstr "Ник %s добавлен в список игнорирования, продолжительность игнора: %s." + +#: modules/commands/os_ignore.cpp:233 +#, c-format +msgid "%s will now permanently be ignored." +msgstr "" +"Ник %s добавлен в список игнорирования, продолжительность игнора: постоянно." + +#: include/language.h:66 +#, fuzzy, c-format +msgid "%s%s HELP %s for more information." +msgstr "" +"Для более подробной информации о какой-либо конкретной опции, см.\n" +"справку по /msg %s HELP опция" + +#: modules/commands/bs_bot.cpp:270 +msgid "ADD nick user host real" +msgstr "" + +#: modules/commands/bs_bot.cpp:271 +#, fuzzy +msgid "CHANGE oldnick newnick [user [host [real]]]" +msgstr "" +"BOT ADD ник идент хост реальное_имя\n" +"BOT CHANGE старый_ник новый_ник [идент [хост [реальное_имя]]]\n" +"BOT DEL ник" + +#: modules/commands/bs_bot.cpp:272 +#, fuzzy +msgid "DEL nick" +msgstr "DEL <ник>." + +#: modules/commands/os_session.cpp:560 +#, fuzzy +msgid "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." +msgstr "" +"Синтаксис: EXCEPTION ADD [+срок_истечения] маска лимит причина\n" +" EXCEPTION DEL {маска | список_записей}\n" +" EXCEPTION MOVE номер позиция\n" +" EXCEPTION LIST [маска | список_записей]\n" +" EXCEPTION VIEW [маска | список_записей]\n" +"\n" +"Позволяет Администраторам сервисов управлять списком хостов, которые\n" +"будут иметь отдельно указанные ограничения на количество сессий.\n" +"Возможности списка исключений позволяют разрешить определенным хостам\n" +"(шеллов или BNC) иметь большее количество клиентов одновременно,\n" +"нежели разрешено по-умолчанию. Как только количество сессий с хоста \n" +"достигнет установленного лимита, все последующие клиенты, пытающиеся\n" +"подключиться с данного хоста, будут автоматически отключаться.\n" +"Перед отключением, пользователь получит уведомление от %s\n" +"о том, что с его хоста превышен лимит подключений. Тект сообщения\n" +"можно изменить в конфигурационном файле сервисов.\n" +"\n" +"Команда EXCEPTION ADD позволяет добавить указанную маску в список\n" +"исключений. Учтите, что общие хостмастки вида ник!идент@хост или\n" +"идент@хост недопустимы! Вы должны указывать только реальные хосты\n" +"вида box.host.dom и *.host.dom, так как ограничение сессий не\n" +"использует при проверке ники и/или иденты. Значение лимита должно\n" +"быть целым числом, больше или равным нулю. Данный параметр определяет,\n" +"как много сессий данный хост может использовать одновременно.\n" +"Установка этого значения равным 0 позволит хосту иметь неограниченное\n" +"число сессий. Для более подробной информации о сроке истечения см.\n" +"справку по команде AKILL.\n" +"\n" +"Команда EXCEPTION DEL позволяет удалить указанную маску (или\n" +"диапазон записей) из списка исключений.\n" +"\n" +"Команда EXCEPTION MOVE позволяет переместить указанное исключение\n" +"под указанным номером на указанную позицию. Соответственно, n-ое\n" +"количество записей списка исключений будет сдвинуто выше или ниже,\n" +"чтобы заполнить образовавшийся промежуток.\n" +"\n" +"Команды EXCEPTION LIST и EXCEPTION VIEW позволяют получить текущий\n" +"список исключений. Если в качестве параметра указана маска, будут\n" +"отображены только совпадающие с ней записи.\n" +"\n" +"Команда EXCEPTION VIEW позволяет получить более подробную информацию\n" +"об исключении: ник добавившего запись, установленный лимит, указанную\n" +"при установке причину, сам хост, срок истечения записи и дату ее\n" +"создания.\n" +"\n" +"Стоит заметить, что сервисы будут использовать значения первой же\n" +"совпадающей записи из списка исключений для попадающего под условия\n" +"хоста. Слишком большой список исключений с широкими масками в\n" +"достаточной мере влияет на производительность сервисов." + +#: modules/commands/os_noop.cpp:68 +msgid "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." +msgstr "" + +#: modules/commands/cs_access.cpp:611 +#, c-format +msgid "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." +msgstr "" + +#: modules/commands/ms_read.cpp:35 +#, c-format +msgid "[auto-memo] The memo you sent to %s has been viewed." +msgstr "" +"[авто-сообщение] Мемо-сообщение, которые вы посылали %s, было прочитано." + +#: modules/commands/ns_group.cpp:92 +#, fuzzy +msgid "[target] [password]" +msgstr "GROUP главный_ник пароль" + +#: modules/commands/ns_set.cpp:453 +msgid "address" +msgstr "" + +#: modules/commands/bs_set.cpp:162 +#, fuzzy +msgid "botname {ON|OFF}" +msgstr "SASET ник AUTOOP {ON | OFF}" + +#: modules/extra/stats/cs_fantasy_top.cpp:39 +#: modules/extra/stats/cs_fantasy_top.cpp:51 +#: modules/commands/cs_suspend.cpp:152 modules/commands/cs_sync.cpp:20 +#: modules/commands/cs_log.cpp:106 modules/commands/bs_assign.cpp:91 +#: modules/commands/cs_info.cpp:20 modules/commands/cs_getkey.cpp:20 +#, fuzzy +msgid "channel" +msgstr "DROP #канал" + +#: modules/commands/cs_set.cpp:138 +#, fuzzy +msgid "channel bantype" +msgstr "ACT #канал текст" + +#: modules/commands/cs_drop.cpp:20 +#, fuzzy +msgid "channel channel" +msgstr "TOPIC #канал [текст_топика]" + +#: modules/commands/cs_log.cpp:107 +#, fuzzy +msgid "channel command method [status]" +msgstr "KICK #канал опция {ON|OFF} [параметры]" + +#: modules/commands/cs_kick.cpp:21 +#, fuzzy +msgid "channel mask [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_mode.cpp:20 +#, fuzzy +msgid "channel modes" +msgstr "MODE #канал режимы" + +#: modules/commands/cs_set.cpp:267 modules/commands/bs_assign.cpp:20 +#, fuzzy +msgid "channel nick" +msgstr "UNBAN #канал [nick]" + +#: modules/commands/cs_kick.cpp:20 +#, fuzzy +msgid "channel nick [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_clone.cpp:115 +#, fuzzy +msgid "channel target [what]" +msgstr "CLEAR #канал что_именно" + +#: modules/commands/bs_control.cpp:20 modules/commands/bs_control.cpp:80 +#, fuzzy +msgid "channel text" +msgstr "ACT #канал текст" + +#: modules/commands/bs_set.cpp:91 +#, fuzzy +msgid "channel time" +msgstr "ACT #канал текст" + +#: modules/commands/os_kick.cpp:20 +#, fuzzy +msgid "channel user reason" +msgstr "KICK #канал ник причина" + +#: modules/commands/cs_enforce.cpp:228 +#, fuzzy +msgid "channel what" +msgstr "TOPIC #канал [текст_топика]" + +#: modules/commands/cs_xop.cpp:481 +#, fuzzy +msgid "channel ADD mask" +msgstr "MODE #канал режимы" + +#: modules/commands/cs_access.cpp:499 +msgid "channel ADD mask level" +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:194 +#, fuzzy +msgid "channel ADD message" +msgstr "MODE #канал режимы" + +#: modules/commands/bs_badwords.cpp:371 +msgid "channel ADD word [SINGLE | START | END]" +msgstr "" + +#: modules/commands/cs_akick.cpp:435 +#, fuzzy +msgid "channel ADD {nick | mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_topic.cpp:151 +#, fuzzy +msgid "channel APPEND topic" +msgstr "TOPIC #канал [текст_топика]" + +#: modules/commands/cs_access.cpp:503 modules/commands/cs_flags.cpp:376 +#: modules/commands/cs_xop.cpp:484 modules/commands/cs_entrymsg.cpp:197 +#: modules/commands/bs_badwords.cpp:374 modules/commands/cs_akick.cpp:440 +#, fuzzy +msgid "channel CLEAR" +msgstr "DROP #канал" + +#: modules/commands/cs_mode.cpp:736 +#, fuzzy +msgid "channel CLEAR [what]" +msgstr "TOPIC #канал [текст_топика]" + +#: modules/commands/os_mode.cpp:21 +#, fuzzy +msgid "channel CLEAR [ALL]" +msgstr "DROP #канал" + +#: modules/commands/cs_entrymsg.cpp:195 +#, fuzzy +msgid "channel DEL num" +msgstr "MODE #канал режимы" + +#: modules/commands/cs_access.cpp:500 modules/commands/cs_xop.cpp:482 +#, fuzzy +msgid "channel DEL {mask | entry-num | list}" +msgstr "DEL [#канал] {номер_сообщения | список_записей | ALL}" + +#: modules/commands/cs_akick.cpp:436 +#, fuzzy +msgid "channel DEL {nick | mask | entry-num | list}" +msgstr "AOP #канал {ADD|DEL|LIST|CLEAR} [ник | номер запис]" + +#: modules/commands/bs_badwords.cpp:372 +#, fuzzy +msgid "channel DEL {word | entry-num | list}" +msgstr "DEL [#канал] {номер_сообщения | список_записей | ALL}" + +#: modules/commands/cs_akick.cpp:439 +msgid "channel ENFORCE" +msgstr "" + +#: modules/commands/cs_access.cpp:744 modules/commands/cs_entrymsg.cpp:196 +#, fuzzy +msgid "channel LIST" +msgstr "DROP #канал" + +#: modules/commands/cs_akick.cpp:437 +#, fuzzy +msgid "channel LIST [mask | entry-num | list]" +msgstr "AOP #канал {ADD|DEL|LIST|CLEAR} [ник | номер запис]" + +#: modules/commands/cs_access.cpp:501 modules/commands/cs_xop.cpp:483 +#: modules/commands/bs_badwords.cpp:373 +#, fuzzy +msgid "channel LIST [mask | list]" +msgstr "AOP #канал {ADD|DEL|LIST|CLEAR} [ник | номер запис]" + +#: modules/commands/cs_flags.cpp:375 +msgid "channel LIST [mask | +flags]" +msgstr "" + +#: modules/commands/cs_mode.cpp:734 +#, fuzzy +msgid "channel LOCK {ADD|DEL|SET|LIST} [what]" +msgstr "AOP #канал {ADD|DEL|LIST|CLEAR} [ник | номер запис]" + +#: modules/commands/cs_access.cpp:745 +#, fuzzy +msgid "channel RESET" +msgstr "SET #канал GREET {ON|OFF}" + +#: modules/commands/cs_mode.cpp:735 +#, fuzzy +msgid "channel SET modes" +msgstr "MODE #канал режимы" + +#: modules/commands/cs_access.cpp:742 +msgid "channel SET type level" +msgstr "" + +#: modules/commands/cs_akick.cpp:438 +#, fuzzy +msgid "channel VIEW [mask | entry-num | list]" +msgstr "AOP #канал {ADD|DEL|LIST|CLEAR} [ник | номер запис]" + +#: modules/commands/cs_access.cpp:502 +#, fuzzy +msgid "channel VIEW [mask | list]" +msgstr "DEL [#канал] {номер_сообщения | список_записей | ALL}" + +#: modules/commands/cs_register.cpp:20 modules/commands/cs_set.cpp:205 +#, fuzzy +msgid "channel [description]" +msgstr "REGISTER #канал описание" + +#: modules/commands/cs_set.cpp:950 modules/commands/cs_invite.cpp:20 +#: modules/commands/cs_unban.cpp:20 +#, fuzzy +msgid "channel [nick]" +msgstr "UNBAN #канал [nick]" + +#: modules/commands/cs_set_misc.cpp:96 +#, fuzzy +msgid "channel [parameters]" +msgstr "CLEAR #канал что_именно" + +#: modules/commands/cs_mode.cpp:807 modules/commands/cs_status.cpp:20 +#, fuzzy +msgid "channel [user]" +msgstr "UNBAN #канал [nick]" + +#: modules/commands/cs_suspend.cpp:59 +#, fuzzy +msgid "channel [+expiry] [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_ban.cpp:40 +#, fuzzy +msgid "channel [+expiry] {nick | mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_flags.cpp:374 +#, fuzzy +msgid "channel [MODIFY] mask changes" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_topic.cpp:150 +#, fuzzy +msgid "channel [SET] [topic]" +msgstr "TOPIC #канал [текст_топика]" + +#: modules/commands/cs_topic.cpp:152 +#, fuzzy +msgid "channel [UNLOCK|LOCK]" +msgstr "DROP #канал" + +#: modules/fantasy.cpp:20 modules/commands/greet.cpp:20 +#: modules/commands/bs_assign.cpp:154 +#, fuzzy +msgid "channel {ON|OFF}" +msgstr "SET #канал XOP {ON | OFF}" + +#: modules/commands/bs_kick.cpp:491 +#, fuzzy +msgid "channel {ON|OFF} [ttb [ln [secs]]]" +msgstr "KICK #канал опция {ON|OFF} [параметры]" + +#: modules/commands/bs_kick.cpp:361 +#, fuzzy +msgid "channel {ON|OFF} [ttb [min [percent]]]" +msgstr "KICK #канал опция {ON|OFF} [параметры]" + +#: modules/commands/bs_kick.cpp:623 +#, fuzzy +msgid "channel {ON|OFF} [ttb [num]]" +msgstr "KICK #канал опция {ON|OFF} [параметры]" + +#: modules/commands/bs_kick.cpp:252 modules/commands/bs_kick.cpp:288 +#: modules/commands/bs_kick.cpp:327 modules/commands/bs_kick.cpp:457 +#: modules/commands/bs_kick.cpp:589 modules/commands/bs_kick.cpp:724 +#: modules/commands/bs_kick.cpp:758 +#, fuzzy +msgid "channel {ON|OFF} [ttb]" +msgstr "SET #канал XOP {ON | OFF}" + +#: modules/commands/cs_access.cpp:743 +msgid "channel {DIS | DISABLE} type" +msgstr "" + +#: modules/commands/cs_set.cpp:873 +#, fuzzy +msgid "channel {ON | LEVEL | OFF}" +msgstr "SET #канал SIGNKICK {ON | LEVEL | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:18 modules/commands/cs_set.cpp:75 +#: modules/commands/cs_set.cpp:336 modules/commands/cs_set.cpp:401 +#: modules/commands/cs_set.cpp:473 modules/commands/cs_set.cpp:622 +#: modules/commands/cs_set.cpp:684 modules/commands/cs_set.cpp:747 +#: modules/commands/cs_set.cpp:811 modules/commands/cs_set.cpp:1044 +#: modules/commands/bs_kick.cpp:792 modules/commands/bs_kick.cpp:857 +#: modules/commands/cs_topic.cpp:21 modules/commands/cs_list.cpp:181 +#, fuzzy +msgid "channel {ON | OFF}" +msgstr "SET #канал XOP {ON | OFF}" + +#: modules/commands/ns_getemail.cpp:24 +msgid "email" +msgstr "" + +#: modules/commands/ns_set.cpp:794 +#, fuzzy +msgid "language" +msgstr "SET LANGUAGE номер" + +#: modules/commands/ms_sendall.cpp:25 modules/commands/ms_staff.cpp:25 +#, fuzzy +msgid "memo-text" +msgstr "STAFF memo-text" + +#: modules/commands/gl_global.cpp:22 modules/commands/greet.cpp:84 +#, fuzzy +msgid "message" +msgstr "GLOBAL сообщение" + +#: modules/commands/os_modinfo.cpp:20 modules/commands/os_module.cpp:20 +#: modules/commands/os_module.cpp:57 modules/commands/os_module.cpp:129 +msgid "modname" +msgstr "" + +#: modules/commands/ns_set.cpp:330 +msgid "new-display" +msgstr "" + +#: modules/commands/ns_set.cpp:120 +#, fuzzy +msgid "new-password" +msgstr "GROUP главный_ник пароль" + +#: modules/extra/stats/cs_fantasy_stats.cpp:52 modules/commands/hs_del.cpp:20 +#: modules/commands/hs_del.cpp:60 modules/commands/ms_check.cpp:20 +#: modules/commands/hs_request.cpp:192 modules/commands/cs_seen.cpp:262 +#, fuzzy +msgid "nick" +msgstr "INFO ник" + +#: modules/commands/os_svs.cpp:79 +#, fuzzy +msgid "nick channel" +msgstr "CANCEL {ник | #канал}" + +#: modules/commands/os_svs.cpp:123 +#, fuzzy +msgid "nick channel [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_oline.cpp:20 +#, fuzzy +msgid "nick flags" +msgstr "OLINE ник +флаги" + +#: modules/commands/hs_set.cpp:20 modules/commands/hs_set.cpp:126 +#, fuzzy +msgid "nick hostmask" +msgstr "SET <ник> <хостмаска>." + +#: modules/commands/os_svs.cpp:20 +#, fuzzy +msgid "nick newnick" +msgstr "SVSNICK ник новый_ник " + +#: modules/commands/hs_request.cpp:241 +#, fuzzy +msgid "nick [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/ns_getpass.cpp:20 modules/commands/ns_drop.cpp:19 +#: modules/commands/ns_suspend.cpp:161 +#, fuzzy +msgid "nickname" +msgstr "CHECK ник" + +#: modules/commands/ns_set.cpp:546 +#, fuzzy +msgid "nickname address" +msgstr "FORBID ник причина" + +#: modules/commands/ns_resetpass.cpp:22 +#, fuzzy +msgid "nickname email" +msgstr "FORBID ник причина" + +#: modules/commands/ns_set.cpp:872 +#, fuzzy +msgid "nickname language" +msgstr "FORBID ник причина" + +#: modules/commands/greet.cpp:145 +#, fuzzy +msgid "nickname message" +msgstr "FORBID ник причина" + +#: modules/commands/ns_set.cpp:399 +#, fuzzy +msgid "nickname new-display" +msgstr "FORBID ник причина" + +#: modules/commands/ns_set.cpp:173 +#, fuzzy +msgid "nickname new-password" +msgstr "GHOST ник [пароль]" + +#: modules/commands/ns_set_misc.cpp:170 +#, fuzzy +msgid "nickname [parameter]" +msgstr "GHOST ник [пароль]" + +#: modules/commands/ns_recover.cpp:150 +#, fuzzy +msgid "nickname [password]" +msgstr "GHOST ник [пароль]" + +#: modules/commands/ns_suspend.cpp:61 +#, fuzzy +msgid "nickname [+expiry] [reason]" +msgstr "FORBID ник причина" + +#: modules/commands/ns_info.cpp:239 +#, fuzzy +msgid "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +msgstr "SET HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:130 modules/commands/ns_set.cpp:302 +#: modules/commands/ns_set.cpp:631 modules/commands/ns_set.cpp:985 +#: modules/commands/ns_set.cpp:1076 modules/commands/ns_set.cpp:1105 +#: modules/commands/ns_list.cpp:252 +#, fuzzy +msgid "nickname {ON | OFF}" +msgstr "SASET ник AUTOOP {ON | OFF}" + +#: modules/commands/ns_set.cpp:760 +#, fuzzy +msgid "nickname {ON | QUICK | IMMED | OFF}" +msgstr "SASET ник KILL {ON | QUICK | IMMED | OFF}" + +#: modules/commands/bs_set.cpp:20 +#, fuzzy +msgid "option (channel | bot) settings" +msgstr "SET (#канал | бот) опция параметр" + +#: modules/commands/cs_set.cpp:21 +#, fuzzy +msgid "option channel parameters" +msgstr "SEND {ник | #канал} текст_сообщения" + +#: modules/commands/bs_kick.cpp:120 +#, fuzzy +msgid "option channel {ON|OFF} [settings]" +msgstr "KICK #канал опция {ON|OFF} [параметры]" + +#: modules/commands/ns_set.cpp:75 +msgid "option nickname parameters" +msgstr "" + +#: modules/commands/ms_set.cpp:207 modules/commands/ns_set.cpp:20 +#, fuzzy +msgid "option parameters" +msgstr "SET опция параметры" + +#: modules/commands/os_set.cpp:170 +#, fuzzy +msgid "option setting" +msgstr "SET опция параметры" + +#: modules/commands/ns_register.cpp:22 +#, fuzzy +msgid "passcode" +msgstr "REGISTER пароль email" + +#: modules/commands/os_login.cpp:19 +#, fuzzy +msgid "password" +msgstr "GROUP главный_ник пароль" + +#: modules/commands/ns_register.cpp:124 +#, fuzzy +msgid "password [email]" +msgstr "REGISTER пароль email" + +#: modules/commands/ns_register.cpp:122 +#, fuzzy +msgid "password email" +msgstr "REGISTER пароль email" + +#: modules/commands/cs_list.cpp:21 +#, fuzzy +msgid "pattern [SUSPENDED] [NOEXPIRE]" +msgstr "LIST маска [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/ns_list.cpp:20 +#, fuzzy +msgid "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" +msgstr "LIST маска [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/os_jupe.cpp:20 +#, fuzzy +msgid "server [reason]" +msgstr "JUPE имя_сервера [причина]" + +#: modules/commands/os_mode.cpp:147 +#, fuzzy +msgid "user modes" +msgstr "MODE #канал режимы" + +#: modules/commands/os_kill.cpp:20 +#, fuzzy +msgid "user [reason]" +msgstr "JUPE имя_сервера [причина]" + +#: modules/commands/os_sxline.cpp:440 +#, fuzzy +msgid "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." +msgstr "" +"Синтаксис: AKILL ADD [+срок_истечения] маска причина\n" +" AKILL DEL {маска | номер_записи | список_записей}\n" +" AKILL LIST [маска | список_записей]\n" +" AKILL VIEW [маска | список_записей]\n" +" AKILL CLEAR\n" +"\n" +"Позволяет Операторам сервисов управлять списком сервисных AKILL'ов.\n" +"Любой пользователь, подпадающий под маску AKILL'а, будет немедленно\n" +"отключен от сети посредством сервисного KILL'а с указанной причиной,\n" +"и не важно, на каком сервере он сидит или к какому подключается.\n" +"Помимо этого, если IRCd вашей сети это поддерживает, сервисы \n" +"установят KLINE/GLINE на всех серверах вашей сети, в качестве маски\n" +"бана будет использована соответствующая запись AKILL'а.\n" +"\n" +"Команда AKILL ADD добавляет маску вида идент@хост/ip с указанной\n" +"причиной в список AKILL'ов (наличие причины - обязательно).\n" +"Значение срока истечения - это целое число, которое может быть\n" +"одним из: d (дней), h (часов), или m (минут). Такие сочетания\n" +"как 1h30m - недопустимы. Если единица измерения не указана, то\n" +"по-умолчанию, она будет принята за \"d\" - \"дни\" (таким образом,\n" +"+30 будет означать 30 дней). Чтобы добавить постоянный AKILL,\n" +"используйте время истечения равным +0. Помните, что если в качестве\n" +"первого символа второго параметра указан знак \"+\" - вы должны\n" +"обозначить сроки истечения записи, даже если это будет значение\n" +"по-умочанию.\n" +"Текущее время истечения AKILL'а по-умолчанию, можно узнать с помощью\n" +"команды STATS AKILL.\n" +"\n" +"Команда AKILL DEL удаляет указанную маску из списка AKILL'ов.\n" +"В качестве параметра вы можете указать не только маску AKILL'а, но\n" +"и конкретный номер записи или список записей (см. примеры\n" +"использования команды LIST ниже).\n" +"\n" +"Команда AKILL LIST показывает текущий список AKILL'ов.\n" +"В качестве дополнительного параметра, вы можете указать символьную\n" +"маску, что позволит вам получить список с конкретными записями,\n" +"попадающими под эту маску, или же, вы можете указать список записей.\n" +"Например:\n" +"\n" +" AKILL LIST 2-5,7-9\n" +" отобразит все записи с 2-ой по 5-ю и с 7-ой по 9-ю.\n" +"\n" +"AKILL VIEW более подробная версия AKILL LIST, она покажет вам\n" +"кто добавил AKILL, время установки AKILL'а, когда он истекает, ну\n" +"и, конечно же, маску вида идент@хост/ip и причину AKILL'а.\n" +"\n" +"AKILL CLEAR позволяет полностью очистить список AKILL'ов." + +#: modules/commands/os_sxline.cpp:678 +#, fuzzy +msgid "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Синтаксис: AKILL ADD [+срок_истечения] маска причина\n" +" AKILL DEL {маска | номер_записи | список_записей}\n" +" AKILL LIST [маска | список_записей]\n" +" AKILL VIEW [маска | список_записей]\n" +" AKILL CLEAR\n" +"\n" +"Позволяет Операторам сервисов управлять списком сервисных AKILL'ов.\n" +"Любой пользователь, подпадающий под маску AKILL'а, будет немедленно\n" +"отключен от сети посредством сервисного KILL'а с указанной причиной,\n" +"и не важно, на каком сервере он сидит или к какому подключается.\n" +"Помимо этого, если IRCd вашей сети это поддерживает, сервисы \n" +"установят KLINE/GLINE на всех серверах вашей сети, в качестве маски\n" +"бана будет использована соответствующая запись AKILL'а.\n" +"\n" +"Команда AKILL ADD добавляет маску вида идент@хост/ip с указанной\n" +"причиной в список AKILL'ов (наличие причины - обязательно).\n" +"Значение срока истечения - это целое число, которое может быть\n" +"одним из: d (дней), h (часов), или m (минут). Такие сочетания\n" +"как 1h30m - недопустимы. Если единица измерения не указана, то\n" +"по-умолчанию, она будет принята за \"d\" - \"дни\" (таким образом,\n" +"+30 будет означать 30 дней). Чтобы добавить постоянный AKILL,\n" +"используйте время истечения равным +0. Помните, что если в качестве\n" +"первого символа второго параметра указан знак \"+\" - вы должны\n" +"обозначить сроки истечения записи, даже если это будет значение\n" +"по-умочанию.\n" +"Текущее время истечения AKILL'а по-умолчанию, можно узнать с помощью\n" +"команды STATS AKILL.\n" +"\n" +"Команда AKILL DEL удаляет указанную маску из списка AKILL'ов.\n" +"В качестве параметра вы можете указать не только маску AKILL'а, но\n" +"и конкретный номер записи или список записей (см. примеры\n" +"использования команды LIST ниже).\n" +"\n" +"Команда AKILL LIST показывает текущий список AKILL'ов.\n" +"В качестве дополнительного параметра, вы можете указать символьную\n" +"маску, что позволит вам получить список с конкретными записями,\n" +"попадающими под эту маску, или же, вы можете указать список записей.\n" +"Например:\n" +"\n" +" AKILL LIST 2-5,7-9\n" +" отобразит все записи с 2-ой по 5-ю и с 7-ой по 9-ю.\n" +"\n" +"AKILL VIEW более подробная версия AKILL LIST, она покажет вам\n" +"кто добавил AKILL, время установки AKILL'а, когда он истекает, ну\n" +"и, конечно же, маску вида идент@хост/ip и причину AKILL'а.\n" +"\n" +"AKILL CLEAR позволяет полностью очистить список AKILL'ов." + +#: modules/pseudoclients/nickserv.cpp:492 +#, fuzzy, c-format +msgid "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." +msgstr "" +"Помните, что неиспользуемые в течение длительного периода ники\n" +"автоматически удаляются из базы данных. Срок существования неактивных\n" +"ников: %d дней." + +#: modules/pseudoclients/botserv.cpp:143 +#, fuzzy +msgid "" +" \n" +"Available commands are:" +msgstr "Справочная информация по %s отсутствует." + +#: modules/pseudoclients/botserv.cpp:167 +#, c-format +msgid "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." +msgstr "" + +#: modules/fantasy.cpp:69 +#, fuzzy, c-format +msgid "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." +msgstr "" +"Синтаксис: SET #канал FANTASY {ON|OFF}\n" +"\n" +"Активирует/деактивирует FANTASY-режим бота для указанного канала.\n" +"Он позволяет посетителям канала использовать удобные аналоги аналоги\n" +"стандартных команд прямо на канале, например:\n" +"\n" +"!protect, !deprotect - установка статуса защиты (администратора)\n" +" на себя (без парамеров) или указанному нику.\n" +" !halfop, !dehalfop - запрос статуса полуоператора канала, в\n" +" качестве параметра вы можете указать ник\n" +" посетителя канала.\n" +" !owner, !deowner - запрос статуса владельца канала (команда\n" +" доступна лишь владельцу канала).\n" +" !voice, !devoice - запрос статуса войса канала, в качестве\n" +" параметра вы можете указать ник посетителя\n" +" канала.\n" +" !op, !deop - запрос статуса оператора канала, в качестве\n" +" параметра вы можете указать ник посетителя\n" +" канала.\n" +" !kick, !kb - кикнуть или кикнуть и забанить указанного\n" +" посетителя канала с указанной причиной\n" +" (например: !kick Vasya пшел вон отсюда!).\n" +" !seen - запрос информации о том, когда указанный\n" +" ник последний раз был в сети.\n" +"\n" +"Примечание: для использования команд FANTASY-режима, вы должны\n" +"иметь соответствующий уровень доступа на канале (он определяется\n" +"значением настройки FANTASIA, по-умолчанию это 3 или VOP).\n" +"Помимо этого, ваш уровень доступа должен соответсвовать требованиям\n" +"команды, например, вы не сможете использовать команду !op, если\n" +"ваш уровень доступа не соответствует значению для OP/DEOP (или вы\n" +"не AOP/SOP канала).\n" +"\n" +"Примечание 2: такие команды, как: !halfop, !dehalfop, !protect,\n" +"!deprotect, !owner и !deowner - могут быть недоступны в вашей\n" +"сети." + +#: modules/commands/greet.cpp:69 +#, fuzzy +msgid "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." +msgstr "" +"Синтаксис: SET #канал GREET {ON|OFF}\n" +"\n" +"Включает или выключает режим показа приветствий на канале. Если\n" +"опция включена, бот будет показывать приветственные сообщения для\n" +"всех тех пользователей, которые имеют достаточный уровень доступа\n" +"на канале и установили себе текст приветствия (см. настройки ника)." + +#: modules/commands/bs_kick.cpp:843 +#, fuzzy +msgid "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +"Синтаксис: SET #канал DONTKICKOPS {ON|OFF}\n" +"\n" +"Позволяет включить или выключить режим исключения операторов канала\n" +"из условий киков за нарушения. Данное действие распространится на\n" +"всех операторов канала, не важно, соответствует их уровень доступа\n" +"значению установки NOKICK или нет." + +#: modules/commands/bs_kick.cpp:908 +#, fuzzy +msgid "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +"Синтаксис: SET #канал DONTKICKVOICES {ON|OFF}\n" +"\n" +"Позволяет включить или выключить режим исключения войсов канала\n" +"из условий киков за нарушения. Данное действие распространится на\n" +"всех войсов канала, не важно, соответствует их уровень доступа\n" +"значению установки NOKICK или нет." + +#: modules/pseudoclients/botserv.cpp:141 +#, c-format +msgid "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" +msgstr "" + +#: modules/commands/cs_register.cpp:105 +msgid "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." +msgstr "" + +#: modules/pseudoclients/chanserv.cpp:272 +#, fuzzy, c-format +msgid "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." +msgstr "" +"Помните, что любой канал, не использующийся в течение %d дней\n" +"(т.е. ни один пользователь, прописанный в списке доступа канала,\n" +"не посетит канал в течении данного времени), будет автоматически\n" +"удален из базы данных сервисов." + +#: modules/commands/cs_register.cpp:101 +#, c-format +msgid "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +msgstr "" + +#: modules/pseudoclients/nickserv.cpp:486 +#, fuzzy +msgid "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." +msgstr "" +" \n" +"Администраторы сервисов могут удалить любой ник без идентификации\n" +"к нему, а так же, могут смотреть список доступа любого ника\n" +"(более подробно см. /msg %s ACCESS LIST ник)." + +#: modules/pseudoclients/chanserv.cpp:277 +#, fuzzy +msgid "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." +msgstr "" +" \n" +"Администраторы сервисов могут удалить любой канал без идентификации\n" +"к нему в качестве владельца, могут просматривать списки доступа\n" +"каналов, а так же, списки акиков и установки уровней доступа каналов." + +#: modules/commands/bs_set.cpp:147 +msgid "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." +msgstr "" + +#: modules/commands/cs_xop.cpp:542 +#, fuzzy, c-format +msgid "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." +msgstr "" +"Синтаксис: HOP #канал ADD ник\n" +" HOP #канал DEL {ник | номер_записи | список_записей}\n" +" HOP #канал LIST [маска | список_записей]\n" +" HOP #канал CLEAR\n" +"\n" +"Позволяет управлять списком HOP'ов (полуоператоров) вашего канала.\n" +"Привилегии HOP'а дают пользователю возможность получить статус хопа\n" +"сразу при входе на канал, или запросить его вручную, через сервисы.\n" +"\n" +"Команда HOP ADD добавляет указанный ник в список HOP'ов.\n" +"\n" +"Команда HOP DEL удаляет указанный ник из списка HOP'ов. В качестве\n" +"параметра вы можете указать не только ник, но и конкретный номер\n" +"записи или список записей (см. примеры использования LIST ниже).\n" +"\n" +"Команда HOP LIST выводит текущий список HOP'ов канала. В качестве\n" +"дополнительного параметра, вы можете указать символьную маску, что\n" +"позволит вам получить список с конкретными никами, попадающими под\n" +"эту маску, или же, вы можете указать список записей.\n" +"\n" +"Например:\n" +"\n" +" HOP #канал LIST 2-5,7-9\n" +" отобразит все записи со 2-ой по 5-ую, и с 7-ой по 9-ю.\n" +" HOP #канал LIST *vas*\n" +" отобразит все записи, которые содержат подстроку \"vas\"\n" +"\n" +"Команда HOP CLEAR позволяет полностью очистить список HOP'ов.\n" +"\n" +"Команды HOP ADD, HOP DEL и HOP LIST могут использовать AOP'ы\n" +"канала или выше, команду HOP CLEAR может использовать только\n" +"владелец канала.\n" +"\n" +"Помните, что данная команда работает только в случае использования\n" +"системы привилегий xOP. Если вы используете систему LEVELS, все\n" +"изменения списка доступа канала должны производится посредством\n" +"команды ACCESS. Для более подробной информации по использованию\n" +"команды ACCESS и системы привилегий xOP см. справочную информацию\n" +"по /msg %s HELP ACCESS и /msg %s HELP SET XOP." + +#: modules/commands/cs_akick.cpp:508 +#, c-format +msgid "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." +msgstr "" + +#: modules/commands/os_akill.cpp:448 +#, fuzzy +msgid "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." +msgstr "" +"Синтаксис: HOP #канал ADD ник\n" +" HOP #канал DEL {ник | номер_записи | список_записей}\n" +" HOP #канал LIST [маска | список_записей]\n" +" HOP #канал CLEAR\n" +"\n" +"Позволяет управлять списком HOP'ов (полуоператоров) вашего канала.\n" +"Привилегии HOP'а дают пользователю возможность получить статус хопа\n" +"сразу при входе на канал, или запросить его вручную, через сервисы.\n" +"\n" +"Команда HOP ADD добавляет указанный ник в список HOP'ов.\n" +"\n" +"Команда HOP DEL удаляет указанный ник из списка HOP'ов. В качестве\n" +"параметра вы можете указать не только ник, но и конкретный номер\n" +"записи или список записей (см. примеры использования LIST ниже).\n" +"\n" +"Команда HOP LIST выводит текущий список HOP'ов канала. В качестве\n" +"дополнительного параметра, вы можете указать символьную маску, что\n" +"позволит вам получить список с конкретными никами, попадающими под\n" +"эту маску, или же, вы можете указать список записей.\n" +"\n" +"Например:\n" +"\n" +" HOP #канал LIST 2-5,7-9\n" +" отобразит все записи со 2-ой по 5-ую, и с 7-ой по 9-ю.\n" +" HOP #канал LIST *vas*\n" +" отобразит все записи, которые содержат подстроку \"vas\"\n" +"\n" +"Команда HOP CLEAR позволяет полностью очистить список HOP'ов.\n" +"\n" +"Команды HOP ADD, HOP DEL и HOP LIST могут использовать AOP'ы\n" +"канала или выше, команду HOP CLEAR может использовать только\n" +"владелец канала.\n" +"\n" +"Помните, что данная команда работает только в случае использования\n" +"системы привилегий xOP. Если вы используете систему LEVELS, все\n" +"изменения списка доступа канала должны производится посредством\n" +"команды ACCESS. Для более подробной информации по использованию\n" +"команды ACCESS и системы привилегий xOP см. справочную информацию\n" +"по /msg %s HELP ACCESS и /msg %s HELP SET XOP." + +#: modules/commands/os_sxline.cpp:462 +#, fuzzy +msgid "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." +msgstr "" +"Синтаксис: HOP #канал ADD ник\n" +" HOP #канал DEL {ник | номер_записи | список_записей}\n" +" HOP #канал LIST [маска | список_записей]\n" +" HOP #канал CLEAR\n" +"\n" +"Позволяет управлять списком HOP'ов (полуоператоров) вашего канала.\n" +"Привилегии HOP'а дают пользователю возможность получить статус хопа\n" +"сразу при входе на канал, или запросить его вручную, через сервисы.\n" +"\n" +"Команда HOP ADD добавляет указанный ник в список HOP'ов.\n" +"\n" +"Команда HOP DEL удаляет указанный ник из списка HOP'ов. В качестве\n" +"параметра вы можете указать не только ник, но и конкретный номер\n" +"записи или список записей (см. примеры использования LIST ниже).\n" +"\n" +"Команда HOP LIST выводит текущий список HOP'ов канала. В качестве\n" +"дополнительного параметра, вы можете указать символьную маску, что\n" +"позволит вам получить список с конкретными никами, попадающими под\n" +"эту маску, или же, вы можете указать список записей.\n" +"\n" +"Например:\n" +"\n" +" HOP #канал LIST 2-5,7-9\n" +" отобразит все записи со 2-ой по 5-ую, и с 7-ой по 9-ю.\n" +" HOP #канал LIST *vas*\n" +" отобразит все записи, которые содержат подстроку \"vas\"\n" +"\n" +"Команда HOP CLEAR позволяет полностью очистить список HOP'ов.\n" +"\n" +"Команды HOP ADD, HOP DEL и HOP LIST могут использовать AOP'ы\n" +"канала или выше, команду HOP CLEAR может использовать только\n" +"владелец канала.\n" +"\n" +"Помните, что данная команда работает только в случае использования\n" +"системы привилегий xOP. Если вы используете систему LEVELS, все\n" +"изменения списка доступа канала должны производится посредством\n" +"команды ACCESS. Для более подробной информации по использованию\n" +"команды ACCESS и системы привилегий xOP см. справочную информацию\n" +"по /msg %s HELP ACCESS и /msg %s HELP SET XOP." + +#: modules/commands/os_sxline.cpp:697 +#, fuzzy +msgid "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." +msgstr "" +"Синтаксис: HOP #канал ADD ник\n" +" HOP #канал DEL {ник | номер_записи | список_записей}\n" +" HOP #канал LIST [маска | список_записей]\n" +" HOP #канал CLEAR\n" +"\n" +"Позволяет управлять списком HOP'ов (полуоператоров) вашего канала.\n" +"Привилегии HOP'а дают пользователю возможность получить статус хопа\n" +"сразу при входе на канал, или запросить его вручную, через сервисы.\n" +"\n" +"Команда HOP ADD добавляет указанный ник в список HOP'ов.\n" +"\n" +"Команда HOP DEL удаляет указанный ник из списка HOP'ов. В качестве\n" +"параметра вы можете указать не только ник, но и конкретный номер\n" +"записи или список записей (см. примеры использования LIST ниже).\n" +"\n" +"Команда HOP LIST выводит текущий список HOP'ов канала. В качестве\n" +"дополнительного параметра, вы можете указать символьную маску, что\n" +"позволит вам получить список с конкретными никами, попадающими под\n" +"эту маску, или же, вы можете указать список записей.\n" +"\n" +"Например:\n" +"\n" +" HOP #канал LIST 2-5,7-9\n" +" отобразит все записи со 2-ой по 5-ую, и с 7-ой по 9-ю.\n" +" HOP #канал LIST *vas*\n" +" отобразит все записи, которые содержат подстроку \"vas\"\n" +"\n" +"Команда HOP CLEAR позволяет полностью очистить список HOP'ов.\n" +"\n" +"Команды HOP ADD, HOP DEL и HOP LIST могут использовать AOP'ы\n" +"канала или выше, команду HOP CLEAR может использовать только\n" +"владелец канала.\n" +"\n" +"Помните, что данная команда работает только в случае использования\n" +"системы привилегий xOP. Если вы используете систему LEVELS, все\n" +"изменения списка доступа канала должны производится посредством\n" +"команды ACCESS. Для более подробной информации по использованию\n" +"команды ACCESS и системы привилегий xOP см. справочную информацию\n" +"по /msg %s HELP ACCESS и /msg %s HELP SET XOP." + +#: modules/commands/bs_assign.cpp:197 +#, fuzzy +msgid "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." +msgstr "" +"Синтаксис: SET #канал NOBOT {ON|OFF}\n" +"\n" +"Активирует/деактивирует режим NOBOT для указанного канала. Включение\n" +"данного режима запретит администарции канала использовать бота на\n" +"своем канале.\n" +"Если бот уже установлен на канале, он будет автоматически удален с\n" +"него сразу же после включения данной опции." + +#: modules/commands/bs_set.cpp:199 +#, fuzzy +msgid "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." +msgstr "" +"Синтаксис: SET ник_бота PRIVATE {ON|OFF}\n" +"\n" +"Установите данную опцию на указанного бота, если хотите запретить\n" +"обычным пользователям использовать его. Доступ к нему будет только\n" +"у администрации сети." + +#: modules/pseudoclients/memoserv.cpp:227 +#, c-format +msgid "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." +msgstr "" + +#: modules/commands/os_oper.cpp:167 +#, c-format +msgid " %s is online using this oper block." +msgstr "" + +#: modules/commands/os_modinfo.cpp:55 +#, c-format +msgid " Command %s on %s is linked to %s" +msgstr "" + +#: modules/commands/os_modinfo.cpp:43 +#, fuzzy, c-format +msgid " Providing service: %s" +msgstr "Предоставляемая команда: /msg %s %s" + +#: modules/commands/os_oper.cpp:163 +msgid " This oper is configured in the configuration file." +msgstr "" + +#: modules/commands/os_modinfo.cpp:34 +#, c-format +msgid " Loaded at: %p" +msgstr "" + +#: modules/commands/cs_seen.cpp:303 +#, c-format +msgid " but %s mysteriously dematerialized." +msgstr "" + +#: src/messages.cpp:339 +#, c-format +msgid "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." +msgstr "" +"Адресация вида \"/msg %s\" больше не поддерживается. Используйте \"/msg %s@%s" +"\" или \"/%s\"." + +#: modules/commands/os_jupe.cpp:19 +#, fuzzy +msgid "\"Jupiter\" a server" +msgstr " JUPE \"Джуп\" указанного сервера сети" + +#: modules/commands/os_oper.cpp:161 +#, fuzzy, c-format +msgid "%-8s %s" +msgstr "%-20s %s@%s" + +#: modules/extra/stats/cs_fantasy_top.cpp:152 +#, c-format +msgid "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:359 +msgid "%b %d %H:%M:%S %Y %Z" +msgstr "" + +#: modules/commands/cs_log.cpp:205 +#, c-format +msgid "%c is an unknown status mode." +msgstr "" + +#: modules/commands/cs_mode.cpp:431 +#, fuzzy, c-format +msgid "%c%c is not locked on %s." +msgstr "%s не уведомляется о новых собщениях." + +#: modules/commands/cs_mode.cpp:427 +#, fuzzy, c-format +msgid "%c%c%s has been unlocked from %s." +msgstr "Nick %s has been ungrouped from %s." + +#: modules/commands/cs_clone.cpp:56 +#, fuzzy, c-format +msgid "%d access entries from %s have been cloned to %s." +msgstr "Все виртуальные хосты для ников группы %s установлены на %s" + +#: modules/commands/bs_botlist.cpp:56 +#, c-format +msgid "%d bots available." +msgstr "Количество доступных ботов: %d" + +#: modules/commands/os_modinfo.cpp:189 +#, fuzzy, c-format +msgid "%d modules loaded." +msgstr "Количество загруженных модулей: %d" + +#: modules/commands/ns_group.cpp:357 +#, fuzzy, c-format +msgid "%d nickname(s) in the group." +msgstr "Количество ников в группе: %d" + +#: modules/commands/cs_seen.cpp:137 +#, c-format +msgid "%lu nicks are stored in the database, using %.2Lf kB of memory." +msgstr "" + +#: modules/commands/cs_xop.cpp:241 modules/commands/cs_xop.cpp:372 +#: modules/commands/cs_xop.cpp:450 +#, fuzzy, c-format +msgid "%s %s list is empty." +msgstr "Список AOP'ов канала %s пуст." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1181 +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1201 +#: modules/commands/bs_kick.cpp:1211 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban)" +msgstr "Цензор жирных букв...: %s (%d киков до бана)" + +#: modules/commands/bs_kick.cpp:1161 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; %d lines in %ds)" +msgstr "Цензор флуда.........: %s (%d киков до бана; %d линий из %ds)" + +#: modules/commands/bs_kick.cpp:1171 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; %d times)" +msgstr "Цензор повторов......: %s (%d киков до бана; %d раз)" + +#: modules/commands/bs_kick.cpp:1141 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; minimum %d/%d%%)" +msgstr "Цензор CapsLOCK......: %s (%d киков до бана; минимум %d/%d%%)" + +#: modules/commands/bs_kick.cpp:1163 +#, fuzzy, c-format +msgid "%s (%d lines in %ds)" +msgstr " %s (истекает %s)" + +#: modules/commands/bs_kick.cpp:1173 +#, c-format +msgid "%s (%d times)" +msgstr "" + +#: modules/commands/cs_seen.cpp:358 +#, c-format +msgid "%s (%s) was kicked from %s (\"%s\") %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:355 +#, c-format +msgid "%s (%s) was kicked from a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:326 +#, c-format +msgid "%s (%s) was last seen changing nick from %s to %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:321 +#, c-format +msgid "%s (%s) was last seen changing nick to %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:310 +#, c-format +msgid "%s (%s) was last seen connecting %s ago (%s)%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:335 +#, c-format +msgid "%s (%s) was last seen joining %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:332 +#, c-format +msgid "%s (%s) was last seen joining a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:344 +#, c-format +msgid "%s (%s) was last seen parting %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:341 +#, c-format +msgid "%s (%s) was last seen parting a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:349 +#, c-format +msgid "%s (%s) was last seen quitting (%s) %s ago (%s)." +msgstr "" + +#: modules/commands/bs_kick.cpp:1143 +#, fuzzy, c-format +msgid "%s (minimum %d/%d%%)" +msgstr "Цензор CapsLOCK......: %s (минимум %d/%d%%)" + +#: modules/commands/cs_access.cpp:245 modules/commands/cs_access.cpp:349 +#: modules/commands/cs_access.cpp:454 modules/commands/cs_access.cpp:467 +#: modules/commands/cs_flags.cpp:295 +#, c-format +msgid "%s access list is empty." +msgstr "Список доступа канала %s пуст." + +#: modules/commands/ns_ajoin.cpp:184 +#, fuzzy, c-format +msgid "%s added to %s's auto join list." +msgstr "Запись вида %s успешно добавлена в список автокиков канала %s." + +#: src/xline.cpp:389 +#, fuzzy, c-format +msgid "%s already exists." +msgstr "Бот с ником %s уже существует." + +#: modules/commands/cs_akick.cpp:202 modules/commands/cs_akick.cpp:387 +#: modules/commands/cs_akick.cpp:400 +#, c-format +msgid "%s autokick list is empty." +msgstr "Список автокиков канала %s пуст." + +#: modules/commands/bs_badwords.cpp:198 modules/commands/bs_badwords.cpp:316 +#, c-format +msgid "%s bad words list is empty." +msgstr "Список плохих слов канала %s пуст." + +#: modules/commands/cs_set.cpp:993 +#, fuzzy, c-format +msgid "%s cannot be the successor on channel %s as they are the founder." +msgstr "%s не может быть наследником канала %s так как он его владелец." + +#: modules/pseudoclients/global.cpp:90 modules/pseudoclients/hostserv.cpp:78 +#: modules/pseudoclients/operserv.cpp:287 +#, c-format +msgid "%s commands:" +msgstr "Список команд %s:" + +#: include/language.h:69 +#, c-format +msgid "%s coverage is too wide; Please use a more specific mask." +msgstr "" + +#: modules/commands/ms_info.cpp:94 +#, c-format +msgid "%s currently has %d memos, of which %d are unread." +msgstr "%s сейчас имеет %d сообщений, %d из них все еще не прочитаны." + +#: modules/commands/ms_info.cpp:92 +#, c-format +msgid "%s currently has %d memos, of which 1 is unread." +msgstr "%s сейчас имеет %d сообщений, 1 из них все еще не прочитано." + +#: modules/commands/ms_info.cpp:90 +#, c-format +msgid "%s currently has %d memos." +msgstr "%s сейчас имеет %d сообщений." + +#: modules/commands/ms_info.cpp:88 +#, c-format +msgid "%s currently has %d memos; all of them are unread." +msgstr "%s сейчас имеет %d сообщений, ни одно из них не прочитано." + +#: modules/commands/ms_info.cpp:77 +#, c-format +msgid "%s currently has 1 memo, and it has not yet been read." +msgstr "%s сейчас имеет 1 новое, непрочитанное сообщение." + +#: modules/commands/ms_info.cpp:79 +#, c-format +msgid "%s currently has 1 memo." +msgstr "%s сейчас имеет 1 сообщение." + +#: modules/commands/ms_info.cpp:73 +#, c-format +msgid "%s currently has no memos." +msgstr "Список сообщений для %s на данный момент пуст." + +#: modules/commands/os_forbid.cpp:344 +#, fuzzy, c-format +msgid "%s deleted from the %s forbid list." +msgstr "Запись вида %s успешно удалена из списка плохих слов канала %s." + +#: include/language.h:105 +#, fuzzy, c-format +msgid "%s for %s set to %s." +msgstr "Виртуальный хост для %s установлен на %s." + +#: include/language.h:106 +#, fuzzy, c-format +msgid "%s for %s unset." +msgstr "Наследник канал %s удален." + +#: modules/commands/ns_ajoin.cpp:176 +#, c-format +msgid "%s had an invalid key specified, and was thus ignored." +msgstr "" + +#: modules/commands/ms_info.cpp:111 +#, c-format +msgid "%s has no memo limit." +msgstr "Лимит сообщений для %s отключен." + +#: include/language.h:115 +#, fuzzy, c-format +msgid "%s has no memos." +msgstr "Лимит сообщений для %s отключен." + +#: include/language.h:118 +#, fuzzy, c-format +msgid "%s has no new memos." +msgstr "Лимит сообщений для %s отключен." + +#: modules/commands/ns_info.cpp:53 +#, c-format +msgid "%s is %s" +msgstr "%s это %s" + +#: modules/commands/ns_info.cpp:59 +#, fuzzy, c-format +msgid "%s is a Services Operator of type %s." +msgstr "%s is a services operator of type %s." + +#: modules/commands/cs_seen.cpp:281 +#, fuzzy, c-format +msgid "%s is a client on services." +msgstr "%s сейчас в сети." + +#: modules/commands/cs_seen.cpp:200 +#, fuzzy, c-format +msgid "%s is a network service." +msgstr "%s сейчас в сети." + +#: src/xline.cpp:407 +#, fuzzy, c-format +msgid "%s is already covered by %s." +msgstr "" +"Указанная маска вида %s совпадает с одной из масок в списке AKILL'ов: %s." + +#: modules/commands/ns_ajoin.cpp:170 +#, fuzzy, c-format +msgid "%s is already on %s's auto join list." +msgstr "Маска вида %s успешно добавлена в ваш список доступа." + +#: modules/commands/ns_info.cpp:56 +#, fuzzy, c-format +msgid "%s is an unconfirmed nickname." +msgstr "Дополнительно: регистрация этого ника никогда не истечет." + +#: modules/commands/cs_flags.cpp:432 +#, c-format +msgid "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." +msgstr "" + +#: modules/commands/ns_info.cpp:74 +#, c-format +msgid "%s is currently online." +msgstr "%s сейчас в сети." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is disabled" +msgstr "Режим %s: отключен." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is enabled" +msgstr "Режим %s: включен." + +#: modules/commands/os_dns.cpp:507 +#, fuzzy, c-format +msgid "%s is not a valid IP address." +msgstr "Число %s не является валидным номером шаблона банмаски." + +#: modules/commands/cs_log.cpp:167 modules/commands/cs_log.cpp:192 +#, fuzzy, c-format +msgid "%s is not a valid command." +msgstr "Число %s не является валидным номером шаблона банмаски." + +#: modules/commands/cs_log.cpp:198 +#, fuzzy, c-format +msgid "%s is not a valid logging method." +msgstr "Число %s не является валидным номером шаблона банмаски." + +#: modules/commands/ms_info.cpp:124 +#, c-format +msgid "%s is not notified of new memos." +msgstr "%s не уведомляется о новых собщениях." + +#: modules/commands/ms_info.cpp:118 +#, c-format +msgid "%s is notified of new memos at logon and when they arrive." +msgstr "" +"%s уведомляется о новых сообщениях сразу после идентификации или по мере " +"прихода новых собщений." + +#: modules/commands/ms_info.cpp:122 +#, c-format +msgid "%s is notified of new memos at logon." +msgstr "%s уведомляется о новых сообщениях сразу после идентификации к нику." + +#: modules/commands/ms_info.cpp:120 +#, c-format +msgid "%s is notified when new memos arrive." +msgstr "%s уведомляется о новых сообщениях сразу при поступлении оных." + +#: modules/commands/cs_seen.cpp:232 +#, c-format +msgid "%s is on the channel right now (as %s)!" +msgstr "" + +#: modules/commands/cs_seen.cpp:221 +#, fuzzy, c-format +msgid "%s is on the channel right now!" +msgstr "Уровень доступа к %s на канале %s отключен." + +#: modules/commands/cs_xop.cpp:434 +#, fuzzy, c-format +msgid "%s list for %s" +msgstr "Список доступа для %s:" + +#: modules/commands/os_sxline.cpp:69 modules/commands/os_sxline.cpp:113 +#, fuzzy, c-format +msgid "%s list is empty." +msgstr "Список AOP'ов канала %s пуст." + +#: modules/commands/cs_mode.cpp:376 +#, fuzzy, c-format +msgid "%s locked on %s." +msgstr "%s не уведомляется о новых собщениях." + +#: modules/extra/stats/cs_fantasy_stats.cpp:120 +#, fuzzy, c-format +msgid "%s not found." +msgstr "Ник %s в списке AOP'ов канала %s не обнаружен." + +#: modules/commands/os_config.cpp:79 +#, c-format +msgid "%s settings:" +msgstr "" + +#: modules/commands/cs_seen.cpp:255 +#, c-format +msgid "%s was last seen here %s ago." +msgstr "" + +#: modules/commands/ns_ajoin.cpp:213 +#, fuzzy, c-format +msgid "%s was not found on %s's auto join list." +msgstr "Запись вида %s в списке автокиков канала %s не обнаружена." + +#: modules/commands/ns_ajoin.cpp:221 +#, fuzzy, c-format +msgid "%s was removed from %s's auto join list." +msgstr "Запись вида %s удалена из списка автокиков канала %s." + +#: modules/commands/ms_set.cpp:64 +#, c-format +msgid "%s will not send you any notification of memos." +msgstr "С этого момента, %s не будет уведомлять вас о новых сообщениях." + +#: modules/commands/ms_set.cpp:42 +#, c-format +msgid "%s will now notify you of memos when they are sent to you." +msgstr "" +"С этого момента, %s будет уведомлять вас о новых сообщениях сразу по " +"поступлении оных." + +#: modules/commands/ms_set.cpp:30 +#, c-format +msgid "" +"%s will now notify you of memos when you log on and when they are sent to " +"you." +msgstr "" +"С этого момента, %s будет уведомлять вас о новых сообщениях сразу после " +"идентификации к нику или при поступлении новых сообщений." + +#: modules/commands/ms_set.cpp:36 +#, c-format +msgid "%s will now notify you of memos when you log on or unset /AWAY." +msgstr "" +"С этого момента, %s будет уведомлять вас о новых сообщениях сразу после " +"идентификации к нику или по возвращению из режима /AWAY." + +#: modules/commands/bs_bot.cpp:89 +#, c-format +msgid "%s!%s@%s (%s) added to the bot list." +msgstr "%s!%s@%s (%s) добавлен в список ботов." + +#: modules/commands/ns_access.cpp:83 +#, fuzzy, c-format +msgid "%s's access list is empty." +msgstr "Список доступа канала %s пуст." + +#: modules/commands/ns_ajoin.cpp:96 +#, fuzzy, c-format +msgid "%s's auto join list is empty." +msgstr "Список автокиков канала %s пуст." + +#: modules/commands/ns_ajoin.cpp:111 +#, fuzzy, c-format +msgid "%s's auto join list:" +msgstr " AKICK Управление списком автокиков канала" + +#: modules/commands/ns_cert.cpp:242 +#, fuzzy, c-format +msgid "%s's certificate list is empty." +msgstr "Ваш список доступа пуст." + +#: modules/commands/ms_info.cpp:99 modules/commands/ms_info.cpp:106 +#, c-format +msgid "%s's memo limit is %d, and may not be changed." +msgstr "Лимит собщений для %s равен %d и не может быть изменен." + +#: modules/commands/ms_info.cpp:101 modules/commands/ms_info.cpp:108 +#, c-format +msgid "%s's memo limit is %d." +msgstr "Лимит сообщений для %s равен %d." + +#: src/misc.cpp:363 +#, c-format +msgid "(%s ago)" +msgstr "" + +#: src/misc.cpp:365 +#, c-format +msgid "(%s from now)" +msgstr "" + +#: modules/commands/os_dns.cpp:244 +msgid "(Split)" +msgstr "" + +#: modules/commands/os_info.cpp:268 +#, c-format +msgid "(by %s on %s) %s" +msgstr "" + +#: modules/commands/cs_access.cpp:710 +#, fuzzy +msgid "(disabled)" +msgstr "Режим %s: включен." + +#: modules/commands/cs_access.cpp:712 +msgid "(founder only)" +msgstr "" + +#: src/misc.cpp:367 +msgid "(now)" +msgstr "" + +#: modules/commands/os_defcon.cpp:168 +msgid "* AKILL any new clients connecting" +msgstr "* Автоматическая установка AKILL'ов на всех новых клиентов." + +#: modules/commands/os_defcon.cpp:158 +#, fuzzy, c-format +msgid "* Force channel modes (%s) to be set on all channels" +msgstr "* Принудительная установка режимов %s на все каналы сети." + +#: modules/commands/os_defcon.cpp:164 +#, fuzzy +msgid "* Ignore non-opers with a message" +msgstr "* Игнорирование простых пользователей с оповещением их об этом." + +#: modules/commands/os_defcon.cpp:162 +#, fuzzy +msgid "* Kill any new clients connecting" +msgstr "* Автоматическое отключение от сети всех новых клиентов." + +#: modules/commands/os_defcon.cpp:156 +#, fuzzy +msgid "* No mode lock changes" +msgstr "* Запрет на изменение параметров MLOCK." + +#: modules/commands/os_defcon.cpp:152 +msgid "* No new channel registrations" +msgstr "* Запрет на регистрацию каналов." + +#: modules/commands/os_defcon.cpp:170 +msgid "* No new memos sent" +msgstr "* Запрет на отправку мемо-сообщений." + +#: modules/commands/os_defcon.cpp:154 +msgid "* No new nick registrations" +msgstr "* Запрет на регистрацию ников." + +#: modules/commands/os_defcon.cpp:166 +msgid "* Silently ignore non-opers" +msgstr "* Игнорирование простых пользователей без уведомления их об этом." + +#: modules/commands/os_defcon.cpp:160 +#, c-format +msgid "* Use the reduced session limit of %d" +msgstr "* Уменьшение лимита сессий с одного хоста до %d." + +#: modules/commands/cs_seen.cpp:319 +#, c-format +msgid ", but %s mysteriously dematerialized." +msgstr "" + +#: modules/commands/cs_seen.cpp:317 +#, fuzzy, c-format +msgid ". %s is still online." +msgstr "%s сейчас в сети." + +#: include/language.h:87 +msgid "" +msgstr "" + +#: modules/commands/ns_set.cpp:504 +#, fuzzy, c-format +msgid "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." +msgstr "" +"Auth-код был выслан на %s, для завершения регистрации используйте команду /" +"msg %s confirm auth-код" + +#: modules/commands/ms_sendall.cpp:45 +msgid "A massmemo has been sent to all registered users." +msgstr "" +"Массовое сообщение успешно отправлено всем зарегистрированным пользователям." + +#: modules/commands/hs_request.cpp:285 +msgid "" +"A memo informing the user will also be sent, which includes the reason for " +"the rejection if supplied." +msgstr "" + +#: modules/commands/hs_request.cpp:229 +msgid "A memo informing the user will also be sent." +msgstr "" + +#: modules/commands/ms_read.cpp:42 +#, c-format +msgid "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." +msgstr "" +"Мемо-извещение было автоматически послано для %s, информирующее отправителя " +"о том, что вы прочитали его/ее сообщение." + +#: include/language.h:123 +msgid "A vHost ident must be in the format of a valid ident." +msgstr "" + +#: include/language.h:122 +msgid "A vHost must be in the format of a valid hostname." +msgstr "" + +#: modules/commands/os_ignore.cpp:342 +#, fuzzy +msgid "ADD expiry {nick|mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_oper.cpp:70 +msgid "ADD oper type" +msgstr "" + +#: modules/commands/os_info.cpp:102 +#, fuzzy +msgid "ADD target info" +msgstr "GROUP главный_ник пароль" + +#: modules/commands/os_news.cpp:278 +msgid "ADD text" +msgstr "" + +#: modules/commands/os_session.cpp:523 +#, fuzzy +msgid "ADD [+expiry] mask limit reason" +msgstr "CHANKILL [+срок_истечения] {#канал} [причина]" + +#: modules/commands/ns_ajoin.cpp:231 +#, fuzzy +msgid "ADD [nickname] channel [key]" +msgstr "CHANKILL [+срок_истечения] {#канал} [причина]" + +#: modules/commands/ns_access.cpp:102 +#, fuzzy +msgid "ADD [nickname] mask" +msgstr "CHANKILL [+срок_истечения] {#канал} [причина]" + +#: modules/commands/ns_cert.cpp:258 +#, fuzzy +msgid "ADD [nickname] [fingerprint]" +msgstr "FORBID ник причина" + +#: modules/commands/os_sxline.cpp:659 modules/commands/os_akill.cpp:386 +#, fuzzy +msgid "ADD [+expiry] mask reason" +msgstr "CHANKILL [+срок_истечения] {#канал} [причина]" + +#: modules/commands/os_sxline.cpp:425 +#, fuzzy +msgid "ADD [+expiry] mask:reason" +msgstr "CHANKILL [+срок_истечения] {#канал} [причина]" + +#: modules/commands/os_forbid.cpp:157 +#, fuzzy +msgid "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" +msgstr "CHANKILL [+срок_истечения] {#канал} [причина]" + +#: modules/commands/os_dns.cpp:665 +msgid "ADDIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:663 +msgid "ADDSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:661 +msgid "ADDZONE zone.name" +msgstr "" + +#: modules/commands/cs_akick.cpp:38 +#, c-format +msgid "AKICK ENFORCE for %s complete; %d users were affected." +msgstr "AKICK ENFORCE на канале %s завершен, пользователей забанено: %d " + +#: modules/commands/os_chankill.cpp:21 +#, fuzzy +msgid "AKILL all users on a specific channel" +msgstr " CHANKILL \"Прибить\" всех пользователей на указанном канале" + +#: modules/commands/os_akill.cpp:222 modules/commands/os_akill.cpp:339 +#: modules/commands/os_akill.cpp:353 +msgid "AKILL list is empty." +msgstr "Список AKILL'ов пуст." + +#: modules/commands/bs_kick.cpp:1211 modules/commands/bs_kick.cpp:1213 +#: modules/commands/bs_kick.cpp:1216 +#, fuzzy +msgid "AMSG kicker" +msgstr "Цензор CapsLOCK......: %s" + +#: modules/commands/ns_alist.cpp:48 +#, fuzzy +msgid "Access" +msgstr "Ваш текущий список доступа:" + +#: include/language.h:72 +#, fuzzy +msgid "Access denied." +msgstr "Ваш текущий список доступа:" + +#: modules/commands/cs_status.cpp:58 +#, fuzzy, c-format +msgid "Access for %s on %s:" +msgstr "Уровень доступа для %s на канале %s изменен на %d." + +#: include/language.h:107 +#, fuzzy, c-format +msgid "Access level must be between %d and %d inclusive." +msgstr "Уровень должен быть числом между %d и %d включительно." + +#: modules/commands/cs_access.cpp:108 +msgid "Access level must be non-zero." +msgstr "Уровень доступа должен быть отличен от нуля." + +#: modules/commands/cs_access.cpp:694 +#, c-format +msgid "Access level settings for channel %s:" +msgstr "Установки списка доступа для канала %s:" + +#: modules/commands/cs_access.cpp:734 +#, c-format +msgid "Access levels for %s reset to defaults." +msgstr "Уровни доступа для канала %s сброшены на значения по-умолчанию." + +#: modules/commands/cs_access.cpp:439 modules/commands/ns_access.cpp:87 +#, fuzzy, c-format +msgid "Access list for %s:" +msgstr "Список доступа для %s:" + +#: modules/commands/help.cpp:166 +#, c-format +msgid "" +"Access to this command requires the permission %s to be present in your " +"opertype." +msgstr "" +"Access to this command requires the permission %s to be present in your " +"opertype." + +#: modules/commands/ns_cert.cpp:368 modules/commands/ns_cert.cpp:392 +#: modules/commands/ns_identify.cpp:94 +#, c-format +msgid "" +"Account %s has already reached the maximum number of simultaneous logins " +"(%u)." +msgstr "" + +#: modules/commands/cs_set.cpp:683 +#, fuzzy +msgid "Activate security features" +msgstr " SECURE дополнительные возможности %s'а по безопасности" + +#: modules/commands/hs_request.cpp:227 +msgid "Activate the requested vHost for the given nick." +msgstr "" + +#: modules/commands/hs_on.cpp:55 +#, fuzzy +msgid "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." +msgstr "" +"Синтаксис: ON\n" +"\n" +"Активирует ваш виртуальный хост, при условии, конечно, что он у вас\n" +"установлен. Сразу после активации, ваш реальный хост/IP-адрес будет\n" +"заменен на виртуальный, и, соответственно, он и будет показан в\n" +"/WHOIS-информации вашего ника." + +#: modules/commands/hs_on.cpp:19 +#, fuzzy +msgid "Activates your assigned vhost" +msgstr " ON Активирует назначенный вам виртуальный хост" + +#: modules/commands/os_info.cpp:243 +msgid "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." +msgstr "" + +#: modules/commands/os_dns.cpp:515 +#, c-format +msgid "Added IP %s to %s." +msgstr "" + +#: modules/commands/os_forbid.cpp:239 +#, c-format +msgid "Added a forbid on %s of type %s to expire on %s." +msgstr "" + +#: modules/commands/os_info.cpp:164 +#, fuzzy, c-format +msgid "Added info to %s." +msgstr "Мемо-сообщение для %s успешно отправлено." + +#: modules/commands/os_news.cpp:34 +#, fuzzy +msgid "Added new logon news item." +msgstr "Новость успешно добавлена, ее номер: #%d" + +#: modules/commands/os_news.cpp:44 +#, fuzzy +msgid "Added new oper news item." +msgstr "Новость успешно добавлена, ее номер: #%d" + +#: modules/commands/os_news.cpp:54 +#, fuzzy +msgid "Added new random news item." +msgstr "Новость успешно добавлена, ее номер: #%d" + +#: modules/commands/os_dns.cpp:395 +#, fuzzy, c-format +msgid "Added server %s." +msgstr "Uplink-сервер: %s" + +#: modules/commands/os_dns.cpp:300 +#, c-format +msgid "Added zone %s." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:257 +msgid "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." +msgstr "" + +#: modules/commands/ns_register.cpp:104 +msgid "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." +msgstr "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." + +#: modules/pseudoclients/botserv.cpp:172 +#, c-format +msgid "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" +msgstr "" + +#: modules/commands/os_noop.cpp:58 +#, c-format +msgid "All O:lines of %s have been reset." +msgstr "Все OLINE-записи на сервере %s восстановлены." + +#: modules/commands/cs_clone.cpp:71 +#, fuzzy, c-format +msgid "All akick entries from %s have been cloned to %s." +msgstr "Все виртуальные хосты для ников группы %s установлены на %s" + +#: modules/commands/help.cpp:57 +#, fuzzy, c-format +msgid "All available commands for %s:" +msgstr "Справочная информация по %s отсутствует." + +#: modules/commands/cs_clone.cpp:96 +#, fuzzy, c-format +msgid "All badword entries from %s have been cloned to %s." +msgstr "Все виртуальные хосты для ников группы %s установлены на %s" + +#: modules/commands/cs_clone.cpp:108 +#, fuzzy, c-format +msgid "All level entries from %s have been cloned into %s." +msgstr "Все виртуальные хосты для ников группы %s установлены на %s" + +#: modules/commands/os_news.cpp:38 +msgid "All logon news items deleted." +msgstr "Список новостей полностью очищен." + +#: modules/commands/ms_del.cpp:115 +#, c-format +msgid "All memos for channel %s have been deleted." +msgstr "Все сообщения канала %s были удалены." + +#: modules/commands/os_mode.cpp:61 +#, c-format +msgid "All modes cleared on %s." +msgstr "" + +#: modules/commands/ns_register.cpp:258 modules/commands/ns_register.cpp:389 +msgid "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." +msgstr "" + +#: modules/commands/ms_del.cpp:119 +msgid "All of your memos have been deleted." +msgstr "Все ваши вообщения были удалены." + +#: modules/commands/os_news.cpp:48 +msgid "All oper news items deleted." +msgstr "Список новостей для операторов полностью очищен." + +#: modules/commands/os_noop.cpp:41 +#, fuzzy, c-format +msgid "All operators from %s have been removed." +msgstr "Все OLINE-записи на сервере %s были удалены." + +#: modules/commands/os_news.cpp:58 +msgid "All random news items deleted." +msgstr "Список случайных новостей полностью очищен." + +#: modules/commands/cs_clone.cpp:211 +#, fuzzy, c-format +msgid "All settings from %s have been cloned to %s." +msgstr "Все виртуальные хосты для ников группы %s установлены на %s" + +#: modules/commands/cs_sync.cpp:41 +#, fuzzy, c-format +msgid "All user modes on %s have been synced." +msgstr "Все OLINE-записи на сервере %s восстановлены." + +#: modules/commands/hs_group.cpp:60 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s." +msgstr "Все виртуальные хосты для ников группы %s установлены на %s" + +#: modules/commands/hs_group.cpp:58 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s@%s." +msgstr "Все виртуальные хосты для ников группы %s установлены на %s@%s" + +#: src/access.cpp:40 +msgid "Allowed to (de)halfop him/herself" +msgstr "" + +#: src/access.cpp:39 +msgid "Allowed to (de)halfop users" +msgstr "" + +#: src/access.cpp:48 +msgid "Allowed to (de)op him/herself" +msgstr "" + +#: src/access.cpp:47 +msgid "Allowed to (de)op users" +msgstr "" + +#: src/access.cpp:50 +msgid "Allowed to (de)owner him/herself" +msgstr "" + +#: src/access.cpp:49 +msgid "Allowed to (de)owner users" +msgstr "" + +#: src/access.cpp:52 +msgid "Allowed to (de)protect him/herself" +msgstr "" + +#: src/access.cpp:51 +msgid "Allowed to (de)protect users" +msgstr "" + +#: src/access.cpp:59 +msgid "Allowed to (de)voice him/herself" +msgstr "" + +#: src/access.cpp:58 +msgid "Allowed to (de)voice users" +msgstr "" + +#: src/access.cpp:27 +msgid "Allowed to assign/unassign a bot" +msgstr "" + +#: src/access.cpp:34 +msgid "Allowed to ban users" +msgstr "" + +#: src/access.cpp:56 +#, fuzzy +msgid "Allowed to change channel topics" +msgstr "%s принудительно изменил ваши пользовательские режимы." + +#: src/access.cpp:41 +msgid "Allowed to get full INFO output" +msgstr "" + +#: src/access.cpp:36 +msgid "Allowed to issue commands restricted to channel founders" +msgstr "" + +#: src/access.cpp:33 +msgid "Allowed to modify channel badwords list" +msgstr "" + +#: src/access.cpp:24 +#, fuzzy +msgid "Allowed to modify the access list" +msgstr "Ник %s успешно удален из списка доступа канала %s." + +#: src/access.cpp:44 +msgid "Allowed to read channel memos" +msgstr "" + +#: src/access.cpp:54 +#, fuzzy +msgid "Allowed to set channel settings" +msgstr "* Запрет на регистрацию каналов." + +#: src/access.cpp:57 +msgid "Allowed to unban users" +msgstr "" + +#: src/access.cpp:37 +msgid "Allowed to use GETKEY command" +msgstr "" + +#: src/access.cpp:53 +msgid "Allowed to use SAY and ACT commands" +msgstr "" + +#: src/access.cpp:35 +#, fuzzy +msgid "Allowed to use fantasy commands" +msgstr " PEACE активирование режима \"спокойствия\" на канале" + +#: src/access.cpp:26 +#, fuzzy +msgid "Allowed to use the AKICK command" +msgstr "You cannot use this command." + +#: src/access.cpp:42 +msgid "Allowed to use the INVITE command" +msgstr "" + +#: src/access.cpp:43 +#, fuzzy +msgid "Allowed to use the KICK command" +msgstr "You cannot use this command." + +#: src/access.cpp:45 +#, fuzzy +msgid "Allowed to use the MODE command" +msgstr "You cannot use this command." + +#: src/access.cpp:25 +#, fuzzy +msgid "Allowed to view the access list" +msgstr "Ник %s успешно удален из списка доступа канала %s." + +#: modules/commands/gl_global.cpp:42 +#, fuzzy, c-format +msgid "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." +msgstr "" +"Синтаксис: GLOBAL сообщение\n" +"\n" +"Позволяет Администраторам сервисов отправлять глобальные сообщения\n" +"всем пользователям сети. В качестве ника отправителя будет указан\n" +"%s." + +#: modules/commands/os_mode.cpp:133 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." +msgstr "" +"Синтаксис: MODE #канал режимы\n" +"\n" +"Позволяет Операторам сервисов изменять режимы на каком-либо канале.\n" +"В качестве второго параметра команды, вы должны указать режимы в\n" +"том же формате, в котором указываете при ручной установке, с помощью\n" +"команды /MODE." + +#: modules/commands/os_mode.cpp:173 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." +msgstr "" +"Синтаксис: MODE #канал режимы\n" +"\n" +"Позволяет Операторам сервисов изменять режимы на каком-либо канале.\n" +"В качестве второго параметра команды, вы должны указать режимы в\n" +"том же формате, в котором указываете при ручной установке, с помощью\n" +"команды /MODE." + +#: modules/commands/bs_bot.cpp:352 +#, fuzzy +msgid "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." +msgstr "" +"Синтаксис: BOT ADD ник идент хост реальное_имя\n" +" BOT CHANGE старый ник новый_ник [идент [хост [реальное_имя]]]\n" +" BOT DEL ник\n" +"\n" +"Позволяет Администраторам сервисов создавать, изменять или удалять\n" +"ботов, которые в дальнейшем могут быть использованы пользователями\n" +"сети на своих каналах.\n" +"\n" +"Команда BOT ADD добавляет бота с указанным ником, идентом, хостом\n" +"и реальным именем. Так как корректность этих значений не проверяется,\n" +"будьте крайне внимательны при добавлении/изменении хаарктеристик бота.\n" +"\n" +"Команда BOT CHANGE позволяет изменить ник, идент, хост или реальное\n" +"имя бота без необходимости его удаления.\n" +"\n" +"Команда BOT DEL удаляет указанного бота из списка ботов.\n" +"\n" +"Примечание: вы не можете создать бота с ником, который уже кем-то\n" +"зарегистрирован. Если же вы создаете бота с незарегистрированным ником,\n" +"любой, кто использует этот ник на момент создания бота - будет тут\n" +"же отключен от сети." + +#: modules/commands/os_oline.cpp:56 +#, fuzzy +msgid "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." +msgstr "" +"Синтаксис: OLINE ник оперфлаги\n" +"\n" +"Позволяет Администраторам сервисов установить флаги IRC-Оператора\n" +"любому посетителю сети. Перед флагами должен присутствовать префикс\n" +"\"+\" - для установки, или \"-\" - соответственно для снятия.\n" +"Чтобы удалить все флаги, используйте \"-\" вместо какого-либо флага.\n" +"\n" +"Для использования этой команды необходимы права Супер-Администратора." + +#: modules/commands/os_ignore.cpp:370 +#, fuzzy +msgid "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." +msgstr "" +"Синтаксис: IGNORE {ADD|DEL|LIST|CLEAR} [время] [ник|маска]\n" +"\n" +"Позволяет Администраторам сервисов управлять списком игнорируемых\n" +"сервисами пользователей.\n" +"По-умолчанию, параметр [время] является секундами. Однако, вы можете\n" +"указать и иные единицы измерения, используя: s для секунд, m для\n" +"минут, h для часов и d для дней. Комбинации этих единиц измерения\n" +"недопустимы. Установка времени игнора в 0 сделает его постоянным.\n" +"В качестве последнего значения вы должны указать валидный ник или\n" +"маску вида ник!идент@хост или идент@хост. Любые другие значения будут\n" +"расцениваться в качестве ника.\n" +"Пользователи со статусом IRC-оператора игнорироваться сервисами не\n" +"будут, даже если они присутствуют в списке игнора." + +#: modules/commands/os_akill.cpp:420 +#, fuzzy +msgid "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Синтаксис: AKILL ADD [+срок_истечения] маска причина\n" +" AKILL DEL {маска | номер_записи | список_записей}\n" +" AKILL LIST [маска | список_записей]\n" +" AKILL VIEW [маска | список_записей]\n" +" AKILL CLEAR\n" +"\n" +"Позволяет Операторам сервисов управлять списком сервисных AKILL'ов.\n" +"Любой пользователь, подпадающий под маску AKILL'а, будет немедленно\n" +"отключен от сети посредством сервисного KILL'а с указанной причиной,\n" +"и не важно, на каком сервере он сидит или к какому подключается.\n" +"Помимо этого, если IRCd вашей сети это поддерживает, сервисы \n" +"установят KLINE/GLINE на всех серверах вашей сети, в качестве маски\n" +"бана будет использована соответствующая запись AKILL'а.\n" +"\n" +"Команда AKILL ADD добавляет маску вида идент@хост/ip с указанной\n" +"причиной в список AKILL'ов (наличие причины - обязательно).\n" +"Значение срока истечения - это целое число, которое может быть\n" +"одним из: d (дней), h (часов), или m (минут). Такие сочетания\n" +"как 1h30m - недопустимы. Если единица измерения не указана, то\n" +"по-умолчанию, она будет принята за \"d\" - \"дни\" (таким образом,\n" +"+30 будет означать 30 дней). Чтобы добавить постоянный AKILL,\n" +"используйте время истечения равным +0. Помните, что если в качестве\n" +"первого символа второго параметра указан знак \"+\" - вы должны\n" +"обозначить сроки истечения записи, даже если это будет значение\n" +"по-умочанию.\n" +"Текущее время истечения AKILL'а по-умолчанию, можно узнать с помощью\n" +"команды STATS AKILL.\n" +"\n" +"Команда AKILL DEL удаляет указанную маску из списка AKILL'ов.\n" +"В качестве параметра вы можете указать не только маску AKILL'а, но\n" +"и конкретный номер записи или список записей (см. примеры\n" +"использования команды LIST ниже).\n" +"\n" +"Команда AKILL LIST показывает текущий список AKILL'ов.\n" +"В качестве дополнительного параметра, вы можете указать символьную\n" +"маску, что позволит вам получить список с конкретными записями,\n" +"попадающими под эту маску, или же, вы можете указать список записей.\n" +"Например:\n" +"\n" +" AKILL LIST 2-5,7-9\n" +" отобразит все записи с 2-ой по 5-ю и с 7-ой по 9-ю.\n" +"\n" +"AKILL VIEW более подробная версия AKILL LIST, она покажет вам\n" +"кто добавил AKILL, время установки AKILL'а, когда он истекает, ну\n" +"и, конечно же, маску вида идент@хост/ip и причину AKILL'а.\n" +"\n" +"AKILL CLEAR позволяет полностью очистить список AKILL'ов." + +#: modules/commands/os_sxline.cpp:436 +msgid "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." +msgstr "" + +#: modules/commands/os_sxline.cpp:670 +msgid "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." +msgstr "" + +#: modules/commands/os_session.cpp:551 +msgid "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." +msgstr "" + +#: modules/commands/os_session.cpp:270 +#, fuzzy +msgid "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." +msgstr "" +"Синтаксис: SESSION LIST порог\n" +" SESSION VIEW хост\n" +"\n" +"Позволяет Администраторам сервисов просматривать список сессий.\n" +"\n" +"Команда SESSION LIST позволяет получить список хостов с количеством\n" +"сессий большим или равным порогу. Значение порога должно быть\n" +"целым числом и больше 1. Это позволит избежать слишком большого списка\n" +"хостов с единичным количеством сессий.\n" +"\n" +"Команда SESSION VIEW покажет детальную информацию об указанном\n" +"хосте - текущее количестов сессий и ограничение для указанного хоста.\n" +"Помните, что указанный хост не должен включать в себя подстановочные\n" +"символы вида '*' и '?'.\n" +"\n" +"См. EXCEPTION HELP для более подробной информации о лимитировании\n" +"сессий и как установить отдельный лимит сессий для определенного\n" +"хоста или группы хостов." + +#: modules/commands/cs_topic.cpp:193 +msgid "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do " +"not have\n" +"the TOPIC privilege." +msgstr "" + +#: modules/commands/os_kick.cpp:62 +#, fuzzy, c-format +msgid "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" +msgstr "" +"Синтаксис: KICK #канал ник причина\n" +"\n" +"Позволяет Операторам сервисов выкинуть какого-либо пользователя с\n" +"указанного канала сети.\n" +"Параметры данной команды аналогичны параметрам стандартной команды\n" +"/KICK. Причина кика будет включать в себя ник Оператора сервисов,\n" +"который использовал данную команду, например:\n" +"\n" +"*** SpamMan was kicked by %s (Alcan (Flood))" + +#: modules/commands/cs_set.cpp:33 +#, fuzzy +msgid "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" +msgstr "" +"Синтаксис: SET #канал опция параметр\n" +"\n" +"Позволяет владельцу канала менять различные настройки канала.\n" +"Доступные опции:" + +#: modules/commands/os_oper.cpp:250 +msgid "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." +msgstr "" + +#: modules/commands/os_config.cpp:127 +msgid "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" +msgstr "" + +#: modules/commands/ns_set.cpp:992 +#, fuzzy +msgid "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." +msgstr "" +"Синтаксис: SASET ник MSG {ON | OFF}\n" +"\n" +"Позволяет вам выбрать способ общения сервисов с указанным ником.\n" +"Укажите ON, что бы активировать режим приватных сообщений - в\n" +"этом случае все сообщения от сервисов будут приходить владельцу в\n" +"приват. Параметр OFF заставит сервисы использовать режим\n" +"уведомлений (notice, нотисы).\n" +"Примечание: настройка данной опции может быть заблокирована." + +#: modules/commands/ns_set.cpp:966 +#, fuzzy, c-format +msgid "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." +msgstr "" +"Синтаксис: SET MSG {ON | OFF}\n" +"\n" +"Позволяет вам выбрать способ общения сервисов с вами. Укажите ON,\n" +"что бы активировать режим приватных сообщений - в этом случае все\n" +"сообщения от сервисов будут приходить вам в приват. Параметр OFF\n" +"заставит сервисы использовать режим уведомлений (notice, нотисы).\n" +"Примечание: настройка данной опции может быть заблокирована." + +#: modules/commands/ms_ignore.cpp:113 +msgid "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." +msgstr "" + +#: modules/commands/os_kill.cpp:48 +msgid "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." +msgstr "" + +#: modules/commands/ns_info.cpp:252 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Синтаксис: SASET ник HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}\n" +"\n" +"Данная опция позволяет вам скрыть часть информации об указанном\n" +"нике, которая может запрошена у %s с помощью команды INFO\n" +"\n" +"В качестве второго параметра вы должны указать что именно будет\n" +"скрыто:\n" +"QUIT - для скрытия последнего quit-сообщения владельца\n" +"EMAIL - для скрытия ассоциированного email-адреса владельца\n" +"STATUS - для скрытия уровня доступа к сервисам\n" +"USERMASK - для скрытия последней хостмаски владельца (идент@хост)\n" +"\n" +"В качестве третьего параметра вы должны указать либо ON либо OFF.\n" +"Первый активирует скрытие, второй, соответственно, деактивирует." + +#: modules/commands/ns_info.cpp:223 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Синтаксис: SET HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}\n" +"\n" +"Данная опция позволяет вам скрыть часть информации о вашем нике,\n" +"которая может запрошена у %s с помощью команды INFO\n" +"\n" +"В качестве второго параметра вы должны указать что именно будет\n" +"скрыто:\n" +"USERMASK - для скрытия вашей последней хостмаски вида идент@хост\n" +" STATUS - для скрытия вашего уровня доступа к сервисам\n" +" EMAIL - для скрытия ассоциированного email-адреса.\n" +" QUIT - для скрытия вашего последнего quit-сообщения\n" +"\n" +"В качестве третьего параметра вы должны указать либо ON либо OFF.\n" +"Первый активирует скрытие, второй, соответственно, деактивирует." + +#: modules/commands/bs_info.cpp:118 +#, fuzzy, c-format +msgid "Allows you to see %s information about a channel or a bot" +msgstr "INFO Запрос информации о боте и его настройках на канале" + +#: modules/commands/bs_info.cpp:108 +#, fuzzy, c-format +msgid "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." +msgstr "" +"Синтаксис: INFO {#канал | ник}\n" +"\n" +"Позволяет просмотреть различную информацию о самом боте (ник, идент,\n" +"хост, дату создания, количество обслуживаемых каналов), или о его\n" +"настройках на конкретном #канале (условия киков и установленные\n" +"опции).\n" +"Примечание: данные будут посланы от лица %s" + +#: modules/commands/cs_xop.cpp:567 +msgid "" +"Alternative methods of modifying channel access lists are\n" +"available. " +msgstr "" + +#: modules/commands/hs_request.cpp:191 +#, fuzzy +msgid "Approve the requested vHost of a user" +msgstr " DEL Удаление виртуального хоста" + +#: modules/commands/ns_drop.cpp:68 +#, fuzzy +msgid "As a Services Operator, you may drop any nick." +msgstr "%s is a services operator of type %s." + +#: modules/commands/bs_assign.cpp:19 +#, fuzzy +msgid "Assigns a bot to a channel" +msgstr "ASSIGN Установка бота на указанный канал" + +#: modules/commands/bs_assign.cpp:78 +#, fuzzy +msgid "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." +msgstr "" +"Синтаксис: ASSIGN #канал ник\n" +"\n" +"Позволяет установить указанного бота (ник) на указанный канал. Сразу\n" +"же после установки, вы сможете сконфигурировать опции бота по своему\n" +"усмотрению." + +#: data/chanserv.example.conf:1197 +#, fuzzy +msgid "Associate a URL with the channel" +msgstr "ASSIGN Установка бота на указанный канал" + +#: data/nickserv.example.conf:594 +msgid "Associate a URL with this account" +msgstr "" + +#: data/nickserv.example.conf:593 +#, fuzzy +msgid "Associate a URL with your account" +msgstr " GREET установка приветственного сообщения" + +#: modules/commands/greet.cpp:83 +#, fuzzy +msgid "Associate a greet message with your nickname" +msgstr " GREET установка приветственного сообщения" + +#: data/chanserv.example.conf:1198 +#, fuzzy +msgid "Associate an E-mail address with the channel" +msgstr " EMAIL установка email-адреса на ник" + +#: modules/commands/ns_set.cpp:452 +#, fuzzy +msgid "Associate an E-mail address with your nickname" +msgstr " EMAIL установка email-адреса на ник" + +#: modules/commands/os_info.cpp:101 +#, fuzzy +msgid "Associate oper info with a nick or channel" +msgstr "ASSIGN Установка бота на указанный канал" + +#: modules/commands/ns_set.cpp:558 +#, fuzzy +msgid "Associates the given E-mail address with the nickname." +msgstr " EMAIL установка email-адреса на ник" + +#: modules/commands/ns_set.cpp:533 +#, fuzzy +msgid "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." +msgstr "" +"Синтаксис: SET EMAIL адрес@email\n" +"\n" +"Ассоциирует email-адрес с вашим ником. Данный email будет показан\n" +"в информации о вашем нике, предоставляемой по команде INFO." + +#: modules/commands/ns_set.cpp:1315 +msgid "Auto-op" +msgstr "Автостатус" + +#: modules/commands/cs_akick.cpp:374 +#, c-format +msgid "Autokick list for %s:" +msgstr "Список автокиков канала %s:" + +#: src/access.cpp:29 +msgid "Automatic channel operator status upon join" +msgstr "" + +#: src/access.cpp:28 +msgid "Automatic halfop upon join" +msgstr "" + +#: src/access.cpp:30 +msgid "Automatic owner upon join" +msgstr "" + +#: src/access.cpp:31 +msgid "Automatic protect upon join" +msgstr "" + +#: src/access.cpp:32 +msgid "Automatic voice on join" +msgstr "" + +#: modules/commands/os_oper.cpp:196 +#, fuzzy, c-format +msgid "Available commands for %s:" +msgstr "Справочная информация по %s отсутствует." + +#: modules/commands/os_oper.cpp:175 +#, fuzzy +msgid "Available opertypes:" +msgstr "Справочная информация по %s отсутствует." + +#: modules/commands/os_oper.cpp:218 +#, c-format +msgid "Available privileges for %s:" +msgstr "" + +#: modules/commands/cs_enforce.cpp:162 +msgid "BANS enforced by " +msgstr "" + +#: modules/commands/bs_kick.cpp:1121 modules/commands/bs_kick.cpp:1123 +#: modules/commands/bs_kick.cpp:1126 +#, fuzzy +msgid "Bad words kicker" +msgstr "Цензор плохих слов...: %s" + +#: modules/commands/bs_badwords.cpp:252 +#, fuzzy, c-format +msgid "Bad words list for %s:" +msgstr "Список доступа для %s:" + +#: modules/commands/bs_badwords.cpp:364 +msgid "Bad words list is now empty." +msgstr "Список \"плохих\" слов полностью очищен." + +#: modules/commands/bs_set.cpp:129 +msgid "Ban expiry may not be longer than 1 day." +msgstr "" + +#: modules/commands/cs_ban.cpp:140 modules/commands/cs_ban.cpp:175 +#, fuzzy, c-format +msgid "Ban on %s expires in %s." +msgstr "Бот с ником %s уже существует." + +#: modules/commands/cs_info.cpp:60 +msgid "Ban type" +msgstr "" + +#: modules/commands/cs_set.cpp:174 +#, c-format +msgid "Ban type for channel %s is now #%d." +msgstr "Шаблон банмаски на канале %s изменен на #%d." + +#: modules/commands/cs_ban.cpp:39 +#, fuzzy +msgid "Bans a given nick or mask on a channel" +msgstr " BAN Установка бана на канале" + +#: modules/commands/cs_ban.cpp:227 +#, fuzzy +msgid "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." +msgstr "" +"Синтаксис: BAN #канал ник [причина]\n" +"\n" +"Банит указанного пользователя на указанном канале.\n" +"\n" +"По-умолчанию, данная команда может быть использована AOP'ами или\n" +"лицами с уровнем доступа 5 и выше." + +#: modules/commands/cs_enforce.cpp:166 +#, fuzzy, c-format +msgid "Bans enforced on %s." +msgstr "%s не уведомляется о новых собщениях." + +#: modules/commands/bs_kick.cpp:1131 modules/commands/bs_kick.cpp:1133 +#: modules/commands/bs_kick.cpp:1136 +#, fuzzy +msgid "Bolds kicker" +msgstr "Цензор жирных букв...: %s" + +#: modules/commands/bs_bot.cpp:26 modules/commands/bs_bot.cpp:175 +#, c-format +msgid "Bot %s already exists." +msgstr "Бот с ником %s уже существует." + +#: include/language.h:119 +#, fuzzy, c-format +msgid "Bot %s does not exist." +msgstr "Бот с ником %s уже существует." + +#: modules/commands/bs_assign.cpp:71 modules/commands/bs_assign.cpp:246 +#, c-format +msgid "Bot %s has been assigned to %s." +msgstr "Бот %s успешно назначен на канал %s." + +#: modules/commands/bs_bot.cpp:228 +#, fuzzy, c-format +msgid "Bot %s has been changed to %s!%s@%s (%s)." +msgstr "Данные о боте %s были изменены на %s!%s@%s (%s)" + +#: modules/commands/bs_bot.cpp:262 +#, c-format +msgid "Bot %s has been deleted." +msgstr "Бот под ником %s успешно удален." + +#: modules/commands/bs_assign.cpp:63 modules/commands/bs_assign.cpp:241 +#, c-format +msgid "Bot %s is already assigned to channel %s." +msgstr "Бот %s уже назначен на канал %s." + +#: modules/commands/bs_kick.cpp:832 +#, c-format +msgid "Bot will kick ops on channel %s." +msgstr "С этого момента, бот будет кикать операторов канала %s за нарушения." + +#: modules/commands/bs_kick.cpp:897 +#, c-format +msgid "Bot will kick voices on channel %s." +msgstr "С этого момента бот будет кикать войсов канала %s за нарушения." + +#: modules/commands/bs_kick.cpp:824 +#, c-format +msgid "Bot won't kick ops on channel %s." +msgstr "" +"Теперь, операторы канала %s будут исключены из условий кика за нарушения." + +#: modules/commands/bs_kick.cpp:889 +#, c-format +msgid "Bot won't kick voices on channel %s." +msgstr "Теперь, войсы канала %s будут исключены из условий кика за нарушения." + +#: modules/commands/bs_bot.cpp:118 +#, fuzzy, c-format +msgid "Bot %s is not changeable." +msgstr "Режим без-бота для канала %s активирован." + +#: modules/commands/bs_bot.cpp:254 +#, fuzzy, c-format +msgid "Bot %s is not deletable." +msgstr "Бот под ником %s успешно удален." + +#: modules/commands/bs_set.cpp:141 +#, c-format +msgid "Bot bans will automatically expire after %s." +msgstr "" + +#: modules/commands/bs_set.cpp:139 +#, fuzzy +msgid "Bot bans will no longer automatically expire." +msgstr "Режим автостатуса для %s отключен" + +#: modules/commands/bs_bot.cpp:46 modules/commands/bs_bot.cpp:138 +#, fuzzy, c-format +msgid "Bot hosts may only be %d characters long." +msgstr "Хост бота не должен превышать %d символов." + +#: modules/commands/bs_bot.cpp:64 modules/commands/bs_bot.cpp:167 +#, fuzzy +msgid "Bot hosts may only contain valid host characters." +msgstr "Указанный для бота хост содержит недопустимые символы." + +#: modules/commands/bs_bot.cpp:40 modules/commands/bs_bot.cpp:132 +#, fuzzy, c-format +msgid "Bot idents may only be %d characters long." +msgstr "Идент бота не должен превышать %d символов." + +#: modules/commands/bs_bot.cpp:58 modules/commands/bs_bot.cpp:161 +#, fuzzy +msgid "Bot idents may only contain valid ident characters." +msgstr "Указанный для бота идент содержит недопустимые символы." + +#: include/language.h:121 +#, fuzzy, c-format +msgid "Bot is not on channel %s." +msgstr "С этого момента, бот будет кикать операторов канала %s за нарушения." + +#: modules/commands/bs_botlist.cpp:51 +msgid "Bot list:" +msgstr "Список ботов:" + +#: modules/commands/bs_info.cpp:87 +msgid "Bot nick" +msgstr "" + +#: modules/commands/bs_bot.cpp:34 modules/commands/bs_bot.cpp:126 +#, fuzzy, c-format +msgid "Bot nicks may only be %d characters long." +msgstr "Идент бота не должен превышать %d символов." + +#: modules/commands/bs_bot.cpp:52 modules/commands/bs_bot.cpp:155 +#, fuzzy +msgid "Bot nicks may only contain valid nick characters." +msgstr "Указанный для бота ник содержит недопустимые символы." + +#: modules/commands/bs_kick.cpp:225 +#, fuzzy, c-format +msgid "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." +msgstr "" +"Bot will now kick italics, and will place a ban after %d\n" +"kicks for the same user." + +#: modules/commands/bs_kick.cpp:228 +#, fuzzy, c-format +msgid "Bot will now kick for %s." +msgstr "Режим кика за использование жирного шрифта активирован." + +#: modules/commands/bs_kick.cpp:416 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." +msgstr "" +"Режим кика за чрезмерное использование CapsLOCK активирован. Бот\n" +"будет кикать посетителя, если его фраза содержит не менее %d больших\n" +"символов и они составляют не менее %d%% от общего кол-ва символов.\n" +"Дополнительно, после %d предупреждающих киков, бот забанит нарушителя." + +#: modules/commands/bs_kick.cpp:420 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." +msgstr "" +"Режим кика за чрезмерное использование CapsLOCK активирован. Бот\n" +"будет кикать посетителя, если его фраза содержит не менее %d больших\n" +"символов и они составляют не менее %d%% от общего кол-ва символов." + +#: modules/commands/bs_kick.cpp:551 +#, fuzzy, c-format +msgid "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." +msgstr "" +"Режим кика за флуд активирован (условие: %d линий за %d секунд).\n" +"Дополнительно, после %d предупреждающих киков, бот забанит нарушителя." + +#: modules/commands/bs_kick.cpp:554 +#, fuzzy, c-format +msgid "Bot will now kick for flood (%d lines in %d seconds)." +msgstr "Режим кика за флуд активирован (условие: %d линий за %d секунд)." + +#: modules/commands/bs_kick.cpp:677 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Режим кика за чрезмерные повторы активирован.\n" +"Бот будет кикать пользователя после %d повторов подряд и ставить\n" +"бан после %d предупреждающих киков." + +#: modules/commands/bs_kick.cpp:687 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." +msgstr "" +"Режим кика за чрезмерные повторы активирован. Бот будет кикать\n" +"посетителя если он повторит одну и ту же фразу %d раз подряд." + +#: modules/commands/bs_kick.cpp:673 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Режим кика за чрезмерные повторы активирован.\n" +"Бот будет кикать пользователя после %d повторов подряд и ставить\n" +"бан после %d предупреждающих киков." + +#: modules/commands/bs_kick.cpp:684 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." +msgstr "" +"Режим кика за чрезмерные повторы активирован. Бот будет кикать\n" +"посетителя если он повторит одну и ту же фразу %d раз подряд." + +#: modules/commands/bs_kick.cpp:239 +#, fuzzy, c-format +msgid "Bot won't kick for %s anymore." +msgstr "Режим кика за чрезмерное использование CapsLOCK отключен." + +#: modules/commands/bs_kick.cpp:426 +#, fuzzy +msgid "Bot won't kick for caps anymore." +msgstr "Режим кика за чрезмерное использование CapsLOCK отключен." + +#: modules/commands/bs_kick.cpp:559 +#, fuzzy +msgid "Bot won't kick for flood anymore." +msgstr "Режим кика за флуд отключен." + +#: modules/commands/bs_kick.cpp:694 +#, fuzzy +msgid "Bot won't kick for repeats anymore." +msgstr "Режим кика за чрезмерные повторы отключен." + +#: modules/commands/cs_access.cpp:472 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_session.cpp:514 +msgid "By" +msgstr "" + +#: modules/commands/os_info.cpp:104 +msgid "CLEAR target" +msgstr "" + +#: modules/commands/cs_seen.cpp:119 +msgid "CLEAR time" +msgstr "" + +#: modules/commands/ms_cancel.cpp:19 +#, fuzzy +msgid "Cancel the last memo you sent" +msgstr " CANCEL Отмена последнего отправленного вами мемо-сообщения" + +#: modules/commands/cs_drop.cpp:19 +#, fuzzy +msgid "Cancel the registration of a channel" +msgstr " DROP Удаление канала из базы данных сервисов" + +#: modules/commands/ns_drop.cpp:20 +#, fuzzy +msgid "Cancel the registration of a nickname" +msgstr " DROP Отмена регистрации ника (удаление)" + +#: modules/commands/ms_cancel.cpp:84 +#, fuzzy +msgid "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." +msgstr "" +"Синтаксис: CANCEL {ник | #канал}\n" +"\n" +"Отменяет последнее сообщение, отправленное вами указанному нику\n" +"или каналу, тем самым предохраняя его от прочтения адресатом." + +#: modules/commands/cs_clone.cpp:149 +#, fuzzy, c-format +msgid "Cannot clone channel %s to itself!" +msgstr "С этого момента, бот будет кикать операторов канала %s за нарушения." + +#: modules/commands/ns_register.cpp:332 +msgid "Cannot send mail now; please retry a little later." +msgstr "На данный момент отправка email невозможна, попробуйте позже." + +#: modules/commands/bs_kick.cpp:1141 modules/commands/bs_kick.cpp:1143 +#: modules/commands/bs_kick.cpp:1146 +#, fuzzy +msgid "Caps kicker" +msgstr "Цензор CapsLOCK......: %s" + +#: modules/commands/os_shutdown.cpp:34 +#, fuzzy +msgid "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." +msgstr "" +"Синтаксис: QUIT\n" +"\n" +"Заставляет сервисы немедленно завершить свою работу. Все данные,\n" +"накопленные с момента последнего обновления баз данных, сохранены\n" +"не будут! Эта команда должна использоваться только в тех случаях,\n" +"когда текущая загруженная в память база данных содержит какие-либо\n" +"ошибки, сохранения которых нужно избежать.\n" +"Для нормального завершения работы сервисов используйте команду SHUTDOWN." + +#: modules/commands/os_reload.cpp:47 +#, fuzzy +msgid "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." +msgstr "" +"Синтаксис: RELOAD\n" +"\n" +"Заставляет сервисы перечитать конфигурационный файл services.conf.\n" +"Примечание: активация некоторых новых/измененных директив конфига\n" +"требует полного перезапуска сервисов (например: изменение ников\n" +"сервисов, активация лимитирования сессий, и т.д.)" + +#: modules/commands/os_shutdown.cpp:62 +#, fuzzy +msgid "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." +msgstr "" +"Синтаксис: RESTART\n" +"\n" +"Заставляет сервисы сохранить все базы данных и тут же перезапуститься." + +#: modules/commands/os_shutdown.cpp:89 +#, fuzzy +msgid "Causes Services to save all databases and then shut down." +msgstr "" +"Синтаксис: SHUTDOWN\n" +"\n" +"Заставляет сервисы сохранить все базы данных и завершить свою работу." + +#: modules/commands/os_update.cpp:34 +#, fuzzy +msgid "" +"Causes Services to update all database files as soon as you\n" +"send the command." +msgstr "" +"Синтаксис: UPDATE\n" +"\n" +"Заставляет сервисы немедленно сохранить все базы данных на диск." + +#: modules/commands/ns_cert.cpp:246 +#, fuzzy, c-format +msgid "Certificate list for %s:" +msgstr "Список доступа для %s:" + +#: modules/commands/cs_set.cpp:528 modules/commands/cs_set.cpp:570 +msgid "ChanServ is required to enable persist on this network." +msgstr "" + +#: modules/commands/os_mode.cpp:19 +#, fuzzy +msgid "Change channel modes" +msgstr "%s принудительно изменил ваши пользовательские режимы." + +#: modules/commands/ns_set.cpp:905 +#, fuzzy +msgid "Change the communication method of Services" +msgstr " MSG выбор метода общения сервисов с вами" + +#: modules/commands/os_mode.cpp:146 +#, fuzzy +msgid "Change user modes" +msgstr "%s принудительно изменил ваши пользовательские режимы." + +#: modules/commands/os_mode.cpp:161 +#, fuzzy, c-format +msgid "Changed usermodes of %s to %s." +msgstr "Режимы пользователя %s изменены." + +#: modules/commands/ns_set.cpp:411 +#, fuzzy +msgid "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." +msgstr "" +"Синтаксис: SET DISPLAY новый_ник\n" +"\n" +"Позволяет переназначить главный ник группы. Именно этот ник будет\n" +"отображаться в списке доступа каналов, где вы прописаны.\n" +"Примечание: новый главный ник должен состоять в вашей группе ников." + +#: modules/commands/ns_set.cpp:387 +#, fuzzy +msgid "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." +msgstr "" +"Синтаксис: SET DISPLAY новый_ник\n" +"\n" +"Позволяет переназначить главный ник группы. Именно этот ник будет\n" +"отображаться в списке доступа каналов, где вы прописаны.\n" +"Примечание: новый главный ник должен состоять в вашей группе ников." + +#: modules/commands/cs_set.cpp:324 +#, fuzzy +msgid "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." +msgstr "" +"Синтаксис: %s #канал FOUNDER ник\n" +"\n" +"Позволяет передать права на владение каналом другому пользователю.\n" +"Ник нового владельца канала должен быть зарегистрированным." + +#: modules/commands/ns_set.cpp:884 +#, fuzzy +msgid "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Синтаксис: SET LANGUAGE номер\n" +"\n" +"Позволяет выбрать язык, на котором сервисы будут посылать вам\n" +"различные сообщения. Например, текст справочной системы, который вы\n" +"сейчас и читаете.\n" +"В качестве номера, вы должны указать конкретный номер языка из\n" +"списка поддерживаемых языков:" + +#: modules/commands/ns_set.cpp:848 +#, fuzzy +msgid "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Синтаксис: SET LANGUAGE номер\n" +"\n" +"Позволяет выбрать язык, на котором сервисы будут посылать вам\n" +"различные сообщения. Например, текст справочной системы, который вы\n" +"сейчас и читаете.\n" +"В качестве номера, вы должны указать конкретный номер языка из\n" +"списка поддерживаемых языков:" + +#: modules/commands/ns_set.cpp:227 +#, fuzzy +msgid "Changes the password used to identify as the nick's owner." +msgstr "" +"Синтаксис: SET PASSWORD новый_пароль\n" +"\n" +"Позволяет изменить пароль ника, используемый для идентификации к\n" +"нему в качестве полноправного владельца." + +#: modules/commands/ns_set.cpp:161 +#, fuzzy +msgid "" +"Changes the password used to identify you as the nick's\n" +"owner." +msgstr "" +"Синтаксис: SET PASSWORD новый_пароль\n" +"\n" +"Позволяет изменить пароль ника, используемый для идентификации к\n" +"нему в качестве полноправного владельца." + +#: modules/commands/cs_set.cpp:1017 +#, fuzzy +msgid "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." +msgstr "" +"Синтаксис: %s #канал SUCCESSOR ник\n" +"\n" +"Позволяет назначить наследника канала. Если ник текущего владельца\n" +"канала будет удален ввиду истечения срока регистрации или по каким\n" +"иным причинам, назначенный наследник станет новым владельцем канала.\n" +"Так же, стоит заметить, что если наследник уже зарегистрировал\n" +"чересчур много каналов (более %d), он не получит прав на владение\n" +"каналом и тот будет удален. Ко всему прочему, ник наследника канала\n" +"должен быть зарегистрированным ником." + +#: modules/commands/ns_alist.cpp:48 modules/commands/ns_ajoin.cpp:100 +#, fuzzy +msgid "Channel" +msgstr "DROP #канал" + +#: include/language.h:84 +#, fuzzy, c-format +msgid "Channel %s doesn't exist." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_drop.cpp:63 +#, c-format +msgid "Channel %s has been dropped." +msgstr "Канал %s удален из базы данных." + +#: modules/commands/cs_getkey.cpp:43 +#, fuzzy, c-format +msgid "Channel %s has no key." +msgstr "Канал %s не имеет ключа (no key)." + +#: modules/commands/cs_register.cpp:47 +#, c-format +msgid "Channel %s is already registered!" +msgstr "Канал %s уже зарегистрирован!" + +#: modules/commands/os_forbid.cpp:524 +#, fuzzy, c-format +msgid "Channel %s is forbidden by %s: %s" +msgstr "Этот канал был зарегистрирован с помощью %s" + +#: modules/commands/os_forbid.cpp:526 +#, fuzzy, c-format +msgid "Channel %s is forbidden." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_set.cpp:580 +#, fuzzy, c-format +msgid "Channel %s is no longer persistent." +msgstr "Channel %s is no longer persistant." + +#: modules/commands/cs_set.cpp:542 +#, fuzzy, c-format +msgid "Channel %s is now persistent." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_suspend.cpp:180 +#, c-format +msgid "Channel %s is now released." +msgstr "Канал %s успешно восстановлен из режима саспенда." + +#: modules/commands/cs_suspend.cpp:125 +#, c-format +msgid "Channel %s is now suspended." +msgstr "Активность канала %s приостановлена." + +#: include/language.h:83 +#, fuzzy, c-format +msgid "Channel %s isn't registered." +msgstr "Канал %s не может быть зарегистрирован." + +#: modules/commands/cs_suspend.cpp:172 +#, fuzzy, c-format +msgid "Channel %s isn't suspended." +msgstr "Активность канала %s приостановлена." + +#: modules/commands/cs_register.cpp:68 +#, fuzzy, c-format +msgid "Channel %s registered under your account: %s" +msgstr "" +"Ник %s успешно зарегистрирован, в ACCESS-список добавлена хостмаска: %s" + +#: modules/commands/cs_set.cpp:1078 +#, c-format +msgid "Channel %s will expire." +msgstr "Режим истечения по времени для канала %s активирована." + +#: modules/commands/cs_set.cpp:1072 +#, c-format +msgid "Channel %s will not expire." +msgstr "С этого момента, регистрация канала %s никогда не истечет." + +#: modules/commands/cs_xop.cpp:475 +#, fuzzy, c-format +msgid "Channel %s %s list has been cleared." +msgstr "Список AOP'ов канала %s был полностью очищен." + +#: modules/commands/cs_access.cpp:486 modules/commands/cs_flags.cpp:361 +#, c-format +msgid "Channel %s access list has been cleared." +msgstr "Список доступа канала %s был полностью очищен." + +#: modules/commands/cs_akick.cpp:428 +#, c-format +msgid "Channel %s akick list has been cleared." +msgstr "Список AKICK'ов на канале %s был полностью очищен." + +#: modules/commands/cs_mode.cpp:444 +#, fuzzy, c-format +msgid "Channel %s has no mode locks." +msgstr "Канал %s успешно восстановлен из режима саспенда." + +#: include/language.h:82 +#, fuzzy, c-format +msgid "Channel %s is currently suspended." +msgstr "Активность канала %s приостановлена." + +#: include/language.h:101 +#, fuzzy, c-format +msgid "Channel %s is not a valid channel." +msgstr "Число %s не является валидным номером шаблона банмаски." + +#: modules/commands/os_list.cpp:70 +#, fuzzy +msgid "Channel list:" +msgstr "Список ботов:" + +#: modules/extra/stats/cs_fantasy_stats.cpp:148 +#, fuzzy, c-format +msgid "Channel stats for %s on %s:" +msgstr "" +"Каналы, на которых у %s есть уровни доступа:\n" +"Номер Канал Уровень Описание" + +#: modules/commands/cs_access.cpp:142 modules/commands/cs_flags.cpp:97 +#: modules/commands/cs_xop.cpp:139 +#, fuzzy +msgid "Channels may not be on access lists." +msgstr "Ник %s в списке доступа канала %s не обнаружен." + +#: modules/commands/ns_alist.cpp:114 +#, fuzzy, c-format +msgid "Channels that %s has access on:" +msgstr "" +"Каналы, на которых у %s есть уровни доступа:\n" +"Номер Канал Уровень Описание" + +#: modules/commands/os_stats.cpp:181 +#, c-format +msgid "Channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:517 +#: modules/extra/stats/m_chanstats.cpp:525 +msgid "Chanstats" +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:102 +#, fuzzy, c-format +msgid "Chanstats statistics are now disabled for %s" +msgstr " SECURE активирование/деактивирование режима безопасности" + +#: modules/extra/stats/m_chanstats.cpp:51 +msgid "Chanstats statistics are now disabled for this channel." +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:104 +#, fuzzy +msgid "Chanstats statistics are now disabled for your nick." +msgstr " SECURE активирование/деактивирование режима безопасности" + +#: modules/extra/stats/m_chanstats.cpp:93 +#, fuzzy, c-format +msgid "Chanstats statistics are now enabled for %s" +msgstr " SECURE активирование/деактивирование режима безопасности" + +#: modules/extra/stats/m_chanstats.cpp:44 +msgid "Chanstats statistics are now enabled for this channel." +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:95 +#, fuzzy +msgid "Chanstats statistics are now enabled for your nick." +msgstr " SECURE активирование/деактивирование режима безопасности" + +#: modules/commands/cs_seen.cpp:367 +msgid "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." +msgstr "" + +#: modules/commands/ms_check.cpp:19 +#, fuzzy +msgid "Checks if last memo to a nick was read" +msgstr "" +" CHECK Проверка на то, было ли прочитано последнее посланное вами " +"сообщение" + +#: modules/commands/ms_check.cpp:69 +#, fuzzy +msgid "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." +msgstr "" +"Синтаксис: CHECK ник\n" +"\n" +"Проверяет, было ли прочитано последнее посланное вами сообщения\n" +"указанным ником.\n" +"Примечание: команда работает только для ников, не для каналов." + +#: modules/commands/os_info.cpp:227 +#, c-format +msgid "Cleared info from %s." +msgstr "" + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1153 +#: modules/commands/bs_kick.cpp:1156 +#, fuzzy +msgid "Colors kicker" +msgstr "KICK Настройка условий KICK'а" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Command" +msgstr "Список команд %s:" + +#: modules/commands/bs_kick.cpp:251 +#, fuzzy +msgid "Configures AMSG kicker" +msgstr "KICK Настройка условий KICK'а" + +#: modules/commands/bs_kick.cpp:287 +#, fuzzy +msgid "Configures badwords kicker" +msgstr "KICK Настройка условий KICK'а" + +#: modules/commands/bs_kick.cpp:326 +#, fuzzy +msgid "Configures bolds kicker" +msgstr "KICK Настройка условий KICK'а" + +#: modules/commands/bs_kick.cpp:132 +#, fuzzy +msgid "Configures bot kickers. option can be one of:" +msgstr "" +"Синтаксис: SET опция параметры\n" +"\n" +"Команда SET позволяет вам настроить различные опции ника.\n" +"Список опций:" + +#: modules/commands/bs_set.cpp:19 +#, fuzzy +msgid "Configures bot options" +msgstr "SET Настройка различных опций бота" + +#: modules/commands/bs_set.cpp:32 +#, fuzzy +msgid "" +"Configures bot options.\n" +" \n" +"Available options:" +msgstr "SET Настройка различных опций бота" + +#: modules/commands/bs_kick.cpp:360 +#, fuzzy +msgid "Configures caps kicker" +msgstr "KICK Настройка условий KICK'а" + +#: modules/commands/cs_log.cpp:105 +#, fuzzy +msgid "Configures channel logging settings" +msgstr "* Запрет на регистрацию каналов." + +#: modules/commands/bs_kick.cpp:456 +#, fuzzy +msgid "Configures color kicker" +msgstr "KICK Настройка условий KICK'а" + +#: modules/commands/bs_kick.cpp:490 +#, fuzzy +msgid "Configures flood kicker" +msgstr "KICK Настройка условий KICK'а" + +#: modules/commands/bs_kick.cpp:588 +#, fuzzy +msgid "Configures italics kicker" +msgstr "KICK Настройка условий KICK'а" + +#: modules/commands/bs_kick.cpp:119 +#, fuzzy +msgid "Configures kickers" +msgstr "KICK Настройка условий KICK'а" + +#: modules/commands/bs_kick.cpp:622 +#, fuzzy +msgid "Configures repeat kicker" +msgstr "KICK Настройка условий KICK'а" + +#: modules/commands/bs_kick.cpp:723 +#, fuzzy +msgid "Configures reverses kicker" +msgstr "KICK Настройка условий KICK'а" + +#: modules/commands/bs_set.cpp:90 +#, fuzzy +msgid "Configures the time bot bans expire in" +msgstr "SET Настройка различных опций бота" + +#: modules/commands/bs_kick.cpp:757 +#, fuzzy +msgid "Configures underlines kicker" +msgstr "KICK Настройка условий KICK'а" + +#: modules/commands/ns_register.cpp:21 +#, fuzzy +msgid "Confirm a passcode" +msgstr " CONFIRM Подтверждение регистрации кодом аутенфикации" + +#: modules/commands/cs_mode.cpp:733 +#, fuzzy +msgid "Control modes and mode locks on a channel" +msgstr " CLEARMODES Очистка всех режимов указанного канала" + +#: modules/commands/cs_entrymsg.cpp:239 +msgid "" +"Controls what messages will be sent to users when they join the channel." +msgstr "" + +#: modules/commands/cs_clone.cpp:242 +msgid "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." +msgstr "" + +#: modules/commands/cs_clone.cpp:114 +#, fuzzy +msgid "Copy all settings from one channel to another" +msgstr "" +" UNBAN Remove all bans preventing a user from entering a channel" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/bs_info.cpp:57 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Created" +msgstr "Создан..........: %s" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_ignore.cpp:266 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_news.cpp:156 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Creator" +msgstr "Создан..........: %s" + +#: modules/commands/os_sxline.cpp:180 +#, fuzzy, c-format +msgid "Current %s list:" +msgstr "Текущий список AKILL'ов:" + +#: modules/commands/os_akill.cpp:323 +#, fuzzy +msgid "Current AKILL list:" +msgstr "Текущий список AKILL'ов:" + +#: modules/commands/os_session.cpp:493 +msgid "Current Session Limit Exception list:" +msgstr "Текущий список исключений из лимита сессий:" + +#: modules/commands/os_modinfo.cpp:116 +#, fuzzy +msgid "Current module list:" +msgstr "Текущий список модулей:" + +#: modules/commands/os_stats.cpp:69 +#, c-format +msgid "Current number of AKILLs: %d" +msgstr "Текущее количество AKILL'ов : %d" + +#: modules/commands/os_stats.cpp:89 +#, c-format +msgid "Current number of SNLINEs: %d" +msgstr "Текущее количество SNLINE'ов : %d" + +#: modules/commands/os_stats.cpp:109 +#, c-format +msgid "Current number of SQLINEs: %d" +msgstr "Текущее количество SQLINE'ов : %d" + +#: modules/commands/os_stats.cpp:138 +#, c-format +msgid "Current users: %d (%d ops)" +msgstr "Текущее кол-во пользователей: %d, IRC-операторов: %d " + +#: modules/commands/os_oper.cpp:71 +#, fuzzy +msgid "DEL oper" +msgstr "DEL <ник>." + +#: modules/commands/os_info.cpp:103 +#, fuzzy +msgid "DEL target info" +msgstr "GROUP главный_ник пароль" + +#: modules/commands/ns_ajoin.cpp:232 +#, fuzzy +msgid "DEL [nickname] channel" +msgstr "MODE #канал режимы" + +#: modules/commands/ns_cert.cpp:259 +#, fuzzy +msgid "DEL [nickname] fingerprint" +msgstr "FORBID ник причина" + +#: modules/commands/ns_access.cpp:103 +#, fuzzy +msgid "DEL [nickname] mask" +msgstr "MODE #канал режимы" + +#: modules/commands/os_sxline.cpp:426 modules/commands/os_sxline.cpp:660 +#: modules/commands/os_akill.cpp:387 +#, fuzzy +msgid "DEL {mask | entry-num | list | id}" +msgstr "DEL [#канал] {номер_сообщения | список_записей | ALL}" + +#: modules/commands/os_session.cpp:524 +#, fuzzy +msgid "DEL {mask | entry-num | list}" +msgstr "DEL [#канал] {номер_сообщения | список_записей | ALL}" + +#: modules/commands/os_ignore.cpp:343 +#, fuzzy +msgid "DEL {nick|mask}" +msgstr "DEL <ник>." + +#: modules/commands/os_news.cpp:279 +#, fuzzy +msgid "DEL {num | ALL}" +msgstr "Синтаксис: OPERNEWS DEL {номер | ALL}" + +#: modules/commands/os_forbid.cpp:158 +msgid "DEL {NICK|CHAN|EMAIL|REGISTER} entry" +msgstr "" + +#: modules/commands/os_dns.cpp:666 +msgid "DELIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:664 +msgid "DELSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:662 +msgid "DELZONE zone.name" +msgstr "" + +#: modules/commands/os_dns.cpp:669 +#, fuzzy +msgid "DEPOOL server.name" +msgstr "NOOP {SET|REVOKE} сервер" + +#: modules/commands/cs_seen.cpp:162 +#, c-format +msgid "Database cleared, removed %lu nicks that were added after %s." +msgstr "" + +#: modules/commands/ms_list.cpp:64 +msgid "Date/Time" +msgstr "" + +#: modules/commands/hs_off.cpp:49 +#, fuzzy +msgid "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." +msgstr "" +"Синтаксис: OFF\n" +"\n" +"Деактивирует ваш текущий виртуальный хост, при условии, конечно,\n" +"что таковой установлен на момент использования команды." + +#: modules/commands/hs_off.cpp:19 +#, fuzzy +msgid "Deactivates your assigned vhost" +msgstr " OFF Деактивирует ваш текущий виртуальный хост" + +#: modules/commands/os_stats.cpp:72 +#, c-format +msgid "Default AKILL expiry time: %d days" +msgstr "Время истечения AKILL'а по-умолчанию : %d дней" + +#: modules/commands/os_stats.cpp:76 +#, c-format +msgid "Default AKILL expiry time: %d hours" +msgstr "Время истечения AKILL'а по-умолчанию : %d часов" + +#: modules/commands/os_stats.cpp:80 +#, c-format +msgid "Default AKILL expiry time: %d minutes" +msgstr "Время истечения AKILL'а по-умолчанию : %d минут" + +#: modules/commands/os_stats.cpp:74 +msgid "Default AKILL expiry time: 1 day" +msgstr "Время истечения AKILL'а по-умолчанию : 1 день" + +#: modules/commands/os_stats.cpp:78 +msgid "Default AKILL expiry time: 1 hour" +msgstr "Время истечения AKILL'а по-умолчанию : 1 час" + +#: modules/commands/os_stats.cpp:82 +msgid "Default AKILL expiry time: 1 minute" +msgstr "Время истечения AKILL'а по-умолчанию : 1 минута" + +#: modules/commands/os_stats.cpp:84 +msgid "Default AKILL expiry time: No expiration" +msgstr "Время истечения AKILL'а по-умолчанию : никогда" + +#: modules/commands/os_stats.cpp:92 +#, c-format +msgid "Default SNLINE expiry time: %d days" +msgstr "Время истечения SNLINE'а по-умолчанию : %d дней" + +#: modules/commands/os_stats.cpp:96 +#, c-format +msgid "Default SNLINE expiry time: %d hours" +msgstr "Время истечения SNLINE'а по-умолчанию : %d часов" + +#: modules/commands/os_stats.cpp:100 +#, c-format +msgid "Default SNLINE expiry time: %d minutes" +msgstr "Время истечения SNLINE'а по-умолчанию : %d минут" + +#: modules/commands/os_stats.cpp:94 +msgid "Default SNLINE expiry time: 1 day" +msgstr "Время истечения SNLINE'а по-умолчанию : 1 день" + +#: modules/commands/os_stats.cpp:98 +msgid "Default SNLINE expiry time: 1 hour" +msgstr "Время истечения SNLINE'а по-умолчанию : 1 час" + +#: modules/commands/os_stats.cpp:102 +msgid "Default SNLINE expiry time: 1 minute" +msgstr "Время истечения SNLINE'а по-умолчанию : 1 минута" + +#: modules/commands/os_stats.cpp:104 +msgid "Default SNLINE expiry time: No expiration" +msgstr "Время истечения SNLINE'а по-умолчанию : никогда" + +#: modules/commands/os_stats.cpp:112 +#, c-format +msgid "Default SQLINE expiry time: %d days" +msgstr "Время истечения SQGLINE'а по-умолчанию: %d дней" + +#: modules/commands/os_stats.cpp:116 +#, c-format +msgid "Default SQLINE expiry time: %d hours" +msgstr "Время истечения SQGLINE'а по-умолчанию: %d часов" + +#: modules/commands/os_stats.cpp:120 +#, c-format +msgid "Default SQLINE expiry time: %d minutes" +msgstr "Время истечения SQGLINE'а по-умолчанию: %d минут" + +#: modules/commands/os_stats.cpp:114 +msgid "Default SQLINE expiry time: 1 day" +msgstr "Время истечения SQGLINE'а по-умолчанию: 1 день" + +#: modules/commands/os_stats.cpp:118 +msgid "Default SQLINE expiry time: 1 hour" +msgstr "Время истечения SQGLINE'а по-умолчанию: 1 час" + +#: modules/commands/os_stats.cpp:122 +msgid "Default SQLINE expiry time: 1 minute" +msgstr "Время истечения SQGLINE'а по-умолчанию: 1 минута" + +#: modules/commands/os_stats.cpp:124 +msgid "Default SQLINE expiry time: No expiration" +msgstr "Время истечения SQGLINE'а по-умолчанию: никогда" + +#: modules/commands/os_news.cpp:351 +#, fuzzy +msgid "Define messages to be randomly shown to users at logon" +msgstr " LOGONNEWS Управление списком новостей при подключении" + +#: modules/commands/os_news.cpp:297 +#, fuzzy +msgid "Define messages to be shown to users at logon" +msgstr " LOGONNEWS Управление списком новостей при подключении" + +#: modules/commands/os_news.cpp:324 +#, fuzzy +msgid "Define messages to be shown to users who oper" +msgstr " OPERNEWS Управление списком опер-новостей" + +#: modules/commands/ms_del.cpp:44 +#, fuzzy +msgid "Delete a memo or memos" +msgstr " DEL Удаление мемо-сообщений" + +#: modules/commands/hs_del.cpp:19 +#, fuzzy +msgid "Delete the vhost of another user" +msgstr " DEL Удаление виртуального хоста" + +#: modules/commands/cs_xop.cpp:302 +#, fuzzy, c-format +msgid "Deleted %d entries from %s %s list." +msgstr "Удалено %d записей из списка AOP'ов канала %s." + +#: modules/commands/cs_access.cpp:277 +#, c-format +msgid "Deleted %d entries from %s access list." +msgstr "Удалено %d записей из списка доступа канала %s." + +#: modules/commands/cs_akick.cpp:228 +#, c-format +msgid "Deleted %d entries from %s autokick list." +msgstr "Удалено %d записей из списка актокиков канала %s." + +#: modules/commands/bs_badwords.cpp:170 +#, c-format +msgid "Deleted %d entries from %s bad words list." +msgstr "Удалено %d записей из списка плохих слов канала %s." + +#: modules/commands/os_session.cpp:149 +#, c-format +msgid "Deleted %d entries from session-limit exception list." +msgstr "Удалено %d записей из списка исключений лимита сессий." + +#: modules/commands/os_sxline.cpp:32 +#, fuzzy, c-format +msgid "Deleted %d entries from the %s list." +msgstr "Удалено %d записей из списка AOP'ов канала %s." + +#: modules/commands/os_akill.cpp:33 +#, c-format +msgid "Deleted %d entries from the AKILL list." +msgstr "Удалено %d записей из списка AKILL'ов." + +#: modules/commands/cs_access.cpp:275 +#, c-format +msgid "Deleted 1 entry from %s access list." +msgstr "Удалена 1 запись из списка доступа канала %s." + +#: modules/commands/cs_akick.cpp:226 +#, c-format +msgid "Deleted 1 entry from %s autokick list." +msgstr "Удалена 1 запись из списка автокиков канала %s." + +#: modules/commands/bs_badwords.cpp:168 +#, c-format +msgid "Deleted 1 entry from %s bad words list." +msgstr "Удалена 1 запись из списка плохих слов канала %s." + +#: modules/commands/os_session.cpp:147 +msgid "Deleted 1 entry from session-limit exception list." +msgstr "Удалена 1 запись из списка исключений лимита сессий." + +#: modules/commands/os_sxline.cpp:30 +#, fuzzy, c-format +msgid "Deleted 1 entry from the %s list." +msgstr "Удалена 1 запись из спика AKILL'ов." + +#: modules/commands/os_akill.cpp:31 +msgid "Deleted 1 entry from the AKILL list." +msgstr "Удалена 1 запись из спика AKILL'ов." + +#: modules/commands/os_info.cpp:208 +#, fuzzy, c-format +msgid "Deleted info from %s." +msgstr "Удалена 1 запись из спика AKILL'ов." + +#: modules/commands/cs_xop.cpp:300 +#, fuzzy, c-format +msgid "Deleted one entry from %s %s list." +msgstr "Удалена 1 запись из списка AOP'ов канала %s." + +#: modules/commands/ms_del.cpp:129 +#, fuzzy +msgid "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Синтаксис: DEL [#канал] {номер | список_записей | LAST | ALL}\n" +"\n" +"Позволяет удалить указанное сообщение. В зависимости от указанного\n" +"параметра, вы можете удалить сразу несколько сообщений или целый\n" +"диапазон сообщений (см. пример ниже).\n" +"\n" +"Параметр LAST позволяет удалить последнее полученное сообщение.\n" +"Параметр ALL позволяет полностью очистить список сообщений.\n" +"\n" +"Примеры:\n" +"\n" +" DEL 1\n" +" удалит сообщение под номером 1.\n" +"\n" +" DEL 2-5,7-9\n" +" удалит все сообщения с 2-го по 5-ое и с 7-го по 9-ое." + +#: modules/commands/hs_del.cpp:48 +#, fuzzy +msgid "" +"Deletes the vhost assigned to the given nick from the\n" +"database." +msgstr "" +"Синтаксис: DEL <ник>\n" +"\n" +"Удаляет виртуальный хост назначенный указанному нику." + +#: modules/commands/hs_del.cpp:59 +#, fuzzy +msgid "Deletes the vhost for all nicks in a group" +msgstr " DELALL Удаление вирт. хоста у всех ников указанной группы" + +#: modules/commands/hs_del.cpp:93 +#, fuzzy +msgid "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." +msgstr "" +"Синтаксис: DELALL <ник>.\n" +"\n" +"Удаляет виртуальные хосты у всех ников указанной группы." + +#: modules/commands/os_dns.cpp:653 +#, c-format +msgid "Depooled %s." +msgstr "" + +#: modules/commands/cs_access.cpp:799 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_list.cpp:75 modules/commands/cs_info.cpp:53 +#, fuzzy +msgid "Description" +msgstr "Описание канала %s изменено на %s." + +#: modules/commands/cs_set.cpp:239 +#, c-format +msgid "Description of %s changed to %s." +msgstr "Описание канала %s изменено на %s." + +#: modules/commands/cs_set.cpp:245 +#, fuzzy, c-format +msgid "Description of %s unset." +msgstr "Описание канала %s изменено на %s." + +#: modules/commands/bs_kick.cpp:1115 modules/commands/bs_info.cpp:90 +#, fuzzy +msgid "Disabled" +msgstr "Режим %s: включен." + +#: modules/commands/cs_suspend.cpp:134 +#, fuzzy +msgid "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." +msgstr "" +"Синтаксис: SUSPEND #канал [причина]\n" +"\n" +"Приостанавливает любую активность указанного канала (замораживает).\n" +"В режиме саспенда, на канал не действуют условия истечения регистрации\n" +"по времени, канал невозможно использовать или удалить. Единственное,\n" +"что владелец все еще может - это изменять настройки своего канала.\n" +"Эффект \"заморозки\" отменяется путем использования команды UNSUSPEND,\n" +"которая полностью восстанавливает активность канала со всеми его\n" +"настройками.\n" +"\n" +"Примечание: в зависимости от настроек сервисов, причина может\n" +"быть параметром как опциональным, так и необходимым." + +#: modules/commands/hs_request.cpp:337 +#, fuzzy, c-format +msgid "Displayed %d records (%d total)." +msgstr "Конец списка хостов, записей насчитано: %d" + +#: modules/commands/hs_list.cpp:122 +#, fuzzy, c-format +msgid "Displayed all records (count: %d)." +msgstr "Конец списка хостов, записей насчитано: %d" + +#: modules/commands/hs_list.cpp:120 +#, fuzzy, c-format +msgid "Displayed records from %d to %d." +msgstr "Конец списка записей с %d по %d" + +#: modules/commands/hs_list.cpp:116 +#, fuzzy, c-format +msgid "Displayed records matching key %s (count: %d)." +msgstr "Конец списка хостов по маске %s, записей насчитано: %d" + +#: modules/commands/ns_info.cpp:19 +#, fuzzy +msgid "Displays information about a given nickname" +msgstr " INFO Информация о каком-либо нике" + +#: modules/commands/ns_info.cpp:125 +#, fuzzy +msgid "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." +msgstr "" +"Синтаксис: INFO ник\n" +"\n" +"Запрашивает у сервисов информацию об указанном нике. В частности\n" +"будут показаны: реальное имя владельца (realname), его последняя\n" +"хостмаска, когда он последний раз был в IRC под этим ником. Если вы\n" +"запрашиваете информацию относительно своего ника, вы можете указать\n" +"параметр ALL, чтобы получить всю доступную информацию, в том числе\n" +"и ту, которая скрыта." + +#: modules/commands/ms_info.cpp:19 +#, fuzzy +msgid "Displays information about your memos" +msgstr " INFO Информация о кол-ве сообщений и настройках оповещения" + +#: modules/commands/hs_list.cpp:19 +#, fuzzy +msgid "Displays one or more vhost entries" +msgstr " LIST Вывод списка всех виртуальных хостов" + +#: modules/extra/stats/cs_fantasy_top.cpp:50 +#, fuzzy +msgid "Displays the top 10 users of a channel" +msgstr " FOUNDER смена владельца канала" + +#: modules/extra/stats/cs_fantasy_top.cpp:73 +msgid "Displays the top 10 users of the network" +msgstr "" + +#: modules/extra/stats/cs_fantasy_top.cpp:38 +#, fuzzy +msgid "Displays the top 3 users of a channel" +msgstr " FOUNDER смена владельца канала" + +#: modules/extra/stats/cs_fantasy_top.cpp:62 +msgid "Displays the top 3 users of the network" +msgstr "" + +#: modules/commands/help.cpp:33 +#, fuzzy +msgid "Displays this list and give information about commands" +msgstr " INFO Информация о кол-ве сообщений и настройках оповещения" + +#: modules/extra/stats/cs_fantasy_stats.cpp:39 +msgid "Displays your Channel Stats" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:51 +msgid "Displays your Global Stats" +msgstr "" + +#: modules/commands/bs_kick.cpp:1463 +msgid "Don't use AMSGs!" +msgstr "" + +#: modules/commands/bs_kick.cpp:1266 +msgid "Don't use bolds on this channel!" +msgstr "Использование жирного шрифта у нас тут не приветствуется!" + +#: modules/commands/bs_kick.cpp:1274 +msgid "Don't use colors on this channel!" +msgstr "Использование цветов у нас тут не приветствуется!" + +#: modules/commands/bs_kick.cpp:1290 +msgid "Don't use italics on this channel!" +msgstr "Don't use italics on this channel!" + +#: modules/commands/bs_kick.cpp:1282 +msgid "Don't use reverses on this channel!" +msgstr "Использование инверсии у нас тут не приветствуется!" + +#: modules/commands/bs_kick.cpp:1408 +#, c-format +msgid "Don't use the word \"%s\" on this channel!" +msgstr "Слово %s запрещено на этом канале!" + +#: modules/commands/bs_kick.cpp:1298 +msgid "Don't use underlines on this channel!" +msgstr "Использование подчеркиваний у нас тут не приветствуется!" + +#: modules/commands/ns_drop.cpp:61 +msgid "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." +msgstr "" + +#: modules/commands/ns_set.cpp:513 +#, c-format +msgid "E-mail address for %s changed to %s." +msgstr "Email-адрес для %s изменен на %s." + +#: modules/commands/ns_set.cpp:519 +#, c-format +msgid "E-mail address for %s unset." +msgstr "Email-адрес для %s удален." + +#: src/mail.cpp:80 +#, c-format +msgid "E-mail for %s is invalid." +msgstr "Email-адрес для %s некорректен." + +#: modules/commands/os_news.cpp:309 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Синтаксис: LOGONNEWS ADD текст\n" +" LOGONNEWS DEL {номер | ALL}\n" +" LOGONNEWS LIST\n" +"\n" +"Позволяет управлять списком новостей, которые будут автоматически\n" +"выдаваться пользователю сразу же, как только он подключится к сети.\n" +"Стоит заметить, что во избежание флуда пользователь получит только\n" +"%d новость(и), так что если у вас в списке их больше - показаны\n" +"будут только последние из них. Значение NewsCount, отвечающее за\n" +"одновременно посылаемое кол-во новостей, указывается в services.conf\n" +"\n" +"Команда LOGONNEWS ADD позволяет добавить новость в список.\n" +"\n" +"Команда LOGONNEWS DEL позволяет удалить новость из списка. В\n" +"качестве параметра вы можете указать номер новости - что бы удалить\n" +"одну новость, или ALL - что бы очистить список новостей полностью.\n" +"\n" +"LOGONNEWS may only be used by Services Operators." + +#: modules/commands/os_news.cpp:336 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Синтаксис: OPERNEWS ADD текст\n" +" OPERNEWS DEL {номер | ALL}\n" +" OPERNEWS LIST\n" +"\n" +"Позволяет управлять списком новостей для IRC-Операторов. Как только\n" +"пользователь получит статус IRC-оператора (использовав команду /OPER),\n" +"данные сообщения будут ему отправлены автоматически.\n" +"Стоит заметить, что во избежание флуда пользователь получит только\n" +"%d новость(и), так что если у вас в списке их больше - показаны\n" +"будут только последние из них. Значение NewsCount, отвечающее за\n" +"одновременно посылаемое кол-во новостей, указывается в services.conf\n" +"\n" +"Команда OPERNEWS ADD позволяет добавить новость в список.\n" +"\n" +"Команда OPERNEWS DEL позволяет удалить новость из списка. В\n" +"качестве параметра вы можете указать номер новости - что бы удалить\n" +"одну новость, или ALL - что бы очистить список новостей полностью.\n" +"\n" +"OPERNEWS may only be used by Services Operators." + +#: modules/commands/os_news.cpp:363 +#, fuzzy +msgid "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." +msgstr "" +"Синтаксис: RANDOMNEWS ADD текст\n" +" RANDOMNEWS DEL {текст | ALL}\n" +" RANDOMNEWS LIST\n" +"\n" +"Позволяет управлять списком случайных новостей.\n" +"Как только пользователь успешно подключится к IRC-сети, одна (и\n" +"только одна) из случайных новостей будет выбрана сервисами наугад и\n" +"отправлена ему.\n" +"\n" +"Команда RANDOMNEWS ADD позволяет добавить новость в список.\n" +"\n" +"Команда RANDOMNEWS DEL позволяет удалить новость из списка. В\n" +"качестве параметра вы можете указать номер новости - что бы удалить\n" +"одну новость, или ALL - что бы очистить список новостей полностью.\n" +"\n" +"RANDOMNEWS may only be used by Services Operators." + +#: modules/commands/ns_info.cpp:98 +#, fuzzy +msgid "Email address" +msgstr "Email-адрес.............: %s" + +#: modules/commands/ns_getemail.cpp:41 +#, fuzzy, c-format +msgid "Email matched: %s (%s) to %s." +msgstr "Найдено соответствие для ника %s: %s." + +#: modules/fantasy.cpp:19 +msgid "Enable fantaisist commands" +msgstr "" + +#: modules/commands/greet.cpp:19 +msgid "Enable greet messages" +msgstr "" + +#: modules/commands/ns_set.cpp:568 +msgid "Enable or disable keep modes" +msgstr "" + +#: modules/commands/bs_kick.cpp:1114 modules/commands/bs_info.cpp:89 +#, fuzzy +msgid "Enabled" +msgstr "Режим %s: включен." + +#: modules/commands/cs_set.cpp:124 +#, fuzzy, c-format +msgid "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." +msgstr "" +"Синтаксис: %s #канал SECUREOPS {ON | OFF}\n" +"\n" +"Активирует/деактивирует режим ограничения на получение статуса\n" +"оператора канала. Данный режим позволяет запретить возможность\n" +"получения статуса опа тем пользователям, которые не присутствуют\n" +"в списке доступа канала или права которых не соответствуют\n" +"получаемому статусу." + +#: modules/commands/cs_set.cpp:388 +#, fuzzy +msgid "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." +msgstr "" +"Синтаксис: %s #канал KEEPTOPIC {ON | OFF}\n" +"\n" +"Позволяет активировать/деактивировать опцию хранения топика на\n" +"канале. При включенном режиме хранения топика, текст топика канала\n" +"будет сохраняться в базе данных %s после того, как последний\n" +"пользователь покинет канал, и автоматически восстанавливаться сразу\n" +"же, как только канал снова станет активным (то есть, на него опять\n" +"кто-либо зайдет)." + +#: modules/commands/ns_set.cpp:643 +msgid "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." +msgstr "" + +#: modules/commands/ns_set.cpp:618 +msgid "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." +msgstr "" + +#: modules/commands/cs_set.cpp:733 +#, fuzzy +msgid "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." +msgstr "" +"Синтаксис: %s #канал SECURE {ON | OFF}\n" +"\n" +"Активирует/деактивирует режим безопасности для канала.\n" +"Когда SECURE включено, только пользователи с зарегистрированными\n" +"никами, проидентифицировавшиеся к ним через пароль и включенные в\n" +"список доступа канала, смогут запросить статус на канале с помощью\n" +"%s.\n" +"Если безопасность отключена, пользователи, прописанные на канале,\n" +"смогут запросить статус даже если имеют авторизацию к своему нику\n" +"всего лишь через список масок на %s." + +#: modules/commands/cs_set.cpp:932 +#, fuzzy +msgid "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." +msgstr "" +"Синтаксис: %s #канал SIGNKICK {ON | LEVEL | OFF}\n" +"\n" +"Включает или выключает опцию \"подписанных киков\" на канале.\n" +"Активирование режима SIGNKICK заставит %s автоматически\n" +"добавлять к причине кика ник того, кто использовал команду KICK.\n" +"\n" +"В качестве дополнительного параметра для опции SIGNKICK вы можете\n" +"указать значение LEVEL. Это позволит более тонко лимитировать\n" +"действие данного режима, при условии конечно, что вы используете\n" +"систему LEVELS на канале (см. /msg %s HELP LEVELS для\n" +"более подробной информации)." + +#: modules/commands/cs_set.cpp:452 +#, fuzzy, c-format +msgid "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." +msgstr "" +"Синтаксис: %s #канал PEACE {ON | OFF}\n" +"\n" +"Активирует/деактивирует опцию спокойствия на канале. Данный режим\n" +"позволяет запретить использование таких команд %s'а как BAN,\n" +"OP, DEOP, KICK и т. д. относительно тех, кто выше или равен по\n" +"статусу относительно использующего.\n" +"Примечание: тем не менее любой, имеющий доступ к этим командам,\n" +"сможет использовать их относительно себя." + +#: modules/commands/cs_list.cpp:232 +msgid "Enables or disables the private option for a channel." +msgstr "" + +#: modules/commands/cs_set.cpp:671 +#, fuzzy +msgid "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." +msgstr "" +"Синтаксис: %s #канал RESTRICTED {ON | OFF}\n" +"\n" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." + +#: modules/commands/cs_set.cpp:796 +#, fuzzy +msgid "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." +msgstr "" +"Синтаксис: %s #канал SECUREFOUNDER {ON | OFF}\n" +"\n" +"Активирует/деактивирует режим безопасности владельца на канале.\n" +"Активирование SECUREFOUNDER позволяет вам ограничить возможность\n" +"удаления канала, изменения его пароля, владельца или наследника до\n" +"реального владельца, прописанного в графе Founder (Владелец канала).\n" +"(и не важно, кто там идентифицировался к каналу через %s ID)." + +#: modules/commands/cs_set.cpp:860 +#, fuzzy +msgid "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." +msgstr "" +"Синтаксис: %s #канал SECUREOPS {ON | OFF}\n" +"\n" +"Активирует/деактивирует режим ограничения на получение статуса\n" +"оператора канала. Данный режим позволяет запретить возможность\n" +"получения статуса опа тем пользователям, которые не присутствуют\n" +"в списке доступа канала или права которых не соответствуют\n" +"получаемому статусу." + +#: modules/commands/cs_topic.cpp:70 +#, fuzzy, c-format +msgid "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." +msgstr "" +"Синтаксис: %s #канал KEEPTOPIC {ON | OFF}\n" +"\n" +"Позволяет активировать/деактивировать опцию хранения топика на\n" +"канале. При включенном режиме хранения топика, текст топика канала\n" +"будет сохраняться в базе данных %s после того, как последний\n" +"пользователь покинет канал, и автоматически восстанавливаться сразу\n" +"же, как только канал снова станет активным (то есть, на него опять\n" +"кто-либо зайдет)." + +#: modules/commands/cs_set.cpp:592 +#, fuzzy, c-format +msgid "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." +msgstr "" +"Syntax: %s channel PERSIST {ON | OFF}\n" +"Enables or disables the persistant channel setting.\n" +"When persistant is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +"\n" +"If your IRCd does not a permanent (persistant) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +"\n" +"If this network does not have BotServ enabled and does\n" +"not have a permanent channel mode, ChanServ will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +"\n" +"If your IRCd has a permanent (persistant) channel mode\n" +"and is is set or unset (for any reason, including MLOCK),\n" +"persist is automatically set and unset for the channel aswell.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." + +#: modules/commands/os_akill.cpp:331 +#, fuzzy +msgid "End of AKILL list." +msgstr "Конец списка пользователей." + +#: modules/commands/cs_access.cpp:444 +#, fuzzy +msgid "End of access list" +msgstr "Конец списка доступа." + +#: modules/commands/cs_flags.cpp:347 +#, fuzzy, c-format +msgid "End of access list - %d/%d entries shown." +msgstr "Конец списка - %d/%d записей показано." + +#: modules/commands/cs_flags.cpp:345 +msgid "End of access list." +msgstr "Конец списка доступа." + +#: modules/commands/cs_akick.cpp:379 +#, fuzzy +msgid "End of autokick list" +msgstr "Конец списка доступа." + +#: modules/commands/bs_badwords.cpp:257 +#, fuzzy +msgid "End of bad words list." +msgstr "Конец списка пользователей." + +#: modules/commands/os_list.cpp:100 +#, fuzzy, c-format +msgid "End of channel list. %u channels shown." +msgstr "Конец списка - %d/%d записей показано." + +#: modules/commands/os_config.cpp:117 +msgid "End of configuration." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:134 +#, fuzzy +msgid "End of entry message list." +msgstr "Конец списка пользователей." + +#: modules/commands/os_forbid.cpp:407 +#, fuzzy, c-format +msgid "End of forbid list - %d/%d entries shown." +msgstr "Конец списка - %d/%d записей показано." + +#: modules/commands/os_forbid.cpp:405 +#, fuzzy +msgid "End of forbid list." +msgstr "Конец списка пользователей." + +#: modules/commands/ns_alist.cpp:119 +#, fuzzy, c-format +msgid "End of list - %d channels shown." +msgstr "Конец списка - %d/%d записей показано." + +#: modules/commands/ns_list.cpp:131 modules/commands/cs_list.cpp:130 +#, c-format +msgid "End of list - %d/%d matches shown." +msgstr "Конец списка - %d/%d записей показано." + +#: modules/commands/os_news.cpp:176 +#, fuzzy +msgid "End of news list." +msgstr "Конец списка пользователей." + +#: modules/commands/os_list.cpp:235 +#, fuzzy, c-format +msgid "End of users list. %u users shown." +msgstr "Конец списка - %d/%d записей показано." + +#: modules/commands/cs_enforce.cpp:227 +msgid "Enforce various channel modes and set options" +msgstr "" + +#: modules/commands/cs_enforce.cpp:263 +msgid "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." +msgstr "" + +#: src/language.cpp:43 modules/commands/ns_set.cpp:836 +#: modules/commands/ns_set.cpp:856 modules/commands/ns_set.cpp:891 +msgid "English" +msgstr "Русский" + +#: modules/commands/cs_entrymsg.cpp:170 +#, fuzzy, c-format +msgid "Entry message %i for %s deleted." +msgstr "Приветствие для %s удалено." + +#: modules/commands/cs_entrymsg.cpp:177 +#, fuzzy, c-format +msgid "Entry message %s not found on channel %s." +msgstr "FANTASY-режим для канала %s активирован." + +#: modules/commands/cs_entrymsg.cpp:147 +#, fuzzy, c-format +msgid "Entry message added to %s" +msgstr "Приветствие для %s изменено на %s." + +#: modules/commands/cs_entrymsg.cpp:109 modules/commands/cs_entrymsg.cpp:158 +#, fuzzy, c-format +msgid "Entry message list for %s is empty." +msgstr "Список доступа для %s пуст." + +#: modules/commands/cs_entrymsg.cpp:113 +#, fuzzy, c-format +msgid "Entry message list for %s:" +msgstr "Список доступа для %s:" + +#: modules/commands/cs_entrymsg.cpp:187 +#, fuzzy, c-format +msgid "Entry messages for %s have been cleared." +msgstr "Все сообщения канала %s были удалены." + +#: modules/commands/os_reload.cpp:39 +#, fuzzy, c-format +msgid "Error reloading configuration file: %s" +msgstr " RELOAD Перезагрузка конфигурационного файла сервисов" + +#: include/language.h:125 +#, c-format +msgid "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." +msgstr "" + +#: include/language.h:124 +#, c-format +msgid "" +"Error! The vHost is too long, please use a hostname shorter than %d " +"characters." +msgstr "" + +#: modules/commands/ns_cert.cpp:325 +msgid "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." +msgstr "" + +#: modules/commands/os_session.cpp:358 +#, c-format +msgid "Exception for %s has been updated to %d." +msgstr "Лимит сессий для записи вида %s был изменен на %d." + +#: modules/pseudoclients/chanserv.cpp:465 +#: modules/pseudoclients/nickserv.cpp:557 +#: modules/pseudoclients/nickserv.cpp:562 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_session.cpp:514 modules/commands/ns_group.cpp:327 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Expires" +msgstr "Регистрация истекает....: %s" + +#: src/xline.cpp:397 +#, fuzzy, c-format +msgid "Expiry and reason updated for %s." +msgstr "Лимит сессий для записи вида %s был изменен на %d." + +#: src/xline.cpp:400 +#, fuzzy, c-format +msgid "Expiry for %s updated." +msgstr "Срок истечения записи %s успешно изменен." + +#: modules/fantasy.cpp:214 +msgid "Fantasy" +msgstr "FANTASY-режим" + +#: modules/fantasy.cpp:60 +#, fuzzy, c-format +msgid "Fantasy mode is now off on channel %s." +msgstr "FANTASY-режим для канала %s активирован." + +#: modules/fantasy.cpp:52 +#, fuzzy, c-format +msgid "Fantasy mode is now on on channel %s." +msgstr "FANTASY-режим для канала %s активирован." + +#: modules/commands/cs_status.cpp:19 +#, fuzzy +msgid "Find a user's status on a channel" +msgstr " DEOWNER Снимает с вас статус владельца канала" + +#: modules/commands/ns_cert.cpp:192 +#, fuzzy, c-format +msgid "Fingerprint %s already present on %s's certificate list." +msgstr "Маска вида %s уже присутствует в вашем списке доступа." + +#: modules/commands/ns_cert.cpp:198 +#, fuzzy, c-format +msgid "Fingerprint %s is already in use." +msgstr "You are already in %s! " + +#: modules/commands/cs_flags.cpp:301 +msgid "Flags" +msgstr "" + +#: modules/commands/cs_flags.cpp:286 +#, fuzzy, c-format +msgid "Flags for %s on %s set to +%s" +msgstr "Уровень доступа для %s на канале %s изменен на %d." + +#: modules/commands/cs_flags.cpp:341 +#, fuzzy, c-format +msgid "Flags list for %s" +msgstr "Список доступа для %s:" + +#: modules/commands/bs_kick.cpp:1161 modules/commands/bs_kick.cpp:1163 +#: modules/commands/bs_kick.cpp:1166 +#, fuzzy +msgid "Flood kicker" +msgstr "Цензор флуда.........: %s" + +#: modules/commands/os_forbid.cpp:421 +msgid "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." +msgstr "" + +#: modules/commands/os_forbid.cpp:354 +#, fuzzy +msgid "Forbid list is empty." +msgstr "Список игнорируемых ников пуст." + +#: modules/commands/os_forbid.cpp:396 +#, fuzzy +msgid "Forbid list:" +msgstr "Список ботов:" + +#: modules/commands/os_forbid.cpp:348 +#, c-format +msgid "Forbid on %s was not found." +msgstr "" + +#: modules/commands/os_forbid.cpp:156 +msgid "Forbid usage of nicknames, channels, and emails" +msgstr "" + +#: modules/commands/os_update.cpp:19 +#, fuzzy +msgid "Force the Services databases to be updated immediately" +msgstr " UPDATE Обновление баз данных сервисов (сохранение на диск)" + +#: modules/commands/os_svs.cpp:19 +#, fuzzy +msgid "Forcefully change a user's nickname" +msgstr " SVSNICK Принудительное изменение ника пользователя сети" + +#: modules/commands/os_svs.cpp:68 +#, fuzzy +msgid "Forcefully changes a user's nickname from nick to newnick." +msgstr "" +"Синтаксис: SVSNICK ник новый_ник\n" +"\n" +"Позволяет принудительно изменить указанный ник на новый_ник." + +#: modules/commands/os_svs.cpp:78 +#, fuzzy +msgid "Forcefully join a user to a channel" +msgstr " SVSNICK Принудительное изменение ника пользователя сети" + +#: modules/commands/os_svs.cpp:112 +#, fuzzy +msgid "Forcefully join a user to a channel." +msgstr " SVSNICK Принудительное изменение ника пользователя сети" + +#: modules/commands/os_svs.cpp:122 +#, fuzzy +msgid "Forcefully part a user from a channel" +msgstr " KICK Кикнуть пользователя с канала посредством сервисов" + +#: modules/commands/os_svs.cpp:160 +#, fuzzy +msgid "Forcefully part a user from a channel." +msgstr " KICK Кикнуть пользователя с канала посредством сервисов" + +#: modules/commands/ns_alist.cpp:64 modules/commands/cs_info.cpp:47 +#, fuzzy +msgid "Founder" +msgstr "Безопасность владельца" + +#: modules/commands/cs_set.cpp:315 +#, fuzzy, c-format +msgid "Founder of %s changed to %s." +msgstr "Все права на владение каналом %s успешно переданы пользователю %s." + +#: modules/commands/ns_getpass.cpp:41 +msgid "GETPASS command unavailable because encryption is in use." +msgstr "Команда GETPASS недоступна, так как включено шифрование паролей." + +#: modules/commands/ns_recover.cpp:84 +msgid "Ghost with your nick has been killed." +msgstr "Сессия с вашим зависшим ником успешно закрыта." + +#: modules/commands/os_oline.cpp:19 +#, fuzzy +msgid "Give Operflags to a certain user" +msgstr " OLINE Установка оперфлагов указанному пользователю сети" + +#: modules/commands/cs_mode.cpp:905 +#, c-format +msgid "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." +msgstr "" + +#: modules/commands/cs_mode.cpp:888 +#, fuzzy, c-format +msgid "Gives you or the specified nick %s status on a channel" +msgstr " OWNER Запрос статуса владельца на канале" + +#: modules/commands/greet.cpp:206 modules/commands/greet.cpp:212 +msgid "Greet" +msgstr "Приветствия" + +#: src/access.cpp:38 +#, fuzzy +msgid "Greet message displayed on join" +msgstr "Приветствие для %s изменено на %s." + +#: modules/commands/greet.cpp:112 +#, c-format +msgid "Greet message for %s changed to %s." +msgstr "Приветствие для %s изменено на %s." + +#: modules/commands/greet.cpp:118 +#, c-format +msgid "Greet message for %s unset." +msgstr "Приветствие для %s удалено." + +#: modules/commands/greet.cpp:60 +#, fuzzy, c-format +msgid "Greet mode is now off on channel %s." +msgstr "Режим приветствий для канала %s активирован." + +#: modules/commands/greet.cpp:52 +#, fuzzy, c-format +msgid "Greet mode is now on on channel %s." +msgstr "Режим приветствий для канала %s активирован." + +#: modules/commands/ns_resetpass.cpp:21 +#, fuzzy +msgid "Helps you reset lost passwords" +msgstr " RESETPASS Helps you reset lost passwords" + +#: modules/commands/ns_info.cpp:141 +#, fuzzy +msgid "Hide certain pieces of nickname information" +msgstr " HIDE скрытие различной информации о вашем нике" + +#: modules/commands/cs_list.cpp:180 +#, fuzzy +msgid "Hide channel from the LIST command" +msgstr " PRIVATE скрытие канала в списке каналов выводимых по LIST" + +#: modules/commands/os_session.cpp:192 +msgid "Host" +msgstr "" + +#: modules/commands/os_session.cpp:207 +#, c-format +msgid "Hosts with at least %d sessions:" +msgstr "Список хостов с количеством сессий %d и более:" + +#: modules/commands/cs_seen.cpp:207 +#, c-format +msgid "I don't know who %s is." +msgstr "" + +#: modules/commands/cs_seen.cpp:253 +#, fuzzy, c-format +msgid "I've never seen %s on this channel." +msgstr "Использование инверсии у нас тут не приветствуется!" + +#: modules/commands/os_sxline.cpp:203 modules/commands/os_akill.cpp:360 +msgid "ID" +msgstr "" + +#: modules/commands/os_oper.cpp:72 +msgid "INFO [type]" +msgstr "" + +#: modules/commands/os_dns.cpp:218 +msgid "IP" +msgstr "" + +#: modules/commands/os_dns.cpp:500 +#, fuzzy, c-format +msgid "IP %s already exists for %s." +msgstr "Бот с ником %s уже существует." + +#: modules/commands/os_dns.cpp:562 +#, fuzzy, c-format +msgid "IP %s does not exist for %s." +msgstr "Бот с ником %s уже существует." + +#: modules/commands/ns_identify.cpp:65 +#, fuzzy +msgid "Identify yourself with your password" +msgstr " IDENTIFY Идентификация к нику в качестве владельца" + +#: modules/pseudoclients/nickserv.cpp:205 +#: modules/pseudoclients/nickserv.cpp:211 +#, fuzzy, c-format +msgid "If you do not change within %s, I will change your nick." +msgstr "" +"Если вы не выполните указанные рекомендации, ваш ник будет принудительно " +"изменен в течении 20 секунд." + +#: modules/commands/os_ignore.cpp:333 +msgid "Ignore list has been cleared." +msgstr "Список игнорируемых ников полностью очищен." + +#: modules/commands/os_ignore.cpp:262 +msgid "Ignore list is empty." +msgstr "Список игнорируемых ников пуст." + +#: modules/commands/ms_ignore.cpp:94 +#, fuzzy +msgid "Ignore list:" +msgstr "Список ботов:" + +#: modules/commands/ns_set.cpp:1305 +#, fuzzy +msgid "Immediate protection" +msgstr "Не кикать войсов" + +#: modules/commands/ns_resetpass.cpp:33 +#, fuzzy +msgid "Incorrect email address." +msgstr "Email-адрес.............: %s" + +#: include/language.h:89 +msgid "Incorrect range specified. The correct syntax is #from-to." +msgstr "" + +#: modules/commands/os_modinfo.cpp:19 +#, fuzzy +msgid "Info about a loaded module" +msgstr " MODINFO Информация о загруженном модуле" + +#: modules/commands/bs_info.cpp:54 +#, c-format +msgid "Information for bot %s:" +msgstr "Информация о боте %s:" + +#: include/language.h:108 +#, fuzzy, c-format +msgid "Information for channel %s:" +msgstr "Информация о боте %s:" + +#: modules/commands/os_logsearch.cpp:57 +#, c-format +msgid "Invalid duration %s, using %d days." +msgstr "" + +#: include/language.h:68 +msgid "Invalid expiry time." +msgstr "" + +#: modules/commands/os_session.cpp:346 +#, fuzzy +msgid "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not " +"matched against nicks or usernames." +msgstr "" +"Указана некорректная хостмаска. Только реальный хост, не содержащий ников и " +"идентов пользователей, может быть добавлен в список исключения." + +#: modules/commands/os_logsearch.cpp:73 +#, c-format +msgid "Invalid limit %s, using %d." +msgstr "" + +#: include/language.h:99 +msgid "" +"Invalid passcode has been entered, please check the e-mail again, and retry." +msgstr "" + +#: modules/commands/ns_register.cpp:83 modules/commands/ns_register.cpp:86 +msgid "Invalid passcode." +msgstr "" + +#: modules/commands/os_session.cpp:339 +#, c-format +msgid "" +"Invalid session limit. It must be a valid integer greater than or equal to " +"zero and less than %d." +msgstr "" +"Некорректное значение лимита. Оно должно быть целым числом, больше или " +"равным нулю, и меньше %d." + +#: modules/commands/os_session.cpp:188 +msgid "Invalid threshold value. It must be a valid integer greater than 1." +msgstr "" +"Некорректное значение для порога сессий. В качестве параметра должно быть " +"целое число >1." + +#: modules/commands/os_dns.cpp:591 +msgid "Invalid value for LIMIT. Must be numerical." +msgstr "" + +#: modules/commands/cs_invite.cpp:19 +#, fuzzy +msgid "Invites you or an optionally specified nick into a channel" +msgstr "" +" OP Установка статуса оператора (+o) указанному нику на канале" + +#: modules/commands/bs_kick.cpp:1201 modules/commands/bs_kick.cpp:1203 +#: modules/commands/bs_kick.cpp:1206 +#, fuzzy +msgid "Italics kicker" +msgstr "Italics kicker : %s" + +#: modules/commands/ns_group.cpp:91 +#, fuzzy +msgid "Join a group" +msgstr " GROUP Объединение ников в группы" + +#: modules/commands/cs_set.cpp:1305 modules/commands/ns_set.cpp:1319 +#, fuzzy +msgid "Keep modes" +msgstr "Режим приватных сообщений" + +#: modules/commands/cs_set.cpp:377 modules/commands/ns_set.cpp:603 +#, fuzzy, c-format +msgid "Keep modes for %s is now off." +msgstr "Режим спокойствия для канала %s активирован." + +#: modules/commands/cs_set.cpp:369 modules/commands/ns_set.cpp:597 +#, fuzzy, c-format +msgid "Keep modes for %s is now on." +msgstr "Режим спокойствия для канала %s активирован." + +#: modules/commands/ns_ajoin.cpp:100 +msgid "Key" +msgstr "" + +#: modules/commands/cs_getkey.cpp:50 +#, c-format +msgid "Key for channel %s is %s." +msgstr "Key for channel %s is %s." + +#: modules/commands/os_kick.cpp:19 +#, fuzzy +msgid "Kick a user from a channel" +msgstr " KICK Кикнуть пользователя с канала посредством сервисов" + +#: modules/commands/cs_ban.cpp:217 modules/commands/cs_kick.cpp:116 +#, c-format +msgid "Kicked %d/%d users matching %s from %s." +msgstr "" + +#: modules/commands/cs_kick.cpp:19 +#, fuzzy +msgid "Kicks a specified nick from a channel" +msgstr " KICK Выкидывает указанного пользователя с канала" + +#: modules/commands/cs_kick.cpp:128 +#, fuzzy +msgid "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." +msgstr "" +"Синтаксис: KICK #канал ник [причина]\n" +"\n" +"Выкидывает указанного пользователя с указанного канала.\n" +"\n" +"По-умолчанию, данная команда может быть использована AOP'ами или\n" +"лицами с уровнем доступа 5 и выше." + +#: modules/commands/os_kill.cpp:19 +msgid "Kill a user" +msgstr "" + +#: modules/commands/cs_enforce.cpp:217 +msgid "LIMIT enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:221 +#, c-format +msgid "LIMIT enforced on %s, %d users removed." +msgstr "" + +#: modules/commands/os_session.cpp:246 +msgid "LIST threshold" +msgstr "" + +#: modules/commands/os_sxline.cpp:427 modules/commands/os_sxline.cpp:661 +#: modules/commands/os_akill.cpp:388 +#, fuzzy +msgid "LIST [mask | list | id]" +msgstr "LIST [#канал] [список_записей | NEW]" + +#: modules/commands/os_session.cpp:525 +#, fuzzy +msgid "LIST [mask | list]" +msgstr "LIST [#канал] [список_записей | NEW]" + +#: modules/commands/ns_access.cpp:104 modules/commands/ns_cert.cpp:260 +#: modules/commands/ns_ajoin.cpp:233 +#, fuzzy +msgid "LIST [nickname]" +msgstr "CHECK ник" + +#: modules/commands/os_news.cpp:31 +msgid "LOGONNEWS {ADD|DEL|LIST} [text|num]" +msgstr "LOGONNEWS {ADD|DEL|LIST} [текст|номер]" + +#: modules/commands/ns_set.cpp:834 +msgid "Language changed to English." +msgstr "Язык сервисов изменен на Русский." + +#: modules/commands/ns_set.cpp:836 +#, fuzzy, c-format +msgid "Language for %s changed to %s." +msgstr "Наследником канала %s назначен пользователь %s." + +#: modules/commands/ms_cancel.cpp:72 +#, c-format +msgid "Last memo to %s has been cancelled." +msgstr "Последнее ваше сообщение адресату %s успешно отменено." + +#: modules/commands/ns_info.cpp:95 +#, fuzzy +msgid "Last quit message" +msgstr "Последнее quit-сообщение: %s" + +#: modules/commands/cs_access.cpp:472 modules/commands/ns_info.cpp:92 +#, fuzzy +msgid "Last seen" +msgstr "Последний раз замечен...: %s" + +#: modules/commands/ns_info.cpp:81 modules/commands/ns_info.cpp:86 +#, fuzzy +msgid "Last seen address" +msgstr "Последняя маска.........: %s" + +#: modules/commands/cs_topic.cpp:264 +msgid "Last topic" +msgstr "" + +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_info.cpp:56 +#, fuzzy +msgid "Last used" +msgstr "Последний раз замечен...: %s" + +#: modules/commands/ns_list.cpp:75 +#, fuzzy +msgid "Last usermask" +msgstr "Последний раз замечен...: %s" + +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +#: modules/commands/cs_access.cpp:697 +msgid "Level" +msgstr "" + +#: modules/commands/cs_access.cpp:660 +#, c-format +msgid "Level for %s on channel %s changed to %d." +msgstr "Уровень доступа к %s на канале %s изменен на %d." + +#: modules/commands/cs_access.cpp:658 +#, c-format +msgid "Level for %s on channel %s changed to founder only." +msgstr "Level for %s on channel %s changed to founder only." + +#: modules/commands/cs_access.cpp:643 +#, c-format +msgid "Level must be between %d and %d inclusive." +msgstr "Уровень должен быть числом между %d и %d включительно." + +#: modules/commands/os_dns.cpp:218 modules/commands/os_session.cpp:506 +#: modules/commands/os_session.cpp:514 +msgid "Limit" +msgstr "" + +#: modules/commands/ns_list.cpp:19 +#, fuzzy +msgid "List all registered nicknames that match a given pattern" +msgstr " LIST Список всех зарегистрированных ников по маске" + +#: modules/commands/ns_alist.cpp:24 +#, fuzzy +msgid "List channels you have access on" +msgstr " ALIST Вывод списка каналов, на которых у вас есть доступ" + +#: modules/commands/cs_mode.cpp:341 +#, c-format +msgid "List for mode %c is full." +msgstr "" + +#: modules/commands/os_modinfo.cpp:80 +#, fuzzy +msgid "List loaded modules" +msgstr " MODLIST Список загруженных модулей" + +#: modules/commands/ns_list.cpp:123 modules/commands/cs_list.cpp:72 +#, fuzzy, c-format +msgid "List of entries matching %s:" +msgstr "Список ников в группе %s:" + +#: modules/commands/ns_group.cpp:350 +#, c-format +msgid "List of nicknames in the group of %s:" +msgstr "Список ников в группе %s:" + +#: modules/commands/ns_group.cpp:350 +msgid "List of nicknames in your group:" +msgstr "Список ников в вашей группе:" + +#: modules/commands/ms_list.cpp:19 +#, fuzzy +msgid "List your memos" +msgstr " LIST Список ваших мемо-сообщений" + +#: modules/commands/bs_botlist.cpp:64 +#, fuzzy +msgid "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." +msgstr "" +"Синтаксис: BOTLIST\n" +"\n" +"Выведет список всех доступных для установки ботов." + +#: modules/commands/os_list.cpp:19 +#, fuzzy +msgid "Lists all channel records" +msgstr " CHANLIST Список текущих активных каналов сети" + +#: modules/commands/os_list.cpp:107 +#, fuzzy +msgid "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." +msgstr "" +"Синтаксис: CHANLIST [{маска | ник} [SECRET]]\n" +"\n" +"Выводит список всех активных (на данный момент) каналов сети, вне\n" +"зависимости от того, зарегистрированы они или нет.\n" +"\n" +"В качестве параметра вы можете указать маску имени канала, что бы\n" +"получить только конкретные, совпадающие записи. Если же вы укажите\n" +"ник, будет выведен список всех каналов, на которых находится этот\n" +"пользователь.\n" +"Дополнительный параметр SECRET позволяет получить список каналов\n" +"с режимами +s/+p, совпадающих с указанной символьной маской." + +#: modules/commands/ns_alist.cpp:127 +msgid "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" +msgstr "" + +#: modules/commands/ns_group.cpp:299 +#, fuzzy +msgid "Lists all nicknames in your group" +msgstr "Список ников в вашей группе:" + +#: modules/commands/cs_list.cpp:20 +#, fuzzy +msgid "Lists all registered channels matching the given pattern" +msgstr " LIST Запрос списка всех зарегистрированных каналов" + +#: modules/commands/cs_list.cpp:137 +#, fuzzy +msgid "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." +msgstr "" +"Синтаксис: LIST маска [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]\n" +"\n" +"Показывает список всех зарегистрированных ников, которые совпадают\n" +"с указанной в качестве основного параметра маской. Формат маски:\n" +"ник!идент@хост допустимо использование подстановочных символов.\n" +"Ники, у которых включена опция PRIVATE, будут показаны только\n" +"Администраторам сервисов. Ники с включенным параметром NOEXPIRE\n" +"будут показаны с префиксом !.\n" +"\n" +"В качестве дополнительных опций команды LIST вы можете указать\n" +"FORBIDDEN, SUSPENDED, NOEXPIRE или UNCONFIRMED. Это позволит вам\n" +"получить список ников, отвечающих определенным критериям, таким как:\n" +"FORBIDDEN - ники, запрещенные к использованию, SUSPENDED - ники,\n" +"\"замороженные\" до поры до времени, UNCONFIRMED - ники, регистрация\n" +"которых все еще не подтверждена, и NOEXPIRE - ники, находящиеся в\n" +"режиме \"не-истечения\". Если указаны все четыре опции, то все 4 типа\n" +"ников будут перечислены в списке.\n" +"\n" +"Примеры:\n" +"\n" +" LIST *!joeuser@foo.com\n" +" покажет все ники, маска которых совпадает с joeuser@foo.com\n" +" LIST *Bot*!*@*\n" +" покажет все зарегистрированные ники, которые содержат слово\n" +" Bot (вне зависимости от регистра).\n" +" LIST * NOEXPIRE\n" +" Покажет все зарегистрированные ники у которых включена опция\n" +" NOEXPIRE." + +#: modules/commands/ns_list.cpp:139 +#, fuzzy +msgid "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." +msgstr "" +"Синтаксис: LIST маска [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]\n" +"\n" +"Показывает список всех зарегистрированных ников, которые совпадают\n" +"с указанной в качестве основного параметра маской. Формат маски:\n" +"ник!идент@хост допустимо использование подстановочных символов.\n" +"Ники, у которых включена опция PRIVATE, будут показаны только\n" +"Администраторам сервисов. Ники с включенным параметром NOEXPIRE\n" +"будут показаны с префиксом !.\n" +"\n" +"В качестве дополнительных опций команды LIST вы можете указать\n" +"FORBIDDEN, SUSPENDED, NOEXPIRE или UNCONFIRMED. Это позволит вам\n" +"получить список ников, отвечающих определенным критериям, таким как:\n" +"FORBIDDEN - ники, запрещенные к использованию, SUSPENDED - ники,\n" +"\"замороженные\" до поры до времени, UNCONFIRMED - ники, регистрация\n" +"которых все еще не подтверждена, и NOEXPIRE - ники, находящиеся в\n" +"режиме \"не-истечения\". Если указаны все четыре опции, то все 4 типа\n" +"ников будут перечислены в списке.\n" +"\n" +"Примеры:\n" +"\n" +" LIST *!joeuser@foo.com\n" +" покажет все ники, маска которых совпадает с joeuser@foo.com\n" +" LIST *Bot*!*@*\n" +" покажет все зарегистрированные ники, которые содержат слово\n" +" Bot (вне зависимости от регистра).\n" +" LIST * NOEXPIRE\n" +" Покажет все зарегистрированные ники у которых включена опция\n" +" NOEXPIRE." + +#: modules/commands/os_list.cpp:132 +#, fuzzy +msgid "Lists all user records" +msgstr " USERLIST Список текущих пользователей сети" + +#: modules/commands/os_list.cpp:243 +#, fuzzy +msgid "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only " +"users\n" +"with the +i flag will be listed." +msgstr "" +"Синтаксис: USERLIST [{хостмаска | #канал} [INVISIBLE]]\n" +"\n" +"Выводит список всех пользователей, находящихся в данный момент в сети.\n" +"Зарегистрирован их ник или нет - роли не играет.\n" +"\n" +"В качестве параметра, вы можете указать пользовательскую хостмаску\n" +"вида ник!идент@хост - это позволит получить только конкретные,\n" +"совпадающие с маской записи. Если же вы укажите #канал, будет\n" +"выведен список всех посетителей указанного канала.\n" +"Дополнительный параметр INVISIBLE позволяет получить список ников\n" +"с режимом +i, данные которых совпадают с указанной в качестве второго\n" +"параметра хостмаской." + +#: modules/commands/ms_list.cpp:142 +#, fuzzy +msgid "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Синтаксис: LIST [#канал] [список_записей | NEW]\n" +"\n" +"Выводит текущий список сообщений. С параметром NEW, покажет только\n" +"новые (непрочитанные) сообщения, они будут помечены значком \"*\"\n" +"слева от номера сообщения.\n" +"Помимо этого, вы можете указать список записей или номер записи,\n" +"например:\n" +"\n" +" LIST 2-5,7-9\n" +" покажет сообщения с 2-го по 5-ое и с 7-го по 9-ое." + +#: modules/commands/bs_botlist.cpp:19 +#, fuzzy +msgid "Lists available bots" +msgstr "BOTLIST Список доступных для установки ботов" + +#: modules/commands/os_modinfo.cpp:196 +#, fuzzy +msgid "Lists currently loaded modules." +msgstr " MODLIST Список загруженных модулей" + +#: modules/commands/cs_info.cpp:19 +#, fuzzy +msgid "Lists information about the specified registered channel" +msgstr " INFO Запрос информации об указанном канале" + +#: modules/commands/cs_info.cpp:76 +#, fuzzy +msgid "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." +msgstr "" +"Синтаксис: INFO #канал\n" +"\n" +"Позволяет получить подробную информацию о зарегистрированом канале,\n" +"в частности такую как: ник владельца, время регистрации канала, дату\n" +"его последнего использования и описание. С параметром ALL будут\n" +"так же показаны заблокированные режимы, опции канала и его наследник.\n" +"Примечание: по-умолчанию, использовать команду с параметром ALL\n" +"может только владелец канала." + +#: modules/commands/os_module.cpp:19 +#, fuzzy +msgid "Load a module" +msgstr " MODLOAD Загрузить модуль" + +#: modules/commands/cs_register.cpp:39 +msgid "Local channels cannot be registered." +msgstr "Локальные каналы не могут быть зарегистрированы." + +#: modules/commands/cs_log.cpp:142 +#, fuzzy, c-format +msgid "Log list for %s:" +msgstr "Список доступа для %s:" + +#: modules/commands/cs_log.cpp:227 +#, c-format +msgid "Logging changed for command %s on %s, now using log method %s%s%s." +msgstr "" + +#: modules/commands/cs_log.cpp:220 +#, c-format +msgid "Logging for command %s on %s with log method %s%s%s has been removed." +msgstr "" + +#: modules/commands/cs_log.cpp:248 +#, c-format +msgid "Logging is now active for command %s on %s, using log method %s%s%s." +msgstr "" + +#: modules/commands/os_login.cpp:60 +#, c-format +msgid "Login to %s" +msgstr "" + +#: modules/commands/os_news.cpp:36 +#, c-format +msgid "Logon news item #%d deleted." +msgstr "Новость под номером #%d удалена." + +#: modules/commands/os_news.cpp:35 +#, fuzzy, c-format +msgid "Logon news item #%s not found!" +msgstr "Новость под номером #%d не обнаружена." + +#: modules/commands/os_news.cpp:32 +msgid "Logon news items:" +msgstr "Текущие список новостей:" + +#: modules/commands/os_login.cpp:102 +#, fuzzy, c-format +msgid "Logout from %s" +msgstr "Список доступа для %s:" + +#: modules/commands/os_login.cpp:52 +#, c-format +msgid "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." +msgstr "" + +#: modules/commands/os_login.cpp:94 +#, c-format +msgid "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." +msgstr "" + +#: modules/commands/cs_seen.cpp:213 +#, c-format +msgid "Looking for yourself, eh %s?" +msgstr "" + +#: modules/commands/cs_mode.cpp:773 +#, c-format +msgid "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a " +"channel.\n" +"If a mode is locked on or off, services will not allow that mode to be " +"changed. The SET\n" +"command will clear all existing mode locks and set the new one given, while " +"ADD and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * " +"and ? may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may " +"be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, " +"halfops, and voices. If what\n" +"is not given then all basic modes are removed." +msgstr "" + +#: modules/commands/cs_akick.cpp:434 +#, fuzzy +msgid "Maintain the AutoKick list" +msgstr " AKICK Управление списком автокиков канала" + +#: modules/commands/bs_bot.cpp:269 +#, fuzzy +msgid "Maintains network bot list" +msgstr "BOT Управление сервисными ботами" + +#: modules/commands/cs_xop.cpp:522 +#, c-format +msgid "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " +msgstr "" + +#: modules/commands/cs_akick.cpp:493 +#, c-format +msgid "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" +msgstr "" + +#: modules/commands/cs_access.cpp:568 +#, c-format +msgid "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." +msgstr "" + +#: modules/commands/bs_badwords.cpp:424 +#, fuzzy, c-format +msgid "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" +msgstr "" +"Синтаксис: BADWORDS #канал ADD слово [SINGLE | START | END]\n" +" BADWORDS #канал DEL {слово | номер_записи | список_записей}\n" +" BADWORDS #канал LIST [маска | список_записей]\n" +" BADWORDS #канал CLEAR\n" +"\n" +"Данная команда позволяет модифицировать список \"плохих\" слов канала.\n" +"Этот список определяет, за использование каких слов пользователь\n" +"будет кикнут ботом, при условии, конечно, что данная возможность\n" +"активирована.\n" +"Для более подробной информации по активации данного режима смотрите\n" +"%s%s HELP KICK BADWORDS.\n" +"\n" +"Команда BADWORDS ADD добавляет новое слово в список \"плохих\" слов.\n" +"Вы можете указать дополнительные условия обработки для добавляемого\n" +"слова, например: опциональный параметр SINGLE заставит бота\n" +"учитывать только факт полного употребления данного слова, параметр\n" +"START заставит бота учитывать факт совпадения по маске \"слово*\"\n" +"(то есть, совпадение какой-либо START-записи из списка с началом\n" +"сказанного слова), ну и последний параметр END будет срабатывать\n" +"при употреблении \"*слова\". Если вы не укажете ни один из этих\n" +"параметров для добавляемого слова, будет использоваться совпадение\n" +"по \"*слову*\".\n" +"Примеры:\n" +"\n" +"BADWORDS #chuvaki ADD пес\n" +"-> добавит слово \"пес\" в список плохих слов и заставит бота кикать\n" +" не только за употребление самого этого слова, но и любых его\n" +" словоформ, содержащих в себе оригин (например: пес, песок и т.д.)\n" +"\n" +"BADWORDS #chuvaki ADD пес SINGLE\n" +"-> добавит слово \"пес\" в список плохих слов и заставит бота кикать\n" +" только за употребление самого этого слова, и никак иначе.\n" +"\n" +"Команда BADWORDS DEL удаляет указанное слово из списка плохих слов.\n" +"В качестве параметра вы можете указать не только конкретную запись,\n" +"но и номер записи или список записей (см. примеры использования\n" +"команды LIST ниже).\n" +"\n" +"Команда BADWORDS LIST покажет текущий список плохих слов.\n" +"В качестве дополнительного параметра, вы можете указать символьную\n" +"маску, что позволит вам получить список с конкре" + +#: modules/commands/bs_badwords.cpp:370 +#, fuzzy +msgid "Maintains the bad words list" +msgstr "BADWORDS Управление списком \"плохих\" слов" + +#: modules/commands/bs_control.cpp:79 +#, fuzzy +msgid "Makes the bot do the equivalent of a \"/me\" command" +msgstr "ACT Выполнить действие от лица бота на указанном канале" + +#: modules/commands/bs_control.cpp:127 +#, fuzzy +msgid "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." +msgstr "" +"Синтаксис: ACT #канал текст\n" +"\n" +"Заставляет бота выполнить команду, эквивалентную команде \"/me\"\n" +"в IRC-клиенте mIRC. Вы должны указать оба параметра: текст действия\n" +"и #канал." + +#: modules/commands/bs_control.cpp:19 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel" +msgstr "SAY Послать на указанный канал текст от лица бота" + +#: modules/commands/bs_control.cpp:69 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel." +msgstr "SAY Послать на указанный канал текст от лица бота" + +#: modules/commands/greet.cpp:157 +#, fuzzy +msgid "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." +msgstr "" +"Синтаксис: SASET ник GREET текст\n" +"\n" +"Позволяет назначить приветственное сообщение, которое сервисный\n" +"бот будет говорить каждый раз, когда ник зайдет на канал. Учтите,\n" +"что для отображения приветсвия, на канале должна быть активирована\n" +"опция GREET и ник должен иметь соответствующий уровень доступа." + +#: modules/commands/greet.cpp:131 +#, fuzzy +msgid "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." +msgstr "" +"Синтаксис: SET GREET сообщение\n" +"\n" +"Позволяет назначить приветственное сообщение, которое сервисный\n" +"бот будет говорить каждый раз, когда вы заходите на канал. Учтите,\n" +"что для отображения приветствия, на канале должна быть активирована\n" +"опция GREET и вы должны иметь соответствующий уровень доступа." + +#: modules/commands/os_dns.cpp:660 +#, fuzzy +msgid "Manage DNS zones for this network" +msgstr "Возможность удаления email-адреса в вашей IRC-сети недоступна." + +#: modules/commands/cs_entrymsg.cpp:193 +#, fuzzy +msgid "Manage the channel's entry messages" +msgstr " PERSIST Set the channel as permanent" + +#: modules/commands/ms_ignore.cpp:19 +#, fuzzy +msgid "Manage the memo ignore list" +msgstr " IGNORE Управление игнор-списком сервисов" + +#: modules/commands/ns_ajoin.cpp:230 +#, fuzzy +msgid "Manage your auto join list" +msgstr " AKICK Управление списком автокиков канала" + +#: modules/commands/os_sxline.cpp:233 +#, fuzzy, c-format +msgid "Manipulate the %s list" +msgstr " AKILL Управление списком AKILL'ов" + +#: modules/commands/os_akill.cpp:385 +#, fuzzy +msgid "Manipulate the AKILL list" +msgstr " AKILL Управление списком AKILL'ов" + +#: modules/commands/os_defcon.cpp:176 +#, fuzzy +msgid "Manipulate the DefCon system" +msgstr " DEFCON Управление системой DefCon (защитных контрмер)" + +#: modules/commands/cs_topic.cpp:149 +#, fuzzy +msgid "Manipulate the topic of the specified channel" +msgstr " TOPIC Установка топика на канале посредством сервисов" + +#: modules/commands/bs_botlist.cpp:27 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_forbid.cpp:358 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/ms_ignore.cpp:86 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_list.cpp:153 modules/commands/bs_info.cpp:55 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +msgid "Mask" +msgstr "" + +#: modules/commands/ns_access.cpp:39 +#, fuzzy, c-format +msgid "Mask %s already present on %s's access list." +msgstr "Маска вида %s уже присутствует в вашем списке доступа." + +#: include/language.h:67 +msgid "Mask must be in the form user@host." +msgstr "" + +#: modules/commands/cs_access.cpp:166 modules/commands/cs_flags.cpp:120 +#: modules/commands/cs_xop.cpp:162 +#, fuzzy +msgid "Masks and unregistered users may not be on access lists." +msgstr "Маска вида %s уже присутствует в вашем списке доступа." + +#: modules/commands/ns_getemail.cpp:23 +#, fuzzy +msgid "Matches and returns all users that registered using given email" +msgstr " GETEMAIL Запрос списка всех ников с указанным email" + +#: modules/commands/os_logsearch.cpp:148 +#, fuzzy, c-format +msgid "Matches for %s:" +msgstr "Блокировка режимов........: %s" + +#: modules/commands/os_stats.cpp:139 +#, c-format +msgid "Maximum users: %d (%s)" +msgstr "Зафиксированный максимум пользователей: %d (на %s)" + +#: modules/commands/ms_read.cpp:84 modules/commands/ms_read.cpp:86 +#, fuzzy, c-format +msgid "Memo %d from %s (%s)." +msgstr "Блокировка режимов........: %s" + +#: modules/commands/ms_del.cpp:33 modules/commands/ms_del.cpp:101 +#, c-format +msgid "Memo %d has been deleted." +msgstr "Сообщение под номером %d было удалено." + +#: modules/commands/ms_ignore.cpp:82 +#, fuzzy +msgid "Memo ignore list is empty." +msgstr "Список игнорируемых ников пуст." + +#: modules/commands/ms_set.cpp:199 +#, c-format +msgid "Memo limit disabled for %s." +msgstr "Лимит сообщений для %s отключен." + +#: modules/commands/ms_set.cpp:185 +#, c-format +msgid "Memo limit for %s set to %d." +msgstr "Лимит собщений для %s установлен на %d." + +#: modules/commands/ms_set.cpp:192 +#, c-format +msgid "Memo limit for %s set to 0." +msgstr "Лимит сообщений для %s установлен на 0." + +#: modules/commands/ms_rsend.cpp:63 modules/commands/ms_send.cpp:51 +#, c-format +msgid "Memo sent to %s." +msgstr "Мемо-сообщение для %s успешно отправлено." + +#: modules/commands/ms_list.cpp:131 +#, fuzzy, c-format +msgid "Memos for %s:" +msgstr "Блокировка режимов........: %s" + +#: modules/commands/cs_entrymsg.cpp:116 +#, fuzzy +msgid "Message" +msgstr "GLOBAL сообщение" + +#: modules/commands/ns_set.cpp:1313 +msgid "Message mode" +msgstr "Режим приватных сообщений" + +#: modules/commands/cs_log.cpp:127 +msgid "Method" +msgstr "" + +#: modules/commands/cs_mode.cpp:329 modules/commands/cs_mode.cpp:420 +#, c-format +msgid "Missing parameter for mode %c." +msgstr "" + +#: modules/commands/cs_mode.cpp:449 +msgid "Mode" +msgstr "" + +#: modules/commands/cs_mode.cpp:718 +#, fuzzy, c-format +msgid "Mode %s is a virtual mode and can't be cleared." +msgstr "Указанный ник %s содержит недопустимые символы." + +#: modules/commands/cs_mode.cpp:712 +#, fuzzy, c-format +msgid "Mode %s is not a status or list mode." +msgstr "Ник %s в списке игнорируемых не обнаружен." + +#: modules/commands/cs_mode.cpp:1065 +#, fuzzy +msgid "Mode lock" +msgstr "Блокировка режимов........: %s" + +#: modules/commands/cs_mode.cpp:466 +#, fuzzy, c-format +msgid "Mode locks for %s:" +msgstr "Блокировка режимов........: %s" + +#: modules/commands/os_list.cpp:43 +msgid "Modes" +msgstr "" + +#: modules/commands/os_mode.cpp:44 +#, c-format +msgid "Modes cleared on %s and the channel destroyed." +msgstr "" + +#: modules/commands/ns_access.cpp:166 +#, fuzzy, c-format +msgid "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." +msgstr "" +"Синтаксис: ACCESS ADD маска\n" +" ACCESS DEL маска\n" +" ACCESS LIST\n" +"\n" +"Позволяет просматривать/изменять список масок доступа на ваш ник.\n" +"Имеется ввиду список хостмасок вида идент@хост, с которых %s\n" +"позволит использовать ваш ник даже без и дентификации к нему.\n" +"В противном случае, чтобы использовать ник с хостмаски которая не\n" +"присутствует в списоке доступа, вам необходимо будет использовать\n" +"команду IDENTIFY для идентификации на %s.\n" +"\n" +"Примеры:\n" +"\n" +" ACCESS ADD anyone@*.set.ru\n" +" позволяет использовать ник всем, кто имеет идент anyone\n" +" и чей хост попадает под маску *.set.ru.\n" +" ACCESS DEL anyone@*.set.ru\n" +" антоним предыдущей команды - удаляет маску из списка.\n" +" ACCESS LIST\n" +" выводит текущий список \"доверенных\" хостмасок." + +#: modules/commands/ns_cert.cpp:319 +msgid "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" +msgstr "" + +#: modules/commands/os_ignore.cpp:341 +#, fuzzy +msgid "Modify the Services ignore list" +msgstr " IGNORE Управление игнор-списком сервисов" + +#: modules/commands/cs_xop.cpp:489 +#, fuzzy, c-format +msgid "Modify the list of %s users" +msgstr " AOP Управление списком AOP'ов канала" + +#: modules/commands/ns_access.cpp:101 +#, fuzzy +msgid "Modify the list of authorized addresses" +msgstr " ACCESS Управление ACCESS-списком ника (списком хостмасок)" + +#: modules/commands/cs_access.cpp:498 modules/commands/cs_flags.cpp:373 +#, fuzzy +msgid "Modify the list of privileged users" +msgstr " ACCESS Управление ACCESS-списком привилегий канала" + +#: modules/commands/ns_cert.cpp:257 +#, fuzzy +msgid "Modify the nickname client certificate list" +msgstr " IGNORE Управление игнор-списком сервисов" + +#: modules/commands/os_session.cpp:522 +#, fuzzy +msgid "Modify the session-limit exception list" +msgstr " EXCEPTION Управление списком исключений из лимита сессий" + +#: modules/commands/os_module.cpp:34 +#, c-format +msgid "Module %s is already loaded." +msgstr "Module %s is already loaded." + +#: modules/commands/os_module.cpp:67 modules/commands/os_module.cpp:139 +#, c-format +msgid "Module %s isn't loaded." +msgstr "Module %s isn't loaded." + +#: modules/commands/os_module.cpp:31 +#, fuzzy, c-format +msgid "Module %s loaded." +msgstr "Модуль %s успешно загружен." + +#: modules/commands/os_module.cpp:98 +#, fuzzy, c-format +msgid "Module %s reloaded." +msgstr "Модуль %s успешно загружен." + +#: modules/commands/os_module.cpp:156 +#, fuzzy, c-format +msgid "Module %s unloaded." +msgstr "Модуль %s успешно выгружен." + +#: modules/commands/os_config.cpp:88 +#, fuzzy +msgid "Module Name" +msgstr "Модуль %s успешно загружен." + +#: modules/commands/os_config.cpp:112 +msgid "Module settings:" +msgstr "" + +#: modules/commands/os_modinfo.cpp:32 +#, fuzzy, c-format +msgid "Module: %s Version: %s Author: %s Loaded: %s" +msgstr "Модуль: %s Версия: %s Автор: %s Загружен: %s" + +#: modules/commands/os_modinfo.cpp:183 +#, c-format +msgid "Module: %s [%s] [%s]" +msgstr "Модуль: %s [%s] [%s]" + +#: modules/commands/cs_access.cpp:697 modules/commands/cs_access.cpp:799 +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +#: modules/commands/cs_list.cpp:75 modules/commands/os_list.cpp:43 +#: modules/commands/os_list.cpp:153 +msgid "Name" +msgstr "" + +#: modules/commands/os_oper.cpp:153 +msgid "Name Type" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:146 +#, fuzzy, c-format +msgid "Network stats for %s:" +msgstr "Список доступа для %s:" + +#: modules/commands/os_forbid.cpp:384 +msgid "Never" +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/bs_botlist.cpp:27 +#: modules/commands/hs_request.cpp:305 modules/commands/ns_list.cpp:75 +#: modules/commands/ns_group.cpp:327 +#, fuzzy +msgid "Nick" +msgstr "INFO ник" + +#: modules/commands/ns_register.cpp:42 +#, fuzzy, c-format +msgid "Nick %s has been confirmed." +msgstr "Ник %s успешно удален из базы данных сервисов." + +#: modules/commands/os_oper.cpp:95 +#, fuzzy, c-format +msgid "Nick %s is already an operator." +msgstr "Ник %s уже зарегистрирован!" + +#: modules/commands/ns_register.cpp:36 +#, fuzzy, c-format +msgid "Nick %s is already confirmed." +msgstr "Ник %s уже зарегистрирован!" + +#: modules/commands/os_svs.cpp:46 +#, c-format +msgid "Nick %s is an illegal nickname and cannot be used." +msgstr "Указанный ник %s содержит недопустимые символы." + +#: modules/commands/bs_bot.cpp:81 modules/commands/bs_bot.cpp:181 +#: modules/commands/os_svs.cpp:54 +#, c-format +msgid "Nick %s is currently in use." +msgstr "Ник %s на данный момент используется кем-то другим." + +#: modules/commands/os_forbid.cpp:512 +#, fuzzy, c-format +msgid "Nick %s is forbidden by %s: %s" +msgstr "Ник %s на данный момент используется кем-то другим." + +#: modules/commands/os_forbid.cpp:514 +#, fuzzy, c-format +msgid "Nick %s is forbidden." +msgstr "На данный момент, ник %s сервисами не удерживается." + +#: modules/commands/os_oper.cpp:134 +#, fuzzy, c-format +msgid "Nick %s is not a Services Operator." +msgstr "%s is a services operator of type %s." + +#: modules/commands/ns_info.cpp:34 +#, c-format +msgid "Nick %s is part of this Network's Services." +msgstr "Ник %s является ником одного из сервисных псевдоклиентов данной сети." + +#: include/language.h:79 +#, fuzzy, c-format +msgid "Nick %s isn't currently in use." +msgstr "Ник %s на данный момент используется кем-то другим." + +#: include/language.h:78 +#, fuzzy, c-format +msgid "Nick %s isn't registered." +msgstr "Ник %s успешно зарегистрирован." + +#: modules/commands/os_svs.cpp:39 +#, c-format +msgid "Nick %s was truncated to %d characters." +msgstr "Ник %s был усечен до %d символов." + +#: modules/commands/ns_set.cpp:1135 +#, c-format +msgid "Nick %s will expire." +msgstr "C этого момента ник %s снова в режиме истечения." + +#: modules/commands/ns_set.cpp:1129 +#, c-format +msgid "Nick %s will not expire." +msgstr "С этого момента регистрация ника %s никогда не истечет." + +#: modules/commands/ms_check.cpp:60 +#, c-format +msgid "Nick %s doesn't have a memo from you." +msgstr "Ник %s не получал от вас никаких сообщений." + +#: modules/commands/ns_logout.cpp:48 +#, c-format +msgid "Nick %s has been logged out." +msgstr "Ник %s успешно деидентифицирован." + +#: modules/commands/ns_group.cpp:272 +#, c-format +msgid "Nick %s has been ungrouped from %s." +msgstr "Nick %s has been ungrouped from %s." + +#: include/language.h:81 +#, fuzzy, c-format +msgid "Nick %s is currently suspended." +msgstr "С этого момента ник %s находится режиме саспенда." + +#: modules/commands/ns_group.cpp:250 +#, fuzzy, c-format +msgid "Nick %s is not in your group." +msgstr "The nick %s is not in your group." + +#: modules/commands/ns_suspend.cpp:180 +#, fuzzy, c-format +msgid "Nick %s is not suspended." +msgstr "С этого момента ник %s находится режиме саспенда." + +#: modules/commands/ns_suspend.cpp:190 +#, c-format +msgid "Nick %s is now released." +msgstr "Режим саспенда с ника %s успешно снят." + +#: modules/commands/ns_suspend.cpp:138 +#, c-format +msgid "Nick %s is now suspended." +msgstr "С этого момента ник %s находится режиме саспенда." + +#: modules/commands/cs_seen.cpp:275 +#, c-format +msgid "Nick too long, max length is %u characters." +msgstr "" + +#: modules/commands/ns_drop.cpp:53 +#, c-format +msgid "Nickname %s has been dropped." +msgstr "Ник %s успешно удален из базы данных сервисов." + +#: include/language.h:97 +#, fuzzy, c-format +msgid "Nickname %s is already registered!" +msgstr "Канал %s уже зарегистрирован!" + +#: include/language.h:96 +#, fuzzy, c-format +msgid "Nickname %s may not be registered." +msgstr "Канал %s не может быть зарегистрирован." + +#: modules/commands/ns_register.cpp:226 +#, fuzzy, c-format +msgid "Nickname %s registered under your user@host-mask: %s" +msgstr "" +"Ник %s успешно зарегистрирован, в ACCESS-список добавлена хостмаска: %s" + +#: modules/commands/ns_register.cpp:228 +#, fuzzy, c-format +msgid "Nickname %s registered." +msgstr "Ник %s успешно зарегистрирован." + +#: modules/commands/cs_set.cpp:1307 +#, fuzzy +msgid "No auto-op" +msgstr "Автостатус" + +#: modules/commands/bs_assign.cpp:252 +msgid "No bot" +msgstr "Без ботов" + +#: modules/commands/cs_set.cpp:1303 modules/commands/ns_set.cpp:1317 +#, fuzzy +msgid "No expire" +msgstr "никогда не истечет" + +#: modules/commands/help.cpp:184 +#, c-format +msgid "No help available for %s." +msgstr "Справочная информация по %s отсутствует." + +#: modules/commands/os_modinfo.cpp:61 +#, fuzzy, c-format +msgid "No information about module %s is available." +msgstr "Информация о модуле %s недоступна. " + +#: modules/commands/cs_enforce.cpp:177 +#, fuzzy, c-format +msgid "No limit is set on %s." +msgstr "Лимит собщений для %s установлен на %d." + +#: modules/commands/os_news.cpp:37 +msgid "No logon news items to delete!" +msgstr "Список новостей пуст, удалять нечего." + +#: modules/commands/os_logsearch.cpp:133 +#, fuzzy, c-format +msgid "No matches for %s found." +msgstr "Ники с email-адресом %s не обнаружены." + +#: modules/commands/cs_xop.cpp:294 +#, fuzzy, c-format +msgid "No matching entries on %s %s list." +msgstr "Совпадающих записей в списке AOP'ов канала %s не обнаружено." + +#: modules/commands/cs_access.cpp:269 modules/commands/cs_access.cpp:433 +#: modules/commands/cs_flags.cpp:335 modules/commands/cs_xop.cpp:428 +#, c-format +msgid "No matching entries on %s access list." +msgstr "Совпадающих записей в списке доступа канала %s не обнаружено." + +#: modules/commands/cs_akick.cpp:224 modules/commands/cs_akick.cpp:368 +#, c-format +msgid "No matching entries on %s autokick list." +msgstr "Совпадающих значений в списке автокиков канала %s не обнаружено." + +#: modules/commands/bs_badwords.cpp:166 modules/commands/bs_badwords.cpp:246 +#, c-format +msgid "No matching entries on %s bad words list." +msgstr "В списке плохих слов канала %s совпадающих записей не обнаружено." + +#: modules/commands/os_session.cpp:145 modules/commands/os_session.cpp:490 +msgid "No matching entries on session-limit exception list." +msgstr "" +"Совпадающих значений в списке исключений из лимита сессий не обнаружено." + +#: modules/commands/os_sxline.cpp:28 modules/commands/os_sxline.cpp:177 +#, fuzzy, c-format +msgid "No matching entries on the %s list." +msgstr "Совпадающих записей в списке AOP'ов канала %s не обнаружено." + +#: modules/commands/os_akill.cpp:29 modules/commands/os_akill.cpp:320 +msgid "No matching entries on the AKILL list." +msgstr "Совпадающих записей не обнаружено." + +#: modules/commands/ms_cancel.cpp:77 +msgid "No memo was cancelable." +msgstr "Нет сообщений доступных для отмены." + +#: modules/commands/ms_read.cpp:65 +msgid "No memos to display." +msgstr "" + +#: modules/commands/os_modinfo.cpp:187 +#, fuzzy +msgid "No modules currently loaded matching that criteria." +msgstr "Список модулей пуст." + +#: modules/commands/ns_recover.cpp:55 +msgid "No one is using your nick, and services are not holding it." +msgstr "" + +#: modules/commands/os_login.cpp:30 modules/commands/os_login.cpp:77 +msgid "No oper block for your nick." +msgstr "" + +#: modules/commands/os_news.cpp:47 +msgid "No oper news items to delete!" +msgstr "Список опер-новостей пуст, удалять нечего." + +#: modules/commands/os_news.cpp:57 +msgid "No random news items to delete!" +msgstr "Список случайных новостей пуст, удалять нечего." + +#: modules/commands/hs_list.cpp:111 +msgid "No records to display." +msgstr "" + +#: modules/commands/ns_getemail.cpp:47 +#, fuzzy, c-format +msgid "No registrations matching %s were found." +msgstr "* Запрет на регистрацию ников." + +#: modules/commands/hs_request.cpp:220 modules/commands/hs_request.cpp:276 +#, c-format +msgid "No request for nick %s found." +msgstr "" + +#: src/access.cpp:55 +msgid "No signed kick when SIGNKICK LEVEL is used" +msgstr "" + +#: modules/extra/stats/cs_fantasy_top.cpp:159 +#: modules/extra/stats/cs_fantasy_stats.cpp:156 +#, fuzzy, c-format +msgid "No stats for %s." +msgstr "Список доступа для %s:" + +#: modules/commands/os_info.cpp:201 +#, fuzzy, c-format +msgid "No such info \"%s\" on %s." +msgstr "%s has been invited to %s." + +#: modules/commands/cs_ban.cpp:219 modules/commands/cs_kick.cpp:118 +#, fuzzy, c-format +msgid "No users on %s match %s." +msgstr "Режимы пользователя %s изменены." + +#: modules/commands/bs_assign.cpp:188 +#, fuzzy, c-format +msgid "No-bot mode is now off on channel %s." +msgstr "Режим без-бота для канала %s активирован." + +#: modules/commands/bs_assign.cpp:181 +#, fuzzy, c-format +msgid "No-bot mode is now on on channel %s." +msgstr "Режим без-бота для канала %s активирован." + +#: modules/commands/os_mode.cpp:64 +#, c-format +msgid "Non-status modes cleared on %s." +msgstr "" + +#: modules/commands/os_dns.cpp:226 modules/commands/bs_info.cpp:58 +msgid "None" +msgstr "отсутствуют" + +#: modules/commands/cs_set.cpp:1029 +#, c-format +msgid "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." +msgstr "" + +#: modules/commands/cs_mode.cpp:380 modules/commands/cs_mode.cpp:437 +msgid "Nothing to do." +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:201 modules/commands/ms_list.cpp:64 +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_log.cpp:127 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +#: modules/commands/ns_ajoin.cpp:100 +msgid "Number" +msgstr "" + +#: modules/commands/os_news.cpp:41 +msgid "OPERNEWS {ADD|DEL|LIST} [text|num]" +msgstr "OPERNEWS {ADD|DEL|LIST} [текст|номер]" + +#: modules/commands/ns_info.cpp:68 modules/commands/ns_info.cpp:72 +#, fuzzy +msgid "Online from" +msgstr "Сейчас онлайн, c маской.: %s" + +#: modules/commands/os_oper.cpp:138 +#, c-format +msgid "" +"Oper %s is configured in the configuration file(s) and can not be removed by " +"this command." +msgstr "" + +#: modules/commands/os_info.cpp:268 +msgid "Oper Info" +msgstr "" + +#: modules/commands/os_info.cpp:182 modules/commands/os_info.cpp:221 +#, fuzzy, c-format +msgid "Oper info list for %s is empty." +msgstr "Список доступа для %s пуст." + +#: modules/commands/os_news.cpp:46 +#, c-format +msgid "Oper news item #%d deleted." +msgstr "Новость под номером #%d удалена." + +#: modules/commands/os_news.cpp:45 +#, fuzzy, c-format +msgid "Oper news item #%s not found!" +msgstr "Новость под номером #%d не обнаружена." + +#: modules/commands/os_news.cpp:42 +msgid "Oper news items:" +msgstr "Список новостей для IRC-операторов:" + +#: modules/commands/os_oper.cpp:148 +#, c-format +msgid "Oper privileges removed from %s (%s)." +msgstr "" + +#: modules/commands/os_oper.cpp:101 modules/commands/os_oper.cpp:189 +#, fuzzy, c-format +msgid "Oper type %s has not been configured." +msgstr "Ник %s успешно удален из базы данных сервисов." + +#: modules/commands/os_oline.cpp:37 +#, c-format +msgid "Operflags %s have been added for %s." +msgstr "OLINE-флаги %s успешно установлены для сессий пользователя %s" + +#: modules/commands/os_oline.cpp:43 +#, fuzzy, c-format +msgid "Operflags %s have been removed from %s." +msgstr "OLINE-флаги %s успешно установлены для сессий пользователя %s" + +#: modules/commands/os_oper.cpp:193 +#, c-format +msgid "Opertype %s has no allowed commands." +msgstr "" + +#: modules/commands/os_oper.cpp:215 +#, c-format +msgid "Opertype %s has no allowed privileges." +msgstr "" + +#: modules/commands/os_oper.cpp:237 +#, c-format +msgid "Opertype %s receives modes %s once identified." +msgstr "" + +#: modules/commands/bs_kick.cpp:1219 +msgid "Ops protection" +msgstr "Не кикать операторов" + +#: src/misc.cpp:258 modules/commands/bs_info.cpp:58 +#, fuzzy +msgid "Options" +msgstr "Опции...........: %s" + +#: modules/commands/os_dns.cpp:668 +#, fuzzy +msgid "POOL server.name" +msgstr "NOOP {SET|REVOKE} сервер" + +#: modules/commands/cs_mode.cpp:449 +msgid "Param" +msgstr "" + +#: modules/commands/ns_identify.cpp:38 +msgid "Password accepted - you are now recognized." +msgstr "Пароль принят - вы признаны как владелец ника." + +#: modules/commands/os_login.cpp:44 +#, fuzzy +msgid "Password accepted." +msgstr "Вы указали неверный пароль." + +#: include/language.h:85 +msgid "Password authentication required for that command." +msgstr "" + +#: modules/commands/ns_set.cpp:152 modules/commands/ns_set.cpp:218 +#, fuzzy, c-format +msgid "Password for %s changed to %s." +msgstr "Наследником канала %s назначен пользователь %s." + +#: modules/commands/ns_set.cpp:154 modules/commands/ns_set.cpp:220 +#, fuzzy, c-format +msgid "Password for %s changed." +msgstr "Пароль для ника %s был выслан на его email-адрес." + +#: modules/commands/ns_getpass.cpp:38 +#, c-format +msgid "Password for %s is %s." +msgstr "Пароль для ника %s - %s" + +#: include/language.h:71 +#, fuzzy +msgid "Password incorrect." +msgstr "Вы указали неверный пароль." + +#: modules/commands/ns_resetpass.cpp:39 +#, c-format +msgid "Password reset email for %s has been sent." +msgstr "Password reset email for %s has been sent." + +#: modules/commands/cs_set.cpp:1289 +msgid "Peace" +msgstr "Спокойствие" + +#: modules/commands/cs_set.cpp:440 +#, fuzzy, c-format +msgid "Peace option for %s is now off." +msgstr "Режим спокойствия для канала %s активирован." + +#: modules/commands/cs_set.cpp:434 +#, fuzzy, c-format +msgid "Peace option for %s is now on." +msgstr "Режим спокойствия для канала %s активирован." + +#: modules/commands/cs_set.cpp:1301 +#, fuzzy +msgid "Persistent" +msgstr "Persistant" + +#: include/language.h:126 +msgid "Please contact an Operator to get a vHost assigned to this nick." +msgstr "" + +#: include/language.h:73 +msgid "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." +msgstr "" + +#: modules/commands/os_jupe.cpp:30 +#, fuzzy +msgid "Please use a valid server name when juping." +msgstr "" +"В качестве основного параметра вы должны указать реальное имя серевера " + +#: include/language.h:104 +msgid "Please use the symbol of # when attempting to register." +msgstr "" + +#: src/mail.cpp:78 +#, c-format +msgid "Please wait %d seconds and retry." +msgstr "Пожалуйста, подождите %d секунд и повторите запрос." + +#: modules/commands/hs_request.cpp:158 +#, fuzzy, c-format +msgid "Please wait %d seconds before requesting a new vHost." +msgstr "" +"Пожалуйста, подождите %d секунд перед повторным использованием команды SEND." + +#: modules/commands/ms_rsend.cpp:58 modules/commands/ms_send.cpp:57 +#, fuzzy, c-format +msgid "Please wait %d seconds before using the %s command again." +msgstr "" +"Пожалуйста, подождите %d секунд перед повторным использованием команды SEND." + +#: modules/commands/ns_group.cpp:149 +#, c-format +msgid "Please wait %d seconds before using the GROUP command again." +msgstr "Подождите %d секунд перед повторным использованием команды GROUP." + +#: modules/commands/ns_register.cpp:198 +#, c-format +msgid "Please wait %d seconds before using the REGISTER command again." +msgstr "Подождите %d секунд перед повторным использованием команды REGISTER." + +#: modules/commands/os_dns.cpp:628 +#, c-format +msgid "Pooled %s." +msgstr "" + +#: modules/commands/os_dns.cpp:237 +msgid "Pooled/Active" +msgstr "" + +#: modules/commands/os_dns.cpp:239 +msgid "Pooled/Not Active" +msgstr "" + +#: modules/commands/bs_set.cpp:161 +msgid "Prevent a bot from being assigned by non IRC operators" +msgstr "" + +#: modules/commands/bs_assign.cpp:153 +#, fuzzy +msgid "Prevent a bot from being assigned to a channel" +msgstr "" +" SUSPEND Приостановка работы канала, с сохранением всех данных\n" +" и настроек канала" + +#: modules/commands/cs_suspend.cpp:58 +#, fuzzy +msgid "Prevent a channel from being used preserving channel data and settings" +msgstr "" +" SUSPEND Приостановка работы канала, с сохранением всех данных\n" +" и настроек канала" + +#: modules/commands/cs_set.cpp:1043 +#, fuzzy +msgid "Prevent the channel from expiring" +msgstr " NOEXPIRE Prevent the channel from expiring" + +#: modules/commands/ns_list.cpp:186 +#, fuzzy +msgid "Prevent the nickname from appearing in the LIST command" +msgstr " PRIVATE скрытие ника в списке ников по /msg %s LIST" + +#: modules/commands/ns_set.cpp:1104 +#, fuzzy +msgid "Prevent the nickname from expiring" +msgstr " NOEXPIRE установка на ник т.н. режима 'не-истечения'" + +#: src/access.cpp:46 +msgid "Prevents users being kicked by Services" +msgstr "" + +#: modules/commands/ns_list.cpp:297 modules/commands/cs_list.cpp:262 +#: modules/commands/bs_info.cpp:58 +msgid "Private" +msgstr "Приватность" + +#: modules/commands/bs_set.cpp:190 +#, fuzzy, c-format +msgid "Private mode of bot %s is now off." +msgstr "Бот под ником %s успешно помечен как приватный." + +#: modules/commands/bs_set.cpp:185 +#, fuzzy, c-format +msgid "Private mode of bot %s is now on." +msgstr "Бот под ником %s успешно помечен как приватный." + +#: modules/commands/cs_list.cpp:220 +#, fuzzy, c-format +msgid "Private option for %s is now off." +msgstr "Режим приватности канала %s активирован." + +#: modules/commands/cs_list.cpp:214 +#, fuzzy, c-format +msgid "Private option for %s is now on." +msgstr "Режим приватности канала %s активирован." + +#: modules/commands/ns_list.cpp:221 +#, fuzzy, c-format +msgid "Private option is now off for %s." +msgstr "Режим приватности для %s активирован." + +#: modules/commands/ns_list.cpp:215 +#, fuzzy, c-format +msgid "Private option is now on for %s." +msgstr "Режим приватности для %s активирован." + +#: modules/commands/cs_flags.cpp:281 +#, c-format +msgid "Privilege %s added to %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/cs_flags.cpp:283 +#, c-format +msgid "Privilege %s removed from %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/ns_set.cpp:1309 +msgid "Protection" +msgstr "Защита" + +#: modules/commands/ns_set.cpp:721 +#, fuzzy, c-format +msgid "Protection is now off for %s." +msgstr "Защита ника %s активирована, лимит времени на ввод пароля: 60 секунд." + +#: modules/commands/ns_set.cpp:700 +#, fuzzy, c-format +msgid "Protection is now on for %s, with a reduced delay." +msgstr "Защита ника %s активирована,лимит времени на ввод пароля: 20 секунд." + +#: modules/commands/ns_set.cpp:710 +#, fuzzy, c-format +msgid "Protection is now on for %s, with no delay." +msgstr "Защита ника %s активирована, лимит времени на ввод пароля: 0 секунд." + +#: modules/commands/ns_set.cpp:692 +#, fuzzy, c-format +msgid "Protection is now on for %s." +msgstr "Защита ника %s активирована, лимит времени на ввод пароля: 60 секунд." + +#: modules/commands/os_chankill.cpp:100 +#, fuzzy +msgid "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." +msgstr "" +"Синтаксис: CHANKILL [+срок_истечения] #канал причина\n" +"Добавляет в AKILL-список всех пользователей указанного канала с\n" +"указанной причиной на указанный промежуток времени. В качестве маски\n" +"AKILL'ов будут использованы маски посетителей канала вида идент@хост." + +#: modules/commands/ns_set.cpp:1307 +#, fuzzy +msgid "Quick protection" +msgstr "Не кикать войсов" + +#: modules/commands/os_news.cpp:51 +msgid "RANDOMNEWS {ADD|DEL|LIST} [text|num]" +msgstr "RANDOMNEWS {ADD|DEL|LIST} [текст|номер]" + +#: modules/commands/cs_enforce.cpp:99 +msgid "REGONLY enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:68 +msgid "RESTRICTED enforced by " +msgstr "" + +#: modules/commands/os_noop.cpp:21 +#, fuzzy +msgid "REVOKE server" +msgstr "NOOP {SET|REVOKE} сервер" + +#: modules/commands/os_news.cpp:56 +#, c-format +msgid "Random news item #%d deleted." +msgstr "Новость под номером #%d удалена." + +#: modules/commands/os_news.cpp:55 +#, fuzzy, c-format +msgid "Random news item #%s not found!" +msgstr "Новость под номером #%d не обнаружена." + +#: modules/commands/os_news.cpp:52 +msgid "Random news items:" +msgstr "Список случайных новостей:" + +#: modules/commands/ms_read.cpp:112 +#, fuzzy +msgid "Read a memo or memos" +msgstr " READ Чтение какого-либо сообщения, группы сообщений" + +#: modules/commands/bs_info.cpp:56 +#, fuzzy +msgid "Real name" +msgstr "Реальное имя....: %s" + +#: modules/commands/os_list.cpp:153 +#, fuzzy +msgid "Realname" +msgstr "Реальное имя....: %s" + +#: modules/commands/os_ignore.cpp:266 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:204 modules/commands/os_forbid.cpp:358 +#: modules/commands/cs_akick.cpp:392 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:361 +msgid "Reason" +msgstr "" + +#: src/xline.cpp:386 +#, fuzzy, c-format +msgid "Reason for %s updated." +msgstr "Наследник канал %s удален." + +#: modules/commands/ns_recover.cpp:214 +msgid "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." +msgstr "" + +#: modules/commands/cs_access.cpp:741 +#, fuzzy +msgid "Redefine the meanings of access levels" +msgstr " LEVELS Переустановка значения уровней доступа канала" + +#: modules/commands/ns_recover.cpp:149 +#, fuzzy +msgid "Regains control of your nick" +msgstr "" +" RELEASE Снятие защиты сервисов с вашего ника после команды RECOVER" + +#: modules/commands/os_sxline.cpp:330 modules/commands/os_sxline.cpp:545 +#: modules/commands/os_akill.cpp:129 +#, fuzzy +msgid "Regex is disabled." +msgstr "Режим %s: включен." + +#: modules/commands/os_sxline.cpp:459 modules/commands/os_sxline.cpp:694 +#: modules/commands/os_akill.cpp:444 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." +msgstr "" + +#: modules/commands/os_ignore.cpp:386 modules/commands/os_forbid.cpp:428 +#: modules/commands/ns_list.cpp:172 modules/commands/cs_list.cpp:167 +#: modules/commands/os_list.cpp:119 modules/commands/os_list.cpp:255 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." +msgstr "" + +#: modules/commands/cs_register.cpp:19 +#, fuzzy +msgid "Register a channel" +msgstr " REGISTER Регистрация ника" + +#: modules/commands/ns_register.cpp:120 +#, fuzzy +msgid "Register a nickname" +msgstr " REGISTER Регистрация ника" + +#: modules/commands/ns_info.cpp:89 modules/commands/cs_info.cpp:55 +#, fuzzy +msgid "Registered" +msgstr "Зарегистрирован.........: %s" + +#: modules/commands/os_stats.cpp:184 +#, c-format +msgid "Registered channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:190 +#, c-format +msgid "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:187 +#, c-format +msgid "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/cs_enforce.cpp:105 +#, c-format +msgid "Registered only enforced on %s." +msgstr "" + +#: modules/commands/cs_register.cpp:86 +#, fuzzy, c-format +msgid "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." +msgstr "" +"Синтаксис: REGISTER #канал описание\n" +"\n" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which must be included, is a\n" +"general description of the channel's purpose.\n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel.\n" +"See the ACCESS command (/msg %s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname. If you haven't,\n" +"/msg %s HELP for information on how to do so." + +#: modules/commands/ns_register.cpp:269 +#, fuzzy, c-format +msgid "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." +msgstr "" +"Синтаксис: REGISTER пароль [email]\n" +"\n" +"Позволяет зарегистрировать ваш текущий ник в базе данных %s.\n" +"После успешной его регистрации, вы можете использовать команды\n" +"SET и ACCESS что бы сконфигурировать параметры ника так, как\n" +"вам будет угодно. Постарайтесь не забыть указанный при регистрации\n" +"пароль - он понадобится вам для дальнейшего использования ника!\n" +"\n" +"Принципы выбора пароля:\n" +"Пароли не должны быть легко угадываемы. Например, использование\n" +"вашего реального имени в качестве пароля - плохая идея.\n" +"Использование вашего ника в качестве пароля - совсем плохая идея,\n" +"%s просто-напросто не допустит этого. Также, короткие пароли\n" +"очень легко подбираются простым перебором, поэтому длина пароля\n" +"должна быть больше 5 символов. Пробелы и знаки табуляции в пароле\n" +"недопустимы, вы можете использовать только латинские буквы и цифры.\n" +"Примечание: все пароли чувствительны к регистру! MYPASSWORD,\n" +"MyPassword, и mypassword - это разные пароли!\n" +"\n" +"Указанный в качестве дополнительного параметра email будет\n" +"автоматически ассоциирован с регистрируемым ником. Данный параметр\n" +"может быть как опциональным, так и обязательным - это зависит от\n" +"требований и настроек IRC-сети.\n" +"Вы можете не беспокоиться о приватности вашего email-адреса - никто\n" +"из посторонних лиц его не получит.\n" +"\n" +"Так же, регистрация нового ника автоматически создает для него новую\n" +"группу. Возможности групп ников позволяют вам иметь несколько ников\n" +"с общей для них информацией, настройками, списком доступа. Для более\n" +"подробной информации см. /msg %s HELP GROUP" + +#: modules/commands/ns_register.cpp:145 +#, fuzzy +msgid "Registration is currently disabled." +msgstr "Извините, регистрация каналов временно приостановлена." + +#: modules/commands/cs_set.cpp:400 +#, fuzzy +msgid "Regulate the use of critical commands" +msgstr " PEACE активирование режима \"спокойствия\" на канале" + +#: modules/commands/hs_request.cpp:283 +#, fuzzy +msgid "Reject the requested vHost for the given nick." +msgstr "" +" STATUS Запрос статуса идентификации указанного ника на сервисах" + +#: modules/commands/hs_request.cpp:240 +#, fuzzy +msgid "Reject the requested vHost of a user" +msgstr " DEL Удаление виртуального хоста" + +#: modules/commands/cs_suspend.cpp:151 +#, fuzzy +msgid "Releases a suspended channel" +msgstr " UNSUSPEND Снятие режима саспенда с канала (восстановление)" + +#: modules/commands/cs_suspend.cpp:191 +#, fuzzy +msgid "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." +msgstr "" +"Синтаксис: UNSUSPEND #канал\n" +"\n" +"Полностью восстанавливает активность приостановленного канала." + +#: modules/commands/os_module.cpp:56 +#, fuzzy +msgid "Reload a module" +msgstr " MODLOAD Загрузить модуль" + +#: modules/commands/os_reload.cpp:19 +#, fuzzy +msgid "Reload services' configuration file" +msgstr " RELOAD Перезагрузка конфигурационного файла сервисов" + +#: modules/commands/ns_group.cpp:236 +#, fuzzy +msgid "Remove a nick from a group" +msgstr " UNGROUP Remove a nick from a group" + +#: modules/commands/cs_unban.cpp:19 +#, fuzzy +msgid "Remove all bans preventing a user from entering a channel" +msgstr "" +" UNBAN Remove all bans preventing a user from entering a channel" + +#: modules/commands/os_noop.cpp:19 +#, fuzzy +msgid "Remove all operators from a server remotely" +msgstr "" +" NOOP Временное удаление всех O:line'ов с указанного\n" +" сервера сети" + +#: modules/commands/os_dns.cpp:543 +#, fuzzy, c-format +msgid "Removed IP %s from %s." +msgstr "Блокировка режимов........: %s" + +#: modules/commands/os_dns.cpp:460 +#, c-format +msgid "Removed server %s from zone %s." +msgstr "" + +#: modules/commands/os_dns.cpp:483 +#, c-format +msgid "Removed server %s." +msgstr "" + +#: modules/commands/cs_mode.cpp:909 +#, c-format +msgid "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." +msgstr "" + +#: modules/commands/cs_mode.cpp:890 +#, fuzzy, c-format +msgid "Removes %s status from you or the specified nick on a channel" +msgstr "" +" OP Установка статуса оператора (+o) указанному нику на канале" + +#: modules/commands/cs_updown.cpp:146 +#, fuzzy +msgid "Removes a selected nicks status from a channel" +msgstr " KICK Выкидывает указанного пользователя с канала" + +#: modules/commands/cs_updown.cpp:223 +msgid "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." +msgstr "" + +#: src/xline.cpp:412 +#, c-format +msgid "Removing %s because %s covers it." +msgstr "" + +#: modules/commands/bs_kick.cpp:1171 modules/commands/bs_kick.cpp:1173 +#: modules/commands/bs_kick.cpp:1176 +#, fuzzy +msgid "Repeat kicker" +msgstr "Цензор повторов......: %s" + +#: modules/commands/hs_request.cpp:78 +#, fuzzy +msgid "Request a vHost for your nick" +msgstr "Для вашего ника не установлен email-адрес." + +#: modules/commands/hs_request.cpp:179 +msgid "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." +msgstr "" + +#: modules/commands/ns_register.cpp:312 +#, fuzzy +msgid "Resend registration confirmation email" +msgstr " RELOAD Перезагрузка конфигурационного файла сервисов" + +#: modules/commands/cs_set.cpp:621 +#, fuzzy +msgid "Restrict access to the channel" +msgstr " RESTRICTED ограничение уровня доступа на канал до прописанных" + +#: modules/commands/cs_set.cpp:1291 +#, fuzzy +msgid "Restricted access" +msgstr "Ограниченный доступ" + +#: modules/commands/cs_set.cpp:661 +#, fuzzy, c-format +msgid "Restricted access option for %s is now off." +msgstr "Режим ограниченного доступа на канал %s активирован." + +#: modules/commands/cs_set.cpp:655 +#, fuzzy, c-format +msgid "Restricted access option for %s is now on." +msgstr "Режим ограниченного доступа на канал %s активирован." + +#: modules/commands/cs_enforce.cpp:73 +#, fuzzy, c-format +msgid "Restricted enforced on %s." +msgstr "Ограниченный доступ" + +#: modules/commands/cs_set.cpp:335 +#, fuzzy +msgid "Retain modes when channel is not in use" +msgstr " KEEPTOPIC активирование автосохранения топика канала" + +#: modules/commands/cs_topic.cpp:20 +#, fuzzy +msgid "Retain topic when channel is not in use" +msgstr " KEEPTOPIC активирование автосохранения топика канала" + +#: modules/commands/ns_getpass.cpp:19 +#, fuzzy +msgid "Retrieve the password for a nickname" +msgstr " GETPASS Запрос пароля указанного ника" + +#: modules/commands/hs_request.cpp:296 +msgid "Retrieves the vhost requests" +msgstr "" + +#: modules/commands/cs_getkey.cpp:19 +#, fuzzy +msgid "Returns the key of the given channel" +msgstr " GETKEY Запрос установленного на канале ключа (+k)" + +#: modules/commands/cs_getkey.cpp:57 +#, fuzzy +msgid "Returns the key of the given channel." +msgstr " GETKEY Запрос установленного на канале ключа (+k)" + +#: modules/commands/ns_getemail.cpp:58 +#, fuzzy +msgid "Returns the matching accounts that used given email." +msgstr " GETKEY Запрос установленного на канале ключа (+k)" + +#: modules/commands/ns_status.cpp:19 +#, fuzzy +msgid "Returns the owner status of the given nickname" +msgstr "" +" STATUS Запрос статуса идентификации указанного ника на сервисах" + +#: modules/commands/ns_getpass.cpp:50 +#, fuzzy +msgid "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." +msgstr "" +"Синтаксис: GETPASS ник\n" +"\n" +"Позволяет получить пароль указанного ника.\n" +"Примечание: сразу по использовании данной команды, сервисы пошлют\n" +"по WALLOPS/GLOBOPS сообщение, содержащие ник использовавшего команду,\n" +"и ник, относительно которого была использована данная команда.\n" +"Одновременно с этим, событие будет записано в лог-файл.\n" +"Примечание 2: команда недоступна, если включено шифрование паролей." + +#: modules/commands/ns_status.cpp:55 +#, fuzzy +msgid "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." +msgstr "" +"Синтаксис: STATUS ник1 ник2 ник3...\n" +"\n" +"Запрашивает информацию о статусе ника на сервисах - идентифицировался\n" +"ли использующий его как владелец. Ответ выводится в формате:\n" +"\n" +" ник код-статуса status account\n" +"\n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +"\n" +"0 - такого пользователя нет в онлайне или этот ник не зарегистрирован\n" +"1 - пользователь не идентифицирован как владелец ника\n" +"2 - пользователь идентифицирован как владелец ника через список хостмасок\n" +"3 - пользователь идентифицирован как владелец ника через идентификацию " +"паролем\n" +"\n" +"Вы можете запросить статус сразу у 16 ников (разделяя их пробелом),\n" +"все лишние буду проигнорированы. Если параметр не указан - команда\n" +"вернет ваш текущий статус на сервисах." + +#: modules/commands/bs_kick.cpp:1181 modules/commands/bs_kick.cpp:1183 +#: modules/commands/bs_kick.cpp:1186 +#, fuzzy +msgid "Reverses kicker" +msgstr "Цензор инверсий......: %s" + +#: modules/commands/ns_logout.cpp:21 +#, fuzzy +msgid "Reverses the effect of the IDENTIFY command" +msgstr " LOGOUT Деидентификация от используемого на данный момент ника" + +#: modules/commands/os_noop.cpp:20 +#, fuzzy +msgid "SET server" +msgstr "NOOP {SET|REVOKE} сервер" + +#: modules/commands/os_dns.cpp:667 +msgid "SET server.name option value" +msgstr "" + +#: modules/commands/ns_cert.cpp:378 +#, fuzzy, c-format +msgid "SSL certificate fingerprint accepted, you are now identified to %s." +msgstr "Пароль принят - вы признаны как владелец ника." + +#: modules/commands/ns_cert.cpp:398 +#, fuzzy +msgid "SSL certificate fingerprint accepted, you are now identified." +msgstr "Пароль принят - вы признаны как владелец ника." + +#: modules/commands/cs_enforce.cpp:137 +#, c-format +msgid "SSL only enforced on %s." +msgstr "" + +#: modules/commands/cs_enforce.cpp:131 +msgid "SSLONLY enforced by " +msgstr "" + +#: modules/commands/os_shutdown.cpp:47 +#, fuzzy +msgid "Save databases and restart Services" +msgstr " RESTART Сохранить базы данных и перезапустить сервисы" + +#: modules/commands/os_logsearch.cpp:32 +msgid "Searches logs for a matching pattern" +msgstr "" + +#: modules/commands/cs_set.cpp:1295 +#, fuzzy +msgid "Secure founder" +msgstr "Безопасность владельца" + +#: modules/commands/cs_set.cpp:786 +#, fuzzy, c-format +msgid "Secure founder option for %s is now off." +msgstr "Режим безопасности владельца для канала %s активирован." + +#: modules/commands/cs_set.cpp:780 +#, fuzzy, c-format +msgid "Secure founder option for %s is now on." +msgstr "Режим безопасности владельца для канала %s активирован." + +#: modules/commands/cs_set.cpp:1297 +#, fuzzy +msgid "Secure ops" +msgstr "Контроль статуса оператора" + +#: modules/commands/cs_set.cpp:850 +#, fuzzy, c-format +msgid "Secure ops option for %s is now off." +msgstr "Режим контроля за статусом оператора для канала %s активирован." + +#: modules/commands/cs_set.cpp:844 +#, fuzzy, c-format +msgid "Secure ops option for %s is now on." +msgstr "Режим контроля за статусом оператора для канала %s активирован." + +#: modules/commands/cs_set.cpp:723 +#, fuzzy, c-format +msgid "Secure option for %s is now off." +msgstr "Режим безопасности для канала %s активирован." + +#: modules/commands/cs_set.cpp:717 +#, fuzzy, c-format +msgid "Secure option for %s is now on." +msgstr "Режим безопасности для канала %s активирован." + +#: modules/commands/ns_set.cpp:1044 +#, fuzzy, c-format +msgid "Secure option is now off for %s." +msgstr "Режим безопасности для %s активирован." + +#: modules/commands/ns_set.cpp:1038 +#, fuzzy, c-format +msgid "Secure option is now on for %s." +msgstr "Режим безопасности для %s активирован." + +#: modules/commands/cs_enforce.cpp:42 +#, fuzzy, c-format +msgid "Secureops enforced on %s." +msgstr "Режим безопасности для %s активирован." + +#: modules/commands/cs_set.cpp:1293 modules/commands/ns_set.cpp:1311 +msgid "Security" +msgstr "Безопасность" + +#: modules/commands/cs_xop.cpp:570 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the access list." +msgstr "" +"Для более подробной информации о какой-либо конкретной опции, см.\n" +"справку по /msg %s HELP опция" + +#: modules/commands/cs_xop.cpp:573 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the flags system." +msgstr "" +"Для более подробной информации о какой-либо конкретной опции, см.\n" +"справку по /msg %s HELP опция" + +#: modules/commands/ms_send.cpp:24 +#, fuzzy +msgid "Send a memo to a nick or channel" +msgstr " SEND Отправка мемо-сообщения указанному нику или каналу" + +#: modules/commands/ms_staff.cpp:24 +#, fuzzy +msgid "Send a memo to all opers/admins" +msgstr "" +" STAFF Отправка мемо-сообщения всем операторам/администраторам сети" + +#: modules/commands/ms_sendall.cpp:24 +#, fuzzy +msgid "Send a memo to all registered users" +msgstr " SENDALL Отправка массового мемо-сообщения всем пользователям сети" + +#: modules/commands/gl_global.cpp:21 +#, fuzzy +msgid "Send a message to all users" +msgstr " GLOBAL Отправка глобального сообщения всем пользователям сети" + +#: modules/commands/ms_list.cpp:64 +#, fuzzy +msgid "Sender" +msgstr "Безопасность владельца" + +#: modules/commands/ms_rsend.cpp:24 +#, fuzzy +msgid "Sends a memo and requests a read receipt" +msgstr "" +" RSEND Отправка мемо-сообщения с условием подтверждения о прочтении" + +#: modules/commands/ns_resetpass.cpp:50 +#, fuzzy +msgid "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." +msgstr "" +"Syntax: RESETPASS nickname\n" +"\n" +"Sends a code key to the nickname with the instructions on how to\n" +"reset their password." + +#: modules/commands/ms_sendall.cpp:52 +#, fuzzy +msgid "Sends all registered users a memo containing memo-text." +msgstr "" +"Синтаксис: SENDALL текст_сообщения\n" +"\n" +"Отправляет массовое мемо-сообщение всем зарегистрированным\n" +"пользователям сети." + +#: modules/commands/ms_staff.cpp:48 +#, fuzzy +msgid "Sends all services staff a memo containing memo-text." +msgstr "" +"Синтаксис: STAFF текст_сообщения\n" +"\n" +"Позволяет отправить мемо-сообщение всем операторам/администраторам\n" +"сервисов сети." + +#: modules/commands/ms_send.cpp:66 +#, fuzzy +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." +msgstr "" +"Синтаксис: SEND {ник | #канал} текст_сообщения\n" +"\n" +"Отправляет сообщение для ника или для #канала, содержащее\n" +"текст_сообщения. Если в качестве получателя указан ник, то он\n" +"будет уведомлен о том, что вы отправили ему мемо-собщение.\n" +"Примечание: получатель, будь то ник или канал, должен быть\n" +"зарегистрирован, для возможности отправки/получения мемо-сообщений." + +#: modules/commands/ms_rsend.cpp:80 +#, fuzzy +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." +msgstr "" +"Синтаксис: RSEND {ник | #канал} текст_сообщения\n" +"\n" +"Данная команда аналогична команде SEND и позволяет послать\n" +"сообщение для указанного ника или канала. Отличительной ее\n" +"особенностью является то, что сразу после прочтения адресатом\n" +"сообщения, отправитель автоматически получит извещение о прочтении.\n" +"Само собой разумеется, что ник/канал отправителя/получателя должны\n" +"быть зарегистрированы." + +#: modules/commands/ms_read.cpp:199 +#, fuzzy +msgid "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Синтаксис: READ [#канал] {номер | список_записей | LAST | NEW}\n" +"\n" +"Позволяет прочесть указанные сообщения. С параметром LAST - выведет\n" +"текст последнего полученного вами сообщения, с параметром NEW -\n" +"отобразит все непрочитанные вами сообщения.\n" +"Помимо этого, вы можете указать список записей или номер записи,\n" +"например:\n" +"\n" +" READ 2-5,7-9\n" +" выведет текст всех сообщений с 2-го по 5-ое и с 7-го по 9-ое." + +#: modules/commands/os_dns.cpp:218 +#, fuzzy +msgid "Server" +msgstr "NOOP {SET|REVOKE} сервер" + +#: modules/commands/os_dns.cpp:375 +#, fuzzy, c-format +msgid "Server %s added to zone %s." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:345 +#, fuzzy, c-format +msgid "Server %s already exists." +msgstr "Бот с ником %s уже существует." + +#: modules/commands/os_noop.cpp:31 modules/commands/os_dns.cpp:430 +#: modules/commands/os_dns.cpp:493 modules/commands/os_dns.cpp:532 +#: modules/commands/os_dns.cpp:571 modules/commands/os_dns.cpp:604 +#: modules/commands/os_dns.cpp:639 +#, fuzzy, c-format +msgid "Server %s does not exist." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:619 +#, fuzzy, c-format +msgid "Server %s has no configured IPs." +msgstr "Ник %s успешно удален из базы данных сервисов." + +#: modules/commands/os_dns.cpp:357 +#, fuzzy, c-format +msgid "Server %s is already in zone %s." +msgstr "You are already in %s! " + +#: modules/commands/os_dns.cpp:614 +#, fuzzy, c-format +msgid "Server %s is already pooled." +msgstr "Module %s is already loaded." + +#: modules/commands/os_dns.cpp:609 +#, fuzzy, c-format +msgid "Server %s is not currently linked." +msgstr "%s сейчас в сети." + +#: modules/commands/os_dns.cpp:443 +#, fuzzy, c-format +msgid "Server %s is not in zone %s." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:384 +#, fuzzy, c-format +msgid "Server %s is not linked to the network." +msgstr "Бот с канала %s успешно удален." + +#: modules/commands/os_dns.cpp:644 +#, fuzzy, c-format +msgid "Server %s is not pooled." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:465 +#, c-format +msgid "Server %s must be quit before it can be deleted." +msgstr "" + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Servers" +msgstr "NOOP {SET|REVOKE} сервер" + +#: modules/commands/os_stats.cpp:155 +#, c-format +msgid "Servers found: %d" +msgstr "Текущее кол-во серверов: %d" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Service" +msgstr "Текущее кол-во серверов: %d" + +#: modules/commands/ns_recover.cpp:51 +#, fuzzy, c-format +msgid "Service's hold on %s has been released." +msgstr "Ваш ник освобожден от удержания сервисами." + +#: data/nickserv.example.conf:236 data/chanserv.example.conf:827 +#, fuzzy +msgid "Services Operator commands" +msgstr "%s is a services operator of type %s." + +#: modules/commands/os_defcon.cpp:443 modules/commands/os_defcon.cpp:454 +#: modules/commands/os_defcon.cpp:462 modules/commands/os_defcon.cpp:470 +#: modules/commands/os_defcon.cpp:478 +#, fuzzy +msgid "Services are in DefCon mode, please try again later." +msgstr "" +"На данный момент сервисы работают в DEFCON-режиме. Повторите свой запрос " +"позже." + +#: include/language.h:70 +#, fuzzy +msgid "Services are in read-only mode!" +msgstr "Сервисы перешли в режим read-only (только чтение)." + +#: modules/commands/os_defcon.cpp:186 modules/commands/os_defcon.cpp:213 +#, fuzzy, c-format +msgid "Services are now at DEFCON %d." +msgstr "DEFCON-режим активирован, уровень защиты: %d" + +#: modules/commands/os_set.cpp:128 +#, fuzzy, c-format +msgid "Services are now in debug mode (level %d)." +msgstr "Режим работы сервисов изменен: активирован DEBUG-режим (уровень %d)." + +#: modules/commands/os_set.cpp:114 +#, fuzzy +msgid "Services are now in debug mode." +msgstr "Режим работы сервисов изменен: активирован DEBUG-режим (отладка)." + +#: modules/commands/os_set.cpp:159 +msgid "Services are now in expire mode." +msgstr "Режим работы сервисов изменен: NOEXPIRE-режим деактивирован." + +#: modules/commands/os_set.cpp:153 +msgid "Services are now in no expire mode." +msgstr "" +"Режим работы сервисов изменен: активирован NOEXPIRE-режим (режим 'не-" +"истечения')." + +#: modules/commands/os_set.cpp:120 +#, fuzzy +msgid "Services are now in non-debug mode." +msgstr "Режим работы сервисов изменен: DEBUG-режим деактивирован." + +#: modules/commands/os_set.cpp:47 +msgid "Services are now in read-only mode." +msgstr "Сервисы перешли в режим read-only (только чтение)." + +#: modules/commands/os_set.cpp:53 +msgid "Services are now in read-write mode." +msgstr "Сервисы перешли в режим read-write (чтение-запись)." + +#: src/mail.cpp:76 +msgid "Services have been configured to not send mail." +msgstr "" +"Настройки mail-функций сервисов некорректны или отключены, возможность " +"отправки email недоступна." + +#: modules/commands/os_ignore.cpp:280 +#, fuzzy +msgid "Services ignore list:" +msgstr " IGNORE Управление игнор-списком сервисов" + +#: modules/commands/os_mode.cpp:33 modules/commands/os_kick.cpp:39 +#, fuzzy +msgid "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" +msgstr "" +"Возможность изменять режимы сервисам недоступна. Вы вообще уверены, что U:" +"line-записи ваших серверов корректны?" + +#: modules/commands/os_stats.cpp:140 +#, fuzzy, c-format +msgid "Services up %s." +msgstr "Текущее кол-во серверов: %d" + +#: modules/commands/ns_set.cpp:266 +#, fuzzy, c-format +msgid "Services will from now on set status modes on %s in channels." +msgstr "Режим автостатуса для %s отключен" + +#: modules/commands/cs_set.cpp:114 +#, fuzzy, c-format +msgid "Services will no longer automatically give modes to users in %s." +msgstr "Режим автостатуса для %s отключен" + +#: modules/commands/ns_set.cpp:272 +#, fuzzy, c-format +msgid "Services will no longer set status modes on %s in channels." +msgstr "Режим автостатуса для %s отключен" + +#: modules/commands/cs_set.cpp:108 +#, fuzzy, c-format +msgid "Services will now automatically give modes to users in %s." +msgstr "Режим автостатуса для %s активирован" + +#: modules/commands/ns_set.cpp:940 +#, c-format +msgid "Services will now reply to %s with messages." +msgstr "" +"Режим приватных сообщений для %s активирован, теперь сервисы будут отвечать " +"ему в приват." + +#: modules/commands/ns_set.cpp:946 +#, c-format +msgid "Services will now reply to %s with notices." +msgstr "" +"Режим приватных сообщений для %s отключен, сервисы будут отвечать ему " +"посредством нотисов." + +#: modules/commands/os_reload.cpp:34 +#, fuzzy +msgid "Services' configuration has been reloaded." +msgstr "Конфигурационный файл сервисов был считан заново." + +#: modules/commands/os_session.cpp:192 +msgid "Session" +msgstr "" + +#: modules/commands/os_session.cpp:382 +#, c-format +msgid "Session limit for %s set to %d." +msgstr "Лимит сессий для %s установлен на %d." + +#: modules/commands/os_session.cpp:257 modules/commands/os_session.cpp:534 +msgid "Session limiting is disabled." +msgstr "Ограничение сессий отключено, список исключений не требуется." + +#: modules/commands/os_stats.cpp:195 +#, c-format +msgid "Sessions: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/ns_set.cpp:74 +#, fuzzy +msgid "Set SET-options on another nickname" +msgstr " SASET Установка различных опций какого-либо ника" + +#: modules/commands/cs_set.cpp:20 +#, fuzzy +msgid "Set channel options and information" +msgstr " SET Настройка различных опций канала" + +#: modules/commands/cs_set.cpp:137 +#, fuzzy +msgid "Set how Services make bans on the channel" +msgstr " BANTYPE установка типа бана сервисами на канале" + +#: modules/commands/ms_set.cpp:206 +#, fuzzy +msgid "Set options related to memos" +msgstr " SET Установка опций для мемо-сообщений" + +#: modules/commands/ns_set.cpp:19 +#, fuzzy +msgid "Set options, including kill protection" +msgstr " SET Настройка опций ника, включая защиту KILL'ом" + +#: modules/commands/cs_set.cpp:472 +#, fuzzy +msgid "Set the channel as permanent" +msgstr " PERSIST Set the channel as permanent" + +#: modules/commands/cs_set.cpp:204 +#, fuzzy +msgid "Set the channel description" +msgstr " DESC изменение описания канала" + +#: modules/commands/ns_set.cpp:329 +#, fuzzy +msgid "Set the display of your group in Services" +msgstr " DISPLAY установка главного ника группы" + +#: modules/commands/cs_set.cpp:266 +#, fuzzy +msgid "Set the founder of a channel" +msgstr " FOUNDER смена владельца канала" + +#: modules/commands/ns_set.cpp:793 +#, fuzzy +msgid "Set the language Services will use when messaging you" +msgstr "" +" LANGUAGE выбор языка, посредством которого\n" +" сервисы будут с вами общаться" + +#: modules/commands/ns_set.cpp:172 +#, fuzzy +msgid "Set the nickname password" +msgstr " PASSWORD изменение текущего пароля на ник" + +#: modules/commands/cs_set.cpp:949 +#, fuzzy +msgid "Set the successor for a channel" +msgstr " SUCCESSOR установка наследника канала" + +#: modules/commands/hs_set.cpp:125 +#, fuzzy +msgid "Set the vhost for all nicks in a group" +msgstr " SETALL Установка вирт. хоста для всех ников указанной группы" + +#: modules/commands/hs_set.cpp:19 +#, fuzzy +msgid "Set the vhost of another user" +msgstr " SET Установка виртуального хоста указанному пользователю" + +#: modules/commands/os_set.cpp:169 +#, fuzzy +msgid "Set various global Services options" +msgstr " SET Настройка различных опций сервисов" + +#: modules/commands/ns_set.cpp:119 +#, fuzzy +msgid "Set your nickname password" +msgstr " PASSWORD изменение текущего пароля на ник" + +#: modules/commands/bs_kick.cpp:271 +#, fuzzy, c-format +msgid "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK channel ITALICS {ON|OFF} [ttb]\n" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +"ttb is the number of times a user can be kicked\n" +"before it get banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:307 +#, fuzzy, c-format +msgid "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Синтаксис: KICK #канал BADWORDS {ON|OFF} [ttb]\n" +"\n" +"Активируйте данную опцию с нужными вам значениями, если хотите\n" +"чтобы бот кикал посетителей за использование на канале \"плохих\" слов.\n" +"\n" +"База \"плохих\" слов канала модифицируется посредством дополнительной\n" +"команды BADWORDS. Для более подробной информации смотрите справку\n" +"по /msg %s HELP BADWORDS.\n" +"\n" +"Параметр ttb - это количество киков, по превышению которого бот\n" +"поставит бан. Укажите вместо положительного числа значение \"0\" или\n" +"\"-\" если не хотите чтобы бот банил нарушителя." + +#: modules/commands/cs_set.cpp:186 +#, fuzzy +msgid "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" +msgstr "" +"Синтаксис: %s #канал BANTYPE тип_бана\n" +"\n" +"Позволяет установить шаблон банмаски, по которой будет забанен\n" +"пользователь канала, относительно которого применяется сервисная\n" +"команда BAN.\n" +"\n" +"Значение типа бана должно быть кокретным числом, от 0 до 3\n" +"включительно. Допустимые значения представлены ниже:\n" +"\n" +"0 - бан вида *!идент@хост\n" +"1 - бан вида *!*идент@хост\n" +"2 - бан вида *!*@хост\n" +"3 - бан вида *!*идент@*.домен" + +#: modules/commands/bs_kick.cpp:345 +#, fuzzy +msgid "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Синтаксис: KICK #канал BOLDS {ON|OFF} [ttb]\n" +"\n" +"Активируйте данную опцию с нужными вам значениями, если хотите\n" +"чтобы бот кикал посетителей за чрезмерное использование жирного\n" +"текста.\n" +"\n" +"Параметр ttb - это количество киков, по превышению которого бот\n" +"поставит бан. Укажите вместо положительного числа значение \"0\" или\n" +"\"-\" если не хотите чтобы бот банил нарушителя." + +#: modules/commands/bs_kick.cpp:436 +#, fuzzy, c-format +msgid "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Синтаксис: KICK #канал CAPS {ON|OFF} [ttb [минимум [проценты]]]\n" +"\n" +"Активируйте данную опцию с нужными вам значениями, если хотите\n" +"чтобы бот кикал посетителей за чрезмерное использование CapsLOCK.\n" +"\n" +"Условия наказания рассчитываются следующим образом: строка, которую\n" +"послал посетитель, должна содержать X больших букв, определенных\n" +"минимумом, и количество этих заглавных букв должно составлять как\n" +"минимум X процентов%% от числа букв всей строки.\n" +"Например: предположим, что настройки у нас стоят как 10 и 25,\n" +"тогда строка вида:\n" +"\n" +"BLABLABLAB BLABLABLAB BLABLABlab blablablab blablablab blablablab\n" +"blablablab blablablab blablablab blablablab\n" +"\n" +"будет попадать под следующее условие: количество заглавных букв\n" +"больше 10 и и процентаж его относительно общего кол-ва букв > 25%.\n" +"Как видите, выставленное нами условие в данном случае сработает и\n" +"пользователь будет кикнут с соответствующей причиной.\n" +"\n" +"Если вы не укажете параметры режима, будут использованы значения\n" +"по-умолчанию: 10 для минимума букв и 25% для процентажа.\n" +"\n" +"Параметр ttb - это количество киков, по превышению которого бот\n" +"поставит бан. Укажите вместо положительного числа значение \"0\" или\n" +"\"-\" если не хотите чтобы бот банил нарушителя." + +#: modules/commands/bs_kick.cpp:475 +#, fuzzy +msgid "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Синтаксис: KICK #канал COLORS {ON|OFF} [ttb]\n" +"\n" +"Активируйте данную опцию с нужными вам значениями, если хотите\n" +"чтобы бот кикал посетителей за чрезмерное использование цветного\n" +"текста.\n" +"\n" +"Параметр ttb - это количество киков, по превышению которого бот\n" +"поставит бан. Укажите вместо положительного числа значение \"0\" или\n" +"\"-\" если не хотите чтобы бот банил нарушителя." + +#: modules/commands/cs_set.cpp:255 +#, fuzzy +msgid "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." +msgstr "" +"Синтаксис: %s #канал DESC описание\n" +"\n" +"Позволяет установить описание канала, которое будет показано при\n" +"использовании команд LIST и INFO." + +#: modules/commands/bs_kick.cpp:571 +#, fuzzy +msgid "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Синтаксис: KICK #канал FLOOD {ON|OFF} [ttb [линий [секунды]]]\n" +"\n" +"Активируйте данную опцию с нужными вам значениями, если хотите\n" +"чтобы бот кикал посетителей за флуд.\n" +"\n" +"Условия наказания рассчитываются следующим образом: пользователь\n" +"должен послать на канал количество сообщений, превыщающее параметр\n" +"линий, и, если это произошло в указанный промежуток секунды -\n" +"бот кикнет его с соответствующей причиной.\n" +"\n" +"Если вы не укажете параметры режима, будут использованы значения\n" +"по-умолчанию: 6 строк за 10 секунд.\n" +"\n" +"Параметр ttb - это количество киков, по превышению которого бот\n" +"поставит бан. Укажите вместо положительного числа значение \"0\" или\n" +"\"-\" если не хотите чтобы бот банил нарушителя." + +#: modules/commands/bs_kick.cpp:607 +#, fuzzy +msgid "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK channel ITALICS {ON|OFF} [ttb]\n" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +"ttb is the number of times a user can be kicked\n" +"before it get banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:706 +#, fuzzy +msgid "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Синтаксис: KICK #канал REPEAT {ON|OFF} [ttb [число_повторов]]\n" +"\n" +"Активируйте данную опцию с нужными вам значениями, если хотите\n" +"чтобы бот кикал посетителей за повторы.\n" +"\n" +"Условия наказания рассчитываются следующим образом: пользователь\n" +"должен X раз подряд послать на канал одинаковое сообщение, при этом\n" +"сообщения других пользователей, посланные в это же время, никоим\n" +"образом несбрасывают счетчик числа_повторов этого пользователя. \n" +"\n" +"Если вы не укажете параметры режима, будут использованы значения\n" +"по-умолчанию: 3 повтора подряд.\n" +"\n" +"Параметр ttb - это количество киков, по превышению которого бот\n" +"поставит бан. Укажите вместо положительного числа значение \"0\" или\n" +"\"-\" если не хотите чтобы бот банил нарушителя." + +#: modules/commands/bs_kick.cpp:742 +#, fuzzy +msgid "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Синтаксис: KICK #канал REVERSES {ON|OFF} [ttb]\n" +"\n" +"Активируйте данную опцию с нужными вам значениями, если хотите\n" +"чтобы бот кикал посетителей за чрезмерное использование инверсного\n" +"текста.\n" +"\n" +"Параметр ttb - это количество киков, по превышению которого бот\n" +"поставит бан. Укажите вместо положительного числа значение \"0\" или\n" +"\"-\" если не хотите чтобы бот банил нарушителя." + +#: modules/commands/bs_kick.cpp:776 +#, fuzzy +msgid "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Синтаксис: KICK #канал UNDERLINES {ON|OFF} [ttb]\n" +"\n" +"Активируйте данную опцию с нужными вам значениями, если хотите\n" +"чтобы бот кикал посетителей за чрезмерное использование подчеркиваний.\n" +"\n" +"Параметр ttb - это количество киков, по превышению которого бот\n" +"поставит бан. Укажите вместо положительного числа значение \"0\" или\n" +"\"-\" если не хотите чтобы бот банил нарушителя." + +#: modules/commands/hs_set.cpp:206 +#, fuzzy +msgid "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." +msgstr "" +"Синтаксис: SETALL <ник> <хостмаска>.\n" +"\n" +"Устанавливает виртуальный хост для всех ников указанной группы.Если\n" +"IRCd вашей сети подерживает виртуальные иденты, можно использовать\n" +"формат SETALL <ник> <идент>@<хостмаска> для установки виртуальных\n" +"идента и хоста одновременно.\n" +"\n" +"Примечание: виртуальный хост устанавливается для всех текущих\n" +"ников указанной группы и не будет автоматически обновлен для нового\n" +"ника, внесенного в группу уже после установки виртуального хоста." + +#: modules/commands/hs_set.cpp:99 +#, fuzzy +msgid "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." +msgstr "" +"Синтаксис: SET <ник> <хостмаска>.\n" +"\n" +"Устанавливает указанный виртуальный хост для указанного ника. Если\n" +"IRCd вашей сети подерживает виртуальные иденты, можно использовать\n" +"формат SET <ник> <идент>@<хостмаска> для установки виртуальных\n" +"идента и хоста одновременно." + +#: modules/commands/os_set.cpp:199 +#, fuzzy +msgid "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" +msgstr "" +"Синтаксис: SET опция параметр\n" +"\n" +"Позволяет настроить различные глобальные опции сервисов.\n" +"Доступные опции:\n" +"\n" +" READONLY активация/деактивация режима read-only (только-чтение)\n" +" LOGCHAN активация/деактивация логирования событий на сервисный канал\n" +" DEBUG активация/деактивация режим отладки (debug mode)\n" +" NOEXPIRE активация/деактивация режима не-истечения\n" +" IGNORE активация/деактивация обработки списка игнора\n" +" LIST просмотр статуса всех вышеперечисленных опций\n" +" SUPERADMIN активация/деактивация режима Супер-Администратора\n" +" (относительно использующего команду)" + +#: modules/commands/ms_set.cpp:235 +#, fuzzy, c-format +msgid "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Синтаксис: SET опция параметры\n" +"\n" +"Позволяет настроить ваши личные опции службы сообщений.\n" +"Валидные опции:\n" +"\n" +" NOTIFY выбор способа уведомления о новых собщениях\n" +" LIMIT установка вашего максимального лимита сообщений\n" +"\n" +"Для более подробной информации о конкретной опции воспользуйтесь\n" +"командой /msg %s HELP SET опция." + +#: modules/commands/ns_set.cpp:33 modules/commands/ns_set.cpp:88 +#, fuzzy +msgid "Sets various nickname options. option can be one of:" +msgstr "" +"Синтаксис: SET опция параметры\n" +"\n" +"Команда SET позволяет вам настроить различные опции ника.\n" +"Список опций:" + +#: modules/commands/ns_set.cpp:237 +msgid "" +"Sets whether services should set channel status modes on you automatically." +msgstr "" + +#: modules/commands/cs_set.cpp:1090 +#, fuzzy +msgid "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." +msgstr "" +"Синтаксис: SET #канал NOEXPIRE {ON | OFF}\n" +"\n" +"Позволяет установить режим не-истечения для указанного канала.\n" +"Активирование этой опции автоматически исключит канал из условий\n" +"истечения его регистрации по времени. Соответственно деактивирование\n" +"режима вернет все на круги своя." + +#: modules/commands/ns_set.cpp:315 +#, fuzzy, c-format +msgid "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." +msgstr "" +"Синтаксис: SASET ник AUTOOP {ON | OFF}\n" +"\n" +"Активирует/деактивирует режим автоматического получения статуса.\n" +"Укажите ON, если хотите что бы сервисы автоматически давали\n" +"владельцу ника статус при входе на канал. Соответственно OFF -\n" +"для отключения." + +#: modules/commands/ns_set.cpp:1145 +#, fuzzy +msgid "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." +msgstr "" +"Синтаксис: SASET ник NOEXPIRE {ON | OFF}\n" +"\n" +"Позволяет исключить указанный ник из условий истечения регистрации\n" +"по времени. Укажите ON, что бы активировать так называемый режим\n" +"'не-истечения'. Параметр OFF снова возвращает ник в режим истечения." + +#: modules/commands/ns_set.cpp:288 +#, fuzzy, c-format +msgid "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." +msgstr "" +"Синтаксис: SET AUTOOP {ON | OFF}\n" +"\n" +"Активирует/деактивирует режим втоматического получения статуса.\n" +"Укажите ON, если хотите что бы сервисы автоматически давали вам\n" +"статус при входе на канал. Соответственно OFF - для отключения." + +#: modules/commands/cs_access.cpp:648 modules/commands/cs_access.cpp:689 +#, fuzzy, c-format +msgid "" +"Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." +msgstr "" +"Неизвестный пункт %s. Для получения списка всех доступных значений см. /msg " +"%s HELP LEVELS DESC" + +#: modules/commands/os_set.cpp:133 +#, fuzzy +msgid "Setting for DEBUG must be ON, OFF, or a positive number." +msgstr "" +"В качестве параметра для опции DEBUG вы должны указать ON, OFF, либо " +"положительное число." + +#: modules/commands/os_set.cpp:162 +#, fuzzy +msgid "Setting for NOEXPIRE must be ON or OFF." +msgstr "" +"В качестве параметра для опции NOEXPIRE вы должны указать либо ON, либо OFF." + +#: modules/commands/os_set.cpp:56 +#, fuzzy +msgid "Setting for READONLY must be ON or OFF." +msgstr "" +"В качестве параметра для опции READONLY вы должны указать либо ON, либо OFF." + +#: modules/commands/os_set.cpp:95 +#, fuzzy +msgid "Setting for super admin must be ON or OFF." +msgstr "" +"В качестве параметра для опции READONLY вы должны указать либо ON, либо OFF." + +#: modules/commands/cs_set.cpp:74 +#, fuzzy +msgid "Should services automatically give status to users" +msgstr " AUTOOP активирование/деактивирование автостатуса" + +#: modules/commands/os_stats.cpp:203 +#, fuzzy +msgid "Show status of Services and network" +msgstr " STATS Запрос информаци о статусе сервисов и сети" + +#: modules/commands/os_logsearch.cpp:152 +#, c-format +msgid "Showed %d/%d matches for %s." +msgstr "" + +#: modules/commands/cs_set.cpp:872 +#, fuzzy +msgid "Sign kicks that are done with the KICK command" +msgstr " SIGNKICK настройка режима \"подписанных киков\"" + +#: modules/commands/cs_set.cpp:921 +#, fuzzy, c-format +msgid "Signed kick option for %s is now off." +msgstr "Режим подписанных киков для канала %s активирован." + +#: modules/commands/cs_set.cpp:913 +#, fuzzy, c-format +msgid "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." +msgstr "" +"Режим подписанных киков для канала %s активирован,\n" +"но будет работать в зависимости от настроек уровней доступа." + +#: modules/commands/cs_set.cpp:906 +#, fuzzy, c-format +msgid "Signed kick option for %s is now on." +msgstr "Режим подписанных киков для канала %s активирован." + +#: modules/commands/cs_set.cpp:1299 +msgid "Signed kicks" +msgstr "Подписанные кики" + +#: modules/commands/ms_rsend.cpp:60 modules/commands/ms_send.cpp:59 +#, fuzzy, c-format +msgid "Sorry, %s currently has too many memos and cannot receive more." +msgstr "" +"Список сообщений для %s переполнен и принимать на данный момент новые он не " +"может." + +#: modules/commands/cs_seen.cpp:294 +#, c-format +msgid "Sorry, I have not seen %s." +msgstr "" + +#: modules/commands/bs_badwords.cpp:404 +#, fuzzy +msgid "Sorry, bad words list modification is temporarily disabled." +msgstr "Извините, изменение базы данных плохих слов временно невозможно." + +#: modules/commands/bs_assign.cpp:30 modules/commands/bs_assign.cpp:98 +#, fuzzy +msgid "Sorry, bot assignment is temporarily disabled." +msgstr "Извините, но возможность настройки опций бота временно недоступна." + +#: modules/commands/bs_bot.cpp:281 modules/commands/bs_assign.cpp:164 +msgid "Sorry, bot modification is temporarily disabled." +msgstr "Извините, изменение настроек ботов временно недоступно." + +#: modules/fantasy.cpp:42 modules/commands/bs_kick.cpp:813 +#: modules/commands/bs_kick.cpp:878 +msgid "Sorry, bot option setting is temporarily disabled." +msgstr "Извините, но возможность настройки опций бота временно недоступна." + +#: modules/commands/bs_set.cpp:115 +#, fuzzy +msgid "Sorry, changing bot options is temporarily disabled." +msgstr "Извините, но возможность настройки опций бота временно недоступна." + +#: modules/commands/cs_xop.cpp:112 modules/commands/cs_xop.cpp:235 +#: modules/commands/cs_xop.cpp:444 +#, fuzzy, c-format +msgid "Sorry, channel %s list modification is temporarily disabled." +msgstr "" +"Извините, но возможность модификации списка AOP'ов временно недоступна." + +#: modules/commands/cs_access.cpp:547 modules/commands/cs_flags.cpp:405 +msgid "Sorry, channel access list modification is temporarily disabled." +msgstr "" +"Извините, но возможность модификации списка доступа канала временно " +"недоступна." + +#: modules/commands/cs_akick.cpp:469 +msgid "Sorry, channel autokick list modification is temporarily disabled." +msgstr "" +"Извините, но возможность модификации списка автокиков канала временно " +"недоступна." + +#: modules/commands/cs_drop.cpp:29 +msgid "Sorry, channel de-registration is temporarily disabled." +msgstr "Извините, возможность удаление каналов временно недоступна." + +#: modules/commands/cs_register.cpp:35 +msgid "Sorry, channel registration is temporarily disabled." +msgstr "Извините, регистрация каналов временно приостановлена." + +#: modules/commands/bs_kick.cpp:181 +msgid "Sorry, kicker configuration is temporarily disabled." +msgstr "" +"Извините, но возможность конфигурации условий киков временно недоступна." + +#: modules/commands/ms_set.cpp:216 +msgid "Sorry, memo option setting is temporarily disabled." +msgstr "Извините, но настройка опций службы сообщений временно невозможна." + +#: include/language.h:116 +#, fuzzy +msgid "Sorry, memo sending is temporarily disabled." +msgstr "Извините, но настройка опций службы сообщений временно невозможна." + +#: modules/commands/ns_drop.cpp:29 +msgid "Sorry, nickname de-registration is temporarily disabled." +msgstr "Извините, но возможность удаления ников временно недоступна." + +#: modules/commands/ns_group.cpp:120 +msgid "Sorry, nickname grouping is temporarily disabled." +msgstr "Извините, но возможность группировки ников временно недоступна." + +#: modules/commands/ns_register.cpp:139 +msgid "Sorry, nickname registration is temporarily disabled." +msgstr "Извините, но регистрация ников временно приостановлена." + +#: modules/commands/ns_access.cpp:33 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d access entries has been reached." +msgstr "Извините, в списке доступа канала может быть не более %d записей." + +#: modules/commands/ns_ajoin.cpp:141 +#, c-format +msgid "Sorry, the maximum of %d auto join entries has been reached." +msgstr "" + +#: modules/commands/ns_cert.cpp:173 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d certificate entries has been reached." +msgstr "Извините, но количество записей в списке доступа не может превышать %d" + +#: modules/commands/ms_ignore.cpp:55 +#, fuzzy, c-format +msgid "Sorry, the memo ignore list for %s is full." +msgstr "Приветствие для %s удалено." + +#: modules/commands/cs_access.cpp:204 modules/commands/cs_flags.cpp:174 +#: modules/commands/cs_xop.cpp:201 +#, fuzzy, c-format +msgid "" +"Sorry, you can only have %d access entries on a channel, including access " +"entries from other channels." +msgstr "Извините, в списке доступа канала может быть не более %d записей." + +#: modules/commands/cs_akick.cpp:177 +#, c-format +msgid "Sorry, you can only have %d autokick masks on a channel." +msgstr "Список автокиков канала может содержать не более %d записей." + +#: modules/commands/bs_badwords.cpp:286 +#, c-format +msgid "Sorry, you can only have %d bad words entries on a channel." +msgstr "Размер базы данных плохих слов не может превышать %d записей." + +#: include/language.h:103 +#, fuzzy, c-format +msgid "Sorry, you have already exceeded your limit of %d channels." +msgstr "Размер базы данных плохих слов не может превышать %d записей." + +#: include/language.h:102 +#, fuzzy, c-format +msgid "Sorry, you have already reached your limit of %d channels." +msgstr "Размер базы данных плохих слов не может превышать %d записей." + +#: modules/commands/os_dns.cpp:218 +msgid "State" +msgstr "" + +#: modules/commands/cs_seen.cpp:117 +msgid "Statistics and maintenance for seen data" +msgstr "" + +#: modules/commands/os_stats.cpp:131 +msgid "Statistics reset." +msgstr "Статистические данные сброшены." + +#: modules/commands/ns_update.cpp:36 +msgid "Status updated (memos, vhost, chmodes, flags)." +msgstr "" +"Статус на сервисах обновлен (мемо-сообщения, вирутальный хост, и т.д.)." + +#: modules/commands/bs_kick.cpp:1432 +msgid "Stop flooding!" +msgstr "Хватит флудить!" + +#: modules/commands/bs_kick.cpp:1448 +msgid "Stop repeating yourself!" +msgstr "Хватит повторов!" + +#: modules/commands/cs_set.cpp:746 +#, fuzzy +msgid "Stricter control of channel founder status" +msgstr " SECUREFOUNDER ограничение на получение статуса владельца канала" + +#: modules/commands/cs_set.cpp:810 +#, fuzzy +msgid "Stricter control of chanop status" +msgstr " SECUREOPS контроль за получением статуса оператора канала" + +#: modules/commands/ns_alist.cpp:75 modules/commands/cs_info.cpp:50 +msgid "Successor" +msgstr "" + +#: modules/commands/cs_set.cpp:1006 +#, fuzzy, c-format +msgid "Successor for %s changed to %s." +msgstr "Наследником канала %s назначен пользователь %s." + +#: modules/commands/cs_set.cpp:1008 +#, c-format +msgid "Successor for %s unset." +msgstr "Наследник канал %s удален." + +#: modules/commands/os_set.cpp:81 +#, fuzzy +msgid "" +"Super admin can not be set because it is not enabled in the configuration." +msgstr "Директива SuperAdmin отключена в конфигурационном файле сервисов." + +#: modules/commands/ns_suspend.cpp:60 +#, fuzzy +msgid "Suspend a given nick" +msgstr " SUSPEND Установка режима саспенда (\"заморозки\") на ник" + +#: modules/commands/cs_suspend.cpp:236 modules/commands/ns_suspend.cpp:250 +#, fuzzy +msgid "Suspend reason" +msgstr "JUPE имя_сервера [причина]" + +#: modules/commands/cs_suspend.cpp:232 modules/commands/ns_suspend.cpp:246 +msgid "Suspended" +msgstr "" + +#: modules/commands/cs_suspend.cpp:234 modules/commands/ns_suspend.cpp:248 +msgid "Suspended by" +msgstr "" + +#: modules/commands/cs_suspend.cpp:238 modules/commands/ns_suspend.cpp:252 +#, fuzzy +msgid "Suspended on" +msgstr " SUSPEND Установка режима саспенда (\"заморозки\") на ник" + +#: modules/commands/ns_suspend.cpp:147 +#, fuzzy +msgid "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." +msgstr "" +"Синтаксис: SUSPEND #канал [причина]\n" +"\n" +"Приостанавливает любую активность указанного канала (замораживает).\n" +"В режиме саспенда, на канал не действуют условия истечения регистрации\n" +"по времени, канал невозможно использовать или удалить. Единственное,\n" +"что владелец все еще может - это изменять настройки своего канала.\n" +"Эффект \"заморозки\" отменяется путем использования команды UNSUSPEND,\n" +"которая полностью восстанавливает активность канала со всеми его\n" +"настройками.\n" +"\n" +"Примечание: в зависимости от настроек сервисов, причина может\n" +"быть параметром как опциональным, так и необходимым." + +#: modules/commands/cs_suspend.cpp:240 modules/commands/ns_suspend.cpp:254 +#, fuzzy +msgid "Suspension expires" +msgstr " %s (does not expire)" + +#: modules/commands/cs_sync.cpp:19 +#, fuzzy +msgid "Sync users channel modes" +msgstr "%s принудительно изменил ваши пользовательские режимы." + +#: modules/commands/cs_sync.cpp:49 +msgid "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." +msgstr "" + +#: modules/commands/hs_group.cpp:42 +#, fuzzy +msgid "Syncs the vhost for all nicks in a group" +msgstr " GROUP Синхронизирует виртуальный хост для всех ников группы" + +#: src/command.cpp:146 +msgid "Syntax" +msgstr "" + +#: modules/commands/ns_group.cpp:373 +#, fuzzy, c-format +msgid "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." +msgstr "" +"Синтаксис: GLIST\n" +"\n" +"Выводит список ников в вашей группе." + +#: modules/commands/ns_group.cpp:363 +#, fuzzy, c-format +msgid "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." +msgstr "" +"Синтаксис: GLIST [ник]\n" +"\n" +"Без параметров, покажет список ников в вашей группе. С параметром,\n" +"покажет все ники находящиеся в группе указанного ника.\n" +"Для использования этой команды необходимы права Администратора сервисов." + +#: modules/commands/os_set.cpp:227 +#, fuzzy +msgid "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." +msgstr "" +"Синтаксис: SET NOEXPIRE {ON | OFF}\n" +"\n" +"Включает или выключает режим глобального \"не-истечения\". В этом\n" +"режиме, все ники, каналы, AKILL'ы и исключения из лимита сессий -\n" +"никогда не истекут, по крайней мере до тех пор, пока эта опция не\n" +"будет отключена.\n" +"\n" +"Активирование данной опции эквивалентно запуску сервисов с ключом\n" +"-noexpire." + +#: modules/commands/ms_set.cpp:287 +#, fuzzy, c-format +msgid "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." +msgstr "" +"Синтаксис: SET LIMIT [#канал] предел\n" +"\n" +"Позволяет ограничить максимальное количество сообщений, которое вы\n" +"(или канал) можете принять. Установка значения в 0 полностью отключит\n" +"возможность принятия сообщений.\n" +"Максимально допустимое значение: %d." + +#: modules/commands/ms_set.cpp:267 +#, fuzzy, c-format +msgid "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." +msgstr "" +"Синтаксис: SET LIMIT [пользователь | #канал] {предел | NONE} [HARD]\n" +"\n" +"Устанавливает лимит на максимальное количество сообщений, которое\n" +"пользователь (или канал) смогут принимать. Установка лимита равным\n" +"0 отключит возможность принятия сообщения вообще, установка в NONE\n" +"разрешает пользователю принимать и сохранять столько сообщений,\n" +"сколько он пожелает. Если вы не укажете пользователя или канал,\n" +"настройки буду применены относительно вас.\n" +"\n" +"Дополнительный параметр HARD запретит указанному пользователю\n" +"изменять свой лимит сообщений. Соответственно установка лимита без\n" +"параметра HARD отменяет эффект запрета и разрешает пользователю\n" +"настраивать свой лимит сообщений.\n" +"\n" +"Расширенное использование команды SET LIMIT доступно только для\n" +"Администраторов сервисов. Обычные пользователи могуть менять лимит\n" +"только для себя или для канала, на котором у них есть соответствующие\n" +"привилегии. Они не могут удалить свой лимит, не могут установить\n" +"лимит выше %d, и не могут использовать опцию HARD." + +#: modules/commands/os_set.cpp:208 +#, fuzzy, c-format +msgid "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." +msgstr "" +"Синтаксис: SET LIST\n" +"\n" +"Отображает статус различных сервисных настроек (вкл/выкл)." + +#: modules/commands/os_set.cpp:234 +#, fuzzy +msgid "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." +msgstr "" +"Синтаксис: SET NOEXPIRE {ON | OFF}\n" +"\n" +"Включает или выключает режим глобального \"не-истечения\". В этом\n" +"режиме, все ники, каналы, AKILL'ы и исключения из лимита сессий -\n" +"никогда не истекут, по крайней мере до тех пор, пока эта опция не\n" +"будет отключена.\n" +"\n" +"Активирование данной опции эквивалентно запуску сервисов с ключом\n" +"-noexpire." + +#: modules/commands/ms_set.cpp:246 +#, fuzzy +msgid "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." +msgstr "" +"Синтаксис: SET NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +"\n" +"Данная опция позволяет настроить ваш личный метод уведомления о\n" +"новых сообщениях, посланных вам кем-либо.\n" +"Доступные режимы:\n" +" ON уведомление будет поступать сразу, как только вы\n" +" идентифицируетесь к нику, снимете с себя статус\n" +" /AWAY или кто-то отправит вам новое сообщение.\n" +" LOGON уведомление будет поступать сразу, как только вы\n" +" идентифицируетесь к нику или снимете с себя статус\n" +" /AWAY (отошел).\n" +" NEW уведомление будет поступать сразу, как только кто-то\n" +" отправит вам новое сообщение.\n" +" MAIL You will be notified of memos by email aswell as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF уведомлений о получении новых сообщений поступать\n" +" не будет\n" +"\n" +"Параметр ON является комбинацией значений LOGON и NEW." + +#: modules/commands/os_set.cpp:212 +#, fuzzy +msgid "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." +msgstr "" +"Синтаксис: SET READONLY {ON | OFF}\n" +"\n" +"Включает или выключает глобальный режим READONLY - только-чтение.\n" +"Работа сервисов в данном режиме запрещает обычным пользователям\n" +"изменять какие-либо сервисные данные, например - списки доступа для\n" +"ников или каналов, их настройки и т. д. Тем не менее, IRC-операторы\n" +"с достаточными привилегиями на сервисах смогут модифицировать список\n" +"AKILL'ов и удалять или запрещать ники и каналы, но все эти изменения\n" +"не будут сохранены до тех пор, пока режим READONLY активен. Что бы\n" +"сохранить все изменения, сделанные во время работы сервисов в этом\n" +"режиме, вы должны деактивировать режим только-чтения прежде, чем\n" +"работа сервисов будет завершена или они будут перезапущены.\n" +"\n" +"Активирование данной опции эквивалентно запуску сервисов с ключом\n" +"-readonly." + +#: modules/commands/os_set.cpp:243 +#, fuzzy +msgid "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." +msgstr "" +"Синтаксис: SET SUPERADMIN {ON | OFF}\n" +"\n" +"Режим Супер-Администратора не влияет на саму работу сервисов как\n" +"таковую, однако его активирование влияет на условия проверки уровня\n" +"доступа пользователя к тем или иным функциям. В частности, данный\n" +"режим предоставляет использовавшему его Руту сервисов неограниченные\n" +"привилегии на сервисах, например такие, как статус владельца на всех\n" +"каналах сети, и т. п.\n" +"\n" +"Эта опция не постоянная и должна использоваться только при крайней\n" +"необходимости. Отключите ее сразу, как только перестанете нуждаться\n" +"в ней." + +#: modules/commands/ns_identify.cpp:107 +#, fuzzy, c-format +msgid "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." +msgstr "" +"Синтаксис: IDENTIFY [account] пароль\n" +"\n" +"Позволяет вам идентифицироваться на %s к зарегистрированному\n" +"ранее нику. Большинство сервисных команд, такие как SET, OP, BAN\n" +"и т. д., требуют идентификации перед использованием. В качестве\n" +"пароля вы должны указать тот самый пароль, который указывали при\n" +"регистрации вашего ника." + +#: modules/commands/cs_invite.cpp:91 +#, fuzzy, c-format +msgid "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Синтаксис: INVITE #канал\n" +"\n" +"Заставляет %s пригласить вас на указанный канал.\n" +"\n" +"По-умолчанию, данная команда может быть использована AOP'ами или\n" +"лицами с уровнем доступа 5 и выше." + +#: modules/commands/cs_unban.cpp:103 +#, fuzzy, c-format +msgid "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Синтаксис: UNBAN #канал [nick]\n" +"\n" +"Remove all bans preventing a user from entering a channel\n" +"user from entering the given channel.\n" +"\n" +"По-умолчанию, данная команда может быть использована AOP'ами\n" +"или лицами с уровнем доступа 5 и выше." + +#: modules/commands/os_jupe.cpp:56 +#, fuzzy +msgid "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." +msgstr "" +"Синтаксис: JUPE сервер [причина]\n" +"\n" +"Позволяет \"джупнуть\" указанный сервер с указанной причиной.\n" +"В данном случае эффект джупа состоит в следующем: сервисы посылают\n" +"SQUIT указанному серверу, тем самым отключая его от сети, а затем\n" +"тут же создают виртуальный сервер с тем же именем, и причиной в\n" +"качестве описания сервера (server description). Данный фальшивый\n" +"сервер не позволит присоединиться к сети реальному, джупнутому\n" +"серверу. Отменить эффект вы можете путем SQUIT'а виртуальной копии\n" +"джупнутого сервера.\n" +"Примечание: параметр причина является не обязательным, если вы его\n" +"не укажете, будет использована стандартная, вида: \"Juped by <ник>\"." + +#: modules/commands/cs_seen.cpp:261 +msgid "Tells you about the last time a user was seen" +msgstr "" + +#: modules/commands/os_shutdown.cpp:19 +#, fuzzy +msgid "Terminate Services WITHOUT saving" +msgstr " SHUTDOWN Завершить работу сервисов с сохранением базы данных" + +#: modules/commands/os_shutdown.cpp:73 +#, fuzzy +msgid "Terminate services with save" +msgstr " SHUTDOWN Завершить работу сервисов с сохранением базы данных" + +#: modules/commands/os_news.cpp:156 +msgid "Text" +msgstr "" + +#: modules/commands/cs_access.cpp:576 +msgid "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." +msgstr "" + +#: modules/commands/cs_access.cpp:587 +msgid "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." +msgstr "" + +#: modules/commands/cs_access.cpp:593 +msgid "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." +msgstr "" + +#: modules/commands/cs_flags.cpp:447 +msgid "" +"The CLEAR command clears the channel access list. This requires channel " +"founder access." +msgstr "" + +#: modules/commands/cs_seen.cpp:173 +#, c-format +msgid "" +"The CLEAR command lets you clean the database by removing all entries from " +"the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." +msgstr "" + +#: modules/commands/bs_badwords.cpp:438 +#, fuzzy +msgid "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." +msgstr "" +"Синтаксис: HOP #канал ADD ник\n" +" HOP #канал DEL {ник | номер_записи | список_записей}\n" +" HOP #канал LIST [маска | список_записей]\n" +" HOP #канал CLEAR\n" +"\n" +"Позволяет управлять списком HOP'ов (полуоператоров) вашего канала.\n" +"Привилегии HOP'а дают пользователю возможность получить статус хопа\n" +"сразу при входе на канал, или запросить его вручную, через сервисы.\n" +"\n" +"Команда HOP ADD добавляет указанный ник в список HOP'ов.\n" +"\n" +"Команда HOP DEL удаляет указанный ник из списка HOP'ов. В качестве\n" +"параметра вы можете указать не только ник, но и конкретный номер\n" +"записи или список записей (см. примеры использования LIST ниже).\n" +"\n" +"Команда HOP LIST выводит текущий список HOP'ов канала. В качестве\n" +"дополнительного параметра, вы можете указать символьную маску, что\n" +"позволит вам получить список с конкретными никами, попадающими под\n" +"эту маску, или же, вы можете указать список записей.\n" +"\n" +"Например:\n" +"\n" +" HOP #канал LIST 2-5,7-9\n" +" отобразит все записи со 2-ой по 5-ую, и с 7-ой по 9-ю.\n" +" HOP #канал LIST *vas*\n" +" отобразит все записи, которые содержат подстроку \"vas\"\n" +"\n" +"Команда HOP CLEAR позволяет полностью очистить список HOP'ов.\n" +"\n" +"Команды HOP ADD, HOP DEL и HOP LIST могут использовать AOP'ы\n" +"канала или выше, команду HOP CLEAR может использовать только\n" +"владелец канала.\n" +"\n" +"Помните, что данная команда работает только в случае использования\n" +"системы привилегий xOP. Если вы используете систему LEVELS, все\n" +"изменения списка доступа канала должны производится посредством\n" +"команды ACCESS. Для более подробной информации по использованию\n" +"команды ACCESS и системы привилегий xOP см. справочную информацию\n" +"по /msg %s HELP ACCESS и /msg %s HELP SET XOP." + +#: modules/commands/cs_entrymsg.cpp:241 +msgid "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:253 +msgid "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:245 +msgid "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:250 +msgid "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." +msgstr "" + +#: modules/commands/ns_set.cpp:713 +msgid "The IMMED option is not available on this network." +msgstr "Возможность установки режима IMMED в вашей IRC-сети недоступна." + +#: modules/commands/cs_access.cpp:821 +#, fuzzy, c-format +msgid "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." +msgstr "" +"Синтаксис: LEVELS #канал SET тип [уровень|FOUNDER]\n" +" LEVELS #канал {DIS | DISABLE} тип\n" +" LEVELS #канал LIST\n" +" LEVELS #канал RESET\n" +"\n" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +"\n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it).\n" +"\n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel (see\n" +"HELP ACCESS LEVELS).\n" +"\n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." + +#: modules/commands/cs_flags.cpp:442 +msgid "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." +msgstr "" + +#: modules/commands/cs_flags.cpp:435 +msgid "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access " +"list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. " +"You are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of " +"what your access is." +msgstr "" + +#: modules/commands/cs_seen.cpp:172 +msgid "" +"The STATS command prints out statistics about stored nicks and memory usage." +msgstr "" + +#: modules/commands/ns_register.cpp:291 +#, fuzzy +msgid "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." +msgstr "" +"Используйте команду /msg %s SET EMAIL email-адрес чтобы установить email-" +"адрес.\n" +"Не волнуйтесь, данный email-адрес знать будете лишь вы и Администрация сети." + +#: modules/commands/cs_log.cpp:258 +#, c-format +msgid "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." +msgstr "" + +#: modules/commands/cs_ban.cpp:64 +#, fuzzy, c-format +msgid "The %s list for %s is full." +msgstr "Приветствие для %s удалено." + +#: modules/commands/os_sxline.cpp:220 +#, fuzzy, c-format +msgid "The %s list has been cleared." +msgstr "Список AKILL'ов полностью очищен." + +#: modules/commands/os_akill.cpp:377 +msgid "The AKILL list has been cleared." +msgstr "Список AKILL'ов полностью очищен." + +#: modules/commands/os_defcon.cpp:136 modules/commands/os_defcon.cpp:225 +#, fuzzy, c-format +msgid "The Defcon level is now at: %d" +msgstr "Уровень DEFCON теперь равен %d" + +#: modules/commands/ns_info.cpp:171 +#, c-format +msgid "The E-mail address of %s will now be hidden from %s INFO displays." +msgstr "" +"С этого момента, email-адрес ника %s будет скрыт из информации по %s INFO." + +#: modules/commands/ns_info.cpp:172 +#, c-format +msgid "The E-mail address of %s will now be shown in %s INFO displays." +msgstr "" +"Теперь, email-адрес ника %s будет показываться в информации по %s INFO." + +#: modules/commands/cs_flags.cpp:449 +msgid "The available flags are:" +msgstr "" + +#: modules/commands/os_defcon.cpp:240 +#, fuzzy +msgid "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." +msgstr "" +"Синтаксис: DEFCON [1|2|3|4|5]\n" +"\n" +"Система DEFCON позволяет вам устанавливать определенные глобальные\n" +"ограничения в сети со стороны сервисов. Данные ограничения могут\n" +"касаться не только работы самих сервисов, но и функционирования сети\n" +"в целом, что, порою, весьма полезно при разного рода атаках на сеть." + +#: modules/ns_maxemail.cpp:51 +#, c-format +msgid "The email address %s has reached its usage limit of %d users." +msgstr "" + +#: modules/ns_maxemail.cpp:49 +#, c-format +msgid "The email address %s has reached its usage limit of 1 user." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:142 +#, fuzzy, c-format +msgid "The entry message list for %s is full." +msgstr "Приветствие для %s удалено." + +#: modules/commands/cs_access.cpp:796 +msgid "The following feature/function names are available:" +msgstr "" + +#: modules/commands/cs_access.cpp:584 +msgid "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." +msgstr "" + +#: modules/commands/os_session.cpp:240 +#, fuzzy, c-format +msgid "" +"The host %s currently has %d sessions with a limit of %d because it matches " +"entry: %s." +msgstr "" +"Количество сессий с хоста %s: %d, допустимый максимум для данного хоста: %d" + +#: modules/commands/ms_check.cpp:54 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has been read." +msgstr "" +"Последнее сообщение, которое вы посылали для %s (а было это %s) уже " +"прочитано." + +#: modules/commands/ms_check.cpp:52 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has not yet been read." +msgstr "" +"Последнее сообщение, которое вы посылали для %s (а было это %s) еще не " +"прочитано." + +#: modules/commands/ns_info.cpp:189 +#, c-format +msgid "The last quit message of %s will now be hidden from %s INFO displays." +msgstr "" +"Последнее quit-сообщение для %s теперь будет скрыто из информации по %s INFO." + +#: modules/commands/ns_info.cpp:190 +#, c-format +msgid "The last quit message of %s will now be shown in %s INFO displays." +msgstr "" +"Последнее quit-сообщение для %s теперь будет показываться в информации по %s " +"INFO." + +#: modules/commands/ns_info.cpp:177 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." +msgstr "" +"Последняя маска (идент@хост) для %s теперь будет скрыта из информации по %s " +"INFO." + +#: modules/commands/ns_info.cpp:178 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." +msgstr "" +"Последняя маска (идент@хост) для %s теперь будет показываться в информации " +"по %s INFO." + +#: modules/commands/cs_enforce.cpp:190 +#, fuzzy, c-format +msgid "The limit on %s is not valid." +msgstr "Лимит сообщений для %s не может быть изменен." + +#: modules/commands/os_forbid.cpp:193 +msgid "The mask must contain at least one non wildcard character." +msgstr "" + +#: modules/commands/ms_set.cpp:153 +#, c-format +msgid "The memo limit for %s may not be changed." +msgstr "Лимит сообщений для %s не может быть изменен." + +#: modules/commands/cs_mode.cpp:347 +#, fuzzy, c-format +msgid "The mode lock list of %s is full." +msgstr "Приветствие для %s удалено." + +#: modules/commands/ns_set.cpp:355 +#, c-format +msgid "The new display MUST be a nickname of the nickname group %s." +msgstr "" + +#: include/language.h:98 +#, fuzzy, c-format +msgid "The new display is now %s." +msgstr "Уровень DEFCON теперь равен %d" + +#: modules/commands/os_svs.cpp:57 +#, c-format +msgid "The nick %s is now being changed to %s." +msgstr "Ник пользователя %s был изменен на %s." + +#: modules/commands/bs_bot.cpp:149 +msgid "The old information is the same as the new information specified." +msgstr "" + +#: modules/commands/os_info.cpp:157 +#, fuzzy, c-format +msgid "The oper info already exists on %s." +msgstr "Бот с ником %s уже существует." + +#: modules/commands/os_info.cpp:147 +#, fuzzy, c-format +msgid "The oper info list for %s is full." +msgstr "Приветствие для %s удалено." + +#: modules/commands/ns_info.cpp:183 +#, c-format +msgid "" +"The services access status of %s will now be hidden from %s INFO displays." +msgstr "" +"Уровень доступа к сервисам для %s теперь будет скрыт из информации по %s " +"INFO." + +#: modules/commands/ns_info.cpp:184 +#, c-format +msgid "The services access status of %s will now be shown in %s INFO displays." +msgstr "" +"Уровень доступа к сервисам для %s теперь будет показываться в информации по " +"%s INFO." + +#: modules/commands/os_session.cpp:433 +#, fuzzy +msgid "The session exception list is empty." +msgstr " EXCEPTION Управление списком исключений из лимита сессий" + +#: modules/commands/ns_recover.cpp:121 +msgid "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:195 +#, c-format +msgid "There are %d memos on channel %s." +msgstr "%d сообщений на канале %s." + +#: modules/commands/bs_botlist.cpp:47 +msgid "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" +msgstr "" +"Список доступных ботов пуст.\n" +"По вопросам создания ботов обращайтесь к Администраторам сервисов." + +#: modules/commands/os_dns.cpp:213 +msgid "There are no configured servers." +msgstr "" + +#: modules/commands/os_forbid.cpp:392 +#, fuzzy, c-format +msgid "There are no forbids of type %s." +msgstr "%d сообщений на канале %s." + +#: modules/commands/ns_group.cpp:162 +#, fuzzy +msgid "There are too many nicks in your group." +msgstr " DELALL Удаление вирт. хоста у всех ников указанной группы" + +#: modules/commands/cs_log.cpp:123 +#, fuzzy, c-format +msgid "There currently are no logging configurations for %s." +msgstr " RELOAD Перезагрузка конфигурационного файла сервисов" + +#: modules/pseudoclients/memoserv.cpp:193 +#, c-format +msgid "There is %d memo on channel %s." +msgstr "%d сообщение на канале %s." + +#: include/language.h:110 +#, fuzzy, c-format +msgid "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." +msgstr "Напишите /msg %s READ %d чтобы прочитать его." + +#: modules/commands/bs_assign.cpp:132 +#, c-format +msgid "There is no bot assigned to %s anymore." +msgstr "Бот с канала %s успешно удален." + +#: modules/commands/os_news.cpp:33 +msgid "There is no logon news." +msgstr "Список новостей пуст." + +#: modules/commands/os_news.cpp:43 +msgid "There is no oper news." +msgstr "Список опер-новостей пуст." + +#: modules/commands/os_news.cpp:53 +msgid "There is no random news." +msgstr "Список случайных новостей пуст." + +#: modules/commands/os_config.cpp:41 +#, fuzzy, c-format +msgid "There is no such configuration block %s." +msgstr " RELOAD Перезагрузка конфигурационного файла сервисов" + +#: modules/commands/cs_mode.cpp:706 +#, fuzzy, c-format +msgid "There is no such mode %s." +msgstr "Список опер-новостей пуст." + +#: modules/commands/ms_set.cpp:52 +msgid "There's no email address set for your nick." +msgstr "Для вашего ника не установлен email-адрес." + +#: modules/commands/os_forbid.cpp:304 modules/commands/os_forbid.cpp:496 +#, fuzzy, c-format +msgid "This channel has been forbidden: %s" +msgstr "Этот канал был зарегистрирован с помощью %s" + +#: modules/commands/cs_suspend.cpp:121 +#, fuzzy +msgid "This channel has been suspended." +msgstr "Использование данного канала запрещено." + +#: modules/commands/cs_suspend.cpp:232 +#, fuzzy +msgid "This channel is suspended." +msgstr "Использование данного канала запрещено." + +#: modules/commands/cs_suspend.cpp:268 +msgid "This channel may not be used." +msgstr "Использование данного канала запрещено." + +#: modules/commands/os_dns.cpp:702 +msgid "" +"This command allows managing DNS zones used for controlling what servers " +"users\n" +"are directed to when connecting. Omitting all parameters prints out the " +"status of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to " +"this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, " +"the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given " +"zones." +msgstr "" + +#: modules/commands/hs_group.cpp:72 +#, fuzzy +msgid "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." +msgstr "" +"Синтаксис: GROUP\n" +"\n" +"Эта команда позволяет пользователям установить виртуальный хост\n" +"с их ТЕКУЩЕГО ника на все ники группы." + +#: modules/commands/ns_register.cpp:299 +msgid "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." +msgstr "" + +#: modules/m_rewrite.cpp:145 +#, c-format +msgid "This command is an alias to the command %s." +msgstr "" + +#: modules/commands/ns_register.cpp:95 +#, fuzzy +msgid "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." +msgstr "" +"Синтаксис: CONFIRM auth-код\n" +"\n" +"Данная команда необходима, что бы завершить второй шаг регистрации\n" +"ника - подтверждение. После выполнения данного тербования, ваш ник\n" +"будет зарегистрирован на %s.\n" +"Кодовая фраза, которая указывается в качестве параметра, высылается\n" +"на ваш e-mail в первой части процесса регистрации ника. Для более\n" +"подробной информации см. /msg %s HELP REGISTER\n" +"\n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." + +#: modules/commands/os_modinfo.cpp:70 +#, fuzzy +msgid "This command lists information about the specified loaded module." +msgstr "" +"Синтаксис: MODINFO имя_файла\n" +"\n" +"Выводит подробную информацию о конкретном загруженном модуле." + +#: modules/commands/hs_list.cpp:136 +#, fuzzy +msgid "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." +msgstr "" +"Синтаксис: LIST [<маска>|<#X-Y>]\n" +"\n" +"Выводит список всех виртуальных хостов и ников, на которые эти хосты\n" +"установлены.\n" +"\n" +"В качестве дополнительного параметра, вы можете указать маску поиска,\n" +"что позволит вам получить только совпадающие по символьной маске\n" +"записи. Помимо этого, вы, так же, можете указать спискок записей в\n" +"формате #X-Y, где X - номер стартовой запись, а Y - конечной.\n" +"\n" +"Например:\n" +"\n" +" LIST *invis*\n" +" выведет список записей, ник или вирт. хост которых содержит\n" +" подстроку *invis* (invisible, covinis и т. д.)\n" +"\n" +" LIST #2-5\n" +" выведет список записей со 2-ой по 5-ю.\n" +"\n" +"Лимит одновременно показываемых записей ограничен числом, указанным\n" +"в конфигурационном файле сервисов директивой NSListMax." + +#: modules/commands/os_module.cpp:45 +#, fuzzy +msgid "" +"This command loads the module named modname from the modules\n" +"directory." +msgstr "" +"Синтаксис: MODLOAD имя_файла\n" +"\n" +"Позволяет загрузить какой-либо дополнительный модуль из директории\n" +"с модулями (modules/). " + +#: modules/commands/ns_group.cpp:201 +#, fuzzy +msgid "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." +msgstr "" +"Синтаксис: GROUP главный_ник пароль\n" +"\n" +"Данная команда позволяет вам присоединить ваш текущий ник к группе\n" +"главного_ника. В качестве пароля вам необходимо указать пароль\n" +"главного ника.\n" +"\n" +"Использование групп дает вам возможность объединить несколько ников\n" +"в одну группу с едиными настройками и привилегиями на каналах,\n" +"едиными ассоциированными данными и паролем, единым списком сообщений.\n" +"Группа существует и активна пока используется. Даже если вы удалите\n" +"один из ников группы, все вышеописанные данные (ну и сама регистрация)\n" +"будут существовать до тех пор, пока в группе есть хотя бы 1 ник.\n" +"\n" +"Вы можете использовать эту команду даже если ваш текущий ник все еще\n" +"незарегистрирован. В противном случае, для использования описываемой\n" +"команды вам необходимо будет идентифицироваться к группируемому нику.\n" +"См. /msg %s HELP IDENTIFY для более подробной информации.\n" +"Примечание: возможность группировки уже зарегистрированных ников\n" +"может быть недоступна в вашей IRC-сети.\n" +"\n" +"Оптимальным вариантом будет объединение еще не зарегистрированных\n" +"ников с уже зарегистрированным (они указываются как главный ник).\n" +"В противном случае, все данные группируемого ника будут уничтожены\n" +"в процессе объединения двух ников. Именно поэтому, слияние групп -\n" +"невозможно. Один зарегистрированный ник, не состоящий ни в одной\n" +"группе - уже образует группу. И находится в двух группах этот ник\n" +"никак неможет.\n" +"Примечание 2: у всех ников в группе - единый пароль." + +#: modules/commands/ns_ajoin.cpp:292 +msgid "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." +msgstr "" + +#: modules/commands/ns_set.cpp:345 modules/commands/ns_set.cpp:669 +msgid "" +"This command may not be used on this network because nickname ownership is " +"disabled." +msgstr "" + +#: modules/commands/os_module.cpp:118 +#, fuzzy +msgid "This command reloads the module named modname." +msgstr "" +"Синтаксис: MODLOAD имя_файла\n" +"\n" +"Позволяет загрузить какой-либо дополнительный модуль из директории\n" +"с модулями (modules/). " + +#: modules/commands/hs_request.cpp:344 +msgid "This command retrieves the vhost requests." +msgstr "" + +#: modules/commands/os_logsearch.cpp:159 +msgid "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." +msgstr "" + +#: modules/commands/cs_status.cpp:106 +msgid "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." +msgstr "" + +#: modules/commands/ns_group.cpp:285 +#, fuzzy +msgid "" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." +msgstr "" +"Syntax: UNGROUP [nick]\n" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, url, and icq. Everything\n" +"else is reset. You may not ungroup yourself if there is only one\n" +"nick in your group." + +#: modules/commands/os_module.cpp:168 +#, fuzzy +msgid "This command unloads the module named modname." +msgstr "" +"Синтаксис: MODLOAD имя_файла\n" +"\n" +"Позволяет загрузить какой-либо дополнительный модуль из директории\n" +"с модулями (modules/). " + +#: modules/commands/ns_register.cpp:353 +msgid "This command will resend you the registration confirmation email." +msgstr "" + +#: include/language.h:90 +#, c-format +msgid "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" +msgstr "" + +#: modules/commands/os_forbid.cpp:469 +#, fuzzy, c-format +msgid "This nickname has been forbidden: %s" +msgstr "Дополнительно: этот ник находится в режиме саспенда по причине: %s" + +#: modules/commands/ns_recover.cpp:99 +#, fuzzy, c-format +msgid "This nickname has been recovered by %s." +msgstr "Дополнительно: этот ник находится в режиме саспенда по причине: %s" + +#: modules/commands/ns_recover.cpp:77 +#, c-format +msgid "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." +msgstr "" + +#: include/language.h:95 +#, fuzzy +msgid "This nickname has been registered; you may not use it." +msgstr "Этот канал был зарегистрирован с помощью %s" + +#: modules/commands/ns_suspend.cpp:246 +#, fuzzy +msgid "This nickname is suspended." +msgstr "Использование данного канала запрещено." + +#: include/language.h:92 +#, c-format +msgid "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." +msgstr "" + +#: modules/commands/ms_read.cpp:95 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %d" +msgstr "" +"Сообщение %d от %s (%s). Чтобы удалить его, напишите команду: /msg %s DEL %s " +"%d" + +#: modules/commands/ms_read.cpp:93 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %s %d" +msgstr "" +"Сообщение %d от %s (%s). Чтобы удалить его, напишите команду: /msg %s DEL %s " +"%d" + +#: modules/commands/bs_kick.cpp:791 +msgid "To protect ops against bot kicks" +msgstr "" + +#: modules/commands/bs_kick.cpp:856 +msgid "To protect voices against bot kicks" +msgstr "" + +#: modules/commands/cs_list.cpp:46 +msgid "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." +msgstr "" +"Что бы найти канал, начинающийся с символа #, просто укажите его\n" +"название без #. Например anope вместо #anope." + +#: modules/commands/os_logsearch.cpp:139 +#, fuzzy, c-format +msgid "Too many results for %s." +msgstr "Список доступа для %s:" + +#: modules/extra/stats/cs_fantasy_top.cpp:149 +#, c-format +msgid "Top %i of %s" +msgstr "" + +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Topic" +msgstr "Блокировка топика" + +#: modules/commands/cs_topic.cpp:258 +#, fuzzy +msgid "Topic lock" +msgstr "Блокировка топика" + +#: modules/commands/cs_topic.cpp:114 +#, fuzzy, c-format +msgid "Topic lock option for %s is now off." +msgstr "Режим блокировки топика для канала %s активирован." + +#: modules/commands/cs_topic.cpp:97 +#, fuzzy, c-format +msgid "Topic lock option for %s is now on." +msgstr "Режим блокировки топика для канала %s активирован." + +#: modules/commands/cs_topic.cpp:256 +#, fuzzy +msgid "Topic retention" +msgstr "Хранение топика" + +#: modules/commands/cs_topic.cpp:60 +#, fuzzy, c-format +msgid "Topic retention option for %s is now off." +msgstr "Режим хранения топика для канала %s активирован." + +#: modules/commands/cs_topic.cpp:54 +#, fuzzy, c-format +msgid "Topic retention option for %s is now on." +msgstr "Режим хранения топика для канала %s активирован." + +#: modules/commands/cs_topic.cpp:265 +msgid "Topic set by" +msgstr "" + +#: modules/commands/bs_kick.cpp:1323 +msgid "Turn caps lock OFF!" +msgstr "Выключи CapsLOCK!" + +#: modules/extra/stats/m_chanstats.cpp:17 +#: modules/extra/stats/m_chanstats.cpp:71 +#, fuzzy +msgid "Turn chanstats statistics on or off" +msgstr " SECURE активирование/деактивирование режима безопасности" + +#: modules/commands/ns_set.cpp:1009 +#, fuzzy +msgid "Turn nickname security on or off" +msgstr " SECURE активирование/деактивирование режима безопасности" + +#: modules/commands/ns_set.cpp:655 +#, fuzzy +msgid "Turn protection on or off" +msgstr " KILL активирование/деактивирование режима защиты" + +#: modules/commands/ns_list.cpp:264 +#, fuzzy, c-format +msgid "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Синтаксис: SASET ник PRIVATE {ON | OFF}\n" +"\n" +"Активируетдеактивирует опцию приватности указанного ника.\n" +"Включенная таким образом PRIVATE скрывает отображение ника в\n" +"списках по %s LIST.\n" +"Примечание: тем не менее любой, кто знает точное написание ника,\n" +"имеет возможность получить информацию о нем используя команду INFO." + +#: modules/commands/ns_list.cpp:236 +#, fuzzy, c-format +msgid "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Синтаксис: SET PRIVATE {ON | OFF}\n" +"\n" +"Активируетдеактивирует опцию приватности вашего ника на %s.\n" +"Включенная таким образом PRIVATE скрывает ваш ник из информации\n" +"по %s LIST.\n" +"Примечание: тем не менее, любой, кто знает ваш ник, имеет возможность\n" +"получить информацию о вас используя команду INFO." + +#: modules/commands/ns_set.cpp:1059 modules/commands/ns_set.cpp:1088 +#, fuzzy, c-format +msgid "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." +msgstr "" +"Синтаксис: SET SECURE {ON | OFF}\n" +"\n" +"Активирует/деактивирует режим безопасности для вашего ника. При\n" +"включенной опции SECURE вы должны идентифицироваться на %s \n" +"с помощью пароля, чтобы подтвердить что именно вы владелец текущего\n" +"используемого вами ника. При этом на список хостмасок ника сервисы\n" +"внимания не обращают.\n" +"Отключение этой опции позволит вам идентифицироваться на %s\n" +"через список масок ника, однако, максимально допустимый статус в\n" +"данном случае будет равняться 2.\n" +"\n" +"Стоит также заметить, что сервисы не будут принудительно менять ваш\n" +"ник, если в ACCESS-списке зарегистрированного ника есть хотя бы одна\n" +"хостмаска, совпадающая с вашей текущей. Режим опции KILL при этом\n" +"значения не имеет." + +#: modules/extra/stats/m_chanstats.cpp:142 +#, fuzzy +msgid "Turns chanstats channel statistics ON or OFF for this user." +msgstr " SECURE активирование/деактивирование режима безопасности" + +#: modules/extra/stats/m_chanstats.cpp:61 +#: modules/extra/stats/m_chanstats.cpp:119 +#, fuzzy +msgid "Turns chanstats statistics ON or OFF." +msgstr " SECURE активирование/деактивирование режима безопасности" + +#: modules/commands/ns_set.cpp:772 +#, fuzzy, c-format +msgid "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Синтаксис: SASET ник KILL {ON | QUICK | IMMED | OFF}\n" +"\n" +"Активирует/деактивирует автоматическую защиту для указанного ника.\n" +"Активирование защиты ника позволяет вам лимитировать период времени\n" +"на ввод пароля идентификации. ON выставляет период в 60 секунд,\n" +"по истечении которого %s принудительно сменит ник лже-владельца,\n" +"попытавшегося взять указанный ник.\n" +"\n" +"Параметр QUICK позволяет назначить 20-секундный период.\n" +"Параметр IMMED позволяет отключить этот период вообще. Помните,\n" +"что активирование данной опции может привести к тому, что указанный\n" +"ник не сможет взять никто! Не используйте эту опцию без крайней\n" +"необходимости, а перед ее включением убедитесь, что ACCESS-список\n" +"указанного ника содержит хотя бы одну из хостмасок, с которой его\n" +"владелец заходит в IRC.\n" +"Примечание: возможность установки метода защиты IMMED может быть\n" +"отключена в вашей IRC-сети." + +#: modules/commands/ns_set.cpp:738 +#, fuzzy, c-format +msgid "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Синтаксис: SET KILL {ON | QUICK | IMMED | OFF}\n" +"\n" +"Активирует/деактивирует автоматическую защиту для вашего ника.\n" +"Активирование защиты ника позволяет вам лимитировать период времени\n" +"на ввод пароля для идентификации. ON выставляет период в 60 секунд,\n" +"по истечении которого сервисы принудительно сменят ник лже-владельца\n" +"(или ваш, если вы не успели ввести пароль вовремя).\n" +"\n" +"Параметр QUICK позволяет назначить 20-секундный период.\n" +"\n" +"Параметр IMMED позволяет отключить этот период вообще. Помните,\n" +"что активирование этой опции может привести к потере вашего ника!\n" +"Не используйте эту опцию без крайней на то необходимости, а перед ее\n" +"включением, убедитесь, что ACCESS-список вашего ника содержит хотя\n" +"бы одну из хостмасок, которая совпадает с вашей текущей.\n" +"Примечание: возможность установки метода защиты IMMED может быть\n" +"отключена в вашей IRC-сети." + +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_forbid.cpp:358 +msgid "Type" +msgstr "" + +#: modules/commands/ns_set.cpp:62 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Для более подробной информации о какой-либо конкретной опции, см.\n" +"справку по /msg %s HELP опция" + +#: modules/commands/bs_kick.cpp:151 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." +msgstr "" +"Чтобы получить справочную информацию по отдельно взятой опции\n" +"воспользуйтесь командой /msg %s HELP SASET опция\n" +"Помните, вы должны указать ник, опции которого вы хотите изменить." + +#: modules/commands/ns_set.cpp:107 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." +msgstr "" +"Чтобы получить справочную информацию по отдельно взятой опции\n" +"воспользуйтесь командой /msg %s HELP SASET опция\n" +"Помните, вы должны указать ник, опции которого вы хотите изменить." + +#: modules/commands/bs_set.cpp:62 modules/commands/cs_set.cpp:63 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." +msgstr "" +"Для более подробной информации о какой-либо конкретной опции, см.\n" +"справку по /msg %s HELP опция" + +#: modules/pseudoclients/nickserv.cpp:361 +#, fuzzy, c-format +msgid "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." +msgstr "" +"Используйте команду /msg %s SET EMAIL email-адрес чтобы установить email-" +"адрес.\n" +"Не волнуйтесь, данный email-адрес знать будете лишь вы и Администрация сети." + +#: modules/commands/os_module.cpp:128 +#, fuzzy +msgid "Un-Load a module" +msgstr " MODUNLOAD Выгрузить модуль" + +#: modules/commands/os_sxline.cpp:337 modules/commands/os_sxline.cpp:552 +#: modules/commands/os_akill.cpp:136 +#, fuzzy, c-format +msgid "Unable to find regex engine %s." +msgstr "Невозможно выгрузить модуль %s" + +#: modules/commands/os_module.cpp:36 modules/commands/os_module.cpp:108 +#, fuzzy, c-format +msgid "Unable to load module %s." +msgstr "Невозможно загрузить модуль %s" + +#: modules/commands/os_module.cpp:73 modules/commands/os_module.cpp:90 +#: modules/commands/os_module.cpp:145 modules/commands/os_module.cpp:159 +#, fuzzy, c-format +msgid "Unable to remove module %s." +msgstr "Невозможно выгрузить модуль %s" + +#: modules/commands/bs_assign.cpp:90 +#, fuzzy +msgid "Unassigns a bot from a channel" +msgstr "UNASSIGN Снять бота с указанного канала" + +#: modules/commands/bs_assign.cpp:139 +#, fuzzy +msgid "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." +msgstr "" +"Синтаксис: UNASSIGN #канал\n" +"\n" +"Позволяет снять бота с указанного канала. Канал будет удален из базы\n" +"данных бота и сам бот больше на него заходить не будет, однако, все\n" +"данные и настройки канала буду сохранены. В дальнейшем, это позволит\n" +"вам переназначить бота на канал с восстановлением всех старых настроек." + +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1193 +#: modules/commands/bs_kick.cpp:1196 +#, fuzzy +msgid "Underlines kicker" +msgstr "Цензор подчеркиваний.: %s" + +#: modules/commands/os_dns.cpp:595 +#, fuzzy +msgid "Unknown SET option." +msgstr "Неизвестная SASET-опция %s." + +#: modules/commands/os_stats.cpp:229 +#, fuzzy, c-format +msgid "Unknown STATS option: %s" +msgstr "Неизвестный STATS-параметр %s." + +#: src/command.cpp:222 src/command.cpp:233 +#, fuzzy, c-format +msgid "Unknown command %s." +msgstr "Неизвестная опция %s." + +#: src/command.cpp:220 src/command.cpp:231 +#, fuzzy, c-format +msgid "Unknown command %s. \"%s%s HELP\" for help." +msgstr "Неизвестная команда %s. Список команд доступен по %s%s HELP" + +#: modules/commands/cs_mode.cpp:317 modules/commands/cs_mode.cpp:409 +#, fuzzy, c-format +msgid "Unknown mode character %c ignored." +msgstr "Неизвестный режим %c - проигнорирован." + +#: modules/commands/os_logsearch.cpp:78 +#, fuzzy, c-format +msgid "Unknown parameter: %s" +msgstr "SET опция параметры" + +#: modules/commands/os_dns.cpp:241 +msgid "Unpooled" +msgstr "" + +#: modules/commands/cs_drop.cpp:77 +#, fuzzy +msgid "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." +msgstr "" +"Синтаксис: DROP #канал\n" +"\n" +"Удаляет указанный канал из базы данных сервисов. Использовать DROP\n" +"может лишь владелец канала." + +#: modules/commands/cs_drop.cpp:74 +#, fuzzy +msgid "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." +msgstr "" +"Синтаксис: DROP #канал\n" +"\n" +"Удаляет указанный канал из базы данных сервисов. Вы м ожете удалить\n" +"только те каналы, которыми вы владеете.\n" +"Как Администратор сервисов, вы можете удалить любой зарегистрированный\n" +"канал сети без какой-либо идентификации к нему." + +#: modules/commands/ns_suspend.cpp:160 +#, fuzzy +msgid "Unsuspend a given nick" +msgstr " UNSUSPEND Снятие режима саспенда с ника" + +#: modules/commands/ns_suspend.cpp:199 +msgid "Unsuspends a nickname which allows it to be used again." +msgstr "" + +#: modules/commands/cs_updown.cpp:126 +msgid "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." +msgstr "" + +#: modules/commands/cs_updown.cpp:48 +#, fuzzy +msgid "Updates a selected nicks status on a channel" +msgstr " BAN Установка бана на канале" + +#: modules/commands/ns_update.cpp:19 +#, fuzzy +msgid "Updates your current status, i.e. it checks for new memos" +msgstr " UPDATE Обновление вашего текущего статуса на сервисах" + +#: modules/commands/ns_update.cpp:43 +#, fuzzy +msgid "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." +msgstr "" +"Синтаксис: UPDATE\n" +"Обновляет ваш текущий статус на сервисах, в частности, проверяет на\n" +"наличие новых мемо-сообщений, устанавливает необходимые режимы на\n" +"всех каналах, где у вас есть статус (ModeonID), обновляет ваши\n" +"виртуальные хосты и настройки (дата последнего посещения IRC, и т.д.)." + +#: modules/commands/os_update.cpp:25 +msgid "Updating databases." +msgstr "Обновление баз данных..." + +#: modules/commands/os_stats.cpp:154 +#, c-format +msgid "Uplink capab: %s" +msgstr "Uplink capab: %s" + +#: modules/commands/os_stats.cpp:153 +#, c-format +msgid "Uplink server: %s" +msgstr "Uplink-сервер: %s" + +#: modules/commands/help.cpp:127 +#, c-format +msgid "Use the %s ALL command to list all commands and their descriptions." +msgstr "" + +#: modules/commands/bs_info.cpp:59 +msgid "Used on" +msgstr "" + +#: data/chanserv.example.conf:821 +#, fuzzy +msgid "Used to manage channels" +msgstr "%s принудительно изменил ваши пользовательские режимы." + +#: data/chanserv.example.conf:809 +#, fuzzy +msgid "Used to manage the list of privileged users" +msgstr " ACCESS Управление ACCESS-списком привилегий канала" + +#: data/chanserv.example.conf:815 +msgid "Used to modify the channel status of you or other users" +msgstr "" + +#: modules/commands/cs_akick.cpp:575 +#, fuzzy +msgid "User has been banned from the channel" +msgstr "Вы были разбанены на канале %s." + +#: modules/commands/os_dns.cpp:587 +#, fuzzy, c-format +msgid "User limit for %s removed." +msgstr "Виртуальный хост для %s удален." + +#: modules/commands/os_dns.cpp:585 +#, fuzzy, c-format +msgid "User limit for %s set to %d." +msgstr "Лимит собщений для %s установлен на %d." + +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Users" +msgstr "Список ботов:" + +#: modules/commands/os_stats.cpp:172 +#, c-format +msgid "Users (nick): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:177 +#, c-format +msgid "Users (uid): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_list.cpp:184 +#, fuzzy +msgid "Users list:" +msgstr "Список ботов:" + +#: modules/commands/ns_info.cpp:105 modules/commands/ns_info.cpp:107 +msgid "VHost" +msgstr "" + +#: modules/commands/hs_set.cpp:92 +#, fuzzy, c-format +msgid "VHost for %s set to %s." +msgstr "Виртуальный хост для %s установлен на %s." + +#: modules/commands/hs_set.cpp:90 +#, fuzzy, c-format +msgid "VHost for %s set to %s@%s." +msgstr "Виртуальный хост для %s установлен на %s@%s." + +#: modules/commands/hs_set.cpp:199 +#, fuzzy, c-format +msgid "VHost for group %s set to %s." +msgstr "Виртуальный хост для группы %s установлен на %s." + +#: modules/commands/hs_set.cpp:197 +#, fuzzy, c-format +msgid "VHost for group %s set to %s@%s." +msgstr "Виртуальный хост для группы %s установлен в %s@%s." + +#: modules/commands/os_session.cpp:247 +msgid "VIEW host" +msgstr "" + +#: modules/commands/os_sxline.cpp:428 modules/commands/os_sxline.cpp:662 +#: modules/commands/os_akill.cpp:389 +#, fuzzy +msgid "VIEW [mask | list | id]" +msgstr "LIST [#канал] [список_записей | NEW]" + +#: modules/commands/os_session.cpp:526 +msgid "VIEW [mask | list]" +msgstr "" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +msgid "Value" +msgstr "" + +#: modules/commands/os_config.cpp:48 +#, fuzzy, c-format +msgid "Value of %s:%s changed to %s" +msgstr "Все права на владение каналом %s успешно переданы пользователю %s." + +#: modules/commands/hs_list.cpp:58 modules/commands/hs_request.cpp:305 +msgid "Vhost" +msgstr "" + +#: modules/commands/hs_del.cpp:38 +#, fuzzy, c-format +msgid "Vhost for %s removed." +msgstr "Виртуальный хост для %s удален." + +#: modules/commands/os_oper.cpp:69 +#, fuzzy +msgid "View and change Services Operators" +msgstr "%s is a services operator of type %s." + +#: modules/commands/os_config.cpp:19 +msgid "View and change configuration file settings" +msgstr "" + +#: modules/commands/os_session.cpp:245 +#, fuzzy +msgid "View the list of host sessions" +msgstr " SESSION Просмотр количества сессий с указанного хоста" + +#: modules/commands/bs_kick.cpp:1221 +msgid "Voices protection" +msgstr "Не кикать войсов" + +#: modules/commands/bs_kick.cpp:1406 +msgid "Watch your language!" +msgstr "Следи за своим языком!" + +#: modules/commands/cs_list.cpp:237 +#, c-format +msgid "" +"When private is set, the channel will not appear in\n" +"%s's %s command." +msgstr "" + +#: modules/commands/ms_info.cpp:204 +#, fuzzy +msgid "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." +msgstr "" +"Синтаксис: INFO [ник | #канал]\n" +"\n" +"Без параметров, покажет общее количество сообщений, которое вы\n" +"имеете, сколько из них непрочитано, и сколько всего сообщений вы\n" +"можете принимать.\n" +"\n" +"Если указать канал, покажет ту же информацию об указанном канале.\n" +"\n" +"Если указать в качестве параметра ник, покажет ту же информацию об\n" +"указанном нике.\n" +"Данный параметр могут использовать только Администраторы сервисов." + +#: modules/commands/ns_logout.cpp:66 +#, fuzzy +msgid "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." +msgstr "" +"Синтаксис: LOGOUT [ник [REVALIDATE]]\n" +"\n" +"Использованная без параметров, команда LOGOUT производит эффект,\n" +"обратный эффекту команды IDENTIFY, то есть - деидентифицирует вас\n" +"от используемого на данный момент ника. Тем не менее, сервисы не\n" +"пошлют повторный запрос на идентификацию.\n" +"\n" +"Если в качестве параметра вы укажете ник - деидентифицирует указанный\n" +"ник. Дополнительно указанный параметр REVALIDATE заставит сервисы\n" +"послать дендинтифицированному нику запрос на переавторизацию.\n" +"Использовать параметры ник и REVALIDATE могут лишь Администраторы\n" +"сервисов." + +#: modules/commands/os_stats.cpp:236 +#, fuzzy +msgid "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." +msgstr "" +"Синтаксис: STATS [AKILL | ALL | RESET | MEMORY | UPLINK]\n" +"\n" +"Использованная без параметров, команда покажет текущее количество\n" +"пользователей сети, текущее кол-во IRC-операторов (за исключением\n" +"самих сервисов), максимально зафиксированное число пользователей\n" +"и время работы сервисов в сети.\n" +"\n" +"С параметром AKILL, покажет текущий размер списка AKILL'ов и время\n" +"истечения AKILL'ов по-умолчанию (AKILL, SZLINE, ZGLINE, ZQLINE).\n" +"\n" +"Параметр RESET сбрасывает счетчик зафиксированного максимума \n" +"пользователей сети.\n" +"\n" +"Параметр MEMORY выведет информацию об использовании сервисами\n" +"оперативной памяти. Запросы подобной статистики могу затормозить\n" +"работу сервисов на определенный промежуток времени, поэтому, не\n" +"рекомендуется использовать параметр MEMORY слишком часто.\n" +"\n" +"Параметр UPLINK покажет информацию о сервере, к которому\n" +"прилинкованы сервисы сети.\n" +"\n" +"Параметр ALL выведет общую статистику в комбинации с данными из\n" +"MEMORY и UPLINK." + +#: modules/commands/bs_badwords.cpp:194 +msgid "Word" +msgstr "" + +#: modules/commands/ns_group.cpp:158 +#, c-format +msgid "You are already a member of the group of %s." +msgstr "Вы уже состоите в группе %s." + +#: modules/commands/os_login.cpp:34 modules/commands/ns_identify.cpp:87 +msgid "You are already identified." +msgstr "Вы уже идентифицированы." + +#: modules/commands/cs_invite.cpp:64 +#, fuzzy, c-format +msgid "You are already in %s!" +msgstr "You are already in %s! " + +#: modules/commands/os_set.cpp:91 +#, fuzzy +msgid "You are no longer a super admin." +msgstr "Режим Супер-Администратора деактивирован." + +#: modules/commands/os_login.cpp:81 +#, fuzzy +msgid "You are not identified." +msgstr "Вы уже идентифицированы." + +#: include/language.h:100 +#, fuzzy +msgid "You are not permitted to be on this channel." +msgstr "Вам запрещено изменять свой лимит сообщений." + +#: modules/commands/ms_set.cpp:158 +msgid "You are not permitted to change your memo limit." +msgstr "Вам запрещено изменять свой лимит сообщений." + +#: modules/commands/ns_cert.cpp:183 +#, fuzzy +msgid "You are not using a client certificate." +msgstr "Вы уже идентифицированы." + +#: modules/commands/os_set.cpp:85 +#, fuzzy +msgid "You are now a super admin." +msgstr "Режим Супер-Администратора активирован." + +#: modules/commands/os_oline.cpp:36 +msgid "You are now an IRC Operator." +msgstr "Теперь вы IRC-оператор." + +#: modules/commands/ns_resetpass.cpp:108 +#, fuzzy +msgid "You are now identified for your nick. Change your password now." +msgstr "You are now identified for your nick. Change your password now." + +#: modules/commands/ns_group.cpp:64 +#, c-format +msgid "You are now in the group of %s." +msgstr "Вы успешно внесены в группу %s." + +#: modules/pseudoclients/memoserv.cpp:147 +#, fuzzy, c-format +msgid "" +"You are over your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Внимание: вы превысили лимит максимально допустимого числа хранимых " +"сообщений (%d). Вы не сможете принимать новые сообщения, пока вы не удалите " +"лишние." + +#: modules/commands/os_noop.cpp:33 +msgid "You can not NOOP Services." +msgstr "" + +#: modules/commands/cs_access.cpp:672 +msgid "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." +msgstr "" + +#: modules/commands/os_jupe.cpp:34 +#, fuzzy +msgid "You can not jupe an already juped server." +msgstr "You can not jupe your services server or your uplink server." + +#: modules/commands/os_jupe.cpp:32 +#, fuzzy +msgid "You can not jupe your Services' pseudoserver or your uplink server." +msgstr "You can not jupe your services server or your uplink server." + +#: modules/commands/os_module.cpp:80 +#, c-format +msgid "You can not reload this module directly, instead reload %s." +msgstr "" + +#: modules/commands/ms_rsend.cpp:46 +msgid "You can not request a receipt when sending a memo to yourself." +msgstr "" +"Вы не можете запросить информацию о получении, когда посылаете сообщение " +"себе." + +#: modules/commands/ns_recover.cpp:163 +#, fuzzy, c-format +msgid "You can't %s yourself!" +msgstr "Вы не можете закрыть свою сессию!" + +#: modules/commands/cs_access.cpp:154 modules/commands/cs_flags.cpp:109 +#: modules/commands/cs_xop.cpp:151 +#, fuzzy +msgid "You can't add a channel to its own access list." +msgstr "Совпадающих записей в списке доступа канала %s не обнаружено." + +#: modules/commands/ns_logout.cpp:37 +#, fuzzy, c-format +msgid "You can't logout %s, they are a Services Operator." +msgstr "Невозможно деидентифицировать %s так как он Администратор сервисов." + +#: modules/commands/ns_set.cpp:927 +#, fuzzy, c-format +msgid "You cannot %s on this network." +msgstr "Возможность удаления email-адреса в вашей IRC-сети недоступна." + +#: modules/commands/cs_flags.cpp:231 +#, fuzzy, c-format +msgid "You cannot set the %c flag." +msgstr "You cannot use this command." + +#: modules/commands/ms_set.cpp:173 +#, c-format +msgid "You cannot set the memo limit for %s higher than %d." +msgstr "Вы не можете установить лимит сообщений для %s больше чем %d." + +#: modules/commands/ms_set.cpp:175 +#, c-format +msgid "You cannot set your memo limit higher than %d." +msgstr "Вы не можете установить лимит сообщений больше чем %d." + +#: modules/commands/bs_assign.cpp:124 +#, fuzzy +msgid "You cannot unassign bots while persist is set on the channel." +msgstr "You can not unassign bots while persist is set on the channel." + +#: modules/commands/ns_set.cpp:480 +msgid "You cannot unset the e-mail on this network." +msgstr "Возможность удаления email-адреса в вашей IRC-сети недоступна." + +#: modules/commands/help.cpp:177 +msgid "You cannot use this command." +msgstr "You cannot use this command." + +#: modules/commands/ms_info.cpp:151 +#, c-format +msgid "You currently have %d memos, of which %d are unread." +msgstr "На данный момент у вас имеется %d сообщений, %d из них не прочитано." + +#: modules/commands/ms_info.cpp:149 +#, c-format +msgid "You currently have %d memos, of which 1 is unread." +msgstr "На данный момент у вас имеется %d сообщений, 1 из них не прочитано." + +#: modules/commands/ms_info.cpp:147 +#, c-format +msgid "You currently have %d memos." +msgstr "На данный момент у вас имеется %d сообщений." + +#: modules/commands/ms_info.cpp:145 +#, c-format +msgid "You currently have %d memos; all of them are unread." +msgstr "" +"На данный момент у вас имеется %d сообщений, ни одно из них не прочитано." + +#: modules/commands/ms_info.cpp:134 +msgid "You currently have 1 memo, and it has not yet been read." +msgstr "На данный момент у вас имеется 1 новое, непрочитанное сообщение." + +#: modules/commands/ms_info.cpp:136 +msgid "You currently have 1 memo." +msgstr "На данный момент у вас имеется 1 сообщение." + +#: modules/commands/ms_info.cpp:130 +msgid "You currently have no memos." +msgstr "На данный момент у вас нет сообщений." + +#: modules/commands/cs_mode.cpp:564 modules/commands/cs_mode.cpp:621 +#, c-format +msgid "You do not have access to set mode %c." +msgstr "" + +#: modules/commands/cs_mode.cpp:578 modules/commands/cs_mode.cpp:590 +#: modules/commands/cs_mode.cpp:631 +#, c-format +msgid "You do not have the access to change %s's modes." +msgstr "" + +#: modules/commands/cs_seen.cpp:198 +#, c-format +msgid "You found me, %s!" +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:143 +#, c-format +msgid "You have %d new memos." +msgstr "Вам пришло %d новых сообщений." + +#: modules/pseudoclients/memoserv.cpp:143 +msgid "You have 1 new memo." +msgstr "Вам пришло 1 новое сообщение." + +#: include/language.h:112 +#, fuzzy, c-format +msgid "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." +msgstr "Напишите /msg %s READ %d чтобы прочитать его." + +#: modules/commands/cs_invite.cpp:76 +#, fuzzy, c-format +msgid "You have been invited to %s by %s." +msgstr "You have been invited to %s." + +#: modules/commands/cs_invite.cpp:81 +#, c-format +msgid "You have been invited to %s." +msgstr "You have been invited to %s." + +#: modules/protocol/ratbox.cpp:166 modules/commands/ns_recover.cpp:96 +#, fuzzy, c-format +msgid "You have been logged in as %s." +msgstr "Деидентификация выполнена успешно." + +#: modules/commands/os_login.cpp:86 +#, fuzzy +msgid "You have been logged out." +msgstr "Деидентификация выполнена успешно." + +#: modules/commands/cs_unban.cpp:94 +#, c-format +msgid "You have been unbanned from %s." +msgstr "Вы были разбанены на канале %s." + +#: modules/commands/cs_unban.cpp:54 +#, fuzzy, c-format +msgid "You have been unbanned from %d channels." +msgstr "Вы были разбанены на канале %s." + +#: modules/commands/ms_info.cpp:169 +msgid "You have no limit on the number of memos you may keep." +msgstr "У вас нет ограничения на количество хранимых сообщений." + +#: include/language.h:114 +#, fuzzy +msgid "You have no memos." +msgstr "Вам пришло %d новых сообщений." + +#: include/language.h:117 +#, fuzzy +msgid "You have no new memos." +msgstr "Вам пришло %d новых сообщений." + +#: modules/pseudoclients/memoserv.cpp:149 +#, fuzzy, c-format +msgid "" +"You have reached your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Внимание: вы достигли максимально допустимого числа хранимых сообщений (%d). " +"Вы не сможете принимать новые сообщения, пока не удалите лишние." + +#: modules/commands/ns_recover.cpp:117 +#, fuzzy, c-format +msgid "You have regained control of %s." +msgstr "You have been invited to %s." + +#: modules/commands/ns_drop.cpp:66 +#, fuzzy +msgid "You may drop any nick within your group." +msgstr " DELALL Удаление вирт. хоста у всех ников указанной группы" + +#: modules/commands/cs_mode.cpp:322 modules/commands/cs_mode.cpp:414 +#, c-format +msgid "You may not (un)lock mode %c." +msgstr "" + +#: modules/commands/ns_set.cpp:485 +#, fuzzy +msgid "You may not change the e-mail of other Services Operators." +msgstr "Возможность удаления email-адреса в вашей IRC-сети недоступна." + +#: modules/commands/ns_set.cpp:474 +#, fuzzy +msgid "You may not change the email of an unconfirmed account." +msgstr "Возможность удаления email-адреса в вашей IRC-сети недоступна." + +#: modules/commands/ns_set.cpp:196 +#, fuzzy +msgid "You may not change the password of other Services Operators." +msgstr "Невозможно деидентифицировать %s так как он Администратор сервисов." + +#: modules/commands/ns_drop.cpp:45 +#, fuzzy +msgid "You may not drop other Services Operators' nicknames." +msgstr "%s is a services operator of type %s." + +#: modules/commands/ns_getpass.cpp:32 +#, fuzzy +msgid "You may not get the password of other Services Operators." +msgstr "Невозможно деидентифицировать %s так как он Администратор сервисов." + +#: modules/commands/ns_suspend.cpp:100 +#, fuzzy +msgid "You may not suspend other Services Operators' nicknames." +msgstr "Невозможно деидентифицировать %s так как он Администратор сервисов." + +#: modules/commands/ns_access.cpp:136 +#, fuzzy +msgid "" +"You may view but not modify the access list of other Services Operators." +msgstr "Невозможно деидентифицировать %s так как он Администратор сервисов." + +#: modules/commands/ns_cert.cpp:292 +#, fuzzy +msgid "" +"You may view but not modify the certificate list of other Services Operators." +msgstr "Невозможно деидентифицировать %s так как он Администратор сервисов." + +#: modules/commands/cs_seen.cpp:287 +#, c-format +msgid "You might see yourself in the mirror, %s." +msgstr "" + +#: include/language.h:120 +msgid "You must assign a bot to the channel before using this command." +msgstr "" + +#: modules/commands/cs_register.cpp:49 +msgid "You must be a channel operator to register the channel." +msgstr "Чтобы зарегистрировать канал, вы должны быть его оператором." + +#: modules/commands/cs_updown.cpp:94 modules/commands/cs_updown.cpp:192 +#, fuzzy, c-format +msgid "You must be in %s to use this command." +msgstr "You need to be identified to use this command." + +#: modules/commands/cs_register.cpp:37 +#, fuzzy +msgid "You must confirm your account before you can register a channel." +msgstr "Чтобы зарегистрировать канал, вы должны быть его оператором." + +#: modules/commands/hs_request.cpp:100 +#, fuzzy +msgid "You must confirm your account before you may request a vhost." +msgstr "Чтобы зарегистрировать канал, вы должны быть его оператором." + +#: modules/commands/ms_send.cpp:44 +#, fuzzy +msgid "You must confirm your account before you may send a memo." +msgstr "Чтобы зарегистрировать канал, вы должны быть его оператором." + +#: modules/commands/cs_drop.cpp:42 +#, c-format +msgid "" +"You must enter the channel name twice as a confirmation that you wish to drop" +" %s." +msgstr "" + +#: modules/commands/ns_register.cpp:153 +#, c-format +msgid "You must have been using this nick for at least %d seconds to register." +msgstr "" +"Чтобы начать регистрацию вашего текущего ника, вы должны использовать его не " +"менее %d секунд" + +#: modules/commands/cs_mode.cpp:913 +#, fuzzy, c-format +msgid "You must have the %s(ME) privilege on the channel to use this command." +msgstr "You need to be identified to use this command." + +#: modules/pseudoclients/nickserv.cpp:358 +msgid "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." +msgstr "" +"Сначала вы должны установить email-адрес для вашего ника. Реальный email-" +"адрес\n" +"позволит вам использовать функцию восстановления пароля, если вы его " +"забудете." + +#: modules/commands/help.cpp:172 +msgid "You need to be identified to use this command." +msgstr "You need to be identified to use this command." + +#: modules/commands/ms_info.cpp:182 +#, fuzzy +msgid "You will be notified by message and by mail when new memos arrive." +msgstr "Вы будете уведомлены о новых сообщениях сразу при поступлении оных." + +#: modules/commands/ms_info.cpp:175 +#, fuzzy +msgid "" +"You will be notified of new memos at logon and when they arrive, and by mail " +"when they arrive." +msgstr "" +"Вы будете уведомлены о новых сообщениях сразу после идентификации к нику или " +"при поступлении новых сообщений." + +#: modules/commands/ms_info.cpp:177 +msgid "You will be notified of new memos at logon and when they arrive." +msgstr "" +"Вы будете уведомлены о новых сообщениях сразу после идентификации к нику или " +"при поступлении новых сообщений." + +#: modules/commands/ms_info.cpp:189 +#, fuzzy +msgid "" +"You will be notified of new memos at logon, and by mail when they arrive." +msgstr "" +"Вы будете уведомлены о новых сообщениях сразу после идентификации к нику или " +"при поступлении новых сообщений." + +#: modules/commands/ms_info.cpp:191 +msgid "You will be notified of new memos at logon." +msgstr "" +"Вы будете уведомлены о новых сообщениях сразу после идентификации к нику" + +#: modules/commands/ms_info.cpp:184 +msgid "You will be notified when new memos arrive." +msgstr "Вы будете уведомлены о новых сообщениях сразу при поступлении оных." + +#: modules/commands/ms_set.cpp:190 +msgid "You will no longer be able to receive memos." +msgstr "Лимит сообщений установлен на 0, возможность их получения отключена." + +#: modules/commands/ms_set.cpp:57 +msgid "You will no longer be informed via email." +msgstr "Оповещение о новых сообщениях посредством email отключено" + +#: modules/commands/ms_info.cpp:195 +msgid "You will not be notified of new memos." +msgstr "Уведомление о новых сообщениях отключено." + +#: modules/commands/ms_set.cpp:49 +msgid "You will now be informed about new memos via email." +msgstr "" +"С этого момента, вы будете получать уведомления о новых сообщениях по email." + +#: modules/commands/os_svs.cpp:86 +msgid "Your IRCd does not support SVSJOIN." +msgstr "" + +#: modules/commands/os_svs.cpp:31 +msgid "Your IRCd does not support SVSNICK." +msgstr "" + +#: modules/commands/os_svs.cpp:130 +msgid "Your IRCd does not support SVSPART." +msgstr "" + +#: include/language.h:127 +msgid "" +"Your IRCd does not support vIdent's, if this is incorrect, please report " +"this as a possible bug" +msgstr "" + +#: modules/extra/m_ldap_authentication.cpp:110 +#: modules/extra/m_sql_authentication.cpp:55 +#, fuzzy, c-format +msgid "Your account %s has been successfully created." +msgstr "Бот под ником %s успешно удален." + +#: modules/commands/ns_register.cpp:328 +#, fuzzy +msgid "Your account is already confirmed." +msgstr "Вы уже идентифицированы." + +#: modules/commands/ns_register.cpp:396 +#, fuzzy, c-format +msgid "Your account will expire, if not confirmed, in %s." +msgstr "Вы уже идентифицированы." + +#: modules/commands/ns_set.cpp:1274 +#, fuzzy, c-format +msgid "Your email address has been changed to %s." +msgstr "Email-адрес для %s изменен на %s." + +#: modules/commands/os_forbid.cpp:544 modules/commands/os_forbid.cpp:553 +#, fuzzy +msgid "Your email address is not allowed, choose a different one." +msgstr "Все OLINE-записи на сервере %s были удалены." + +#: modules/commands/ns_register.cpp:260 modules/commands/ns_register.cpp:391 +msgid "" +"Your email address is not confirmed. To confirm it, follow the instructions " +"that were emailed to you." +msgstr "" + +#: modules/commands/ns_register.cpp:67 +#, fuzzy, c-format +msgid "Your email address of %s has been confirmed." +msgstr "Все OLINE-записи на сервере %s были удалены." + +#: modules/extra/m_ldap_authentication.cpp:159 +#, fuzzy, c-format +msgid "Your email has been updated to %s" +msgstr "Email-адрес для %s изменен на %s." + +#: modules/extra/m_sql_authentication.cpp:62 +#, fuzzy, c-format +msgid "Your email has been updated to %s." +msgstr "Email-адрес для %s изменен на %s." + +#: modules/commands/ms_set.cpp:197 +msgid "Your memo limit has been disabled." +msgstr "Лимититирование вашего списка сообщений отключено." + +#: modules/commands/ms_set.cpp:183 +#, c-format +msgid "Your memo limit has been set to %d." +msgstr "Лимит сообщений был установлен на %d." + +#: modules/commands/ms_info.cpp:164 +#, c-format +msgid "Your memo limit is %d, and may not be changed." +msgstr "Ваш лимит сообщений равен %d и не может быть изменен." + +#: modules/commands/ms_info.cpp:166 +#, c-format +msgid "Your memo limit is %d." +msgstr "Ваш лимит сообщений равен %d." + +#: modules/commands/ms_info.cpp:159 +msgid "Your memo limit is 0; you will not receive any new memos." +msgstr "Ваш лимит сообщений равен 0 и принимать их вы не можете." + +#: modules/commands/ms_info.cpp:157 +#, fuzzy +msgid "" +"Your memo limit is 0; you will not receive any new memos. You cannot change " +"this limit." +msgstr "" +"Ваш лимит сообщений равен 0, у вас нет возможности принимать сообщения и/или " +"изменять лимит." + +#: modules/commands/ns_logout.cpp:50 +msgid "Your nick has been logged out." +msgstr "Деидентификация выполнена успешно." + +#: modules/commands/ns_group.cpp:156 +#, fuzzy +msgid "Your nick is already registered." +msgstr "" +"Перед внесением ника в группу, вы должны удалить его командой /msg %s DROP." + +#: modules/commands/ns_group.cpp:246 +msgid "Your nick is not grouped to anything, you can't ungroup it." +msgstr "Your nick is not grouped to anything, you can't ungroup it." + +#: include/language.h:77 +#, fuzzy +msgid "Your nick isn't registered." +msgstr "Ник %s успешно зарегистрирован." + +#: modules/pseudoclients/nickserv.cpp:254 +#, c-format +msgid "Your nickname is now being changed to %s" +msgstr "Ваш ник изменен на %s" + +#: modules/commands/os_login.cpp:32 modules/commands/os_login.cpp:79 +msgid "Your oper block doesn't require logging in." +msgstr "" + +#: modules/commands/ns_register.cpp:336 +#, c-format +msgid "Your passcode has been re-sent to %s." +msgstr "Ваш код аутенфикации был заново выслан на %s." + +#: modules/commands/ns_register.cpp:232 +#, c-format +msgid "Your password is %s - remember this for later use." +msgstr "" +"Пароль для вашего ника - %s - запомните его, он пригодится вам в дальнейшем!" + +#: include/language.h:76 +#, c-format +msgid "Your password is too long. It must not exceed %u characters." +msgstr "" + +#: modules/commands/ns_resetpass.cpp:96 +msgid "Your password reset request has expired." +msgstr "Your password reset request has expired." + +#: modules/commands/hs_request.cpp:170 +#, fuzzy +msgid "Your vHost has been requested." +msgstr "Бот под ником %s успешно удален." + +#: modules/pseudoclients/hostserv.cpp:64 +#: modules/pseudoclients/hostserv.cpp:103 modules/commands/hs_on.cpp:37 +#, c-format +msgid "Your vhost of %s is now activated." +msgstr "Ваш виртуальный хост %s активирован." + +#: modules/pseudoclients/hostserv.cpp:62 +#: modules/pseudoclients/hostserv.cpp:101 modules/commands/hs_on.cpp:35 +#, c-format +msgid "Your vhost of %s@%s is now activated." +msgstr "Ваш виртуальный хост %s@%s активирован." + +#: modules/commands/hs_off.cpp:39 +msgid "Your vhost was removed and the normal cloaking restored." +msgstr "Your vhost was removed and the normal cloaking restored." + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Zone" +msgstr "отсутствуют" + +#: modules/commands/os_dns.cpp:290 +#, fuzzy, c-format +msgid "Zone %s already exists." +msgstr "Бот с ником %s уже существует." + +#: modules/commands/os_dns.cpp:310 modules/commands/os_dns.cpp:352 +#: modules/commands/os_dns.cpp:402 modules/commands/os_dns.cpp:438 +#, fuzzy, c-format +msgid "Zone %s does not exist." +msgstr "Бот с ником %s уже существует." + +#: modules/commands/os_dns.cpp:332 +#, fuzzy, c-format +msgid "Zone %s removed." +msgstr "Виртуальный хост для %s удален." + +#: modules/commands/os_defcon.cpp:177 +#, fuzzy +msgid "[1|2|3|4|5]" +msgstr "DEFCON [1|2|3|4|5]" + +#: modules/commands/os_news.cpp:400 +#, c-format +msgid "[Logon News - %s] %s" +msgstr "[Новости сети - %s] %s" + +#: modules/commands/os_news.cpp:402 +#, c-format +msgid "[Oper News - %s] %s" +msgstr "[Опер-новости - %s] %s" + +#: modules/commands/os_news.cpp:404 +#, c-format +msgid "[Random News - %s] %s" +msgstr "[Случайная новость - %s] %s" + +#: modules/commands/ns_identify.cpp:66 +#, fuzzy +msgid "[account] password" +msgstr "IDENTIFY пароль" + +#: modules/commands/cs_updown.cpp:49 modules/commands/cs_updown.cpp:147 +#, fuzzy +msgid "[channel [nick]]" +msgstr "OP #channel [nick]" + +#: modules/commands/ms_ignore.cpp:20 +#, fuzzy +msgid "[channel] ADD entry" +msgstr "AOP #канал {ADD|DEL|LIST|CLEAR} [ник | номер запис]" + +#: modules/commands/ms_ignore.cpp:21 +#, fuzzy +msgid "[channel] DEL entry" +msgstr "MODE #канал режимы" + +#: modules/commands/ms_ignore.cpp:22 +#, fuzzy +msgid "[channel] LIST" +msgstr "DROP #канал" + +#: modules/commands/ms_list.cpp:20 +#, fuzzy +msgid "[channel] [list | NEW]" +msgstr "LIST [#канал] [список_записей | NEW]" + +#: modules/extra/stats/cs_fantasy_stats.cpp:40 +#, fuzzy +msgid "[channel] [nick]" +msgstr "OP #channel [nick]" + +#: modules/commands/ms_del.cpp:45 +#, fuzzy +msgid "[channel] {num | list | LAST | ALL}" +msgstr "DEL [#канал] {номер_сообщения | список_записей | ALL}" + +#: modules/commands/ms_read.cpp:113 +#, fuzzy +msgid "[channel] {num | list | LAST | NEW | ALL}" +msgstr "DEL [#канал] {номер_сообщения | список_записей | ALL}" + +#: modules/commands/hs_list.cpp:20 +msgid "[key|#X-Y]" +msgstr "" + +#: modules/commands/ms_info.cpp:20 +#, fuzzy +msgid "[nick | channel]" +msgstr "CANCEL {ник | #канал}" + +#: modules/commands/ns_group.cpp:237 +#, fuzzy +msgid "[nick]" +msgstr "INFO ник" + +#: modules/commands/ns_logout.cpp:22 +msgid "[nickname [REVALIDATE]]" +msgstr "" + +#: modules/commands/ns_alist.cpp:25 modules/commands/ns_status.cpp:20 +#: modules/commands/ns_info.cpp:20 +#, fuzzy +msgid "[nickname]" +msgstr "CHECK ник" + +#: modules/commands/ns_set_misc.cpp:96 +msgid "[parameter]" +msgstr "" + +#: modules/commands/os_logsearch.cpp:33 +msgid "[+daysd] [+limitl] pattern" +msgstr "" + +#: modules/commands/os_chankill.cpp:22 +#, fuzzy +msgid "[+expiry] channel reason" +msgstr "CHANKILL [+срок_истечения] {#канал} [причина]" + +#: modules/commands/ns_list.cpp:110 +msgid "[Hostname hidden]" +msgstr "" + +#: modules/commands/ns_list.cpp:112 modules/commands/cs_list.cpp:115 +msgid "[Suspended]" +msgstr "" + +#: modules/commands/ns_list.cpp:114 +msgid "[Unconfirmed]" +msgstr "" + +#: modules/commands/hs_request.cpp:213 +#, fuzzy +msgid "[auto memo] Your requested vHost has been approved." +msgstr "" +"[авто-сообщение] Мемо-сообщение, которые вы посылали %s, было прочитано." + +#: modules/commands/hs_request.cpp:267 +#, fuzzy +msgid "[auto memo] Your requested vHost has been rejected." +msgstr "" +"[авто-сообщение] Мемо-сообщение, которые вы посылали %s, было прочитано." + +#: modules/commands/hs_request.cpp:265 +#, c-format +msgid "[auto memo] Your requested vHost has been rejected. Reason: %s" +msgstr "" + +#: modules/commands/hs_request.cpp:388 +#, fuzzy, c-format +msgid "[auto memo] vHost %s has been requested by %s." +msgstr "Последнее ваше сообщение адресату %s успешно отменено." + +#: modules/commands/os_list.cpp:133 +msgid "[{pattern | channel} [INVISIBLE]]" +msgstr "" + +#: modules/commands/os_list.cpp:20 +msgid "[{pattern | nick} [SECRET]]" +msgstr "" + +#: src/misc.cpp:337 +msgid "day" +msgstr "" + +#: src/misc.cpp:337 +msgid "days" +msgstr "" + +#: include/language.h:88 +#, fuzzy +msgid "does not expire" +msgstr " %s (does not expire)" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d day" +msgstr "истечет через %d дней" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d days" +msgstr "истечет через %d дней" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minute" +msgstr "истечет через %d часов %d минут" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minutes" +msgstr "истечет через %d часов, %d минут" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minute" +msgstr "истечет через %d часов, %d минут" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minutes" +msgstr "истечет через %d часов, %d минут" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minute" +msgstr "истечет через %d минут" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minutes" +msgstr "истечет через %d минут" + +#: src/misc.cpp:375 +#, fuzzy +msgid "expires momentarily" +msgstr "истечет через %d дней" + +#: src/misc.cpp:343 +msgid "hour" +msgstr "" + +#: src/misc.cpp:343 +msgid "hours" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:150 +#, c-format +msgid "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:349 +msgid "minute" +msgstr "" + +#: src/misc.cpp:349 +msgid "minutes" +msgstr "" + +#: modules/commands/bs_info.cpp:87 +msgid "not assigned yet" +msgstr "" + +#: src/misc.cpp:324 +msgid "second" +msgstr "" + +#: src/misc.cpp:324 +#, fuzzy +msgid "seconds" +msgstr "Список команд %s:" + +#: modules/commands/hs_request.cpp:215 +#, fuzzy, c-format +msgid "vHost for %s has been activated." +msgstr "Ваш виртуальный хост %s активирован." + +#: modules/commands/hs_request.cpp:272 +#, fuzzy, c-format +msgid "vHost for %s has been rejected." +msgstr "Бот под ником %s успешно удален." + +#: modules/commands/hs_request.cpp:79 +msgid "vhost" +msgstr "" + +#: modules/commands/hs_del.cpp:83 +#, c-format +msgid "vhosts for group %s have been removed." +msgstr "Все виртуальные хосты для группы %s были удалены." + +#: src/misc.cpp:331 +msgid "year" +msgstr "" + +#: src/misc.cpp:331 +msgid "years" +msgstr "" + +#: modules/commands/os_config.cpp:20 +msgid "{MODIFY|VIEW} [block name item name item value]" +msgstr "" + +#: modules/commands/bs_info.cpp:41 +#, fuzzy +msgid "{channel | nickname}" +msgstr "UNBAN #канал [nick]" + +#: modules/commands/ms_cancel.cpp:20 +#, fuzzy +msgid "{nick | channel}" +msgstr "CANCEL {ник | #канал}" + +#: modules/commands/ms_rsend.cpp:25 modules/commands/ms_send.cpp:25 +#, fuzzy +msgid "{nick | channel} memo-text" +msgstr "SEND {ник | #канал} текст_сообщения" diff --git a/language/anope.tr_TR.po b/language/anope.tr_TR.po new file mode 100644 index 0000000..deed448 --- /dev/null +++ b/language/anope.tr_TR.po @@ -0,0 +1,11767 @@ +# Anope IRC Services language file +# Copyright (C) 2011 +# This file is distributed under the same license as the Anope IRC Services package. +# Adam , 2011. +# +msgid "" +msgstr "" +"Project-Id-Version: Anope\n" +"Report-Msgid-Bugs-To: \n" +"POT-Creation-Date: 2020-01-06 18:19+0100\n" +"PO-Revision-Date: 2010-09-19 21:13-0400\n" +"Last-Translator: Adam \n" +"Language-Team: Turkish\n" +"Language: tr_TR\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Plural-Forms: nplurals=1; plural=0;\n" + +#: modules/commands/os_forbid.cpp:324 +#, c-format +msgid "%d channel(s) cleared, and %d channel(s) dropped." +msgstr "" + +#: modules/commands/os_forbid.cpp:265 +#, fuzzy, c-format +msgid "%d nickname(s) dropped." +msgstr "Nickinizin kaydı silindi (dropped)." + +#: modules/commands/cs_xop.cpp:219 +#, fuzzy, c-format +msgid "%s added to %s %s list." +msgstr "%s AKILL listesine eklendi." + +#: modules/commands/cs_access.cpp:225 +#, c-format +msgid "%s added to %s access list at level %d." +msgstr "%s nicki %s kanalinin access listesine %d seviyeden eklendi." + +#: modules/commands/cs_access.cpp:223 +#, fuzzy, c-format +msgid "%s added to %s access list at privilege %s (level %d)" +msgstr "%s nicki %s kanalinin access listesine %d seviyeden eklendi." + +#: modules/commands/cs_akick.cpp:190 +#, c-format +msgid "%s added to %s autokick list." +msgstr "%s nicki %s kanalının akick listesine eklendi." + +#: modules/commands/bs_badwords.cpp:307 +#, c-format +msgid "%s added to %s bad words list." +msgstr "%s %s kanalının küfür listesine eklendi." + +#: modules/commands/ns_access.cpp:45 +#, fuzzy, c-format +msgid "%s added to %s's access list." +msgstr "%s access listenize eklendi." + +#: modules/commands/ns_cert.cpp:204 +#, fuzzy, c-format +msgid "%s added to %s's certificate list." +msgstr "%s access listenize eklendi." + +#: modules/commands/ms_ignore.cpp:62 +#, fuzzy, c-format +msgid "%s added to ignore list." +msgstr "%s access listenize eklendi." + +#: modules/commands/os_sxline.cpp:415 modules/commands/os_sxline.cpp:649 +#, fuzzy, c-format +msgid "%s added to the %s list." +msgstr "%s AKILL listesine eklendi." + +#: modules/commands/os_akill.cpp:203 +#, c-format +msgid "%s added to the AKILL list." +msgstr "%s AKILL listesine eklendi." + +#: modules/pseudoclients/botserv.cpp:134 +#, c-format +msgid "" +"%s allows you to execute \"fantasy\" commands in the channel.\n" +"Fantasy commands are commands that can be executed from messaging a\n" +"channel, and provide a more convenient way to execute commands. Commands " +"that\n" +"require a channel as a parameter will automatically have that parameter\n" +"given.\n" +msgstr "" + +#: modules/pseudoclients/botserv.cpp:148 +#, fuzzy, c-format +msgid "" +"%s allows you to have a bot on your own channel.\n" +"It has been created for users that can't host or\n" +"configure a bot, or for use on networks that don't\n" +"allow user bots. Available commands are listed\n" +"below; to use them, type %s%s command. For\n" +"more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s kanalınızda bir botunuzun olmasını sağlar. Bu\n" +"servis bot konfigürasyonundan anlamayanlar yada\n" +"bota izin vermeyen networkler için geliştirilmiştir.\n" +"Mevcut komutlar aşağıda listelenmiştir. Kullanmak için\n" +"/msg %s command yazın. Belirli bir komut hakkında\n" +"daha fazla bilgi için, /msg %s HELP komut\n" +"yazın." + +#: modules/pseudoclients/nickserv.cpp:466 +#, fuzzy, c-format +msgid "" +"%s allows you to register a nickname and\n" +"prevent others from using it. The following\n" +"commands allow for registration and maintenance of\n" +"nicknames; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s nickinizi \"kayıt\" etmenizi ve diğerlerinin nickinizi \n" +"kullanmalarını engellemeyi sağlar. Aşağıdaki komutlar nicki\n" +"kayıt etmeye ve korumaya izin verir, kullanmak için, \n" +"/msg %s komut yazın. Belirli bir komut hakkında daha \n" +"fazla bilgi için, /msg %s HELP komut yazın." + +#: modules/pseudoclients/nickserv.cpp:473 +#, fuzzy, c-format +msgid "" +"%s allows you to register an account.\n" +"The following commands allow for registration and maintenance of\n" +"accounts; to use them, type %s%s command.\n" +"For more information on a specific command, type\n" +"%s%s %s command.\n" +msgstr "" +"%s nickinizi \"kayıt\" etmenizi ve diğerlerinin nickinizi \n" +"kullanmalarını engellemeyi sağlar. Aşağıdaki komutlar nicki\n" +"kayıt etmeye ve korumaya izin verir, kullanmak için, \n" +"/msg %s komut yazın. Belirli bir komut hakkında daha \n" +"fazla bilgi için, /msg %s HELP komut yazın." + +#: modules/pseudoclients/chanserv.cpp:255 +#, fuzzy, c-format +msgid "" +"%s allows you to register and control various\n" +"aspects of channels. %s can often prevent\n" +"malicious users from \"taking over\" channels by limiting\n" +"who is allowed channel operator privileges. Available\n" +"commands are listed below; to use them, type\n" +"%s%s command. For more information on a\n" +"specific command, type %s%s HELP command.\n" +msgstr "" +"%s kanallarınızı kayıt etmenizi ve kontrol etmenizi\n" +"sağlar. %s kötü niyetli kullanıcıların kanalları ele \n" +"geçirmelerini(takeover), kanalda kimlerin op olacağını sizin\n" +"tarafınızdan beliryerek engeller. Mevcut komutlar aşağıda \n" +"listelenmiştir; onları kullanmak için /msg %s komut\n" +"yazın. Belirli bir komut hakkında daha fazla bilgi için,\n" +"/msg %s HELP komut yazın.\n" +" " + +#: modules/commands/bs_badwords.cpp:298 +#, c-format +msgid "%s already exists in %s bad words list." +msgstr "%s zaten %s kanalının küfür listesinde var." + +#: modules/commands/cs_akick.cpp:170 +#, c-format +msgid "%s already exists on %s autokick list." +msgstr "%s nicki %s kanalının akick listesinde zaten var." + +#: modules/commands/os_session.cpp:361 +#, c-format +msgid "%s already exists on the EXCEPTION list." +msgstr "%s already exists on the EXCEPTION list." + +#: modules/commands/bs_kick.cpp:214 modules/commands/bs_kick.cpp:389 +#: modules/commands/bs_kick.cpp:520 modules/commands/bs_kick.cpp:651 +#, c-format +msgid "%s cannot be taken as times to ban." +msgstr "%s değeri kullanılamaz." + +#: modules/commands/os_mode.cpp:163 +#, fuzzy, c-format +msgid "%s changed your usermodes to %s." +msgstr "%s changed your usermodes." + +#: modules/commands/os_list.cpp:47 +#, fuzzy, c-format +msgid "%s channel list:" +msgstr "Kanal listesi sonu." + +#: modules/commands/cs_xop.cpp:343 +#, fuzzy, c-format +msgid "%s deleted from %s %s list." +msgstr "%s %s kanali AOP listesinden silindi." + +#: modules/commands/cs_access.cpp:326 +#, c-format +msgid "%s deleted from %s access list." +msgstr "%s %s kanalının access listesinden silindi." + +#: modules/commands/cs_akick.cpp:276 +#, c-format +msgid "%s deleted from %s autokick list." +msgstr "%s %s kanalının akick listesinden silindi." + +#: modules/commands/bs_badwords.cpp:348 +#, c-format +msgid "%s deleted from %s bad words list." +msgstr "%s %s kanalının küfür listesinden çıkarıldı." + +#: modules/commands/ns_access.cpp:72 +#, fuzzy, c-format +msgid "%s deleted from %s's access list." +msgstr "%s %s kanalının access listesinden silindi." + +#: modules/commands/ns_cert.cpp:233 +#, fuzzy, c-format +msgid "%s deleted from %s's certificate list." +msgstr "%s access listenizden silindi." + +#: modules/commands/os_session.cpp:414 +#, c-format +msgid "%s deleted from session-limit exception list." +msgstr "%s session-limit exception listesinden silindi." + +#: modules/commands/os_sxline.cpp:99 +#, fuzzy, c-format +msgid "%s deleted from the %s list." +msgstr "%s %s kanali AOP listesinden silindi." + +#: modules/commands/os_akill.cpp:246 +#, c-format +msgid "%s deleted from the AKILL list." +msgstr "%s AKILL listesinden silindi." + +#: modules/commands/cs_access.cpp:685 +#, c-format +msgid "%s disabled on channel %s." +msgstr "%s %s kanalında iptal edildi." + +#: modules/commands/cs_invite.cpp:75 +#, c-format +msgid "%s has been invited to %s." +msgstr "%s has been invited to %s." + +#: modules/commands/os_svs.cpp:104 +#, fuzzy, c-format +msgid "%s has been joined to %s." +msgstr "%s has been invited to %s." + +#: modules/commands/os_svs.cpp:152 +#, fuzzy, c-format +msgid "%s has been parted from %s." +msgstr "%s has been unbanned from %s." + +#: modules/commands/cs_unban.cpp:96 +#, c-format +msgid "%s has been unbanned from %s." +msgstr "%s has been unbanned from %s." + +#: modules/commands/ns_alist.cpp:110 +#, fuzzy, c-format +msgid "%s has no access in any channels." +msgstr "%s %s kanalında iptal edildi." + +#: modules/commands/cs_status.cpp:55 +#, fuzzy, c-format +msgid "%s has no access on %s." +msgstr "%s has been invited to %s." + +#: modules/commands/cs_set.cpp:307 +#, c-format +msgid "%s has too many channels registered." +msgstr "%s çok fazla kanala sahip." + +#: modules/commands/cs_status.cpp:51 +#, fuzzy, c-format +msgid "%s is a super administrator." +msgstr "%s is a services operator of type %s." + +#: modules/pseudoclients/memoserv.cpp:214 +#, fuzzy, c-format +msgid "" +"%s is a utility allowing IRC users to send short\n" +"messages to other IRC users, whether they are online at\n" +"the time or not, or to channels(*). Both the sender's\n" +"nickname and the target nickname or channel must be\n" +"registered in order to send a memo.\n" +"%s's commands include:" +msgstr "" +"%s kullanıcıların birbirlerine veya kanallara(*) online \n" +"olmasalar bile mesaj göndermelerini sağlar. Mesaj gönderebilmek\n" +"için gönderenin nicki, gönderilenin nicki veya kanalın kayıtlı\n" +"olması gereklidir.\n" +"\n" +"%s'ün mevcut komutları:" + +#: modules/commands/cs_invite.cpp:66 +#, fuzzy, c-format +msgid "%s is already in %s!" +msgstr "You are already in %s! " + +#: modules/commands/os_svs.cpp:99 +#, fuzzy, c-format +msgid "%s is already in %s." +msgstr "You are already in %s! " + +#: modules/commands/ms_ignore.cpp:65 +#, fuzzy, c-format +msgid "%s is already on the ignore list." +msgstr "%s access listenize eklendi." + +#: modules/commands/cs_suspend.cpp:97 modules/commands/ns_suspend.cpp:106 +#, fuzzy, c-format +msgid "%s is already suspended." +msgstr "You are already in %s! " + +#: modules/commands/ms_rsend.cpp:56 modules/commands/ms_send.cpp:55 +#, fuzzy, c-format +msgid "%s is not a registered unforbidden nick or channel." +msgstr "%s geçerli bir bot yada kanal değil." + +#: modules/commands/cs_set.cpp:178 +#, c-format +msgid "%s is not a valid ban type." +msgstr "%s geçerli bir ban tipi değil." + +#: modules/commands/bs_info.cpp:101 +#, c-format +msgid "%s is not a valid bot or registered channel." +msgstr "%s geçerli bir bot yada kanal değil." + +#: include/language.h:86 +#, fuzzy, c-format +msgid "%s is not a valid e-mail address." +msgstr "%s geçerli bir ban tipi değil." + +#: include/language.h:80 +#, fuzzy, c-format +msgid "%s is not currently on channel %s." +msgstr "%s %s kanalında iptal edildi." + +#: modules/commands/os_svs.cpp:144 +#, fuzzy, c-format +msgid "%s is not in %s." +msgstr "You are already in %s! " + +#: modules/commands/ms_ignore.cpp:77 +#, fuzzy, c-format +msgid "%s is not on the ignore list." +msgstr "%s not found on ignore list." + +#: modules/commands/cs_status.cpp:90 +#, fuzzy, c-format +msgid "%s is on the auto kick list of %s (%s)." +msgstr "%s nicki %s kanalının akick listesine eklendi." + +#: modules/commands/cs_status.cpp:53 +#, fuzzy, c-format +msgid "%s is the founder of %s." +msgstr "%s %s kanalında iptal edildi." + +#: modules/commands/cs_status.cpp:78 +#, c-format +msgid "%s matches access entry %s (from entry %s), which has privilege %s." +msgstr "" + +#: modules/commands/cs_status.cpp:71 +#, c-format +msgid "%s matches access entry %s, which has privilege %s." +msgstr "" + +#: include/language.h:109 +#, c-format +msgid "" +"%s matches an except on %s and cannot be banned until the except has been " +"removed." +msgstr "" + +#: modules/commands/cs_status.cpp:96 +#, fuzzy, c-format +msgid "%s matches auto kick entry %s on %s (%s)." +msgstr "%s nicki %s kanalının akick listesine eklendi." + +#: modules/commands/cs_xop.cpp:353 +#, fuzzy, c-format +msgid "%s not found on %s %s list." +msgstr "%s %s kanali AOP listesinde bulunamadi." + +#: modules/commands/cs_access.cpp:338 modules/commands/cs_flags.cpp:255 +#, c-format +msgid "%s not found on %s access list." +msgstr "%s %s kanalının access listesinde bulunamadı." + +#: modules/commands/cs_akick.cpp:265 +#, c-format +msgid "%s not found on %s autokick list." +msgstr "%s %s kanalının akick listesinde bulunamadı." + +#: modules/commands/bs_badwords.cpp:341 +#, c-format +msgid "%s not found on %s bad words list." +msgstr "%s %s kanalının küfür listesinde bulunamadı." + +#: modules/commands/ns_access.cpp:66 +#, fuzzy, c-format +msgid "%s not found on %s's access list." +msgstr "%s %s kanalının access listesinde bulunamadı." + +#: modules/commands/ns_cert.cpp:226 +#, fuzzy, c-format +msgid "%s not found on %s's certificate list." +msgstr "%s access listenizde bulunamadı." + +#: modules/commands/os_ignore.cpp:320 +#, fuzzy, c-format +msgid "%s not found on ignore list." +msgstr "%s not found on ignore list." + +#: modules/commands/os_session.cpp:238 +#, c-format +msgid "" +"%s not found on session list, but has a limit of %d because it matches entry:" +" %s." +msgstr "" + +#: modules/commands/os_session.cpp:418 +#, c-format +msgid "%s not found on session-limit exception list." +msgstr "%s session-limit exception listesinde bulunamadı." + +#: modules/commands/os_sxline.cpp:92 +#, fuzzy, c-format +msgid "%s not found on the %s list." +msgstr "%s %s kanali AOP listesinde bulunamadi." + +#: modules/commands/os_akill.cpp:237 +#, c-format +msgid "%s not found on the AKILL list." +msgstr "%s AKILL listesinde bulunamadı." + +#: modules/commands/cs_flags.cpp:251 +#, fuzzy, c-format +msgid "%s removed from the %s access list." +msgstr "%s %s kanalının access listesinden silindi." + +#: modules/commands/ms_ignore.cpp:74 +#, fuzzy, c-format +msgid "%s removed from the ignore list." +msgstr "%s access listenizden silindi." + +#: modules/commands/os_list.cpp:157 +#, fuzzy, c-format +msgid "%s users list:" +msgstr "Kullanıcı listesi sonu." + +#: modules/commands/os_ignore.cpp:316 +#, c-format +msgid "%s will no longer be ignored." +msgstr "%s will no longer be ignored." + +#: modules/commands/os_ignore.cpp:238 +#, c-format +msgid "%s will now be ignored for %s." +msgstr "%s will now be ignored for %s." + +#: modules/commands/os_ignore.cpp:233 +#, c-format +msgid "%s will now permanently be ignored." +msgstr "%s will now permanently be ignored." + +#: include/language.h:66 +#, fuzzy, c-format +msgid "%s%s HELP %s for more information." +msgstr "" +"Belirli bir özellik hakkında daha fazla bilgi için\n" +"/msg %s HELP özellik yazın." + +#: modules/commands/bs_bot.cpp:270 +msgid "ADD nick user host real" +msgstr "" + +#: modules/commands/bs_bot.cpp:271 +#, fuzzy +msgid "CHANGE oldnick newnick [user [host [real]]]" +msgstr "" +"BOT ADD nick user host gerçekismi\n" +"BOT CHANGE eskinick yeninick [user [host [gerçekismi]]]\n" +"BOT DEL nick" + +#: modules/commands/bs_bot.cpp:272 +#, fuzzy +msgid "DEL nick" +msgstr "DEL ." + +#: modules/commands/os_session.cpp:560 +#, fuzzy +msgid "" +"EXCEPTION ADD adds the given host mask to the exception list.\n" +"Note that nick!user@host and user@host masks are invalid!\n" +"Only real host masks, such as box.host.dom and *.host.dom,\n" +"are allowed because sessions limiting does not take nick or\n" +"user names into account. limit must be a number greater than\n" +"or equal to zero. This determines how many sessions this host\n" +"may carry at a time. A value of zero means the host has an\n" +"unlimited session limit. See the AKILL help for details about\n" +"the format of the optional expiry parameter.\n" +" \n" +"EXCEPTION DEL removes the given mask from the exception list.\n" +" \n" +"EXCEPTION LIST and EXCEPTION VIEW show all current\n" +"sessions if the optional mask is given, the list is limited\n" +"to those sessions matching the mask. The difference is that\n" +"EXCEPTION VIEW is more verbose, displaying the name of the\n" +"person who added the exception, its session limit, reason,\n" +"host mask and the expiry date and time.\n" +" \n" +"Note that a connecting client will \"use\" the first exception\n" +"their host matches." +msgstr "" +"Kullanımı: EXCEPTION ADD [+zamanaşımı] mask limit sebep\n" +" EXCEPTION DEL {mask | liste}\n" +" EXCEPTION MOVE num pozisyon\n" +" EXCEPTION LIST [mask | liste]\n" +" EXCEPTION VIEW [mask | liste]\n" +"\n" +"Servis adminlerinin, belirli oturum limiti olan hostların \n" +"listesini değiştirmesini sağlar. Shell server gibi bazı \n" +"makinaların varsayılandan daha fazla kullanıcıyı aynı anda\n" +"taşımasını sağlar. Eğer bir host session(oturum) limitine\n" +"ulaşmışsa o hosttan bağlanmaya çalışan tüm kullanıcılar \n" +"kill lenir. Kill lenmeden önce, %s'ün /NOTICE i ile\n" +"uyarılarak session limiti hakkında yardım verilir. Bu uyarının\n" +"içeriği ayar yapmayla ilgilidir.\n" +"\n" +"EXCEPTION ADD exception(istisna) listesine belirtilen hostmaskı\n" +"ekler. nick!user@host ve user@host masklarının geçersiz \n" +"olduğunu unutmayın! Sadece box.host.dom ve *.host.dom gibi \n" +"gerçek hostmasklar kullanılabilinir, çünkü session limitleme \n" +"nickleri ve username leri hesaba almaz. limit sıfırdan büyük \n" +"yada eşit bir rakam olmalıdır. Bu o host un aynı anda kaç oturum\n" +"(session) kaldırabileceğini belirler. Sıfır değeri o host un\n" +"sınırsız oturum limiti olduğunu belirtir. Opsiyonel zamanaşımı \n" +"parametresinin formatı ile ilgili yardım için AKILL in \n" +"yardımına bakınız.\n" +"EXCEPTION DEL listesinden belirtilen mask ı çıkarır.\n" +"EXCEPTION MOVE exception numarasını(num) pozisyona (position)\n" +"çevirir. Aralarındaki exceptionların yeri aralığı doldurmak için \n" +"yukarı yada aşşağı değiştirilecektir.\n" +"EXCEPTION LIST ve EXCEPTION VIEW tüm mevcut exceptionları \n" +"gösterir; eğer opsiyonel olarak mask belirtilmişse, liste\n" +"bu masklarla uyuşan exceptionlarla sınırlandırılır. Aradaki fark\n" +"EXCEPTION VIEW daha gelismis bir komuttur ve exception ı ekleyenin \n" +"nickini, o exceptionın session limitini, sebebi, host maskı ve zaman \n" +"aşımı tarih ve zamanını gösterir.\n" +"\n" +"Bağlanan kullanıcı, hostuyla uyuşan ilk exceptionı kullanır. Büyük \n" +"exception listeleri ve geniş olarak uyuşan exception maskları \n" +"servislerin performansını düşürür. \n" +"\n" +"Servis adminleri tarafından kullanılabilir." + +#: modules/commands/os_noop.cpp:68 +msgid "" +"SET kills all operators from the given\n" +"server and prevents operators from opering\n" +"up on the given server. REVOKE removes this\n" +"restriction." +msgstr "" + +#: modules/commands/cs_access.cpp:611 +#, c-format +msgid "" +"User access levels can be seen by using the\n" +"%s command; type %s%s HELP LEVELS for\n" +"information." +msgstr "" + +#: modules/commands/ms_read.cpp:35 +#, c-format +msgid "[auto-memo] The memo you sent to %s has been viewed." +msgstr "[auto-memo] The memo you sent to %s has been viewed." + +#: modules/commands/ns_group.cpp:92 +#, fuzzy +msgid "[target] [password]" +msgstr "GROUP hedef şifre" + +#: modules/commands/ns_set.cpp:453 +msgid "address" +msgstr "" + +#: modules/commands/bs_set.cpp:162 +#, fuzzy +msgid "botname {ON|OFF}" +msgstr "SASET nickname AUTOOP {ON | OFF}" + +#: modules/extra/stats/cs_fantasy_top.cpp:39 +#: modules/extra/stats/cs_fantasy_top.cpp:51 +#: modules/commands/cs_suspend.cpp:152 modules/commands/cs_sync.cpp:20 +#: modules/commands/cs_log.cpp:106 modules/commands/bs_assign.cpp:91 +#: modules/commands/cs_info.cpp:20 modules/commands/cs_getkey.cpp:20 +#, fuzzy +msgid "channel" +msgstr "DROP kanaladı" + +#: modules/commands/cs_set.cpp:138 +#, fuzzy +msgid "channel bantype" +msgstr "ACT kanaladı yazı" + +#: modules/commands/cs_drop.cpp:20 +#, fuzzy +msgid "channel channel" +msgstr "TOPIC kanaladi [konu]" + +#: modules/commands/cs_log.cpp:107 +#, fuzzy +msgid "channel command method [status]" +msgstr "KICK kanaladı özellik {ON|OFF} [ayarlar]" + +#: modules/commands/cs_kick.cpp:21 +#, fuzzy +msgid "channel mask [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_mode.cpp:20 +#, fuzzy +msgid "channel modes" +msgstr "MODE kanaladı modlar" + +#: modules/commands/cs_set.cpp:267 modules/commands/bs_assign.cpp:20 +#, fuzzy +msgid "channel nick" +msgstr "UNBAN kanaladı [name]" + +#: modules/commands/cs_kick.cpp:20 +#, fuzzy +msgid "channel nick [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_clone.cpp:115 +#, fuzzy +msgid "channel target [what]" +msgstr "CLEAR kanaladı neyi" + +#: modules/commands/bs_control.cpp:20 modules/commands/bs_control.cpp:80 +#, fuzzy +msgid "channel text" +msgstr "ACT kanaladı yazı" + +#: modules/commands/bs_set.cpp:91 +#, fuzzy +msgid "channel time" +msgstr "ACT kanaladı yazı" + +#: modules/commands/os_kick.cpp:20 +#, fuzzy +msgid "channel user reason" +msgstr "KICK kanaladı kullanıcı sebep" + +#: modules/commands/cs_enforce.cpp:228 +#, fuzzy +msgid "channel what" +msgstr "TOPIC kanaladi [konu]" + +#: modules/commands/cs_xop.cpp:481 +#, fuzzy +msgid "channel ADD mask" +msgstr "MODE kanaladı modlar" + +#: modules/commands/cs_access.cpp:499 +msgid "channel ADD mask level" +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:194 +#, fuzzy +msgid "channel ADD message" +msgstr "MODE kanaladı modlar" + +#: modules/commands/bs_badwords.cpp:371 +msgid "channel ADD word [SINGLE | START | END]" +msgstr "" + +#: modules/commands/cs_akick.cpp:435 +#, fuzzy +msgid "channel ADD {nick | mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_topic.cpp:151 +#, fuzzy +msgid "channel APPEND topic" +msgstr "TOPIC kanaladi [konu]" + +#: modules/commands/cs_access.cpp:503 modules/commands/cs_flags.cpp:376 +#: modules/commands/cs_xop.cpp:484 modules/commands/cs_entrymsg.cpp:197 +#: modules/commands/bs_badwords.cpp:374 modules/commands/cs_akick.cpp:440 +#, fuzzy +msgid "channel CLEAR" +msgstr "DROP kanaladı" + +#: modules/commands/cs_mode.cpp:736 +#, fuzzy +msgid "channel CLEAR [what]" +msgstr "TOPIC kanaladi [konu]" + +#: modules/commands/os_mode.cpp:21 +#, fuzzy +msgid "channel CLEAR [ALL]" +msgstr "DROP kanaladı" + +#: modules/commands/cs_entrymsg.cpp:195 +#, fuzzy +msgid "channel DEL num" +msgstr "MODE kanaladı modlar" + +#: modules/commands/cs_access.cpp:500 modules/commands/cs_xop.cpp:482 +#, fuzzy +msgid "channel DEL {mask | entry-num | list}" +msgstr "DEL [kanaladı] {num | liste | ALL}" + +#: modules/commands/cs_akick.cpp:436 +#, fuzzy +msgid "channel DEL {nick | mask | entry-num | list}" +msgstr "AOP kanal {ADD|DEL|LIST|CLEAR} [nick | liste-no]" + +#: modules/commands/bs_badwords.cpp:372 +#, fuzzy +msgid "channel DEL {word | entry-num | list}" +msgstr "DEL [kanaladı] {num | liste | ALL}" + +#: modules/commands/cs_akick.cpp:439 +msgid "channel ENFORCE" +msgstr "" + +#: modules/commands/cs_access.cpp:744 modules/commands/cs_entrymsg.cpp:196 +#, fuzzy +msgid "channel LIST" +msgstr "DROP kanaladı" + +#: modules/commands/cs_akick.cpp:437 +#, fuzzy +msgid "channel LIST [mask | entry-num | list]" +msgstr "AOP kanal {ADD|DEL|LIST|CLEAR} [nick | liste-no]" + +#: modules/commands/cs_access.cpp:501 modules/commands/cs_xop.cpp:483 +#: modules/commands/bs_badwords.cpp:373 +#, fuzzy +msgid "channel LIST [mask | list]" +msgstr "AOP kanal {ADD|DEL|LIST|CLEAR} [nick | liste-no]" + +#: modules/commands/cs_flags.cpp:375 +msgid "channel LIST [mask | +flags]" +msgstr "" + +#: modules/commands/cs_mode.cpp:734 +#, fuzzy +msgid "channel LOCK {ADD|DEL|SET|LIST} [what]" +msgstr "AOP kanal {ADD|DEL|LIST|CLEAR} [nick | liste-no]" + +#: modules/commands/cs_access.cpp:745 +#, fuzzy +msgid "channel RESET" +msgstr "SET kanaladı GREET {ON|OFF}" + +#: modules/commands/cs_mode.cpp:735 +#, fuzzy +msgid "channel SET modes" +msgstr "MODE kanaladı modlar" + +#: modules/commands/cs_access.cpp:742 +msgid "channel SET type level" +msgstr "" + +#: modules/commands/cs_akick.cpp:438 +#, fuzzy +msgid "channel VIEW [mask | entry-num | list]" +msgstr "AOP kanal {ADD|DEL|LIST|CLEAR} [nick | liste-no]" + +#: modules/commands/cs_access.cpp:502 +#, fuzzy +msgid "channel VIEW [mask | list]" +msgstr "DEL [kanaladı] {num | liste | ALL}" + +#: modules/commands/cs_register.cpp:20 modules/commands/cs_set.cpp:205 +#, fuzzy +msgid "channel [description]" +msgstr "REGISTER kanaladı açıklama" + +#: modules/commands/cs_set.cpp:950 modules/commands/cs_invite.cpp:20 +#: modules/commands/cs_unban.cpp:20 +#, fuzzy +msgid "channel [nick]" +msgstr "UNBAN kanaladı [name]" + +#: modules/commands/cs_set_misc.cpp:96 +#, fuzzy +msgid "channel [parameters]" +msgstr "CLEAR kanaladı neyi" + +#: modules/commands/cs_mode.cpp:807 modules/commands/cs_status.cpp:20 +#, fuzzy +msgid "channel [user]" +msgstr "UNBAN kanaladı [name]" + +#: modules/commands/cs_suspend.cpp:59 +#, fuzzy +msgid "channel [+expiry] [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_ban.cpp:40 +#, fuzzy +msgid "channel [+expiry] {nick | mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_flags.cpp:374 +#, fuzzy +msgid "channel [MODIFY] mask changes" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/cs_topic.cpp:150 +#, fuzzy +msgid "channel [SET] [topic]" +msgstr "TOPIC kanaladi [konu]" + +#: modules/commands/cs_topic.cpp:152 +#, fuzzy +msgid "channel [UNLOCK|LOCK]" +msgstr "DROP kanaladı" + +#: modules/fantasy.cpp:20 modules/commands/greet.cpp:20 +#: modules/commands/bs_assign.cpp:154 +#, fuzzy +msgid "channel {ON|OFF}" +msgstr "SET kanaladi XOP {ON | OFF}" + +#: modules/commands/bs_kick.cpp:491 +#, fuzzy +msgid "channel {ON|OFF} [ttb [ln [secs]]]" +msgstr "KICK kanaladı özellik {ON|OFF} [ayarlar]" + +#: modules/commands/bs_kick.cpp:361 +#, fuzzy +msgid "channel {ON|OFF} [ttb [min [percent]]]" +msgstr "KICK kanaladı özellik {ON|OFF} [ayarlar]" + +#: modules/commands/bs_kick.cpp:623 +#, fuzzy +msgid "channel {ON|OFF} [ttb [num]]" +msgstr "KICK kanaladı özellik {ON|OFF} [ayarlar]" + +#: modules/commands/bs_kick.cpp:252 modules/commands/bs_kick.cpp:288 +#: modules/commands/bs_kick.cpp:327 modules/commands/bs_kick.cpp:457 +#: modules/commands/bs_kick.cpp:589 modules/commands/bs_kick.cpp:724 +#: modules/commands/bs_kick.cpp:758 +#, fuzzy +msgid "channel {ON|OFF} [ttb]" +msgstr "SET kanaladi XOP {ON | OFF}" + +#: modules/commands/cs_access.cpp:743 +msgid "channel {DIS | DISABLE} type" +msgstr "" + +#: modules/commands/cs_set.cpp:873 +#, fuzzy +msgid "channel {ON | LEVEL | OFF}" +msgstr "SET kanaladı SIGNKICK {ON | LEVEL | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:18 modules/commands/cs_set.cpp:75 +#: modules/commands/cs_set.cpp:336 modules/commands/cs_set.cpp:401 +#: modules/commands/cs_set.cpp:473 modules/commands/cs_set.cpp:622 +#: modules/commands/cs_set.cpp:684 modules/commands/cs_set.cpp:747 +#: modules/commands/cs_set.cpp:811 modules/commands/cs_set.cpp:1044 +#: modules/commands/bs_kick.cpp:792 modules/commands/bs_kick.cpp:857 +#: modules/commands/cs_topic.cpp:21 modules/commands/cs_list.cpp:181 +#, fuzzy +msgid "channel {ON | OFF}" +msgstr "SET kanaladi XOP {ON | OFF}" + +#: modules/commands/ns_getemail.cpp:24 +msgid "email" +msgstr "" + +#: modules/commands/ns_set.cpp:794 +#, fuzzy +msgid "language" +msgstr "SET LANGUAGE numara" + +#: modules/commands/ms_sendall.cpp:25 modules/commands/ms_staff.cpp:25 +#, fuzzy +msgid "memo-text" +msgstr "STAFF memo-text" + +#: modules/commands/gl_global.cpp:22 modules/commands/greet.cpp:84 +#, fuzzy +msgid "message" +msgstr "GLOBAL mesaj" + +#: modules/commands/os_modinfo.cpp:20 modules/commands/os_module.cpp:20 +#: modules/commands/os_module.cpp:57 modules/commands/os_module.cpp:129 +msgid "modname" +msgstr "" + +#: modules/commands/ns_set.cpp:330 +msgid "new-display" +msgstr "" + +#: modules/commands/ns_set.cpp:120 +#, fuzzy +msgid "new-password" +msgstr "GROUP hedef şifre" + +#: modules/extra/stats/cs_fantasy_stats.cpp:52 modules/commands/hs_del.cpp:20 +#: modules/commands/hs_del.cpp:60 modules/commands/ms_check.cpp:20 +#: modules/commands/hs_request.cpp:192 modules/commands/cs_seen.cpp:262 +#, fuzzy +msgid "nick" +msgstr "INFO nick" + +#: modules/commands/os_svs.cpp:79 +#, fuzzy +msgid "nick channel" +msgstr "CANCEL {nick | kanaladı}" + +#: modules/commands/os_svs.cpp:123 +#, fuzzy +msgid "nick channel [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_oline.cpp:20 +#, fuzzy +msgid "nick flags" +msgstr "OLINE nick flags" + +#: modules/commands/hs_set.cpp:20 modules/commands/hs_set.cpp:126 +#, fuzzy +msgid "nick hostmask" +msgstr "SET  ." + +#: modules/commands/os_svs.cpp:20 +#, fuzzy +msgid "nick newnick" +msgstr "SVSNICK nick newnick " + +#: modules/commands/hs_request.cpp:241 +#, fuzzy +msgid "nick [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/ns_getpass.cpp:20 modules/commands/ns_drop.cpp:19 +#: modules/commands/ns_suspend.cpp:161 +#, fuzzy +msgid "nickname" +msgstr "CHECK nickname" + +#: modules/commands/ns_set.cpp:546 +#, fuzzy +msgid "nickname address" +msgstr "FORBID nick sebep" + +#: modules/commands/ns_resetpass.cpp:22 +#, fuzzy +msgid "nickname email" +msgstr "FORBID nick sebep" + +#: modules/commands/ns_set.cpp:872 +#, fuzzy +msgid "nickname language" +msgstr "FORBID nick sebep" + +#: modules/commands/greet.cpp:145 +#, fuzzy +msgid "nickname message" +msgstr "FORBID nick sebep" + +#: modules/commands/ns_set.cpp:399 +#, fuzzy +msgid "nickname new-display" +msgstr "FORBID nick sebep" + +#: modules/commands/ns_set.cpp:173 +#, fuzzy +msgid "nickname new-password" +msgstr "GHOST nick [şifre]" + +#: modules/commands/ns_set_misc.cpp:170 +#, fuzzy +msgid "nickname [parameter]" +msgstr "GHOST nick [şifre]" + +#: modules/commands/ns_recover.cpp:150 +#, fuzzy +msgid "nickname [password]" +msgstr "GHOST nick [şifre]" + +#: modules/commands/ns_suspend.cpp:61 +#, fuzzy +msgid "nickname [+expiry] [reason]" +msgstr "FORBID nick sebep" + +#: modules/commands/ns_info.cpp:239 +#, fuzzy +msgid "nickname {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" +msgstr "SET HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}" + +#: modules/extra/stats/m_chanstats.cpp:130 modules/commands/ns_set.cpp:302 +#: modules/commands/ns_set.cpp:631 modules/commands/ns_set.cpp:985 +#: modules/commands/ns_set.cpp:1076 modules/commands/ns_set.cpp:1105 +#: modules/commands/ns_list.cpp:252 +#, fuzzy +msgid "nickname {ON | OFF}" +msgstr "SASET nickname AUTOOP {ON | OFF}" + +#: modules/commands/ns_set.cpp:760 +#, fuzzy +msgid "nickname {ON | QUICK | IMMED | OFF}" +msgstr "SASET nickname KILL {ON | QUICK | IMMED | OFF}" + +#: modules/commands/bs_set.cpp:20 +#, fuzzy +msgid "option (channel | bot) settings" +msgstr "SET kanaladı özellik ayarlar" + +#: modules/commands/cs_set.cpp:21 +#, fuzzy +msgid "option channel parameters" +msgstr "SEND {nick | kanaladı} mesaj" + +#: modules/commands/bs_kick.cpp:120 +#, fuzzy +msgid "option channel {ON|OFF} [settings]" +msgstr "KICK kanaladı özellik {ON|OFF} [ayarlar]" + +#: modules/commands/ns_set.cpp:75 +msgid "option nickname parameters" +msgstr "" + +#: modules/commands/ms_set.cpp:207 modules/commands/ns_set.cpp:20 +#, fuzzy +msgid "option parameters" +msgstr "SET özellik ayar" + +#: modules/commands/os_set.cpp:170 +#, fuzzy +msgid "option setting" +msgstr "SET özellik ayar" + +#: modules/commands/ns_register.cpp:22 +#, fuzzy +msgid "passcode" +msgstr "REGISTER şifreniz emailiniz" + +#: modules/commands/os_login.cpp:19 +#, fuzzy +msgid "password" +msgstr "GROUP hedef şifre" + +#: modules/commands/ns_register.cpp:124 +#, fuzzy +msgid "password [email]" +msgstr "REGISTER şifreniz emailiniz" + +#: modules/commands/ns_register.cpp:122 +#, fuzzy +msgid "password email" +msgstr "REGISTER şifreniz emailiniz" + +#: modules/commands/cs_list.cpp:21 +#, fuzzy +msgid "pattern [SUSPENDED] [NOEXPIRE]" +msgstr "LIST model [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/ns_list.cpp:20 +#, fuzzy +msgid "pattern [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" +msgstr "LIST model [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]" + +#: modules/commands/os_jupe.cpp:20 +#, fuzzy +msgid "server [reason]" +msgstr "JUPE serverismi [sebep]" + +#: modules/commands/os_mode.cpp:147 +#, fuzzy +msgid "user modes" +msgstr "MODE kanaladı modlar" + +#: modules/commands/os_kill.cpp:20 +#, fuzzy +msgid "user [reason]" +msgstr "JUPE serverismi [sebep]" + +#: modules/commands/os_sxline.cpp:440 +#, fuzzy +msgid "" +" \n" +"SNLINE ADD adds the given realname mask to the SNLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SNLINE which does not expire, use +0. If the\n" +"realname mask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current SNLINE default expiry time can be found with the\n" +"STATS AKILL command.\n" +" \n" +"Note: because the realname mask may contain spaces, the\n" +"separator between it and the reason is a colon." +msgstr "" +"Kullanımı: AKILL ADD [+zamanaşımı] mask sebep\n" +" AKILL DEL {mask | kayıt-no | liste}\n" +" AKILL LIST [mask | liste]\n" +" AKILL VIEW [mask | liste]\n" +" AKILL CLEAR\n" +"\n" +"Servis operatörlerinin AKILL listesini işletmesini sağlar.\n" +"Eğer AKILL listesineki mask la uyuşan bir kullanıcı\n" +"bağlanmaya çalışırsa, Servisler o kullanıcıyı KILL ler ve,\n" +"destekleyen server tiplerinde, tüm serverların o maska K-line\n" +"koymasını sağlar.\n" +"\n" +"AKILL ADD belirtilen user@host maskını AKILL listesine\n" +"belirtilen sebeple(mutlaka belirtilmelidir) birlikte\n" +"ekler. AKILL DEL belirtilen maskı eğer listedeyse AKILL \n" +"listesinden çıkarır. AKILL LIST mevcut tüm AKILL leri\n" +"gösterir; eğer opsiyonel olarak mask belirtilmişse, AKILL\n" +"listesi belirtilen maskla uyuşanlarla sınırlandırılır. \n" +"\n" +"AKILL VIEW, AKILL LIST in daha açıklayıcı versiyonudur, \n" +"ve AKILL i ekleyeni, eklenme tarihini, ne zaman sona ereceğini,\n" +"user@host maskıyla ve sebeple birlikte gösterir.\n" +"\n" +"Opsiyonel olarak, zaman aşımı süresi AKILL ADD komutuyla\n" +"birlikte belirtilebilir. Zaman aşımı süresi user@host maskından\n" +"önce gelir, ve bir tamsayı olarak şunlardan birinden önce gelir, \n" +"d (gün), h (saat), veya m (dakika). 1h30m gibi kombinasyonlar \n" +"kullanılamaz. Eğer birim belirleyici belirtilmemişse varsayılan \n" +"olarak gün kullanılır (yani +30 un anlamı 30 gündür). Zaman \n" +"aşımına uğramayacak bir AKILL eklemek için +0 kullanın. Eğer \n" +"eklenecek mask + ile başlarsa zaman aşımı süresi belirtilmelidir. \n" +"Mevcut varsayılan AKILL zaman aşımı süresi STATS AKILL komutuyla \n" +"bulunabilir.\n" +"AKILL CLEAR AKILL listesindeki tüm kayıtları siler.\n" +"\n" +"sebep sadece IRC operatörleri tarafından kullanılmak içindir,\n" +"ve kullanıcıların KILL mesajlarında gözükmez.\n" +"\n" +"Servis operatörlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/os_sxline.cpp:678 +#, fuzzy +msgid "" +" \n" +"SQLINE ADD adds the given (nick's) mask to the SQLINE\n" +"list for the given reason (which must be given).\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an SQLINE which does not expire, use +0.\n" +"If the mask to be added starts with a +, an expiry time\n" +"must be given, even if it is the same as the default. The\n" +"current SQLINE default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Kullanımı: AKILL ADD [+zamanaşımı] mask sebep\n" +" AKILL DEL {mask | kayıt-no | liste}\n" +" AKILL LIST [mask | liste]\n" +" AKILL VIEW [mask | liste]\n" +" AKILL CLEAR\n" +"\n" +"Servis operatörlerinin AKILL listesini işletmesini sağlar.\n" +"Eğer AKILL listesineki mask la uyuşan bir kullanıcı\n" +"bağlanmaya çalışırsa, Servisler o kullanıcıyı KILL ler ve,\n" +"destekleyen server tiplerinde, tüm serverların o maska K-line\n" +"koymasını sağlar.\n" +"\n" +"AKILL ADD belirtilen user@host maskını AKILL listesine\n" +"belirtilen sebeple(mutlaka belirtilmelidir) birlikte\n" +"ekler. AKILL DEL belirtilen maskı eğer listedeyse AKILL \n" +"listesinden çıkarır. AKILL LIST mevcut tüm AKILL leri\n" +"gösterir; eğer opsiyonel olarak mask belirtilmişse, AKILL\n" +"listesi belirtilen maskla uyuşanlarla sınırlandırılır. \n" +"\n" +"AKILL VIEW, AKILL LIST in daha açıklayıcı versiyonudur, \n" +"ve AKILL i ekleyeni, eklenme tarihini, ne zaman sona ereceğini,\n" +"user@host maskıyla ve sebeple birlikte gösterir.\n" +"\n" +"Opsiyonel olarak, zaman aşımı süresi AKILL ADD komutuyla\n" +"birlikte belirtilebilir. Zaman aşımı süresi user@host maskından\n" +"önce gelir, ve bir tamsayı olarak şunlardan birinden önce gelir, \n" +"d (gün), h (saat), veya m (dakika). 1h30m gibi kombinasyonlar \n" +"kullanılamaz. Eğer birim belirleyici belirtilmemişse varsayılan \n" +"olarak gün kullanılır (yani +30 un anlamı 30 gündür). Zaman \n" +"aşımına uğramayacak bir AKILL eklemek için +0 kullanın. Eğer \n" +"eklenecek mask + ile başlarsa zaman aşımı süresi belirtilmelidir. \n" +"Mevcut varsayılan AKILL zaman aşımı süresi STATS AKILL komutuyla \n" +"bulunabilir.\n" +"AKILL CLEAR AKILL listesindeki tüm kayıtları siler.\n" +"\n" +"sebep sadece IRC operatörleri tarafından kullanılmak içindir,\n" +"ve kullanıcıların KILL mesajlarında gözükmez.\n" +"\n" +"Servis operatörlerinin Kullanımıyla sınırlıdır." + +#: modules/pseudoclients/nickserv.cpp:492 +#, fuzzy, c-format +msgid "" +" \n" +"Accounts that are not used anymore are subject to\n" +"the automatic expiration, i.e. they will be deleted\n" +"after %d days if not used." +msgstr "" +"Daha fazla kullanılmayan nicklerin otomatik olarak\n" +"kaydının silinmesi söz konusudur, mesela kullanılmayan\n" +"nickler %d gün sonra silinirler." + +#: modules/pseudoclients/botserv.cpp:143 +#, fuzzy +msgid "" +" \n" +"Available commands are:" +msgstr "%s hakkında yardım bulunamadı." + +#: modules/pseudoclients/botserv.cpp:167 +#, c-format +msgid "" +" \n" +"Bot will join a channel whenever there is at least\n" +"%d user(s) on it." +msgstr "" + +#: modules/fantasy.cpp:69 +#, fuzzy, c-format +msgid "" +" \n" +"Enables or disables fantasy mode on a channel.\n" +"When it is enabled, users will be able to use\n" +"fantasy commands on a channel when prefixed\n" +"with one of the following fantasy characters: %s\n" +" \n" +"Note that users wanting to use fantaisist\n" +"commands MUST have enough access for both\n" +"the FANTASIA and the command they are executing." +msgstr "" +"Kullanımı: SET kanaladı FANTASY {ON|OFF}\n" +"\n" +"Kanalda fantazi modunu açar yada kapatır.\n" +"Aktifleştirildiği zaman, kulanıcılar kanalda\n" +"!op, !deop, !voice, !devoice, !kick, !kb, \n" +"!unban, !seen gibi komutları kullanabilirler. \n" +"(nasıl kullanıldıklarını öğrenmek için; onları \n" +"nickle ve nicksiz kullanın vede bazılarındada sebep \n" +"belirtin).\n" +"\n" +"Unutmayınki fantazi komutlarını kullanmak\n" +"isteyen kullanıcıların FANTASIA ve komutun \n" +"gerektirdiği diğer seviyelere yeterli access\n" +"seviyesi olması gereklidir. (örneğin, !op\n" +"komutunu kullanmak için, kullanıcının OPDEOP\n" +"seviyesine yeterli access i olmalıdır)." + +#: modules/commands/greet.cpp:69 +#, fuzzy +msgid "" +" \n" +"Enables or disables greet mode on a channel.\n" +"When it is enabled, the bot will display greet\n" +"messages of users joining the channel, provided\n" +"they have enough access to the channel." +msgstr "" +"Kullanımı: SET kanaladı GREET {ON|OFF}\n" +"\n" +"Kanalda karşılama modunu açar yada kapatır.\n" +"Aktifleştirildiği zaman, bot kanala giren \n" +"kullanıcılara bir karşılama mesajı gönderir,\n" +"tabi eğer bu kişilerin yeterli access leri varsa." + +#: modules/commands/bs_kick.cpp:843 +#, fuzzy +msgid "" +" \n" +"Enables or disables ops protection mode on a channel.\n" +"When it is enabled, ops won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +"Kullanımı: SET kanaladı DONTKICKOPS {ON|OFF}\n" +"\n" +"Kanalda op korumasını açar yada kapatır.\n" +"Aktifleştirildiği zaman, oplar bot tarafında NOKICK\n" +"seviyeleri olmasalar bile atılmazlar." + +#: modules/commands/bs_kick.cpp:908 +#, fuzzy +msgid "" +" \n" +"Enables or disables voices protection mode on a channel.\n" +"When it is enabled, voices won't be kicked by the bot\n" +"even if they don't match the NOKICK level." +msgstr "" +"Kullanımı: SET kanaladı DONTKICKVOICES {ON|OFF}\n" +"\n" +"Kanalda voice korumasını açar yada kapatır.\n" +"Aktifleştirildiği zaman, voice lar bot tarafından\n" +"NOKICK seviyeleri olmasalar bile atılmazlar." + +#: modules/pseudoclients/botserv.cpp:141 +#, c-format +msgid "" +" \n" +"Fantasy commands may be prefixed with one of the following characters: %s\n" +msgstr "" + +#: modules/commands/cs_register.cpp:105 +msgid "" +" \n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname." +msgstr "" + +#: modules/pseudoclients/chanserv.cpp:272 +#, fuzzy, c-format +msgid "" +" \n" +"Note that any channel which is not used for %d days\n" +"(i.e. which no user on the channel's access list enters\n" +"for that period of time) will be automatically dropped." +msgstr "" +"Unutmayın %d gün kullanılmayan kanalların\n" +"(kanalın access listesinde olan bir kimse o süre içinde \n" +"kanala girmezse ) kaydı silinir." + +#: modules/commands/cs_register.cpp:101 +#, c-format +msgid "" +" \n" +"See the %s command (%s%s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +msgstr "" + +#: modules/pseudoclients/nickserv.cpp:486 +#, fuzzy +msgid "" +" \n" +"Services Operators can also drop any nickname without needing\n" +"to identify for the nick, and may view the access list for\n" +"any nickname." +msgstr "" +"Servis adminleri herhangi bir nickin tanıtmasına gerek olmadan \n" +"kaydını silebilir(drop) ve herhangi bir nickin access listesini \n" +"görüntüleyebilir. (/msg %s ACCESS LIST nick)." + +#: modules/pseudoclients/chanserv.cpp:277 +#, fuzzy +msgid "" +" \n" +"Services Operators can also, depending on their access drop\n" +"any channel, view (and modify) the access, levels and akick\n" +"lists and settings for any channel." +msgstr "" +" \n" +"Servis adminleri kanalın kaydını şifreyle tanıtmadan silebilir,\n" +"ve access, Akick ve seviye ayarlarını görüntüleyebilirler." + +#: modules/commands/bs_set.cpp:147 +msgid "" +" \n" +"Sets the time bot bans expire in. If enabled, any bans placed by\n" +"bots, such as flood kicker, badwords kicker, etc. will automatically\n" +"be removed after the given time. Set to 0 to disable bans from\n" +"automatically expiring." +msgstr "" + +#: modules/commands/cs_xop.cpp:542 +#, fuzzy, c-format +msgid "" +" \n" +"The %s ADD command adds the given nickname to the\n" +"%s list.\n" +" \n" +"The %s DEL command removes the given nick from the\n" +"%s list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The %s LIST command displays the %s list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" %s #channel LIST 2-5,7-9\n" +" Lists %s entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The %s CLEAR command clears all entries of the\n" +"%s list." +msgstr "" +"Kullanımı: HOP kanaladi ADD nick\n" +" HOP kanaladi DEL {nick | kayit-no | liste}\n" +" HOP kanaladi LIST [mask | liste]\n" +" HOP kanaladi CLEAR\n" +"\n" +"Bir kanalin HOP (HalfOP) listesini düzenler. HOP\n" +"listesinde bulunan bir kisi kanalda otomatik olarak\n" +"halfop olur.\n" +"\n" +"HOP ADD komutu belirtilen nicki HOP listesine ekler.\n" +"\n" +"HOP DEL komutu belirtilen nicki HOP listesinden siler.\n" +"Eger kayit numaralari listesi belirtilirse, bu kayitlar\n" +"silinir. (Asagidaki örnegi inceleyin.)\n" +"\n" +"HOP LIST komutu HOP listesini gösterir. Eger bir hostmask\n" +"belirtilmisse, o hostmask la uyusan kayitlar gösterilir.\n" +"Eger kayit numaralari listesi belirtilmisse, o numaralardaki\n" +"nickler gösterilir; örnegin:\n" +" HOP #kanaladi LIST 2-5,7-9\n" +" 2 den 5 e ve 7 den 9 a kadar olan kayitlari gösterir.\n" +" \n" +"HOP CLEAR komutu HOP listesindeki tüm kayitlari temziler.\n" +"\n" +"HOP ADD, HOP DEL ve HOP LIST komutlarini AOP lar ve üstü\n" +"HOP CLEAR komutunu ise sadece founder kullanabilir.\n" +"\n" +"Bu komutu kanaliniz için devre disi birakabilirsiniz. O zaman\n" +"access komutlarini kullanmalisiniz. Access komutlari hakkinda\n" +"bilgi almak için /msg %s HELP ACCESS yazin. \n" +"Access ile xOP arasinda geçis yapabilmek için gerekli bilgilere\n" +"/msg %s HELP SET XOP yazarak ulasabilirsiniz." + +#: modules/commands/cs_akick.cpp:508 +#, c-format +msgid "" +" \n" +"The AKICK DEL command removes the given nick or mask\n" +"from the AutoKick list. It does not, however, remove any\n" +"bans placed by an AutoKick; those must be removed\n" +"manually.\n" +" \n" +"The AKICK LIST command displays the AutoKick list, or\n" +"optionally only those AutoKick entries which match the\n" +"given mask.\n" +" \n" +"The AKICK VIEW command is a more verbose version of the\n" +"AKICK LIST command.\n" +" \n" +"The AKICK ENFORCE command causes %s to enforce the\n" +"current AKICK list by removing those users who match an\n" +"AKICK mask.\n" +" \n" +"The AKICK CLEAR command clears all entries of the\n" +"akick list." +msgstr "" + +#: modules/commands/os_akill.cpp:448 +#, fuzzy +msgid "" +" \n" +"The AKILL DEL command removes the given mask from the\n" +"AKILL list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The AKILL LIST command displays the AKILL list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" AKILL LIST 2-5,7-9\n" +" Lists AKILL entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"AKILL VIEW is a more verbose version of AKILL LIST, and\n" +"will show who added an AKILL, the date it was added, and when\n" +"it expires, as well as the user@host/ip mask and reason.\n" +" \n" +"AKILL CLEAR clears all entries of the AKILL list." +msgstr "" +"Kullanımı: HOP kanaladi ADD nick\n" +" HOP kanaladi DEL {nick | kayit-no | liste}\n" +" HOP kanaladi LIST [mask | liste]\n" +" HOP kanaladi CLEAR\n" +"\n" +"Bir kanalin HOP (HalfOP) listesini düzenler. HOP\n" +"listesinde bulunan bir kisi kanalda otomatik olarak\n" +"halfop olur.\n" +"\n" +"HOP ADD komutu belirtilen nicki HOP listesine ekler.\n" +"\n" +"HOP DEL komutu belirtilen nicki HOP listesinden siler.\n" +"Eger kayit numaralari listesi belirtilirse, bu kayitlar\n" +"silinir. (Asagidaki örnegi inceleyin.)\n" +"\n" +"HOP LIST komutu HOP listesini gösterir. Eger bir hostmask\n" +"belirtilmisse, o hostmask la uyusan kayitlar gösterilir.\n" +"Eger kayit numaralari listesi belirtilmisse, o numaralardaki\n" +"nickler gösterilir; örnegin:\n" +" HOP #kanaladi LIST 2-5,7-9\n" +" 2 den 5 e ve 7 den 9 a kadar olan kayitlari gösterir.\n" +" \n" +"HOP CLEAR komutu HOP listesindeki tüm kayitlari temziler.\n" +"\n" +"HOP ADD, HOP DEL ve HOP LIST komutlarini AOP lar ve üstü\n" +"HOP CLEAR komutunu ise sadece founder kullanabilir.\n" +"\n" +"Bu komutu kanaliniz için devre disi birakabilirsiniz. O zaman\n" +"access komutlarini kullanmalisiniz. Access komutlari hakkinda\n" +"bilgi almak için /msg %s HELP ACCESS yazin. \n" +"Access ile xOP arasinda geçis yapabilmek için gerekli bilgilere\n" +"/msg %s HELP SET XOP yazarak ulasabilirsiniz." + +#: modules/commands/os_sxline.cpp:462 +#, fuzzy +msgid "" +" \n" +"The SNLINE DEL command removes the given mask from the\n" +"SNLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SNLINE LIST command displays the SNLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SNLINE LIST 2-5,7-9\n" +" Lists SNLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SNLINE VIEW is a more verbose version of SNLINE LIST, and\n" +"will show who added an SNLINE, the date it was added, and when\n" +"it expires, as well as the realname mask and reason.\n" +" \n" +"SNLINE CLEAR clears all entries of the SNLINE list." +msgstr "" +"Kullanımı: HOP kanaladi ADD nick\n" +" HOP kanaladi DEL {nick | kayit-no | liste}\n" +" HOP kanaladi LIST [mask | liste]\n" +" HOP kanaladi CLEAR\n" +"\n" +"Bir kanalin HOP (HalfOP) listesini düzenler. HOP\n" +"listesinde bulunan bir kisi kanalda otomatik olarak\n" +"halfop olur.\n" +"\n" +"HOP ADD komutu belirtilen nicki HOP listesine ekler.\n" +"\n" +"HOP DEL komutu belirtilen nicki HOP listesinden siler.\n" +"Eger kayit numaralari listesi belirtilirse, bu kayitlar\n" +"silinir. (Asagidaki örnegi inceleyin.)\n" +"\n" +"HOP LIST komutu HOP listesini gösterir. Eger bir hostmask\n" +"belirtilmisse, o hostmask la uyusan kayitlar gösterilir.\n" +"Eger kayit numaralari listesi belirtilmisse, o numaralardaki\n" +"nickler gösterilir; örnegin:\n" +" HOP #kanaladi LIST 2-5,7-9\n" +" 2 den 5 e ve 7 den 9 a kadar olan kayitlari gösterir.\n" +" \n" +"HOP CLEAR komutu HOP listesindeki tüm kayitlari temziler.\n" +"\n" +"HOP ADD, HOP DEL ve HOP LIST komutlarini AOP lar ve üstü\n" +"HOP CLEAR komutunu ise sadece founder kullanabilir.\n" +"\n" +"Bu komutu kanaliniz için devre disi birakabilirsiniz. O zaman\n" +"access komutlarini kullanmalisiniz. Access komutlari hakkinda\n" +"bilgi almak için /msg %s HELP ACCESS yazin. \n" +"Access ile xOP arasinda geçis yapabilmek için gerekli bilgilere\n" +"/msg %s HELP SET XOP yazarak ulasabilirsiniz." + +#: modules/commands/os_sxline.cpp:697 +#, fuzzy +msgid "" +" \n" +"The SQLINE DEL command removes the given mask from the\n" +"SQLINE list if it is present. If a list of entry numbers is\n" +"given, those entries are deleted. (See the example for LIST\n" +"below.)\n" +" \n" +"The SQLINE LIST command displays the SQLINE list.\n" +"If a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" SQLINE LIST 2-5,7-9\n" +" Lists SQLINE entries numbered 2 through 5 and 7\n" +" through 9.\n" +" \n" +"SQLINE VIEW is a more verbose version of SQLINE LIST, and\n" +"will show who added an SQLINE, the date it was added, and when\n" +"it expires, as well as the mask and reason.\n" +" \n" +"SQLINE CLEAR clears all entries of the SQLINE list." +msgstr "" +"Kullanımı: HOP kanaladi ADD nick\n" +" HOP kanaladi DEL {nick | kayit-no | liste}\n" +" HOP kanaladi LIST [mask | liste]\n" +" HOP kanaladi CLEAR\n" +"\n" +"Bir kanalin HOP (HalfOP) listesini düzenler. HOP\n" +"listesinde bulunan bir kisi kanalda otomatik olarak\n" +"halfop olur.\n" +"\n" +"HOP ADD komutu belirtilen nicki HOP listesine ekler.\n" +"\n" +"HOP DEL komutu belirtilen nicki HOP listesinden siler.\n" +"Eger kayit numaralari listesi belirtilirse, bu kayitlar\n" +"silinir. (Asagidaki örnegi inceleyin.)\n" +"\n" +"HOP LIST komutu HOP listesini gösterir. Eger bir hostmask\n" +"belirtilmisse, o hostmask la uyusan kayitlar gösterilir.\n" +"Eger kayit numaralari listesi belirtilmisse, o numaralardaki\n" +"nickler gösterilir; örnegin:\n" +" HOP #kanaladi LIST 2-5,7-9\n" +" 2 den 5 e ve 7 den 9 a kadar olan kayitlari gösterir.\n" +" \n" +"HOP CLEAR komutu HOP listesindeki tüm kayitlari temziler.\n" +"\n" +"HOP ADD, HOP DEL ve HOP LIST komutlarini AOP lar ve üstü\n" +"HOP CLEAR komutunu ise sadece founder kullanabilir.\n" +"\n" +"Bu komutu kanaliniz için devre disi birakabilirsiniz. O zaman\n" +"access komutlarini kullanmalisiniz. Access komutlari hakkinda\n" +"bilgi almak için /msg %s HELP ACCESS yazin. \n" +"Access ile xOP arasinda geçis yapabilmek için gerekli bilgilere\n" +"/msg %s HELP SET XOP yazarak ulasabilirsiniz." + +#: modules/commands/bs_assign.cpp:197 +#, fuzzy +msgid "" +" \n" +"This option makes a channel unassignable. If a bot\n" +"is already assigned to the channel, it is unassigned\n" +"automatically when you enable it." +msgstr "" +"Kullanımı: SET kanaladı NOBOT {ON|OFF}\n" +"\n" +"Bu özellik bir kanalı bot sokulamaz hale getirir. Eğer\n" +"kanala zaten bir bot sokulmuşsa otomatik olarak o bot\n" +"kanaldan çıkarılır.\n" +"\n" +"Servis adminlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/bs_set.cpp:199 +#, fuzzy +msgid "" +" \n" +"This option prevents a bot from being assigned to a\n" +"channel by users that aren't IRC Operators." +msgstr "" +"Kullanımı: SET botun-nicki PRIVATE {ON|OFF}\n" +"\n" +"Bu özellik IRC Operatörleri disindaki userlarin bu\n" +"botlari kanallara sokmalarini engeller.\n" +"\n" +"Bu komutu Servis Adminleri kullanabilir." + +#: modules/pseudoclients/memoserv.cpp:227 +#, c-format +msgid "" +" \n" +"Type %s%s HELP command for help on any of the\n" +"above commands." +msgstr "" + +#: modules/commands/os_oper.cpp:167 +#, c-format +msgid " %s is online using this oper block." +msgstr "" + +#: modules/commands/os_modinfo.cpp:55 +#, c-format +msgid " Command %s on %s is linked to %s" +msgstr "" + +#: modules/commands/os_modinfo.cpp:43 +#, fuzzy, c-format +msgid " Providing service: %s" +msgstr "Providing command: /msg %s %s" + +#: modules/commands/os_oper.cpp:163 +msgid " This oper is configured in the configuration file." +msgstr "" + +#: modules/commands/os_modinfo.cpp:34 +#, c-format +msgid " Loaded at: %p" +msgstr "" + +#: modules/commands/cs_seen.cpp:303 +#, c-format +msgid " but %s mysteriously dematerialized." +msgstr "" + +#: src/messages.cpp:339 +#, c-format +msgid "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." +msgstr "" +"\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead." + +#: modules/commands/os_jupe.cpp:19 +#, fuzzy +msgid "\"Jupiter\" a server" +msgstr " JUPE Bir server'ı \"Kullanılmaz\" yapar" + +#: modules/commands/os_oper.cpp:161 +#, fuzzy, c-format +msgid "%-8s %s" +msgstr "%-20s %s@%s" + +#: modules/extra/stats/cs_fantasy_top.cpp:152 +#, c-format +msgid "%2lu %-16s letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:359 +msgid "%b %d %H:%M:%S %Y %Z" +msgstr "" + +#: modules/commands/cs_log.cpp:205 +#, c-format +msgid "%c is an unknown status mode." +msgstr "" + +#: modules/commands/cs_mode.cpp:431 +#, fuzzy, c-format +msgid "%c%c is not locked on %s." +msgstr "%s yeni mesajlar için uyarılmayacak." + +#: modules/commands/cs_mode.cpp:427 +#, fuzzy, c-format +msgid "%c%c%s has been unlocked from %s." +msgstr "Nick %s has been ungrouped from %s." + +#: modules/commands/cs_clone.cpp:56 +#, fuzzy, c-format +msgid "%d access entries from %s have been cloned to %s." +msgstr "All vhost's in the group %s have been set to %s" + +#: modules/commands/bs_botlist.cpp:56 +#, c-format +msgid "%d bots available." +msgstr "%d bot mevcut." + +#: modules/commands/os_modinfo.cpp:189 +#, fuzzy, c-format +msgid "%d modules loaded." +msgstr "%d Modules loaded." + +#: modules/commands/ns_group.cpp:357 +#, fuzzy, c-format +msgid "%d nickname(s) in the group." +msgstr "Grupta %d nick var." + +#: modules/commands/cs_seen.cpp:137 +#, c-format +msgid "%lu nicks are stored in the database, using %.2Lf kB of memory." +msgstr "" + +#: modules/commands/cs_xop.cpp:241 modules/commands/cs_xop.cpp:372 +#: modules/commands/cs_xop.cpp:450 +#, fuzzy, c-format +msgid "%s %s list is empty." +msgstr "%s kanalinin AOP listesi bos." + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1181 +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1201 +#: modules/commands/bs_kick.cpp:1211 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban)" +msgstr " Kalın yazıda atma : %s (%d tanede ban)" + +#: modules/commands/bs_kick.cpp:1161 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; %d lines in %ds)" +msgstr " Floodda atma : %s (%d tanede ban; %d sıra %ds)" + +#: modules/commands/bs_kick.cpp:1171 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; %d times)" +msgstr " Tekrarda atma : %s (%d tanede ban; %d kez)" + +#: modules/commands/bs_kick.cpp:1141 +#, fuzzy, c-format +msgid "%s (%d kick(s) to ban; minimum %d/%d%%)" +msgstr " Büyük yazıda atma : %s (%d tanede ban; minimum %d/%d%%)" + +#: modules/commands/bs_kick.cpp:1163 +#, fuzzy, c-format +msgid "%s (%d lines in %ds)" +msgstr " %s (expires in %s)" + +#: modules/commands/bs_kick.cpp:1173 +#, c-format +msgid "%s (%d times)" +msgstr "" + +#: modules/commands/cs_seen.cpp:358 +#, c-format +msgid "%s (%s) was kicked from %s (\"%s\") %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:355 +#, c-format +msgid "%s (%s) was kicked from a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:326 +#, c-format +msgid "%s (%s) was last seen changing nick from %s to %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:321 +#, c-format +msgid "%s (%s) was last seen changing nick to %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:310 +#, c-format +msgid "%s (%s) was last seen connecting %s ago (%s)%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:335 +#, c-format +msgid "%s (%s) was last seen joining %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:332 +#, c-format +msgid "%s (%s) was last seen joining a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:344 +#, c-format +msgid "%s (%s) was last seen parting %s %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:341 +#, c-format +msgid "%s (%s) was last seen parting a secret channel %s ago%s" +msgstr "" + +#: modules/commands/cs_seen.cpp:349 +#, c-format +msgid "%s (%s) was last seen quitting (%s) %s ago (%s)." +msgstr "" + +#: modules/commands/bs_kick.cpp:1143 +#, fuzzy, c-format +msgid "%s (minimum %d/%d%%)" +msgstr " Büyük yazıda atma : %s (minimum %d/%d%%)" + +#: modules/commands/cs_access.cpp:245 modules/commands/cs_access.cpp:349 +#: modules/commands/cs_access.cpp:454 modules/commands/cs_access.cpp:467 +#: modules/commands/cs_flags.cpp:295 +#, c-format +msgid "%s access list is empty." +msgstr "%s kanalının access listesi boş." + +#: modules/commands/ns_ajoin.cpp:184 +#, fuzzy, c-format +msgid "%s added to %s's auto join list." +msgstr "%s nicki %s kanalının akick listesine eklendi." + +#: src/xline.cpp:389 +#, fuzzy, c-format +msgid "%s already exists." +msgstr "%s nickli bot zaten var." + +#: modules/commands/cs_akick.cpp:202 modules/commands/cs_akick.cpp:387 +#: modules/commands/cs_akick.cpp:400 +#, c-format +msgid "%s autokick list is empty." +msgstr "%s kanalının akick listesi boş." + +#: modules/commands/bs_badwords.cpp:198 modules/commands/bs_badwords.cpp:316 +#, c-format +msgid "%s bad words list is empty." +msgstr "%s kanalının küfür listesi boş." + +#: modules/commands/cs_set.cpp:993 +#, fuzzy, c-format +msgid "%s cannot be the successor on channel %s as they are the founder." +msgstr "%s %s kanalında successor olamaz çünkü zaten o kanalın founderı." + +#: modules/pseudoclients/global.cpp:90 modules/pseudoclients/hostserv.cpp:78 +#: modules/pseudoclients/operserv.cpp:287 +#, c-format +msgid "%s commands:" +msgstr "%s commands:" + +#: include/language.h:69 +#, c-format +msgid "%s coverage is too wide; Please use a more specific mask." +msgstr "" + +#: modules/commands/ms_info.cpp:94 +#, c-format +msgid "%s currently has %d memos, of which %d are unread." +msgstr "%s nickinin şu an %d mesajı var, %d tanesi okunmamış." + +#: modules/commands/ms_info.cpp:92 +#, c-format +msgid "%s currently has %d memos, of which 1 is unread." +msgstr "%s nickinin şu an %d mesajı var, 1 tanesi okunmamış." + +#: modules/commands/ms_info.cpp:90 +#, c-format +msgid "%s currently has %d memos." +msgstr "%s nickinin şu an %d mesajı var." + +#: modules/commands/ms_info.cpp:88 +#, c-format +msgid "%s currently has %d memos; all of them are unread." +msgstr "%s nickinin şu an %d mesajı var; hiçbiri okunmamış." + +#: modules/commands/ms_info.cpp:77 +#, c-format +msgid "%s currently has 1 memo, and it has not yet been read." +msgstr "%s nickinin şu an 1 mesajı var, ve daha okunmamış." + +#: modules/commands/ms_info.cpp:79 +#, c-format +msgid "%s currently has 1 memo." +msgstr "%s nickinin şu an 1 mesajı var." + +#: modules/commands/ms_info.cpp:73 +#, c-format +msgid "%s currently has no memos." +msgstr "%s nickinin şu an hiç mesajı yok." + +#: modules/commands/os_forbid.cpp:344 +#, fuzzy, c-format +msgid "%s deleted from the %s forbid list." +msgstr "%s %s kanalının küfür listesinden çıkarıldı." + +#: include/language.h:105 +#, fuzzy, c-format +msgid "%s for %s set to %s." +msgstr "vhost for %s set to %s." + +#: include/language.h:106 +#, fuzzy, c-format +msgid "%s for %s unset." +msgstr "%s için successor kaldırıldı." + +#: modules/commands/ns_ajoin.cpp:176 +#, c-format +msgid "%s had an invalid key specified, and was thus ignored." +msgstr "" + +#: modules/commands/ms_info.cpp:111 +#, c-format +msgid "%s has no memo limit." +msgstr "%s nickinin mesaj limiti yok." + +#: include/language.h:115 +#, fuzzy, c-format +msgid "%s has no memos." +msgstr "%s nickinin mesaj limiti yok." + +#: include/language.h:118 +#, fuzzy, c-format +msgid "%s has no new memos." +msgstr "%s nickinin mesaj limiti yok." + +#: modules/commands/ns_info.cpp:53 +#, c-format +msgid "%s is %s" +msgstr " %s isim: %s" + +#: modules/commands/ns_info.cpp:59 +#, fuzzy, c-format +msgid "%s is a Services Operator of type %s." +msgstr "%s is a services operator of type %s." + +#: modules/commands/cs_seen.cpp:281 +#, fuzzy, c-format +msgid "%s is a client on services." +msgstr " %s şu an bağlı." + +#: modules/commands/cs_seen.cpp:200 +#, fuzzy, c-format +msgid "%s is a network service." +msgstr " %s şu an bağlı." + +#: src/xline.cpp:407 +#, fuzzy, c-format +msgid "%s is already covered by %s." +msgstr "%s zaten %s tarafından değiştirildi." + +#: modules/commands/ns_ajoin.cpp:170 +#, fuzzy, c-format +msgid "%s is already on %s's auto join list." +msgstr "%s access listenize eklendi." + +#: modules/commands/ns_info.cpp:56 +#, fuzzy, c-format +msgid "%s is an unconfirmed nickname." +msgstr "Bu nick zaman aşımına uğramayacak." + +#: modules/commands/cs_flags.cpp:432 +#, c-format +msgid "" +"%s is another way to modify the channel access list, similar to\n" +"the XOP and ACCESS methods." +msgstr "" + +#: modules/commands/ns_info.cpp:74 +#, c-format +msgid "%s is currently online." +msgstr " %s şu an bağlı." + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is disabled" +msgstr "%s is disabled" + +#: modules/commands/os_set.cpp:23 modules/commands/os_set.cpp:25 +#: modules/commands/os_set.cpp:27 +#, c-format +msgid "%s is enabled" +msgstr "%s is enable" + +#: modules/commands/os_dns.cpp:507 +#, fuzzy, c-format +msgid "%s is not a valid IP address." +msgstr "%s geçerli bir ban tipi değil." + +#: modules/commands/cs_log.cpp:167 modules/commands/cs_log.cpp:192 +#, fuzzy, c-format +msgid "%s is not a valid command." +msgstr "%s geçerli bir ban tipi değil." + +#: modules/commands/cs_log.cpp:198 +#, fuzzy, c-format +msgid "%s is not a valid logging method." +msgstr "%s geçerli bir ban tipi değil." + +#: modules/commands/ms_info.cpp:124 +#, c-format +msgid "%s is not notified of new memos." +msgstr "%s yeni mesajlar için uyarılmayacak." + +#: modules/commands/ms_info.cpp:118 +#, c-format +msgid "%s is notified of new memos at logon and when they arrive." +msgstr "" +"%s yeni mesajlar için bağlandığında ve mesajlar ulaştığı anda uyarılacak." + +#: modules/commands/ms_info.cpp:122 +#, c-format +msgid "%s is notified of new memos at logon." +msgstr "%s yeni mesajlar için bağlandığında uyarılacak." + +#: modules/commands/ms_info.cpp:120 +#, c-format +msgid "%s is notified when new memos arrive." +msgstr "%s yeni mesajlar ulaştığı anda uyarılacak." + +#: modules/commands/cs_seen.cpp:232 +#, c-format +msgid "%s is on the channel right now (as %s)!" +msgstr "" + +#: modules/commands/cs_seen.cpp:221 +#, fuzzy, c-format +msgid "%s is on the channel right now!" +msgstr "%s %s kanalında iptal edildi." + +#: modules/commands/cs_xop.cpp:434 +#, fuzzy, c-format +msgid "%s list for %s" +msgstr "%s nickinin access listesi:" + +#: modules/commands/os_sxline.cpp:69 modules/commands/os_sxline.cpp:113 +#, fuzzy, c-format +msgid "%s list is empty." +msgstr "%s kanalinin AOP listesi bos." + +#: modules/commands/cs_mode.cpp:376 +#, fuzzy, c-format +msgid "%s locked on %s." +msgstr "%s yeni mesajlar için uyarılmayacak." + +#: modules/extra/stats/cs_fantasy_stats.cpp:120 +#, fuzzy, c-format +msgid "%s not found." +msgstr "%s %s kanali AOP listesinde bulunamadi." + +#: modules/commands/os_config.cpp:79 +#, c-format +msgid "%s settings:" +msgstr "" + +#: modules/commands/cs_seen.cpp:255 +#, c-format +msgid "%s was last seen here %s ago." +msgstr "" + +#: modules/commands/ns_ajoin.cpp:213 +#, fuzzy, c-format +msgid "%s was not found on %s's auto join list." +msgstr "%s %s kanalının akick listesinde bulunamadı." + +#: modules/commands/ns_ajoin.cpp:221 +#, fuzzy, c-format +msgid "%s was removed from %s's auto join list." +msgstr "%s %s kanalının akick listesinden silindi." + +#: modules/commands/ms_set.cpp:64 +#, c-format +msgid "%s will not send you any notification of memos." +msgstr "%s sizi yeni mesajlar için uyarmayacak." + +#: modules/commands/ms_set.cpp:42 +#, c-format +msgid "%s will now notify you of memos when they are sent to you." +msgstr "%s sizi yeni mesajlar için size gönderildiği anda uyaracak." + +#: modules/commands/ms_set.cpp:30 +#, c-format +msgid "" +"%s will now notify you of memos when you log on and when they are sent to " +"you." +msgstr "" +"%s sizi yeni mesajlar için bağlandığınızda veya mesajlar size gönderildiği " +"anda uyaracak." + +#: modules/commands/ms_set.cpp:36 +#, c-format +msgid "%s will now notify you of memos when you log on or unset /AWAY." +msgstr "" +"%s sizi yeni mesajlar için bağlandığınızda veya AWAY modundan dönüşte " +"uyaracak." + +#: modules/commands/bs_bot.cpp:89 +#, c-format +msgid "%s!%s@%s (%s) added to the bot list." +msgstr "%s!%s@%s (%s) bot listesine eklendi." + +#: modules/commands/ns_access.cpp:83 +#, fuzzy, c-format +msgid "%s's access list is empty." +msgstr "%s kanalının access listesi boş." + +#: modules/commands/ns_ajoin.cpp:96 +#, fuzzy, c-format +msgid "%s's auto join list is empty." +msgstr "%s kanalının akick listesi boş." + +#: modules/commands/ns_ajoin.cpp:111 +#, fuzzy, c-format +msgid "%s's auto join list:" +msgstr " AKICK Autokick listesini düzenler" + +#: modules/commands/ns_cert.cpp:242 +#, fuzzy, c-format +msgid "%s's certificate list is empty." +msgstr "Your access list is empty." + +#: modules/commands/ms_info.cpp:99 modules/commands/ms_info.cpp:106 +#, c-format +msgid "%s's memo limit is %d, and may not be changed." +msgstr "%s nickinin mesaj limiti %d, ve değiştirilemez." + +#: modules/commands/ms_info.cpp:101 modules/commands/ms_info.cpp:108 +#, c-format +msgid "%s's memo limit is %d." +msgstr "%s nickinin mesaj limiti %d." + +#: src/misc.cpp:363 +#, c-format +msgid "(%s ago)" +msgstr "" + +#: src/misc.cpp:365 +#, c-format +msgid "(%s from now)" +msgstr "" + +#: modules/commands/os_dns.cpp:244 +msgid "(Split)" +msgstr "" + +#: modules/commands/os_info.cpp:268 +#, c-format +msgid "(by %s on %s) %s" +msgstr "" + +#: modules/commands/cs_access.cpp:710 +#, fuzzy +msgid "(disabled)" +msgstr "%s is enable" + +#: modules/commands/cs_access.cpp:712 +msgid "(founder only)" +msgstr "" + +#: src/misc.cpp:367 +msgid "(now)" +msgstr "" + +#: modules/commands/os_defcon.cpp:168 +msgid "* AKILL any new clients connecting" +msgstr "* AKILL any new clients connecting" + +#: modules/commands/os_defcon.cpp:158 +#, fuzzy, c-format +msgid "* Force channel modes (%s) to be set on all channels" +msgstr "* Force Chan Modes (%s) to be set on all channels" + +#: modules/commands/os_defcon.cpp:164 +#, fuzzy +msgid "* Ignore non-opers with a message" +msgstr "* Ignore any non-opers with message" + +#: modules/commands/os_defcon.cpp:162 +#, fuzzy +msgid "* Kill any new clients connecting" +msgstr "* Kill any NEW clients connecting" + +#: modules/commands/os_defcon.cpp:156 +#, fuzzy +msgid "* No mode lock changes" +msgstr "* No MLOCK changes" + +#: modules/commands/os_defcon.cpp:152 +msgid "* No new channel registrations" +msgstr "* No new channel registrations" + +#: modules/commands/os_defcon.cpp:170 +msgid "* No new memos sent" +msgstr "* No new memos sent" + +#: modules/commands/os_defcon.cpp:154 +msgid "* No new nick registrations" +msgstr "* No new nick registrations" + +#: modules/commands/os_defcon.cpp:166 +msgid "* Silently ignore non-opers" +msgstr "* Silently ignore non-opers" + +#: modules/commands/os_defcon.cpp:160 +#, c-format +msgid "* Use the reduced session limit of %d" +msgstr "* Use the reduced session limit of %d" + +#: modules/commands/cs_seen.cpp:319 +#, c-format +msgid ", but %s mysteriously dematerialized." +msgstr "" + +#: modules/commands/cs_seen.cpp:317 +#, fuzzy, c-format +msgid ". %s is still online." +msgstr " %s şu an bağlı." + +#: include/language.h:87 +msgid "" +msgstr "" + +#: modules/commands/ns_set.cpp:504 +#, fuzzy, c-format +msgid "" +"A confirmation e-mail has been sent to %s. Follow the instructions in it to " +"change your e-mail address." +msgstr "" +"A passcode has been sent to %s, please type /msg %s confirm to " +"complete registration" + +#: modules/commands/ms_sendall.cpp:45 +msgid "A massmemo has been sent to all registered users." +msgstr "A massmemo has been sent to all registered users." + +#: modules/commands/hs_request.cpp:285 +msgid "" +"A memo informing the user will also be sent, which includes the reason for " +"the rejection if supplied." +msgstr "" + +#: modules/commands/hs_request.cpp:229 +msgid "A memo informing the user will also be sent." +msgstr "" + +#: modules/commands/ms_read.cpp:42 +#, c-format +msgid "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." +msgstr "" +"A notification memo has been sent to %s informing him/her you have\n" +"read his/her memo." + +#: include/language.h:123 +msgid "A vHost ident must be in the format of a valid ident." +msgstr "" + +#: include/language.h:122 +msgid "A vHost must be in the format of a valid hostname." +msgstr "" + +#: modules/commands/os_ignore.cpp:342 +#, fuzzy +msgid "ADD expiry {nick|mask} [reason]" +msgstr "BAN #channel nick [reason]" + +#: modules/commands/os_oper.cpp:70 +msgid "ADD oper type" +msgstr "" + +#: modules/commands/os_info.cpp:102 +#, fuzzy +msgid "ADD target info" +msgstr "GROUP hedef şifre" + +#: modules/commands/os_news.cpp:278 +msgid "ADD text" +msgstr "" + +#: modules/commands/os_session.cpp:523 +#, fuzzy +msgid "ADD [+expiry] mask limit reason" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/ns_ajoin.cpp:231 +#, fuzzy +msgid "ADD [nickname] channel [key]" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/ns_access.cpp:102 +#, fuzzy +msgid "ADD [nickname] mask" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/ns_cert.cpp:258 +#, fuzzy +msgid "ADD [nickname] [fingerprint]" +msgstr "FORBID nick sebep" + +#: modules/commands/os_sxline.cpp:659 modules/commands/os_akill.cpp:386 +#, fuzzy +msgid "ADD [+expiry] mask reason" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/os_sxline.cpp:425 +#, fuzzy +msgid "ADD [+expiry] mask:reason" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/os_forbid.cpp:157 +#, fuzzy +msgid "ADD {NICK|CHAN|EMAIL|REGISTER} [+expiry] entry reason" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/os_dns.cpp:665 +msgid "ADDIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:663 +msgid "ADDSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:661 +msgid "ADDZONE zone.name" +msgstr "" + +#: modules/commands/cs_akick.cpp:38 +#, c-format +msgid "AKICK ENFORCE for %s complete; %d users were affected." +msgstr " %s için AKICK uygulaması tamam; %d kullanıcı için geçerli." + +#: modules/commands/os_chankill.cpp:21 +#, fuzzy +msgid "AKILL all users on a specific channel" +msgstr " CHANKILL AKILL all users on a specific channel" + +#: modules/commands/os_akill.cpp:222 modules/commands/os_akill.cpp:339 +#: modules/commands/os_akill.cpp:353 +msgid "AKILL list is empty." +msgstr "AKILL listesi boş." + +#: modules/commands/bs_kick.cpp:1211 modules/commands/bs_kick.cpp:1213 +#: modules/commands/bs_kick.cpp:1216 +#, fuzzy +msgid "AMSG kicker" +msgstr " Büyük yazıda atma : %s" + +#: modules/commands/ns_alist.cpp:48 +#, fuzzy +msgid "Access" +msgstr "Access listesi:" + +#: include/language.h:72 +#, fuzzy +msgid "Access denied." +msgstr "Access listesi:" + +#: modules/commands/cs_status.cpp:58 +#, fuzzy, c-format +msgid "Access for %s on %s:" +msgstr "%s nickinin access seviyesi %s kanalında %d olarak değiştirildi." + +#: include/language.h:107 +#, fuzzy, c-format +msgid "Access level must be between %d and %d inclusive." +msgstr "Level %d ile %d arasında olmalıdır." + +#: modules/commands/cs_access.cpp:108 +msgid "Access level must be non-zero." +msgstr "Access seviyesi sıfırdan farklı bir sayı olmalıdır." + +#: modules/commands/cs_access.cpp:694 +#, c-format +msgid "Access level settings for channel %s:" +msgstr "%s kanalı için access level ayarları:" + +#: modules/commands/cs_access.cpp:734 +#, c-format +msgid "Access levels for %s reset to defaults." +msgstr "%s için access levelleri varsayılanlarla değiştirildi." + +#: modules/commands/cs_access.cpp:439 modules/commands/ns_access.cpp:87 +#, fuzzy, c-format +msgid "Access list for %s:" +msgstr "%s nickinin access listesi:" + +#: modules/commands/help.cpp:166 +#, c-format +msgid "" +"Access to this command requires the permission %s to be present in your " +"opertype." +msgstr "" +"Access to this command requires the permission %s to be present in your " +"opertype." + +#: modules/commands/ns_cert.cpp:368 modules/commands/ns_cert.cpp:392 +#: modules/commands/ns_identify.cpp:94 +#, c-format +msgid "" +"Account %s has already reached the maximum number of simultaneous logins " +"(%u)." +msgstr "" + +#: modules/commands/cs_set.cpp:683 +#, fuzzy +msgid "Activate security features" +msgstr " SECURE %s güvenlik özelliklerini aktifleştirir" + +#: modules/commands/hs_request.cpp:227 +msgid "Activate the requested vHost for the given nick." +msgstr "" + +#: modules/commands/hs_on.cpp:55 +#, fuzzy +msgid "" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real host/IP address." +msgstr "" +"Syntax: ON\n" +"Activates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see the vhost instead of your real IP address." + +#: modules/commands/hs_on.cpp:19 +#, fuzzy +msgid "Activates your assigned vhost" +msgstr " ON Activates your assigned vhost" + +#: modules/commands/os_info.cpp:243 +msgid "" +"Add or delete oper information for a given nick or channel.\n" +"This will show to opers in the respective info command for\n" +"the nick or channel." +msgstr "" + +#: modules/commands/os_dns.cpp:515 +#, c-format +msgid "Added IP %s to %s." +msgstr "" + +#: modules/commands/os_forbid.cpp:239 +#, c-format +msgid "Added a forbid on %s of type %s to expire on %s." +msgstr "" + +#: modules/commands/os_info.cpp:164 +#, fuzzy, c-format +msgid "Added info to %s." +msgstr "%s nickine mesajınız gönderildi." + +#: modules/commands/os_news.cpp:34 +#, fuzzy +msgid "Added new logon news item." +msgstr "Yeni bağlantı haberleri maddesi eklendi (#%d)." + +#: modules/commands/os_news.cpp:44 +#, fuzzy +msgid "Added new oper news item." +msgstr "Yeni operatör haberleri maddesi eklendi (#%d)." + +#: modules/commands/os_news.cpp:54 +#, fuzzy +msgid "Added new random news item." +msgstr "Yeni karisik haber eklendi (#%d)." + +#: modules/commands/os_dns.cpp:395 +#, fuzzy, c-format +msgid "Added server %s." +msgstr "Uplink server: %s" + +#: modules/commands/os_dns.cpp:300 +#, c-format +msgid "Added zone %s." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:257 +msgid "" +"Adding, deleting, or clearing entry messages requires the\n" +"SET permission." +msgstr "" + +#: modules/commands/ns_register.cpp:104 +msgid "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." +msgstr "" +"Additionally, Services Operators with the nickserv/confirm permission can\n" +"replace passcode with a users nick to force validate them." + +#: modules/pseudoclients/botserv.cpp:172 +#, c-format +msgid "" +"Additionally, if fantasy is enabled fantasy commands\n" +"can be executed by prefixing the command name with\n" +"one of the following characters: %s" +msgstr "" + +#: modules/commands/os_noop.cpp:58 +#, c-format +msgid "All O:lines of %s have been reset." +msgstr "%s serverındaki tüm O:line lar resetlendi." + +#: modules/commands/cs_clone.cpp:71 +#, fuzzy, c-format +msgid "All akick entries from %s have been cloned to %s." +msgstr "All vhost's in the group %s have been set to %s" + +#: modules/commands/help.cpp:57 +#, fuzzy, c-format +msgid "All available commands for %s:" +msgstr "%s hakkında yardım bulunamadı." + +#: modules/commands/cs_clone.cpp:96 +#, fuzzy, c-format +msgid "All badword entries from %s have been cloned to %s." +msgstr "All vhost's in the group %s have been set to %s" + +#: modules/commands/cs_clone.cpp:108 +#, fuzzy, c-format +msgid "All level entries from %s have been cloned into %s." +msgstr "All vhost's in the group %s have been set to %s" + +#: modules/commands/os_news.cpp:38 +msgid "All logon news items deleted." +msgstr "Tüm bağlantı haberleri silindi." + +#: modules/commands/ms_del.cpp:115 +#, c-format +msgid "All memos for channel %s have been deleted." +msgstr "All memos for channel %s have been deleted." + +#: modules/commands/os_mode.cpp:61 +#, c-format +msgid "All modes cleared on %s." +msgstr "" + +#: modules/commands/ns_register.cpp:258 modules/commands/ns_register.cpp:389 +msgid "" +"All new accounts must be validated by an administrator. Please wait for your " +"registration to be confirmed." +msgstr "" + +#: modules/commands/ms_del.cpp:119 +msgid "All of your memos have been deleted." +msgstr "Tüm mesajlarınız silindi." + +#: modules/commands/os_news.cpp:48 +msgid "All oper news items deleted." +msgstr "Tüm operatör haberleri maddeleri silindi." + +#: modules/commands/os_noop.cpp:41 +#, fuzzy, c-format +msgid "All operators from %s have been removed." +msgstr "%s serverındaki tüm O:line lar silindi." + +#: modules/commands/os_news.cpp:58 +msgid "All random news items deleted." +msgstr "Tüm karisik haberler silindi." + +#: modules/commands/cs_clone.cpp:211 +#, fuzzy, c-format +msgid "All settings from %s have been cloned to %s." +msgstr "All vhost's in the group %s have been set to %s" + +#: modules/commands/cs_sync.cpp:41 +#, fuzzy, c-format +msgid "All user modes on %s have been synced." +msgstr "%s serverındaki tüm O:line lar resetlendi." + +#: modules/commands/hs_group.cpp:60 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s." +msgstr "All vhost's in the group %s have been set to %s" + +#: modules/commands/hs_group.cpp:58 +#, fuzzy, c-format +msgid "All vhosts in the group %s have been set to %s@%s." +msgstr "All vhost's in the group %s have been set to %s@%s" + +#: src/access.cpp:40 +msgid "Allowed to (de)halfop him/herself" +msgstr "" + +#: src/access.cpp:39 +msgid "Allowed to (de)halfop users" +msgstr "" + +#: src/access.cpp:48 +msgid "Allowed to (de)op him/herself" +msgstr "" + +#: src/access.cpp:47 +msgid "Allowed to (de)op users" +msgstr "" + +#: src/access.cpp:50 +msgid "Allowed to (de)owner him/herself" +msgstr "" + +#: src/access.cpp:49 +msgid "Allowed to (de)owner users" +msgstr "" + +#: src/access.cpp:52 +msgid "Allowed to (de)protect him/herself" +msgstr "" + +#: src/access.cpp:51 +msgid "Allowed to (de)protect users" +msgstr "" + +#: src/access.cpp:59 +msgid "Allowed to (de)voice him/herself" +msgstr "" + +#: src/access.cpp:58 +msgid "Allowed to (de)voice users" +msgstr "" + +#: src/access.cpp:27 +msgid "Allowed to assign/unassign a bot" +msgstr "" + +#: src/access.cpp:34 +msgid "Allowed to ban users" +msgstr "" + +#: src/access.cpp:56 +#, fuzzy +msgid "Allowed to change channel topics" +msgstr "%s changed your usermodes." + +#: src/access.cpp:41 +msgid "Allowed to get full INFO output" +msgstr "" + +#: src/access.cpp:36 +msgid "Allowed to issue commands restricted to channel founders" +msgstr "" + +#: src/access.cpp:33 +msgid "Allowed to modify channel badwords list" +msgstr "" + +#: src/access.cpp:24 +#, fuzzy +msgid "Allowed to modify the access list" +msgstr "%s %s kanalının access listesinden silindi." + +#: src/access.cpp:44 +msgid "Allowed to read channel memos" +msgstr "" + +#: src/access.cpp:54 +#, fuzzy +msgid "Allowed to set channel settings" +msgstr "* No new channel registrations" + +#: src/access.cpp:57 +msgid "Allowed to unban users" +msgstr "" + +#: src/access.cpp:37 +msgid "Allowed to use GETKEY command" +msgstr "" + +#: src/access.cpp:53 +msgid "Allowed to use SAY and ACT commands" +msgstr "" + +#: src/access.cpp:35 +#, fuzzy +msgid "Allowed to use fantasy commands" +msgstr " PEACE kritik komutlarin kullanilmasini engeller" + +#: src/access.cpp:26 +#, fuzzy +msgid "Allowed to use the AKICK command" +msgstr "You cannot use this command." + +#: src/access.cpp:42 +msgid "Allowed to use the INVITE command" +msgstr "" + +#: src/access.cpp:43 +#, fuzzy +msgid "Allowed to use the KICK command" +msgstr "You cannot use this command." + +#: src/access.cpp:45 +#, fuzzy +msgid "Allowed to use the MODE command" +msgstr "You cannot use this command." + +#: src/access.cpp:25 +#, fuzzy +msgid "Allowed to view the access list" +msgstr "%s %s kanalının access listesinden silindi." + +#: modules/commands/gl_global.cpp:42 +#, fuzzy, c-format +msgid "" +"Allows Administrators to send messages to all users on the\n" +"network. The message will be sent from the nick %s." +msgstr "" +"Kullanımı: GLOBAL mesaj\n" +"\n" +"IRCopların networkteki tüm kullanıcılara mesaj yollamasını\n" +"sağlar. Mesajlar %s nickinden gönderilir." + +#: modules/commands/os_mode.cpp:133 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any channel.\n" +"Parameters are the same as for the standard /MODE command.\n" +"Alternatively, CLEAR may be given to clear all modes on the channel.\n" +"If CLEAR ALL is given then all modes, including user status, is removed." +msgstr "" +"Kullanımı: MODE kanaladı modlar\n" +"\n" +"Servis operatörlerinin herhangi bir kanalın modlarını\n" +"ayarlamasını sağlar. Parametreler standart /MODE komutununkiyle\n" +"aynıdır.\n" +"\n" +"Servis operatörlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/os_mode.cpp:173 +#, fuzzy +msgid "" +"Allows Services Operators to change modes for any user.\n" +"Parameters are the same as for the standard /MODE command." +msgstr "" +"Kullanımı: MODE kanaladı modlar\n" +"\n" +"Servis operatörlerinin herhangi bir kanalın modlarını\n" +"ayarlamasını sağlar. Parametreler standart /MODE komutununkiyle\n" +"aynıdır.\n" +"\n" +"Servis operatörlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/bs_bot.cpp:352 +#, fuzzy +msgid "" +"Allows Services Operators to create, modify, and delete\n" +"bots that users will be able to use on their own\n" +"channels.\n" +" \n" +"BOT ADD adds a bot with the given nickname, username,\n" +"hostname and realname. Since no integrity checks are done\n" +"for these settings, be really careful.\n" +" \n" +"BOT CHANGE allows you to change the nickname, username, hostname\n" +"or realname of a bot without deleting it (and\n" +"all the data associated with it).\n" +" \n" +"BOT DEL removes the given bot from the bot list.\n" +" \n" +"Note: You cannot create a bot with a nick that is\n" +"currently registered. If an unregistered user is currently\n" +"using the nick, they will be killed." +msgstr "" +"Kullanımı: BOT ADD nick user host gerçekismi\n" +" BOT CHANGE eskinick yeninick [user [host [gerçekismi]]]\n" +" BOT DEL nick\n" +"\n" +"Servis adminlerinin kullanıcıların kanallarında kullanması \n" +"için botları yaratmasını, değiştirmesini ve silmesini sağlar.\n" +"\n" +"BOT ADD belirtilen nickte, username, hostname ve gerçek \n" +"isimde bir bot ekler. Doğruluk sınaması yapılmadığında komutu\n" +"kullanırken çok dikkatli olun.\n" +"BOT CHANGE botun nickini, username ini, hostname ini veya\n" +"gerçek ismini silmeye gerek kalmadan değiştirmeyi sağlar.\n" +"BOT DEL belirtilen botu bot listesinden siler.\n" +"\n" +"Not: Eğer botun nicki olarak, kayıtlı bir nick\n" +"kullanırsanız o nickin kaydı silinir(drop). Ayrıca\n" +"o an bir kuulanıcı bu nicki kullanıyorsa kill lenir." + +#: modules/commands/os_oline.cpp:56 +#, fuzzy +msgid "" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." +msgstr "" +"Syntax: OLINE user flags\n" +"\n" +"Allows Services Operators to give Operflags to any user.\n" +"Flags have to be prefixed with a \"+\" or a \"-\". To\n" +"remove all flags simply type a \"-\" instead of any flags." + +#: modules/commands/os_ignore.cpp:370 +#, fuzzy +msgid "" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes,\n" +"h for hours and d for days.\n" +"Combinations of these units are not permitted.\n" +"To make Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format nick!user@host,\n" +"everything else will be considered a nick. Wildcards are permitted.\n" +" \n" +"Ignores will not be enforced on IRC Operators." +msgstr "" +"Syntax: IGNORE {ADD|DEL|LIST|CLEAR} [time] [nick | mask]\n" +"\n" +"Allows Services Operators to make Services ignore a nick or mask\n" +"for a certain time or until the next restart. The default\n" +"time format is seconds. You can specify it by using units.\n" +"Valid units are: s for seconds, m for minutes, \n" +"h for hours and d for days. \n" +"Combinations of these units are not permitted. To make\n" +"Services permanently ignore the user, type 0 as time.\n" +"When adding a mask, it should be in the format user@host\n" +"or nick!user@host, everything else will be considered a nick.\n" +"Wildcards are permitted.\n" +"\n" +"Ignores will not be enforced on IRC Operators." + +#: modules/commands/os_akill.cpp:420 +#, fuzzy +msgid "" +"Allows Services Operators to manipulate the AKILL list. If\n" +"a user matching an AKILL mask attempts to connect, Services\n" +"will issue a KILL for that user and, on supported server\n" +"types, will instruct all servers to add a ban for the mask\n" +"which the user matched.\n" +" \n" +"AKILL ADD adds the given mask to the AKILL\n" +"list for the given reason, which must be given.\n" +"Mask should be in the format of nick!user@host#real name,\n" +"though all that is required is user@host. If a real name is specified,\n" +"the reason must be prepended with a :.\n" +"expiry is specified as an integer followed by one of d\n" +"(days), h (hours), or m (minutes). Combinations (such as\n" +"1h30m) are not permitted. If a unit specifier is not\n" +"included, the default is days (so +30 by itself means 30\n" +"days). To add an AKILL which does not expire, use +0. If the\n" +"usermask to be added starts with a +, an expiry time must\n" +"be given, even if it is the same as the default. The\n" +"current AKILL default expiry time can be found with the\n" +"STATS AKILL command." +msgstr "" +"Kullanımı: AKILL ADD [+zamanaşımı] mask sebep\n" +" AKILL DEL {mask | kayıt-no | liste}\n" +" AKILL LIST [mask | liste]\n" +" AKILL VIEW [mask | liste]\n" +" AKILL CLEAR\n" +"\n" +"Servis operatörlerinin AKILL listesini işletmesini sağlar.\n" +"Eğer AKILL listesineki mask la uyuşan bir kullanıcı\n" +"bağlanmaya çalışırsa, Servisler o kullanıcıyı KILL ler ve,\n" +"destekleyen server tiplerinde, tüm serverların o maska K-line\n" +"koymasını sağlar.\n" +"\n" +"AKILL ADD belirtilen user@host maskını AKILL listesine\n" +"belirtilen sebeple(mutlaka belirtilmelidir) birlikte\n" +"ekler. AKILL DEL belirtilen maskı eğer listedeyse AKILL \n" +"listesinden çıkarır. AKILL LIST mevcut tüm AKILL leri\n" +"gösterir; eğer opsiyonel olarak mask belirtilmişse, AKILL\n" +"listesi belirtilen maskla uyuşanlarla sınırlandırılır. \n" +"\n" +"AKILL VIEW, AKILL LIST in daha açıklayıcı versiyonudur, \n" +"ve AKILL i ekleyeni, eklenme tarihini, ne zaman sona ereceğini,\n" +"user@host maskıyla ve sebeple birlikte gösterir.\n" +"\n" +"Opsiyonel olarak, zaman aşımı süresi AKILL ADD komutuyla\n" +"birlikte belirtilebilir. Zaman aşımı süresi user@host maskından\n" +"önce gelir, ve bir tamsayı olarak şunlardan birinden önce gelir, \n" +"d (gün), h (saat), veya m (dakika). 1h30m gibi kombinasyonlar \n" +"kullanılamaz. Eğer birim belirleyici belirtilmemişse varsayılan \n" +"olarak gün kullanılır (yani +30 un anlamı 30 gündür). Zaman \n" +"aşımına uğramayacak bir AKILL eklemek için +0 kullanın. Eğer \n" +"eklenecek mask + ile başlarsa zaman aşımı süresi belirtilmelidir. \n" +"Mevcut varsayılan AKILL zaman aşımı süresi STATS AKILL komutuyla \n" +"bulunabilir.\n" +"AKILL CLEAR AKILL listesindeki tüm kayıtları siler.\n" +"\n" +"sebep sadece IRC operatörleri tarafından kullanılmak içindir,\n" +"ve kullanıcıların KILL mesajlarında gözükmez.\n" +"\n" +"Servis operatörlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/os_sxline.cpp:436 +msgid "" +"Allows Services Operators to manipulate the SNLINE list. If\n" +"a user with a realname matching an SNLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session." +msgstr "" + +#: modules/commands/os_sxline.cpp:670 +msgid "" +"Allows Services Operators to manipulate the SQLINE list. If\n" +"a user with a nick matching an SQLINE mask attempts to\n" +"connect, Services will not allow it to pursue his IRC\n" +"session.\n" +"If the first character of the mask is #, services will\n" +"prevent the use of matching channels. If the mask is a\n" +"regular expression, the expression will be matched against\n" +"channels too." +msgstr "" + +#: modules/commands/os_session.cpp:551 +msgid "" +"Allows Services Operators to manipulate the list of hosts that\n" +"have specific session limits - allowing certain machines,\n" +"such as shell servers, to carry more than the default number\n" +"of clients at a time. Once a host reaches its session limit,\n" +"all clients attempting to connect from that host will be\n" +"killed. Before the user is killed, they are notified, of a\n" +"source of help regarding session limiting. The content of\n" +"this notice is a config setting." +msgstr "" + +#: modules/commands/os_session.cpp:270 +#, fuzzy +msgid "" +"Allows Services Operators to view the session list.\n" +" \n" +"SESSION LIST lists hosts with at least threshold sessions.\n" +"The threshold must be a number greater than 1. This is to\n" +"prevent accidental listing of the large number of single\n" +"session hosts.\n" +" \n" +"SESSION VIEW displays detailed information about a specific\n" +"host - including the current session count and session limit.\n" +"The host value may not include wildcards.\n" +" \n" +"See the EXCEPTION help for more information about session\n" +"limiting and how to set session limits specific to certain\n" +"hosts and groups thereof." +msgstr "" +"Kullanımı: SESSION LIST threshold\n" +" SESSION VIEW host\n" +"\n" +"Servis adminlerinin session listesini görüntülemesini sağlar.\n" +"\n" +"SESSION LIST en az threshold sessionlardaki hostları listeler.\n" +"Threshold(eşik) 1 den büyük bir sayı olmalıdır. Bu büyük \n" +"ölçüdeki tek session hostların yanlışlıkla listelenmelerini \n" +"önlemek içindir.\n" +"SESSION VIEW belirli bir host hakkında ayrıntılı bilgileri \n" +"görüntüler. Bu o anki session sayısını ve session limitinide\n" +"gösterir. host değeri wildcard(açık olarak yazılmalıdır) \n" +"içermemelidir.\n" +"\n" +"Session limitleme ve belirli hostlara ve gruplara nasıl session \n" +"limit koyulacağı hakkında yardım için EXCEPTION yardımına bakın.\n" +"\n" +"Servis adminleri tarafından kullanılabilir." + +#: modules/commands/cs_topic.cpp:193 +msgid "" +"Allows manipulating the topic of the specified channel.\n" +"The SET command changes the topic of the channel to the given topic\n" +"or unsets the topic if no topic is given. The APPEND command appends\n" +"the given topic to the existing topic.\n" +" \n" +"LOCK and UNLOCK may be used to enable and disable topic lock. When\n" +"topic lock is set, the channel topic will be unchangeable by users who do " +"not have\n" +"the TOPIC privilege." +msgstr "" + +#: modules/commands/os_kick.cpp:62 +#, fuzzy, c-format +msgid "" +"Allows staff to kick a user from any channel.\n" +"Parameters are the same as for the standard /KICK\n" +"command. The kick message will have the nickname of the\n" +"IRCop sending the KICK command prepended; for example:\n" +" \n" +"*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))" +msgstr "" +"Kullanımı: KICK kanaladı kullanıcı sebep\n" +"\n" +"IRCopların herhangi bir kullanıcıyı kanaldan atmalarını\n" +"sağlar. Parametreler standart /KICK komutununkiyle aynıdır.\n" +"Kick mesajında komutu kullanan IRCop un nickide belirtilir.\n" +"Örneğin:\n" +"\n" +"*** SpamMan has been kicked off channel #my_channel by %s (MJJ (Flood))\n" +"\n" +"Servis operatörlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/cs_set.cpp:33 +#, fuzzy +msgid "" +"Allows the channel founder to set various channel options\n" +"and other information.\n" +" \n" +"Available options:" +msgstr "" +"Kullanımı: SET kanaladı özellik parametre\n" +"\n" +"Kanal founderının çeşitli kanal özelliklerini ve diğer bilgileri\n" +"ayarlamasını sağlar.\n" +"\n" +"Mevcut özellikler:" + +#: modules/commands/os_oper.cpp:250 +msgid "" +"Allows you to change and view Services Operators.\n" +"Note that operators removed by this command but are still set in\n" +"the configuration file are not permanently affected by this." +msgstr "" + +#: modules/commands/os_config.cpp:127 +msgid "" +"Allows you to change and view configuration settings.\n" +"Settings changed by this command are temporary and will not be reflected\n" +"back into the configuration file, and will be lost if Anope is shut down,\n" +"restarted, or the configuration is reloaded.\n" +" \n" +"Example:\n" +" MODIFY nickserv forcemail no" +msgstr "" + +#: modules/commands/ns_set.cpp:992 +#, fuzzy +msgid "" +"Allows you to choose the way Services are communicating with\n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." +msgstr "" +"Syntax: SASET nickname MSG {ON | OFF}\n" +"\n" +"Allows you to choose the way Services are communicating with \n" +"the given user. With MSG set, Services will use messages,\n" +"else they'll use notices." + +#: modules/commands/ns_set.cpp:966 +#, fuzzy, c-format +msgid "" +"Allows you to choose the way Services are communicating with\n" +"you. With %s set, Services will use messages, else they'll\n" +"use notices." +msgstr "" +"Syntax: SET MSG {ON | OFF}\n" +"\n" +"Allows you to choose the way Services are communicating with \n" +"you. With MSG set, Services will use messages, else they'll \n" +"use notices." + +#: modules/commands/ms_ignore.cpp:113 +msgid "" +"Allows you to ignore users by nick or host from memoing\n" +"you or a channel. If someone on the memo ignore list tries\n" +"to memo you or a channel, they will not be told that you have\n" +"them ignored." +msgstr "" + +#: modules/commands/os_kill.cpp:48 +msgid "" +"Allows you to kill a user from the network.\n" +"Parameters are the same as for the standard /KILL\n" +"command." +msgstr "" + +#: modules/commands/ns_info.cpp:252 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Syntax: SASET nickname HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}\n" +"\n" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on the\n" +"nick. You can hide the E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), the services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." + +#: modules/commands/ns_info.cpp:223 +#, fuzzy, c-format +msgid "" +"Allows you to prevent certain pieces of information from\n" +"being displayed when someone does a %s INFO on your\n" +"nick. You can hide your E-mail address (EMAIL), last seen\n" +"user@host mask (USERMASK), your services access status\n" +"(STATUS) and last quit message (QUIT).\n" +"The second parameter specifies whether the information should\n" +"be displayed (OFF) or hidden (ON)." +msgstr "" +"Kullanımı: SET HIDE {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}\n" +"\n" +"Birisi hakkınızda bilgi almak için %s INFO komutunu \n" +"kullandığında bazı bilgilerin burada gözükmemesini sağlar.\n" +"E-mail adresinizi (EMAIL), son göründüğünüz user@host \n" +"maskını (USERMASK), ve son çıkış mesajınızı (QUIT)\n" +"saklayabilirsiniz. İkinici parametre bilginin görünüp (OFF)\n" +"görünmeyeceğini (ON) belirtmenizi sağlar." + +#: modules/commands/bs_info.cpp:118 +#, fuzzy, c-format +msgid "Allows you to see %s information about a channel or a bot" +msgstr "" +"INFO Allows you to see BotServ information about a channel or " +"a bot" + +#: modules/commands/bs_info.cpp:108 +#, fuzzy, c-format +msgid "" +"Allows you to see %s information about a channel or a bot.\n" +"If the parameter is a channel, then you'll get information\n" +"such as enabled kickers. If the parameter is a nick,\n" +"you'll get information about a bot, such as creation\n" +"time or number of channels it is on." +msgstr "" +"Kullanımı: INFO {kanaladı | botunnicki}\n" +"\n" +"Bir kanal yada bot hakkında %s bilgisini gösterir. Eğer\n" +"parametre kanalsa, aktif atma özellikleri hakkında bilgi\n" +"alırsınız. Eğer parametre nickse, bot hakkında yaratılma \n" +"zamanı veya bulunduğu kanal sayısı gibi bilgiler alırsınız." + +#: modules/commands/cs_xop.cpp:567 +msgid "" +"Alternative methods of modifying channel access lists are\n" +"available. " +msgstr "" + +#: modules/commands/hs_request.cpp:191 +#, fuzzy +msgid "Approve the requested vHost of a user" +msgstr " DEL Delete the vhost of another user" + +#: modules/commands/ns_drop.cpp:68 +#, fuzzy +msgid "As a Services Operator, you may drop any nick." +msgstr "%s is a services operator of type %s." + +#: modules/commands/bs_assign.cpp:19 +#, fuzzy +msgid "Assigns a bot to a channel" +msgstr "ASSIGN Kanala bot sokar" + +#: modules/commands/bs_assign.cpp:78 +#, fuzzy +msgid "" +"Assigns the specified bot to a channel. You\n" +"can then configure the bot for the channel so it fits\n" +"your needs." +msgstr "" +"Kullanımı: ASSIGN kanaladı botunnicki\n" +"\n" +"Belirtilen nickteki botu belirtilen kanala sokar. Bundan \n" +"sonra botun ayarlarını ihtiyaçlarınıza uygun şekilde \n" +"yapabilirsiniz." + +#: data/chanserv.example.conf:1197 +#, fuzzy +msgid "Associate a URL with the channel" +msgstr "ASSIGN Kanala bot sokar" + +#: data/nickserv.example.conf:594 +msgid "Associate a URL with this account" +msgstr "" + +#: data/nickserv.example.conf:593 +#, fuzzy +msgid "Associate a URL with your account" +msgstr " GREET Nickiniz için bir karşılama mesajı belirler" + +#: modules/commands/greet.cpp:83 +#, fuzzy +msgid "Associate a greet message with your nickname" +msgstr " GREET Nickiniz için bir karşılama mesajı belirler" + +#: data/chanserv.example.conf:1198 +#, fuzzy +msgid "Associate an E-mail address with the channel" +msgstr " EMAIL Nickinizle bir email adresini ilişkilendirir" + +#: modules/commands/ns_set.cpp:452 +#, fuzzy +msgid "Associate an E-mail address with your nickname" +msgstr " EMAIL Nickinizle bir email adresini ilişkilendirir" + +#: modules/commands/os_info.cpp:101 +#, fuzzy +msgid "Associate oper info with a nick or channel" +msgstr "ASSIGN Kanala bot sokar" + +#: modules/commands/ns_set.cpp:558 +#, fuzzy +msgid "Associates the given E-mail address with the nickname." +msgstr " EMAIL Nickinizle bir email adresini ilişkilendirir" + +#: modules/commands/ns_set.cpp:533 +#, fuzzy +msgid "" +"Associates the given E-mail address with your nickname.\n" +"This address will be displayed whenever someone requests\n" +"information on the nickname with the INFO command." +msgstr "" +"Kullanımı: SET EMAIL email adresiniz\n" +"\n" +"Nickiniz için bir email adresi belirtir. Bu email adresi\n" +"birisi sizin hakkınızda bilgi almak için INFO komutunu \n" +"kullandığında görünür." + +#: modules/commands/ns_set.cpp:1315 +msgid "Auto-op" +msgstr "Auto-op" + +#: modules/commands/cs_akick.cpp:374 +#, c-format +msgid "Autokick list for %s:" +msgstr "%s kanalının akick listesi:" + +#: src/access.cpp:29 +msgid "Automatic channel operator status upon join" +msgstr "" + +#: src/access.cpp:28 +msgid "Automatic halfop upon join" +msgstr "" + +#: src/access.cpp:30 +msgid "Automatic owner upon join" +msgstr "" + +#: src/access.cpp:31 +msgid "Automatic protect upon join" +msgstr "" + +#: src/access.cpp:32 +msgid "Automatic voice on join" +msgstr "" + +#: modules/commands/os_oper.cpp:196 +#, fuzzy, c-format +msgid "Available commands for %s:" +msgstr "%s hakkında yardım bulunamadı." + +#: modules/commands/os_oper.cpp:175 +#, fuzzy +msgid "Available opertypes:" +msgstr "%s hakkında yardım bulunamadı." + +#: modules/commands/os_oper.cpp:218 +#, c-format +msgid "Available privileges for %s:" +msgstr "" + +#: modules/commands/cs_enforce.cpp:162 +msgid "BANS enforced by " +msgstr "" + +#: modules/commands/bs_kick.cpp:1121 modules/commands/bs_kick.cpp:1123 +#: modules/commands/bs_kick.cpp:1126 +#, fuzzy +msgid "Bad words kicker" +msgstr " Küfürde atma : %s" + +#: modules/commands/bs_badwords.cpp:252 +#, fuzzy, c-format +msgid "Bad words list for %s:" +msgstr "%s nickinin access listesi:" + +#: modules/commands/bs_badwords.cpp:364 +msgid "Bad words list is now empty." +msgstr "Küfür listesi şimdi boş." + +#: modules/commands/bs_set.cpp:129 +msgid "Ban expiry may not be longer than 1 day." +msgstr "" + +#: modules/commands/cs_ban.cpp:140 modules/commands/cs_ban.cpp:175 +#, fuzzy, c-format +msgid "Ban on %s expires in %s." +msgstr "%s nickli bot zaten var." + +#: modules/commands/cs_info.cpp:60 +msgid "Ban type" +msgstr "" + +#: modules/commands/cs_set.cpp:174 +#, c-format +msgid "Ban type for channel %s is now #%d." +msgstr "%s kanalının ban tipi #%d olarak değiştirildi." + +#: modules/commands/cs_ban.cpp:39 +#, fuzzy +msgid "Bans a given nick or mask on a channel" +msgstr " BAN Bans a selected nick on a channel" + +#: modules/commands/cs_ban.cpp:227 +#, fuzzy +msgid "" +"Bans a given nick or mask on a channel. An optional expiry may\n" +"be given to cause services to remove the ban after a set amount\n" +"of time.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders may ban masks." +msgstr "" +"Kullanımı: BAN #kanaladi nick [sebep]\n" +"\n" +"Belirtilen nicki kanaldan banlar.\n" +"\n" +"Varsayilan olarak, AOP larin veya 5. seviyeden access i olanlarin\n" +"ve üstünün kullanma yetkisi vardir." + +#: modules/commands/cs_enforce.cpp:166 +#, fuzzy, c-format +msgid "Bans enforced on %s." +msgstr "%s yeni mesajlar için uyarılmayacak." + +#: modules/commands/bs_kick.cpp:1131 modules/commands/bs_kick.cpp:1133 +#: modules/commands/bs_kick.cpp:1136 +#, fuzzy +msgid "Bolds kicker" +msgstr " Kalın yazıda atma : %s" + +#: modules/commands/bs_bot.cpp:26 modules/commands/bs_bot.cpp:175 +#, c-format +msgid "Bot %s already exists." +msgstr "%s nickli bot zaten var." + +#: include/language.h:119 +#, fuzzy, c-format +msgid "Bot %s does not exist." +msgstr "%s nickli bot zaten var." + +#: modules/commands/bs_assign.cpp:71 modules/commands/bs_assign.cpp:246 +#, c-format +msgid "Bot %s has been assigned to %s." +msgstr "%s botu %s kanalına sokuldu." + +#: modules/commands/bs_bot.cpp:228 +#, fuzzy, c-format +msgid "Bot %s has been changed to %s!%s@%s (%s)." +msgstr "%s botu %s!%s@%s (%s) olarak değiştirildi." + +#: modules/commands/bs_bot.cpp:262 +#, c-format +msgid "Bot %s has been deleted." +msgstr "%s botu silindi." + +#: modules/commands/bs_assign.cpp:63 modules/commands/bs_assign.cpp:241 +#, c-format +msgid "Bot %s is already assigned to channel %s." +msgstr "Bot %s is already assigned to channel %s." + +#: modules/commands/bs_kick.cpp:832 +#, c-format +msgid "Bot will kick ops on channel %s." +msgstr "Bot %s kanalında oplarıda atacak." + +#: modules/commands/bs_kick.cpp:897 +#, c-format +msgid "Bot will kick voices on channel %s." +msgstr "Bot %s kanalında voicelarıda atacak." + +#: modules/commands/bs_kick.cpp:824 +#, c-format +msgid "Bot won't kick ops on channel %s." +msgstr "Bot %s kanalında opları atmayacak ." + +#: modules/commands/bs_kick.cpp:889 +#, c-format +msgid "Bot won't kick voices on channel %s." +msgstr "Bot %s kanalında voiceları atmayacak." + +#: modules/commands/bs_bot.cpp:118 +#, fuzzy, c-format +msgid "Bot %s is not changeable." +msgstr "Bot yok modu %s kanalı için AKTİF." + +#: modules/commands/bs_bot.cpp:254 +#, fuzzy, c-format +msgid "Bot %s is not deletable." +msgstr "%s botu silindi." + +#: modules/commands/bs_set.cpp:141 +#, c-format +msgid "Bot bans will automatically expire after %s." +msgstr "" + +#: modules/commands/bs_set.cpp:139 +#, fuzzy +msgid "Bot bans will no longer automatically expire." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/bs_bot.cpp:46 modules/commands/bs_bot.cpp:138 +#, fuzzy, c-format +msgid "Bot hosts may only be %d characters long." +msgstr "Bot Hosts may only contain %d characters." + +#: modules/commands/bs_bot.cpp:64 modules/commands/bs_bot.cpp:167 +#, fuzzy +msgid "Bot hosts may only contain valid host characters." +msgstr "Bot Hosts may only contain valid host characters." + +#: modules/commands/bs_bot.cpp:40 modules/commands/bs_bot.cpp:132 +#, fuzzy, c-format +msgid "Bot idents may only be %d characters long." +msgstr "Bot Idents may only contain %d characters." + +#: modules/commands/bs_bot.cpp:58 modules/commands/bs_bot.cpp:161 +#, fuzzy +msgid "Bot idents may only contain valid ident characters." +msgstr "Bot Idents may only contain valid characters." + +#: include/language.h:121 +#, fuzzy, c-format +msgid "Bot is not on channel %s." +msgstr "Bot %s kanalında oplarıda atacak." + +#: modules/commands/bs_botlist.cpp:51 +msgid "Bot list:" +msgstr "Bot listesi:" + +#: modules/commands/bs_info.cpp:87 +msgid "Bot nick" +msgstr "" + +#: modules/commands/bs_bot.cpp:34 modules/commands/bs_bot.cpp:126 +#, fuzzy, c-format +msgid "Bot nicks may only be %d characters long." +msgstr "Bot Idents may only contain %d characters." + +#: modules/commands/bs_bot.cpp:52 modules/commands/bs_bot.cpp:155 +#, fuzzy +msgid "Bot nicks may only contain valid nick characters." +msgstr "Bot Nicks may only contain valid nick characters." + +#: modules/commands/bs_kick.cpp:225 +#, fuzzy, c-format +msgid "" +"Bot will now kick for %s, and will place a ban\n" +"after %d kicks for the same user." +msgstr "" +"Bot will now kick italics, and will place a ban after %d\n" +"kicks for the same user." + +#: modules/commands/bs_kick.cpp:228 +#, fuzzy, c-format +msgid "Bot will now kick for %s." +msgstr "Bot şimdi kalın yazıda atacak." + +#: modules/commands/bs_kick.cpp:416 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message), and will\n" +"place a ban after %d kicks for the same user." +msgstr "" +"Bot şimdi büyük yazıda atacak(Tüm mesajın en az\n" +"%d karakterini ve %d%% kadarını içermelidir), ve \n" +"%d atma sonrasında aynı kullanıcıyı banlayacak." + +#: modules/commands/bs_kick.cpp:420 +#, fuzzy, c-format +msgid "" +"Bot will now kick for caps (they must constitute at least\n" +"%d characters and %d%% of the entire message)." +msgstr "" +"Bot şimdi büyük yazıda atacak(Tüm mesajın en az\n" +"%d karakterini ve %d%% kadarını içermelidir)." + +#: modules/commands/bs_kick.cpp:551 +#, fuzzy, c-format +msgid "" +"Bot will now kick for flood (%d lines in %d seconds\n" +"and will place a ban after %d kicks for the same user." +msgstr "" +"Bot şimdi text floodda atacak(%d sira %d saniyede), ve \n" +"%d atma sonrasında aynı kullanıcıyı banlayacak." + +#: modules/commands/bs_kick.cpp:554 +#, fuzzy, c-format +msgid "Bot will now kick for flood (%d lines in %d seconds)." +msgstr "Bot şimdi text floodda atacak(%d sıra %d saniyede)." + +#: modules/commands/bs_kick.cpp:677 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Bot şimdi tekrarda atacak(kullanıcı %d kez\n" +"aynı şeyi söylerse), ve %d atma sonrasında\n" +"aynı kullanıcıyı banlayacak." + +#: modules/commands/bs_kick.cpp:687 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d time)." +msgstr "" +"Bot şimdi tekrarda atacak(kullanıcı %d kez\n" +"aynı şeyi söylerse)." + +#: modules/commands/bs_kick.cpp:673 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times), and will place a ban after %d\n" +"kicks for the same user." +msgstr "" +"Bot şimdi tekrarda atacak(kullanıcı %d kez\n" +"aynı şeyi söylerse), ve %d atma sonrasında\n" +"aynı kullanıcıyı banlayacak." + +#: modules/commands/bs_kick.cpp:684 +#, fuzzy, c-format +msgid "" +"Bot will now kick for repeats (users that repeat the\n" +"same message %d times)." +msgstr "" +"Bot şimdi tekrarda atacak(kullanıcı %d kez\n" +"aynı şeyi söylerse)." + +#: modules/commands/bs_kick.cpp:239 +#, fuzzy, c-format +msgid "Bot won't kick for %s anymore." +msgstr "Bot artık büyük yazıda atmayacak." + +#: modules/commands/bs_kick.cpp:426 +#, fuzzy +msgid "Bot won't kick for caps anymore." +msgstr "Bot artık büyük yazıda atmayacak." + +#: modules/commands/bs_kick.cpp:559 +#, fuzzy +msgid "Bot won't kick for flood anymore." +msgstr "Bot artık text floodda atmayacak." + +#: modules/commands/bs_kick.cpp:694 +#, fuzzy +msgid "Bot won't kick for repeats anymore." +msgstr "Bot artık tekrarda atmayacak." + +#: modules/commands/cs_access.cpp:472 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_session.cpp:514 +msgid "By" +msgstr "" + +#: modules/commands/os_info.cpp:104 +msgid "CLEAR target" +msgstr "" + +#: modules/commands/cs_seen.cpp:119 +msgid "CLEAR time" +msgstr "" + +#: modules/commands/ms_cancel.cpp:19 +#, fuzzy +msgid "Cancel the last memo you sent" +msgstr " CANCEL Son gönderilen mesajı iptal eder" + +#: modules/commands/cs_drop.cpp:19 +#, fuzzy +msgid "Cancel the registration of a channel" +msgstr " DROP Kanal kaydını siler" + +#: modules/commands/ns_drop.cpp:20 +#, fuzzy +msgid "Cancel the registration of a nickname" +msgstr " DROP Nickin kaydını siler" + +#: modules/commands/ms_cancel.cpp:84 +#, fuzzy +msgid "" +"Cancels the last memo you sent to the given nick or channel,\n" +"provided it has not been read at the time you use the command." +msgstr "" +"Kullanımı: CANCEL {nick | kanaladı}\n" +"\n" +"Belirtilen kanala yada nicke gönderilen son mesajı iptal eder,\n" +"tabi eğer o mesaj siz komutu kullandığınız sırada okunmamışsa." + +#: modules/commands/cs_clone.cpp:149 +#, fuzzy, c-format +msgid "Cannot clone channel %s to itself!" +msgstr "Bot %s kanalında oplarıda atacak." + +#: modules/commands/ns_register.cpp:332 +msgid "Cannot send mail now; please retry a little later." +msgstr "Şu an mail gönderilemiyor; lütfen az sonra tekrar deneyin." + +#: modules/commands/bs_kick.cpp:1141 modules/commands/bs_kick.cpp:1143 +#: modules/commands/bs_kick.cpp:1146 +#, fuzzy +msgid "Caps kicker" +msgstr " Büyük yazıda atma : %s" + +#: modules/commands/os_shutdown.cpp:34 +#, fuzzy +msgid "" +"Causes Services to do an immediate shutdown; databases are\n" +"not saved. This command should not be used unless\n" +"damage to the in-memory copies of the databases is feared\n" +"and they should not be saved." +msgstr "" +"Kullanımı: QUIT\n" +"\n" +"Servislerin birden kapanmasına neden olur; veritabanları\n" +"kaydedilmez. Bu komut veritabanlarının hafızadaki \n" +"kopyalarına zarar gelmesinden korkuluyorsa ve \n" +"yedeklenmemişlerse kullanılmamalıdır. Normal kapatmalar \n" +"için, SHUTDOWN komutunu kullanın.\n" +"\n" +"Servis adminlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/os_reload.cpp:47 +#, fuzzy +msgid "" +"Causes Services to reload the configuration file. Note that\n" +"some directives still need the restart of the Services to\n" +"take effect (such as Services' nicknames, activation of the\n" +"session limitation, etc.)." +msgstr "" +"Kullanımı: RELOAD\n" +"\n" +"Servislerin conf dosyasını yeniden yüklemesine neden olur.\n" +"Unutmayınki bazı direktifler hala servislerin yeniden \n" +"başlatılmasını gerektirir. (Servislerin nickleri, session \n" +"limitinin aktifleştirilmesi, etc.)\n" +"\n" +"Servis adminlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/os_shutdown.cpp:62 +#, fuzzy +msgid "" +"Causes Services to save all databases and then restart\n" +"(i.e. exit and immediately re-run the executable)." +msgstr "" +"Kullanımı: RESTART\n" +"\n" +"Servislerin tüm veritabanlarını kaydederek yeniden \n" +"başlamasını sağlar.\n" +"\n" +"Servis adminlerinin Kullanımıyla sınırlıdır.\t" + +#: modules/commands/os_shutdown.cpp:89 +#, fuzzy +msgid "Causes Services to save all databases and then shut down." +msgstr "" +"Kulanımı: SHUTDOWN\n" +"\n" +"Servislerin tüm veritabanlarını kaydederek kapanmasını sağlar.\n" +"\n" +"Servis adminlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/os_update.cpp:34 +#, fuzzy +msgid "" +"Causes Services to update all database files as soon as you\n" +"send the command." +msgstr "" +"Kullanımı: UPDATE\n" +"\n" +"Komutu gönderir gönderirmez servislerin tüm veri tabanı \n" +"dosyalarını güncellemelerini sağlar.\n" +"\n" +"Servis adminlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/ns_cert.cpp:246 +#, fuzzy, c-format +msgid "Certificate list for %s:" +msgstr "%s nickinin access listesi:" + +#: modules/commands/cs_set.cpp:528 modules/commands/cs_set.cpp:570 +msgid "ChanServ is required to enable persist on this network." +msgstr "" + +#: modules/commands/os_mode.cpp:19 +#, fuzzy +msgid "Change channel modes" +msgstr "%s changed your usermodes." + +#: modules/commands/ns_set.cpp:905 +#, fuzzy +msgid "Change the communication method of Services" +msgstr " MSG Change the communication method of Services" + +#: modules/commands/os_mode.cpp:146 +#, fuzzy +msgid "Change user modes" +msgstr "%s changed your usermodes." + +#: modules/commands/os_mode.cpp:161 +#, fuzzy, c-format +msgid "Changed usermodes of %s to %s." +msgstr "Changed usermodes of %s." + +#: modules/commands/ns_set.cpp:411 +#, fuzzy +msgid "" +"Changes the display used to refer to the nickname group in\n" +"Services. The new display MUST be a nick of the group." +msgstr "" +"Kullanımı: SET DISPLAY yeni-görünüm\n" +"\n" +"Servislerde grubunuzdaki nicklerden hangisinin gözükeceğini\n" +"ayarlar. Yeni görünüm grubunuzda bulunan nicklerden biri \n" +"olmalıdır." + +#: modules/commands/ns_set.cpp:387 +#, fuzzy +msgid "" +"Changes the display used to refer to your nickname group in\n" +"Services. The new display MUST be a nick of your group." +msgstr "" +"Kullanımı: SET DISPLAY yeni-görünüm\n" +"\n" +"Servislerde grubunuzdaki nicklerden hangisinin gözükeceğini\n" +"ayarlar. Yeni görünüm grubunuzda bulunan nicklerden biri \n" +"olmalıdır." + +#: modules/commands/cs_set.cpp:324 +#, fuzzy +msgid "" +"Changes the founder of a channel. The new nickname must\n" +"be a registered one." +msgstr "" +"Kullanımı: %s kanaladı FOUNDER nick\n" +"\n" +"Kanal founderını değiştirir. Yeni nickin kayıtlı \n" +"olması gereklidir." + +#: modules/commands/ns_set.cpp:884 +#, fuzzy +msgid "" +"Changes the language Services uses when sending messages to\n" +"the given user (for example, when responding to a command they send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Kullanımı: SET LANGUAGE numara\n" +"\n" +"Servislerin size hitap edeceği dili belirlemenizi sağlar.\n" +"(örneğin, bir komut yazdığınızda gelecek cevabın dili gibi).\n" +"numara aşağıdaki listede desteklenen dillerden biri olarak \n" +"belirlenir:" + +#: modules/commands/ns_set.cpp:848 +#, fuzzy +msgid "" +"Changes the language Services uses when sending messages to\n" +"you (for example, when responding to a command you send).\n" +"language should be chosen from the following list of\n" +"supported languages:" +msgstr "" +"Kullanımı: SET LANGUAGE numara\n" +"\n" +"Servislerin size hitap edeceği dili belirlemenizi sağlar.\n" +"(örneğin, bir komut yazdığınızda gelecek cevabın dili gibi).\n" +"numara aşağıdaki listede desteklenen dillerden biri olarak \n" +"belirlenir:" + +#: modules/commands/ns_set.cpp:227 +#, fuzzy +msgid "Changes the password used to identify as the nick's owner." +msgstr "" +"Kullanımı: SET PASSWORD yeni şifre\n" +"\n" +"Nickinizi tanıtmak için kullandığınız şifreyi\n" +"değiştirir." + +#: modules/commands/ns_set.cpp:161 +#, fuzzy +msgid "" +"Changes the password used to identify you as the nick's\n" +"owner." +msgstr "" +"Kullanımı: SET PASSWORD yeni şifre\n" +"\n" +"Nickinizi tanıtmak için kullandığınız şifreyi\n" +"değiştirir." + +#: modules/commands/cs_set.cpp:1017 +#, fuzzy +msgid "" +"Changes the successor of a channel. If the founder's\n" +"nickname expires or is dropped while the channel is still\n" +"registered, the successor will become the new founder of the\n" +"channel. The successor's nickname must be a registered one.\n" +"If there's no successor set, then the first nickname on the\n" +"access list (with the highest access, if applicable) will\n" +"become the new founder, but if the access list is empty, the\n" +"channel will be dropped." +msgstr "" +"Kullanımı: %s kanaladı SUCCESSOR nick\n" +"\n" +"Kanal successorını belirler, değiştirir. Eğer bir kanalın\n" +"founderının nicki zaman aşımına uğrayıp kaydı silinirse\n" +"yada kanal kayıtlıyken nickin kaydı bilerek silinirse(drop)\n" +"successor kanalın yeni founderı durumuna gelir. Fakat eğer\n" +"successorında çok fazla kayıtlı kanalı varsa(%d) veya kanal\n" +"için bir successor belirtilmemişse kanalın kaydı silinir(drop).\n" +"Komutta belirtilen nickin kayıtlı olması gereklidir." + +#: modules/commands/ns_alist.cpp:48 modules/commands/ns_ajoin.cpp:100 +#, fuzzy +msgid "Channel" +msgstr "DROP kanaladı" + +#: include/language.h:84 +#, fuzzy, c-format +msgid "Channel %s doesn't exist." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_drop.cpp:63 +#, c-format +msgid "Channel %s has been dropped." +msgstr "%s kanalının kaydı silinmiştir (dropped)." + +#: modules/commands/cs_getkey.cpp:43 +#, fuzzy, c-format +msgid "Channel %s has no key." +msgstr "The channel %s has no key." + +#: modules/commands/cs_register.cpp:47 +#, c-format +msgid "Channel %s is already registered!" +msgstr "%s kanalı zaten kayıtlı!" + +#: modules/commands/os_forbid.cpp:524 +#, fuzzy, c-format +msgid "Channel %s is forbidden by %s: %s" +msgstr "Bu kanal %s ile kayıtlıdır." + +#: modules/commands/os_forbid.cpp:526 +#, fuzzy, c-format +msgid "Channel %s is forbidden." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_set.cpp:580 +#, fuzzy, c-format +msgid "Channel %s is no longer persistent." +msgstr "Channel %s is no longer persistant." + +#: modules/commands/cs_set.cpp:542 +#, fuzzy, c-format +msgid "Channel %s is now persistent." +msgstr "Channel %s is now persistant." + +#: modules/commands/cs_suspend.cpp:180 +#, c-format +msgid "Channel %s is now released." +msgstr "Channel %s is now released." + +#: modules/commands/cs_suspend.cpp:125 +#, c-format +msgid "Channel %s is now suspended." +msgstr "Channel %s is now suspended." + +#: include/language.h:83 +#, fuzzy, c-format +msgid "Channel %s isn't registered." +msgstr "%s kanalı kayıt edilemez." + +#: modules/commands/cs_suspend.cpp:172 +#, fuzzy, c-format +msgid "Channel %s isn't suspended." +msgstr "Channel %s is now suspended." + +#: modules/commands/cs_register.cpp:68 +#, fuzzy, c-format +msgid "Channel %s registered under your account: %s" +msgstr "%s nicki sizin adınıza kayıt edildi: %s" + +#: modules/commands/cs_set.cpp:1078 +#, c-format +msgid "Channel %s will expire." +msgstr "%s kanalı zaman aşımına eklendi." + +#: modules/commands/cs_set.cpp:1072 +#, c-format +msgid "Channel %s will not expire." +msgstr "%s kanalı zaman aşımından çıkarıldı." + +#: modules/commands/cs_xop.cpp:475 +#, fuzzy, c-format +msgid "Channel %s %s list has been cleared." +msgstr "Kanalin %s AOP listesi temizlendi." + +#: modules/commands/cs_access.cpp:486 modules/commands/cs_flags.cpp:361 +#, c-format +msgid "Channel %s access list has been cleared." +msgstr "Kanal %s access listesi temizlendi." + +#: modules/commands/cs_akick.cpp:428 +#, c-format +msgid "Channel %s akick list has been cleared." +msgstr "Kanal %s akick listesi temizlendi." + +#: modules/commands/cs_mode.cpp:444 +#, fuzzy, c-format +msgid "Channel %s has no mode locks." +msgstr "Channel %s is now released." + +#: include/language.h:82 +#, fuzzy, c-format +msgid "Channel %s is currently suspended." +msgstr "Channel %s is now suspended." + +#: include/language.h:101 +#, fuzzy, c-format +msgid "Channel %s is not a valid channel." +msgstr "%s geçerli bir ban tipi değil." + +#: modules/commands/os_list.cpp:70 +#, fuzzy +msgid "Channel list:" +msgstr "Bot listesi:" + +#: modules/extra/stats/cs_fantasy_stats.cpp:148 +#, fuzzy, c-format +msgid "Channel stats for %s on %s:" +msgstr "" +"Channels that %s has access on:\n" +" Num Channel Level Description " + +#: modules/commands/cs_access.cpp:142 modules/commands/cs_flags.cpp:97 +#: modules/commands/cs_xop.cpp:139 +#, fuzzy +msgid "Channels may not be on access lists." +msgstr "%s %s kanalının access listesinde bulunamadı." + +#: modules/commands/ns_alist.cpp:114 +#, fuzzy, c-format +msgid "Channels that %s has access on:" +msgstr "" +"Channels that %s has access on:\n" +" Num Channel Level Description " + +#: modules/commands/os_stats.cpp:181 +#, c-format +msgid "Channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:517 +#: modules/extra/stats/m_chanstats.cpp:525 +msgid "Chanstats" +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:102 +#, fuzzy, c-format +msgid "Chanstats statistics are now disabled for %s" +msgstr " SECURE Nick güvenliğini açar kapatır" + +#: modules/extra/stats/m_chanstats.cpp:51 +msgid "Chanstats statistics are now disabled for this channel." +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:104 +#, fuzzy +msgid "Chanstats statistics are now disabled for your nick." +msgstr " SECURE Nick güvenliğini açar kapatır" + +#: modules/extra/stats/m_chanstats.cpp:93 +#, fuzzy, c-format +msgid "Chanstats statistics are now enabled for %s" +msgstr " SECURE Nick güvenliğini açar kapatır" + +#: modules/extra/stats/m_chanstats.cpp:44 +msgid "Chanstats statistics are now enabled for this channel." +msgstr "" + +#: modules/extra/stats/m_chanstats.cpp:95 +#, fuzzy +msgid "Chanstats statistics are now enabled for your nick." +msgstr " SECURE Nick güvenliğini açar kapatır" + +#: modules/commands/cs_seen.cpp:367 +msgid "" +"Checks for the last time nick was seen joining, leaving,\n" +"or changing nick on the network and tells you when and, depending\n" +"on channel or user settings, where it was." +msgstr "" + +#: modules/commands/ms_check.cpp:19 +#, fuzzy +msgid "Checks if last memo to a nick was read" +msgstr " CHECK Checks if last memo to a nick was read" + +#: modules/commands/ms_check.cpp:69 +#, fuzzy +msgid "" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this only works with nicks, not with channels." +msgstr "" +"Syntax: CHECK nick\n" +"\n" +"Checks whether the _last_ memo you sent to nick has been read\n" +"or not. Note that this does only work with nicks, not with chans." + +#: modules/commands/os_info.cpp:227 +#, c-format +msgid "Cleared info from %s." +msgstr "" + +#: modules/commands/bs_kick.cpp:1151 modules/commands/bs_kick.cpp:1153 +#: modules/commands/bs_kick.cpp:1156 +#, fuzzy +msgid "Colors kicker" +msgstr "KICK Atma özelliklerini ayarlar" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Command" +msgstr "%s commands:" + +#: modules/commands/bs_kick.cpp:251 +#, fuzzy +msgid "Configures AMSG kicker" +msgstr "KICK Atma özelliklerini ayarlar" + +#: modules/commands/bs_kick.cpp:287 +#, fuzzy +msgid "Configures badwords kicker" +msgstr "KICK Atma özelliklerini ayarlar" + +#: modules/commands/bs_kick.cpp:326 +#, fuzzy +msgid "Configures bolds kicker" +msgstr "KICK Atma özelliklerini ayarlar" + +#: modules/commands/bs_kick.cpp:132 +#, fuzzy +msgid "Configures bot kickers. option can be one of:" +msgstr "" +"Kullanımı: SET özellik parametre\n" +"\n" +"Çeşitli nick özelliklerini ayarlar. özellik şunlardan biri \n" +"olabilir:" + +#: modules/commands/bs_set.cpp:19 +#, fuzzy +msgid "Configures bot options" +msgstr "SET Bot özelliklerini ayarlar" + +#: modules/commands/bs_set.cpp:32 +#, fuzzy +msgid "" +"Configures bot options.\n" +" \n" +"Available options:" +msgstr "SET Bot özelliklerini ayarlar" + +#: modules/commands/bs_kick.cpp:360 +#, fuzzy +msgid "Configures caps kicker" +msgstr "KICK Atma özelliklerini ayarlar" + +#: modules/commands/cs_log.cpp:105 +#, fuzzy +msgid "Configures channel logging settings" +msgstr "* No new channel registrations" + +#: modules/commands/bs_kick.cpp:456 +#, fuzzy +msgid "Configures color kicker" +msgstr "KICK Atma özelliklerini ayarlar" + +#: modules/commands/bs_kick.cpp:490 +#, fuzzy +msgid "Configures flood kicker" +msgstr "KICK Atma özelliklerini ayarlar" + +#: modules/commands/bs_kick.cpp:588 +#, fuzzy +msgid "Configures italics kicker" +msgstr "KICK Atma özelliklerini ayarlar" + +#: modules/commands/bs_kick.cpp:119 +#, fuzzy +msgid "Configures kickers" +msgstr "KICK Atma özelliklerini ayarlar" + +#: modules/commands/bs_kick.cpp:622 +#, fuzzy +msgid "Configures repeat kicker" +msgstr "KICK Atma özelliklerini ayarlar" + +#: modules/commands/bs_kick.cpp:723 +#, fuzzy +msgid "Configures reverses kicker" +msgstr "KICK Atma özelliklerini ayarlar" + +#: modules/commands/bs_set.cpp:90 +#, fuzzy +msgid "Configures the time bot bans expire in" +msgstr "SET Bot özelliklerini ayarlar" + +#: modules/commands/bs_kick.cpp:757 +#, fuzzy +msgid "Configures underlines kicker" +msgstr "KICK Atma özelliklerini ayarlar" + +#: modules/commands/ns_register.cpp:21 +#, fuzzy +msgid "Confirm a passcode" +msgstr " CONFIRM Confirm a nickserv auth code" + +#: modules/commands/cs_mode.cpp:733 +#, fuzzy +msgid "Control modes and mode locks on a channel" +msgstr " CLEARMODES Bir kanalın modlarını temizler" + +#: modules/commands/cs_entrymsg.cpp:239 +msgid "" +"Controls what messages will be sent to users when they join the channel." +msgstr "" + +#: modules/commands/cs_clone.cpp:242 +msgid "" +"Copies all settings, access, akicks, etc from channel to the\n" +"target channel. If what is ACCESS, AKICK, BADWORDS,\n" +"or LEVELS then only the respective settings are cloned.\n" +"You must be the founder of channel and target." +msgstr "" + +#: modules/commands/cs_clone.cpp:114 +#, fuzzy +msgid "Copy all settings from one channel to another" +msgstr "" +" UNBAN Remove all bans preventing a user from entering a channel" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/bs_info.cpp:57 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Created" +msgstr " Yaratılış : %s" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_mode.cpp:449 modules/commands/cs_entrymsg.cpp:116 +#: modules/commands/os_ignore.cpp:266 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_news.cpp:156 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Creator" +msgstr " Yaratılış : %s" + +#: modules/commands/os_sxline.cpp:180 +#, fuzzy, c-format +msgid "Current %s list:" +msgstr "Şu anki AKILL listesi:" + +#: modules/commands/os_akill.cpp:323 +#, fuzzy +msgid "Current AKILL list:" +msgstr "Şu anki AKILL listesi:" + +#: modules/commands/os_session.cpp:493 +msgid "Current Session Limit Exception list:" +msgstr "Şu anki Session Limit Exception listesi:" + +#: modules/commands/os_modinfo.cpp:116 +#, fuzzy +msgid "Current module list:" +msgstr "Current Module list:" + +#: modules/commands/os_stats.cpp:69 +#, c-format +msgid "Current number of AKILLs: %d" +msgstr "Şu anki AKILL sayısı: %d" + +#: modules/commands/os_stats.cpp:89 +#, c-format +msgid "Current number of SNLINEs: %d" +msgstr "Şu anki SNLINE sayısı: %d" + +#: modules/commands/os_stats.cpp:109 +#, c-format +msgid "Current number of SQLINEs: %d" +msgstr "Su anki SQLINE sayisi: %d" + +#: modules/commands/os_stats.cpp:138 +#, c-format +msgid "Current users: %d (%d ops)" +msgstr "Şu anki kullanıcı sayısı: %d (%d op)" + +#: modules/commands/os_oper.cpp:71 +#, fuzzy +msgid "DEL oper" +msgstr "DEL ." + +#: modules/commands/os_info.cpp:103 +#, fuzzy +msgid "DEL target info" +msgstr "GROUP hedef şifre" + +#: modules/commands/ns_ajoin.cpp:232 +#, fuzzy +msgid "DEL [nickname] channel" +msgstr "MODE kanaladı modlar" + +#: modules/commands/ns_cert.cpp:259 +#, fuzzy +msgid "DEL [nickname] fingerprint" +msgstr "FORBID nick sebep" + +#: modules/commands/ns_access.cpp:103 +#, fuzzy +msgid "DEL [nickname] mask" +msgstr "MODE kanaladı modlar" + +#: modules/commands/os_sxline.cpp:426 modules/commands/os_sxline.cpp:660 +#: modules/commands/os_akill.cpp:387 +#, fuzzy +msgid "DEL {mask | entry-num | list | id}" +msgstr "DEL [kanaladı] {num | liste | ALL}" + +#: modules/commands/os_session.cpp:524 +#, fuzzy +msgid "DEL {mask | entry-num | list}" +msgstr "DEL [kanaladı] {num | liste | ALL}" + +#: modules/commands/os_ignore.cpp:343 +#, fuzzy +msgid "DEL {nick|mask}" +msgstr "DEL ." + +#: modules/commands/os_news.cpp:279 +#, fuzzy +msgid "DEL {num | ALL}" +msgstr "Kullanımı: OPERNEWS DEL {num | ALL}" + +#: modules/commands/os_forbid.cpp:158 +msgid "DEL {NICK|CHAN|EMAIL|REGISTER} entry" +msgstr "" + +#: modules/commands/os_dns.cpp:666 +msgid "DELIP server.name ip" +msgstr "" + +#: modules/commands/os_dns.cpp:664 +msgid "DELSERVER server.name [zone.name]" +msgstr "" + +#: modules/commands/os_dns.cpp:662 +msgid "DELZONE zone.name" +msgstr "" + +#: modules/commands/os_dns.cpp:669 +#, fuzzy +msgid "DEPOOL server.name" +msgstr "NOOP {SET|REVOKE} server" + +#: modules/commands/cs_seen.cpp:162 +#, c-format +msgid "Database cleared, removed %lu nicks that were added after %s." +msgstr "" + +#: modules/commands/ms_list.cpp:64 +msgid "Date/Time" +msgstr "" + +#: modules/commands/hs_off.cpp:49 +#, fuzzy +msgid "" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real host/IP address." +msgstr "" +"Syntax: OFF\n" +"Deactivates the vhost currently assigned to the nick in use.\n" +"When you use this command any user who performs a /whois\n" +"on you will see your real IP address." + +#: modules/commands/hs_off.cpp:19 +#, fuzzy +msgid "Deactivates your assigned vhost" +msgstr " OFF Deactivates your assigned vhost" + +#: modules/commands/os_stats.cpp:72 +#, c-format +msgid "Default AKILL expiry time: %d days" +msgstr "Varsayılan AKILL zaman aşımı: %d gün" + +#: modules/commands/os_stats.cpp:76 +#, c-format +msgid "Default AKILL expiry time: %d hours" +msgstr "Varsayılan AKILL zaman aşımı: %d saat" + +#: modules/commands/os_stats.cpp:80 +#, c-format +msgid "Default AKILL expiry time: %d minutes" +msgstr "Varsayılan AKILL zaman aşımı: %d dakika" + +#: modules/commands/os_stats.cpp:74 +msgid "Default AKILL expiry time: 1 day" +msgstr "Varsayılan AKILL zaman aşımı: 1 gün" + +#: modules/commands/os_stats.cpp:78 +msgid "Default AKILL expiry time: 1 hour" +msgstr "Varsayılan AKILL zaman aşımı: 1 saat" + +#: modules/commands/os_stats.cpp:82 +msgid "Default AKILL expiry time: 1 minute" +msgstr "Varsayılan AKILL zaman aşımı: 1 dakika" + +#: modules/commands/os_stats.cpp:84 +msgid "Default AKILL expiry time: No expiration" +msgstr "Varsayılan AKILL zaman aşımı: zaman aşımı yok" + +#: modules/commands/os_stats.cpp:92 +#, c-format +msgid "Default SNLINE expiry time: %d days" +msgstr "Varsayılan SNLINE zaman aşımı süresi: %d gün" + +#: modules/commands/os_stats.cpp:96 +#, c-format +msgid "Default SNLINE expiry time: %d hours" +msgstr "Varsayılan SNLINE zaman aşımı süresi: %d saat" + +#: modules/commands/os_stats.cpp:100 +#, c-format +msgid "Default SNLINE expiry time: %d minutes" +msgstr "Varsayılan SNLINE zaman aşımı süresi: %d dakika" + +#: modules/commands/os_stats.cpp:94 +msgid "Default SNLINE expiry time: 1 day" +msgstr "Varsayılan SNLINE zaman aşımı süresi: 1 gün" + +#: modules/commands/os_stats.cpp:98 +msgid "Default SNLINE expiry time: 1 hour" +msgstr "Varsayılan SNLINE zaman aşımı süresi: 1 saat" + +#: modules/commands/os_stats.cpp:102 +msgid "Default SNLINE expiry time: 1 minute" +msgstr "Varsayılan SNLINE zaman aşımı süresi: 1 dakika" + +#: modules/commands/os_stats.cpp:104 +msgid "Default SNLINE expiry time: No expiration" +msgstr "Varsayılan SNLINE zaman aşımı süresi: Zaman aşımı yok" + +#: modules/commands/os_stats.cpp:112 +#, c-format +msgid "Default SQLINE expiry time: %d days" +msgstr "Varsayilan SQLINE zaman asimi süresi: %d gün" + +#: modules/commands/os_stats.cpp:116 +#, c-format +msgid "Default SQLINE expiry time: %d hours" +msgstr "Varsayilan SQLINE zaman asimi süresi: %d saat" + +#: modules/commands/os_stats.cpp:120 +#, c-format +msgid "Default SQLINE expiry time: %d minutes" +msgstr "Varsayilan SQLINE zaman asimi süresi: %d dakika" + +#: modules/commands/os_stats.cpp:114 +msgid "Default SQLINE expiry time: 1 day" +msgstr "Varsayilan SQLINE zaman asimi süresi: 1 gün" + +#: modules/commands/os_stats.cpp:118 +msgid "Default SQLINE expiry time: 1 hour" +msgstr "Varsayilan SQLINE zaman asimi süresi: 1 saat" + +#: modules/commands/os_stats.cpp:122 +msgid "Default SQLINE expiry time: 1 minute" +msgstr "Varsayilan SQLINE zaman asimi süresi: 1 dakika" + +#: modules/commands/os_stats.cpp:124 +msgid "Default SQLINE expiry time: No expiration" +msgstr "Varsayilan SQLINE zaman asimi süresi: Zaman asimi yok" + +#: modules/commands/os_news.cpp:351 +#, fuzzy +msgid "Define messages to be randomly shown to users at logon" +msgstr "" +" LOGONNEWS Bağlantı sırasında kullanıcının göreceği mesajı \n" +" belirler" + +#: modules/commands/os_news.cpp:297 +#, fuzzy +msgid "Define messages to be shown to users at logon" +msgstr "" +" LOGONNEWS Bağlantı sırasında kullanıcının göreceği mesajı \n" +" belirler" + +#: modules/commands/os_news.cpp:324 +#, fuzzy +msgid "Define messages to be shown to users who oper" +msgstr "" +" OPERNEWS Oper olan kullanıcıların görüntüleyeceği mesajı \n" +" belirler" + +#: modules/commands/ms_del.cpp:44 +#, fuzzy +msgid "Delete a memo or memos" +msgstr " DEL Mesajları silmenizi sağlar" + +#: modules/commands/hs_del.cpp:19 +#, fuzzy +msgid "Delete the vhost of another user" +msgstr " DEL Delete the vhost of another user" + +#: modules/commands/cs_xop.cpp:302 +#, fuzzy, c-format +msgid "Deleted %d entries from %s %s list." +msgstr "Deleted %d entries from %s AOP list." + +#: modules/commands/cs_access.cpp:277 +#, c-format +msgid "Deleted %d entries from %s access list." +msgstr "Deleted %d entries from %s access list." + +#: modules/commands/cs_akick.cpp:228 +#, c-format +msgid "Deleted %d entries from %s autokick list." +msgstr "Deleted %d entries from %s autokick list." + +#: modules/commands/bs_badwords.cpp:170 +#, c-format +msgid "Deleted %d entries from %s bad words list." +msgstr "Deleted %d entries from %s bad words list." + +#: modules/commands/os_session.cpp:149 +#, c-format +msgid "Deleted %d entries from session-limit exception list." +msgstr "Session-limit exception listesinden %d kayıt silindi." + +#: modules/commands/os_sxline.cpp:32 +#, fuzzy, c-format +msgid "Deleted %d entries from the %s list." +msgstr "Deleted %d entries from %s AOP list." + +#: modules/commands/os_akill.cpp:33 +#, c-format +msgid "Deleted %d entries from the AKILL list." +msgstr "AKILL listesinden %d kayıt silindi." + +#: modules/commands/cs_access.cpp:275 +#, c-format +msgid "Deleted 1 entry from %s access list." +msgstr "%s kanalının access listesinden 1 kayıt silindi." + +#: modules/commands/cs_akick.cpp:226 +#, c-format +msgid "Deleted 1 entry from %s autokick list." +msgstr "%s kanalının akick listesinden 1 kayıt silindi." + +#: modules/commands/bs_badwords.cpp:168 +#, c-format +msgid "Deleted 1 entry from %s bad words list." +msgstr "%s kanalının küfür listesinden 1 kayıt silindi." + +#: modules/commands/os_session.cpp:147 +msgid "Deleted 1 entry from session-limit exception list." +msgstr "Session-limit exception listesinden 1 kayıt silindi." + +#: modules/commands/os_sxline.cpp:30 +#, fuzzy, c-format +msgid "Deleted 1 entry from the %s list." +msgstr "AKILL listesinden 1 kayıt silindi." + +#: modules/commands/os_akill.cpp:31 +msgid "Deleted 1 entry from the AKILL list." +msgstr "AKILL listesinden 1 kayıt silindi." + +#: modules/commands/os_info.cpp:208 +#, fuzzy, c-format +msgid "Deleted info from %s." +msgstr "AKILL listesinden 1 kayıt silindi." + +#: modules/commands/cs_xop.cpp:300 +#, fuzzy, c-format +msgid "Deleted one entry from %s %s list." +msgstr "%s kanalinin AOP listesinden 1 kayit silindi." + +#: modules/commands/ms_del.cpp:129 +#, fuzzy +msgid "" +"Deletes the specified memo or memos. You can supply\n" +"multiple memo numbers or ranges of numbers instead of a\n" +"single number, as in the second example below.\n" +" \n" +"If LAST is given, the last memo will be deleted.\n" +"If ALL is given, deletes all of your memos.\n" +" \n" +"Examples:\n" +" \n" +" DEL 1\n" +" Deletes your first memo.\n" +" \n" +" DEL 2-5,7-9\n" +" Deletes memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Kullanımı: DEL [kanaladı] {num | liste | LAST | ALL}\n" +"\n" +"Belirtilen mesajları siler. Aşağıdaki örnekteki gibi birden\n" +"fazla mesajıda silebilirsiniz.\n" +"\n" +"If LAST is given, the last memo will be deleted.\n" +"Eğer ALL parametresi belirtilmişse, tüm mesajlarınız silinir.\n" +"\n" +"Örnekler:\n" +"\n" +" DEL 1\n" +" İlk gelen mesajınızı siler.\n" +"\n" +" DEL 2-5,7-9\n" +" 2'den 5'e ve 7'den 9'a kadar olan mesajları siler." + +#: modules/commands/hs_del.cpp:48 +#, fuzzy +msgid "" +"Deletes the vhost assigned to the given nick from the\n" +"database." +msgstr "" +"Syntax: DEL \n" +"Deletes the vhost assigned to the given nick from the\n" +"database." + +#: modules/commands/hs_del.cpp:59 +#, fuzzy +msgid "Deletes the vhost for all nicks in a group" +msgstr " DELALL Delete the vhost for all nicks in a group" + +#: modules/commands/hs_del.cpp:93 +#, fuzzy +msgid "" +"Deletes the vhost for all nicks in the same group as\n" +"that of the given nick." +msgstr "" +"Syntax: DELALL .\n" +"Deletes the vhost for all nick's in the same group as\n" +"that of the given nick." + +#: modules/commands/os_dns.cpp:653 +#, c-format +msgid "Depooled %s." +msgstr "" + +#: modules/commands/cs_access.cpp:799 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_list.cpp:75 modules/commands/cs_info.cpp:53 +#, fuzzy +msgid "Description" +msgstr "%s kanalının açıklaması %s olarak değiştirildi." + +#: modules/commands/cs_set.cpp:239 +#, c-format +msgid "Description of %s changed to %s." +msgstr "%s kanalının açıklaması %s olarak değiştirildi." + +#: modules/commands/cs_set.cpp:245 +#, fuzzy, c-format +msgid "Description of %s unset." +msgstr "%s kanalının açıklaması %s olarak değiştirildi." + +#: modules/commands/bs_kick.cpp:1115 modules/commands/bs_info.cpp:90 +#, fuzzy +msgid "Disabled" +msgstr "%s is enable" + +#: modules/commands/cs_suspend.cpp:134 +#, fuzzy +msgid "" +"Disallows anyone from using the given channel.\n" +"May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"If an expiry is given the channel will be unsuspended after\n" +"that period of time, else the default expiry from the\n" +"configuration is used.\n" +" \n" +"Reason may be required on certain networks." +msgstr "" +"Syntax: SUSPEND channel [reason]\n" +"\n" +"Disallows anyone from registering or using the given\n" +"channel. May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"\n" +"Reason may be required on certain networks." + +#: modules/commands/hs_request.cpp:337 +#, fuzzy, c-format +msgid "Displayed %d records (%d total)." +msgstr "Displayed all records (Count: %d)" + +#: modules/commands/hs_list.cpp:122 +#, fuzzy, c-format +msgid "Displayed all records (count: %d)." +msgstr "Displayed all records (Count: %d)" + +#: modules/commands/hs_list.cpp:120 +#, fuzzy, c-format +msgid "Displayed records from %d to %d." +msgstr "Displayed records from %d to %d" + +#: modules/commands/hs_list.cpp:116 +#, fuzzy, c-format +msgid "Displayed records matching key %s (count: %d)." +msgstr "Displayed records matching key %s (Count: %d)" + +#: modules/commands/ns_info.cpp:19 +#, fuzzy +msgid "Displays information about a given nickname" +msgstr " INFO Displays information about a given nickname" + +#: modules/commands/ns_info.cpp:125 +#, fuzzy +msgid "" +"Displays information about the given nickname, such as\n" +"the nick's owner, last seen address and time, and nick\n" +"options. If no nick is given, and you are identified,\n" +"your account name is used, else your current nickname is\n" +"used." +msgstr "" +"Kullanımı: INFO nick\n" +"\n" +"Belirtilen nick hakkında o nickin sahibi, son görüldüğü adres ve \n" +"zaman, ve nickin özellikleri gibi bilgiler verir. Eğer nick \n" +"hakkında bilgi alırken o nickin sahibi sizseniz ve tanıtmışsanız \n" +"ALL parametresini kullandığınızda bilgiler gizli olsa bile o \n" +"nick hakkındaki tüm bilgiler görünür." + +#: modules/commands/ms_info.cpp:19 +#, fuzzy +msgid "Displays information about your memos" +msgstr " INFO Displays information about your memos" + +#: modules/commands/hs_list.cpp:19 +#, fuzzy +msgid "Displays one or more vhost entries" +msgstr " LIST Displays one or more vhost entries." + +#: modules/extra/stats/cs_fantasy_top.cpp:50 +#, fuzzy +msgid "Displays the top 10 users of a channel" +msgstr " FOUNDER Kanal founderını belirler" + +#: modules/extra/stats/cs_fantasy_top.cpp:73 +msgid "Displays the top 10 users of the network" +msgstr "" + +#: modules/extra/stats/cs_fantasy_top.cpp:38 +#, fuzzy +msgid "Displays the top 3 users of a channel" +msgstr " FOUNDER Kanal founderını belirler" + +#: modules/extra/stats/cs_fantasy_top.cpp:62 +msgid "Displays the top 3 users of the network" +msgstr "" + +#: modules/commands/help.cpp:33 +#, fuzzy +msgid "Displays this list and give information about commands" +msgstr " INFO Displays information about your memos" + +#: modules/extra/stats/cs_fantasy_stats.cpp:39 +msgid "Displays your Channel Stats" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:51 +msgid "Displays your Global Stats" +msgstr "" + +#: modules/commands/bs_kick.cpp:1463 +msgid "Don't use AMSGs!" +msgstr "" + +#: modules/commands/bs_kick.cpp:1266 +msgid "Don't use bolds on this channel!" +msgstr "Bu kanalda kalın yazı kullanılması yasaktır!" + +#: modules/commands/bs_kick.cpp:1274 +msgid "Don't use colors on this channel!" +msgstr "Lütfen bu kanalda renkli yazı kullanmayın!" + +#: modules/commands/bs_kick.cpp:1290 +msgid "Don't use italics on this channel!" +msgstr "Don't use italics on this channel!" + +#: modules/commands/bs_kick.cpp:1282 +msgid "Don't use reverses on this channel!" +msgstr "Lütfen bu kanalda Ctrl+R ile yazılmış yazı kullanmayın!" + +#: modules/commands/bs_kick.cpp:1408 +#, c-format +msgid "Don't use the word \"%s\" on this channel!" +msgstr "%s kelimesinin bu kanalda kullanılması yasaktır!" + +#: modules/commands/bs_kick.cpp:1298 +msgid "Don't use underlines on this channel!" +msgstr "Lütfen bu kanalda altı çizili yazı kullanmayın!" + +#: modules/commands/ns_drop.cpp:61 +msgid "" +"Drops the given nick from the database. Once your nickname\n" +"is dropped you may lose all of your access and channels that\n" +"you may own. Any other user will be able to gain control of\n" +"this nick." +msgstr "" + +#: modules/commands/ns_set.cpp:513 +#, c-format +msgid "E-mail address for %s changed to %s." +msgstr "E-mail address for %s changed to %s." + +#: modules/commands/ns_set.cpp:519 +#, c-format +msgid "E-mail address for %s unset." +msgstr "E-mail address for %s unset." + +#: src/mail.cpp:80 +#, c-format +msgid "E-mail for %s is invalid." +msgstr "%s için mail adresi geçerli değil." + +#: modules/commands/os_news.cpp:309 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Syntax: LOGONNEWS ADD text\n" +" LOGONNEWS DEL {num | ALL}\n" +" LOGONNEWS LIST\n" +"\n" +"Edits or displays the list of logon news messages. When a\n" +"user connects to the network, these messages will be sent\n" +"to them. (However, no more than %d messages will be\n" +"sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent.)\n" +"NewsCount can be configured in services.conf.\n" +"\n" +"LOGONNEWS may only be used by Services Operators." + +#: modules/commands/os_news.cpp:336 +#, fuzzy, c-format +msgid "" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent." +msgstr "" +"Syntax: OPERNEWS ADD text\n" +" OPERNEWS DEL {num | ALL}\n" +" OPERNEWS LIST\n" +"\n" +"Edits or displays the list of oper news messages. When a\n" +"user opers up (with the /OPER command), these messages will\n" +"be sent to them. (However, no more than %d messages will\n" +"be sent in order to avoid flooding the user. If there are\n" +"more news messages, only the most recent will be sent.)\n" +"NewsCount can be configured in services.conf.\n" +"\n" +"OPERNEWS may only be used by Services Operators." + +#: modules/commands/os_news.cpp:363 +#, fuzzy +msgid "" +"Edits or displays the list of random news messages. When a\n" +"user connects to the network, one (and only one) of the\n" +"random news will be randomly chosen and sent to them." +msgstr "" +"Kullanimi: RANDOMNEWS ADD yazi\n" +" RANDOMNEWS DEL {no | ALL}\n" +" RANDOMNEWS LIST\n" +"\n" +"Karisik haberleri düzenlemenizi saglar. Bir kullanici\n" +"network e baglandigi zaman, karisik haberlerden bir tanesi\n" +"seçilerek kullaniciya gönderilir.\n" +"\n" +"RANDOMNEWS may only be used by Services Operators." + +#: modules/commands/ns_info.cpp:98 +#, fuzzy +msgid "Email address" +msgstr " E-mail adresi: %s" + +#: modules/commands/ns_getemail.cpp:41 +#, fuzzy, c-format +msgid "Email matched: %s (%s) to %s." +msgstr "Emails Match %s to %s." + +#: modules/fantasy.cpp:19 +msgid "Enable fantaisist commands" +msgstr "" + +#: modules/commands/greet.cpp:19 +msgid "Enable greet messages" +msgstr "" + +#: modules/commands/ns_set.cpp:568 +msgid "Enable or disable keep modes" +msgstr "" + +#: modules/commands/bs_kick.cpp:1114 modules/commands/bs_info.cpp:89 +#, fuzzy +msgid "Enabled" +msgstr "%s is enable" + +#: modules/commands/cs_set.cpp:124 +#, fuzzy, c-format +msgid "" +"Enables or disables %s's autoop feature for a\n" +"channel. When disabled, users who join the channel will\n" +"not automatically gain any status from %s." +msgstr "" +"Kullanımı: %s kanaladı SECUREOPS {ON | OFF}\n" +"\n" +"Bir kanal için güvenli op özelliğini açar veya kapatır.\n" +"güvenli op özelliği aktifse, access listesinde olmayan\n" +"kullanıcılar kanalda op olamazlar." + +#: modules/commands/cs_set.cpp:388 +#, fuzzy +msgid "" +"Enables or disables keepmodes for the given channel. If keep\n" +"modes is enabled, services will remember modes set on the channel\n" +"and attempt to re-set them the next time the channel is created." +msgstr "" +"Kullanımı: %s kanaladı KEEPTOPIC {ON | OFF}\n" +"\n" +"Bir kanal için topic hatırlamayı aktifleştirir yada kapatır.\n" +"topic hatırlama aktifse kanal kapansa bile kanal topic i\n" +"%s tarafından hatırlanır ve birisi kanala girdiğinde bu\n" +"topic geçerli olur." + +#: modules/commands/ns_set.cpp:643 +msgid "" +"Enables or disables keepmodes for the given nick. If keep\n" +"modes is enabled, services will remember users' usermodes\n" +"and attempt to re-set them the next time they authenticate." +msgstr "" + +#: modules/commands/ns_set.cpp:618 +msgid "" +"Enables or disables keepmodes for your nick. If keep\n" +"modes is enabled, services will remember your usermodes\n" +"and attempt to re-set them the next time you authenticate." +msgstr "" + +#: modules/commands/cs_set.cpp:733 +#, fuzzy +msgid "" +"Enables or disables security features for a\n" +"channel. When SECURE is set, only users who have\n" +"identified to services, and are not only recognized, will be\n" +"given access to channels from account-based access entries." +msgstr "" +"Kullanımı: %s kanaladı SECURE {ON | OFF}\n" +"\n" +"Bir kanal için %s'ün güvenlik özelliklerini açar veya \n" +"kapatır. SECURE özelliği aktifse, sadece nicki kayıtlı\n" +"ve %s ile nickini tanıtmış kullanıcılar kanalda access \n" +"alabilirler ve access listesindeki statülerini\n" +"alabilirler.(mesela op olabilirler)" + +#: modules/commands/cs_set.cpp:932 +#, fuzzy +msgid "" +"Enables or disables signed kicks for a\n" +"channel. When SIGNKICK is set, kicks issued with\n" +"the KICK command will have the nick that used the\n" +"command in their reason.\n" +" \n" +"If you use LEVEL, those who have a level that is superior\n" +"or equal to the SIGNKICK level on the channel won't have their\n" +"kicks signed." +msgstr "" +"Kullanımı: %s kanaladı SIGNKICK {ON | LEVEL | OFF}\n" +"\n" +"Bir kanal için işaretli atmayı açar yada kapatır.\n" +"SIGNKICK ayarlandığı zaman, %s KICK\n" +"komutuyla yapılan atmalarda komutu kullanan kişinin\n" +"nicki atma sebebinde yer alır.\n" +"\n" +"Eğer LEVEL parametresini kullanırsanız, seviyesi\n" +"SIGNKICK seviyesine eşit yada fazla olanların yaptığı\n" +"atmalarda atanın nicki sebepte gözükmez. Daha fazla\n" +"bilgi için /msg %s HELP LEVELS yazın." + +#: modules/commands/cs_set.cpp:452 +#, fuzzy, c-format +msgid "" +"Enables or disables the peace option for a channel.\n" +"When peace is set, a user won't be able to kick,\n" +"ban or remove a channel status of a user that has\n" +"a level superior or equal to his via %s commands." +msgstr "" +"Kullanimi: %s kanaladi PEACE {ON | OFF}\n" +"\n" +"Bir kanalin peace özelligini açar veya kapatir.\n" +"peace özelligi ayarlandiginda, hic kimse seviyesi kendinden\n" +"yüksek veya esit olanlari atamaz, banlayamaz veya %s\n" +"seviyesini degistiremez." + +#: modules/commands/cs_list.cpp:232 +msgid "Enables or disables the private option for a channel." +msgstr "" + +#: modules/commands/cs_set.cpp:671 +#, fuzzy +msgid "" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." +msgstr "" +"Kullanımı: %s kanaladı RESTRICTED {ON | OFF}\n" +"\n" +"Enables or disables the restricted access option for a\n" +"channel. When restricted access is set, users not on the access list will\n" +"instead be kicked and banned from the channel." + +#: modules/commands/cs_set.cpp:796 +#, fuzzy +msgid "" +"Enables or disables the secure founder option for a channel.\n" +"When secure founder is set, only the real founder will be\n" +"able to drop the channel, change its founder and its successor,\n" +"and not those who have founder level access through\n" +"the access/qop command." +msgstr "" +"Kullanımı: %s kanaladı SECUREFOUNDER {ON | OFF}\n" +"\n" +"Bir kanal için güvenli founder özelliğini açar yada kapatır.\n" +"güvenli founder özelliği aktifse, sadece gerçek founder \n" +"kanalın kaydını silebilir, kanal şifresini değiştirebilir yada\n" +"kanal founderını ve successor ını değiştirebilir. Kanal \n" +"şifresiyle kendilerini %s'e kanal founderı olarak tanıtan \n" +"ama nicki founderın nicki olmayanlar bu komutları kullanamazlar." + +#: modules/commands/cs_set.cpp:860 +#, fuzzy +msgid "" +"Enables or disables the secure ops option for a channel.\n" +"When secure ops is set, users who are not on the access list\n" +"will not be allowed channel operator status." +msgstr "" +"Kullanımı: %s kanaladı SECUREOPS {ON | OFF}\n" +"\n" +"Bir kanal için güvenli op özelliğini açar veya kapatır.\n" +"güvenli op özelliği aktifse, access listesinde olmayan\n" +"kullanıcılar kanalda op olamazlar." + +#: modules/commands/cs_topic.cpp:70 +#, fuzzy, c-format +msgid "" +"Enables or disables the topic retention option for a\n" +"channel. When %s is set, the topic for the\n" +"channel will be remembered by %s even after the\n" +"last user leaves the channel, and will be restored the\n" +"next time the channel is created." +msgstr "" +"Kullanımı: %s kanaladı KEEPTOPIC {ON | OFF}\n" +"\n" +"Bir kanal için topic hatırlamayı aktifleştirir yada kapatır.\n" +"topic hatırlama aktifse kanal kapansa bile kanal topic i\n" +"%s tarafından hatırlanır ve birisi kanala girdiğinde bu\n" +"topic geçerli olur." + +#: modules/commands/cs_set.cpp:592 +#, fuzzy, c-format +msgid "" +"Enables or disables the persistent channel setting.\n" +"When persistent is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +" \n" +"If your IRCd does not have a permanent (persistent) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +" \n" +"If this network does not have %s enabled and does\n" +"not have a permanent channel mode, %s will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +" \n" +"If your IRCd has a permanent (persistent) channel mode\n" +"and it is set or unset (for any reason, including MODE LOCK),\n" +"persist is automatically set and unset for the channel as well.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." +msgstr "" +"Syntax: %s channel PERSIST {ON | OFF}\n" +"Enables or disables the persistant channel setting.\n" +"When persistant is set, the service bot will remain\n" +"in the channel when it has emptied of users.\n" +"\n" +"If your IRCd does not a permanent (persistant) channel\n" +"mode you must have a service bot in your channel to\n" +"set persist on, and it can not be unassigned while persist\n" +"is on.\n" +"\n" +"If this network does not have BotServ enabled and does\n" +"not have a permanent channel mode, ChanServ will\n" +"join your channel when you set persist on (and leave when\n" +"it has been set off).\n" +"\n" +"If your IRCd has a permanent (persistant) channel mode\n" +"and is is set or unset (for any reason, including MLOCK),\n" +"persist is automatically set and unset for the channel aswell.\n" +"Additionally, services will set or unset this mode when you\n" +"set persist on or off." + +#: modules/commands/os_akill.cpp:331 +#, fuzzy +msgid "End of AKILL list." +msgstr "Kullanıcı listesi sonu." + +#: modules/commands/cs_access.cpp:444 +#, fuzzy +msgid "End of access list" +msgstr "access listenin sonu." + +#: modules/commands/cs_flags.cpp:347 +#, fuzzy, c-format +msgid "End of access list - %d/%d entries shown." +msgstr "Liste sonu - %d/%d ." + +#: modules/commands/cs_flags.cpp:345 +msgid "End of access list." +msgstr "access listenin sonu." + +#: modules/commands/cs_akick.cpp:379 +#, fuzzy +msgid "End of autokick list" +msgstr "access listenin sonu." + +#: modules/commands/bs_badwords.cpp:257 +#, fuzzy +msgid "End of bad words list." +msgstr "Kullanıcı listesi sonu." + +#: modules/commands/os_list.cpp:100 +#, fuzzy, c-format +msgid "End of channel list. %u channels shown." +msgstr "Liste sonu - %d/%d ." + +#: modules/commands/os_config.cpp:117 +msgid "End of configuration." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:134 +#, fuzzy +msgid "End of entry message list." +msgstr "Kullanıcı listesi sonu." + +#: modules/commands/os_forbid.cpp:407 +#, fuzzy, c-format +msgid "End of forbid list - %d/%d entries shown." +msgstr "Liste sonu - %d/%d ." + +#: modules/commands/os_forbid.cpp:405 +#, fuzzy +msgid "End of forbid list." +msgstr "Kullanıcı listesi sonu." + +#: modules/commands/ns_alist.cpp:119 +#, fuzzy, c-format +msgid "End of list - %d channels shown." +msgstr "Liste sonu - %d/%d ." + +#: modules/commands/ns_list.cpp:131 modules/commands/cs_list.cpp:130 +#, c-format +msgid "End of list - %d/%d matches shown." +msgstr "Liste sonu - %d/%d ." + +#: modules/commands/os_news.cpp:176 +#, fuzzy +msgid "End of news list." +msgstr "Kullanıcı listesi sonu." + +#: modules/commands/os_list.cpp:235 +#, fuzzy, c-format +msgid "End of users list. %u users shown." +msgstr "Liste sonu - %d/%d ." + +#: modules/commands/cs_enforce.cpp:227 +msgid "Enforce various channel modes and set options" +msgstr "" + +#: modules/commands/cs_enforce.cpp:263 +msgid "" +"Enforce various channel modes and set options. The channel\n" +"option indicates what channel to enforce the modes and options\n" +"on. The what option indicates what modes and options to\n" +"enforce, and can be any of SECUREOPS, RESTRICTED, REGONLY, SSLONLY,\n" +"BANS, or LIMIT.\n" +" \n" +"Use SECUREOPS to enforce the SECUREOPS option, even if it is not\n" +"enabled. Use RESTRICTED to enforce the RESTRICTED option, also\n" +"if it's not enabled. Use REGONLY to kick all unregistered users\n" +"from the channel. Use SSLONLY to kick all users not using a secure\n" +"connection from the channel. BANS will enforce bans on the channel by\n" +"kicking users affected by them, and LIMIT will kick users until the\n" +"user count drops below the channel limit, if one is set." +msgstr "" + +#: src/language.cpp:43 modules/commands/ns_set.cpp:836 +#: modules/commands/ns_set.cpp:856 modules/commands/ns_set.cpp:891 +msgid "English" +msgstr "Türkçe" + +#: modules/commands/cs_entrymsg.cpp:170 +#, fuzzy, c-format +msgid "Entry message %i for %s deleted." +msgstr "Greet message for %s unset." + +#: modules/commands/cs_entrymsg.cpp:177 +#, fuzzy, c-format +msgid "Entry message %s not found on channel %s." +msgstr "Fantazi modu %s kanalında AKTİF." + +#: modules/commands/cs_entrymsg.cpp:147 +#, fuzzy, c-format +msgid "Entry message added to %s" +msgstr "Greet message for %s changed to %s." + +#: modules/commands/cs_entrymsg.cpp:109 modules/commands/cs_entrymsg.cpp:158 +#, fuzzy, c-format +msgid "Entry message list for %s is empty." +msgstr "Access list for %s is empty." + +#: modules/commands/cs_entrymsg.cpp:113 +#, fuzzy, c-format +msgid "Entry message list for %s:" +msgstr "%s nickinin access listesi:" + +#: modules/commands/cs_entrymsg.cpp:187 +#, fuzzy, c-format +msgid "Entry messages for %s have been cleared." +msgstr "All memos for channel %s have been deleted." + +#: modules/commands/os_reload.cpp:39 +#, fuzzy, c-format +msgid "Error reloading configuration file: %s" +msgstr " RELOAD Servislerin conf dosyasını yeniden yükler" + +#: include/language.h:125 +#, c-format +msgid "" +"Error! The vHost ident is too long, please use an ident shorter than %d " +"characters." +msgstr "" + +#: include/language.h:124 +#, c-format +msgid "" +"Error! The vHost is too long, please use a hostname shorter than %d " +"characters." +msgstr "" + +#: modules/commands/ns_cert.cpp:325 +msgid "" +"Examples:\n" +" \n" +" CERT ADD\n" +" Adds your current fingerprint to the certificate list and\n" +" automatically identifies you when you connect to IRC\n" +" using this fingerprint.\n" +" \n" +" CERT DEL \n" +" Removes the fingerprint from your certificate list.\n" +" \n" +" CERT LIST\n" +" Displays the current certificate list." +msgstr "" + +#: modules/commands/os_session.cpp:358 +#, c-format +msgid "Exception for %s has been updated to %d." +msgstr "Exception for %s has been updated to %d." + +#: modules/pseudoclients/chanserv.cpp:465 +#: modules/pseudoclients/nickserv.cpp:557 +#: modules/pseudoclients/nickserv.cpp:562 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:201 modules/commands/os_forbid.cpp:358 +#: modules/commands/os_session.cpp:514 modules/commands/ns_group.cpp:327 +#: modules/commands/os_akill.cpp:358 +#, fuzzy +msgid "Expires" +msgstr "Expires in: %s" + +#: src/xline.cpp:397 +#, fuzzy, c-format +msgid "Expiry and reason updated for %s." +msgstr "Exception for %s has been updated to %d." + +#: src/xline.cpp:400 +#, fuzzy, c-format +msgid "Expiry for %s updated." +msgstr "%s nickinin zaman aşımı süresi değiştirildi." + +#: modules/fantasy.cpp:214 +msgid "Fantasy" +msgstr "Fantazi" + +#: modules/fantasy.cpp:60 +#, fuzzy, c-format +msgid "Fantasy mode is now off on channel %s." +msgstr "Fantazi modu %s kanalında AKTİF." + +#: modules/fantasy.cpp:52 +#, fuzzy, c-format +msgid "Fantasy mode is now on on channel %s." +msgstr "Fantazi modu %s kanalında AKTİF." + +#: modules/commands/cs_status.cpp:19 +#, fuzzy +msgid "Find a user's status on a channel" +msgstr " DEOWNER Removes your owner status on a channel" + +#: modules/commands/ns_cert.cpp:192 +#, fuzzy, c-format +msgid "Fingerprint %s already present on %s's certificate list." +msgstr "%s access listenizde zaten var." + +#: modules/commands/ns_cert.cpp:198 +#, fuzzy, c-format +msgid "Fingerprint %s is already in use." +msgstr "You are already in %s! " + +#: modules/commands/cs_flags.cpp:301 +msgid "Flags" +msgstr "" + +#: modules/commands/cs_flags.cpp:286 +#, fuzzy, c-format +msgid "Flags for %s on %s set to +%s" +msgstr "%s nickinin access seviyesi %s kanalında %d olarak değiştirildi." + +#: modules/commands/cs_flags.cpp:341 +#, fuzzy, c-format +msgid "Flags list for %s" +msgstr "%s nickinin access listesi:" + +#: modules/commands/bs_kick.cpp:1161 modules/commands/bs_kick.cpp:1163 +#: modules/commands/bs_kick.cpp:1166 +#, fuzzy +msgid "Flood kicker" +msgstr " Floodda atma : %s" + +#: modules/commands/os_forbid.cpp:421 +msgid "" +"Forbid allows you to forbid usage of certain nicknames, channels,\n" +"and email addresses. Wildcards are accepted for all entries." +msgstr "" + +#: modules/commands/os_forbid.cpp:354 +#, fuzzy +msgid "Forbid list is empty." +msgstr "Ignore listesi boş." + +#: modules/commands/os_forbid.cpp:396 +#, fuzzy +msgid "Forbid list:" +msgstr "Bot listesi:" + +#: modules/commands/os_forbid.cpp:348 +#, c-format +msgid "Forbid on %s was not found." +msgstr "" + +#: modules/commands/os_forbid.cpp:156 +msgid "Forbid usage of nicknames, channels, and emails" +msgstr "" + +#: modules/commands/os_update.cpp:19 +#, fuzzy +msgid "Force the Services databases to be updated immediately" +msgstr "" +" UPDATE Diskteki Servis veritabanının hemen\n" +" güncellenmesini sağlar" + +#: modules/commands/os_svs.cpp:19 +#, fuzzy +msgid "Forcefully change a user's nickname" +msgstr " SVSNICK Forcefully change a user's nickname" + +#: modules/commands/os_svs.cpp:68 +#, fuzzy +msgid "Forcefully changes a user's nickname from nick to newnick." +msgstr "" +"Syntax: SVSNICK nick newnick\n" +"\n" +"Forcefully changes a user's nickname from nick to newnick." + +#: modules/commands/os_svs.cpp:78 +#, fuzzy +msgid "Forcefully join a user to a channel" +msgstr " SVSNICK Forcefully change a user's nickname" + +#: modules/commands/os_svs.cpp:112 +#, fuzzy +msgid "Forcefully join a user to a channel." +msgstr " SVSNICK Forcefully change a user's nickname" + +#: modules/commands/os_svs.cpp:122 +#, fuzzy +msgid "Forcefully part a user from a channel" +msgstr " KICK Bir kullanıcıyı kanaldan atar" + +#: modules/commands/os_svs.cpp:160 +#, fuzzy +msgid "Forcefully part a user from a channel." +msgstr " KICK Bir kullanıcıyı kanaldan atar" + +#: modules/commands/ns_alist.cpp:64 modules/commands/cs_info.cpp:47 +#, fuzzy +msgid "Founder" +msgstr "Secure Founder" + +#: modules/commands/cs_set.cpp:315 +#, fuzzy, c-format +msgid "Founder of %s changed to %s." +msgstr "%s kanalının founderı %s olarak değiştirildi." + +#: modules/commands/ns_getpass.cpp:41 +msgid "GETPASS command unavailable because encryption is in use." +msgstr "GETPASS komutu devre dışı çünkü şifreleme(encryption) devrede." + +#: modules/commands/ns_recover.cpp:84 +msgid "Ghost with your nick has been killed." +msgstr "Asılı kalan nickiniz kill lendi." + +#: modules/commands/os_oline.cpp:19 +#, fuzzy +msgid "Give Operflags to a certain user" +msgstr " OLINE Give Operflags to a certain user" + +#: modules/commands/cs_mode.cpp:905 +#, c-format +msgid "" +"Gives %s status to the selected nick on a channel. If nick is\n" +"not given, it will %s you." +msgstr "" + +#: modules/commands/cs_mode.cpp:888 +#, fuzzy, c-format +msgid "Gives you or the specified nick %s status on a channel" +msgstr " OWNER Gives you owner status on channel" + +#: modules/commands/greet.cpp:206 modules/commands/greet.cpp:212 +msgid "Greet" +msgstr "Karşılama" + +#: src/access.cpp:38 +#, fuzzy +msgid "Greet message displayed on join" +msgstr "Greet message for %s changed to %s." + +#: modules/commands/greet.cpp:112 +#, c-format +msgid "Greet message for %s changed to %s." +msgstr "Greet message for %s changed to %s." + +#: modules/commands/greet.cpp:118 +#, c-format +msgid "Greet message for %s unset." +msgstr "Greet message for %s unset." + +#: modules/commands/greet.cpp:60 +#, fuzzy, c-format +msgid "Greet mode is now off on channel %s." +msgstr "Karşılama modu %s kanalında AKTİF." + +#: modules/commands/greet.cpp:52 +#, fuzzy, c-format +msgid "Greet mode is now on on channel %s." +msgstr "Karşılama modu %s kanalında AKTİF." + +#: modules/commands/ns_resetpass.cpp:21 +#, fuzzy +msgid "Helps you reset lost passwords" +msgstr " RESETPASS Helps you reset lost passwords" + +#: modules/commands/ns_info.cpp:141 +#, fuzzy +msgid "Hide certain pieces of nickname information" +msgstr " HIDE Nickinizle ilgili bazı bilgileri saklar" + +#: modules/commands/cs_list.cpp:180 +#, fuzzy +msgid "Hide channel from the LIST command" +msgstr " PRIVATE LIST komutuyla kanal listelenmez" + +#: modules/commands/os_session.cpp:192 +msgid "Host" +msgstr "" + +#: modules/commands/os_session.cpp:207 +#, c-format +msgid "Hosts with at least %d sessions:" +msgstr "En az %d sessionlı hostlar:" + +#: modules/commands/cs_seen.cpp:207 +#, c-format +msgid "I don't know who %s is." +msgstr "" + +#: modules/commands/cs_seen.cpp:253 +#, fuzzy, c-format +msgid "I've never seen %s on this channel." +msgstr "Lütfen bu kanalda Ctrl+R ile yazılmış yazı kullanmayın!" + +#: modules/commands/os_sxline.cpp:203 modules/commands/os_akill.cpp:360 +msgid "ID" +msgstr "" + +#: modules/commands/os_oper.cpp:72 +msgid "INFO [type]" +msgstr "" + +#: modules/commands/os_dns.cpp:218 +msgid "IP" +msgstr "" + +#: modules/commands/os_dns.cpp:500 +#, fuzzy, c-format +msgid "IP %s already exists for %s." +msgstr "%s nickli bot zaten var." + +#: modules/commands/os_dns.cpp:562 +#, fuzzy, c-format +msgid "IP %s does not exist for %s." +msgstr "%s nickli bot zaten var." + +#: modules/commands/ns_identify.cpp:65 +#, fuzzy +msgid "Identify yourself with your password" +msgstr " IDENTIFY Şifrenizle nickinizi tanıtır" + +#: modules/pseudoclients/nickserv.cpp:205 +#: modules/pseudoclients/nickserv.cpp:211 +#, fuzzy, c-format +msgid "If you do not change within %s, I will change your nick." +msgstr "Eğer 20 saniye içinde nickinizi değiştirmezseniz, Ben değiştireceğim." + +#: modules/commands/os_ignore.cpp:333 +msgid "Ignore list has been cleared." +msgstr "Ignore list has been cleared." + +#: modules/commands/os_ignore.cpp:262 +msgid "Ignore list is empty." +msgstr "Ignore listesi boş." + +#: modules/commands/ms_ignore.cpp:94 +#, fuzzy +msgid "Ignore list:" +msgstr "Bot listesi:" + +#: modules/commands/ns_set.cpp:1305 +#, fuzzy +msgid "Immediate protection" +msgstr "Voiceları koruma" + +#: modules/commands/ns_resetpass.cpp:33 +#, fuzzy +msgid "Incorrect email address." +msgstr " E-mail adresi: %s" + +#: include/language.h:89 +msgid "Incorrect range specified. The correct syntax is #from-to." +msgstr "" + +#: modules/commands/os_modinfo.cpp:19 +#, fuzzy +msgid "Info about a loaded module" +msgstr " MODINFO Info about a loaded module" + +#: modules/commands/bs_info.cpp:54 +#, c-format +msgid "Information for bot %s:" +msgstr "%s botunun bilgileri:" + +#: include/language.h:108 +#, fuzzy, c-format +msgid "Information for channel %s:" +msgstr "%s botunun bilgileri:" + +#: modules/commands/os_logsearch.cpp:57 +#, c-format +msgid "Invalid duration %s, using %d days." +msgstr "" + +#: include/language.h:68 +msgid "Invalid expiry time." +msgstr "" + +#: modules/commands/os_session.cpp:346 +#, fuzzy +msgid "" +"Invalid hostmask. Only real hostmasks are valid, as exceptions are not " +"matched against nicks or usernames." +msgstr "" +"Geçersiz hostmask. Sadece gerçek hostmasklar exception olarak geçerlidir." + +#: modules/commands/os_logsearch.cpp:73 +#, c-format +msgid "Invalid limit %s, using %d." +msgstr "" + +#: include/language.h:99 +msgid "" +"Invalid passcode has been entered, please check the e-mail again, and retry." +msgstr "" + +#: modules/commands/ns_register.cpp:83 modules/commands/ns_register.cpp:86 +msgid "Invalid passcode." +msgstr "" + +#: modules/commands/os_session.cpp:339 +#, c-format +msgid "" +"Invalid session limit. It must be a valid integer greater than or equal to " +"zero and less than %d." +msgstr "" +"Geçersiz session limiti. Sıfırdan büyük yada eşit ve %d den az bir geçerli " +"tamsayı olmalıdır." + +#: modules/commands/os_session.cpp:188 +msgid "Invalid threshold value. It must be a valid integer greater than 1." +msgstr "Geçersiz threshold değeri. 1 den büyük geçerli tamsayı olmalıdır." + +#: modules/commands/os_dns.cpp:591 +msgid "Invalid value for LIMIT. Must be numerical." +msgstr "" + +#: modules/commands/cs_invite.cpp:19 +#, fuzzy +msgid "Invites you or an optionally specified nick into a channel" +msgstr " OP Gives Op status to a selected nick on a channel" + +#: modules/commands/bs_kick.cpp:1201 modules/commands/bs_kick.cpp:1203 +#: modules/commands/bs_kick.cpp:1206 +#, fuzzy +msgid "Italics kicker" +msgstr " Italics kicker : %s" + +#: modules/commands/ns_group.cpp:91 +#, fuzzy +msgid "Join a group" +msgstr " GROUP Bir gruba dahil eder" + +#: modules/commands/cs_set.cpp:1305 modules/commands/ns_set.cpp:1319 +#, fuzzy +msgid "Keep modes" +msgstr "Message mode" + +#: modules/commands/cs_set.cpp:377 modules/commands/ns_set.cpp:603 +#, fuzzy, c-format +msgid "Keep modes for %s is now off." +msgstr "Peace option for %s is now ON." + +#: modules/commands/cs_set.cpp:369 modules/commands/ns_set.cpp:597 +#, fuzzy, c-format +msgid "Keep modes for %s is now on." +msgstr "Peace option for %s is now ON." + +#: modules/commands/ns_ajoin.cpp:100 +msgid "Key" +msgstr "" + +#: modules/commands/cs_getkey.cpp:50 +#, c-format +msgid "Key for channel %s is %s." +msgstr "Key for channel %s is %s." + +#: modules/commands/os_kick.cpp:19 +#, fuzzy +msgid "Kick a user from a channel" +msgstr " KICK Bir kullanıcıyı kanaldan atar" + +#: modules/commands/cs_ban.cpp:217 modules/commands/cs_kick.cpp:116 +#, c-format +msgid "Kicked %d/%d users matching %s from %s." +msgstr "" + +#: modules/commands/cs_kick.cpp:19 +#, fuzzy +msgid "Kicks a specified nick from a channel" +msgstr " KICK Kicks a selected nick from a channel" + +#: modules/commands/cs_kick.cpp:128 +#, fuzzy +msgid "" +"Kicks a specified nick from a channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access\n" +"and above on the channel. Channel founders can also specify masks." +msgstr "" +"Kullanımı: KICK #kanaladı nick [sebep]\n" +"\n" +"Belirtilen nicki kanaldan atar.\n" +"\n" +"Varsayılan olarak, AOP lar ile access seviyesi 5 ve üzeri\n" +"olanlar bu komutu kullanabilir." + +#: modules/commands/os_kill.cpp:19 +msgid "Kill a user" +msgstr "" + +#: modules/commands/cs_enforce.cpp:217 +msgid "LIMIT enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:221 +#, c-format +msgid "LIMIT enforced on %s, %d users removed." +msgstr "" + +#: modules/commands/os_session.cpp:246 +msgid "LIST threshold" +msgstr "" + +#: modules/commands/os_sxline.cpp:427 modules/commands/os_sxline.cpp:661 +#: modules/commands/os_akill.cpp:388 +#, fuzzy +msgid "LIST [mask | list | id]" +msgstr "LIST [kanaladı] [liste | NEW]" + +#: modules/commands/os_session.cpp:525 +#, fuzzy +msgid "LIST [mask | list]" +msgstr "LIST [kanaladı] [liste | NEW]" + +#: modules/commands/ns_access.cpp:104 modules/commands/ns_cert.cpp:260 +#: modules/commands/ns_ajoin.cpp:233 +#, fuzzy +msgid "LIST [nickname]" +msgstr "CHECK nickname" + +#: modules/commands/os_news.cpp:31 +msgid "LOGONNEWS {ADD|DEL|LIST} [text|num]" +msgstr "LOGONNEWS {ADD|DEL|LIST} [yazı|num]" + +#: modules/commands/ns_set.cpp:834 +msgid "Language changed to English." +msgstr "Dil Türkçe olarak değiştirildi." + +#: modules/commands/ns_set.cpp:836 +#, fuzzy, c-format +msgid "Language for %s changed to %s." +msgstr "%s için successor %s olarak değiştirildi." + +#: modules/commands/ms_cancel.cpp:72 +#, c-format +msgid "Last memo to %s has been cancelled." +msgstr "%s nickine gönderilen son mesaj iptal edildi." + +#: modules/commands/ns_info.cpp:95 +#, fuzzy +msgid "Last quit message" +msgstr " Son çıkış mesajı: %s" + +#: modules/commands/cs_access.cpp:472 modules/commands/ns_info.cpp:92 +#, fuzzy +msgid "Last seen" +msgstr " Son görüldüğü tarih: %s" + +#: modules/commands/ns_info.cpp:81 modules/commands/ns_info.cpp:86 +#, fuzzy +msgid "Last seen address" +msgstr " Son görüldüğü adres: %s" + +#: modules/commands/cs_topic.cpp:264 +msgid "Last topic" +msgstr "" + +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_info.cpp:56 +#, fuzzy +msgid "Last used" +msgstr " Son görüldüğü tarih: %s" + +#: modules/commands/ns_list.cpp:75 +#, fuzzy +msgid "Last usermask" +msgstr " Son görüldüğü tarih: %s" + +#: modules/commands/cs_access.cpp:459 modules/commands/cs_access.cpp:472 +#: modules/commands/cs_access.cpp:697 +msgid "Level" +msgstr "" + +#: modules/commands/cs_access.cpp:660 +#, c-format +msgid "Level for %s on channel %s changed to %d." +msgstr "%s için level %s kanalında %d olarak değiştirildi." + +#: modules/commands/cs_access.cpp:658 +#, c-format +msgid "Level for %s on channel %s changed to founder only." +msgstr "Level for %s on channel %s changed to founder only." + +#: modules/commands/cs_access.cpp:643 +#, c-format +msgid "Level must be between %d and %d inclusive." +msgstr "Level %d ile %d arasında olmalıdır." + +#: modules/commands/os_dns.cpp:218 modules/commands/os_session.cpp:506 +#: modules/commands/os_session.cpp:514 +msgid "Limit" +msgstr "" + +#: modules/commands/ns_list.cpp:19 +#, fuzzy +msgid "List all registered nicknames that match a given pattern" +msgstr "" +" LIST List all registered nicknames that match a given pattern" + +#: modules/commands/ns_alist.cpp:24 +#, fuzzy +msgid "List channels you have access on" +msgstr " ALIST List channels you have access on" + +#: modules/commands/cs_mode.cpp:341 +#, c-format +msgid "List for mode %c is full." +msgstr "" + +#: modules/commands/os_modinfo.cpp:80 +#, fuzzy +msgid "List loaded modules" +msgstr " MODLIST List loaded modules" + +#: modules/commands/ns_list.cpp:123 modules/commands/cs_list.cpp:72 +#, fuzzy, c-format +msgid "List of entries matching %s:" +msgstr "%s grubundaki nicklerin listesi:" + +#: modules/commands/ns_group.cpp:350 +#, c-format +msgid "List of nicknames in the group of %s:" +msgstr "%s grubundaki nicklerin listesi:" + +#: modules/commands/ns_group.cpp:350 +msgid "List of nicknames in your group:" +msgstr "Grubunuzdaki nicklerin listesi:" + +#: modules/commands/ms_list.cpp:19 +#, fuzzy +msgid "List your memos" +msgstr " LIST Mesajlarınızı listeler" + +#: modules/commands/bs_botlist.cpp:64 +#, fuzzy +msgid "" +"Lists all available bots on this network.\n" +"Bots prefixed by a * are reserved for IRC Operators." +msgstr "" +"Kullanımı: BOTLIST\n" +"\n" +"Networkte mevcut olan tüm botları listeler." + +#: modules/commands/os_list.cpp:19 +#, fuzzy +msgid "Lists all channel records" +msgstr " CHANLIST Tüm kanal kayıtlarını listeler" + +#: modules/commands/os_list.cpp:107 +#, fuzzy +msgid "" +"Lists all channels currently in use on the IRC network, whether they\n" +"are registered or not.\n" +" \n" +"If pattern is given, lists only channels that match it. If a nickname\n" +"is given, lists only the channels the user using it is on. If SECRET is\n" +"specified, lists only channels matching pattern that have the +s or\n" +"+p mode." +msgstr "" +"Kullanımı: CHANLIST [{model | nick} [SECRET]]\n" +"\n" +"Networkte o an kullanılan kanalları kayıtlı olsun olmasın \n" +"listeler.\n" +"\n" +"Eğer model belirtilmişse, onla uyuşan kanalları listeler. \n" +"Eğer nickname belirtilmişse, o kullanıcının bulunduğu \n" +"kanalları listeler. Eğer SECRET belirtilmişse, sadece model\n" +"le uyuşan ve +s veya +p modunda olan kanallar listelenir.\n" +"\n" +"Servis adminlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/ns_alist.cpp:127 +msgid "" +"Lists all channels you have access on.\n" +" \n" +"Channels that have the NOEXPIRE option set will be\n" +"prefixed by an exclamation mark. The nickname parameter is\n" +"limited to Services Operators" +msgstr "" + +#: modules/commands/ns_group.cpp:299 +#, fuzzy +msgid "Lists all nicknames in your group" +msgstr "Grubunuzdaki nicklerin listesi:" + +#: modules/commands/cs_list.cpp:20 +#, fuzzy +msgid "Lists all registered channels matching the given pattern" +msgstr "" +" LIST Lists all registered channels matching the given pattern" + +#: modules/commands/cs_list.cpp:137 +#, fuzzy +msgid "" +"Lists all registered channels matching the given pattern.\n" +"Channels with the PRIVATE option set will only be\n" +"displayed to Services Operators with the proper access.\n" +"Channels with the NOEXPIRE option set will have\n" +"a ! prefixed to the channel for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range, channel names\n" +"are to be written without '#'.\n" +" \n" +"If the SUSPENDED or NOEXPIRE options are given, only channels\n" +"which, respectively, are SUSPENDED or have the NOEXPIRE\n" +"flag set will be displayed. If multiple options are given,\n" +"all channels matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *anope*\n" +" Lists all registered channels with anope in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered channels which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered channels within the given range (51-100)." +msgstr "" +"Kullanımı: LIST model [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]\n" +"\n" +"Belirtilen modele uyuşan tüm kayıtlı nickleri nick!user@host \n" +"formatında listeler. PRIVATE özelliğ aktif olan kullanıcılar \n" +"sadece servis adminleri tarafından görüntülenir. NOEXPIRE \n" +"ayarı olan nicklerde servis adminleri için asılı bir ! bulunur.\n" +"\n" +"If the FORBIDDEN, SUSPENDED, NOEXPIRE or UNCONFIRMED options are given, " +"only\n" +"nicks which, respectively, are FORBIDDEN, SUSPENDED, UNCONFIRMED or have " +"the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"These options are limited to Services Operators. \n" +"\n" +"Örnekler:\n" +"\n" +" LIST *!aliuser@ixir.com\n" +" identi aliuser@ixir.com olan tüm kayıtlı nickler \n" +" listelenir.\n" +"\n" +" LIST *Bot*!*@*\n" +" İsimlerinde Bot yazan tüm kayıtlı nickler listelenir\n" +" (küçük büyük harf hassasiyeti vardır).\n" +"\n" +" LIST * NOEXPIRE\n" +" Zaman asimi olmayan tüm kayıtlı nickler listelenir." + +#: modules/commands/ns_list.cpp:139 +#, fuzzy +msgid "" +"Lists all registered nicknames which match the given\n" +"pattern, in nick!user@host format. Nicks with the PRIVATE\n" +"option set will only be displayed to Services Operators with the\n" +"proper access. Nicks with the NOEXPIRE option set will have\n" +"a ! prefixed to the nickname for Services Operators to see.\n" +" \n" +"Note that a preceding '#' specifies a range.\n" +" \n" +"If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" +"nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"Note that these options are limited to Services Operators.\n" +" \n" +"Examples:\n" +" \n" +" LIST *!joeuser@foo.com\n" +" Lists all registered nicks owned by joeuser@foo.com.\n" +" \n" +" LIST *Bot*!*@*\n" +" Lists all registered nicks with Bot in their\n" +" names (case insensitive).\n" +" \n" +" LIST * NOEXPIRE\n" +" Lists all registered nicks which have been set to not expire.\n" +" \n" +" LIST #51-100\n" +" Lists all registered nicks within the given range (51-100)." +msgstr "" +"Kullanımı: LIST model [FORBIDDEN] [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]\n" +"\n" +"Belirtilen modele uyuşan tüm kayıtlı nickleri nick!user@host \n" +"formatında listeler. PRIVATE özelliğ aktif olan kullanıcılar \n" +"sadece servis adminleri tarafından görüntülenir. NOEXPIRE \n" +"ayarı olan nicklerde servis adminleri için asılı bir ! bulunur.\n" +"\n" +"If the FORBIDDEN, SUSPENDED, NOEXPIRE or UNCONFIRMED options are given, " +"only\n" +"nicks which, respectively, are FORBIDDEN, SUSPENDED, UNCONFIRMED or have " +"the\n" +"NOEXPIRE flag set will be displayed. If multiple options are\n" +"given, all nicks matching at least one option will be displayed.\n" +"These options are limited to Services Operators. \n" +"\n" +"Örnekler:\n" +"\n" +" LIST *!aliuser@ixir.com\n" +" identi aliuser@ixir.com olan tüm kayıtlı nickler \n" +" listelenir.\n" +"\n" +" LIST *Bot*!*@*\n" +" İsimlerinde Bot yazan tüm kayıtlı nickler listelenir\n" +" (küçük büyük harf hassasiyeti vardır).\n" +"\n" +" LIST * NOEXPIRE\n" +" Zaman asimi olmayan tüm kayıtlı nickler listelenir." + +#: modules/commands/os_list.cpp:132 +#, fuzzy +msgid "Lists all user records" +msgstr " USERLIST Tüm kullanıcı kayıtlarını listeler" + +#: modules/commands/os_list.cpp:243 +#, fuzzy +msgid "" +"Lists all users currently online on the IRC network, whether their\n" +"nick is registered or not.\n" +" \n" +"If pattern is given, lists only users that match it (it must be in\n" +"the format nick!user@host[#realname]). If channel is given, lists\n" +"only users that are on the given channel. If INVISIBLE is specified, only " +"users\n" +"with the +i flag will be listed." +msgstr "" +"Kullanımı: USERLIST [{model | kanaladı} [INVISIBLE]]\n" +"\n" +"Networkte o an bulunan tüm kullanıcıları kayıtlı olsun olmasın \n" +"listeler.\n" +"\n" +"Eğer model belirtilmişse, onla uyuşan kullanıcıları listeler\n" +"(nick!user@host formatında olmalıdır). Eğer kanaladı \n" +"belirtilmişse, sadece o kanalda bulunan kullanıcıları listeler.\n" +"Eğer INVISIBLE belirtilmişse, sadece +i modundaki kullanıcılar \n" +"listelenir.\n" +"\n" +"Servis adminlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/ms_list.cpp:142 +#, fuzzy +msgid "" +"Lists any memos you currently have. With NEW, lists only\n" +"new (unread) memos. Unread memos are marked with a \"*\"\n" +"to the left of the memo number. You can also specify a list\n" +"of numbers, as in the example below:\n" +" LIST 2-5,7-9\n" +" Lists memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Kullanımı: LIST [kanaladı] [liste | NEW]\n" +"\n" +"Mevcut mesajlarınızı listeler. NEW parametresi sadece yeni\n" +"okunmamış mesajları listeler. Okunmamış mesajlar mesaj \n" +"numarasının solunda \"*\" ile işaretlidir. Aşağıdaki örnekte\n" +"olduğu gibi belirli numaralarıda listeleyebilirsiniz:\n" +"\n" +" LIST 2-5,7-9\n" +" 2'den 5'e ve 7'den 9'a kadar olan mesajları listeler." + +#: modules/commands/bs_botlist.cpp:19 +#, fuzzy +msgid "Lists available bots" +msgstr "BOTLIST Mevcut botları listeler" + +#: modules/commands/os_modinfo.cpp:196 +#, fuzzy +msgid "Lists currently loaded modules." +msgstr " MODLIST List loaded modules" + +#: modules/commands/cs_info.cpp:19 +#, fuzzy +msgid "Lists information about the specified registered channel" +msgstr " INFO Lists information about the named registered channel" + +#: modules/commands/cs_info.cpp:76 +#, fuzzy +msgid "" +"Lists information about the specified registered channel,\n" +"including its founder, time of registration, last\n" +"time used, and description. If the user issuing the\n" +"command has the appropriate access for it, then the\n" +"successor, last topic set, settings and expiration\n" +"time will also be displayed when applicable." +msgstr "" +"Kullanımı: INFO kanaladı\n" +"\n" +"Belirtilen kayıtlı kanalla ilgili bilgiler sunar. Bu \n" +"bilgilerin içeriğinde kanalın founderı, kayıt zamanı,\n" +"son kullanıldığı zaman, açıklaması, ve varsa mod kilidi\n" +"bulunur. Eğer kanalın founderı olarak kendinizi \n" +"tanıtmışsanız ve ALL parametresini belirtmişseniz\n" +"giriş mesajı ve successor hakkındada bilgi alabilirsiniz.\n" +"Varsayilan olarak, ALL seçenegini founderlar kullanabilir." + +#: modules/commands/os_module.cpp:19 +#, fuzzy +msgid "Load a module" +msgstr " MODLOAD Load a module" + +#: modules/commands/cs_register.cpp:39 +msgid "Local channels cannot be registered." +msgstr "Local kanallar kayıt edilemezler." + +#: modules/commands/cs_log.cpp:142 +#, fuzzy, c-format +msgid "Log list for %s:" +msgstr "%s nickinin access listesi:" + +#: modules/commands/cs_log.cpp:227 +#, c-format +msgid "Logging changed for command %s on %s, now using log method %s%s%s." +msgstr "" + +#: modules/commands/cs_log.cpp:220 +#, c-format +msgid "Logging for command %s on %s with log method %s%s%s has been removed." +msgstr "" + +#: modules/commands/cs_log.cpp:248 +#, c-format +msgid "Logging is now active for command %s on %s, using log method %s%s%s." +msgstr "" + +#: modules/commands/os_login.cpp:60 +#, c-format +msgid "Login to %s" +msgstr "" + +#: modules/commands/os_news.cpp:36 +#, c-format +msgid "Logon news item #%d deleted." +msgstr "Bağlantı haberleri maddesi #%d silindi." + +#: modules/commands/os_news.cpp:35 +#, fuzzy, c-format +msgid "Logon news item #%s not found!" +msgstr "Bağlantı haberleri maddesi #%d bulunamadı!" + +#: modules/commands/os_news.cpp:32 +msgid "Logon news items:" +msgstr "Bağlantı haberleri:" + +#: modules/commands/os_login.cpp:102 +#, fuzzy, c-format +msgid "Logout from %s" +msgstr "%s nickinin access listesi:" + +#: modules/commands/os_login.cpp:52 +#, c-format +msgid "" +"Logs you in to %s so you gain Services Operator privileges.\n" +"This command may be unnecessary if your oper block is\n" +"configured without a password." +msgstr "" + +#: modules/commands/os_login.cpp:94 +#, c-format +msgid "" +"Logs you out from %s so you lose Services Operator privileges.\n" +"This command is only useful if your oper block is configured\n" +"with a password." +msgstr "" + +#: modules/commands/cs_seen.cpp:213 +#, c-format +msgid "Looking for yourself, eh %s?" +msgstr "" + +#: modules/commands/cs_mode.cpp:773 +#, c-format +msgid "" +"Mainly controls mode locks and mode access (which is different from channel " +"access)\n" +"on a channel.\n" +" \n" +"The %s LOCK command allows you to add, delete, and view mode locks on a " +"channel.\n" +"If a mode is locked on or off, services will not allow that mode to be " +"changed. The SET\n" +"command will clear all existing mode locks and set the new one given, while " +"ADD and DEL\n" +"modify the existing mode lock.\n" +"Example:\n" +" MODE #channel LOCK ADD +bmnt *!*@*aol*\n" +" \n" +"The %s SET command allows you to set modes through services. Wildcards * " +"and ? may\n" +"be given as parameters for list and status modes.\n" +"Example:\n" +" MODE #channel SET +v *\n" +" Sets voice status to all users in the channel.\n" +" \n" +" MODE #channel SET -b ~c:*\n" +" Clears all extended bans that start with ~c:\n" +" \n" +"The %s CLEAR command is an easy way to clear modes on a channel. what may " +"be\n" +"any mode name. Examples include bans, excepts, inviteoverrides, ops, " +"halfops, and voices. If what\n" +"is not given then all basic modes are removed." +msgstr "" + +#: modules/commands/cs_akick.cpp:434 +#, fuzzy +msgid "Maintain the AutoKick list" +msgstr " AKICK Autokick listesini düzenler" + +#: modules/commands/bs_bot.cpp:269 +#, fuzzy +msgid "Maintains network bot list" +msgstr "BOT Networkün bot listesini düzenler" + +#: modules/commands/cs_xop.cpp:522 +#, c-format +msgid "" +"Maintains the %s list for a channel. Users who match an access entry\n" +"on the %s list receive the following privileges:\n" +" " +msgstr "" + +#: modules/commands/cs_akick.cpp:493 +#, c-format +msgid "" +"Maintains the AutoKick list for a channel. If a user\n" +"on the AutoKick list attempts to join the channel,\n" +"%s will ban that user from the channel, then kick\n" +"the user.\n" +" \n" +"The AKICK ADD command adds the given nick or usermask\n" +"to the AutoKick list. If a reason is given with\n" +"the command, that reason will be used when the user is\n" +"kicked; if not, the default reason is \"User has been\n" +"banned from the channel\".\n" +"When akicking a registered nick the %s account\n" +"will be added to the akick list instead of the mask.\n" +"All users within that nickgroup will then be akicked.\n" +msgstr "" + +#: modules/commands/cs_access.cpp:568 +#, c-format +msgid "" +"Maintains the access list for a channel. The access\n" +"list specifies which users are allowed chanop status or\n" +"access to %s commands on the channel. Different\n" +"user levels allow for access to different subsets of\n" +"privileges. Any registered user not on the access list has\n" +"a user level of 0, and any unregistered user has a user level\n" +"of -1." +msgstr "" + +#: modules/commands/bs_badwords.cpp:424 +#, fuzzy, c-format +msgid "" +"Maintains the bad words list for a channel. The bad\n" +"words list determines which words are to be kicked\n" +"when the bad words kicker is enabled. For more information,\n" +"type %s%s HELP KICK %s.\n" +" \n" +"The ADD command adds the given word to the\n" +"bad words list. If SINGLE is specified, a kick will be\n" +"done only if a user says the entire word. If START is\n" +"specified, a kick will be done if a user says a word\n" +"that starts with word. If END is specified, a kick\n" +"will be done if a user says a word that ends with\n" +"word. If you don't specify anything, a kick will\n" +"be issued every time word is said by a user.\n" +" \n" +msgstr "" +"Kullanımı: BADWORDS kanaladı ADD kelime [SINGLE | START | END]\n" +" BADWORDS kanaladı DEL {kelime | kayıt-no | liste}\n" +" BADWORDS kanaladı LIST [mask | liste]\n" +" BADWORDS kanaladı CLEAR\n" +"\n" +"Bir kanal için küfür listesi düzenler. Küfür listesi\n" +"küfürde atma aktifleştirildiği zaman hangi kelimelerde\n" +"atılacağını belirler. Daha fazla bilgi için \n" +"/msg %s HELP KICK BADWORDS yazın.\n" +"\n" +"BADWORDS ADD komutu belirtilen kelimeyi küfür listesine\n" +"ekler. Eğer SINGLE parametresi belirtilmişse, atma işlemi\n" +"kullanıcı o kelimenin tamamını söylerse yapılır. Eğer START\n" +"parametresi belirtilmişse, kullanıcı o kelimeyle başlayan \n" +"birşey söylediğinde atılır. Eğer END parametresi belirtilmişse\n" +"kullanıcı o kelimeyle biten birşey söylediğinde atılır.\n" +"Eğer bir parametre kullanmazsanız, atma işlemi kullanıcı o \n" +"kelimeyi her kullandığında yapılır.\n" +"\n" +"BADWORDS DEL komutu belirtilen kelimeyi küfür listesinden \n" +"siler. Eğer kayıt numarası listesi verilirse, o kelimeler\n" +"silinir. (LIST için aşağıdaki örneği inceleyin) \n" +"\n" +"BADWORDS LIST komutu küfür listesini görüntüler. Eğer\n" +"bir küfürün bir kısmı belirtilmişse, o kısma uyan küfürler\n" +"listelenir. Eğer bir kayıt numarası listesi belirtilmişse,\n" +"sadece o küfürler listelenir; örneğin:\n" +"\n" +" BADWORDS #kanaladı LIST 2-5,7-9\n" +" 2'den 5'e ve 7'den 9'a kadar olan küfürler \n" +" listelenir.\n" +" \n" +"BADWORDS CLEAR komutu tüm küfür listesini temizler." + +#: modules/commands/bs_badwords.cpp:370 +#, fuzzy +msgid "Maintains the bad words list" +msgstr "BADWORDS Küfür listesi oluşturur" + +#: modules/commands/bs_control.cpp:79 +#, fuzzy +msgid "Makes the bot do the equivalent of a \"/me\" command" +msgstr "" +"ACT Makes the bot do the equivalent of a \"/me\" command" + +#: modules/commands/bs_control.cpp:127 +#, fuzzy +msgid "" +"Makes the bot do the equivalent of a \"/me\" command\n" +"on the specified channel using the specified text." +msgstr "" +"Kullanımı: ACT kanaladı yazı\n" +"\n" +"Botun belirtilen yazıyla belirtilen kanalda \"/me\" komutunun \n" +"yaptığını kendi üzerinde yapmasını sağlar." + +#: modules/commands/bs_control.cpp:19 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel" +msgstr "" +"SAY Makes the bot say the given text on the given channel" + +#: modules/commands/bs_control.cpp:69 +#, fuzzy +msgid "Makes the bot say the specified text on the specified channel." +msgstr "" +"SAY Makes the bot say the given text on the given channel" + +#: modules/commands/greet.cpp:157 +#, fuzzy +msgid "" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary\n" +"access on it." +msgstr "" +"Syntax: SASET nickname GREET message\n" +"\n" +"Makes the given message the greet of the nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that the user has the necessary \n" +"access on it." + +#: modules/commands/greet.cpp:131 +#, fuzzy +msgid "" +"Makes the given message the greet of your nickname, that\n" +"will be displayed when joining a channel that has GREET\n" +"option enabled, provided that you have the necessary\n" +"access on it." +msgstr "" +"Kullanımı: SET GREET mesaj\n" +"\n" +"Yazdığınız mesajı nickinizin karşılama mesajı olarak\n" +"belirler, bu mesaj GREET özelliği aktif bir kanala \n" +"girdiğinizde gönderilir, kanaldaki access seviyenize\n" +"bağlıdır." + +#: modules/commands/os_dns.cpp:660 +#, fuzzy +msgid "Manage DNS zones for this network" +msgstr "E-mail adresini bu networkte silemezsiniz." + +#: modules/commands/cs_entrymsg.cpp:193 +#, fuzzy +msgid "Manage the channel's entry messages" +msgstr " PERSIST Set the channel as permanent" + +#: modules/commands/ms_ignore.cpp:19 +#, fuzzy +msgid "Manage the memo ignore list" +msgstr " IGNORE Modify the Services ignore list" + +#: modules/commands/ns_ajoin.cpp:230 +#, fuzzy +msgid "Manage your auto join list" +msgstr " AKICK Autokick listesini düzenler" + +#: modules/commands/os_sxline.cpp:233 +#, fuzzy, c-format +msgid "Manipulate the %s list" +msgstr " AKILL AKILL listesini düzenler" + +#: modules/commands/os_akill.cpp:385 +#, fuzzy +msgid "Manipulate the AKILL list" +msgstr " AKILL AKILL listesini düzenler" + +#: modules/commands/os_defcon.cpp:176 +#, fuzzy +msgid "Manipulate the DefCon system" +msgstr " DEFCON Manipulate the DefCon system" + +#: modules/commands/cs_topic.cpp:149 +#, fuzzy +msgid "Manipulate the topic of the specified channel" +msgstr " TOPIC Manipulate the topic of the specified channel" + +#: modules/commands/bs_botlist.cpp:27 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/os_ignore.cpp:266 +#: modules/commands/os_sxline.cpp:193 modules/commands/os_sxline.cpp:201 +#: modules/commands/os_forbid.cpp:358 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/ms_ignore.cpp:86 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_list.cpp:153 modules/commands/bs_info.cpp:55 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +msgid "Mask" +msgstr "" + +#: modules/commands/ns_access.cpp:39 +#, fuzzy, c-format +msgid "Mask %s already present on %s's access list." +msgstr "%s access listenizde zaten var." + +#: include/language.h:67 +msgid "Mask must be in the form user@host." +msgstr "" + +#: modules/commands/cs_access.cpp:166 modules/commands/cs_flags.cpp:120 +#: modules/commands/cs_xop.cpp:162 +#, fuzzy +msgid "Masks and unregistered users may not be on access lists." +msgstr "%s access listenizde zaten var." + +#: modules/commands/ns_getemail.cpp:23 +#, fuzzy +msgid "Matches and returns all users that registered using given email" +msgstr "" +" GETEMAIL Matches and returns all users that registered using given " +"email" + +#: modules/commands/os_logsearch.cpp:148 +#, fuzzy, c-format +msgid "Matches for %s:" +msgstr " Mod kilidi: %s" + +#: modules/commands/os_stats.cpp:139 +#, c-format +msgid "Maximum users: %d (%s)" +msgstr "Maximum kullanıcı sayısı: %d (%s)" + +#: modules/commands/ms_read.cpp:84 modules/commands/ms_read.cpp:86 +#, fuzzy, c-format +msgid "Memo %d from %s (%s)." +msgstr " Mod kilidi: %s" + +#: modules/commands/ms_del.cpp:33 modules/commands/ms_del.cpp:101 +#, c-format +msgid "Memo %d has been deleted." +msgstr "%d nolu mesaj silindi." + +#: modules/commands/ms_ignore.cpp:82 +#, fuzzy +msgid "Memo ignore list is empty." +msgstr "Ignore listesi boş." + +#: modules/commands/ms_set.cpp:199 +#, c-format +msgid "Memo limit disabled for %s." +msgstr "%s nickinin mesaj limiti kapatıldı." + +#: modules/commands/ms_set.cpp:185 +#, c-format +msgid "Memo limit for %s set to %d." +msgstr "%s nickinin mesaj limiti %d olarak ayarlandı." + +#: modules/commands/ms_set.cpp:192 +#, c-format +msgid "Memo limit for %s set to 0." +msgstr "%s nickinin mesaj limiti 0 olarak ayarlandı." + +#: modules/commands/ms_rsend.cpp:63 modules/commands/ms_send.cpp:51 +#, c-format +msgid "Memo sent to %s." +msgstr "%s nickine mesajınız gönderildi." + +#: modules/commands/ms_list.cpp:131 +#, fuzzy, c-format +msgid "Memos for %s:" +msgstr " Mod kilidi: %s" + +#: modules/commands/cs_entrymsg.cpp:116 +#, fuzzy +msgid "Message" +msgstr "GLOBAL mesaj" + +#: modules/commands/ns_set.cpp:1313 +msgid "Message mode" +msgstr "Message mode" + +#: modules/commands/cs_log.cpp:127 +msgid "Method" +msgstr "" + +#: modules/commands/cs_mode.cpp:329 modules/commands/cs_mode.cpp:420 +#, c-format +msgid "Missing parameter for mode %c." +msgstr "" + +#: modules/commands/cs_mode.cpp:449 +msgid "Mode" +msgstr "" + +#: modules/commands/cs_mode.cpp:718 +#, fuzzy, c-format +msgid "Mode %s is a virtual mode and can't be cleared." +msgstr "Nick %s is an illegal nickname and cannot be used." + +#: modules/commands/cs_mode.cpp:712 +#, fuzzy, c-format +msgid "Mode %s is not a status or list mode." +msgstr "%s not found on ignore list." + +#: modules/commands/cs_mode.cpp:1065 +#, fuzzy +msgid "Mode lock" +msgstr " Mod kilidi: %s" + +#: modules/commands/cs_mode.cpp:466 +#, fuzzy, c-format +msgid "Mode locks for %s:" +msgstr " Mod kilidi: %s" + +#: modules/commands/os_list.cpp:43 +msgid "Modes" +msgstr "" + +#: modules/commands/os_mode.cpp:44 +#, c-format +msgid "Modes cleared on %s and the channel destroyed." +msgstr "" + +#: modules/commands/ns_access.cpp:166 +#, fuzzy, c-format +msgid "" +"Modifies or displays the access list for your nick. This\n" +"is the list of addresses which will be automatically\n" +"recognized by %s as allowed to use the nick. If\n" +"you want to use the nick from a different address, you\n" +"need to send an IDENTIFY command to make %s\n" +"recognize you. Services Operators may provide a nick\n" +"to modify other users' access lists.\n" +" \n" +"Examples:\n" +" \n" +" ACCESS ADD anyone@*.bepeg.com\n" +" Allows access to user anyone from any machine in\n" +" the bepeg.com domain.\n" +" \n" +" ACCESS DEL anyone@*.bepeg.com\n" +" Reverses the previous command.\n" +" \n" +" ACCESS LIST\n" +" Displays the current access list." +msgstr "" +"Kullanımı: ACCESS ADD mask\n" +" ACCESS DEL mask\n" +" ACCESS LIST\n" +"\n" +"Nickinizin access litesini görüntüler ve değişiklikler \n" +"yapmanızı sağlar. Bu listede belirtilen adresler %s \n" +"tarafından nickinizi kullanabilmek için otomatik olarak \n" +"tanınacak adreslerdir. (böylece identify komutunu \n" +"kullanmanıza gerek kalmaz.) Eğer belirtilenden farklı bir \n" +"adresle bağlanmışsanız %s 'ün sizi tanıması için \n" +"IDENTIFY komutunu kullanmanız gerekir.\n" +"\n" +"Örnekler:\n" +"\n" +" ACCESS ADD birisi@*.ixir.com\n" +" Kullanıcı birisi'ne ixir.com \n" +" domaininden herhangi bir makineden \n" +" erişim sağlar.\n" +"\n" +" ACCESS DEL birisi@*.ixir.com\n" +" Önceki komutun tersini yapar(siler).\n" +"\n" +" ACCESS LIST\n" +" Mevcut access listesini görüntüler." + +#: modules/commands/ns_cert.cpp:319 +msgid "" +"Modifies or displays the certificate list for your nick.\n" +"If you connect to IRC and provide a client certificate with a\n" +"matching fingerprint in the cert list, you will be\n" +"automatically identified to services. Services Operators\n" +"may provide a nick to modify other users' certificate lists.\n" +" \n" +msgstr "" + +#: modules/commands/os_ignore.cpp:341 +#, fuzzy +msgid "Modify the Services ignore list" +msgstr " IGNORE Modify the Services ignore list" + +#: modules/commands/cs_xop.cpp:489 +#, fuzzy, c-format +msgid "Modify the list of %s users" +msgstr " AOP AOP listesini düzenler" + +#: modules/commands/ns_access.cpp:101 +#, fuzzy +msgid "Modify the list of authorized addresses" +msgstr " ACCESS İzinli adreslerin listesini düzenler" + +#: modules/commands/cs_access.cpp:498 modules/commands/cs_flags.cpp:373 +#, fuzzy +msgid "Modify the list of privileged users" +msgstr " ACCESS Ayrıcalıklı kullanıcıları belirler değiştirir" + +#: modules/commands/ns_cert.cpp:257 +#, fuzzy +msgid "Modify the nickname client certificate list" +msgstr " IGNORE Modify the Services ignore list" + +#: modules/commands/os_session.cpp:522 +#, fuzzy +msgid "Modify the session-limit exception list" +msgstr " EXCEPTION Session-limit exception listesini düzenler" + +#: modules/commands/os_module.cpp:34 +#, c-format +msgid "Module %s is already loaded." +msgstr "Module %s is already loaded." + +#: modules/commands/os_module.cpp:67 modules/commands/os_module.cpp:139 +#, c-format +msgid "Module %s isn't loaded." +msgstr "Module %s isn't loaded." + +#: modules/commands/os_module.cpp:31 +#, fuzzy, c-format +msgid "Module %s loaded." +msgstr "Module %s loaded" + +#: modules/commands/os_module.cpp:98 +#, fuzzy, c-format +msgid "Module %s reloaded." +msgstr "Module %s loaded" + +#: modules/commands/os_module.cpp:156 +#, fuzzy, c-format +msgid "Module %s unloaded." +msgstr "Module %s unloaded" + +#: modules/commands/os_config.cpp:88 +#, fuzzy +msgid "Module Name" +msgstr "Module %s loaded" + +#: modules/commands/os_config.cpp:112 +msgid "Module settings:" +msgstr "" + +#: modules/commands/os_modinfo.cpp:32 +#, fuzzy, c-format +msgid "Module: %s Version: %s Author: %s Loaded: %s" +msgstr "Module: %s Version: %s Author: %s loaded: %s" + +#: modules/commands/os_modinfo.cpp:183 +#, c-format +msgid "Module: %s [%s] [%s]" +msgstr "Module: %s [%s] [%s]" + +#: modules/commands/cs_access.cpp:697 modules/commands/cs_access.cpp:799 +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +#: modules/commands/cs_list.cpp:75 modules/commands/os_list.cpp:43 +#: modules/commands/os_list.cpp:153 +msgid "Name" +msgstr "" + +#: modules/commands/os_oper.cpp:153 +msgid "Name Type" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:146 +#, fuzzy, c-format +msgid "Network stats for %s:" +msgstr "%s nickinin access listesi:" + +#: modules/commands/os_forbid.cpp:384 +msgid "Never" +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/bs_botlist.cpp:27 +#: modules/commands/hs_request.cpp:305 modules/commands/ns_list.cpp:75 +#: modules/commands/ns_group.cpp:327 +#, fuzzy +msgid "Nick" +msgstr "INFO nick" + +#: modules/commands/ns_register.cpp:42 +#, fuzzy, c-format +msgid "Nick %s has been confirmed." +msgstr "%s nickinin kaydı silindi (dropped)." + +#: modules/commands/os_oper.cpp:95 +#, fuzzy, c-format +msgid "Nick %s is already an operator." +msgstr "%s nicki zaten kayıtlı!" + +#: modules/commands/ns_register.cpp:36 +#, fuzzy, c-format +msgid "Nick %s is already confirmed." +msgstr "%s nicki zaten kayıtlı!" + +#: modules/commands/os_svs.cpp:46 +#, c-format +msgid "Nick %s is an illegal nickname and cannot be used." +msgstr "Nick %s is an illegal nickname and cannot be used." + +#: modules/commands/bs_bot.cpp:81 modules/commands/bs_bot.cpp:181 +#: modules/commands/os_svs.cpp:54 +#, c-format +msgid "Nick %s is currently in use." +msgstr "Nick %s is currently in use." + +#: modules/commands/os_forbid.cpp:512 +#, fuzzy, c-format +msgid "Nick %s is forbidden by %s: %s" +msgstr "Nick %s is currently in use." + +#: modules/commands/os_forbid.cpp:514 +#, fuzzy, c-format +msgid "Nick %s is forbidden." +msgstr "%s nicki zaten serbest." + +#: modules/commands/os_oper.cpp:134 +#, fuzzy, c-format +msgid "Nick %s is not a Services Operator." +msgstr "%s is a services operator of type %s." + +#: modules/commands/ns_info.cpp:34 +#, c-format +msgid "Nick %s is part of this Network's Services." +msgstr "Nick %s is part of this Network's Services." + +#: include/language.h:79 +#, fuzzy, c-format +msgid "Nick %s isn't currently in use." +msgstr "Nick %s is currently in use." + +#: include/language.h:78 +#, fuzzy, c-format +msgid "Nick %s isn't registered." +msgstr "Nickname %s registered." + +#: modules/commands/os_svs.cpp:39 +#, c-format +msgid "Nick %s was truncated to %d characters." +msgstr "Nick %s was truncated to %d characters." + +#: modules/commands/ns_set.cpp:1135 +#, c-format +msgid "Nick %s will expire." +msgstr "Nick %s will expire." + +#: modules/commands/ns_set.cpp:1129 +#, c-format +msgid "Nick %s will not expire." +msgstr "Nick %s will not expire." + +#: modules/commands/ms_check.cpp:60 +#, c-format +msgid "Nick %s doesn't have a memo from you." +msgstr "Nick %s doesn't have a memo from you." + +#: modules/commands/ns_logout.cpp:48 +#, c-format +msgid "Nick %s has been logged out." +msgstr "%s nickinin çıkışı yapıldı." + +#: modules/commands/ns_group.cpp:272 +#, c-format +msgid "Nick %s has been ungrouped from %s." +msgstr "Nick %s has been ungrouped from %s." + +#: include/language.h:81 +#, fuzzy, c-format +msgid "Nick %s is currently suspended." +msgstr "Nick %s is now suspended." + +#: modules/commands/ns_group.cpp:250 +#, fuzzy, c-format +msgid "Nick %s is not in your group." +msgstr "The nick %s is not in your group." + +#: modules/commands/ns_suspend.cpp:180 +#, fuzzy, c-format +msgid "Nick %s is not suspended." +msgstr "Nick %s is now suspended." + +#: modules/commands/ns_suspend.cpp:190 +#, c-format +msgid "Nick %s is now released." +msgstr "Nick %s is now released." + +#: modules/commands/ns_suspend.cpp:138 +#, c-format +msgid "Nick %s is now suspended." +msgstr "Nick %s is now suspended." + +#: modules/commands/cs_seen.cpp:275 +#, c-format +msgid "Nick too long, max length is %u characters." +msgstr "" + +#: modules/commands/ns_drop.cpp:53 +#, c-format +msgid "Nickname %s has been dropped." +msgstr "%s nickinin kaydı silindi (dropped)." + +#: include/language.h:97 +#, fuzzy, c-format +msgid "Nickname %s is already registered!" +msgstr "%s kanalı zaten kayıtlı!" + +#: include/language.h:96 +#, fuzzy, c-format +msgid "Nickname %s may not be registered." +msgstr "%s kanalı kayıt edilemez." + +#: modules/commands/ns_register.cpp:226 +#, fuzzy, c-format +msgid "Nickname %s registered under your user@host-mask: %s" +msgstr "%s nicki sizin adınıza kayıt edildi: %s" + +#: modules/commands/ns_register.cpp:228 +#, fuzzy, c-format +msgid "Nickname %s registered." +msgstr "Nickname %s registered." + +#: modules/commands/cs_set.cpp:1307 +#, fuzzy +msgid "No auto-op" +msgstr "Auto-op" + +#: modules/commands/bs_assign.cpp:252 +msgid "No bot" +msgstr "Bot yok" + +#: modules/commands/cs_set.cpp:1303 modules/commands/ns_set.cpp:1317 +#, fuzzy +msgid "No expire" +msgstr "zaman aşımı yok" + +#: modules/commands/help.cpp:184 +#, c-format +msgid "No help available for %s." +msgstr "%s hakkında yardım bulunamadı." + +#: modules/commands/os_modinfo.cpp:61 +#, fuzzy, c-format +msgid "No information about module %s is available." +msgstr "No information about module %s is available" + +#: modules/commands/cs_enforce.cpp:177 +#, fuzzy, c-format +msgid "No limit is set on %s." +msgstr "%s nickinin mesaj limiti %d olarak ayarlandı." + +#: modules/commands/os_news.cpp:37 +msgid "No logon news items to delete!" +msgstr "Silebileceğiniz bağlantı haberleri maddesi yok!" + +#: modules/commands/os_logsearch.cpp:133 +#, fuzzy, c-format +msgid "No matches for %s found." +msgstr "No Emails listed for %s." + +#: modules/commands/cs_xop.cpp:294 +#, fuzzy, c-format +msgid "No matching entries on %s %s list." +msgstr "%s kanali AOP listesinde uyusan kayit bulunamadi." + +#: modules/commands/cs_access.cpp:269 modules/commands/cs_access.cpp:433 +#: modules/commands/cs_flags.cpp:335 modules/commands/cs_xop.cpp:428 +#, c-format +msgid "No matching entries on %s access list." +msgstr "Uyuşan kayıt %s kanalının access listesinde yok." + +#: modules/commands/cs_akick.cpp:224 modules/commands/cs_akick.cpp:368 +#, c-format +msgid "No matching entries on %s autokick list." +msgstr "Uyuşan kayıt %s kanalının akick listesinde bulunamadı." + +#: modules/commands/bs_badwords.cpp:166 modules/commands/bs_badwords.cpp:246 +#, c-format +msgid "No matching entries on %s bad words list." +msgstr "Uyuşan kayıt %s kanalının küfür listesinde bulunamadı." + +#: modules/commands/os_session.cpp:145 modules/commands/os_session.cpp:490 +msgid "No matching entries on session-limit exception list." +msgstr "session-limit exception listesinde uyuşan kayıt bulunamadı." + +#: modules/commands/os_sxline.cpp:28 modules/commands/os_sxline.cpp:177 +#, fuzzy, c-format +msgid "No matching entries on the %s list." +msgstr "%s kanali AOP listesinde uyusan kayit bulunamadi." + +#: modules/commands/os_akill.cpp:29 modules/commands/os_akill.cpp:320 +msgid "No matching entries on the AKILL list." +msgstr "Uyuşan kayıt AKILL listesinde bulunamadı." + +#: modules/commands/ms_cancel.cpp:77 +msgid "No memo was cancelable." +msgstr "İptal edilecek mesaj yoktu." + +#: modules/commands/ms_read.cpp:65 +msgid "No memos to display." +msgstr "" + +#: modules/commands/os_modinfo.cpp:187 +#, fuzzy +msgid "No modules currently loaded matching that criteria." +msgstr "No modules currently loaded" + +#: modules/commands/ns_recover.cpp:55 +msgid "No one is using your nick, and services are not holding it." +msgstr "" + +#: modules/commands/os_login.cpp:30 modules/commands/os_login.cpp:77 +msgid "No oper block for your nick." +msgstr "" + +#: modules/commands/os_news.cpp:47 +msgid "No oper news items to delete!" +msgstr "Silebileceğiniz operatör haberleri maddesi yok!" + +#: modules/commands/os_news.cpp:57 +msgid "No random news items to delete!" +msgstr "Silinecek karisik haber yok!" + +#: modules/commands/hs_list.cpp:111 +msgid "No records to display." +msgstr "" + +#: modules/commands/ns_getemail.cpp:47 +#, fuzzy, c-format +msgid "No registrations matching %s were found." +msgstr "* No new nick registrations" + +#: modules/commands/hs_request.cpp:220 modules/commands/hs_request.cpp:276 +#, c-format +msgid "No request for nick %s found." +msgstr "" + +#: src/access.cpp:55 +msgid "No signed kick when SIGNKICK LEVEL is used" +msgstr "" + +#: modules/extra/stats/cs_fantasy_top.cpp:159 +#: modules/extra/stats/cs_fantasy_stats.cpp:156 +#, fuzzy, c-format +msgid "No stats for %s." +msgstr "%s nickinin access listesi:" + +#: modules/commands/os_info.cpp:201 +#, fuzzy, c-format +msgid "No such info \"%s\" on %s." +msgstr "%s has been invited to %s." + +#: modules/commands/cs_ban.cpp:219 modules/commands/cs_kick.cpp:118 +#, fuzzy, c-format +msgid "No users on %s match %s." +msgstr "Changed usermodes of %s." + +#: modules/commands/bs_assign.cpp:188 +#, fuzzy, c-format +msgid "No-bot mode is now off on channel %s." +msgstr "Bot yok modu %s kanalı için AKTİF." + +#: modules/commands/bs_assign.cpp:181 +#, fuzzy, c-format +msgid "No-bot mode is now on on channel %s." +msgstr "Bot yok modu %s kanalı için AKTİF." + +#: modules/commands/os_mode.cpp:64 +#, c-format +msgid "Non-status modes cleared on %s." +msgstr "" + +#: modules/commands/os_dns.cpp:226 modules/commands/bs_info.cpp:58 +msgid "None" +msgstr "YOK" + +#: modules/commands/cs_set.cpp:1029 +#, c-format +msgid "" +"Note, however, if the successor already has too many\n" +"channels registered (%d), they will not be able to\n" +"become the new founder and it will be as if the\n" +"channel had no successor set." +msgstr "" + +#: modules/commands/cs_mode.cpp:380 modules/commands/cs_mode.cpp:437 +msgid "Nothing to do." +msgstr "" + +#: modules/commands/hs_list.cpp:58 modules/commands/cs_access.cpp:459 +#: modules/commands/cs_access.cpp:472 modules/commands/cs_flags.cpp:301 +#: modules/commands/cs_xop.cpp:377 modules/commands/ns_alist.cpp:48 +#: modules/commands/cs_entrymsg.cpp:116 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:201 modules/commands/ms_list.cpp:64 +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_news.cpp:156 +#: modules/commands/hs_request.cpp:305 modules/commands/cs_akick.cpp:392 +#: modules/commands/cs_akick.cpp:405 modules/commands/cs_log.cpp:127 +#: modules/commands/os_session.cpp:506 modules/commands/os_session.cpp:514 +#: modules/commands/os_akill.cpp:344 modules/commands/os_akill.cpp:358 +#: modules/commands/ns_ajoin.cpp:100 +msgid "Number" +msgstr "" + +#: modules/commands/os_news.cpp:41 +msgid "OPERNEWS {ADD|DEL|LIST} [text|num]" +msgstr "OPERNEWS {ADD|DEL|LIST} [yazı|num]" + +#: modules/commands/ns_info.cpp:68 modules/commands/ns_info.cpp:72 +#, fuzzy +msgid "Online from" +msgstr " Bağlandığı adres: %s" + +#: modules/commands/os_oper.cpp:138 +#, c-format +msgid "" +"Oper %s is configured in the configuration file(s) and can not be removed by " +"this command." +msgstr "" + +#: modules/commands/os_info.cpp:268 +msgid "Oper Info" +msgstr "" + +#: modules/commands/os_info.cpp:182 modules/commands/os_info.cpp:221 +#, fuzzy, c-format +msgid "Oper info list for %s is empty." +msgstr "Access list for %s is empty." + +#: modules/commands/os_news.cpp:46 +#, c-format +msgid "Oper news item #%d deleted." +msgstr "Operatör haberleri maddesi #%d silindi." + +#: modules/commands/os_news.cpp:45 +#, fuzzy, c-format +msgid "Oper news item #%s not found!" +msgstr "Operatör haberleri maddesi #%d bulunamadı!" + +#: modules/commands/os_news.cpp:42 +msgid "Oper news items:" +msgstr "Operatör haberleri:" + +#: modules/commands/os_oper.cpp:148 +#, c-format +msgid "Oper privileges removed from %s (%s)." +msgstr "" + +#: modules/commands/os_oper.cpp:101 modules/commands/os_oper.cpp:189 +#, fuzzy, c-format +msgid "Oper type %s has not been configured." +msgstr "%s nickinin kaydı silindi (dropped)." + +#: modules/commands/os_oline.cpp:37 +#, c-format +msgid "Operflags %s have been added for %s." +msgstr "An O:Line with the flags %s has been added for %s." + +#: modules/commands/os_oline.cpp:43 +#, fuzzy, c-format +msgid "Operflags %s have been removed from %s." +msgstr "An O:Line with the flags %s has been added for %s." + +#: modules/commands/os_oper.cpp:193 +#, c-format +msgid "Opertype %s has no allowed commands." +msgstr "" + +#: modules/commands/os_oper.cpp:215 +#, c-format +msgid "Opertype %s has no allowed privileges." +msgstr "" + +#: modules/commands/os_oper.cpp:237 +#, c-format +msgid "Opertype %s receives modes %s once identified." +msgstr "" + +#: modules/commands/bs_kick.cpp:1219 +msgid "Ops protection" +msgstr "Opları koruma" + +#: src/misc.cpp:258 modules/commands/bs_info.cpp:58 +#, fuzzy +msgid "Options" +msgstr " Ayarlar : %s" + +#: modules/commands/os_dns.cpp:668 +#, fuzzy +msgid "POOL server.name" +msgstr "NOOP {SET|REVOKE} server" + +#: modules/commands/cs_mode.cpp:449 +msgid "Param" +msgstr "" + +#: modules/commands/ns_identify.cpp:38 +msgid "Password accepted - you are now recognized." +msgstr "Şifre kabul edildi." + +#: modules/commands/os_login.cpp:44 +#, fuzzy +msgid "Password accepted." +msgstr "Şifre geçersiz." + +#: include/language.h:85 +msgid "Password authentication required for that command." +msgstr "" + +#: modules/commands/ns_set.cpp:152 modules/commands/ns_set.cpp:218 +#, fuzzy, c-format +msgid "Password for %s changed to %s." +msgstr "%s için successor %s olarak değiştirildi." + +#: modules/commands/ns_set.cpp:154 modules/commands/ns_set.cpp:220 +#, fuzzy, c-format +msgid "Password for %s changed." +msgstr "%s nickinin şifresi gönderildi." + +#: modules/commands/ns_getpass.cpp:38 +#, c-format +msgid "Password for %s is %s." +msgstr "%s nickinin şifresi %s." + +#: include/language.h:71 +#, fuzzy +msgid "Password incorrect." +msgstr "Şifre geçersiz." + +#: modules/commands/ns_resetpass.cpp:39 +#, c-format +msgid "Password reset email for %s has been sent." +msgstr "Password reset email for %s has been sent." + +#: modules/commands/cs_set.cpp:1289 +msgid "Peace" +msgstr "Baris" + +#: modules/commands/cs_set.cpp:440 +#, fuzzy, c-format +msgid "Peace option for %s is now off." +msgstr "Peace option for %s is now ON." + +#: modules/commands/cs_set.cpp:434 +#, fuzzy, c-format +msgid "Peace option for %s is now on." +msgstr "Peace option for %s is now ON." + +#: modules/commands/cs_set.cpp:1301 +#, fuzzy +msgid "Persistent" +msgstr "Persistant" + +#: include/language.h:126 +msgid "Please contact an Operator to get a vHost assigned to this nick." +msgstr "" + +#: include/language.h:73 +msgid "" +"Please try again with a more obscure password. Passwords should be at least\n" +"five characters long, should not be something easily guessed\n" +"(e.g. your real name or your nick), and cannot contain the space or tab " +"characters." +msgstr "" + +#: modules/commands/os_jupe.cpp:30 +#, fuzzy +msgid "Please use a valid server name when juping." +msgstr "Please use a valid server name when juping" + +#: include/language.h:104 +msgid "Please use the symbol of # when attempting to register." +msgstr "" + +#: src/mail.cpp:78 +#, c-format +msgid "Please wait %d seconds and retry." +msgstr "Lütfen %d saniye bekleyin ve tekrar deneyin." + +#: modules/commands/hs_request.cpp:158 +#, fuzzy, c-format +msgid "Please wait %d seconds before requesting a new vHost." +msgstr "Lütfen %d saniye SEND komutunu tekrar kullanmak için bekleyin." + +#: modules/commands/ms_rsend.cpp:58 modules/commands/ms_send.cpp:57 +#, fuzzy, c-format +msgid "Please wait %d seconds before using the %s command again." +msgstr "Lütfen %d saniye SEND komutunu tekrar kullanmak için bekleyin." + +#: modules/commands/ns_group.cpp:149 +#, c-format +msgid "Please wait %d seconds before using the GROUP command again." +msgstr "GROUP komutunu tekrar kullanmadan önce lütfen %d saniye bekleyin." + +#: modules/commands/ns_register.cpp:198 +#, c-format +msgid "Please wait %d seconds before using the REGISTER command again." +msgstr "Lütfen %d saniye REGISTER komutunu tekrar kullanmak için bekleyin." + +#: modules/commands/os_dns.cpp:628 +#, c-format +msgid "Pooled %s." +msgstr "" + +#: modules/commands/os_dns.cpp:237 +msgid "Pooled/Active" +msgstr "" + +#: modules/commands/os_dns.cpp:239 +msgid "Pooled/Not Active" +msgstr "" + +#: modules/commands/bs_set.cpp:161 +msgid "Prevent a bot from being assigned by non IRC operators" +msgstr "" + +#: modules/commands/bs_assign.cpp:153 +#, fuzzy +msgid "Prevent a bot from being assigned to a channel" +msgstr "" +" SUSPEND Prevent a channel from being used preserving\n" +" channel data and settings" + +#: modules/commands/cs_suspend.cpp:58 +#, fuzzy +msgid "Prevent a channel from being used preserving channel data and settings" +msgstr "" +" SUSPEND Prevent a channel from being used preserving\n" +" channel data and settings" + +#: modules/commands/cs_set.cpp:1043 +#, fuzzy +msgid "Prevent the channel from expiring" +msgstr " NOEXPIRE Prevent the channel from expiring" + +#: modules/commands/ns_list.cpp:186 +#, fuzzy +msgid "Prevent the nickname from appearing in the LIST command" +msgstr "" +" PRIVATE Prevent the nickname from appearing in a\n" +" /msg %s LIST" + +#: modules/commands/ns_set.cpp:1104 +#, fuzzy +msgid "Prevent the nickname from expiring" +msgstr " NOEXPIRE Prevent the nickname from expiring" + +#: src/access.cpp:46 +msgid "Prevents users being kicked by Services" +msgstr "" + +#: modules/commands/ns_list.cpp:297 modules/commands/cs_list.cpp:262 +#: modules/commands/bs_info.cpp:58 +msgid "Private" +msgstr "Özel" + +#: modules/commands/bs_set.cpp:190 +#, fuzzy, c-format +msgid "Private mode of bot %s is now off." +msgstr "%s botunun özel seçenegi artik AKTIF." + +#: modules/commands/bs_set.cpp:185 +#, fuzzy, c-format +msgid "Private mode of bot %s is now on." +msgstr "%s botunun özel seçenegi artik AKTIF." + +#: modules/commands/cs_list.cpp:220 +#, fuzzy, c-format +msgid "Private option for %s is now off." +msgstr "Private option for %s is now ON." + +#: modules/commands/cs_list.cpp:214 +#, fuzzy, c-format +msgid "Private option for %s is now on." +msgstr "Private option for %s is now ON." + +#: modules/commands/ns_list.cpp:221 +#, fuzzy, c-format +msgid "Private option is now off for %s." +msgstr "Private option is now ON for %s." + +#: modules/commands/ns_list.cpp:215 +#, fuzzy, c-format +msgid "Private option is now on for %s." +msgstr "Private option is now ON for %s." + +#: modules/commands/cs_flags.cpp:281 +#, c-format +msgid "Privilege %s added to %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/cs_flags.cpp:283 +#, c-format +msgid "Privilege %s removed from %s on %s, new flags are +%s" +msgstr "" + +#: modules/commands/ns_set.cpp:1309 +msgid "Protection" +msgstr "Kill koruması" + +#: modules/commands/ns_set.cpp:721 +#, fuzzy, c-format +msgid "Protection is now off for %s." +msgstr "Protection is now ON for %s." + +#: modules/commands/ns_set.cpp:700 +#, fuzzy, c-format +msgid "Protection is now on for %s, with a reduced delay." +msgstr "Protection is now ON for %s, with a reduced delay." + +#: modules/commands/ns_set.cpp:710 +#, fuzzy, c-format +msgid "Protection is now on for %s, with no delay." +msgstr "Protection is now ON for %s, with no delay." + +#: modules/commands/ns_set.cpp:692 +#, fuzzy, c-format +msgid "Protection is now on for %s." +msgstr "Protection is now ON for %s." + +#: modules/commands/os_chankill.cpp:100 +#, fuzzy +msgid "" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire real ident@host for every nick, and\n" +"then enforces the AKILL." +msgstr "" +"Syntax: CHANKILL [+expiry] channel reason\n" +"Puts an AKILL for every nick on the specified channel. It\n" +"uses the entire and complete real ident@host for every nick,\n" +"then enforces the AKILL. " + +#: modules/commands/ns_set.cpp:1307 +#, fuzzy +msgid "Quick protection" +msgstr "Voiceları koruma" + +#: modules/commands/os_news.cpp:51 +msgid "RANDOMNEWS {ADD|DEL|LIST} [text|num]" +msgstr "RANDOMNEWS {ADD|DEL|LIST} [yazi|no]" + +#: modules/commands/cs_enforce.cpp:99 +msgid "REGONLY enforced by " +msgstr "" + +#: modules/commands/cs_enforce.cpp:68 +msgid "RESTRICTED enforced by " +msgstr "" + +#: modules/commands/os_noop.cpp:21 +#, fuzzy +msgid "REVOKE server" +msgstr "NOOP {SET|REVOKE} server" + +#: modules/commands/os_news.cpp:56 +#, c-format +msgid "Random news item #%d deleted." +msgstr "#%d numarali karisik haber silindi." + +#: modules/commands/os_news.cpp:55 +#, fuzzy, c-format +msgid "Random news item #%s not found!" +msgstr "#%d numarali karisik haber bulunamadi!" + +#: modules/commands/os_news.cpp:52 +msgid "Random news items:" +msgstr "Karisik haberler:" + +#: modules/commands/ms_read.cpp:112 +#, fuzzy +msgid "Read a memo or memos" +msgstr " READ Mesajları okumanızı sağlar" + +#: modules/commands/bs_info.cpp:56 +#, fuzzy +msgid "Real name" +msgstr " Gerçek ismi : %s" + +#: modules/commands/os_list.cpp:153 +#, fuzzy +msgid "Realname" +msgstr " Gerçek ismi : %s" + +#: modules/commands/os_ignore.cpp:266 modules/commands/os_sxline.cpp:193 +#: modules/commands/os_sxline.cpp:204 modules/commands/os_forbid.cpp:358 +#: modules/commands/cs_akick.cpp:392 modules/commands/cs_akick.cpp:405 +#: modules/commands/os_session.cpp:514 modules/commands/os_akill.cpp:344 +#: modules/commands/os_akill.cpp:361 +msgid "Reason" +msgstr "" + +#: src/xline.cpp:386 +#, fuzzy, c-format +msgid "Reason for %s updated." +msgstr "%s için successor kaldırıldı." + +#: modules/commands/ns_recover.cpp:214 +msgid "" +"Recovers your nick from another user or from services.\n" +"If services are currently holding your nick, the hold\n" +"will be released. If another user is holding your nick\n" +"and is identified they will be killed (similar to the old\n" +"GHOST command). If they are not identified they will be\n" +"forced off of the nick." +msgstr "" + +#: modules/commands/cs_access.cpp:741 +#, fuzzy +msgid "Redefine the meanings of access levels" +msgstr " LEVELS Access seviyelerini isteğinize göre düzenler" + +#: modules/commands/ns_recover.cpp:149 +#, fuzzy +msgid "Regains control of your nick" +msgstr "" +" RELEASE RECOVER komutundan sonra nickinizi serbest \n" +" bırakır" + +#: modules/commands/os_sxline.cpp:330 modules/commands/os_sxline.cpp:545 +#: modules/commands/os_akill.cpp:129 +#, fuzzy +msgid "Regex is disabled." +msgstr "%s is enable" + +#: modules/commands/os_sxline.cpp:459 modules/commands/os_sxline.cpp:694 +#: modules/commands/os_akill.cpp:444 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your mask in // if this is desired." +msgstr "" + +#: modules/commands/os_ignore.cpp:386 modules/commands/os_forbid.cpp:428 +#: modules/commands/ns_list.cpp:172 modules/commands/cs_list.cpp:167 +#: modules/commands/os_list.cpp:119 modules/commands/os_list.cpp:255 +#, c-format +msgid "" +"Regex matches are also supported using the %s engine.\n" +"Enclose your pattern in // if this is desired." +msgstr "" + +#: modules/commands/cs_register.cpp:19 +#, fuzzy +msgid "Register a channel" +msgstr " REGISTER Nickinizi kaydeder" + +#: modules/commands/ns_register.cpp:120 +#, fuzzy +msgid "Register a nickname" +msgstr " REGISTER Nickinizi kaydeder" + +#: modules/commands/ns_info.cpp:89 modules/commands/cs_info.cpp:55 +#, fuzzy +msgid "Registered" +msgstr " Kayıt zamanı: %s" + +#: modules/commands/os_stats.cpp:184 +#, c-format +msgid "Registered channels: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:190 +#, c-format +msgid "Registered nick groups: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:187 +#, c-format +msgid "Registered nicknames: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/cs_enforce.cpp:105 +#, c-format +msgid "Registered only enforced on %s." +msgstr "" + +#: modules/commands/cs_register.cpp:86 +#, fuzzy, c-format +msgid "" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which is optional, is a\n" +"general description of the channel's purpose.\n" +" \n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel." +msgstr "" +"Kullanımı: REGISTER kanaladı açıklama\n" +"\n" +"Registers a channel in the %s database. In order\n" +"to use this command, you must first be a channel operator\n" +"on the channel you're trying to register.\n" +"The description, which must be included, is a\n" +"general description of the channel's purpose.\n" +"When you register a channel, you are recorded as the\n" +"\"founder\" of the channel. The channel founder is allowed\n" +"to change all of the channel settings for the channel;\n" +"%s will also automatically give the founder\n" +"channel-operator privileges when s/he enters the channel.\n" +"See the ACCESS command (/msg %s HELP ACCESS) for\n" +"information on giving a subset of these privileges to\n" +"other channel users.\n" +"NOTICE: In order to register a channel, you must have\n" +"first registered your nickname. If you haven't,\n" +"/msg %s HELP for information on how to do so." + +#: modules/commands/ns_register.cpp:269 +#, fuzzy, c-format +msgid "" +"Registers your nickname in the %s database. Once\n" +"your nick is registered, you can use the SET and ACCESS\n" +"commands to configure your nick's settings as you like\n" +"them. Make sure you remember the password you use when\n" +"registering - you'll need it to make changes to your nick\n" +"later. (Note that case matters! ANOPE, Anope, and\n" +"anope are all different passwords!)\n" +" \n" +"Guidelines on choosing passwords:\n" +" \n" +"Passwords should not be easily guessable. For example,\n" +"using your real name as a password is a bad idea. Using\n" +"your nickname as a password is a much worse idea ;) and,\n" +"in fact, %s will not allow it. Also, short\n" +"passwords are vulnerable to trial-and-error searches, so\n" +"you should choose a password at least 5 characters long.\n" +"Finally, the space character cannot be used in passwords." +msgstr "" +"Kullanımı: REGISTER şifre [email]\n" +"\n" +"%s 'ün veritabanına nickinizi kaydeder. Nickinizi \n" +"bir kere kayıt ettikten sonra nickinizin özelliklerini \n" +"istediğiniz gibi belirlemek için SET ve ACCESS \n" +"komutlarını kullanabilirsiniz. Kayıtta kullandığınız şifrenin\n" +"hatırlanabilecek birşey olmasına dikkat edin - ilerde\n" +"nickinizin özelliklerinde değişiklik yaparken ve sunucuda\n" +"kullanabilmek için ihtiyacınız olacak. (Şifrelerin büyük\n" +"küçük harf hassasiyeti olduğunu unutmayın! İXİR, İxir, \n" +"ve ixir şifreleri birbirinden farklıdır.)\n" +"\n" +"Şifreleri seçme konusunda rehber:\n" +"\n" +"Şifreler kolayca tahmin edilebilir olmamalıdır. Örneğin,\n" +"gerçek isminizi şifre olarak kullanmak kötü bir fikirdir.\n" +"Nickinizi şifre olarak kullanmak daha kötü bir fikirdir :)\n" +"ve zaten %s buna izin vermez. Ayrıca kısa şifreler \n" +"deneme yanılma yöntemiyle bulunabilirler, bu yüzden şifrenizin\n" +"en az 5 karakter olmasına dikkat edin. Son olarak şifrede\n" +"boşluk kullanmamanız gerekir.\n" +"\n" +"email parametresi opsiyoneldir ve nickiniz için bir \n" +"email adresi belirler. Fakat bazı networklerde bu\n" +"parametrenin kullanılması zorunlu olabilir.(Unutmayın\n" +"email adresinizi doğru olarak vermeniz ilerde şifrenizi \n" +"unutmanız halinde çok işe yarayacaktır)\n" +"Gizliliğinize saygı duyulacak ve mail adresiniz herhangi \n" +"üçüncü şahıslara söylenmeyecektir.\n" +"Bu komut ayrıca nickiniz için yeni bir grup oluşturur ki bu\n" +"ilerde gruba kaydedeceğiniz nickler için aynı özellikleri, \n" +"memo ayarlarını ve aynı kanal ayrıcalıklarını paylaşmanızı \n" +"sağlar. Bu özellik hakkında daha fazla bilgi için, \n" +"/msg %s HELP GROUP yazın." + +#: modules/commands/ns_register.cpp:145 +#, fuzzy +msgid "Registration is currently disabled." +msgstr "Kanal kaydı geçici olarak devre dışıdır." + +#: modules/commands/cs_set.cpp:400 +#, fuzzy +msgid "Regulate the use of critical commands" +msgstr " PEACE kritik komutlarin kullanilmasini engeller" + +#: modules/commands/hs_request.cpp:283 +#, fuzzy +msgid "Reject the requested vHost for the given nick." +msgstr " STATUS Returns the owner status of the given nickname" + +#: modules/commands/hs_request.cpp:240 +#, fuzzy +msgid "Reject the requested vHost of a user" +msgstr " DEL Delete the vhost of another user" + +#: modules/commands/cs_suspend.cpp:151 +#, fuzzy +msgid "Releases a suspended channel" +msgstr " UNSUSPEND Releases a suspended channel" + +#: modules/commands/cs_suspend.cpp:191 +#, fuzzy +msgid "" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." +msgstr "" +"Syntax: UNSUSPEND channel\n" +"\n" +"Releases a suspended channel. All data and settings\n" +"are preserved from before the suspension." + +#: modules/commands/os_module.cpp:56 +#, fuzzy +msgid "Reload a module" +msgstr " MODLOAD Load a module" + +#: modules/commands/os_reload.cpp:19 +#, fuzzy +msgid "Reload services' configuration file" +msgstr " RELOAD Servislerin conf dosyasını yeniden yükler" + +#: modules/commands/ns_group.cpp:236 +#, fuzzy +msgid "Remove a nick from a group" +msgstr " UNGROUP Remove a nick from a group" + +#: modules/commands/cs_unban.cpp:19 +#, fuzzy +msgid "Remove all bans preventing a user from entering a channel" +msgstr "" +" UNBAN Remove all bans preventing a user from entering a channel" + +#: modules/commands/os_noop.cpp:19 +#, fuzzy +msgid "Remove all operators from a server remotely" +msgstr " NOOP Geçici olarak tüm O:line ları kaldırır" + +#: modules/commands/os_dns.cpp:543 +#, fuzzy, c-format +msgid "Removed IP %s from %s." +msgstr " Mod kilidi: %s" + +#: modules/commands/os_dns.cpp:460 +#, c-format +msgid "Removed server %s from zone %s." +msgstr "" + +#: modules/commands/os_dns.cpp:483 +#, c-format +msgid "Removed server %s." +msgstr "" + +#: modules/commands/cs_mode.cpp:909 +#, c-format +msgid "" +"Removes %s status from the selected nick on a channel. If nick is\n" +"not given, it will de%s you." +msgstr "" + +#: modules/commands/cs_mode.cpp:890 +#, fuzzy, c-format +msgid "Removes %s status from you or the specified nick on a channel" +msgstr " OP Gives Op status to a selected nick on a channel" + +#: modules/commands/cs_updown.cpp:146 +#, fuzzy +msgid "Removes a selected nicks status from a channel" +msgstr " KICK Kicks a selected nick from a channel" + +#: modules/commands/cs_updown.cpp:223 +msgid "" +"Removes a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is removed. If channel is omitted then\n" +"your channel status is removed on every channel you are in." +msgstr "" + +#: src/xline.cpp:412 +#, c-format +msgid "Removing %s because %s covers it." +msgstr "" + +#: modules/commands/bs_kick.cpp:1171 modules/commands/bs_kick.cpp:1173 +#: modules/commands/bs_kick.cpp:1176 +#, fuzzy +msgid "Repeat kicker" +msgstr " Tekrarda atma : %s" + +#: modules/commands/hs_request.cpp:78 +#, fuzzy +msgid "Request a vHost for your nick" +msgstr "There's no email address set for your nick." + +#: modules/commands/hs_request.cpp:179 +msgid "" +"Request the given vHost to be activated for your nick by the\n" +"network administrators. Please be patient while your request\n" +"is being considered." +msgstr "" + +#: modules/commands/ns_register.cpp:312 +#, fuzzy +msgid "Resend registration confirmation email" +msgstr " RELOAD Servislerin conf dosyasını yeniden yükler" + +#: modules/commands/cs_set.cpp:621 +#, fuzzy +msgid "Restrict access to the channel" +msgstr " RESTRICTED Kanala izinli giriş gerektirir" + +#: modules/commands/cs_set.cpp:1291 +#, fuzzy +msgid "Restricted access" +msgstr "Kisitli Erisim." + +#: modules/commands/cs_set.cpp:661 +#, fuzzy, c-format +msgid "Restricted access option for %s is now off." +msgstr "Restricted access option for %s is now ON." + +#: modules/commands/cs_set.cpp:655 +#, fuzzy, c-format +msgid "Restricted access option for %s is now on." +msgstr "Restricted access option for %s is now ON." + +#: modules/commands/cs_enforce.cpp:73 +#, fuzzy, c-format +msgid "Restricted enforced on %s." +msgstr "Kisitli Erisim." + +#: modules/commands/cs_set.cpp:335 +#, fuzzy +msgid "Retain modes when channel is not in use" +msgstr " KEEPTOPIC Kanalda kimse olmasa bile topiği hatırlar" + +#: modules/commands/cs_topic.cpp:20 +#, fuzzy +msgid "Retain topic when channel is not in use" +msgstr " KEEPTOPIC Kanalda kimse olmasa bile topiği hatırlar" + +#: modules/commands/ns_getpass.cpp:19 +#, fuzzy +msgid "Retrieve the password for a nickname" +msgstr "" +" GETPASS Bir nickin şifresini öğrenmek içindir\n" +" (Sadece şifreleme(encryption) devre dışıysa)" + +#: modules/commands/hs_request.cpp:296 +msgid "Retrieves the vhost requests" +msgstr "" + +#: modules/commands/cs_getkey.cpp:19 +#, fuzzy +msgid "Returns the key of the given channel" +msgstr " GETKEY Returns the key of the given channel" + +#: modules/commands/cs_getkey.cpp:57 +#, fuzzy +msgid "Returns the key of the given channel." +msgstr " GETKEY Returns the key of the given channel" + +#: modules/commands/ns_getemail.cpp:58 +#, fuzzy +msgid "Returns the matching accounts that used given email." +msgstr " GETKEY Returns the key of the given channel" + +#: modules/commands/ns_status.cpp:19 +#, fuzzy +msgid "Returns the owner status of the given nickname" +msgstr " STATUS Returns the owner status of the given nickname" + +#: modules/commands/ns_getpass.cpp:50 +#, fuzzy +msgid "" +"Returns the password for the given nickname. Note that\n" +"whenever this command is used, a message including the\n" +"person who issued the command and the nickname it was used\n" +"on will be logged and sent out as a WALLOPS/GLOBOPS." +msgstr "" +"Kullanımı: GETPASS nick\n" +"\n" +"Belirtilen nickin şifresini söyler. Unutmayınki bu komutun\n" +"her kullanılışında , kullanılan nick ve komutu kullanan\n" +"kişi kaydedilerek WALLOPS/GLOBOPS olarak gönderilir.\n" +"\n" +"Sadece Servis adminleri tarafından kullanılır.\n" +"\n" +"(Bu komut şifreleme(encryption) aktif olduğu zaman devre dışıdır.)" + +#: modules/commands/ns_status.cpp:55 +#, fuzzy +msgid "" +"Returns whether the user using the given nickname is\n" +"recognized as the owner of the nickname. The response has\n" +"this format:\n" +" \n" +" nickname status-code account\n" +" \n" +"where nickname is the nickname sent with the command,\n" +"status-code is one of the following, and account\n" +"is the account they are logged in as.\n" +" \n" +" 0 - no such user online or nickname not registered\n" +" 1 - user not recognized as nickname's owner\n" +" 2 - user recognized as owner via access list only\n" +" 3 - user recognized as owner via password identification\n" +" \n" +"If no nickname is given, your status will be returned." +msgstr "" +"Kullanımı: STATUS nick...\n" +"\n" +"Nickin kullanıcı tarafından nickin sahibi olarak tanıtılıp \n" +"tanıtılmadığını gösterir. Cevap şu formattadır:\n" +"\n" +" nick durum-kodu account\n" +"\n" +"where nick is the nickname sent with the command,\n" +"durum-kodu is one of the following, and account\n" +"is the account they are logged in as.\n" +"\n" +" 0 - Böyle bir kullanıcı bağlı değil veya nick \n" +" kayıtlı değil\n" +" 1 - Kullanıcı nickin sahibi olarak tanıtılmamış\n" +" 2 - Kullanıcı nickin sahibi olarak access listesinden \n" +" tanıtılmış\n" +" 3 - Kullanıcı nickin sahibi olarak şifreyle tanıtılmış\n" +"\n" +"Her komutta en fazla 16 nick için cevap verilir; gerisi \n" +"yoksayılır. If no nickname is given, your status\n" +"will be returned." + +#: modules/commands/bs_kick.cpp:1181 modules/commands/bs_kick.cpp:1183 +#: modules/commands/bs_kick.cpp:1186 +#, fuzzy +msgid "Reverses kicker" +msgstr " Ctrl+R de atma : %s" + +#: modules/commands/ns_logout.cpp:21 +#, fuzzy +msgid "Reverses the effect of the IDENTIFY command" +msgstr " LOGOUT Reverses the effect of the IDENTIFY command" + +#: modules/commands/os_noop.cpp:20 +#, fuzzy +msgid "SET server" +msgstr "NOOP {SET|REVOKE} server" + +#: modules/commands/os_dns.cpp:667 +msgid "SET server.name option value" +msgstr "" + +#: modules/commands/ns_cert.cpp:378 +#, fuzzy, c-format +msgid "SSL certificate fingerprint accepted, you are now identified to %s." +msgstr "Şifre kabul edildi." + +#: modules/commands/ns_cert.cpp:398 +#, fuzzy +msgid "SSL certificate fingerprint accepted, you are now identified." +msgstr "Şifre kabul edildi." + +#: modules/commands/cs_enforce.cpp:137 +#, c-format +msgid "SSL only enforced on %s." +msgstr "" + +#: modules/commands/cs_enforce.cpp:131 +msgid "SSLONLY enforced by " +msgstr "" + +#: modules/commands/os_shutdown.cpp:47 +#, fuzzy +msgid "Save databases and restart Services" +msgstr "" +" RESTART Veritabanını kaydeder ve servisleri yeniden \n" +" başlatır" + +#: modules/commands/os_logsearch.cpp:32 +msgid "Searches logs for a matching pattern" +msgstr "" + +#: modules/commands/cs_set.cpp:1295 +#, fuzzy +msgid "Secure founder" +msgstr "Secure Founder" + +#: modules/commands/cs_set.cpp:786 +#, fuzzy, c-format +msgid "Secure founder option for %s is now off." +msgstr "Secure founder option for %s is now ON." + +#: modules/commands/cs_set.cpp:780 +#, fuzzy, c-format +msgid "Secure founder option for %s is now on." +msgstr "Secure founder option for %s is now ON." + +#: modules/commands/cs_set.cpp:1297 +#, fuzzy +msgid "Secure ops" +msgstr "Secure Ops" + +#: modules/commands/cs_set.cpp:850 +#, fuzzy, c-format +msgid "Secure ops option for %s is now off." +msgstr "Secure ops option for %s is now ON." + +#: modules/commands/cs_set.cpp:844 +#, fuzzy, c-format +msgid "Secure ops option for %s is now on." +msgstr "Secure ops option for %s is now ON." + +#: modules/commands/cs_set.cpp:723 +#, fuzzy, c-format +msgid "Secure option for %s is now off." +msgstr "Secure option for %s is now ON." + +#: modules/commands/cs_set.cpp:717 +#, fuzzy, c-format +msgid "Secure option for %s is now on." +msgstr "Secure option for %s is now ON." + +#: modules/commands/ns_set.cpp:1044 +#, fuzzy, c-format +msgid "Secure option is now off for %s." +msgstr "Secure option is now ON for %s." + +#: modules/commands/ns_set.cpp:1038 +#, fuzzy, c-format +msgid "Secure option is now on for %s." +msgstr "Secure option is now ON for %s." + +#: modules/commands/cs_enforce.cpp:42 +#, fuzzy, c-format +msgid "Secureops enforced on %s." +msgstr "Secure option is now ON for %s." + +#: modules/commands/cs_set.cpp:1293 modules/commands/ns_set.cpp:1311 +msgid "Security" +msgstr "Güvenlik" + +#: modules/commands/cs_xop.cpp:570 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the access list." +msgstr "" +"Belirli bir özellik hakkında daha fazla bilgi için\n" +"/msg %s HELP özellik yazın." + +#: modules/commands/cs_xop.cpp:573 +#, fuzzy, c-format +msgid "" +"See %s%s HELP %s for more information\n" +"about the flags system." +msgstr "" +"Belirli bir özellik hakkında daha fazla bilgi için\n" +"/msg %s HELP özellik yazın." + +#: modules/commands/ms_send.cpp:24 +#, fuzzy +msgid "Send a memo to a nick or channel" +msgstr " SEND Nicke veya kanala mesaj gönderir" + +#: modules/commands/ms_staff.cpp:24 +#, fuzzy +msgid "Send a memo to all opers/admins" +msgstr " STAFF Send a memo to all opers/admins" + +#: modules/commands/ms_sendall.cpp:24 +#, fuzzy +msgid "Send a memo to all registered users" +msgstr " SENDALL Send a memo to all registered users" + +#: modules/commands/gl_global.cpp:21 +#, fuzzy +msgid "Send a message to all users" +msgstr " GLOBAL Tüm kullanıcılara mesaj gönderir" + +#: modules/commands/ms_list.cpp:64 +#, fuzzy +msgid "Sender" +msgstr "Secure Founder" + +#: modules/commands/ms_rsend.cpp:24 +#, fuzzy +msgid "Sends a memo and requests a read receipt" +msgstr " RSEND Sends a memo and requests a read receipt" + +#: modules/commands/ns_resetpass.cpp:50 +#, fuzzy +msgid "" +"Sends a passcode to the nickname with instructions on how to\n" +"reset their password. Email must be the email address associated\n" +"to the nickname." +msgstr "" +"Syntax: RESETPASS nickname\n" +"\n" +"Sends a code key to the nickname with instructions on how to\n" +"reset their password." + +#: modules/commands/ms_sendall.cpp:52 +#, fuzzy +msgid "Sends all registered users a memo containing memo-text." +msgstr "" +"Syntax: SENDALL memo-text\n" +"Sends all registered users a memo containing memo-text." + +#: modules/commands/ms_staff.cpp:48 +#, fuzzy +msgid "Sends all services staff a memo containing memo-text." +msgstr "" +"Syntax: STAFF memo-text\n" +"Sends all services staff a memo containing memo-text." + +#: modules/commands/ms_send.cpp:66 +#, fuzzy +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered." +msgstr "" +"Kullanımı: SEND {nick | kanaladı} mesaj\n" +"\n" +"Belirtilen nicke veya kanala yazılan mesajı gönderir.\n" +"Nicke gönderirken, gönderilen kişi yeni mesajı olduğuna dair\n" +"bir not alır. Mesaj gönderilen nick/kanal kayıtlı olmalıdır." + +#: modules/commands/ms_rsend.cpp:80 +#, fuzzy +msgid "" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recipient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." +msgstr "" +"Syntax: RSEND {nick | channel} memo-text\n" +"\n" +"Sends the named nick or channel a memo containing\n" +"memo-text. When sending to a nickname, the recipient will\n" +"receive a notice that he/she has a new memo. The target\n" +"nickname/channel must be registered.\n" +"Once the memo is read by its recepient, an automatic notification\n" +"memo will be sent to the sender informing him/her that the memo\n" +"has been read." + +#: modules/commands/ms_read.cpp:199 +#, fuzzy +msgid "" +"Sends you the text of the memos specified. If LAST is\n" +"given, sends you the memo you most recently received. If\n" +"NEW is given, sends you all of your new memos. If ALL is\n" +"given, sends you all of your memos. Otherwise, sends you\n" +"memo number num. You can also give a list of numbers,\n" +"as in this example:\n" +" \n" +" READ 2-5,7-9\n" +" Displays memos numbered 2 through 5 and 7 through 9." +msgstr "" +"Kullanımı: READ [kanaladı] {num | liste | LAST | NEW}\n" +"\n" +"Belirtilen mesajları okumanızı sağlar. Eğer LAST belirtilmişse\n" +"en son gelen mesajınızı okursunuz. Eğer NEW belirtilmişse tüm \n" +"yeni mesajlarını okursunuz. Eğer bir numara belirtirseniz (num)\n" +"o numaraya ait mesajı okursunuz. Aşağıdaki örnekteki gibi belirli\n" +"numaralarıda okuyabilirsiniz:\n" +"\n" +" READ 2-5,7-9\n" +" 2'den 5'e ve 7'den 9'a kadar olan mesajları gösterir." + +#: modules/commands/os_dns.cpp:218 +#, fuzzy +msgid "Server" +msgstr "NOOP {SET|REVOKE} server" + +#: modules/commands/os_dns.cpp:375 +#, fuzzy, c-format +msgid "Server %s added to zone %s." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:345 +#, fuzzy, c-format +msgid "Server %s already exists." +msgstr "%s nickli bot zaten var." + +#: modules/commands/os_noop.cpp:31 modules/commands/os_dns.cpp:430 +#: modules/commands/os_dns.cpp:493 modules/commands/os_dns.cpp:532 +#: modules/commands/os_dns.cpp:571 modules/commands/os_dns.cpp:604 +#: modules/commands/os_dns.cpp:639 +#, fuzzy, c-format +msgid "Server %s does not exist." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:619 +#, fuzzy, c-format +msgid "Server %s has no configured IPs." +msgstr "%s nickinin kaydı silindi (dropped)." + +#: modules/commands/os_dns.cpp:357 +#, fuzzy, c-format +msgid "Server %s is already in zone %s." +msgstr "You are already in %s! " + +#: modules/commands/os_dns.cpp:614 +#, fuzzy, c-format +msgid "Server %s is already pooled." +msgstr "Module %s is already loaded." + +#: modules/commands/os_dns.cpp:609 +#, fuzzy, c-format +msgid "Server %s is not currently linked." +msgstr " %s şu an bağlı." + +#: modules/commands/os_dns.cpp:443 +#, fuzzy, c-format +msgid "Server %s is not in zone %s." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:384 +#, fuzzy, c-format +msgid "Server %s is not linked to the network." +msgstr "%s kanalından bot çıkarıldı." + +#: modules/commands/os_dns.cpp:644 +#, fuzzy, c-format +msgid "Server %s is not pooled." +msgstr " %s (does not expire)" + +#: modules/commands/os_dns.cpp:465 +#, c-format +msgid "Server %s must be quit before it can be deleted." +msgstr "" + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Servers" +msgstr "NOOP {SET|REVOKE} server" + +#: modules/commands/os_stats.cpp:155 +#, c-format +msgid "Servers found: %d" +msgstr "Servers found: %d" + +#: modules/commands/cs_log.cpp:127 +#, fuzzy +msgid "Service" +msgstr "Servers found: %d" + +#: modules/commands/ns_recover.cpp:51 +#, fuzzy, c-format +msgid "Service's hold on %s has been released." +msgstr "Nickiniz serbest bırakıldı." + +#: data/nickserv.example.conf:236 data/chanserv.example.conf:827 +#, fuzzy +msgid "Services Operator commands" +msgstr "%s is a services operator of type %s." + +#: modules/commands/os_defcon.cpp:443 modules/commands/os_defcon.cpp:454 +#: modules/commands/os_defcon.cpp:462 modules/commands/os_defcon.cpp:470 +#: modules/commands/os_defcon.cpp:478 +#, fuzzy +msgid "Services are in DefCon mode, please try again later." +msgstr "This service is temporarly disabled, please try again later" + +#: include/language.h:70 +#, fuzzy +msgid "Services are in read-only mode!" +msgstr "Servisler şimdi read-only modunda." + +#: modules/commands/os_defcon.cpp:186 modules/commands/os_defcon.cpp:213 +#, fuzzy, c-format +msgid "Services are now at DEFCON %d." +msgstr "Services are now at DEFCON %d" + +#: modules/commands/os_set.cpp:128 +#, fuzzy, c-format +msgid "Services are now in debug mode (level %d)." +msgstr "Servisler şimdi debug modunda (seviye %d)." + +#: modules/commands/os_set.cpp:114 +#, fuzzy +msgid "Services are now in debug mode." +msgstr "Servisler şimdi debug modunda." + +#: modules/commands/os_set.cpp:159 +msgid "Services are now in expire mode." +msgstr "Servisler şimdi expire modunda." + +#: modules/commands/os_set.cpp:153 +msgid "Services are now in no expire mode." +msgstr "Servisler şimdi no expire modunda." + +#: modules/commands/os_set.cpp:120 +#, fuzzy +msgid "Services are now in non-debug mode." +msgstr "Servisler şimdi non-debug modunda." + +#: modules/commands/os_set.cpp:47 +msgid "Services are now in read-only mode." +msgstr "Servisler şimdi read-only modunda." + +#: modules/commands/os_set.cpp:53 +msgid "Services are now in read-write mode." +msgstr "Servisler şimdi read-write modunda." + +#: src/mail.cpp:76 +msgid "Services have been configured to not send mail." +msgstr "Servislerin mail gönderme özelliği devre dışıdır." + +#: modules/commands/os_ignore.cpp:280 +#, fuzzy +msgid "Services ignore list:" +msgstr " IGNORE Modify the Services ignore list" + +#: modules/commands/os_mode.cpp:33 modules/commands/os_kick.cpp:39 +#, fuzzy +msgid "" +"Services is unable to change modes. Are your servers' U:lines configured " +"correctly?" +msgstr "" +"Servisler mod değiştiremiyor. Serverin U:line larının doğru ayarlandığına " +"emin olun." + +#: modules/commands/os_stats.cpp:140 +#, fuzzy, c-format +msgid "Services up %s." +msgstr "Servers found: %d" + +#: modules/commands/ns_set.cpp:266 +#, fuzzy, c-format +msgid "Services will from now on set status modes on %s in channels." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/cs_set.cpp:114 +#, fuzzy, c-format +msgid "Services will no longer automatically give modes to users in %s." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/ns_set.cpp:272 +#, fuzzy, c-format +msgid "Services will no longer set status modes on %s in channels." +msgstr "Services will no longer autoop %s in channels." + +#: modules/commands/cs_set.cpp:108 +#, fuzzy, c-format +msgid "Services will now automatically give modes to users in %s." +msgstr "Services will now autoop %s in channels." + +#: modules/commands/ns_set.cpp:940 +#, c-format +msgid "Services will now reply to %s with messages." +msgstr "Services will now reply to %s with messages." + +#: modules/commands/ns_set.cpp:946 +#, c-format +msgid "Services will now reply to %s with notices." +msgstr "Services will now reply to %s with notices." + +#: modules/commands/os_reload.cpp:34 +#, fuzzy +msgid "Services' configuration has been reloaded." +msgstr "Servislerin conf dosyası yeniden yüklendi." + +#: modules/commands/os_session.cpp:192 +msgid "Session" +msgstr "" + +#: modules/commands/os_session.cpp:382 +#, c-format +msgid "Session limit for %s set to %d." +msgstr "%s için session limit %d olarak değiştirildi." + +#: modules/commands/os_session.cpp:257 modules/commands/os_session.cpp:534 +msgid "Session limiting is disabled." +msgstr "Session limit koyma devre dışı." + +#: modules/commands/os_stats.cpp:195 +#, c-format +msgid "Sessions: %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/ns_set.cpp:74 +#, fuzzy +msgid "Set SET-options on another nickname" +msgstr " SASET Set SET-options on another nickname" + +#: modules/commands/cs_set.cpp:20 +#, fuzzy +msgid "Set channel options and information" +msgstr " SET Kanal özelliklerini ve bilgisini ayarlar" + +#: modules/commands/cs_set.cpp:137 +#, fuzzy +msgid "Set how Services make bans on the channel" +msgstr " BANTYPE Servislerin kanalda ne tip ban koyacağını belirler" + +#: modules/commands/ms_set.cpp:206 +#, fuzzy +msgid "Set options related to memos" +msgstr " SET Mesajlarla ilgili ayarları yapar" + +#: modules/commands/ns_set.cpp:19 +#, fuzzy +msgid "Set options, including kill protection" +msgstr " SET Ayarlar, kill korumasını içerir" + +#: modules/commands/cs_set.cpp:472 +#, fuzzy +msgid "Set the channel as permanent" +msgstr " PERSIST Set the channel as permanent" + +#: modules/commands/cs_set.cpp:204 +#, fuzzy +msgid "Set the channel description" +msgstr " DESC Kanal açıklamasını belirler" + +#: modules/commands/ns_set.cpp:329 +#, fuzzy +msgid "Set the display of your group in Services" +msgstr " DISPLAY Grubunuzun servislerde nasıl görüneceğini ayarlar" + +#: modules/commands/cs_set.cpp:266 +#, fuzzy +msgid "Set the founder of a channel" +msgstr " FOUNDER Kanal founderını belirler" + +#: modules/commands/ns_set.cpp:793 +#, fuzzy +msgid "Set the language Services will use when messaging you" +msgstr "" +" LANGUAGE Servislerin size hitap edeceği \n" +" dili belirler" + +#: modules/commands/ns_set.cpp:172 +#, fuzzy +msgid "Set the nickname password" +msgstr " PASSWORD Set the nickname password" + +#: modules/commands/cs_set.cpp:949 +#, fuzzy +msgid "Set the successor for a channel" +msgstr " SUCCESSOR Kanal successorını belirler" + +#: modules/commands/hs_set.cpp:125 +#, fuzzy +msgid "Set the vhost for all nicks in a group" +msgstr " SETALL Set the vhost for all nicks in a group" + +#: modules/commands/hs_set.cpp:19 +#, fuzzy +msgid "Set the vhost of another user" +msgstr " SET Set the vhost of another user" + +#: modules/commands/os_set.cpp:169 +#, fuzzy +msgid "Set various global Services options" +msgstr " SET Çeşitli global servis özelliklerini ayarlar" + +#: modules/commands/ns_set.cpp:119 +#, fuzzy +msgid "Set your nickname password" +msgstr " PASSWORD Nickinize şifre belirtir" + +#: modules/commands/bs_kick.cpp:271 +#, fuzzy, c-format +msgid "" +"Sets the AMSG kicker on or off. When enabled, the bot will\n" +"kick users who send the same message to multiple channels\n" +"where %s bots are.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before they get banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK channel ITALICS {ON|OFF} [ttb]\n" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +"ttb is the number of times a user can be kicked\n" +"before it get banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:307 +#, fuzzy, c-format +msgid "" +"Sets the bad words kicker on or off. When enabled, this\n" +"option tells the bot to kick users who say certain words\n" +"on the channels.\n" +"You can define bad words for your channel using the\n" +"BADWORDS command. Type %s%s HELP BADWORDS for\n" +"more information.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Kullanımı: KICK #channel BADWORDS {ON|OFF} [böas]\n" +"\n" +"Küfürde atmayı açar yada kapatır. Aktifleştirildiğinde\n" +"bu özellik bota küfür edenleri atmasını söyler.\n" +"\n" +"Bir kanal için küfür belirlemek için BADWORDS komutunu\n" +"kullanabilirsiniz. Ayrıntılar için /msg %s HELP BADWORDS\n" +"yazın.\n" +"\n" +"böas banlamadan önce kişinin kaç kez atılacağını \n" +"belirler. Kaldırmak için komutta böas ı belirtmeyin." + +#: modules/commands/cs_set.cpp:186 +#, fuzzy +msgid "" +"Sets the ban type that will be used by services whenever\n" +"they need to ban someone from your channel.\n" +" \n" +"Bantype is a number between 0 and 3 that means:\n" +" \n" +"0: ban in the form *!user@host\n" +"1: ban in the form *!*user@host\n" +"2: ban in the form *!*@host\n" +"3: ban in the form *!*user@*.domain" +msgstr "" +"Kullanımı: %s kanaladı BANTYPE bantipi\n" +"\n" +"Servislerin birini kanaldan banlarken kullanacağı ban \n" +"tipini belirler.\n" +"\n" +"bantipi 0 ile 3 arasında bir sayıdır ve anlamları şudur:\n" +"\n" +"0: *!user@host formatında ban için\n" +"1: *!*user@host formatında ban için\n" +"2: *!*@host formatında ban için\n" +"3: *!*user@*.domain formatında ban için" + +#: modules/commands/bs_kick.cpp:345 +#, fuzzy +msgid "" +"Sets the bolds kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use bolds.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Kullanımı: KICK kanaladı BOLDS {ON|OFF} [böas]\n" +"\n" +"Kalın yazıda atmayı açar yada kapatır. \n" +"Aktifleştirildiğinde bu özellik bota kalın yazı\n" +"kullananları atmasını söyler.\n" +"\n" +"böas banlamadan önce kişinin kaç kez atılacağını \n" +"belirler. Kaldırmak için komutta böas ı belirtmeyin." + +#: modules/commands/bs_kick.cpp:436 +#, fuzzy, c-format +msgid "" +"Sets the caps kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are talking in\n" +"CAPS.\n" +"The bot kicks only if there are at least min caps\n" +"and they constitute at least percent%% of the total\n" +"text line (if not given, it defaults to 10 characters\n" +"and 25%%).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Kullanımı: KICK kanaladı CAPS {ON|OFF} [böas [min [yüzde]]]\n" +"\n" +"Büyük yazıda atmayı açar yada kapatır.\n" +"Aktifleştirildiğinde bu özellik bota büyük yazı\n" +"kullananları atmasını söyler.\n" +"\n" +"Bot belirtilen en az(min) büyük harfin toplam yazının\n" +"yüzdesine%% bağlı olarak atar. (Belirtilmemişse,\n" +"varsayılan olarak 10 karakter ve 25%% de atar).\n" +"\n" +"böas banlamadan önce kişinin kaç kez atılacağını \n" +"belirler. Kaldırmak için komutta böas ı belirtmeyin." + +#: modules/commands/bs_kick.cpp:475 +#, fuzzy +msgid "" +"Sets the colors kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use colors.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Kullanımı: KICK kanaladı COLORS {ON|OFF} [böas]\n" +"\n" +"Renkli yazıda atmayı açar yada kapatır. \n" +"Aktifleştirildiğinde bu özellik bota renkli yazı \n" +"kullananları atmasını söyler.\n" +"\n" +"böas banlamadan önce kişinin kaç kez atılacağını \n" +"belirler. Kaldırmak için komutta böas ı belirtmeyin." + +#: modules/commands/cs_set.cpp:255 +#, fuzzy +msgid "" +"Sets the description for the channel, which shows up with\n" +"the LIST and INFO commands." +msgstr "" +"Kullanımı: %s kanaladı DESC açıklama\n" +"\n" +"LIST ve INFO komutları kullanıldığında gözükecek kanal \n" +"açıklamasını belirler." + +#: modules/commands/bs_kick.cpp:571 +#, fuzzy +msgid "" +"Sets the flood kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are flooding\n" +"the channel using at least ln lines in secs seconds\n" +"(if not given, it defaults to 6 lines in 10 seconds).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Kullanımı: KICK kanaladı FLOOD {ON|OFF} [böas [sıra [sn]]]\n" +"\n" +"Flood da atmayı açar yada kapatır. Aktifleştirildiğinde\n" +"bu özellik bota sn saniyede enaz sıra sırada flood\n" +"yapanları atmasını söyler. (Belirtilmemişse varsayılan\n" +"olarak 10 saniyede 6 sıra da atar).\n" +"\n" +"böas banlamadan önce kişinin kaç kez atılacağını \n" +"belirler. Kaldırmak için komutta böas ı belirtmeyin." + +#: modules/commands/bs_kick.cpp:607 +#, fuzzy +msgid "" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Syntax: KICK channel ITALICS {ON|OFF} [ttb]\n" +"Sets the italics kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use italics.\n" +"ttb is the number of times a user can be kicked\n" +"before it get banned. Don't give ttb to disable\n" +"the ban system once activated." + +#: modules/commands/bs_kick.cpp:706 +#, fuzzy +msgid "" +"Sets the repeat kicker on or off. When enabled, this\n" +"option tells the bot to kick users who are repeating\n" +"themselves num times (if num is not given, it\n" +"defaults to 3).\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Kullanımı: KICK #kanaladı REPEAT {ON|OFF} [böas [sayı]]\n" +"\n" +"Tekrar yazılan aynı yazıda atmayı açar yada kapar.\n" +"Aktifleştirildiğinde bu özellik bota kendilerini\n" +"sayı kez tekrar edenleri atmasını söyler. (Eğer\n" +"sayı belirtilmemişse, varsayılan olarak 3 tür).\n" +"\n" +"böas banlamadan önce kişinin kaç kez atılacağını \n" +"belirler. Kaldırmak için komutta böas ı belirtmeyin." + +#: modules/commands/bs_kick.cpp:742 +#, fuzzy +msgid "" +"Sets the reverses kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use reverses.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Kullanımı: KICK kanaladı REVERSES {ON|OFF} [böas]\n" +"\n" +"Ctrl+r nin kullanılmasında atmayı açar yada kapatır. \n" +"Aktifleştirildiğinde bu özellik bota Ctrl+r yi \n" +"kullananları atmasını söyler.\n" +"\n" +"böas banlamadan önce kişinin kaç kez atılacağını \n" +"belirler. Kaldırmak için komutta böas ı belirtmeyin." + +#: modules/commands/bs_kick.cpp:776 +#, fuzzy +msgid "" +"Sets the underlines kicker on or off. When enabled, this\n" +"option tells the bot to kick users who use underlines.\n" +" \n" +"ttb is the number of times a user can be kicked\n" +"before it gets banned. Don't give ttb to disable\n" +"the ban system once activated." +msgstr "" +"Kullanımı: KICK kanaladı UNDERLINES {ON|OFF} [böas]\n" +"\n" +"Altıçizgili yazıda atmayı açar yada kapatır.\n" +"Aktifleştirildiğinde bu özellik bota altıçizgili\n" +"yazanları atmasını söyler.\n" +"\n" +"böas banlamadan önce kişinin kaç kez atılacağını \n" +"belirler. Kaldırmak için komutta böas ı belirtmeyin." + +#: modules/commands/hs_set.cpp:206 +#, fuzzy +msgid "" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nicks\n" +"added to the group after this command was used." +msgstr "" +"Syntax: SETALL  .\n" +"Sets the vhost for all nicks in the same group as that\n" +"of the given nick. If your IRCD supports vIdents, then\n" +"using SETALL @ will set idents\n" +"for users as well as vhosts.\n" +"* NOTE, this will not update the vhost for any nick's\n" +"added to the group after this command was used." + +#: modules/commands/hs_set.cpp:99 +#, fuzzy +msgid "" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as\n" +"well as vhosts." +msgstr "" +"Syntax: SET  .\n" +"Sets the vhost for the given nick to that of the given\n" +"hostmask. If your IRCD supports vIdents, then using\n" +"SET @ set idents for users as \n" +"well as vhosts." + +#: modules/commands/os_set.cpp:199 +#, fuzzy +msgid "" +"Sets various global Services options. Option names\n" +"currently defined are:\n" +" READONLY Set read-only or read-write mode\n" +" DEBUG Activate or deactivate debug mode\n" +" NOEXPIRE Activate or deactivate no expire mode\n" +" SUPERADMIN Activate or deactivate super admin mode\n" +" LIST List the options" +msgstr "" +"Kullanımı: SET özellik ayar\n" +"\n" +"Çeşitli global servis özelliklerini ayarlar. Özellikler\n" +"aşağıda tanımlanmıştır:\n" +" READONLY Read-only ve read-write modunu ayarlar\n" +" LOGCHAN Report log messages to a channel\n" +" DEBUG Debug modunu aktifleştirir yada kapatır\n" +" NOEXPIRE No expire modunu aktifleştirir yada kapatır\n" +" SUPERADMIN Activate or deactivate super-admin mode\n" +" IGNORE Activate or deactivate ignore mode\n" +" LIST List the options\n" +"\n" +"Servis adminlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/ms_set.cpp:235 +#, fuzzy, c-format +msgid "" +"Sets various memo options. option can be one of:\n" +" \n" +" NOTIFY Changes when you will be notified about\n" +" new memos (only for nicknames)\n" +" LIMIT Sets the maximum number of memos you can\n" +" receive\n" +" \n" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Kullanımı: SET özellik parametre\n" +"\n" +"Çeşitli mesaj ayarlarını yapar. özellik aşağıdakilerden \n" +"biri olabilir:\n" +"\n" +" NOTIFY Yeni mesajlarda ne zaman uyarılacağınızı\n" +" belirler (sadece nickler içindir)\n" +" LIMIT Alabileceğiniz maksimum mesaj sayısını\n" +" belirler\n" +"\n" +"Belirli bir özellik hakkında daha fazla bilgi için, \n" +"/msg %s HELP SET özellik yazın." + +#: modules/commands/ns_set.cpp:33 modules/commands/ns_set.cpp:88 +#, fuzzy +msgid "Sets various nickname options. option can be one of:" +msgstr "" +"Kullanımı: SET özellik parametre\n" +"\n" +"Çeşitli nick özelliklerini ayarlar. özellik şunlardan biri \n" +"olabilir:" + +#: modules/commands/ns_set.cpp:237 +msgid "" +"Sets whether services should set channel status modes on you automatically." +msgstr "" + +#: modules/commands/cs_set.cpp:1090 +#, fuzzy +msgid "" +"Sets whether the given channel will expire. Setting this\n" +"to ON prevents the channel from expiring." +msgstr "" +"Kullanımı: SET kanaladı NOEXPIRE {ON | OFF}\n" +"\n" +"Belirtilen kanalın zaman asimina uğrayıp uğramayacağını \n" +"belirler. Bunu ON olarak ayarlamak kanalın zaman aşımına \n" +"uğramasını engelleyecektir.\n" +"\n" +"Servis adminlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/ns_set.cpp:315 +#, fuzzy, c-format +msgid "" +"Sets whether the given nickname will be given its status modes\n" +"in channels automatically. Set to ON to allow %s\n" +"to set status modes on the given nickname automatically when it\n" +"is entering channels. Note that depending on channel settings\n" +"some modes may not get set automatically." +msgstr "" +"Syntax: SASET nickname AUTOOP {ON | OFF}\n" +"\n" +"Sets whether the given nickname will be opped automatically.\n" +"Set to ON to allow ChanServ to op the given nickname \n" +"automatically when joining channels." + +#: modules/commands/ns_set.cpp:1145 +#, fuzzy +msgid "" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." +msgstr "" +"Syntax: SASET nickname NOEXPIRE {ON | OFF}\n" +"\n" +"Sets whether the given nickname will expire. Setting this\n" +"to ON prevents the nickname from expiring." + +#: modules/commands/ns_set.cpp:288 +#, fuzzy, c-format +msgid "" +"Sets whether you will be given your channel status modes automatically.\n" +"Set to ON to allow %s to set status modes on you automatically\n" +"when entering channels. Note that depending on channel settings some modes\n" +"may not get set automatically." +msgstr "" +"Syntax: SET AUTOOP {ON | OFF}\n" +"\n" +"Sets whether you will be opped automatically. Set to ON to \n" +"allow ChanServ to op you automatically when entering channels." + +#: modules/commands/cs_access.cpp:648 modules/commands/cs_access.cpp:689 +#, fuzzy, c-format +msgid "" +"Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings." +msgstr "" +"Varolmayan ayar: %s. Geçerli ayar listesi için /msg %s HELP LEVELS DESC " +"yazınız." + +#: modules/commands/os_set.cpp:133 +#, fuzzy +msgid "Setting for DEBUG must be ON, OFF, or a positive number." +msgstr "DEBUG ayarı ON, OFF, veya pozitif bir sayı olmalıdır." + +#: modules/commands/os_set.cpp:162 +#, fuzzy +msgid "Setting for NOEXPIRE must be ON or OFF." +msgstr "NOEXPIRE ayarı ON yada OFF olmalıdır." + +#: modules/commands/os_set.cpp:56 +#, fuzzy +msgid "Setting for READONLY must be ON or OFF." +msgstr "READONLY ayarı ON veya OFF şeklinde olmalıdır." + +#: modules/commands/os_set.cpp:95 +#, fuzzy +msgid "Setting for super admin must be ON or OFF." +msgstr "READONLY ayarı ON veya OFF şeklinde olmalıdır." + +#: modules/commands/cs_set.cpp:74 +#, fuzzy +msgid "Should services automatically give status to users" +msgstr " AUTOOP Should services op you automatically. " + +#: modules/commands/os_stats.cpp:203 +#, fuzzy +msgid "Show status of Services and network" +msgstr " STATS Servislerin ve networkun durumunu gösterir" + +#: modules/commands/os_logsearch.cpp:152 +#, c-format +msgid "Showed %d/%d matches for %s." +msgstr "" + +#: modules/commands/cs_set.cpp:872 +#, fuzzy +msgid "Sign kicks that are done with the KICK command" +msgstr " SIGNKICK KICK komutuyla yapılan atmaları işaretler" + +#: modules/commands/cs_set.cpp:921 +#, fuzzy, c-format +msgid "Signed kick option for %s is now off." +msgstr "Signed kick option for %s is now ON." + +#: modules/commands/cs_set.cpp:913 +#, fuzzy, c-format +msgid "" +"Signed kick option for %s is now on, but depends of the\n" +"level of the user that is using the command." +msgstr "" +"Signed kick option for %s is now ON, but depends of the\n" +"level of the user that is using the command." + +#: modules/commands/cs_set.cpp:906 +#, fuzzy, c-format +msgid "Signed kick option for %s is now on." +msgstr "Signed kick option for %s is now ON." + +#: modules/commands/cs_set.cpp:1299 +msgid "Signed kicks" +msgstr "İşaretli atma" + +#: modules/commands/ms_rsend.cpp:60 modules/commands/ms_send.cpp:59 +#, fuzzy, c-format +msgid "Sorry, %s currently has too many memos and cannot receive more." +msgstr "%s nickinin limiti dolduğundan daha fazla mesaj alamaz." + +#: modules/commands/cs_seen.cpp:294 +#, c-format +msgid "Sorry, I have not seen %s." +msgstr "" + +#: modules/commands/bs_badwords.cpp:404 +#, fuzzy +msgid "Sorry, bad words list modification is temporarily disabled." +msgstr "Kanalın küfür listesinde değişiklik yapma geçici olarak devre dışıdır." + +#: modules/commands/bs_assign.cpp:30 modules/commands/bs_assign.cpp:98 +#, fuzzy +msgid "Sorry, bot assignment is temporarily disabled." +msgstr "Bot özellik ayarı geçici olarak devre dışı." + +#: modules/commands/bs_bot.cpp:281 modules/commands/bs_assign.cpp:164 +msgid "Sorry, bot modification is temporarily disabled." +msgstr "Botta değişiklik yapma geçici olarak devre dışı." + +#: modules/fantasy.cpp:42 modules/commands/bs_kick.cpp:813 +#: modules/commands/bs_kick.cpp:878 +msgid "Sorry, bot option setting is temporarily disabled." +msgstr "Bot özellik ayarı geçici olarak devre dışı." + +#: modules/commands/bs_set.cpp:115 +#, fuzzy +msgid "Sorry, changing bot options is temporarily disabled." +msgstr "Bot özellik ayarı geçici olarak devre dışı." + +#: modules/commands/cs_xop.cpp:112 modules/commands/cs_xop.cpp:235 +#: modules/commands/cs_xop.cpp:444 +#, fuzzy, c-format +msgid "Sorry, channel %s list modification is temporarily disabled." +msgstr "Kanal AOP listesi degisiklikleri geçici olarak devre disidir." + +#: modules/commands/cs_access.cpp:547 modules/commands/cs_flags.cpp:405 +msgid "Sorry, channel access list modification is temporarily disabled." +msgstr "Kanal access listesinin değiştirilmesi geçici olarak devre dışıdır." + +#: modules/commands/cs_akick.cpp:469 +msgid "Sorry, channel autokick list modification is temporarily disabled." +msgstr "Kanal Akick listesinin değiştirilmesi geçici olarak devre dışıdır." + +#: modules/commands/cs_drop.cpp:29 +msgid "Sorry, channel de-registration is temporarily disabled." +msgstr "Kanal kaydının silinmesi(DROP) geçici olarak devre dışıdır." + +#: modules/commands/cs_register.cpp:35 +msgid "Sorry, channel registration is temporarily disabled." +msgstr "Kanal kaydı geçici olarak devre dışıdır." + +#: modules/commands/bs_kick.cpp:181 +msgid "Sorry, kicker configuration is temporarily disabled." +msgstr "Atma ayarları geçici olarak devre dışı." + +#: modules/commands/ms_set.cpp:216 +msgid "Sorry, memo option setting is temporarily disabled." +msgstr "MemoServ'ün SET komutu geçici olarak devre dışıdır." + +#: include/language.h:116 +#, fuzzy +msgid "Sorry, memo sending is temporarily disabled." +msgstr "MemoServ'ün SET komutu geçici olarak devre dışıdır." + +#: modules/commands/ns_drop.cpp:29 +msgid "Sorry, nickname de-registration is temporarily disabled." +msgstr "Nick kaydı silinmesi geçici olarak devre dışıdır." + +#: modules/commands/ns_group.cpp:120 +msgid "Sorry, nickname grouping is temporarily disabled." +msgstr "Nick gruplama geçici olarak devre dışı." + +#: modules/commands/ns_register.cpp:139 +msgid "Sorry, nickname registration is temporarily disabled." +msgstr "Nick kaydı geçici olarak devre dışıdır." + +#: modules/commands/ns_access.cpp:33 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d access entries has been reached." +msgstr "Kanalda sadece %d tane access kaydı olabilir." + +#: modules/commands/ns_ajoin.cpp:141 +#, c-format +msgid "Sorry, the maximum of %d auto join entries has been reached." +msgstr "" + +#: modules/commands/ns_cert.cpp:173 +#, fuzzy, c-format +msgid "Sorry, the maximum of %d certificate entries has been reached." +msgstr "Bir nick için sadece %d tane access girilebilir." + +#: modules/commands/ms_ignore.cpp:55 +#, fuzzy, c-format +msgid "Sorry, the memo ignore list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/cs_access.cpp:204 modules/commands/cs_flags.cpp:174 +#: modules/commands/cs_xop.cpp:201 +#, fuzzy, c-format +msgid "" +"Sorry, you can only have %d access entries on a channel, including access " +"entries from other channels." +msgstr "Kanalda sadece %d tane access kaydı olabilir." + +#: modules/commands/cs_akick.cpp:177 +#, c-format +msgid "Sorry, you can only have %d autokick masks on a channel." +msgstr "Bir kanalın akick listesinde en fazla %d kişi olabilir." + +#: modules/commands/bs_badwords.cpp:286 +#, c-format +msgid "Sorry, you can only have %d bad words entries on a channel." +msgstr "Bir kanalda sadece %d tane küfür kaydı olabilir." + +#: include/language.h:103 +#, fuzzy, c-format +msgid "Sorry, you have already exceeded your limit of %d channels." +msgstr "Bir kanalda sadece %d tane küfür kaydı olabilir." + +#: include/language.h:102 +#, fuzzy, c-format +msgid "Sorry, you have already reached your limit of %d channels." +msgstr "Bir kanalda sadece %d tane küfür kaydı olabilir." + +#: modules/commands/os_dns.cpp:218 +msgid "State" +msgstr "" + +#: modules/commands/cs_seen.cpp:117 +msgid "Statistics and maintenance for seen data" +msgstr "" + +#: modules/commands/os_stats.cpp:131 +msgid "Statistics reset." +msgstr "İstatistikler resetlendi." + +#: modules/commands/ns_update.cpp:36 +msgid "Status updated (memos, vhost, chmodes, flags)." +msgstr "Status updated (memos, vhost, chmodes, flags)." + +#: modules/commands/bs_kick.cpp:1432 +msgid "Stop flooding!" +msgstr "Flood yapma!" + +#: modules/commands/bs_kick.cpp:1448 +msgid "Stop repeating yourself!" +msgstr "Kendini tekrar etme!" + +#: modules/commands/cs_set.cpp:746 +#, fuzzy +msgid "Stricter control of channel founder status" +msgstr " SECUREFOUNDER Kanal founderı durumunun sıkı kontrolünü sağlar" + +#: modules/commands/cs_set.cpp:810 +#, fuzzy +msgid "Stricter control of chanop status" +msgstr " SECUREOPS Kanal opu durumunun sıkı kontrolünü sağlar" + +#: modules/commands/ns_alist.cpp:75 modules/commands/cs_info.cpp:50 +msgid "Successor" +msgstr "" + +#: modules/commands/cs_set.cpp:1006 +#, fuzzy, c-format +msgid "Successor for %s changed to %s." +msgstr "%s için successor %s olarak değiştirildi." + +#: modules/commands/cs_set.cpp:1008 +#, c-format +msgid "Successor for %s unset." +msgstr "%s için successor kaldırıldı." + +#: modules/commands/os_set.cpp:81 +#, fuzzy +msgid "" +"Super admin can not be set because it is not enabled in the configuration." +msgstr "SuperAdmin setting not enabled in services.conf" + +#: modules/commands/ns_suspend.cpp:60 +#, fuzzy +msgid "Suspend a given nick" +msgstr " SUSPEND Suspend a given nick" + +#: modules/commands/cs_suspend.cpp:236 modules/commands/ns_suspend.cpp:250 +#, fuzzy +msgid "Suspend reason" +msgstr "JUPE serverismi [sebep]" + +#: modules/commands/cs_suspend.cpp:232 modules/commands/ns_suspend.cpp:246 +msgid "Suspended" +msgstr "" + +#: modules/commands/cs_suspend.cpp:234 modules/commands/ns_suspend.cpp:248 +msgid "Suspended by" +msgstr "" + +#: modules/commands/cs_suspend.cpp:238 modules/commands/ns_suspend.cpp:252 +#, fuzzy +msgid "Suspended on" +msgstr " SUSPEND Suspend a given nick" + +#: modules/commands/ns_suspend.cpp:147 +#, fuzzy +msgid "" +"Suspends a registered nickname, which prevents it from being used\n" +"while keeping all the data for that nick. If an expiry is given\n" +"the nick will be unsuspended after that period of time, else the\n" +"default expiry from the configuration is used." +msgstr "" +"Syntax: SUSPEND channel [reason]\n" +"\n" +"Disallows anyone from registering or using the given\n" +"channel. May be cancelled by using the UNSUSPEND\n" +"command to preserve all previous channel data/settings.\n" +"\n" +"Reason may be required on certain networks." + +#: modules/commands/cs_suspend.cpp:240 modules/commands/ns_suspend.cpp:254 +#, fuzzy +msgid "Suspension expires" +msgstr " %s (does not expire)" + +#: modules/commands/cs_sync.cpp:19 +#, fuzzy +msgid "Sync users channel modes" +msgstr "%s changed your usermodes." + +#: modules/commands/cs_sync.cpp:49 +msgid "" +"Syncs all modes set on users on the channel with the modes\n" +"they should have based on their access." +msgstr "" + +#: modules/commands/hs_group.cpp:42 +#, fuzzy +msgid "Syncs the vhost for all nicks in a group" +msgstr " GROUP Syncs the vhost for all nicks in a group" + +#: src/command.cpp:146 +msgid "Syntax" +msgstr "" + +#: modules/commands/ns_group.cpp:373 +#, fuzzy, c-format +msgid "" +"Syntax: %s\n" +" \n" +"Lists all nicks in your group." +msgstr "" +"Syntax: GLIST\n" +"\n" +"Lists all nicks in your group." + +#: modules/commands/ns_group.cpp:363 +#, fuzzy, c-format +msgid "" +"Syntax: %s [nickname]\n" +" \n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +" \n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick.\n" +"Specifying a nick is limited to Services Operators." +msgstr "" +"Syntax: GLIST [nickname]\n" +"\n" +"Without a parameter, lists all nicknames that are in\n" +"your group.\n" +"\n" +"With a parameter, lists all nicknames that are in the\n" +"group of the given nick." + +#: modules/commands/os_set.cpp:227 +#, fuzzy +msgid "" +"Syntax: DEBUG {ON | OFF}\n" +" \n" +"Sets debug mode on or off.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--debug." +msgstr "" +"Kullanımı: SET NOEXPIRE {ON | OFF}\n" +"\n" +"No expire modunu açar yada kapatır. No expire modunda,\n" +"nickler, kanallar, akiller, ve exceptionlar mod kapanana\n" +"kadar zaman aşımına uğramazlar.\n" +"\n" +"-noexpire komut satırı özelliğiyle aynıdır." + +#: modules/commands/ms_set.cpp:287 +#, fuzzy, c-format +msgid "" +"Syntax: LIMIT [channel] limit\n" +" \n" +"Sets the maximum number of memos you (or the given channel)\n" +"are allowed to have. If you set this to 0, no one will be\n" +"able to send any memos to you. However, you cannot set\n" +"this any higher than %d." +msgstr "" +"Kullanımı: SET LIMIT [kanaladı] limit\n" +"\n" +"Sizin alabileceğiniz (yada belirtilen kanalın) maksimum mesaj\n" +"sayısını belirler. Eğer bunu 0 yaparsanız kimse size mesaj \n" +"gönderemeyecektir. Ayrıca bu limiti %d den fazla yapamazsınız." + +#: modules/commands/ms_set.cpp:267 +#, fuzzy, c-format +msgid "" +"Syntax: LIMIT [user | channel] {limit | NONE} [HARD]\n" +" \n" +"Sets the maximum number of memos a user or channel is\n" +"allowed to have. Setting the limit to 0 prevents the user\n" +"from receiving any memos; setting it to NONE allows the\n" +"user to receive and keep as many memos as they want. If\n" +"you do not give a nickname or channel, your own limit is\n" +"set.\n" +" \n" +"Adding HARD prevents the user from changing the limit. Not\n" +"adding HARD has the opposite effect, allowing the user to\n" +"change the limit (even if a previous limit was set with\n" +"HARD).\n" +" \n" +"This use of the SET LIMIT command is limited to Services\n" +"Operators. Other users may only enter a limit for themselves\n" +"or a channel on which they have such privileges, may not\n" +"remove their limit, may not set a limit above %d, and may\n" +"not set a hard limit." +msgstr "" +"Kullanımı: SET LIMIT [kullanıcı | kanaladı] {limit | NONE} [HARD]\n" +"\n" +"Bir kullanıcıcn yada kanalın alabileceği maksimum mesaj\n" +"sayısını belirler. Bunu 0 yapmak kullanıcının mesaj almasını \n" +"engeller; NONE yapmaksa kullanıcının istediği kadar mesaj\n" +"alıp saklamasını sağlar. Eğer kanal veya nick belirtilmezse,\n" +"kendi limitinizi ayarlarsınız.\n" +"\n" +"HARD parametresini eklemek kullanıcının bu limiti değiştirmesini\n" +"engeller. Bunu eklememekde, kullanıcının limiti değiştirmesine izin\n" +"verir. (Bir önceki limit ayarında HARD kullanılmış olsa bile).\n" +"\n" +"SET LIMIT komutunun Kullanımı Servis adminleriyle sınırlıdır.\n" +"Diğer kullanıcılar limitlerini kaldıramaz, %d üzeri bir limit \n" +"belirleyemez, ve hard limitini ayarlayamaz. Sadece gerekli \n" +"ayrıcalıkları varsa bir kanalın mesaj limitini ve kendi mesaj\n" +"limitlerini ayarlayabilirler." + +#: modules/commands/os_set.cpp:208 +#, fuzzy, c-format +msgid "" +"Syntax: LIST\n" +" \n" +"Display the various %s settings." +msgstr "" +"Syntax: SET LIST\n" +"Display the various %s settings" + +#: modules/commands/os_set.cpp:234 +#, fuzzy +msgid "" +"Syntax: NOEXPIRE {ON | OFF}\n" +" \n" +"Sets no expire mode on or off. In no expire mode, nicks,\n" +"channels, akills and exceptions won't expire until the\n" +"option is unset.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--noexpire." +msgstr "" +"Kullanımı: SET NOEXPIRE {ON | OFF}\n" +"\n" +"No expire modunu açar yada kapatır. No expire modunda,\n" +"nickler, kanallar, akiller, ve exceptionlar mod kapanana\n" +"kadar zaman aşımına uğramazlar.\n" +"\n" +"-noexpire komut satırı özelliğiyle aynıdır." + +#: modules/commands/ms_set.cpp:246 +#, fuzzy +msgid "" +"Syntax: NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +" \n" +"Changes when you will be notified about new memos:\n" +" \n" +" ON You will be notified of memos when you log on,\n" +" when you unset /AWAY, and when they are sent\n" +" to you.\n" +" LOGON You will only be notified of memos when you log\n" +" on or when you unset /AWAY.\n" +" NEW You will only be notified of memos when they\n" +" are sent to you.\n" +" MAIL You will be notified of memos by email as well as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF You will not receive any notification of memos.\n" +" \n" +"ON is essentially LOGON and NEW combined." +msgstr "" +"Kullanımı: SET NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\n" +"\n" +"Yeni mesajlarda ne zaman uyarılacağınızı belirler:\n" +"\n" +" ON Yeni mesajlar için bağlandığınızda, away den \n" +" dönüşte ve size gönderildikleri anda \n" +" uyarılırsınız.\n" +" LOGON Yeni mesajlar için bağlandığınızda ve away den\n" +" dönüşte uyarılırsınız.\n" +" NEW Yeni mesajlar için sadece size gönderildikleri \n" +" anda uyarılırsınız.\n" +" MAIL You will be notified of memos by email aswell as\n" +" any other settings you have.\n" +" NOMAIL You will not be notified of memos by email.\n" +" OFF Yeni mesajlar için herhangi bir uyarı almazsınız.\n" +"\n" +"ON parametresi LOGON ve NEW 'in kombinasyonudur" + +#: modules/commands/os_set.cpp:212 +#, fuzzy +msgid "" +"Syntax: READONLY {ON | OFF}\n" +" \n" +"Sets read-only mode on or off. In read-only mode, normal\n" +"users will not be allowed to modify any Services data,\n" +"including channel and nickname access lists, etc. IRCops\n" +"with sufficient Services privileges will be able to modify\n" +"Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" +"suspend or forbid nicknames and channels, and manage news,\n" +"oper info and DNS, but any such changes will not be saved\n" +"unless read-only mode is deactivated before Services are\n" +"terminated or restarted.\n" +" \n" +"This option is equivalent to the command-line option\n" +"--readonly." +msgstr "" +"Kullanımı: SET READONLY {ON | OFF}\n" +"\n" +"Read-only modunu açar yada kapatır. Read-only modunda,\n" +"normal kullanıcılar herhangi bir servis verisini değiştiremezler,\n" +"bunun içinde kanal ve nick access listeleri v.s. vardır.\n" +"Yeterli ayrıcalıkları olan IRCoplar servislerin AKILL listesini\n" +"değiştirebilir, nicklerin ve kanalların kaydını silebilir yada \n" +"yasaklayabilir, fakat değişiklikler servisler kapatılmadan yada\n" +"tekrar başlatılmadan önce read-only modu kapatılmazsa kaydedilmez.\n" +"\n" +"-readonly komut satırı özelliğiyle aynıdır." + +#: modules/commands/os_set.cpp:243 +#, fuzzy +msgid "" +"Syntax: SUPERADMIN {ON | OFF}\n" +" \n" +"Setting this will grant you extra privileges such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +" \n" +"This option is not persistent, and should only be used when\n" +"needed, and set back to OFF when no longer needed." +msgstr "" +"Syntax: SET SUPERADMIN {ON | OFF}\n" +"Setting this will grant you extra privlages such as the\n" +"ability to be \"founder\" on all channel's etc...\n" +"This opion is _NOT_ persistant, and should only be used when\n" +"needed, and set back to OFF when no longer needed." + +#: modules/commands/ns_identify.cpp:107 +#, fuzzy, c-format +msgid "" +"Tells %s that you are really the owner of this\n" +"nick. Many commands require you to authenticate yourself\n" +"with this command before you use them. The password\n" +"should be the same one you sent with the REGISTER\n" +"command." +msgstr "" +"Kullanımı: IDENTIFY [account] şifreniz\n" +"\n" +"%s 'e kullandığınız nickin gerçek sahibinin siz olduğunu\n" +"belirtir. Çoğu komut kullanılmadan önce bu komutla \n" +"tanıtılmanızı gerektirir. Şifreniz nickinizi kayıt ederken \n" +"REGISTER komutuyla beraber kullandığınızla aynıdır." + +#: modules/commands/cs_invite.cpp:91 +#, fuzzy, c-format +msgid "" +"Tells %s to invite you or an optionally specified\n" +"nick into the given channel.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Kullanımı: INVITE kanaladı\n" +"\n" +"%s'e sizi belirtilen kanala davet etmesini söyler.\n" +"Varsayılan olarak AOP lar ile access seviyesi 5 veya\n" +"üzeri olanlar kullanabilir." + +#: modules/commands/cs_unban.cpp:103 +#, fuzzy, c-format +msgid "" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel. If no channel is\n" +"given, all bans affecting you in channels you have access\n" +"in are removed.\n" +" \n" +"By default, limited to AOPs or those with level 5 access and above\n" +"on the channel." +msgstr "" +"Kullanımı: UNBAN kanaladı [nick]\n" +"\n" +"Tells %s to remove all bans preventing you or the given\n" +"user from entering the given channel.\n" +"Varsayılan olarak, AOP lar ile 5 ve üzeri access seviyesi olanlar\n" +"kullanabilir." + +#: modules/commands/os_jupe.cpp:56 +#, fuzzy +msgid "" +"Tells Services to jupiter a server -- that is, to create\n" +"a fake \"server\" connected to Services which prevents\n" +"the real server of that name from connecting. The jupe\n" +"may be removed using a standard SQUIT. If a reason is\n" +"given, it is placed in the server information field;\n" +"otherwise, the server information field will contain the\n" +"text \"Juped by \", showing the nickname of the\n" +"person who jupitered the server." +msgstr "" +"Kullanımı: JUPE server [sebep]\n" +"\n" +"Servislere bir serverın Jupiter yapılmasını söyler. -- Bu,\n" +"servislere bir sahte server bağlayarak, gerçek serverın o \n" +"isimden bağlanmasını engeller. JUPE modu standart SQUIT\n" +"kullanılarak kaldırılabilir. Eğer sebep belirtilmişse,\n" +"bu server bilgi satırına yazılır; belirtilmezse server bilgi\n" +"satırında \"Jupitered by \" yazısı yer alır, ve serverı \n" +"jupiter edenin nicki yazılır.\n" +"\n" +"Servis adminlerinin Kullanımıyla sınırlıdır." + +#: modules/commands/cs_seen.cpp:261 +msgid "Tells you about the last time a user was seen" +msgstr "" + +#: modules/commands/os_shutdown.cpp:19 +#, fuzzy +msgid "Terminate Services WITHOUT saving" +msgstr " SHUTDOWN Servisler programını kayıt ederek kapatır" + +#: modules/commands/os_shutdown.cpp:73 +#, fuzzy +msgid "Terminate services with save" +msgstr " SHUTDOWN Servisler programını kayıt ederek kapatır" + +#: modules/commands/os_news.cpp:156 +msgid "Text" +msgstr "" + +#: modules/commands/cs_access.cpp:576 +msgid "" +"The ACCESS ADD command adds the given mask to the\n" +"access list with the given user level; if the mask is\n" +"already present on the list, its access level is changed to\n" +"the level specified in the command. The level specified\n" +"may be a numerical level or the name of a privilege (eg AUTOOP).\n" +"When a user joins the channel the access they receive is from the\n" +"highest level entry in the access list." +msgstr "" + +#: modules/commands/cs_access.cpp:587 +msgid "" +"The ACCESS DEL command removes the given nick from the\n" +"access list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +"You may remove yourself from an access list, even if you\n" +"do not have access to modify that list otherwise." +msgstr "" + +#: modules/commands/cs_access.cpp:593 +msgid "" +"The ACCESS LIST command displays the access list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" ACCESS #channel LIST 2-5,7-9\n" +" Lists access entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The ACCESS VIEW command displays the access list similar\n" +"to ACCESS LIST but shows the creator and last used time.\n" +" \n" +"The ACCESS CLEAR command clears all entries of the\n" +"access list." +msgstr "" + +#: modules/commands/cs_flags.cpp:447 +msgid "" +"The CLEAR command clears the channel access list. This requires channel " +"founder access." +msgstr "" + +#: modules/commands/cs_seen.cpp:173 +#, c-format +msgid "" +"The CLEAR command lets you clean the database by removing all entries from " +"the\n" +"database that were added within time.\n" +" \n" +"Example:\n" +" %s CLEAR 30m\n" +" Will remove all entries that were added within the last 30 minutes." +msgstr "" + +#: modules/commands/bs_badwords.cpp:438 +#, fuzzy +msgid "" +"The DEL command removes the given word from the\n" +"bad words list. If a list of entry numbers is given, those\n" +"entries are deleted. (See the example for LIST below.)\n" +" \n" +"The LIST command displays the bad words list. If\n" +"a wildcard mask is given, only those entries matching the\n" +"mask are displayed. If a list of entry numbers is given,\n" +"only those entries are shown; for example:\n" +" #channel LIST 2-5,7-9\n" +" Lists bad words entries numbered 2 through 5 and\n" +" 7 through 9.\n" +" \n" +"The CLEAR command clears all entries from the\n" +"bad words list." +msgstr "" +"Kullanımı: HOP kanaladi ADD nick\n" +" HOP kanaladi DEL {nick | kayit-no | liste}\n" +" HOP kanaladi LIST [mask | liste]\n" +" HOP kanaladi CLEAR\n" +"\n" +"Bir kanalin HOP (HalfOP) listesini düzenler. HOP\n" +"listesinde bulunan bir kisi kanalda otomatik olarak\n" +"halfop olur.\n" +"\n" +"HOP ADD komutu belirtilen nicki HOP listesine ekler.\n" +"\n" +"HOP DEL komutu belirtilen nicki HOP listesinden siler.\n" +"Eger kayit numaralari listesi belirtilirse, bu kayitlar\n" +"silinir. (Asagidaki örnegi inceleyin.)\n" +"\n" +"HOP LIST komutu HOP listesini gösterir. Eger bir hostmask\n" +"belirtilmisse, o hostmask la uyusan kayitlar gösterilir.\n" +"Eger kayit numaralari listesi belirtilmisse, o numaralardaki\n" +"nickler gösterilir; örnegin:\n" +" HOP #kanaladi LIST 2-5,7-9\n" +" 2 den 5 e ve 7 den 9 a kadar olan kayitlari gösterir.\n" +" \n" +"HOP CLEAR komutu HOP listesindeki tüm kayitlari temziler.\n" +"\n" +"HOP ADD, HOP DEL ve HOP LIST komutlarini AOP lar ve üstü\n" +"HOP CLEAR komutunu ise sadece founder kullanabilir.\n" +"\n" +"Bu komutu kanaliniz için devre disi birakabilirsiniz. O zaman\n" +"access komutlarini kullanmalisiniz. Access komutlari hakkinda\n" +"bilgi almak için /msg %s HELP ACCESS yazin. \n" +"Access ile xOP arasinda geçis yapabilmek için gerekli bilgilere\n" +"/msg %s HELP SET XOP yazarak ulasabilirsiniz." + +#: modules/commands/cs_entrymsg.cpp:241 +msgid "" +"The ENTRYMSG ADD command adds the given message to\n" +"the list of messages shown to users when they join\n" +"the channel." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:253 +msgid "" +"The ENTRYMSG CLEAR command clears all entries from\n" +"the list of messages shown to users when they join\n" +"the channel, effectively disabling entry messages." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:245 +msgid "" +"The ENTRYMSG DEL command removes the specified message from\n" +"the list of messages shown to users when they join\n" +"the channel. You can remove a message by specifying its number\n" +"which you can get by listing the messages as explained below." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:250 +msgid "" +"The ENTRYMSG LIST command displays a listing of messages\n" +"shown to users when they join the channel." +msgstr "" + +#: modules/commands/ns_set.cpp:713 +msgid "The IMMED option is not available on this network." +msgstr "HEMEN seçeneği bu networkte aktif değil." + +#: modules/commands/cs_access.cpp:821 +#, fuzzy, c-format +msgid "" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +" \n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it). Use LEVELS SET founder to make a level\n" +"founder only.\n" +" \n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel.\n" +" \n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." +msgstr "" +"Kullanımı: LEVELS kanaladı SET tip [seviye|FOUNDER]\n" +" LEVELS kanaladı {DIS | DISABLE} tip\n" +" LEVELS kanaladı LIST\n" +" LEVELS kanaladı RESET\n" +"\n" +"The LEVELS command allows fine control over the meaning of\n" +"the numeric access levels used for channels. With this\n" +"command, you can define the access level required for most\n" +"of %s's functions. (The SET FOUNDER and this command\n" +"are always restricted to the channel founder.)\n" +"\n" +"LEVELS SET allows the access level for a function or group of\n" +"functions to be changed. LEVELS DISABLE (or DIS for short)\n" +"disables an automatic feature or disallows access to a\n" +"function by anyone, INCLUDING the founder (although, the founder\n" +"can always reenable it).\n" +"\n" +"LEVELS LIST shows the current levels for each function or\n" +"group of functions. LEVELS RESET resets the levels to the\n" +"default levels of a newly-created channel (see\n" +"HELP ACCESS LEVELS).\n" +"\n" +"For a list of the features and functions whose levels can be\n" +"set, see HELP LEVELS DESC." + +#: modules/commands/cs_flags.cpp:442 +msgid "" +"The LIST command allows you to list existing entries on the channel access " +"list.\n" +"If a mask is given, the mask is wildcard matched against all existing " +"entries on the\n" +"access list, and only those entries are returned. If a set of flags is " +"given, only those\n" +"on the access list with the specified flags are returned." +msgstr "" + +#: modules/commands/cs_flags.cpp:435 +msgid "" +"The MODIFY command allows you to modify the access list. If the mask is\n" +"not already on the access list it is added, then the changes are applied.\n" +"If the mask has no more flags, then the mask is removed from the access " +"list.\n" +"Additionally, you may use +* or -* to add or remove all flags, respectively. " +"You are\n" +"only able to modify the access list if you have the proper permission on the " +"channel,\n" +"and even then you can only give other people access to the equivalent of " +"what your access is." +msgstr "" + +#: modules/commands/cs_seen.cpp:172 +msgid "" +"The STATS command prints out statistics about stored nicks and memory usage." +msgstr "" + +#: modules/commands/ns_register.cpp:291 +#, fuzzy +msgid "" +"The email parameter is optional and will set the email\n" +"for your nick immediately.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person. You may also wish to SET HIDE it\n" +"after registering if it isn't the default setting already." +msgstr "" +"Mail adresinizi ayarlamak için /msg %s SET EMAIL e-mailadresiniz \n" +"yazın. Gizliliğiniz korunacaktır; bu mail adresi herhangi üçüncü \n" +"şahıslara verilmeyecektir." + +#: modules/commands/cs_log.cpp:258 +#, c-format +msgid "" +"The %s command allows users to configure logging settings\n" +"for their channel. If no parameters are given this command\n" +"lists the current logging methods in place for this channel.\n" +" \n" +"Otherwise, command must be a command name, and method\n" +"is one of the following logging methods:\n" +" \n" +" MESSAGE [status], NOTICE [status], MEMO\n" +" \n" +"Which are used to message, notice, and memo the channel respectively.\n" +"With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" +"to your channel. Status may be a channel status such as @ or +.\n" +" \n" +"To remove a logging method use the same syntax as you would to add it.\n" +" \n" +"Example:\n" +" %s #anope chanserv/access MESSAGE @\n" +" Would message any channel operators whenever someone used the\n" +" ACCESS command on ChanServ on the channel." +msgstr "" + +#: modules/commands/cs_ban.cpp:64 +#, fuzzy, c-format +msgid "The %s list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/os_sxline.cpp:220 +#, fuzzy, c-format +msgid "The %s list has been cleared." +msgstr "AKILL listesi temizlendi." + +#: modules/commands/os_akill.cpp:377 +msgid "The AKILL list has been cleared." +msgstr "AKILL listesi temizlendi." + +#: modules/commands/os_defcon.cpp:136 modules/commands/os_defcon.cpp:225 +#, fuzzy, c-format +msgid "The Defcon level is now at: %d" +msgstr "The Defcon Level is now at Level: %d" + +#: modules/commands/ns_info.cpp:171 +#, c-format +msgid "The E-mail address of %s will now be hidden from %s INFO displays." +msgstr "The E-mail address of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:172 +#, c-format +msgid "The E-mail address of %s will now be shown in %s INFO displays." +msgstr "The E-mail address of %s will now be shown in %s INFO displays." + +#: modules/commands/cs_flags.cpp:449 +msgid "The available flags are:" +msgstr "" + +#: modules/commands/os_defcon.cpp:240 +#, fuzzy +msgid "" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." +msgstr "" +"Syntax: DEFCON [1|2|3|4|5]\n" +"The defcon system can be used to implement a pre-defined\n" +"set of restrictions to services useful during an attempted\n" +"attack on the network." + +#: modules/ns_maxemail.cpp:51 +#, c-format +msgid "The email address %s has reached its usage limit of %d users." +msgstr "" + +#: modules/ns_maxemail.cpp:49 +#, c-format +msgid "The email address %s has reached its usage limit of 1 user." +msgstr "" + +#: modules/commands/cs_entrymsg.cpp:142 +#, fuzzy, c-format +msgid "The entry message list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/cs_access.cpp:796 +msgid "The following feature/function names are available:" +msgstr "" + +#: modules/commands/cs_access.cpp:584 +msgid "" +"The given mask may also be a channel, which will use the\n" +"access list from the other channel up to the given level." +msgstr "" + +#: modules/commands/os_session.cpp:240 +#, fuzzy, c-format +msgid "" +"The host %s currently has %d sessions with a limit of %d because it matches " +"entry: %s." +msgstr "Host %s şu anda %d session a sahip ve %d ile limitli." + +#: modules/commands/ms_check.cpp:54 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has been read." +msgstr "The last memo you sent to %s (sent on %s) has been read." + +#: modules/commands/ms_check.cpp:52 +#, c-format +msgid "The last memo you sent to %s (sent on %s) has not yet been read." +msgstr "The last memo you sent to %s (sent on %s) has not yet been read." + +#: modules/commands/ns_info.cpp:189 +#, c-format +msgid "The last quit message of %s will now be hidden from %s INFO displays." +msgstr "The last quit message of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:190 +#, c-format +msgid "The last quit message of %s will now be shown in %s INFO displays." +msgstr "The last quit message of %s will now be shown in %s INFO displays." + +#: modules/commands/ns_info.cpp:177 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." +msgstr "" +"The last seen user@host mask of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:178 +#, c-format +msgid "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." +msgstr "" +"The last seen user@host mask of %s will now be shown in %s INFO displays." + +#: modules/commands/cs_enforce.cpp:190 +#, fuzzy, c-format +msgid "The limit on %s is not valid." +msgstr "%s nickinin mesaj limiti değiştirelemez." + +#: modules/commands/os_forbid.cpp:193 +msgid "The mask must contain at least one non wildcard character." +msgstr "" + +#: modules/commands/ms_set.cpp:153 +#, c-format +msgid "The memo limit for %s may not be changed." +msgstr "%s nickinin mesaj limiti değiştirelemez." + +#: modules/commands/cs_mode.cpp:347 +#, fuzzy, c-format +msgid "The mode lock list of %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/ns_set.cpp:355 +#, c-format +msgid "The new display MUST be a nickname of the nickname group %s." +msgstr "" + +#: include/language.h:98 +#, fuzzy, c-format +msgid "The new display is now %s." +msgstr "The Defcon Level is now at Level: %d" + +#: modules/commands/os_svs.cpp:57 +#, c-format +msgid "The nick %s is now being changed to %s." +msgstr "The nick %s is now being changed to %s." + +#: modules/commands/bs_bot.cpp:149 +msgid "The old information is the same as the new information specified." +msgstr "" + +#: modules/commands/os_info.cpp:157 +#, fuzzy, c-format +msgid "The oper info already exists on %s." +msgstr "%s nickli bot zaten var." + +#: modules/commands/os_info.cpp:147 +#, fuzzy, c-format +msgid "The oper info list for %s is full." +msgstr "Greet message for %s unset." + +#: modules/commands/ns_info.cpp:183 +#, c-format +msgid "" +"The services access status of %s will now be hidden from %s INFO displays." +msgstr "" +"The services access status of %s will now be hidden from %s INFO displays." + +#: modules/commands/ns_info.cpp:184 +#, c-format +msgid "The services access status of %s will now be shown in %s INFO displays." +msgstr "" +"The services access status of %s will now be shown in %s INFO displays." + +#: modules/commands/os_session.cpp:433 +#, fuzzy +msgid "The session exception list is empty." +msgstr " EXCEPTION Session-limit exception listesini düzenler" + +#: modules/commands/ns_recover.cpp:121 +msgid "" +"The user with your nick has been removed. Use this command again\n" +"to release services's hold on your nick." +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:195 +#, c-format +msgid "There are %d memos on channel %s." +msgstr "There are %d memos on channel %s." + +#: modules/commands/bs_botlist.cpp:47 +msgid "" +"There are no bots available at this time.\n" +"Ask a Services Operator to create one!" +msgstr "" +"Şu an mevcut bot yok.\n" +"Server adminine bir tane yaratmasını söyleyin!" + +#: modules/commands/os_dns.cpp:213 +msgid "There are no configured servers." +msgstr "" + +#: modules/commands/os_forbid.cpp:392 +#, fuzzy, c-format +msgid "There are no forbids of type %s." +msgstr "There are %d memos on channel %s." + +#: modules/commands/ns_group.cpp:162 +#, fuzzy +msgid "There are too many nicks in your group." +msgstr " DELALL Delete the vhost for all nicks in a group" + +#: modules/commands/cs_log.cpp:123 +#, fuzzy, c-format +msgid "There currently are no logging configurations for %s." +msgstr " RELOAD Servislerin conf dosyasını yeniden yükler" + +#: modules/pseudoclients/memoserv.cpp:193 +#, c-format +msgid "There is %d memo on channel %s." +msgstr "There is %d memo on channel %s." + +#: include/language.h:110 +#, fuzzy, c-format +msgid "" +"There is a new memo on channel %s.\n" +"Type %s%s READ %s %d to read it." +msgstr "Okumak için /msg %s READ %d yazın." + +#: modules/commands/bs_assign.cpp:132 +#, c-format +msgid "There is no bot assigned to %s anymore." +msgstr "%s kanalından bot çıkarıldı." + +#: modules/commands/os_news.cpp:33 +msgid "There is no logon news." +msgstr "Hiç bağlantı haberi yok." + +#: modules/commands/os_news.cpp:43 +msgid "There is no oper news." +msgstr "Hiç operatör haberi yok." + +#: modules/commands/os_news.cpp:53 +msgid "There is no random news." +msgstr "Hiç karisik haber yok." + +#: modules/commands/os_config.cpp:41 +#, fuzzy, c-format +msgid "There is no such configuration block %s." +msgstr " RELOAD Servislerin conf dosyasını yeniden yükler" + +#: modules/commands/cs_mode.cpp:706 +#, fuzzy, c-format +msgid "There is no such mode %s." +msgstr "Hiç operatör haberi yok." + +#: modules/commands/ms_set.cpp:52 +msgid "There's no email address set for your nick." +msgstr "There's no email address set for your nick." + +#: modules/commands/os_forbid.cpp:304 modules/commands/os_forbid.cpp:496 +#, fuzzy, c-format +msgid "This channel has been forbidden: %s" +msgstr "Bu kanal %s ile kayıtlıdır." + +#: modules/commands/cs_suspend.cpp:121 +#, fuzzy +msgid "This channel has been suspended." +msgstr "Bu kanal kullanılamaz." + +#: modules/commands/cs_suspend.cpp:232 +#, fuzzy +msgid "This channel is suspended." +msgstr "Bu kanal kullanılamaz." + +#: modules/commands/cs_suspend.cpp:268 +msgid "This channel may not be used." +msgstr "Bu kanal kullanılamaz." + +#: modules/commands/os_dns.cpp:702 +msgid "" +"This command allows managing DNS zones used for controlling what servers " +"users\n" +"are directed to when connecting. Omitting all parameters prints out the " +"status of\n" +"the DNS zone.\n" +" \n" +"ADDZONE adds a zone, eg us.yournetwork.tld. Servers can then be added to " +"this\n" +"zone with the ADDSERVER command.\n" +" \n" +"The ADDSERVER command adds a server to the given zone. When a query is done, " +"the\n" +"zone in question is served if it exists, else all servers in all zones are " +"served.\n" +"A server may be in more than one zone.\n" +" \n" +"The ADDIP command associates an IP with a server.\n" +" \n" +"The POOL and DEPOOL commands actually add and remove servers to their given " +"zones." +msgstr "" + +#: modules/commands/hs_group.cpp:72 +#, fuzzy +msgid "" +"This command allows users to set the vhost of their\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." +msgstr "" +"Syntax: GROUP\n" +"\n" +"This command allows users to set the vhost of thier\n" +"CURRENT nick to be the vhost for all nicks in the same\n" +"group." + +#: modules/commands/ns_register.cpp:299 +msgid "" +"This command also creates a new group for your nickname,\n" +"that will allow you to register other nicks later sharing\n" +"the same configuration, the same set of memos and the\n" +"same channel privileges." +msgstr "" + +#: modules/m_rewrite.cpp:145 +#, c-format +msgid "This command is an alias to the command %s." +msgstr "" + +#: modules/commands/ns_register.cpp:95 +#, fuzzy +msgid "" +"This command is used by several commands as a way to confirm\n" +"changes made to your account.\n" +" \n" +"This is most commonly used to confirm your email address once\n" +"you register or change it.\n" +" \n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." +msgstr "" +"Syntax: CONFIRM passcode\n" +"\n" +"This is the second step of nickname registration process.\n" +"You must perform this command in order to get your nickname\n" +"registered with %s. The passcode (or called auth code also)\n" +"is sent to your e-mail address in the first step of the\n" +"registration process. For more information about the first\n" +"stage of the registration process, type: /msg %s HELP REGISTER\n" +"\n" +"This is also used after the RESETPASS command has been used to\n" +"force identify you to your nick so you may change your password." + +#: modules/commands/os_modinfo.cpp:70 +#, fuzzy +msgid "This command lists information about the specified loaded module." +msgstr "" +"Syntax: MODINFO FileName\n" +"This command lists information about the specified loaded module" + +#: modules/commands/hs_list.cpp:136 +#, fuzzy +msgid "" +"This command lists registered vhosts to the operator.\n" +"If a key is specified, only entries whose nick or vhost match\n" +"the pattern given in key are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries." +msgstr "" +"Syntax: LIST [|<#X-Y>]\n" +"This command lists registered vhosts to the operator\n" +"if a Key is specified, only entries whos nick or vhost match\n" +"the pattern given in are displayed e.g. Rob* for all\n" +"entries beginning with \"Rob\"\n" +"If a #X-Y style is used, only entries between the range of X\n" +"and Y will be displayed, e.g. #1-3 will display the first 3\n" +"nick/vhost entries.\n" +"The list uses the value of NSListMax as a hard limit for the\n" +"number of items to display to a operator at any 1 time." + +#: modules/commands/os_module.cpp:45 +#, fuzzy +msgid "" +"This command loads the module named modname from the modules\n" +"directory." +msgstr "" +"Syntax: MODLOAD FileName\n" +"This command loads the module named FileName from the modules\n" +"directory." + +#: modules/commands/ns_group.cpp:201 +#, fuzzy +msgid "" +"This command makes your nickname join the target nickname's\n" +"group. password is the password of the target nickname.\n" +" \n" +"Joining a group will allow you to share your configuration,\n" +"memos, and channel privileges with all the nicknames in the\n" +"group, and much more!\n" +" \n" +"A group exists as long as it is useful. This means that even\n" +"if a nick of the group is dropped, you won't lose the\n" +"shared things described above, as long as there is at\n" +"least one nick remaining in the group.\n" +" \n" +"You may be able to use this command even if you have not registered\n" +"your nick yet. If your nick is already registered, you'll\n" +"need to identify yourself before using this command.\n" +" \n" +"It is recommended to use this command with a non-registered\n" +"nick because it will be registered automatically when\n" +"using this command. You may use it with a registered nick (to\n" +"change your group) only if your network administrators allowed\n" +"it.\n" +" \n" +"You can only be in one group at a time. Group merging is\n" +"not possible.\n" +" \n" +"Note: all the nicknames of a group have the same password." +msgstr "" +"Kullanımı: GROUP hedef şifre\n" +"\n" +"Bu komut nickinizin hedef gösterilen nickin grubuna katılmasını\n" +"sağlar. şifre hedef gösterilen nickin şifresidir.\n" +"\n" +"Bir gruba dahil olmak size o gruba dahil olan tüm nicklerinizin\n" +"ayarlarını, memolarını, ve kanal ayrıcalıklarını paylaşmanızı ve \n" +"daha fazlasını sağlar!\n" +" \n" +"Bir grup kullanışlı olduğu sürece kalıcıdır. Bu demektirki eğer\n" +"gruba dahil nickleriniz kaydını silerseniz, grupta en az bir nick \n" +"kalması kaydiyle yukarda açıklanan paylaşımları kaybetmezseniz.\n" +"\n" +"Bu komutu nickinizi kaydetmemiş olsanız bile kullanabilirsiniz.\n" +"Eğer nickiniz zaten kayıtlı ise, bu komutu kullanmadan önce\n" +"nickinizi tanıtmanız gerekir, daha fazla bilgi için\n" +"/msg %s HELP IDENTIFY yazın. Sizin IRC networkunuzda\n" +"bu mümkün olmayabilir.\n" +"\n" +"Bu komutu kayıtlı olmayan bir nickle kullanmanız önerilir çünkü\n" +"bu komutu kullanıcı o nick otomatik olarak kaydedilir. Bunu\n" +"kayıtlı bir nicklede eğer network adminleri buna izin veriyorsa\n" +"kullanabilirsiniz.\n" +"\n" +"Bir seferde sadece bir grupta olabilirsiniz. Grup karıştırma\n" +"mümkün değildir.\n" +"\n" +"Not: bir gruptaki tüm nickler bir şifreye sahip olurlar." + +#: modules/commands/ns_ajoin.cpp:292 +msgid "" +"This command manages your auto join list. When you identify\n" +"you will automatically join the channels on your auto join list.\n" +"Services Operators may provide a nick to modify other users'\n" +"auto join lists." +msgstr "" + +#: modules/commands/ns_set.cpp:345 modules/commands/ns_set.cpp:669 +msgid "" +"This command may not be used on this network because nickname ownership is " +"disabled." +msgstr "" + +#: modules/commands/os_module.cpp:118 +#, fuzzy +msgid "This command reloads the module named modname." +msgstr "" +"Syntax: MODLOAD FileName\n" +"This command loads the module named FileName from the modules\n" +"directory." + +#: modules/commands/hs_request.cpp:344 +msgid "This command retrieves the vhost requests." +msgstr "" + +#: modules/commands/os_logsearch.cpp:159 +msgid "" +"This command searches the Services logfiles for messages\n" +"that match the given pattern. The day and limit argument\n" +"may be used to specify how many days of logs to search\n" +"and the number of replies to limit to. By default this\n" +"command searches one week of logs, and limits replies\n" +"to 50.\n" +" \n" +"For example:\n" +" LOGSEARCH +21d +500l Anope\n" +" Searches the last 21 days worth of logs for messages\n" +" containing Anope and lists the most recent 500 of them." +msgstr "" + +#: modules/commands/cs_status.cpp:106 +msgid "" +"This command tells you what a users access is on a channel\n" +"and what access entries, if any, they match. Additionally it\n" +"will tell you of any auto kick entries they match. Usage of\n" +"this command is limited to users who have the ability to modify\n" +"access entries on the channel." +msgstr "" + +#: modules/commands/ns_group.cpp:285 +#, fuzzy +msgid "" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, and url. Everything else\n" +"is reset. You may not ungroup yourself if there is only one nick in\n" +"your group." +msgstr "" +"Syntax: UNGROUP [nick]\n" +"This command ungroups your nick, or if given, the specificed nick,\n" +"from the group it is in. The ungrouped nick keeps its registration\n" +"time, password, email, greet, language, url, and icq. Everything\n" +"else is reset. You may not ungroup yourself if there is only one\n" +"nick in your group." + +#: modules/commands/os_module.cpp:168 +#, fuzzy +msgid "This command unloads the module named modname." +msgstr "" +"Syntax: MODLOAD FileName\n" +"This command loads the module named FileName from the modules\n" +"directory." + +#: modules/commands/ns_register.cpp:353 +msgid "This command will resend you the registration confirmation email." +msgstr "" + +#: include/language.h:90 +#, c-format +msgid "" +"This nick is owned by someone else. Please choose another.\n" +"(If this is your nick, type %s%s IDENTIFY password.)" +msgstr "" + +#: modules/commands/os_forbid.cpp:469 +#, fuzzy, c-format +msgid "This nickname has been forbidden: %s" +msgstr "This nickname is currently suspended, reason: %s" + +#: modules/commands/ns_recover.cpp:99 +#, fuzzy, c-format +msgid "This nickname has been recovered by %s." +msgstr "This nickname is currently suspended, reason: %s" + +#: modules/commands/ns_recover.cpp:77 +#, c-format +msgid "" +"This nickname has been recovered by %s. If you did not do\n" +"this then %s may have your password, and you should change it." +msgstr "" + +#: include/language.h:95 +#, fuzzy +msgid "This nickname has been registered; you may not use it." +msgstr "Bu kanal %s ile kayıtlıdır." + +#: modules/commands/ns_suspend.cpp:246 +#, fuzzy +msgid "This nickname is suspended." +msgstr "Bu kanal kullanılamaz." + +#: include/language.h:92 +#, c-format +msgid "" +"This nickname is registered and protected. If it is your\n" +"nick, type %s%s IDENTIFY password. Otherwise,\n" +"please choose a different nick." +msgstr "" + +#: modules/commands/ms_read.cpp:95 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %d" +msgstr "" +"%d nolu mesaj %s nickinden (%s). Silmek için: /msg %s DEL %s %d yazın." + +#: modules/commands/ms_read.cpp:93 +#, fuzzy, c-format +msgid "To delete, type: %s%s %s %s %d" +msgstr "" +"%d nolu mesaj %s nickinden (%s). Silmek için: /msg %s DEL %s %d yazın." + +#: modules/commands/bs_kick.cpp:791 +msgid "To protect ops against bot kicks" +msgstr "" + +#: modules/commands/bs_kick.cpp:856 +msgid "To protect voices against bot kicks" +msgstr "" + +#: modules/commands/cs_list.cpp:46 +msgid "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." +msgstr "" +"To search for channels starting with #, search for the channel\n" +"name without the #-sign prepended (anope instead of #anope)." + +#: modules/commands/os_logsearch.cpp:139 +#, fuzzy, c-format +msgid "Too many results for %s." +msgstr "%s nickinin access listesi:" + +#: modules/extra/stats/cs_fantasy_top.cpp:149 +#, c-format +msgid "Top %i of %s" +msgstr "" + +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Topic" +msgstr "Topic kilidi" + +#: modules/commands/cs_topic.cpp:258 +#, fuzzy +msgid "Topic lock" +msgstr "Topic kilidi" + +#: modules/commands/cs_topic.cpp:114 +#, fuzzy, c-format +msgid "Topic lock option for %s is now off." +msgstr "Topic lock option for %s is now ON." + +#: modules/commands/cs_topic.cpp:97 +#, fuzzy, c-format +msgid "Topic lock option for %s is now on." +msgstr "Topic lock option for %s is now ON." + +#: modules/commands/cs_topic.cpp:256 +#, fuzzy +msgid "Topic retention" +msgstr "Topic hatırlama" + +#: modules/commands/cs_topic.cpp:60 +#, fuzzy, c-format +msgid "Topic retention option for %s is now off." +msgstr "Topic retention option for %s is now ON." + +#: modules/commands/cs_topic.cpp:54 +#, fuzzy, c-format +msgid "Topic retention option for %s is now on." +msgstr "Topic retention option for %s is now ON." + +#: modules/commands/cs_topic.cpp:265 +msgid "Topic set by" +msgstr "" + +#: modules/commands/bs_kick.cpp:1323 +msgid "Turn caps lock OFF!" +msgstr "Lütfen büyük harf kullanmayın!" + +#: modules/extra/stats/m_chanstats.cpp:17 +#: modules/extra/stats/m_chanstats.cpp:71 +#, fuzzy +msgid "Turn chanstats statistics on or off" +msgstr " SECURE Nick güvenliğini açar kapatır" + +#: modules/commands/ns_set.cpp:1009 +#, fuzzy +msgid "Turn nickname security on or off" +msgstr " SECURE Nick güvenliğini açar kapatır" + +#: modules/commands/ns_set.cpp:655 +#, fuzzy +msgid "Turn protection on or off" +msgstr " KILL Korumayı açar kapatır" + +#: modules/commands/ns_list.cpp:264 +#, fuzzy, c-format +msgid "" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Syntax: SASET nickname PRIVATE {ON | OFF}\n" +"\n" +"Turns %s's privacy option on or off for the nick.\n" +"With PRIVATE set, the nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows the nickname can still get\n" +"information on it using the INFO command.)" + +#: modules/commands/ns_list.cpp:236 +#, fuzzy, c-format +msgid "" +"Turns %s's privacy option on or off for your nick.\n" +"With PRIVATE set, your nickname will not appear in\n" +"nickname lists generated with %s's LIST command.\n" +"(However, anyone who knows your nickname can still get\n" +"information on it using the INFO command.)" +msgstr "" +"Kullanımı: SET PRIVATE {ON | OFF}\n" +"\n" +"%s'ün özel nick özelliğini açar kapatır. PRIVATE ayarı\n" +"ile, %s'ün LIST komutu kullanıldığında nickiniz listede\n" +"gözükmeyecektir.(Buna rağmen, nickinizi bilen biri INFO \n" +"komutunu kullanarak hakkınızda bilgi alabilir.)" + +#: modules/commands/ns_set.cpp:1059 modules/commands/ns_set.cpp:1088 +#, fuzzy, c-format +msgid "" +"Turns %s's security features on or off for your\n" +"nick. With SECURE set, you must enter your password\n" +"before you will be recognized as the owner of the nick,\n" +"regardless of whether your address is on the access\n" +"list. However, if you are on the access list, %s\n" +"will not auto-kill you regardless of the setting of the\n" +"KILL option." +msgstr "" +"Kullanımı: SET SECURE {ON | OFF}\n" +"\n" +"%s'ün güvenlik özelliklerini açar ve kapatır. SECURE \n" +"ayarı ile, nickin sahibi olarak tanınmanız için önce şifreyle \n" +"kendinizi tanıtmanız gerekir(adresinizin nickin access\n" +"listesinde olup olmamasına bağlı olarak). Fakat, eğer \n" +"adresiniz nickin access listesindeyse KILL özelliği\n" +"kullanılmış olsa bile %s sizi otomatik olarak kill\n" +"lemeyecektir." + +#: modules/extra/stats/m_chanstats.cpp:142 +#, fuzzy +msgid "Turns chanstats channel statistics ON or OFF for this user." +msgstr " SECURE Nick güvenliğini açar kapatır" + +#: modules/extra/stats/m_chanstats.cpp:61 +#: modules/extra/stats/m_chanstats.cpp:119 +#, fuzzy +msgid "Turns chanstats statistics ON or OFF." +msgstr " SECURE Nick güvenliğini açar kapatır" + +#: modules/commands/ns_set.cpp:772 +#, fuzzy, c-format +msgid "" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Syntax: SASET nickname KILL {ON | QUICK | IMMED | OFF}\n" +"\n" +"Turns the automatic protection option for the nick\n" +"on or off. With protection on, if another user\n" +"tries to take the nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +"\n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." + +#: modules/commands/ns_set.cpp:738 +#, fuzzy, c-format +msgid "" +"Turns the automatic protection option for your nick\n" +"on or off. With protection on, if another user\n" +"tries to take your nick, they will be given one minute to\n" +"change to another nick, after which %s will forcibly change\n" +"their nick.\n" +" \n" +"If you select QUICK, the user will be given only 20 seconds\n" +"to change nicks instead of the usual 60. If you select\n" +"IMMED, the user's nick will be changed immediately without being\n" +"warned first or given a chance to change their nick; please\n" +"do not use this option unless necessary. Also, your\n" +"network's administrators may have disabled this option." +msgstr "" +"Kullanımı: SET KILL {ON | QUICK | IMMED | OFF}\n" +"\n" +"Nickiniz için otomatik koruma özelliğini açar ve kapatır.\n" +"Koruma açıkken eğer bir başkası sizin nickinizi kullanmaya \n" +"kalkarsa, o kişiye nicki değiştirmesi için bir dakika süre \n" +"verilir, eğer değiştirmezse %s tarafından otomatik olarak\n" +"değiştirilir.\n" +"\n" +"Eğer QUICK parametresini seçerseniz, kullanıcıya nickini\n" +"değiştirmesi için 60 saniye yerine sadece 20 saniye verilir.\n" +"Eğer IMMED parametresini seçerseniz kullanıcının nicki\n" +"uyarılmadan hemen değiştirilir; lütfen çok gerekmedikçe\n" +"bu özelliği kullanmayın. Hatta network yöneticileri bu\n" +"özelliği devre dışı bırakmış olabilirler." + +#: modules/commands/bs_badwords.cpp:194 modules/commands/os_forbid.cpp:358 +msgid "Type" +msgstr "" + +#: modules/commands/ns_set.cpp:62 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option." +msgstr "" +"Belirli bir özellik hakkında daha fazla bilgi için\n" +"/msg %s HELP özellik yazın." + +#: modules/commands/bs_kick.cpp:151 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option.\n" +" \n" +"Note: access to this command is controlled by the\n" +"level SET." +msgstr "" +"Type /msg %s HELP SASET option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." + +#: modules/commands/ns_set.cpp:107 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." +msgstr "" +"Type /msg %s HELP SASET option for more information\n" +"on a specific option. The options will be set on the given\n" +"nickname." + +#: modules/commands/bs_set.cpp:62 modules/commands/cs_set.cpp:63 +#, fuzzy, c-format +msgid "" +"Type %s%s HELP %s option for more information on a\n" +"particular option." +msgstr "" +"Belirli bir özellik hakkında daha fazla bilgi için\n" +"/msg %s HELP özellik yazın." + +#: modules/pseudoclients/nickserv.cpp:361 +#, fuzzy, c-format +msgid "" +"Type %s%s SET EMAIL e-mail in order to set your e-mail.\n" +"Your privacy is respected; this e-mail won't be given to\n" +"any third-party person." +msgstr "" +"Mail adresinizi ayarlamak için /msg %s SET EMAIL e-mailadresiniz \n" +"yazın. Gizliliğiniz korunacaktır; bu mail adresi herhangi üçüncü \n" +"şahıslara verilmeyecektir." + +#: modules/commands/os_module.cpp:128 +#, fuzzy +msgid "Un-Load a module" +msgstr " MODUNLOAD Un-Load a module" + +#: modules/commands/os_sxline.cpp:337 modules/commands/os_sxline.cpp:552 +#: modules/commands/os_akill.cpp:136 +#, fuzzy, c-format +msgid "Unable to find regex engine %s." +msgstr "Unable to remove module %s" + +#: modules/commands/os_module.cpp:36 modules/commands/os_module.cpp:108 +#, fuzzy, c-format +msgid "Unable to load module %s." +msgstr "Unable to load module %s" + +#: modules/commands/os_module.cpp:73 modules/commands/os_module.cpp:90 +#: modules/commands/os_module.cpp:145 modules/commands/os_module.cpp:159 +#, fuzzy, c-format +msgid "Unable to remove module %s." +msgstr "Unable to remove module %s" + +#: modules/commands/bs_assign.cpp:90 +#, fuzzy +msgid "Unassigns a bot from a channel" +msgstr "UNASSIGN Unassigns a bot from a channel" + +#: modules/commands/bs_assign.cpp:139 +#, fuzzy +msgid "" +"Unassigns a bot from a channel. When you use this command,\n" +"the bot won't join the channel anymore. However, bot\n" +"configuration for the channel is kept, so you will always\n" +"be able to reassign a bot later without having to reconfigure\n" +"it entirely." +msgstr "" +"Kullanımı: UNASSIGN kanaladı\n" +"\n" +"Belirtilen kanaldan botu çıkarır. Bu komutu kullandıktan\n" +"sonra bot bir daha kanala girmeyecektir. Fakat yapılmış bot\n" +"ayarları saklanır, böylece istediğinz zaman tekrar ayar \n" +"yapmaya gerek olmadan kanala bot sokabilirsiniz." + +#: modules/commands/bs_kick.cpp:1191 modules/commands/bs_kick.cpp:1193 +#: modules/commands/bs_kick.cpp:1196 +#, fuzzy +msgid "Underlines kicker" +msgstr "Altıçizili yazıda atma : %s" + +#: modules/commands/os_dns.cpp:595 +#, fuzzy +msgid "Unknown SET option." +msgstr "Unknown SASET option %s." + +#: modules/commands/os_stats.cpp:229 +#, fuzzy, c-format +msgid "Unknown STATS option: %s" +msgstr "Varolmayan STATS özelliği: %s." + +#: src/command.cpp:222 src/command.cpp:233 +#, fuzzy, c-format +msgid "Unknown command %s." +msgstr "Varolmayan özellik %s." + +#: src/command.cpp:220 src/command.cpp:231 +#, fuzzy, c-format +msgid "Unknown command %s. \"%s%s HELP\" for help." +msgstr "Varolmayan komut %s. yardım için \"%s%s HELP\" yazınız." + +#: modules/commands/cs_mode.cpp:317 modules/commands/cs_mode.cpp:409 +#, fuzzy, c-format +msgid "Unknown mode character %c ignored." +msgstr "Varolmayan mod karakteri %c yoksayıldı." + +#: modules/commands/os_logsearch.cpp:78 +#, fuzzy, c-format +msgid "Unknown parameter: %s" +msgstr "SET özellik ayar" + +#: modules/commands/os_dns.cpp:241 +msgid "Unpooled" +msgstr "" + +#: modules/commands/cs_drop.cpp:77 +#, fuzzy +msgid "" +"Unregisters the named channel. Can only be used by\n" +"the channel founder." +msgstr "" +"Kullanımı: DROP kanaladı\n" +"\n" +"Kanalın kaydını siler." + +#: modules/commands/cs_drop.cpp:74 +#, fuzzy +msgid "" +"Unregisters the specified channel. Only Services Operators\n" +"can drop a channel of which they are not the founder of." +msgstr "" +"Kullanımı: DROP kanaladı\n" +"\n" +"Belirtilen kanalın kaydını siler. Sadece Servis adminleri\n" +"kanalı tanıtmadan kaydını silebilirler." + +#: modules/commands/ns_suspend.cpp:160 +#, fuzzy +msgid "Unsuspend a given nick" +msgstr " UNSUSPEND Unsuspend a given nick" + +#: modules/commands/ns_suspend.cpp:199 +msgid "Unsuspends a nickname which allows it to be used again." +msgstr "" + +#: modules/commands/cs_updown.cpp:126 +msgid "" +"Updates a selected nicks status modes on a channel. If nick is\n" +"omitted then your status is updated. If channel is omitted then\n" +"your channel status is updated on every channel you are in." +msgstr "" + +#: modules/commands/cs_updown.cpp:48 +#, fuzzy +msgid "Updates a selected nicks status on a channel" +msgstr " BAN Bans a selected nick on a channel" + +#: modules/commands/ns_update.cpp:19 +#, fuzzy +msgid "Updates your current status, i.e. it checks for new memos" +msgstr "" +" UPDATE Updates your current status, i.e. it checks for new memos" + +#: modules/commands/ns_update.cpp:43 +#, fuzzy +msgid "" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed channel modes and updates your vhost and\n" +"your userflags (lastseentime, etc)." +msgstr "" +"Syntax: UPDATE\n" +"Updates your current status, i.e. it checks for new memos,\n" +"sets needed chanmodes (ModeonID) and updates your vhost and\n" +"your userflags (lastseentime, etc)." + +#: modules/commands/os_update.cpp:25 +msgid "Updating databases." +msgstr "Veritabanı güncelleniyor." + +#: modules/commands/os_stats.cpp:154 +#, c-format +msgid "Uplink capab: %s" +msgstr "Uplink capab: %s" + +#: modules/commands/os_stats.cpp:153 +#, c-format +msgid "Uplink server: %s" +msgstr "Uplink server: %s" + +#: modules/commands/help.cpp:127 +#, c-format +msgid "Use the %s ALL command to list all commands and their descriptions." +msgstr "" + +#: modules/commands/bs_info.cpp:59 +msgid "Used on" +msgstr "" + +#: data/chanserv.example.conf:821 +#, fuzzy +msgid "Used to manage channels" +msgstr "%s changed your usermodes." + +#: data/chanserv.example.conf:809 +#, fuzzy +msgid "Used to manage the list of privileged users" +msgstr " ACCESS Ayrıcalıklı kullanıcıları belirler değiştirir" + +#: data/chanserv.example.conf:815 +msgid "Used to modify the channel status of you or other users" +msgstr "" + +#: modules/commands/cs_akick.cpp:575 +#, fuzzy +msgid "User has been banned from the channel" +msgstr "%s kanalındaki banınız kaldırıldı." + +#: modules/commands/os_dns.cpp:587 +#, fuzzy, c-format +msgid "User limit for %s removed." +msgstr "vhost for %s removed." + +#: modules/commands/os_dns.cpp:585 +#, fuzzy, c-format +msgid "User limit for %s set to %d." +msgstr "%s nickinin mesaj limiti %d olarak ayarlandı." + +#: modules/commands/os_list.cpp:43 +#, fuzzy +msgid "Users" +msgstr "Bot listesi:" + +#: modules/commands/os_stats.cpp:172 +#, c-format +msgid "Users (nick): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_stats.cpp:177 +#, c-format +msgid "Users (uid): %lu entries, %lu buckets, longest chain is %d" +msgstr "" + +#: modules/commands/os_list.cpp:184 +#, fuzzy +msgid "Users list:" +msgstr "Bot listesi:" + +#: modules/commands/ns_info.cpp:105 modules/commands/ns_info.cpp:107 +msgid "VHost" +msgstr "" + +#: modules/commands/hs_set.cpp:92 +#, fuzzy, c-format +msgid "VHost for %s set to %s." +msgstr "vhost for %s set to %s." + +#: modules/commands/hs_set.cpp:90 +#, fuzzy, c-format +msgid "VHost for %s set to %s@%s." +msgstr "vhost for %s set to %s@%s." + +#: modules/commands/hs_set.cpp:199 +#, fuzzy, c-format +msgid "VHost for group %s set to %s." +msgstr "vhost for group %s set to %s." + +#: modules/commands/hs_set.cpp:197 +#, fuzzy, c-format +msgid "VHost for group %s set to %s@%s." +msgstr "vhost for group %s set to %s@%s." + +#: modules/commands/os_session.cpp:247 +msgid "VIEW host" +msgstr "" + +#: modules/commands/os_sxline.cpp:428 modules/commands/os_sxline.cpp:662 +#: modules/commands/os_akill.cpp:389 +#, fuzzy +msgid "VIEW [mask | list | id]" +msgstr "LIST [kanaladı] [liste | NEW]" + +#: modules/commands/os_session.cpp:526 +msgid "VIEW [mask | list]" +msgstr "" + +#: modules/commands/os_config.cpp:66 modules/commands/os_config.cpp:88 +msgid "Value" +msgstr "" + +#: modules/commands/os_config.cpp:48 +#, fuzzy, c-format +msgid "Value of %s:%s changed to %s" +msgstr "%s kanalının founderı %s olarak değiştirildi." + +#: modules/commands/hs_list.cpp:58 modules/commands/hs_request.cpp:305 +msgid "Vhost" +msgstr "" + +#: modules/commands/hs_del.cpp:38 +#, fuzzy, c-format +msgid "Vhost for %s removed." +msgstr "vhost for %s removed." + +#: modules/commands/os_oper.cpp:69 +#, fuzzy +msgid "View and change Services Operators" +msgstr "%s is a services operator of type %s." + +#: modules/commands/os_config.cpp:19 +msgid "View and change configuration file settings" +msgstr "" + +#: modules/commands/os_session.cpp:245 +#, fuzzy +msgid "View the list of host sessions" +msgstr " SESSION Host session(oturum) ların listesini gösterir" + +#: modules/commands/bs_kick.cpp:1221 +msgid "Voices protection" +msgstr "Voiceları koruma" + +#: modules/commands/bs_kick.cpp:1406 +msgid "Watch your language!" +msgstr "Konuşmalarına dikkat et!" + +#: modules/commands/cs_list.cpp:237 +#, c-format +msgid "" +"When private is set, the channel will not appear in\n" +"%s's %s command." +msgstr "" + +#: modules/commands/ms_info.cpp:204 +#, fuzzy +msgid "" +"Without a parameter, displays information on the number of\n" +"memos you have, how many of them are unread, and how many\n" +"total memos you can receive.\n" +" \n" +"With a channel parameter, displays the same information for\n" +"the given channel.\n" +" \n" +"With a nickname parameter, displays the same information\n" +"for the given nickname. This is limited to Services\n" +"Operators." +msgstr "" +"Kullanımı: INFO [nick | kanaladı]\n" +"\n" +"Parametre kullanılmazsa, sahip olduğunuz mesajları, kaç \n" +"tanesinin okunmamış olduğunu, ve toplam kaç tane mesaj \n" +"alabileceğiniz hakkında bilgiler verir.\n" +"\n" +"Kanaladı parametresiyle, aynı bilgiyi belirtilen kanal\n" +"için verir.\n" +"\n" +"Nick parametresiyle, aynı bilgiyi belirtilen nick için\n" +"verir. Kullanımı Servis adminleriyle sınırlıdır." + +#: modules/commands/ns_logout.cpp:66 +#, fuzzy +msgid "" +"Without a parameter, reverses the effect of the IDENTIFY\n" +"command, i.e. make you not recognized as the real owner of the nick\n" +"anymore. Note, however, that you won't be asked to reidentify\n" +"yourself.\n" +" \n" +"With a parameter, does the same for the given nick. If you\n" +"specify REVALIDATE as well, Services will ask the given nick\n" +"to re-identify. This is limited to Services Operators." +msgstr "" +"Kullanımı: LOGOUT [nick [REVALIDATE]]\n" +"\n" +"Parametre kullanılmazsa, IDENTIFY komutunun yaptığı \n" +"etkiyi tersine çevirir, yani artık o nickin gerçek sahibi\n" +"olarak tanınmamanızı sağlar. Fakat sizden nickinizi tekrar\n" +"identify etmeniz istenmez.\n" +"\n" +"Parametre kullanılırsada aynısını yapar ama buna ek olarak\n" +"REVALIDATE belirtilirse servisler o kişiye nickini yeniden \n" +"identify etmesini söyler. Servis adminlerinin Kullanımıyla\n" +"sınırlıdır." + +#: modules/commands/os_stats.cpp:236 +#, fuzzy +msgid "" +"Without any option, shows the current number of users online,\n" +"and the highest number of users online since Services was\n" +"started, and the length of time Services has been running.\n" +" \n" +"With the AKILL option, displays the current size of the\n" +"AKILL list and the current default expiry time.\n" +" \n" +"The RESET option currently resets the maximum user count\n" +"to the number of users currently present on the network.\n" +" \n" +"The UPLINK option displays information about the current\n" +"server Anope uses as an uplink to the network.\n" +" \n" +"The HASH option displays information about the hash maps.\n" +" \n" +"The ALL option displays all of the above statistics." +msgstr "" +"Kullanımı: STATS [AKILL | ALL | RESET]\n" +"\n" +"Hiçbir parametre yokken, mevcut kullanıcı sayısını ve online\n" +"olan IRCopları(Servisler hariç), Servisler başlatıldığından \n" +"beri bağlı olan en fazla kullanıcı sayısını, ve servislerin\n" +"çalışma süresini gösterir.\n" +"\n" +"AKILL parametresiyle, mevcut AKILL listesini ve o anki \n" +"varsayılan zaman aşımı süresini gösterir.\n" +"\n" +"ALL parametresi sadece Servis adminleri tarafından \n" +"kullanılabilir, ve servislerin kullandığı hafıza(memory) \n" +"hakkında bilgi verir. Büyük networklerde bu komutun kullanılması\n" +"servisleri kısa bir süre dondurabilir, bu yüzden tekrar kullanmaya\n" +"kalkmayın!\n" +"\n" +"RESET parametresi önceki maksimum kullanıcı sayısını o anda\n" +"networkte bulunan kullanıcı sayısıyla değiştirir." + +#: modules/commands/bs_badwords.cpp:194 +msgid "Word" +msgstr "" + +#: modules/commands/ns_group.cpp:158 +#, c-format +msgid "You are already a member of the group of %s." +msgstr "%s grubunun zaten bir üyesisiniz." + +#: modules/commands/os_login.cpp:34 modules/commands/ns_identify.cpp:87 +msgid "You are already identified." +msgstr "You are already identified." + +#: modules/commands/cs_invite.cpp:64 +#, fuzzy, c-format +msgid "You are already in %s!" +msgstr "You are already in %s! " + +#: modules/commands/os_set.cpp:91 +#, fuzzy +msgid "You are no longer a super admin." +msgstr "You are no longer a SuperAdmin" + +#: modules/commands/os_login.cpp:81 +#, fuzzy +msgid "You are not identified." +msgstr "You are already identified." + +#: include/language.h:100 +#, fuzzy +msgid "You are not permitted to be on this channel." +msgstr "Mesaj limitinizi belirlemeye izinli değilsiniz." + +#: modules/commands/ms_set.cpp:158 +msgid "You are not permitted to change your memo limit." +msgstr "Mesaj limitinizi belirlemeye izinli değilsiniz." + +#: modules/commands/ns_cert.cpp:183 +#, fuzzy +msgid "You are not using a client certificate." +msgstr "You are already identified." + +#: modules/commands/os_set.cpp:85 +#, fuzzy +msgid "You are now a super admin." +msgstr "You are now a SuperAdmin" + +#: modules/commands/os_oline.cpp:36 +msgid "You are now an IRC Operator." +msgstr "You are now an IRC Operator." + +#: modules/commands/ns_resetpass.cpp:108 +#, fuzzy +msgid "You are now identified for your nick. Change your password now." +msgstr "You are now identified for your nick. Change your password now." + +#: modules/commands/ns_group.cpp:64 +#, c-format +msgid "You are now in the group of %s." +msgstr "%s grubuna dahil edildiniz." + +#: modules/pseudoclients/memoserv.cpp:147 +#, fuzzy, c-format +msgid "" +"You are over your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Dikkat: Maksimum mesaj sayınızı aştınız (%d). Şimdiki mesajlarınızdan bir " +"kaçını silmezseniz yeni mesaj alamayacaksınız." + +#: modules/commands/os_noop.cpp:33 +msgid "You can not NOOP Services." +msgstr "" + +#: modules/commands/cs_access.cpp:672 +msgid "" +"You can not disable the founder privilege because it would be impossible to " +"reenable it at a later time." +msgstr "" + +#: modules/commands/os_jupe.cpp:34 +#, fuzzy +msgid "You can not jupe an already juped server." +msgstr "You can not jupe your services server or your uplink server." + +#: modules/commands/os_jupe.cpp:32 +#, fuzzy +msgid "You can not jupe your Services' pseudoserver or your uplink server." +msgstr "You can not jupe your services server or your uplink server." + +#: modules/commands/os_module.cpp:80 +#, c-format +msgid "You can not reload this module directly, instead reload %s." +msgstr "" + +#: modules/commands/ms_rsend.cpp:46 +msgid "You can not request a receipt when sending a memo to yourself." +msgstr "You can not request a receipt when sending a memo to yourself." + +#: modules/commands/ns_recover.cpp:163 +#, fuzzy, c-format +msgid "You can't %s yourself!" +msgstr "Kendinizi ghost edemezsiniz!" + +#: modules/commands/cs_access.cpp:154 modules/commands/cs_flags.cpp:109 +#: modules/commands/cs_xop.cpp:151 +#, fuzzy +msgid "You can't add a channel to its own access list." +msgstr "Uyuşan kayıt %s kanalının access listesinde yok." + +#: modules/commands/ns_logout.cpp:37 +#, fuzzy, c-format +msgid "You can't logout %s, they are a Services Operator." +msgstr "Can't logout %s because he's a Services Operator." + +#: modules/commands/ns_set.cpp:927 +#, fuzzy, c-format +msgid "You cannot %s on this network." +msgstr "E-mail adresini bu networkte silemezsiniz." + +#: modules/commands/cs_flags.cpp:231 +#, fuzzy, c-format +msgid "You cannot set the %c flag." +msgstr "You cannot use this command." + +#: modules/commands/ms_set.cpp:173 +#, c-format +msgid "You cannot set the memo limit for %s higher than %d." +msgstr "%s nickinin mesaj limitini %d sayısından daha fazla yapamazsınız." + +#: modules/commands/ms_set.cpp:175 +#, c-format +msgid "You cannot set your memo limit higher than %d." +msgstr "Mesaj limitinizi %d sayısından daha fazla yapamazsınız." + +#: modules/commands/bs_assign.cpp:124 +#, fuzzy +msgid "You cannot unassign bots while persist is set on the channel." +msgstr "You can not unassign bots while persist is set on the channel." + +#: modules/commands/ns_set.cpp:480 +msgid "You cannot unset the e-mail on this network." +msgstr "E-mail adresini bu networkte silemezsiniz." + +#: modules/commands/help.cpp:177 +msgid "You cannot use this command." +msgstr "You cannot use this command." + +#: modules/commands/ms_info.cpp:151 +#, c-format +msgid "You currently have %d memos, of which %d are unread." +msgstr "Şu an %d mesajınız var, %d tanesi okunmamış." + +#: modules/commands/ms_info.cpp:149 +#, c-format +msgid "You currently have %d memos, of which 1 is unread." +msgstr "Şu an %d mesajınız var, 1 tanesi okunmamış." + +#: modules/commands/ms_info.cpp:147 +#, c-format +msgid "You currently have %d memos." +msgstr "Şu an %d mesajınız var." + +#: modules/commands/ms_info.cpp:145 +#, c-format +msgid "You currently have %d memos; all of them are unread." +msgstr "Şu an %d mesajınız var; hiçbiri okunmamış." + +#: modules/commands/ms_info.cpp:134 +msgid "You currently have 1 memo, and it has not yet been read." +msgstr "Şu an 1 mesajınız var, ve henüz okunmadı." + +#: modules/commands/ms_info.cpp:136 +msgid "You currently have 1 memo." +msgstr "Şu an 1 mesajınız var." + +#: modules/commands/ms_info.cpp:130 +msgid "You currently have no memos." +msgstr "Şu an hiç mesajınız yok." + +#: modules/commands/cs_mode.cpp:564 modules/commands/cs_mode.cpp:621 +#, c-format +msgid "You do not have access to set mode %c." +msgstr "" + +#: modules/commands/cs_mode.cpp:578 modules/commands/cs_mode.cpp:590 +#: modules/commands/cs_mode.cpp:631 +#, c-format +msgid "You do not have the access to change %s's modes." +msgstr "" + +#: modules/commands/cs_seen.cpp:198 +#, c-format +msgid "You found me, %s!" +msgstr "" + +#: modules/pseudoclients/memoserv.cpp:143 +#, c-format +msgid "You have %d new memos." +msgstr "%d yeni mesajınız var." + +#: modules/pseudoclients/memoserv.cpp:143 +msgid "You have 1 new memo." +msgstr "1 yeni mesajınız var." + +#: include/language.h:112 +#, fuzzy, c-format +msgid "" +"You have a new memo from %s.\n" +"Type %s%s READ %d to read it." +msgstr "Okumak için /msg %s READ %d yazın." + +#: modules/commands/cs_invite.cpp:76 +#, fuzzy, c-format +msgid "You have been invited to %s by %s." +msgstr "You have been invited to %s." + +#: modules/commands/cs_invite.cpp:81 +#, c-format +msgid "You have been invited to %s." +msgstr "You have been invited to %s." + +#: modules/protocol/ratbox.cpp:166 modules/commands/ns_recover.cpp:96 +#, fuzzy, c-format +msgid "You have been logged in as %s." +msgstr "Nickinizin çıkışı yapıldı." + +#: modules/commands/os_login.cpp:86 +#, fuzzy +msgid "You have been logged out." +msgstr "Nickinizin çıkışı yapıldı." + +#: modules/commands/cs_unban.cpp:94 +#, c-format +msgid "You have been unbanned from %s." +msgstr "%s kanalındaki banınız kaldırıldı." + +#: modules/commands/cs_unban.cpp:54 +#, fuzzy, c-format +msgid "You have been unbanned from %d channels." +msgstr "%s kanalındaki banınız kaldırıldı." + +#: modules/commands/ms_info.cpp:169 +msgid "You have no limit on the number of memos you may keep." +msgstr "Saklayabileceğiniz mesaj sayısında limit yok." + +#: include/language.h:114 +#, fuzzy +msgid "You have no memos." +msgstr "%d yeni mesajınız var." + +#: include/language.h:117 +#, fuzzy +msgid "You have no new memos." +msgstr "%d yeni mesajınız var." + +#: modules/pseudoclients/memoserv.cpp:149 +#, fuzzy, c-format +msgid "" +"You have reached your maximum number of memos (%d). You will be unable to " +"receive any new memos until you delete some of your current ones." +msgstr "" +"Dikkat: Maksimum mesaj sayınıza ulaştınız (%d). Şimdiki mesajlarınızdan bir " +"kaçını silmezseniz yeni mesaj alamayacaksınız." + +#: modules/commands/ns_recover.cpp:117 +#, fuzzy, c-format +msgid "You have regained control of %s." +msgstr "You have been invited to %s." + +#: modules/commands/ns_drop.cpp:66 +#, fuzzy +msgid "You may drop any nick within your group." +msgstr " DELALL Delete the vhost for all nicks in a group" + +#: modules/commands/cs_mode.cpp:322 modules/commands/cs_mode.cpp:414 +#, c-format +msgid "You may not (un)lock mode %c." +msgstr "" + +#: modules/commands/ns_set.cpp:485 +#, fuzzy +msgid "You may not change the e-mail of other Services Operators." +msgstr "E-mail adresini bu networkte silemezsiniz." + +#: modules/commands/ns_set.cpp:474 +#, fuzzy +msgid "You may not change the email of an unconfirmed account." +msgstr "E-mail adresini bu networkte silemezsiniz." + +#: modules/commands/ns_set.cpp:196 +#, fuzzy +msgid "You may not change the password of other Services Operators." +msgstr "Can't logout %s because he's a Services Operator." + +#: modules/commands/ns_drop.cpp:45 +#, fuzzy +msgid "You may not drop other Services Operators' nicknames." +msgstr "%s is a services operator of type %s." + +#: modules/commands/ns_getpass.cpp:32 +#, fuzzy +msgid "You may not get the password of other Services Operators." +msgstr "Can't logout %s because he's a Services Operator." + +#: modules/commands/ns_suspend.cpp:100 +#, fuzzy +msgid "You may not suspend other Services Operators' nicknames." +msgstr "Can't logout %s because he's a Services Operator." + +#: modules/commands/ns_access.cpp:136 +#, fuzzy +msgid "" +"You may view but not modify the access list of other Services Operators." +msgstr "Can't logout %s because he's a Services Operator." + +#: modules/commands/ns_cert.cpp:292 +#, fuzzy +msgid "" +"You may view but not modify the certificate list of other Services Operators." +msgstr "Can't logout %s because he's a Services Operator." + +#: modules/commands/cs_seen.cpp:287 +#, c-format +msgid "You might see yourself in the mirror, %s." +msgstr "" + +#: include/language.h:120 +msgid "You must assign a bot to the channel before using this command." +msgstr "" + +#: modules/commands/cs_register.cpp:49 +msgid "You must be a channel operator to register the channel." +msgstr "" +"Kanal kayıt edebilmeniz için kayıt edilmemiş bir kanala ilk girip op olmanız " +"gerekmektedir." + +#: modules/commands/cs_updown.cpp:94 modules/commands/cs_updown.cpp:192 +#, fuzzy, c-format +msgid "You must be in %s to use this command." +msgstr "You need to be identified to use this command." + +#: modules/commands/cs_register.cpp:37 +#, fuzzy +msgid "You must confirm your account before you can register a channel." +msgstr "" +"Kanal kayıt edebilmeniz için kayıt edilmemiş bir kanala ilk girip op olmanız " +"gerekmektedir." + +#: modules/commands/hs_request.cpp:100 +#, fuzzy +msgid "You must confirm your account before you may request a vhost." +msgstr "" +"Kanal kayıt edebilmeniz için kayıt edilmemiş bir kanala ilk girip op olmanız " +"gerekmektedir." + +#: modules/commands/ms_send.cpp:44 +#, fuzzy +msgid "You must confirm your account before you may send a memo." +msgstr "" +"Kanal kayıt edebilmeniz için kayıt edilmemiş bir kanala ilk girip op olmanız " +"gerekmektedir." + +#: modules/commands/cs_drop.cpp:42 +#, c-format +msgid "" +"You must enter the channel name twice as a confirmation that you wish to drop" +" %s." +msgstr "" + +#: modules/commands/ns_register.cpp:153 +#, c-format +msgid "You must have been using this nick for at least %d seconds to register." +msgstr "You have to be connected longer than %d seconds to register your nick." + +#: modules/commands/cs_mode.cpp:913 +#, fuzzy, c-format +msgid "You must have the %s(ME) privilege on the channel to use this command." +msgstr "You need to be identified to use this command." + +#: modules/pseudoclients/nickserv.cpp:358 +msgid "" +"You must now supply an e-mail for your nick.\n" +"This e-mail will allow you to retrieve your password in\n" +"case you forget it." +msgstr "" +"Şimdi nickiniz için bir e-mail adresi belirtmelisiniz.\n" +"Bu e-mail adresi şifrenizi unutmanız halinde şifrenizi\n" +"isterken kullanılacaktır." + +#: modules/commands/help.cpp:172 +msgid "You need to be identified to use this command." +msgstr "You need to be identified to use this command." + +#: modules/commands/ms_info.cpp:182 +#, fuzzy +msgid "You will be notified by message and by mail when new memos arrive." +msgstr "Yeni mesajlar için ulaştıkları anda uyarılacaksınız." + +#: modules/commands/ms_info.cpp:175 +#, fuzzy +msgid "" +"You will be notified of new memos at logon and when they arrive, and by mail " +"when they arrive." +msgstr "" +"Yeni mesajlar için bağlandığınızda ve size ulaştığında uyarılacaksınız." + +#: modules/commands/ms_info.cpp:177 +msgid "You will be notified of new memos at logon and when they arrive." +msgstr "" +"Yeni mesajlar için bağlandığınızda ve size ulaştığında uyarılacaksınız." + +#: modules/commands/ms_info.cpp:189 +#, fuzzy +msgid "" +"You will be notified of new memos at logon, and by mail when they arrive." +msgstr "" +"Yeni mesajlar için bağlandığınızda ve size ulaştığında uyarılacaksınız." + +#: modules/commands/ms_info.cpp:191 +msgid "You will be notified of new memos at logon." +msgstr "Yeni mesajlar için bağlandığınızda uyarılacaksınız." + +#: modules/commands/ms_info.cpp:184 +msgid "You will be notified when new memos arrive." +msgstr "Yeni mesajlar için ulaştıkları anda uyarılacaksınız." + +#: modules/commands/ms_set.cpp:190 +msgid "You will no longer be able to receive memos." +msgstr "Limitiniz sıfır olduğundan artık mesaj alamayacaksınız." + +#: modules/commands/ms_set.cpp:57 +msgid "You will no longer be informed via email." +msgstr "You will no longer be informed via email." + +#: modules/commands/ms_info.cpp:195 +msgid "You will not be notified of new memos." +msgstr "Yeni mesajlar için uyarılmayacaksınız." + +#: modules/commands/ms_set.cpp:49 +msgid "You will now be informed about new memos via email." +msgstr "You will now be informed about new memos via email." + +#: modules/commands/os_svs.cpp:86 +msgid "Your IRCd does not support SVSJOIN." +msgstr "" + +#: modules/commands/os_svs.cpp:31 +msgid "Your IRCd does not support SVSNICK." +msgstr "" + +#: modules/commands/os_svs.cpp:130 +msgid "Your IRCd does not support SVSPART." +msgstr "" + +#: include/language.h:127 +msgid "" +"Your IRCd does not support vIdent's, if this is incorrect, please report " +"this as a possible bug" +msgstr "" + +#: modules/extra/m_ldap_authentication.cpp:110 +#: modules/extra/m_sql_authentication.cpp:55 +#, fuzzy, c-format +msgid "Your account %s has been successfully created." +msgstr "%s botu silindi." + +#: modules/commands/ns_register.cpp:328 +#, fuzzy +msgid "Your account is already confirmed." +msgstr "You are already identified." + +#: modules/commands/ns_register.cpp:396 +#, fuzzy, c-format +msgid "Your account will expire, if not confirmed, in %s." +msgstr "You are already identified." + +#: modules/commands/ns_set.cpp:1274 +#, fuzzy, c-format +msgid "Your email address has been changed to %s." +msgstr "E-mail address for %s changed to %s." + +#: modules/commands/os_forbid.cpp:544 modules/commands/os_forbid.cpp:553 +#, fuzzy +msgid "Your email address is not allowed, choose a different one." +msgstr "%s serverındaki tüm O:line lar silindi." + +#: modules/commands/ns_register.cpp:260 modules/commands/ns_register.cpp:391 +msgid "" +"Your email address is not confirmed. To confirm it, follow the instructions " +"that were emailed to you." +msgstr "" + +#: modules/commands/ns_register.cpp:67 +#, fuzzy, c-format +msgid "Your email address of %s has been confirmed." +msgstr "%s serverındaki tüm O:line lar silindi." + +#: modules/extra/m_ldap_authentication.cpp:159 +#, fuzzy, c-format +msgid "Your email has been updated to %s" +msgstr "E-mail address for %s changed to %s." + +#: modules/extra/m_sql_authentication.cpp:62 +#, fuzzy, c-format +msgid "Your email has been updated to %s." +msgstr "E-mail address for %s changed to %s." + +#: modules/commands/ms_set.cpp:197 +msgid "Your memo limit has been disabled." +msgstr "Mesaj limitiniz kapatıldı." + +#: modules/commands/ms_set.cpp:183 +#, c-format +msgid "Your memo limit has been set to %d." +msgstr "Mesaj limitiniz %d olarak ayarlandı." + +#: modules/commands/ms_info.cpp:164 +#, c-format +msgid "Your memo limit is %d, and may not be changed." +msgstr "Mesaj limitiniz %d, ve değiştirilemez." + +#: modules/commands/ms_info.cpp:166 +#, c-format +msgid "Your memo limit is %d." +msgstr "Mesaj limitiniz %d." + +#: modules/commands/ms_info.cpp:159 +msgid "Your memo limit is 0; you will not receive any new memos." +msgstr "Mesaj limitiniz 0; hiç mesaj alamayacaksınız." + +#: modules/commands/ms_info.cpp:157 +#, fuzzy +msgid "" +"Your memo limit is 0; you will not receive any new memos. You cannot change " +"this limit." +msgstr "" +"Mesaj limitiniz 0; hiç yeni mesaj alamayacaksınız. Bu limiti " +"değiştiremezsiniz." + +#: modules/commands/ns_logout.cpp:50 +msgid "Your nick has been logged out." +msgstr "Nickinizin çıkışı yapıldı." + +#: modules/commands/ns_group.cpp:156 +#, fuzzy +msgid "Your nick is already registered." +msgstr "Nickiniz zaten kayıtlı; önce /msg %s DROP yazın." + +#: modules/commands/ns_group.cpp:246 +msgid "Your nick is not grouped to anything, you can't ungroup it." +msgstr "Your nick is not grouped to anything, you can't ungroup it." + +#: include/language.h:77 +#, fuzzy +msgid "Your nick isn't registered." +msgstr "Nickname %s registered." + +#: modules/pseudoclients/nickserv.cpp:254 +#, c-format +msgid "Your nickname is now being changed to %s" +msgstr "Nickiniz %s olarak değiştirildi." + +#: modules/commands/os_login.cpp:32 modules/commands/os_login.cpp:79 +msgid "Your oper block doesn't require logging in." +msgstr "" + +#: modules/commands/ns_register.cpp:336 +#, c-format +msgid "Your passcode has been re-sent to %s." +msgstr "Your passcode has been re-sent to %s." + +#: modules/commands/ns_register.cpp:232 +#, c-format +msgid "Your password is %s - remember this for later use." +msgstr "" +"Nick Şifreniz %s - İlerde kullanacağınız için unutmayınız ve kimseye " +"söylemeyiniz." + +#: include/language.h:76 +#, c-format +msgid "Your password is too long. It must not exceed %u characters." +msgstr "" + +#: modules/commands/ns_resetpass.cpp:96 +msgid "Your password reset request has expired." +msgstr "Your password reset request has expired." + +#: modules/commands/hs_request.cpp:170 +#, fuzzy +msgid "Your vHost has been requested." +msgstr "%s botu silindi." + +#: modules/pseudoclients/hostserv.cpp:64 +#: modules/pseudoclients/hostserv.cpp:103 modules/commands/hs_on.cpp:37 +#, c-format +msgid "Your vhost of %s is now activated." +msgstr "Your vhost of %s is now activated." + +#: modules/pseudoclients/hostserv.cpp:62 +#: modules/pseudoclients/hostserv.cpp:101 modules/commands/hs_on.cpp:35 +#, c-format +msgid "Your vhost of %s@%s is now activated." +msgstr "Your vhost of %s@%s is now activated." + +#: modules/commands/hs_off.cpp:39 +msgid "Your vhost was removed and the normal cloaking restored." +msgstr "Your vhost was removed and the normal cloaking restored." + +#: modules/commands/os_dns.cpp:255 +#, fuzzy +msgid "Zone" +msgstr "YOK" + +#: modules/commands/os_dns.cpp:290 +#, fuzzy, c-format +msgid "Zone %s already exists." +msgstr "%s nickli bot zaten var." + +#: modules/commands/os_dns.cpp:310 modules/commands/os_dns.cpp:352 +#: modules/commands/os_dns.cpp:402 modules/commands/os_dns.cpp:438 +#, fuzzy, c-format +msgid "Zone %s does not exist." +msgstr "%s nickli bot zaten var." + +#: modules/commands/os_dns.cpp:332 +#, fuzzy, c-format +msgid "Zone %s removed." +msgstr "vhost for %s removed." + +#: modules/commands/os_defcon.cpp:177 +#, fuzzy +msgid "[1|2|3|4|5]" +msgstr "DEFCON [1|2|3|4|5]" + +#: modules/commands/os_news.cpp:400 +#, c-format +msgid "[Logon News - %s] %s" +msgstr "[Bağlantı Haberleri - %s] %s" + +#: modules/commands/os_news.cpp:402 +#, c-format +msgid "[Oper News - %s] %s" +msgstr "[Operatör Haberleri - %s] %s" + +#: modules/commands/os_news.cpp:404 +#, c-format +msgid "[Random News - %s] %s" +msgstr "[Karisik Haberler - %s] %s" + +#: modules/commands/ns_identify.cpp:66 +#, fuzzy +msgid "[account] password" +msgstr "IDENTIFY şifreniz" + +#: modules/commands/cs_updown.cpp:49 modules/commands/cs_updown.cpp:147 +#, fuzzy +msgid "[channel [nick]]" +msgstr "OP #channel [nick]" + +#: modules/commands/ms_ignore.cpp:20 +#, fuzzy +msgid "[channel] ADD entry" +msgstr "AOP kanal {ADD|DEL|LIST|CLEAR} [nick | liste-no]" + +#: modules/commands/ms_ignore.cpp:21 +#, fuzzy +msgid "[channel] DEL entry" +msgstr "MODE kanaladı modlar" + +#: modules/commands/ms_ignore.cpp:22 +#, fuzzy +msgid "[channel] LIST" +msgstr "DROP kanaladı" + +#: modules/commands/ms_list.cpp:20 +#, fuzzy +msgid "[channel] [list | NEW]" +msgstr "LIST [kanaladı] [liste | NEW]" + +#: modules/extra/stats/cs_fantasy_stats.cpp:40 +#, fuzzy +msgid "[channel] [nick]" +msgstr "OP #channel [nick]" + +#: modules/commands/ms_del.cpp:45 +#, fuzzy +msgid "[channel] {num | list | LAST | ALL}" +msgstr "DEL [kanaladı] {num | liste | ALL}" + +#: modules/commands/ms_read.cpp:113 +#, fuzzy +msgid "[channel] {num | list | LAST | NEW | ALL}" +msgstr "DEL [kanaladı] {num | liste | ALL}" + +#: modules/commands/hs_list.cpp:20 +msgid "[key|#X-Y]" +msgstr "" + +#: modules/commands/ms_info.cpp:20 +#, fuzzy +msgid "[nick | channel]" +msgstr "CANCEL {nick | kanaladı}" + +#: modules/commands/ns_group.cpp:237 +#, fuzzy +msgid "[nick]" +msgstr "INFO nick" + +#: modules/commands/ns_logout.cpp:22 +msgid "[nickname [REVALIDATE]]" +msgstr "" + +#: modules/commands/ns_alist.cpp:25 modules/commands/ns_status.cpp:20 +#: modules/commands/ns_info.cpp:20 +#, fuzzy +msgid "[nickname]" +msgstr "CHECK nickname" + +#: modules/commands/ns_set_misc.cpp:96 +msgid "[parameter]" +msgstr "" + +#: modules/commands/os_logsearch.cpp:33 +msgid "[+daysd] [+limitl] pattern" +msgstr "" + +#: modules/commands/os_chankill.cpp:22 +#, fuzzy +msgid "[+expiry] channel reason" +msgstr "CHANKILL [+expiry] {#channel} [reason]" + +#: modules/commands/ns_list.cpp:110 +msgid "[Hostname hidden]" +msgstr "" + +#: modules/commands/ns_list.cpp:112 modules/commands/cs_list.cpp:115 +msgid "[Suspended]" +msgstr "" + +#: modules/commands/ns_list.cpp:114 +msgid "[Unconfirmed]" +msgstr "" + +#: modules/commands/hs_request.cpp:213 +#, fuzzy +msgid "[auto memo] Your requested vHost has been approved." +msgstr "[auto-memo] The memo you sent to %s has been viewed." + +#: modules/commands/hs_request.cpp:267 +#, fuzzy +msgid "[auto memo] Your requested vHost has been rejected." +msgstr "[auto-memo] The memo you sent to %s has been viewed." + +#: modules/commands/hs_request.cpp:265 +#, c-format +msgid "[auto memo] Your requested vHost has been rejected. Reason: %s" +msgstr "" + +#: modules/commands/hs_request.cpp:388 +#, fuzzy, c-format +msgid "[auto memo] vHost %s has been requested by %s." +msgstr "%s nickine gönderilen son mesaj iptal edildi." + +#: modules/commands/os_list.cpp:133 +msgid "[{pattern | channel} [INVISIBLE]]" +msgstr "" + +#: modules/commands/os_list.cpp:20 +msgid "[{pattern | nick} [SECRET]]" +msgstr "" + +#: src/misc.cpp:337 +msgid "day" +msgstr "" + +#: src/misc.cpp:337 +msgid "days" +msgstr "" + +#: include/language.h:88 +#, fuzzy +msgid "does not expire" +msgstr " %s (does not expire)" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d day" +msgstr "%d gün sonra zaman aşımı süresi dolacak" + +#: src/misc.cpp:384 +#, c-format +msgid "expires in %d days" +msgstr "%d gün sonra zaman aşımı süresi dolacak" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minute" +msgstr "%d saat, %d dakika sonra zaman aşımı süresi dolacak" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hour, %d minutes" +msgstr "%d saat, %d dakika sonra zaman aşımı süresi dolacak" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minute" +msgstr "%d saat, %d dakika sonra zaman aşımı süresi dolacak" + +#: src/misc.cpp:398 +#, c-format +msgid "expires in %d hours, %d minutes" +msgstr "%d saat, %d dakika sonra zaman aşımı süresi dolacak" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minute" +msgstr "%d dakika sonra zaman aşımı süresi dolacak" + +#: src/misc.cpp:391 +#, c-format +msgid "expires in %d minutes" +msgstr "%d dakika sonra zaman aşımı süresi dolacak" + +#: src/misc.cpp:375 +#, fuzzy +msgid "expires momentarily" +msgstr "%d gün sonra zaman aşımı süresi dolacak" + +#: src/misc.cpp:343 +msgid "hour" +msgstr "" + +#: src/misc.cpp:343 +msgid "hours" +msgstr "" + +#: modules/extra/stats/cs_fantasy_stats.cpp:150 +#, c-format +msgid "letters: %s, words: %s, lines: %s, smileys: %s, actions: %s" +msgstr "" + +#: src/misc.cpp:349 +msgid "minute" +msgstr "" + +#: src/misc.cpp:349 +msgid "minutes" +msgstr "" + +#: modules/commands/bs_info.cpp:87 +msgid "not assigned yet" +msgstr "" + +#: src/misc.cpp:324 +msgid "second" +msgstr "" + +#: src/misc.cpp:324 +#, fuzzy +msgid "seconds" +msgstr "%s commands:" + +#: modules/commands/hs_request.cpp:215 +#, fuzzy, c-format +msgid "vHost for %s has been activated." +msgstr "Your vhost of %s is now activated." + +#: modules/commands/hs_request.cpp:272 +#, fuzzy, c-format +msgid "vHost for %s has been rejected." +msgstr "%s botu silindi." + +#: modules/commands/hs_request.cpp:79 +msgid "vhost" +msgstr "" + +#: modules/commands/hs_del.cpp:83 +#, c-format +msgid "vhosts for group %s have been removed." +msgstr "vhosts for group %s have been removed." + +#: src/misc.cpp:331 +msgid "year" +msgstr "" + +#: src/misc.cpp:331 +msgid "years" +msgstr "" + +#: modules/commands/os_config.cpp:20 +msgid "{MODIFY|VIEW} [block name item name item value]" +msgstr "" + +#: modules/commands/bs_info.cpp:41 +#, fuzzy +msgid "{channel | nickname}" +msgstr "UNBAN kanaladı [name]" + +#: modules/commands/ms_cancel.cpp:20 +#, fuzzy +msgid "{nick | channel}" +msgstr "CANCEL {nick | kanaladı}" + +#: modules/commands/ms_rsend.cpp:25 modules/commands/ms_send.cpp:25 +#, fuzzy +msgid "{nick | channel} memo-text" +msgstr "SEND {nick | kanaladı} mesaj" diff --git a/language/update.sh b/language/update.sh new file mode 100755 index 0000000..279ed3d --- /dev/null +++ b/language/update.sh @@ -0,0 +1,16 @@ +#!/bin/bash + +rm -f anope.pot +touch anope.pot + +cd .. +FILES=`find ./ -name *.cpp -o -name *.h -o -name *.conf | grep -v /modules/third/` +xgettext -E -C -s -d Anope -j -o language/anope.pot --from-code=utf-8 --keyword --keyword=_ $FILES +cd - + +for f in *.po +do + msgmerge -v -s -U $f `echo $f | cut -d'.' -f1`.pot +done + +rm -f *~ diff --git a/modules/CMakeLists.txt b/modules/CMakeLists.txt new file mode 100644 index 0000000..4b0fd6e --- /dev/null +++ b/modules/CMakeLists.txt @@ -0,0 +1,169 @@ +# If using Windows, add the MODULE_COMPILE define +if(WIN32) + add_definitions(-DMODULE_COMPILE) +endif(WIN32) + +macro(build_modules SRC) + if(NOT ${SRC} STREQUAL ${CMAKE_CURRENT_SOURCE_DIR} AND EXISTS "${SRC}/CMakeLists.txt") + add_subdirectory("${SRC}") + else(NOT ${SRC} STREQUAL ${CMAKE_CURRENT_SOURCE_DIR} AND EXISTS "${SRC}/CMakeLists.txt") + file(GLOB MODULES_SRCS "${SRC}/*") + foreach(MODULE_SRC ${MODULES_SRCS}) + if(IS_DIRECTORY "${MODULE_SRC}") + build_modules("${MODULE_SRC}") + else(IS_DIRECTORY "${MODULE_SRC}") + string(REGEX MATCH "\\.c$" ANOPE18MODULE ${MODULE_SRC}) + if(ANOPE18MODULE) + message(FATAL_ERROR "Anope 1 modules are not compatible with Anope 2!\nOffending module: ${MODULE_SRC}") + endif(ANOPE18MODULE) + string(REGEX MATCH "\\.cpp$" CPP ${MODULE_SRC}) + if(CPP) + set_source_files_properties(${MODULE_SRC} PROPERTIES LANGUAGE CXX COMPILE_FLAGS "${CXXFLAGS}") + + file(RELATIVE_PATH FNAME ${SRC} ${MODULE_SRC}) + # Convert the real source file extension to have a .so extension + string(REGEX REPLACE "\\.cpp$" ".so" SO ${FNAME}) + # Temporary variable for the current source's include directories + set(TEMP_INCLUDES) + # Calculate the header file dependencies for the given source file + calculate_depends(${MODULE_SRC} TEMP_INCLUDES) + # If there were some extra include directories, add them to the list + if(TEMP_INCLUDES) + append_to_list(EXTRA_INCLUDES ${TEMP_INCLUDES}) + endif(TEMP_INCLUDES) + + # Reset linker flags + set(TEMP_LDFLAGS) + # Reset extra dependencies + set(TEMP_DEPENDENCIES) + # Calculate the library dependencies for the given source file + calculate_libraries(${MODULE_SRC} TEMP_LDFLAGS TEMP_DEPENDENCIES) + # Reset has_function + set(HAS_FUNCTION) + # Check the function dependencies for the given source file + check_functions(${MODULE_SRC} HAS_FUNCTION) + # Only continue if this module has all of the required functions + if(HAS_FUNCTION) + # For Visual Studio only, include win32_memory static library, required to override Visual Studio's overrides of the new/delete operators + if(MSVC) + set(WIN32_MEMORY win32_memory) + else(MSVC) + set(WIN32_MEMORY) + endif(MSVC) + # Generate the module and set its linker flags, also set it to depend on the main Anope executable to be built beforehand + add_library(${SO} MODULE ${MODULE_SRC}) + # Windows requires this because it's weird + if(WIN32) + set(WIN32_NO_LIBS "/nodefaultlib:\"libcmt.lib\" /OPT:NOREF") + else(WIN32) + set(WIN32_NO_LIBS) + endif(WIN32) + set_target_properties(${SO} PROPERTIES LINKER_LANGUAGE CXX PREFIX "" SUFFIX "" LINK_FLAGS "${TEMP_LDFLAGS} ${WIN32_NO_LIBS}" INSTALL_RPATH_USE_LINK_PATH ON BUILD_WITH_INSTALL_RPATH ON) + add_dependencies(${SO} ${PROGRAM_NAME}) + if(GETTEXT_FOUND) + add_dependencies(${SO} module_language) + endif(GETTEXT_FOUND) + target_link_libraries(${SO} ${TEMP_DEPENDENCIES}) + # For Windows only, have the module link to the export library of Anope as well as wsock32 and Ws2_32 libraries (most of the modules probably don't need this, but this is to be on the safe side), also set its version + if(WIN32) + target_link_libraries(${SO} ${PROGRAM_NAME} wsock32 Ws2_32 ${WIN32_MEMORY}) + set_target_properties(${PROGRAM_NAME} PROPERTIES VERSION "${VERSION_DOTTED}") + else(WIN32) + if(APPLE) + target_link_libraries(${SO} ${PROGRAM_NAME}) + endif(APPLE) + endif(WIN32) + # Set the module to be installed to the module directory under the data directory + install(TARGETS ${SO} DESTINATION ${LIB_DIR}/modules) + endif(HAS_FUNCTION) + endif(CPP) + endif(IS_DIRECTORY "${MODULE_SRC}") + endforeach(MODULE_SRC ${MODULES_SRCS}) + endif(NOT ${SRC} STREQUAL ${CMAKE_CURRENT_SOURCE_DIR} AND EXISTS "${SRC}/CMakeLists.txt") +endmacro(build_modules) + +macro(build_subdir) + file(GLOB_RECURSE MODULES_SUBDIR_SRCS RELATIVE ${CMAKE_CURRENT_SOURCE_DIR} "*.cpp") + sort_list(MODULES_SUBDIR_SRCS) + + GET_FILENAME_COMPONENT(FOLDER_NAME ${CMAKE_CURRENT_SOURCE_DIR} NAME) + set(SO "${FOLDER_NAME}.so") + + # Set all the files to use C++ as well as set their compile flags (use the module-specific compile flags, though) + set_source_files_properties(${MODULES_SUBDIR_SRCS} PROPERTIES LANGUAGE CXX COMPILE_FLAGS "${CXXFLAGS}") + + set(HAS_FUNCTION TRUE) + + # Iterate through the source files in the subdirectory + foreach(SRC ${MODULES_SUBDIR_SRCS}) + if(HAS_FUNCTION) + # Temporary variable for the current source's include directories + set(TEMP_INCLUDES) + # Calculate the header file dependencies for the given source file + calculate_depends(${SRC} TEMP_INCLUDES) + # If there were some extra include directories, add them to the list + if(TEMP_INCLUDES) + include_directories(${TEMP_INCLUDES}) + endif(TEMP_INCLUDES) + + # Reset linker flags + set(TEMP_LDFLAGS) + # Reset extra dependencies + set(TEMP_DEPENDENCIES) + # Calculate the library dependencies for the given source file + calculate_libraries(${SRC} SKIP_LIBRARIES MODULE TEMP_LDFLAGS TEMP_DEPENDENCIES) + # Check the function dependencies for the given source file + check_functions(${SRC} HAS_FUNCTION) + + # Append this source file's linker flags to the subdirectoy's linker flags, if there are any to append + if(TEMP_DEPENDENCIES) + append_to_list(SUBDIR_EXTRA_DEPENDS ${TEMP_DEPENDENCIES}) + endif(TEMP_DEPENDENCIES) + endif(HAS_FUNCTION) + endforeach(SRC ${MODULES_SUBDIR_SRCS}) + + # Continue if library and function requirements are met + if(HAS_FUNCTION) + # Remove duplicates from the linker flags + if(SUBDIR_LDFLAGS) + remove_list_duplicates(SUBDIR_LDFLAGS) + endif(SUBDIR_LDFLAGS) + + # Remove duplicates from the extra dependencies + if(SUBDIR_EXTRA_DEPENDS) + remove_list_duplicates(SUBDIR_EXTRA_DEPENDS) + endif(SUBDIR_EXTRA_DEPENDS) + + # For Visual Studio only, include win32_memory static library, required to override Visual Studio's overrides of the new/delete operators + if(MSVC) + set(WIN32_MEMORY win32_memory) + else(MSVC) + set(WIN32_MEMORY) + endif(MSVC) + + # Generate the module and set it's linker flags, also set it to depend on the main Anope executable to be built beforehand + add_library(${SO} MODULE ${MODULES_SUBDIR_SRCS}) + set_target_properties(${SO} PROPERTIES LINKER_LANGUAGE CXX PREFIX "" SUFFIX "" LINK_FLAGS "${SUBDIR_LDFLAGS}" INSTALL_RPATH_USE_LINK_PATH ON BUILD_WITH_INSTALL_RPATH ON) + add_dependencies(${SO} ${PROGRAM_NAME}) + if(GETTEXT_FOUND) + add_dependencies(${SO} module_language) + endif(GETTEXT_FOUND) + target_link_libraries(${SO} ${SUBDIR_EXTRA_DEPENDS}) + # For Windows only, have the module link to the export library of Anope as well as wsock32 and Ws2_32 libraries (most of the modules probably don't need this, but this is to be on the safe side), also set it's version + if(WIN32) + target_link_libraries(${SO} ${PROGRAM_NAME} wsock32 Ws2_32 ${WIN32_MEMORY}) + set_target_properties(${PROGRAM_NAME} PROPERTIES VERSION "${VERSION_DOTTED}") + else(WIN32) + if(APPLE) + target_link_libraries(${SO} ${PROGRAM_NAME}) + endif(APPLE) + endif(WIN32) + + # Set the module to be installed to the module directory under the data directory + install(TARGETS ${SO} DESTINATION ${LIB_DIR}/modules) + + endif(HAS_FUNCTION) +endmacro(build_subdir) + +include_directories(${CMAKE_CURRENT_SOURCE_DIR}) +build_modules(${CMAKE_CURRENT_SOURCE_DIR}) diff --git a/modules/bs_autoassign.cpp b/modules/bs_autoassign.cpp new file mode 100644 index 0000000..b242baf --- /dev/null +++ b/modules/bs_autoassign.cpp @@ -0,0 +1,36 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + */ + +#include "module.h" + +class BSAutoAssign : public Module +{ + public: + BSAutoAssign(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR) + { + } + + void OnChanRegistered(ChannelInfo *ci) anope_override + { + const Anope::string &bot = Config->GetModule(this)->Get("bot"); + if (bot.empty()) + return; + + BotInfo *bi = BotInfo::Find(bot, true); + if (bi == NULL) + { + Log(this) << "bs_autoassign is configured to assign bot " << bot << ", but it does not exist?"; + return; + } + + bi->Assign(NULL, ci); + } +}; + +MODULE_INIT(BSAutoAssign) diff --git a/modules/commands/bs_assign.cpp b/modules/commands/bs_assign.cpp new file mode 100644 index 0000000..e5625e5 --- /dev/null +++ b/modules/commands/bs_assign.cpp @@ -0,0 +1,256 @@ +/* BotServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandBSAssign : public Command +{ + public: + CommandBSAssign(Module *creator) : Command(creator, "botserv/assign", 2, 2) + { + this->SetDesc(_("Assigns a bot to a channel")); + this->SetSyntax(_("\037channel\037 \037nick\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &chan = params[0]; + const Anope::string &nick = params[1]; + + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, bot assignment is temporarily disabled.")); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + BotInfo *bi = BotInfo::Find(nick, true); + if (!bi) + { + source.Reply(BOT_DOES_NOT_EXIST, nick.c_str()); + return; + } + + AccessGroup access = source.AccessFor(ci); + if (ci->HasExt("BS_NOBOT") || (!access.HasPriv("ASSIGN") && !source.HasPriv("botserv/administration"))) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (bi->oper_only && !source.HasPriv("botserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (ci->bi == bi) + { + source.Reply(_("Bot \002%s\002 is already assigned to channel \002%s\002."), ci->bi->nick.c_str(), chan.c_str()); + return; + } + + bool override = !access.HasPriv("ASSIGN"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "for " << bi->nick; + + bi->Assign(source.GetUser(), ci); + source.Reply(_("Bot \002%s\002 has been assigned to %s."), bi->nick.c_str(), ci->name.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Assigns the specified bot to a channel. You\n" + "can then configure the bot for the channel so it fits\n" + "your needs.")); + return true; + } +}; + +class CommandBSUnassign : public Command +{ + public: + CommandBSUnassign(Module *creator) : Command(creator, "botserv/unassign", 1, 1) + { + this->SetDesc(_("Unassigns a bot from a channel")); + this->SetSyntax(_("\037channel\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, bot assignment is temporarily disabled.")); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + AccessGroup access = source.AccessFor(ci); + if (!source.HasPriv("botserv/administration") && !access.HasPriv("ASSIGN")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (!ci->bi) + { + source.Reply(BOT_NOT_ASSIGNED); + return; + } + + if (ci->HasExt("PERSIST") && !ModeManager::FindChannelModeByName("PERM")) + { + source.Reply(_("You cannot unassign bots while persist is set on the channel.")); + return; + } + + bool override = !access.HasPriv("ASSIGN"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "for " << ci->bi->nick; + + ci->bi->UnAssign(source.GetUser(), ci); + source.Reply(_("There is no bot assigned to %s anymore."), ci->name.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Unassigns a bot from a channel. When you use this command,\n" + "the bot won't join the channel anymore. However, bot\n" + "configuration for the channel is kept, so you will always\n" + "be able to reassign a bot later without having to reconfigure\n" + "it entirely.")); + return true; + } +}; + +class CommandBSSetNoBot : public Command +{ + public: + CommandBSSetNoBot(Module *creator, const Anope::string &sname = "botserv/set/nobot") : Command(creator, sname, 2, 2) + { + this->SetDesc(_("Prevent a bot from being assigned to a channel")); + this->SetSyntax(_("\037channel\037 {\037ON|OFF\037}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci = ChannelInfo::Find(params[0]); + const Anope::string &value = params[1]; + + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, bot modification is temporarily disabled.")); + return; + } + + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + if (value.equals_ci("ON")) + { + Log(LOG_ADMIN, source, this, ci) << "to enable nobot"; + + ci->Extend("BS_NOBOT"); + if (ci->bi) + ci->bi->UnAssign(source.GetUser(), ci); + source.Reply(_("No-bot mode is now \002on\002 on channel %s."), ci->name.c_str()); + } + else if (value.equals_ci("OFF")) + { + Log(LOG_ADMIN, source, this, ci) << "to disable nobot"; + + ci->Shrink("BS_NOBOT"); + source.Reply(_("No-bot mode is now \002off\002 on channel %s."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, source.command); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(_(" \n" + "This option makes a channel unassignable. If a bot\n" + "is already assigned to the channel, it is unassigned\n" + "automatically when you enable it.")); + return true; + } +}; + +class BSAssign : public Module +{ + ExtensibleItem nobot; + + CommandBSAssign commandbsassign; + CommandBSUnassign commandbsunassign; + CommandBSSetNoBot commandbssetnobot; + + public: + BSAssign(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + nobot(this, "BS_NOBOT"), + commandbsassign(this), commandbsunassign(this), commandbssetnobot(this) + { + } + + void OnInvite(User *source, Channel *c, User *targ) anope_override + { + BotInfo *bi; + if (Anope::ReadOnly || !c->ci || targ->server != Me || !(bi = dynamic_cast(targ))) + return; + + AccessGroup access = c->ci->AccessFor(source); + if (nobot.HasExt(c->ci) || (!access.HasPriv("ASSIGN") && !source->HasPriv("botserv/administration"))) + { + targ->SendMessage(bi, ACCESS_DENIED); + return; + } + + if (bi->oper_only && !source->HasPriv("botserv/administration")) + { + targ->SendMessage(bi, ACCESS_DENIED); + return; + } + + if (c->ci->bi == bi) + { + targ->SendMessage(bi, _("Bot \002%s\002 is already assigned to channel \002%s\002."), c->ci->bi->nick.c_str(), c->name.c_str()); + return; + } + + bi->Assign(source, c->ci); + targ->SendMessage(bi, _("Bot \002%s\002 has been assigned to %s."), bi->nick.c_str(), c->name.c_str()); + } + + void OnBotInfo(CommandSource &source, BotInfo *bi, ChannelInfo *ci, InfoFormatter &info) anope_override + { + if (nobot.HasExt(ci)) + info.AddOption(_("No bot")); + } +}; + +MODULE_INIT(BSAssign) diff --git a/modules/commands/bs_badwords.cpp b/modules/commands/bs_badwords.cpp new file mode 100644 index 0000000..3c63b4a --- /dev/null +++ b/modules/commands/bs_badwords.cpp @@ -0,0 +1,469 @@ +/* BotServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/bs_badwords.h" + +struct BadWordImpl : BadWord, Serializable +{ + BadWordImpl() : Serializable("BadWord") { } + ~BadWordImpl(); + + void Serialize(Serialize::Data &data) const anope_override + { + data["ci"] << this->chan; + data["word"] << this->word; + data.SetType("type", Serialize::Data::DT_INT); data["type"] << this->type; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &); +}; + +struct BadWordsImpl : BadWords +{ + Serialize::Reference ci; + typedef std::vector list; + Serialize::Checker badwords; + + BadWordsImpl(Extensible *obj) : ci(anope_dynamic_static_cast(obj)), badwords("BadWord") { } + + ~BadWordsImpl(); + + BadWord* AddBadWord(const Anope::string &word, BadWordType type) anope_override + { + BadWordImpl *bw = new BadWordImpl(); + bw->chan = ci->name; + bw->word = word; + bw->type = type; + + this->badwords->push_back(bw); + + FOREACH_MOD(OnBadWordAdd, (ci, bw)); + + return bw; + } + + BadWord* GetBadWord(unsigned index) const anope_override + { + if (this->badwords->empty() || index >= this->badwords->size()) + return NULL; + + BadWordImpl *bw = (*this->badwords)[index]; + bw->QueueUpdate(); + return bw; + } + + unsigned GetBadWordCount() const anope_override + { + return this->badwords->size(); + } + + void EraseBadWord(unsigned index) anope_override + { + if (this->badwords->empty() || index >= this->badwords->size()) + return; + + FOREACH_MOD(OnBadWordDel, (ci, (*this->badwords)[index])); + + delete this->badwords->at(index); + } + + void ClearBadWords() anope_override + { + while (!this->badwords->empty()) + delete this->badwords->back(); + } + + void Check() anope_override + { + if (this->badwords->empty()) + ci->Shrink("badwords"); + } +}; + +BadWordsImpl::~BadWordsImpl() +{ + for (list::iterator it = badwords->begin(); it != badwords->end();) + { + BadWord *bw = *it; + ++it; + delete bw; + } +} + +BadWordImpl::~BadWordImpl() +{ + ChannelInfo *ci = ChannelInfo::Find(chan); + if (ci) + { + BadWordsImpl *badwords = ci->GetExt("badwords"); + if (badwords) + { + BadWordsImpl::list::iterator it = std::find(badwords->badwords->begin(), badwords->badwords->end(), this); + if (it != badwords->badwords->end()) + badwords->badwords->erase(it); + } + } +} + +Serializable* BadWordImpl::Unserialize(Serializable *obj, Serialize::Data &data) +{ + Anope::string sci, sword; + + data["ci"] >> sci; + data["word"] >> sword; + + ChannelInfo *ci = ChannelInfo::Find(sci); + if (!ci) + return NULL; + + unsigned int n; + data["type"] >> n; + + BadWordImpl *bw; + if (obj) + bw = anope_dynamic_static_cast(obj); + else + bw = new BadWordImpl(); + bw->chan = sci; + bw->word = sword; + bw->type = static_cast(n); + + BadWordsImpl *bws = ci->Require("badwords"); + if (!obj) + bws->badwords->push_back(bw); + + return bw; +} + +class BadwordsDelCallback : public NumberList +{ + CommandSource &source; + ChannelInfo *ci; + BadWords *bw; + Command *c; + unsigned deleted; + bool override; + public: + BadwordsDelCallback(CommandSource &_source, ChannelInfo *_ci, Command *_c, const Anope::string &list) : NumberList(list, true), source(_source), ci(_ci), c(_c), deleted(0), override(false) + { + if (!source.AccessFor(ci).HasPriv("BADWORDS") && source.HasPriv("botserv/administration")) + this->override = true; + bw = ci->Require("badwords"); + } + + ~BadwordsDelCallback() + { + if (!deleted) + source.Reply(_("No matching entries on %s bad words list."), ci->name.c_str()); + else if (deleted == 1) + source.Reply(_("Deleted 1 entry from %s bad words list."), ci->name.c_str()); + else + source.Reply(_("Deleted %d entries from %s bad words list."), deleted, ci->name.c_str()); + } + + void HandleNumber(unsigned Number) anope_override + { + if (!bw || !Number || Number > bw->GetBadWordCount()) + return; + + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, c, ci) << "DEL " << bw->GetBadWord(Number - 1)->word; + ++deleted; + bw->EraseBadWord(Number - 1); + } +}; + +class CommandBSBadwords : public Command +{ + private: + void DoList(CommandSource &source, ChannelInfo *ci, const Anope::string &word) + { + bool override = !source.AccessFor(ci).HasPriv("BADWORDS"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "LIST"; + ListFormatter list(source.GetAccount()); + BadWords *bw = ci->GetExt("badwords"); + + list.AddColumn(_("Number")).AddColumn(_("Word")).AddColumn(_("Type")); + + if (!bw || !bw->GetBadWordCount()) + { + source.Reply(_("%s bad words list is empty."), ci->name.c_str()); + return; + } + else if (!word.empty() && word.find_first_not_of("1234567890,-") == Anope::string::npos) + { + class BadwordsListCallback : public NumberList + { + ListFormatter &list; + BadWords *bw; + public: + BadwordsListCallback(ListFormatter &_list, BadWords *_bw, const Anope::string &numlist) : NumberList(numlist, false), list(_list), bw(_bw) + { + } + + void HandleNumber(unsigned Number) anope_override + { + if (!Number || Number > bw->GetBadWordCount()) + return; + + const BadWord *b = bw->GetBadWord(Number - 1); + ListFormatter::ListEntry entry; + entry["Number"] = stringify(Number); + entry["Word"] = b->word; + entry["Type"] = b->type == BW_SINGLE ? "(SINGLE)" : (b->type == BW_START ? "(START)" : (b->type == BW_END ? "(END)" : "")); + this->list.AddEntry(entry); + } + } + nl_list(list, bw, word); + nl_list.Process(); + } + else + { + for (unsigned i = 0, end = bw->GetBadWordCount(); i < end; ++i) + { + const BadWord *b = bw->GetBadWord(i); + + if (!word.empty() && !Anope::Match(b->word, word)) + continue; + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(i + 1); + entry["Word"] = b->word; + entry["Type"] = b->type == BW_SINGLE ? "(SINGLE)" : (b->type == BW_START ? "(START)" : (b->type == BW_END ? "(END)" : "")); + list.AddEntry(entry); + } + } + + if (list.IsEmpty()) + source.Reply(_("No matching entries on %s bad words list."), ci->name.c_str()); + else + { + std::vector replies; + list.Process(replies); + + source.Reply(_("Bad words list for %s:"), ci->name.c_str()); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("End of bad words list.")); + } + } + + void DoAdd(CommandSource &source, ChannelInfo *ci, const Anope::string &word) + { + size_t pos = word.rfind(' '); + BadWordType bwtype = BW_ANY; + Anope::string realword = word; + BadWords *badwords = ci->Require("badwords"); + + if (pos != Anope::string::npos) + { + Anope::string opt = word.substr(pos + 1); + if (!opt.empty()) + { + if (opt.equals_ci("SINGLE")) + bwtype = BW_SINGLE; + else if (opt.equals_ci("START")) + bwtype = BW_START; + else if (opt.equals_ci("END")) + bwtype = BW_END; + } + realword = word.substr(0, pos); + } + + unsigned badwordsmax = Config->GetModule(this->module)->Get("badwordsmax"); + if (badwords->GetBadWordCount() >= badwordsmax) + { + source.Reply(_("Sorry, you can only have %d bad words entries on a channel."), badwordsmax); + return; + } + + bool casesensitive = Config->GetModule(this->module)->Get("casesensitive"); + + for (unsigned i = 0, end = badwords->GetBadWordCount(); i < end; ++i) + { + const BadWord *bw = badwords->GetBadWord(i); + + if ((casesensitive && realword.equals_cs(bw->word)) || (!casesensitive && realword.equals_ci(bw->word))) + { + source.Reply(_("\002%s\002 already exists in %s bad words list."), bw->word.c_str(), ci->name.c_str()); + return; + } + } + + bool override = !source.AccessFor(ci).HasPriv("BADWORDS"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "ADD " << realword; + badwords->AddBadWord(realword, bwtype); + + source.Reply(_("\002%s\002 added to %s bad words list."), realword.c_str(), ci->name.c_str()); + } + + void DoDelete(CommandSource &source, ChannelInfo *ci, const Anope::string &word) + { + BadWords *badwords = ci->GetExt("badwords"); + + if (!badwords || !badwords->GetBadWordCount()) + { + source.Reply(_("%s bad words list is empty."), ci->name.c_str()); + return; + } + + /* Special case: is it a number/list? Only do search if it isn't. */ + if (!word.empty() && isdigit(word[0]) && word.find_first_not_of("1234567890,-") == Anope::string::npos) + { + BadwordsDelCallback list(source, ci, this, word); + list.Process(); + } + else + { + unsigned i, end; + const BadWord *badword; + + for (i = 0, end = badwords->GetBadWordCount(); i < end; ++i) + { + badword = badwords->GetBadWord(i); + + if (word.equals_ci(badword->word)) + break; + } + + if (i == end) + { + source.Reply(_("\002%s\002 not found on %s bad words list."), word.c_str(), ci->name.c_str()); + return; + } + + bool override = !source.AccessFor(ci).HasPriv("BADWORDS"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "DEL " << badword->word; + + source.Reply(_("\002%s\002 deleted from %s bad words list."), badword->word.c_str(), ci->name.c_str()); + + badwords->EraseBadWord(i); + } + + badwords->Check(); + } + + void DoClear(CommandSource &source, ChannelInfo *ci) + { + bool override = !source.AccessFor(ci).HasPriv("BADWORDS"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "CLEAR"; + + BadWords *badwords = ci->GetExt("badwords"); + if (badwords) + badwords->ClearBadWords(); + source.Reply(_("Bad words list is now empty.")); + } + + public: + CommandBSBadwords(Module *creator) : Command(creator, "botserv/badwords", 2, 3) + { + this->SetDesc(_("Maintains the bad words list")); + this->SetSyntax(_("\037channel\037 ADD \037word\037 [\037SINGLE\037 | \037START\037 | \037END\037]")); + this->SetSyntax(_("\037channel\037 DEL {\037word\037 | \037entry-num\037 | \037list\037}")); + this->SetSyntax(_("\037channel\037 LIST [\037mask\037 | \037list\037]")); + this->SetSyntax(_("\037channel\037 CLEAR")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[1]; + const Anope::string &word = params.size() > 2 ? params[2] : ""; + bool need_args = cmd.equals_ci("LIST") || cmd.equals_ci("CLEAR"); + + if (!need_args && word.empty()) + { + this->OnSyntaxError(source, cmd); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + if (!source.AccessFor(ci).HasPriv("BADWORDS") && !source.HasPriv("botserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, bad words list modification is temporarily disabled.")); + return; + } + + if (cmd.equals_ci("ADD")) + return this->DoAdd(source, ci, word); + else if (cmd.equals_ci("DEL")) + return this->DoDelete(source, ci, word); + else if (cmd.equals_ci("LIST")) + return this->DoList(source, ci, word); + else if (cmd.equals_ci("CLEAR")) + return this->DoClear(source, ci); + else + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Maintains the \002bad words list\002 for a channel. The bad\n" + "words list determines which words are to be kicked\n" + "when the bad words kicker is enabled. For more information,\n" + "type \002%s%s HELP KICK %s\002.\n" + " \n" + "The \002ADD\002 command adds the given word to the\n" + "bad words list. If SINGLE is specified, a kick will be\n" + "done only if a user says the entire word. If START is\n" + "specified, a kick will be done if a user says a word\n" + "that starts with \037word\037. If END is specified, a kick\n" + "will be done if a user says a word that ends with\n" + "\037word\037. If you don't specify anything, a kick will\n" + "be issued every time \037word\037 is said by a user.\n" + " \n"), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), source.command.c_str()); + source.Reply(_("The \002DEL\002 command removes the given word from the\n" + "bad words list. If a list of entry numbers is given, those\n" + "entries are deleted. (See the example for LIST below.)\n" + " \n" + "The \002LIST\002 command displays the bad words list. If\n" + "a wildcard mask is given, only those entries matching the\n" + "mask are displayed. If a list of entry numbers is given,\n" + "only those entries are shown; for example:\n" + " \002#channel LIST 2-5,7-9\002\n" + " Lists bad words entries numbered 2 through 5 and\n" + " 7 through 9.\n" + " \n" + "The \002CLEAR\002 command clears all entries from the\n" + "bad words list.")); + return true; + } +}; + +class BSBadwords : public Module +{ + CommandBSBadwords commandbsbadwords; + ExtensibleItem badwords; + Serialize::Type badword_type; + + public: + BSBadwords(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandbsbadwords(this), badwords(this, "badwords"), badword_type("BadWord", BadWordImpl::Unserialize) + { + } +}; + +MODULE_INIT(BSBadwords) diff --git a/modules/commands/bs_bot.cpp b/modules/commands/bs_bot.cpp new file mode 100644 index 0000000..7a88e51 --- /dev/null +++ b/modules/commands/bs_bot.cpp @@ -0,0 +1,385 @@ +/* BotServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandBSBot : public Command +{ + private: + void DoAdd(CommandSource &source, const std::vector ¶ms) + { + const Anope::string &nick = params[1]; + const Anope::string &user = params[2]; + const Anope::string &host = params[3]; + const Anope::string &real = params[4]; + + if (BotInfo::Find(nick, true)) + { + source.Reply(_("Bot \002%s\002 already exists."), nick.c_str()); + return; + } + + Configuration::Block *networkinfo = Config->GetBlock("networkinfo"); + + if (nick.length() > networkinfo->Get("nicklen")) + { + source.Reply(_("Bot nicks may only be %d characters long."), networkinfo->Get("nicklen")); + return; + } + + if (user.length() > networkinfo->Get("userlen")) + { + source.Reply(_("Bot idents may only be %d characters long."), networkinfo->Get("userlen")); + return; + } + + if (host.length() > networkinfo->Get("hostlen")) + { + source.Reply(_("Bot hosts may only be %d characters long."), networkinfo->Get("hostlen")); + return; + } + + if (!IRCD->IsNickValid(nick)) + { + source.Reply(_("Bot nicks may only contain valid nick characters.")); + return; + } + + if (!IRCD->IsIdentValid(user)) + { + source.Reply(_("Bot idents may only contain valid ident characters.")); + return; + } + + if (!IRCD->IsHostValid(host)) + { + source.Reply(_("Bot hosts may only contain valid host characters.")); + return; + } + + /* We check whether the nick is registered, and inform the user + * if so. You need to drop the nick manually before you can use + * it as a bot nick from now on -GD + */ + if (NickAlias::Find(nick)) + { + source.Reply(NICK_ALREADY_REGISTERED, nick.c_str()); + return; + } + + User *u = User::Find(nick, true); + if (u) + { + source.Reply(_("Nick \002%s\002 is currently in use."), u->nick.c_str()); + return; + } + + BotInfo *bi = new BotInfo(nick, user, host, real); + + Log(LOG_ADMIN, source, this) << "ADD " << bi->GetMask() << " " << bi->realname; + + source.Reply(_("%s!%s@%s (%s) added to the bot list."), bi->nick.c_str(), bi->GetIdent().c_str(), bi->host.c_str(), bi->realname.c_str()); + + FOREACH_MOD(OnBotCreate, (bi)); + return; + } + + void DoChange(CommandSource &source, const std::vector ¶ms) + { + const Anope::string &oldnick = params[1]; + const Anope::string &nick = params.size() > 2 ? params[2] : ""; + const Anope::string &user = params.size() > 3 ? params[3] : ""; + const Anope::string &host = params.size() > 4 ? params[4] : ""; + const Anope::string &real = params.size() > 5 ? params[5] : ""; + + if (oldnick.empty() || nick.empty()) + { + this->OnSyntaxError(source, "CHANGE"); + return; + } + + BotInfo *bi = BotInfo::Find(oldnick, true); + if (!bi) + { + source.Reply(BOT_DOES_NOT_EXIST, oldnick.c_str()); + return; + } + + if (bi->conf) + { + source.Reply(_("Bot %s is not changeable."), bi->nick.c_str()); + return; + } + + Configuration::Block *networkinfo = Config->GetBlock("networkinfo"); + + if (nick.length() > networkinfo->Get("nicklen")) + { + source.Reply(_("Bot nicks may only be %d characters long."), networkinfo->Get("nicklen")); + return; + } + + if (user.length() > networkinfo->Get("userlen")) + { + source.Reply(_("Bot idents may only be %d characters long."), networkinfo->Get("userlen")); + return; + } + + if (host.length() > networkinfo->Get("hostlen")) + { + source.Reply(_("Bot hosts may only be %d characters long."), networkinfo->Get("hostlen")); + return; + } + + /* Checks whether there *are* changes. + * Case sensitive because we may want to change just the case. + * And we must finally check that the nick is not already + * taken by another bot. + */ + if (nick.equals_cs(bi->nick) && (!user.empty() ? user.equals_cs(bi->GetIdent()) : 1) && (!host.empty() ? host.equals_cs(bi->host) : 1) && (!real.empty() ? real.equals_cs(bi->realname) : 1)) + { + source.Reply(_("The old information is the same as the new information specified.")); + return; + } + + if (!IRCD->IsNickValid(nick)) + { + source.Reply(_("Bot nicks may only contain valid nick characters.")); + return; + } + + if (!user.empty() && !IRCD->IsIdentValid(user)) + { + source.Reply(_("Bot idents may only contain valid ident characters.")); + return; + } + + if (!host.empty() && !IRCD->IsHostValid(host)) + { + source.Reply(_("Bot hosts may only contain valid host characters.")); + return; + } + + if (!nick.equals_ci(bi->nick)) + { + if (BotInfo::Find(nick, true)) + { + source.Reply(_("Bot \002%s\002 already exists."), nick.c_str()); + return; + } + + if (User::Find(nick, true)) + { + source.Reply(_("Nick \002%s\002 is currently in use."), nick.c_str()); + return; + } + } + + if (!nick.equals_ci(bi->nick)) + { + /* We check whether the nick is registered, and inform the user + * if so. You need to drop the nick manually before you can use + * it as a bot nick from now on -GD + */ + if (NickAlias::Find(nick)) + { + source.Reply(NICK_ALREADY_REGISTERED, nick.c_str()); + return; + } + + /* The new nick is really different, so we remove the Q line for the old nick. */ + XLine x_del(bi->nick); + IRCD->SendSQLineDel(&x_del); + + /* Add a Q line for the new nick */ + XLine x(nick, "Reserved for services"); + IRCD->SendSQLine(NULL, &x); + } + + if (!user.empty()) + { + IRCD->SendQuit(bi, "Quit: Be right back"); + bi->introduced = false; + } + else + IRCD->SendNickChange(bi, nick); + + if (!nick.equals_cs(bi->nick)) + bi->SetNewNick(nick); + + if (!user.empty() && !user.equals_cs(bi->GetIdent())) + bi->SetIdent(user); + if (!host.empty() && !host.equals_cs(bi->host)) + bi->host = host; + if (!real.empty() && !real.equals_cs(bi->realname)) + bi->realname = real; + + if (!user.empty()) + bi->OnKill(); + + source.Reply(_("Bot \002%s\002 has been changed to %s!%s@%s (%s)."), oldnick.c_str(), bi->nick.c_str(), bi->GetIdent().c_str(), bi->host.c_str(), bi->realname.c_str()); + Log(LOG_ADMIN, source, this) << "CHANGE " << oldnick << " to " << bi->GetMask() << " " << bi->realname; + + FOREACH_MOD(OnBotChange, (bi)); + return; + } + + void DoDel(CommandSource &source, const std::vector ¶ms) + { + const Anope::string &nick = params[1]; + + if (nick.empty()) + { + this->OnSyntaxError(source, "DEL"); + return; + } + + BotInfo *bi = BotInfo::Find(nick, true); + if (!bi) + { + source.Reply(BOT_DOES_NOT_EXIST, nick.c_str()); + return; + } + + if (bi->conf) + { + source.Reply(_("Bot %s is not deletable."), bi->nick.c_str()); + return; + } + + FOREACH_MOD(OnBotDelete, (bi)); + + Log(LOG_ADMIN, source, this) << "DEL " << bi->nick; + + source.Reply(_("Bot \002%s\002 has been deleted."), nick.c_str()); + delete bi; + return; + } + public: + CommandBSBot(Module *creator) : Command(creator, "botserv/bot", 1, 6) + { + this->SetDesc(_("Maintains network bot list")); + this->SetSyntax(_("\002ADD \037nick\037 \037user\037 \037host\037 \037real\037\002")); + this->SetSyntax(_("\002CHANGE \037oldnick\037 \037newnick\037 [\037user\037 [\037host\037 [\037real\037]]]\002")); + this->SetSyntax(_("\002DEL \037nick\037\002")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[0]; + + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, bot modification is temporarily disabled.")); + return; + } + + if (cmd.equals_ci("ADD")) + { + // ADD nick user host real - 5 + if (!source.HasCommand("botserv/bot/add")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params.size() < 5) + { + this->OnSyntaxError(source, "ADD"); + return; + } + + std::vector tempparams = params; + // ADD takes less params than CHANGE, so we need to take 6 if given and append it with a space to 5. + if (tempparams.size() >= 6) + tempparams[4] = tempparams[4] + " " + tempparams[5]; + + return this->DoAdd(source, tempparams); + } + else if (cmd.equals_ci("CHANGE")) + { + // CHANGE oldn newn user host real - 6 + // but only oldn and newn are required + if (!source.HasCommand("botserv/bot/change")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params.size() < 3) + { + this->OnSyntaxError(source, "CHANGE"); + return; + } + + return this->DoChange(source, params); + } + else if (cmd.equals_ci("DEL")) + { + // DEL nick + if (!source.HasCommand("botserv/bot/del")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params.size() < 1) + { + this->OnSyntaxError(source, "DEL"); + return; + } + + return this->DoDel(source, params); + } + else + this->OnSyntaxError(source, ""); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows Services Operators to create, modify, and delete\n" + "bots that users will be able to use on their own\n" + "channels.\n" + " \n" + "\002BOT ADD\002 adds a bot with the given nickname, username,\n" + "hostname and realname. Since no integrity checks are done\n" + "for these settings, be really careful.\n" + " \n" + "\002BOT CHANGE\002 allows you to change the nickname, username, hostname\n" + "or realname of a bot without deleting it (and\n" + "all the data associated with it).\n" + " \n" + "\002BOT DEL\002 removes the given bot from the bot list.\n" + " \n" + "\002Note\002: You cannot create a bot with a nick that is\n" + "currently registered. If an unregistered user is currently\n" + "using the nick, they will be killed.")); + return true; + } +}; + +class BSBot : public Module +{ + CommandBSBot commandbsbot; + + public: + BSBot(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandbsbot(this) + { + + } +}; + +MODULE_INIT(BSBot) diff --git a/modules/commands/bs_botlist.cpp b/modules/commands/bs_botlist.cpp new file mode 100644 index 0000000..65c8dab --- /dev/null +++ b/modules/commands/bs_botlist.cpp @@ -0,0 +1,82 @@ +/* BotServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandBSBotList : public Command +{ + public: + CommandBSBotList(Module *creator) : Command(creator, "botserv/botlist", 0, 0) + { + this->SetDesc(_("Lists available bots")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + unsigned count = 0; + ListFormatter list(source.GetAccount()); + + list.AddColumn(_("Nick")).AddColumn(_("Mask")); + + for (botinfo_map::const_iterator it = BotListByNick->begin(), it_end = BotListByNick->end(); it != it_end; ++it) + { + BotInfo *bi = it->second; + + if (source.HasPriv("botserv/administration") || !bi->oper_only) + { + ++count; + ListFormatter::ListEntry entry; + entry["Nick"] = (bi->oper_only ? "* " : "") + bi->nick; + entry["Mask"] = bi->GetIdent() + "@" + bi->host; + list.AddEntry(entry); + } + } + + std::vector replies; + list.Process(replies); + + if (!count) + source.Reply(_("There are no bots available at this time.\n" + "Ask a Services Operator to create one!")); + else + { + source.Reply(_("Bot list:")); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("%d bots available."), count); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Lists all available bots on this network.\n" + "Bots prefixed by a * are reserved for IRC Operators.")); + return true; + } +}; + +class BSBotList : public Module +{ + CommandBSBotList commandbsbotlist; + + public: + BSBotList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandbsbotlist(this) + { + + } +}; + +MODULE_INIT(BSBotList) diff --git a/modules/commands/bs_control.cpp b/modules/commands/bs_control.cpp new file mode 100644 index 0000000..27bc598 --- /dev/null +++ b/modules/commands/bs_control.cpp @@ -0,0 +1,146 @@ +/* BotServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandBSSay : public Command +{ + public: + CommandBSSay(Module *creator) : Command(creator, "botserv/say", 2, 2) + { + this->SetDesc(_("Makes the bot say the specified text on the specified channel")); + this->SetSyntax(_("\037channel\037 \037text\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &text = params[1]; + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + if (!source.AccessFor(ci).HasPriv("SAY") && !source.HasPriv("botserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (!ci->bi) + { + source.Reply(BOT_NOT_ASSIGNED); + return; + } + + if (!ci->c || !ci->c->FindUser(ci->bi)) + { + source.Reply(BOT_NOT_ON_CHANNEL, ci->name.c_str()); + return; + } + + if (text[0] == '\001') + { + this->OnSyntaxError(source, ""); + return; + } + + IRCD->SendPrivmsg(*ci->bi, ci->name, "%s", text.c_str()); + ci->bi->lastmsg = Anope::CurTime; + + bool override = !source.AccessFor(ci).HasPriv("SAY"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to say: " << text; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Makes the bot say the specified text on the specified channel.")); + return true; + } +}; + +class CommandBSAct : public Command +{ + public: + CommandBSAct(Module *creator) : Command(creator, "botserv/act", 2, 2) + { + this->SetDesc(_("Makes the bot do the equivalent of a \"/me\" command")); + this->SetSyntax(_("\037channel\037 \037text\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + Anope::string message = params[1]; + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + if (!source.AccessFor(ci).HasPriv("SAY") && !source.HasPriv("botserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (!ci->bi) + { + source.Reply(BOT_NOT_ASSIGNED); + return; + } + + if (!ci->c || !ci->c->FindUser(ci->bi)) + { + source.Reply(BOT_NOT_ON_CHANNEL, ci->name.c_str()); + return; + } + + message = message.replace_all_cs("\1", ""); + if (message.empty()) + return; + + IRCD->SendAction(*ci->bi, ci->name, "%s", message.c_str()); + ci->bi->lastmsg = Anope::CurTime; + + bool override = !source.AccessFor(ci).HasPriv("SAY"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to say: " << message; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Makes the bot do the equivalent of a \"/me\" command\n" + "on the specified channel using the specified text.")); + return true; + } +}; + +class BSControl : public Module +{ + CommandBSSay commandbssay; + CommandBSAct commandbsact; + + public: + BSControl(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandbssay(this), commandbsact(this) + { + + } +}; + +MODULE_INIT(BSControl) diff --git a/modules/commands/bs_info.cpp b/modules/commands/bs_info.cpp new file mode 100644 index 0000000..3ea986f --- /dev/null +++ b/modules/commands/bs_info.cpp @@ -0,0 +1,134 @@ +/* BotServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandBSInfo : public Command +{ + private: + void send_bot_channels(std::vector &buffers, const BotInfo *bi) + { + Anope::string buf; + for (registered_channel_map::const_iterator it = RegisteredChannelList->begin(), it_end = RegisteredChannelList->end(); it != it_end; ++it) + { + const ChannelInfo *ci = it->second; + + if (ci->bi == bi) + { + buf += " " + ci->name + " "; + if (buf.length() > 300) + { + buffers.push_back(buf); + buf.clear(); + } + } + } + if (!buf.empty()) + buffers.push_back(buf); + } + + public: + CommandBSInfo(Module *creator) : Command(creator, "botserv/info", 1, 1) + { + this->SetSyntax(_("{\037channel\037 | \037nickname\037}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &query = params[0]; + + BotInfo *bi = BotInfo::Find(query, true); + ChannelInfo *ci = ChannelInfo::Find(query); + InfoFormatter info(source.nc); + + if (bi) + { + source.Reply(_("Information for bot \002%s\002:"), bi->nick.c_str()); + info[_("Mask")] = bi->GetIdent() + "@" + bi->host; + info[_("Real name")] = bi->realname; + info[_("Created")] = Anope::strftime(bi->created, source.GetAccount()); + info[_("Options")] = bi->oper_only ? _("Private") : _("None"); + info[_("Used on")] = stringify(bi->GetChannelCount()) + " channel(s)"; + + FOREACH_MOD(OnBotInfo, (source, bi, ci, info)); + + std::vector replies; + info.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + if (source.HasPriv("botserv/administration")) + { + std::vector buf; + this->send_bot_channels(buf, bi); + for (unsigned i = 0; i < buf.size(); ++i) + source.Reply(buf[i]); + } + + } + else if (ci) + { + if (!source.AccessFor(ci).HasPriv("INFO") && !source.HasPriv("botserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + source.Reply(CHAN_INFO_HEADER, ci->name.c_str()); + info[_("Bot nick")] = ci->bi ? ci->bi->nick : _("not assigned yet"); + + Anope::string enabled = Language::Translate(source.nc, _("Enabled")); + Anope::string disabled = Language::Translate(source.nc, _("Disabled")); + + FOREACH_MOD(OnBotInfo, (source, bi, ci, info)); + + std::vector replies; + info.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + else + source.Reply(_("\002%s\002 is not a valid bot or registered channel."), query.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows you to see %s information about a channel or a bot.\n" + "If the parameter is a channel, then you'll get information\n" + "such as enabled kickers. If the parameter is a nick,\n" + "you'll get information about a bot, such as creation\n" + "time or number of channels it is on."), source.service->nick.c_str()); + return true; + } + + const Anope::string GetDesc(CommandSource &source) const anope_override + { + return Anope::printf(Language::Translate(source.GetAccount(), _("Allows you to see %s information about a channel or a bot")), source.service->nick.c_str()); + } +}; + +class BSInfo : public Module +{ + CommandBSInfo commandbsinfo; + + public: + BSInfo(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandbsinfo(this) + { + + } +}; + +MODULE_INIT(BSInfo) diff --git a/modules/commands/bs_kick.cpp b/modules/commands/bs_kick.cpp new file mode 100644 index 0000000..240ad22 --- /dev/null +++ b/modules/commands/bs_kick.cpp @@ -0,0 +1,1474 @@ +/* BotServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/bs_kick.h" +#include "modules/bs_badwords.h" + +static Module *me; + +struct KickerDataImpl : KickerData +{ + KickerDataImpl(Extensible *obj) + { + amsgs = badwords = bolds = caps = colors = flood = italics = repeat = reverses = underlines = false; + for (int16_t i = 0; i < TTB_SIZE; ++i) + ttb[i] = 0; + capsmin = capspercent = 0; + floodlines = floodsecs = 0; + repeattimes = 0; + + dontkickops = dontkickvoices = false; + } + + void Check(ChannelInfo *ci) anope_override + { + if (amsgs || badwords || bolds || caps || colors || flood || italics || repeat || reverses || underlines) + return; + + ci->Shrink("kickerdata"); + } + + struct ExtensibleItem : ::ExtensibleItem + { + ExtensibleItem(Module *m, const Anope::string &ename) : ::ExtensibleItem(m, ename) { } + + void ExtensibleSerialize(const Extensible *e, const Serializable *s, Serialize::Data &data) const anope_override + { + if (s->GetSerializableType()->GetName() != "ChannelInfo") + return; + + const ChannelInfo *ci = anope_dynamic_static_cast(e); + KickerData *kd = this->Get(ci); + if (kd == NULL) + return; + + data["kickerdata:amsgs"] << kd->amsgs; + data["kickerdata:badwords"] << kd->badwords; + data["kickerdata:bolds"] << kd->bolds; + data["kickerdata:caps"] << kd->caps; + data["kickerdata:colors"] << kd->colors; + data["kickerdata:flood"] << kd->flood; + data["kickerdata:italics"] << kd->italics; + data["kickerdata:repeat"] << kd->repeat; + data["kickerdata:reverses"] << kd->reverses; + data["kickerdata:underlines"] << kd->underlines; + + data.SetType("capsmin", Serialize::Data::DT_INT); data["capsmin"] << kd->capsmin; + data.SetType("capspercent", Serialize::Data::DT_INT); data["capspercent"] << kd->capspercent; + data.SetType("floodlines", Serialize::Data::DT_INT); data["floodlines"] << kd->floodlines; + data.SetType("floodsecs", Serialize::Data::DT_INT); data["floodsecs"] << kd->floodsecs; + data.SetType("repeattimes", Serialize::Data::DT_INT); data["repeattimes"] << kd->repeattimes; + for (int16_t i = 0; i < TTB_SIZE; ++i) + data["ttb"] << kd->ttb[i] << " "; + } + + void ExtensibleUnserialize(Extensible *e, Serializable *s, Serialize::Data &data) anope_override + { + if (s->GetSerializableType()->GetName() != "ChannelInfo") + return; + + ChannelInfo *ci = anope_dynamic_static_cast(e); + KickerData *kd = ci->Require("kickerdata"); + + data["kickerdata:amsgs"] >> kd->amsgs; + data["kickerdata:badwords"] >> kd->badwords; + data["kickerdata:bolds"] >> kd->bolds; + data["kickerdata:caps"] >> kd->caps; + data["kickerdata:colors"] >> kd->colors; + data["kickerdata:flood"] >> kd->flood; + data["kickerdata:italics"] >> kd->italics; + data["kickerdata:repeat"] >> kd->repeat; + data["kickerdata:reverses"] >> kd->reverses; + data["kickerdata:underlines"] >> kd->underlines; + + data["capsmin"] >> kd->capsmin; + data["capspercent"] >> kd->capspercent; + data["floodlines"] >> kd->floodlines; + data["floodsecs"] >> kd->floodsecs; + data["repeattimes"] >> kd->repeattimes; + + Anope::string ttb, tok; + data["ttb"] >> ttb; + spacesepstream sep(ttb); + for (int i = 0; sep.GetToken(tok) && i < TTB_SIZE; ++i) + try + { + kd->ttb[i] = convertTo(tok); + } + catch (const ConvertException &) { } + + kd->Check(ci); + } + }; +}; + +class CommandBSKick : public Command +{ + public: + CommandBSKick(Module *creator) : Command(creator, "botserv/kick", 0) + { + this->SetDesc(_("Configures kickers")); + this->SetSyntax(_("\037option\037 \037channel\037 {\037ON|OFF\037} [\037settings\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Configures bot kickers. \037option\037 can be one of:")); + + Anope::string this_name = source.command; + for (CommandInfo::map::const_iterator it = source.service->commands.begin(), it_end = source.service->commands.end(); it != it_end; ++it) + { + const Anope::string &c_name = it->first; + const CommandInfo &info = it->second; + + if (c_name.find_ci(this_name + " ") == 0) + { + ServiceReference command("Command", info.name); + if (command) + { + source.command = c_name; + command->OnServHelp(source); + } + } + } + + source.Reply(_("Type \002%s%s HELP %s \037option\037\002 for more information\n" + "on a specific option.\n" + " \n" + "Note: access to this command is controlled by the\n" + "level SET."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), this_name.c_str()); + + return true; + } +}; + +class CommandBSKickBase : public Command +{ + public: + CommandBSKickBase(Module *creator, const Anope::string &cname, int minarg, int maxarg) : Command(creator, cname, minarg, maxarg) + { + } + + virtual void Execute(CommandSource &source, const std::vector ¶ms) anope_override = 0; + + virtual bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override = 0; + + protected: + bool CheckArguments(CommandSource &source, const std::vector ¶ms, ChannelInfo* &ci) + { + const Anope::string &chan = params[0]; + const Anope::string &option = params[1]; + + ci = ChannelInfo::Find(chan); + + if (Anope::ReadOnly) + source.Reply(_("Sorry, kicker configuration is temporarily disabled.")); + else if (ci == NULL) + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + else if (option.empty()) + this->OnSyntaxError(source, ""); + else if (!option.equals_ci("ON") && !option.equals_ci("OFF")) + this->OnSyntaxError(source, ""); + else if (!source.AccessFor(ci).HasPriv("SET") && !source.HasPriv("botserv/administration")) + source.Reply(ACCESS_DENIED); + else if (!ci->bi) + source.Reply(BOT_NOT_ASSIGNED); + else + return true; + + return false; + } + + void Process(CommandSource &source, ChannelInfo *ci, const Anope::string ¶m, const Anope::string &ttb, size_t ttb_idx, const Anope::string &optname, KickerData *kd, bool &val) + { + if (param.equals_ci("ON")) + { + if (!ttb.empty()) + { + int16_t i; + + try + { + i = convertTo(ttb); + if (i < 0) + throw ConvertException(); + } + catch (const ConvertException &) + { + source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); + return; + } + + kd->ttb[ttb_idx] = i; + } + else + kd->ttb[ttb_idx] = 0; + + val = true; + if (kd->ttb[ttb_idx]) + source.Reply(_("Bot will now kick for \002%s\002, and will place a ban\n" + "after %d kicks for the same user."), optname.c_str(), kd->ttb[ttb_idx]); + else + source.Reply(_("Bot will now kick for \002%s\002."), optname.c_str()); + + bool override = !source.AccessFor(ci).HasPriv("SET"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to enable the " << optname << " kicker"; + } + else if (param.equals_ci("OFF")) + { + bool override = !source.AccessFor(ci).HasPriv("SET"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to disable the " << optname << " kicker"; + + val = false; + source.Reply(_("Bot won't kick for \002%s\002 anymore."), optname.c_str()); + } + else + this->OnSyntaxError(source, ""); + } +}; + +class CommandBSKickAMSG : public CommandBSKickBase +{ + public: + CommandBSKickAMSG(Module *creator) : CommandBSKickBase(creator, "botserv/kick/amsg", 2, 3) + { + this->SetDesc(_("Configures AMSG kicker")); + this->SetSyntax(_("\037channel\037 {\037ON|OFF\037} [\037ttb\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci; + if (CheckArguments(source, params, ci)) + { + KickerData *kd = ci->Require("kickerdata"); + Process(source, ci, params[1], params.size() > 2 ? params[2] : "", TTB_AMSGS, "AMSG", kd, kd->amsgs); + kd->Check(ci); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + BotInfo *bi = Config->GetClient("BotServ"); + source.Reply(_("Sets the AMSG kicker on or off. When enabled, the bot will\n" + "kick users who send the same message to multiple channels\n" + "where %s bots are.\n" + " \n" + "\037ttb\037 is the number of times a user can be kicked\n" + "before they get banned. Don't give ttb to disable\n" + "the ban system once activated."), bi ? bi->nick.c_str() : "BotServ"); + return true; + } +}; + +class CommandBSKickBadwords : public CommandBSKickBase +{ + public: + CommandBSKickBadwords(Module *creator) : CommandBSKickBase(creator, "botserv/kick/badwords", 2, 3) + { + this->SetDesc(_("Configures badwords kicker")); + this->SetSyntax(_("\037channel\037 {\037ON|OFF\037} [\037ttb\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci; + if (CheckArguments(source, params, ci)) + { + KickerData *kd = ci->Require("kickerdata"); + Process(source, ci, params[1], params.size() > 2 ? params[2] : "", TTB_BADWORDS, "badwords", kd, kd->badwords); + kd->Check(ci); + } + + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets the bad words kicker on or off. When enabled, this\n" + "option tells the bot to kick users who say certain words\n" + "on the channels.\n" + "You can define bad words for your channel using the\n" + "\002BADWORDS\002 command. Type \002%s%s HELP BADWORDS\002 for\n" + "more information.\n" + " \n" + "\037ttb\037 is the number of times a user can be kicked\n" + "before it gets banned. Don't give ttb to disable\n" + "the ban system once activated."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str()); + return true; + } +}; + +class CommandBSKickBolds : public CommandBSKickBase +{ + public: + CommandBSKickBolds(Module *creator) : CommandBSKickBase(creator, "botserv/kick/bolds", 2, 3) + { + this->SetDesc(_("Configures bolds kicker")); + this->SetSyntax(_("\037channel\037 {\037ON|OFF\037} [\037ttb\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci; + if (CheckArguments(source, params, ci)) + { + KickerData *kd = ci->Require("kickerdata"); + Process(source, ci, params[1], params.size() > 2 ? params[2] : "", TTB_BOLDS, "bolds", kd, kd->bolds); + kd->Check(ci); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets the bolds kicker on or off. When enabled, this\n" + "option tells the bot to kick users who use bolds.\n" + " \n" + "\037ttb\037 is the number of times a user can be kicked\n" + "before it gets banned. Don't give ttb to disable\n" + "the ban system once activated.")); + return true; + } +}; + +class CommandBSKickCaps : public CommandBSKickBase +{ + public: + CommandBSKickCaps(Module *creator) : CommandBSKickBase(creator, "botserv/kick/caps", 2, 5) + { + this->SetDesc(_("Configures caps kicker")); + this->SetSyntax(_("\037channel\037 {\037ON|OFF\037} [\037ttb\037 [\037min\037 [\037percent\037]]]\002")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci; + if (!CheckArguments(source, params, ci)) + return; + + KickerData *kd = ci->Require("kickerdata"); + + if (params[1].equals_ci("ON")) + { + const Anope::string &ttb = params.size() > 2 ? params[2] : "", + &min = params.size() > 3 ? params[3] : "", + &percent = params.size() > 4 ? params[4] : ""; + + if (!ttb.empty()) + { + try + { + kd->ttb[TTB_CAPS] = convertTo(ttb); + if (kd->ttb[TTB_CAPS] < 0) + throw ConvertException(); + } + catch (const ConvertException &) + { + kd->ttb[TTB_CAPS] = 0; + source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); + return; + } + } + else + kd->ttb[TTB_CAPS] = 0; + + kd->capsmin = 10; + try + { + kd->capsmin = convertTo(min); + } + catch (const ConvertException &) { } + if (kd->capsmin < 1) + kd->capsmin = 10; + + kd->capspercent = 25; + try + { + kd->capspercent = convertTo(percent); + } + catch (const ConvertException &) { } + if (kd->capspercent < 1 || kd->capspercent > 100) + kd->capspercent = 25; + + kd->caps = true; + if (kd->ttb[TTB_CAPS]) + source.Reply(_("Bot will now kick for \002caps\002 (they must constitute at least\n" + "%d characters and %d%% of the entire message), and will\n" + "place a ban after %d kicks for the same user."), kd->capsmin, kd->capspercent, kd->ttb[TTB_CAPS]); + else + source.Reply(_("Bot will now kick for \002caps\002 (they must constitute at least\n" + "%d characters and %d%% of the entire message)."), kd->capsmin, kd->capspercent); + } + else + { + kd->caps = false; + source.Reply(_("Bot won't kick for \002caps\002 anymore.")); + } + + kd->Check(ci); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets the caps kicker on or off. When enabled, this\n" + "option tells the bot to kick users who are talking in\n" + "CAPS.\n" + "The bot kicks only if there are at least \002min\002 caps\n" + "and they constitute at least \002percent\002%% of the total\n" + "text line (if not given, it defaults to 10 characters\n" + "and 25%%).\n" + " \n" + "\037ttb\037 is the number of times a user can be kicked\n" + "before it gets banned. Don't give ttb to disable\n" + "the ban system once activated.")); + return true; + } +}; + +class CommandBSKickColors : public CommandBSKickBase +{ + public: + CommandBSKickColors(Module *creator) : CommandBSKickBase(creator, "botserv/kick/colors", 2, 3) + { + this->SetDesc(_("Configures color kicker")); + this->SetSyntax(_("\037channel\037 {\037ON|OFF\037} [\037ttb\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci; + if (CheckArguments(source, params, ci)) + { + KickerData *kd = ci->Require("kickerdata"); + Process(source, ci, params[1], params.size() > 2 ? params[2] : "", TTB_COLORS, "colors", kd, kd->colors); + kd->Check(ci); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets the colors kicker on or off. When enabled, this\n" + "option tells the bot to kick users who use colors.\n" + " \n" + "\037ttb\037 is the number of times a user can be kicked\n" + "before it gets banned. Don't give ttb to disable\n" + "the ban system once activated.")); + return true; + } +}; + +class CommandBSKickFlood : public CommandBSKickBase +{ + public: + CommandBSKickFlood(Module *creator) : CommandBSKickBase(creator, "botserv/kick/flood", 2, 5) + { + this->SetDesc(_("Configures flood kicker")); + this->SetSyntax(_("\037channel\037 {\037ON|OFF\037} [\037ttb\037 [\037ln\037 [\037secs\037]]]\002")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci; + if (!CheckArguments(source, params, ci)) + return; + + KickerData *kd = ci->Require("kickerdata"); + + if (params[1].equals_ci("ON")) + { + const Anope::string &ttb = params.size() > 2 ? params[2] : "", + &lines = params.size() > 3 ? params[3] : "", + &secs = params.size() > 4 ? params[4] : ""; + + if (!ttb.empty()) + { + int16_t i; + + try + { + i = convertTo(ttb); + if (i < 0) + throw ConvertException(); + } + catch (const ConvertException &) + { + source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); + return; + } + + kd->ttb[TTB_FLOOD] = i; + } + else + kd->ttb[TTB_FLOOD] = 0; + + kd->floodlines = 6; + try + { + kd->floodlines = convertTo(lines); + } + catch (const ConvertException &) { } + if (kd->floodlines < 2) + kd->floodlines = 6; + + kd->floodsecs = 10; + try + { + kd->floodsecs = convertTo(secs); + } + catch (const ConvertException &) { } + if (kd->floodsecs < 1) + kd->floodsecs = 10; + if (kd->floodsecs > Config->GetModule(me)->Get("keepdata")) + kd->floodsecs = Config->GetModule(me)->Get("keepdata"); + + kd->flood = true; + if (kd->ttb[TTB_FLOOD]) + source.Reply(_("Bot will now kick for \002flood\002 (%d lines in %d seconds\n" + "and will place a ban after %d kicks for the same user."), kd->floodlines, kd->floodsecs, kd->ttb[TTB_FLOOD]); + else + source.Reply(_("Bot will now kick for \002flood\002 (%d lines in %d seconds)."), kd->floodlines, kd->floodsecs); + } + else if (params[1].equals_ci("OFF")) + { + kd->flood = false; + source.Reply(_("Bot won't kick for \002flood\002 anymore.")); + } + else + this->OnSyntaxError(source, params[1]); + + kd->Check(ci); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets the flood kicker on or off. When enabled, this\n" + "option tells the bot to kick users who are flooding\n" + "the channel using at least \002ln\002 lines in \002secs\002 seconds\n" + "(if not given, it defaults to 6 lines in 10 seconds).\n" + " \n" + "\037ttb\037 is the number of times a user can be kicked\n" + "before it gets banned. Don't give ttb to disable\n" + "the ban system once activated.")); + return true; + } +}; + +class CommandBSKickItalics : public CommandBSKickBase +{ + public: + CommandBSKickItalics(Module *creator) : CommandBSKickBase(creator, "botserv/kick/italics", 2, 3) + { + this->SetDesc(_("Configures italics kicker")); + this->SetSyntax(_("\037channel\037 {\037ON|OFF\037} [\037ttb\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci; + if (CheckArguments(source, params, ci)) + { + KickerData *kd = ci->Require("kickerdata"); + Process(source, ci, params[1], params.size() > 2 ? params[2] : "", TTB_ITALICS, "italics", kd, kd->italics); + kd->Check(ci); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets the italics kicker on or off. When enabled, this\n" + "option tells the bot to kick users who use italics.\n" + " \n" + "\037ttb\037 is the number of times a user can be kicked\n" + "before it gets banned. Don't give ttb to disable\n" + "the ban system once activated.")); + return true; + } +}; + +class CommandBSKickRepeat : public CommandBSKickBase +{ + public: + CommandBSKickRepeat(Module *creator) : CommandBSKickBase(creator, "botserv/kick/repeat", 2, 4) + { + this->SetDesc(_("Configures repeat kicker")); + this->SetSyntax(_("\037channel\037 {\037ON|OFF\037} [\037ttb\037 [\037num\037]]\002")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci; + if (!CheckArguments(source, params, ci)) + return; + + KickerData *kd = ci->Require("kickerdata"); + + if (params[1].equals_ci("ON")) + { + const Anope::string &ttb = params.size() > 2 ? params[2] : "", + × = params.size() > 3 ? params[3] : ""; + + if (!ttb.empty()) + { + int16_t i; + + try + { + i = convertTo(ttb); + if (i < 0) + throw ConvertException(); + } + catch (const ConvertException &) + { + source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); + return; + } + + kd->ttb[TTB_REPEAT] = i; + } + else + kd->ttb[TTB_REPEAT] = 0; + + kd->repeattimes = 3; + try + { + kd->repeattimes = convertTo(times); + } + catch (const ConvertException &) { } + if (kd->repeattimes < 1) + kd->repeattimes = 3; + + kd->repeat = true; + if (kd->ttb[TTB_REPEAT]) + { + if (kd->repeattimes != 1) + source.Reply(_("Bot will now kick for \002repeats\002 (users that repeat the\n" + "same message %d times), and will place a ban after %d\n" + "kicks for the same user."), kd->repeattimes, kd->ttb[TTB_REPEAT]); + else + source.Reply(_("Bot will now kick for \002repeats\002 (users that repeat the\n" + "same message %d time), and will place a ban after %d\n" + "kicks for the same user."), kd->repeattimes, kd->ttb[TTB_REPEAT]); + } + else + { + if (kd->repeattimes != 1) + source.Reply(_("Bot will now kick for \002repeats\002 (users that repeat the\n" + "same message %d times)."), kd->repeattimes); + else + source.Reply(_("Bot will now kick for \002repeats\002 (users that repeat the\n" + "same message %d time)."), kd->repeattimes); + } + } + else if (params[1].equals_ci("OFF")) + { + kd->repeat = false; + source.Reply(_("Bot won't kick for \002repeats\002 anymore.")); + } + else + this->OnSyntaxError(source, params[1]); + + kd->Check(ci); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets the repeat kicker on or off. When enabled, this\n" + "option tells the bot to kick users who are repeating\n" + "themselves \002num\002 times (if num is not given, it\n" + "defaults to 3).\n" + " \n" + "\037ttb\037 is the number of times a user can be kicked\n" + "before it gets banned. Don't give ttb to disable\n" + "the ban system once activated.")); + return true; + } +}; + +class CommandBSKickReverses : public CommandBSKickBase +{ + public: + CommandBSKickReverses(Module *creator) : CommandBSKickBase(creator, "botserv/kick/reverses", 2, 3) + { + this->SetDesc(_("Configures reverses kicker")); + this->SetSyntax(_("\037channel\037 {\037ON|OFF\037} [\037ttb\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci; + if (CheckArguments(source, params, ci)) + { + KickerData *kd = ci->Require("kickerdata"); + Process(source, ci, params[1], params.size() > 2 ? params[2] : "", TTB_REVERSES, "reverses", kd, kd->reverses); + kd->Check(ci); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets the reverses kicker on or off. When enabled, this\n" + "option tells the bot to kick users who use reverses.\n" + " \n" + "\037ttb\037 is the number of times a user can be kicked\n" + "before it gets banned. Don't give ttb to disable\n" + "the ban system once activated.")); + return true; + } +}; + +class CommandBSKickUnderlines : public CommandBSKickBase +{ + public: + CommandBSKickUnderlines(Module *creator) : CommandBSKickBase(creator, "botserv/kick/underlines", 2, 3) + { + this->SetDesc(_("Configures underlines kicker")); + this->SetSyntax(_("\037channel\037 {\037ON|OFF\037} [\037ttb\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci; + if (CheckArguments(source, params, ci)) + { + KickerData *kd = ci->Require("kickerdata"); + Process(source, ci, params[1], params.size() > 2 ? params[2] : "", TTB_UNDERLINES, "underlines", kd, kd->underlines); + kd->Check(ci); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets the underlines kicker on or off. When enabled, this\n" + "option tells the bot to kick users who use underlines.\n" + " \n" + "\037ttb\037 is the number of times a user can be kicked\n" + "before it gets banned. Don't give ttb to disable\n" + "the ban system once activated.")); + return true; + } +}; + +class CommandBSSetDontKickOps : public Command +{ + public: + CommandBSSetDontKickOps(Module *creator, const Anope::string &sname = "botserv/set/dontkickops") : Command(creator, sname, 2, 2) + { + this->SetDesc(_("To protect ops against bot kicks")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + AccessGroup access = source.AccessFor(ci); + if (!source.HasPriv("botserv/administration") && !access.HasPriv("SET")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, bot option setting is temporarily disabled.")); + return; + } + + KickerData *kd = ci->Require("kickerdata"); + if (params[1].equals_ci("ON")) + { + bool override = !access.HasPriv("SET"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to enable dontkickops"; + + kd->dontkickops = true; + source.Reply(_("Bot \002won't kick ops\002 on channel %s."), ci->name.c_str()); + } + else if (params[1].equals_ci("OFF")) + { + bool override = !access.HasPriv("SET"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to disable dontkickops"; + + kd->dontkickops = false; + source.Reply(_("Bot \002will kick ops\002 on channel %s."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, source.command); + + kd->Check(ci); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(_(" \n" + "Enables or disables \002ops protection\002 mode on a channel.\n" + "When it is enabled, ops won't be kicked by the bot\n" + "even if they don't match the NOKICK level.")); + return true; + } +}; + +class CommandBSSetDontKickVoices : public Command +{ + public: + CommandBSSetDontKickVoices(Module *creator, const Anope::string &sname = "botserv/set/dontkickvoices") : Command(creator, sname, 2, 2) + { + this->SetDesc(_("To protect voices against bot kicks")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + AccessGroup access = source.AccessFor(ci); + if (!source.HasPriv("botserv/administration") && !access.HasPriv("SET")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, bot option setting is temporarily disabled.")); + return; + } + + KickerData *kd = ci->Require("kickerdata"); + if (params[1].equals_ci("ON")) + { + bool override = !access.HasPriv("SET"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to enable dontkickvoices"; + + kd->dontkickvoices = true; + source.Reply(_("Bot \002won't kick voices\002 on channel %s."), ci->name.c_str()); + } + else if (params[1].equals_ci("OFF")) + { + bool override = !access.HasPriv("SET"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to disable dontkickvoices"; + + kd->dontkickvoices = false; + source.Reply(_("Bot \002will kick voices\002 on channel %s."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, source.command); + + kd->Check(ci); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(_(" \n" + "Enables or disables \002voices protection\002 mode on a channel.\n" + "When it is enabled, voices won't be kicked by the bot\n" + "even if they don't match the NOKICK level.")); + return true; + } +}; + +struct BanData +{ + struct Data + { + Anope::string mask; + time_t last_use; + int16_t ttb[TTB_SIZE]; + + Data() + { + last_use = 0; + for (int i = 0; i < TTB_SIZE; ++i) + this->ttb[i] = 0; + } + }; + + private: + typedef Anope::map data_type; + data_type data_map; + + public: + BanData(Extensible *) { } + + Data &get(const Anope::string &key) + { + return this->data_map[key]; + } + + bool empty() const + { + return this->data_map.empty(); + } + + void purge() + { + time_t keepdata = Config->GetModule(me)->Get("keepdata"); + for (data_type::iterator it = data_map.begin(), it_end = data_map.end(); it != it_end;) + { + const Anope::string &user = it->first; + Data &bd = it->second; + ++it; + + if (Anope::CurTime - bd.last_use > keepdata) + data_map.erase(user); + } + } +}; + +struct UserData +{ + UserData(Extensible *) + { + last_use = last_start = Anope::CurTime; + lines = times = 0; + lastline.clear(); + } + + /* Data validity */ + time_t last_use; + + /* for flood kicker */ + int16_t lines; + time_t last_start; + + /* for repeat kicker */ + Anope::string lasttarget; + int16_t times; + + Anope::string lastline; +}; + +class BanDataPurger : public Timer +{ + public: + BanDataPurger(Module *o) : Timer(o, 300, Anope::CurTime, true) { } + + void Tick(time_t) anope_override + { + Log(LOG_DEBUG) << "bs_main: Running bandata purger"; + + for (channel_map::iterator it = ChannelList.begin(), it_end = ChannelList.end(); it != it_end; ++it) + { + Channel *c = it->second; + + BanData *bd = c->GetExt("bandata"); + if (bd != NULL) + { + bd->purge(); + if (bd->empty()) + c->Shrink("bandata"); + } + } + } +}; + +class BSKick : public Module +{ + ExtensibleItem bandata; + ExtensibleItem userdata; + KickerDataImpl::ExtensibleItem kickerdata; + + CommandBSKick commandbskick; + CommandBSKickAMSG commandbskickamsg; + CommandBSKickBadwords commandbskickbadwords; + CommandBSKickBolds commandbskickbolds; + CommandBSKickCaps commandbskickcaps; + CommandBSKickColors commandbskickcolors; + CommandBSKickFlood commandbskickflood; + CommandBSKickItalics commandbskickitalics; + CommandBSKickRepeat commandbskickrepeat; + CommandBSKickReverses commandbskickreverse; + CommandBSKickUnderlines commandbskickunderlines; + + CommandBSSetDontKickOps commandbssetdontkickops; + CommandBSSetDontKickVoices commandbssetdontkickvoices; + + BanDataPurger purger; + + BanData::Data &GetBanData(User *u, Channel *c) + { + BanData *bd = bandata.Require(c); + return bd->get(u->GetMask()); + } + + UserData *GetUserData(User *u, Channel *c) + { + ChanUserContainer *uc = c->FindUser(u); + if (uc == NULL) + return NULL; + + UserData *ud = userdata.Require(uc); + return ud; + } + + void check_ban(ChannelInfo *ci, User *u, KickerData *kd, int ttbtype) + { + /* Don't ban ulines or protected users */ + if (u->IsProtected()) + return; + + BanData::Data &bd = this->GetBanData(u, ci->c); + + ++bd.ttb[ttbtype]; + if (kd->ttb[ttbtype] && bd.ttb[ttbtype] >= kd->ttb[ttbtype]) + { + /* Should not use == here because bd.ttb[ttbtype] could possibly be > kd->ttb[ttbtype] + * if the TTB was changed after it was not set (0) before and the user had already been + * kicked a few times. Bug #1056 - Adam */ + + bd.ttb[ttbtype] = 0; + + Anope::string mask = ci->GetIdealBan(u); + + ci->c->SetMode(NULL, "BAN", mask); + FOREACH_MOD(OnBotBan, (u, ci, mask)); + } + } + + void bot_kick(ChannelInfo *ci, User *u, const char *message, ...) + { + va_list args; + char buf[1024]; + + if (!ci || !ci->bi || !ci->c || !u || u->IsProtected() || !ci->c->FindUser(u)) + return; + + Anope::string fmt = Language::Translate(u, message); + va_start(args, message); + vsnprintf(buf, sizeof(buf), fmt.c_str(), args); + va_end(args); + + ci->c->Kick(ci->bi, u, "%s", buf); + } + + public: + BSKick(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + bandata(this, "bandata"), + userdata(this, "userdata"), + kickerdata(this, "kickerdata"), + + commandbskick(this), + commandbskickamsg(this), commandbskickbadwords(this), commandbskickbolds(this), commandbskickcaps(this), + commandbskickcolors(this), commandbskickflood(this), commandbskickitalics(this), commandbskickrepeat(this), + commandbskickreverse(this), commandbskickunderlines(this), + + commandbssetdontkickops(this), commandbssetdontkickvoices(this), + + purger(this) + { + me = this; + + } + + void OnBotInfo(CommandSource &source, BotInfo *bi, ChannelInfo *ci, InfoFormatter &info) anope_override + { + if (!ci) + return; + + Anope::string enabled = Language::Translate(source.nc, _("Enabled")); + Anope::string disabled = Language::Translate(source.nc, _("Disabled")); + KickerData *kd = kickerdata.Get(ci); + + if (kd && kd->badwords) + { + if (kd->ttb[TTB_BADWORDS]) + info[_("Bad words kicker")] = Anope::printf("%s (%d kick(s) to ban)", enabled.c_str(), kd->ttb[TTB_BADWORDS]); + else + info[_("Bad words kicker")] = enabled; + } + else + info[_("Bad words kicker")] = disabled; + + if (kd && kd->bolds) + { + if (kd->ttb[TTB_BOLDS]) + info[_("Bolds kicker")] = Anope::printf("%s (%d kick(s) to ban)", enabled.c_str(), kd->ttb[TTB_BOLDS]); + else + info[_("Bolds kicker")] = enabled; + } + else + info[_("Bolds kicker")] = disabled; + + if (kd && kd->caps) + { + if (kd->ttb[TTB_CAPS]) + info[_("Caps kicker")] = Anope::printf(_("%s (%d kick(s) to ban; minimum %d/%d%%)"), enabled.c_str(), kd->ttb[TTB_CAPS], kd->capsmin, kd->capspercent); + else + info[_("Caps kicker")] = Anope::printf(_("%s (minimum %d/%d%%)"), enabled.c_str(), kd->capsmin, kd->capspercent); + } + else + info[_("Caps kicker")] = disabled; + + if (kd && kd->colors) + { + if (kd->ttb[TTB_COLORS]) + info[_("Colors kicker")] = Anope::printf(_("%s (%d kick(s) to ban)"), enabled.c_str(), kd->ttb[TTB_COLORS]); + else + info[_("Colors kicker")] = enabled; + } + else + info[_("Colors kicker")] = disabled; + + if (kd && kd->flood) + { + if (kd->ttb[TTB_FLOOD]) + info[_("Flood kicker")] = Anope::printf(_("%s (%d kick(s) to ban; %d lines in %ds)"), enabled.c_str(), kd->ttb[TTB_FLOOD], kd->floodlines, kd->floodsecs); + else + info[_("Flood kicker")] = Anope::printf(_("%s (%d lines in %ds)"), enabled.c_str(), kd->floodlines, kd->floodsecs); + } + else + info[_("Flood kicker")] = disabled; + + if (kd && kd->repeat) + { + if (kd->ttb[TTB_REPEAT]) + info[_("Repeat kicker")] = Anope::printf(_("%s (%d kick(s) to ban; %d times)"), enabled.c_str(), kd->ttb[TTB_REPEAT], kd->repeattimes); + else + info[_("Repeat kicker")] = Anope::printf(_("%s (%d times)"), enabled.c_str(), kd->repeattimes); + } + else + info[_("Repeat kicker")] = disabled; + + if (kd && kd->reverses) + { + if (kd->ttb[TTB_REVERSES]) + info[_("Reverses kicker")] = Anope::printf(_("%s (%d kick(s) to ban)"), enabled.c_str(), kd->ttb[TTB_REVERSES]); + else + info[_("Reverses kicker")] = enabled; + } + else + info[_("Reverses kicker")] = disabled; + + if (kd && kd->underlines) + { + if (kd->ttb[TTB_UNDERLINES]) + info[_("Underlines kicker")] = Anope::printf(_("%s (%d kick(s) to ban)"), enabled.c_str(), kd->ttb[TTB_UNDERLINES]); + else + info[_("Underlines kicker")] = enabled; + } + else + info[_("Underlines kicker")] = disabled; + + if (kd && kd->italics) + { + if (kd->ttb[TTB_ITALICS]) + info[_("Italics kicker")] = Anope::printf(_("%s (%d kick(s) to ban)"), enabled.c_str(), kd->ttb[TTB_ITALICS]); + else + info[_("Italics kicker")] = enabled; + } + else + info[_("Italics kicker")] = disabled; + + if (kd && kd->amsgs) + { + if (kd->ttb[TTB_AMSGS]) + info[_("AMSG kicker")] = Anope::printf(_("%s (%d kick(s) to ban)"), enabled.c_str(), kd->ttb[TTB_AMSGS]); + else + info[_("AMSG kicker")] = enabled; + } + else + info[_("AMSG kicker")] = disabled; + + if (kd && kd->dontkickops) + info.AddOption(_("Ops protection")); + if (kd && kd->dontkickvoices) + info.AddOption(_("Voices protection")); + } + + void OnPrivmsg(User *u, Channel *c, Anope::string &msg) anope_override + { + /* Now we can make kicker stuff. We try to order the checks + * from the fastest one to the slowest one, since there's + * no need to process other kickers if a user is kicked before + * the last kicker check. + * + * But FIRST we check whether the user is protected in any + * way. + */ + ChannelInfo *ci = c->ci; + if (ci == NULL) + return; + KickerData *kd = kickerdata.Get(ci); + if (kd == NULL) + return; + + if (ci->AccessFor(u).HasPriv("NOKICK")) + return; + else if (kd->dontkickops && (c->HasUserStatus(u, "HALFOP") || c->HasUserStatus(u, "OP") || c->HasUserStatus(u, "PROTECT") || c->HasUserStatus(u, "OWNER"))) + return; + else if (kd->dontkickvoices && c->HasUserStatus(u, "VOICE")) + return; + + Anope::string realbuf = msg; + + /* If it's a /me, cut the CTCP part because the ACTION will cause + * problems with the caps or badwords kicker + */ + if (realbuf.substr(0, 8).equals_ci("\1ACTION ") && realbuf[realbuf.length() - 1] == '\1') + { + realbuf.erase(0, 8); + realbuf.erase(realbuf.length() - 1); + } + + if (realbuf.empty()) + return; + + /* Bolds kicker */ + if (kd->bolds && realbuf.find(2) != Anope::string::npos) + { + check_ban(ci, u, kd, TTB_BOLDS); + bot_kick(ci, u, _("Don't use bolds on this channel!")); + return; + } + + /* Color kicker */ + if (kd->colors && realbuf.find(3) != Anope::string::npos) + { + check_ban(ci, u, kd, TTB_COLORS); + bot_kick(ci, u, _("Don't use colors on this channel!")); + return; + } + + /* Reverses kicker */ + if (kd->reverses && realbuf.find(22) != Anope::string::npos) + { + check_ban(ci, u, kd, TTB_REVERSES); + bot_kick(ci, u, _("Don't use reverses on this channel!")); + return; + } + + /* Italics kicker */ + if (kd->italics && realbuf.find(29) != Anope::string::npos) + { + check_ban(ci, u, kd, TTB_ITALICS); + bot_kick(ci, u, _("Don't use italics on this channel!")); + return; + } + + /* Underlines kicker */ + if (kd->underlines && realbuf.find(31) != Anope::string::npos) + { + check_ban(ci, u, kd, TTB_UNDERLINES); + bot_kick(ci, u, _("Don't use underlines on this channel!")); + return; + } + + /* Caps kicker */ + if (kd->caps && realbuf.length() >= static_cast(kd->capsmin)) + { + int i = 0, l = 0; + + for (unsigned j = 0, end = realbuf.length(); j < end; ++j) + { + if (isupper(realbuf[j])) + ++i; + else if (islower(realbuf[j])) + ++l; + } + + /* i counts uppercase chars, l counts lowercase chars. Only + * alphabetic chars (so islower || isupper) qualify for the + * percentage of caps to kick for; the rest is ignored. -GD + */ + + if ((i || l) && i >= kd->capsmin && i * 100 / (i + l) >= kd->capspercent) + { + check_ban(ci, u, kd, TTB_CAPS); + bot_kick(ci, u, _("Turn caps lock OFF!")); + return; + } + } + + /* Bad words kicker */ + if (kd->badwords) + { + bool mustkick = false; + BadWords *badwords = ci->GetExt("badwords"); + + /* Normalize the buffer */ + Anope::string nbuf = Anope::NormalizeBuffer(realbuf); + bool casesensitive = Config->GetModule("botserv")->Get("casesensitive"); + + /* Normalize can return an empty string if this only contains control codes etc */ + if (badwords && !nbuf.empty()) + for (unsigned i = 0; i < badwords->GetBadWordCount(); ++i) + { + const BadWord *bw = badwords->GetBadWord(i); + + if (bw->word.empty()) + continue; // Shouldn't happen + + if (bw->word.length() > nbuf.length()) + continue; // This can't ever match + + if (bw->type == BW_ANY && ((casesensitive && nbuf.find(bw->word) != Anope::string::npos) || (!casesensitive && nbuf.find_ci(bw->word) != Anope::string::npos))) + mustkick = true; + else if (bw->type == BW_SINGLE) + { + size_t len = bw->word.length(); + + if ((casesensitive && bw->word.equals_cs(nbuf)) || (!casesensitive && bw->word.equals_ci(nbuf))) + mustkick = true; + else if (nbuf.find(' ') == len && ((casesensitive && bw->word.equals_cs(nbuf.substr(0, len))) || (!casesensitive && bw->word.equals_ci(nbuf.substr(0, len))))) + mustkick = true; + else + { + if (len < nbuf.length() && nbuf.rfind(' ') == nbuf.length() - len - 1 && ((casesensitive && nbuf.find(bw->word) == nbuf.length() - len) || (!casesensitive && nbuf.find_ci(bw->word) == nbuf.length() - len))) + mustkick = true; + else + { + Anope::string wordbuf = " " + bw->word + " "; + + if ((casesensitive && nbuf.find(wordbuf) != Anope::string::npos) || (!casesensitive && nbuf.find_ci(wordbuf) != Anope::string::npos)) + mustkick = true; + } + } + } + else if (bw->type == BW_START) + { + size_t len = bw->word.length(); + + if ((casesensitive && nbuf.substr(0, len).equals_cs(bw->word)) || (!casesensitive && nbuf.substr(0, len).equals_ci(bw->word))) + mustkick = true; + else + { + Anope::string wordbuf = " " + bw->word; + + if ((casesensitive && nbuf.find(wordbuf) != Anope::string::npos) || (!casesensitive && nbuf.find_ci(wordbuf) != Anope::string::npos)) + mustkick = true; + } + } + else if (bw->type == BW_END) + { + size_t len = bw->word.length(); + + if ((casesensitive && nbuf.substr(nbuf.length() - len).equals_cs(bw->word)) || (!casesensitive && nbuf.substr(nbuf.length() - len).equals_ci(bw->word))) + mustkick = true; + else + { + Anope::string wordbuf = bw->word + " "; + + if ((casesensitive && nbuf.find(wordbuf) != Anope::string::npos) || (!casesensitive && nbuf.find_ci(wordbuf) != Anope::string::npos)) + mustkick = true; + } + } + + if (mustkick) + { + check_ban(ci, u, kd, TTB_BADWORDS); + if (Config->GetModule(me)->Get("gentlebadwordreason")) + bot_kick(ci, u, _("Watch your language!")); + else + bot_kick(ci, u, _("Don't use the word \"%s\" on this channel!"), bw->word.c_str()); + + return; + } + } /* for */ + } /* if badwords */ + + UserData *ud = GetUserData(u, c); + + if (ud) + { + /* Flood kicker */ + if (kd->flood) + { + if (Anope::CurTime - ud->last_start > kd->floodsecs) + { + ud->last_start = Anope::CurTime; + ud->lines = 0; + } + + ++ud->lines; + if (ud->lines >= kd->floodlines) + { + check_ban(ci, u, kd, TTB_FLOOD); + bot_kick(ci, u, _("Stop flooding!")); + return; + } + } + + /* Repeat kicker */ + if (kd->repeat) + { + if (!ud->lastline.equals_ci(realbuf)) + ud->times = 0; + else + ++ud->times; + + if (ud->times >= kd->repeattimes) + { + check_ban(ci, u, kd, TTB_REPEAT); + bot_kick(ci, u, _("Stop repeating yourself!")); + return; + } + } + + if (ud->lastline.equals_ci(realbuf) && !ud->lasttarget.empty() && !ud->lasttarget.equals_ci(ci->name)) + { + for (User::ChanUserList::iterator it = u->chans.begin(); it != u->chans.end();) + { + Channel *chan = it->second->chan; + ++it; + + if (chan->ci && kd->amsgs && !chan->ci->AccessFor(u).HasPriv("NOKICK")) + { + check_ban(chan->ci, u, kd, TTB_AMSGS); + bot_kick(chan->ci, u, _("Don't use AMSGs!")); + } + } + } + + ud->lasttarget = ci->name; + ud->lastline = realbuf; + } + } +}; + +MODULE_INIT(BSKick) diff --git a/modules/commands/bs_set.cpp b/modules/commands/bs_set.cpp new file mode 100644 index 0000000..3c6335b --- /dev/null +++ b/modules/commands/bs_set.cpp @@ -0,0 +1,228 @@ +/* BotServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandBSSet : public Command +{ + public: + CommandBSSet(Module *creator) : Command(creator, "botserv/set", 3, 3) + { + this->SetDesc(_("Configures bot options")); + this->SetSyntax(_("\037option\037 \037(channel | bot)\037 \037settings\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Configures bot options.\n" + " \n" + "Available options:")); + bool hide_privileged_commands = Config->GetBlock("options")->Get("hideprivilegedcommands"), + hide_registered_commands = Config->GetBlock("options")->Get("hideregisteredcommands"); + Anope::string this_name = source.command; + for (CommandInfo::map::const_iterator it = source.service->commands.begin(), it_end = source.service->commands.end(); it != it_end; ++it) + { + const Anope::string &c_name = it->first; + const CommandInfo &info = it->second; + if (c_name.find_ci(this_name + " ") == 0) + { + if (info.hide) + continue; + + ServiceReference command("Command", info.name); + if (command) + { + // XXX dup + if (hide_registered_commands && !command->AllowUnregistered() && !source.GetAccount()) + continue; + + if (hide_privileged_commands && !info.permission.empty() && !source.HasCommand(info.permission)) + continue; + + source.command = it->first; + command->OnServHelp(source); + } + } + } + source.Reply(_("Type \002%s%s HELP %s \037option\037\002 for more information on a\n" + "particular option."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), this_name.c_str()); + + return true; + } +}; + +class CommandBSSetBanExpire : public Command +{ + public: + class UnbanTimer : public Timer + { + Anope::string chname; + Anope::string mask; + + public: + UnbanTimer(Module *creator, const Anope::string &ch, const Anope::string &bmask, time_t t) : Timer(creator, t), chname(ch), mask(bmask) { } + + void Tick(time_t) anope_override + { + Channel *c = Channel::Find(chname); + if (c) + c->RemoveMode(NULL, "BAN", mask); + } + }; + + CommandBSSetBanExpire(Module *creator, const Anope::string &sname = "botserv/set/banexpire") : Command(creator, sname, 2, 2) + { + this->SetDesc(_("Configures the time bot bans expire in")); + this->SetSyntax(_("\037channel\037 \037time\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &chan = params[0]; + const Anope::string &arg = params[1]; + + ChannelInfo *ci = ChannelInfo::Find(chan); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); + return; + } + + AccessGroup access = source.AccessFor(ci); + if (!source.HasPriv("botserv/administration") && !access.HasPriv("SET")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, changing bot options is temporarily disabled.")); + return; + } + + time_t t = Anope::DoTime(arg); + if (t < 0) + { + source.Reply(BAD_EXPIRY_TIME); + return; + } + + /* cap at 1 day */ + if (t > 86400) + { + source.Reply(_("Ban expiry may not be longer than 1 day.")); + return; + } + + ci->banexpire = t; + + bool override = !access.HasPriv("SET"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to change banexpire to " << ci->banexpire; + + if (!ci->banexpire) + source.Reply(_("Bot bans will no longer automatically expire.")); + else + source.Reply(_("Bot bans will automatically expire after %s."), Anope::Duration(ci->banexpire, source.GetAccount()).c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(_(" \n" + "Sets the time bot bans expire in. If enabled, any bans placed by\n" + "bots, such as flood kicker, badwords kicker, etc. will automatically\n" + "be removed after the given time. Set to 0 to disable bans from\n" + "automatically expiring.")); + return true; + } +}; + +class CommandBSSetPrivate : public Command +{ + public: + CommandBSSetPrivate(Module *creator, const Anope::string &sname = "botserv/set/private") : Command(creator, sname, 2, 2) + { + this->SetDesc(_("Prevent a bot from being assigned by non IRC operators")); + this->SetSyntax(_("\037botname\037 {\037ON|OFF\037}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + BotInfo *bi = BotInfo::Find(params[0], true); + const Anope::string &value = params[1]; + + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + if (bi == NULL) + { + source.Reply(BOT_DOES_NOT_EXIST, params[0].c_str()); + return; + } + + if (value.equals_ci("ON")) + { + bi->oper_only = true; + source.Reply(_("Private mode of bot %s is now \002on\002."), bi->nick.c_str()); + } + else if (value.equals_ci("OFF")) + { + bi->oper_only = false; + source.Reply(_("Private mode of bot %s is now \002off\002."), bi->nick.c_str()); + } + else + this->OnSyntaxError(source, source.command); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(_(" \n" + "This option prevents a bot from being assigned to a\n" + "channel by users that aren't IRC Operators.")); + return true; + } +}; + +class BSSet : public Module +{ + CommandBSSet commandbsset; + CommandBSSetBanExpire commandbssetbanexpire; + CommandBSSetPrivate commandbssetprivate; + + public: + BSSet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandbsset(this), commandbssetbanexpire(this), + commandbssetprivate(this) + { + } + + void OnBotBan(User *u, ChannelInfo *ci, const Anope::string &mask) anope_override + { + if (!ci->banexpire) + return; + + new CommandBSSetBanExpire::UnbanTimer(this, ci->name, mask, ci->banexpire); + } +}; + +MODULE_INIT(BSSet) diff --git a/modules/commands/cs_access.cpp b/modules/commands/cs_access.cpp new file mode 100644 index 0000000..6f6cbfd --- /dev/null +++ b/modules/commands/cs_access.cpp @@ -0,0 +1,917 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +static std::map defaultLevels; + +static inline void reset_levels(ChannelInfo *ci) +{ + ci->ClearLevels(); + for (std::map::iterator it = defaultLevels.begin(), it_end = defaultLevels.end(); it != it_end; ++it) + ci->SetLevel(it->first, it->second); +} + +class AccessChanAccess : public ChanAccess +{ + public: + int level; + + AccessChanAccess(AccessProvider *p) : ChanAccess(p), level(0) + { + } + + bool HasPriv(const Anope::string &name) const anope_override + { + return this->ci->GetLevel(name) != ACCESS_INVALID && this->level >= this->ci->GetLevel(name); + } + + Anope::string AccessSerialize() const anope_override + { + return stringify(this->level); + } + + void AccessUnserialize(const Anope::string &data) anope_override + { + try + { + this->level = convertTo(data); + } + catch (const ConvertException &) + { + } + } + + bool operator>(const ChanAccess &other) const anope_override + { + if (this->provider != other.provider) + return ChanAccess::operator>(other); + else + return this->level > anope_dynamic_static_cast(&other)->level; + } + + bool operator<(const ChanAccess &other) const anope_override + { + if (this->provider != other.provider) + return ChanAccess::operator<(other); + else + return this->level < anope_dynamic_static_cast(&other)->level; + } +}; + +class AccessAccessProvider : public AccessProvider +{ + public: + static AccessAccessProvider *me; + + AccessAccessProvider(Module *o) : AccessProvider(o, "access/access") + { + me = this; + } + + ChanAccess *Create() anope_override + { + return new AccessChanAccess(this); + } +}; +AccessAccessProvider* AccessAccessProvider::me; + +class CommandCSAccess : public Command +{ + void DoAdd(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + Anope::string mask = params[2]; + Privilege *p = NULL; + int level = ACCESS_INVALID; + + try + { + level = convertTo(params[3]); + } + catch (const ConvertException &) + { + p = PrivilegeManager::FindPrivilege(params[3]); + if (p != NULL && defaultLevels[p->name]) + level = defaultLevels[p->name]; + } + + if (!level) + { + source.Reply(_("Access level must be non-zero.")); + return; + } + else if (level <= ACCESS_INVALID || level >= ACCESS_FOUNDER) + { + source.Reply(CHAN_ACCESS_LEVEL_RANGE, ACCESS_INVALID + 1, ACCESS_FOUNDER - 1); + return; + } + + AccessGroup u_access = source.AccessFor(ci); + const ChanAccess *highest = u_access.Highest(); + + AccessChanAccess tmp_access(AccessAccessProvider::me); + tmp_access.ci = ci; + tmp_access.level = level; + + bool override = false; + const NickAlias *na = NULL; + + if ((!highest || *highest <= tmp_access) && !u_access.founder) + { + if (source.HasPriv("chanserv/access/modify")) + override = true; + else + { + source.Reply(ACCESS_DENIED); + return; + } + } + + if (IRCD->IsChannelValid(mask)) + { + if (Config->GetModule("chanserv")->Get("disallow_channel_access")) + { + source.Reply(_("Channels may not be on access lists.")); + return; + } + + ChannelInfo *targ_ci = ChannelInfo::Find(mask); + if (targ_ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, mask.c_str()); + return; + } + else if (ci == targ_ci) + { + source.Reply(_("You can't add a channel to its own access list.")); + return; + } + + mask = targ_ci->name; + } + else + { + na = NickAlias::Find(mask); + + if (!na && Config->GetModule("chanserv")->Get("disallow_hostmask_access")) + { + source.Reply(_("Masks and unregistered users may not be on access lists.")); + return; + } + else if (mask.find_first_of("!*@") == Anope::string::npos && !na) + { + User *targ = User::Find(mask, true); + if (targ != NULL) + mask = "*!*@" + targ->GetDisplayedHost(); + else + { + source.Reply(NICK_X_NOT_REGISTERED, mask.c_str()); + return; + } + } + + if (na) + mask = na->nick; + } + + for (unsigned i = ci->GetAccessCount(); i > 0; --i) + { + const ChanAccess *access = ci->GetAccess(i - 1); + if ((na && na->nc == access->GetAccount()) || mask.equals_ci(access->Mask())) + { + /* Don't allow lowering from a level >= u_level */ + if ((!highest || *access >= *highest) && !u_access.founder && !source.HasPriv("chanserv/access/modify")) + { + source.Reply(ACCESS_DENIED); + return; + } + delete ci->EraseAccess(i - 1); + break; + } + } + + unsigned access_max = Config->GetModule("chanserv")->Get("accessmax", "1024"); + if (access_max && ci->GetDeepAccessCount() >= access_max) + { + source.Reply(_("Sorry, you can only have %d access entries on a channel, including access entries from other channels."), access_max); + return; + } + + ServiceReference provider("AccessProvider", "access/access"); + if (!provider) + return; + AccessChanAccess *access = anope_dynamic_static_cast(provider->Create()); + access->SetMask(mask, ci); + access->creator = source.GetNick(); + access->level = level; + access->last_seen = 0; + access->created = Anope::CurTime; + ci->AddAccess(access); + + FOREACH_MOD(OnAccessAdd, (ci, source, access)); + + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to add " << mask << " with level " << level; + if (p != NULL) + source.Reply(_("\002%s\002 added to %s access list at privilege %s (level %d)"), access->Mask().c_str(), ci->name.c_str(), p->name.c_str(), level); + else + source.Reply(_("\002%s\002 added to %s access list at level \002%d\002."), access->Mask().c_str(), ci->name.c_str(), level); + } + + void DoDel(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + Anope::string mask = params[2]; + + if (!isdigit(mask[0]) && mask.find_first_of("#!*@") == Anope::string::npos && !NickAlias::Find(mask)) + { + User *targ = User::Find(mask, true); + if (targ != NULL) + mask = "*!*@" + targ->GetDisplayedHost(); + else + { + source.Reply(NICK_X_NOT_REGISTERED, mask.c_str()); + return; + } + } + + if (!ci->GetAccessCount()) + source.Reply(_("%s access list is empty."), ci->name.c_str()); + else if (isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) + { + class AccessDelCallback : public NumberList + { + CommandSource &source; + ChannelInfo *ci; + Command *c; + unsigned deleted; + Anope::string Nicks; + bool denied; + bool override; + public: + AccessDelCallback(CommandSource &_source, ChannelInfo *_ci, Command *_c, const Anope::string &numlist) : NumberList(numlist, true), source(_source), ci(_ci), c(_c), deleted(0), denied(false), override(false) + { + if (!source.AccessFor(ci).HasPriv("ACCESS_CHANGE") && source.HasPriv("chanserv/access/modify")) + this->override = true; + } + + ~AccessDelCallback() + { + if (denied && !deleted) + source.Reply(ACCESS_DENIED); + else if (!deleted) + source.Reply(_("No matching entries on %s access list."), ci->name.c_str()); + else + { + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, c, ci) << "to delete " << Nicks; + + if (deleted == 1) + source.Reply(_("Deleted 1 entry from %s access list."), ci->name.c_str()); + else + source.Reply(_("Deleted %d entries from %s access list."), deleted, ci->name.c_str()); + } + } + + void HandleNumber(unsigned Number) anope_override + { + if (!Number || Number > ci->GetAccessCount()) + return; + + ChanAccess *access = ci->GetAccess(Number - 1); + + AccessGroup ag = source.AccessFor(ci); + const ChanAccess *u_highest = ag.Highest(); + + if ((!u_highest || *u_highest <= *access) && !ag.founder && !this->override && access->GetAccount() != source.nc) + { + denied = true; + return; + } + + ++deleted; + if (!Nicks.empty()) + Nicks += ", " + access->Mask(); + else + Nicks = access->Mask(); + + ci->EraseAccess(Number - 1); + + FOREACH_MOD(OnAccessDel, (ci, source, access)); + delete access; + } + } + delcallback(source, ci, this, mask); + delcallback.Process(); + } + else + { + AccessGroup u_access = source.AccessFor(ci); + const ChanAccess *highest = u_access.Highest(); + + for (unsigned i = ci->GetAccessCount(); i > 0; --i) + { + ChanAccess *access = ci->GetAccess(i - 1); + if (mask.equals_ci(access->Mask())) + { + if (access->GetAccount() != source.nc && !u_access.founder && (!highest || *highest <= *access) && !source.HasPriv("chanserv/access/modify")) + source.Reply(ACCESS_DENIED); + else + { + source.Reply(_("\002%s\002 deleted from %s access list."), access->Mask().c_str(), ci->name.c_str()); + bool override = !u_access.founder && !u_access.HasPriv("ACCESS_CHANGE") && access->GetAccount() != source.nc; + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to delete " << access->Mask(); + + ci->EraseAccess(i - 1); + FOREACH_MOD(OnAccessDel, (ci, source, access)); + delete access; + } + return; + } + } + + source.Reply(_("\002%s\002 not found on %s access list."), mask.c_str(), ci->name.c_str()); + } + + return; + } + + void ProcessList(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms, ListFormatter &list) + { + const Anope::string &nick = params.size() > 2 ? params[2] : ""; + + if (!ci->GetAccessCount()) + source.Reply(_("%s access list is empty."), ci->name.c_str()); + else if (!nick.empty() && nick.find_first_not_of("1234567890,-") == Anope::string::npos) + { + class AccessListCallback : public NumberList + { + ListFormatter &list; + ChannelInfo *ci; + + public: + AccessListCallback(ListFormatter &_list, ChannelInfo *_ci, const Anope::string &numlist) : NumberList(numlist, false), list(_list), ci(_ci) + { + } + + void HandleNumber(unsigned number) anope_override + { + if (!number || number > ci->GetAccessCount()) + return; + + const ChanAccess *access = ci->GetAccess(number - 1); + + Anope::string timebuf; + if (ci->c) + for (Channel::ChanUserList::const_iterator cit = ci->c->users.begin(), cit_end = ci->c->users.end(); cit != cit_end; ++cit) + { + ChannelInfo *p; + if (access->Matches(cit->second->user, cit->second->user->Account(), p)) + timebuf = "Now"; + } + if (timebuf.empty()) + { + if (access->last_seen == 0) + timebuf = "Never"; + else + timebuf = Anope::strftime(access->last_seen, NULL, true); + } + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(number); + entry["Level"] = access->AccessSerialize(); + entry["Mask"] = access->Mask(); + entry["By"] = access->creator; + entry["Last seen"] = timebuf; + this->list.AddEntry(entry); + } + } + nl_list(list, ci, nick); + nl_list.Process(); + } + else + { + for (unsigned i = 0, end = ci->GetAccessCount(); i < end; ++i) + { + const ChanAccess *access = ci->GetAccess(i); + + if (!nick.empty() && !Anope::Match(access->Mask(), nick)) + continue; + + Anope::string timebuf; + if (ci->c) + for (Channel::ChanUserList::const_iterator cit = ci->c->users.begin(), cit_end = ci->c->users.end(); cit != cit_end; ++cit) + { + ChannelInfo *p; + if (access->Matches(cit->second->user, cit->second->user->Account(), p)) + timebuf = "Now"; + } + if (timebuf.empty()) + { + if (access->last_seen == 0) + timebuf = "Never"; + else + timebuf = Anope::strftime(access->last_seen, NULL, true); + } + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(i + 1); + entry["Level"] = access->AccessSerialize(); + entry["Mask"] = access->Mask(); + entry["By"] = access->creator; + entry["Last seen"] = timebuf; + list.AddEntry(entry); + } + } + + if (list.IsEmpty()) + source.Reply(_("No matching entries on %s access list."), ci->name.c_str()); + else + { + std::vector replies; + list.Process(replies); + + source.Reply(_("Access list for %s:"), ci->name.c_str()); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("End of access list")); + } + + return; + } + + void DoList(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + if (!ci->GetAccessCount()) + { + source.Reply(_("%s access list is empty."), ci->name.c_str()); + return; + } + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Level")).AddColumn(_("Mask")); + this->ProcessList(source, ci, params, list); + } + + void DoView(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + if (!ci->GetAccessCount()) + { + source.Reply(_("%s access list is empty."), ci->name.c_str()); + return; + } + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Level")).AddColumn(_("Mask")).AddColumn(_("By")).AddColumn(_("Last seen")); + this->ProcessList(source, ci, params, list); + } + + void DoClear(CommandSource &source, ChannelInfo *ci) + { + if (!source.IsFounder(ci) && !source.HasPriv("chanserv/access/modify")) + source.Reply(ACCESS_DENIED); + else + { + FOREACH_MOD(OnAccessClear, (ci, source)); + + ci->ClearAccess(); + + source.Reply(_("Channel %s access list has been cleared."), ci->name.c_str()); + + bool override = !source.IsFounder(ci); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to clear the access list"; + } + + return; + } + + public: + CommandCSAccess(Module *creator) : Command(creator, "chanserv/access", 2, 4) + { + this->SetDesc(_("Modify the list of privileged users")); + this->SetSyntax(_("\037channel\037 ADD \037mask\037 \037level\037")); + this->SetSyntax(_("\037channel\037 DEL {\037mask\037 | \037entry-num\037 | \037list\037}")); + this->SetSyntax(_("\037channel\037 LIST [\037mask\037 | \037list\037]")); + this->SetSyntax(_("\037channel\037 VIEW [\037mask\037 | \037list\037]")); + this->SetSyntax(_("\037channel\037 CLEAR")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[1]; + const Anope::string &nick = params.size() > 2 ? params[2] : ""; + const Anope::string &s = params.size() > 3 ? params[3] : ""; + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + bool is_list = cmd.equals_ci("LIST") || cmd.equals_ci("VIEW"); + bool is_clear = cmd.equals_ci("CLEAR"); + bool is_del = cmd.equals_ci("DEL"); + + bool has_access = false; + if (source.HasPriv("chanserv/access/modify")) + has_access = true; + else if (is_list && source.HasPriv("chanserv/access/list")) + has_access = true; + else if (is_list && source.AccessFor(ci).HasPriv("ACCESS_LIST")) + has_access = true; + else if (source.AccessFor(ci).HasPriv("ACCESS_CHANGE")) + has_access = true; + else if (is_del) + { + const NickAlias *na = NickAlias::Find(nick); + if (na && na->nc == source.GetAccount()) + has_access = true; + } + + /* If LIST, we don't *require* any parameters, but we can take any. + * If DEL, we require a nick and no level. + * Else (ADD), we require a level (which implies a nick). */ + if (is_list || is_clear ? 0 : (cmd.equals_ci("DEL") ? (nick.empty() || !s.empty()) : s.empty())) + this->OnSyntaxError(source, cmd); + else if (!has_access) + source.Reply(ACCESS_DENIED); + else if (Anope::ReadOnly && !is_list) + source.Reply(_("Sorry, channel access list modification is temporarily disabled.")); + else if (cmd.equals_ci("ADD")) + this->DoAdd(source, ci, params); + else if (cmd.equals_ci("DEL")) + this->DoDel(source, ci, params); + else if (cmd.equals_ci("LIST")) + this->DoList(source, ci, params); + else if (cmd.equals_ci("VIEW")) + this->DoView(source, ci, params); + else if (cmd.equals_ci("CLEAR")) + this->DoClear(source, ci); + else + this->OnSyntaxError(source, ""); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Maintains the \002access list\002 for a channel. The access\n" + "list specifies which users are allowed chanop status or\n" + "access to %s commands on the channel. Different\n" + "user levels allow for access to different subsets of\n" + "privileges. Any registered user not on the access list has\n" + "a user level of 0, and any unregistered user has a user level\n" + "of -1."), source.service->nick.c_str()); + source.Reply(" "); + source.Reply(_("The \002ACCESS ADD\002 command adds the given mask to the\n" + "access list with the given user level; if the mask is\n" + "already present on the list, its access level is changed to\n" + "the level specified in the command. The \037level\037 specified\n" + "may be a numerical level or the name of a privilege (eg AUTOOP).\n" + "When a user joins the channel the access they receive is from the\n" + "highest level entry in the access list.")); + if (!Config->GetModule("chanserv")->Get("disallow_channel_access")) + source.Reply(_("The given mask may also be a channel, which will use the\n" + "access list from the other channel up to the given \037level\037.")); + source.Reply(" "); + source.Reply(_("The \002ACCESS DEL\002 command removes the given nick from the\n" + "access list. If a list of entry numbers is given, those\n" + "entries are deleted. (See the example for LIST below.)\n" + "You may remove yourself from an access list, even if you\n" + "do not have access to modify that list otherwise.")); + source.Reply(" "); + source.Reply(_("The \002ACCESS LIST\002 command displays the access list. If\n" + "a wildcard mask is given, only those entries matching the\n" + "mask are displayed. If a list of entry numbers is given,\n" + "only those entries are shown; for example:\n" + " \002ACCESS #channel LIST 2-5,7-9\002\n" + " Lists access entries numbered 2 through 5 and\n" + " 7 through 9.\n" + " \n" + "The \002ACCESS VIEW\002 command displays the access list similar\n" + "to \002ACCESS LIST\002 but shows the creator and last used time.\n" + " \n" + "The \002ACCESS CLEAR\002 command clears all entries of the\n" + "access list.")); + source.Reply(" "); + + BotInfo *bi; + Anope::string cmd; + if (Command::FindCommandFromService("chanserv/levels", bi, cmd)) + source.Reply(_("\002User access levels\002 can be seen by using the\n" + "\002%s\002 command; type \002%s%s HELP LEVELS\002 for\n" + "information."), cmd.c_str(), Config->StrictPrivmsg.c_str(), bi->nick.c_str()); + return true; + } +}; + +class CommandCSLevels : public Command +{ + void DoSet(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + const Anope::string &what = params[2]; + const Anope::string &lev = params[3]; + + int level; + + if (lev.equals_ci("FOUNDER")) + level = ACCESS_FOUNDER; + else + { + try + { + level = convertTo(lev); + } + catch (const ConvertException &) + { + this->OnSyntaxError(source, "SET"); + return; + } + } + + if (level <= ACCESS_INVALID || level > ACCESS_FOUNDER) + source.Reply(_("Level must be between %d and %d inclusive."), ACCESS_INVALID + 1, ACCESS_FOUNDER - 1); + else + { + Privilege *p = PrivilegeManager::FindPrivilege(what); + if (p == NULL) + source.Reply(_("Setting \002%s\002 not known. Type \002%s%s HELP LEVELS\002 for a list of valid settings."), what.c_str(), Config->StrictPrivmsg.c_str(), source.service->nick.c_str()); + else + { + bool override = !source.AccessFor(ci).HasPriv("FOUNDER"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to set " << p->name << " to level " << level; + + ci->SetLevel(p->name, level); + FOREACH_MOD(OnLevelChange, (source, ci, p->name, level)); + + if (level == ACCESS_FOUNDER) + source.Reply(_("Level for %s on channel %s changed to founder only."), p->name.c_str(), ci->name.c_str()); + else + source.Reply(_("Level for \002%s\002 on channel %s changed to \002%d\002."), p->name.c_str(), ci->name.c_str(), level); + } + } + } + + void DoDisable(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + const Anope::string &what = params[2]; + + /* Don't allow disabling of the founder level. It would be hard to change it back if you don't have access to use this command */ + if (what.equals_ci("FOUNDER")) + { + source.Reply(_("You can not disable the founder privilege because it would be impossible to reenable it at a later time.")); + return; + } + + Privilege *p = PrivilegeManager::FindPrivilege(what); + if (p != NULL) + { + bool override = !source.AccessFor(ci).HasPriv("FOUNDER"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to disable " << p->name; + + ci->SetLevel(p->name, ACCESS_INVALID); + FOREACH_MOD(OnLevelChange, (source, ci, p->name, ACCESS_INVALID)); + + source.Reply(_("\002%s\002 disabled on channel %s."), p->name.c_str(), ci->name.c_str()); + return; + } + + source.Reply(_("Setting \002%s\002 not known. Type \002%s%s HELP LEVELS\002 for a list of valid settings."), what.c_str(), Config->StrictPrivmsg.c_str(), source.service->nick.c_str()); + } + + void DoList(CommandSource &source, ChannelInfo *ci) + { + source.Reply(_("Access level settings for channel %s:"), ci->name.c_str()); + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Name")).AddColumn(_("Level")); + + const std::vector &privs = PrivilegeManager::GetPrivileges(); + + for (unsigned i = 0; i < privs.size(); ++i) + { + const Privilege &p = privs[i]; + int16_t j = ci->GetLevel(p.name); + + ListFormatter::ListEntry entry; + entry["Name"] = p.name; + + if (j == ACCESS_INVALID) + entry["Level"] = Language::Translate(source.GetAccount(), _("(disabled)")); + else if (j == ACCESS_FOUNDER) + entry["Level"] = Language::Translate(source.GetAccount(), _("(founder only)")); + else + entry["Level"] = stringify(j); + + list.AddEntry(entry); + } + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + + void DoReset(CommandSource &source, ChannelInfo *ci) + { + bool override = !source.AccessFor(ci).HasPriv("FOUNDER"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to reset all levels"; + + reset_levels(ci); + FOREACH_MOD(OnLevelChange, (source, ci, "ALL", 0)); + + source.Reply(_("Access levels for \002%s\002 reset to defaults."), ci->name.c_str()); + return; + } + + public: + CommandCSLevels(Module *creator) : Command(creator, "chanserv/levels", 2, 4) + { + this->SetDesc(_("Redefine the meanings of access levels")); + this->SetSyntax(_("\037channel\037 SET \037type\037 \037level\037")); + this->SetSyntax(_("\037channel\037 {DIS | DISABLE} \037type\037")); + this->SetSyntax(_("\037channel\037 LIST")); + this->SetSyntax(_("\037channel\037 RESET")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[1]; + const Anope::string &what = params.size() > 2 ? params[2] : ""; + const Anope::string &s = params.size() > 3 ? params[3] : ""; + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + bool has_access = false; + if (source.HasPriv("chanserv/access/modify")) + has_access = true; + else if (cmd.equals_ci("LIST") && source.HasPriv("chanserv/access/list")) + has_access = true; + else if (source.AccessFor(ci).HasPriv("FOUNDER")) + has_access = true; + + /* If SET, we want two extra parameters; if DIS[ABLE] or FOUNDER, we want only + * one; else, we want none. + */ + if (cmd.equals_ci("SET") ? s.empty() : (cmd.substr(0, 3).equals_ci("DIS") ? (what.empty() || !s.empty()) : !what.empty())) + this->OnSyntaxError(source, cmd); + else if (!has_access) + source.Reply(ACCESS_DENIED); + else if (Anope::ReadOnly && !cmd.equals_ci("LIST")) + source.Reply(READ_ONLY_MODE); + else if (cmd.equals_ci("SET")) + this->DoSet(source, ci, params); + else if (cmd.equals_ci("DIS") || cmd.equals_ci("DISABLE")) + this->DoDisable(source, ci, params); + else if (cmd.equals_ci("LIST")) + this->DoList(source, ci); + else if (cmd.equals_ci("RESET")) + this->DoReset(source, ci); + else + this->OnSyntaxError(source, ""); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + if (subcommand.equals_ci("DESC")) + { + source.Reply(_("The following feature/function names are available:")); + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Name")).AddColumn(_("Description")); + + const std::vector &privs = PrivilegeManager::GetPrivileges(); + for (unsigned i = 0; i < privs.size(); ++i) + { + const Privilege &p = privs[i]; + ListFormatter::ListEntry entry; + entry["Name"] = p.name; + entry["Description"] = Language::Translate(source.nc, p.desc.c_str()); + list.AddEntry(entry); + } + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + else + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("The \002LEVELS\002 command allows fine control over the meaning of\n" + "the numeric access levels used for channels. With this\n" + "command, you can define the access level required for most\n" + "of %s's functions. (The \002SET FOUNDER\002 and this command\n" + "are always restricted to the channel founder.)\n" + " \n" + "\002LEVELS SET\002 allows the access level for a function or group of\n" + "functions to be changed. \002LEVELS DISABLE\002 (or \002DIS\002 for short)\n" + "disables an automatic feature or disallows access to a\n" + "function by anyone, INCLUDING the founder (although, the founder\n" + "can always reenable it). Use \002LEVELS SET founder\002 to make a level\n" + "founder only.\n" + " \n" + "\002LEVELS LIST\002 shows the current levels for each function or\n" + "group of functions. \002LEVELS RESET\002 resets the levels to the\n" + "default levels of a newly-created channel.\n" + " \n" + "For a list of the features and functions whose levels can be\n" + "set, see \002HELP LEVELS DESC\002."), source.service->nick.c_str()); + } + return true; + } +}; + +class CSAccess : public Module +{ + AccessAccessProvider accessprovider; + CommandCSAccess commandcsaccess; + CommandCSLevels commandcslevels; + + public: + CSAccess(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + accessprovider(this), commandcsaccess(this), commandcslevels(this) + { + this->SetPermanent(true); + + } + + void OnReload(Configuration::Conf *conf) anope_override + { + defaultLevels.clear(); + + for (int i = 0; i < conf->CountBlock("privilege"); ++i) + { + Configuration::Block *priv = conf->GetBlock("privilege", i); + + const Anope::string &pname = priv->Get("name"); + + Privilege *p = PrivilegeManager::FindPrivilege(pname); + if (p == NULL) + continue; + + const Anope::string &value = priv->Get("level"); + if (value.empty()) + continue; + else if (value.equals_ci("founder")) + defaultLevels[p->name] = ACCESS_FOUNDER; + else if (value.equals_ci("disabled")) + defaultLevels[p->name] = ACCESS_INVALID; + else + defaultLevels[p->name] = priv->Get("level"); + } + } + + void OnCreateChan(ChannelInfo *ci) anope_override + { + reset_levels(ci); + } + + EventReturn OnGroupCheckPriv(const AccessGroup *group, const Anope::string &priv) anope_override + { + if (group->ci == NULL) + return EVENT_CONTINUE; + + const ChanAccess *highest = group->Highest(); + if (highest && highest->provider == &accessprovider) + { + /* Access accessprovider is the only accessprovider with the concept of negative access, + * so check they don't have negative access + */ + const AccessChanAccess *aca = anope_dynamic_static_cast(highest); + + if (aca->level < 0) + return EVENT_CONTINUE; + } + + /* Special case. Allows a level of -1 to match anyone, and a level of 0 to match anyone identified. */ + int16_t level = group->ci->GetLevel(priv); + if (level == -1) + return EVENT_ALLOW; + else if (level == 0 && group->nc && !group->nc->HasExt("UNCONFIRMED")) + return EVENT_ALLOW; + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(CSAccess) diff --git a/modules/commands/cs_akick.cpp b/modules/commands/cs_akick.cpp new file mode 100644 index 0000000..b1de7f9 --- /dev/null +++ b/modules/commands/cs_akick.cpp @@ -0,0 +1,584 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandCSAKick : public Command +{ + void Enforce(CommandSource &source, ChannelInfo *ci) + { + Channel *c = ci->c; + int count = 0; + + if (!c) + { + return; + } + + for (Channel::ChanUserList::iterator it = c->users.begin(), it_end = c->users.end(); it != it_end; ) + { + ChanUserContainer *uc = it->second; + ++it; + + if (c->CheckKick(uc->user)) + ++count; + } + + bool override = !source.AccessFor(ci).HasPriv("AKICK"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "ENFORCE, affects " << count << " users"; + + source.Reply(_("AKICK ENFORCE for \002%s\002 complete; \002%d\002 users were affected."), ci->name.c_str(), count); + } + + void DoAdd(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + Anope::string mask = params[2]; + Anope::string reason = params.size() > 3 ? params[3] : ""; + const NickAlias *na = NickAlias::Find(mask); + NickCore *nc = NULL; + const AutoKick *akick; + unsigned reasonmax = Config->GetModule("chanserv")->Get("reasonmax", "200"); + + if (reason.length() > reasonmax) + reason = reason.substr(0, reasonmax); + + if (IRCD->IsExtbanValid(mask)) + ; /* If this is an extban don't try to complete the mask */ + else if (IRCD->IsChannelValid(mask)) + { + /* Also don't try to complete the mask if this is a channel */ + + if (mask.equals_ci(ci->name) && ci->HasExt("PEACE")) + { + source.Reply(ACCESS_DENIED); + return; + } + } + else if (!na) + { + /* If the mask contains a realname the reason must be prepended with a : */ + if (mask.find('#') != Anope::string::npos) + { + size_t r = reason.find(':'); + if (r != Anope::string::npos) + { + mask += " " + reason.substr(0, r); + mask.trim(); + reason = reason.substr(r + 1); + reason.trim(); + } + else + { + mask = mask + " " + reason; + reason.clear(); + } + } + + Entry e("", mask); + + mask = (e.nick.empty() ? "*" : e.nick) + "!" + + (e.user.empty() ? "*" : e.user) + "@" + + (e.host.empty() ? "*" : e.host); + if (!e.real.empty()) + mask += "#" + e.real; + } + else + nc = na->nc; + + /* Check excepts BEFORE we get this far */ + if (ci->c) + { + std::vector modes = ci->c->GetModeList("EXCEPT"); + for (unsigned int i = 0; i < modes.size(); ++i) + { + if (Anope::Match(modes[i], mask)) + { + source.Reply(CHAN_EXCEPTED, mask.c_str(), ci->name.c_str()); + return; + } + } + } + + bool override = !source.AccessFor(ci).HasPriv("AKICK"); + /* Opers overriding get to bypass PEACE */ + if (override) + ; + /* These peace checks are only for masks */ + else if (IRCD->IsChannelValid(mask)) + ; + /* Check whether target nick has equal/higher access + * or whether the mask matches a user with higher/equal access - Viper */ + else if (ci->HasExt("PEACE") && nc) + { + AccessGroup nc_access = ci->AccessFor(nc), u_access = source.AccessFor(ci); + if (nc == ci->GetFounder() || nc_access >= u_access) + { + source.Reply(ACCESS_DENIED); + return; + } + } + else if (ci->HasExt("PEACE")) + { + /* Match against all currently online users with equal or + * higher access. - Viper */ + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + { + User *u2 = it->second; + + AccessGroup nc_access = ci->AccessFor(nc), u_access = source.AccessFor(ci); + Entry entry_mask("", mask); + + if ((ci->AccessFor(u2).HasPriv("FOUNDER") || nc_access >= u_access) && entry_mask.Matches(u2)) + { + source.Reply(ACCESS_DENIED); + return; + } + } + + /* Match against the lastusermask of all nickalias's with equal + * or higher access. - Viper */ + for (nickalias_map::const_iterator it = NickAliasList->begin(), it_end = NickAliasList->end(); it != it_end; ++it) + { + na = it->second; + + AccessGroup nc_access = ci->AccessFor(na->nc), u_access = source.AccessFor(ci); + if (na->nc && (na->nc == ci->GetFounder() || nc_access >= u_access)) + { + Anope::string buf = na->nick + "!" + na->last_usermask; + if (Anope::Match(buf, mask)) + { + source.Reply(ACCESS_DENIED); + return; + } + } + } + } + + for (unsigned j = 0, end = ci->GetAkickCount(); j < end; ++j) + { + akick = ci->GetAkick(j); + if (akick->nc ? akick->nc == nc : mask.equals_ci(akick->mask)) + { + source.Reply(_("\002%s\002 already exists on %s autokick list."), akick->nc ? akick->nc->display.c_str() : akick->mask.c_str(), ci->name.c_str()); + return; + } + } + + if (ci->GetAkickCount() >= Config->GetModule(this->owner)->Get("autokickmax")) + { + source.Reply(_("Sorry, you can only have %d autokick masks on a channel."), Config->GetModule(this->owner)->Get("autokickmax")); + return; + } + + if (nc) + akick = ci->AddAkick(source.GetNick(), nc, reason); + else + akick = ci->AddAkick(source.GetNick(), mask, reason); + + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to add " << mask << (reason == "" ? "" : ": ") << reason; + + FOREACH_MOD(OnAkickAdd, (source, ci, akick)); + + source.Reply(_("\002%s\002 added to %s autokick list."), mask.c_str(), ci->name.c_str()); + + this->Enforce(source, ci); + } + + void DoDel(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + const Anope::string &mask = params[2]; + unsigned i, end; + + if (!ci->GetAkickCount()) + { + source.Reply(_("%s autokick list is empty."), ci->name.c_str()); + return; + } + + /* Special case: is it a number/list? Only do search if it isn't. */ + if (isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) + { + class AkickDelCallback : public NumberList + { + CommandSource &source; + ChannelInfo *ci; + Command *c; + unsigned deleted; + AccessGroup ag; + public: + AkickDelCallback(CommandSource &_source, ChannelInfo *_ci, Command *_c, const Anope::string &list) : NumberList(list, true), source(_source), ci(_ci), c(_c), deleted(0), ag(source.AccessFor(ci)) + { + } + + ~AkickDelCallback() + { + if (!deleted) + source.Reply(_("No matching entries on %s autokick list."), ci->name.c_str()); + else if (deleted == 1) + source.Reply(_("Deleted 1 entry from %s autokick list."), ci->name.c_str()); + else + source.Reply(_("Deleted %d entries from %s autokick list."), deleted, ci->name.c_str()); + } + + void HandleNumber(unsigned number) anope_override + { + if (!number || number > ci->GetAkickCount()) + return; + + const AutoKick *akick = ci->GetAkick(number - 1); + + FOREACH_MOD(OnAkickDel, (source, ci, akick)); + + bool override = !ag.HasPriv("AKICK"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, c, ci) << "to delete " << (akick->nc ? akick->nc->display : akick->mask); + + ++deleted; + ci->EraseAkick(number - 1); + } + } + delcallback(source, ci, this, mask); + delcallback.Process(); + } + else + { + const NickAlias *na = NickAlias::Find(mask); + const NickCore *nc = na ? *na->nc : NULL; + + for (i = 0, end = ci->GetAkickCount(); i < end; ++i) + { + const AutoKick *akick = ci->GetAkick(i); + + if (akick->nc ? akick->nc == nc : mask.equals_ci(akick->mask)) + break; + } + + if (i == ci->GetAkickCount()) + { + source.Reply(_("\002%s\002 not found on %s autokick list."), mask.c_str(), ci->name.c_str()); + return; + } + + bool override = !source.AccessFor(ci).HasPriv("AKICK"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to delete " << mask; + + FOREACH_MOD(OnAkickDel, (source, ci, ci->GetAkick(i))); + + ci->EraseAkick(i); + + source.Reply(_("\002%s\002 deleted from %s autokick list."), mask.c_str(), ci->name.c_str()); + } + } + + void ProcessList(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms, ListFormatter &list) + { + const Anope::string &mask = params.size() > 2 ? params[2] : ""; + + if (!mask.empty() && isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) + { + class AkickListCallback : public NumberList + { + ListFormatter &list; + ChannelInfo *ci; + + public: + AkickListCallback(ListFormatter &_list, ChannelInfo *_ci, const Anope::string &numlist) : NumberList(numlist, false), list(_list), ci(_ci) + { + } + + void HandleNumber(unsigned number) anope_override + { + if (!number || number > ci->GetAkickCount()) + return; + + const AutoKick *akick = ci->GetAkick(number - 1); + + Anope::string timebuf, lastused; + if (akick->addtime) + timebuf = Anope::strftime(akick->addtime, NULL, true); + else + timebuf = UNKNOWN; + if (akick->last_used) + lastused = Anope::strftime(akick->last_used, NULL, true); + else + lastused = UNKNOWN; + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(number); + if (akick->nc) + entry["Mask"] = akick->nc->display; + else + entry["Mask"] = akick->mask; + entry["Creator"] = akick->creator; + entry["Created"] = timebuf; + entry["Last used"] = lastused; + entry["Reason"] = akick->reason; + this->list.AddEntry(entry); + } + } + nl_list(list, ci, mask); + nl_list.Process(); + } + else + { + for (unsigned i = 0, end = ci->GetAkickCount(); i < end; ++i) + { + const AutoKick *akick = ci->GetAkick(i); + + if (!mask.empty()) + { + if (!akick->nc && !Anope::Match(akick->mask, mask)) + continue; + if (akick->nc && !Anope::Match(akick->nc->display, mask)) + continue; + } + + Anope::string timebuf, lastused; + if (akick->addtime) + timebuf = Anope::strftime(akick->addtime, NULL, true); + else + timebuf = UNKNOWN; + if (akick->last_used) + lastused = Anope::strftime(akick->last_used, NULL, true); + else + lastused = UNKNOWN; + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(i + 1); + if (akick->nc) + entry["Mask"] = akick->nc->display; + else + entry["Mask"] = akick->mask; + entry["Creator"] = akick->creator; + entry["Created"] = timebuf; + entry["Last used"] = lastused; + entry["Reason"] = akick->reason; + list.AddEntry(entry); + } + } + + if (list.IsEmpty()) + source.Reply(_("No matching entries on %s autokick list."), ci->name.c_str()); + else + { + std::vector replies; + list.Process(replies); + + source.Reply(_("Autokick list for %s:"), ci->name.c_str()); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("End of autokick list")); + } + } + + void DoList(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + if (!ci->GetAkickCount()) + { + source.Reply(_("%s autokick list is empty."), ci->name.c_str()); + return; + } + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Mask")).AddColumn(_("Reason")); + this->ProcessList(source, ci, params, list); + } + + void DoView(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + if (!ci->GetAkickCount()) + { + source.Reply(_("%s autokick list is empty."), ci->name.c_str()); + return; + } + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Mask")).AddColumn(_("Creator")).AddColumn(_("Created")).AddColumn(_("Last used")).AddColumn(_("Reason")); + this->ProcessList(source, ci, params, list); + } + + void DoEnforce(CommandSource &source, ChannelInfo *ci) + { + Channel *c = ci->c; + + if (!c) + { + source.Reply(CHAN_X_NOT_IN_USE, ci->name.c_str()); + return; + } + + this->Enforce(source, ci); + } + + void DoClear(CommandSource &source, ChannelInfo *ci) + { + bool override = !source.AccessFor(ci).HasPriv("AKICK"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to clear the akick list"; + + ci->ClearAkick(); + source.Reply(_("Channel %s akick list has been cleared."), ci->name.c_str()); + } + + public: + CommandCSAKick(Module *creator) : Command(creator, "chanserv/akick", 2, 4) + { + this->SetDesc(_("Maintain the AutoKick list")); + this->SetSyntax(_("\037channel\037 ADD {\037nick\037 | \037mask\037} [\037reason\037]")); + this->SetSyntax(_("\037channel\037 DEL {\037nick\037 | \037mask\037 | \037entry-num\037 | \037list\037}")); + this->SetSyntax(_("\037channel\037 LIST [\037mask\037 | \037entry-num\037 | \037list\037]")); + this->SetSyntax(_("\037channel\037 VIEW [\037mask\037 | \037entry-num\037 | \037list\037]")); + this->SetSyntax(_("\037channel\037 ENFORCE")); + this->SetSyntax(_("\037channel\037 CLEAR")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + Anope::string chan = params[0]; + Anope::string cmd = params[1]; + Anope::string mask = params.size() > 2 ? params[2] : ""; + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + bool is_list = cmd.equals_ci("LIST") || cmd.equals_ci("VIEW"); + + bool has_access = false; + if (source.AccessFor(ci).HasPriv("AKICK") || source.HasPriv("chanserv/access/modify")) + has_access = true; + else if (is_list && source.HasPriv("chanserv/access/list")) + has_access = true; + + if (mask.empty() && (cmd.equals_ci("ADD") || cmd.equals_ci("DEL"))) + this->OnSyntaxError(source, cmd); + else if (!has_access) + source.Reply(ACCESS_DENIED); + else if (!cmd.equals_ci("LIST") && !cmd.equals_ci("VIEW") && !cmd.equals_ci("ENFORCE") && Anope::ReadOnly) + source.Reply(_("Sorry, channel autokick list modification is temporarily disabled.")); + else if (cmd.equals_ci("ADD")) + this->DoAdd(source, ci, params); + else if (cmd.equals_ci("DEL")) + this->DoDel(source, ci, params); + else if (cmd.equals_ci("LIST")) + this->DoList(source, ci, params); + else if (cmd.equals_ci("VIEW")) + this->DoView(source, ci, params); + else if (cmd.equals_ci("ENFORCE")) + this->DoEnforce(source, ci); + else if (cmd.equals_ci("CLEAR")) + this->DoClear(source, ci); + else + this->OnSyntaxError(source, ""); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + BotInfo *bi = Config->GetClient("NickServ"); + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Maintains the \002AutoKick list\002 for a channel. If a user\n" + "on the AutoKick list attempts to join the channel,\n" + "%s will ban that user from the channel, then kick\n" + "the user.\n" + " \n" + "The \002AKICK ADD\002 command adds the given nick or usermask\n" + "to the AutoKick list. If a \037reason\037 is given with\n" + "the command, that reason will be used when the user is\n" + "kicked; if not, the default reason is \"User has been\n" + "banned from the channel\".\n" + "When akicking a \037registered nick\037 the %s account\n" + "will be added to the akick list instead of the mask.\n" + "All users within that nickgroup will then be akicked.\n"), + source.service->nick.c_str(), bi ? bi->nick.c_str() : "NickServ"); + source.Reply(_( + " \n" + "The \002AKICK DEL\002 command removes the given nick or mask\n" + "from the AutoKick list. It does not, however, remove any\n" + "bans placed by an AutoKick; those must be removed\n" + "manually.\n" + " \n" + "The \002AKICK LIST\002 command displays the AutoKick list, or\n" + "optionally only those AutoKick entries which match the\n" + "given mask.\n" + " \n" + "The \002AKICK VIEW\002 command is a more verbose version of the\n" + "\002AKICK LIST\002 command.\n" + " \n" + "The \002AKICK ENFORCE\002 command causes %s to enforce the\n" + "current AKICK list by removing those users who match an\n" + "AKICK mask.\n" + " \n" + "The \002AKICK CLEAR\002 command clears all entries of the\n" + "akick list."), source.service->nick.c_str()); + return true; + } +}; + +class CSAKick : public Module +{ + CommandCSAKick commandcsakick; + + public: + CSAKick(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcsakick(this) + { + } + + EventReturn OnCheckKick(User *u, Channel *c, Anope::string &mask, Anope::string &reason) anope_override + { + if (!c->ci || c->MatchesList(u, "EXCEPT")) + return EVENT_CONTINUE; + + for (unsigned j = 0, end = c->ci->GetAkickCount(); j < end; ++j) + { + AutoKick *autokick = c->ci->GetAkick(j); + bool kick = false; + + if (autokick->nc) + kick = autokick->nc == u->Account(); + else if (IRCD->IsChannelValid(autokick->mask)) + { + Channel *chan = Channel::Find(autokick->mask); + kick = chan != NULL && chan->FindUser(u); + } + else + kick = Entry("BAN", autokick->mask).Matches(u); + + if (kick) + { + Log(LOG_DEBUG_2) << u->nick << " matched akick " << (autokick->nc ? autokick->nc->display : autokick->mask); + autokick->last_used = Anope::CurTime; + if (!autokick->nc && autokick->mask.find('#') == Anope::string::npos) + mask = autokick->mask; + reason = autokick->reason; + if (reason.empty()) + { + reason = Language::Translate(u, Config->GetModule(this)->Get("autokickreason").c_str()); + reason = reason.replace_all_cs("%n", u->nick) + .replace_all_cs("%c", c->name); + } + if (reason.empty()) + reason = Language::Translate(u, _("User has been banned from the channel")); + return EVENT_STOP; + } + } + + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(CSAKick) diff --git a/modules/commands/cs_ban.cpp b/modules/commands/cs_ban.cpp new file mode 100644 index 0000000..9fe004e --- /dev/null +++ b/modules/commands/cs_ban.cpp @@ -0,0 +1,251 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +static Module *me; + +class TempBan : public Timer +{ + private: + Anope::string channel; + Anope::string mask; + Anope::string mode; + + public: + TempBan(time_t seconds, Channel *c, const Anope::string &banmask, const Anope::string &mod) : Timer(me, seconds), channel(c->name), mask(banmask), mode(mod) { } + + void Tick(time_t ctime) anope_override + { + Channel *c = Channel::Find(this->channel); + if (c) + c->RemoveMode(NULL, mode, this->mask); + } +}; + +class CommandCSBan : public Command +{ + public: + CommandCSBan(Module *creator) : Command(creator, "chanserv/ban", 2, 4) + { + this->SetDesc(_("Bans a given nick or mask on a channel")); + this->SetSyntax(_("\037channel\037 [+\037expiry\037] {\037nick\037 | \037mask\037} [\037reason\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + Configuration::Block *block = Config->GetCommand(source); + const Anope::string &mode = block->Get("mode", "BAN"); + ChannelMode *cm = ModeManager::FindChannelModeByName(mode); + if (cm == NULL) + return; + + const Anope::string &chan = params[0]; + ChannelInfo *ci = ChannelInfo::Find(chan); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); + return; + } + + Channel *c = ci->c; + if (c == NULL) + { + source.Reply(CHAN_X_NOT_IN_USE, chan.c_str()); + return; + } + else if (IRCD->GetMaxListFor(c, cm) && c->HasMode(mode) >= IRCD->GetMaxListFor(c, cm)) + { + source.Reply(_("The %s list for %s is full."), mode.lower().c_str(), c->name.c_str()); + return; + } + + Anope::string expiry, target, reason; + time_t ban_time; + if (params[1][0] == '+') + { + ban_time = Anope::DoTime(params[1]); + if (ban_time < 0) + { + source.Reply(BAD_EXPIRY_TIME); + return; + } + if (params.size() < 3) + { + this->SendSyntax(source); + return; + } + target = params[2]; + reason = "Requested"; + if (params.size() > 3) + reason = params[3]; + } + else + { + ban_time = 0; + target = params[1]; + reason = "Requested"; + if (params.size() > 2) + reason = params[2]; + if (params.size() > 3) + reason += " " + params[3]; + } + + unsigned reasonmax = Config->GetModule("chanserv")->Get("reasonmax", "200"); + if (reason.length() > reasonmax) + reason = reason.substr(0, reasonmax); + + Anope::string signkickformat = Config->GetModule("chanserv")->Get("signkickformat", "%m (%n)"); + signkickformat = signkickformat.replace_all_cs("%n", source.GetNick()); + + User *u = source.GetUser(); + User *u2 = User::Find(target, true); + + AccessGroup u_access = source.AccessFor(ci); + + if (!u_access.HasPriv("BAN") && !source.HasPriv("chanserv/kick")) + source.Reply(ACCESS_DENIED); + else if (u2) + { + AccessGroup u2_access = ci->AccessFor(u2); + + if (u != u2 && ci->HasExt("PEACE") && u2_access >= u_access && !source.HasPriv("chanserv/kick")) + source.Reply(ACCESS_DENIED); + /* + * Don't ban/kick the user on channels where he is excepted + * to prevent services <-> server wars. + */ + else if (c->MatchesList(u2, "EXCEPT")) + source.Reply(CHAN_EXCEPTED, u2->nick.c_str(), ci->name.c_str()); + else if (u2->IsProtected()) + source.Reply(ACCESS_DENIED); + else + { + Anope::string mask = ci->GetIdealBan(u2); + + bool override = !u_access.HasPriv("BAN") || (u != u2 && ci->HasExt("PEACE") && u2_access >= u_access); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "for " << mask; + + if (!c->HasMode(mode, mask)) + { + c->SetMode(NULL, mode, mask); + if (ban_time) + { + new TempBan(ban_time, c, mask, mode); + source.Reply(_("Ban on \002%s\002 expires in %s."), mask.c_str(), Anope::Duration(ban_time, source.GetAccount()).c_str()); + } + } + + /* We still allow host banning while not allowing to kick */ + if (!c->FindUser(u2)) + return; + + if (block->Get("kick", "yes")) + { + if (ci->HasExt("SIGNKICK") || (ci->HasExt("SIGNKICK_LEVEL") && !source.AccessFor(ci).HasPriv("SIGNKICK"))) + { + signkickformat = signkickformat.replace_all_cs("%m", reason); + c->Kick(ci->WhoSends(), u2, "%s", signkickformat.c_str()); + } + else + c->Kick(ci->WhoSends(), u2, "%s", reason.c_str()); + } + } + } + else + { + bool founder = u_access.HasPriv("FOUNDER"); + bool override = !founder && !u_access.HasPriv("BAN"); + + Anope::string mask = IRCD->NormalizeMask(target); + + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "for " << mask; + + if (!c->HasMode(mode, mask)) + { + c->SetMode(NULL, mode, mask); + if (ban_time) + { + new TempBan(ban_time, c, mask, mode); + source.Reply(_("Ban on \002%s\002 expires in %s."), mask.c_str(), Anope::Duration(ban_time, source.GetAccount()).c_str()); + } + } + + int matched = 0, kicked = 0; + for (Channel::ChanUserList::iterator it = c->users.begin(), it_end = c->users.end(); it != it_end;) + { + ChanUserContainer *uc = it->second; + ++it; + + Entry e(mode, mask); + if (e.Matches(uc->user)) + { + ++matched; + + AccessGroup u2_access = ci->AccessFor(uc->user); + + if (matched > 1 && !founder) + continue; + if (u != uc->user && ci->HasExt("PEACE") && u2_access >= u_access) + continue; + else if (ci->c->MatchesList(uc->user, "EXCEPT")) + continue; + else if (uc->user->IsProtected()) + continue; + + if (block->Get("kick", "yes")) + { + ++kicked; + if (ci->HasExt("SIGNKICK") || (ci->HasExt("SIGNKICK_LEVEL") && !u_access.HasPriv("SIGNKICK"))) + { + reason += " (Matches " + mask + ")"; + signkickformat = signkickformat.replace_all_cs("%m", reason); + c->Kick(ci->WhoSends(), uc->user, "%s", signkickformat.c_str()); + } + else + c->Kick(ci->WhoSends(), uc->user, "%s (Matches %s)", reason.c_str(), mask.c_str()); + } + } + } + + if (matched) + source.Reply(_("Kicked %d/%d users matching %s from %s."), kicked, matched, mask.c_str(), c->name.c_str()); + else + source.Reply(_("No users on %s match %s."), c->name.c_str(), mask.c_str()); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Bans a given nick or mask on a channel. An optional expiry may\n" + "be given to cause services to remove the ban after a set amount\n" + "of time.\n" + " \n" + "By default, limited to AOPs or those with level 5 access\n" + "and above on the channel. Channel founders may ban masks.")); + return true; + } +}; + +class CSBan : public Module +{ + CommandCSBan commandcsban; + + public: + CSBan(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), commandcsban(this) + { + me = this; + } +}; + +MODULE_INIT(CSBan) diff --git a/modules/commands/cs_clone.cpp b/modules/commands/cs_clone.cpp new file mode 100644 index 0000000..e5542a9 --- /dev/null +++ b/modules/commands/cs_clone.cpp @@ -0,0 +1,261 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/bs_badwords.h" + +class CommandCSClone : public Command +{ + void CopySetting(ChannelInfo *ci, ChannelInfo *target_ci, const Anope::string &setting) + { + if (ci->HasExt(setting)) + target_ci->Extend(setting); + } + + void CopyAccess(CommandSource &source, ChannelInfo *ci, ChannelInfo *target_ci) + { + std::set masks; + unsigned access_max = Config->GetModule("chanserv")->Get("accessmax", "1024"); + unsigned count = 0; + + for (unsigned i = 0; i < target_ci->GetAccessCount(); ++i) + masks.insert(target_ci->GetAccess(i)->Mask()); + + for (unsigned i = 0; i < ci->GetAccessCount(); ++i) + { + const ChanAccess *taccess = ci->GetAccess(i); + AccessProvider *provider = taccess->provider; + + if (access_max && target_ci->GetDeepAccessCount() >= access_max) + break; + + if (masks.count(taccess->Mask())) + continue; + masks.insert(taccess->Mask()); + + ChanAccess *newaccess = provider->Create(); + newaccess->SetMask(taccess->Mask(), target_ci); + newaccess->creator = taccess->creator; + newaccess->last_seen = taccess->last_seen; + newaccess->created = taccess->created; + newaccess->AccessUnserialize(taccess->AccessSerialize()); + + target_ci->AddAccess(newaccess); + + ++count; + } + + source.Reply(_("%d access entries from \002%s\002 have been cloned to \002%s\002."), count, ci->name.c_str(), target_ci->name.c_str()); + } + + void CopyAkick(CommandSource &source, ChannelInfo *ci, ChannelInfo *target_ci) + { + target_ci->ClearAkick(); + for (unsigned i = 0; i < ci->GetAkickCount(); ++i) + { + const AutoKick *akick = ci->GetAkick(i); + if (akick->nc) + target_ci->AddAkick(akick->creator, akick->nc, akick->reason, akick->addtime, akick->last_used); + else + target_ci->AddAkick(akick->creator, akick->mask, akick->reason, akick->addtime, akick->last_used); + } + + source.Reply(_("All akick entries from \002%s\002 have been cloned to \002%s\002."), ci->name.c_str(), target_ci->name.c_str()); + } + + void CopyBadwords(CommandSource &source, ChannelInfo *ci, ChannelInfo *target_ci) + { + BadWords *target_badwords = target_ci->Require("badwords"), + *badwords = ci->Require("badwords"); + + if (!target_badwords || !badwords) + { + source.Reply(ACCESS_DENIED); // BotServ doesn't exist/badwords isn't loaded + return; + } + + target_badwords->ClearBadWords(); + + for (unsigned i = 0; i < badwords->GetBadWordCount(); ++i) + { + const BadWord *bw = badwords->GetBadWord(i); + target_badwords->AddBadWord(bw->word, bw->type); + } + + badwords->Check(); + target_badwords->Check(); + + source.Reply(_("All badword entries from \002%s\002 have been cloned to \002%s\002."), ci->name.c_str(), target_ci->name.c_str()); + } + + void CopyLevels(CommandSource &source, ChannelInfo *ci, ChannelInfo *target_ci) + { + const Anope::map &cilevels = ci->GetLevelEntries(); + + for (Anope::map::const_iterator it = cilevels.begin(); it != cilevels.end(); ++it) + { + target_ci->SetLevel(it->first, it->second); + } + + source.Reply(_("All level entries from \002%s\002 have been cloned into \002%s\002."), ci->name.c_str(), target_ci->name.c_str()); + } + +public: + CommandCSClone(Module *creator) : Command(creator, "chanserv/clone", 2, 3) + { + this->SetDesc(_("Copy all settings from one channel to another")); + this->SetSyntax(_("\037channel\037 \037target\037 [\037what\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &channel = params[0]; + const Anope::string &target = params[1]; + Anope::string what = params.size() > 2 ? params[2] : ""; + + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + User *u = source.GetUser(); + ChannelInfo *ci = ChannelInfo::Find(channel); + bool override = false; + + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, channel.c_str()); + return; + } + + ChannelInfo *target_ci = ChannelInfo::Find(target); + if (!target_ci) + { + source.Reply(CHAN_X_NOT_REGISTERED, target.c_str()); + return; + } + + if (ci == target_ci) + { + source.Reply(_("Cannot clone channel \002%s\002 to itself!"), target.c_str()); + return; + } + + if (!source.IsFounder(ci) || !source.IsFounder(target_ci)) + { + if (!source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + else + override = true; + } + + if (what.equals_ci("ALL")) + what.clear(); + + if (what.empty()) + { + delete target_ci; + target_ci = new ChannelInfo(*ci); + target_ci->name = target; + target_ci->time_registered = Anope::CurTime; + (*RegisteredChannelList)[target_ci->name] = target_ci; + target_ci->c = Channel::Find(target_ci->name); + + target_ci->bi = NULL; + if (ci->bi) + ci->bi->Assign(u, target_ci); + + if (target_ci->c) + { + target_ci->c->ci = target_ci; + + target_ci->c->CheckModes(); + + target_ci->c->SetCorrectModes(u, true); + } + + if (target_ci->c && !target_ci->c->topic.empty()) + { + target_ci->last_topic = target_ci->c->topic; + target_ci->last_topic_setter = target_ci->c->topic_setter; + target_ci->last_topic_time = target_ci->c->topic_time; + } + else + target_ci->last_topic_setter = source.service->nick; + + const Anope::string settings[] = { "NOAUTOOP", "CS_KEEP_MODES", "PEACE", "PERSIST", "RESTRICTED", + "CS_SECURE", "SECUREFOUNDER", "SECUREOPS", "SIGNKICK", "SIGNKICK_LEVEL", "CS_NO_EXPIRE" }; + + for (unsigned int i = 0; i < sizeof(settings) / sizeof(Anope::string); ++i) + CopySetting(ci, target_ci, settings[i]); + + CopyAccess(source, ci, target_ci); + CopyAkick(source, ci, target_ci); + CopyBadwords(source, ci, target_ci); + CopyLevels(source, ci, target_ci); + + FOREACH_MOD(OnChanRegistered, (target_ci)); + + source.Reply(_("All settings from \002%s\002 have been cloned to \002%s\002."), ci->name.c_str(), target_ci->name.c_str()); + } + else if (what.equals_ci("ACCESS")) + { + CopyAccess(source, ci, target_ci); + } + else if (what.equals_ci("AKICK")) + { + CopyAkick(source, ci, target_ci); + } + else if (what.equals_ci("BADWORDS")) + { + CopyBadwords(source, ci, target_ci); + } + else if (what.equals_ci("LEVELS")) + { + CopyLevels(source, ci, target_ci); + } + else + { + this->OnSyntaxError(source, ""); + return; + } + + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to clone " << (what.empty() ? "everything from it" : what) << " to " << target_ci->name; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Copies all settings, access, akicks, etc from \002channel\002 to the\n" + "\002target\002 channel. If \037what\037 is \002ACCESS\002, \002AKICK\002, \002BADWORDS\002,\n" + "or \002LEVELS\002 then only the respective settings are cloned.\n" + "You must be the founder of \037channel\037 and \037target\037.")); + return true; + } +}; + +class CSClone : public Module +{ + CommandCSClone commandcsclone; + + public: + CSClone(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), commandcsclone(this) + { + + } +}; + +MODULE_INIT(CSClone) diff --git a/modules/commands/cs_drop.cpp b/modules/commands/cs_drop.cpp new file mode 100644 index 0000000..5962292 --- /dev/null +++ b/modules/commands/cs_drop.cpp @@ -0,0 +1,95 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandCSDrop : public Command +{ + public: + CommandCSDrop(Module *creator) : Command(creator, "chanserv/drop", 1, 2) + { + this->SetDesc(_("Cancel the registration of a channel")); + this->SetSyntax(_("\037channel\037 \037channel\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &chan = params[0]; + + if (Anope::ReadOnly && !source.HasPriv("chanserv/administration")) + { + source.Reply(_("Sorry, channel de-registration is temporarily disabled.")); // XXX: READ_ONLY_MODE? + return; + } + + ChannelInfo *ci = ChannelInfo::Find(chan); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + if (params.size() < 2 || !chan.equals_ci(params[1])) + { + source.Reply(_("You must enter the channel name twice as a confirmation that you wish to drop \002%s\002."), chan.c_str()); + return; + } + + if ((ci->HasExt("SECUREFOUNDER") ? !source.IsFounder(ci) : !source.AccessFor(ci).HasPriv("FOUNDER")) && !source.HasCommand("chanserv/drop")) + { + source.Reply(ACCESS_DENIED); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnChanDrop, MOD_RESULT, (source, ci)); + if (MOD_RESULT == EVENT_STOP) + return; + + bool override = (ci->HasExt("SECUREFOUNDER") ? !source.IsFounder(ci) : !source.AccessFor(ci).HasPriv("FOUNDER")); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "(founder was: " << (ci->GetFounder() ? ci->GetFounder()->display : "none") << ")"; + + Reference c = ci->c; + delete ci; + + source.Reply(_("Channel \002%s\002 has been dropped."), chan.c_str()); + + if (c) + c->CheckModes(); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + if (source.IsServicesOper()) + source.Reply(_("Unregisters the specified channel. Only \002Services Operators\002\n" + "can drop a channel of which they are not the founder of.")); + else + source.Reply(_("Unregisters the named channel. Can only be used by\n" + "the \002channel founder\002.")); + + return true; + } +}; + +class CSDrop : public Module +{ + CommandCSDrop commandcsdrop; + + public: + CSDrop(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), commandcsdrop(this) + { + + } +}; + +MODULE_INIT(CSDrop) diff --git a/modules/commands/cs_enforce.cpp b/modules/commands/cs_enforce.cpp new file mode 100644 index 0000000..1bb5ad3 --- /dev/null +++ b/modules/commands/cs_enforce.cpp @@ -0,0 +1,292 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Original Coder: GeniusDex + * + * Please read COPYING and README for further details. + * + * Send any bug reports to the Anope Coder, as he will be able + * to deal with it best. + */ + +#include "module.h" + +class CommandCSEnforce : public Command +{ + private: + void DoSecureOps(CommandSource &source, ChannelInfo *ci) + { + bool override = !source.AccessFor(ci).HasPriv("AKICK") && source.HasPriv("chanserv/access/modify"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to enforce secureops"; + + /* Dirty hack to allow Channel::SetCorrectModes to work ok. + * We pretend like SECUREOPS is on so it doesn't ignore that + * part of the code. This way we can enforce SECUREOPS even + * if it's off. + */ + bool hadsecureops = ci->HasExt("SECUREOPS"); + ci->Extend("SECUREOPS"); + + for (Channel::ChanUserList::iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end; ++it) + { + ChanUserContainer *uc = it->second; + + ci->c->SetCorrectModes(uc->user, false); + } + + if (!hadsecureops) + ci->Shrink("SECUREOPS"); + + source.Reply(_("Secureops enforced on %s."), ci->name.c_str()); + } + + void DoRestricted(CommandSource &source, ChannelInfo *ci) + { + bool override = !source.AccessFor(ci).HasPriv("AKICK") && source.HasPriv("chanserv/access/modify"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to enforce restricted"; + + std::vector users; + for (Channel::ChanUserList::iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end; ++it) + { + ChanUserContainer *uc = it->second; + User *user = uc->user; + + if (user->IsProtected()) + continue; + + if (ci->AccessFor(user).empty()) + users.push_back(user); + } + + for (unsigned i = 0; i < users.size(); ++i) + { + User *user = users[i]; + + Anope::string mask = ci->GetIdealBan(user); + Anope::string reason = Language::Translate(user, _("RESTRICTED enforced by ")) + source.GetNick(); + ci->c->SetMode(NULL, "BAN", mask); + ci->c->Kick(NULL, user, "%s", reason.c_str()); + } + + source.Reply(_("Restricted enforced on %s."), ci->name.c_str()); + } + + void DoRegOnly(CommandSource &source, ChannelInfo *ci) + { + bool override = !source.AccessFor(ci).HasPriv("AKICK") && source.HasPriv("chanserv/access/modify"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to enforce registered only"; + + std::vector users; + for (Channel::ChanUserList::iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end; ++it) + { + ChanUserContainer *uc = it->second; + User *user = uc->user; + + if (user->IsProtected()) + continue; + + if (!user->IsIdentified()) + users.push_back(user); + } + + for (unsigned i = 0; i < users.size(); ++i) + { + User *user = users[i]; + + Anope::string mask = ci->GetIdealBan(user); + Anope::string reason = Language::Translate(user, _("REGONLY enforced by ")) + source.GetNick(); + if (!ci->c->HasMode("REGISTEREDONLY")) + ci->c->SetMode(NULL, "BAN", mask); + ci->c->Kick(NULL, user, "%s", reason.c_str()); + } + + source.Reply(_("Registered only enforced on %s."), ci->name.c_str()); + } + + void DoSSLOnly(CommandSource &source, ChannelInfo *ci) + { + bool override = !source.AccessFor(ci).HasPriv("AKICK") && source.HasPriv("chanserv/access/modify"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to enforce SSL only"; + + std::vector users; + for (Channel::ChanUserList::iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end; ++it) + { + ChanUserContainer *uc = it->second; + User *user = uc->user; + + if (user->IsProtected()) + continue; + + if (!user->HasMode("SSL") && !user->HasExt("ssl")) + users.push_back(user); + } + + for (unsigned i = 0; i < users.size(); ++i) + { + User *user = users[i]; + + Anope::string mask = ci->GetIdealBan(user); + Anope::string reason = Language::Translate(user, _("SSLONLY enforced by ")) + source.GetNick(); + if (!ci->c->HasMode("SSL")) + ci->c->SetMode(NULL, "BAN", mask); + ci->c->Kick(NULL, user, "%s", reason.c_str()); + } + + source.Reply(_("SSL only enforced on %s."), ci->name.c_str()); + } + + void DoBans(CommandSource &source, ChannelInfo *ci) + { + bool override = !source.AccessFor(ci).HasPriv("AKICK") && source.HasPriv("chanserv/access/modify"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to enforce bans"; + + std::vector users; + for (Channel::ChanUserList::iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end; ++it) + { + ChanUserContainer *uc = it->second; + User *user = uc->user; + + if (user->IsProtected()) + continue; + + if (ci->c->MatchesList(user, "BAN") && !ci->c->MatchesList(user, "EXCEPT")) + users.push_back(user); + } + + for (unsigned i = 0; i < users.size(); ++i) + { + User *user = users[i]; + + Anope::string reason = Language::Translate(user, _("BANS enforced by ")) + source.GetNick(); + ci->c->Kick(NULL, user, "%s", reason.c_str()); + } + + source.Reply(_("Bans enforced on %s."), ci->name.c_str()); + } + + void DoLimit(CommandSource &source, ChannelInfo *ci) + { + bool override = !source.AccessFor(ci).HasPriv("AKICK") && source.HasPriv("chanserv/access/modify"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to enforce limit"; + + Anope::string l_str; + if (!ci->c->GetParam("LIMIT", l_str)) + { + source.Reply(_("No limit is set on %s."), ci->name.c_str()); + return; + } + + int l; + try + { + l = convertTo(l_str); + if (l < 0) + throw ConvertException(); + } + catch (const ConvertException &) + { + source.Reply(_("The limit on %s is not valid."), ci->name.c_str()); + return; + } + + std::vector users; + /* The newer users are at the end of the list, so kick users starting from the end */ + for (Channel::ChanUserList::reverse_iterator it = ci->c->users.rbegin(), it_end = ci->c->users.rend(); it != it_end; ++it) + { + ChanUserContainer *uc = it->second; + User *user = uc->user; + + if (user->IsProtected()) + continue; + + if (!ci->AccessFor(user).empty()) + continue; + + if (ci->c->users.size() - users.size() <= static_cast(l)) + continue; + + users.push_back(user); + } + + for (unsigned i = 0; i < users.size(); ++i) + { + User *user = users[i]; + + Anope::string reason = Language::Translate(user, _("LIMIT enforced by ")) + source.GetNick(); + ci->c->Kick(NULL, user, "%s", reason.c_str()); + } + + source.Reply(_("LIMIT enforced on %s, %d users removed."), ci->name.c_str(), users.size()); + } + + public: + CommandCSEnforce(Module *creator) : Command(creator, "chanserv/enforce", 2, 2) + { + this->SetDesc(_("Enforce various channel modes and set options")); + this->SetSyntax(_("\037channel\037 \037what\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &what = params.size() > 1 ? params[1] : ""; + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + + if (!ci) + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + else if (!ci->c) + source.Reply(CHAN_X_NOT_IN_USE, ci->name.c_str()); + else if (!source.AccessFor(ci).HasPriv("AKICK") && !source.HasPriv("chanserv/access/modify")) + source.Reply(ACCESS_DENIED); + else if (what.equals_ci("SECUREOPS")) + this->DoSecureOps(source, ci); + else if (what.equals_ci("RESTRICTED")) + this->DoRestricted(source, ci); + else if (what.equals_ci("REGONLY")) + this->DoRegOnly(source, ci); + else if (what.equals_ci("SSLONLY")) + this->DoSSLOnly(source, ci); + else if (what.equals_ci("BANS")) + this->DoBans(source, ci); + else if (what.equals_ci("LIMIT")) + this->DoLimit(source, ci); + else + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enforce various channel modes and set options. The \037channel\037\n" + "option indicates what channel to enforce the modes and options\n" + "on. The \037what\037 option indicates what modes and options to\n" + "enforce, and can be any of \002SECUREOPS\002, \002RESTRICTED\002, \002REGONLY\002, \002SSLONLY\002,\n" + "\002BANS\002, or \002LIMIT\002.\n" + " \n" + "Use \002SECUREOPS\002 to enforce the SECUREOPS option, even if it is not\n" + "enabled. Use \002RESTRICTED\002 to enforce the RESTRICTED option, also\n" + "if it's not enabled. Use \002REGONLY\002 to kick all unregistered users\n" + "from the channel. Use \002SSLONLY\002 to kick all users not using a secure\n" + "connection from the channel. \002BANS\002 will enforce bans on the channel by\n" + "kicking users affected by them, and \002LIMIT\002 will kick users until the\n" + "user count drops below the channel limit, if one is set.")); + return true; + } +}; + +class CSEnforce : public Module +{ + CommandCSEnforce commandcsenforce; + + public: + CSEnforce(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcsenforce(this) + { + + } +}; + +MODULE_INIT(CSEnforce) diff --git a/modules/commands/cs_entrymsg.cpp b/modules/commands/cs_entrymsg.cpp new file mode 100644 index 0000000..0c27571 --- /dev/null +++ b/modules/commands/cs_entrymsg.cpp @@ -0,0 +1,289 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/cs_entrymsg.h" + +struct EntryMsgImpl : EntryMsg, Serializable +{ + EntryMsgImpl() : Serializable("EntryMsg") + { + } + + EntryMsgImpl(ChannelInfo *c, const Anope::string &cname, const Anope::string &cmessage, time_t ct = Anope::CurTime) : Serializable("EntryMsg") + { + this->chan = c->name; + this->creator = cname; + this->message = cmessage; + this->when = ct; + } + + ~EntryMsgImpl(); + + void Serialize(Serialize::Data &data) const anope_override + { + data["ci"] << this->chan; + data["creator"] << this->creator; + data["message"] << this->message; + data.SetType("when", Serialize::Data::DT_INT); data["when"] << this->when; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data); +}; + +struct EntryMessageListImpl : EntryMessageList +{ + EntryMessageListImpl(Extensible *) { } + + EntryMsg* Create() anope_override + { + return new EntryMsgImpl(); + } +}; + +EntryMsgImpl::~EntryMsgImpl() +{ + ChannelInfo *ci = ChannelInfo::Find(this->chan); + if (!ci) + return; + + EntryMessageList *messages = ci->GetExt("entrymsg"); + if (!messages) + return; + + std::vector::iterator it = std::find((*messages)->begin(), (*messages)->end(), this); + if (it != (*messages)->end()) + (*messages)->erase(it); +} + + +Serializable* EntryMsgImpl::Unserialize(Serializable *obj, Serialize::Data &data) +{ + Anope::string sci, screator, smessage; + time_t swhen; + + data["ci"] >> sci; + data["creator"] >> screator; + data["message"] >> smessage; + + ChannelInfo *ci = ChannelInfo::Find(sci); + if (!ci) + return NULL; + + if (obj) + { + EntryMsgImpl *msg = anope_dynamic_static_cast(obj); + msg->chan = ci->name; + data["creator"] >> msg->creator; + data["message"] >> msg->message; + data["when"] >> msg->when; + return msg; + } + + EntryMessageList *messages = ci->Require("entrymsg"); + + data["when"] >> swhen; + + EntryMsgImpl *m = new EntryMsgImpl(ci, screator, smessage, swhen); + (*messages)->push_back(m); + return m; +} + +class CommandEntryMessage : public Command +{ + private: + void DoList(CommandSource &source, ChannelInfo *ci) + { + EntryMessageList *messages = ci->Require("entrymsg"); + + if ((*messages)->empty()) + { + source.Reply(_("Entry message list for \002%s\002 is empty."), ci->name.c_str()); + return; + } + + source.Reply(_("Entry message list for \002%s\002:"), ci->name.c_str()); + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Creator")).AddColumn(_("Created")).AddColumn(_("Message")); + for (unsigned i = 0; i < (*messages)->size(); ++i) + { + EntryMsg *msg = (*messages)->at(i); + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(i + 1); + entry["Creator"] = msg->creator; + entry["Created"] = Anope::strftime(msg->when, NULL, true); + entry["Message"] = msg->message; + list.AddEntry(entry); + } + + std::vector replies; + list.Process(replies); + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("End of entry message list.")); + } + + void DoAdd(CommandSource &source, ChannelInfo *ci, const Anope::string &message) + { + EntryMessageList *messages = ci->Require("entrymsg"); + + if ((*messages)->size() >= Config->GetModule(this->owner)->Get("maxentries")) + source.Reply(_("The entry message list for \002%s\002 is full."), ci->name.c_str()); + else + { + (*messages)->push_back(new EntryMsgImpl(ci, source.GetNick(), message)); + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to add a message"; + source.Reply(_("Entry message added to \002%s\002"), ci->name.c_str()); + } + } + + void DoDel(CommandSource &source, ChannelInfo *ci, const Anope::string &message) + { + EntryMessageList *messages = ci->Require("entrymsg"); + + if (!message.is_pos_number_only()) + source.Reply(("Entry message \002%s\002 not found on channel \002%s\002."), message.c_str(), ci->name.c_str()); + else if ((*messages)->empty()) + source.Reply(_("Entry message list for \002%s\002 is empty."), ci->name.c_str()); + else + { + try + { + unsigned i = convertTo(message); + if (i > 0 && i <= (*messages)->size()) + { + delete (*messages)->at(i - 1); + if ((*messages)->empty()) + ci->Shrink("entrymsg"); + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to remove a message"; + source.Reply(_("Entry message \002%i\002 for \002%s\002 deleted."), i, ci->name.c_str()); + } + else + throw ConvertException(); + } + catch (const ConvertException &) + { + source.Reply(_("Entry message \002%s\002 not found on channel \002%s\002."), message.c_str(), ci->name.c_str()); + } + } + } + + void DoClear(CommandSource &source, ChannelInfo *ci) + { + ci->Shrink("entrymsg"); + + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to remove all messages"; + source.Reply(_("Entry messages for \002%s\002 have been cleared."), ci->name.c_str()); + } + + public: + CommandEntryMessage(Module *creator) : Command(creator, "chanserv/entrymsg", 2, 3) + { + this->SetDesc(_("Manage the channel's entry messages")); + this->SetSyntax(_("\037channel\037 ADD \037message\037")); + this->SetSyntax(_("\037channel\037 DEL \037num\037")); + this->SetSyntax(_("\037channel\037 LIST")); + this->SetSyntax(_("\037channel\037 CLEAR")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + if (Anope::ReadOnly && !params[1].equals_ci("LIST")) + { + source.Reply(READ_ONLY_MODE); + return; + } + + if (!source.AccessFor(ci).HasPriv("SET") && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params[1].equals_ci("LIST")) + this->DoList(source, ci); + else if (params[1].equals_ci("CLEAR")) + this->DoClear(source, ci); + else if (params.size() < 3) + this->OnSyntaxError(source, ""); + else if (params[1].equals_ci("ADD")) + this->DoAdd(source, ci, params[2]); + else if (params[1].equals_ci("DEL")) + this->DoDel(source, ci, params[2]); + else + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Controls what messages will be sent to users when they join the channel.")); + source.Reply(" "); + source.Reply(_("The \002ENTRYMSG ADD\002 command adds the given message to\n" + "the list of messages shown to users when they join\n" + "the channel.")); + source.Reply(" "); + source.Reply(_("The \002ENTRYMSG DEL\002 command removes the specified message from\n" + "the list of messages shown to users when they join\n" + "the channel. You can remove a message by specifying its number\n" + "which you can get by listing the messages as explained below.")); + source.Reply(" "); + source.Reply(_("The \002ENTRYMSG LIST\002 command displays a listing of messages\n" + "shown to users when they join the channel.")); + source.Reply(" "); + source.Reply(_("The \002ENTRYMSG CLEAR\002 command clears all entries from\n" + "the list of messages shown to users when they join\n" + "the channel, effectively disabling entry messages.")); + source.Reply(" "); + source.Reply(_("Adding, deleting, or clearing entry messages requires the\n" + "SET permission.")); + return true; + } +}; + +class CSEntryMessage : public Module +{ + CommandEntryMessage commandentrymsg; + ExtensibleItem eml; + Serialize::Type entrymsg_type; + + public: + CSEntryMessage(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandentrymsg(this), + eml(this, "entrymsg"), entrymsg_type("EntryMsg", EntryMsgImpl::Unserialize) + { + } + + void OnJoinChannel(User *u, Channel *c) anope_override + { + if (u && c && c->ci && u->server->IsSynced()) + { + EntryMessageList *messages = c->ci->GetExt("entrymsg"); + + if (messages != NULL) + for (unsigned i = 0; i < (*messages)->size(); ++i) + u->SendMessage(c->ci->WhoSends(), "[%s] %s", c->ci->name.c_str(), (*messages)->at(i)->message.c_str()); + } + } +}; + +MODULE_INIT(CSEntryMessage) diff --git a/modules/commands/cs_flags.cpp b/modules/commands/cs_flags.cpp new file mode 100644 index 0000000..6ffddfc --- /dev/null +++ b/modules/commands/cs_flags.cpp @@ -0,0 +1,504 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +static std::map defaultFlags; + +class FlagsChanAccess : public ChanAccess +{ + public: + std::set flags; + + FlagsChanAccess(AccessProvider *p) : ChanAccess(p) + { + } + + bool HasPriv(const Anope::string &priv) const anope_override + { + std::map::iterator it = defaultFlags.find(priv); + if (it != defaultFlags.end() && this->flags.count(it->second) > 0) + return true; + return false; + } + + Anope::string AccessSerialize() const anope_override + { + return Anope::string(this->flags.begin(), this->flags.end()); + } + + void AccessUnserialize(const Anope::string &data) anope_override + { + for (unsigned i = data.length(); i > 0; --i) + this->flags.insert(data[i - 1]); + } + + static Anope::string DetermineFlags(const ChanAccess *access) + { + if (access->provider->name == "access/flags") + return access->AccessSerialize(); + + std::set buffer; + + for (std::map::iterator it = defaultFlags.begin(), it_end = defaultFlags.end(); it != it_end; ++it) + if (access->HasPriv(it->first)) + buffer.insert(it->second); + + if (buffer.empty()) + return "(none)"; + else + return Anope::string(buffer.begin(), buffer.end()); + } +}; + +class FlagsAccessProvider : public AccessProvider +{ + public: + static FlagsAccessProvider *ap; + + FlagsAccessProvider(Module *o) : AccessProvider(o, "access/flags") + { + ap = this; + } + + ChanAccess *Create() anope_override + { + return new FlagsChanAccess(this); + } +}; +FlagsAccessProvider* FlagsAccessProvider::ap; + +class CommandCSFlags : public Command +{ + void DoModify(CommandSource &source, ChannelInfo *ci, Anope::string mask, const Anope::string &flags) + { + if (flags.empty()) + { + this->OnSyntaxError(source, ""); + return; + } + + AccessGroup u_access = source.AccessFor(ci); + const ChanAccess *highest = u_access.Highest(); + const NickAlias *na = NULL; + + if (IRCD->IsChannelValid(mask)) + { + if (Config->GetModule("chanserv")->Get("disallow_channel_access")) + { + source.Reply(_("Channels may not be on access lists.")); + return; + } + + ChannelInfo *targ_ci = ChannelInfo::Find(mask); + if (targ_ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, mask.c_str()); + return; + } + else if (ci == targ_ci) + { + source.Reply(_("You can't add a channel to its own access list.")); + return; + } + + mask = targ_ci->name; + } + else + { + na = NickAlias::Find(mask); + if (!na && Config->GetModule("chanserv")->Get("disallow_hostmask_access")) + { + source.Reply(_("Masks and unregistered users may not be on access lists.")); + return; + } + else if (mask.find_first_of("!*@") == Anope::string::npos && !na) + { + User *targ = User::Find(mask, true); + if (targ != NULL) + mask = "*!*@" + targ->GetDisplayedHost(); + else + { + source.Reply(NICK_X_NOT_REGISTERED, mask.c_str()); + return; + } + } + + if (na) + mask = na->nick; + } + + ChanAccess *current = NULL; + unsigned current_idx; + std::set current_flags; + bool override = false; + for (current_idx = ci->GetAccessCount(); current_idx > 0; --current_idx) + { + ChanAccess *access = ci->GetAccess(current_idx - 1); + if ((na && na->nc == access->GetAccount()) || mask.equals_ci(access->Mask())) + { + // Flags allows removing others that have the same access as you, + // but no other access system does. + if (highest && highest->provider != FlagsAccessProvider::ap && !u_access.founder) + // operator<= on the non-me entry! + if (*highest <= *access) + { + if (source.HasPriv("chanserv/access/modify")) + override = true; + else + { + source.Reply(ACCESS_DENIED); + return; + } + } + + current = access; + Anope::string cur_flags = FlagsChanAccess::DetermineFlags(access); + for (unsigned j = cur_flags.length(); j > 0; --j) + current_flags.insert(cur_flags[j - 1]); + break; + } + } + + unsigned access_max = Config->GetModule("chanserv")->Get("accessmax", "1024"); + if (access_max && ci->GetDeepAccessCount() >= access_max) + { + source.Reply(_("Sorry, you can only have %d access entries on a channel, including access entries from other channels."), access_max); + return; + } + + Privilege *p = NULL; + bool add = true; + for (size_t i = 0; i < flags.length(); ++i) + { + char f = flags[i]; + switch (f) + { + case '+': + add = true; + break; + case '-': + add = false; + break; + case '*': + for (std::map::iterator it = defaultFlags.begin(), it_end = defaultFlags.end(); it != it_end; ++it) + { + bool has = current_flags.count(it->second); + // If we are adding a flag they already have or removing one they don't have, don't bother + if (add == has) + continue; + + if (!u_access.HasPriv(it->first) && !u_access.founder) + { + if (source.HasPriv("chanserv/access/modify")) + override = true; + else + continue; + } + + if (add) + current_flags.insert(it->second); + else + current_flags.erase(it->second); + } + break; + default: + p = PrivilegeManager::FindPrivilege(flags.substr(i)); + if (p != NULL && defaultFlags[p->name]) + { + f = defaultFlags[p->name]; + i = flags.length(); + } + + for (std::map::iterator it = defaultFlags.begin(), it_end = defaultFlags.end(); it != it_end; ++it) + { + if (f != it->second) + continue; + else if (!u_access.HasPriv(it->first) && !u_access.founder) + { + if (source.HasPriv("chanserv/access/modify")) + override = true; + else + { + source.Reply(_("You cannot set the \002%c\002 flag."), f); + break; + } + } + if (add) + current_flags.insert(f); + else + current_flags.erase(f); + break; + } + } + } + if (current_flags.empty()) + { + if (current != NULL) + { + ci->EraseAccess(current_idx - 1); + FOREACH_MOD(OnAccessDel, (ci, source, current)); + delete current; + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to delete " << mask; + source.Reply(_("\002%s\002 removed from the %s access list."), mask.c_str(), ci->name.c_str()); + } + else + { + source.Reply(_("\002%s\002 not found on %s access list."), mask.c_str(), ci->name.c_str()); + } + return; + } + + ServiceReference provider("AccessProvider", "access/flags"); + if (!provider) + return; + FlagsChanAccess *access = anope_dynamic_static_cast(provider->Create()); + access->SetMask(mask, ci); + access->creator = source.GetNick(); + access->last_seen = current ? current->last_seen : 0; + access->created = Anope::CurTime; + access->flags = current_flags; + + if (current != NULL) + delete current; + + ci->AddAccess(access); + + FOREACH_MOD(OnAccessAdd, (ci, source, access)); + + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to modify " << mask << "'s flags to " << access->AccessSerialize(); + if (p != NULL) + { + if (add) + source.Reply(_("Privilege \002%s\002 added to \002%s\002 on \002%s\002, new flags are +\002%s\002"), p->name.c_str(), access->Mask().c_str(), ci->name.c_str(), access->AccessSerialize().c_str()); + else + source.Reply(_("Privilege \002%s\002 removed from \002%s\002 on \002%s\002, new flags are +\002%s\002"), p->name.c_str(), access->Mask().c_str(), ci->name.c_str(), access->AccessSerialize().c_str()); + } + else + source.Reply(_("Flags for \002%s\002 on %s set to +\002%s\002"), access->Mask().c_str(), ci->name.c_str(), access->AccessSerialize().c_str()); + } + + void DoList(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + const Anope::string &arg = params.size() > 2 ? params[2] : ""; + + if (!ci->GetAccessCount()) + { + source.Reply(_("%s access list is empty."), ci->name.c_str()); + return; + } + + ListFormatter list(source.GetAccount()); + + list.AddColumn(_("Number")).AddColumn(_("Mask")).AddColumn(_("Flags")).AddColumn(_("Creator")).AddColumn(_("Created")); + + unsigned count = 0; + for (unsigned i = 0, end = ci->GetAccessCount(); i < end; ++i) + { + const ChanAccess *access = ci->GetAccess(i); + const Anope::string &flags = FlagsChanAccess::DetermineFlags(access); + + if (!arg.empty()) + { + if (arg[0] == '+') + { + bool pass = true; + for (size_t j = 1; j < arg.length(); ++j) + if (flags.find(arg[j]) == Anope::string::npos) + pass = false; + if (pass == false) + continue; + } + else if (!Anope::Match(access->Mask(), arg)) + continue; + } + + ListFormatter::ListEntry entry; + ++count; + entry["Number"] = stringify(i + 1); + entry["Mask"] = access->Mask(); + entry["Flags"] = flags; + entry["Creator"] = access->creator; + entry["Created"] = Anope::strftime(access->created, source.nc, true); + list.AddEntry(entry); + } + + if (list.IsEmpty()) + source.Reply(_("No matching entries on %s access list."), ci->name.c_str()); + else + { + std::vector replies; + list.Process(replies); + + source.Reply(_("Flags list for %s"), ci->name.c_str()); + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + if (count == ci->GetAccessCount()) + source.Reply(_("End of access list.")); + else + source.Reply(_("End of access list - %d/%d entries shown."), count, ci->GetAccessCount()); + } + } + + void DoClear(CommandSource &source, ChannelInfo *ci) + { + if (!source.IsFounder(ci) && !source.HasPriv("chanserv/access/modify")) + source.Reply(ACCESS_DENIED); + else + { + ci->ClearAccess(); + + FOREACH_MOD(OnAccessClear, (ci, source)); + + source.Reply(_("Channel %s access list has been cleared."), ci->name.c_str()); + + bool override = !source.IsFounder(ci); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to clear the access list"; + } + + return; + } + + public: + CommandCSFlags(Module *creator) : Command(creator, "chanserv/flags", 1, 4) + { + this->SetDesc(_("Modify the list of privileged users")); + this->SetSyntax(_("\037channel\037 [MODIFY] \037mask\037 \037changes\037")); + this->SetSyntax(_("\037channel\037 LIST [\037mask\037 | +\037flags\037]")); + this->SetSyntax(_("\037channel\037 CLEAR")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &chan = params[0]; + const Anope::string &cmd = params.size() > 1 ? params[1] : ""; + + ChannelInfo *ci = ChannelInfo::Find(chan); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); + return; + } + + bool is_list = cmd.empty() || cmd.equals_ci("LIST"); + bool has_access = false; + if (source.HasPriv("chanserv/access/modify")) + has_access = true; + else if (is_list && source.HasPriv("chanserv/access/list")) + has_access = true; + else if (is_list && source.AccessFor(ci).HasPriv("ACCESS_LIST")) + has_access = true; + else if (source.AccessFor(ci).HasPriv("ACCESS_CHANGE")) + has_access = true; + + if (!has_access) + source.Reply(ACCESS_DENIED); + else if (Anope::ReadOnly && !is_list) + source.Reply(_("Sorry, channel access list modification is temporarily disabled.")); + else if (is_list) + this->DoList(source, ci, params); + else if (cmd.equals_ci("CLEAR")) + this->DoClear(source, ci); + else + { + Anope::string mask, flags; + if (cmd.equals_ci("MODIFY")) + { + mask = params.size() > 2 ? params[2] : ""; + flags = params.size() > 3 ? params[3] : ""; + } + else + { + mask = cmd; + flags = params.size() > 2 ? params[2] : ""; + } + + this->DoModify(source, ci, mask, flags); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("%s is another way to modify the channel access list, similar to\n" + "the XOP and ACCESS methods."), source.command.c_str()); + source.Reply(" "); + source.Reply(_("The \002MODIFY\002 command allows you to modify the access list. If the mask is\n" + "not already on the access list it is added, then the changes are applied.\n" + "If the mask has no more flags, then the mask is removed from the access list.\n" + "Additionally, you may use +* or -* to add or remove all flags, respectively. You are\n" + "only able to modify the access list if you have the proper permission on the channel,\n" + "and even then you can only give other people access to the equivalent of what your access is.")); + source.Reply(" "); + source.Reply(_("The \002LIST\002 command allows you to list existing entries on the channel access list.\n" + "If a mask is given, the mask is wildcard matched against all existing entries on the\n" + "access list, and only those entries are returned. If a set of flags is given, only those\n" + "on the access list with the specified flags are returned.")); + source.Reply(" "); + source.Reply(_("The \002CLEAR\002 command clears the channel access list. This requires channel founder access.")); + source.Reply(" "); + source.Reply(_("The available flags are:")); + + typedef std::multimap reverse_map; + reverse_map reverse; + for (std::map::iterator it = defaultFlags.begin(), it_end = defaultFlags.end(); it != it_end; ++it) + reverse.insert(std::make_pair(it->second, it->first)); + + for (reverse_map::iterator it = reverse.begin(), it_end = reverse.end(); it != it_end; ++it) + { + Privilege *p = PrivilegeManager::FindPrivilege(it->second); + if (p == NULL) + continue; + source.Reply(" %c - %s", it->first, Language::Translate(source.nc, p->desc.c_str())); + } + + return true; + } +}; + +class CSFlags : public Module +{ + FlagsAccessProvider accessprovider; + CommandCSFlags commandcsflags; + + public: + CSFlags(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + accessprovider(this), commandcsflags(this) + { + this->SetPermanent(true); + + } + + void OnReload(Configuration::Conf *conf) anope_override + { + defaultFlags.clear(); + + for (int i = 0; i < conf->CountBlock("privilege"); ++i) + { + Configuration::Block *priv = conf->GetBlock("privilege", i); + + const Anope::string &pname = priv->Get("name"); + + Privilege *p = PrivilegeManager::FindPrivilege(pname); + if (p == NULL) + continue; + + const Anope::string &value = priv->Get("flag"); + if (value.empty()) + continue; + + defaultFlags[p->name] = value[0]; + } + } +}; + +MODULE_INIT(CSFlags) diff --git a/modules/commands/cs_getkey.cpp b/modules/commands/cs_getkey.cpp new file mode 100644 index 0000000..086b040 --- /dev/null +++ b/modules/commands/cs_getkey.cpp @@ -0,0 +1,73 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandCSGetKey : public Command +{ + public: + CommandCSGetKey(Module *creator) : Command(creator, "chanserv/getkey", 1, 1) + { + this->SetDesc(_("Returns the key of the given channel")); + this->SetSyntax(_("\037channel\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &chan = params[0]; + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + if (!source.AccessFor(ci).HasPriv("GETKEY") && !source.HasCommand("chanserv/getkey")) + { + source.Reply(ACCESS_DENIED); + return; + } + + Anope::string key; + if (!ci->c || !ci->c->GetParam("KEY", key)) + { + source.Reply(_("Channel \002%s\002 has no key."), chan.c_str()); + return; + } + + bool override = !source.AccessFor(ci).HasPriv("GETKEY"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci); + + source.Reply(_("Key for channel \002%s\002 is \002%s\002."), chan.c_str(), key.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Returns the key of the given channel.")); + return true; + } +}; + +class CSGetKey : public Module +{ + CommandCSGetKey commandcsgetkey; + + public: + CSGetKey(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), commandcsgetkey(this) + { + + } +}; + +MODULE_INIT(CSGetKey) diff --git a/modules/commands/cs_info.cpp b/modules/commands/cs_info.cpp new file mode 100644 index 0000000..d200974 --- /dev/null +++ b/modules/commands/cs_info.cpp @@ -0,0 +1,98 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandCSInfo : public Command +{ + public: + CommandCSInfo(Module *creator) : Command(creator, "chanserv/info", 1, 2) + { + this->SetDesc(_("Lists information about the specified registered channel")); + this->SetSyntax(_("\037channel\037")); + this->AllowUnregistered(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &chan = params[0]; + + NickCore *nc = source.nc; + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + bool has_auspex = source.HasPriv("chanserv/auspex"); + bool show_all = false; + + /* Should we show all fields? Only for sadmins and identified users */ + if (source.AccessFor(ci).HasPriv("INFO") || has_auspex) + show_all = true; + + InfoFormatter info(nc); + + source.Reply(CHAN_INFO_HEADER, chan.c_str()); + if (ci->GetFounder()) + info[_("Founder")] = ci->GetFounder()->display; + + if (show_all && ci->GetSuccessor()) + info[_("Successor")] = ci->GetSuccessor()->display; + + if (!ci->desc.empty()) + info[_("Description")] = ci->desc; + + info[_("Registered")] = Anope::strftime(ci->time_registered, source.GetAccount()); + info[_("Last used")] = Anope::strftime(ci->last_used, source.GetAccount()); + + if (show_all) + { + info[_("Ban type")] = stringify(ci->bantype); + } + + FOREACH_MOD(OnChanInfo, (source, ci, info, show_all)); + + std::vector replies; + info.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Lists information about the specified registered channel,\n" + "including its founder, time of registration, last\n" + "time used, and description. If the user issuing the\n" + "command has the appropriate access for it, then the\n" + "successor, last topic set, settings and expiration\n" + "time will also be displayed when applicable.")); + return true; + } +}; + +class CSInfo : public Module +{ + CommandCSInfo commandcsinfo; + + public: + CSInfo(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcsinfo(this) + { + + } +}; + +MODULE_INIT(CSInfo) diff --git a/modules/commands/cs_invite.cpp b/modules/commands/cs_invite.cpp new file mode 100644 index 0000000..9d26f45 --- /dev/null +++ b/modules/commands/cs_invite.cpp @@ -0,0 +1,111 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandCSInvite : public Command +{ + public: + CommandCSInvite(Module *creator) : Command(creator, "chanserv/invite", 1, 3) + { + this->SetDesc(_("Invites you or an optionally specified nick into a channel")); + this->SetSyntax(_("\037channel\037 [\037nick\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &chan = params[0]; + + User *u = source.GetUser(); + Channel *c = Channel::Find(chan); + + if (!c) + { + source.Reply(CHAN_X_NOT_IN_USE, chan.c_str()); + return; + } + + ChannelInfo *ci = c->ci; + if (!ci) + { + source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); + return; + } + + if (!source.AccessFor(ci).HasPriv("INVITE") && !source.HasCommand("chanserv/invite")) + { + source.Reply(ACCESS_DENIED); + return; + } + + User *u2; + if (params.size() == 1) + u2 = u; + else + u2 = User::Find(params[1], true); + + if (!u2) + { + source.Reply(NICK_X_NOT_IN_USE, params.size() > 1 ? params[1].c_str() : source.GetNick().c_str()); + return; + } + + if (c->FindUser(u2)) + { + if (u2 == u) + source.Reply(_("You are already in \002%s\002!"), c->name.c_str()); + else + source.Reply(_("\002%s\002 is already in \002%s\002!"), u2->nick.c_str(), c->name.c_str()); + } + else + { + bool override = !source.AccessFor(ci).HasPriv("INVITE"); + + IRCD->SendInvite(ci->WhoSends(), c, u2); + if (u2 != u) + { + source.Reply(_("\002%s\002 has been invited to \002%s\002."), u2->nick.c_str(), c->name.c_str()); + u2->SendMessage(ci->WhoSends(), _("You have been invited to \002%s\002 by \002%s\002."), c->name.c_str(), source.GetNick().c_str()); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "for " << u2->nick; + } + else + { + u2->SendMessage(ci->WhoSends(), _("You have been invited to \002%s\002."), c->name.c_str()); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci); + } + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Tells %s to invite you or an optionally specified\n" + "nick into the given channel.\n" + " \n" + "By default, limited to AOPs or those with level 5 access and above\n" + "on the channel."), source.service->nick.c_str()); + return true; + } +}; + +class CSInvite : public Module +{ + CommandCSInvite commandcsinvite; + + public: + CSInvite(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), commandcsinvite(this) + { + + } +}; + +MODULE_INIT(CSInvite) diff --git a/modules/commands/cs_kick.cpp b/modules/commands/cs_kick.cpp new file mode 100644 index 0000000..46278be --- /dev/null +++ b/modules/commands/cs_kick.cpp @@ -0,0 +1,147 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandCSKick : public Command +{ + public: + CommandCSKick(Module *creator) : Command(creator, "chanserv/kick", 2, 3) + { + this->SetDesc(_("Kicks a specified nick from a channel")); + this->SetSyntax(_("\037channel\037 \037nick\037 [\037reason\037]")); + this->SetSyntax(_("\037channel\037 \037mask\037 [\037reason\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &chan = params[0]; + const Anope::string &target = params[1]; + Anope::string reason = params.size() > 2 ? params[2] : "Requested"; + + User *u = source.GetUser(); + ChannelInfo *ci = ChannelInfo::Find(params[0]); + Channel *c = Channel::Find(params[0]); + User *u2 = User::Find(target, true); + + if (!c) + { + source.Reply(CHAN_X_NOT_IN_USE, chan.c_str()); + return; + } + else if (!ci) + { + source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); + return; + } + + unsigned reasonmax = Config->GetModule("chanserv")->Get("reasonmax", "200"); + if (reason.length() > reasonmax) + reason = reason.substr(0, reasonmax); + + Anope::string signkickformat = Config->GetModule("chanserv")->Get("signkickformat", "%m (%n)"); + signkickformat = signkickformat.replace_all_cs("%n", source.GetNick()); + + AccessGroup u_access = source.AccessFor(ci); + + if (!u_access.HasPriv("KICK") && !source.HasPriv("chanserv/kick")) + source.Reply(ACCESS_DENIED); + else if (u2) + { + AccessGroup u2_access = ci->AccessFor(u2); + if (u != u2 && ci->HasExt("PEACE") && u2_access >= u_access && !source.HasPriv("chanserv/kick")) + source.Reply(ACCESS_DENIED); + else if (u2->IsProtected()) + source.Reply(ACCESS_DENIED); + else if (!c->FindUser(u2)) + source.Reply(NICK_X_NOT_ON_CHAN, u2->nick.c_str(), c->name.c_str()); + else + { + bool override = !u_access.HasPriv("KICK") || (u != u2 && ci->HasExt("PEACE") && u2_access >= u_access); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "for " << u2->nick; + + if (ci->HasExt("SIGNKICK") || (ci->HasExt("SIGNKICK_LEVEL") && !u_access.HasPriv("SIGNKICK"))) + { + signkickformat = signkickformat.replace_all_cs("%m", reason); + c->Kick(ci->WhoSends(), u2, "%s", signkickformat.c_str()); + } + else + c->Kick(ci->WhoSends(), u2, "%s", reason.c_str()); + } + } + else if (u_access.HasPriv("FOUNDER")) + { + Anope::string mask = IRCD->NormalizeMask(target); + + Log(LOG_COMMAND, source, this, ci) << "for " << mask; + + int matched = 0, kicked = 0; + for (Channel::ChanUserList::iterator it = c->users.begin(), it_end = c->users.end(); it != it_end;) + { + ChanUserContainer *uc = it->second; + ++it; + + Entry e("", mask); + if (e.Matches(uc->user)) + { + ++matched; + + AccessGroup u2_access = ci->AccessFor(uc->user); + if (u != uc->user && ci->HasExt("PEACE") && u2_access >= u_access) + continue; + else if (uc->user->IsProtected()) + continue; + + ++kicked; + if (ci->HasExt("SIGNKICK") || (ci->HasExt("SIGNKICK_LEVEL") && !u_access.HasPriv("SIGNKICK"))) + { + reason += " (Matches " + mask + ")"; + signkickformat = signkickformat.replace_all_cs("%m", reason); + c->Kick(ci->WhoSends(), uc->user, "%s", signkickformat.c_str()); + } + else + c->Kick(ci->WhoSends(), uc->user, "%s (Matches %s)", reason.c_str(), mask.c_str()); + } + } + + if (matched) + source.Reply(_("Kicked %d/%d users matching %s from %s."), kicked, matched, mask.c_str(), c->name.c_str()); + else + source.Reply(_("No users on %s match %s."), c->name.c_str(), mask.c_str()); + } + else + source.Reply(NICK_X_NOT_IN_USE, target.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Kicks a specified nick from a channel.\n" + " \n" + "By default, limited to AOPs or those with level 5 access\n" + "and above on the channel. Channel founders can also specify masks.")); + return true; + } +}; + +class CSKick : public Module +{ + CommandCSKick commandcskick; + + public: + CSKick(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), commandcskick(this) + { + + } +}; + +MODULE_INIT(CSKick) diff --git a/modules/commands/cs_list.cpp b/modules/commands/cs_list.cpp new file mode 100644 index 0000000..86d1cb3 --- /dev/null +++ b/modules/commands/cs_list.cpp @@ -0,0 +1,266 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/cs_mode.h" + +class CommandCSList : public Command +{ + public: + CommandCSList(Module *creator) : Command(creator, "chanserv/list", 1, 2) + { + this->SetDesc(_("Lists all registered channels matching the given pattern")); + this->SetSyntax(_("\037pattern\037 [SUSPENDED] [NOEXPIRE]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + Anope::string pattern = params[0]; + unsigned nchans; + bool is_servadmin = source.HasCommand("chanserv/list"); + int count = 0, from = 0, to = 0; + bool suspended = false, channoexpire = false; + + if (pattern[0] == '#') + { + Anope::string n1, n2; + sepstream(pattern.substr(1), '-').GetToken(n1, 0); + sepstream(pattern, '-').GetToken(n2, 1); + + try + { + from = convertTo(n1); + to = convertTo(n2); + } + catch (const ConvertException &) + { + source.Reply(LIST_INCORRECT_RANGE); + source.Reply(_("To search for channels starting with #, search for the channel\n" + "name without the #-sign prepended (\002anope\002 instead of \002#anope\002).")); + return; + } + + pattern = "*"; + } + + nchans = 0; + + if (is_servadmin && params.size() > 1) + { + Anope::string keyword; + spacesepstream keywords(params[1]); + while (keywords.GetToken(keyword)) + { + if (keyword.equals_ci("SUSPENDED")) + suspended = true; + if (keyword.equals_ci("NOEXPIRE")) + channoexpire = true; + } + } + + Anope::string spattern = "#" + pattern; + unsigned listmax = Config->GetModule(this->owner)->Get("listmax", "50"); + + source.Reply(_("List of entries matching \002%s\002:"), pattern.c_str()); + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Name")).AddColumn(_("Description")); + + Anope::map ordered_map; + for (registered_channel_map::const_iterator it = RegisteredChannelList->begin(), it_end = RegisteredChannelList->end(); it != it_end; ++it) + ordered_map[it->first] = it->second; + + for (Anope::map::const_iterator it = ordered_map.begin(), it_end = ordered_map.end(); it != it_end; ++it) + { + const ChannelInfo *ci = it->second; + + if (!is_servadmin) + { + if (ci->HasExt("CS_PRIVATE") || ci->HasExt("CS_SUSPENDED")) + continue; + if (ci->c && ci->c->HasMode("SECRET")) + continue; + + ModeLocks *ml = ci->GetExt("modelocks"); + const ModeLock *secret = ml ? ml->GetMLock("SECRET") : NULL; + if (secret && secret->set) + continue; + } + + if (suspended && !ci->HasExt("CS_SUSPENDED")) + continue; + + if (channoexpire && !ci->HasExt("CS_NO_EXPIRE")) + continue; + + if (pattern.equals_ci(ci->name) || ci->name.equals_ci(spattern) || Anope::Match(ci->name, pattern, false, true) || Anope::Match(ci->name, spattern, false, true) || Anope::Match(ci->desc, pattern, false, true) || Anope::Match(ci->last_topic, pattern, false, true)) + { + if (((count + 1 >= from && count + 1 <= to) || (!from && !to)) && ++nchans <= listmax) + { + bool isnoexpire = false; + if (is_servadmin && (ci->HasExt("CS_NO_EXPIRE"))) + isnoexpire = true; + + ListFormatter::ListEntry entry; + entry["Name"] = (isnoexpire ? "!" : "") + ci->name; + if (ci->HasExt("CS_SUSPENDED")) + entry["Description"] = Language::Translate(source.GetAccount(), _("[Suspended]")); + else + entry["Description"] = ci->desc; + list.AddEntry(entry); + } + ++count; + } + } + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("End of list - %d/%d matches shown."), nchans > listmax ? listmax : nchans, nchans); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Lists all registered channels matching the given pattern.\n" + "Channels with the \002PRIVATE\002 option set will only be\n" + "displayed to Services Operators with the proper access.\n" + "Channels with the \002NOEXPIRE\002 option set will have\n" + "a \002!\002 prefixed to the channel for Services Operators to see.\n" + " \n" + "Note that a preceding '#' specifies a range, channel names\n" + "are to be written without '#'.\n" + " \n" + "If the SUSPENDED or NOEXPIRE options are given, only channels\n" + "which, respectively, are SUSPENDED or have the NOEXPIRE\n" + "flag set will be displayed. If multiple options are given,\n" + "all channels matching at least one option will be displayed.\n" + "Note that these options are limited to \037Services Operators\037.\n" + " \n" + "Examples:\n" + " \n" + " \002LIST *anope*\002\n" + " Lists all registered channels with \002anope\002 in their\n" + " names (case insensitive).\n" + " \n" + " \002LIST * NOEXPIRE\002\n" + " Lists all registered channels which have been set to not expire.\n" + " \n" + " \002LIST #51-100\002\n" + " Lists all registered channels within the given range (51-100).")); + + if (!Config->GetBlock("options")->Get("regexengine").empty()) + { + source.Reply(" "); + source.Reply(_("Regex matches are also supported using the %s engine.\n" + "Enclose your pattern in // if this is desired."), Config->GetBlock("options")->Get("regexengine").c_str()); + } + + return true; + } +}; + +class CommandCSSetPrivate : public Command +{ + public: + CommandCSSetPrivate(Module *creator, const Anope::string &cname = "chanserv/set/private") : Command(creator, cname, 2, 2) + { + this->SetDesc(_("Hide channel from the LIST command")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params[1].equals_ci("ON")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to enable private"; + ci->Extend("CS_PRIVATE"); + source.Reply(_("Private option for %s is now \002on\002."), ci->name.c_str()); + } + else if (params[1].equals_ci("OFF")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to disable private"; + ci->Shrink("CS_PRIVATE"); + source.Reply(_("Private option for %s is now \002off\002."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, "PRIVATE"); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enables or disables the \002private\002 option for a channel.")); + + BotInfo *bi; + Anope::string cmd; + if (Command::FindCommandFromService("chanserv/list", bi, cmd)) + source.Reply(_("When \002private\002 is set, the channel will not appear in\n" + "%s's %s command."), bi->nick.c_str(), cmd.c_str()); + return true; + } +}; + +class CSList : public Module +{ + CommandCSList commandcslist; + CommandCSSetPrivate commandcssetprivate; + + SerializableExtensibleItem priv; + + public: + CSList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcslist(this), commandcssetprivate(this), priv(this, "CS_PRIVATE") + { + } + + void OnChanInfo(CommandSource &source, ChannelInfo *ci, InfoFormatter &info, bool show_all) anope_override + { + if (!show_all) + return; + + if (priv.HasExt(ci)) + info.AddOption(_("Private")); + } +}; + +MODULE_INIT(CSList) diff --git a/modules/commands/cs_log.cpp b/modules/commands/cs_log.cpp new file mode 100644 index 0000000..4867244 --- /dev/null +++ b/modules/commands/cs_log.cpp @@ -0,0 +1,399 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/cs_log.h" + +struct LogSettingImpl : LogSetting, Serializable +{ + LogSettingImpl() : Serializable("LogSetting") + { + } + + ~LogSettingImpl() + { + ChannelInfo *ci = ChannelInfo::Find(chan); + if (ci) + { + LogSettings *ls = ci->GetExt("logsettings"); + if (ls) + { + LogSettings::iterator it = std::find((*ls)->begin(), (*ls)->end(), this); + if (it != (*ls)->end()) + (*ls)->erase(it); + } + } + } + + void Serialize(Serialize::Data &data) const anope_override + { + data["ci"] << chan; + data["service_name"] << service_name; + data["command_service"] << command_service; + data["command_name"] << command_name; + data["method"] << method; + data["extra"] << extra; + data["creator"] << creator; + data.SetType("created", Serialize::Data::DT_INT); data["created"] << created; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data) + { + Anope::string sci; + data["ci"] >> sci; + + ChannelInfo *ci = ChannelInfo::Find(sci); + if (ci == NULL) + return NULL; + + LogSettingImpl *ls; + if (obj) + ls = anope_dynamic_static_cast(obj); + else + { + LogSettings *lsettings = ci->Require("logsettings"); + ls = new LogSettingImpl(); + (*lsettings)->push_back(ls); + } + + ls->chan = ci->name; + data["service_name"] >> ls->service_name; + data["command_service"] >> ls->command_service; + data["command_name"] >> ls->command_name; + data["method"] >> ls->method; + data["extra"] >> ls->extra; + data["creator"] >> ls->creator; + data["created"] >> ls->created; + + return ls; + } +}; + +struct LogSettingsImpl : LogSettings +{ + LogSettingsImpl(Extensible *) { } + + ~LogSettingsImpl() + { + for (iterator it = (*this)->begin(); it != (*this)->end();) + { + LogSetting *ls = *it; + ++it; + delete ls; + } + } + + LogSetting *Create() anope_override + { + return new LogSettingImpl(); + } +}; + +class CommandCSLog : public Command +{ +public: + CommandCSLog(Module *creator) : Command(creator, "chanserv/log", 1, 4) + { + this->SetDesc(_("Configures channel logging settings")); + this->SetSyntax(_("\037channel\037")); + this->SetSyntax(_("\037channel\037 \037command\037 \037method\037 [\037status\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &channel = params[0]; + + ChannelInfo *ci = ChannelInfo::Find(channel); + if (ci == NULL) + source.Reply(CHAN_X_NOT_REGISTERED, channel.c_str()); + else if (!source.AccessFor(ci).HasPriv("SET") && !source.HasPriv("chanserv/administration")) + source.Reply(ACCESS_DENIED); + else if (params.size() == 1) + { + LogSettings *ls = ci->Require("logsettings"); + if (!ls || (*ls)->empty()) + source.Reply(_("There currently are no logging configurations for %s."), ci->name.c_str()); + else + { + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Service")).AddColumn(_("Command")).AddColumn(_("Method")).AddColumn(""); + + for (unsigned i = 0; i < (*ls)->size(); ++i) + { + const LogSetting *log = (*ls)->at(i); + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(i + 1); + entry["Service"] = log->command_service; + entry["Command"] = !log->command_name.empty() ? log->command_name : log->service_name; + entry["Method"] = log->method; + entry[""] = log->extra; + list.AddEntry(entry); + } + + source.Reply(_("Log list for %s:"), ci->name.c_str()); + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + } + else if (params.size() > 2) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + LogSettings *ls = ci->Require("logsettings"); + const Anope::string &command = params[1]; + const Anope::string &method = params[2]; + const Anope::string &extra = params.size() > 3 ? params[3] : ""; + + size_t sl = command.find('/'); + if (sl == Anope::string::npos) + { + source.Reply(_("%s is not a valid command."), command.c_str()); + return; + } + + Anope::string service = command.substr(0, sl), + command_name = command.substr(sl + 1); + BotInfo *bi = BotInfo::Find(service, true); + + Anope::string service_name; + + /* Allow either a command name or a service name. */ + if (bi && bi->commands.count(command_name)) + { + /* Get service name from command */ + service_name = bi->commands[command_name].name; + } + else if (ServiceReference("Command", command.lower())) + { + /* This is the service name, don't use any specific command */ + service_name = command; + bi = NULL; + command_name.clear(); + } + else + { + source.Reply(_("%s is not a valid command."), command.c_str()); + return; + } + + if (!method.equals_ci("MESSAGE") && !method.equals_ci("NOTICE") && !method.equals_ci("MEMO")) + { + source.Reply(_("%s is not a valid logging method."), method.c_str()); + return; + } + + for (unsigned i = 0; i < extra.length(); ++i) + if (ModeManager::GetStatusChar(extra[i]) == 0) + { + source.Reply(_("%c is an unknown status mode."), extra[i]); + return; + } + + bool override = !source.AccessFor(ci).HasPriv("SET"); + + for (unsigned i = (*ls)->size(); i > 0; --i) + { + LogSetting *log = (*ls)->at(i - 1); + + if (log->service_name == service_name && log->method.equals_ci(method) && command_name.equals_ci(log->command_name)) + { + if (log->extra == extra) + { + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to remove logging for " << command << " with method " << method << (extra == "" ? "" : " ") << extra; + source.Reply(_("Logging for command %s on %s with log method %s%s%s has been removed."), !log->command_name.empty() ? log->command_name.c_str() : log->service_name.c_str(), !log->command_service.empty() ? log->command_service.c_str() : "any service", method.c_str(), extra.empty() ? "" : " ", extra.empty() ? "" : extra.c_str()); + delete log; + } + else + { + log->extra = extra; + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to change logging for " << command << " to method " << method << (extra == "" ? "" : " ") << extra; + source.Reply(_("Logging changed for command %s on %s, now using log method %s%s%s."), !log->command_name.empty() ? log->command_name.c_str() : log->service_name.c_str(), !log->command_service.empty() ? log->command_service.c_str() : "any service", method.c_str(), extra.empty() ? "" : " ", extra.empty() ? "" : extra.c_str()); + } + return; + } + } + + LogSetting *log = new LogSettingImpl(); + log->chan = ci->name; + log->service_name = service_name; + if (bi) + log->command_service = bi->nick; + log->command_name = command_name; + log->method = method; + log->extra = extra; + log->created = Anope::CurTime; + log->creator = source.GetNick(); + + (*ls)->push_back(log); + + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to log " << command << " with method " << method << (extra == "" ? "" : " ") << extra; + + source.Reply(_("Logging is now active for command %s on %s, using log method %s%s%s."), !command_name.empty() ? command_name.c_str() : service_name.c_str(), bi ? bi->nick.c_str() : "any service", method.c_str(), extra.empty() ? "" : " ", extra.empty() ? "" : extra.c_str()); + } + else + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("The %s command allows users to configure logging settings\n" + "for their channel. If no parameters are given this command\n" + "lists the current logging methods in place for this channel.\n" + " \n" + "Otherwise, \037command\037 must be a command name, and \037method\037\n" + "is one of the following logging methods:\n" + " \n" + " MESSAGE [status], NOTICE [status], MEMO\n" + " \n" + "Which are used to message, notice, and memo the channel respectively.\n" + "With MESSAGE or NOTICE you must have a service bot assigned to and joined\n" + "to your channel. Status may be a channel status such as @ or +.\n" + " \n" + "To remove a logging method use the same syntax as you would to add it.\n" + " \n" + "Example:\n" + " %s #anope chanserv/access MESSAGE @\n" + " Would message any channel operators whenever someone used the\n" + " ACCESS command on ChanServ on the channel."), + source.command.upper().c_str(), source.command.upper().c_str()); + return true; + } +}; + +class CSLog : public Module +{ + ServiceReference MSService; + CommandCSLog commandcslog; + ExtensibleItem logsettings; + Serialize::Type logsetting_type; + + struct LogDefault + { + Anope::string service, command, method; + }; + + std::vector defaults; + + public: + CSLog(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + MSService("MemoServService", "MemoServ"), commandcslog(this), + logsettings(this, "logsettings"), logsetting_type("LogSetting", LogSettingImpl::Unserialize) + { + + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *block = conf->GetModule(this); + defaults.clear(); + + for (int i = 0; i < block->CountBlock("default"); ++i) + { + Configuration::Block *def = block->GetBlock("default", i); + + LogDefault ld; + + ld.service = def->Get("service"); + ld.command = def->Get("command"); + ld.method = def->Get("method"); + + defaults.push_back(ld); + } + } + + void OnChanRegistered(ChannelInfo *ci) anope_override + { + if (defaults.empty()) + return; + + LogSettings *ls = logsettings.Require(ci); + for (unsigned i = 0; i < defaults.size(); ++i) + { + LogDefault &d = defaults[i]; + + LogSetting *log = new LogSettingImpl(); + log->chan = ci->name; + + if (!d.service.empty()) + { + log->service_name = d.service.lower() + "/" + d.command.lower(); + log->command_service = d.service; + log->command_name = d.command; + } + else + log->service_name = d.command; + + spacesepstream sep(d.method); + sep.GetToken(log->method); + log->extra = sep.GetRemaining(); + + log->created = Anope::CurTime; + log->creator = ci->GetFounder() ? ci->GetFounder()->display : "(default)"; + + (*ls)->push_back(log); + } + } + + void OnLog(Log *l) anope_override + { + if (l->type != LOG_COMMAND || l->u == NULL || l->c == NULL || l->ci == NULL || !Me || !Me->IsSynced()) + return; + + LogSettings *ls = logsettings.Get(l->ci); + if (ls) + for (unsigned i = 0; i < (*ls)->size(); ++i) + { + const LogSetting *log = (*ls)->at(i); + + /* wrong command */ + if (log->service_name != l->c->name) + continue; + + /* if a command name is given check the service and the command */ + if (!log->command_name.empty()) + { + /* wrong service (only check if not a fantasy command, though) */ + if (!l->source->c && log->command_service != l->source->service->nick) + continue; + + if (!log->command_name.equals_ci(l->source->command)) + continue; + } + + Anope::string buffer = l->u->nick + " used " + l->source->command.upper() + " " + l->buf.str(); + + if (log->method.equals_ci("MEMO") && MSService && l->ci->WhoSends() != NULL) + MSService->Send(l->ci->WhoSends()->nick, l->ci->name, buffer, true); + else if (l->source->c) + /* Sending a channel message or notice in response to a fantasy command */; + else if (log->method.equals_ci("MESSAGE") && l->ci->c) + { + IRCD->SendPrivmsg(l->ci->WhoSends(), log->extra + l->ci->c->name, "%s", buffer.c_str()); + l->ci->WhoSends()->lastmsg = Anope::CurTime; + } + else if (log->method.equals_ci("NOTICE") && l->ci->c) + IRCD->SendNotice(l->ci->WhoSends(), log->extra + l->ci->c->name, "%s", buffer.c_str()); + } + } +}; + +MODULE_INIT(CSLog) diff --git a/modules/commands/cs_mode.cpp b/modules/commands/cs_mode.cpp new file mode 100644 index 0000000..7872f72 --- /dev/null +++ b/modules/commands/cs_mode.cpp @@ -0,0 +1,1069 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/cs_mode.h" + +struct ModeLockImpl : ModeLock, Serializable +{ + ModeLockImpl() : Serializable("ModeLock") + { + } + + ~ModeLockImpl() + { + ChannelInfo *chan = ChannelInfo::Find(ci); + if (chan) + { + ModeLocks *ml = chan->GetExt("modelocks"); + if (ml) + ml->RemoveMLock(this); + } + } + + void Serialize(Serialize::Data &data) const anope_override; + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data); +}; + +struct ModeLocksImpl : ModeLocks +{ + Serialize::Reference ci; + Serialize::Checker mlocks; + + ModeLocksImpl(Extensible *obj) : ci(anope_dynamic_static_cast(obj)), mlocks("ModeLock") + { + } + + ~ModeLocksImpl() + { + ModeList modelist; + mlocks->swap(modelist); + for (ModeList::iterator it = modelist.begin(); it != modelist.end(); ++it) + { + ModeLock *ml = *it; + delete ml; + } + } + + bool HasMLock(ChannelMode *mode, const Anope::string ¶m, bool status) const anope_override + { + if (!mode) + return false; + + for (ModeList::const_iterator it = this->mlocks->begin(); it != this->mlocks->end(); ++it) + { + const ModeLock *ml = *it; + + if (ml->name == mode->name && ml->set == status && ml->param == param) + return true; + } + + return false; + } + + bool SetMLock(ChannelMode *mode, bool status, const Anope::string ¶m, Anope::string setter, time_t created = Anope::CurTime) anope_override + { + if (!mode) + return false; + + RemoveMLock(mode, status, param); + + if (setter.empty()) + setter = ci->GetFounder() ? ci->GetFounder()->display : "Unknown"; + + ModeLock *ml = new ModeLockImpl(); + ml->ci = ci->name; + ml->set = status; + ml->name = mode->name; + ml->param = param; + ml->setter = setter; + ml->created = created; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnMLock, MOD_RESULT, (this->ci, ml)); + if (MOD_RESULT == EVENT_STOP) + { + delete ml; + return false; + } + + this->mlocks->push_back(ml); + return true; + } + + bool RemoveMLock(ChannelMode *mode, bool status, const Anope::string ¶m = "") anope_override + { + if (!mode) + return false; + + for (ModeList::iterator it = this->mlocks->begin(); it != this->mlocks->end(); ++it) + { + ModeLock *m = *it; + + if (m->name == mode->name) + { + // For list or status modes, we must check the parameter + if (mode->type == MODE_LIST || mode->type == MODE_STATUS) + if (m->param != param) + continue; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnUnMLock, MOD_RESULT, (this->ci, m)); + if (MOD_RESULT == EVENT_STOP) + break; + + delete m; + return true; + } + } + + return false; + } + + void RemoveMLock(ModeLock *mlock) anope_override + { + ModeList::iterator it = std::find(this->mlocks->begin(), this->mlocks->end(), mlock); + if (it != this->mlocks->end()) + this->mlocks->erase(it); + } + + void ClearMLock() anope_override + { + ModeList ml; + this->mlocks->swap(ml); + for (unsigned i = 0; i < ml.size(); ++i) + delete ml[i]; + } + + const ModeList &GetMLock() const anope_override + { + return this->mlocks; + } + + std::list GetModeLockList(const Anope::string &name) anope_override + { + std::list mlist; + for (ModeList::const_iterator it = this->mlocks->begin(); it != this->mlocks->end(); ++it) + { + ModeLock *m = *it; + if (m->name == name) + mlist.push_back(m); + } + return mlist; + } + + const ModeLock *GetMLock(const Anope::string &mname, const Anope::string ¶m = "") anope_override + { + for (ModeList::const_iterator it = this->mlocks->begin(); it != this->mlocks->end(); ++it) + { + ModeLock *m = *it; + + if (m->name == mname && m->param == param) + return m; + } + + return NULL; + } + + Anope::string GetMLockAsString(bool complete) const anope_override + { + Anope::string pos = "+", neg = "-", params; + + for (ModeList::const_iterator it = this->mlocks->begin(); it != this->mlocks->end(); ++it) + { + const ModeLock *ml = *it; + ChannelMode *cm = ModeManager::FindChannelModeByName(ml->name); + + if (!cm || cm->type == MODE_LIST || cm->type == MODE_STATUS) + continue; + + if (ml->set) + pos += cm->mchar; + else + neg += cm->mchar; + + if (complete && ml->set && !ml->param.empty() && cm->type == MODE_PARAM) + params += " " + ml->param; + } + + if (pos.length() == 1) + pos.clear(); + if (neg.length() == 1) + neg.clear(); + + return pos + neg + params; + } + + void Check() anope_override + { + if (this->mlocks->empty()) + ci->Shrink("modelocks"); + } +}; + +void ModeLockImpl::Serialize(Serialize::Data &data) const +{ + data["ci"] << this->ci; + data["set"] << this->set; + data["name"] << this->name; + data["param"] << this->param; + data["setter"] << this->setter; + data.SetType("created", Serialize::Data::DT_INT); data["created"] << this->created; +} + +Serializable* ModeLockImpl::Unserialize(Serializable *obj, Serialize::Data &data) +{ + Anope::string sci; + + data["ci"] >> sci; + + ChannelInfo *ci = ChannelInfo::Find(sci); + if (!ci) + return NULL; + + ModeLockImpl *ml; + if (obj) + ml = anope_dynamic_static_cast(obj); + else + { + ml = new ModeLockImpl(); + ml->ci = ci->name; + } + + data["set"] >> ml->set; + data["created"] >> ml->created; + data["setter"] >> ml->setter; + data["name"] >> ml->name; + data["param"] >> ml->param; + + if (!obj) + ci->Require("modelocks")->mlocks->push_back(ml); + + return ml; +} + +class CommandCSMode : public Command +{ + bool CanSet(CommandSource &source, ChannelInfo *ci, ChannelMode *cm, bool self) + { + if (!ci || !cm || cm->type != MODE_STATUS) + return false; + + return source.AccessFor(ci).HasPriv(cm->name + (self ? "ME" : "")); + } + + void DoLock(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + User *u = source.GetUser(); + const Anope::string &subcommand = params[2]; + const Anope::string ¶m = params.size() > 3 ? params[3] : ""; + + bool override = !source.AccessFor(ci).HasPriv("MODE"); + ModeLocks *modelocks = ci->Require("modelocks"); + + if (Anope::ReadOnly && !subcommand.equals_ci("LIST")) + { + source.Reply(READ_ONLY_MODE); + return; + } + + if ((subcommand.equals_ci("ADD") || subcommand.equals_ci("SET")) && !param.empty()) + { + /* If setting, remove the existing locks */ + if (subcommand.equals_ci("SET")) + { + const ModeLocks::ModeList mlocks = modelocks->GetMLock(); + for (ModeLocks::ModeList::const_iterator it = mlocks.begin(); it != mlocks.end(); ++it) + { + const ModeLock *ml = *it; + ChannelMode *cm = ModeManager::FindChannelModeByName(ml->name); + if (cm && cm->CanSet(source.GetUser())) + modelocks->RemoveMLock(cm, ml->set, ml->param); + } + } + + spacesepstream sep(param); + Anope::string modes; + + sep.GetToken(modes); + + Anope::string pos = "+", neg = "-", pos_params, neg_params; + + int adding = 1; + bool needreply = true; + for (size_t i = 0; i < modes.length(); ++i) + { + switch (modes[i]) + { + case '+': + adding = 1; + break; + case '-': + adding = 0; + break; + default: + needreply = false; + ChannelMode *cm = ModeManager::FindChannelModeByChar(modes[i]); + if (!cm) + { + source.Reply(_("Unknown mode character %c ignored."), modes[i]); + break; + } + else if (u && !cm->CanSet(u)) + { + source.Reply(_("You may not (un)lock mode %c."), modes[i]); + break; + } + + Anope::string mode_param; + if (((cm->type == MODE_STATUS || cm->type == MODE_LIST) && !sep.GetToken(mode_param)) || (cm->type == MODE_PARAM && adding && !sep.GetToken(mode_param))) + { + source.Reply(_("Missing parameter for mode %c."), cm->mchar); + continue; + } + + if (cm->type == MODE_STATUS && !CanSet(source, ci, cm, false)) + { + source.Reply(ACCESS_DENIED); + continue; + } + + if (cm->type == MODE_LIST && ci->c && IRCD->GetMaxListFor(ci->c, cm) && ci->c->HasMode(cm->name) >= IRCD->GetMaxListFor(ci->c, cm)) + { + source.Reply(_("List for mode %c is full."), cm->mchar); + continue; + } + + if (modelocks->GetMLock().size() >= Config->GetModule(this->owner)->Get("max", "32")) + { + source.Reply(_("The mode lock list of \002%s\002 is full."), ci->name.c_str()); + continue; + } + + modelocks->SetMLock(cm, adding, mode_param, source.GetNick()); + + if (adding) + { + pos += cm->mchar; + if (!mode_param.empty()) + pos_params += " " + mode_param; + } + else + { + neg += cm->mchar; + if (!mode_param.empty()) + neg_params += " " + mode_param; + } + } + } + + if (pos == "+") + pos.clear(); + if (neg == "-") + neg.clear(); + Anope::string reply = pos + neg + pos_params + neg_params; + + if (!reply.empty()) + { + source.Reply(_("%s locked on %s."), reply.c_str(), ci->name.c_str()); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to lock " << reply; + } + else if (needreply) + source.Reply(_("Nothing to do.")); + + if (ci->c) + ci->c->CheckModes(); + } + else if (subcommand.equals_ci("DEL") && !param.empty()) + { + spacesepstream sep(param); + Anope::string modes; + + sep.GetToken(modes); + + int adding = 1; + bool needreply = true; + for (size_t i = 0; i < modes.length(); ++i) + { + switch (modes[i]) + { + case '+': + adding = 1; + break; + case '-': + adding = 0; + break; + default: + needreply = false; + ChannelMode *cm = ModeManager::FindChannelModeByChar(modes[i]); + if (!cm) + { + source.Reply(_("Unknown mode character %c ignored."), modes[i]); + break; + } + else if (u && !cm->CanSet(u)) + { + source.Reply(_("You may not (un)lock mode %c."), modes[i]); + break; + } + + Anope::string mode_param; + if (cm->type != MODE_REGULAR && !sep.GetToken(mode_param)) + source.Reply(_("Missing parameter for mode %c."), cm->mchar); + else + { + if (modelocks->RemoveMLock(cm, adding, mode_param)) + { + if (!mode_param.empty()) + mode_param = " " + mode_param; + source.Reply(_("%c%c%s has been unlocked from %s."), adding == 1 ? '+' : '-', cm->mchar, mode_param.c_str(), ci->name.c_str()); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to unlock " << (adding ? '+' : '-') << cm->mchar << mode_param; + } + else + source.Reply(_("%c%c is not locked on %s."), adding == 1 ? '+' : '-', cm->mchar, ci->name.c_str()); + } + } + } + + if (needreply) + source.Reply(_("Nothing to do.")); + } + else if (subcommand.equals_ci("LIST")) + { + const ModeLocks::ModeList mlocks = modelocks->GetMLock(); + if (mlocks.empty()) + { + source.Reply(_("Channel %s has no mode locks."), ci->name.c_str()); + } + else + { + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Mode")).AddColumn(_("Param")).AddColumn(_("Creator")).AddColumn(_("Created")); + + for (ModeLocks::ModeList::const_iterator it = mlocks.begin(), it_end = mlocks.end(); it != it_end; ++it) + { + const ModeLock *ml = *it; + ChannelMode *cm = ModeManager::FindChannelModeByName(ml->name); + if (!cm) + continue; + + ListFormatter::ListEntry entry; + entry["Mode"] = Anope::printf("%c%c", ml->set ? '+' : '-', cm->mchar); + entry["Param"] = ml->param; + entry["Creator"] = ml->setter; + entry["Created"] = Anope::strftime(ml->created, NULL, true); + list.AddEntry(entry); + } + + source.Reply(_("Mode locks for %s:"), ci->name.c_str()); + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + } + else + this->OnSyntaxError(source, subcommand); + } + + void DoSet(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + User *u = source.GetUser(); + + bool has_access = source.AccessFor(ci).HasPriv("MODE") || source.HasPriv("chanserv/administration"); + bool can_override = source.HasPriv("chanserv/administration"); + + spacesepstream sep(params.size() > 3 ? params[3] : ""); + Anope::string modes = params[2], param; + + bool override = !source.AccessFor(ci).HasPriv("MODE") && source.HasPriv("chanserv/administration"); + + int adding = -1; + for (size_t i = 0; i < modes.length(); ++i) + { + switch (modes[i]) + { + case '+': + adding = 1; + break; + case '-': + adding = 0; + break; + case '*': + if (adding == -1 || !has_access) + break; + for (unsigned j = 0; j < ModeManager::GetChannelModes().size() && ci->c; ++j) + { + ChannelMode *cm = ModeManager::GetChannelModes()[j]; + + if (!u || cm->CanSet(u) || can_override) + { + if (cm->type == MODE_REGULAR || (!adding && cm->type == MODE_PARAM)) + { + if (adding) + ci->c->SetMode(NULL, cm); + else + ci->c->RemoveMode(NULL, cm); + } + } + } + break; + default: + if (adding == -1) + break; + ChannelMode *cm = ModeManager::FindChannelModeByChar(modes[i]); + if (!cm || (u && !cm->CanSet(u) && !can_override)) + continue; + switch (cm->type) + { + case MODE_REGULAR: + if (!has_access) + break; + if (adding) + ci->c->SetMode(NULL, cm); + else + ci->c->RemoveMode(NULL, cm); + break; + case MODE_PARAM: + if (!has_access) + break; + if (adding && !sep.GetToken(param)) + break; + if (adding) + ci->c->SetMode(NULL, cm, param); + else + ci->c->RemoveMode(NULL, cm); + break; + case MODE_STATUS: + { + if (!sep.GetToken(param)) + param = source.GetNick(); + + AccessGroup u_access = source.AccessFor(ci); + + if (param.find_first_of("*?") != Anope::string::npos) + { + if (!this->CanSet(source, ci, cm, false)) + { + if (can_override) + { + override = true; + } + else + { + source.Reply(_("You do not have access to set mode %c."), cm->mchar); + break; + } + } + + for (Channel::ChanUserList::const_iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end;) + { + ChanUserContainer *uc = it->second; + ++it; + + AccessGroup targ_access = ci->AccessFor(uc->user); + + if (uc->user->IsProtected()) + { + source.Reply(_("You do not have the access to change %s's modes."), uc->user->nick.c_str()); + continue; + } + + if (ci->HasExt("PEACE") && targ_access >= u_access) + { + if (can_override) + { + override = true; + } + else + { + source.Reply(_("You do not have the access to change %s's modes."), uc->user->nick.c_str()); + continue; + } + } + + if (Anope::Match(uc->user->GetMask(), param)) + { + if (adding) + ci->c->SetMode(NULL, cm, uc->user->GetUID()); + else + ci->c->RemoveMode(NULL, cm, uc->user->GetUID()); + } + } + } + else + { + User *target = User::Find(param, true); + if (target == NULL) + { + source.Reply(NICK_X_NOT_IN_USE, param.c_str()); + break; + } + + if (!this->CanSet(source, ci, cm, source.GetUser() == target)) + { + if (can_override) + { + override = true; + } + else + { + source.Reply(_("You do not have access to set mode %c."), cm->mchar); + break; + } + } + + if (source.GetUser() != target) + { + AccessGroup targ_access = ci->AccessFor(target); + if (ci->HasExt("PEACE") && targ_access >= u_access) + { + source.Reply(_("You do not have the access to change %s's modes."), target->nick.c_str()); + break; + } + else if (can_override) + { + override = true; + } + else if (target->IsProtected()) + { + source.Reply(ACCESS_DENIED); + break; + } + } + + if (adding) + ci->c->SetMode(NULL, cm, target->GetUID()); + else + ci->c->RemoveMode(NULL, cm, target->GetUID()); + } + break; + } + case MODE_LIST: + if (!has_access) + break; + if (!sep.GetToken(param)) + break; + + // Change to internal name, eg giving -b ~q:* + cm = cm->Unwrap(param); + + if (adding) + { + if (IRCD->GetMaxListFor(ci->c, cm) && ci->c->HasMode(cm->name) < IRCD->GetMaxListFor(ci->c, cm)) + ci->c->SetMode(NULL, cm, param); + } + else + { + std::vector v = ci->c->GetModeList(cm->name); + for (unsigned j = 0; j < v.size(); ++j) + if (Anope::Match(v[j], param)) + ci->c->RemoveMode(NULL, cm, v[j]); + } + } + } // switch + } + + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to set " << modes << (params.size() > 3 ? " " + params[3] : ""); + } + + void DoClear(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + const Anope::string ¶m = params.size() > 2 ? params[2] : ""; + + if (param.empty()) + { + std::vector new_params; + new_params.push_back(params[0]); + new_params.push_back("SET"); + new_params.push_back("-*"); + this->DoSet(source, ci, new_params); + return; + } + + ChannelMode *cm; + if (param.length() == 1) + cm = ModeManager::FindChannelModeByChar(param[0]); + else + { + cm = ModeManager::FindChannelModeByName(param.upper()); + if (!cm) + cm = ModeManager::FindChannelModeByName(param.substr(0, param.length() - 1).upper()); + } + + if (!cm) + { + source.Reply(_("There is no such mode %s."), param.c_str()); + return; + } + + if (cm->type != MODE_STATUS && cm->type != MODE_LIST) + { + source.Reply(_("Mode %s is not a status or list mode."), param.c_str()); + return; + } + + if (!cm->mchar) + { + source.Reply(_("Mode %s is a virtual mode and can't be cleared."), cm->name.c_str()); + return; + } + + std::vector new_params; + new_params.push_back(params[0]); + new_params.push_back("SET"); + new_params.push_back("-" + stringify(cm->mchar)); + new_params.push_back("*"); + this->DoSet(source, ci, new_params); + } + + public: + CommandCSMode(Module *creator) : Command(creator, "chanserv/mode", 2, 4) + { + this->SetDesc(_("Control modes and mode locks on a channel")); + this->SetSyntax(_("\037channel\037 LOCK {ADD|DEL|SET|LIST} [\037what\037]")); + this->SetSyntax(_("\037channel\037 SET \037modes\037")); + this->SetSyntax(_("\037channel\037 CLEAR [\037what\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &subcommand = params[1]; + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + + if (!ci) + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + else if (subcommand.equals_ci("LOCK") && params.size() > 2) + { + if (!source.AccessFor(ci).HasPriv("MODE") && !source.HasPriv("chanserv/administration")) + source.Reply(ACCESS_DENIED); + else + this->DoLock(source, ci, params); + } + else if (!ci->c) + source.Reply(CHAN_X_NOT_IN_USE, params[0].c_str()); + else if (subcommand.equals_ci("SET") && params.size() > 2) + this->DoSet(source, ci, params); + else if (subcommand.equals_ci("CLEAR")) + { + if (!source.AccessFor(ci).HasPriv("MODE") && !source.HasPriv("chanserv/administration")) + source.Reply(ACCESS_DENIED); + else + this->DoClear(source, ci, params); + } + else + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Mainly controls mode locks and mode access (which is different from channel access)\n" + "on a channel.\n" + " \n" + "The \002%s LOCK\002 command allows you to add, delete, and view mode locks on a channel.\n" + "If a mode is locked on or off, services will not allow that mode to be changed. The \002SET\002\n" + "command will clear all existing mode locks and set the new one given, while \002ADD\002 and \002DEL\002\n" + "modify the existing mode lock.\n" + "Example:\n" + " \002MODE #channel LOCK ADD +bmnt *!*@*aol*\002\n" + " \n" + "The \002%s SET\002 command allows you to set modes through services. Wildcards * and ? may\n" + "be given as parameters for list and status modes.\n" + "Example:\n" + " \002MODE #channel SET +v *\002\n" + " Sets voice status to all users in the channel.\n" + " \n" + " \002MODE #channel SET -b ~c:*\n" + " Clears all extended bans that start with ~c:\n" + " \n" + "The \002%s CLEAR\002 command is an easy way to clear modes on a channel. \037what\037 may be\n" + "any mode name. Examples include bans, excepts, inviteoverrides, ops, halfops, and voices. If \037what\037\n" + "is not given then all basic modes are removed."), + source.command.upper().c_str(), source.command.upper().c_str(), source.command.upper().c_str()); + return true; + } +}; + +static Anope::map > modes; + +class CommandCSModes : public Command +{ + public: + CommandCSModes(Module *creator) : Command(creator, "chanserv/modes", 1, 2) + { + this->SetSyntax(_("\037channel\037 [\037user\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(), + *targ = params.size() > 1 ? User::Find(params[1], true) : u; + ChannelInfo *ci = ChannelInfo::Find(params[0]); + + if (!targ) + { + if (params.size() > 1) + source.Reply(NICK_X_NOT_IN_USE, params[1].c_str()); + return; + } + + if (!ci) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + else if (!ci->c) + { + source.Reply(CHAN_X_NOT_IN_USE, ci->name.c_str()); + return; + } + + AccessGroup u_access = source.AccessFor(ci), targ_access = ci->AccessFor(targ); + const std::pair &m = modes[source.command]; + + bool can_override = source.HasPriv("chanserv/administration"); + bool override = false; + + if (m.second.empty()) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (u == targ ? !u_access.HasPriv(m.second + "ME") : !u_access.HasPriv(m.second)) + { + if (!can_override) + { + source.Reply(ACCESS_DENIED); + return; + } + else + override = true; + } + + if (!override && !m.first && u != targ && (targ->IsProtected() || (ci->HasExt("PEACE") && targ_access >= u_access))) + { + if (!can_override) + { + source.Reply(ACCESS_DENIED); + return; + } + else + override = true; + } + + if (!ci->c->FindUser(targ)) + { + source.Reply(NICK_X_NOT_ON_CHAN, targ->nick.c_str(), ci->name.c_str()); + return; + } + + if (m.first) + ci->c->SetMode(NULL, m.second, targ->GetUID()); + else + ci->c->RemoveMode(NULL, m.second, targ->GetUID()); + + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "on " << targ->nick; + } + + const Anope::string GetDesc(CommandSource &source) const anope_override + { + const std::pair &m = modes[source.command]; + if (!m.second.empty()) + { + if (m.first) + return Anope::printf(Language::Translate(source.GetAccount(), _("Gives you or the specified nick %s status on a channel")), m.second.c_str()); + else + return Anope::printf(Language::Translate(source.GetAccount(), _("Removes %s status from you or the specified nick on a channel")), m.second.c_str()); + } + else + return ""; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + const std::pair &m = modes[source.command]; + if (m.second.empty()) + return false; + + this->SendSyntax(source); + source.Reply(" "); + if (m.first) + source.Reply(_("Gives %s status to the selected nick on a channel. If \037nick\037 is\n" + "not given, it will %s you."), + m.second.upper().c_str(), m.second.lower().c_str()); + else + source.Reply(_("Removes %s status from the selected nick on a channel. If \037nick\037 is\n" + "not given, it will de%s you."), + m.second.upper().c_str(), m.second.lower().c_str()); + source.Reply(" "); + source.Reply(_("You must have the %s(ME) privilege on the channel to use this command."), m.second.upper().c_str()); + + return true; + } +}; + +class CSMode : public Module +{ + CommandCSMode commandcsmode; + CommandCSModes commandcsmodes; + ExtensibleItem modelocks; + Serialize::Type modelocks_type; + + public: + CSMode(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcsmode(this), commandcsmodes(this), + modelocks(this, "modelocks"), + modelocks_type("ModeLock", ModeLockImpl::Unserialize) + { + + } + + void OnReload(Configuration::Conf *conf) anope_override + { + modes.clear(); + + for (int i = 0; i < conf->CountBlock("command"); ++i) + { + Configuration::Block *block = conf->GetBlock("command", i); + + const Anope::string &cname = block->Get("name"), + &cmd = block->Get("command"); + + if (cname.empty() || cmd != "chanserv/modes") + continue; + + const Anope::string &set = block->Get("set"), + &unset = block->Get("unset"); + + if (set.empty() && unset.empty()) + continue; + + modes[cname] = std::make_pair(!set.empty(), !set.empty() ? set : unset); + } + } + + void OnCheckModes(Reference &c) anope_override + { + if (!c || !c->ci) + return; + + ModeLocks *locks = modelocks.Get(c->ci); + if (locks) + for (ModeLocks::ModeList::const_iterator it = locks->GetMLock().begin(), it_end = locks->GetMLock().end(); it != it_end; ++it) + { + const ModeLock *ml = *it; + ChannelMode *cm = ModeManager::FindChannelModeByName(ml->name); + if (!cm) + continue; + + if (cm->type == MODE_REGULAR) + { + if (!c->HasMode(cm->name) && ml->set) + c->SetMode(NULL, cm, "", false); + else if (c->HasMode(cm->name) && !ml->set) + c->RemoveMode(NULL, cm, "", false); + } + else if (cm->type == MODE_PARAM) + { + /* If the channel doesn't have the mode, or it does and it isn't set correctly */ + if (ml->set) + { + Anope::string param; + c->GetParam(cm->name, param); + + if (!c->HasMode(cm->name) || (!param.empty() && !ml->param.empty() && !param.equals_cs(ml->param))) + c->SetMode(NULL, cm, ml->param, false); + } + else + { + if (c->HasMode(cm->name)) + c->RemoveMode(NULL, cm, "", false); + } + + } + else if (cm->type == MODE_LIST || cm->type == MODE_STATUS) + { + if (ml->set) + c->SetMode(NULL, cm, ml->param, false); + else + c->RemoveMode(NULL, cm, ml->param, false); + } + } + } + + void OnChanRegistered(ChannelInfo *ci) anope_override + { + ModeLocks *ml = modelocks.Require(ci); + Anope::string mlock; + spacesepstream sep(Config->GetModule(this)->Get("mlock", "+nt")); + if (sep.GetToken(mlock)) + { + bool add = true; + for (unsigned i = 0; i < mlock.length(); ++i) + { + if (mlock[i] == '+') + { + add = true; + continue; + } + + if (mlock[i] == '-') + { + add = false; + continue; + } + + ChannelMode *cm = ModeManager::FindChannelModeByChar(mlock[i]); + if (!cm) + continue; + + Anope::string param; + if (cm->type == MODE_PARAM) + { + ChannelModeParam *cmp = anope_dynamic_static_cast(cm); + if (add || !cmp->minus_no_arg) + { + sep.GetToken(param); + if (param.empty() || !cmp->IsValid(param)) + continue; + } + } + else if (cm->type != MODE_REGULAR) + { + sep.GetToken(param); + if (param.empty()) + continue; + } + + ml->SetMLock(cm, add, param); + } + } + ml->Check(); + } + + void OnChanInfo(CommandSource &source, ChannelInfo *ci, InfoFormatter &info, bool show_hidden) anope_override + { + if (!show_hidden) + return; + + ModeLocks *ml = modelocks.Get(ci); + if (ml) + info[_("Mode lock")] = ml->GetMLockAsString(true); + } +}; + +MODULE_INIT(CSMode) diff --git a/modules/commands/cs_register.cpp b/modules/commands/cs_register.cpp new file mode 100644 index 0000000..9661907 --- /dev/null +++ b/modules/commands/cs_register.cpp @@ -0,0 +1,124 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandCSRegister : public Command +{ + public: + CommandCSRegister(Module *creator) : Command(creator, "chanserv/register", 1, 2) + { + this->SetDesc(_("Register a channel")); + this->SetSyntax(_("\037channel\037 [\037description\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &chan = params[0]; + const Anope::string &chdesc = params.size() > 1 ? params[1] : ""; + unsigned maxregistered = Config->GetModule("chanserv")->Get("maxregistered"); + + User *u = source.GetUser(); + NickCore *nc = source.nc; + Channel *c = Channel::Find(params[0]); + ChannelInfo *ci = ChannelInfo::Find(params[0]); + + if (Anope::ReadOnly) + source.Reply(_("Sorry, channel registration is temporarily disabled.")); + else if (nc->HasExt("UNCONFIRMED")) + source.Reply(_("You must confirm your account before you can register a channel.")); + else if (chan[0] == '&') + source.Reply(_("Local channels cannot be registered.")); + else if (chan[0] != '#') + source.Reply(CHAN_SYMBOL_REQUIRED); + else if (!IRCD->IsChannelValid(chan)) + source.Reply(CHAN_X_INVALID, chan.c_str()); + else if (!c && u) + source.Reply(CHAN_X_NOT_IN_USE, chan.c_str()); + else if (ci) + source.Reply(_("Channel \002%s\002 is already registered!"), chan.c_str()); + else if (c && u && !c->HasUserStatus(u, "OP")) + source.Reply(_("You must be a channel operator to register the channel.")); + else if (maxregistered && nc->channelcount >= maxregistered && !source.HasPriv("chanserv/no-register-limit")) + source.Reply(nc->channelcount > maxregistered ? CHAN_EXCEEDED_CHANNEL_LIMIT : CHAN_REACHED_CHANNEL_LIMIT, maxregistered); + else + { + ci = new ChannelInfo(chan); + ci->SetFounder(nc); + ci->desc = chdesc; + + if (c && !c->topic.empty()) + { + ci->last_topic = c->topic; + ci->last_topic_setter = c->topic_setter; + ci->last_topic_time = c->topic_time; + } + else + ci->last_topic_setter = source.service->nick; + + Log(LOG_COMMAND, source, this, ci); + source.Reply(_("Channel \002%s\002 registered under your account: %s"), chan.c_str(), nc->display.c_str()); + + FOREACH_MOD(OnChanRegistered, (ci)); + + /* Implement new mode lock */ + if (c) + { + c->CheckModes(); + if (u) + c->SetCorrectModes(u, true); + } + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Registers a channel in the %s database. In order\n" + "to use this command, you must first be a channel operator\n" + "on the channel you're trying to register.\n" + "The description, which is optional, is a\n" + "general description of the channel's purpose.\n" + " \n" + "When you register a channel, you are recorded as the\n" + "\"founder\" of the channel. The channel founder is allowed\n" + "to change all of the channel settings for the channel;\n" + "%s will also automatically give the founder\n" + "channel-operator privileges when s/he enters the channel."), + source.service->nick.c_str(), source.service->nick.c_str()); + BotInfo *bi; + Anope::string cmd; + if (Command::FindCommandFromService("chanserv/access", bi, cmd)) + source.Reply(_(" \n" + "See the \002%s\002 command (\002%s%s HELP ACCESS\002) for\n" + "information on giving a subset of these privileges to\n" + "other channel users.\n"), cmd.c_str(), Config->StrictPrivmsg.c_str(), bi->nick.c_str()); + source.Reply(_(" \n" + "NOTICE: In order to register a channel, you must have\n" + "first registered your nickname.")); + return true; + } +}; + + +class CSRegister : public Module +{ + CommandCSRegister commandcsregister; + + public: + CSRegister(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcsregister(this) + { + } +}; + +MODULE_INIT(CSRegister) diff --git a/modules/commands/cs_seen.cpp b/modules/commands/cs_seen.cpp new file mode 100644 index 0000000..6206a6a --- /dev/null +++ b/modules/commands/cs_seen.cpp @@ -0,0 +1,460 @@ +/* cs_seen: provides a seen command by tracking all users + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +enum TypeInfo +{ + NEW, NICK_TO, NICK_FROM, JOIN, PART, QUIT, KICK +}; + +static bool simple; +struct SeenInfo; +static SeenInfo *FindInfo(const Anope::string &nick); +typedef Anope::hash_map database_map; +database_map database; + +struct SeenInfo : Serializable +{ + Anope::string nick; + Anope::string vhost; + TypeInfo type; + Anope::string nick2; // for nickchanges and kicks + Anope::string channel; // for join/part/kick + Anope::string message; // for part/kick/quit + time_t last; // the time when the user was last seen + + SeenInfo() : Serializable("SeenInfo") + { + } + + ~SeenInfo() + { + database_map::iterator iter = database.find(nick); + if (iter != database.end() && iter->second == this) + database.erase(iter); + } + + void Serialize(Serialize::Data &data) const anope_override + { + data["nick"] << nick; + data["vhost"] << vhost; + data["type"] << type; + data["nick2"] << nick2; + data["channel"] << channel; + data["message"] << message; + data.SetType("last", Serialize::Data::DT_INT); data["last"] << last; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data) + { + Anope::string snick; + + data["nick"] >> snick; + + SeenInfo *s; + if (obj) + s = anope_dynamic_static_cast(obj); + else + { + SeenInfo* &info = database[snick]; + if (!info) + info = new SeenInfo(); + s = info; + } + + s->nick = snick; + data["vhost"] >> s->vhost; + unsigned int n; + data["type"] >> n; + s->type = static_cast(n); + data["nick2"] >> s->nick2; + data["channel"] >> s->channel; + data["message"] >> s->message; + data["last"] >> s->last; + + if (!obj) + database[s->nick] = s; + return s; + } +}; + +static SeenInfo *FindInfo(const Anope::string &nick) +{ + database_map::iterator iter = database.find(nick); + if (iter != database.end()) + return iter->second; + return NULL; +} + +static bool ShouldHide(const Anope::string &channel, User *u) +{ + Channel *targetchan = Channel::Find(channel); + const ChannelInfo *targetchan_ci = targetchan ? *targetchan->ci : ChannelInfo::Find(channel); + + if (targetchan && targetchan->HasMode("SECRET")) + return true; + else if (targetchan_ci && targetchan_ci->HasExt("CS_PRIVATE")) + return true; + else if (u && u->HasMode("PRIV")) + return true; + return false; +} + +class CommandOSSeen : public Command +{ + public: + CommandOSSeen(Module *creator) : Command(creator, "operserv/seen", 1, 2) + { + this->SetDesc(_("Statistics and maintenance for seen data")); + this->SetSyntax("STATS"); + this->SetSyntax(_("CLEAR \037time\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (params[0].equals_ci("STATS")) + { + size_t mem_counter; + mem_counter = sizeof(database_map); + for (database_map::iterator it = database.begin(), it_end = database.end(); it != it_end; ++it) + { + mem_counter += (5 * sizeof(Anope::string)) + sizeof(TypeInfo) + sizeof(time_t); + mem_counter += it->first.capacity(); + mem_counter += it->second->vhost.capacity(); + mem_counter += it->second->nick2.capacity(); + mem_counter += it->second->channel.capacity(); + mem_counter += it->second->message.capacity(); + } + source.Reply(_("%lu nicks are stored in the database, using %.2Lf kB of memory."), database.size(), static_cast(mem_counter) / 1024); + } + else if (params[0].equals_ci("CLEAR")) + { + time_t time = 0; + if ((params.size() < 2) || (0 >= (time = Anope::DoTime(params[1])))) + { + this->OnSyntaxError(source, params[0]); + return; + } + time = Anope::CurTime - time; + database_map::iterator buf; + size_t counter = 0; + for (database_map::iterator it = database.begin(), it_end = database.end(); it != it_end;) + { + buf = it; + ++it; + if (time < buf->second->last) + { + Log(LOG_DEBUG) << buf->first << " was last seen " << Anope::strftime(buf->second->last) << ", deleting entry"; + delete buf->second; + counter++; + } + } + Log(LOG_ADMIN, source, this) << "CLEAR and removed " << counter << " nicks that were added after " << Anope::strftime(time, NULL, true); + source.Reply(_("Database cleared, removed %lu nicks that were added after %s."), counter, Anope::strftime(time, source.nc, true).c_str()); + } + else + this->SendSyntax(source); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("The \002STATS\002 command prints out statistics about stored nicks and memory usage.")); + source.Reply(_("The \002CLEAR\002 command lets you clean the database by removing all entries from the\n" + "database that were added within \037time\037.\n" + " \n" + "Example:\n" + " %s CLEAR 30m\n" + " Will remove all entries that were added within the last 30 minutes."), source.command.c_str()); + return true; + } +}; + +class CommandSeen : public Command +{ + void SimpleSeen(CommandSource &source, const std::vector ¶ms) + { + if (!source.c || !source.c->ci) + { + if (source.IsOper()) + source.Reply("Seen in simple mode is designed as a fantasy command only!"); + return; + } + + BotInfo *bi = BotInfo::Find(params[0], true); + if (bi) + { + if (bi == source.c->ci->bi) + source.Reply(_("You found me, %s!"), source.GetNick().c_str()); + else + source.Reply(_("%s is a network service."), bi->nick.c_str()); + return; + } + + NickAlias *na = NickAlias::Find(params[0]); + if (!na) + { + source.Reply(_("I don't know who %s is."), params[0].c_str()); + return; + } + + if (source.GetAccount() == na->nc) + { + source.Reply(_("Looking for yourself, eh %s?"), source.GetNick().c_str()); + return; + } + + User *target = User::Find(params[0], true); + + if (target && source.c->FindUser(target)) + { + source.Reply(_("%s is on the channel right now!"), target->nick.c_str()); + return; + } + + for (Channel::ChanUserList::const_iterator it = source.c->users.begin(), it_end = source.c->users.end(); it != it_end; ++it) + { + ChanUserContainer *uc = it->second; + User *u = uc->user; + + if (u->Account() == na->nc) + { + source.Reply(_("%s is on the channel right now (as %s)!"), params[0].c_str(), u->nick.c_str()); + return; + } + } + + AccessGroup ag = source.c->ci->AccessFor(na->nc); + time_t last = 0; + for (unsigned int i = 0; i < ag.paths.size(); ++i) + { + ChanAccess::Path &p = ag.paths[i]; + + if (p.empty()) + continue; + + ChanAccess *a = p[p.size() - 1]; + + if (a->GetAccount() == na->nc && a->last_seen > last) + last = a->last_seen; + } + + if (last > Anope::CurTime || !last) + source.Reply(_("I've never seen %s on this channel."), na->nick.c_str()); + else + source.Reply(_("%s was last seen here %s ago."), na->nick.c_str(), Anope::Duration(Anope::CurTime - last, source.GetAccount()).c_str()); + } + + public: + CommandSeen(Module *creator) : Command(creator, "chanserv/seen", 1, 2) + { + this->SetDesc(_("Tells you about the last time a user was seen")); + this->SetSyntax(_("\037nick\037")); + this->AllowUnregistered(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &target = params[0]; + + if (simple) + return this->SimpleSeen(source, params); + + if (target.length() > Config->GetBlock("networkinfo")->Get("nicklen")) + { + source.Reply(_("Nick too long, max length is %u characters."), Config->GetBlock("networkinfo")->Get("nicklen")); + return; + } + + if (BotInfo::Find(target, true) != NULL) + { + source.Reply(_("%s is a client on services."), target.c_str()); + return; + } + + if (target.equals_ci(source.GetNick())) + { + source.Reply(_("You might see yourself in the mirror, %s."), source.GetNick().c_str()); + return; + } + + SeenInfo *info = FindInfo(target); + if (!info) + { + source.Reply(_("Sorry, I have not seen %s."), target.c_str()); + return; + } + + User *u2 = User::Find(target, true); + Anope::string onlinestatus; + if (u2) + onlinestatus = "."; + else + onlinestatus = Anope::printf(Language::Translate(source.nc, _(" but %s mysteriously dematerialized.")), target.c_str()); + + Anope::string timebuf = Anope::Duration(Anope::CurTime - info->last, source.nc); + Anope::string timebuf2 = Anope::strftime(info->last, source.nc, true); + + if (info->type == NEW) + { + source.Reply(_("%s (%s) was last seen connecting %s ago (%s)%s"), + target.c_str(), info->vhost.c_str(), timebuf.c_str(), timebuf2.c_str(), onlinestatus.c_str()); + } + else if (info->type == NICK_TO) + { + u2 = User::Find(info->nick2, true); + if (u2) + onlinestatus = Anope::printf(Language::Translate(source.nc, _(". %s is still online.")), u2->nick.c_str()); + else + onlinestatus = Anope::printf(Language::Translate(source.nc, _(", but %s mysteriously dematerialized.")), info->nick2.c_str()); + + source.Reply(_("%s (%s) was last seen changing nick to %s %s ago%s"), + target.c_str(), info->vhost.c_str(), info->nick2.c_str(), timebuf.c_str(), onlinestatus.c_str()); + } + else if (info->type == NICK_FROM) + { + source.Reply(_("%s (%s) was last seen changing nick from %s to %s %s ago%s"), + target.c_str(), info->vhost.c_str(), info->nick2.c_str(), target.c_str(), timebuf.c_str(), onlinestatus.c_str()); + } + else if (info->type == JOIN) + { + if (ShouldHide(info->channel, u2)) + source.Reply(_("%s (%s) was last seen joining a secret channel %s ago%s"), + target.c_str(), info->vhost.c_str(), timebuf.c_str(), onlinestatus.c_str()); + else + source.Reply(_("%s (%s) was last seen joining %s %s ago%s"), + target.c_str(), info->vhost.c_str(), info->channel.c_str(), timebuf.c_str(), onlinestatus.c_str()); + } + else if (info->type == PART) + { + if (ShouldHide(info->channel, u2)) + source.Reply(_("%s (%s) was last seen parting a secret channel %s ago%s"), + target.c_str(), info->vhost.c_str(), timebuf.c_str(), onlinestatus.c_str()); + else + source.Reply(_("%s (%s) was last seen parting %s %s ago%s"), + target.c_str(), info->vhost.c_str(), info->channel.c_str(), timebuf.c_str(), onlinestatus.c_str()); + } + else if (info->type == QUIT) + { + source.Reply(_("%s (%s) was last seen quitting (%s) %s ago (%s)."), + target.c_str(), info->vhost.c_str(), info->message.c_str(), timebuf.c_str(), timebuf2.c_str()); + } + else if (info->type == KICK) + { + if (ShouldHide(info->channel, u2)) + source.Reply(_("%s (%s) was kicked from a secret channel %s ago%s"), + target.c_str(), info->vhost.c_str(), timebuf.c_str(), onlinestatus.c_str()); + else + source.Reply(_("%s (%s) was kicked from %s (\"%s\") %s ago%s"), + target.c_str(), info->vhost.c_str(), info->channel.c_str(), info->message.c_str(), timebuf.c_str(), onlinestatus.c_str()); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Checks for the last time \037nick\037 was seen joining, leaving,\n" + "or changing nick on the network and tells you when and, depending\n" + "on channel or user settings, where it was.")); + return true; + } +}; + +class CSSeen : public Module +{ + Serialize::Type seeninfo_type; + CommandSeen commandseen; + CommandOSSeen commandosseen; + public: + CSSeen(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), seeninfo_type("SeenInfo", SeenInfo::Unserialize), commandseen(this), commandosseen(this) + { + } + + void OnReload(Configuration::Conf *conf) anope_override + { + simple = conf->GetModule(this)->Get("simple"); + } + + void OnExpireTick() anope_override + { + size_t previous_size = database.size(); + time_t purgetime = Config->GetModule(this)->Get("purgetime"); + if (!purgetime) + purgetime = Anope::DoTime("30d"); + for (database_map::iterator it = database.begin(), it_end = database.end(); it != it_end;) + { + database_map::iterator cur = it; + ++it; + + if ((Anope::CurTime - cur->second->last) > purgetime) + { + Log(LOG_DEBUG) << cur->first << " was last seen " << Anope::strftime(cur->second->last) << ", purging entries"; + delete cur->second; + } + } + Log(LOG_DEBUG) << "cs_seen: Purged database, checked " << previous_size << " nicks and removed " << (previous_size - database.size()) << " old entries."; + } + + void OnUserConnect(User *u, bool &exempt) anope_override + { + if (!u->Quitting()) + UpdateUser(u, NEW, u->nick, "", "", ""); + } + + void OnUserNickChange(User *u, const Anope::string &oldnick) anope_override + { + UpdateUser(u, NICK_TO, oldnick, u->nick, "", ""); + UpdateUser(u, NICK_FROM, u->nick, oldnick, "", ""); + } + + void OnUserQuit(User *u, const Anope::string &msg) anope_override + { + UpdateUser(u, QUIT, u->nick, "", "", msg); + } + + void OnJoinChannel(User *u, Channel *c) anope_override + { + UpdateUser(u, JOIN, u->nick, "", c->name, ""); + } + + void OnPartChannel(User *u, Channel *c, const Anope::string &channel, const Anope::string &msg) anope_override + { + UpdateUser(u, PART, u->nick, "", channel, msg); + } + + void OnPreUserKicked(const MessageSource &source, ChanUserContainer *cu, const Anope::string &msg) anope_override + { + UpdateUser(cu->user, KICK, cu->user->nick, source.GetSource(), cu->chan->name, msg); + } + + private: + void UpdateUser(const User *u, const TypeInfo Type, const Anope::string &nick, const Anope::string &nick2, const Anope::string &channel, const Anope::string &message) + { + if (simple || !u->server->IsSynced()) + return; + + SeenInfo* &info = database[nick]; + if (!info) + info = new SeenInfo(); + info->nick = nick; + info->vhost = u->GetVIdent() + "@" + u->GetDisplayedHost(); + info->type = Type; + info->last = Anope::CurTime; + info->nick2 = nick2; + info->channel = channel; + info->message = message; + } +}; + +MODULE_INIT(CSSeen) diff --git a/modules/commands/cs_set.cpp b/modules/commands/cs_set.cpp new file mode 100644 index 0000000..8e88db5 --- /dev/null +++ b/modules/commands/cs_set.cpp @@ -0,0 +1,1311 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/cs_mode.h" + +class CommandCSSet : public Command +{ + public: + CommandCSSet(Module *creator) : Command(creator, "chanserv/set", 2, 3) + { + this->SetDesc(_("Set channel options and information")); + this->SetSyntax(_("\037option\037 \037channel\037 \037parameters\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows the channel founder to set various channel options\n" + "and other information.\n" + " \n" + "Available options:")); + Anope::string this_name = source.command; + bool hide_privileged_commands = Config->GetBlock("options")->Get("hideprivilegedcommands"), + hide_registered_commands = Config->GetBlock("options")->Get("hideregisteredcommands"); + for (CommandInfo::map::const_iterator it = source.service->commands.begin(), it_end = source.service->commands.end(); it != it_end; ++it) + { + const Anope::string &c_name = it->first; + const CommandInfo &info = it->second; + if (c_name.find_ci(this_name + " ") == 0) + { + if (info.hide) + continue; + + ServiceReference c("Command", info.name); + + // XXX dup + if (!c) + continue; + else if (hide_registered_commands && !c->AllowUnregistered() && !source.GetAccount()) + continue; + else if (hide_privileged_commands && !info.permission.empty() && !source.HasCommand(info.permission)) + continue; + + source.command = it->first; + c->OnServHelp(source); + } + } + source.Reply(_("Type \002%s%s HELP %s \037option\037\002 for more information on a\n" + "particular option."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), this_name.c_str()); + return true; + } +}; + +class CommandCSSetAutoOp : public Command +{ + public: + CommandCSSetAutoOp(Module *creator, const Anope::string &cname = "chanserv/set/autoop") : Command(creator, cname, 2, 2) + { + this->SetDesc(_("Should services automatically give status to users")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params[1].equals_ci("ON")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to enable autoop"; + ci->Shrink("NOAUTOOP"); + source.Reply(_("Services will now automatically give modes to users in \002%s\002."), ci->name.c_str()); + } + else if (params[1].equals_ci("OFF")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to disable autoop"; + ci->Extend("NOAUTOOP"); + source.Reply(_("Services will no longer automatically give modes to users in \002%s\002."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, "AUTOOP"); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enables or disables %s's autoop feature for a\n" + "channel. When disabled, users who join the channel will\n" + "not automatically gain any status from %s."), source.service->nick.c_str(), + source.service->nick.c_str(), this->name.c_str()); + return true; + } +}; + +class CommandCSSetBanType : public Command +{ + public: + CommandCSSetBanType(Module *creator, const Anope::string &cname = "chanserv/set/bantype") : Command(creator, cname, 2, 2) + { + this->SetDesc(_("Set how Services make bans on the channel")); + this->SetSyntax(_("\037channel\037 \037bantype\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + try + { + int16_t new_type = convertTo(params[1]); + if (new_type < 0 || new_type > 3) + throw ConvertException("Invalid range"); + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to change the ban type to " << new_type; + ci->bantype = new_type; + source.Reply(_("Ban type for channel %s is now #%d."), ci->name.c_str(), ci->bantype); + } + catch (const ConvertException &) + { + source.Reply(_("\002%s\002 is not a valid ban type."), params[1].c_str()); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets the ban type that will be used by services whenever\n" + "they need to ban someone from your channel.\n" + " \n" + "Bantype is a number between 0 and 3 that means:\n" + " \n" + "0: ban in the form *!user@host\n" + "1: ban in the form *!*user@host\n" + "2: ban in the form *!*@host\n" + "3: ban in the form *!*user@*.domain"), this->name.c_str()); + return true; + } +}; + +class CommandCSSetDescription : public Command +{ + public: + CommandCSSetDescription(Module *creator, const Anope::string &cname = "chanserv/set/description") : Command(creator, cname, 1, 2) + { + this->SetDesc(_("Set the channel description")); + this->SetSyntax(_("\037channel\037 [\037description\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + const Anope::string ¶m = params.size() > 1 ? params[1] : ""; + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (!param.empty()) + { + ci->desc = param; + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to change the description to " << ci->desc; + source.Reply(_("Description of %s changed to \002%s\002."), ci->name.c_str(), ci->desc.c_str()); + } + else + { + ci->desc.clear(); + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to unset the description"; + source.Reply(_("Description of %s unset."), ci->name.c_str()); + } + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets the description for the channel, which shows up with\n" + "the \002LIST\002 and \002INFO\002 commands."), this->name.c_str()); + return true; + } +}; + +class CommandCSSetFounder : public Command +{ + public: + CommandCSSetFounder(Module *creator, const Anope::string &cname = "chanserv/set/founder") : Command(creator, cname, 2, 2) + { + this->SetDesc(_("Set the founder of a channel")); + this->SetSyntax(_("\037channel\037 \037nick\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && (ci->HasExt("SECUREFOUNDER") ? !source.IsFounder(ci) : !source.AccessFor(ci).HasPriv("FOUNDER")) && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + const NickAlias *na = NickAlias::Find(params[1]); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, params[1].c_str()); + return; + } + + NickCore *nc = na->nc; + unsigned max_reg = Config->GetModule("chanserv")->Get("maxregistered"); + if (max_reg && nc->channelcount >= max_reg && !source.HasPriv("chanserv/no-register-limit")) + { + source.Reply(_("\002%s\002 has too many channels registered."), na->nick.c_str()); + return; + } + + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to change the founder from " << (ci->GetFounder() ? ci->GetFounder()->display : "(none)") << " to " << nc->display; + + ci->SetFounder(nc); + + source.Reply(_("Founder of \002%s\002 changed to \002%s\002."), ci->name.c_str(), na->nick.c_str()); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Changes the founder of a channel. The new nickname must\n" + "be a registered one."), this->name.c_str()); + return true; + } +}; + +class CommandCSSetKeepModes : public Command +{ + public: + CommandCSSetKeepModes(Module *creator, const Anope::string &cname = "chanserv/set/keepmodes") : Command(creator, cname, 2, 2) + { + this->SetDesc(_("Retain modes when channel is not in use")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params[1].equals_ci("ON")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to enable keep modes"; + ci->Extend("CS_KEEP_MODES"); + source.Reply(_("Keep modes for %s is now \002on\002."), ci->name.c_str()); + if (ci->c) + ci->last_modes = ci->c->GetModes(); + } + else if (params[1].equals_ci("OFF")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to disable keep modes"; + ci->Shrink("CS_KEEP_MODES"); + source.Reply(_("Keep modes for %s is now \002off\002."), ci->name.c_str()); + ci->last_modes.clear(); + } + else + this->OnSyntaxError(source, "KEEPMODES"); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enables or disables keepmodes for the given channel. If keep\n" + "modes is enabled, services will remember modes set on the channel\n" + "and attempt to re-set them the next time the channel is created.")); + return true; + } +}; + +class CommandCSSetPeace : public Command +{ + public: + CommandCSSetPeace(Module *creator, const Anope::string &cname = "chanserv/set/peace") : Command(creator, cname, 2, 2) + { + this->SetDesc(_("Regulate the use of critical commands")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params[1].equals_ci("ON")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to enable peace"; + ci->Extend("PEACE"); + source.Reply(_("Peace option for %s is now \002on\002."), ci->name.c_str()); + } + else if (params[1].equals_ci("OFF")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to disable peace"; + ci->Shrink("PEACE"); + source.Reply(_("Peace option for %s is now \002off\002."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, "PEACE"); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enables or disables the \002peace\002 option for a channel.\n" + "When \002peace\002 is set, a user won't be able to kick,\n" + "ban or remove a channel status of a user that has\n" + "a level superior or equal to his via %s commands."), source.service->nick.c_str()); + return true; + } +}; + +inline static Anope::string BotModes() +{ + return Config->GetModule("botserv")->Get("botmodes", + Config->GetModule("chanserv")->Get("botmodes", "o") + ); +} + +class CommandCSSetPersist : public Command +{ + public: + CommandCSSetPersist(Module *creator, const Anope::string &cname = "chanserv/set/persist") : Command(creator, cname, 2, 2) + { + this->SetDesc(_("Set the channel as permanent")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + ChannelMode *cm = ModeManager::FindChannelModeByName("PERM"); + + if (params[1].equals_ci("ON")) + { + if (!ci->HasExt("PERSIST")) + { + ci->Extend("PERSIST"); + + /* Set the perm mode */ + if (cm) + { + if (ci->c && !ci->c->HasMode("PERM")) + ci->c->SetMode(NULL, cm); + /* Add it to the channels mlock */ + ModeLocks *ml = ci->Require("modelocks"); + if (ml) + ml->SetMLock(cm, true, "", source.GetNick()); + } + /* No botserv bot, no channel mode, give them ChanServ. + * Yes, this works fine with no BotServ. + */ + else if (!ci->bi) + { + BotInfo *ChanServ = Config->GetClient("ChanServ"); + if (!ChanServ) + { + source.Reply(_("ChanServ is required to enable persist on this network.")); + return; + } + + ChanServ->Assign(NULL, ci); + if (ci->c && !ci->c->FindUser(ChanServ)) + { + ChannelStatus status(BotModes()); + ChanServ->Join(ci->c, &status); + } + } + } + + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to enable persist"; + source.Reply(_("Channel \002%s\002 is now persistent."), ci->name.c_str()); + } + else if (params[1].equals_ci("OFF")) + { + if (ci->HasExt("PERSIST")) + { + ci->Shrink("PERSIST"); + + BotInfo *ChanServ = Config->GetClient("ChanServ"), + *BotServ = Config->GetClient("BotServ"); + + /* Unset perm mode */ + if (cm) + { + if (ci->c && ci->c->HasMode("PERM")) + ci->c->RemoveMode(NULL, cm); + /* Remove from mlock */ + ModeLocks *ml = ci->GetExt("modelocks"); + if (ml) + ml->RemoveMLock(cm, true); + } + /* No channel mode, no BotServ, but using ChanServ as the botserv bot + * which was assigned when persist was set on + */ + else if (!cm && !BotServ && ci->bi) + { + if (!ChanServ) + { + source.Reply(_("ChanServ is required to enable persist on this network.")); + return; + } + + /* Unassign bot */ + ChanServ->UnAssign(NULL, ci); + } + } + + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to disable persist"; + source.Reply(_("Channel \002%s\002 is no longer persistent."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, "PERSIST"); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + BotInfo *BotServ = Config->GetClient("BotServ"); + BotInfo *ChanServ = Config->GetClient("ChanServ"); + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enables or disables the persistent channel setting.\n" + "When persistent is set, the service bot will remain\n" + "in the channel when it has emptied of users.\n" + " \n" + "If your IRCd does not have a permanent (persistent) channel\n" + "mode you must have a service bot in your channel to\n" + "set persist on, and it can not be unassigned while persist\n" + "is on.\n" + " \n" + "If this network does not have %s enabled and does\n" + "not have a permanent channel mode, %s will\n" + "join your channel when you set persist on (and leave when\n" + "it has been set off).\n" + " \n" + "If your IRCd has a permanent (persistent) channel mode\n" + "and it is set or unset (for any reason, including MODE LOCK),\n" + "persist is automatically set and unset for the channel as well.\n" + "Additionally, services will set or unset this mode when you\n" + "set persist on or off."), BotServ ? BotServ->nick.c_str() : "BotServ", + ChanServ ? ChanServ->nick.c_str() : "ChanServ"); + return true; + } +}; + +class CommandCSSetRestricted : public Command +{ + public: + CommandCSSetRestricted(Module *creator, const Anope::string &cname = "chanserv/set/restricted") : Command(creator, cname, 2, 2) + { + this->SetDesc(_("Restrict access to the channel")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params[1].equals_ci("ON")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to enable restricted"; + ci->Extend("RESTRICTED"); + source.Reply(_("Restricted access option for %s is now \002on\002."), ci->name.c_str()); + } + else if (params[1].equals_ci("OFF")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to disable restricted"; + ci->Shrink("RESTRICTED"); + source.Reply(_("Restricted access option for %s is now \002off\002."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, "RESTRICTED"); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enables or disables the \002restricted access\002 option for a\n" + "channel. When \002restricted access\002 is set, users not on the access list will\n" + "instead be kicked and banned from the channel.")); + return true; + } +}; + +class CommandCSSetSecure : public Command +{ + public: + CommandCSSetSecure(Module *creator, const Anope::string &cname = "chanserv/set/secure") : Command(creator, cname, 2, 2) + { + this->SetDesc(_("Activate security features")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params[1].equals_ci("ON")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to enable secure"; + ci->Extend("CS_SECURE"); + source.Reply(_("Secure option for %s is now \002on\002."), ci->name.c_str()); + } + else if (params[1].equals_ci("OFF")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to disable secure"; + ci->Shrink("CS_SECURE"); + source.Reply(_("Secure option for %s is now \002off\002."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, "SECURE"); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enables or disables security features for a\n" + "channel. When \002SECURE\002 is set, only users who have\n" + "identified to services, and are not only recognized, will be\n" + "given access to channels from account-based access entries.")); + return true; + } +}; + +class CommandCSSetSecureFounder : public Command +{ + public: + CommandCSSetSecureFounder(Module *creator, const Anope::string &cname = "chanserv/set/securefounder") : Command(creator, cname, 2, 2) + { + this->SetDesc(_("Stricter control of channel founder status")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && (ci->HasExt("SECUREFOUNDER") ? !source.IsFounder(ci) : !source.AccessFor(ci).HasPriv("FOUNDER")) && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params[1].equals_ci("ON")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to enable secure founder"; + ci->Extend("SECUREFOUNDER"); + source.Reply(_("Secure founder option for %s is now \002on\002."), ci->name.c_str()); + } + else if (params[1].equals_ci("OFF")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to disable secure founder"; + ci->Shrink("SECUREFOUNDER"); + source.Reply(_("Secure founder option for %s is now \002off\002."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, "SECUREFOUNDER"); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enables or disables the \002secure founder\002 option for a channel.\n" + "When \002secure founder\002 is set, only the real founder will be\n" + "able to drop the channel, change its founder and its successor,\n" + "and not those who have founder level access through\n" + "the access/qop command.")); + return true; + } +}; + +class CommandCSSetSecureOps : public Command +{ + public: + CommandCSSetSecureOps(Module *creator, const Anope::string &cname = "chanserv/set/secureops") : Command(creator, cname, 2, 2) + { + this->SetDesc(_("Stricter control of chanop status")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params[1].equals_ci("ON")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to enable secure ops"; + ci->Extend("SECUREOPS"); + source.Reply(_("Secure ops option for %s is now \002on\002."), ci->name.c_str()); + } + else if (params[1].equals_ci("OFF")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to disable secure ops"; + ci->Shrink("SECUREOPS"); + source.Reply(_("Secure ops option for %s is now \002off\002."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, "SECUREOPS"); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enables or disables the \002secure ops\002 option for a channel.\n" + "When \002secure ops\002 is set, users who are not on the access list\n" + "will not be allowed channel operator status.")); + return true; + } +}; + +class CommandCSSetSignKick : public Command +{ + public: + CommandCSSetSignKick(Module *creator, const Anope::string &cname = "chanserv/set/signkick") : Command(creator, cname, 2, 2) + { + this->SetDesc(_("Sign kicks that are done with the KICK command")); + this->SetSyntax(_("\037channel\037 {ON | LEVEL | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params[1].equals_ci("ON")) + { + ci->Extend("SIGNKICK"); + ci->Shrink("SIGNKICK_LEVEL"); + source.Reply(_("Signed kick option for %s is now \002on\002."), ci->name.c_str()); + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to enable sign kick"; + } + else if (params[1].equals_ci("LEVEL")) + { + ci->Extend("SIGNKICK_LEVEL"); + ci->Shrink("SIGNKICK"); + source.Reply(_("Signed kick option for %s is now \002on\002, but depends of the\n" + "level of the user that is using the command."), ci->name.c_str()); + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to enable sign kick level"; + } + else if (params[1].equals_ci("OFF")) + { + ci->Shrink("SIGNKICK"); + ci->Shrink("SIGNKICK_LEVEL"); + source.Reply(_("Signed kick option for %s is now \002off\002."), ci->name.c_str()); + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to disable sign kick"; + } + else + this->OnSyntaxError(source, "SIGNKICK"); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enables or disables signed kicks for a\n" + "channel. When \002SIGNKICK\002 is set, kicks issued with\n" + "the \002KICK\002 command will have the nick that used the\n" + "command in their reason.\n" + " \n" + "If you use \002LEVEL\002, those who have a level that is superior\n" + "or equal to the SIGNKICK level on the channel won't have their\n" + "kicks signed.")); + return true; + } +}; + +class CommandCSSetSuccessor : public Command +{ + public: + CommandCSSetSuccessor(Module *creator, const Anope::string &cname = "chanserv/set/successor") : Command(creator, cname, 1, 2) + { + this->SetDesc(_("Set the successor for a channel")); + this->SetSyntax(_("\037channel\037 [\037nick\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + const Anope::string ¶m = params.size() > 1 ? params[1] : ""; + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && (ci->HasExt("SECUREFOUNDER") ? !source.IsFounder(ci) : !source.AccessFor(ci).HasPriv("FOUNDER")) && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + NickCore *nc; + + if (!param.empty()) + { + const NickAlias *na = NickAlias::Find(param); + + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, param.c_str()); + return; + } + if (na->nc == ci->GetFounder()) + { + source.Reply(_("%s cannot be the successor on channel %s as they are the founder."), na->nick.c_str(), ci->name.c_str()); + return; + } + nc = na->nc; + } + else + nc = NULL; + + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to change the successor from " << (ci->GetSuccessor() ? ci->GetSuccessor()->display : "(none)") << " to " << (nc ? nc->display : "(none)"); + + ci->SetSuccessor(nc); + + if (nc) + source.Reply(_("Successor for \002%s\002 changed to \002%s\002."), ci->name.c_str(), nc->display.c_str()); + else + source.Reply(_("Successor for \002%s\002 unset."), ci->name.c_str()); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Changes the successor of a channel. If the founder's\n" + "nickname expires or is dropped while the channel is still\n" + "registered, the successor will become the new founder of the\n" + "channel. The successor's nickname must be a registered one.\n" + "If there's no successor set, then the first nickname on the\n" + "access list (with the highest access, if applicable) will\n" + "become the new founder, but if the access list is empty, the\n" + "channel will be dropped.")); + unsigned max_reg = Config->GetModule("chanserv")->Get("maxregistered"); + if (max_reg) + { + source.Reply(" "); + source.Reply(_("Note, however, if the successor already has too many\n" + "channels registered (%d), they will not be able to\n" + "become the new founder and it will be as if the\n" + "channel had no successor set."), max_reg); + } + return true; + } +}; + +class CommandCSSetNoexpire : public Command +{ + public: + CommandCSSetNoexpire(Module *creator) : Command(creator, "chanserv/saset/noexpire", 2, 2) + { + this->SetDesc(_("Prevent the channel from expiring")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + if (source.permission.empty() && !source.AccessFor(ci).HasPriv("SET")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params[1].equals_ci("ON")) + { + Log(LOG_ADMIN, source, this, ci) << "to enable noexpire"; + ci->Extend("CS_NO_EXPIRE"); + source.Reply(_("Channel %s \002will not\002 expire."), ci->name.c_str()); + } + else if (params[1].equals_ci("OFF")) + { + Log(LOG_ADMIN, source, this, ci) << "to disable noexpire"; + ci->Shrink("CS_NO_EXPIRE"); + source.Reply(_("Channel %s \002will\002 expire."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, "NOEXPIRE"); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets whether the given channel will expire. Setting this\n" + "to ON prevents the channel from expiring.")); + return true; + } +}; + +class CSSet : public Module +{ + SerializableExtensibleItem noautoop, peace, securefounder, + restricted, secure, secureops, signkick, signkick_level, noexpire, + persist; + + struct KeepModes : SerializableExtensibleItem + { + KeepModes(Module *m, const Anope::string &n) : SerializableExtensibleItem(m, n) { } + + void ExtensibleSerialize(const Extensible *e, const Serializable *s, Serialize::Data &data) const anope_override + { + SerializableExtensibleItem::ExtensibleSerialize(e, s, data); + + if (s->GetSerializableType()->GetName() != "ChannelInfo") + return; + + const ChannelInfo *ci = anope_dynamic_static_cast(s); + Anope::string modes; + for (Channel::ModeList::const_iterator it = ci->last_modes.begin(); it != ci->last_modes.end(); ++it) + { + if (!modes.empty()) + modes += " "; + modes += it->first; + if (!it->second.empty()) + modes += "," + it->second; + } + data["last_modes"] << modes; + } + + void ExtensibleUnserialize(Extensible *e, Serializable *s, Serialize::Data &data) anope_override + { + SerializableExtensibleItem::ExtensibleUnserialize(e, s, data); + + if (s->GetSerializableType()->GetName() != "ChannelInfo") + return; + + ChannelInfo *ci = anope_dynamic_static_cast(s); + Anope::string modes; + data["last_modes"] >> modes; + ci->last_modes.clear(); + for (spacesepstream sep(modes); sep.GetToken(modes);) + { + size_t c = modes.find(','); + if (c == Anope::string::npos) + ci->last_modes.insert(std::make_pair(modes, "")); + else + ci->last_modes.insert(std::make_pair(modes.substr(0, c), modes.substr(c + 1))); + } + } + } keep_modes; + + CommandCSSet commandcsset; + CommandCSSetAutoOp commandcssetautoop; + CommandCSSetBanType commandcssetbantype; + CommandCSSetDescription commandcssetdescription; + CommandCSSetFounder commandcssetfounder; + CommandCSSetKeepModes commandcssetkeepmodes; + CommandCSSetPeace commandcssetpeace; + CommandCSSetPersist commandcssetpersist; + CommandCSSetRestricted commandcssetrestricted; + CommandCSSetSecure commandcssetsecure; + CommandCSSetSecureFounder commandcssetsecurefounder; + CommandCSSetSecureOps commandcssetsecureops; + CommandCSSetSignKick commandcssetsignkick; + CommandCSSetSuccessor commandcssetsuccessor; + CommandCSSetNoexpire commandcssetnoexpire; + + ExtensibleRef inhabit; + + bool persist_lower_ts; + + public: + CSSet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + noautoop(this, "NOAUTOOP"), peace(this, "PEACE"), + securefounder(this, "SECUREFOUNDER"), restricted(this, "RESTRICTED"), + secure(this, "CS_SECURE"), secureops(this, "SECUREOPS"), signkick(this, "SIGNKICK"), + signkick_level(this, "SIGNKICK_LEVEL"), noexpire(this, "CS_NO_EXPIRE"), + persist(this, "PERSIST"), + keep_modes(this, "CS_KEEP_MODES"), + + commandcsset(this), commandcssetautoop(this), commandcssetbantype(this), + commandcssetdescription(this), commandcssetfounder(this), commandcssetkeepmodes(this), + commandcssetpeace(this), commandcssetpersist(this), commandcssetrestricted(this), + commandcssetsecure(this), commandcssetsecurefounder(this), commandcssetsecureops(this), commandcssetsignkick(this), + commandcssetsuccessor(this), commandcssetnoexpire(this), + + inhabit("inhabit") + { + } + + void OnReload(Configuration::Conf *conf) anope_override + { + persist_lower_ts = conf->GetModule(this)->Get("persist_lower_ts"); + } + + void OnCreateChan(ChannelInfo *ci) anope_override + { + ci->bantype = Config->GetModule(this)->Get("defbantype", "2"); + } + + void OnChannelSync(Channel *c) anope_override + { + if (c->ci && keep_modes.HasExt(c->ci)) + { + Channel::ModeList ml = c->ci->last_modes; + for (Channel::ModeList::iterator it = ml.begin(); it != ml.end(); ++it) + c->SetMode(c->ci->WhoSends(), it->first, it->second); + } + } + + EventReturn OnCheckKick(User *u, Channel *c, Anope::string &mask, Anope::string &reason) anope_override + { + if (!c->ci || !restricted.HasExt(c->ci) || c->MatchesList(u, "EXCEPT")) + return EVENT_CONTINUE; + + if (c->ci->AccessFor(u).empty() && (!c->ci->GetFounder() || u->Account() != c->ci->GetFounder())) + return EVENT_STOP; + + return EVENT_CONTINUE; + } + + void OnDelChan(ChannelInfo *ci) anope_override + { + if (ci->c && persist.HasExt(ci)) + ci->c->RemoveMode(ci->WhoSends(), "PERM", "", false); + persist.Unset(ci); + } + + EventReturn OnChannelModeSet(Channel *c, MessageSource &setter, ChannelMode *mode, const Anope::string ¶m) anope_override + { + if (c->ci) + { + /* Channel mode +P or so was set, mark this channel as persistent */ + if (mode->name == "PERM") + persist.Set(c->ci, true); + + if (mode->type != MODE_STATUS && !c->syncing && Me->IsSynced() && (!inhabit || !inhabit->HasExt(c))) + c->ci->last_modes = c->GetModes(); + } + + return EVENT_CONTINUE; + } + + EventReturn OnChannelModeUnset(Channel *c, MessageSource &setter, ChannelMode *mode, const Anope::string ¶m) anope_override + { + if (mode->name == "PERM") + { + if (c->ci) + persist.Unset(c->ci); + } + + if (c->ci && mode->type != MODE_STATUS && !c->syncing && Me->IsSynced() && (!inhabit || !inhabit->HasExt(c))) + c->ci->last_modes = c->GetModes(); + + return EVENT_CONTINUE; + } + + void OnJoinChannel(User *u, Channel *c) anope_override + { + if (u->server != Me && persist_lower_ts && c->ci && persist.HasExt(c->ci) && c->creation_time > c->ci->time_registered) + { + Log(LOG_DEBUG) << "Changing TS of " << c->name << " from " << c->creation_time << " to " << c->ci->time_registered; + c->creation_time = c->ci->time_registered; + IRCD->SendChannel(c); + c->Reset(); + } + } + + void OnSetCorrectModes(User *user, Channel *chan, AccessGroup &access, bool &give_modes, bool &take_modes) anope_override + { + if (chan->ci) + { + if (noautoop.HasExt(chan->ci)) + give_modes = false; + if (secureops.HasExt(chan->ci) && !user->HasPriv("chanserv/administration")) + // This overrides what chanserv does because it is loaded after chanserv + take_modes = true; + } + } + + void OnPreChanExpire(ChannelInfo *ci, bool &expire) anope_override + { + if (noexpire.HasExt(ci)) + expire = false; + } + + void OnChanInfo(CommandSource &source, ChannelInfo *ci, InfoFormatter &info, bool show_all) anope_override + { + if (!show_all) + return; + + if (peace.HasExt(ci)) + info.AddOption(_("Peace")); + if (restricted.HasExt(ci)) + info.AddOption(_("Restricted access")); + if (secure.HasExt(ci)) + info.AddOption(_("Security")); + if (securefounder.HasExt(ci)) + info.AddOption(_("Secure founder")); + if (secureops.HasExt(ci)) + info.AddOption(_("Secure ops")); + if (signkick.HasExt(ci) || signkick_level.HasExt(ci)) + info.AddOption(_("Signed kicks")); + if (persist.HasExt(ci)) + info.AddOption(_("Persistent")); + if (noexpire.HasExt(ci)) + info.AddOption(_("No expire")); + if (keep_modes.HasExt(ci)) + info.AddOption(_("Keep modes")); + if (noautoop.HasExt(ci)) + info.AddOption(_("No auto-op")); + } +}; + +MODULE_INIT(CSSet) diff --git a/modules/commands/cs_set_misc.cpp b/modules/commands/cs_set_misc.cpp new file mode 100644 index 0000000..80167af --- /dev/null +++ b/modules/commands/cs_set_misc.cpp @@ -0,0 +1,219 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/set_misc.h" + +static Module *me; + +static Anope::map descriptions; + +struct CSMiscData; +static Anope::map *> items; + +static ExtensibleItem *GetItem(const Anope::string &name) +{ + ExtensibleItem* &it = items[name]; + if (!it) + try + { + it = new ExtensibleItem(me, name); + } + catch (const ModuleException &) { } + return it; +} + +struct CSMiscData : MiscData, Serializable +{ + CSMiscData(Extensible *obj) : Serializable("CSMiscData") { } + + CSMiscData(ChannelInfo *c, const Anope::string &n, const Anope::string &d) : Serializable("CSMiscData") + { + object = c->name; + name = n; + data = d; + } + + void Serialize(Serialize::Data &sdata) const anope_override + { + sdata["ci"] << this->object; + sdata["name"] << this->name; + sdata["data"] << this->data; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data) + { + Anope::string sci, sname, sdata; + + data["ci"] >> sci; + data["name"] >> sname; + data["data"] >> sdata; + + ChannelInfo *ci = ChannelInfo::Find(sci); + if (ci == NULL) + return NULL; + + CSMiscData *d = NULL; + if (obj) + { + d = anope_dynamic_static_cast(obj); + d->object = ci->name; + data["name"] >> d->name; + data["data"] >> d->data; + } + else + { + ExtensibleItem *item = GetItem(sname); + if (item) + d = item->Set(ci, CSMiscData(ci, sname, sdata)); + } + + return d; + } +}; + +static Anope::string GetAttribute(const Anope::string &command) +{ + size_t sp = command.rfind(' '); + if (sp != Anope::string::npos) + return command.substr(sp + 1); + return command; +} + +class CommandCSSetMisc : public Command +{ + public: + CommandCSSetMisc(Module *creator, const Anope::string &cname = "chanserv/set/misc") : Command(creator, cname, 1, 2) + { + this->SetSyntax(_("\037channel\037 [\037parameters\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + const Anope::string ¶m = params.size() > 1 ? params[1] : ""; + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + Anope::string scommand = GetAttribute(source.command); + Anope::string key = "cs_set_misc:" + scommand; + ExtensibleItem *item = GetItem(key); + if (item == NULL) + return; + + if (!param.empty()) + { + item->Set(ci, CSMiscData(ci, key, param)); + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to change it to " << param; + source.Reply(CHAN_SETTING_CHANGED, scommand.c_str(), ci->name.c_str(), params[1].c_str()); + } + else + { + item->Unset(ci); + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to unset it"; + source.Reply(CHAN_SETTING_UNSET, scommand.c_str(), ci->name.c_str()); + } + } + + void OnServHelp(CommandSource &source) anope_override + { + if (descriptions.count(source.command)) + { + this->SetDesc(descriptions[source.command]); + Command::OnServHelp(source); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + if (descriptions.count(source.command)) + { + this->SendSyntax(source); + source.Reply("%s", Language::Translate(source.nc, descriptions[source.command].c_str())); + return true; + } + return false; + } +}; + +class CSSetMisc : public Module +{ + CommandCSSetMisc commandcssetmisc; + Serialize::Type csmiscdata_type; + + public: + CSSetMisc(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcssetmisc(this), csmiscdata_type("CSMiscData", CSMiscData::Unserialize) + { + me = this; + } + + ~CSSetMisc() + { + for (Anope::map *>::iterator it = items.begin(); it != items.end(); ++it) + delete it->second; + } + + void OnReload(Configuration::Conf *conf) anope_override + { + descriptions.clear(); + + for (int i = 0; i < conf->CountBlock("command"); ++i) + { + Configuration::Block *block = conf->GetBlock("command", i); + + if (block->Get("command") != "chanserv/set/misc") + continue; + + Anope::string cname = block->Get("name"); + Anope::string desc = block->Get("misc_description"); + + if (cname.empty() || desc.empty()) + continue; + + descriptions[cname] = desc; + } + } + + void OnChanInfo(CommandSource &source, ChannelInfo *ci, InfoFormatter &info, bool) anope_override + { + for (Anope::map *>::iterator it = items.begin(); it != items.end(); ++it) + { + ExtensibleItem *e = it->second; + MiscData *data = e->Get(ci); + + if (data != NULL) + info[e->name.substr(12).replace_all_cs("_", " ")] = data->data; + } + } +}; + +MODULE_INIT(CSSetMisc) diff --git a/modules/commands/cs_status.cpp b/modules/commands/cs_status.cpp new file mode 100644 index 0000000..82ca2ce --- /dev/null +++ b/modules/commands/cs_status.cpp @@ -0,0 +1,125 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandCSStatus : public Command +{ +public: + CommandCSStatus(Module *creator) : Command(creator, "chanserv/status", 1, 2) + { + this->SetDesc(_("Find a user's status on a channel")); + this->SetSyntax(_("\037channel\037 [\037user\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &channel = params[0]; + + ChannelInfo *ci = ChannelInfo::Find(channel); + if (ci == NULL) + source.Reply(CHAN_X_NOT_REGISTERED, channel.c_str()); + else if (!source.AccessFor(ci).HasPriv("ACCESS_CHANGE") && !source.HasPriv("chanserv/auspex")) + source.Reply(ACCESS_DENIED); + else + { + Anope::string nick = source.GetNick(); + if (params.size() > 1) + nick = params[1]; + + AccessGroup ag; + User *u = User::Find(nick, true); + NickAlias *na = NULL; + if (u != NULL) + ag = ci->AccessFor(u); + else + { + na = NickAlias::Find(nick); + if (na != NULL) + ag = ci->AccessFor(na->nc); + } + + if (ag.super_admin) + source.Reply(_("\002%s\002 is a super administrator."), nick.c_str()); + else if (ag.founder) + source.Reply(_("\002%s\002 is the founder of \002%s\002."), nick.c_str(), ci->name.c_str()); + else if (ag.empty()) + source.Reply(_("\002%s\002 has no access on \002%s\002."), nick.c_str(), ci->name.c_str()); + else + { + source.Reply(_("Access for \002%s\002 on \002%s\002:"), nick.c_str(), ci->name.c_str()); + + for (unsigned i = 0; i < ag.paths.size(); ++i) + { + ChanAccess::Path &p = ag.paths[i]; + + if (p.empty()) + continue; + + if (p.size() == 1) + { + ChanAccess *acc = p[0]; + + source.Reply(_("\002%s\002 matches access entry %s, which has privilege %s."), nick.c_str(), acc->Mask().c_str(), acc->AccessSerialize().c_str()); + } + else + { + ChanAccess *first = p[0]; + ChanAccess *acc = p[p.size() - 1]; + + source.Reply(_("\002%s\002 matches access entry %s (from entry %s), which has privilege %s."), nick.c_str(), acc->Mask().c_str(), first->Mask().c_str(), acc->AccessSerialize().c_str()); + } + } + } + + for (unsigned j = 0, end = ci->GetAkickCount(); j < end; ++j) + { + AutoKick *autokick = ci->GetAkick(j); + + if (autokick->nc) + { + if (na && *autokick->nc == na->nc) + source.Reply(_("\002%s\002 is on the auto kick list of \002%s\002 (%s)."), na->nc->display.c_str(), ci->name.c_str(), autokick->reason.c_str()); + } + else if (u != NULL) + { + Entry akick_mask("", autokick->mask); + if (akick_mask.Matches(u)) + source.Reply(_("\002%s\002 matches auto kick entry %s on \002%s\002 (%s)."), u->nick.c_str(), autokick->mask.c_str(), ci->name.c_str(), autokick->reason.c_str()); + } + } + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command tells you what a users access is on a channel\n" + "and what access entries, if any, they match. Additionally it\n" + "will tell you of any auto kick entries they match. Usage of\n" + "this command is limited to users who have the ability to modify\n" + "access entries on the channel.")); + return true; + } +}; + +class CSStatus : public Module +{ + CommandCSStatus commandcsstatus; + + public: + CSStatus(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), commandcsstatus(this) + { + } +}; + +MODULE_INIT(CSStatus) diff --git a/modules/commands/cs_suspend.cpp b/modules/commands/cs_suspend.cpp new file mode 100644 index 0000000..7ecfbdf --- /dev/null +++ b/modules/commands/cs_suspend.cpp @@ -0,0 +1,285 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/suspend.h" + +struct CSSuspendInfo : SuspendInfo, Serializable +{ + CSSuspendInfo(Extensible *) : Serializable("CSSuspendInfo") { } + + void Serialize(Serialize::Data &data) const anope_override + { + data["chan"] << what; + data["by"] << by; + data["reason"] << reason; + data["time"] << when; + data["expires"] << expires; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data) + { + Anope::string schan; + data["chan"] >> schan; + + CSSuspendInfo *si; + if (obj) + si = anope_dynamic_static_cast(obj); + else + { + ChannelInfo *ci = ChannelInfo::Find(schan); + if (!ci) + return NULL; + si = ci->Extend("CS_SUSPENDED"); + data["chan"] >> si->what; + } + + data["by"] >> si->by; + data["reason"] >> si->reason; + data["time"] >> si->when; + data["expires"] >> si->expires; + return si; + } +}; + +class CommandCSSuspend : public Command +{ + public: + CommandCSSuspend(Module *creator) : Command(creator, "chanserv/suspend", 2, 3) + { + this->SetDesc(_("Prevent a channel from being used preserving channel data and settings")); + this->SetSyntax(_("\037channel\037 [+\037expiry\037] [\037reason\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &chan = params[0]; + Anope::string expiry = params[1]; + Anope::string reason = params.size() > 2 ? params[2] : ""; + time_t expiry_secs = Config->GetModule(this->owner)->Get("expire"); + + if (!expiry.empty() && expiry[0] != '+') + { + reason = expiry + " " + reason; + reason.trim(); + expiry.clear(); + } + else + { + expiry_secs = Anope::DoTime(expiry); + if (expiry_secs < 0) + { + source.Reply(BAD_EXPIRY_TIME); + return; + } + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + ChannelInfo *ci = ChannelInfo::Find(chan); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); + return; + } + + if (ci->HasExt("CS_SUSPENDED")) + { + source.Reply(_("\002%s\002 is already suspended."), ci->name.c_str()); + return; + } + + CSSuspendInfo *si = ci->Extend("CS_SUSPENDED"); + si->what = ci->name; + si->by = source.GetNick(); + si->reason = reason; + si->when = Anope::CurTime; + si->expires = expiry_secs ? expiry_secs + Anope::CurTime : 0; + + if (ci->c) + { + std::vector users; + + for (Channel::ChanUserList::iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end; ++it) + { + ChanUserContainer *uc = it->second; + User *user = uc->user; + if (!user->HasMode("OPER") && user->server != Me) + users.push_back(user); + } + + for (unsigned i = 0; i < users.size(); ++i) + ci->c->Kick(NULL, users[i], "%s", !reason.empty() ? reason.c_str() : Language::Translate(users[i], _("This channel has been suspended."))); + } + + Log(LOG_ADMIN, source, this, ci) << "(" << (!reason.empty() ? reason : "No reason") << "), expires on " << (expiry_secs ? Anope::strftime(Anope::CurTime + expiry_secs) : "never"); + source.Reply(_("Channel \002%s\002 is now suspended."), ci->name.c_str()); + + FOREACH_MOD(OnChanSuspend, (ci)); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Disallows anyone from using the given channel.\n" + "May be cancelled by using the \002UNSUSPEND\002\n" + "command to preserve all previous channel data/settings.\n" + "If an expiry is given the channel will be unsuspended after\n" + "that period of time, else the default expiry from the\n" + "configuration is used.\n" + " \n" + "Reason may be required on certain networks.")); + return true; + } +}; + +class CommandCSUnSuspend : public Command +{ + public: + CommandCSUnSuspend(Module *creator) : Command(creator, "chanserv/unsuspend", 1, 1) + { + this->SetDesc(_("Releases a suspended channel")); + this->SetSyntax(_("\037channel\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + /* Only UNSUSPEND already suspended channels */ + CSSuspendInfo *si = ci->GetExt("CS_SUSPENDED"); + if (!si) + { + source.Reply(_("Channel \002%s\002 isn't suspended."), ci->name.c_str()); + return; + } + + Log(LOG_ADMIN, source, this, ci) << "which was suspended by " << si->by << " for: " << (!si->reason.empty() ? si->reason : "No reason"); + + ci->Shrink("CS_SUSPENDED"); + + source.Reply(_("Channel \002%s\002 is now released."), ci->name.c_str()); + + FOREACH_MOD(OnChanUnsuspend, (ci)); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Releases a suspended channel. All data and settings\n" + "are preserved from before the suspension.")); + return true; + } +}; + +class CSSuspend : public Module +{ + CommandCSSuspend commandcssuspend; + CommandCSUnSuspend commandcsunsuspend; + ExtensibleItem suspend; + Serialize::Type suspend_type; + std::vector show; + + struct trim + { + Anope::string operator()(Anope::string s) const + { + return s.trim(); + } + }; + + bool Show(CommandSource &source, const Anope::string &what) const + { + return source.IsOper() || std::find(show.begin(), show.end(), what) != show.end(); + } + + public: + CSSuspend(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcssuspend(this), commandcsunsuspend(this), suspend(this, "CS_SUSPENDED"), + suspend_type("CSSuspendInfo", CSSuspendInfo::Unserialize) + { + } + + void OnChanInfo(CommandSource &source, ChannelInfo *ci, InfoFormatter &info, bool show_hidden) anope_override + { + CSSuspendInfo *si = suspend.Get(ci); + if (!si) + return; + + if (show_hidden || Show(source, "suspended")) + info[_("Suspended")] = _("This channel is \002suspended\002."); + if (!si->by.empty() && (show_hidden || Show(source, "by"))) + info[_("Suspended by")] = si->by; + if (!si->reason.empty() && (show_hidden || Show(source, "reason"))) + info[_("Suspend reason")] = si->reason; + if (si->when && (show_hidden || Show(source, "on"))) + info[_("Suspended on")] = Anope::strftime(si->when, source.GetAccount()); + if (si->expires && (show_hidden || Show(source, "expires"))) + info[_("Suspension expires")] = Anope::strftime(si->expires, source.GetAccount()); + } + + void OnPreChanExpire(ChannelInfo *ci, bool &expire) anope_override + { + CSSuspendInfo *si = suspend.Get(ci); + if (!si) + return; + + expire = false; + + if (!si->expires) + return; + + if (si->expires < Anope::CurTime) + { + ci->last_used = Anope::CurTime; + suspend.Unset(ci); + + Log(this) << "Expiring suspend for " << ci->name; + } + } + + EventReturn OnCheckKick(User *u, Channel *c, Anope::string &mask, Anope::string &reason) anope_override + { + if (u->HasMode("OPER") || !c->ci || !suspend.HasExt(c->ci)) + return EVENT_CONTINUE; + + reason = Language::Translate(u, _("This channel may not be used.")); + return EVENT_STOP; + } + + EventReturn OnChanDrop(CommandSource &source, ChannelInfo *ci) anope_override + { + CSSuspendInfo *si = suspend.Get(ci); + if (si && !source.HasCommand("chanserv/drop")) + { + source.Reply(CHAN_X_SUSPENDED, ci->name.c_str()); + return EVENT_STOP; + } + + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(CSSuspend) diff --git a/modules/commands/cs_sync.cpp b/modules/commands/cs_sync.cpp new file mode 100644 index 0000000..a7897d1 --- /dev/null +++ b/modules/commands/cs_sync.cpp @@ -0,0 +1,66 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandCSSync : public Command +{ + public: + CommandCSSync(Module *creator) : Command(creator, "chanserv/sync", 1, 1) + { + this->SetDesc(_("Sync users channel modes")); + this->SetSyntax(_("\037channel\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci = ChannelInfo::Find(params[0]); + + if (ci == NULL) + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + else if (ci->c == NULL) + source.Reply(CHAN_X_NOT_IN_USE, params[0].c_str()); + else if (!source.AccessFor(ci).HasPriv("ACCESS_CHANGE") && !source.HasPriv("chanserv/administration")) + source.Reply(ACCESS_DENIED); + else + { + bool override = !source.AccessFor(ci).HasPriv("ACCESS_CHANGE") && source.HasPriv("chanserv/administration"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci); + + for (Channel::ChanUserList::iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end; ++it) + ci->c->SetCorrectModes(it->second->user, true); + + source.Reply(_("All user modes on \002%s\002 have been synced."), ci->name.c_str()); + } + } + + bool OnHelp(CommandSource &source, const Anope::string ¶ms) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Syncs all modes set on users on the channel with the modes\n" + "they should have based on their access.")); + return true; + } +}; + +class CSSync : public Module +{ + CommandCSSync commandcssync; + public: + CSSync(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcssync(this) + { + + } +}; + +MODULE_INIT(CSSync) diff --git a/modules/commands/cs_topic.cpp b/modules/commands/cs_topic.cpp new file mode 100644 index 0000000..98a51fe --- /dev/null +++ b/modules/commands/cs_topic.cpp @@ -0,0 +1,270 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/cs_mode.h" + +class CommandCSSetKeepTopic : public Command +{ + public: + CommandCSSetKeepTopic(Module *creator, const Anope::string &cname = "chanserv/set/keeptopic") : Command(creator, cname, 2, 2) + { + this->SetDesc(_("Retain topic when channel is not in use")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params[1].equals_ci("ON")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to enable keeptopic"; + ci->Extend("KEEPTOPIC"); + source.Reply(_("Topic retention option for %s is now \002on\002."), ci->name.c_str()); + } + else if (params[1].equals_ci("OFF")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to disable keeptopic"; + ci->Shrink("KEEPTOPIC"); + source.Reply(_("Topic retention option for %s is now \002off\002."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, "KEEPTOPIC"); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enables or disables the \002topic retention\002 option for a\n" + "channel. When \002%s\002 is set, the topic for the\n" + "channel will be remembered by %s even after the\n" + "last user leaves the channel, and will be restored the\n" + "next time the channel is created."), source.command.c_str(), source.service->nick.c_str()); + return true; + } +}; + +class CommandCSTopic : public Command +{ + ExtensibleRef topiclock; + + void Lock(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, "topiclock on")); + if (MOD_RESULT == EVENT_STOP) + return; + + topiclock->Set(ci, true); + source.Reply(_("Topic lock option for %s is now \002on\002."), ci->name.c_str()); + } + + void Unlock(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, "topiclock off")); + if (MOD_RESULT == EVENT_STOP) + return; + + topiclock->Unset(ci); + source.Reply(_("Topic lock option for %s is now \002off\002."), ci->name.c_str()); + } + + void Set(CommandSource &source, ChannelInfo *ci, const Anope::string &topic) + { + bool has_topiclock = topiclock->HasExt(ci); + topiclock->Unset(ci); + ci->c->ChangeTopic(source.GetNick(), topic, Anope::CurTime); + if (has_topiclock) + topiclock->Set(ci); + + bool override = !source.AccessFor(ci).HasPriv("TOPIC"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << (!topic.empty() ? "to change the topic to: " : "to unset the topic") << (!topic.empty() ? topic : ""); + } + + void Append(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + const Anope::string &topic = params[2]; + + Anope::string new_topic; + if (!ci->c->topic.empty()) + { + new_topic = ci->c->topic + " " + topic; + ci->last_topic.clear(); + } + else + new_topic = topic; + + this->Set(source, ci, new_topic); + } + + public: + CommandCSTopic(Module *creator) : Command(creator, "chanserv/topic", 2, 3), + topiclock("TOPICLOCK") + { + this->SetDesc(_("Manipulate the topic of the specified channel")); + this->SetSyntax(_("\037channel\037 [SET] [\037topic\037]")); + this->SetSyntax(_("\037channel\037 APPEND \037topic\037")); + this->SetSyntax(_("\037channel\037 [UNLOCK|LOCK]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &subcmd = params[1]; + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + else if (!source.AccessFor(ci).HasPriv("TOPIC") && !source.HasCommand("chanserv/topic")) + source.Reply(ACCESS_DENIED); + else if (subcmd.equals_ci("LOCK")) + this->Lock(source, ci, params); + else if (subcmd.equals_ci("UNLOCK")) + this->Unlock(source, ci, params); + else if (!ci->c) + source.Reply(CHAN_X_NOT_IN_USE, ci->name.c_str()); + else if (subcmd.equals_ci("APPEND") && params.size() > 2) + this->Append(source, ci, params); + else + { + Anope::string topic; + if (subcmd.equals_ci("SET")) + { + topic = params.size() > 2 ? params[2] : ""; + } + else + { + topic = subcmd; + if (params.size() > 2) + topic += " " + params[2]; + } + this->Set(source, ci, topic); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows manipulating the topic of the specified channel.\n" + "The \002SET\002 command changes the topic of the channel to the given topic\n" + "or unsets the topic if no topic is given. The \002APPEND\002 command appends\n" + "the given topic to the existing topic.\n" + " \n" + "\002LOCK\002 and \002UNLOCK\002 may be used to enable and disable topic lock. When\n" + "topic lock is set, the channel topic will be unchangeable by users who do not have\n" + "the \002TOPIC\002 privilege.")); + return true; + } +}; + +class CSTopic : public Module +{ + CommandCSTopic commandcstopic; + CommandCSSetKeepTopic commandcssetkeeptopic; + + SerializableExtensibleItem topiclock, keeptopic; + + public: + CSTopic(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcstopic(this), commandcssetkeeptopic(this), topiclock(this, "TOPICLOCK"), keeptopic(this, "KEEPTOPIC") + { + + } + + void OnChannelSync(Channel *c) anope_override + { + if (c->ci) + { + /* Update channel topic */ + if ((topiclock.HasExt(c->ci) || keeptopic.HasExt(c->ci)) && c->ci->last_topic != c->topic) + { + c->ChangeTopic(!c->ci->last_topic_setter.empty() ? c->ci->last_topic_setter : c->ci->WhoSends()->nick, c->ci->last_topic, c->ci->last_topic_time ? c->ci->last_topic_time : Anope::CurTime); + } + } + } + + void OnTopicUpdated(User *source, Channel *c, const Anope::string &user, const Anope::string &topic) anope_override + { + if (!c->ci) + return; + + /* We only compare the topics here, not the time or setter. This is because some (old) IRCds do not + * allow us to set the topic as someone else, meaning we have to bump the TS and change the setter to us. + * This desyncs what is really set with what we have stored, and we end up resetting the topic often when + * it is not required + */ + if (topiclock.HasExt(c->ci) && c->ci->last_topic != c->topic && (!source || !c->ci->AccessFor(source).HasPriv("TOPIC"))) + { + c->ChangeTopic(c->ci->last_topic_setter, c->ci->last_topic, c->ci->last_topic_time); + } + else + { + c->ci->last_topic = c->topic; + c->ci->last_topic_setter = c->topic_setter; + c->ci->last_topic_time = c->topic_ts; + } + } + + void OnChanInfo(CommandSource &source, ChannelInfo *ci, InfoFormatter &info, bool show_all) anope_override + { + if (keeptopic.HasExt(ci)) + info.AddOption(_("Topic retention")); + if (topiclock.HasExt(ci)) + info.AddOption(_("Topic lock")); + + ModeLocks *ml = ci->GetExt("modelocks"); + const ModeLock *secret = ml ? ml->GetMLock("SECRET") : NULL; + if (!ci->last_topic.empty() && (show_all || ((!secret || secret->set == false) && (!ci->c || !ci->c->HasMode("SECRET"))))) + { + info[_("Last topic")] = ci->last_topic; + info[_("Topic set by")] = ci->last_topic_setter; + } + } +}; + +MODULE_INIT(CSTopic) diff --git a/modules/commands/cs_unban.cpp b/modules/commands/cs_unban.cpp new file mode 100644 index 0000000..93175f3 --- /dev/null +++ b/modules/commands/cs_unban.cpp @@ -0,0 +1,130 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandCSUnban : public Command +{ + public: + CommandCSUnban(Module *creator) : Command(creator, "chanserv/unban", 0, 2) + { + this->SetDesc(_("Remove all bans preventing a user from entering a channel")); + this->SetSyntax(_("\037channel\037 [\037nick\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelMode *cm = ModeManager::FindChannelModeByName("BAN"); + if (!cm) + return; + + std::vector modes = cm->listeners; + modes.push_back(cm); + + if (params.empty()) + { + if (!source.GetUser()) + return; + + std::deque queue; + source.GetAccount()->GetChannelReferences(queue); + + unsigned count = 0; + for (unsigned i = 0; i < queue.size(); ++i) + { + ChannelInfo *ci = queue[i]; + + if (!ci->c || !source.AccessFor(ci).HasPriv("UNBAN")) + continue; + + FOREACH_MOD(OnChannelUnban, (source.GetUser(), ci)); + + for (unsigned j = 0; j < modes.size(); ++j) + if (ci->c->Unban(source.GetUser(), modes[j]->name, true)) + ++count; + } + + Log(LOG_COMMAND, source, this, NULL) << "on all channels"; + source.Reply(_("You have been unbanned from %d channels."), count); + + return; + } + + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + if (ci->c == NULL) + { + source.Reply(CHAN_X_NOT_IN_USE, ci->name.c_str()); + return; + } + + if (!source.AccessFor(ci).HasPriv("UNBAN") && !source.HasPriv("chanserv/kick")) + { + source.Reply(ACCESS_DENIED); + return; + } + + User *u2 = source.GetUser(); + if (params.size() > 1) + u2 = User::Find(params[1], true); + + if (!u2) + { + source.Reply(NICK_X_NOT_IN_USE, params[1].c_str()); + return; + } + + bool override = !source.AccessFor(ci).HasPriv("UNBAN") && source.HasPriv("chanserv/kick"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to unban " << u2->nick; + + FOREACH_MOD(OnChannelUnban, (u2, ci)); + + for (unsigned i = 0; i < modes.size(); ++i) + ci->c->Unban(u2, modes[i]->name, source.GetUser() == u2); + if (u2 == source.GetUser()) + source.Reply(_("You have been unbanned from \002%s\002."), ci->c->name.c_str()); + else + source.Reply(_("\002%s\002 has been unbanned from \002%s\002."), u2->nick.c_str(), ci->c->name.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Tells %s to remove all bans preventing you or the given\n" + "user from entering the given channel. If no channel is\n" + "given, all bans affecting you in channels you have access\n" + "in are removed.\n" + " \n" + "By default, limited to AOPs or those with level 5 access and above\n" + "on the channel."), source.service->nick.c_str()); + return true; + } +}; + +class CSUnban : public Module +{ + CommandCSUnban commandcsunban; + + public: + CSUnban(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcsunban(this) + { + + } +}; + +MODULE_INIT(CSUnban) diff --git a/modules/commands/cs_updown.cpp b/modules/commands/cs_updown.cpp new file mode 100644 index 0000000..5fc6f86 --- /dev/null +++ b/modules/commands/cs_updown.cpp @@ -0,0 +1,243 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandCSUp : public Command +{ + void SetModes(User *u, Channel *c) + { + if (!c->ci) + return; + + /* whether or not we are giving modes */ + bool giving = true; + /* whether or not we have given a mode */ + bool given = false; + AccessGroup u_access = c->ci->AccessFor(u); + + for (unsigned i = 0; i < ModeManager::GetStatusChannelModesByRank().size(); ++i) + { + ChannelModeStatus *cm = ModeManager::GetStatusChannelModesByRank()[i]; + bool has_priv = u_access.HasPriv("AUTO" + cm->name) || u_access.HasPriv(cm->name); + + if (has_priv) + { + /* Always give op. If we have already given one mode, don't give more until it has a symbol */ + if (cm->name == "OP" || !given || (giving && cm->symbol)) + { + c->SetMode(NULL, cm, u->GetUID(), false); + /* Now if this contains a symbol don't give any more modes, to prevent setting +qaohv etc on users */ + giving = !cm->symbol; + given = true; + } + } + } + } + public: + CommandCSUp(Module *creator) : Command(creator, "chanserv/up", 0, 2) + { + this->SetDesc(_("Updates a selected nicks status on a channel")); + this->SetSyntax(_("[\037channel\037 [\037nick\037]]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (params.empty()) + { + if (!source.GetUser()) + return; + for (User::ChanUserList::iterator it = source.GetUser()->chans.begin(); it != source.GetUser()->chans.end(); ++it) + { + Channel *c = it->second->chan; + SetModes(source.GetUser(), c); + } + Log(LOG_COMMAND, source, this, NULL) << "on all channels to update their status modes"; + } + else + { + const Anope::string &channel = params[0]; + const Anope::string &nick = params.size() > 1 ? params[1] : source.GetNick(); + + Channel *c = Channel::Find(channel); + + if (c == NULL) + { + source.Reply(CHAN_X_NOT_IN_USE, channel.c_str()); + return; + } + else if (!c->ci) + { + source.Reply(CHAN_X_NOT_REGISTERED, channel.c_str()); + return; + } + + User *u = User::Find(nick, true); + User *srcu = source.GetUser(); + bool override = false; + + if (u == NULL) + { + source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); + return; + } + else if (srcu && !srcu->FindChannel(c)) + { + source.Reply(_("You must be in \002%s\002 to use this command."), c->name.c_str()); + return; + } + else if (!u->FindChannel(c)) + { + source.Reply(NICK_X_NOT_ON_CHAN, nick.c_str(), channel.c_str()); + return; + } + else if (source.GetUser() && u != source.GetUser() && c->ci->HasExt("PEACE")) + { + if (c->ci->AccessFor(u) >= c->ci->AccessFor(source.GetUser())) + { + if (source.HasPriv("chanserv/administration")) + override = true; + else + { + source.Reply(ACCESS_DENIED); + return; + } + } + } + + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, c->ci) << "to update the status modes of " << u->nick; + SetModes(u, c); + } + + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Updates a selected nicks status modes on a channel. If \037nick\037 is\n" + "omitted then your status is updated. If \037channel\037 is omitted then\n" + "your channel status is updated on every channel you are in.")); + return true; + } +}; + +class CommandCSDown : public Command +{ + void RemoveAll(User *u, Channel *c) + { + ChanUserContainer *cu = c->FindUser(u); + if (cu != NULL) + for (size_t i = cu->status.Modes().length(); i > 0;) + c->RemoveMode(NULL, ModeManager::FindChannelModeByChar(cu->status.Modes()[--i]), u->GetUID()); + } + + public: + CommandCSDown(Module *creator) : Command(creator, "chanserv/down", 0, 2) + { + this->SetDesc(_("Removes a selected nicks status from a channel")); + this->SetSyntax(_("[\037channel\037 [\037nick\037]]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (params.empty()) + { + if (!source.GetUser()) + return; + for (User::ChanUserList::iterator it = source.GetUser()->chans.begin(); it != source.GetUser()->chans.end(); ++it) + { + Channel *c = it->second->chan; + RemoveAll(source.GetUser(), c); + } + Log(LOG_COMMAND, source, this, NULL) << "on all channels to remove their status modes"; + } + else + { + const Anope::string &channel = params[0]; + const Anope::string &nick = params.size() > 1 ? params[1] : source.GetNick(); + + Channel *c = Channel::Find(channel); + + if (c == NULL) + { + source.Reply(CHAN_X_NOT_IN_USE, channel.c_str()); + return; + } + else if (!c->ci) + { + source.Reply(CHAN_X_NOT_REGISTERED, channel.c_str()); + return; + } + + User *u = User::Find(nick, true); + User *srcu = source.GetUser(); + bool override = false; + + if (u == NULL) + { + source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); + return; + } + else if (srcu && !srcu->FindChannel(c)) + { + source.Reply(_("You must be in \002%s\002 to use this command."), c->name.c_str()); + return; + } + else if (!u->FindChannel(c)) + { + source.Reply(NICK_X_NOT_ON_CHAN, nick.c_str(), channel.c_str()); + return; + } + else if (source.GetUser() && u != source.GetUser() && c->ci->HasExt("PEACE")) + { + if (c->ci->AccessFor(u) >= c->ci->AccessFor(source.GetUser())) + { + if (source.HasPriv("chanserv/administration")) + override = true; + else + { + source.Reply(ACCESS_DENIED); + return; + } + } + } + + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, c->ci) << "to remove the status modes from " << u->nick; + RemoveAll(u, c); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Removes a selected nicks status modes on a channel. If \037nick\037 is\n" + "omitted then your status is removed. If \037channel\037 is omitted then\n" + "your channel status is removed on every channel you are in.")); + return true; + } +}; + +class CSUpDown : public Module +{ + CommandCSUp commandcsup; + CommandCSDown commandcsdown; + + public: + CSUpDown(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcsup(this), commandcsdown(this) + { + + } +}; + +MODULE_INIT(CSUpDown) diff --git a/modules/commands/cs_xop.cpp b/modules/commands/cs_xop.cpp new file mode 100644 index 0000000..f4e2dd3 --- /dev/null +++ b/modules/commands/cs_xop.cpp @@ -0,0 +1,627 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +namespace +{ + std::vector order; + std::map > permissions; +} + +class XOPChanAccess : public ChanAccess +{ + public: + Anope::string type; + + XOPChanAccess(AccessProvider *p) : ChanAccess(p) + { + } + + bool HasPriv(const Anope::string &priv) const anope_override + { + for (std::vector::iterator it = std::find(order.begin(), order.end(), this->type); it != order.end(); ++it) + { + const std::vector &privs = permissions[*it]; + if (std::find(privs.begin(), privs.end(), priv) != privs.end()) + return true; + } + return false; + } + + Anope::string AccessSerialize() const anope_override + { + return this->type; + } + + void AccessUnserialize(const Anope::string &data) anope_override + { + this->type = data; + } + + static Anope::string DetermineLevel(const ChanAccess *access) + { + if (access->provider->name == "access/xop") + { + const XOPChanAccess *xaccess = anope_dynamic_static_cast(access); + return xaccess->type; + } + else + { + std::map count; + + for (std::map >::const_iterator it = permissions.begin(), it_end = permissions.end(); it != it_end; ++it) + { + int &c = count[it->first]; + const std::vector &perms = it->second; + for (unsigned i = 0; i < perms.size(); ++i) + if (access->HasPriv(perms[i])) + ++c; + } + + Anope::string max; + int maxn = 0; + for (std::map::iterator it = count.begin(), it_end = count.end(); it != it_end; ++it) + if (it->second > maxn) + { + maxn = it->second; + max = it->first; + } + + return max; + } + } +}; + +class XOPAccessProvider : public AccessProvider +{ + public: + XOPAccessProvider(Module *o) : AccessProvider(o, "access/xop") + { + } + + ChanAccess *Create() anope_override + { + return new XOPChanAccess(this); + } +}; + +class CommandCSXOP : public Command +{ + private: + void DoAdd(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + Anope::string mask = params.size() > 2 ? params[2] : ""; + + if (mask.empty()) + { + this->OnSyntaxError(source, "ADD"); + return; + } + + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, channel %s list modification is temporarily disabled."), source.command.c_str()); + return; + } + + AccessGroup access = source.AccessFor(ci); + const ChanAccess *highest = access.Highest(); + bool override = false; + const NickAlias *na = NULL; + + std::vector::iterator cmd_it = std::find(order.begin(), order.end(), source.command.upper()), + access_it = highest ? std::find(order.begin(), order.end(), XOPChanAccess::DetermineLevel(highest)) : order.end(); + + if (!access.founder && (!access.HasPriv("ACCESS_CHANGE") || cmd_it <= access_it)) + { + if (source.HasPriv("chanserv/access/modify")) + override = true; + else + { + source.Reply(ACCESS_DENIED); + return; + } + } + + if (IRCD->IsChannelValid(mask)) + { + if (Config->GetModule("chanserv")->Get("disallow_channel_access")) + { + source.Reply(_("Channels may not be on access lists.")); + return; + } + + ChannelInfo *targ_ci = ChannelInfo::Find(mask); + if (targ_ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, mask.c_str()); + return; + } + else if (ci == targ_ci) + { + source.Reply(_("You can't add a channel to its own access list.")); + return; + } + + mask = targ_ci->name; + } + else + { + na = NickAlias::Find(mask); + if (!na && Config->GetModule("chanserv")->Get("disallow_hostmask_access")) + { + source.Reply(_("Masks and unregistered users may not be on access lists.")); + return; + } + else if (mask.find_first_of("!*@") == Anope::string::npos && !na) + { + User *targ = User::Find(mask, true); + if (targ != NULL) + mask = "*!*@" + targ->GetDisplayedHost(); + else + { + source.Reply(NICK_X_NOT_REGISTERED, mask.c_str()); + return; + } + } + + if (na) + mask = na->nick; + } + + for (unsigned i = 0; i < ci->GetAccessCount(); ++i) + { + const ChanAccess *a = ci->GetAccess(i); + + if ((na && na->nc == a->GetAccount()) || mask.equals_ci(a->Mask())) + { + if ((!highest || *a >= *highest) && !access.founder && !source.HasPriv("chanserv/access/modify")) + { + source.Reply(ACCESS_DENIED); + return; + } + + delete ci->EraseAccess(i); + break; + } + } + + unsigned access_max = Config->GetModule("chanserv")->Get("accessmax", "1024"); + if (access_max && ci->GetDeepAccessCount() >= access_max) + { + source.Reply(_("Sorry, you can only have %d access entries on a channel, including access entries from other channels."), access_max); + return; + } + + ServiceReference provider("AccessProvider", "access/xop"); + if (!provider) + return; + XOPChanAccess *acc = anope_dynamic_static_cast(provider->Create()); + acc->SetMask(mask, ci); + acc->creator = source.GetNick(); + acc->type = source.command.upper(); + acc->last_seen = 0; + acc->created = Anope::CurTime; + ci->AddAccess(acc); + + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to add " << mask; + + FOREACH_MOD(OnAccessAdd, (ci, source, acc)); + source.Reply(_("\002%s\002 added to %s %s list."), acc->Mask().c_str(), ci->name.c_str(), source.command.c_str()); + } + + void DoDel(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + NickCore *nc = source.nc; + Anope::string mask = params.size() > 2 ? params[2] : ""; + + if (mask.empty()) + { + this->OnSyntaxError(source, "DEL"); + return; + } + + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, channel %s list modification is temporarily disabled."), source.command.c_str()); + return; + } + + if (!ci->GetAccessCount()) + { + source.Reply(_("%s %s list is empty."), ci->name.c_str(), source.command.c_str()); + return; + } + + AccessGroup access = source.AccessFor(ci); + const ChanAccess *highest = access.Highest(); + bool override = false; + + if (!isdigit(mask[0]) && mask.find_first_of("#!*@") == Anope::string::npos && !NickAlias::Find(mask)) + { + User *targ = User::Find(mask, true); + if (targ != NULL) + mask = "*!*@" + targ->GetDisplayedHost(); + else + { + source.Reply(NICK_X_NOT_REGISTERED, mask.c_str()); + return; + } + } + + std::vector::iterator cmd_it = std::find(order.begin(), order.end(), source.command.upper()), + access_it = highest ? std::find(order.begin(), order.end(), XOPChanAccess::DetermineLevel(highest)) : order.end(); + + if (!mask.equals_ci(nc->display) && !access.founder && (!access.HasPriv("ACCESS_CHANGE") || cmd_it <= access_it)) + { + if (source.HasPriv("chanserv/access/modify")) + override = true; + else + { + source.Reply(ACCESS_DENIED); + return; + } + } + + /* Special case: is it a number/list? Only do search if it isn't. */ + if (isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) + { + class XOPDelCallback : public NumberList + { + CommandSource &source; + ChannelInfo *ci; + Command *c; + unsigned deleted; + Anope::string nicks; + bool override; + public: + XOPDelCallback(CommandSource &_source, ChannelInfo *_ci, Command *_c, bool _override, const Anope::string &numlist) : NumberList(numlist, true), source(_source), ci(_ci), c(_c), deleted(0), override(_override) + { + } + + ~XOPDelCallback() + { + if (!deleted) + source.Reply(_("No matching entries on %s %s list."), ci->name.c_str(), source.command.c_str()); + else + { + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, c, ci) << "to delete " << nicks; + + if (deleted == 1) + source.Reply(_("Deleted one entry from %s %s list."), ci->name.c_str(), source.command.c_str()); + else + source.Reply(_("Deleted %d entries from %s %s list."), deleted, ci->name.c_str(), source.command.c_str()); + } + } + + void HandleNumber(unsigned number) anope_override + { + if (!number || number > ci->GetAccessCount()) + return; + + ChanAccess *caccess = ci->GetAccess(number - 1); + + if (caccess->provider->name != "access/xop" || this->source.command.upper() != caccess->AccessSerialize()) + return; + + ++deleted; + if (!nicks.empty()) + nicks += ", " + caccess->Mask(); + else + nicks = caccess->Mask(); + + ci->EraseAccess(number - 1); + FOREACH_MOD(OnAccessDel, (ci, source, caccess)); + delete caccess; + } + } + delcallback(source, ci, this, override, mask); + delcallback.Process(); + } + else + { + for (unsigned i = 0; i < ci->GetAccessCount(); ++i) + { + ChanAccess *a = ci->GetAccess(i); + + if (a->provider->name != "access/xop" || source.command.upper() != a->AccessSerialize()) + continue; + + if (a->Mask().equals_ci(mask)) + { + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to delete " << a->Mask(); + + source.Reply(_("\002%s\002 deleted from %s %s list."), a->Mask().c_str(), ci->name.c_str(), source.command.c_str()); + + ci->EraseAccess(i); + FOREACH_MOD(OnAccessDel, (ci, source, a)); + delete a; + + return; + } + } + + source.Reply(_("\002%s\002 not found on %s %s list."), mask.c_str(), ci->name.c_str(), source.command.c_str()); + } + } + + void DoList(CommandSource &source, ChannelInfo *ci, const std::vector ¶ms) + { + + const Anope::string &nick = params.size() > 2 ? params[2] : ""; + + AccessGroup access = source.AccessFor(ci); + + if (!access.HasPriv("ACCESS_LIST") && !source.HasPriv("chanserv/access/list")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (!ci->GetAccessCount()) + { + source.Reply(_("%s %s list is empty."), ci->name.c_str(), source.command.c_str()); + return; + } + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Mask")); + + if (!nick.empty() && nick.find_first_not_of("1234567890,-") == Anope::string::npos) + { + class XOPListCallback : public NumberList + { + ListFormatter &list; + ChannelInfo *ci; + CommandSource &source; + public: + XOPListCallback(ListFormatter &_list, ChannelInfo *_ci, const Anope::string &numlist, CommandSource &src) : NumberList(numlist, false), list(_list), ci(_ci), source(src) + { + } + + void HandleNumber(unsigned Number) anope_override + { + if (!Number || Number > ci->GetAccessCount()) + return; + + const ChanAccess *a = ci->GetAccess(Number - 1); + + if (a->provider->name != "access/xop" || this->source.command.upper() != a->AccessSerialize()) + return; + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(Number); + entry["Mask"] = a->Mask(); + this->list.AddEntry(entry); + } + } nl_list(list, ci, nick, source); + nl_list.Process(); + } + else + { + for (unsigned i = 0, end = ci->GetAccessCount(); i < end; ++i) + { + const ChanAccess *a = ci->GetAccess(i); + + if (a->provider->name != "access/xop" || source.command.upper() != a->AccessSerialize()) + continue; + else if (!nick.empty() && !Anope::Match(a->Mask(), nick)) + continue; + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(i + 1); + entry["Mask"] = a->Mask(); + list.AddEntry(entry); + } + } + + if (list.IsEmpty()) + source.Reply(_("No matching entries on %s access list."), ci->name.c_str()); + else + { + std::vector replies; + list.Process(replies); + + source.Reply(_("%s list for %s"), source.command.c_str(), ci->name.c_str()); + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + } + + void DoClear(CommandSource &source, ChannelInfo *ci) + { + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, channel %s list modification is temporarily disabled."), source.command.c_str()); + return; + } + + if (!ci->GetAccessCount()) + { + source.Reply(_("%s %s list is empty."), ci->name.c_str(), source.command.c_str()); + return; + } + + if (!source.AccessFor(ci).HasPriv("FOUNDER") && !source.HasPriv("chanserv/access/modify")) + { + source.Reply(ACCESS_DENIED); + return; + } + + bool override = !source.AccessFor(ci).HasPriv("FOUNDER"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to clear the access list"; + + for (unsigned i = ci->GetAccessCount(); i > 0; --i) + { + const ChanAccess *access = ci->GetAccess(i - 1); + + if (access->provider->name != "access/xop" || source.command.upper() != access->AccessSerialize()) + continue; + + delete ci->EraseAccess(i - 1); + } + + FOREACH_MOD(OnAccessClear, (ci, source)); + + source.Reply(_("Channel %s %s list has been cleared."), ci->name.c_str(), source.command.c_str()); + } + + public: + CommandCSXOP(Module *modname) : Command(modname, "chanserv/xop", 2, 4) + { + this->SetSyntax(_("\037channel\037 ADD \037mask\037")); + this->SetSyntax(_("\037channel\037 DEL {\037mask\037 | \037entry-num\037 | \037list\037}")); + this->SetSyntax(_("\037channel\037 LIST [\037mask\037 | \037list\037]")); + this->SetSyntax(_("\037channel\037 CLEAR")); + } + + const Anope::string GetDesc(CommandSource &source) const anope_override + { + return Anope::printf(Language::Translate(source.GetAccount(), _("Modify the list of %s users")), source.command.upper().c_str()); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + const Anope::string &cmd = params[1]; + + if (cmd.equals_ci("ADD")) + return this->DoAdd(source, ci, params); + else if (cmd.equals_ci("DEL")) + return this->DoDel(source, ci, params); + else if (cmd.equals_ci("LIST")) + return this->DoList(source, ci, params); + else if (cmd.equals_ci("CLEAR")) + return this->DoClear(source, ci); + else + this->OnSyntaxError(source, ""); + } + + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + const Anope::string &cmd = source.command.upper(); + + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Maintains the \002%s list\002 for a channel. Users who match an access entry\n" + "on the %s list receive the following privileges:\n" + " "), cmd.c_str(), cmd.c_str()); + + Anope::string buf; + for (unsigned i = 0; i < permissions[cmd].size(); ++i) + { + buf += ", " + permissions[cmd][i]; + if (buf.length() > 75) + { + source.Reply(" %s\n", buf.substr(2).c_str()); + buf.clear(); + } + } + if (!buf.empty()) + { + source.Reply(" %s\n", buf.substr(2).c_str()); + buf.clear(); + } + + source.Reply(_(" \n" + "The \002%s ADD\002 command adds the given nickname to the\n" + "%s list.\n" + " \n" + "The \002%s DEL\002 command removes the given nick from the\n" + "%s list. If a list of entry numbers is given, those\n" + "entries are deleted. (See the example for LIST below.)\n" + " \n" + "The \002%s LIST\002 command displays the %s list. If\n" + "a wildcard mask is given, only those entries matching the\n" + "mask are displayed. If a list of entry numbers is given,\n" + "only those entries are shown; for example:\n" + " \002%s #channel LIST 2-5,7-9\002\n" + " Lists %s entries numbered 2 through 5 and\n" + " 7 through 9.\n" + " \n" + "The \002%s CLEAR\002 command clears all entries of the\n" + "%s list."), cmd.c_str(), cmd.c_str(), cmd.c_str(), cmd.c_str(), + cmd.c_str(), cmd.c_str(), cmd.c_str(), cmd.c_str(), cmd.c_str(), cmd.c_str()); + BotInfo *access_bi, *flags_bi; + Anope::string access_cmd, flags_cmd; + Command::FindCommandFromService("chanserv/access", access_bi, access_cmd); + Command::FindCommandFromService("chanserv/flags", flags_bi, flags_cmd); + if (!access_cmd.empty() || !flags_cmd.empty()) + { + source.Reply(_("Alternative methods of modifying channel access lists are\n" + "available. ")); + if (!access_cmd.empty()) + source.Reply(_("See \002%s%s HELP %s\002 for more information\n" + "about the access list."), Config->StrictPrivmsg.c_str(), access_bi->nick.c_str(), access_cmd.c_str()); + if (!flags_cmd.empty()) + source.Reply(_("See \002%s%s HELP %s\002 for more information\n" + "about the flags system."), Config->StrictPrivmsg.c_str(), flags_bi->nick.c_str(), flags_cmd.c_str()); + } + return true; + } +}; + +class CSXOP : public Module +{ + XOPAccessProvider accessprovider; + CommandCSXOP commandcsxop; + + public: + CSXOP(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + accessprovider(this), commandcsxop(this) + { + this->SetPermanent(true); + + } + + void OnReload(Configuration::Conf *conf) anope_override + { + order.clear(); + permissions.clear(); + + for (int i = 0; i < conf->CountBlock("privilege"); ++i) + { + Configuration::Block *block = conf->GetBlock("privilege", i); + const Anope::string &pname = block->Get("name"); + + Privilege *p = PrivilegeManager::FindPrivilege(pname); + if (p == NULL) + continue; + + const Anope::string &xop = block->Get("xop"); + if (pname.empty() || xop.empty()) + continue; + + permissions[xop].push_back(pname); + } + + for (int i = 0; i < conf->CountBlock("command"); ++i) + { + Configuration::Block *block = conf->GetBlock("command", i); + const Anope::string &cname = block->Get("name"), + &cserv = block->Get("command"); + if (cname.empty() || cserv != "chanserv/xop") + continue; + + order.push_back(cname); + } + } +}; + +MODULE_INIT(CSXOP) diff --git a/modules/commands/gl_global.cpp b/modules/commands/gl_global.cpp new file mode 100644 index 0000000..b4060f0 --- /dev/null +++ b/modules/commands/gl_global.cpp @@ -0,0 +1,66 @@ +/* Global core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandGLGlobal : public Command +{ + ServiceReference GService; + + public: + CommandGLGlobal(Module *creator) : Command(creator, "global/global", 1, 1), GService("GlobalService", "Global") + { + this->SetDesc(_("Send a message to all users")); + this->SetSyntax(_("\037message\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &msg = params[0]; + + if (!GService) + source.Reply("No global reference, is global loaded?"); + else + { + Log(LOG_ADMIN, source, this); + GService->SendGlobal(NULL, source.GetNick(), msg); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + Reference sender; + if (GService) + sender = GService->GetDefaultSender(); + if (!sender) + sender = source.service; + + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows Administrators to send messages to all users on the\n" + "network. The message will be sent from the nick \002%s\002."), sender->nick.c_str()); + return true; + } +}; + +class GLGlobal : public Module +{ + CommandGLGlobal commandglglobal; + + public: + GLGlobal(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandglglobal(this) + { + + } +}; + +MODULE_INIT(GLGlobal) diff --git a/modules/commands/greet.cpp b/modules/commands/greet.cpp new file mode 100644 index 0000000..7d1f2e0 --- /dev/null +++ b/modules/commands/greet.cpp @@ -0,0 +1,216 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandBSSetGreet : public Command +{ + public: + CommandBSSetGreet(Module *creator, const Anope::string &sname = "botserv/set/greet") : Command(creator, sname, 2, 2) + { + this->SetDesc(_("Enable greet messages")); + this->SetSyntax(_("\037channel\037 {\037ON|OFF\037}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci = ChannelInfo::Find(params[0]); + const Anope::string &value = params[1]; + + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + if (!source.HasPriv("botserv/administration") && !source.AccessFor(ci).HasPriv("SET")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + if (value.equals_ci("ON")) + { + bool override = !source.AccessFor(ci).HasPriv("SET"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to enable greets"; + + ci->Extend("BS_GREET"); + source.Reply(_("Greet mode is now \002on\002 on channel %s."), ci->name.c_str()); + } + else if (value.equals_ci("OFF")) + { + bool override = !source.AccessFor(ci).HasPriv("SET"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to disable greets"; + + ci->Shrink("BS_GREET"); + source.Reply(_("Greet mode is now \002off\002 on channel %s."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, source.command); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(_(" \n" + "Enables or disables \002greet\002 mode on a channel.\n" + "When it is enabled, the bot will display greet\n" + "messages of users joining the channel, provided\n" + "they have enough access to the channel.")); + return true; + } +}; + +class CommandNSSetGreet : public Command +{ + public: + CommandNSSetGreet(Module *creator, const Anope::string &sname = "nickserv/set/greet", size_t min = 0) : Command(creator, sname, min, min + 1) + { + this->SetDesc(_("Associate a greet message with your nickname")); + this->SetSyntax(_("\037message\037")); + } + + void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const NickAlias *na = NickAlias::Find(user); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); + return; + } + NickCore *nc = na->nc; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, nc, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (!param.empty()) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to change the greet of " << nc->display; + nc->Extend("greet", param); + source.Reply(_("Greet message for \002%s\002 changed to \002%s\002."), nc->display.c_str(), param.c_str()); + } + else + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to unset the greet of " << nc->display; + nc->Shrink("greet"); + source.Reply(_("Greet message for \002%s\002 unset."), nc->display.c_str()); + } + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, source.nc->display, params.size() > 0 ? params[0] : ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Makes the given message the greet of your nickname, that\n" + "will be displayed when joining a channel that has GREET\n" + "option enabled, provided that you have the necessary\n" + "access on it.")); + return true; + } +}; + +class CommandNSSASetGreet : public CommandNSSetGreet +{ + public: + CommandNSSASetGreet(Module *creator) : CommandNSSetGreet(creator, "nickserv/saset/greet", 1) + { + this->ClearSyntax(); + this->SetSyntax(_("\037nickname\037 \037message\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, params[0], params.size() > 1 ? params[1] : ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Makes the given message the greet of the nickname, that\n" + "will be displayed when joining a channel that has GREET\n" + "option enabled, provided that the user has the necessary\n" + "access on it.")); + return true; + } +}; + +class Greet : public Module +{ + /* channel setting for whether or not greet should be shown */ + SerializableExtensibleItem bs_greet; + /* user greets */ + SerializableExtensibleItem ns_greet; + + CommandBSSetGreet commandbssetgreet; + CommandNSSetGreet commandnssetgreet; + CommandNSSASetGreet commandnssasetgreet; + + public: + Greet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + bs_greet(this, "BS_GREET"), + ns_greet(this, "greet"), + commandbssetgreet(this), + commandnssetgreet(this), commandnssasetgreet(this) + { + } + + void OnJoinChannel(User *user, Channel *c) anope_override + { + /* Only display the greet if the main uplink we're connected + * to has synced, or we'll get greet-floods when the net + * recovers from a netsplit. -GD + */ + if (!c->ci || !c->ci->bi || !user->server->IsSynced() || !user->Account()) + return; + + Anope::string *greet = ns_greet.Get(user->Account()); + if (bs_greet.HasExt(c->ci) && greet != NULL && !greet->empty() && c->FindUser(c->ci->bi) && c->ci->AccessFor(user).HasPriv("GREET")) + { + IRCD->SendPrivmsg(*c->ci->bi, c->name, "[%s] %s", user->Account()->display.c_str(), greet->c_str()); + c->ci->bi->lastmsg = Anope::CurTime; + } + } + + void OnNickInfo(CommandSource &source, NickAlias *na, InfoFormatter &info, bool show_hidden) anope_override + { + Anope::string *greet = ns_greet.Get(na->nc); + if (greet != NULL) + info[_("Greet")] = *greet; + } + + void OnBotInfo(CommandSource &source, BotInfo *bi, ChannelInfo *ci, InfoFormatter &info) anope_override + { + if (bs_greet.HasExt(ci)) + info.AddOption(_("Greet")); + } +}; + +MODULE_INIT(Greet) diff --git a/modules/commands/help.cpp b/modules/commands/help.cpp new file mode 100644 index 0000000..eb417bb --- /dev/null +++ b/modules/commands/help.cpp @@ -0,0 +1,205 @@ +/* Core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandHelp : public Command +{ + static const unsigned help_wrap_len = 40; + + static CommandGroup *FindGroup(const Anope::string &name) + { + for (unsigned i = 0; i < Config->CommandGroups.size(); ++i) + { + CommandGroup &gr = Config->CommandGroups[i]; + if (gr.name == name) + return &gr; + } + + return NULL; + } + + public: + CommandHelp(Module *creator) : Command(creator, "generic/help", 0) + { + this->SetDesc(_("Displays this list and give information about commands")); + this->AllowUnregistered(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + EventReturn MOD_RESULT; + FOREACH_RESULT(OnPreHelp, MOD_RESULT, (source, params)); + if (MOD_RESULT == EVENT_STOP) + return; + + Anope::string source_command = source.command; + const BotInfo *bi = source.service; + const CommandInfo::map &map = source.c ? Config->Fantasy : bi->commands; + bool hide_privileged_commands = Config->GetBlock("options")->Get("hideprivilegedcommands"), + hide_registered_commands = Config->GetBlock("options")->Get("hideregisteredcommands"); + + if (params.empty() || params[0].equals_ci("ALL")) + { + bool all = !params.empty() && params[0].equals_ci("ALL"); + typedef std::map > GroupInfo; + GroupInfo groups; + + if (all) + source.Reply(_("All available commands for \002%s\002:"), source.service->nick.c_str()); + + for (CommandInfo::map::const_iterator it = map.begin(), it_end = map.end(); it != it_end; ++it) + { + const Anope::string &c_name = it->first; + const CommandInfo &info = it->second; + + if (info.hide) + continue; + + // Smaller command exists + Anope::string cmd; + spacesepstream(c_name).GetToken(cmd, 0); + if (cmd != it->first && map.count(cmd)) + continue; + + ServiceReference c("Command", info.name); + if (!c) + continue; + + if (hide_registered_commands && !c->AllowUnregistered() && !source.GetAccount()) + continue; + + if (hide_privileged_commands && !info.permission.empty() && !source.HasCommand(info.permission)) + continue; + + if (!info.group.empty() && !all) + { + CommandGroup *gr = FindGroup(info.group); + if (gr != NULL) + { + groups[gr].push_back(c_name); + continue; + } + } + + source.command = c_name; + c->OnServHelp(source); + + } + + for (GroupInfo::iterator it = groups.begin(), it_end = groups.end(); it != it_end; ++it) + { + CommandGroup *gr = it->first; + + source.Reply(" "); + source.Reply("%s", gr->description.c_str()); + + Anope::string buf; + for (std::list::iterator it2 = it->second.begin(), it2_end = it->second.end(); it2 != it2_end; ++it2) + { + const Anope::string &c_name = *it2; + + buf += ", " + c_name; + + if (buf.length() > help_wrap_len) + { + source.Reply(" %s", buf.substr(2).c_str()); + buf.clear(); + } + } + if (buf.length() > 2) + { + source.Reply(" %s", buf.substr(2).c_str()); + buf.clear(); + } + } + if (!groups.empty()) + { + source.Reply(" "); + source.Reply(_("Use the \002%s ALL\002 command to list all commands and their descriptions."), source_command.c_str()); + } + } + else + { + bool helped = false; + for (unsigned max = params.size(); max > 0; --max) + { + Anope::string full_command; + for (unsigned i = 0; i < max; ++i) + full_command += " " + params[i]; + full_command.erase(full_command.begin()); + + CommandInfo::map::const_iterator it = map.find(full_command); + if (it == map.end()) + continue; + + const CommandInfo &info = it->second; + + ServiceReference c("Command", info.name); + if (!c) + continue; + + if (hide_privileged_commands && !info.permission.empty() && !source.HasCommand(info.permission)) + continue; + + // Allow unregistered users to see help for commands that they explicitly request help for + + const Anope::string &subcommand = params.size() > max ? params[max] : ""; + source.command = it->first; + if (!c->OnHelp(source, subcommand)) + continue; + + helped = true; + + /* Inform the user what permission is required to use the command */ + if (!info.permission.empty()) + { + source.Reply(" "); + source.Reply(_("Access to this command requires the permission \002%s\002 to be present in your opertype."), info.permission.c_str()); + } + if (!c->AllowUnregistered() && !source.nc) + { + if (info.permission.empty()) + source.Reply(" "); + source.Reply( _("You need to be identified to use this command.")); + } + /* User doesn't have the proper permission to use this command */ + else if (!info.permission.empty() && !source.HasCommand(info.permission)) + { + source.Reply(_("You cannot use this command.")); + } + + break; + } + + if (helped == false) + source.Reply(_("No help available for \002%s\002."), params[0].c_str()); + } + + FOREACH_MOD(OnPostHelp, (source, params)); + + return; + } +}; + +class Help : public Module +{ + CommandHelp commandhelp; + + public: + Help(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandhelp(this) + { + + } +}; + +MODULE_INIT(Help) diff --git a/modules/commands/hs_del.cpp b/modules/commands/hs_del.cpp new file mode 100644 index 0000000..cda9ea1 --- /dev/null +++ b/modules/commands/hs_del.cpp @@ -0,0 +1,113 @@ +/* HostServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandHSDel : public Command +{ + public: + CommandHSDel(Module *creator) : Command(creator, "hostserv/del", 1, 1) + { + this->SetDesc(_("Delete the vhost of another user")); + this->SetSyntax(_("\037nick\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const Anope::string &nick = params[0]; + NickAlias *na = NickAlias::Find(nick); + if (na) + { + Log(LOG_ADMIN, source, this) << "for user " << na->nick; + FOREACH_MOD(OnDeleteVhost, (na)); + na->RemoveVhost(); + source.Reply(_("Vhost for \002%s\002 removed."), nick.c_str()); + } + else + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Deletes the vhost assigned to the given nick from the\n" + "database.")); + return true; + } +}; + +class CommandHSDelAll : public Command +{ + public: + CommandHSDelAll(Module *creator) : Command(creator, "hostserv/delall", 1, 1) + { + this->SetDesc(_("Deletes the vhost for all nicks in a group")); + this->SetSyntax(_("\037nick\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const Anope::string &nick = params[0]; + NickAlias *na = NickAlias::Find(nick); + if (na) + { + FOREACH_MOD(OnDeleteVhost, (na)); + const NickCore *nc = na->nc; + for (unsigned i = 0; i < nc->aliases->size(); ++i) + { + na = nc->aliases->at(i); + na->RemoveVhost(); + } + Log(LOG_ADMIN, source, this) << "for all nicks in group " << nc->display; + source.Reply(_("vhosts for group \002%s\002 have been removed."), nc->display.c_str()); + } + else + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Deletes the vhost for all nicks in the same group as\n" + "that of the given nick.")); + return true; + } +}; + +class HSDel : public Module +{ + CommandHSDel commandhsdel; + CommandHSDelAll commandhsdelall; + + public: + HSDel(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandhsdel(this), commandhsdelall(this) + { + if (!IRCD || !IRCD->CanSetVHost) + throw ModuleException("Your IRCd does not support vhosts"); + } +}; + +MODULE_INIT(HSDel) diff --git a/modules/commands/hs_group.cpp b/modules/commands/hs_group.cpp new file mode 100644 index 0000000..a7dd1b7 --- /dev/null +++ b/modules/commands/hs_group.cpp @@ -0,0 +1,117 @@ +/* HostServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandHSGroup : public Command +{ + bool setting; + + public: + void Sync(const NickAlias *na) + { + if (setting) + return; + + if (!na || !na->HasVhost()) + return; + + setting = true; + for (unsigned i = 0; i < na->nc->aliases->size(); ++i) + { + NickAlias *nick = na->nc->aliases->at(i); + if (nick) + { + nick->SetVhost(na->GetVhostIdent(), na->GetVhostHost(), na->GetVhostCreator()); + FOREACH_MOD(OnSetVhost, (nick)); + } + } + setting = false; + } + + CommandHSGroup(Module *creator) : Command(creator, "hostserv/group", 0, 0), setting(false) + { + this->SetDesc(_("Syncs the vhost for all nicks in a group")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + NickAlias *na = NickAlias::Find(source.GetNick()); + if (na && source.GetAccount() == na->nc && na->HasVhost()) + { + this->Sync(na); + if (!na->GetVhostIdent().empty()) + source.Reply(_("All vhosts in the group \002%s\002 have been set to \002%s\002@\002%s\002."), source.nc->display.c_str(), na->GetVhostIdent().c_str(), na->GetVhostHost().c_str()); + else + source.Reply(_("All vhosts in the group \002%s\002 have been set to \002%s\002."), source.nc->display.c_str(), na->GetVhostHost().c_str()); + } + else + source.Reply(HOST_NOT_ASSIGNED); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command allows users to set the vhost of their\n" + "CURRENT nick to be the vhost for all nicks in the same\n" + "group.")); + return true; + } +}; + +class HSGroup : public Module +{ + CommandHSGroup commandhsgroup; + bool syncongroup; + bool synconset; + + public: + HSGroup(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandhsgroup(this) + { + if (!IRCD || !IRCD->CanSetVHost) + throw ModuleException("Your IRCd does not support vhosts"); + } + + void OnSetVhost(NickAlias *na) anope_override + { + if (!synconset) + return; + + commandhsgroup.Sync(na); + } + + void OnNickGroup(User *u, NickAlias *na) anope_override + { + if (!syncongroup) + return; + + commandhsgroup.Sync(na); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *block = conf->GetModule(this); + syncongroup = block->Get("syncongroup"); + synconset = block->Get("synconset"); + } +}; + +MODULE_INIT(HSGroup) diff --git a/modules/commands/hs_list.cpp b/modules/commands/hs_list.cpp new file mode 100644 index 0000000..354f149 --- /dev/null +++ b/modules/commands/hs_list.cpp @@ -0,0 +1,160 @@ +/* HostServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandHSList : public Command +{ + public: + CommandHSList(Module *creator) : Command(creator, "hostserv/list", 0, 1) + { + this->SetDesc(_("Displays one or more vhost entries")); + this->SetSyntax(_("[\037key\037|\037#X-Y\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &key = !params.empty() ? params[0] : ""; + int from = 0, to = 0, counter = 1; + + /** + * Do a check for a range here, then in the next loop + * we'll only display what has been requested.. + **/ + if (!key.empty() && key[0] == '#') + { + size_t tmp = key.find('-'); + if (tmp == Anope::string::npos || tmp == key.length() || tmp == 1) + { + source.Reply(LIST_INCORRECT_RANGE); + return; + } + for (unsigned i = 1, end = key.length(); i < end; ++i) + { + if (!isdigit(key[i]) && i != tmp) + { + source.Reply(LIST_INCORRECT_RANGE); + return; + } + try + { + from = convertTo(key.substr(1, tmp - 1)); + to = convertTo(key.substr(tmp + 1)); + } + catch (const ConvertException &) { } + } + } + + unsigned display_counter = 0, listmax = Config->GetModule(this->owner)->Get("listmax", "50"); + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Nick")).AddColumn(_("Vhost")).AddColumn(_("Creator")).AddColumn(_("Created")); + + for (nickalias_map::const_iterator it = NickAliasList->begin(), it_end = NickAliasList->end(); it != it_end; ++it) + { + const NickAlias *na = it->second; + + if (!na->HasVhost()) + continue; + + if (!key.empty() && key[0] != '#') + { + if ((Anope::Match(na->nick, key) || Anope::Match(na->GetVhostHost(), key)) && display_counter < listmax) + { + ++display_counter; + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(display_counter); + entry["Nick"] = na->nick; + if (!na->GetVhostIdent().empty()) + entry["Vhost"] = na->GetVhostIdent() + "@" + na->GetVhostHost(); + else + entry["Vhost"] = na->GetVhostHost(); + entry["Creator"] = na->GetVhostCreator(); + entry["Created"] = Anope::strftime(na->GetVhostCreated(), NULL, true); + list.AddEntry(entry); + } + } + else + { + /** + * List the host if its in the display range, and not more + * than NSListMax records have been displayed... + **/ + if (((counter >= from && counter <= to) || (!from && !to)) && display_counter < listmax) + { + ++display_counter; + ListFormatter::ListEntry entry; + entry["Number"] = stringify(display_counter); + entry["Nick"] = na->nick; + if (!na->GetVhostIdent().empty()) + entry["Vhost"] = na->GetVhostIdent() + "@" + na->GetVhostHost(); + else + entry["Vhost"] = na->GetVhostHost(); + entry["Creator"] = na->GetVhostCreator(); + entry["Created"] = Anope::strftime(na->GetVhostCreated(), NULL, true); + list.AddEntry(entry); + } + } + ++counter; + } + + if (!display_counter) + { + source.Reply(_("No records to display.")); + return; + } + + if (!key.empty()) + source.Reply(_("Displayed records matching key \002%s\002 (count: \002%d\002)."), key.c_str(), display_counter); + else + { + if (from) + source.Reply(_("Displayed records from \002%d\002 to \002%d\002."), from, to); + else + source.Reply(_("Displayed all records (count: \002%d\002)."), display_counter); + } + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command lists registered vhosts to the operator.\n" + "If a \037key\037 is specified, only entries whose nick or vhost match\n" + "the pattern given in \037key\037 are displayed e.g. Rob* for all\n" + "entries beginning with \"Rob\"\n" + "If a \037#X-Y\037 style is used, only entries between the range of \002X\002\n" + "and \002Y\002 will be displayed, e.g. \002#1-3\002 will display the first 3\n" + "nick/vhost entries.")); + return true; + } +}; + +class HSList : public Module +{ + CommandHSList commandhslist; + + public: + HSList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandhslist(this) + { + if (!IRCD || !IRCD->CanSetVHost) + throw ModuleException("Your IRCd does not support vhosts"); + } +}; + +MODULE_INIT(HSList) diff --git a/modules/commands/hs_off.cpp b/modules/commands/hs_off.cpp new file mode 100644 index 0000000..24657d4 --- /dev/null +++ b/modules/commands/hs_off.cpp @@ -0,0 +1,69 @@ +/* HostServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandHSOff : public Command +{ + public: + CommandHSOff(Module *creator) : Command(creator, "hostserv/off", 0, 0) + { + this->SetDesc(_("Deactivates your assigned vhost")); + this->RequireUser(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + + const NickAlias *na = NickAlias::Find(u->nick); + if (!na || na->nc != u->Account() || !na->HasVhost()) + na = NickAlias::Find(u->Account()->display); + + if (!na || !na->HasVhost()) + source.Reply(HOST_NOT_ASSIGNED); + else + { + u->vhost.clear(); + IRCD->SendVhostDel(u); + u->UpdateHost(); + Log(LOG_COMMAND, source, this) << "to disable their vhost"; + source.Reply(_("Your vhost was removed and the normal cloaking restored.")); + } + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Deactivates the vhost currently assigned to the nick in use.\n" + "When you use this command any user who performs a /whois\n" + "on you will see your real host/IP address.")); + return true; + } +}; + +class HSOff : public Module +{ + CommandHSOff commandhsoff; + + public: + HSOff(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandhsoff(this) + { + if (!IRCD || !IRCD->CanSetVHost) + throw ModuleException("Your IRCd does not support vhosts"); + } +}; + +MODULE_INIT(HSOff) diff --git a/modules/commands/hs_on.cpp b/modules/commands/hs_on.cpp new file mode 100644 index 0000000..3ff721d --- /dev/null +++ b/modules/commands/hs_on.cpp @@ -0,0 +1,75 @@ +/* HostServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandHSOn : public Command +{ + public: + CommandHSOn(Module *creator) : Command(creator, "hostserv/on", 0, 0) + { + this->SetDesc(_("Activates your assigned vhost")); + this->RequireUser(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!IRCD->CanSetVHost) + return; // HostServ wouldn't even be loaded at this point + + User *u = source.GetUser(); + const NickAlias *na = NickAlias::Find(u->nick); + if (!na || na->nc != u->Account() || !na->HasVhost()) + na = NickAlias::Find(u->Account()->display); + if (na && u->Account() == na->nc && na->HasVhost()) + { + if (!na->GetVhostIdent().empty()) + source.Reply(_("Your vhost of \002%s\002@\002%s\002 is now activated."), na->GetVhostIdent().c_str(), na->GetVhostHost().c_str()); + else + source.Reply(_("Your vhost of \002%s\002 is now activated."), na->GetVhostHost().c_str()); + Log(LOG_COMMAND, source, this) << "to enable their vhost of " << (!na->GetVhostIdent().empty() ? na->GetVhostIdent() + "@" : "") << na->GetVhostHost(); + IRCD->SendVhost(u, na->GetVhostIdent(), na->GetVhostHost()); + u->vhost = na->GetVhostHost(); + if (IRCD->CanSetVIdent && !na->GetVhostIdent().empty()) + u->SetVIdent(na->GetVhostIdent()); + u->UpdateHost(); + } + else + source.Reply(HOST_NOT_ASSIGNED); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Activates the vhost currently assigned to the nick in use.\n" + "When you use this command any user who performs a /whois\n" + "on you will see the vhost instead of your real host/IP address.")); + return true; + } +}; + +class HSOn : public Module +{ + CommandHSOn commandhson; + + public: + HSOn(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandhson(this) + { + if (!IRCD || !IRCD->CanSetVHost) + throw ModuleException("Your IRCd does not support vhosts"); + } +}; + +MODULE_INIT(HSOn) diff --git a/modules/commands/hs_request.cpp b/modules/commands/hs_request.cpp new file mode 100644 index 0000000..4717d0c --- /dev/null +++ b/modules/commands/hs_request.cpp @@ -0,0 +1,394 @@ +/* hs_request.c - Add request and activate functionality to HostServ + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Based on the original module by Rob + * Included in the Anope module pack since Anope 1.7.11 + * Anope Coder: GeniusDex + * + * Please read COPYING and README for further details. + * + * Send bug reports to the Anope Coder instead of the module + * author, because any changes since the inclusion into anope + * are not supported by the original author. + */ + +#include "module.h" + +static ServiceReference memoserv("MemoServService", "MemoServ"); + +static void req_send_memos(Module *me, CommandSource &source, const Anope::string &vIdent, const Anope::string &vHost); + +struct HostRequest : Serializable +{ + Anope::string nick; + Anope::string ident; + Anope::string host; + time_t time; + + HostRequest(Extensible *) : Serializable("HostRequest") { } + + void Serialize(Serialize::Data &data) const anope_override + { + data["nick"] << this->nick; + data["ident"] << this->ident; + data["host"] << this->host; + data.SetType("time", Serialize::Data::DT_INT); data["time"] << this->time; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data) + { + Anope::string snick; + data["nick"] >> snick; + + NickAlias *na = NickAlias::Find(snick); + if (na == NULL) + return NULL; + + HostRequest *req; + if (obj) + req = anope_dynamic_static_cast(obj); + else + req = na->Extend("hostrequest"); + if (req) + { + req->nick = na->nick; + data["ident"] >> req->ident; + data["host"] >> req->host; + data["time"] >> req->time; + } + + return req; + } +}; + +class CommandHSRequest : public Command +{ + bool isvalidchar(char c) + { + if ((c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || (c >= '0' && c <= '9') || c == '.' || c == '-') + return true; + return false; + } + + public: + CommandHSRequest(Module *creator) : Command(creator, "hostserv/request", 1, 1) + { + this->SetDesc(_("Request a vHost for your nick")); + this->SetSyntax(_("vhost")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + User *u = source.GetUser(); + NickAlias *na = NickAlias::Find(source.GetNick()); + if (!na || na->nc != source.GetAccount()) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (source.GetAccount()->HasExt("UNCONFIRMED")) + { + source.Reply(_("You must confirm your account before you may request a vhost.")); + return; + } + + Anope::string rawhostmask = params[0]; + + Anope::string user, host; + size_t a = rawhostmask.find('@'); + + if (a == Anope::string::npos) + host = rawhostmask; + else + { + user = rawhostmask.substr(0, a); + host = rawhostmask.substr(a + 1); + } + + if (host.empty()) + { + this->OnSyntaxError(source, ""); + return; + } + + if (!user.empty()) + { + if (user.length() > Config->GetBlock("networkinfo")->Get("userlen")) + { + source.Reply(HOST_SET_IDENTTOOLONG, Config->GetBlock("networkinfo")->Get("userlen")); + return; + } + else if (!IRCD->CanSetVIdent) + { + source.Reply(HOST_NO_VIDENT); + return; + } + for (Anope::string::iterator s = user.begin(), s_end = user.end(); s != s_end; ++s) + if (!isvalidchar(*s)) + { + source.Reply(HOST_SET_IDENT_ERROR); + return; + } + } + + if (host.length() > Config->GetBlock("networkinfo")->Get("hostlen")) + { + source.Reply(HOST_SET_TOOLONG, Config->GetBlock("networkinfo")->Get("hostlen")); + return; + } + + if (!IRCD->IsHostValid(host)) + { + source.Reply(HOST_SET_ERROR); + return; + } + + time_t send_delay = Config->GetModule("memoserv")->Get("senddelay"); + if (Config->GetModule(this->owner)->Get("memooper") && send_delay > 0 && u && u->lastmemosend + send_delay > Anope::CurTime) + { + source.Reply(_("Please wait %d seconds before requesting a new vHost."), send_delay); + u->lastmemosend = Anope::CurTime; + return; + } + + HostRequest req(na); + req.nick = source.GetNick(); + req.ident = user; + req.host = host; + req.time = Anope::CurTime; + na->Extend("hostrequest", req); + + source.Reply(_("Your vHost has been requested.")); + req_send_memos(owner, source, user, host); + Log(LOG_COMMAND, source, this) << "to request new vhost " << (!user.empty() ? user + "@" : "") << host; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Request the given vHost to be activated for your nick by the\n" + "network administrators. Please be patient while your request\n" + "is being considered.")); + return true; + } +}; + +class CommandHSActivate : public Command +{ + public: + CommandHSActivate(Module *creator) : Command(creator, "hostserv/activate", 1, 1) + { + this->SetDesc(_("Approve the requested vHost of a user")); + this->SetSyntax(_("\037nick\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const Anope::string &nick = params[0]; + + NickAlias *na = NickAlias::Find(nick); + HostRequest *req = na ? na->GetExt("hostrequest") : NULL; + if (req) + { + na->SetVhost(req->ident, req->host, source.GetNick(), req->time); + FOREACH_MOD(OnSetVhost, (na)); + + if (Config->GetModule(this->owner)->Get("memouser") && memoserv) + memoserv->Send(source.service->nick, na->nick, _("[auto memo] Your requested vHost has been approved."), true); + + source.Reply(_("vHost for %s has been activated."), na->nick.c_str()); + Log(LOG_COMMAND, source, this) << "for " << na->nick << " for vhost " << (!req->ident.empty() ? req->ident + "@" : "") << req->host; + na->Shrink("hostrequest"); + } + else + source.Reply(_("No request for nick %s found."), nick.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Activate the requested vHost for the given nick.")); + if (Config->GetModule(this->owner)->Get("memouser")) + source.Reply(_("A memo informing the user will also be sent.")); + + return true; + } +}; + +class CommandHSReject : public Command +{ + public: + CommandHSReject(Module *creator) : Command(creator, "hostserv/reject", 1, 2) + { + this->SetDesc(_("Reject the requested vHost of a user")); + this->SetSyntax(_("\037nick\037 [\037reason\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const Anope::string &nick = params[0]; + const Anope::string &reason = params.size() > 1 ? params[1] : ""; + + NickAlias *na = NickAlias::Find(nick); + HostRequest *req = na ? na->GetExt("hostrequest") : NULL; + if (req) + { + na->Shrink("hostrequest"); + + if (Config->GetModule(this->owner)->Get("memouser") && memoserv) + { + Anope::string message; + if (!reason.empty()) + message = Anope::printf(_("[auto memo] Your requested vHost has been rejected. Reason: %s"), reason.c_str()); + else + message = _("[auto memo] Your requested vHost has been rejected."); + + memoserv->Send(source.service->nick, nick, Language::Translate(source.GetAccount(), message.c_str()), true); + } + + source.Reply(_("vHost for %s has been rejected."), nick.c_str()); + Log(LOG_COMMAND, source, this) << "to reject vhost for " << nick << " (" << (!reason.empty() ? reason : "no reason") << ")"; + } + else + source.Reply(_("No request for nick %s found."), nick.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Reject the requested vHost for the given nick.")); + if (Config->GetModule(this->owner)->Get("memouser")) + source.Reply(_("A memo informing the user will also be sent, which includes the reason for the rejection if supplied.")); + + return true; + } +}; + +class CommandHSWaiting : public Command +{ + public: + CommandHSWaiting(Module *creator) : Command(creator, "hostserv/waiting", 0, 0) + { + this->SetDesc(_("Retrieves the vhost requests")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + unsigned counter = 0; + unsigned display_counter = 0, listmax = Config->GetModule(this->owner)->Get("listmax"); + ListFormatter list(source.GetAccount()); + + list.AddColumn(_("Number")).AddColumn(_("Nick")).AddColumn(_("Vhost")).AddColumn(_("Created")); + + for (nickalias_map::const_iterator it = NickAliasList->begin(), it_end = NickAliasList->end(); it != it_end; ++it) + { + const NickAlias *na = it->second; + HostRequest *hr = na->GetExt("hostrequest"); + if (!hr) + continue; + + if (!listmax || display_counter < listmax) + { + ++display_counter; + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(display_counter); + entry["Nick"] = it->first; + if (!hr->ident.empty()) + entry["Vhost"] = hr->ident + "@" + hr->host; + else + entry["Vhost"] = hr->host; + entry["Created"] = Anope::strftime(hr->time, NULL, true); + list.AddEntry(entry); + } + ++counter; + } + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("Displayed \002%d\002 records (\002%d\002 total)."), display_counter, counter); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command retrieves the vhost requests.")); + + return true; + } +}; + +class HSRequest : public Module +{ + CommandHSRequest commandhsrequest; + CommandHSActivate commandhsactive; + CommandHSReject commandhsreject; + CommandHSWaiting commandhswaiting; + ExtensibleItem hostrequest; + Serialize::Type request_type; + + public: + HSRequest(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandhsrequest(this), commandhsactive(this), + commandhsreject(this), commandhswaiting(this), hostrequest(this, "hostrequest"), request_type("HostRequest", HostRequest::Unserialize) + { + if (!IRCD || !IRCD->CanSetVHost) + throw ModuleException("Your IRCd does not support vhosts"); + } +}; + +static void req_send_memos(Module *me, CommandSource &source, const Anope::string &vIdent, const Anope::string &vHost) +{ + Anope::string host; + std::list >::iterator it, it_end; + + if (!vIdent.empty()) + host = vIdent + "@" + vHost; + else + host = vHost; + + if (Config->GetModule(me)->Get("memooper") && memoserv) + for (unsigned i = 0; i < Oper::opers.size(); ++i) + { + Oper *o = Oper::opers[i]; + + const NickAlias *na = NickAlias::Find(o->name); + if (!na) + continue; + + Anope::string message = Anope::printf(_("[auto memo] vHost \002%s\002 has been requested by %s."), host.c_str(), source.GetNick().c_str()); + + memoserv->Send(source.service->nick, na->nick, message, true); + } +} + +MODULE_INIT(HSRequest) diff --git a/modules/commands/hs_set.cpp b/modules/commands/hs_set.cpp new file mode 100644 index 0000000..c0d12b7 --- /dev/null +++ b/modules/commands/hs_set.cpp @@ -0,0 +1,229 @@ +/* HostServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandHSSet : public Command +{ + public: + CommandHSSet(Module *creator) : Command(creator, "hostserv/set", 2, 2) + { + this->SetDesc(_("Set the vhost of another user")); + this->SetSyntax(_("\037nick\037 \037hostmask\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const Anope::string &nick = params[0]; + + NickAlias *na = NickAlias::Find(nick); + if (na == NULL) + { + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + return; + } + + Anope::string rawhostmask = params[1]; + + Anope::string user, host; + size_t a = rawhostmask.find('@'); + + if (a == Anope::string::npos) + host = rawhostmask; + else + { + user = rawhostmask.substr(0, a); + host = rawhostmask.substr(a + 1); + } + + if (host.empty()) + { + this->OnSyntaxError(source, ""); + return; + } + + if (!user.empty()) + { + if (!IRCD->CanSetVIdent) + { + source.Reply(HOST_NO_VIDENT); + return; + } + else if (!IRCD->IsIdentValid(user)) + { + source.Reply(HOST_SET_IDENT_ERROR); + return; + } + } + + if (host.length() > Config->GetBlock("networkinfo")->Get("hostlen")) + { + source.Reply(HOST_SET_TOOLONG, Config->GetBlock("networkinfo")->Get("hostlen")); + return; + } + + if (!IRCD->IsHostValid(host)) + { + source.Reply(HOST_SET_ERROR); + return; + } + + Log(LOG_ADMIN, source, this) << "to set the vhost of " << na->nick << " to " << (!user.empty() ? user + "@" : "") << host; + + na->SetVhost(user, host, source.GetNick()); + FOREACH_MOD(OnSetVhost, (na)); + if (!user.empty()) + source.Reply(_("VHost for \002%s\002 set to \002%s\002@\002%s\002."), nick.c_str(), user.c_str(), host.c_str()); + else + source.Reply(_("VHost for \002%s\002 set to \002%s\002."), nick.c_str(), host.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets the vhost for the given nick to that of the given\n" + "hostmask. If your IRCD supports vIdents, then using\n" + "SET @ set idents for users as\n" + "well as vhosts.")); + return true; + } +}; + +class CommandHSSetAll : public Command +{ + void Sync(const NickAlias *na) + { + if (!na || !na->HasVhost()) + return; + + for (unsigned i = 0; i < na->nc->aliases->size(); ++i) + { + NickAlias *nick = na->nc->aliases->at(i); + if (nick) + nick->SetVhost(na->GetVhostIdent(), na->GetVhostHost(), na->GetVhostCreator()); + } + } + + public: + CommandHSSetAll(Module *creator) : Command(creator, "hostserv/setall", 2, 2) + { + this->SetDesc(_("Set the vhost for all nicks in a group")); + this->SetSyntax(_("\037nick\037 \037hostmask\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + Anope::string nick = params[0]; + + NickAlias *na = NickAlias::Find(nick); + if (na == NULL) + { + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + return; + } + + Anope::string rawhostmask = params[1]; + + Anope::string user, host; + size_t a = rawhostmask.find('@'); + + if (a == Anope::string::npos) + host = rawhostmask; + else + { + user = rawhostmask.substr(0, a); + host = rawhostmask.substr(a + 1); + } + + if (host.empty()) + { + this->OnSyntaxError(source, ""); + return; + } + + if (!user.empty()) + { + if (!IRCD->CanSetVIdent) + { + source.Reply(HOST_NO_VIDENT); + return; + } + else if (!IRCD->IsIdentValid(user)) + { + source.Reply(HOST_SET_IDENT_ERROR); + return; + } + } + + if (host.length() > Config->GetBlock("networkinfo")->Get("hostlen")) + { + source.Reply(HOST_SET_TOOLONG, Config->GetBlock("networkinfo")->Get("hostlen")); + return; + } + + if (!IRCD->IsHostValid(host)) + { + source.Reply(HOST_SET_ERROR); + return; + } + + Log(LOG_ADMIN, source, this) << "to set the vhost of " << na->nick << " to " << (!user.empty() ? user + "@" : "") << host; + + na->SetVhost(user, host, source.GetNick()); + this->Sync(na); + FOREACH_MOD(OnSetVhost, (na)); + if (!user.empty()) + source.Reply(_("VHost for group \002%s\002 set to \002%s\002@\002%s\002."), nick.c_str(), user.c_str(), host.c_str()); + else + source.Reply(_("VHost for group \002%s\002 set to \002%s\002."), nick.c_str(), host.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets the vhost for all nicks in the same group as that\n" + "of the given nick. If your IRCD supports vIdents, then\n" + "using SETALL @ will set idents\n" + "for users as well as vhosts.\n" + "* NOTE, this will not update the vhost for any nicks\n" + "added to the group after this command was used.")); + return true; + } +}; + +class HSSet : public Module +{ + CommandHSSet commandhsset; + CommandHSSetAll commandhssetall; + + public: + HSSet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), commandhsset(this), commandhssetall(this) + { + if (!IRCD || !IRCD->CanSetVHost) + throw ModuleException("Your IRCd does not support vhosts"); + } +}; + +MODULE_INIT(HSSet) diff --git a/modules/commands/ms_cancel.cpp b/modules/commands/ms_cancel.cpp new file mode 100644 index 0000000..de693f1 --- /dev/null +++ b/modules/commands/ms_cancel.cpp @@ -0,0 +1,101 @@ +/* MemoServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandMSCancel : public Command +{ + public: + CommandMSCancel(Module *creator) : Command(creator, "memoserv/cancel", 1, 1) + { + this->SetDesc(_("Cancel the last memo you sent")); + this->SetSyntax(_("{\037nick\037 | \037channel\037}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const Anope::string &nname = params[0]; + + bool ischan; + MemoInfo *mi = MemoInfo::GetMemoInfo(nname, ischan); + + if (mi == NULL) + { + source.Reply(ischan ? CHAN_X_NOT_REGISTERED : NICK_X_NOT_REGISTERED, nname.c_str()); + return; + } + + ChannelInfo *ci = NULL; + NickAlias *na = NULL; + if (ischan) + { + ci = ChannelInfo::Find(nname); + + if (ci == NULL) + return; // can't happen + } + else + { + na = NickAlias::Find(nname); + + if (na == NULL) + return; // can't happen + } + + for (int i = mi->memos->size() - 1; i >= 0; --i) + { + Memo *m = mi->GetMemo(i); + + if (!m->unread) + continue; + + NickAlias *sender = NickAlias::Find(m->sender); + + if (sender && sender->nc == source.GetAccount()) + { + FOREACH_MOD(OnMemoDel, (ischan ? ci->name : na->nc->display, mi, m)); + mi->Del(i); + source.Reply(_("Last memo to \002%s\002 has been cancelled."), (ischan ? ci->name : na->nc->display).c_str()); + return; + } + } + + source.Reply(_("No memo was cancelable.")); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Cancels the last memo you sent to the given nick or channel,\n" + "provided it has not been read at the time you use the command.")); + return true; + } +}; + +class MSCancel : public Module +{ + CommandMSCancel commandmscancel; + + public: + MSCancel(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandmscancel(this) + { + } +}; + +MODULE_INIT(MSCancel) diff --git a/modules/commands/ms_check.cpp b/modules/commands/ms_check.cpp new file mode 100644 index 0000000..7bd8b65 --- /dev/null +++ b/modules/commands/ms_check.cpp @@ -0,0 +1,87 @@ +/* MemoServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandMSCheck : public Command +{ + public: + CommandMSCheck(Module *creator) : Command(creator, "memoserv/check", 1, 1) + { + this->SetDesc(_("Checks if last memo to a nick was read")); + this->SetSyntax(_("\037nick\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + + const Anope::string &recipient = params[0]; + + bool found = false; + + const NickAlias *na = NickAlias::Find(recipient); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, recipient.c_str()); + return; + } + + MemoInfo *mi = &na->nc->memos; + + /* Okay, I know this looks strange but we want to get the LAST memo, so we + have to loop backwards */ + + for (unsigned i = mi->memos->size(); i > 0; --i) + { + Memo *m = mi->GetMemo(i - 1); + NickAlias *na2 = NickAlias::Find(m->sender); + + if (na2 != NULL && na2->nc == source.GetAccount()) + { + found = true; /* Yes, we've found the memo */ + + if (m->unread) + source.Reply(_("The last memo you sent to %s (sent on %s) has not yet been read."), na->nick.c_str(), Anope::strftime(m->time, source.GetAccount()).c_str()); + else + source.Reply(_("The last memo you sent to %s (sent on %s) has been read."), na->nick.c_str(), Anope::strftime(m->time, source.GetAccount()).c_str()); + break; + } + } + + if (!found) + source.Reply(_("Nick %s doesn't have a memo from you."), na->nick.c_str()); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Checks whether the _last_ memo you sent to \037nick\037 has been read\n" + "or not. Note that this only works with nicks, not with channels.")); + return true; + } +}; + +class MSCheck : public Module +{ + CommandMSCheck commandmscheck; + + public: + MSCheck(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandmscheck(this) + { + + } +}; + +MODULE_INIT(MSCheck) diff --git a/modules/commands/ms_del.cpp b/modules/commands/ms_del.cpp new file mode 100644 index 0000000..07ee73c --- /dev/null +++ b/modules/commands/ms_del.cpp @@ -0,0 +1,159 @@ +/* MemoServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class MemoDelCallback : public NumberList +{ + CommandSource &source; + Command *cmd; + ChannelInfo *ci; + MemoInfo *mi; + public: + MemoDelCallback(CommandSource &_source, Command *c, ChannelInfo *_ci, MemoInfo *_mi, const Anope::string &list) : NumberList(list, true), source(_source), cmd(c), ci(_ci), mi(_mi) + { + } + + void HandleNumber(unsigned number) anope_override + { + if (!number || number > mi->memos->size()) + return; + + FOREACH_MOD(OnMemoDel, (ci ? ci->name : source.nc->display, mi, mi->GetMemo(number - 1))); + + mi->Del(number - 1); + source.Reply(_("Memo %d has been deleted."), number); + if (ci) + Log(LOG_COMMAND, source, cmd, ci) << "on memo " << number; + } +}; + +class CommandMSDel : public Command +{ + public: + CommandMSDel(Module *creator) : Command(creator, "memoserv/del", 0, 2) + { + this->SetDesc(_("Delete a memo or memos")); + this->SetSyntax(_("[\037channel\037] {\037num\037 | \037list\037 | LAST | ALL}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + MemoInfo *mi; + ChannelInfo *ci = NULL; + Anope::string numstr = !params.empty() ? params[0] : "", chan; + + if (!numstr.empty() && numstr[0] == '#') + { + chan = numstr; + numstr = params.size() > 1 ? params[1] : ""; + + ci = ChannelInfo::Find(chan); + if (!ci) + { + source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); + return; + } + else if (!source.AccessFor(ci).HasPriv("MEMO")) + { + source.Reply(ACCESS_DENIED); + return; + } + mi = &ci->memos; + } + else + mi = &source.nc->memos; + if (numstr.empty() || (!isdigit(numstr[0]) && !numstr.equals_ci("ALL") && !numstr.equals_ci("LAST"))) + this->OnSyntaxError(source, numstr); + else if (mi->memos->empty()) + { + if (!chan.empty()) + source.Reply(MEMO_X_HAS_NO_MEMOS, chan.c_str()); + else + source.Reply(MEMO_HAVE_NO_MEMOS); + } + else + { + if (isdigit(numstr[0])) + { + MemoDelCallback list(source, this, ci, mi, numstr); + list.Process(); + } + else if (numstr.equals_ci("LAST")) + { + /* Delete last memo. */ + FOREACH_MOD(OnMemoDel, (ci ? ci->name : source.nc->display, mi, mi->GetMemo(mi->memos->size() - 1))); + mi->Del(mi->memos->size() - 1); + source.Reply(_("Memo %d has been deleted."), mi->memos->size() + 1); + if (ci) + Log(LOG_COMMAND, source, this, ci) << "on LAST memo"; + } + else + { + /* Delete all memos. */ + for (unsigned i = mi->memos->size(); i > 0; --i) + { + FOREACH_MOD(OnMemoDel, (ci ? ci->name : source.nc->display, mi, mi->GetMemo(i))); + mi->Del(i - 1); + } + if (!chan.empty()) + { + source.Reply(_("All memos for channel %s have been deleted."), chan.c_str()); + Log(LOG_COMMAND, source, this, ci) << "on ALL memos"; + } + else + source.Reply(_("All of your memos have been deleted.")); + } + } + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Deletes the specified memo or memos. You can supply\n" + "multiple memo numbers or ranges of numbers instead of a\n" + "single number, as in the second example below.\n" + " \n" + "If \002LAST\002 is given, the last memo will be deleted.\n" + "If \002ALL\002 is given, deletes all of your memos.\n" + " \n" + "Examples:\n" + " \n" + " \002DEL 1\002\n" + " Deletes your first memo.\n" + " \n" + " \002DEL 2-5,7-9\002\n" + " Deletes memos numbered 2 through 5 and 7 through 9.")); + return true; + } +}; + +class MSDel : public Module +{ + CommandMSDel commandmsdel; + + public: + MSDel(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandmsdel(this) + { + + } +}; + +MODULE_INIT(MSDel) diff --git a/modules/commands/ms_ignore.cpp b/modules/commands/ms_ignore.cpp new file mode 100644 index 0000000..584e6e4 --- /dev/null +++ b/modules/commands/ms_ignore.cpp @@ -0,0 +1,132 @@ +/* MemoServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandMSIgnore : public Command +{ + public: + CommandMSIgnore(Module *creator) : Command(creator, "memoserv/ignore", 1, 3) + { + this->SetDesc(_("Manage the memo ignore list")); + this->SetSyntax(_("[\037channel\037] ADD \037entry\037")); + this->SetSyntax(_("[\037channel\037] DEL \037entry\037")); + this->SetSyntax(_("[\037channel\037] LIST")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + Anope::string channel = params[0]; + Anope::string command = (params.size() > 1 ? params[1] : ""); + Anope::string param = (params.size() > 2 ? params[2] : ""); + + if (channel[0] != '#') + { + param = command; + command = channel; + channel = source.GetNick(); + } + + bool ischan; + MemoInfo *mi = MemoInfo::GetMemoInfo(channel, ischan); + ChannelInfo *ci = ChannelInfo::Find(channel); + if (!mi) + source.Reply(ischan ? CHAN_X_NOT_REGISTERED : _(NICK_X_NOT_REGISTERED), channel.c_str()); + else if (ischan && !source.AccessFor(ci).HasPriv("MEMO")) + source.Reply(ACCESS_DENIED); + else if (command.equals_ci("ADD") && !param.empty()) + { + if (mi->ignores.size() >= Config->GetModule(this->owner)->Get("max", "32")) + { + source.Reply(_("Sorry, the memo ignore list for \002%s\002 is full."), channel.c_str()); + return; + } + + if (std::find(mi->ignores.begin(), mi->ignores.end(), param.ci_str()) == mi->ignores.end()) + { + mi->ignores.push_back(param.ci_str()); + source.Reply(_("\002%s\002 added to ignore list."), param.c_str()); + } + else + source.Reply(_("\002%s\002 is already on the ignore list."), param.c_str()); + } + else if (command.equals_ci("DEL") && !param.empty()) + { + std::vector::iterator it = std::find(mi->ignores.begin(), mi->ignores.end(), param.ci_str()); + + if (it != mi->ignores.end()) + { + mi->ignores.erase(it); + source.Reply(_("\002%s\002 removed from the ignore list."), param.c_str()); + } + else + source.Reply(_("\002%s\002 is not on the ignore list."), param.c_str()); + } + else if (command.equals_ci("LIST")) + { + if (mi->ignores.empty()) + source.Reply(_("Memo ignore list is empty.")); + else + { + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Mask")); + for (unsigned i = 0; i < mi->ignores.size(); ++i) + { + ListFormatter::ListEntry entry; + entry["Mask"] = mi->ignores[i]; + list.AddEntry(entry); + } + + source.Reply(_("Ignore list:")); + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + } + else + this->OnSyntaxError(source, ""); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows you to ignore users by nick or host from memoing\n" + "you or a channel. If someone on the memo ignore list tries\n" + "to memo you or a channel, they will not be told that you have\n" + "them ignored.")); + return true; + } +}; + +class MSIgnore : public Module +{ + CommandMSIgnore commandmsignore; + + public: + MSIgnore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandmsignore(this) + { + } +}; + +MODULE_INIT(MSIgnore) diff --git a/modules/commands/ms_info.cpp b/modules/commands/ms_info.cpp new file mode 100644 index 0000000..0fc059f --- /dev/null +++ b/modules/commands/ms_info.cpp @@ -0,0 +1,231 @@ +/* MemoServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandMSInfo : public Command +{ + public: + CommandMSInfo(Module *creator) : Command(creator, "memoserv/info", 0, 1) + { + this->SetDesc(_("Displays information about your memos")); + this->SetSyntax(_("[\037nick\037 | \037channel\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + NickCore *nc = source.nc; + const MemoInfo *mi; + const NickAlias *na = NULL; + ChannelInfo *ci = NULL; + const Anope::string &nname = !params.empty() ? params[0] : ""; + bool hardmax; + + if (!nname.empty() && nname[0] != '#' && source.HasPriv("memoserv/info")) + { + na = NickAlias::Find(nname); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, nname.c_str()); + return; + } + mi = &na->nc->memos; + hardmax = na->nc->HasExt("MEMO_HARDMAX"); + } + else if (!nname.empty() && nname[0] == '#') + { + ci = ChannelInfo::Find(nname); + if (!ci) + { + source.Reply(CHAN_X_NOT_REGISTERED, nname.c_str()); + return; + } + else if (!source.AccessFor(ci).HasPriv("MEMO")) + { + source.Reply(ACCESS_DENIED); + return; + } + mi = &ci->memos; + hardmax = ci->HasExt("MEMO_HARDMAX"); + } + else if (!nname.empty()) /* It's not a chan and we aren't services admin */ + { + source.Reply(ACCESS_DENIED); + return; + } + else + { + mi = &nc->memos; + hardmax = nc->HasExt("MEMO_HARDMAX"); + } + + if (!nname.empty() && (ci || na->nc != nc)) + { + if (mi->memos->empty()) + source.Reply(_("%s currently has no memos."), nname.c_str()); + else if (mi->memos->size() == 1) + { + if (mi->GetMemo(0)->unread) + source.Reply(_("%s currently has \0021\002 memo, and it has not yet been read."), nname.c_str()); + else + source.Reply(_("%s currently has \0021\002 memo."), nname.c_str()); + } + else + { + unsigned count = 0, i, end; + for (i = 0, end = mi->memos->size(); i < end; ++i) + if (mi->GetMemo(i)->unread) + ++count; + if (count == mi->memos->size()) + source.Reply(_("%s currently has \002%d\002 memos; all of them are unread."), nname.c_str(), count); + else if (!count) + source.Reply(_("%s currently has \002%d\002 memos."), nname.c_str(), mi->memos->size()); + else if (count == 1) + source.Reply(_("%s currently has \002%d\002 memos, of which \0021\002 is unread."), nname.c_str(), mi->memos->size()); + else + source.Reply(_("%s currently has \002%d\002 memos, of which \002%d\002 are unread."), nname.c_str(), mi->memos->size(), count); + } + if (!mi->memomax) + { + if (hardmax) + source.Reply(_("%s's memo limit is \002%d\002, and may not be changed."), nname.c_str(), mi->memomax); + else + source.Reply(_("%s's memo limit is \002%d\002."), nname.c_str(), mi->memomax); + } + else if (mi->memomax > 0) + { + if (hardmax) + source.Reply(_("%s's memo limit is \002%d\002, and may not be changed."), nname.c_str(), mi->memomax); + else + source.Reply(_("%s's memo limit is \002%d\002."), nname.c_str(), mi->memomax); + } + else + source.Reply(_("%s has no memo limit."), nname.c_str()); + + /* I ripped this code out of ircservices 4.4.5, since I didn't want + to rewrite the whole thing (it pisses me off). */ + if (na) + { + if (na->nc->HasExt("MEMO_RECEIVE") && na->nc->HasExt("MEMO_SIGNON")) + source.Reply(_("%s is notified of new memos at logon and when they arrive."), nname.c_str()); + else if (na->nc->HasExt("MEMO_RECEIVE")) + source.Reply(_("%s is notified when new memos arrive."), nname.c_str()); + else if (na->nc->HasExt("MEMO_SIGNON")) + source.Reply(_("%s is notified of new memos at logon."), nname.c_str()); + else + source.Reply(_("%s is not notified of new memos."), nname.c_str()); + } + } + else /* !nname || (!ci || na->nc == nc) */ + { + if (mi->memos->empty()) + source.Reply(_("You currently have no memos.")); + else if (mi->memos->size() == 1) + { + if (mi->GetMemo(0)->unread) + source.Reply(_("You currently have \0021\002 memo, and it has not yet been read.")); + else + source.Reply(_("You currently have \0021\002 memo.")); + } + else + { + unsigned count = 0, i, end; + for (i = 0, end = mi->memos->size(); i < end; ++i) + if (mi->GetMemo(i)->unread) + ++count; + if (count == mi->memos->size()) + source.Reply(_("You currently have \002%d\002 memos; all of them are unread."), count); + else if (!count) + source.Reply(_("You currently have \002%d\002 memos."), mi->memos->size()); + else if (count == 1) + source.Reply(_("You currently have \002%d\002 memos, of which \0021\002 is unread."), mi->memos->size()); + else + source.Reply(_("You currently have \002%d\002 memos, of which \002%d\002 are unread."), mi->memos->size(), count); + } + + if (!mi->memomax) + { + if (!source.IsServicesOper() && hardmax) + source.Reply(_("Your memo limit is \0020\002; you will not receive any new memos. You cannot change this limit.")); + else + source.Reply(_("Your memo limit is \0020\002; you will not receive any new memos.")); + } + else if (mi->memomax > 0) + { + if (!source.IsServicesOper() && hardmax) + source.Reply(_("Your memo limit is \002%d\002, and may not be changed."), mi->memomax); + else + source.Reply(_("Your memo limit is \002%d\002."), mi->memomax); + } + else + source.Reply(_("You have no limit on the number of memos you may keep.")); + + bool memo_mail = nc->HasExt("MEMO_MAIL"); + if (nc->HasExt("MEMO_RECEIVE") && nc->HasExt("MEMO_SIGNON")) + { + if (memo_mail) + source.Reply(_("You will be notified of new memos at logon and when they arrive, and by mail when they arrive.")); + else + source.Reply(_("You will be notified of new memos at logon and when they arrive.")); + } + else if (nc->HasExt("MEMO_RECEIVE")) + { + if (memo_mail) + source.Reply(_("You will be notified by message and by mail when new memos arrive.")); + else + source.Reply(_("You will be notified when new memos arrive.")); + } + else if (nc->HasExt("MEMO_SIGNON")) + { + if (memo_mail) + source.Reply(_("You will be notified of new memos at logon, and by mail when they arrive.")); + else + source.Reply(_("You will be notified of new memos at logon.")); + } + else + { + source.Reply(_("You will not be notified of new memos.")); + } + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Without a parameter, displays information on the number of\n" + "memos you have, how many of them are unread, and how many\n" + "total memos you can receive.\n" + " \n" + "With a channel parameter, displays the same information for\n" + "the given channel.\n" + " \n" + "With a nickname parameter, displays the same information\n" + "for the given nickname. This is limited to \002Services\002\n" + "\002Operators\002.")); + + return true; + } +}; + +class MSInfo : public Module +{ + CommandMSInfo commandmsinfo; + + public: + MSInfo(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandmsinfo(this) + { + + } +}; + +MODULE_INIT(MSInfo) diff --git a/modules/commands/ms_list.cpp b/modules/commands/ms_list.cpp new file mode 100644 index 0000000..63c6235 --- /dev/null +++ b/modules/commands/ms_list.cpp @@ -0,0 +1,164 @@ +/* MemoServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandMSList : public Command +{ + public: + CommandMSList(Module *creator) : Command(creator, "memoserv/list", 0, 2) + { + this->SetDesc(_("List your memos")); + this->SetSyntax(_("[\037channel\037] [\037list\037 | NEW]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + + Anope::string param = !params.empty() ? params[0] : "", chan; + ChannelInfo *ci = NULL; + const MemoInfo *mi; + + if (!param.empty() && param[0] == '#') + { + chan = param; + param = params.size() > 1 ? params[1] : ""; + + ci = ChannelInfo::Find(chan); + if (!ci) + { + source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); + return; + } + else if (!source.AccessFor(ci).HasPriv("MEMO")) + { + source.Reply(ACCESS_DENIED); + return; + } + mi = &ci->memos; + } + else + mi = &source.nc->memos; + + if (!param.empty() && !isdigit(param[0]) && !param.equals_ci("NEW")) + this->OnSyntaxError(source, param); + else if (!mi->memos->size()) + { + if (!chan.empty()) + source.Reply(MEMO_X_HAS_NO_MEMOS, chan.c_str()); + else + source.Reply(MEMO_HAVE_NO_MEMOS); + } + else + { + ListFormatter list(source.GetAccount()); + + list.AddColumn(_("Number")).AddColumn(_("Sender")).AddColumn(_("Date/Time")); + + if (!param.empty() && isdigit(param[0])) + { + class MemoListCallback : public NumberList + { + ListFormatter &list; + CommandSource &source; + const MemoInfo *mi; + public: + MemoListCallback(ListFormatter &_list, CommandSource &_source, const MemoInfo *_mi, const Anope::string &numlist) : NumberList(numlist, false), list(_list), source(_source), mi(_mi) + { + } + + void HandleNumber(unsigned number) anope_override + { + if (!number || number > mi->memos->size()) + return; + + const Memo *m = mi->GetMemo(number - 1); + + ListFormatter::ListEntry entry; + entry["Number"] = (m->unread ? "* " : " ") + stringify(number); + entry["Sender"] = m->sender; + entry["Date/Time"] = Anope::strftime(m->time, source.GetAccount()); + this->list.AddEntry(entry); + } + } + mlc(list, source, mi, param); + mlc.Process(); + } + else + { + if (!param.empty()) + { + unsigned i, end; + for (i = 0, end = mi->memos->size(); i < end; ++i) + if (mi->GetMemo(i)->unread) + break; + if (i == end) + { + if (!chan.empty()) + source.Reply(MEMO_X_HAS_NO_NEW_MEMOS, chan.c_str()); + else + source.Reply(MEMO_HAVE_NO_NEW_MEMOS); + return; + } + } + + for (unsigned i = 0, end = mi->memos->size(); i < end; ++i) + { + if (!param.empty() && !mi->GetMemo(i)->unread) + continue; + + const Memo *m = mi->GetMemo(i); + + ListFormatter::ListEntry entry; + entry["Number"] = (m->unread ? "* " : " ") + stringify(i + 1); + entry["Sender"] = m->sender; + entry["Date/Time"] = Anope::strftime(m->time, source.GetAccount()); + list.AddEntry(entry); + } + } + + std::vector replies; + list.Process(replies); + + source.Reply(_("Memos for %s:"), ci ? ci->name.c_str() : source.GetNick().c_str()); + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Lists any memos you currently have. With \002NEW\002, lists only\n" + "new (unread) memos. Unread memos are marked with a \"*\"\n" + "to the left of the memo number. You can also specify a list\n" + "of numbers, as in the example below:\n" + " \002LIST 2-5,7-9\002\n" + " Lists memos numbered 2 through 5 and 7 through 9.")); + return true; + } +}; + +class MSList : public Module +{ + CommandMSList commandmslist; + + public: + MSList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandmslist(this) + { + + } +}; + +MODULE_INIT(MSList) diff --git a/modules/commands/ms_read.cpp b/modules/commands/ms_read.cpp new file mode 100644 index 0000000..515f4de --- /dev/null +++ b/modules/commands/ms_read.cpp @@ -0,0 +1,224 @@ +/* MemoServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +static ServiceReference MemoServService("MemoServService", "MemoServ"); + +static void rsend_notify(CommandSource &source, MemoInfo *mi, Memo *m, const Anope::string &targ) +{ + /* Only send receipt if memos are allowed */ + if (MemoServService && !Anope::ReadOnly) + { + /* Get nick alias for sender */ + const NickAlias *na = NickAlias::Find(m->sender); + + if (!na) + return; + + /* Get nick core for sender */ + const NickCore *nc = na->nc; + + if (!nc) + return; + + /* Text of the memo varies if the recipient was a + nick or channel */ + Anope::string text = Anope::printf(Language::Translate(na->nc, _("\002[auto-memo]\002 The memo you sent to %s has been viewed.")), targ.c_str()); + + /* Send notification */ + MemoServService->Send(source.GetNick(), m->sender, text, true); + + /* Notify recipient of the memo that a notification has + been sent to the sender */ + source.Reply(_("A notification memo has been sent to %s informing him/her you have\n" + "read his/her memo."), nc->display.c_str()); + } + + /* Remove receipt flag from the original memo */ + m->receipt = false; +} + +class MemoListCallback : public NumberList +{ + CommandSource &source; + MemoInfo *mi; + const ChannelInfo *ci; + bool found; + public: + MemoListCallback(CommandSource &_source, MemoInfo *_mi, const ChannelInfo *_ci, const Anope::string &numlist) : NumberList(numlist, false), source(_source), mi(_mi), ci(_ci) + { + found = false; + } + + ~MemoListCallback() + { + if (!found) + source.Reply(_("No memos to display.")); + } + + void HandleNumber(unsigned number) anope_override + { + if (!number || number > mi->memos->size()) + return; + + MemoListCallback::DoRead(source, mi, ci, number - 1); + found = true; + } + + static void DoRead(CommandSource &source, MemoInfo *mi, const ChannelInfo *ci, unsigned index) + { + Memo *m = mi->GetMemo(index); + if (!m) + return; + + if (ci) + source.Reply(_("Memo %d from %s (%s)."), index + 1, m->sender.c_str(), Anope::strftime(m->time, source.GetAccount()).c_str()); + else + source.Reply(_("Memo %d from %s (%s)."), index + 1, m->sender.c_str(), Anope::strftime(m->time, source.GetAccount()).c_str()); + + BotInfo *bi; + Anope::string cmd; + if (Command::FindCommandFromService("memoserv/del", bi, cmd)) + { + if (ci) + source.Reply(_("To delete, type: \002%s%s %s %s %d\002"), Config->StrictPrivmsg.c_str(), bi->nick.c_str(), cmd.c_str(), ci->name.c_str(), index + 1); + else + source.Reply(_("To delete, type: \002%s%s %s %d\002"), Config->StrictPrivmsg.c_str(), bi->nick.c_str(), cmd.c_str(), index + 1); + } + + source.Reply("%s", m->text.c_str()); + m->unread = false; + + /* Check if a receipt notification was requested */ + if (m->receipt) + rsend_notify(source, mi, m, ci ? ci->name : source.GetNick()); + } +}; + +class CommandMSRead : public Command +{ + public: + CommandMSRead(Module *creator) : Command(creator, "memoserv/read", 1, 2) + { + this->SetDesc(_("Read a memo or memos")); + this->SetSyntax(_("[\037channel\037] {\037num\037 | \037list\037 | LAST | NEW | ALL}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + + MemoInfo *mi; + ChannelInfo *ci = NULL; + Anope::string numstr = params[0], chan; + + if (!numstr.empty() && numstr[0] == '#') + { + chan = numstr; + numstr = params.size() > 1 ? params[1] : ""; + + ci = ChannelInfo::Find(chan); + if (!ci) + { + source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); + return; + } + else if (!source.AccessFor(ci).HasPriv("MEMO")) + { + source.Reply(ACCESS_DENIED); + return; + } + mi = &ci->memos; + } + else + mi = &source.nc->memos; + + if (numstr.empty() || (!numstr.equals_ci("LAST") && !numstr.equals_ci("NEW") && !numstr.equals_ci("ALL") && numstr.find_first_not_of("0123456789.,-") != Anope::string::npos)) + this->OnSyntaxError(source, numstr); + else if (mi->memos->empty()) + { + if (!chan.empty()) + source.Reply(MEMO_X_HAS_NO_MEMOS, chan.c_str()); + else + source.Reply(MEMO_HAVE_NO_MEMOS); + } + else + { + int i, end; + + if (numstr.equals_ci("NEW")) + { + int readcount = 0; + for (i = 0, end = mi->memos->size(); i < end; ++i) + if (mi->GetMemo(i)->unread) + { + MemoListCallback::DoRead(source, mi, ci, i); + ++readcount; + } + if (!readcount) + { + if (!chan.empty()) + source.Reply(MEMO_X_HAS_NO_NEW_MEMOS, chan.c_str()); + else + source.Reply(MEMO_HAVE_NO_NEW_MEMOS); + } + } + else if (numstr.equals_ci("LAST")) + { + for (i = 0, end = mi->memos->size() - 1; i < end; ++i); + MemoListCallback::DoRead(source, mi, ci, i); + } + else if (numstr.equals_ci("ALL")) + { + for (i = 0, end = mi->memos->size(); i < end; ++i) + { + MemoListCallback::DoRead(source, mi, ci, i); + } + } + else /* number[s] */ + { + MemoListCallback list(source, mi, ci, numstr); + list.Process(); + } + } + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sends you the text of the memos specified. If LAST is\n" + "given, sends you the memo you most recently received. If\n" + "NEW is given, sends you all of your new memos. If ALL is\n" + "given, sends you all of your memos. Otherwise, sends you\n" + "memo number \037num\037. You can also give a list of numbers,\n" + "as in this example:\n" + " \n" + " \002READ 2-5,7-9\002\n" + " Displays memos numbered 2 through 5 and 7 through 9.")); + return true; + } +}; + +class MSRead : public Module +{ + CommandMSRead commandmsread; + + public: + MSRead(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandmsread(this) + { + + } +}; + +MODULE_INIT(MSRead) diff --git a/modules/commands/ms_rsend.cpp b/modules/commands/ms_rsend.cpp new file mode 100644 index 0000000..eacc1e9 --- /dev/null +++ b/modules/commands/ms_rsend.cpp @@ -0,0 +1,104 @@ +/* MemoServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +namespace +{ + ServiceReference memoserv("MemoServService", "MemoServ"); +} + +class CommandMSRSend : public Command +{ + public: + CommandMSRSend(Module *creator) : Command(creator, "memoserv/rsend", 2, 2) + { + this->SetDesc(_("Sends a memo and requests a read receipt")); + this->SetSyntax(_("{\037nick\037 | \037channel\037} \037memo-text\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!memoserv) + return; + + if (Anope::ReadOnly && !source.IsOper()) + { + source.Reply(MEMO_SEND_DISABLED); + return; + } + + const Anope::string &nick = params[0]; + const Anope::string &text = params[1]; + const NickAlias *na = NULL; + + /* prevent user from rsend to themselves */ + if ((na = NickAlias::Find(nick)) && na->nc == source.GetAccount()) + { + source.Reply(_("You can not request a receipt when sending a memo to yourself.")); + return; + } + + if (Config->GetModule(this->owner)->Get("operonly") && !source.IsServicesOper()) + source.Reply(ACCESS_DENIED); + else + { + MemoServService::MemoResult result = memoserv->Send(source.GetNick(), nick, text); + if (result == MemoServService::MEMO_INVALID_TARGET) + source.Reply(_("\002%s\002 is not a registered unforbidden nick or channel."), nick.c_str()); + else if (result == MemoServService::MEMO_TOO_FAST) + source.Reply(_("Please wait %d seconds before using the %s command again."), Config->GetModule("memoserv")->Get("senddelay"), source.command.c_str()); + else if (result == MemoServService::MEMO_TARGET_FULL) + source.Reply(_("Sorry, %s currently has too many memos and cannot receive more."), nick.c_str()); + else + { + source.Reply(_("Memo sent to \002%s\002."), nick.c_str()); + + bool ischan; + MemoInfo *mi = MemoInfo::GetMemoInfo(nick, ischan); + if (mi == NULL) + throw CoreException("NULL mi in ms_rsend"); + Memo *m = (mi->memos->size() ? mi->GetMemo(mi->memos->size() - 1) : NULL); + if (m != NULL) + m->receipt = true; + } + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sends the named \037nick\037 or \037channel\037 a memo containing\n" + "\037memo-text\037. When sending to a nickname, the recipient will\n" + "receive a notice that he/she has a new memo. The target\n" + "nickname/channel must be registered.\n" + "Once the memo is read by its recipient, an automatic notification\n" + "memo will be sent to the sender informing him/her that the memo\n" + "has been read.")); + return true; + } +}; + +class MSRSend : public Module +{ + CommandMSRSend commandmsrsend; + + public: + MSRSend(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandmsrsend(this) + { + if (!memoserv) + throw ModuleException("No MemoServ!"); + } +}; + +MODULE_INIT(MSRSend) diff --git a/modules/commands/ms_send.cpp b/modules/commands/ms_send.cpp new file mode 100644 index 0000000..d47ce4a --- /dev/null +++ b/modules/commands/ms_send.cpp @@ -0,0 +1,88 @@ +/* MemoServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +namespace +{ + ServiceReference memoserv("MemoServService", "MemoServ"); +} + +class CommandMSSend : public Command +{ + public: + CommandMSSend(Module *creator) : Command(creator, "memoserv/send", 2, 2) + { + this->SetDesc(_("Send a memo to a nick or channel")); + this->SetSyntax(_("{\037nick\037 | \037channel\037} \037memo-text\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!memoserv) + return; + + const Anope::string &nick = params[0]; + const Anope::string &text = params[1]; + + if (Anope::ReadOnly && !source.IsOper()) + { + source.Reply(MEMO_SEND_DISABLED); + return; + } + + if (source.GetAccount()->HasExt("UNCONFIRMED")) + { + source.Reply(_("You must confirm your account before you may send a memo.")); + return; + } + + MemoServService::MemoResult result = memoserv->Send(source.GetNick(), nick, text); + if (result == MemoServService::MEMO_SUCCESS) + { + source.Reply(_("Memo sent to \002%s\002."), nick.c_str()); + Log(LOG_COMMAND, source, this) << "to send a memo to " << nick; + } + else if (result == MemoServService::MEMO_INVALID_TARGET) + source.Reply(_("\002%s\002 is not a registered unforbidden nick or channel."), nick.c_str()); + else if (result == MemoServService::MEMO_TOO_FAST) + source.Reply(_("Please wait %d seconds before using the %s command again."), Config->GetModule("memoserv")->Get("senddelay"), source.command.c_str()); + else if (result == MemoServService::MEMO_TARGET_FULL) + source.Reply(_("Sorry, %s currently has too many memos and cannot receive more."), nick.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sends the named \037nick\037 or \037channel\037 a memo containing\n" + "\037memo-text\037. When sending to a nickname, the recipient will\n" + "receive a notice that he/she has a new memo. The target\n" + "nickname/channel must be registered.")); + return true; + } +}; + +class MSSend : public Module +{ + CommandMSSend commandmssend; + + public: + MSSend(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandmssend(this) + { + + if (!memoserv) + throw ModuleException("No MemoServ!"); + } +}; + +MODULE_INIT(MSSend) diff --git a/modules/commands/ms_sendall.cpp b/modules/commands/ms_sendall.cpp new file mode 100644 index 0000000..f99826e --- /dev/null +++ b/modules/commands/ms_sendall.cpp @@ -0,0 +1,70 @@ +/* MemoServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +namespace +{ + ServiceReference memoserv("MemoServService", "MemoServ"); +} + +class CommandMSSendAll : public Command +{ + public: + CommandMSSendAll(Module *creator) : Command(creator, "memoserv/sendall", 1, 1) + { + this->SetDesc(_("Send a memo to all registered users")); + this->SetSyntax(_("\037memo-text\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!memoserv) + return; + + const Anope::string &text = params[0]; + + Log(LOG_ADMIN, source, this) << "to send " << text; + + for (nickcore_map::const_iterator it = NickCoreList->begin(), it_end = NickCoreList->end(); it != it_end; ++it) + { + const NickCore *nc = it->second; + + if (nc != source.nc) + memoserv->Send(source.GetNick(), nc->display, text); + } + + source.Reply(_("A massmemo has been sent to all registered users.")); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sends all registered users a memo containing \037memo-text\037.")); + return true; + } +}; + +class MSSendAll : public Module +{ + CommandMSSendAll commandmssendall; + + public: + MSSendAll(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandmssendall(this) + { + if (!memoserv) + throw ModuleException("No MemoServ!"); + } +}; + +MODULE_INIT(MSSendAll) diff --git a/modules/commands/ms_set.cpp b/modules/commands/ms_set.cpp new file mode 100644 index 0000000..2404c22 --- /dev/null +++ b/modules/commands/ms_set.cpp @@ -0,0 +1,315 @@ +/* MemoServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandMSSet : public Command +{ + private: + void DoNotify(CommandSource &source, const std::vector ¶ms, MemoInfo *mi) + { + const Anope::string ¶m = params[1]; + NickCore *nc = source.nc; + BotInfo *MemoServ = Config->GetClient("MemoServ"); + + if (!MemoServ) + return; + + if (param.equals_ci("ON")) + { + nc->Extend("MEMO_SIGNON"); + nc->Extend("MEMO_RECEIVE"); + source.Reply(_("%s will now notify you of memos when you log on and when they are sent to you."), MemoServ->nick.c_str()); + } + else if (param.equals_ci("LOGON")) + { + nc->Extend("MEMO_SIGNON"); + nc->Shrink("MEMO_RECEIVE"); + source.Reply(_("%s will now notify you of memos when you log on or unset /AWAY."), MemoServ->nick.c_str()); + } + else if (param.equals_ci("NEW")) + { + nc->Shrink("MEMO_SIGNON"); + nc->Extend("MEMO_RECEIVE"); + source.Reply(_("%s will now notify you of memos when they are sent to you."), MemoServ->nick.c_str()); + } + else if (param.equals_ci("MAIL")) + { + if (!nc->email.empty()) + { + nc->Extend("MEMO_MAIL"); + source.Reply(_("You will now be informed about new memos via email.")); + } + else + source.Reply(_("There's no email address set for your nick.")); + } + else if (param.equals_ci("NOMAIL")) + { + nc->Shrink("MEMO_MAIL"); + source.Reply(_("You will no longer be informed via email.")); + } + else if (param.equals_ci("OFF")) + { + nc->Shrink("MEMO_SIGNON"); + nc->Shrink("MEMO_RECEIVE"); + nc->Shrink("MEMO_MAIL"); + source.Reply(_("%s will not send you any notification of memos."), MemoServ->nick.c_str()); + } + else + this->OnSyntaxError(source, ""); + } + + void DoLimit(CommandSource &source, const std::vector ¶ms, MemoInfo *mi) + { + + Anope::string p1 = params[1]; + Anope::string p2 = params.size() > 2 ? params[2] : ""; + Anope::string p3 = params.size() > 3 ? params[3] : ""; + Anope::string user, chan; + int16_t limit; + NickCore *nc = source.nc; + ChannelInfo *ci = NULL; + bool is_servadmin = source.HasPriv("memoserv/set-limit"); + + if (p1[0] == '#') + { + chan = p1; + p1 = p2; + p2 = p3; + p3 = params.size() > 4 ? params[4] : ""; + + ci = ChannelInfo::Find(chan); + if (!ci) + { + source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); + return; + } + else if (!is_servadmin && !source.AccessFor(ci).HasPriv("MEMO")) + { + source.Reply(ACCESS_DENIED); + return; + } + mi = &ci->memos; + } + if (is_servadmin) + { + if (!p2.empty() && !p2.equals_ci("HARD") && chan.empty()) + { + const NickAlias *na; + if (!(na = NickAlias::Find(p1))) + { + source.Reply(NICK_X_NOT_REGISTERED, p1.c_str()); + return; + } + user = p1; + mi = &na->nc->memos; + nc = na->nc; + p1 = p2; + p2 = p3; + } + else if (p1.empty() || (!p1.is_pos_number_only() && !p1.equals_ci("NONE")) || (!p2.empty() && !p2.equals_ci("HARD"))) + { + this->OnSyntaxError(source, ""); + return; + } + if (!chan.empty()) + { + if (!p2.empty()) + ci->Extend("MEMO_HARDMAX"); + else + ci->Shrink("MEMO_HARDMAX"); + } + else + { + if (!p2.empty()) + nc->Extend("MEMO_HARDMAX"); + else + nc->Shrink("MEMO_HARDMAX"); + } + limit = -1; + try + { + limit = convertTo(p1); + } + catch (const ConvertException &) { } + } + else + { + if (p1.empty() || !p2.empty() || !isdigit(p1[0])) + { + this->OnSyntaxError(source, ""); + return; + } + if (!chan.empty() && ci->HasExt("MEMO_HARDMAX")) + { + source.Reply(_("The memo limit for %s may not be changed."), chan.c_str()); + return; + } + else if (chan.empty() && nc->HasExt("MEMO_HARDMAX")) + { + source.Reply(_("You are not permitted to change your memo limit.")); + return; + } + int max_memos = Config->GetModule("memoserv")->Get("maxmemos"); + limit = -1; + try + { + limit = convertTo(p1); + } + catch (const ConvertException &) { } + /* The first character is a digit, but we could still go negative + * from overflow... watch out! */ + if (limit < 0 || (max_memos > 0 && limit > max_memos)) + { + if (!chan.empty()) + source.Reply(_("You cannot set the memo limit for %s higher than %d."), chan.c_str(), max_memos); + else + source.Reply(_("You cannot set your memo limit higher than %d."), max_memos); + return; + } + } + mi->memomax = limit; + if (limit > 0) + { + if (chan.empty() && nc == source.nc) + source.Reply(_("Your memo limit has been set to \002%d\002."), limit); + else + source.Reply(_("Memo limit for %s set to \002%d\002."), !chan.empty() ? chan.c_str() : user.c_str(), limit); + } + else if (!limit) + { + if (chan.empty() && nc == source.nc) + source.Reply(_("You will no longer be able to receive memos.")); + else + source.Reply(_("Memo limit for %s set to \0020\002."), !chan.empty() ? chan.c_str() : user.c_str()); + } + else + { + if (chan.empty() && nc == source.nc) + source.Reply(_("Your memo limit has been disabled.")); + else + source.Reply(_("Memo limit \002disabled\002 for %s."), !chan.empty() ? chan.c_str() : user.c_str()); + } + return; + } + public: + CommandMSSet(Module *creator) : Command(creator, "memoserv/set", 2, 5) + { + this->SetDesc(_("Set options related to memos")); + this->SetSyntax(_("\037option\037 \037parameters\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[0]; + MemoInfo *mi = &source.nc->memos; + + if (Anope::ReadOnly) + source.Reply(_("Sorry, memo option setting is temporarily disabled.")); + else if (cmd.equals_ci("NOTIFY")) + return this->DoNotify(source, params, mi); + else if (cmd.equals_ci("LIMIT")) + return this->DoLimit(source, params, mi); + else + { + this->OnSyntaxError(source, ""); + } + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + if (subcommand.empty()) + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets various memo options. \037option\037 can be one of:\n" + " \n" + " NOTIFY Changes when you will be notified about\n" + " new memos (only for nicknames)\n" + " LIMIT Sets the maximum number of memos you can\n" + " receive\n" + " \n" + "Type \002%s%s HELP %s \037option\037\002 for more information\n" + "on a specific option."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), source.command.c_str()); + } + else if (subcommand.equals_ci("NOTIFY")) + source.Reply(_("Syntax: \002NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\002\n" + " \n" + "Changes when you will be notified about new memos:\n" + " \n" + " ON You will be notified of memos when you log on,\n" + " when you unset /AWAY, and when they are sent\n" + " to you.\n" + " LOGON You will only be notified of memos when you log\n" + " on or when you unset /AWAY.\n" + " NEW You will only be notified of memos when they\n" + " are sent to you.\n" + " MAIL You will be notified of memos by email as well as\n" + " any other settings you have.\n" + " NOMAIL You will not be notified of memos by email.\n" + " OFF You will not receive any notification of memos.\n" + " \n" + "\002ON\002 is essentially \002LOGON\002 and \002NEW\002 combined.")); + else if (subcommand.equals_ci("LIMIT")) + { + int max_memos = Config->GetModule("memoserv")->Get("maxmemos"); + if (source.IsServicesOper()) + source.Reply(_("Syntax: \002LIMIT [\037user\037 | \037channel\037] {\037limit\037 | NONE} [HARD]\002\n" + " \n" + "Sets the maximum number of memos a user or channel is\n" + "allowed to have. Setting the limit to 0 prevents the user\n" + "from receiving any memos; setting it to \002NONE\002 allows the\n" + "user to receive and keep as many memos as they want. If\n" + "you do not give a nickname or channel, your own limit is\n" + "set.\n" + " \n" + "Adding \002HARD\002 prevents the user from changing the limit. Not\n" + "adding \002HARD\002 has the opposite effect, allowing the user to\n" + "change the limit (even if a previous limit was set with\n" + "\002HARD\002).\n" + " \n" + "This use of the \002SET LIMIT\002 command is limited to \002Services\002\n" + "\002Operators\002. Other users may only enter a limit for themselves\n" + "or a channel on which they have such privileges, may not\n" + "remove their limit, may not set a limit above %d, and may\n" + "not set a hard limit."), max_memos); + else + source.Reply(_("Syntax: \002LIMIT [\037channel\037] \037limit\037\002\n" + " \n" + "Sets the maximum number of memos you (or the given channel)\n" + "are allowed to have. If you set this to 0, no one will be\n" + "able to send any memos to you. However, you cannot set\n" + "this any higher than %d."), max_memos); + } + else + return false; + + return true; + } +}; + +class MSSet : public Module +{ + CommandMSSet commandmsset; + SerializableExtensibleItem memo_signon, memo_receive, memo_mail, memo_hardmax; + + public: + MSSet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandmsset(this), memo_signon(this, "MEMO_SIGNON"), memo_receive(this, "MEMO_RECEIVE"), memo_mail(this, "MEMO_MAIL"), + memo_hardmax(this, "MEMO_HARDMAX") + { + + } +}; + +MODULE_INIT(MSSet) diff --git a/modules/commands/ms_staff.cpp b/modules/commands/ms_staff.cpp new file mode 100644 index 0000000..9494566 --- /dev/null +++ b/modules/commands/ms_staff.cpp @@ -0,0 +1,67 @@ +/* MemoServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +namespace +{ + ServiceReference memoserv("MemoServService", "MemoServ"); +} + +class CommandMSStaff : public Command +{ + public: + CommandMSStaff(Module *creator) : Command(creator, "memoserv/staff", 1, 1) + { + this->SetDesc(_("Send a memo to all opers/admins")); + this->SetSyntax(_("\037memo-text\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!memoserv) + return; + + const Anope::string &text = params[0]; + + for (nickcore_map::const_iterator it = NickCoreList->begin(), it_end = NickCoreList->end(); it != it_end; ++it) + { + const NickCore *nc = it->second; + + if (source.nc != nc && nc->IsServicesOper()) + memoserv->Send(source.GetNick(), nc->display, text, true); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sends all services staff a memo containing \037memo-text\037.")); + + return true; + } +}; + +class MSStaff : public Module +{ + CommandMSStaff commandmsstaff; + + public: + MSStaff(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandmsstaff(this) + { + if (!memoserv) + throw ModuleException("No MemoServ!"); + } +}; + +MODULE_INIT(MSStaff) diff --git a/modules/commands/ns_access.cpp b/modules/commands/ns_access.cpp new file mode 100644 index 0000000..e93ab74 --- /dev/null +++ b/modules/commands/ns_access.cpp @@ -0,0 +1,206 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandNSAccess : public Command +{ + private: + void DoAdd(CommandSource &source, NickCore *nc, const Anope::string &mask) + { + if (mask.empty()) + { + this->OnSyntaxError(source, "ADD"); + return; + } + + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + if (nc->access.size() >= Config->GetModule(this->owner)->Get("accessmax", "32")) + { + source.Reply(_("Sorry, the maximum of %d access entries has been reached."), Config->GetModule(this->owner)->Get("accessmax")); + return; + } + + if (nc->FindAccess(mask)) + { + source.Reply(_("Mask \002%s\002 already present on %s's access list."), mask.c_str(), nc->display.c_str()); + return; + } + + nc->AddAccess(mask); + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to ADD mask " << mask << " to " << nc->display; + source.Reply(_("\002%s\002 added to %s's access list."), mask.c_str(), nc->display.c_str()); + + return; + } + + void DoDel(CommandSource &source, NickCore *nc, const Anope::string &mask) + { + if (mask.empty()) + { + this->OnSyntaxError(source, "DEL"); + return; + } + + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + if (!nc->FindAccess(mask)) + { + source.Reply(_("\002%s\002 not found on %s's access list."), mask.c_str(), nc->display.c_str()); + return; + } + + nc->EraseAccess(mask); + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to DELETE mask " << mask << " from " << nc->display; + source.Reply(_("\002%s\002 deleted from %s's access list."), mask.c_str(), nc->display.c_str()); + + return; + } + + void DoList(CommandSource &source, NickCore *nc, const Anope::string &mask) + { + unsigned i, end; + + if (nc->access.empty()) + { + source.Reply(_("%s's access list is empty."), nc->display.c_str()); + return; + } + + source.Reply(_("Access list for %s:"), nc->display.c_str()); + for (i = 0, end = nc->access.size(); i < end; ++i) + { + Anope::string access = nc->GetAccess(i); + if (!mask.empty() && !Anope::Match(access, mask)) + continue; + source.Reply(" %s", access.c_str()); + } + + return; + } + public: + CommandNSAccess(Module *creator) : Command(creator, "nickserv/access", 1, 3) + { + this->SetDesc(_("Modify the list of authorized addresses")); + this->SetSyntax(_("ADD [\037nickname\037] \037mask\037")); + this->SetSyntax(_("DEL [\037nickname\037] \037mask\037")); + this->SetSyntax(_("LIST [\037nickname\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[0]; + Anope::string nick, mask; + + if (cmd.equals_ci("LIST")) + nick = params.size() > 1 ? params[1] : ""; + else + { + nick = params.size() == 3 ? params[1] : ""; + mask = params.size() > 1 ? params[params.size() - 1] : ""; + } + + NickCore *nc; + if (!nick.empty()) + { + const NickAlias *na = NickAlias::Find(nick); + if (na == NULL) + { + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + return; + } + else if (na->nc != source.GetAccount() && !source.HasPriv("nickserv/access")) + { + source.Reply(ACCESS_DENIED); + return; + } + else if (Config->GetModule("nickserv")->Get("secureadmins", "yes") && source.GetAccount() != na->nc && na->nc->IsServicesOper() && !cmd.equals_ci("LIST")) + { + source.Reply(_("You may view but not modify the access list of other Services Operators.")); + return; + } + + nc = na->nc; + } + else + nc = source.nc; + + if (!mask.empty() && (mask.find('@') == Anope::string::npos || mask.find('!') != Anope::string::npos)) + { + source.Reply(BAD_USERHOST_MASK); + source.Reply(MORE_INFO, Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), source.command.c_str()); + } + else if (cmd.equals_ci("LIST")) + return this->DoList(source, nc, mask); + else if (nc->HasExt("NS_SUSPENDED")) + source.Reply(NICK_X_SUSPENDED, nc->display.c_str()); + else if (cmd.equals_ci("ADD")) + return this->DoAdd(source, nc, mask); + else if (cmd.equals_ci("DEL")) + return this->DoDel(source, nc, mask); + else + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Modifies or displays the access list for your nick. This\n" + "is the list of addresses which will be automatically\n" + "recognized by %s as allowed to use the nick. If\n" + "you want to use the nick from a different address, you\n" + "need to send an \002IDENTIFY\002 command to make %s\n" + "recognize you. Services Operators may provide a nick\n" + "to modify other users' access lists.\n" + " \n" + "Examples:\n" + " \n" + " \002ACCESS ADD anyone@*.bepeg.com\002\n" + " Allows access to user \002anyone\002 from any machine in\n" + " the \002bepeg.com\002 domain.\n" + " \n" + " \002ACCESS DEL anyone@*.bepeg.com\002\n" + " Reverses the previous command.\n" + " \n" + " \002ACCESS LIST\002\n" + " Displays the current access list."), source.service->nick.c_str(), source.service->nick.c_str()); + return true; + } +}; + +class NSAccess : public Module +{ + CommandNSAccess commandnsaccess; + + public: + NSAccess(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsaccess(this) + { + } + + void OnNickRegister(User *u, NickAlias *na, const Anope::string &) anope_override + { + if (u && Config->GetModule(this)->Get("addaccessonreg")) + na->nc->AddAccess(u->Mask()); + } +}; + +MODULE_INIT(NSAccess) diff --git a/modules/commands/ns_ajoin.cpp b/modules/commands/ns_ajoin.cpp new file mode 100644 index 0000000..523b439 --- /dev/null +++ b/modules/commands/ns_ajoin.cpp @@ -0,0 +1,405 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +struct AJoinEntry; + +struct AJoinList : Serialize::Checker > +{ + AJoinList(Extensible *) : Serialize::Checker >("AJoinEntry") { } + ~AJoinList(); +}; + +struct AJoinEntry : Serializable +{ + Serialize::Reference owner; + Anope::string channel; + Anope::string key; + + AJoinEntry(Extensible *) : Serializable("AJoinEntry") { } + + ~AJoinEntry() + { + AJoinList *channels = owner->GetExt("ajoinlist"); + if (channels) + { + std::vector::iterator it = std::find((*channels)->begin(), (*channels)->end(), this); + if (it != (*channels)->end()) + (*channels)->erase(it); + } + } + + void Serialize(Serialize::Data &sd) const anope_override + { + if (!this->owner) + return; + + sd["owner"] << this->owner->display; + sd["channel"] << this->channel; + sd["key"] << this->key; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &sd) + { + Anope::string sowner; + + sd["owner"] >> sowner; + + NickCore *nc = NickCore::Find(sowner); + if (nc == NULL) + return NULL; + + AJoinEntry *aj; + if (obj) + aj = anope_dynamic_static_cast(obj); + else + { + aj = new AJoinEntry(nc); + aj->owner = nc; + } + + sd["channel"] >> aj->channel; + sd["key"] >> aj->key; + + if (!obj) + { + AJoinList *channels = nc->Require("ajoinlist"); + (*channels)->push_back(aj); + } + + return aj; + } +}; + +AJoinList::~AJoinList() +{ + for (unsigned i = 0; i < (*this)->size(); ++i) + delete (*this)->at(i); +} + +class CommandNSAJoin : public Command +{ + void DoList(CommandSource &source, NickCore *nc) + { + AJoinList *channels = nc->Require("ajoinlist"); + + if ((*channels)->empty()) + source.Reply(_("%s's auto join list is empty."), nc->display.c_str()); + else + { + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Channel")).AddColumn(_("Key")); + for (unsigned i = 0; i < (*channels)->size(); ++i) + { + AJoinEntry *aj = (*channels)->at(i); + ListFormatter::ListEntry entry; + entry["Number"] = stringify(i + 1); + entry["Channel"] = aj->channel; + entry["Key"] = aj->key; + list.AddEntry(entry); + } + + source.Reply(_("%s's auto join list:"), nc->display.c_str()); + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + } + + void DoAdd(CommandSource &source, NickCore *nc, const Anope::string &chans, const Anope::string &keys) + { + AJoinList *channels = nc->Require("ajoinlist"); + + Anope::string addedchans; + Anope::string alreadyadded; + Anope::string invalidkey; + commasepstream ksep(keys, true); + commasepstream csep(chans); + for (Anope::string chan, key; csep.GetToken(chan);) + { + ksep.GetToken(key); + + unsigned i = 0; + for (; i < (*channels)->size(); ++i) + if ((*channels)->at(i)->channel.equals_ci(chan)) + break; + + if ((*channels)->size() >= Config->GetModule(this->owner)->Get("ajoinmax")) + { + source.Reply(_("Sorry, the maximum of %d auto join entries has been reached."), Config->GetModule(this->owner)->Get("ajoinmax")); + return; + } + else if (i != (*channels)->size()) + alreadyadded += chan + ", "; + else if (IRCD->IsChannelValid(chan) == false) + source.Reply(CHAN_X_INVALID, chan.c_str()); + else + { + Channel *c = Channel::Find(chan); + Anope::string k; + if (c && c->GetParam("KEY", k) && key != k) + { + invalidkey += chan + ", "; + continue; + } + + AJoinEntry *entry = new AJoinEntry(nc); + entry->owner = nc; + entry->channel = chan; + entry->key = key; + (*channels)->push_back(entry); + addedchans += chan + ", "; + } + } + + if (!alreadyadded.empty()) + { + alreadyadded = alreadyadded.substr(0, alreadyadded.length() - 2); + source.Reply(_("%s is already on %s's auto join list."), alreadyadded.c_str(), nc->display.c_str()); + } + + if (!invalidkey.empty()) + { + invalidkey = invalidkey.substr(0, invalidkey.length() - 2); + source.Reply(_("%s had an invalid key specified, and was thus ignored."), invalidkey.c_str()); + } + + if (addedchans.empty()) + return; + + addedchans = addedchans.substr(0, addedchans.length() - 2); + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to ADD channel " << addedchans << " to " << nc->display; + source.Reply(_("%s added to %s's auto join list."), addedchans.c_str(), nc->display.c_str()); + } + + void DoDel(CommandSource &source, NickCore *nc, const Anope::string &chans) + { + AJoinList *channels = nc->Require("ajoinlist"); + Anope::string delchans; + Anope::string notfoundchans; + commasepstream sep(chans); + + for (Anope::string chan; sep.GetToken(chan);) + { + unsigned i = 0; + for (; i < (*channels)->size(); ++i) + if ((*channels)->at(i)->channel.equals_ci(chan)) + break; + + if (i == (*channels)->size()) + notfoundchans += chan + ", "; + else + { + delete (*channels)->at(i); + delchans += chan + ", "; + } + } + + if (!notfoundchans.empty()) + { + notfoundchans = notfoundchans.substr(0, notfoundchans.length() - 2); + source.Reply(_("%s was not found on %s's auto join list."), notfoundchans.c_str(), nc->display.c_str()); + } + + if (delchans.empty()) + return; + + delchans = delchans.substr(0, delchans.length() - 2); + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to DELETE channel " << delchans << " from " << nc->display; + source.Reply(_("%s was removed from %s's auto join list."), delchans.c_str(), nc->display.c_str()); + + if ((*channels)->empty()) + nc->Shrink("ajoinlist"); + } + + public: + CommandNSAJoin(Module *creator) : Command(creator, "nickserv/ajoin", 1, 4) + { + this->SetDesc(_("Manage your auto join list")); + this->SetSyntax(_("ADD [\037nickname\037] \037channel\037 [\037key\037]")); + this->SetSyntax(_("DEL [\037nickname\037] \037channel\037")); + this->SetSyntax(_("LIST [\037nickname\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[0]; + Anope::string nick, param, param2; + + if (cmd.equals_ci("LIST")) + nick = params.size() > 1 ? params[1] : ""; + else + nick = (params.size() > 2 && IRCD->IsChannelValid(params[2])) ? params[1] : ""; + + NickCore *nc; + if (!nick.empty()) + { + const NickAlias *na = NickAlias::Find(nick); + if (na == NULL) + { + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + return; + } + else if (na->nc != source.GetAccount() && !source.HasCommand("nickserv/ajoin")) + { + source.Reply(ACCESS_DENIED); + return; + } + + nc = na->nc; + param = params.size() > 2 ? params[2] : ""; + param2 = params.size() > 3 ? params[3] : ""; + } + else + { + nc = source.nc; + param = params.size() > 1 ? params[1] : ""; + param2 = params.size() > 2 ? params[2] : ""; + } + + if (cmd.equals_ci("LIST")) + return this->DoList(source, nc); + else if (nc->HasExt("NS_SUSPENDED")) + source.Reply(NICK_X_SUSPENDED, nc->display.c_str()); + else if (param.empty()) + this->OnSyntaxError(source, ""); + else if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + else if (cmd.equals_ci("ADD")) + return this->DoAdd(source, nc, param, param2); + else if (cmd.equals_ci("DEL")) + return this->DoDel(source, nc, param); + else + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command manages your auto join list. When you identify\n" + "you will automatically join the channels on your auto join list.\n" + "Services Operators may provide a nick to modify other users'\n" + "auto join lists.")); + return true; + } +}; + +class NSAJoin : public Module +{ + CommandNSAJoin commandnsajoin; + ExtensibleItem ajoinlist; + Serialize::Type ajoinentry_type; + + public: + NSAJoin(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsajoin(this), ajoinlist(this, "ajoinlist"), + ajoinentry_type("AJoinEntry", AJoinEntry::Unserialize) + { + + if (!IRCD || !IRCD->CanSVSJoin) + throw ModuleException("Your IRCd does not support SVSJOIN"); + + } + + void OnUserLogin(User *u) anope_override + { + BotInfo *NickServ = Config->GetClient("NickServ"); + if (!NickServ) + return; + + AJoinList *channels = u->Account()->GetExt("ajoinlist"); + if (channels == NULL) + return; + + /* Set +r now, so we can ajoin users into +R channels */ + ModeManager::ProcessModes(); + + for (unsigned i = 0; i < (*channels)->size(); ++i) + { + AJoinEntry *entry = (*channels)->at(i); + Channel *c = Channel::Find(entry->channel); + ChannelInfo *ci; + + if (c) + ci = c->ci; + else + ci = ChannelInfo::Find(entry->channel); + + bool need_invite = false; + Anope::string key = entry->key; + AccessGroup u_access; + + if (ci != NULL) + { + if (ci->HasExt("CS_SUSPENDED")) + continue; + u_access = ci->AccessFor(u); + } + if (c != NULL) + { + if (c->FindUser(u) != NULL) + continue; + else if (c->HasMode("OPERONLY") && !u->HasMode("OPER")) + continue; + else if (c->HasMode("ADMINONLY") && !u->HasMode("ADMIN")) + continue; + else if (c->HasMode("SSL") && !(u->HasMode("SSL") || u->HasExt("ssl"))) + continue; + else if (c->MatchesList(u, "BAN") == true && c->MatchesList(u, "EXCEPT") == false) + need_invite = true; + else if (c->HasMode("INVITE") && c->MatchesList(u, "INVITEOVERRIDE") == false) + need_invite = true; + + if (c->HasMode("KEY")) + { + Anope::string k; + if (c->GetParam("KEY", k)) + { + if (u_access.HasPriv("GETKEY")) + key = k; + else if (key != k) + need_invite = true; + } + } + if (c->HasMode("LIMIT")) + { + Anope::string l; + if (c->GetParam("LIMIT", l)) + { + try + { + unsigned limit = convertTo(l); + if (c->users.size() >= limit) + need_invite = true; + } + catch (const ConvertException &) { } + } + } + } + + if (need_invite && c != NULL) + { + if (!u_access.HasPriv("INVITE")) + continue; + IRCD->SendInvite(NickServ, c, u); + } + + IRCD->SendSVSJoin(NickServ, u, entry->channel, key); + } + } +}; + +MODULE_INIT(NSAJoin) diff --git a/modules/commands/ns_alist.cpp b/modules/commands/ns_alist.cpp new file mode 100644 index 0000000..f151d9e --- /dev/null +++ b/modules/commands/ns_alist.cpp @@ -0,0 +1,149 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandNSAList : public Command +{ + static bool ChannelSort(ChannelInfo *ci1, ChannelInfo *ci2) + { + return ci::less()(ci1->name, ci2->name); + } + + public: + CommandNSAList(Module *creator) : Command(creator, "nickserv/alist", 0, 2) + { + this->SetDesc(_("List channels you have access on")); + this->SetSyntax(_("[\037nickname\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + Anope::string nick = source.GetNick(); + NickCore *nc = source.nc; + + if (params.size() && source.HasPriv("nickserv/alist")) + { + nick = params[0]; + const NickAlias *na = NickAlias::Find(nick); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + return; + } + nc = na->nc; + } + + ListFormatter list(source.GetAccount()); + int chan_count = 0; + + list.AddColumn(_("Number")).AddColumn(_("Channel")).AddColumn(_("Access")).AddColumn(_("Description")); + + std::deque queue; + nc->GetChannelReferences(queue); + std::sort(queue.begin(), queue.end(), ChannelSort); + + for (unsigned i = 0; i < queue.size(); ++i) + { + ChannelInfo *ci = queue[i]; + ListFormatter::ListEntry entry; + + if (ci->GetFounder() == nc) + { + ++chan_count; + entry["Number"] = stringify(chan_count); + entry["Channel"] = (ci->HasExt("CS_NO_EXPIRE") ? "!" : "") + ci->name; + entry["Access"] = Language::Translate(source.GetAccount(), _("Founder")); + entry["Description"] = ci->desc; + list.AddEntry(entry); + continue; + } + + if (ci->GetSuccessor() == nc) + { + ++chan_count; + entry["Number"] = stringify(chan_count); + entry["Channel"] = (ci->HasExt("CS_NO_EXPIRE") ? "!" : "") + ci->name; + entry["Access"] = Language::Translate(source.GetAccount(), _("Successor")); + entry["Description"] = ci->desc; + list.AddEntry(entry); + continue; + } + + AccessGroup access = ci->AccessFor(nc, false); + if (access.empty()) + continue; + + ++chan_count; + + entry["Number"] = stringify(chan_count); + entry["Channel"] = (ci->HasExt("CS_NO_EXPIRE") ? "!" : "") + ci->name; + for (unsigned j = 0; j < access.paths.size(); ++j) + { + ChanAccess::Path &p = access.paths[j]; + + // not interested in indirect access + if (p.size() != 1) + continue; + + ChanAccess *a = p[0]; + entry["Access"] = entry["Access"] + ", " + a->AccessSerialize(); + } + entry["Access"] = entry["Access"].substr(2); + entry["Description"] = ci->desc; + list.AddEntry(entry); + } + + std::vector replies; + list.Process(replies); + + if (!chan_count) + { + source.Reply(_("\002%s\002 has no access in any channels."), nc->display.c_str()); + } + else + { + source.Reply(_("Channels that \002%s\002 has access on:"), nc->display.c_str()); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("End of list - %d channels shown."), chan_count); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Lists all channels you have access on.\n" + " \n" + "Channels that have the \037NOEXPIRE\037 option set will be\n" + "prefixed by an exclamation mark. The nickname parameter is\n" + "limited to Services Operators")); + + return true; + } +}; + +class NSAList : public Module +{ + CommandNSAList commandnsalist; + + public: + NSAList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsalist(this) + { + + } +}; + +MODULE_INIT(NSAList) diff --git a/modules/commands/ns_cert.cpp b/modules/commands/ns_cert.cpp new file mode 100644 index 0000000..1d730b3 --- /dev/null +++ b/modules/commands/ns_cert.cpp @@ -0,0 +1,407 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/ns_cert.h" + +static Anope::hash_map certmap; + +struct CertServiceImpl : CertService +{ + CertServiceImpl(Module *o) : CertService(o) { } + + NickCore* FindAccountFromCert(const Anope::string &cert) anope_override + { + Anope::hash_map::iterator it = certmap.find(cert); + if (it != certmap.end()) + return it->second; + return NULL; + } +}; + +struct NSCertListImpl : NSCertList +{ + Serialize::Reference nc; + std::vector certs; + + public: + NSCertListImpl(Extensible *obj) : nc(anope_dynamic_static_cast(obj)) { } + + ~NSCertListImpl() + { + ClearCert(); + } + + /** Add an entry to the nick's certificate list + * + * @param entry The fingerprint to add to the cert list + * + * Adds a new entry into the cert list. + */ + void AddCert(const Anope::string &entry) anope_override + { + this->certs.push_back(entry); + certmap[entry] = nc; + FOREACH_MOD(OnNickAddCert, (this->nc, entry)); + } + + /** Get an entry from the nick's cert list by index + * + * @param entry Index in the certificate list vector to retrieve + * @return The fingerprint entry of the given index if within bounds, an empty string if the vector is empty or the index is out of bounds + * + * Retrieves an entry from the certificate list corresponding to the given index. + */ + Anope::string GetCert(unsigned entry) const anope_override + { + if (entry >= this->certs.size()) + return ""; + return this->certs[entry]; + } + + unsigned GetCertCount() const anope_override + { + return this->certs.size(); + } + + /** Find an entry in the nick's cert list + * + * @param entry The fingerprint to search for + * @return True if the fingerprint is found in the cert list, false otherwise + * + * Search for an fingerprint within the cert list. + */ + bool FindCert(const Anope::string &entry) const anope_override + { + return std::find(this->certs.begin(), this->certs.end(), entry) != this->certs.end(); + } + + /** Erase a fingerprint from the nick's certificate list + * + * @param entry The fingerprint to remove + * + * Removes the specified fingerprint from the cert list. + */ + void EraseCert(const Anope::string &entry) anope_override + { + std::vector::iterator it = std::find(this->certs.begin(), this->certs.end(), entry); + if (it != this->certs.end()) + { + FOREACH_MOD(OnNickEraseCert, (this->nc, entry)); + certmap.erase(entry); + this->certs.erase(it); + } + } + + /** Clears the entire nick's cert list + * + * Deletes all the memory allocated in the certificate list vector and then clears the vector. + */ + void ClearCert() anope_override + { + FOREACH_MOD(OnNickClearCert, (this->nc)); + for (unsigned i = 0; i < certs.size(); ++i) + certmap.erase(certs[i]); + this->certs.clear(); + } + + void Check() anope_override + { + if (this->certs.empty()) + nc->Shrink("certificates"); + } + + struct ExtensibleItem : ::ExtensibleItem + { + ExtensibleItem(Module *m, const Anope::string &ename) : ::ExtensibleItem(m, ename) { } + + void ExtensibleSerialize(const Extensible *e, const Serializable *s, Serialize::Data &data) const anope_override + { + if (s->GetSerializableType()->GetName() != "NickCore") + return; + + const NickCore *n = anope_dynamic_static_cast(e); + NSCertList *c = this->Get(n); + if (c == NULL || !c->GetCertCount()) + return; + + for (unsigned i = 0; i < c->GetCertCount(); ++i) + data["cert"] << c->GetCert(i) << " "; + } + + void ExtensibleUnserialize(Extensible *e, Serializable *s, Serialize::Data &data) anope_override + { + if (s->GetSerializableType()->GetName() != "NickCore") + return; + + NickCore *n = anope_dynamic_static_cast(e); + NSCertListImpl *c = this->Require(n); + + Anope::string buf; + data["cert"] >> buf; + spacesepstream sep(buf); + for (unsigned i = 0; i < c->certs.size(); ++i) + certmap.erase(c->certs[i]); + c->certs.clear(); + while (sep.GetToken(buf)) + { + c->certs.push_back(buf); + certmap[buf] = n; + } + } + }; +}; + +class CommandNSCert : public Command +{ + private: + void DoAdd(CommandSource &source, NickCore *nc, Anope::string certfp) + { + NSCertList *cl = nc->Require("certificates"); + unsigned max = Config->GetModule(this->owner)->Get("max", "5"); + + if (cl->GetCertCount() >= max) + { + source.Reply(_("Sorry, the maximum of %d certificate entries has been reached."), max); + return; + } + + if (source.GetAccount() == nc) + { + User *u = source.GetUser(); + + if (!u || u->fingerprint.empty()) + { + source.Reply(_("You are not using a client certificate.")); + return; + } + + certfp = u->fingerprint; + } + + if (cl->FindCert(certfp)) + { + source.Reply(_("Fingerprint \002%s\002 already present on %s's certificate list."), certfp.c_str(), nc->display.c_str()); + return; + } + + if (certmap.find(certfp) != certmap.end()) + { + source.Reply(_("Fingerprint \002%s\002 is already in use."), certfp.c_str()); + return; + } + + cl->AddCert(certfp); + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to ADD certificate fingerprint " << certfp << " to " << nc->display; + source.Reply(_("\002%s\002 added to %s's certificate list."), certfp.c_str(), nc->display.c_str()); + } + + void DoDel(CommandSource &source, NickCore *nc, Anope::string certfp) + { + NSCertList *cl = nc->Require("certificates"); + + if (certfp.empty()) + { + User *u = source.GetUser(); + if (u) + certfp = u->fingerprint; + } + + if (certfp.empty()) + { + this->OnSyntaxError(source, "DEL"); + return; + } + + if (!cl->FindCert(certfp)) + { + source.Reply(_("\002%s\002 not found on %s's certificate list."), certfp.c_str(), nc->display.c_str()); + return; + } + + cl->EraseCert(certfp); + cl->Check(); + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to DELETE certificate fingerprint " << certfp << " from " << nc->display; + source.Reply(_("\002%s\002 deleted from %s's certificate list."), certfp.c_str(), nc->display.c_str()); + } + + void DoList(CommandSource &source, const NickCore *nc) + { + NSCertList *cl = nc->GetExt("certificates"); + + if (!cl || !cl->GetCertCount()) + { + source.Reply(_("%s's certificate list is empty."), nc->display.c_str()); + return; + } + + source.Reply(_("Certificate list for %s:"), nc->display.c_str()); + for (unsigned i = 0; i < cl->GetCertCount(); ++i) + { + Anope::string fingerprint = cl->GetCert(i); + source.Reply(" %s", fingerprint.c_str()); + } + } + + public: + CommandNSCert(Module *creator) : Command(creator, "nickserv/cert", 1, 3) + { + this->SetDesc(_("Modify the nickname client certificate list")); + this->SetSyntax(_("ADD [\037nickname\037] [\037fingerprint\037]")); + this->SetSyntax(_("DEL [\037nickname\037] \037fingerprint\037")); + this->SetSyntax(_("LIST [\037nickname\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[0]; + Anope::string nick, certfp; + + if (cmd.equals_ci("LIST")) + nick = params.size() > 1 ? params[1] : ""; + else + { + nick = params.size() == 3 ? params[1] : ""; + certfp = params.size() > 1 ? params[params.size() - 1] : ""; + } + + NickCore *nc; + if (!nick.empty()) + { + const NickAlias *na = NickAlias::Find(nick); + if (na == NULL) + { + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + return; + } + else if (na->nc != source.GetAccount() && !source.HasPriv("nickserv/access")) + { + source.Reply(ACCESS_DENIED); + return; + } + else if (Config->GetModule("nickserv")->Get("secureadmins", "yes") && source.GetAccount() != na->nc && na->nc->IsServicesOper() && !cmd.equals_ci("LIST")) + { + source.Reply(_("You may view but not modify the certificate list of other Services Operators.")); + return; + } + + nc = na->nc; + } + else + nc = source.nc; + + if (cmd.equals_ci("LIST")) + return this->DoList(source, nc); + else if (nc->HasExt("NS_SUSPENDED")) + source.Reply(NICK_X_SUSPENDED, nc->display.c_str()); + else if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + else if (cmd.equals_ci("ADD")) + return this->DoAdd(source, nc, certfp); + else if (cmd.equals_ci("DEL")) + return this->DoDel(source, nc, certfp); + else + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Modifies or displays the certificate list for your nick.\n" + "If you connect to IRC and provide a client certificate with a\n" + "matching fingerprint in the cert list, you will be\n" + "automatically identified to services. Services Operators\n" + "may provide a nick to modify other users' certificate lists.\n" + " \n")); + source.Reply(_("Examples:\n" + " \n" + " \002CERT ADD\002\n" + " Adds your current fingerprint to the certificate list and\n" + " automatically identifies you when you connect to IRC\n" + " using this fingerprint.\n" + " \n" + " \002CERT DEL \002\n" + " Removes the fingerprint from your certificate list.\n" + " \n" + " \002CERT LIST\002\n" + " Displays the current certificate list.")); + return true; + } +}; + +class NSCert : public Module +{ + CommandNSCert commandnscert; + NSCertListImpl::ExtensibleItem certs; + CertServiceImpl cs; + + public: + NSCert(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnscert(this), certs(this, "certificates"), cs(this) + { + if (!IRCD || !IRCD->CanCertFP) + throw ModuleException("Your IRCd does not support ssl client certificates"); + } + + void OnFingerprint(User *u) anope_override + { + BotInfo *NickServ = Config->GetClient("NickServ"); + if (!NickServ || u->IsIdentified()) + return; + + NickCore *nc = cs.FindAccountFromCert(u->fingerprint); + if (!nc || nc->HasExt("NS_SUSPENDED")) + return; + + unsigned int maxlogins = Config->GetModule("ns_identify")->Get("maxlogins"); + if (maxlogins && nc->users.size() >= maxlogins) + { + u->SendMessage(NickServ, _("Account \002%s\002 has already reached the maximum number of simultaneous logins (%u)."), nc->display.c_str(), maxlogins); + return; + } + + NickAlias *na = NickAlias::Find(u->nick); + if (na && na->nc == nc) + u->Identify(na); + else + u->Login(nc); + + u->SendMessage(NickServ, _("SSL certificate fingerprint accepted, you are now identified to \002%s\002."), nc->display.c_str()); + Log(NickServ) << u->GetMask() << " automatically identified for account " << nc->display << " via SSL certificate fingerprint"; + } + + EventReturn OnNickValidate(User *u, NickAlias *na) anope_override + { + NSCertList *cl = certs.Get(na->nc); + if (!u->fingerprint.empty() && cl && cl->FindCert(u->fingerprint)) + { + BotInfo *NickServ = Config->GetClient("NickServ"); + + unsigned int maxlogins = Config->GetModule("ns_identify")->Get("maxlogins"); + if (maxlogins && na->nc->users.size() >= maxlogins) + { + u->SendMessage(NickServ, _("Account \002%s\002 has already reached the maximum number of simultaneous logins (%u)."), na->nc->display.c_str(), maxlogins); + return EVENT_CONTINUE; + } + + u->Identify(na); + + u->SendMessage(NickServ, _("SSL certificate fingerprint accepted, you are now identified.")); + Log(NickServ) << u->GetMask() << " automatically identified for account " << na->nc->display << " via SSL certificate fingerprint"; + return EVENT_ALLOW; + } + + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(NSCert) diff --git a/modules/commands/ns_drop.cpp b/modules/commands/ns_drop.cpp new file mode 100644 index 0000000..659d3c6 --- /dev/null +++ b/modules/commands/ns_drop.cpp @@ -0,0 +1,86 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandNSDrop : public Command +{ + public: + CommandNSDrop(Module *creator) : Command(creator, "nickserv/drop", 1, 1) + { + this->SetSyntax(_("\037nickname\037")); + this->SetDesc(_("Cancel the registration of a nickname")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &nick = params[0]; + + if (Anope::ReadOnly && !source.HasPriv("nickserv/drop")) + { + source.Reply(_("Sorry, nickname de-registration is temporarily disabled.")); + return; + } + + NickAlias *na = NickAlias::Find(nick); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + return; + } + + bool is_mine = source.GetAccount() == na->nc; + + if (!is_mine && !source.HasPriv("nickserv/drop")) + source.Reply(ACCESS_DENIED); + else if (Config->GetModule("nickserv")->Get("secureadmins", "yes") && !is_mine && na->nc->IsServicesOper()) + source.Reply(_("You may not drop other Services Operators' nicknames.")); + else + { + FOREACH_MOD(OnNickDrop, (source, na)); + + Log(!is_mine ? LOG_ADMIN : LOG_COMMAND, source, this) << "to drop nickname " << na->nick << " (group: " << na->nc->display << ") (email: " << (!na->nc->email.empty() ? na->nc->email : "none") << ")"; + delete na; + + source.Reply(_("Nickname \002%s\002 has been dropped."), nick.c_str()); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Drops the given nick from the database. Once your nickname\n" + "is dropped you may lose all of your access and channels that\n" + "you may own. Any other user will be able to gain control of\n" + "this nick.")); + if (!source.HasPriv("nickserv/drop")) + source.Reply(_("You may drop any nick within your group.")); + else + source.Reply(_("As a Services Operator, you may drop any nick.")); + + return true; + } +}; + +class NSDrop : public Module +{ + CommandNSDrop commandnsdrop; + + public: + NSDrop(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsdrop(this) + { + + } +}; + +MODULE_INIT(NSDrop) diff --git a/modules/commands/ns_getemail.cpp b/modules/commands/ns_getemail.cpp new file mode 100644 index 0000000..76e756b --- /dev/null +++ b/modules/commands/ns_getemail.cpp @@ -0,0 +1,74 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + * + * A simple call to check for all emails that a user may have registered + * with. It returns the nicks that match the email you provide. Wild + * Cards are not excepted. Must use user@email-host. + */ + +#include "module.h" + +class CommandNSGetEMail : public Command +{ + public: + CommandNSGetEMail(Module *creator) : Command(creator, "nickserv/getemail", 1, 1) + { + this->SetDesc(_("Matches and returns all users that registered using given email")); + this->SetSyntax(_("\037email\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &email = params[0]; + int j = 0; + + Log(LOG_ADMIN, source, this) << "on " << email; + + for (nickcore_map::const_iterator it = NickCoreList->begin(), it_end = NickCoreList->end(); it != it_end; ++it) + { + const NickCore *nc = it->second; + + if (!nc->email.empty() && Anope::Match(nc->email, email)) + { + ++j; + source.Reply(_("Email matched: \002%s\002 (\002%s\002) to \002%s\002."), nc->display.c_str(), nc->email.c_str(), email.c_str()); + } + } + + if (j <= 0) + { + source.Reply(_("No registrations matching \002%s\002 were found."), email.c_str()); + return; + } + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Returns the matching accounts that used given email.")); + return true; + } +}; + +class NSGetEMail : public Module +{ + CommandNSGetEMail commandnsgetemail; + public: + NSGetEMail(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsgetemail(this) + { + + } +}; + +MODULE_INIT(NSGetEMail) diff --git a/modules/commands/ns_getpass.cpp b/modules/commands/ns_getpass.cpp new file mode 100644 index 0000000..d7f6f11 --- /dev/null +++ b/modules/commands/ns_getpass.cpp @@ -0,0 +1,74 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandNSGetPass : public Command +{ + public: + CommandNSGetPass(Module *creator) : Command(creator, "nickserv/getpass", 1, 1) + { + this->SetDesc(_("Retrieve the password for a nickname")); + this->SetSyntax(_("\037nickname\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &nick = params[0]; + Anope::string tmp_pass; + const NickAlias *na; + + if (!(na = NickAlias::Find(nick))) + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + else if (Config->GetModule("nickserv")->Get("secureadmins", "yes") && na->nc->IsServicesOper()) + source.Reply(_("You may not get the password of other Services Operators.")); + else + { + if (Anope::Decrypt(na->nc->pass, tmp_pass) == 1) + { + Log(LOG_ADMIN, source, this) << "for " << nick; + source.Reply(_("Password for %s is \002%s\002."), nick.c_str(), tmp_pass.c_str()); + } + else + source.Reply(_("GETPASS command unavailable because encryption is in use.")); + } + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Returns the password for the given nickname. \002Note\002 that\n" + "whenever this command is used, a message including the\n" + "person who issued the command and the nickname it was used\n" + "on will be logged and sent out as a WALLOPS/GLOBOPS.")); + return true; + } +}; + +class NSGetPass : public Module +{ + CommandNSGetPass commandnsgetpass; + + public: + NSGetPass(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsgetpass(this) + { + + Anope::string tmp_pass = "plain:tmp"; + if (!Anope::Decrypt(tmp_pass, tmp_pass)) + throw ModuleException("Incompatible with the encryption module being used"); + + } +}; + +MODULE_INIT(NSGetPass) diff --git a/modules/commands/ns_group.cpp b/modules/commands/ns_group.cpp new file mode 100644 index 0000000..efca75f --- /dev/null +++ b/modules/commands/ns_group.cpp @@ -0,0 +1,396 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/ns_cert.h" + +class NSGroupRequest : public IdentifyRequest +{ + CommandSource source; + Command *cmd; + Anope::string nick; + Reference target; + + public: + NSGroupRequest(Module *o, CommandSource &src, Command *c, const Anope::string &n, NickAlias *targ, const Anope::string &pass) : IdentifyRequest(o, targ->nc->display, pass), source(src), cmd(c), nick(n), target(targ) { } + + void OnSuccess() anope_override + { + User *u = source.GetUser(); + + /* user changed nick? */ + if (u != NULL && u->nick != nick) + return; + + if (!target || !target->nc) + return; + + NickAlias *na = NickAlias::Find(nick); + /* If the nick is already registered, drop it. */ + if (na) + { + delete na; + } + + na = new NickAlias(nick, target->nc); + na->time_registered = na->last_seen = Anope::CurTime; + + if (u != NULL) + { + na->last_usermask = u->GetIdent() + "@" + u->GetDisplayedHost(); + na->last_realname = u->realname; + } + else + { + na->last_realname = source.GetNick(); + } + + if (u != NULL) + { + IRCD->SendLogin(u, na); // protocol modules prevent this on unconfirmed accounts + u->Login(target->nc); + FOREACH_MOD(OnNickGroup, (u, target)); + } + + Log(LOG_COMMAND, source, cmd) << "to make " << nick << " join group of " << target->nick << " (" << target->nc->display << ") (email: " << (!target->nc->email.empty() ? target->nc->email : "none") << ")"; + source.Reply(_("You are now in the group of \002%s\002."), target->nick.c_str()); + + if (u) + u->lastnickreg = Anope::CurTime; + } + + void OnFail() anope_override + { + User *u = source.GetUser(); + + Log(LOG_COMMAND, source, cmd) << "and failed to group to " << target->nick; + if (NickAlias::Find(GetAccount()) != NULL) + { + source.Reply(PASSWORD_INCORRECT); + if (u) + u->BadPassword(); + } + else + source.Reply(NICK_X_NOT_REGISTERED, GetAccount().c_str()); + } +}; + +class CommandNSGroup : public Command +{ + public: + CommandNSGroup(Module *creator) : Command(creator, "nickserv/group", 0, 2) + { + this->SetDesc(_("Join a group")); + this->SetSyntax(_("\037[target]\037 \037[password]\037")); + this->AllowUnregistered(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + User *user = source.GetUser(); + + Anope::string nick; + if (params.empty()) + { + NickCore* core = source.GetAccount(); + if (core) + nick = core->display; + } + else + nick = params[0]; + + if (nick.empty()) + { + this->SendSyntax(source); + return; + } + + const Anope::string &pass = params.size() > 1 ? params[1] : ""; + + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, nickname grouping is temporarily disabled.")); + return; + } + + if (!IRCD->IsNickValid(source.GetNick())) + { + source.Reply(NICK_CANNOT_BE_REGISTERED, source.GetNick().c_str()); + return; + } + + if (Config->GetModule("nickserv")->Get("restrictopernicks")) + for (unsigned i = 0; i < Oper::opers.size(); ++i) + { + Oper *o = Oper::opers[i]; + + if (user != NULL && !user->HasMode("OPER") && user->nick.find_ci(o->name) != Anope::string::npos) + { + source.Reply(NICK_CANNOT_BE_REGISTERED, user->nick.c_str()); + return; + } + } + + NickAlias *target, *na = NickAlias::Find(source.GetNick()); + const Anope::string &guestnick = Config->GetModule("nickserv")->Get("guestnickprefix", "Guest"); + time_t reg_delay = Config->GetModule("nickserv")->Get("regdelay"); + unsigned maxaliases = Config->GetModule(this->owner)->Get("maxaliases"); + if (!(target = NickAlias::Find(nick))) + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + else if (user && Anope::CurTime < user->lastnickreg + reg_delay) + source.Reply(_("Please wait %d seconds before using the GROUP command again."), (reg_delay + user->lastnickreg) - Anope::CurTime); + else if (target->nc->HasExt("NS_SUSPENDED")) + { + Log(LOG_COMMAND, source, this) << "and tried to group to SUSPENDED nick " << target->nick; + source.Reply(NICK_X_SUSPENDED, target->nick.c_str()); + } + else if (na && Config->GetModule(this->owner)->Get("nogroupchange")) + source.Reply(_("Your nick is already registered.")); + else if (na && *target->nc == *na->nc) + source.Reply(_("You are already a member of the group of \002%s\002."), target->nick.c_str()); + else if (na && na->nc != source.GetAccount()) + source.Reply(NICK_IDENTIFY_REQUIRED); + else if (maxaliases && target->nc->aliases->size() >= maxaliases && !target->nc->IsServicesOper()) + source.Reply(_("There are too many nicks in your group.")); + else if (source.GetNick().length() <= guestnick.length() + 7 && + source.GetNick().length() >= guestnick.length() + 1 && + !source.GetNick().find_ci(guestnick) && !source.GetNick().substr(guestnick.length()).find_first_not_of("1234567890")) + { + source.Reply(NICK_CANNOT_BE_REGISTERED, source.GetNick().c_str()); + } + else + { + bool ok = false; + if (!na && source.GetAccount() == target->nc) + ok = true; + + NSCertList *cl = target->nc->GetExt("certificates"); + if (user != NULL && !user->fingerprint.empty() && cl && cl->FindCert(user->fingerprint)) + ok = true; + + if (ok == false && !pass.empty()) + { + NSGroupRequest *req = new NSGroupRequest(owner, source, this, source.GetNick(), target, pass); + FOREACH_MOD(OnCheckAuthentication, (source.GetUser(), req)); + req->Dispatch(); + } + else + { + NSGroupRequest req(owner, source, this, source.GetNick(), target, pass); + + if (ok) + req.OnSuccess(); + else + req.OnFail(); + } + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command makes your nickname join the \037target\037 nickname's\n" + "group. \037password\037 is the password of the target nickname.\n" + " \n" + "Joining a group will allow you to share your configuration,\n" + "memos, and channel privileges with all the nicknames in the\n" + "group, and much more!\n" + " \n" + "A group exists as long as it is useful. This means that even\n" + "if a nick of the group is dropped, you won't lose the\n" + "shared things described above, as long as there is at\n" + "least one nick remaining in the group.\n" + " \n" + "You may be able to use this command even if you have not registered\n" + "your nick yet. If your nick is already registered, you'll\n" + "need to identify yourself before using this command.\n" + " \n" + "It is recommended to use this command with a non-registered\n" + "nick because it will be registered automatically when\n" + "using this command. You may use it with a registered nick (to\n" + "change your group) only if your network administrators allowed\n" + "it.\n" + " \n" + "You can only be in one group at a time. Group merging is\n" + "not possible.\n" + " \n" + "\037Note\037: all the nicknames of a group have the same password.")); + return true; + } +}; + +class CommandNSUngroup : public Command +{ + public: + CommandNSUngroup(Module *creator) : Command(creator, "nickserv/ungroup", 0, 1) + { + this->SetDesc(_("Remove a nick from a group")); + this->SetSyntax(_("[\037nick\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + Anope::string nick = !params.empty() ? params[0] : ""; + NickAlias *na = NickAlias::Find(!nick.empty() ? nick : source.GetNick()); + + if (source.GetAccount()->aliases->size() == 1) + source.Reply(_("Your nick is not grouped to anything, you can't ungroup it.")); + else if (!na) + source.Reply(NICK_X_NOT_REGISTERED, !nick.empty() ? nick.c_str() : source.GetNick().c_str()); + else if (na->nc != source.GetAccount()) + source.Reply(_("Nick %s is not in your group."), na->nick.c_str()); + else + { + NickCore *oldcore = na->nc; + + std::vector::iterator it = std::find(oldcore->aliases->begin(), oldcore->aliases->end(), na); + if (it != oldcore->aliases->end()) + oldcore->aliases->erase(it); + + if (na->nick.equals_ci(oldcore->display)) + oldcore->SetDisplay(oldcore->aliases->front()); + + NickCore *nc = new NickCore(na->nick); + na->nc = nc; + nc->aliases->push_back(na); + + nc->pass = oldcore->pass; + if (!oldcore->email.empty()) + nc->email = oldcore->email; + nc->language = oldcore->language; + + Log(LOG_COMMAND, source, this) << "to make " << na->nick << " leave group of " << oldcore->display << " (email: " << (!oldcore->email.empty() ? oldcore->email : "none") << ")"; + source.Reply(_("Nick %s has been ungrouped from %s."), na->nick.c_str(), oldcore->display.c_str()); + + User *user = User::Find(na->nick, true); + if (user) + /* The user on the nick who was ungrouped may be identified to the old group, set -r */ + user->RemoveMode(source.service, "REGISTERED"); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command ungroups your nick, or if given, the specified nick,\n" + "from the group it is in. The ungrouped nick keeps its registration\n" + "time, password, email, greet, language, and url. Everything else\n" + "is reset. You may not ungroup yourself if there is only one nick in\n" + "your group.")); + return true; + } +}; + +class CommandNSGList : public Command +{ + public: + CommandNSGList(Module *creator) : Command(creator, "nickserv/glist", 0, 1) + { + this->SetDesc(_("Lists all nicknames in your group")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &nick = !params.empty() ? params[0] : ""; + const NickCore *nc; + + if (!nick.empty()) + { + const NickAlias *na = NickAlias::Find(nick); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + return; + } + else if (na->nc != source.GetAccount() && !source.IsServicesOper()) + { + source.Reply(ACCESS_DENIED); + return; + } + + nc = na->nc; + } + else + nc = source.GetAccount(); + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Nick")).AddColumn(_("Expires")); + time_t nickserv_expire = Config->GetModule("nickserv")->Get("expire", "21d"), + unconfirmed_expire = Config->GetModule("ns_register")->Get("unconfirmedexpire", "1d"); + for (unsigned i = 0; i < nc->aliases->size(); ++i) + { + const NickAlias *na2 = nc->aliases->at(i); + + Anope::string expires; + if (na2->HasExt("NS_NO_EXPIRE")) + expires = NO_EXPIRE; + else if (!nickserv_expire || Anope::NoExpire) + ; + else if (na2->nc->HasExt("UNCONFIRMED") && unconfirmed_expire) + expires = Anope::strftime(na2->time_registered + unconfirmed_expire, source.GetAccount()); + else + expires = Anope::strftime(na2->last_seen + nickserv_expire, source.GetAccount()); + + ListFormatter::ListEntry entry; + entry["Nick"] = na2->nick; + entry["Expires"] = expires; + list.AddEntry(entry); + } + + source.Reply(!nick.empty() ? _("List of nicknames in the group of \002%s\002:") : _("List of nicknames in your group:"), nc->display.c_str()); + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("%d nickname(s) in the group."), nc->aliases->size()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + if (source.IsServicesOper()) + source.Reply(_("Syntax: \002%s [\037nickname\037]\002\n" + " \n" + "Without a parameter, lists all nicknames that are in\n" + "your group.\n" + " \n" + "With a parameter, lists all nicknames that are in the\n" + "group of the given nick.\n" + "Specifying a nick is limited to \002Services Operators\002."), + source.command.c_str()); + else + source.Reply(_("Syntax: \002%s\002\n" + " \n" + "Lists all nicks in your group."), source.command.c_str()); + + return true; + } +}; + +class NSGroup : public Module +{ + CommandNSGroup commandnsgroup; + CommandNSUngroup commandnsungroup; + CommandNSGList commandnsglist; + + public: + NSGroup(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsgroup(this), commandnsungroup(this), commandnsglist(this) + { + if (Config->GetModule("nickserv")->Get("nonicknameownership")) + throw ModuleException(modname + " can not be used with options:nonicknameownership enabled"); + } +}; + +MODULE_INIT(NSGroup) diff --git a/modules/commands/ns_identify.cpp b/modules/commands/ns_identify.cpp new file mode 100644 index 0000000..39b8560 --- /dev/null +++ b/modules/commands/ns_identify.cpp @@ -0,0 +1,128 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class NSIdentifyRequest : public IdentifyRequest +{ + CommandSource source; + Command *cmd; + + public: + NSIdentifyRequest(Module *o, CommandSource &s, Command *c, const Anope::string &acc, const Anope::string &pass) : IdentifyRequest(o, acc, pass), source(s), cmd(c) { } + + void OnSuccess() anope_override + { + if (!source.GetUser()) + return; + + User *u = source.GetUser(); + NickAlias *na = NickAlias::Find(GetAccount()); + + if (!na) + source.Reply(NICK_X_NOT_REGISTERED, GetAccount().c_str()); + else + { + if (u->IsIdentified()) + Log(LOG_COMMAND, source, cmd) << "to log out of account " << u->Account()->display; + + Log(LOG_COMMAND, source, cmd) << "and identified for account " << na->nc->display; + source.Reply(_("Password accepted - you are now recognized.")); + u->Identify(na); + } + } + + void OnFail() anope_override + { + if (source.GetUser()) + { + bool accountexists = NickAlias::Find(GetAccount()) != NULL; + Log(LOG_COMMAND, source, cmd) << "and failed to identify to" << (accountexists ? " " : " nonexistent ") << "account " << GetAccount(); + if (accountexists) + { + source.Reply(PASSWORD_INCORRECT); + source.GetUser()->BadPassword(); + } + else + source.Reply(NICK_X_NOT_REGISTERED, GetAccount().c_str()); + } + } +}; + +class CommandNSIdentify : public Command +{ + public: + CommandNSIdentify(Module *creator) : Command(creator, "nickserv/identify", 1, 2) + { + this->SetDesc(_("Identify yourself with your password")); + this->SetSyntax(_("[\037account\037] \037password\037")); + this->AllowUnregistered(true); + this->RequireUser(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + + const Anope::string &nick = params.size() == 2 ? params[0] : u->nick; + Anope::string pass = params[params.size() - 1]; + + NickAlias *na = NickAlias::Find(nick); + if (na && na->nc->HasExt("NS_SUSPENDED")) + { + source.Reply(NICK_X_SUSPENDED, na->nick.c_str()); + return; + } + + if (u->Account() && na && u->Account() == na->nc) + { + source.Reply(_("You are already identified.")); + return; + } + + unsigned int maxlogins = Config->GetModule(this->owner)->Get("maxlogins"); + if (na && maxlogins && na->nc->users.size() >= maxlogins) + { + source.Reply(_("Account \002%s\002 has already reached the maximum number of simultaneous logins (%u)."), na->nc->display.c_str(), maxlogins); + return; + } + + NSIdentifyRequest *req = new NSIdentifyRequest(owner, source, this, na ? na->nc->display : nick, pass); + FOREACH_MOD(OnCheckAuthentication, (u, req)); + req->Dispatch(); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Tells %s that you are really the owner of this\n" + "nick. Many commands require you to authenticate yourself\n" + "with this command before you use them. The password\n" + "should be the same one you sent with the \002REGISTER\002\n" + "command."), source.service->nick.c_str()); + return true; + } +}; + +class NSIdentify : public Module +{ + CommandNSIdentify commandnsidentify; + + public: + NSIdentify(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsidentify(this) + { + + } +}; + +MODULE_INIT(NSIdentify) diff --git a/modules/commands/ns_info.cpp b/modules/commands/ns_info.cpp new file mode 100644 index 0000000..444f1fa --- /dev/null +++ b/modules/commands/ns_info.cpp @@ -0,0 +1,283 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandNSInfo : public Command +{ + public: + CommandNSInfo(Module *creator) : Command(creator, "nickserv/info", 0, 2) + { + this->SetDesc(_("Displays information about a given nickname")); + this->SetSyntax(_("[\037nickname\037]")); + this->AllowUnregistered(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + + const Anope::string &nick = params.size() ? params[0] : (source.nc ? source.nc->display : source.GetNick()); + NickAlias *na = NickAlias::Find(nick); + bool has_auspex = source.HasPriv("nickserv/auspex"); + + if (!na) + { + if (BotInfo::Find(nick, true)) + source.Reply(_("Nick \002%s\002 is part of this Network's Services."), nick.c_str()); + else + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + } + else + { + bool nick_online = false, show_hidden = false; + + /* Is the real owner of the nick we're looking up online? -TheShadow */ + User *u2 = User::Find(na->nick, true); + if (u2 && u2->Account() == na->nc) + { + nick_online = true; + na->last_seen = Anope::CurTime; + } + + if (has_auspex || na->nc == source.GetAccount()) + show_hidden = true; + + source.Reply(_("%s is %s"), na->nick.c_str(), na->last_realname.c_str()); + + if (na->nc->HasExt("UNCONFIRMED")) + source.Reply(_("%s is an unconfirmed nickname."), na->nick.c_str()); + + if (na->nc->IsServicesOper() && (show_hidden || !na->nc->HasExt("HIDE_STATUS"))) + source.Reply(_("%s is a Services Operator of type %s."), na->nick.c_str(), na->nc->o->ot->GetName().c_str()); + + InfoFormatter info(source.nc); + + info[_("Account")] = na->nc->display; + if (nick_online) + { + bool shown = false; + if (show_hidden && !na->last_realhost.empty()) + { + info[_("Online from")] = na->last_realhost; + shown = true; + } + if ((show_hidden || !na->nc->HasExt("HIDE_MASK")) && (!shown || na->last_usermask != na->last_realhost)) + info[_("Online from")] = na->last_usermask; + else + source.Reply(_("%s is currently online."), na->nick.c_str()); + } + else + { + Anope::string shown; + if (show_hidden || !na->nc->HasExt("HIDE_MASK")) + { + info[_("Last seen address")] = na->last_usermask; + shown = na->last_usermask; + } + + if (show_hidden && !na->last_realhost.empty() && na->last_realhost != shown) + info[_("Last seen address")] = na->last_realhost; + } + + info[_("Registered")] = Anope::strftime(na->time_registered, source.GetAccount()); + + if (!nick_online) + info[_("Last seen")] = Anope::strftime(na->last_seen, source.GetAccount()); + + if (!na->last_quit.empty() && (show_hidden || !na->nc->HasExt("HIDE_QUIT"))) + info[_("Last quit message")] = na->last_quit; + + if (!na->nc->email.empty() && (show_hidden || !na->nc->HasExt("HIDE_EMAIL"))) + info[_("Email address")] = na->nc->email; + + if (show_hidden) + { + if (na->HasVhost()) + { + if (IRCD->CanSetVIdent && !na->GetVhostIdent().empty()) + info[_("VHost")] = na->GetVhostIdent() + "@" + na->GetVhostHost(); + else + info[_("VHost")] = na->GetVhostHost(); + } + } + + FOREACH_MOD(OnNickInfo, (source, na, info, show_hidden)); + + std::vector replies; + info.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Displays information about the given nickname, such as\n" + "the nick's owner, last seen address and time, and nick\n" + "options. If no nick is given, and you are identified,\n" + "your account name is used, else your current nickname is\n" + "used.")); + + return true; + } +}; + + +class CommandNSSetHide : public Command +{ + public: + CommandNSSetHide(Module *creator, const Anope::string &sname = "nickserv/set/hide", size_t min = 2) : Command(creator, sname, min, min + 1) + { + this->SetDesc(_("Hide certain pieces of nickname information")); + this->SetSyntax("{EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}"); + } + + void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m, const Anope::string &arg) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const NickAlias *na = NickAlias::Find(user); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); + return; + } + NickCore *nc = na->nc; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, nc, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + Anope::string onmsg, offmsg, flag; + + if (param.equals_ci("EMAIL")) + { + flag = "HIDE_EMAIL"; + onmsg = _("The E-mail address of \002%s\002 will now be hidden from %s INFO displays."); + offmsg = _("The E-mail address of \002%s\002 will now be shown in %s INFO displays."); + } + else if (param.equals_ci("USERMASK")) + { + flag = "HIDE_MASK"; + onmsg = _("The last seen user@host mask of \002%s\002 will now be hidden from %s INFO displays."); + offmsg = _("The last seen user@host mask of \002%s\002 will now be shown in %s INFO displays."); + } + else if (param.equals_ci("STATUS")) + { + flag = "HIDE_STATUS"; + onmsg = _("The services access status of \002%s\002 will now be hidden from %s INFO displays."); + offmsg = _("The services access status of \002%s\002 will now be shown in %s INFO displays."); + } + else if (param.equals_ci("QUIT")) + { + flag = "HIDE_QUIT"; + onmsg = _("The last quit message of \002%s\002 will now be hidden from %s INFO displays."); + offmsg = _("The last quit message of \002%s\002 will now be shown in %s INFO displays."); + } + else + { + this->OnSyntaxError(source, "HIDE"); + return; + } + + if (arg.equals_ci("ON")) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to change hide " << param.upper() << " to " << arg.upper() << " for " << nc->display; + nc->Extend(flag); + source.Reply(onmsg.c_str(), nc->display.c_str(), source.service->nick.c_str()); + } + else if (arg.equals_ci("OFF")) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to change hide " << param.upper() << " to " << arg.upper() << " for " << nc->display; + nc->Shrink(flag); + source.Reply(offmsg.c_str(), nc->display.c_str(), source.service->nick.c_str()); + } + else + this->OnSyntaxError(source, "HIDE"); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, source.nc->display, params[0], params[1]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows you to prevent certain pieces of information from\n" + "being displayed when someone does a %s \002INFO\002 on your\n" + "nick. You can hide your E-mail address (\002EMAIL\002), last seen\n" + "user@host mask (\002USERMASK\002), your services access status\n" + "(\002STATUS\002) and last quit message (\002QUIT\002).\n" + "The second parameter specifies whether the information should\n" + "be displayed (\002OFF\002) or hidden (\002ON\002)."), source.service->nick.c_str()); + return true; + } +}; + +class CommandNSSASetHide : public CommandNSSetHide +{ + public: + CommandNSSASetHide(Module *creator) : CommandNSSetHide(creator, "nickserv/saset/hide", 3) + { + this->SetSyntax(_("\037nickname\037 {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->ClearSyntax(); + this->Run(source, params[0], params[1], params[2]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows you to prevent certain pieces of information from\n" + "being displayed when someone does a %s \002INFO\002 on the\n" + "nick. You can hide the E-mail address (\002EMAIL\002), last seen\n" + "user@host mask (\002USERMASK\002), the services access status\n" + "(\002STATUS\002) and last quit message (\002QUIT\002).\n" + "The second parameter specifies whether the information should\n" + "be displayed (\002OFF\002) or hidden (\002ON\002)."), source.service->nick.c_str()); + return true; + } +}; + +class NSInfo : public Module +{ + CommandNSInfo commandnsinfo; + + CommandNSSetHide commandnssethide; + CommandNSSASetHide commandnssasethide; + + SerializableExtensibleItem hide_email, hide_usermask, hide_status, hide_quit; + + public: + NSInfo(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsinfo(this), commandnssethide(this), commandnssasethide(this), + hide_email(this, "HIDE_EMAIL"), hide_usermask(this, "HIDE_MASK"), hide_status(this, "HIDE_STATUS"), + hide_quit(this, "HIDE_QUIT") + { + + } +}; + +MODULE_INIT(NSInfo) diff --git a/modules/commands/ns_list.cpp b/modules/commands/ns_list.cpp new file mode 100644 index 0000000..0b14e84 --- /dev/null +++ b/modules/commands/ns_list.cpp @@ -0,0 +1,301 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandNSList : public Command +{ + public: + CommandNSList(Module *creator) : Command(creator, "nickserv/list", 1, 2) + { + this->SetDesc(_("List all registered nicknames that match a given pattern")); + this->SetSyntax(_("\037pattern\037 [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + + Anope::string pattern = params[0]; + const NickCore *mync; + unsigned nnicks; + bool is_servadmin = source.HasCommand("nickserv/list"); + int count = 0, from = 0, to = 0; + bool suspended, nsnoexpire, unconfirmed; + unsigned listmax = Config->GetModule(this->owner)->Get("listmax", "50"); + + suspended = nsnoexpire = unconfirmed = false; + + if (pattern[0] == '#') + { + Anope::string n1, n2; + sepstream(pattern.substr(1), '-').GetToken(n1, 0); + sepstream(pattern, '-').GetToken(n2, 1); + try + { + from = convertTo(n1); + to = convertTo(n2); + } + catch (const ConvertException &) + { + source.Reply(LIST_INCORRECT_RANGE); + return; + } + + pattern = "*"; + } + + nnicks = 0; + + if (is_servadmin && params.size() > 1) + { + Anope::string keyword; + spacesepstream keywords(params[1]); + while (keywords.GetToken(keyword)) + { + if (keyword.equals_ci("NOEXPIRE")) + nsnoexpire = true; + if (keyword.equals_ci("SUSPENDED")) + suspended = true; + if (keyword.equals_ci("UNCONFIRMED")) + unconfirmed = true; + } + } + + mync = source.nc; + ListFormatter list(source.GetAccount()); + + list.AddColumn(_("Nick")).AddColumn(_("Last usermask")); + + Anope::map ordered_map; + for (nickalias_map::const_iterator it = NickAliasList->begin(), it_end = NickAliasList->end(); it != it_end; ++it) + ordered_map[it->first] = it->second; + + for (Anope::map::const_iterator it = ordered_map.begin(), it_end = ordered_map.end(); it != it_end; ++it) + { + const NickAlias *na = it->second; + + /* Don't show private nicks to non-services admins. */ + if (na->nc->HasExt("NS_PRIVATE") && !is_servadmin && na->nc != mync) + continue; + else if (nsnoexpire && !na->HasExt("NS_NO_EXPIRE")) + continue; + else if (suspended && !na->nc->HasExt("NS_SUSPENDED")) + continue; + else if (unconfirmed && !na->nc->HasExt("UNCONFIRMED")) + continue; + + /* We no longer compare the pattern against the output buffer. + * Instead we build a nice nick!user@host buffer to compare. + * The output is then generated separately. -TheShadow */ + Anope::string buf = Anope::printf("%s!%s", na->nick.c_str(), !na->last_usermask.empty() ? na->last_usermask.c_str() : "*@*"); + if (na->nick.equals_ci(pattern) || Anope::Match(buf, pattern, false, true)) + { + if (((count + 1 >= from && count + 1 <= to) || (!from && !to)) && ++nnicks <= listmax) + { + bool isnoexpire = false; + if (is_servadmin && na->HasExt("NS_NO_EXPIRE")) + isnoexpire = true; + + ListFormatter::ListEntry entry; + entry["Nick"] = (isnoexpire ? "!" : "") + na->nick; + if (na->nc->HasExt("HIDE_MASK") && !is_servadmin && na->nc != mync) + entry["Last usermask"] = Language::Translate(source.GetAccount(), _("[Hostname hidden]")); + else if (na->nc->HasExt("NS_SUSPENDED")) + entry["Last usermask"] = Language::Translate(source.GetAccount(), _("[Suspended]")); + else if (na->nc->HasExt("UNCONFIRMED")) + entry["Last usermask"] = Language::Translate(source.GetAccount(), _("[Unconfirmed]")); + else + entry["Last usermask"] = na->last_usermask; + list.AddEntry(entry); + } + ++count; + } + } + + source.Reply(_("List of entries matching \002%s\002:"), pattern.c_str()); + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("End of list - %d/%d matches shown."), nnicks > listmax ? listmax : nnicks, nnicks); + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Lists all registered nicknames which match the given\n" + "pattern, in \037nick!user@host\037 format. Nicks with the \002PRIVATE\002\n" + "option set will only be displayed to Services Operators with the\n" + "proper access. Nicks with the \002NOEXPIRE\002 option set will have\n" + "a \002!\002 prefixed to the nickname for Services Operators to see.\n" + " \n" + "Note that a preceding '#' specifies a range.\n" + " \n" + "If the SUSPENDED, UNCONFIRMED or NOEXPIRE options are given, only\n" + "nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" + "NOEXPIRE flag set will be displayed. If multiple options are\n" + "given, all nicks matching at least one option will be displayed.\n" + "Note that these options are limited to \037Services Operators\037.\n" + " \n" + "Examples:\n" + " \n" + " \002LIST *!joeuser@foo.com\002\n" + " Lists all registered nicks owned by joeuser@foo.com.\n" + " \n" + " \002LIST *Bot*!*@*\002\n" + " Lists all registered nicks with \002Bot\002 in their\n" + " names (case insensitive).\n" + " \n" + " \002LIST * NOEXPIRE\002\n" + " Lists all registered nicks which have been set to not expire.\n" + " \n" + " \002LIST #51-100\002\n" + " Lists all registered nicks within the given range (51-100).")); + + const Anope::string ®exengine = Config->GetBlock("options")->Get("regexengine"); + if (!regexengine.empty()) + { + source.Reply(" "); + source.Reply(_("Regex matches are also supported using the %s engine.\n" + "Enclose your pattern in // if this is desired."), regexengine.c_str()); + } + + return true; + } +}; + + +class CommandNSSetPrivate : public Command +{ + public: + CommandNSSetPrivate(Module *creator, const Anope::string &sname = "nickserv/set/private", size_t min = 1) : Command(creator, sname, min, min + 1) + { + this->SetDesc(_("Prevent the nickname from appearing in the LIST command")); + this->SetSyntax("{ON | OFF}"); + } + + void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const NickAlias *na = NickAlias::Find(user); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); + return; + } + NickCore *nc = na->nc; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, nc, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (param.equals_ci("ON")) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to enable private for " << nc->display; + nc->Extend("NS_PRIVATE"); + source.Reply(_("Private option is now \002on\002 for \002%s\002."), nc->display.c_str()); + } + else if (param.equals_ci("OFF")) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to disable private for " << nc->display; + nc->Shrink("NS_PRIVATE"); + source.Reply(_("Private option is now \002off\002 for \002%s\002."), nc->display.c_str()); + } + else + this->OnSyntaxError(source, "PRIVATE"); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, source.nc->display, params[0]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Turns %s's privacy option on or off for your nick.\n" + "With \002PRIVATE\002 set, your nickname will not appear in\n" + "nickname lists generated with %s's \002LIST\002 command.\n" + "(However, anyone who knows your nickname can still get\n" + "information on it using the \002INFO\002 command.)"), + source.service->nick.c_str(), source.service->nick.c_str()); + return true; + } +}; + +class CommandNSSASetPrivate : public CommandNSSetPrivate +{ + public: + CommandNSSASetPrivate(Module *creator) : CommandNSSetPrivate(creator, "nickserv/saset/private", 2) + { + this->ClearSyntax(); + this->SetSyntax(_("\037nickname\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, params[0], params[1]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Turns %s's privacy option on or off for the nick.\n" + "With \002PRIVATE\002 set, the nickname will not appear in\n" + "nickname lists generated with %s's \002LIST\002 command.\n" + "(However, anyone who knows the nickname can still get\n" + "information on it using the \002INFO\002 command.)"), + source.service->nick.c_str(), source.service->nick.c_str()); + return true; + } +}; + + +class NSList : public Module +{ + CommandNSList commandnslist; + + CommandNSSetPrivate commandnssetprivate; + CommandNSSASetPrivate commandnssasetprivate; + + SerializableExtensibleItem priv; + + public: + NSList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnslist(this), commandnssetprivate(this), commandnssasetprivate(this), + priv(this, "NS_PRIVATE") + { + } + + void OnNickInfo(CommandSource &source, NickAlias *na, InfoFormatter &info, bool show_all) anope_override + { + if (!show_all) + return; + + if (priv.HasExt(na->nc)) + info.AddOption(_("Private")); + } +}; + +MODULE_INIT(NSList) diff --git a/modules/commands/ns_logout.cpp b/modules/commands/ns_logout.cpp new file mode 100644 index 0000000..e863a82 --- /dev/null +++ b/modules/commands/ns_logout.cpp @@ -0,0 +1,91 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +static ServiceReference NickServService("NickServService", "NickServ"); + +class CommandNSLogout : public Command +{ + public: + CommandNSLogout(Module *creator) : Command(creator, "nickserv/logout", 0, 2) + { + this->SetDesc(_("Reverses the effect of the IDENTIFY command")); + this->SetSyntax(_("[\037nickname\037 [REVALIDATE]]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + + const Anope::string &nick = !params.empty() ? params[0] : ""; + const Anope::string ¶m = params.size() > 1 ? params[1] : ""; + + User *u2; + if (!source.IsServicesOper() && !nick.empty()) + this->OnSyntaxError(source, ""); + else if (!(u2 = (!nick.empty() ? User::Find(nick, true) : source.GetUser()))) + source.Reply(NICK_X_NOT_IN_USE, !nick.empty() ? nick.c_str() : source.GetNick().c_str()); + else if (!nick.empty() && u2->IsServicesOper()) + source.Reply(_("You can't logout %s, they are a Services Operator."), nick.c_str()); + else + { + if (!nick.empty() && !param.empty() && param.equals_ci("REVALIDATE") && NickServService) + NickServService->Validate(u2); + + u2->super_admin = false; /* Don't let people logout and remain a SuperAdmin */ + Log(LOG_COMMAND, source, this) << "to logout " << u2->nick; + + /* Remove founder status from this user in all channels */ + if (!nick.empty()) + source.Reply(_("Nick %s has been logged out."), nick.c_str()); + else + source.Reply(_("Your nick has been logged out.")); + + IRCD->SendLogout(u2); + u2->RemoveMode(source.service, "REGISTERED"); + u2->Logout(); + + /* Send out an event */ + FOREACH_MOD(OnNickLogout, (u2)); + } + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Without a parameter, reverses the effect of the \002IDENTIFY\002\n" + "command, i.e. make you not recognized as the real owner of the nick\n" + "anymore. Note, however, that you won't be asked to reidentify\n" + "yourself.\n" + " \n" + "With a parameter, does the same for the given nick. If you\n" + "specify \002REVALIDATE\002 as well, Services will ask the given nick\n" + "to re-identify. This is limited to \002Services Operators\002.")); + + return true; + } +}; + +class NSLogout : public Module +{ + CommandNSLogout commandnslogout; + + public: + NSLogout(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnslogout(this) + { + + } +}; + +MODULE_INIT(NSLogout) diff --git a/modules/commands/ns_recover.cpp b/modules/commands/ns_recover.cpp new file mode 100644 index 0000000..9cb3261 --- /dev/null +++ b/modules/commands/ns_recover.cpp @@ -0,0 +1,298 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/ns_cert.h" + +static ServiceReference nickserv("NickServService", "NickServ"); + +typedef std::map NSRecoverInfo; + +class NSRecoverSvsnick +{ + public: + Reference from; + Anope::string to; +}; + +class NSRecoverRequest : public IdentifyRequest +{ + CommandSource source; + Command *cmd; + Anope::string user; + + public: + NSRecoverRequest(Module *o, CommandSource &src, Command *c, const Anope::string &nick, const Anope::string &pass) : IdentifyRequest(o, nick, pass), source(src), cmd(c), user(nick) { } + + void OnSuccess() anope_override + { + User *u = User::Find(user, true); + if (!source.GetUser() || !source.service) + return; + + NickAlias *na = NickAlias::Find(user); + if (!na) + return; + + Log(LOG_COMMAND, source, cmd) << "for " << na->nick; + + /* Nick is being held by us, release it */ + if (na->HasExt("HELD")) + { + nickserv->Release(na); + source.Reply(_("Service's hold on \002%s\002 has been released."), na->nick.c_str()); + } + else if (!u) + { + source.Reply(_("No one is using your nick, and services are not holding it.")); + } + // If the user being recovered is identified for the account of the nick then the user is the + // same person that is executing the command, so kill them off (old GHOST command). + else if (u->Account() == na->nc) + { + if (!source.GetAccount() && na->nc->HasExt("NS_SECURE")) + { + source.GetUser()->Login(u->Account()); + Log(LOG_COMMAND, source, cmd) << "and was automatically identified to " << u->Account()->display; + } + + if (Config->GetModule("ns_recover")->Get("restoreonrecover")) + { + if (!u->chans.empty()) + { + NSRecoverInfo *ei = source.GetUser()->Extend("recover"); + for (User::ChanUserList::iterator it = u->chans.begin(), it_end = u->chans.end(); it != it_end; ++it) + (*ei)[it->first->name] = it->second->status; + } + } + + u->SendMessage(source.service, _("This nickname has been recovered by %s. If you did not do\n" + "this then %s may have your password, and you should change it."), + source.GetNick().c_str(), source.GetNick().c_str()); + + Anope::string buf = source.command.upper() + " command used by " + source.GetNick(); + u->Kill(*source.service, buf); + + source.Reply(_("Ghost with your nick has been killed.")); + + if (IRCD->CanSVSNick) + IRCD->SendForceNickChange(source.GetUser(), GetAccount(), Anope::CurTime); + } + /* User is not identified or not identified to the same account as the person using this command */ + else + { + if (!source.GetAccount() && na->nc->HasExt("NS_SECURE")) + { + source.GetUser()->Login(na->nc); // Identify the user using the command if they arent identified + Log(LOG_COMMAND, source, cmd) << "and was automatically identified to " << na->nick << " (" << na->nc->display << ")"; + source.Reply(_("You have been logged in as \002%s\002."), na->nc->display.c_str()); + } + + u->SendMessage(source.service, _("This nickname has been recovered by %s."), source.GetNick().c_str()); + + if (IRCD->CanSVSNick) + { + NSRecoverSvsnick *svs = u->Extend("svsnick"); + svs->from = source.GetUser(); + svs->to = u->nick; + } + + if (nickserv) + nickserv->Collide(u, na); + + if (IRCD->CanSVSNick) + { + /* If we can svsnick then release our hold and svsnick the user using the command */ + if (nickserv) + nickserv->Release(na); + + source.Reply(_("You have regained control of \002%s\002."), u->nick.c_str()); + } + else + { + source.Reply(_("The user with your nick has been removed. Use this command again\n" + "to release services's hold on your nick.")); + } + } + } + + void OnFail() anope_override + { + if (NickAlias::Find(GetAccount()) != NULL) + { + source.Reply(ACCESS_DENIED); + if (!GetPassword().empty()) + { + Log(LOG_COMMAND, source, cmd) << "with an invalid password for " << GetAccount(); + if (source.GetUser()) + source.GetUser()->BadPassword(); + } + } + else + source.Reply(NICK_X_NOT_REGISTERED, GetAccount().c_str()); + } +}; + +class CommandNSRecover : public Command +{ + public: + CommandNSRecover(Module *creator) : Command(creator, "nickserv/recover", 1, 2) + { + this->SetDesc(_("Regains control of your nick")); + this->SetSyntax(_("\037nickname\037 [\037password\037]")); + this->AllowUnregistered(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &nick = params[0]; + const Anope::string &pass = params.size() > 1 ? params[1] : ""; + + User *user = User::Find(nick, true); + + if (user && source.GetUser() == user) + { + source.Reply(_("You can't %s yourself!"), source.command.lower().c_str()); + return; + } + + const NickAlias *na = NickAlias::Find(nick); + + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + return; + } + else if (na->nc->HasExt("NS_SUSPENDED")) + { + source.Reply(NICK_X_SUSPENDED, na->nick.c_str()); + return; + } + + bool ok = false; + if (source.GetAccount() == na->nc) + ok = true; + else if (!na->nc->HasExt("NS_SECURE") && source.GetUser() && na->nc->IsOnAccess(source.GetUser())) + ok = true; + + NSCertList *cl = na->nc->GetExt("certificates"); + if (source.GetUser() && !source.GetUser()->fingerprint.empty() && cl && cl->FindCert(source.GetUser()->fingerprint)) + ok = true; + + if (source.HasPriv("nickserv/recover")) + ok = true; + + if (ok == false && !pass.empty()) + { + NSRecoverRequest *req = new NSRecoverRequest(owner, source, this, na->nick, pass); + FOREACH_MOD(OnCheckAuthentication, (source.GetUser(), req)); + req->Dispatch(); + } + else + { + NSRecoverRequest req(owner, source, this, na->nick, pass); + + if (ok) + req.OnSuccess(); + else + req.OnFail(); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Recovers your nick from another user or from services.\n" + "If services are currently holding your nick, the hold\n" + "will be released. If another user is holding your nick\n" + "and is identified they will be killed (similar to the old\n" + "GHOST command). If they are not identified they will be\n" + "forced off of the nick.")); + return true; + } +}; + +class NSRecover : public Module +{ + CommandNSRecover commandnsrecover; + PrimitiveExtensibleItem recover; + PrimitiveExtensibleItem svsnick; + + public: + NSRecover(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsrecover(this), recover(this, "recover"), svsnick(this, "svsnick") + { + + if (Config->GetModule("nickserv")->Get("nonicknameownership")) + throw ModuleException(modname + " can not be used with options:nonicknameownership enabled"); + + } + + void OnUserNickChange(User *u, const Anope::string &oldnick) anope_override + { + if (Config->GetModule(this)->Get("restoreonrecover")) + { + NSRecoverInfo *ei = recover.Get(u); + BotInfo *NickServ = Config->GetClient("NickServ"); + + if (ei != NULL && NickServ != NULL) + for (NSRecoverInfo::iterator it = ei->begin(), it_end = ei->end(); it != it_end;) + { + Channel *c = Channel::Find(it->first); + const Anope::string &cname = it->first; + ++it; + + /* User might already be on the channel */ + if (u->FindChannel(c)) + this->OnJoinChannel(u, c); + else if (IRCD->CanSVSJoin) + IRCD->SendSVSJoin(NickServ, u, cname, ""); + } + } + + NSRecoverSvsnick *svs = svsnick.Get(u); + if (svs) + { + if (svs->from) + { + // svsnick from to to + IRCD->SendForceNickChange(svs->from, svs->to, Anope::CurTime); + } + + svsnick.Unset(u); + } + } + + void OnJoinChannel(User *u, Channel *c) anope_override + { + if (Config->GetModule(this)->Get("restoreonrecover")) + { + NSRecoverInfo *ei = recover.Get(u); + + if (ei != NULL) + { + NSRecoverInfo::iterator it = ei->find(c->name); + if (it != ei->end()) + { + for (size_t i = 0; i < it->second.Modes().length(); ++i) + c->SetMode(c->ci->WhoSends(), ModeManager::FindChannelModeByChar(it->second.Modes()[i]), u->GetUID()); + + ei->erase(it); + if (ei->empty()) + recover.Unset(u); + } + } + } + } +}; + +MODULE_INIT(NSRecover) diff --git a/modules/commands/ns_register.cpp b/modules/commands/ns_register.cpp new file mode 100644 index 0000000..7adf146 --- /dev/null +++ b/modules/commands/ns_register.cpp @@ -0,0 +1,438 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +static bool SendRegmail(User *u, const NickAlias *na, BotInfo *bi); + +class CommandNSConfirm : public Command +{ + public: + CommandNSConfirm(Module *creator) : Command(creator, "nickserv/confirm", 1, 2) + { + this->SetDesc(_("Confirm a passcode")); + this->SetSyntax(_("\037passcode\037")); + this->AllowUnregistered(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &passcode = params[0]; + + if (source.nc && (!source.nc->HasExt("UNCONFIRMED") || source.IsOper()) && source.HasPriv("nickserv/confirm")) + { + NickAlias *na = NickAlias::Find(passcode); + if (na == NULL) + source.Reply(NICK_X_NOT_REGISTERED, passcode.c_str()); + else if (na->nc->HasExt("UNCONFIRMED") == false) + source.Reply(_("Nick \002%s\002 is already confirmed."), na->nick.c_str()); + else + { + na->nc->Shrink("UNCONFIRMED"); + FOREACH_MOD(OnNickConfirm, (source.GetUser(), na->nc)); + Log(LOG_ADMIN, source, this) << "to confirm nick " << na->nick << " (" << na->nc->display << ")"; + source.Reply(_("Nick \002%s\002 has been confirmed."), na->nick.c_str()); + + /* Login the users online already */ + for (std::list::iterator it = na->nc->users.begin(); it != na->nc->users.end(); ++it) + { + User *u = *it; + + IRCD->SendLogin(u, na); + + NickAlias *u_na = NickAlias::Find(u->nick); + + /* Set +r if they're on a nick in the group */ + if (!Config->GetModule("nickserv")->Get("nonicknameownership") && u_na && *u_na->nc == *na->nc) + u->SetMode(source.service, "REGISTERED"); + } + } + } + else if (source.nc) + { + Anope::string *code = source.nc->GetExt("passcode"); + if (code != NULL && *code == passcode) + { + NickCore *nc = source.nc; + nc->Shrink("passcode"); + Log(LOG_COMMAND, source, this) << "to confirm their email"; + source.Reply(_("Your email address of \002%s\002 has been confirmed."), source.nc->email.c_str()); + nc->Shrink("UNCONFIRMED"); + FOREACH_MOD(OnNickConfirm, (source.GetUser(), nc)); + + if (source.GetUser()) + { + NickAlias *na = NickAlias::Find(source.GetNick()); + if (na) + { + IRCD->SendLogin(source.GetUser(), na); + if (!Config->GetModule("nickserv")->Get("nonicknameownership") && na->nc == source.GetAccount() && !na->nc->HasExt("UNCONFIRMED")) + source.GetUser()->SetMode(source.service, "REGISTERED"); + } + } + } + else + source.Reply(_("Invalid passcode.")); + } + else + source.Reply(_("Invalid passcode.")); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command is used by several commands as a way to confirm\n" + "changes made to your account.\n" + " \n" + "This is most commonly used to confirm your email address once\n" + "you register or change it.\n" + " \n" + "This is also used after the RESETPASS command has been used to\n" + "force identify you to your nick so you may change your password.")); + if (source.HasPriv("nickserv/confirm")) + source.Reply(_("Additionally, Services Operators with the \037nickserv/confirm\037 permission can\n" + "replace \037passcode\037 with a users nick to force validate them.")); + return true; + } + + void OnSyntaxError(CommandSource &source, const Anope::string &subcommand) anope_override + { + source.Reply(NICK_CONFIRM_INVALID); + } +}; + +class CommandNSRegister : public Command +{ + public: + CommandNSRegister(Module *creator) : Command(creator, "nickserv/register", 1, 2) + { + this->SetDesc(_("Register a nickname")); + if (Config->GetModule("nickserv")->Get("forceemail", "yes")) + this->SetSyntax(_("\037password\037 \037email\037")); + else + this->SetSyntax(_("\037password\037 \037[email]\037")); + this->AllowUnregistered(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + Anope::string u_nick = source.GetNick(); + size_t nicklen = u_nick.length(); + Anope::string pass = params[0]; + Anope::string email = params.size() > 1 ? params[1] : ""; + const Anope::string &nsregister = Config->GetModule(this->owner)->Get("registration"); + + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, nickname registration is temporarily disabled.")); + return; + } + + if (nsregister.equals_ci("disable")) + { + source.Reply(_("Registration is currently disabled.")); + return; + } + + time_t nickregdelay = Config->GetModule(this->owner)->Get("nickregdelay"); + time_t reg_delay = Config->GetModule("nickserv")->Get("regdelay"); + if (u && !u->HasMode("OPER") && nickregdelay && Anope::CurTime - u->timestamp < nickregdelay) + { + source.Reply(_("You must have been using this nick for at least %d seconds to register."), nickregdelay); + return; + } + + /* Prevent "Guest" nicks from being registered. -TheShadow */ + + /* Guest nick can now have a series of between 1 and 7 digits. + * --lara + */ + const Anope::string &guestnick = Config->GetModule("nickserv")->Get("guestnickprefix", "Guest"); + if (nicklen <= guestnick.length() + 7 && nicklen >= guestnick.length() + 1 && !u_nick.find_ci(guestnick) && u_nick.substr(guestnick.length()).find_first_not_of("1234567890") == Anope::string::npos) + { + source.Reply(NICK_CANNOT_BE_REGISTERED, u_nick.c_str()); + return; + } + + if (!IRCD->IsNickValid(u_nick)) + { + source.Reply(NICK_CANNOT_BE_REGISTERED, u_nick.c_str()); + return; + } + + if (BotInfo::Find(u_nick, true)) + { + source.Reply(NICK_CANNOT_BE_REGISTERED, u_nick.c_str()); + return; + } + + if (Config->GetModule("nickserv")->Get("restrictopernicks")) + { + for (unsigned i = 0; i < Oper::opers.size(); ++i) + { + Oper *o = Oper::opers[i]; + + if (!source.IsOper() && u_nick.find_ci(o->name) != Anope::string::npos) + { + source.Reply(NICK_CANNOT_BE_REGISTERED, u_nick.c_str()); + return; + } + } + } + + unsigned int passlen = Config->GetModule("nickserv")->Get("passlen", "32"); + + if (Config->GetModule("nickserv")->Get("forceemail", "yes") && email.empty()) + this->OnSyntaxError(source, ""); + else if (u && Anope::CurTime < u->lastnickreg + reg_delay) + source.Reply(_("Please wait %d seconds before using the REGISTER command again."), (u->lastnickreg + reg_delay) - Anope::CurTime); + else if (NickAlias::Find(u_nick) != NULL) + source.Reply(NICK_ALREADY_REGISTERED, u_nick.c_str()); + else if (pass.equals_ci(u_nick) || (Config->GetBlock("options")->Get("strictpasswords") && pass.length() < 5)) + source.Reply(MORE_OBSCURE_PASSWORD); + else if (pass.length() > passlen) + source.Reply(PASSWORD_TOO_LONG, passlen); + else if (!email.empty() && !Mail::Validate(email)) + source.Reply(MAIL_X_INVALID, email.c_str()); + else + { + NickCore *nc = new NickCore(u_nick); + NickAlias *na = new NickAlias(u_nick, nc); + Anope::Encrypt(pass, nc->pass); + if (!email.empty()) + nc->email = email; + + if (u) + { + na->last_usermask = u->GetIdent() + "@" + u->GetDisplayedHost(); + na->last_realname = u->realname; + } + else + na->last_realname = source.GetNick(); + + Log(LOG_COMMAND, source, this) << "to register " << na->nick << " (email: " << (!na->nc->email.empty() ? na->nc->email : "none") << ")"; + + if (na->nc->GetAccessCount()) + source.Reply(_("Nickname \002%s\002 registered under your user@host-mask: %s"), u_nick.c_str(), na->nc->GetAccess(0).c_str()); + else + source.Reply(_("Nickname \002%s\002 registered."), u_nick.c_str()); + + Anope::string tmp_pass; + if (Anope::Decrypt(na->nc->pass, tmp_pass) == 1) + source.Reply(_("Your password is \002%s\002 - remember this for later use."), tmp_pass.c_str()); + + if (nsregister.equals_ci("admin")) + { + nc->Extend("UNCONFIRMED"); + } + else if (nsregister.equals_ci("mail")) + { + if (!email.empty()) + { + nc->Extend("UNCONFIRMED"); + SendRegmail(NULL, na, source.service); + } + } + + FOREACH_MOD(OnNickRegister, (source.GetUser(), na, pass)); + + if (u) + { + // This notifies the user that if their registration is unconfirmed + u->Identify(na); + u->lastnickreg = Anope::CurTime; + } + else if (nc->HasExt("UNCONFIRMED")) + { + if (nsregister.equals_ci("admin")) + source.Reply(_("All new accounts must be validated by an administrator. Please wait for your registration to be confirmed.")); + else if (nsregister.equals_ci("mail")) + source.Reply(_("Your email address is not confirmed. To confirm it, follow the instructions that were emailed to you.")); + } + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Registers your nickname in the %s database. Once\n" + "your nick is registered, you can use the \002SET\002 and \002ACCESS\002\n" + "commands to configure your nick's settings as you like\n" + "them. Make sure you remember the password you use when\n" + "registering - you'll need it to make changes to your nick\n" + "later. (Note that \002case matters!\002 \037ANOPE\037, \037Anope\037, and\n" + "\037anope\037 are all different passwords!)\n" + " \n" + "Guidelines on choosing passwords:\n" + " \n" + "Passwords should not be easily guessable. For example,\n" + "using your real name as a password is a bad idea. Using\n" + "your nickname as a password is a much worse idea ;) and,\n" + "in fact, %s will not allow it. Also, short\n" + "passwords are vulnerable to trial-and-error searches, so\n" + "you should choose a password at least 5 characters long.\n" + "Finally, the space character cannot be used in passwords."), + source.service->nick.c_str(), source.service->nick.c_str()); + + if (!Config->GetModule("nickserv")->Get("forceemail", "yes")) + { + source.Reply(" "); + source.Reply(_("The \037email\037 parameter is optional and will set the email\n" + "for your nick immediately.\n" + "Your privacy is respected; this e-mail won't be given to\n" + "any third-party person. You may also wish to \002SET HIDE\002 it\n" + "after registering if it isn't the default setting already.")); + } + + source.Reply(" "); + source.Reply(_("This command also creates a new group for your nickname,\n" + "that will allow you to register other nicks later sharing\n" + "the same configuration, the same set of memos and the\n" + "same channel privileges.")); + return true; + } +}; + +class CommandNSResend : public Command +{ + public: + CommandNSResend(Module *creator) : Command(creator, "nickserv/resend", 0, 0) + { + this->SetDesc(_("Resend registration confirmation email")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!Config->GetModule(this->owner)->Get("registration").equals_ci("mail")) + { + source.Reply(ACCESS_DENIED); + return; + } + + const NickAlias *na = NickAlias::Find(source.GetNick()); + + if (na == NULL) + source.Reply(NICK_NOT_REGISTERED); + else if (na->nc != source.GetAccount() || !source.nc->HasExt("UNCONFIRMED")) + source.Reply(_("Your account is already confirmed.")); + else + { + if (Anope::CurTime < source.nc->lastmail + Config->GetModule(this->owner)->Get("resenddelay")) + source.Reply(_("Cannot send mail now; please retry a little later.")); + else if (SendRegmail(source.GetUser(), na, source.service)) + { + na->nc->lastmail = Anope::CurTime; + source.Reply(_("Your passcode has been re-sent to %s."), na->nc->email.c_str()); + Log(LOG_COMMAND, source, this) << "to resend registration verification code"; + } + else + Log(this->owner) << "Unable to resend registration verification code for " << source.GetNick(); + } + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + if (!Config->GetModule(this->owner)->Get("registration").equals_ci("mail")) + return false; + + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command will resend you the registration confirmation email.")); + return true; + } + + void OnServHelp(CommandSource &source) anope_override + { + if (Config->GetModule(this->owner)->Get("registration").equals_ci("mail")) + Command::OnServHelp(source); + } +}; + +class NSRegister : public Module +{ + CommandNSRegister commandnsregister; + CommandNSConfirm commandnsconfirm; + CommandNSResend commandnsrsend; + + SerializableExtensibleItem unconfirmed; + SerializableExtensibleItem passcode; + + public: + NSRegister(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsregister(this), commandnsconfirm(this), commandnsrsend(this), unconfirmed(this, "UNCONFIRMED"), + passcode(this, "passcode") + { + if (Config->GetModule(this)->Get("registration").equals_ci("disable")) + throw ModuleException("Module " + this->name + " will not load with registration disabled."); + } + + void OnNickIdentify(User *u) anope_override + { + BotInfo *NickServ; + if (unconfirmed.HasExt(u->Account()) && (NickServ = Config->GetClient("NickServ"))) + { + const Anope::string &nsregister = Config->GetModule(this)->Get("registration"); + if (nsregister.equals_ci("admin")) + u->SendMessage(NickServ, _("All new accounts must be validated by an administrator. Please wait for your registration to be confirmed.")); + else + u->SendMessage(NickServ, _("Your email address is not confirmed. To confirm it, follow the instructions that were emailed to you.")); + const NickAlias *this_na = NickAlias::Find(u->Account()->display); + time_t time_registered = Anope::CurTime - this_na->time_registered; + time_t unconfirmed_expire = Config->GetModule(this)->Get("unconfirmedexpire", "1d"); + if (unconfirmed_expire > time_registered) + u->SendMessage(NickServ, _("Your account will expire, if not confirmed, in %s."), Anope::Duration(unconfirmed_expire - time_registered, u->Account()).c_str()); + } + } + + void OnPreNickExpire(NickAlias *na, bool &expire) anope_override + { + if (unconfirmed.HasExt(na->nc)) + { + time_t unconfirmed_expire = Config->GetModule(this)->Get("unconfirmedexpire", "1d"); + if (unconfirmed_expire && Anope::CurTime - na->time_registered >= unconfirmed_expire) + expire = true; + } + } +}; + +static bool SendRegmail(User *u, const NickAlias *na, BotInfo *bi) +{ + NickCore *nc = na->nc; + + Anope::string *code = na->nc->GetExt("passcode"); + if (code == NULL) + { + code = na->nc->Extend("passcode"); + *code = Anope::Random(9); + } + + Anope::string subject = Language::Translate(na->nc, Config->GetBlock("mail")->Get("registration_subject").c_str()), + message = Language::Translate(na->nc, Config->GetBlock("mail")->Get("registration_message").c_str()); + + subject = subject.replace_all_cs("%n", na->nick); + subject = subject.replace_all_cs("%N", Config->GetBlock("networkinfo")->Get("networkname")); + subject = subject.replace_all_cs("%c", *code); + + message = message.replace_all_cs("%n", na->nick); + message = message.replace_all_cs("%N", Config->GetBlock("networkinfo")->Get("networkname")); + message = message.replace_all_cs("%c", *code); + + return Mail::Send(u, nc, bi, subject, message); +} + +MODULE_INIT(NSRegister) diff --git a/modules/commands/ns_resetpass.cpp b/modules/commands/ns_resetpass.cpp new file mode 100644 index 0000000..12fe117 --- /dev/null +++ b/modules/commands/ns_resetpass.cpp @@ -0,0 +1,144 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +static bool SendResetEmail(User *u, const NickAlias *na, BotInfo *bi); + +class CommandNSResetPass : public Command +{ + public: + CommandNSResetPass(Module *creator) : Command(creator, "nickserv/resetpass", 2, 2) + { + this->SetDesc(_("Helps you reset lost passwords")); + this->SetSyntax(_("\037nickname\037 \037email\037")); + this->AllowUnregistered(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const NickAlias *na; + + if (!(na = NickAlias::Find(params[0]))) + source.Reply(NICK_X_NOT_REGISTERED, params[0].c_str()); + else if (!na->nc->email.equals_ci(params[1])) + source.Reply(_("Incorrect email address.")); + else + { + if (SendResetEmail(source.GetUser(), na, source.service)) + { + Log(LOG_COMMAND, source, this) << "for " << na->nick << " (group: " << na->nc->display << ")"; + source.Reply(_("Password reset email for \002%s\002 has been sent."), na->nick.c_str()); + } + } + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sends a passcode to the nickname with instructions on how to\n" + "reset their password. Email must be the email address associated\n" + "to the nickname.")); + return true; + } +}; + +struct ResetInfo +{ + Anope::string code; + time_t time; +}; + +class NSResetPass : public Module +{ + CommandNSResetPass commandnsresetpass; + PrimitiveExtensibleItem reset; + + public: + NSResetPass(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsresetpass(this), reset(this, "reset") + { + if (!Config->GetBlock("mail")->Get("usemail")) + throw ModuleException("Not using mail."); + } + + EventReturn OnPreCommand(CommandSource &source, Command *command, std::vector ¶ms) anope_override + { + if (command->name == "nickserv/confirm" && params.size() > 1) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return EVENT_STOP; + } + + NickAlias *na = NickAlias::Find(params[0]); + + ResetInfo *ri = na ? reset.Get(na->nc) : NULL; + if (na && ri) + { + NickCore *nc = na->nc; + const Anope::string &passcode = params[1]; + if (ri->time < Anope::CurTime - 3600) + { + reset.Unset(nc); + source.Reply(_("Your password reset request has expired.")); + } + else if (passcode.equals_cs(ri->code)) + { + reset.Unset(nc); + nc->Shrink("UNCONFIRMED"); + + Log(LOG_COMMAND, source, &commandnsresetpass) << "to confirm RESETPASS and forcefully identify as " << na->nick; + + if (source.GetUser()) + { + source.GetUser()->Identify(na); + } + + source.Reply(_("You are now identified for your nick. Change your password now.")); + } + else + return EVENT_CONTINUE; + + return EVENT_STOP; + } + } + + return EVENT_CONTINUE; + } +}; + +static bool SendResetEmail(User *u, const NickAlias *na, BotInfo *bi) +{ + Anope::string subject = Language::Translate(na->nc, Config->GetBlock("mail")->Get("reset_subject").c_str()), + message = Language::Translate(na->nc, Config->GetBlock("mail")->Get("reset_message").c_str()), + passcode = Anope::Random(20); + + subject = subject.replace_all_cs("%n", na->nick); + subject = subject.replace_all_cs("%N", Config->GetBlock("networkinfo")->Get("networkname")); + subject = subject.replace_all_cs("%c", passcode); + + message = message.replace_all_cs("%n", na->nick); + message = message.replace_all_cs("%N", Config->GetBlock("networkinfo")->Get("networkname")); + message = message.replace_all_cs("%c", passcode); + + ResetInfo *ri = na->nc->Extend("reset"); + ri->code = passcode; + ri->time = Anope::CurTime; + + return Mail::Send(u, na->nc, bi, subject, message); +} + +MODULE_INIT(NSResetPass) diff --git a/modules/commands/ns_set.cpp b/modules/commands/ns_set.cpp new file mode 100644 index 0000000..1bc246f --- /dev/null +++ b/modules/commands/ns_set.cpp @@ -0,0 +1,1350 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandNSSet : public Command +{ + public: + CommandNSSet(Module *creator) : Command(creator, "nickserv/set", 1, 3) + { + this->SetDesc(_("Set options, including kill protection")); + this->SetSyntax(_("\037option\037 \037parameters\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->OnSyntaxError(source, ""); + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets various nickname options. \037option\037 can be one of:")); + + Anope::string this_name = source.command; + bool hide_privileged_commands = Config->GetBlock("options")->Get("hideprivilegedcommands"), + hide_registered_commands = Config->GetBlock("options")->Get("hideregisteredcommands"); + for (CommandInfo::map::const_iterator it = source.service->commands.begin(), it_end = source.service->commands.end(); it != it_end; ++it) + { + const Anope::string &c_name = it->first; + const CommandInfo &info = it->second; + + if (c_name.find_ci(this_name + " ") == 0) + { + if (info.hide) + continue; + + ServiceReference c("Command", info.name); + // XXX dup + if (!c) + continue; + else if (hide_registered_commands && !c->AllowUnregistered() && !source.GetAccount()) + continue; + else if (hide_privileged_commands && !info.permission.empty() && !source.HasCommand(info.permission)) + continue; + + source.command = c_name; + c->OnServHelp(source); + } + } + + source.Reply(_("Type \002%s%s HELP %s \037option\037\002 for more information\n" + "on a specific option."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), this_name.c_str()); + + return true; + } +}; + +class CommandNSSASet : public Command +{ + public: + CommandNSSASet(Module *creator) : Command(creator, "nickserv/saset", 2, 4) + { + this->SetDesc(_("Set SET-options on another nickname")); + this->SetSyntax(_("\037option\037 \037nickname\037 \037parameters\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->OnSyntaxError(source, ""); + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets various nickname options. \037option\037 can be one of:")); + + Anope::string this_name = source.command; + for (CommandInfo::map::const_iterator it = source.service->commands.begin(), it_end = source.service->commands.end(); it != it_end; ++it) + { + const Anope::string &c_name = it->first; + const CommandInfo &info = it->second; + + if (c_name.find_ci(this_name + " ") == 0) + { + ServiceReference command("Command", info.name); + if (command) + { + source.command = c_name; + command->OnServHelp(source); + } + } + } + + source.Reply(_("Type \002%s%s HELP %s \037option\037\002 for more information\n" + "on a specific option. The options will be set on the given\n" + "\037nickname\037."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), this_name.c_str()); + return true; + } +}; + +class CommandNSSetPassword : public Command +{ + public: + CommandNSSetPassword(Module *creator) : Command(creator, "nickserv/set/password", 1) + { + this->SetDesc(_("Set your nickname password")); + this->SetSyntax(_("\037new-password\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string ¶m = params[0]; + unsigned len = param.length(); + + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + if (source.GetNick().equals_ci(param) || (Config->GetBlock("options")->Get("strictpasswords") && len < 5)) + { + source.Reply(MORE_OBSCURE_PASSWORD); + return; + } + + unsigned int passlen = Config->GetModule("nickserv")->Get("passlen", "32"); + if (len > passlen) + { + source.Reply(PASSWORD_TOO_LONG, passlen); + return; + } + + Log(LOG_COMMAND, source, this) << "to change their password"; + + Anope::Encrypt(param, source.nc->pass); + Anope::string tmp_pass; + if (Anope::Decrypt(source.nc->pass, tmp_pass) == 1) + source.Reply(_("Password for \002%s\002 changed to \002%s\002."), source.nc->display.c_str(), tmp_pass.c_str()); + else + source.Reply(_("Password for \002%s\002 changed."), source.nc->display.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Changes the password used to identify you as the nick's\n" + "owner.")); + return true; + } +}; + +class CommandNSSASetPassword : public Command +{ + public: + CommandNSSASetPassword(Module *creator) : Command(creator, "nickserv/saset/password", 2, 2) + { + this->SetDesc(_("Set the nickname password")); + this->SetSyntax(_("\037nickname\037 \037new-password\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const NickAlias *setter_na = NickAlias::Find(params[0]); + if (setter_na == NULL) + { + source.Reply(NICK_X_NOT_REGISTERED, params[0].c_str()); + return; + } + NickCore *nc = setter_na->nc; + + size_t len = params[1].length(); + + if (Config->GetModule("nickserv")->Get("secureadmins", "yes") && source.nc != nc && nc->IsServicesOper()) + { + source.Reply(_("You may not change the password of other Services Operators.")); + return; + } + + if (nc->display.equals_ci(params[1]) || (Config->GetBlock("options")->Get("strictpasswords") && len < 5)) + { + source.Reply(MORE_OBSCURE_PASSWORD); + return; + } + + unsigned int passlen = Config->GetModule("nickserv")->Get("passlen", "32"); + if (len > passlen) + { + source.Reply(PASSWORD_TOO_LONG, passlen); + return; + } + + Log(LOG_ADMIN, source, this) << "to change the password of " << nc->display; + + Anope::Encrypt(params[1], nc->pass); + Anope::string tmp_pass; + if (Anope::Decrypt(nc->pass, tmp_pass) == 1) + source.Reply(_("Password for \002%s\002 changed to \002%s\002."), nc->display.c_str(), tmp_pass.c_str()); + else + source.Reply(_("Password for \002%s\002 changed."), nc->display.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Changes the password used to identify as the nick's owner.")); + return true; + } +}; + +class CommandNSSetAutoOp : public Command +{ + public: + CommandNSSetAutoOp(Module *creator, const Anope::string &sname = "nickserv/set/autoop", size_t min = 1) : Command(creator, sname, min, min + 1) + { + this->SetDesc(_("Sets whether services should set channel status modes on you automatically.")); + this->SetSyntax("{ON | OFF}"); + } + + void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const NickAlias *na = NickAlias::Find(user); + if (na == NULL) + { + source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); + return; + } + NickCore *nc = na->nc; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, nc, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (param.equals_ci("ON")) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to enable autoop for " << na->nc->display; + nc->Extend("AUTOOP"); + source.Reply(_("Services will from now on set status modes on %s in channels."), nc->display.c_str()); + } + else if (param.equals_ci("OFF")) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to disable autoop for " << na->nc->display; + nc->Shrink("AUTOOP"); + source.Reply(_("Services will no longer set status modes on %s in channels."), nc->display.c_str()); + } + else + this->OnSyntaxError(source, "AUTOOP"); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, source.nc->display, params[0]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + BotInfo *bi = Config->GetClient("ChanServ"); + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets whether you will be given your channel status modes automatically.\n" + "Set to \002ON\002 to allow %s to set status modes on you automatically\n" + "when entering channels. Note that depending on channel settings some modes\n" + "may not get set automatically."), bi ? bi->nick.c_str() : "ChanServ"); + return true; + } +}; + +class CommandNSSASetAutoOp : public CommandNSSetAutoOp +{ + public: + CommandNSSASetAutoOp(Module *creator) : CommandNSSetAutoOp(creator, "nickserv/saset/autoop", 2) + { + this->ClearSyntax(); + this->SetSyntax(_("\037nickname\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, params[0], params[1]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + BotInfo *bi = Config->GetClient("ChanServ"); + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets whether the given nickname will be given its status modes\n" + "in channels automatically. Set to \002ON\002 to allow %s\n" + "to set status modes on the given nickname automatically when it\n" + "is entering channels. Note that depending on channel settings\n" + "some modes may not get set automatically."), bi ? bi->nick.c_str() : "ChanServ"); + return true; + } +}; + +class CommandNSSetDisplay : public Command +{ + public: + CommandNSSetDisplay(Module *creator, const Anope::string &sname = "nickserv/set/display", size_t min = 1) : Command(creator, sname, min, min + 1) + { + this->SetDesc(_("Set the display of your group in Services")); + this->SetSyntax(_("\037new-display\037")); + } + + void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + NickAlias *user_na = NickAlias::Find(user), *na = NickAlias::Find(param); + + if (Config->GetModule("nickserv")->Get("nonicknameownership")) + { + source.Reply(_("This command may not be used on this network because nickname ownership is disabled.")); + return; + } + if (user_na == NULL) + { + source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); + return; + } + else if (!na || *na->nc != *user_na->nc) + { + source.Reply(_("The new display MUST be a nickname of the nickname group %s."), user_na->nc->display.c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, user_na->nc, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + Log(user_na->nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to change the display of " << user_na->nc->display << " to " << na->nick; + + user_na->nc->SetDisplay(na); + + /* Send updated account name */ + for (std::list::iterator it = user_na->nc->users.begin(); it != user_na->nc->users.end(); ++it) + { + User *u = *it; + IRCD->SendLogin(u, user_na); + } + + source.Reply(NICK_SET_DISPLAY_CHANGED, user_na->nc->display.c_str()); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, source.nc->display, params[0]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Changes the display used to refer to your nickname group in\n" + "Services. The new display MUST be a nick of your group.")); + return true; + } +}; + +class CommandNSSASetDisplay : public CommandNSSetDisplay +{ + public: + CommandNSSASetDisplay(Module *creator) : CommandNSSetDisplay(creator, "nickserv/saset/display", 2) + { + this->ClearSyntax(); + this->SetSyntax(_("\037nickname\037 \037new-display\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, params[0], params[1]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Changes the display used to refer to the nickname group in\n" + "Services. The new display MUST be a nick of the group.")); + return true; + } +}; + +class CommandNSSetEmail : public Command +{ + static bool SendConfirmMail(User *u, NickCore *nc, BotInfo *bi, const Anope::string &new_email) + { + Anope::string code = Anope::Random(9); + + std::pair *n = nc->Extend >("ns_set_email"); + n->first = new_email; + n->second = code; + + Anope::string subject = Config->GetBlock("mail")->Get("emailchange_subject"), + message = Config->GetBlock("mail")->Get("emailchange_message"); + + subject = subject.replace_all_cs("%e", nc->email); + subject = subject.replace_all_cs("%E", new_email); + subject = subject.replace_all_cs("%n", nc->display); + subject = subject.replace_all_cs("%N", Config->GetBlock("networkinfo")->Get("networkname")); + subject = subject.replace_all_cs("%c", code); + + message = message.replace_all_cs("%e", nc->email); + message = message.replace_all_cs("%E", new_email); + message = message.replace_all_cs("%n", nc->display); + message = message.replace_all_cs("%N", Config->GetBlock("networkinfo")->Get("networkname")); + message = message.replace_all_cs("%c", code); + + Anope::string old = nc->email; + nc->email = new_email; + bool b = Mail::Send(u, nc, bi, subject, message); + nc->email = old; + return b; + } + + public: + CommandNSSetEmail(Module *creator, const Anope::string &cname = "nickserv/set/email", size_t min = 0) : Command(creator, cname, min, min + 1) + { + this->SetDesc(_("Associate an E-mail address with your nickname")); + this->SetSyntax(_("\037address\037")); + } + + void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const NickAlias *na = NickAlias::Find(user); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); + return; + } + NickCore *nc = na->nc; + + if (nc->HasExt("UNCONFIRMED")) + { + source.Reply(_("You may not change the email of an unconfirmed account.")); + return; + } + + if (param.empty() && Config->GetModule("nickserv")->Get("forceemail", "yes")) + { + source.Reply(_("You cannot unset the e-mail on this network.")); + return; + } + else if (Config->GetModule("nickserv")->Get("secureadmins", "yes") && source.nc != nc && nc->IsServicesOper()) + { + source.Reply(_("You may not change the e-mail of other Services Operators.")); + return; + } + else if (!param.empty() && !Mail::Validate(param)) + { + source.Reply(MAIL_X_INVALID, param.c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, nc, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (!param.empty() && Config->GetModule("nickserv")->Get("confirmemailchanges") && !source.IsServicesOper()) + { + if (SendConfirmMail(source.GetUser(), source.GetAccount(), source.service, param)) + { + Log(LOG_COMMAND, source, this) << "to request changing the email of " << nc->display << " to " << param; + source.Reply(_("A confirmation e-mail has been sent to \002%s\002. Follow the instructions in it to change your e-mail address."), param.c_str()); + } + } + else + { + if (!param.empty()) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to change the email of " << nc->display << " to " << param; + nc->email = param; + source.Reply(_("E-mail address for \002%s\002 changed to \002%s\002."), nc->display.c_str(), param.c_str()); + } + else + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to unset the email of " << nc->display; + nc->email.clear(); + source.Reply(_("E-mail address for \002%s\002 unset."), nc->display.c_str()); + } + } + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, source.nc->display, params.size() ? params[0] : ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Associates the given E-mail address with your nickname.\n" + "This address will be displayed whenever someone requests\n" + "information on the nickname with the \002INFO\002 command.")); + return true; + } +}; + +class CommandNSSASetEmail : public CommandNSSetEmail +{ + public: + CommandNSSASetEmail(Module *creator) : CommandNSSetEmail(creator, "nickserv/saset/email", 2) + { + this->ClearSyntax(); + this->SetSyntax(_("\037nickname\037 \037address\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, params[0], params.size() > 1 ? params[1] : ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Associates the given E-mail address with the nickname.")); + return true; + } +}; + +class CommandNSSetKeepModes : public Command +{ + public: + CommandNSSetKeepModes(Module *creator, const Anope::string &sname = "nickserv/set/keepmodes", size_t min = 1) : Command(creator, sname, min, min + 1) + { + this->SetDesc(_("Enable or disable keep modes")); + this->SetSyntax("{ON | OFF}"); + } + + void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const NickAlias *na = NickAlias::Find(user); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); + return; + } + NickCore *nc = na->nc; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, nc, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (param.equals_ci("ON")) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to enable keepmodes for " << nc->display; + nc->Extend("NS_KEEP_MODES"); + source.Reply(_("Keep modes for %s is now \002on\002."), nc->display.c_str()); + } + else if (param.equals_ci("OFF")) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to disable keepmodes for " << nc->display; + nc->Shrink("NS_KEEP_MODES"); + source.Reply(_("Keep modes for %s is now \002off\002."), nc->display.c_str()); + } + else + this->OnSyntaxError(source, ""); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, source.nc->display, params[0]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enables or disables keepmodes for your nick. If keep\n" + "modes is enabled, services will remember your usermodes\n" + "and attempt to re-set them the next time you authenticate.")); + return true; + } +}; + +class CommandNSSASetKeepModes : public CommandNSSetKeepModes +{ + public: + CommandNSSASetKeepModes(Module *creator) : CommandNSSetKeepModes(creator, "nickserv/saset/keepmodes", 2) + { + this->ClearSyntax(); + this->SetSyntax(_("\037nickname\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, params[0], params[1]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Enables or disables keepmodes for the given nick. If keep\n" + "modes is enabled, services will remember users' usermodes\n" + "and attempt to re-set them the next time they authenticate.")); + return true; + } +}; + +class CommandNSSetKill : public Command +{ + public: + CommandNSSetKill(Module *creator, const Anope::string &sname = "nickserv/set/kill", size_t min = 1) : Command(creator, sname, min, min + 1) + { + this->SetDesc(_("Turn protection on or off")); + this->SetSyntax("{ON | QUICK | IMMED | OFF}"); + } + + void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + if (Config->GetModule("nickserv")->Get("nonicknameownership")) + { + source.Reply(_("This command may not be used on this network because nickname ownership is disabled.")); + return; + } + + const NickAlias *na = NickAlias::Find(user); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); + return; + } + NickCore *nc = na->nc; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, nc, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (param.equals_ci("ON")) + { + nc->Extend("KILLPROTECT"); + nc->Shrink("KILL_QUICK"); + nc->Shrink("KILL_IMMED"); + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to set kill on for " << nc->display; + source.Reply(_("Protection is now \002on\002 for \002%s\002."), nc->display.c_str()); + } + else if (param.equals_ci("QUICK")) + { + nc->Extend("KILLPROTECT"); + nc->Extend("KILL_QUICK"); + nc->Shrink("KILL_IMMED"); + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to set kill quick for " << nc->display; + source.Reply(_("Protection is now \002on\002 for \002%s\002, with a reduced delay."), nc->display.c_str()); + } + else if (param.equals_ci("IMMED")) + { + if (Config->GetModule(this->owner)->Get("allowkillimmed")) + { + nc->Extend("KILLPROTECT"); + nc->Shrink("KILL_QUICK"); + nc->Extend("KILL_IMMED"); + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to set kill immed for " << nc->display; + source.Reply(_("Protection is now \002on\002 for \002%s\002, with no delay."), nc->display.c_str()); + } + else + source.Reply(_("The \002IMMED\002 option is not available on this network.")); + } + else if (param.equals_ci("OFF")) + { + nc->Shrink("KILLPROTECT"); + nc->Shrink("KILL_QUICK"); + nc->Shrink("KILL_IMMED"); + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to disable kill for " << nc->display; + source.Reply(_("Protection is now \002off\002 for \002%s\002."), nc->display.c_str()); + } + else + this->OnSyntaxError(source, "KILL"); + + return; + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, source.nc->display, params[0]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Turns the automatic protection option for your nick\n" + "on or off. With protection on, if another user\n" + "tries to take your nick, they will be given one minute to\n" + "change to another nick, after which %s will forcibly change\n" + "their nick.\n" + " \n" + "If you select \002QUICK\002, the user will be given only 20 seconds\n" + "to change nicks instead of the usual 60. If you select\n" + "\002IMMED\002, the user's nick will be changed immediately \037without\037 being\n" + "warned first or given a chance to change their nick; please\n" + "do not use this option unless necessary. Also, your\n" + "network's administrators may have disabled this option."), source.service->nick.c_str()); + return true; + } +}; + +class CommandNSSASetKill : public CommandNSSetKill +{ + public: + CommandNSSASetKill(Module *creator) : CommandNSSetKill(creator, "nickserv/saset/kill", 2) + { + this->ClearSyntax(); + this->SetSyntax(_("\037nickname\037 {ON | QUICK | IMMED | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, params[0], params[1]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Turns the automatic protection option for the nick\n" + "on or off. With protection on, if another user\n" + "tries to take the nick, they will be given one minute to\n" + "change to another nick, after which %s will forcibly change\n" + "their nick.\n" + " \n" + "If you select \002QUICK\002, the user will be given only 20 seconds\n" + "to change nicks instead of the usual 60. If you select\n" + "\002IMMED\002, the user's nick will be changed immediately \037without\037 being\n" + "warned first or given a chance to change their nick; please\n" + "do not use this option unless necessary. Also, your\n" + "network's administrators may have disabled this option."), source.service->nick.c_str()); + return true; + } +}; + +class CommandNSSetLanguage : public Command +{ + public: + CommandNSSetLanguage(Module *creator, const Anope::string &sname = "nickserv/set/language", size_t min = 1) : Command(creator, sname, min, min + 1) + { + this->SetDesc(_("Set the language Services will use when messaging you")); + this->SetSyntax(_("\037language\037")); + } + + void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const NickAlias *na = NickAlias::Find(user); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); + return; + } + NickCore *nc = na->nc; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, nc, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (param != "en_US") + for (unsigned j = 0; j < Language::Languages.size(); ++j) + { + if (Language::Languages[j] == param) + break; + else if (j + 1 == Language::Languages.size()) + { + this->OnSyntaxError(source, ""); + return; + } + } + + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to change the language of " << nc->display << " to " << param; + + nc->language = param; + if (source.GetAccount() == nc) + source.Reply(_("Language changed to \002English\002.")); + else + source.Reply(_("Language for \002%s\002 changed to \002%s\002."), nc->display.c_str(), Language::Translate(param.c_str(), _("English"))); + } + + void Execute(CommandSource &source, const std::vector ¶m) anope_override + { + this->Run(source, source.nc->display, param[0]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Changes the language Services uses when sending messages to\n" + "you (for example, when responding to a command you send).\n" + "\037language\037 should be chosen from the following list of\n" + "supported languages:")); + + source.Reply(" en_US (English)"); + for (unsigned j = 0; j < Language::Languages.size(); ++j) + { + const Anope::string &langname = Language::Translate(Language::Languages[j].c_str(), _("English")); + if (langname == "English") + continue; + source.Reply(" %s (%s)", Language::Languages[j].c_str(), langname.c_str()); + } + + return true; + } +}; + +class CommandNSSASetLanguage : public CommandNSSetLanguage +{ + public: + CommandNSSASetLanguage(Module *creator) : CommandNSSetLanguage(creator, "nickserv/saset/language", 2) + { + this->ClearSyntax(); + this->SetSyntax(_("\037nickname\037 \037language\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, params[0], params[1]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Changes the language Services uses when sending messages to\n" + "the given user (for example, when responding to a command they send).\n" + "\037language\037 should be chosen from the following list of\n" + "supported languages:")); + source.Reply(" en (English)"); + for (unsigned j = 0; j < Language::Languages.size(); ++j) + { + const Anope::string &langname = Language::Translate(Language::Languages[j].c_str(), _("English")); + if (langname == "English") + continue; + source.Reply(" %s (%s)", Language::Languages[j].c_str(), langname.c_str()); + } + return true; + } +}; + +class CommandNSSetMessage : public Command +{ + public: + CommandNSSetMessage(Module *creator, const Anope::string &sname = "nickserv/set/message", size_t min = 1) : Command(creator, sname, min, min + 1) + { + this->SetDesc(_("Change the communication method of Services")); + this->SetSyntax("{ON | OFF}"); + } + + void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const NickAlias *na = NickAlias::Find(user); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); + return; + } + NickCore *nc = na->nc; + + if (!Config->GetBlock("options")->Get("useprivmsg")) + { + source.Reply(_("You cannot %s on this network."), source.command.c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, nc, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (param.equals_ci("ON")) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to enable " << source.command << " for " << nc->display; + nc->Extend("MSG"); + source.Reply(_("Services will now reply to \002%s\002 with \002messages\002."), nc->display.c_str()); + } + else if (param.equals_ci("OFF")) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to disable " << source.command << " for " << nc->display; + nc->Shrink("MSG"); + source.Reply(_("Services will now reply to \002%s\002 with \002notices\002."), nc->display.c_str()); + } + else + this->OnSyntaxError(source, "MSG"); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, source.nc->display, params[0]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + Anope::string cmd = source.command; + size_t i = cmd.find_last_of(' '); + if (i != Anope::string::npos) + cmd = cmd.substr(i + 1); + + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows you to choose the way Services are communicating with\n" + "you. With \002%s\002 set, Services will use messages, else they'll\n" + "use notices."), cmd.upper().c_str()); + return true; + } + + void OnServHelp(CommandSource &source) anope_override + { + if (Config->GetBlock("options")->Get("useprivmsg")) + Command::OnServHelp(source); + } +}; + +class CommandNSSASetMessage : public CommandNSSetMessage +{ + public: + CommandNSSASetMessage(Module *creator) : CommandNSSetMessage(creator, "nickserv/saset/message", 2) + { + this->ClearSyntax(); + this->SetSyntax(_("\037nickname\037 {ON | OFF}")); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows you to choose the way Services are communicating with\n" + "the given user. With \002MSG\002 set, Services will use messages,\n" + "else they'll use notices.")); + return true; + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, params[0], params[1]); + } +}; + +class CommandNSSetSecure : public Command +{ + public: + CommandNSSetSecure(Module *creator, const Anope::string &sname = "nickserv/set/secure", size_t min = 1) : Command(creator, sname, min, min + 1) + { + this->SetDesc(_("Turn nickname security on or off")); + this->SetSyntax("{ON | OFF}"); + } + + void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const NickAlias *na = NickAlias::Find(user); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); + return; + } + NickCore *nc = na->nc; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, nc, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (param.equals_ci("ON")) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to enable secure for " << nc->display; + nc->Extend("NS_SECURE"); + source.Reply(_("Secure option is now \002on\002 for \002%s\002."), nc->display.c_str()); + } + else if (param.equals_ci("OFF")) + { + Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to disable secure for " << nc->display; + nc->Shrink("NS_SECURE"); + source.Reply(_("Secure option is now \002off\002 for \002%s\002."), nc->display.c_str()); + } + else + this->OnSyntaxError(source, "SECURE"); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, source.nc->display, params[0]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Turns %s's security features on or off for your\n" + "nick. With \002SECURE\002 set, you must enter your password\n" + "before you will be recognized as the owner of the nick,\n" + "regardless of whether your address is on the access\n" + "list. However, if you are on the access list, %s\n" + "will not auto-kill you regardless of the setting of the\n" + "\002KILL\002 option."), source.service->nick.c_str(), source.service->nick.c_str()); + return true; + } +}; + +class CommandNSSASetSecure : public CommandNSSetSecure +{ + public: + CommandNSSASetSecure(Module *creator) : CommandNSSetSecure(creator, "nickserv/saset/secure", 2) + { + this->ClearSyntax(); + this->SetSyntax(_("\037nickname\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, params[0], params[1]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Turns %s's security features on or off for your\n" + "nick. With \002SECURE\002 set, you must enter your password\n" + "before you will be recognized as the owner of the nick,\n" + "regardless of whether your address is on the access\n" + "list. However, if you are on the access list, %s\n" + "will not auto-kill you regardless of the setting of the\n" + "\002KILL\002 option."), source.service->nick.c_str(), source.service->nick.c_str()); + return true; + } +}; + +class CommandNSSASetNoexpire : public Command +{ + public: + CommandNSSASetNoexpire(Module *creator) : Command(creator, "nickserv/saset/noexpire", 1, 2) + { + this->SetDesc(_("Prevent the nickname from expiring")); + this->SetSyntax(_("\037nickname\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + NickAlias *na = NickAlias::Find(params[0]); + if (na == NULL) + { + source.Reply(NICK_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + Anope::string param = params.size() > 1 ? params[1] : ""; + + if (param.equals_ci("ON")) + { + Log(LOG_ADMIN, source, this) << "to enable noexpire for " << na->nick << " (" << na->nc->display << ")"; + na->Extend("NS_NO_EXPIRE"); + source.Reply(_("Nick %s \002will not\002 expire."), na->nick.c_str()); + } + else if (param.equals_ci("OFF")) + { + Log(LOG_ADMIN, source, this) << "to disable noexpire for " << na->nick << " (" << na->nc->display << ")"; + na->Shrink("NS_NO_EXPIRE"); + source.Reply(_("Nick %s \002will\002 expire."), na->nick.c_str()); + } + else + this->OnSyntaxError(source, "NOEXPIRE"); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets whether the given nickname will expire. Setting this\n" + "to \002ON\002 prevents the nickname from expiring.")); + return true; + } +}; + +class NSSet : public Module +{ + CommandNSSet commandnsset; + CommandNSSASet commandnssaset; + + CommandNSSetAutoOp commandnssetautoop; + CommandNSSASetAutoOp commandnssasetautoop; + + CommandNSSetDisplay commandnssetdisplay; + CommandNSSASetDisplay commandnssasetdisplay; + + CommandNSSetEmail commandnssetemail; + CommandNSSASetEmail commandnssasetemail; + + CommandNSSetKeepModes commandnssetkeepmodes; + CommandNSSASetKeepModes commandnssasetkeepmodes; + + CommandNSSetKill commandnssetkill; + CommandNSSASetKill commandnssasetkill; + + CommandNSSetLanguage commandnssetlanguage; + CommandNSSASetLanguage commandnssasetlanguage; + + CommandNSSetMessage commandnssetmessage; + CommandNSSASetMessage commandnssasetmessage; + + CommandNSSetPassword commandnssetpassword; + CommandNSSASetPassword commandnssasetpassword; + + CommandNSSetSecure commandnssetsecure; + CommandNSSASetSecure commandnssasetsecure; + + CommandNSSASetNoexpire commandnssasetnoexpire; + + SerializableExtensibleItem autoop, killprotect, kill_quick, kill_immed, + message, secure, noexpire; + + struct KeepModes : SerializableExtensibleItem + { + KeepModes(Module *m, const Anope::string &n) : SerializableExtensibleItem(m, n) { } + + void ExtensibleSerialize(const Extensible *e, const Serializable *s, Serialize::Data &data) const anope_override + { + SerializableExtensibleItem::ExtensibleSerialize(e, s, data); + + if (s->GetSerializableType()->GetName() != "NickCore") + return; + + const NickCore *nc = anope_dynamic_static_cast(s); + Anope::string modes; + for (User::ModeList::const_iterator it = nc->last_modes.begin(); it != nc->last_modes.end(); ++it) + { + if (!modes.empty()) + modes += " "; + modes += it->first; + if (!it->second.empty()) + modes += "," + it->second; + } + data["last_modes"] << modes; + } + + void ExtensibleUnserialize(Extensible *e, Serializable *s, Serialize::Data &data) anope_override + { + SerializableExtensibleItem::ExtensibleUnserialize(e, s, data); + + if (s->GetSerializableType()->GetName() != "NickCore") + return; + + NickCore *nc = anope_dynamic_static_cast(s); + Anope::string modes; + data["last_modes"] >> modes; + nc->last_modes.clear(); + for (spacesepstream sep(modes); sep.GetToken(modes);) + { + size_t c = modes.find(','); + if (c == Anope::string::npos) + nc->last_modes.insert(std::make_pair(modes, "")); + else + nc->last_modes.insert(std::make_pair(modes.substr(0, c), modes.substr(c + 1))); + } + } + } keep_modes; + + /* email, passcode */ + PrimitiveExtensibleItem > ns_set_email; + + public: + NSSet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsset(this), commandnssaset(this), + commandnssetautoop(this), commandnssasetautoop(this), + commandnssetdisplay(this), commandnssasetdisplay(this), + commandnssetemail(this), commandnssasetemail(this), + commandnssetkeepmodes(this), commandnssasetkeepmodes(this), + commandnssetkill(this), commandnssasetkill(this), + commandnssetlanguage(this), commandnssasetlanguage(this), + commandnssetmessage(this), commandnssasetmessage(this), + commandnssetpassword(this), commandnssasetpassword(this), + commandnssetsecure(this), commandnssasetsecure(this), + commandnssasetnoexpire(this), + + autoop(this, "AUTOOP"), + killprotect(this, "KILLPROTECT"), kill_quick(this, "KILL_QUICK"), + kill_immed(this, "KILL_IMMED"), message(this, "MSG"), + secure(this, "NS_SECURE"), noexpire(this, "NS_NO_EXPIRE"), + + keep_modes(this, "NS_KEEP_MODES"), ns_set_email(this, "ns_set_email") + { + + } + + EventReturn OnPreCommand(CommandSource &source, Command *command, std::vector ¶ms) anope_override + { + NickCore *uac = source.nc; + + if (command->name == "nickserv/confirm" && !params.empty() && uac) + { + std::pair *n = ns_set_email.Get(uac); + if (n) + { + if (params[0] == n->second) + { + uac->email = n->first; + Log(LOG_COMMAND, source, command) << "to confirm their email address change to " << uac->email; + source.Reply(_("Your email address has been changed to \002%s\002."), uac->email.c_str()); + ns_set_email.Unset(uac); + return EVENT_STOP; + } + } + } + + return EVENT_CONTINUE; + } + + void OnSetCorrectModes(User *user, Channel *chan, AccessGroup &access, bool &give_modes, bool &take_modes) anope_override + { + if (chan->ci) + { + /* Only give modes if autoop is set */ + give_modes &= !user->Account() || autoop.HasExt(user->Account()); + } + } + + void OnPreNickExpire(NickAlias *na, bool &expire) anope_override + { + if (noexpire.HasExt(na)) + expire = false; + } + + void OnNickInfo(CommandSource &source, NickAlias *na, InfoFormatter &info, bool show_hidden) anope_override + { + if (!show_hidden) + return; + + if (kill_immed.HasExt(na->nc)) + info.AddOption(_("Immediate protection")); + else if (kill_quick.HasExt(na->nc)) + info.AddOption(_("Quick protection")); + else if (killprotect.HasExt(na->nc)) + info.AddOption(_("Protection")); + if (secure.HasExt(na->nc)) + info.AddOption(_("Security")); + if (message.HasExt(na->nc)) + info.AddOption(_("Message mode")); + if (autoop.HasExt(na->nc)) + info.AddOption(_("Auto-op")); + if (noexpire.HasExt(na)) + info.AddOption(_("No expire")); + if (keep_modes.HasExt(na->nc)) + info.AddOption(_("Keep modes")); + } + + void OnUserModeSet(const MessageSource &setter, User *u, const Anope::string &mname) anope_override + { + if (u->Account() && setter.GetUser() == u) + u->Account()->last_modes = u->GetModeList(); + } + + void OnUserModeUnset(const MessageSource &setter, User *u, const Anope::string &mname) anope_override + { + if (u->Account() && setter.GetUser() == u) + u->Account()->last_modes = u->GetModeList(); + } + + void OnUserLogin(User *u) anope_override + { + if (keep_modes.HasExt(u->Account())) + { + User::ModeList modes = u->Account()->last_modes; + for (User::ModeList::iterator it = modes.begin(); it != modes.end(); ++it) + { + UserMode *um = ModeManager::FindUserModeByName(it->first); + /* if the null user can set the mode, then it's probably safe */ + if (um && um->CanSet(NULL)) + u->SetMode(NULL, it->first, it->second); + } + } + } +}; + +MODULE_INIT(NSSet) diff --git a/modules/commands/ns_set_misc.cpp b/modules/commands/ns_set_misc.cpp new file mode 100644 index 0000000..0e53361 --- /dev/null +++ b/modules/commands/ns_set_misc.cpp @@ -0,0 +1,234 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/set_misc.h" + +static Module *me; + +static Anope::map descriptions; + +struct NSMiscData; +static Anope::map *> items; + +static ExtensibleItem *GetItem(const Anope::string &name) +{ + ExtensibleItem* &it = items[name]; + if (!it) + try + { + it = new ExtensibleItem(me, name); + } + catch (const ModuleException &) { } + return it; +} + +struct NSMiscData : MiscData, Serializable +{ + NSMiscData(Extensible *) : Serializable("NSMiscData") { } + + NSMiscData(NickCore *ncore, const Anope::string &n, const Anope::string &d) : Serializable("NSMiscData") + { + object = ncore->display; + name = n; + data = d; + } + + void Serialize(Serialize::Data &sdata) const anope_override + { + sdata["nc"] << this->object; + sdata["name"] << this->name; + sdata["data"] << this->data; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data) + { + Anope::string snc, sname, sdata; + + data["nc"] >> snc; + data["name"] >> sname; + data["data"] >> sdata; + + NickCore *nc = NickCore::Find(snc); + if (nc == NULL) + return NULL; + + NSMiscData *d = NULL; + if (obj) + { + d = anope_dynamic_static_cast(obj); + d->object = nc->display; + data["name"] >> d->name; + data["data"] >> d->data; + } + else + { + ExtensibleItem *item = GetItem(sname); + if (item) + d = item->Set(nc, NSMiscData(nc, sname, sdata)); + } + + return d; + } +}; + +static Anope::string GetAttribute(const Anope::string &command) +{ + size_t sp = command.rfind(' '); + if (sp != Anope::string::npos) + return command.substr(sp + 1); + return command; +} + +class CommandNSSetMisc : public Command +{ + public: + CommandNSSetMisc(Module *creator, const Anope::string &cname = "nickserv/set/misc", size_t min = 0) : Command(creator, cname, min, min + 1) + { + this->SetSyntax(_("[\037parameter\037]")); + } + + void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) + { + if (Anope::ReadOnly) + { + source.Reply(READ_ONLY_MODE); + return; + } + + const NickAlias *na = NickAlias::Find(user); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); + return; + } + NickCore *nc = na->nc; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, nc, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + Anope::string scommand = GetAttribute(source.command); + Anope::string key = "ns_set_misc:" + scommand; + ExtensibleItem *item = GetItem(key); + if (item == NULL) + return; + + if (!param.empty()) + { + item->Set(nc, NSMiscData(nc, key, param)); + source.Reply(CHAN_SETTING_CHANGED, scommand.c_str(), nc->display.c_str(), param.c_str()); + } + else + { + item->Unset(nc); + source.Reply(CHAN_SETTING_UNSET, scommand.c_str(), nc->display.c_str()); + } + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, source.nc->display, !params.empty() ? params[0] : ""); + } + + void OnServHelp(CommandSource &source) anope_override + { + if (descriptions.count(source.command)) + { + this->SetDesc(descriptions[source.command]); + Command::OnServHelp(source); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + if (descriptions.count(source.command)) + { + this->SendSyntax(source); + source.Reply("%s", Language::Translate(source.nc, descriptions[source.command].c_str())); + return true; + } + return false; + } +}; + +class CommandNSSASetMisc : public CommandNSSetMisc +{ + public: + CommandNSSASetMisc(Module *creator) : CommandNSSetMisc(creator, "nickserv/saset/misc", 1) + { + this->ClearSyntax(); + this->SetSyntax(_("\037nickname\037 [\037parameter\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, params[0], params.size() > 1 ? params[1] : ""); + } +}; + +class NSSetMisc : public Module +{ + CommandNSSetMisc commandnssetmisc; + CommandNSSASetMisc commandnssasetmisc; + Serialize::Type nsmiscdata_type; + + public: + NSSetMisc(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnssetmisc(this), commandnssasetmisc(this), nsmiscdata_type("NSMiscData", NSMiscData::Unserialize) + { + me = this; + } + + ~NSSetMisc() + { + for (Anope::map *>::iterator it = items.begin(); it != items.end(); ++it) + delete it->second; + } + + void OnReload(Configuration::Conf *conf) anope_override + { + descriptions.clear(); + + for (int i = 0; i < conf->CountBlock("command"); ++i) + { + Configuration::Block *block = conf->GetBlock("command", i); + + const Anope::string &cmd = block->Get("command"); + + if (cmd != "nickserv/set/misc" && cmd != "nickserv/saset/misc") + continue; + + Anope::string cname = block->Get("name"); + Anope::string desc = block->Get("misc_description"); + + if (cname.empty() || desc.empty()) + continue; + + descriptions[cname] = desc; + } + } + + void OnNickInfo(CommandSource &source, NickAlias *na, InfoFormatter &info, bool) anope_override + { + for (Anope::map *>::iterator it = items.begin(); it != items.end(); ++it) + { + ExtensibleItem *e = it->second; + NSMiscData *data = e->Get(na->nc); + + if (data != NULL) + info[e->name.substr(12).replace_all_cs("_", " ")] = data->data; + } + } +}; + +MODULE_INIT(NSSetMisc) diff --git a/modules/commands/ns_status.cpp b/modules/commands/ns_status.cpp new file mode 100644 index 0000000..4df20e8 --- /dev/null +++ b/modules/commands/ns_status.cpp @@ -0,0 +1,87 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandNSStatus : public Command +{ + public: + CommandNSStatus(Module *creator) : Command(creator, "nickserv/status", 0, 16) + { + this->SetDesc(_("Returns the owner status of the given nickname")); + this->SetSyntax(_("[\037nickname\037]")); + this->AllowUnregistered(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &nick = !params.empty() ? params[0] : source.GetNick(); + const NickAlias *na = NickAlias::Find(nick); + spacesepstream sep(nick); + Anope::string nickbuf; + + while (sep.GetToken(nickbuf)) + { + User *u2 = User::Find(nickbuf, true); + if (!u2) /* Nick is not online */ + source.Reply("STATUS %s %d %s", nickbuf.c_str(), 0, ""); + else if (u2->IsIdentified() && na && na->nc == u2->Account()) /* Nick is identified */ + source.Reply("STATUS %s %d %s", nickbuf.c_str(), 3, u2->Account()->display.c_str()); + else if (u2->IsRecognized()) /* Nick is recognised, but NOT identified */ + source.Reply("STATUS %s %d %s", nickbuf.c_str(), 2, u2->Account() ? u2->Account()->display.c_str() : ""); + else if (!na) /* Nick is online, but NOT a registered */ + source.Reply("STATUS %s %d %s", nickbuf.c_str(), 0, ""); + else + /* Nick is not identified for the nick, but they could be logged into an account, + * so we tell the user about it + */ + source.Reply("STATUS %s %d %s", nickbuf.c_str(), 1, u2->Account() ? u2->Account()->display.c_str() : ""); + } + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Returns whether the user using the given nickname is\n" + "recognized as the owner of the nickname. The response has\n" + "this format:\n" + " \n" + " \037nickname\037 \037status-code\037 \037account\037\n" + " \n" + "where \037nickname\037 is the nickname sent with the command,\n" + "\037status-code\037 is one of the following, and \037account\037\n" + "is the account they are logged in as.\n" + " \n" + " 0 - no such user online \002or\002 nickname not registered\n" + " 1 - user not recognized as nickname's owner\n" + " 2 - user recognized as owner via access list only\n" + " 3 - user recognized as owner via password identification\n" + " \n" + "If no nickname is given, your status will be returned.")); + return true; + } +}; + +class NSStatus : public Module +{ + CommandNSStatus commandnsstatus; + + public: + NSStatus(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsstatus(this) + { + + } +}; + +MODULE_INIT(NSStatus) diff --git a/modules/commands/ns_suspend.cpp b/modules/commands/ns_suspend.cpp new file mode 100644 index 0000000..b575b15 --- /dev/null +++ b/modules/commands/ns_suspend.cpp @@ -0,0 +1,288 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/suspend.h" + +static ServiceReference nickserv("NickServService", "NickServ"); + +struct NSSuspendInfo : SuspendInfo, Serializable +{ + NSSuspendInfo(Extensible *) : Serializable("NSSuspendInfo") { } + + void Serialize(Serialize::Data &data) const anope_override + { + data["nick"] << what; + data["by"] << by; + data["reason"] << reason; + data["time"] << when; + data["expires"] << expires; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data) + { + Anope::string snick; + data["nick"] >> snick; + + NSSuspendInfo *si; + if (obj) + si = anope_dynamic_static_cast(obj); + else + { + NickAlias *na = NickAlias::Find(snick); + if (!na) + return NULL; + si = na->nc->Extend("NS_SUSPENDED"); + data["nick"] >> si->what; + } + + data["by"] >> si->by; + data["reason"] >> si->reason; + data["time"] >> si->when; + data["expires"] >> si->expires; + return si; + } +}; + +class CommandNSSuspend : public Command +{ + public: + CommandNSSuspend(Module *creator) : Command(creator, "nickserv/suspend", 2, 3) + { + this->SetDesc(_("Suspend a given nick")); + this->SetSyntax(_("\037nickname\037 [+\037expiry\037] [\037reason\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + + const Anope::string &nick = params[0]; + Anope::string expiry = params[1]; + Anope::string reason = params.size() > 2 ? params[2] : ""; + time_t expiry_secs = Config->GetModule(this->owner)->Get("suspendexpire"); + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + if (expiry[0] != '+') + { + reason = expiry + " " + reason; + reason.trim(); + expiry.clear(); + } + else + { + expiry_secs = Anope::DoTime(expiry); + if (expiry_secs < 0) + { + source.Reply(BAD_EXPIRY_TIME); + return; + } + } + + NickAlias *na = NickAlias::Find(nick); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + return; + } + + if (Config->GetModule("nickserv")->Get("secureadmins", "yes") && na->nc->IsServicesOper()) + { + source.Reply(_("You may not suspend other Services Operators' nicknames.")); + return; + } + + if (na->nc->HasExt("NS_SUSPENDED")) + { + source.Reply(_("\002%s\002 is already suspended."), na->nc->display.c_str()); + return; + } + + NickCore *nc = na->nc; + + NSSuspendInfo *si = nc->Extend("NS_SUSPENDED"); + si->what = nc->display; + si->by = source.GetNick(); + si->reason = reason; + si->when = Anope::CurTime; + si->expires = expiry_secs ? expiry_secs + Anope::CurTime : 0; + + for (unsigned i = 0; i < nc->aliases->size(); ++i) + { + NickAlias *na2 = nc->aliases->at(i); + + if (na2 && *na2->nc == *na->nc) + { + na2->last_quit = reason; + + User *u2 = User::Find(na2->nick, true); + if (u2) + { + u2->Logout(); + if (nickserv) + nickserv->Collide(u2, na2); + } + } + } + + Log(LOG_ADMIN, source, this) << "for " << nick << " (" << (!reason.empty() ? reason : "No reason") << "), expires on " << (expiry_secs ? Anope::strftime(Anope::CurTime + expiry_secs) : "never"); + source.Reply(_("Nick %s is now suspended."), nick.c_str()); + + FOREACH_MOD(OnNickSuspend, (na)); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Suspends a registered nickname, which prevents it from being used\n" + "while keeping all the data for that nick. If an expiry is given\n" + "the nick will be unsuspended after that period of time, else the\n" + "default expiry from the configuration is used.")); + return true; + } +}; + +class CommandNSUnSuspend : public Command +{ + public: + CommandNSUnSuspend(Module *creator) : Command(creator, "nickserv/unsuspend", 1, 1) + { + this->SetDesc(_("Unsuspend a given nick")); + this->SetSyntax(_("\037nickname\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &nick = params[0]; + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + NickAlias *na = NickAlias::Find(nick); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); + return; + } + + if (!na->nc->HasExt("NS_SUSPENDED")) + { + source.Reply(_("Nick %s is not suspended."), na->nick.c_str()); + return; + } + + NSSuspendInfo *si = na->nc->GetExt("NS_SUSPENDED"); + + Log(LOG_ADMIN, source, this) << "for " << na->nick << " which was suspended by " << (!si->by.empty() ? si->by : "(none)") << " for: " << (!si->reason.empty() ? si->reason : "No reason"); + + na->nc->Shrink("NS_SUSPENDED"); + + source.Reply(_("Nick %s is now released."), nick.c_str()); + + FOREACH_MOD(OnNickUnsuspended, (na)); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Unsuspends a nickname which allows it to be used again.")); + return true; + } +}; + +class NSSuspend : public Module +{ + CommandNSSuspend commandnssuspend; + CommandNSUnSuspend commandnsunsuspend; + ExtensibleItem suspend; + Serialize::Type suspend_type; + std::vector show; + + struct trim + { + Anope::string operator()(Anope::string s) const + { + return s.trim(); + } + }; + + bool Show(CommandSource &source, const Anope::string &what) const + { + return source.IsOper() || std::find(show.begin(), show.end(), what) != show.end(); + } + + public: + NSSuspend(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnssuspend(this), commandnsunsuspend(this), suspend(this, "NS_SUSPENDED"), + suspend_type("NSSuspendInfo", NSSuspendInfo::Unserialize) + { + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Anope::string s = conf->GetModule(this)->Get("show"); + commasepstream(s).GetTokens(show); + std::transform(show.begin(), show.end(), show.begin(), trim()); + } + + void OnNickInfo(CommandSource &source, NickAlias *na, InfoFormatter &info, bool show_hidden) anope_override + { + NSSuspendInfo *s = suspend.Get(na->nc); + if (!s) + return; + + if (show_hidden || Show(source, "suspended")) + info[_("Suspended")] = _("This nickname is \002suspended\002."); + if (!s->by.empty() && (show_hidden || Show(source, "by"))) + info[_("Suspended by")] = s->by; + if (!s->reason.empty() && (show_hidden || Show(source, "reason"))) + info[_("Suspend reason")] = s->reason; + if (s->when && (show_hidden || Show(source, "on"))) + info[_("Suspended on")] = Anope::strftime(s->when, source.GetAccount()); + if (s->expires && (show_hidden || Show(source, "expires"))) + info[_("Suspension expires")] = Anope::strftime(s->expires, source.GetAccount()); + } + + void OnPreNickExpire(NickAlias *na, bool &expire) anope_override + { + NSSuspendInfo *s = suspend.Get(na->nc); + if (!s) + return; + + expire = false; + + if (!s->expires) + return; + + if (s->expires < Anope::CurTime) + { + na->last_seen = Anope::CurTime; + suspend.Unset(na->nc); + + Log(LOG_NORMAL, "nickserv/expire", Config->GetClient("NickServ")) << "Expiring suspend for " << na->nick; + } + } + + EventReturn OnNickValidate(User *u, NickAlias *na) anope_override + { + NSSuspendInfo *s = suspend.Get(na->nc); + if (!s) + return EVENT_CONTINUE; + + u->SendMessage(Config->GetClient("NickServ"), NICK_X_SUSPENDED, u->nick.c_str()); + return EVENT_STOP; + } +}; + +MODULE_INIT(NSSuspend) diff --git a/modules/commands/ns_update.cpp b/modules/commands/ns_update.cpp new file mode 100644 index 0000000..0a8d194 --- /dev/null +++ b/modules/commands/ns_update.cpp @@ -0,0 +1,62 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandNSUpdate : public Command +{ + public: + CommandNSUpdate(Module *creator) : Command(creator, "nickserv/update", 0, 0) + { + this->SetDesc(_("Updates your current status, i.e. it checks for new memos")); + this->RequireUser(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + NickAlias *na = NickAlias::Find(u->nick); + + if (na && na->nc == source.GetAccount()) + { + na->last_realname = u->realname; + na->last_seen = Anope::CurTime; + } + + FOREACH_MOD(OnNickUpdate, (u)); + + source.Reply(_("Status updated (memos, vhost, chmodes, flags).")); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Updates your current status, i.e. it checks for new memos,\n" + "sets needed channel modes and updates your vhost and\n" + "your userflags (lastseentime, etc).")); + return true; + } +}; + +class NSUpdate : public Module +{ + CommandNSUpdate commandnsupdate; + + public: + NSUpdate(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandnsupdate(this) + { + + } +}; + +MODULE_INIT(NSUpdate) diff --git a/modules/commands/os_akill.cpp b/modules/commands/os_akill.cpp new file mode 100644 index 0000000..964026b --- /dev/null +++ b/modules/commands/os_akill.cpp @@ -0,0 +1,483 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +static ServiceReference akills("XLineManager", "xlinemanager/sgline"); + +class AkillDelCallback : public NumberList +{ + CommandSource &source; + unsigned deleted; + Command *cmd; + public: + AkillDelCallback(CommandSource &_source, const Anope::string &numlist, Command *c) : NumberList(numlist, true), source(_source), deleted(0), cmd(c) + { + } + + ~AkillDelCallback() + { + if (!deleted) + source.Reply(_("No matching entries on the AKILL list.")); + else if (deleted == 1) + source.Reply(_("Deleted 1 entry from the AKILL list.")); + else + source.Reply(_("Deleted %d entries from the AKILL list."), deleted); + } + + void HandleNumber(unsigned number) anope_override + { + if (!number) + return; + + XLine *x = akills->GetEntry(number - 1); + + if (!x) + return; + + Log(LOG_ADMIN, source, cmd) << "to remove " << x->mask << " from the list"; + + ++deleted; + DoDel(source, x); + } + + static void DoDel(CommandSource &source, XLine *x) + { + akills->DelXLine(x); + } +}; + +class CommandOSAKill : public Command +{ + private: + void DoAdd(CommandSource &source, const std::vector ¶ms) + { + Anope::string expiry, mask; + + if (params.size() < 2) + { + this->OnSyntaxError(source, "ADD"); + return; + } + + spacesepstream sep(params[1]); + sep.GetToken(mask); + + if (mask[0] == '+') + { + expiry = mask; + sep.GetToken(mask); + } + + time_t expires = !expiry.empty() ? Anope::DoTime(expiry) : Config->GetModule("operserv")->Get("autokillexpiry", "30d"); + /* If the expiry given does not contain a final letter, it's in days, + * said the doc. Ah well. + */ + if (!expiry.empty() && isdigit(expiry[expiry.length() - 1])) + expires *= 86400; + /* Do not allow less than a minute expiry time */ + if (expires && expires < 60) + { + source.Reply(BAD_EXPIRY_TIME); + return; + } + else if (expires > 0) + expires += Anope::CurTime; + + if (sep.StreamEnd()) + { + this->OnSyntaxError(source, "ADD"); + return; + } + + Anope::string reason; + if (mask.find('#') != Anope::string::npos) + { + Anope::string remaining = sep.GetRemaining(); + + size_t co = remaining[0] == ':' ? 0 : remaining.rfind(" :"); + if (co == Anope::string::npos) + { + this->OnSyntaxError(source, "ADD"); + return; + } + + if (co != 0) + ++co; + + reason = remaining.substr(co + 1); + mask += " " + remaining.substr(0, co); + mask.trim(); + } + else + reason = sep.GetRemaining(); + + if (mask[0] == '/' && mask[mask.length() - 1] == '/') + { + const Anope::string ®exengine = Config->GetBlock("options")->Get("regexengine"); + + if (regexengine.empty()) + { + source.Reply(_("Regex is disabled.")); + return; + } + + ServiceReference provider("Regex", regexengine); + if (!provider) + { + source.Reply(_("Unable to find regex engine %s."), regexengine.c_str()); + return; + } + + try + { + Anope::string stripped_mask = mask.substr(1, mask.length() - 2); + delete provider->Compile(stripped_mask); + } + catch (const RegexException &ex) + { + source.Reply("%s", ex.GetReason().c_str()); + return; + } + } + + User *targ = User::Find(mask, true); + if (targ) + mask = "*@" + targ->host; + + if (Config->GetModule("operserv")->Get("addakiller", "yes") && !source.GetNick().empty()) + reason = "[" + source.GetNick() + "] " + reason; + + if (mask.find_first_not_of("/~@.*?") == Anope::string::npos) + { + source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); + return; + } + else if (mask.find('@') == Anope::string::npos) + { + source.Reply(BAD_USERHOST_MASK); + return; + } + + XLine *x = new XLine(mask, source.GetNick(), expires, reason); + if (Config->GetModule("operserv")->Get("akillids")) + x->id = XLineManager::GenerateUID(); + + unsigned int affected = 0; + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + if (akills->Check(it->second, x)) + ++affected; + float percent = static_cast(affected) / static_cast(UserListByNick.size()) * 100.0; + + if (percent > 95) + { + source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); + Log(LOG_ADMIN, source, this) << "tried to akill " << percent << "% of the network (" << affected << " users)"; + delete x; + return; + } + + if (!akills->CanAdd(source, mask, expires, reason)) + return; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnAddXLine, MOD_RESULT, (source, x, akills)); + if (MOD_RESULT == EVENT_STOP) + { + delete x; + return; + } + + akills->AddXLine(x); + if (Config->GetModule("operserv")->Get("akillonadd")) + akills->Send(NULL, x); + + source.Reply(_("\002%s\002 added to the AKILL list."), mask.c_str()); + + Log(LOG_ADMIN, source, this) << "on " << mask << " (" << x->reason << "), expires in " << (expires ? Anope::Duration(expires - Anope::CurTime) : "never") << " [affects " << affected << " user(s) (" << percent << "%)]"; + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + } + + void DoDel(CommandSource &source, const std::vector ¶ms) + { + const Anope::string &mask = params.size() > 1 ? params[1] : ""; + + if (mask.empty()) + { + this->OnSyntaxError(source, "DEL"); + return; + } + + if (akills->GetList().empty()) + { + source.Reply(_("AKILL list is empty.")); + return; + } + + if (isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) + { + AkillDelCallback list(source, mask, this); + list.Process(); + } + else + { + XLine *x = akills->HasEntry(mask); + + if (!x) + { + source.Reply(_("\002%s\002 not found on the AKILL list."), mask.c_str()); + return; + } + + do + { + FOREACH_MOD(OnDelXLine, (source, x, akills)); + + Log(LOG_ADMIN, source, this) << "to remove " << x->mask << " from the list"; + source.Reply(_("\002%s\002 deleted from the AKILL list."), x->mask.c_str()); + AkillDelCallback::DoDel(source, x); + } + while ((x = akills->HasEntry(mask))); + + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + return; + } + + void ProcessList(CommandSource &source, const std::vector ¶ms, ListFormatter &list) + { + const Anope::string &mask = params.size() > 1 ? params[1] : ""; + + if (!mask.empty() && isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) + { + class ListCallback : public NumberList + { + CommandSource &source; + ListFormatter &list; + public: + ListCallback(CommandSource &_source, ListFormatter &_list, const Anope::string &numstr) : NumberList(numstr, false), source(_source), list(_list) + { + } + + void HandleNumber(unsigned number) anope_override + { + if (!number) + return; + + const XLine *x = akills->GetEntry(number - 1); + + if (!x) + return; + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(number); + entry["Mask"] = x->mask; + entry["Creator"] = x->by; + entry["Created"] = Anope::strftime(x->created, NULL, true); + entry["Expires"] = Anope::Expires(x->expires, source.nc); + entry["ID"] = x->id; + entry["Reason"] = x->reason; + this->list.AddEntry(entry); + } + } + nl_list(source, list, mask); + nl_list.Process(); + } + else + { + for (unsigned i = 0, end = akills->GetCount(); i < end; ++i) + { + const XLine *x = akills->GetEntry(i); + + if (mask.empty() || mask.equals_ci(x->mask) || mask == x->id || Anope::Match(x->mask, mask, false, true)) + { + ListFormatter::ListEntry entry; + entry["Number"] = stringify(i + 1); + entry["Mask"] = x->mask; + entry["Creator"] = x->by; + entry["Created"] = Anope::strftime(x->created, NULL, true); + entry["Expires"] = Anope::Expires(x->expires, source.nc); + entry["ID"] = x->id; + entry["Reason"] = x->reason; + list.AddEntry(entry); + } + } + } + + if (list.IsEmpty()) + source.Reply(_("No matching entries on the AKILL list.")); + else + { + source.Reply(_("Current AKILL list:")); + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("End of AKILL list.")); + } + } + + void DoList(CommandSource &source, const std::vector ¶ms) + { + if (akills->GetList().empty()) + { + source.Reply(_("AKILL list is empty.")); + return; + } + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Mask")).AddColumn(_("Reason")); + + this->ProcessList(source, params, list); + } + + void DoView(CommandSource &source, const std::vector ¶ms) + { + if (akills->GetList().empty()) + { + source.Reply(_("AKILL list is empty.")); + return; + } + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Mask")).AddColumn(_("Creator")).AddColumn(_("Created")).AddColumn(_("Expires")); + if (Config->GetModule("operserv")->Get("akillids")) + list.AddColumn(_("ID")); + list.AddColumn(_("Reason")); + + this->ProcessList(source, params, list); + } + + void DoClear(CommandSource &source) + { + + for (unsigned i = akills->GetCount(); i > 0; --i) + { + XLine *x = akills->GetEntry(i - 1); + FOREACH_MOD(OnDelXLine, (source, x, akills)); + akills->DelXLine(x); + } + + Log(LOG_ADMIN, source, this) << "to CLEAR the list"; + source.Reply(_("The AKILL list has been cleared.")); + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + } + public: + CommandOSAKill(Module *creator) : Command(creator, "operserv/akill", 1, 2) + { + this->SetDesc(_("Manipulate the AKILL list")); + this->SetSyntax(_("ADD [+\037expiry\037] \037mask\037 \037reason\037")); + this->SetSyntax(_("DEL {\037mask\037 | \037entry-num\037 | \037list\037 | \037id\037}")); + this->SetSyntax(_("LIST [\037mask\037 | \037list\037 | \037id\037]")); + this->SetSyntax(_("VIEW [\037mask\037 | \037list\037 | \037id\037]")); + this->SetSyntax("CLEAR"); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[0]; + + if (!akills) + return; + + if (cmd.equals_ci("ADD")) + return this->DoAdd(source, params); + else if (cmd.equals_ci("DEL")) + return this->DoDel(source, params); + else if (cmd.equals_ci("LIST")) + return this->DoList(source, params); + else if (cmd.equals_ci("VIEW")) + return this->DoView(source, params); + else if (cmd.equals_ci("CLEAR")) + return this->DoClear(source); + else + this->OnSyntaxError(source, ""); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows Services Operators to manipulate the AKILL list. If\n" + "a user matching an AKILL mask attempts to connect, Services\n" + "will issue a KILL for that user and, on supported server\n" + "types, will instruct all servers to add a ban for the mask\n" + "which the user matched.\n" + " \n" + "\002AKILL ADD\002 adds the given mask to the AKILL\n" + "list for the given reason, which \002must\002 be given.\n" + "Mask should be in the format of nick!user@host#real name,\n" + "though all that is required is user@host. If a real name is specified,\n" + "the reason must be prepended with a :.\n" + "\037expiry\037 is specified as an integer followed by one of \037d\037\n" + "(days), \037h\037 (hours), or \037m\037 (minutes). Combinations (such as\n" + "\0371h30m\037) are not permitted. If a unit specifier is not\n" + "included, the default is days (so \037+30\037 by itself means 30\n" + "days). To add an AKILL which does not expire, use \037+0\037. If the\n" + "usermask to be added starts with a \037+\037, an expiry time must\n" + "be given, even if it is the same as the default. The\n" + "current AKILL default expiry time can be found with the\n" + "\002STATS AKILL\002 command.")); + const Anope::string ®exengine = Config->GetBlock("options")->Get("regexengine"); + if (!regexengine.empty()) + { + source.Reply(" "); + source.Reply(_("Regex matches are also supported using the %s engine.\n" + "Enclose your mask in // if this is desired."), regexengine.c_str()); + } + source.Reply(_( + " \n" + "The \002AKILL DEL\002 command removes the given mask from the\n" + "AKILL list if it is present. If a list of entry numbers is\n" + "given, those entries are deleted. (See the example for LIST\n" + "below.)\n" + " \n" + "The \002AKILL LIST\002 command displays the AKILL list.\n" + "If a wildcard mask is given, only those entries matching the\n" + "mask are displayed. If a list of entry numbers is given,\n" + "only those entries are shown; for example:\n" + " \002AKILL LIST 2-5,7-9\002\n" + " Lists AKILL entries numbered 2 through 5 and 7\n" + " through 9.\n" + " \n" + "\002AKILL VIEW\002 is a more verbose version of \002AKILL LIST\002, and\n" + "will show who added an AKILL, the date it was added, and when\n" + "it expires, as well as the user@host/ip mask and reason.\n" + " \n" + "\002AKILL CLEAR\002 clears all entries of the AKILL list.")); + return true; + } +}; + +class OSAKill : public Module +{ + CommandOSAKill commandosakill; + + public: + OSAKill(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosakill(this) + { + + } +}; + +MODULE_INIT(OSAKill) diff --git a/modules/commands/os_chankill.cpp b/modules/commands/os_chankill.cpp new file mode 100644 index 0000000..e94d064 --- /dev/null +++ b/modules/commands/os_chankill.cpp @@ -0,0 +1,119 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +static ServiceReference akills("XLineManager", "xlinemanager/sgline"); + +class CommandOSChanKill : public Command +{ + public: + CommandOSChanKill(Module *creator) : Command(creator, "operserv/chankill", 2, 3) + { + this->SetDesc(_("AKILL all users on a specific channel")); + this->SetSyntax(_("[+\037expiry\037] \037channel\037 \037reason\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!akills) + return; + + Anope::string expiry, channel; + unsigned last_param = 1; + Channel *c; + + channel = params[0]; + if (!channel.empty() && channel[0] == '+') + { + expiry = channel; + channel = params[1]; + last_param = 2; + } + + time_t expires = !expiry.empty() ? Anope::DoTime(expiry) : Config->GetModule("operserv")->Get("autokillexpiry", "30d"); + if (!expiry.empty() && isdigit(expiry[expiry.length() - 1])) + expires *= 86400; + if (expires && expires < 60) + { + source.Reply(BAD_EXPIRY_TIME); + return; + } + else if (expires > 0) + expires += Anope::CurTime; + + if (params.size() <= last_param) + { + this->OnSyntaxError(source, ""); + return; + } + + Anope::string reason = params[last_param]; + if (params.size() > last_param + 1) + reason += params[last_param + 1]; + if (!reason.empty()) + { + Anope::string realreason; + if (Config->GetModule("operserv")->Get("addakiller") && !source.GetNick().empty()) + realreason = "[" + source.GetNick() + "] " + reason; + else + realreason = reason; + + if ((c = Channel::Find(channel))) + { + for (Channel::ChanUserList::iterator it = c->users.begin(), it_end = c->users.end(); it != it_end; ++it) + { + ChanUserContainer *uc = it->second; + + if (uc->user->server == Me || uc->user->HasMode("OPER")) + continue; + + Anope::string akillmask = "*@" + uc->user->host; + if (akills->HasEntry(akillmask)) + continue; + + XLine *x = new XLine(akillmask, source.GetNick(), expires, realreason, XLineManager::GenerateUID()); + akills->AddXLine(x); + akills->OnMatch(uc->user, x); + } + + Log(LOG_ADMIN, source, this) << "on " << c->name << " (" << realreason << ")"; + } + else + source.Reply(CHAN_X_NOT_IN_USE, channel.c_str()); + } + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Puts an AKILL for every nick on the specified channel. It\n" + "uses the entire real ident@host for every nick, and\n" + "then enforces the AKILL.")); + return true; + } +}; + +class OSChanKill : public Module +{ + CommandOSChanKill commandoschankill; + + public: + OSChanKill(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandoschankill(this) + { + + } +}; + +MODULE_INIT(OSChanKill) diff --git a/modules/commands/os_config.cpp b/modules/commands/os_config.cpp new file mode 100644 index 0000000..3f01c79 --- /dev/null +++ b/modules/commands/os_config.cpp @@ -0,0 +1,150 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSConfig : public Command +{ + public: + CommandOSConfig(Module *creator) : Command(creator, "operserv/config", 1, 4) + { + this->SetDesc(_("View and change configuration file settings")); + this->SetSyntax(_("{\037MODIFY\037|\037VIEW\037} [\037block name\037 \037item name\037 \037item value\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &what = params[0]; + + if (what.equals_ci("MODIFY") && params.size() > 3) + { + if (!source.HasPriv("operserv/config")) + { + source.Reply(ACCESS_DENIED); + return; + } + + Configuration::Block *block = Config->GetBlock(params[1]); + if (!block) + block = Config->GetModule(params[1]); + + if (!block) + { + source.Reply(_("There is no such configuration block %s."), params[1].c_str()); + return; + } + + block->Set(params[2], params[3]); + + Log(LOG_ADMIN, source, this) << "to change the configuration value of " << params[1] << ":" << params[2] << " to " << params[3]; + source.Reply(_("Value of %s:%s changed to %s"), params[1].c_str(), params[2].c_str(), params[3].c_str()); + } + else if (what.equals_ci("VIEW")) + { + /* Blocks we should show */ + const Anope::string show_blocks[] = { "serverinfo", "networkinfo", "options", "" }; + + Log(LOG_ADMIN, source, this) << "VIEW"; + + for (unsigned i = 0; !show_blocks[i].empty(); ++i) + { + Configuration::Block *block = Config->GetBlock(show_blocks[i]); + const Configuration::Block::item_map *items = block->GetItems(); + + if (!items) + continue; + + ListFormatter lflist(source.GetAccount()); + lflist.AddColumn(_("Name")).AddColumn(_("Value")); + + for (Configuration::Block::item_map::const_iterator it = items->begin(), it_end = items->end(); it != it_end; ++it) + { + ListFormatter::ListEntry entry; + entry["Name"] = it->first; + entry["Value"] = it->second; + lflist.AddEntry(entry); + } + + std::vector replies; + lflist.Process(replies); + + source.Reply(_("%s settings:"), block->GetName().c_str()); + + for (unsigned j = 0; j < replies.size(); ++j) + source.Reply(replies[j]); + + source.Reply(" "); + } + + ListFormatter lflist(source.GetAccount()); + lflist.AddColumn(_("Module Name")).AddColumn(_("Name")).AddColumn(_("Value")); + + for (int i = 0; i < Config->CountBlock("module"); ++i) + { + Configuration::Block *block = Config->GetBlock("module", i); + const Configuration::Block::item_map *items = block->GetItems(); + + if (!items || items->size() <= 1) + continue; + + ListFormatter::ListEntry entry; + entry["Module Name"] = block->Get("name"); + + for (Configuration::Block::item_map::const_iterator it = items->begin(), it_end = items->end(); it != it_end; ++it) + { + entry["Name"] = it->first; + entry["Value"] = it->second; + lflist.AddEntry(entry); + } + } + + std::vector replies; + lflist.Process(replies); + + source.Reply(_("Module settings:")); + + for (unsigned j = 0; j < replies.size(); ++j) + source.Reply(replies[j]); + + source.Reply(_("End of configuration.")); + } + else + this->OnSyntaxError(source, what); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows you to change and view configuration settings.\n" + "Settings changed by this command are temporary and will not be reflected\n" + "back into the configuration file, and will be lost if Anope is shut down,\n" + "restarted, or the configuration is reloaded.\n" + " \n" + "Example:\n" + " \002MODIFY nickserv forcemail no\002")); + return true; + } +}; + +class OSConfig : public Module +{ + CommandOSConfig commandosconfig; + + public: + OSConfig(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosconfig(this) + { + + } +}; + +MODULE_INIT(OSConfig) diff --git a/modules/commands/os_defcon.cpp b/modules/commands/os_defcon.cpp new file mode 100644 index 0000000..767a835 --- /dev/null +++ b/modules/commands/os_defcon.cpp @@ -0,0 +1,603 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/os_session.h" + +enum DefconLevel +{ + DEFCON_NO_NEW_CHANNELS, + DEFCON_NO_NEW_NICKS, + DEFCON_NO_MLOCK_CHANGE, + DEFCON_FORCE_CHAN_MODES, + DEFCON_REDUCE_SESSION, + DEFCON_NO_NEW_CLIENTS, + DEFCON_OPER_ONLY, + DEFCON_SILENT_OPER_ONLY, + DEFCON_AKILL_NEW_CLIENTS, + DEFCON_NO_NEW_MEMOS +}; + +bool DefConModesSet = false; + +struct DefconConfig +{ + std::vector > DefCon; + std::set DefConModesOn, DefConModesOff; + std::map DefConModesOnParams; + + int defaultlevel, sessionlimit; + Anope::string chanmodes, message, offmessage, akillreason; + std::vector defcons; + time_t akillexpire, timeout; + bool globalondefcon; + + unsigned max_session_kill; + time_t session_autokill_expiry; + Anope::string sle_reason, sle_detailsloc; + + DefconConfig() + { + this->DefCon.resize(6); + this->defcons.resize(5); + } + + bool Check(DefconLevel level) + { + return this->Check(this->defaultlevel, level); + } + + bool Check(int dlevel, DefconLevel level) + { + return this->DefCon[dlevel].test(level); + } + + void Add(int dlevel, DefconLevel level) + { + this->DefCon[dlevel][level] = true; + } + + void Del(int dlevel, DefconLevel level) + { + this->DefCon[dlevel][level] = false; + } + + bool SetDefConParam(const Anope::string &name, const Anope::string &buf) + { + return DefConModesOnParams.insert(std::make_pair(name, buf)).second; + } + + void UnsetDefConParam(const Anope::string &name) + { + DefConModesOnParams.erase(name); + } + + bool GetDefConParam(const Anope::string &name, Anope::string &buf) + { + std::map::iterator it = DefConModesOnParams.find(name); + + buf.clear(); + + if (it != DefConModesOnParams.end()) + { + buf = it->second; + return true; + } + + return false; + } +}; + +static DefconConfig DConfig; + +static void runDefCon(); +static Anope::string defconReverseModes(const Anope::string &modes); + +static ServiceReference GlobalService("GlobalService", "Global"); + +static Timer *timeout; + +class DefConTimeout : public Timer +{ + int level; + + public: + DefConTimeout(Module *mod, int newlevel) : Timer(mod, DConfig.timeout), level(newlevel) + { + timeout = this; + } + + ~DefConTimeout() + { + timeout = NULL; + } + + void Tick(time_t) anope_override + { + if (DConfig.defaultlevel != level) + { + DConfig.defaultlevel = level; + FOREACH_MOD(OnDefconLevel, (level)); + Log(Config->GetClient("OperServ"), "operserv/defcon") << "Defcon level timeout, returning to level " << level; + + if (DConfig.globalondefcon) + { + if (!DConfig.offmessage.empty()) + GlobalService->SendGlobal(NULL, "", DConfig.offmessage); + else + GlobalService->SendGlobal(NULL, "", Anope::printf(Language::Translate(_("The Defcon level is now at: \002%d\002")), DConfig.defaultlevel)); + + if (!DConfig.message.empty()) + GlobalService->SendGlobal(NULL, "", DConfig.message); + } + + runDefCon(); + } + } +}; + +class CommandOSDefcon : public Command +{ + void SendLevels(CommandSource &source) + { + if (DConfig.Check(DEFCON_NO_NEW_CHANNELS)) + source.Reply(_("* No new channel registrations")); + if (DConfig.Check(DEFCON_NO_NEW_NICKS)) + source.Reply(_("* No new nick registrations")); + if (DConfig.Check(DEFCON_NO_MLOCK_CHANGE)) + source.Reply(_("* No mode lock changes")); + if (DConfig.Check(DEFCON_FORCE_CHAN_MODES) && !DConfig.chanmodes.empty()) + source.Reply(_("* Force channel modes (%s) to be set on all channels"), DConfig.chanmodes.c_str()); + if (DConfig.Check(DEFCON_REDUCE_SESSION)) + source.Reply(_("* Use the reduced session limit of %d"), DConfig.sessionlimit); + if (DConfig.Check(DEFCON_NO_NEW_CLIENTS)) + source.Reply(_("* Kill any new clients connecting")); + if (DConfig.Check(DEFCON_OPER_ONLY)) + source.Reply(_("* Ignore non-opers with a message")); + if (DConfig.Check(DEFCON_SILENT_OPER_ONLY)) + source.Reply(_("* Silently ignore non-opers")); + if (DConfig.Check(DEFCON_AKILL_NEW_CLIENTS)) + source.Reply(_("* AKILL any new clients connecting")); + if (DConfig.Check(DEFCON_NO_NEW_MEMOS)) + source.Reply(_("* No new memos sent")); + } + + public: + CommandOSDefcon(Module *creator) : Command(creator, "operserv/defcon", 1, 1) + { + this->SetDesc(_("Manipulate the DefCon system")); + this->SetSyntax(_("[\0021\002|\0022\002|\0023\002|\0024\002|\0025\002]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &lvl = params[0]; + + if (lvl.empty()) + { + source.Reply(_("Services are now at DEFCON \002%d\002."), DConfig.defaultlevel); + this->SendLevels(source); + return; + } + + int newLevel = 0; + try + { + newLevel = convertTo(lvl); + } + catch (const ConvertException &) { } + + if (newLevel < 1 || newLevel > 5) + { + this->OnSyntaxError(source, ""); + return; + } + + DConfig.defaultlevel = newLevel; + + FOREACH_MOD(OnDefconLevel, (newLevel)); + + delete timeout; + + if (DConfig.timeout) + timeout = new DefConTimeout(this->module, 5); + + source.Reply(_("Services are now at DEFCON \002%d\002."), DConfig.defaultlevel); + this->SendLevels(source); + Log(LOG_ADMIN, source, this) << "to change defcon level to " << newLevel; + + /* Global notice the user what is happening. Also any Message that + the Admin would like to add. Set in config file. */ + if (DConfig.globalondefcon) + { + if (DConfig.defaultlevel == 5 && !DConfig.offmessage.empty()) + GlobalService->SendGlobal(NULL, "", DConfig.offmessage); + else if (DConfig.defaultlevel != 5) + { + GlobalService->SendGlobal(NULL, "", Anope::printf(_("The Defcon level is now at: \002%d\002"), DConfig.defaultlevel)); + if (!DConfig.message.empty()) + GlobalService->SendGlobal(NULL, "", DConfig.message); + } + } + + /* Run any defcon functions, e.g. FORCE CHAN MODE */ + runDefCon(); + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("The defcon system can be used to implement a pre-defined\n" + "set of restrictions to services useful during an attempted\n" + "attack on the network.")); + return true; + } +}; + +class OSDefcon : public Module +{ + ServiceReference session_service; + ServiceReference akills; + CommandOSDefcon commandosdefcon; + + void ParseModeString() + { + int add = -1; /* 1 if adding, 0 if deleting, -1 if neither */ + unsigned char mode; + ChannelMode *cm; + ChannelModeParam *cmp; + Anope::string modes, param; + + spacesepstream ss(DConfig.chanmodes); + + DConfig.DefConModesOn.clear(); + DConfig.DefConModesOff.clear(); + ss.GetToken(modes); + + /* Loop while there are modes to set */ + for (unsigned i = 0, end = modes.length(); i < end; ++i) + { + mode = modes[i]; + + switch (mode) + { + case '+': + add = 1; + continue; + case '-': + add = 0; + continue; + default: + if (add < 0) + continue; + } + + if ((cm = ModeManager::FindChannelModeByChar(mode))) + { + if (cm->type == MODE_STATUS || cm->type == MODE_LIST) + { + Log(this) << "DefConChanModes mode character '" << mode << "' cannot be locked"; + continue; + } + else if (add) + { + DConfig.DefConModesOn.insert(cm->name); + DConfig.DefConModesOff.erase(cm->name); + + if (cm->type == MODE_PARAM) + { + cmp = anope_dynamic_static_cast(cm); + + if (!ss.GetToken(param)) + { + Log(this) << "DefConChanModes mode character '" << mode << "' has no parameter while one is expected"; + continue; + } + + if (!cmp->IsValid(param)) + continue; + + DConfig.SetDefConParam(cmp->name, param); + } + } + else if (DConfig.DefConModesOn.count(cm->name)) + { + DConfig.DefConModesOn.erase(cm->name); + + if (cm->type == MODE_PARAM) + DConfig.UnsetDefConParam(cm->name); + } + } + } + + /* We can't mlock +L if +l is not mlocked as well. */ + if ((cm = ModeManager::FindChannelModeByName("REDIRECT")) && DConfig.DefConModesOn.count(cm->name) && !DConfig.DefConModesOn.count("LIMIT")) + { + DConfig.DefConModesOn.erase("REDIRECT"); + + Log(this) << "DefConChanModes must lock mode +l as well to lock mode +L"; + } + } + + public: + OSDefcon(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), session_service("SessionService", "session"), akills("XLineManager", "xlinemanager/sgline"), commandosdefcon(this) + { + + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *block = conf->GetModule(this); + DefconConfig dconfig; + + dconfig.defaultlevel = block->Get("defaultlevel"); + dconfig.defcons[4] = block->Get("level4"); + dconfig.defcons[3] = block->Get("level3"); + dconfig.defcons[2] = block->Get("level2"); + dconfig.defcons[1] = block->Get("level1"); + dconfig.sessionlimit = block->Get("sessionlimit"); + dconfig.akillreason = block->Get("akillreason"); + dconfig.akillexpire = block->Get("akillexpire"); + dconfig.chanmodes = block->Get("chanmodes"); + dconfig.timeout = block->Get("timeout"); + dconfig.globalondefcon = block->Get("globalondefcon"); + dconfig.message = block->Get("message"); + dconfig.offmessage = block->Get("offmessage"); + + block = conf->GetModule("os_session"); + + dconfig.max_session_kill = block->Get("maxsessionkill"); + dconfig.session_autokill_expiry = block->Get("sessionautokillexpiry"); + dconfig.sle_reason = block->Get("sessionlimitexceeded"); + dconfig.sle_detailsloc = block->Get("sessionlimitdetailsloc"); + + if (dconfig.defaultlevel < 1 || dconfig.defaultlevel > 5) + throw ConfigException("The value for must be between 1 and 5"); + else if (dconfig.akillexpire <= 0) + throw ConfigException("The value for must be greater than zero!"); + + for (unsigned level = 1; level < 5; ++level) + { + spacesepstream operations(dconfig.defcons[level]); + Anope::string operation; + while (operations.GetToken(operation)) + { + if (operation.equals_ci("nonewchannels")) + dconfig.Add(level, DEFCON_NO_NEW_CHANNELS); + else if (operation.equals_ci("nonewnicks")) + dconfig.Add(level, DEFCON_NO_NEW_NICKS); + else if (operation.equals_ci("nomlockchanges")) + dconfig.Add(level, DEFCON_NO_MLOCK_CHANGE); + else if (operation.equals_ci("forcechanmodes")) + dconfig.Add(level, DEFCON_FORCE_CHAN_MODES); + else if (operation.equals_ci("reducedsessions")) + dconfig.Add(level, DEFCON_REDUCE_SESSION); + else if (operation.equals_ci("nonewclients")) + dconfig.Add(level, DEFCON_NO_NEW_CLIENTS); + else if (operation.equals_ci("operonly")) + dconfig.Add(level, DEFCON_OPER_ONLY); + else if (operation.equals_ci("silentoperonly")) + dconfig.Add(level, DEFCON_SILENT_OPER_ONLY); + else if (operation.equals_ci("akillnewclients")) + dconfig.Add(level, DEFCON_AKILL_NEW_CLIENTS); + else if (operation.equals_ci("nonewmemos")) + dconfig.Add(level, DEFCON_NO_NEW_MEMOS); + } + + if (dconfig.Check(level, DEFCON_REDUCE_SESSION) && dconfig.sessionlimit <= 0) + throw ConfigException("The value for must be greater than zero!"); + else if (dconfig.Check(level, DEFCON_AKILL_NEW_CLIENTS) && dconfig.akillreason.empty()) + throw ConfigException("The value for must not be empty!"); + else if (dconfig.Check(level, DEFCON_FORCE_CHAN_MODES) && dconfig.chanmodes.empty()) + throw ConfigException("The value for must not be empty!"); + } + + DConfig = dconfig; + this->ParseModeString(); + } + + EventReturn OnChannelModeSet(Channel *c, MessageSource &source, ChannelMode *mode, const Anope::string ¶m) anope_override + { + if (DConfig.Check(DEFCON_FORCE_CHAN_MODES) && DConfig.DefConModesOff.count(mode->name) && source.GetUser() && !source.GetBot()) + { + c->RemoveMode(Config->GetClient("OperServ"), mode, param); + + return EVENT_STOP; + } + + return EVENT_CONTINUE; + } + + EventReturn OnChannelModeUnset(Channel *c, MessageSource &source, ChannelMode *mode, const Anope::string &) anope_override + { + if (DConfig.Check(DEFCON_FORCE_CHAN_MODES) && DConfig.DefConModesOn.count(mode->name) && source.GetUser() && !source.GetBot()) + { + Anope::string param; + + if (DConfig.GetDefConParam(mode->name, param)) + c->SetMode(Config->GetClient("OperServ"), mode, param); + else + c->SetMode(Config->GetClient("OperServ"), mode); + + return EVENT_STOP; + + } + + return EVENT_CONTINUE; + } + + EventReturn OnPreCommand(CommandSource &source, Command *command, std::vector ¶ms) anope_override + { + if (DConfig.Check(DEFCON_OPER_ONLY) && !source.IsOper()) + { + source.Reply(_("Services are in DefCon mode, please try again later.")); + return EVENT_STOP; + } + else if (DConfig.Check(DEFCON_SILENT_OPER_ONLY) && !source.IsOper()) + { + return EVENT_STOP; + } + else if (command->name == "nickserv/register" || command->name == "nickserv/group") + { + if (DConfig.Check(DEFCON_NO_NEW_NICKS)) + { + source.Reply(_("Services are in DefCon mode, please try again later.")); + return EVENT_STOP; + } + } + else if (command->name == "chanserv/mode" && params.size() > 1 && params[1].equals_ci("LOCK")) + { + if (DConfig.Check(DEFCON_NO_MLOCK_CHANGE)) + { + source.Reply(_("Services are in DefCon mode, please try again later.")); + return EVENT_STOP; + } + } + else if (command->name == "chanserv/register") + { + if (DConfig.Check(DEFCON_NO_NEW_CHANNELS)) + { + source.Reply(_("Services are in DefCon mode, please try again later.")); + return EVENT_STOP; + } + } + else if (command->name == "memoserv/send") + { + if (DConfig.Check(DEFCON_NO_NEW_MEMOS)) + { + source.Reply(_("Services are in DefCon mode, please try again later.")); + return EVENT_STOP; + } + } + + return EVENT_CONTINUE; + } + + void OnUserConnect(User *u, bool &exempt) anope_override + { + if (exempt || u->Quitting() || !u->server->IsSynced() || u->server->IsULined()) + return; + + BotInfo *OperServ = Config->GetClient("OperServ"); + if (DConfig.Check(DEFCON_AKILL_NEW_CLIENTS) && akills) + { + Log(OperServ, "operserv/defcon") << "DEFCON: adding akill for *@" << u->host; + XLine x("*@" + u->host, OperServ ? OperServ->nick : "defcon", Anope::CurTime + DConfig.akillexpire, DConfig.akillreason, XLineManager::GenerateUID()); + akills->Send(NULL, &x); + } + + if (DConfig.Check(DEFCON_NO_NEW_CLIENTS) || DConfig.Check(DEFCON_AKILL_NEW_CLIENTS)) + { + u->Kill(OperServ, DConfig.akillreason); + return; + } + + if (DConfig.sessionlimit <= 0 || !session_service) + return; + + Session *session = session_service->FindSession(u->ip.addr()); + Exception *exception = session_service->FindException(u); + + if (DConfig.Check(DEFCON_REDUCE_SESSION) && !exception) + { + if (session && session->count > static_cast(DConfig.sessionlimit)) + { + if (!DConfig.sle_reason.empty()) + { + Anope::string message = DConfig.sle_reason.replace_all_cs("%IP%", u->ip.addr()); + u->SendMessage(OperServ, message); + } + if (!DConfig.sle_detailsloc.empty()) + u->SendMessage(OperServ, DConfig.sle_detailsloc); + + ++session->hits; + if (akills && DConfig.max_session_kill && session->hits >= DConfig.max_session_kill) + { + XLine x("*@" + session->addr.mask(), OperServ ? OperServ->nick : "", Anope::CurTime + DConfig.session_autokill_expiry, "Defcon session limit exceeded", XLineManager::GenerateUID()); + akills->Send(NULL, &x); + Log(OperServ, "akill/defcon") << "[DEFCON] Added a temporary AKILL for \002*@" << session->addr.mask() << "\002 due to excessive connections"; + } + else + { + u->Kill(OperServ, "Defcon session limit exceeded"); + } + } + } + } + + void OnChannelModeAdd(ChannelMode *cm) anope_override + { + if (DConfig.chanmodes.find(cm->mchar) != Anope::string::npos) + this->ParseModeString(); + } + + void OnChannelSync(Channel *c) anope_override + { + if (DConfig.Check(DEFCON_FORCE_CHAN_MODES)) + c->SetModes(Config->GetClient("OperServ"), false, "%s", DConfig.chanmodes.c_str()); + } +}; + +static void runDefCon() +{ + BotInfo *OperServ = Config->GetClient("OperServ"); + if (DConfig.Check(DEFCON_FORCE_CHAN_MODES)) + { + if (!DConfig.chanmodes.empty() && !DefConModesSet) + { + if (DConfig.chanmodes[0] == '+' || DConfig.chanmodes[0] == '-') + { + Log(OperServ, "operserv/defcon") << "DEFCON: setting " << DConfig.chanmodes << " on all channels"; + DefConModesSet = true; + for (channel_map::const_iterator it = ChannelList.begin(), it_end = ChannelList.end(); it != it_end; ++it) + it->second->SetModes(OperServ, false, "%s", DConfig.chanmodes.c_str()); + } + } + } + else + { + if (!DConfig.chanmodes.empty() && DefConModesSet) + { + if (DConfig.chanmodes[0] == '+' || DConfig.chanmodes[0] == '-') + { + DefConModesSet = false; + Anope::string newmodes = defconReverseModes(DConfig.chanmodes); + if (!newmodes.empty()) + { + Log(OperServ, "operserv/defcon") << "DEFCON: setting " << newmodes << " on all channels"; + for (channel_map::const_iterator it = ChannelList.begin(), it_end = ChannelList.end(); it != it_end; ++it) + it->second->SetModes(OperServ, true, "%s", newmodes.c_str()); + } + } + } + } +} + +static Anope::string defconReverseModes(const Anope::string &modes) +{ + if (modes.empty()) + return ""; + Anope::string newmodes; + for (unsigned i = 0, end = modes.length(); i < end; ++i) + { + if (modes[i] == '+') + newmodes += '-'; + else if (modes[i] == '-') + newmodes += '+'; + else + newmodes += modes[i]; + } + return newmodes; +} + +MODULE_INIT(OSDefcon) diff --git a/modules/commands/os_dns.cpp b/modules/commands/os_dns.cpp new file mode 100644 index 0000000..ef29a89 --- /dev/null +++ b/modules/commands/os_dns.cpp @@ -0,0 +1,948 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/dns.h" + +static ServiceReference dnsmanager("DNS::Manager", "dns/manager"); + +struct DNSZone; +class DNSServer; + +static Serialize::Checker > zones("DNSZone"); +static Serialize::Checker > dns_servers("DNSServer"); + +static std::map > server_quit_times; + +struct DNSZone : Serializable +{ + Anope::string name; + std::set servers; + + DNSZone(const Anope::string &n) : Serializable("DNSZone"), name(n) + { + zones->push_back(this); + } + + ~DNSZone() + { + std::vector::iterator it = std::find(zones->begin(), zones->end(), this); + if (it != zones->end()) + zones->erase(it); + } + + void Serialize(Serialize::Data &data) const anope_override + { + data["name"] << name; + unsigned count = 0; + for (std::set::iterator it = servers.begin(), it_end = servers.end(); it != it_end; ++it) + data["server" + stringify(count++)] << *it; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data) + { + DNSZone *zone; + Anope::string zone_name; + + data["name"] >> zone_name; + + if (obj) + { + zone = anope_dynamic_static_cast(obj); + data["name"] >> zone->name; + } + else + zone = new DNSZone(zone_name); + + zone->servers.clear(); + for (unsigned count = 0; true; ++count) + { + Anope::string server_str; + data["server" + stringify(count)] >> server_str; + if (server_str.empty()) + break; + zone->servers.insert(server_str); + } + + return zone; + } + + static DNSZone *Find(const Anope::string &name) + { + for (unsigned i = 0; i < zones->size(); ++i) + if (zones->at(i)->name.equals_ci(name)) + { + DNSZone *z = zones->at(i); + z->QueueUpdate(); + return z; + } + return NULL; + } +}; + +class DNSServer : public Serializable +{ + Anope::string server_name; + std::vector ips; + unsigned limit; + /* wants to be in the pool */ + bool pooled; + /* is actually in the pool */ + bool active; + + public: + std::set zones; + time_t repool; + + DNSServer(const Anope::string &sn) : Serializable("DNSServer"), server_name(sn), limit(0), pooled(false), active(false), repool(0) + { + dns_servers->push_back(this); + } + + ~DNSServer() + { + std::vector::iterator it = std::find(dns_servers->begin(), dns_servers->end(), this); + if (it != dns_servers->end()) + dns_servers->erase(it); + } + + const Anope::string &GetName() const { return server_name; } + std::vector &GetIPs() { return ips; } + unsigned GetLimit() const { return limit; } + void SetLimit(unsigned l) { limit = l; } + + bool Pooled() const { return pooled; } + void Pool(bool p) + { + if (!p) + this->SetActive(p); + pooled = p; + } + + bool Active() const { return pooled && active; } + void SetActive(bool p) + { + if (p) + this->Pool(p); + active = p; + + if (dnsmanager) + { + dnsmanager->UpdateSerial(); + for (std::set::iterator it = zones.begin(), it_end = zones.end(); it != it_end; ++it) + dnsmanager->Notify(*it); + } + } + + void Serialize(Serialize::Data &data) const anope_override + { + data["server_name"] << server_name; + for (unsigned i = 0; i < ips.size(); ++i) + data["ip" + stringify(i)] << ips[i]; + data["limit"] << limit; + data["pooled"] << pooled; + unsigned count = 0; + for (std::set::iterator it = zones.begin(), it_end = zones.end(); it != it_end; ++it) + data["zone" + stringify(count++)] << *it; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data) + { + DNSServer *req; + Anope::string server_name; + + data["server_name"] >> server_name; + + if (obj) + { + req = anope_dynamic_static_cast(obj); + req->server_name = server_name; + } + else + req = new DNSServer(server_name); + + for (unsigned i = 0; true; ++i) + { + Anope::string ip_str; + data["ip" + stringify(i)] >> ip_str; + if (ip_str.empty()) + break; + req->ips.push_back(ip_str); + } + + data["limit"] >> req->limit; + data["pooled"] >> req->pooled; + + req->zones.clear(); + for (unsigned i = 0; true; ++i) + { + Anope::string zone_str; + data["zone" + stringify(i)] >> zone_str; + if (zone_str.empty()) + break; + req->zones.insert(zone_str); + } + + return req; + } + + static DNSServer *Find(const Anope::string &s) + { + for (unsigned i = 0; i < dns_servers->size(); ++i) + if (dns_servers->at(i)->GetName().equals_ci(s)) + { + DNSServer *serv = dns_servers->at(i); + serv->QueueUpdate(); + return serv; + } + return NULL; + } +}; + +class CommandOSDNS : public Command +{ + void DisplayPoolState(CommandSource &source) + { + if (dns_servers->empty()) + { + source.Reply(_("There are no configured servers.")); + return; + } + + ListFormatter lf(source.GetAccount()); + lf.AddColumn(_("Server")).AddColumn(_("IP")).AddColumn(_("Limit")).AddColumn(_("State")); + for (unsigned i = 0; i < dns_servers->size(); ++i) + { + DNSServer *s = dns_servers->at(i); + Server *srv = Server::Find(s->GetName(), true); + + ListFormatter::ListEntry entry; + entry["Server"] = s->GetName(); + entry["Limit"] = s->GetLimit() ? stringify(s->GetLimit()) : Language::Translate(source.GetAccount(), _("None")); + + Anope::string ip_str; + for (unsigned j = 0; j < s->GetIPs().size(); ++j) + ip_str += s->GetIPs()[j] + " "; + ip_str.trim(); + if (ip_str.empty()) + ip_str = "None"; + entry["IP"] = ip_str; + + if (s->Active()) + entry["State"] = Language::Translate(source.GetAccount(), _("Pooled/Active")); + else if (s->Pooled()) + entry["State"] = Language::Translate(source.GetAccount(), _("Pooled/Not Active")); + else + entry["State"] = Language::Translate(source.GetAccount(), _("Unpooled")); + + if (!srv) + entry["State"] += Anope::string(" ") + Language::Translate(source.GetAccount(), _("(Split)")); + + lf.AddEntry(entry); + } + + std::vector replies; + lf.Process(replies); + + if (!zones->empty()) + { + ListFormatter lf2(source.GetAccount()); + lf2.AddColumn(_("Zone")).AddColumn(_("Servers")); + + for (unsigned i = 0; i < zones->size(); ++i) + { + const DNSZone *z = zones->at(i); + + ListFormatter::ListEntry entry; + entry["Zone"] = z->name; + + Anope::string server_str; + for (std::set::iterator it = z->servers.begin(), it_end = z->servers.end(); it != it_end; ++it) + server_str += *it + " "; + server_str.trim(); + + if (server_str.empty()) + server_str = "None"; + + entry["Servers"] = server_str; + + lf2.AddEntry(entry); + } + + lf2.Process(replies); + } + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + + void AddZone(CommandSource &source, const std::vector ¶ms) + { + const Anope::string &zone = params[1]; + + if (DNSZone::Find(zone)) + { + source.Reply(_("Zone %s already exists."), zone.c_str()); + return; + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + Log(LOG_ADMIN, source, this) << "to add zone " << zone; + + new DNSZone(zone); + source.Reply(_("Added zone %s."), zone.c_str()); + } + + void DelZone(CommandSource &source, const std::vector ¶ms) + { + const Anope::string &zone = params[1]; + + DNSZone *z = DNSZone::Find(zone); + if (!z) + { + source.Reply(_("Zone %s does not exist."), zone.c_str()); + return; + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + Log(LOG_ADMIN, source, this) << "to delete zone " << z->name; + + for (std::set::iterator it = z->servers.begin(), it_end = z->servers.end(); it != it_end; ++it) + { + DNSServer *s = DNSServer::Find(*it); + if (s) + s->zones.erase(z->name); + } + + if (dnsmanager) + { + dnsmanager->UpdateSerial(); + dnsmanager->Notify(z->name); + } + + source.Reply(_("Zone %s removed."), z->name.c_str()); + delete z; + } + + void AddServer(CommandSource &source, const std::vector ¶ms) + { + DNSServer *s = DNSServer::Find(params[1]); + const Anope::string &zone = params.size() > 2 ? params[2] : ""; + + if (s) + { + if (zone.empty()) + { + source.Reply(_("Server %s already exists."), s->GetName().c_str()); + } + else + { + DNSZone *z = DNSZone::Find(zone); + if (!z) + { + source.Reply(_("Zone %s does not exist."), zone.c_str()); + return; + } + else if (z->servers.count(s->GetName())) + { + source.Reply(_("Server %s is already in zone %s."), s->GetName().c_str(), z->name.c_str()); + return; + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + z->servers.insert(s->GetName()); + s->zones.insert(zone); + + if (dnsmanager) + { + dnsmanager->UpdateSerial(); + dnsmanager->Notify(zone); + } + + Log(LOG_ADMIN, source, this) << "to add server " << s->GetName() << " to zone " << z->name; + + source.Reply(_("Server %s added to zone %s."), s->GetName().c_str(), z->name.c_str()); + } + + return; + } + + Server *serv = Server::Find(params[1], true); + if (!serv || serv == Me || serv->IsJuped()) + { + source.Reply(_("Server %s is not linked to the network."), params[1].c_str()); + return; + } + + s = new DNSServer(params[1]); + if (zone.empty()) + { + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + Log(LOG_ADMIN, source, this) << "to add server " << s->GetName(); + source.Reply(_("Added server %s."), s->GetName().c_str()); + } + else + { + DNSZone *z = DNSZone::Find(zone); + if (!z) + { + source.Reply(_("Zone %s does not exist."), zone.c_str()); + delete s; + return; + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + Log(LOG_ADMIN, source, this) << "to add server " << s->GetName() << " to zone " << zone; + + z->servers.insert(s->GetName()); + s->zones.insert(z->name); + + if (dnsmanager) + { + dnsmanager->UpdateSerial(); + dnsmanager->Notify(z->name); + } + } + } + + void DelServer(CommandSource &source, const std::vector ¶ms) + { + DNSServer *s = DNSServer::Find(params[1]); + const Anope::string &zone = params.size() > 2 ? params[2] : ""; + + if (!s) + { + source.Reply(_("Server %s does not exist."), params[1].c_str()); + return; + } + else if (!zone.empty()) + { + DNSZone *z = DNSZone::Find(zone); + if (!z) + { + source.Reply(_("Zone %s does not exist."), zone.c_str()); + return; + } + else if (!z->servers.count(s->GetName())) + { + source.Reply(_("Server %s is not in zone %s."), s->GetName().c_str(), z->name.c_str()); + return; + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + Log(LOG_ADMIN, source, this) << "to remove server " << s->GetName() << " from zone " << z->name; + + if (dnsmanager) + { + dnsmanager->UpdateSerial(); + dnsmanager->Notify(z->name); + } + + z->servers.erase(s->GetName()); + s->zones.erase(z->name); + source.Reply(_("Removed server %s from zone %s."), s->GetName().c_str(), z->name.c_str()); + return; + } + else if (Server::Find(s->GetName(), true)) + { + source.Reply(_("Server %s must be quit before it can be deleted."), s->GetName().c_str()); + return; + } + + for (std::set::iterator it = s->zones.begin(), it_end = s->zones.end(); it != it_end; ++it) + { + DNSZone *z = DNSZone::Find(*it); + if (z) + z->servers.erase(s->GetName()); + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + if (dnsmanager) + dnsmanager->UpdateSerial(); + + Log(LOG_ADMIN, source, this) << "to delete server " << s->GetName(); + source.Reply(_("Removed server %s."), s->GetName().c_str()); + delete s; + } + + void AddIP(CommandSource &source, const std::vector ¶ms) + { + DNSServer *s = DNSServer::Find(params[1]); + + if (!s) + { + source.Reply(_("Server %s does not exist."), params[1].c_str()); + return; + } + + for (unsigned i = 0; i < s->GetIPs().size(); ++i) + if (params[2].equals_ci(s->GetIPs()[i])) + { + source.Reply(_("IP %s already exists for %s."), s->GetIPs()[i].c_str(), s->GetName().c_str()); + return; + } + + sockaddrs addr(params[2]); + if (!addr.valid()) + { + source.Reply(_("%s is not a valid IP address."), params[2].c_str()); + return; + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + s->GetIPs().push_back(params[2]); + source.Reply(_("Added IP %s to %s."), params[2].c_str(), s->GetName().c_str()); + Log(LOG_ADMIN, source, this) << "to add IP " << params[2] << " to " << s->GetName(); + + if (s->Active() && dnsmanager) + { + dnsmanager->UpdateSerial(); + for (std::set::iterator it = s->zones.begin(), it_end = s->zones.end(); it != it_end; ++it) + dnsmanager->Notify(*it); + } + } + + void DelIP(CommandSource &source, const std::vector ¶ms) + { + DNSServer *s = DNSServer::Find(params[1]); + + if (!s) + { + source.Reply(_("Server %s does not exist."), params[1].c_str()); + return; + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + for (unsigned i = 0; i < s->GetIPs().size(); ++i) + if (params[2].equals_ci(s->GetIPs()[i])) + { + s->GetIPs().erase(s->GetIPs().begin() + i); + source.Reply(_("Removed IP %s from %s."), params[2].c_str(), s->GetName().c_str()); + Log(LOG_ADMIN, source, this) << "to remove IP " << params[2] << " from " << s->GetName(); + + if (s->GetIPs().empty()) + { + s->repool = 0; + s->Pool(false); + } + + if (s->Active() && dnsmanager) + { + dnsmanager->UpdateSerial(); + for (std::set::iterator it = s->zones.begin(), it_end = s->zones.end(); it != it_end; ++it) + dnsmanager->Notify(*it); + } + + return; + } + + source.Reply(_("IP %s does not exist for %s."), params[2].c_str(), s->GetName().c_str()); + } + + void OnSet(CommandSource &source, const std::vector ¶ms) + { + DNSServer *s = DNSServer::Find(params[1]); + + if (!s) + { + source.Reply(_("Server %s does not exist."), params[1].c_str()); + return; + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + if (params[2].equals_ci("LIMIT")) + { + try + { + unsigned l = convertTo(params[3]); + s->SetLimit(l); + if (l) + source.Reply(_("User limit for %s set to %d."), s->GetName().c_str(), l); + else + source.Reply(_("User limit for %s removed."), s->GetName().c_str()); + } + catch (const ConvertException &ex) + { + source.Reply(_("Invalid value for LIMIT. Must be numerical.")); + } + } + else + source.Reply(_("Unknown SET option.")); + } + + void OnPool(CommandSource &source, const std::vector ¶ms) + { + DNSServer *s = DNSServer::Find(params[1]); + + if (!s) + { + source.Reply(_("Server %s does not exist."), params[1].c_str()); + return; + } + else if (!Server::Find(s->GetName(), true)) + { + source.Reply(_("Server %s is not currently linked."), s->GetName().c_str()); + return; + } + else if (s->Pooled()) + { + source.Reply(_("Server %s is already pooled."), s->GetName().c_str()); + return; + } + else if (s->GetIPs().empty()) + { + source.Reply(_("Server %s has no configured IPs."), s->GetName().c_str()); + return; + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + s->SetActive(true); + + source.Reply(_("Pooled %s."), s->GetName().c_str()); + Log(LOG_ADMIN, source, this) << "to pool " << s->GetName(); + } + + + void OnDepool(CommandSource &source, const std::vector ¶ms) + { + DNSServer *s = DNSServer::Find(params[1]); + + if (!s) + { + source.Reply(_("Server %s does not exist."), params[1].c_str()); + return; + } + else if (!s->Pooled()) + { + source.Reply(_("Server %s is not pooled."), s->GetName().c_str()); + return; + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + s->Pool(false); + + source.Reply(_("Depooled %s."), s->GetName().c_str()); + Log(LOG_ADMIN, source, this) << "to depool " << s->GetName(); + } + + public: + CommandOSDNS(Module *creator) : Command(creator, "operserv/dns", 0, 4) + { + this->SetDesc(_("Manage DNS zones for this network")); + this->SetSyntax(_("ADDZONE \037zone.name\037")); + this->SetSyntax(_("DELZONE \037zone.name\037")); + this->SetSyntax(_("ADDSERVER \037server.name\037 [\037zone.name\037]")); + this->SetSyntax(_("DELSERVER \037server.name\037 [\037zone.name\037]")); + this->SetSyntax(_("ADDIP \037server.name\037 \037ip\037")); + this->SetSyntax(_("DELIP \037server.name\037 \037ip\037")); + this->SetSyntax(_("SET \037server.name\037 \037option\037 \037value\037")); + this->SetSyntax(_("POOL \037server.name\037")); + this->SetSyntax(_("DEPOOL \037server.name\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (params.empty()) + this->DisplayPoolState(source); + else if (params[0].equals_ci("ADDZONE") && params.size() > 1) + this->AddZone(source, params); + else if (params[0].equals_ci("DELZONE") && params.size() > 1) + this->DelZone(source, params); + else if (params[0].equals_ci("ADDSERVER") && params.size() > 1) + this->AddServer(source, params); + else if (params[0].equals_ci("DELSERVER") && params.size() > 1) + this->DelServer(source, params); + else if (params[0].equals_ci("ADDIP") && params.size() > 2) + this->AddIP(source, params); + else if (params[0].equals_ci("DELIP") && params.size() > 2) + this->DelIP(source, params); + else if (params[0].equals_ci("SET") && params.size() > 3) + this->OnSet(source, params); + else if (params[0].equals_ci("POOL") && params.size() > 1) + this->OnPool(source, params); + else if (params[0].equals_ci("DEPOOL") && params.size() > 1) + this->OnDepool(source, params); + else + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command allows managing DNS zones used for controlling what servers users\n" + "are directed to when connecting. Omitting all parameters prints out the status of\n" + "the DNS zone.\n" + " \n" + "\002ADDZONE\002 adds a zone, eg us.yournetwork.tld. Servers can then be added to this\n" + "zone with the \002ADDSERVER\002 command.\n" + " \n" + "The \002ADDSERVER\002 command adds a server to the given zone. When a query is done, the\n" + "zone in question is served if it exists, else all servers in all zones are served.\n" + "A server may be in more than one zone.\n" + " \n" + "The \002ADDIP\002 command associates an IP with a server.\n" + " \n" + "The \002POOL\002 and \002DEPOOL\002 commands actually add and remove servers to their given zones.")); + return true; + } +}; + +class ModuleDNS : public Module +{ + Serialize::Type zone_type, dns_type; + CommandOSDNS commandosdns; + + time_t ttl; + int user_drop_mark; + time_t user_drop_time; + time_t user_drop_readd_time; + bool remove_split_servers; + bool readd_connected_servers; + + time_t last_warn; + + public: + ModuleDNS(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR), + zone_type("DNSZone", DNSZone::Unserialize), dns_type("DNSServer", DNSServer::Unserialize), commandosdns(this), + last_warn(0) + { + + + for (unsigned j = 0; j < dns_servers->size(); ++j) + { + DNSServer *s = dns_servers->at(j); + if (s->Pooled() && Server::Find(s->GetName(), true)) + s->SetActive(true); + } + } + + ~ModuleDNS() + { + for (unsigned i = zones->size(); i > 0; --i) + delete zones->at(i - 1); + for (unsigned i = dns_servers->size(); i > 0; --i) + delete dns_servers->at(i - 1); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *block = conf->GetModule(this); + this->ttl = block->Get("ttl"); + this->user_drop_mark = block->Get("user_drop_mark"); + this->user_drop_time = block->Get("user_drop_time"); + this->user_drop_readd_time = block->Get("user_drop_readd_time"); + this->remove_split_servers = block->Get("remove_split_servers"); + this->readd_connected_servers = block->Get("readd_connected_servers"); + } + + void OnNewServer(Server *s) anope_override + { + if (s == Me || s->IsJuped()) + return; + if (!Me->IsSynced() || this->readd_connected_servers) + { + DNSServer *dns = DNSServer::Find(s->GetName()); + if (dns && dns->Pooled() && !dns->Active() && !dns->GetIPs().empty()) + { + dns->SetActive(true); + Log(this) << "Pooling server " << s->GetName(); + } + } + } + + void OnServerQuit(Server *s) anope_override + { + DNSServer *dns = DNSServer::Find(s->GetName()); + if (remove_split_servers && dns && dns->Pooled() && dns->Active()) + { + if (readd_connected_servers) + dns->SetActive(false); // Will be reactivated when it comes back + else + dns->Pool(false); // Otherwise permanently pull this + Log(this) << "Depooling delinked server " << s->GetName(); + } + } + + void OnUserConnect(User *u, bool &exempt) anope_override + { + if (!u->Quitting() && u->server) + { + DNSServer *s = DNSServer::Find(u->server->GetName()); + /* Check for user limit reached */ + if (s && s->Pooled() && s->Active() && s->GetLimit() && u->server->users >= s->GetLimit()) + { + Log(this) << "Depooling full server " << s->GetName() << ": " << u->server->users << " users"; + s->SetActive(false); + } + } + } + + void OnPreUserLogoff(User *u) anope_override + { + if (u && u->server) + { + DNSServer *s = DNSServer::Find(u->server->GetName()); + if (!s || !s->Pooled()) + return; + + /* Check for dropping under userlimit */ + if (s->GetLimit() && !s->Active() && s->GetLimit() > u->server->users) + { + Log(this) << "Pooling server " << s->GetName(); + s->SetActive(true); + } + + if (this->user_drop_mark > 0) + { + std::list& times = server_quit_times[u->server->GetName()]; + times.push_back(Anope::CurTime); + if (times.size() > static_cast(this->user_drop_mark)) + times.pop_front(); + + if (times.size() == static_cast(this->user_drop_mark)) + { + time_t diff = Anope::CurTime - *times.begin(); + + /* Check for very fast user drops */ + if (s->Active() && diff <= this->user_drop_time) + { + Log(this) << "Depooling server " << s->GetName() << ": dropped " << this->user_drop_mark << " users in " << diff << " seconds"; + s->repool = Anope::CurTime + this->user_drop_readd_time; + s->SetActive(false); + } + /* Check for needing to re-pool a server that dropped users */ + else if (!s->Active() && s->repool && s->repool <= Anope::CurTime) + { + s->SetActive(true); + s->repool = 0; + Log(this) << "Pooling server " << s->GetName(); + } + } + } + } + } + + void OnDnsRequest(DNS::Query &req, DNS::Query *packet) anope_override + { + if (req.questions.empty()) + return; + /* Currently we reply to any QR for A/AAAA */ + const DNS::Question& q = req.questions[0]; + if (q.type != DNS::QUERY_A && q.type != DNS::QUERY_AAAA && q.type != DNS::QUERY_AXFR && q.type != DNS::QUERY_ANY) + return; + + DNSZone *zone = DNSZone::Find(q.name); + size_t answer_size = packet->answers.size(); + if (zone) + { + for (std::set::iterator it = zone->servers.begin(), it_end = zone->servers.end(); it != it_end; ++it) + { + DNSServer *s = DNSServer::Find(*it); + if (!s || !s->Active()) + continue; + + for (unsigned j = 0; j < s->GetIPs().size(); ++j) + { + DNS::QueryType q_type = s->GetIPs()[j].find(':') != Anope::string::npos ? DNS::QUERY_AAAA : DNS::QUERY_A; + + if (q.type == DNS::QUERY_AXFR || q.type == DNS::QUERY_ANY || q_type == q.type) + { + DNS::ResourceRecord rr(q.name, q_type); + rr.ttl = this->ttl; + rr.rdata = s->GetIPs()[j]; + packet->answers.push_back(rr); + } + } + } + } + + if (packet->answers.size() == answer_size) + { + /* Default zone */ + for (unsigned i = 0; i < dns_servers->size(); ++i) + { + DNSServer *s = dns_servers->at(i); + if (!s->Active()) + continue; + + for (unsigned j = 0; j < s->GetIPs().size(); ++j) + { + DNS::QueryType q_type = s->GetIPs()[j].find(':') != Anope::string::npos ? DNS::QUERY_AAAA : DNS::QUERY_A; + + if (q.type == DNS::QUERY_AXFR || q.type == DNS::QUERY_ANY || q_type == q.type) + { + DNS::ResourceRecord rr(q.name, q_type); + rr.ttl = this->ttl; + rr.rdata = s->GetIPs()[j]; + packet->answers.push_back(rr); + } + } + } + } + + if (packet->answers.size() == answer_size) + { + if (last_warn + 60 < Anope::CurTime) + { + last_warn = Anope::CurTime; + Log(this) << "Warning! There are no pooled servers!"; + } + + /* Something messed up, just return them all and hope one is available */ + for (unsigned i = 0; i < dns_servers->size(); ++i) + { + DNSServer *s = dns_servers->at(i); + + for (unsigned j = 0; j < s->GetIPs().size(); ++j) + { + DNS::QueryType q_type = s->GetIPs()[j].find(':') != Anope::string::npos ? DNS::QUERY_AAAA : DNS::QUERY_A; + + if (q.type == DNS::QUERY_AXFR || q.type == DNS::QUERY_ANY || q_type == q.type) + { + DNS::ResourceRecord rr(q.name, q_type); + rr.ttl = this->ttl; + rr.rdata = s->GetIPs()[j]; + packet->answers.push_back(rr); + } + } + } + + if (packet->answers.size() == answer_size) + { + Log(this) << "Error! There are no servers with any IPs of type " << q.type; + } + } + } +}; + +MODULE_INIT(ModuleDNS) diff --git a/modules/commands/os_forbid.cpp b/modules/commands/os_forbid.cpp new file mode 100644 index 0000000..c2a0ff5 --- /dev/null +++ b/modules/commands/os_forbid.cpp @@ -0,0 +1,571 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/os_forbid.h" + +static ServiceReference nickserv("NickServService", "NickServ"); + +struct ForbidDataImpl : ForbidData, Serializable +{ + ForbidDataImpl() : Serializable("ForbidData") { } + void Serialize(Serialize::Data &data) const anope_override; + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data); +}; + +void ForbidDataImpl::Serialize(Serialize::Data &data) const +{ + data["mask"] << this->mask; + data["creator"] << this->creator; + data["reason"] << this->reason; + data["created"] << this->created; + data["expires"] << this->expires; + data["type"] << this->type; +} + +Serializable* ForbidDataImpl::Unserialize(Serializable *obj, Serialize::Data &data) +{ + if (!forbid_service) + return NULL; + + ForbidDataImpl *fb; + if (obj) + fb = anope_dynamic_static_cast(obj); + else + fb = new ForbidDataImpl(); + + data["mask"] >> fb->mask; + data["creator"] >> fb->creator; + data["reason"] >> fb->reason; + data["created"] >> fb->created; + data["expires"] >> fb->expires; + unsigned int t; + data["type"] >> t; + fb->type = static_cast(t); + + if (t > FT_SIZE - 1) + return NULL; + + if (!obj) + forbid_service->AddForbid(fb); + return fb; +} + +class MyForbidService : public ForbidService +{ + Serialize::Checker[FT_SIZE - 1]> forbid_data; + + inline std::vector& forbids(unsigned t) { return (*this->forbid_data)[t - 1]; } + + public: + MyForbidService(Module *m) : ForbidService(m), forbid_data("ForbidData") { } + + ~MyForbidService() + { + std::vector f = GetForbids(); + for (unsigned i = 0; i < f.size(); ++i) + delete f[i]; + } + + void AddForbid(ForbidData *d) anope_override + { + this->forbids(d->type).push_back(d); + } + + void RemoveForbid(ForbidData *d) anope_override + { + std::vector::iterator it = std::find(this->forbids(d->type).begin(), this->forbids(d->type).end(), d); + if (it != this->forbids(d->type).end()) + this->forbids(d->type).erase(it); + delete d; + } + + ForbidData *CreateForbid() anope_override + { + return new ForbidDataImpl(); + } + + ForbidData *FindForbid(const Anope::string &mask, ForbidType ftype) anope_override + { + for (unsigned i = this->forbids(ftype).size(); i > 0; --i) + { + ForbidData *d = this->forbids(ftype)[i - 1]; + + if (Anope::Match(mask, d->mask, false, true)) + return d; + } + return NULL; + } + + ForbidData *FindForbidExact(const Anope::string &mask, ForbidType ftype) anope_override + { + for (unsigned i = this->forbids(ftype).size(); i > 0; --i) + { + ForbidData *d = this->forbids(ftype)[i - 1]; + + if (d->mask.equals_ci(mask)) + return d; + } + return NULL; + } + + std::vector GetForbids() anope_override + { + std::vector f; + for (unsigned j = FT_NICK; j < FT_SIZE; ++j) + for (unsigned i = this->forbids(j).size(); i > 0; --i) + { + ForbidData *d = this->forbids(j).at(i - 1); + + if (d->expires && !Anope::NoExpire && Anope::CurTime >= d->expires) + { + Anope::string ftype = "none"; + if (d->type == FT_NICK) + ftype = "nick"; + else if (d->type == FT_CHAN) + ftype = "chan"; + else if (d->type == FT_EMAIL) + ftype = "email"; + + Log(LOG_NORMAL, "expire/forbid", Config->GetClient("OperServ")) << "Expiring forbid for " << d->mask << " type " << ftype; + this->forbids(j).erase(this->forbids(j).begin() + i - 1); + delete d; + } + else + f.push_back(d); + } + + return f; + } +}; + +class CommandOSForbid : public Command +{ + ServiceReference fs; + public: + CommandOSForbid(Module *creator) : Command(creator, "operserv/forbid", 1, 5), fs("ForbidService", "forbid") + { + this->SetDesc(_("Forbid usage of nicknames, channels, and emails")); + this->SetSyntax(_("ADD {NICK|CHAN|EMAIL|REGISTER} [+\037expiry\037] \037entry\037 \037reason\037")); + this->SetSyntax(_("DEL {NICK|CHAN|EMAIL|REGISTER} \037entry\037")); + this->SetSyntax("LIST [NICK|CHAN|EMAIL|REGISTER]"); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!this->fs) + return; + + const Anope::string &command = params[0]; + const Anope::string &subcommand = params.size() > 1 ? params[1] : ""; + + ForbidType ftype = FT_SIZE; + if (subcommand.equals_ci("NICK")) + ftype = FT_NICK; + else if (subcommand.equals_ci("CHAN")) + ftype = FT_CHAN; + else if (subcommand.equals_ci("EMAIL")) + ftype = FT_EMAIL; + else if (subcommand.equals_ci("REGISTER")) + ftype = FT_REGISTER; + + if (command.equals_ci("ADD") && params.size() > 3 && ftype != FT_SIZE) + { + const Anope::string &expiry = params[2][0] == '+' ? params[2] : ""; + const Anope::string &entry = !expiry.empty() ? params[3] : params[2]; + Anope::string reason; + if (expiry.empty()) + reason = params[3] + " "; + if (params.size() > 4) + reason += params[4]; + reason.trim(); + + if (entry.replace_all_cs("?*", "").empty()) + { + source.Reply(_("The mask must contain at least one non wildcard character.")); + return; + } + + time_t expiryt = 0; + + if (!expiry.empty()) + { + expiryt = Anope::DoTime(expiry); + if (expiryt < 0) + { + source.Reply(BAD_EXPIRY_TIME); + return; + } + else if (expiryt) + expiryt += Anope::CurTime; + } + + NickAlias *target = NickAlias::Find(entry); + if (target != NULL && Config->GetModule("nickserv")->Get("secureadmins", "yes") && target->nc->IsServicesOper()) + { + source.Reply(ACCESS_DENIED); + return; + } + + ForbidData *d = this->fs->FindForbidExact(entry, ftype); + bool created = false; + if (d == NULL) + { + d = new ForbidDataImpl(); + created = true; + } + + d->mask = entry; + d->creator = source.GetNick(); + d->reason = reason; + d->created = Anope::CurTime; + d->expires = expiryt; + d->type = ftype; + if (created) + this->fs->AddForbid(d); + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + Log(LOG_ADMIN, source, this) << "to add a forbid on " << entry << " of type " << subcommand; + source.Reply(_("Added a forbid on %s of type %s to expire on %s."), entry.c_str(), subcommand.lower().c_str(), d->expires ? Anope::strftime(d->expires, source.GetAccount()).c_str() : "never"); + + /* apply forbid */ + switch (ftype) + { + case FT_NICK: + { + int na_matches = 0; + + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + module->OnUserNickChange(it->second, ""); + + for (nickalias_map::const_iterator it = NickAliasList->begin(), it_end = NickAliasList->end(); it != it_end;) + { + NickAlias *na = it->second; + ++it; + + d = this->fs->FindForbid(na->nick, FT_NICK); + if (d == NULL) + continue; + + ++na_matches; + + delete na; + } + + source.Reply(_("\002%d\002 nickname(s) dropped."), na_matches); + break; + } + case FT_CHAN: + { + int chan_matches = 0, ci_matches = 0; + + for (channel_map::const_iterator it = ChannelList.begin(), it_end = ChannelList.end(); it != it_end;) + { + Channel *c = it->second; + ++it; + + d = this->fs->FindForbid(c->name, FT_CHAN); + if (d == NULL) + continue; + + ServiceReference chanserv("ChanServService", "ChanServ"); + BotInfo *OperServ = Config->GetClient("OperServ"); + if (IRCD->CanSQLineChannel && OperServ) + { + time_t inhabit = Config->GetModule("chanserv")->Get("inhabit", "15s"); + XLine x(c->name, OperServ->nick, Anope::CurTime + inhabit, d->reason); + IRCD->SendSQLine(NULL, &x); + } + else if (chanserv) + { + chanserv->Hold(c); + } + + ++chan_matches; + + for (Channel::ChanUserList::const_iterator cit = c->users.begin(), cit_end = c->users.end(); cit != cit_end;) + { + User *u = cit->first; + ++cit; + + if (u->server == Me || u->HasMode("OPER")) + continue; + + reason = Anope::printf(Language::Translate(u, _("This channel has been forbidden: %s")), d->reason.c_str()); + + c->Kick(source.service, u, "%s", reason.c_str()); + } + } + + for (registered_channel_map::const_iterator it = RegisteredChannelList->begin(); it != RegisteredChannelList->end();) + { + ChannelInfo *ci = it->second; + ++it; + + d = this->fs->FindForbid(ci->name, FT_CHAN); + if (d == NULL) + continue; + + ++ci_matches; + + delete ci; + } + + source.Reply(_("\002%d\002 channel(s) cleared, and \002%d\002 channel(s) dropped."), chan_matches, ci_matches); + + break; + } + default: + break; + } + + } + else if (command.equals_ci("DEL") && params.size() > 2 && ftype != FT_SIZE) + { + const Anope::string &entry = params[2]; + + ForbidData *d = this->fs->FindForbidExact(entry, ftype); + if (d != NULL) + { + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + Log(LOG_ADMIN, source, this) << "to remove forbid on " << d->mask << " of type " << subcommand; + source.Reply(_("%s deleted from the %s forbid list."), d->mask.c_str(), subcommand.c_str()); + this->fs->RemoveForbid(d); + } + else + source.Reply(_("Forbid on %s was not found."), entry.c_str()); + } + else if (command.equals_ci("LIST")) + { + const std::vector &forbids = this->fs->GetForbids(); + if (forbids.empty()) + source.Reply(_("Forbid list is empty.")); + else + { + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Mask")).AddColumn(_("Type")).AddColumn(_("Creator")).AddColumn(_("Expires")).AddColumn(_("Reason")); + + unsigned shown = 0; + for (unsigned i = 0; i < forbids.size(); ++i) + { + ForbidData *d = forbids[i]; + + if (ftype != FT_SIZE && ftype != d->type) + continue; + + Anope::string stype; + if (d->type == FT_NICK) + stype = "NICK"; + else if (d->type == FT_CHAN) + stype = "CHAN"; + else if (d->type == FT_EMAIL) + stype = "EMAIL"; + else if (d->type == FT_REGISTER) + stype = "REGISTER"; + else + continue; + + ListFormatter::ListEntry entry; + entry["Mask"] = d->mask; + entry["Type"] = stype; + entry["Creator"] = d->creator; + entry["Expires"] = d->expires ? Anope::strftime(d->expires, NULL, true).c_str() : Language::Translate(source.GetAccount(), _("Never")); + entry["Reason"] = d->reason; + list.AddEntry(entry); + ++shown; + } + + if (!shown) + { + source.Reply(_("There are no forbids of type %s."), subcommand.upper().c_str()); + } + else + { + source.Reply(_("Forbid list:")); + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + if (shown >= forbids.size()) + source.Reply(_("End of forbid list.")); + else + source.Reply(_("End of forbid list - %d/%d entries shown."), shown, forbids.size()); + } + } + } + else + this->OnSyntaxError(source, command); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Forbid allows you to forbid usage of certain nicknames, channels,\n" + "and email addresses. Wildcards are accepted for all entries.")); + + const Anope::string ®exengine = Config->GetBlock("options")->Get("regexengine"); + if (!regexengine.empty()) + { + source.Reply(" "); + source.Reply(_("Regex matches are also supported using the %s engine.\n" + "Enclose your pattern in // if this is desired."), regexengine.c_str()); + } + + return true; + } +}; + +class OSForbid : public Module +{ + MyForbidService forbidService; + Serialize::Type forbiddata_type; + CommandOSForbid commandosforbid; + + public: + OSForbid(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + forbidService(this), forbiddata_type("ForbidData", ForbidDataImpl::Unserialize), commandosforbid(this) + { + + } + + void OnUserConnect(User *u, bool &exempt) anope_override + { + if (u->Quitting() || exempt) + return; + + this->OnUserNickChange(u, ""); + } + + void OnUserNickChange(User *u, const Anope::string &) anope_override + { + if (u->HasMode("OPER")) + return; + + ForbidData *d = this->forbidService.FindForbid(u->nick, FT_NICK); + if (d != NULL) + { + BotInfo *bi = Config->GetClient("NickServ"); + if (!bi) + bi = Config->GetClient("OperServ"); + if (bi) + u->SendMessage(bi, _("This nickname has been forbidden: %s"), d->reason.c_str()); + if (nickserv) + nickserv->Collide(u, NULL); + } + } + + EventReturn OnCheckKick(User *u, Channel *c, Anope::string &mask, Anope::string &reason) anope_override + { + BotInfo *OperServ = Config->GetClient("OperServ"); + if (u->HasMode("OPER") || !OperServ) + return EVENT_CONTINUE; + + ForbidData *d = this->forbidService.FindForbid(c->name, FT_CHAN); + if (d != NULL) + { + ServiceReference chanserv("ChanServService", "ChanServ"); + if (IRCD->CanSQLineChannel) + { + time_t inhabit = Config->GetModule("chanserv")->Get("inhabit", "15s"); + XLine x(c->name, OperServ->nick, Anope::CurTime + inhabit, d->reason); + IRCD->SendSQLine(NULL, &x); + } + else if (chanserv) + { + chanserv->Hold(c); + } + + reason = Anope::printf(Language::Translate(u, _("This channel has been forbidden: %s")), d->reason.c_str()); + + return EVENT_STOP; + } + + return EVENT_CONTINUE; + } + + EventReturn OnPreCommand(CommandSource &source, Command *command, std::vector ¶ms) anope_override + { + if (command->name == "nickserv/info" && params.size() > 0) + { + ForbidData *d = this->forbidService.FindForbid(params[0], FT_NICK); + if (d != NULL) + { + if (source.IsOper()) + source.Reply(_("Nick \002%s\002 is forbidden by %s: %s"), params[0].c_str(), d->creator.c_str(), d->reason.c_str()); + else + source.Reply(_("Nick \002%s\002 is forbidden."), params[0].c_str()); + return EVENT_STOP; + } + } + else if (command->name == "chanserv/info" && params.size() > 0) + { + ForbidData *d = this->forbidService.FindForbid(params[0], FT_CHAN); + if (d != NULL) + { + if (source.IsOper()) + source.Reply(_("Channel \002%s\002 is forbidden by %s: %s"), params[0].c_str(), d->creator.c_str(), d->reason.c_str()); + else + source.Reply(_("Channel \002%s\002 is forbidden."), params[0].c_str()); + return EVENT_STOP; + } + } + else if (source.IsOper()) + return EVENT_CONTINUE; + else if (command->name == "nickserv/register" && params.size() > 1) + { + ForbidData *d = this->forbidService.FindForbid(source.GetNick(), FT_REGISTER); + if (d != NULL) + { + source.Reply(NICK_CANNOT_BE_REGISTERED, source.GetNick().c_str()); + return EVENT_STOP; + } + + d = this->forbidService.FindForbid(params[1], FT_EMAIL); + if (d != NULL) + { + source.Reply(_("Your email address is not allowed, choose a different one.")); + return EVENT_STOP; + } + } + else if (command->name == "nickserv/set/email" && params.size() > 0) + { + ForbidData *d = this->forbidService.FindForbid(params[0], FT_EMAIL); + if (d != NULL) + { + source.Reply(_("Your email address is not allowed, choose a different one.")); + return EVENT_STOP; + } + } + else if (command->name == "chanserv/register" && !params.empty()) + { + ForbidData *d = this->forbidService.FindForbid(params[0], FT_REGISTER); + if (d != NULL) + { + source.Reply(CHAN_X_INVALID, params[0].c_str()); + return EVENT_STOP; + } + } + + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(OSForbid) diff --git a/modules/commands/os_ignore.cpp b/modules/commands/os_ignore.cpp new file mode 100644 index 0000000..e46f152 --- /dev/null +++ b/modules/commands/os_ignore.cpp @@ -0,0 +1,416 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/os_ignore.h" + +struct IgnoreDataImpl : IgnoreData, Serializable +{ + IgnoreDataImpl() : Serializable("IgnoreData") { } + ~IgnoreDataImpl(); + void Serialize(Serialize::Data &data) const anope_override; + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data); +}; + +IgnoreDataImpl::~IgnoreDataImpl() +{ + if (ignore_service) + ignore_service->DelIgnore(this); +} + +void IgnoreDataImpl::Serialize(Serialize::Data &data) const +{ + data["mask"] << this->mask; + data["creator"] << this->creator; + data["reason"] << this->reason; + data["time"] << this->time; +} + +Serializable* IgnoreDataImpl::Unserialize(Serializable *obj, Serialize::Data &data) +{ + if (!ignore_service) + return NULL; + + IgnoreDataImpl *ign; + if (obj) + ign = anope_dynamic_static_cast(obj); + else + { + ign = new IgnoreDataImpl(); + ignore_service->AddIgnore(ign); + } + + data["mask"] >> ign->mask; + data["creator"] >> ign->creator; + data["reason"] >> ign->reason; + data["time"] >> ign->time; + + return ign; +} + + +class OSIgnoreService : public IgnoreService +{ + Serialize::Checker > ignores; + + public: + OSIgnoreService(Module *o) : IgnoreService(o), ignores("IgnoreData") { } + + void AddIgnore(IgnoreData *ign) anope_override + { + ignores->push_back(ign); + } + + void DelIgnore(IgnoreData *ign) anope_override + { + std::vector::iterator it = std::find(ignores->begin(), ignores->end(), ign); + if (it != ignores->end()) + ignores->erase(it); + } + + void ClearIgnores() anope_override + { + for (unsigned i = ignores->size(); i > 0; --i) + { + IgnoreData *ign = ignores->at(i - 1); + delete ign; + } + } + + IgnoreData *Create() anope_override + { + return new IgnoreDataImpl(); + } + + IgnoreData *Find(const Anope::string &mask) anope_override + { + User *u = User::Find(mask, true); + std::vector::iterator ign = this->ignores->begin(), ign_end = this->ignores->end(); + + if (u) + { + for (; ign != ign_end; ++ign) + { + Entry ignore_mask("", (*ign)->mask); + if (ignore_mask.Matches(u, true)) + break; + } + } + else + { + size_t user, host; + Anope::string tmp; + /* We didn't get a user.. generate a valid mask. */ + if ((host = mask.find('@')) != Anope::string::npos) + { + if ((user = mask.find('!')) != Anope::string::npos) + { + /* this should never happen */ + if (user > host) + return NULL; + tmp = mask; + } + else + /* We have user@host. Add nick wildcard. */ + tmp = "*!" + mask; + } + /* We only got a nick.. */ + else + tmp = mask + "!*@*"; + + for (; ign != ign_end; ++ign) + if (Anope::Match(tmp, (*ign)->mask, false, true)) + break; + } + + /* Check whether the entry has timed out */ + if (ign != ign_end) + { + IgnoreData *id = *ign; + + if (id->time && !Anope::NoExpire && id->time <= Anope::CurTime) + { + Log(LOG_NORMAL, "expire/ignore", Config->GetClient("OperServ")) << "Expiring ignore entry " << id->mask; + delete id; + } + else + return id; + } + + return NULL; + } + + std::vector &GetIgnores() anope_override + { + return *ignores; + } +}; + +class CommandOSIgnore : public Command +{ + private: + Anope::string RealMask(const Anope::string &mask) + { + /* If it s an existing user, we ignore the hostmask. */ + User *u = User::Find(mask, true); + if (u) + return "*!*@" + u->host; + + size_t host = mask.find('@'); + /* Determine whether we get a nick or a mask. */ + if (host != Anope::string::npos) + { + size_t user = mask.find('!'); + /* Check whether we have a nick too.. */ + if (user != Anope::string::npos) + { + if (user > host) + /* this should never happen */ + return ""; + else + return mask; + } + else + /* We have user@host. Add nick wildcard. */ + return "*!" + mask; + } + + /* We only got a nick.. */ + return mask + "!*@*"; + } + + void DoAdd(CommandSource &source, const std::vector ¶ms) + { + if (!ignore_service) + return; + + const Anope::string &time = params.size() > 1 ? params[1] : ""; + const Anope::string &nick = params.size() > 2 ? params[2] : ""; + const Anope::string &reason = params.size() > 3 ? params[3] : ""; + + if (time.empty() || nick.empty()) + { + this->OnSyntaxError(source, "ADD"); + return; + } + else + { + time_t t = Anope::DoTime(time); + + if (t <= -1) + { + source.Reply(BAD_EXPIRY_TIME); + return; + } + + Anope::string mask = RealMask(nick); + if (mask.empty()) + { + source.Reply(BAD_USERHOST_MASK); + return; + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + IgnoreData *ign = new IgnoreDataImpl(); + ign->mask = mask; + ign->creator = source.GetNick(); + ign->reason = reason; + ign->time = t ? Anope::CurTime + t : 0; + + ignore_service->AddIgnore(ign); + if (!t) + { + source.Reply(_("\002%s\002 will now permanently be ignored."), mask.c_str()); + Log(LOG_ADMIN, source, this) << "to add a permanent ignore for " << mask; + } + else + { + source.Reply(_("\002%s\002 will now be ignored for \002%s\002."), mask.c_str(), Anope::Duration(t, source.GetAccount()).c_str()); + Log(LOG_ADMIN, source, this) << "to add an ignore on " << mask << " for " << Anope::Duration(t); + } + } + } + + void DoList(CommandSource &source) + { + if (!ignore_service) + return; + + std::vector &ignores = ignore_service->GetIgnores(); + for (unsigned i = ignores.size(); i > 0; --i) + { + IgnoreData *id = ignores[i - 1]; + + if (id->time && !Anope::NoExpire && id->time <= Anope::CurTime) + { + Log(LOG_NORMAL, "expire/ignore", Config->GetClient("OperServ")) << "Expiring ignore entry " << id->mask; + delete id; + } + } + + if (ignores.empty()) + source.Reply(_("Ignore list is empty.")); + else + { + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Mask")).AddColumn(_("Creator")).AddColumn(_("Reason")).AddColumn(_("Expires")); + + for (unsigned i = ignores.size(); i > 0; --i) + { + const IgnoreData *ignore = ignores[i - 1]; + + ListFormatter::ListEntry entry; + entry["Mask"] = ignore->mask; + entry["Creator"] = ignore->creator; + entry["Reason"] = ignore->reason; + entry["Expires"] = Anope::Expires(ignore->time, source.GetAccount()); + list.AddEntry(entry); + } + + source.Reply(_("Services ignore list:")); + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + } + + void DoDel(CommandSource &source, const std::vector ¶ms) + { + if (!ignore_service) + return; + + const Anope::string nick = params.size() > 1 ? params[1] : ""; + if (nick.empty()) + { + this->OnSyntaxError(source, "DEL"); + return; + } + + Anope::string mask = RealMask(nick); + if (mask.empty()) + { + source.Reply(BAD_USERHOST_MASK); + return; + } + + IgnoreData *ign = ignore_service->Find(mask); + if (ign) + { + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + Log(LOG_ADMIN, source, this) << "to remove an ignore on " << mask; + source.Reply(_("\002%s\002 will no longer be ignored."), mask.c_str()); + delete ign; + } + else + source.Reply(_("\002%s\002 not found on ignore list."), mask.c_str()); + } + + void DoClear(CommandSource &source) + { + if (!ignore_service) + return; + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + ignore_service->ClearIgnores(); + Log(LOG_ADMIN, source, this) << "to CLEAR the list"; + source.Reply(_("Ignore list has been cleared.")); + + return; + } + + public: + CommandOSIgnore(Module *creator) : Command(creator, "operserv/ignore", 1, 4) + { + this->SetDesc(_("Modify the Services ignore list")); + this->SetSyntax(_("ADD \037expiry\037 {\037nick\037|\037mask\037} [\037reason\037]")); + this->SetSyntax(_("DEL {\037nick\037|\037mask\037}")); + this->SetSyntax("LIST"); + this->SetSyntax("CLEAR"); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[0]; + + if (cmd.equals_ci("ADD")) + return this->DoAdd(source, params); + else if (cmd.equals_ci("LIST")) + return this->DoList(source); + else if (cmd.equals_ci("DEL")) + return this->DoDel(source, params); + else if (cmd.equals_ci("CLEAR")) + return this->DoClear(source); + else + this->OnSyntaxError(source, ""); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows Services Operators to make Services ignore a nick or mask\n" + "for a certain time or until the next restart. The default\n" + "time format is seconds. You can specify it by using units.\n" + "Valid units are: \037s\037 for seconds, \037m\037 for minutes,\n" + "\037h\037 for hours and \037d\037 for days.\n" + "Combinations of these units are not permitted.\n" + "To make Services permanently ignore the user, type 0 as time.\n" + "When adding a \037mask\037, it should be in the format nick!user@host,\n" + "everything else will be considered a nick. Wildcards are permitted.\n" + " \n" + "Ignores will not be enforced on IRC Operators.")); + + const Anope::string ®exengine = Config->GetBlock("options")->Get("regexengine"); + if (!regexengine.empty()) + { + source.Reply(" "); + source.Reply(_("Regex matches are also supported using the %s engine.\n" + "Enclose your pattern in // if this is desired."), regexengine.c_str()); + } + + return true; + } +}; + +class OSIgnore : public Module +{ + Serialize::Type ignoredata_type; + OSIgnoreService osignoreservice; + CommandOSIgnore commandosignore; + + public: + OSIgnore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + ignoredata_type("IgnoreData", IgnoreDataImpl::Unserialize), osignoreservice(this), commandosignore(this) + { + + } + + EventReturn OnBotPrivmsg(User *u, BotInfo *bi, Anope::string &message) anope_override + { + if (!u->HasMode("OPER") && this->osignoreservice.Find(u->nick)) + return EVENT_STOP; + + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(OSIgnore) diff --git a/modules/commands/os_info.cpp b/modules/commands/os_info.cpp new file mode 100644 index 0000000..f8ecb37 --- /dev/null +++ b/modules/commands/os_info.cpp @@ -0,0 +1,290 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" + +struct OperInfo : Serializable +{ + Anope::string target; + Anope::string info; + Anope::string adder; + time_t created; + + OperInfo() : Serializable("OperInfo"), created(0) { } + OperInfo(const Anope::string &t, const Anope::string &i, const Anope::string &a, time_t c) : + Serializable("OperInfo"), target(t), info(i), adder(a), created(c) { } + + ~OperInfo(); + + void Serialize(Serialize::Data &data) const anope_override + { + data["target"] << target; + data["info"] << info; + data["adder"] << adder; + data["created"] << created; + } + + static Serializable *Unserialize(Serializable *obj, Serialize::Data &data); +}; + +struct OperInfos : Serialize::Checker > +{ + OperInfos(Extensible *) : Serialize::Checker >("OperInfo") { } + + ~OperInfos() + { + for (unsigned i = (*this)->size(); i > 0; --i) + delete (*this)->at(i - 1); + } + + static Extensible *Find(const Anope::string &target) + { + NickAlias *na = NickAlias::Find(target); + if (na) + return na->nc; + return ChannelInfo::Find(target); + } +}; + +OperInfo::~OperInfo() +{ + Extensible *e = OperInfos::Find(target); + if (e) + { + OperInfos *op = e->GetExt("operinfo"); + if (op) + { + std::vector::iterator it = std::find((*op)->begin(), (*op)->end(), this); + if (it != (*op)->end()) + (*op)->erase(it); + } + } +} + +Serializable *OperInfo::Unserialize(Serializable *obj, Serialize::Data &data) +{ + Anope::string starget; + data["target"] >> starget; + + Extensible *e = OperInfos::Find(starget); + if (!e) + return NULL; + + OperInfos *oi = e->Require("operinfo"); + OperInfo *o; + if (obj) + o = anope_dynamic_static_cast(obj); + else + { + o = new OperInfo(); + o->target = starget; + } + data["info"] >> o->info; + data["adder"] >> o->adder; + data["created"] >> o->created; + + if (!obj) + (*oi)->push_back(o); + return o; +} + +class CommandOSInfo : public Command +{ + public: + CommandOSInfo(Module *creator) : Command(creator, "operserv/info", 2, 3) + { + this->SetDesc(_("Associate oper info with a nick or channel")); + this->SetSyntax(_("ADD \037target\037 \037info\037")); + this->SetSyntax(_("DEL \037target\037 \037info\037")); + this->SetSyntax(_("CLEAR \037target\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[0], target = params[1], info = params.size() > 2 ? params[2] : ""; + + Extensible *e; + if (IRCD->IsChannelValid(target)) + { + ChannelInfo *ci = ChannelInfo::Find(target); + if (!ci) + { + source.Reply(CHAN_X_NOT_REGISTERED, target.c_str()); + return; + } + + e = ci; + } + else + { + NickAlias *na = NickAlias::Find(target); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, target.c_str()); + return; + } + + e = na->nc; + } + + if (cmd.equals_ci("ADD")) + { + if (info.empty()) + { + this->OnSyntaxError(source, cmd); + return; + } + + OperInfos *oi = e->Require("operinfo"); + + if ((*oi)->size() >= Config->GetModule(this->module)->Get("max", "10")) + { + source.Reply(_("The oper info list for \002%s\002 is full."), target.c_str()); + return; + } + + for (unsigned i = 0; i < (*oi)->size(); ++i) + { + OperInfo *o = (*oi)->at(i); + + if (o->info.equals_ci(info)) + { + source.Reply(_("The oper info already exists on \002%s\002."), target.c_str()); + return; + } + } + + (*oi)->push_back(new OperInfo(target, info, source.GetNick(), Anope::CurTime)); + + source.Reply(_("Added info to \002%s\002."), target.c_str()); + Log(LOG_ADMIN, source, this) << "to add information to " << target; + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + } + else if (cmd.equals_ci("DEL")) + { + if (info.empty()) + { + this->OnSyntaxError(source, cmd); + return; + } + + OperInfos *oi = e->GetExt("operinfo"); + + if (!oi) + { + source.Reply(_("Oper info list for \002%s\002 is empty."), target.c_str()); + return; + } + + bool found = false; + for (unsigned i = (*oi)->size(); i > 0; --i) + { + OperInfo *o = (*oi)->at(i - 1); + + if (o->info.equals_ci(info)) + { + delete o; + found = true; + break; + } + } + + if (!found) + { + source.Reply(_("No such info \"%s\" on \002%s\002."), info.c_str(), target.c_str()); + } + else + { + if ((*oi)->empty()) + e->Shrink("operinfo"); + + source.Reply(_("Deleted info from \002%s\002."), target.c_str()); + Log(LOG_ADMIN, source, this) << "to remove information from " << target; + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + } + } + else if (cmd.equals_ci("CLEAR")) + { + OperInfos *oi = e->GetExt("operinfo"); + + if (!oi) + { + source.Reply(_("Oper info list for \002%s\002 is empty."), target.c_str()); + return; + } + + e->Shrink("operinfo"); + + source.Reply(_("Cleared info from \002%s\002."), target.c_str()); + Log(LOG_ADMIN, source, this) << "to clear information for " << target; + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + } + else + { + this->OnSyntaxError(source, cmd); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Add or delete oper information for a given nick or channel.\n" + "This will show to opers in the respective info command for\n" + "the nick or channel.")); + return true; + } +}; + +class OSInfo : public Module +{ + CommandOSInfo commandosinfo; + ExtensibleItem oinfo; + Serialize::Type oinfo_type; + + void OnInfo(CommandSource &source, Extensible *e, InfoFormatter &info) + { + if (!source.IsOper()) + return; + + OperInfos *oi = oinfo.Get(e); + if (!oi) + return; + + for (unsigned i = 0; i < (*oi)->size(); ++i) + { + OperInfo *o = (*oi)->at(i); + info[_("Oper Info")] = Anope::printf(_("(by %s on %s) %s"), o->adder.c_str(), Anope::strftime(o->created, source.GetAccount(), true).c_str(), o->info.c_str()); + } + } + + public: + OSInfo(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosinfo(this), oinfo(this, "operinfo"), oinfo_type("OperInfo", OperInfo::Unserialize) + { + + } + + void OnNickInfo(CommandSource &source, NickAlias *na, InfoFormatter &info, bool show_hidden) anope_override + { + OnInfo(source, na->nc, info); + } + + void OnChanInfo(CommandSource &source, ChannelInfo *ci, InfoFormatter &info, bool show_hidden) anope_override + { + OnInfo(source, ci, info); + } +}; + +MODULE_INIT(OSInfo) diff --git a/modules/commands/os_jupe.cpp b/modules/commands/os_jupe.cpp new file mode 100644 index 0000000..6807f7a --- /dev/null +++ b/modules/commands/os_jupe.cpp @@ -0,0 +1,80 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSJupe : public Command +{ + public: + CommandOSJupe(Module *creator) : Command(creator, "operserv/jupe", 1, 2) + { + this->SetDesc(_("\"Jupiter\" a server")); + this->SetSyntax(_("\037server\037 [\037reason\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &jserver = params[0]; + const Anope::string &reason = params.size() > 1 ? params[1] : ""; + Server *server = Server::Find(jserver, true); + + if (!IRCD->IsHostValid(jserver) || jserver.find('.') == Anope::string::npos) + source.Reply(_("Please use a valid server name when juping.")); + else if (server == Me || server == Servers::GetUplink()) + source.Reply(_("You can not jupe your Services' pseudoserver or your uplink server.")); + else if (server && server->IsJuped()) + source.Reply(_("You can not jupe an already juped server.")); + else + { + Anope::string rbuf = "Juped by " + source.GetNick() + (!reason.empty() ? ": " + reason : ""); + /* Generate the new sid before quitting the old server, so they can't collide */ + Anope::string sid = IRCD->SID_Retrieve(); + if (server) + { + IRCD->SendSquit(server, rbuf); + server->Delete(rbuf); + } + Server *juped_server = new Server(Me, jserver, 1, rbuf, sid, true); + IRCD->SendServer(juped_server); + + Log(LOG_ADMIN, source, this) << "on " << jserver << " (" << rbuf << ")"; + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Tells Services to jupiter a server -- that is, to create\n" + "a fake \"server\" connected to Services which prevents\n" + "the real server of that name from connecting. The jupe\n" + "may be removed using a standard \002SQUIT\002. If a reason is\n" + "given, it is placed in the server information field;\n" + "otherwise, the server information field will contain the\n" + "text \"Juped by \", showing the nickname of the\n" + "person who jupitered the server.")); + return true; + } +}; + +class OSJupe : public Module +{ + CommandOSJupe commandosjupe; + + public: + OSJupe(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosjupe(this) + { + + } +}; + +MODULE_INIT(OSJupe) diff --git a/modules/commands/os_kick.cpp b/modules/commands/os_kick.cpp new file mode 100644 index 0000000..b0fde97 --- /dev/null +++ b/modules/commands/os_kick.cpp @@ -0,0 +1,84 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSKick : public Command +{ + public: + CommandOSKick(Module *creator) : Command(creator, "operserv/kick", 3, 3) + { + this->SetDesc(_("Kick a user from a channel")); + this->SetSyntax(_("\037channel\037 \037user\037 \037reason\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &chan = params[0]; + const Anope::string &nick = params[1]; + const Anope::string &s = params[2]; + Channel *c; + User *u2; + + if (!(c = Channel::Find(chan))) + { + source.Reply(CHAN_X_NOT_IN_USE, chan.c_str()); + return; + } + + if (c->bouncy_modes) + { + source.Reply(_("Services is unable to change modes. Are your servers' U:lines configured correctly?")); + return; + } + + if (!(u2 = User::Find(nick, true))) + { + source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); + return; + } + + if (!c->Kick(source.service, u2, "%s (%s)", source.GetNick().c_str(), s.c_str())) + { + source.Reply(ACCESS_DENIED); + return; + } + + Log(LOG_ADMIN, source, this) << "on " << u2->nick << " in " << c->name << " (" << s << ")"; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows staff to kick a user from any channel.\n" + "Parameters are the same as for the standard /KICK\n" + "command. The kick message will have the nickname of the\n" + "IRCop sending the KICK command prepended; for example:\n" + " \n" + "*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))"), source.service->nick.c_str()); + return true; + } +}; + +class OSKick : public Module +{ + CommandOSKick commandoskick; + + public: + OSKick(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandoskick(this) + { + + } +}; + +MODULE_INIT(OSKick) diff --git a/modules/commands/os_kill.cpp b/modules/commands/os_kill.cpp new file mode 100644 index 0000000..6413fec --- /dev/null +++ b/modules/commands/os_kill.cpp @@ -0,0 +1,67 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSKill : public Command +{ + public: + CommandOSKill(Module *creator) : Command(creator, "operserv/kill", 1, 2) + { + this->SetDesc(_("Kill a user")); + this->SetSyntax(_("\037user\037 [\037reason\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &nick = params[0]; + Anope::string reason = params.size() > 1 ? params[1] : ""; + + User *u2 = User::Find(nick, true); + if (u2 == NULL) + source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); + else if (u2->IsProtected() || u2->server == Me) + source.Reply(ACCESS_DENIED); + else + { + if (reason.empty()) + reason = "No reason specified"; + if (Config->GetModule("operserv")->Get("addakiller")) + reason = "(" + source.GetNick() + ") " + reason; + Log(LOG_ADMIN, source, this) << "on " << u2->nick << " for " << reason; + u2->Kill(*source.service, reason); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows you to kill a user from the network.\n" + "Parameters are the same as for the standard /KILL\n" + "command.")); + return true; + } +}; + +class OSKill : public Module +{ + CommandOSKill commandoskill; + + public: + OSKill(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandoskill(this) + { + + } +}; + +MODULE_INIT(OSKill) diff --git a/modules/commands/os_list.cpp b/modules/commands/os_list.cpp new file mode 100644 index 0000000..f7acf46 --- /dev/null +++ b/modules/commands/os_list.cpp @@ -0,0 +1,276 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSChanList : public Command +{ + public: + CommandOSChanList(Module *creator) : Command(creator, "operserv/chanlist", 0, 2) + { + this->SetDesc(_("Lists all channel records")); + this->SetSyntax(_("[{\037pattern\037 | \037nick\037} [\037SECRET\037]]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &pattern = !params.empty() ? params[0] : ""; + const Anope::string &opt = params.size() > 1 ? params[1] : ""; + std::set modes; + User *u2; + unsigned int count = 0; + + if (!pattern.empty()) + Log(LOG_ADMIN, source, this) << "for " << pattern; + else + Log(LOG_ADMIN, source, this); + + if (!opt.empty() && opt.equals_ci("SECRET")) + { + modes.insert("SECRET"); + modes.insert("PRIVATE"); + } + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Name")).AddColumn(_("Users")).AddColumn(_("Modes")).AddColumn(_("Topic")); + + if (!pattern.empty() && (u2 = User::Find(pattern, true))) + { + source.Reply(_("\002%s\002 channel list:"), u2->nick.c_str()); + + for (User::ChanUserList::iterator uit = u2->chans.begin(), uit_end = u2->chans.end(); uit != uit_end; ++uit) + { + ChanUserContainer *cc = uit->second; + + if (!modes.empty()) + for (std::set::iterator it = modes.begin(), it_end = modes.end(); it != it_end; ++it) + if (!cc->chan->HasMode(*it)) + continue; + + ListFormatter::ListEntry entry; + entry["Name"] = cc->chan->name; + entry["Users"] = stringify(cc->chan->users.size()); + entry["Modes"] = cc->chan->GetModes(true, true); + entry["Topic"] = cc->chan->topic; + list.AddEntry(entry); + + ++count; + } + } + else + { + source.Reply(_("Channel list:")); + + for (channel_map::const_iterator cit = ChannelList.begin(), cit_end = ChannelList.end(); cit != cit_end; ++cit) + { + Channel *c = cit->second; + + if (!pattern.empty() && !Anope::Match(c->name, pattern, false, true)) + continue; + if (!modes.empty()) + for (std::set::iterator it = modes.begin(), it_end = modes.end(); it != it_end; ++it) + if (!c->HasMode(*it)) + continue; + + ListFormatter::ListEntry entry; + entry["Name"] = c->name; + entry["Users"] = stringify(c->users.size()); + entry["Modes"] = c->GetModes(true, true); + entry["Topic"] = c->topic; + list.AddEntry(entry); + + ++count; + } + } + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("End of channel list. \002%u\002 channels shown."), count); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Lists all channels currently in use on the IRC network, whether they\n" + "are registered or not.\n" + " \n" + "If \002pattern\002 is given, lists only channels that match it. If a nickname\n" + "is given, lists only the channels the user using it is on. If SECRET is\n" + "specified, lists only channels matching \002pattern\002 that have the +s or\n" + "+p mode.")); + + const Anope::string ®exengine = Config->GetBlock("options")->Get("regexengine"); + if (!regexengine.empty()) + { + source.Reply(" "); + source.Reply(_("Regex matches are also supported using the %s engine.\n" + "Enclose your pattern in // if this is desired."), regexengine.c_str()); + } + + return true; + } +}; + +class CommandOSUserList : public Command +{ + public: + CommandOSUserList(Module *creator) : Command(creator, "operserv/userlist", 0, 2) + { + this->SetDesc(_("Lists all user records")); + this->SetSyntax(_("[{\037pattern\037 | \037channel\037} [\037INVISIBLE\037]]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &pattern = !params.empty() ? params[0] : ""; + const Anope::string &opt = params.size() > 1 ? params[1] : ""; + Channel *c; + std::set modes; + unsigned int count = 0; + + if (!pattern.empty()) + Log(LOG_ADMIN, source, this) << "for " << pattern; + else + Log(LOG_ADMIN, source, this); + + if (!opt.empty() && opt.equals_ci("INVISIBLE")) + modes.insert("INVIS"); + + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Name")).AddColumn(_("Mask")).AddColumn(_("Realname")); + + if (!pattern.empty() && (c = Channel::Find(pattern))) + { + source.Reply(_("\002%s\002 users list:"), pattern.c_str()); + + for (Channel::ChanUserList::iterator cuit = c->users.begin(), cuit_end = c->users.end(); cuit != cuit_end; ++cuit) + { + ChanUserContainer *uc = cuit->second; + + if (!modes.empty()) + for (std::set::iterator it = modes.begin(), it_end = modes.end(); it != it_end; ++it) + if (!uc->user->HasMode(*it)) + continue; + + ListFormatter::ListEntry entry; + entry["Name"] = uc->user->nick; + entry["Mask"] = uc->user->GetIdent() + "@" + uc->user->GetDisplayedHost(); + entry["Realname"] = uc->user->realname; + list.AddEntry(entry); + + ++count; + } + } + else + { + /* Historically this has been ordered, so... */ + Anope::map ordered_map; + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + ordered_map[it->first] = it->second; + + source.Reply(_("Users list:")); + + for (Anope::map::const_iterator it = ordered_map.begin(); it != ordered_map.end(); ++it) + { + User *u2 = it->second; + + if (!pattern.empty()) + { + /* check displayed host, host, and ip */ + Anope::string masks[] = { + u2->nick + "!" + u2->GetIdent() + "@" + u2->GetDisplayedHost(), + u2->nick + "!" + u2->GetIdent() + "@" + u2->host, + u2->nick + "!" + u2->GetIdent() + "@" + u2->ip.addr() + }; + + bool match = false; + for (unsigned int i = 0; i < sizeof(masks) / sizeof(*masks); ++i) + { + /* Check mask with realname included, too */ + if (Anope::Match(masks[i], pattern, false, true) || Anope::Match(masks[i] + "#" + u2->realname, pattern, false, true)) + { + match = true; + break; + } + } + + if (!match) + continue; + + if (!modes.empty()) + for (std::set::iterator mit = modes.begin(), mit_end = modes.end(); mit != mit_end; ++mit) + if (!u2->HasMode(*mit)) + continue; + } + + ListFormatter::ListEntry entry; + entry["Name"] = u2->nick; + entry["Mask"] = u2->GetIdent() + "@" + u2->GetDisplayedHost(); + entry["Realname"] = u2->realname; + list.AddEntry(entry); + + ++count; + } + } + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("End of users list. \002%u\002 users shown."), count); + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Lists all users currently online on the IRC network, whether their\n" + "nick is registered or not.\n" + " \n" + "If \002pattern\002 is given, lists only users that match it (it must be in\n" + "the format nick!user@host[#realname]). If \002channel\002 is given, lists\n" + "only users that are on the given channel. If INVISIBLE is specified, only users\n" + "with the +i flag will be listed.")); + + const Anope::string ®exengine = Config->GetBlock("options")->Get("regexengine"); + if (!regexengine.empty()) + { + source.Reply(" "); + source.Reply(_("Regex matches are also supported using the %s engine.\n" + "Enclose your pattern in // if this is desired."), regexengine.c_str()); + } + + return true; + } +}; + +class OSList : public Module +{ + CommandOSChanList commandoschanlist; + CommandOSUserList commandosuserlist; + + public: + OSList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandoschanlist(this), commandosuserlist(this) + { + + } +}; + +MODULE_INIT(OSList) diff --git a/modules/commands/os_login.cpp b/modules/commands/os_login.cpp new file mode 100644 index 0000000..cb6f056 --- /dev/null +++ b/modules/commands/os_login.cpp @@ -0,0 +1,132 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSLogin : public Command +{ + public: + CommandOSLogin(Module *creator) : Command(creator, "operserv/login", 1, 1) + { + this->SetSyntax(_("\037password\037")); + this->RequireUser(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &password = params[0]; + + User *u = source.GetUser(); + Oper *o = source.nc->o; + if (o == NULL) + source.Reply(_("No oper block for your nick.")); + else if (o->password.empty()) + source.Reply(_("Your oper block doesn't require logging in.")); + else if (u->HasExt("os_login")) + source.Reply(_("You are already identified.")); + else if (o->password != password) + { + source.Reply(PASSWORD_INCORRECT); + u->BadPassword(); + } + else + { + Log(LOG_ADMIN, source, this) << "and successfully identified to " << source.service->nick; + u->Extend("os_login"); + source.Reply(_("Password accepted.")); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Logs you in to %s so you gain Services Operator privileges.\n" + "This command may be unnecessary if your oper block is\n" + "configured without a password."), source.service->nick.c_str()); + return true; + } + + const Anope::string GetDesc(CommandSource &source) const anope_override + { + return Anope::printf(Language::Translate(source.GetAccount(), _("Login to %s")), source.service->nick.c_str()); + } +}; + +class CommandOSLogout : public Command +{ + public: + CommandOSLogout(Module *creator) : Command(creator, "operserv/logout", 0, 0) + { + this->RequireUser(true); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + Oper *o = source.nc->o; + if (o == NULL) + source.Reply(_("No oper block for your nick.")); + else if (o->password.empty()) + source.Reply(_("Your oper block doesn't require logging in.")); + else if (!u->HasExt("os_login")) + source.Reply(_("You are not identified.")); + else + { + Log(LOG_ADMIN, source, this); + u->Shrink("os_login"); + source.Reply(_("You have been logged out.")); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Logs you out from %s so you lose Services Operator privileges.\n" + "This command is only useful if your oper block is configured\n" + "with a password."), source.service->nick.c_str()); + return true; + } + + const Anope::string GetDesc(CommandSource &source) const anope_override + { + return Anope::printf(Language::Translate(source.GetAccount(), _("Logout from %s")), source.service->nick.c_str()); + } +}; + +class OSLogin : public Module +{ + CommandOSLogin commandoslogin; + CommandOSLogout commandoslogout; + ExtensibleItem os_login; + + public: + OSLogin(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandoslogin(this), commandoslogout(this), os_login(this, "os_login") + { + + } + + EventReturn IsServicesOper(User *u) anope_override + { + if (!u->Account()->o->password.empty()) + { + if (os_login.HasExt(u)) + return EVENT_ALLOW; + return EVENT_STOP; + } + + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(OSLogin) diff --git a/modules/commands/os_logsearch.cpp b/modules/commands/os_logsearch.cpp new file mode 100644 index 0000000..231373e --- /dev/null +++ b/modules/commands/os_logsearch.cpp @@ -0,0 +1,185 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +static unsigned int HARDMAX = 65536; + +class CommandOSLogSearch : public Command +{ + static inline Anope::string CreateLogName(const Anope::string &file, time_t t = Anope::CurTime) + { + char timestamp[32]; + + tm *tm = localtime(&t); + + strftime(timestamp, sizeof(timestamp), "%Y%m%d", tm); + + return Anope::LogDir + "/" + file + "." + timestamp; + } + + public: + CommandOSLogSearch(Module *creator) : Command(creator, "operserv/logsearch", 1, 3) + { + this->SetDesc(_("Searches logs for a matching pattern")); + this->SetSyntax(_("[+\037days\037d] [+\037limit\037l] \037pattern\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + int days = 7, replies = 50; + + unsigned i; + for (i = 0; i < params.size() && params[i][0] == '+'; ++i) + { + switch (params[i][params[i].length() - 1]) + { + case 'd': + if (params[i].length() > 2) + { + Anope::string dur = params[i].substr(1, params[i].length() - 2); + try + { + days = convertTo(dur); + if (days <= 0) + throw ConvertException(); + } + catch (const ConvertException &) + { + source.Reply(_("Invalid duration %s, using %d days."), dur.c_str(), days); + } + } + break; + case 'l': + if (params[i].length() > 2) + { + Anope::string dur = params[i].substr(1, params[i].length() - 2); + try + { + replies = convertTo(dur); + if (replies <= 0) + throw ConvertException(); + } + catch (const ConvertException &) + { + source.Reply(_("Invalid limit %s, using %d."), dur.c_str(), replies); + } + } + break; + default: + source.Reply(_("Unknown parameter: %s"), params[i].c_str()); + } + } + + if (i >= params.size()) + { + this->OnSyntaxError(source, ""); + return; + } + + Anope::string search_string = params[i++]; + for (; i < params.size(); ++i) + search_string += " " + params[i]; + + Log(LOG_ADMIN, source, this) << "for " << search_string; + + bool wildcard = search_string.find_first_of("?*") != Anope::string::npos; + bool regex = search_string.empty() == false && search_string[0] == '/' && search_string[search_string.length() - 1] == '/'; + + const Anope::string &logfile_name = Config->GetModule(this->owner)->Get("logname"); + std::vector matches; + for (int d = days - 1; d >= 0; --d) + { + Anope::string lf_name = CreateLogName(logfile_name, Anope::CurTime - (d * 86400)); + Log(LOG_DEBUG) << "Searching " << lf_name; + std::fstream fd(lf_name.c_str(), std::ios_base::in); + if (!fd.is_open()) + continue; + + for (Anope::string buf, token; std::getline(fd, buf.str());) + { + bool match = false; + + if (regex) + match = Anope::Match(buf, search_string, false, true); + else if (wildcard) + match = Anope::Match(buf, "*" + search_string + "*"); + else + match = buf.find_ci(search_string) != Anope::string::npos; + + if (match) + { + matches.push_back(buf); + + if (matches.size() >= HARDMAX) + break; + } + } + + fd.close(); + } + + unsigned int found = matches.size(); + if (!found) + { + source.Reply(_("No matches for \002%s\002 found."), search_string.c_str()); + return; + } + + if (matches.size() >= HARDMAX) + { + source.Reply(_("Too many results for \002%s\002."), search_string.c_str()); + return; + } + + if (matches.size() > static_cast(replies)) + { + matches.erase(matches.begin(), matches.begin() + (matches.size() - static_cast(replies))); + } + + source.Reply(_("Matches for \002%s\002:"), search_string.c_str()); + unsigned int count = 0; + for (std::vector::iterator it = matches.begin(), it_end = matches.end(); it != it_end; ++it) + source.Reply("#%d: %s", ++count, it->c_str()); + source.Reply(_("Showed %d/%d matches for \002%s\002."), matches.size(), found, search_string.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command searches the Services logfiles for messages\n" + "that match the given pattern. The day and limit argument\n" + "may be used to specify how many days of logs to search\n" + "and the number of replies to limit to. By default this\n" + "command searches one week of logs, and limits replies\n" + "to 50.\n" + " \n" + "For example:\n" + " \002LOGSEARCH +21d +500l Anope\002\n" + " Searches the last 21 days worth of logs for messages\n" + " containing Anope and lists the most recent 500 of them.")); + return true; + } +}; + +class OSLogSearch : public Module +{ + CommandOSLogSearch commandoslogsearch; + + public: + OSLogSearch(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandoslogsearch(this) + { + } +}; + +MODULE_INIT(OSLogSearch) diff --git a/modules/commands/os_mode.cpp b/modules/commands/os_mode.cpp new file mode 100644 index 0000000..4d9cbb4 --- /dev/null +++ b/modules/commands/os_mode.cpp @@ -0,0 +1,192 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSMode : public Command +{ + public: + CommandOSMode(Module *creator) : Command(creator, "operserv/mode", 2, 3) + { + this->SetDesc(_("Change channel modes")); + this->SetSyntax(_("\037channel\037 \037modes\037")); + this->SetSyntax(_("\037channel\037 CLEAR [ALL]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &target = params[0]; + const Anope::string &modes = params[1]; + + Reference c = Channel::Find(target); + if (!c) + source.Reply(CHAN_X_NOT_IN_USE, target.c_str()); + else if (c->bouncy_modes) + source.Reply(_("Services is unable to change modes. Are your servers' U:lines configured correctly?")); + else if (modes.equals_ci("CLEAR")) + { + bool all = params.size() > 2 && params[2].equals_ci("ALL"); + + const Channel::ModeList chmodes = c->GetModes(); + for (Channel::ModeList::const_iterator it = chmodes.begin(), it_end = chmodes.end(); it != it_end && c; ++it) + c->RemoveMode(c->ci->WhoSends(), it->first, it->second, false); + + if (!c) + { + source.Reply(_("Modes cleared on %s and the channel destroyed."), target.c_str()); + return; + } + + if (all) + { + for (Channel::ChanUserList::iterator it = c->users.begin(), it_end = c->users.end(); it != it_end; ++it) + { + ChanUserContainer *uc = it->second; + + if (uc->user->HasMode("OPER")) + continue; + + for (size_t i = uc->status.Modes().length(); i > 0; --i) + c->RemoveMode(c->ci->WhoSends(), ModeManager::FindChannelModeByChar(uc->status.Modes()[i - 1]), uc->user->GetUID(), false); + } + + source.Reply(_("All modes cleared on %s."), c->name.c_str()); + } + else + source.Reply(_("Non-status modes cleared on %s."), c->name.c_str()); + } + else + { + spacesepstream sep(modes + (params.size() > 2 ? " " + params[2] : "")); + Anope::string mode; + int add = 1; + Anope::string log_modes, log_params; + + sep.GetToken(mode); + for (unsigned i = 0; i < mode.length() && c; ++i) + { + char ch = mode[i]; + + if (ch == '+') + { + add = 1; + log_modes += "+"; + continue; + } + else if (ch == '-') + { + add = 0; + log_modes += "-"; + continue; + } + + ChannelMode *cm = ModeManager::FindChannelModeByChar(ch); + if (!cm) + continue; + + Anope::string param, param_log; + if (cm->type != MODE_REGULAR) + { + if (cm->type == MODE_PARAM && !add && anope_dynamic_static_cast(cm)->minus_no_arg) + ; + else if (!sep.GetToken(param)) + continue; + + param_log = param; + + if (cm->type == MODE_STATUS) + { + User *targ = User::Find(param, true); + if (targ == NULL || c->FindUser(targ) == NULL) + continue; + param = targ->GetUID(); + } + } + + log_modes += cm->mchar; + if (!param.empty()) + log_params += " " + param_log; + + if (add) + c->SetMode(source.service, cm, param, false); + else + c->RemoveMode(source.service, cm, param, false); + } + + if (!log_modes.replace_all_cs("+", "").replace_all_cs("-", "").empty()) + Log(LOG_ADMIN, source, this) << log_modes << log_params << " on " << (c ? c->name : target); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows Services Operators to change modes for any channel.\n" + "Parameters are the same as for the standard /MODE command.\n" + "Alternatively, CLEAR may be given to clear all modes on the channel.\n" + "If CLEAR ALL is given then all modes, including user status, is removed.")); + return true; + } +}; + +class CommandOSUMode : public Command +{ + public: + CommandOSUMode(Module *creator) : Command(creator, "operserv/umode", 2, 2) + { + this->SetDesc(_("Change user modes")); + this->SetSyntax(_("\037user\037 \037modes\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &target = params[0]; + const Anope::string &modes = params[1]; + + User *u2 = User::Find(target, true); + if (!u2) + source.Reply(NICK_X_NOT_IN_USE, target.c_str()); + else + { + u2->SetModes(source.service, "%s", modes.c_str()); + source.Reply(_("Changed usermodes of \002%s\002 to %s."), u2->nick.c_str(), modes.c_str()); + + u2->SendMessage(source.service, _("\002%s\002 changed your usermodes to %s."), source.GetNick().c_str(), modes.c_str()); + + Log(LOG_ADMIN, source, this) << modes << " on " << target; + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows Services Operators to change modes for any user.\n" + "Parameters are the same as for the standard /MODE command.")); + return true; + } +}; + +class OSMode : public Module +{ + CommandOSMode commandosmode; + CommandOSUMode commandosumode; + + public: + OSMode(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosmode(this), commandosumode(this) + { + + } +}; + +MODULE_INIT(OSMode) diff --git a/modules/commands/os_modinfo.cpp b/modules/commands/os_modinfo.cpp new file mode 100644 index 0000000..a75aa4a --- /dev/null +++ b/modules/commands/os_modinfo.cpp @@ -0,0 +1,214 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSModInfo : public Command +{ + public: + CommandOSModInfo(Module *creator) : Command(creator, "operserv/modinfo", 1, 1) + { + this->SetDesc(_("Info about a loaded module")); + this->SetSyntax(_("\037modname\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &file = params[0]; + + Log(LOG_ADMIN, source, this) << "on " << file; + + Module *m = ModuleManager::FindModule(file); + if (m) + { + source.Reply(_("Module: \002%s\002 Version: \002%s\002 Author: \002%s\002 Loaded: \002%s\002"), m->name.c_str(), !m->version.empty() ? m->version.c_str() : "?", !m->author.empty() ? m->author.c_str() : "Unknown", Anope::strftime(m->created, source.GetAccount()).c_str()); + if (Anope::Debug) + source.Reply(_(" Loaded at: %p"), m->handle); + + std::vector servicekeys = Service::GetServiceKeys("Command"); + for (unsigned i = 0; i < servicekeys.size(); ++i) + { + ServiceReference c("Command", servicekeys[i]); + if (!c || c->owner != m) + continue; + + source.Reply(_(" Providing service: \002%s\002"), c->name.c_str()); + + for (botinfo_map::const_iterator it = BotListByNick->begin(), it_end = BotListByNick->end(); it != it_end; ++it) + { + const BotInfo *bi = it->second; + + for (CommandInfo::map::const_iterator cit = bi->commands.begin(), cit_end = bi->commands.end(); cit != cit_end; ++cit) + { + const Anope::string &c_name = cit->first; + const CommandInfo &info = cit->second; + if (info.name != c->name) + continue; + source.Reply(_(" Command \002%s\002 on \002%s\002 is linked to \002%s\002"), c_name.c_str(), bi->nick.c_str(), c->name.c_str()); + } + } + } + } + else + source.Reply(_("No information about module \002%s\002 is available."), file.c_str()); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command lists information about the specified loaded module.")); + return true; + } +}; + +class CommandOSModList : public Command +{ + public: + CommandOSModList(Module *creator) : Command(creator, "operserv/modlist", 0, 1) + { + this->SetDesc(_("List loaded modules")); + this->SetSyntax("[all|third|vendor|extra|database|encryption|pseudoclient|protocol]"); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string ¶m = !params.empty() ? params[0] : ""; + + if (!param.empty()) + Log(LOG_ADMIN, source, this) << "for " << param; + else + Log(LOG_ADMIN, source, this); + + bool third = false, vendor = false, extra = false, database = false, encryption = false, pseudoclient = false, protocol = false; + + if (param.equals_ci("all")) + third = vendor = extra = database = encryption = pseudoclient = protocol = true; + else if (param.equals_ci("third")) + third = true; + else if (param.equals_ci("vendor")) + vendor = true; + else if (param.equals_ci("extra")) + extra = true; + else if (param.equals_ci("database")) + database = true; + else if (param.equals_ci("encryption")) + encryption = true; + else if (param.equals_ci("pseudoclient")) + pseudoclient = true; + else if (param.equals_ci("protocol")) + protocol = true; + else + third = extra = database = encryption = protocol = true; + + Module *protomod = ModuleManager::FindFirstOf(PROTOCOL); + + source.Reply(_("Current module list:")); + + int count = 0; + for (std::list::iterator it = ModuleManager::Modules.begin(), it_end = ModuleManager::Modules.end(); it != it_end; ++it) + { + Module *m = *it; + + bool show = false; + Anope::string mtype; + + if (m->type & PROTOCOL) + { + show |= protocol; + if (!mtype.empty()) + mtype += ", "; + mtype += "Protocol"; + } + if (m->type & PSEUDOCLIENT) + { + show |= pseudoclient; + if (!mtype.empty()) + mtype += ", "; + mtype += "Pseudoclient"; + } + if (m->type & ENCRYPTION) + { + show |= encryption; + if (!mtype.empty()) + mtype += ", "; + mtype += "Encryption"; + } + if (m->type & DATABASE) + { + show |= database; + if (!mtype.empty()) + mtype += ", "; + mtype += "Database"; + } + if (m->type & EXTRA) + { + show |= extra; + if (!mtype.empty()) + mtype += ", "; + mtype += "Extra"; + } + if (m->type & VENDOR) + { + show |= vendor; + if (!mtype.empty()) + mtype += ", "; + mtype += "Vendor"; + } + if (m->type & THIRD) + { + show |= third; + if (!mtype.empty()) + mtype += ", "; + mtype += "Third"; + } + + if (!show) + continue; + else if (m->type & PROTOCOL && param.empty() && m != protomod) + continue; + + ++count; + + source.Reply(_("Module: \002%s\002 [%s] [%s]"), m->name.c_str(), m->version.c_str(), mtype.c_str()); + } + + if (!count) + source.Reply(_("No modules currently loaded matching that criteria.")); + else + source.Reply(_("%d modules loaded."), count); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Lists currently loaded modules.")); + return true; + } +}; + +class OSModInfo : public Module +{ + CommandOSModInfo commandosmodinfo; + CommandOSModList commandosmodlist; + + public: + OSModInfo(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosmodinfo(this), commandosmodlist(this) + { + + } +}; + +MODULE_INIT(OSModInfo) diff --git a/modules/commands/os_module.cpp b/modules/commands/os_module.cpp new file mode 100644 index 0000000..1d0d5ee --- /dev/null +++ b/modules/commands/os_module.cpp @@ -0,0 +1,188 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSModLoad : public Command +{ + public: + CommandOSModLoad(Module *creator) : Command(creator, "operserv/modload", 1, 1) + { + this->SetDesc(_("Load a module")); + this->SetSyntax(_("\037modname\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &mname = params[0]; + + ModuleReturn status = ModuleManager::LoadModule(mname, source.GetUser()); + if (status == MOD_ERR_OK) + { + Log(LOG_ADMIN, source, this) << "to load module " << mname; + source.Reply(_("Module \002%s\002 loaded."), mname.c_str()); + } + else if (status == MOD_ERR_EXISTS) + source.Reply(_("Module \002%s\002 is already loaded."), mname.c_str()); + else + source.Reply(_("Unable to load module \002%s\002."), mname.c_str()); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command loads the module named \037modname\037 from the modules\n" + "directory.")); + return true; + } +}; + +class CommandOSModReLoad : public Command +{ + public: + CommandOSModReLoad(Module *creator) : Command(creator, "operserv/modreload", 1, 1) + { + this->SetDesc(_("Reload a module")); + this->SetSyntax(_("\037modname\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &mname = params[0]; + + Module *m = ModuleManager::FindModule(mname); + if (!m) + { + source.Reply(_("Module \002%s\002 isn't loaded."), mname.c_str()); + return; + } + + if (!m->handle || m->GetPermanent()) + { + source.Reply(_("Unable to remove module \002%s\002."), m->name.c_str()); + return; + } + + Module *protocol = ModuleManager::FindFirstOf(PROTOCOL); + if (m->type == PROTOCOL && m != protocol) + { + source.Reply(_("You can not reload this module directly, instead reload %s."), protocol ? protocol->name.c_str() : "(unknown)"); + return; + } + + /* Unrecoverable */ + bool fatal = m->type == PROTOCOL; + ModuleReturn status = ModuleManager::UnloadModule(m, source.GetUser()); + + if (status != MOD_ERR_OK) + { + source.Reply(_("Unable to remove module \002%s\002."), mname.c_str()); + return; + } + + status = ModuleManager::LoadModule(mname, source.GetUser()); + if (status == MOD_ERR_OK) + { + Log(LOG_ADMIN, source, this) << "to reload module " << mname; + source.Reply(_("Module \002%s\002 reloaded."), mname.c_str()); + } + else + { + if (fatal) + { + Anope::QuitReason = "Unable to reload module " + mname; + Anope::Quitting = true; + } + else + source.Reply(_("Unable to load module \002%s\002."), mname.c_str()); + } + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command reloads the module named \037modname\037.")); + return true; + } +}; + +class CommandOSModUnLoad : public Command +{ + public: + CommandOSModUnLoad(Module *creator) : Command(creator, "operserv/modunload", 1, 1) + { + this->SetDesc(_("Un-Load a module")); + this->SetSyntax(_("\037modname\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &mname = params[0]; + + Module *m = ModuleManager::FindModule(mname); + if (!m) + { + source.Reply(_("Module \002%s\002 isn't loaded."), mname.c_str()); + return; + } + + if (!m->handle || m->GetPermanent() || m->type == PROTOCOL) + { + source.Reply(_("Unable to remove module \002%s\002."), m->name.c_str()); + return; + } + + Log(this->owner) << "Trying to unload module [" << mname << "]"; + + ModuleReturn status = ModuleManager::UnloadModule(m, source.GetUser()); + + if (status == MOD_ERR_OK) + { + Log(LOG_ADMIN, source, this) << "to unload module " << mname; + source.Reply(_("Module \002%s\002 unloaded."), mname.c_str()); + } + else + source.Reply(_("Unable to remove module \002%s\002."), mname.c_str()); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("This command unloads the module named \037modname\037.")); + return true; + } +}; + +class OSModule : public Module +{ + CommandOSModLoad commandosmodload; + CommandOSModReLoad commandosmodreload; + CommandOSModUnLoad commandosmodunload; + + public: + OSModule(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosmodload(this), commandosmodreload(this), commandosmodunload(this) + { + this->SetPermanent(true); + + } +}; + +MODULE_INIT(OSModule) diff --git a/modules/commands/os_news.cpp b/modules/commands/os_news.cpp new file mode 100644 index 0000000..3bc0200 --- /dev/null +++ b/modules/commands/os_news.cpp @@ -0,0 +1,464 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/os_news.h" + +/* List of messages for each news type. This simplifies message sending. */ + +enum +{ + MSG_SYNTAX, + MSG_LIST_HEADER, + MSG_LIST_NONE, + MSG_ADDED, + MSG_DEL_NOT_FOUND, + MSG_DELETED, + MSG_DEL_NONE, + MSG_DELETED_ALL +}; + +struct NewsMessages msgarray[] = { + {NEWS_LOGON, "LOGON", + {_("LOGONNEWS {ADD|DEL|LIST} [\037text\037|\037num\037]\002"), + _("Logon news items:"), + _("There is no logon news."), + _("Added new logon news item."), + _("Logon news item #%s not found!"), + _("Logon news item #%d deleted."), + _("No logon news items to delete!"), + _("All logon news items deleted.")} + }, + {NEWS_OPER, "OPER", + {_("OPERNEWS {ADD|DEL|LIST} [\037text\037|\037num\037]\002"), + _("Oper news items:"), + _("There is no oper news."), + _("Added new oper news item."), + _("Oper news item #%s not found!"), + _("Oper news item #%d deleted."), + _("No oper news items to delete!"), + _("All oper news items deleted.")} + }, + {NEWS_RANDOM, "RANDOM", + {_("RANDOMNEWS {ADD|DEL|LIST} [\037text\037|\037num\037]\002"), + _("Random news items:"), + _("There is no random news."), + _("Added new random news item."), + _("Random news item #%s not found!"), + _("Random news item #%d deleted."), + _("No random news items to delete!"), + _("All random news items deleted.")} + } +}; + +struct MyNewsItem : NewsItem +{ + void Serialize(Serialize::Data &data) const anope_override + { + data["type"] << this->type; + data["text"] << this->text; + data["who"] << this->who; + data["time"] << this->time; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data) + { + if (!news_service) + return NULL; + + NewsItem *ni; + if (obj) + ni = anope_dynamic_static_cast(obj); + else + ni = new MyNewsItem(); + + unsigned int t; + data["type"] >> t; + ni->type = static_cast(t); + data["text"] >> ni->text; + data["who"] >> ni->who; + data["time"] >> ni->time; + + if (!obj) + news_service->AddNewsItem(ni); + return ni; + } +}; + +class MyNewsService : public NewsService +{ + std::vector newsItems[3]; + public: + MyNewsService(Module *m) : NewsService(m) { } + + ~MyNewsService() + { + for (unsigned i = 0; i < 3; ++i) + for (unsigned j = 0; j < newsItems[i].size(); ++j) + delete newsItems[i][j]; + } + + NewsItem *CreateNewsItem() anope_override + { + return new MyNewsItem(); + } + + void AddNewsItem(NewsItem *n) anope_override + { + this->newsItems[n->type].push_back(n); + } + + void DelNewsItem(NewsItem *n) anope_override + { + std::vector &list = this->GetNewsList(n->type); + std::vector::iterator it = std::find(list.begin(), list.end(), n); + if (it != list.end()) + list.erase(it); + delete n; + } + + std::vector &GetNewsList(NewsType t) anope_override + { + return this->newsItems[t]; + } +}; + +#define lenof(a) (sizeof(a) / sizeof(*(a))) +static const char **findmsgs(NewsType type) +{ + for (unsigned i = 0; i < lenof(msgarray); ++i) + if (msgarray[i].type == type) + return msgarray[i].msgs; + return NULL; +} + +class NewsBase : public Command +{ + ServiceReference ns; + + protected: + void DoList(CommandSource &source, NewsType ntype, const char **msgs) + { + std::vector &list = this->ns->GetNewsList(ntype); + if (list.empty()) + source.Reply(msgs[MSG_LIST_NONE]); + else + { + ListFormatter lflist(source.GetAccount()); + lflist.AddColumn(_("Number")).AddColumn(_("Creator")).AddColumn(_("Created")).AddColumn(_("Text")); + + for (unsigned i = 0, end = list.size(); i < end; ++i) + { + ListFormatter::ListEntry entry; + entry["Number"] = stringify(i + 1); + entry["Creator"] = list[i]->who; + entry["Created"] = Anope::strftime(list[i]->time, NULL, true); + entry["Text"] = list[i]->text; + lflist.AddEntry(entry); + } + + source.Reply(msgs[MSG_LIST_HEADER]); + + std::vector replies; + lflist.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + + source.Reply(_("End of news list.")); + } + + return; + } + + void DoAdd(CommandSource &source, const std::vector ¶ms, NewsType ntype, const char **msgs) + { + const Anope::string text = params.size() > 1 ? params[1] : ""; + + if (text.empty()) + this->OnSyntaxError(source, "ADD"); + else + { + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + NewsItem *news = new MyNewsItem(); + news->type = ntype; + news->text = text; + news->time = Anope::CurTime; + news->who = source.GetNick(); + + this->ns->AddNewsItem(news); + + source.Reply(msgs[MSG_ADDED]); + Log(LOG_ADMIN, source, this) << "to add a news item"; + } + + return; + } + + void DoDel(CommandSource &source, const std::vector ¶ms, NewsType ntype, const char **msgs) + { + const Anope::string &text = params.size() > 1 ? params[1] : ""; + + if (text.empty()) + this->OnSyntaxError(source, "DEL"); + else + { + std::vector &list = this->ns->GetNewsList(ntype); + if (list.empty()) + source.Reply(msgs[MSG_LIST_NONE]); + else + { + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + if (!text.equals_ci("ALL")) + { + try + { + unsigned num = convertTo(text); + if (num > 0 && num <= list.size()) + { + this->ns->DelNewsItem(list[num - 1]); + source.Reply(msgs[MSG_DELETED], num); + Log(LOG_ADMIN, source, this) << "to delete a news item"; + return; + } + } + catch (const ConvertException &) { } + + source.Reply(msgs[MSG_DEL_NOT_FOUND], text.c_str()); + } + else + { + for (unsigned i = list.size(); i > 0; --i) + this->ns->DelNewsItem(list[i - 1]); + source.Reply(msgs[MSG_DELETED_ALL]); + Log(LOG_ADMIN, source, this) << "to delete all news items"; + } + } + } + + return; + } + + void DoNews(CommandSource &source, const std::vector ¶ms, NewsType ntype) + { + if (!this->ns) + return; + + const Anope::string &cmd = params[0]; + + const char **msgs = findmsgs(ntype); + if (!msgs) + throw CoreException("news: Invalid type to DoNews()"); + + if (cmd.equals_ci("LIST")) + return this->DoList(source, ntype, msgs); + else if (cmd.equals_ci("ADD")) + return this->DoAdd(source, params, ntype, msgs); + else if (cmd.equals_ci("DEL")) + return this->DoDel(source, params, ntype, msgs); + else + this->OnSyntaxError(source, ""); + + return; + } + public: + NewsBase(Module *creator, const Anope::string &newstype) : Command(creator, newstype, 1, 2), ns("NewsService", "news") + { + this->SetSyntax(_("ADD \037text\037")); + this->SetSyntax(_("DEL {\037num\037 | ALL}")); + this->SetSyntax("LIST"); + } + + virtual ~NewsBase() + { + } + + virtual void Execute(CommandSource &source, const std::vector ¶ms) = 0; + + virtual bool OnHelp(CommandSource &source, const Anope::string &subcommand) = 0; +}; + +class CommandOSLogonNews : public NewsBase +{ + public: + CommandOSLogonNews(Module *creator) : NewsBase(creator, "operserv/logonnews") + { + this->SetDesc(_("Define messages to be shown to users at logon")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + return this->DoNews(source, params, NEWS_LOGON); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Edits or displays the list of logon news messages. When a\n" + "user connects to the network, these messages will be sent\n" + "to them. However, no more than \002%d\002 messages will be\n" + "sent in order to avoid flooding the user. If there are\n" + "more news messages, only the most recent will be sent."), + Config->GetModule(this->owner)->Get("newscount", "3")); + return true; + } +}; + +class CommandOSOperNews : public NewsBase +{ + public: + CommandOSOperNews(Module *creator) : NewsBase(creator, "operserv/opernews") + { + this->SetDesc(_("Define messages to be shown to users who oper")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + return this->DoNews(source, params, NEWS_OPER); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Edits or displays the list of oper news messages. When a\n" + "user opers up (with the /OPER command), these messages will\n" + "be sent to them. However, no more than \002%d\002 messages will\n" + "be sent in order to avoid flooding the user. If there are\n" + "more news messages, only the most recent will be sent."), + Config->GetModule(this->owner)->Get("newscount", "3")); + return true; + } +}; + +class CommandOSRandomNews : public NewsBase +{ + public: + CommandOSRandomNews(Module *creator) : NewsBase(creator, "operserv/randomnews") + { + this->SetDesc(_("Define messages to be randomly shown to users at logon")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + return this->DoNews(source, params, NEWS_RANDOM); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Edits or displays the list of random news messages. When a\n" + "user connects to the network, one (and only one) of the\n" + "random news will be randomly chosen and sent to them.")); + return true; + } +}; + +static unsigned cur_rand_news = 0; + +class OSNews : public Module +{ + MyNewsService newsservice; + Serialize::Type newsitem_type; + + CommandOSLogonNews commandoslogonnews; + CommandOSOperNews commandosopernews; + CommandOSRandomNews commandosrandomnews; + + Anope::string oper_announcer, announcer; + unsigned news_count; + + void DisplayNews(User *u, NewsType Type) + { + std::vector &newsList = this->newsservice.GetNewsList(Type); + if (newsList.empty()) + return; + + BotInfo *bi = NULL; + if (Type == NEWS_OPER) + bi = BotInfo::Find(Config->GetModule(this)->Get("oper_announcer", "OperServ"), true); + else + bi = BotInfo::Find(Config->GetModule(this)->Get("announcer", "Global"), true); + if (bi == NULL) + return; + + Anope::string msg; + if (Type == NEWS_LOGON) + msg = _("[\002Logon News\002 - %s] %s"); + else if (Type == NEWS_OPER) + msg = _("[\002Oper News\002 - %s] %s"); + else if (Type == NEWS_RANDOM) + msg = _("[\002Random News\002 - %s] %s"); + + int start = 0; + + if (Type != NEWS_RANDOM) + { + start = newsList.size() - news_count; + if (start < 0) + start = 0; + } + + for (unsigned i = start, end = newsList.size(); i < end; ++i) + { + if (Type == NEWS_RANDOM && i != cur_rand_news) + continue; + + u->SendMessage(bi, msg.c_str(), Anope::strftime(newsList[i]->time, u->Account(), true).c_str(), newsList[i]->text.c_str()); + + if (Type == NEWS_RANDOM) + { + ++cur_rand_news; + break; + } + } + + /* Reset to head of list to get first random news value */ + if (Type == NEWS_RANDOM && cur_rand_news >= newsList.size()) + cur_rand_news = 0; + } + + public: + OSNews(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + newsservice(this), newsitem_type("NewsItem", MyNewsItem::Unserialize), + commandoslogonnews(this), commandosopernews(this), commandosrandomnews(this) + { + } + + void OnReload(Configuration::Conf *conf) anope_override + { + oper_announcer = conf->GetModule(this)->Get("oper_announcer", "OperServ"); + announcer = conf->GetModule(this)->Get("announcer", "Global"); + news_count = conf->GetModule(this)->Get("newscount", "3"); + } + + void OnUserModeSet(const MessageSource &setter, User *u, const Anope::string &mname) anope_override + { + if (mname == "OPER") + DisplayNews(u, NEWS_OPER); + } + + void OnUserConnect(User *user, bool &) anope_override + { + if (user->Quitting() || !user->server->IsSynced()) + return; + + DisplayNews(user, NEWS_LOGON); + DisplayNews(user, NEWS_RANDOM); + } +}; + +MODULE_INIT(OSNews) diff --git a/modules/commands/os_noop.cpp b/modules/commands/os_noop.cpp new file mode 100644 index 0000000..1f0f3a3 --- /dev/null +++ b/modules/commands/os_noop.cpp @@ -0,0 +1,100 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSNOOP : public Command +{ + public: + CommandOSNOOP(Module *creator) : Command(creator, "operserv/noop", 2, 2) + { + this->SetDesc(_("Remove all operators from a server remotely")); + this->SetSyntax(_("SET \037server\037")); + this->SetSyntax(_("REVOKE \037server\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[0]; + const Anope::string &server = params[1]; + + Server *s = Server::Find(server, true); + if (s == NULL) + source.Reply(_("Server %s does not exist."), server.c_str()); + else if (s == Me || s->IsJuped()) + source.Reply(_("You can not NOOP Services.")); + else if (cmd.equals_ci("SET")) + { + /* Remove the O:lines */ + IRCD->SendSVSNOOP(s, true); + s->Extend("noop", source.GetNick()); + + Log(LOG_ADMIN, source, this) << "SET on " << s->GetName(); + source.Reply(_("All operators from \002%s\002 have been removed."), s->GetName().c_str()); + + Anope::string reason = "NOOP command used by " + source.GetNick(); + /* Kill all the IRCops of the server */ + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + { + User *u2 = it->second; + + if (u2->server == s && u2->HasMode("OPER")) + u2->Kill(*source.service, reason); + } + } + else if (cmd.equals_ci("REVOKE")) + { + s->Shrink("noop"); + IRCD->SendSVSNOOP(s, false); + Log(LOG_ADMIN, source, this) << "REVOKE on " << s->GetName(); + source.Reply(_("All O:lines of \002%s\002 have been reset."), s->GetName().c_str()); + } + else + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("\002SET\002 kills all operators from the given\n" + "\002server\002 and prevents operators from opering\n" + "up on the given server. \002REVOKE\002 removes this\n" + "restriction.")); + return true; + } +}; + +class OSNOOP : public Module +{ + CommandOSNOOP commandosnoop; + PrimitiveExtensibleItem noop; + + public: + OSNOOP(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosnoop(this), noop(this, "noop") + { + + } + + void OnUserModeSet(const MessageSource &, User *u, const Anope::string &mname) anope_override + { + Anope::string *setter; + if (mname == "OPER" && (setter = noop.Get(u->server))) + { + Anope::string reason = "NOOP command used by " + *setter; + BotInfo *OperServ = Config->GetClient("OperServ"); + u->Kill(OperServ, reason); + } + } +}; + +MODULE_INIT(OSNOOP) diff --git a/modules/commands/os_oline.cpp b/modules/commands/os_oline.cpp new file mode 100644 index 0000000..5fb2782 --- /dev/null +++ b/modules/commands/os_oline.cpp @@ -0,0 +1,78 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSOLine : public Command +{ + public: + CommandOSOLine(Module *creator) : Command(creator, "operserv/oline", 2, 2) + { + this->SetDesc(_("Give Operflags to a certain user")); + this->SetSyntax(_("\037nick\037 \037flags\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &nick = params[0]; + const Anope::string &flag = params[1]; + User *u2 = NULL; + + /* let's check whether the user is online */ + if (!(u2 = User::Find(nick, true))) + source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); + else if (u2 && flag[0] == '+') + { + IRCD->SendSVSO(source.service, nick, flag); + u2->SetMode(source.service, "OPER"); + u2->SendMessage(source.service, _("You are now an IRC Operator.")); + source.Reply(_("Operflags \002%s\002 have been added for \002%s\002."), flag.c_str(), nick.c_str()); + Log(LOG_ADMIN, source, this) << "for " << nick; + } + else if (u2 && flag[0] == '-') + { + IRCD->SendSVSO(source.service, nick, flag); + source.Reply(_("Operflags \002%s\002 have been removed from \002%s\002."), flag.c_str(), nick.c_str()); + Log(LOG_ADMIN, source, this) << "for " << nick; + } + else + this->OnSyntaxError(source, ""); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows Services Operators to give Operflags to any user.\n" + "Flags have to be prefixed with a \"+\" or a \"-\". To\n" + "remove all flags simply type a \"-\" instead of any flags.")); + return true; + } +}; + +class OSOLine : public Module +{ + CommandOSOLine commandosoline; + + public: + OSOLine(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosoline(this) + { + + if (!IRCD || !IRCD->CanSVSO) + throw ModuleException("Your IRCd does not support OMODE."); + + } +}; + +MODULE_INIT(OSOLine) diff --git a/modules/commands/os_oper.cpp b/modules/commands/os_oper.cpp new file mode 100644 index 0000000..31a6579 --- /dev/null +++ b/modules/commands/os_oper.cpp @@ -0,0 +1,292 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +struct MyOper : Oper, Serializable +{ + MyOper(const Anope::string &n, OperType *o) : Oper(n, o), Serializable("Oper") { } + + void Serialize(Serialize::Data &data) const anope_override + { + data["name"] << this->name; + data["type"] << this->ot->GetName(); + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data) + { + Anope::string stype, sname; + + data["type"] >> stype; + data["name"] >> sname; + + OperType *ot = OperType::Find(stype); + if (ot == NULL) + return NULL; + NickCore *nc = NickCore::Find(sname); + if (nc == NULL) + return NULL; + + MyOper *myo; + if (obj) + myo = anope_dynamic_static_cast(obj); + else + myo = new MyOper(nc->display, ot); + nc->o = myo; + Log(LOG_NORMAL, "operserv/oper") << "Tied oper " << nc->display << " to type " << ot->GetName(); + return myo; + } +}; + +class CommandOSOper : public Command +{ + bool HasPrivs(CommandSource &source, OperType *ot) const + { + std::list commands = ot->GetCommands(), privs = ot->GetPrivs(); + + for (std::list::iterator it = commands.begin(); it != commands.end(); ++it) + if (!source.HasCommand(*it)) + return false; + + for (std::list::iterator it = privs.begin(); it != privs.end(); ++it) + if (!source.HasPriv(*it)) + return false; + + return true; + } + + public: + CommandOSOper(Module *creator) : Command(creator, "operserv/oper", 1, 3) + { + this->SetDesc(_("View and change Services Operators")); + this->SetSyntax(_("ADD \037oper\037 \037type\037")); + this->SetSyntax(_("DEL \037oper\037")); + this->SetSyntax(_("INFO [\037type\037]")); + this->SetSyntax("LIST"); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &subcommand = params[0]; + + if (subcommand.equals_ci("ADD") && params.size() > 2) + { + const Anope::string &oper = params[1]; + const Anope::string &otype = params[2]; + + if (!source.HasPriv("operserv/oper/modify")) + { + source.Reply(ACCESS_DENIED); + return; + } + + const NickAlias *na = NickAlias::Find(oper); + if (na == NULL) + source.Reply(NICK_X_NOT_REGISTERED, oper.c_str()); + else if (na->nc->o) + source.Reply(_("Nick \002%s\002 is already an operator."), na->nick.c_str()); + else + { + OperType *ot = OperType::Find(otype); + if (ot == NULL) + { + source.Reply(_("Oper type \002%s\002 has not been configured."), otype.c_str()); + return; + } + + if (!HasPrivs(source, ot)) + { + source.Reply(ACCESS_DENIED); + return; + } + + na->nc->o = new MyOper(na->nc->display, ot); + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + Log(LOG_ADMIN, source, this) << "ADD " << na->nick << " as type " << ot->GetName(); + source.Reply("%s (%s) added to the \002%s\002 list.", na->nick.c_str(), na->nc->display.c_str(), ot->GetName().c_str()); + } + } + else if (subcommand.equals_ci("DEL") && params.size() > 1) + { + const Anope::string &oper = params[1]; + + if (!source.HasPriv("operserv/oper/modify")) + { + source.Reply(ACCESS_DENIED); + return; + } + + const NickAlias *na = NickAlias::Find(oper); + if (na == NULL) + source.Reply(NICK_X_NOT_REGISTERED, oper.c_str()); + else if (!na->nc || !na->nc->o) + source.Reply(_("Nick \002%s\002 is not a Services Operator."), oper.c_str()); + else if (!HasPrivs(source, na->nc->o->ot)) + source.Reply(ACCESS_DENIED); + else if (std::find(Config->Opers.begin(), Config->Opers.end(), na->nc->o) != Config->Opers.end()) + source.Reply(_("Oper \002%s\002 is configured in the configuration file(s) and can not be removed by this command."), na->nc->display.c_str()); + else + { + delete na->nc->o; + na->nc->o = NULL; + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + Log(LOG_ADMIN, source, this) << "DEL " << na->nick; + source.Reply(_("Oper privileges removed from %s (%s)."), na->nick.c_str(), na->nc->display.c_str()); + } + } + else if (subcommand.equals_ci("LIST")) + { + source.Reply(_("Name Type")); + for (nickcore_map::const_iterator it = NickCoreList->begin(), it_end = NickCoreList->end(); it != it_end; ++it) + { + const NickCore *nc = it->second; + + if (!nc->o) + continue; + + source.Reply(_("%-8s %s"), nc->o->name.c_str(), nc->o->ot->GetName().c_str()); + if (std::find(Config->Opers.begin(), Config->Opers.end(), nc->o) != Config->Opers.end()) + source.Reply(_(" This oper is configured in the configuration file.")); + for (std::list::const_iterator uit = nc->users.begin(); uit != nc->users.end(); ++uit) + { + User *u = *uit; + source.Reply(_(" %s is online using this oper block."), u->nick.c_str()); + } + } + } + else if (subcommand.equals_ci("INFO")) + { + if (params.size() < 2) + { + source.Reply(_("Available opertypes:")); + for (unsigned i = 0; i < Config->MyOperTypes.size(); ++i) + { + OperType *ot = Config->MyOperTypes[i]; + source.Reply("%s", ot->GetName().c_str()); + } + return; + } + + Anope::string fulltype = params[1]; + if (params.size() > 2) + fulltype += " " + params[2]; + OperType *ot = OperType::Find(fulltype); + if (ot == NULL) + source.Reply(_("Oper type \002%s\002 has not been configured."), fulltype.c_str()); + else + { + if (ot->GetCommands().empty()) + source.Reply(_("Opertype \002%s\002 has no allowed commands."), ot->GetName().c_str()); + else + { + source.Reply(_("Available commands for \002%s\002:"), ot->GetName().c_str()); + Anope::string buf; + std::list cmds = ot->GetCommands(); + for (std::list::const_iterator it = cmds.begin(), it_end = cmds.end(); it != it_end; ++it) + { + buf += *it + " "; + if (buf.length() > 400) + { + source.Reply("%s", buf.c_str()); + buf.clear(); + } + } + if (!buf.empty()) + { + source.Reply("%s", buf.c_str()); + buf.clear(); + } + } + if (ot->GetPrivs().empty()) + source.Reply(_("Opertype \002%s\002 has no allowed privileges."), ot->GetName().c_str()); + else + { + source.Reply(_("Available privileges for \002%s\002:"), ot->GetName().c_str()); + Anope::string buf; + std::list privs = ot->GetPrivs(); + for (std::list::const_iterator it = privs.begin(), it_end = privs.end(); it != it_end; ++it) + { + buf += *it + " "; + if (buf.length() > 400) + { + source.Reply("%s", buf.c_str()); + buf.clear(); + } + } + if (!buf.empty()) + { + source.Reply("%s", buf.c_str()); + buf.clear(); + } + } + if (!ot->modes.empty()) + source.Reply(_("Opertype \002%s\002 receives modes \002%s\002 once identified."), ot->GetName().c_str(), ot->modes.c_str()); + } + } + else + this->OnSyntaxError(source, subcommand); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows you to change and view Services Operators.\n" + "Note that operators removed by this command but are still set in\n" + "the configuration file are not permanently affected by this.")); + return true; + } +}; + +class OSOper : public Module +{ + Serialize::Type myoper_type; + CommandOSOper commandosoper; + + public: + OSOper(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + myoper_type("Oper", MyOper::Unserialize), commandosoper(this) + { + } + + ~OSOper() + { + for (nickcore_map::const_iterator it = NickCoreList->begin(), it_end = NickCoreList->end(); it != it_end; ++it) + { + NickCore *nc = it->second; + + if (nc->o && dynamic_cast(nc->o)) + { + delete nc->o; + nc->o = NULL; + } + } + } + + void OnDelCore(NickCore *nc) anope_override + { + if (nc->o && dynamic_cast(nc->o)) + { + delete nc->o; + nc->o = NULL; + } + } +}; + +MODULE_INIT(OSOper) diff --git a/modules/commands/os_reload.cpp b/modules/commands/os_reload.cpp new file mode 100644 index 0000000..44178c5 --- /dev/null +++ b/modules/commands/os_reload.cpp @@ -0,0 +1,67 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSReload : public Command +{ + public: + CommandOSReload(Module *creator) : Command(creator, "operserv/reload", 0, 0) + { + this->SetDesc(_("Reload services' configuration file")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + try + { + Log(LOG_ADMIN, source, this); + + Configuration::Conf *new_config = new Configuration::Conf(); + Configuration::Conf *old = Config; + Config = new_config; + Config->Post(old); + delete old; + + source.Reply(_("Services' configuration has been reloaded.")); + } + catch (const ConfigException &ex) + { + Log(this->owner) << "Error reloading configuration file: " << ex.GetReason(); + source.Reply(_("Error reloading configuration file: %s"), ex.GetReason().c_str()); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Causes Services to reload the configuration file. Note that\n" + "some directives still need the restart of the Services to\n" + "take effect (such as Services' nicknames, activation of the\n" + "session limitation, etc.).")); + return true; + } +}; + +class OSReload : public Module +{ + CommandOSReload commandosreload; + + public: + OSReload(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosreload(this) + { + + } +}; + +MODULE_INIT(OSReload) diff --git a/modules/commands/os_session.cpp b/modules/commands/os_session.cpp new file mode 100644 index 0000000..f8a5568 --- /dev/null +++ b/modules/commands/os_session.cpp @@ -0,0 +1,737 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/os_session.h" + +namespace +{ + /* The default session limit */ + unsigned session_limit; + /* How many times to kill before adding an AKILL */ + unsigned max_session_kill; + /* How long session akills should last */ + time_t session_autokill_expiry; + /* Reason to use for session kills */ + Anope::string sle_reason; + /* Optional second reason */ + Anope::string sle_detailsloc; + + /* Max limit that can be used for exceptions */ + unsigned max_exception_limit; + /* How long before exceptions expire by default */ + time_t exception_expiry; + + /* Number of bits to use when comparing session IPs */ + unsigned ipv4_cidr; + unsigned ipv6_cidr; +} + +class MySessionService : public SessionService +{ + SessionMap Sessions; + Serialize::Checker Exceptions; + public: + MySessionService(Module *m) : SessionService(m), Exceptions("Exception") { } + + Exception *CreateException() anope_override + { + return new Exception(); + } + + void AddException(Exception *e) anope_override + { + this->Exceptions->push_back(e); + } + + void DelException(Exception *e) anope_override + { + ExceptionVector::iterator it = std::find(this->Exceptions->begin(), this->Exceptions->end(), e); + if (it != this->Exceptions->end()) + this->Exceptions->erase(it); + } + + Exception *FindException(User *u) anope_override + { + for (std::vector::const_iterator it = this->Exceptions->begin(), it_end = this->Exceptions->end(); it != it_end; ++it) + { + Exception *e = *it; + if (Anope::Match(u->host, e->mask) || Anope::Match(u->ip.addr(), e->mask)) + return e; + + if (cidr(e->mask).match(u->ip)) + return e; + } + return NULL; + } + + Exception *FindException(const Anope::string &host) anope_override + { + for (std::vector::const_iterator it = this->Exceptions->begin(), it_end = this->Exceptions->end(); it != it_end; ++it) + { + Exception *e = *it; + if (Anope::Match(host, e->mask)) + return e; + + if (cidr(e->mask).match(sockaddrs(host))) + return e; + } + + return NULL; + } + + ExceptionVector &GetExceptions() anope_override + { + return this->Exceptions; + } + + void DelSession(Session *s) + { + this->Sessions.erase(s->addr); + } + + Session *FindSession(const Anope::string &ip) anope_override + { + cidr c(ip, ip.find(':') != Anope::string::npos ? ipv6_cidr : ipv4_cidr); + if (!c.valid()) + return NULL; + SessionMap::iterator it = this->Sessions.find(c); + if (it != this->Sessions.end()) + return it->second; + return NULL; + } + + SessionMap::iterator FindSessionIterator(const sockaddrs &ip) + { + cidr c(ip, ip.ipv6() ? ipv6_cidr : ipv4_cidr); + if (!c.valid()) + return this->Sessions.end(); + return this->Sessions.find(c); + } + + Session* &FindOrCreateSession(const cidr &ip) + { + return this->Sessions[ip]; + } + + SessionMap &GetSessions() anope_override + { + return this->Sessions; + } +}; + +class ExceptionDelCallback : public NumberList +{ + protected: + CommandSource &source; + unsigned deleted; + Command *cmd; + public: + ExceptionDelCallback(CommandSource &_source, const Anope::string &numlist, Command *c) : NumberList(numlist, true), source(_source), deleted(0), cmd(c) + { + } + + ~ExceptionDelCallback() + { + if (!deleted) + source.Reply(_("No matching entries on session-limit exception list.")); + else if (deleted == 1) + source.Reply(_("Deleted 1 entry from session-limit exception list.")); + else + source.Reply(_("Deleted %d entries from session-limit exception list."), deleted); + } + + virtual void HandleNumber(unsigned number) anope_override + { + if (!number || number > session_service->GetExceptions().size()) + return; + + Log(LOG_ADMIN, source, cmd) << "to remove the session limit exception for " << session_service->GetExceptions()[number - 1]->mask; + + ++deleted; + DoDel(source, number - 1); + } + + static void DoDel(CommandSource &source, unsigned index) + { + Exception *e = session_service->GetExceptions()[index]; + FOREACH_MOD(OnExceptionDel, (source, e)); + + session_service->DelException(e); + delete e; + } +}; + +class CommandOSSession : public Command +{ + private: + void DoList(CommandSource &source, const std::vector ¶ms) + { + Anope::string param = params[1]; + + unsigned mincount = 0; + try + { + mincount = convertTo(param); + } + catch (const ConvertException &) { } + + if (mincount <= 1) + source.Reply(_("Invalid threshold value. It must be a valid integer greater than 1.")); + else + { + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Session")).AddColumn(_("Host")); + + for (SessionService::SessionMap::iterator it = session_service->GetSessions().begin(), it_end = session_service->GetSessions().end(); it != it_end; ++it) + { + Session *session = it->second; + + if (session->count >= mincount) + { + ListFormatter::ListEntry entry; + entry["Session"] = stringify(session->count); + entry["Host"] = session->addr.mask(); + list.AddEntry(entry); + } + } + + source.Reply(_("Hosts with at least \002%d\002 sessions:"), mincount); + + std::vector replies; + list.Process(replies); + + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + + return; + } + + void DoView(CommandSource &source, const std::vector ¶ms) + { + Anope::string param = params[1]; + Session *session = session_service->FindSession(param); + + Exception *exception = session_service->FindException(param); + Anope::string entry = "no entry"; + unsigned limit = session_limit; + if (exception) + { + if (!exception->limit) + limit = 0; + else if (exception->limit > limit) + limit = exception->limit; + entry = exception->mask; + } + + if (!session) + source.Reply(_("\002%s\002 not found on session list, but has a limit of \002%d\002 because it matches entry: \002%s\002."), param.c_str(), limit, entry.c_str()); + else + source.Reply(_("The host \002%s\002 currently has \002%d\002 sessions with a limit of \002%d\002 because it matches entry: \002%s\002."), session->addr.mask().c_str(), session->count, limit, entry.c_str()); + } + public: + CommandOSSession(Module *creator) : Command(creator, "operserv/session", 2, 2) + { + this->SetDesc(_("View the list of host sessions")); + this->SetSyntax(_("LIST \037threshold\037")); + this->SetSyntax(_("VIEW \037host\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[0]; + + Log(LOG_ADMIN, source, this) << cmd << " " << params[1]; + + if (!session_limit) + source.Reply(_("Session limiting is disabled.")); + else if (cmd.equals_ci("LIST")) + return this->DoList(source, params); + else if (cmd.equals_ci("VIEW")) + return this->DoView(source, params); + else + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows Services Operators to view the session list.\n" + " \n" + "\002SESSION LIST\002 lists hosts with at least \037threshold\037 sessions.\n" + "The threshold must be a number greater than 1. This is to\n" + "prevent accidental listing of the large number of single\n" + "session hosts.\n" + " \n" + "\002SESSION VIEW\002 displays detailed information about a specific\n" + "host - including the current session count and session limit.\n" + "The \037host\037 value may not include wildcards.\n" + " \n" + "See the \002EXCEPTION\002 help for more information about session\n" + "limiting and how to set session limits specific to certain\n" + "hosts and groups thereof.")); + return true; + } +}; + +class CommandOSException : public Command +{ + private: + void DoAdd(CommandSource &source, const std::vector ¶ms) + { + Anope::string mask, expiry, limitstr; + unsigned last_param = 3; + + mask = params.size() > 1 ? params[1] : ""; + if (!mask.empty() && mask[0] == '+') + { + expiry = mask; + mask = params.size() > 2 ? params[2] : ""; + last_param = 4; + } + + limitstr = params.size() > last_param - 1 ? params[last_param - 1] : ""; + + if (params.size() <= last_param) + { + this->OnSyntaxError(source, "ADD"); + return; + } + + Anope::string reason = params[last_param]; + if (last_param == 3 && params.size() > 4) + reason += " " + params[4]; + if (reason.empty()) + { + this->OnSyntaxError(source, "ADD"); + return; + } + + time_t expires = !expiry.empty() ? Anope::DoTime(expiry) : exception_expiry; + if (expires < 0) + { + source.Reply(BAD_EXPIRY_TIME); + return; + } + else if (expires > 0) + expires += Anope::CurTime; + + unsigned limit = -1; + try + { + limit = convertTo(limitstr); + } + catch (const ConvertException &) { } + + if (limit > max_exception_limit) + { + source.Reply(_("Invalid session limit. It must be a valid integer greater than or equal to zero and less than \002%d\002."), max_exception_limit); + return; + } + else + { + if (mask.find('!') != Anope::string::npos || mask.find('@') != Anope::string::npos) + { + source.Reply(_("Invalid hostmask. Only real hostmasks are valid, as exceptions are not matched against nicks or usernames.")); + return; + } + + for (std::vector::iterator it = session_service->GetExceptions().begin(), it_end = session_service->GetExceptions().end(); it != it_end; ++it) + { + Exception *e = *it; + if (e->mask.equals_ci(mask)) + { + if (e->limit != limit) + { + e->limit = limit; + source.Reply(_("Exception for \002%s\002 has been updated to %d."), mask.c_str(), e->limit); + } + else + source.Reply(_("\002%s\002 already exists on the EXCEPTION list."), mask.c_str()); + return; + } + } + + Exception *exception = new Exception(); + exception->mask = mask; + exception->limit = limit; + exception->reason = reason; + exception->time = Anope::CurTime; + exception->who = source.GetNick(); + exception->expires = expires; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnExceptionAdd, MOD_RESULT, (exception)); + if (MOD_RESULT == EVENT_STOP) + delete exception; + else + { + Log(LOG_ADMIN, source, this) << "to set the session limit for " << mask << " to " << limit; + session_service->AddException(exception); + source.Reply(_("Session limit for \002%s\002 set to \002%d\002."), mask.c_str(), limit); + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + } + } + + return; + } + + void DoDel(CommandSource &source, const std::vector ¶ms) + { + const Anope::string &mask = params.size() > 1 ? params[1] : ""; + + if (mask.empty()) + { + this->OnSyntaxError(source, "DEL"); + return; + } + + if (isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) + { + ExceptionDelCallback list(source, mask, this); + list.Process(); + } + else + { + unsigned i = 0, end = session_service->GetExceptions().size(); + for (; i < end; ++i) + if (mask.equals_ci(session_service->GetExceptions()[i]->mask)) + { + Log(LOG_ADMIN, source, this) << "to remove the session limit exception for " << mask; + ExceptionDelCallback::DoDel(source, i); + source.Reply(_("\002%s\002 deleted from session-limit exception list."), mask.c_str()); + break; + } + if (i == end) + source.Reply(_("\002%s\002 not found on session-limit exception list."), mask.c_str()); + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + return; + } + + void ProcessList(CommandSource &source, const std::vector ¶ms, ListFormatter &list) + { + const Anope::string &mask = params.size() > 1 ? params[1] : ""; + + if (session_service->GetExceptions().empty()) + { + source.Reply(_("The session exception list is empty.")); + return; + } + + if (!mask.empty() && mask.find_first_not_of("1234567890,-") == Anope::string::npos) + { + class ExceptionListCallback : public NumberList + { + CommandSource &source; + ListFormatter &list; + public: + ExceptionListCallback(CommandSource &_source, ListFormatter &_list, const Anope::string &numlist) : NumberList(numlist, false), source(_source), list(_list) + { + } + + void HandleNumber(unsigned Number) anope_override + { + if (!Number || Number > session_service->GetExceptions().size()) + return; + + Exception *e = session_service->GetExceptions()[Number - 1]; + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(Number); + entry["Mask"] = e->mask; + entry["By"] = e->who; + entry["Created"] = Anope::strftime(e->time, NULL, true); + entry["Expires"] = Anope::Expires(e->expires, source.GetAccount()); + entry["Limit"] = stringify(e->limit); + entry["Reason"] = e->reason; + this->list.AddEntry(entry); + } + } + nl_list(source, list, mask); + nl_list.Process(); + } + else + { + for (unsigned i = 0, end = session_service->GetExceptions().size(); i < end; ++i) + { + Exception *e = session_service->GetExceptions()[i]; + if (mask.empty() || Anope::Match(e->mask, mask)) + { + ListFormatter::ListEntry entry; + entry["Number"] = stringify(i + 1); + entry["Mask"] = e->mask; + entry["By"] = e->who; + entry["Created"] = Anope::strftime(e->time, NULL, true); + entry["Expires"] = Anope::Expires(e->expires, source.GetAccount()); + entry["Limit"] = stringify(e->limit); + entry["Reason"] = e->reason; + list.AddEntry(entry); + } + } + } + + if (list.IsEmpty()) + source.Reply(_("No matching entries on session-limit exception list.")); + else + { + source.Reply(_("Current Session Limit Exception list:")); + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + } + + void DoList(CommandSource &source, const std::vector ¶ms) + { + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Limit")).AddColumn(_("Mask")); + + this->ProcessList(source, params, list); + } + + void DoView(CommandSource &source, const std::vector ¶ms) + { + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Mask")).AddColumn(_("By")).AddColumn(_("Created")).AddColumn(_("Expires")).AddColumn(_("Limit")).AddColumn(_("Reason")); + + this->ProcessList(source, params, list); + } + + public: + CommandOSException(Module *creator) : Command(creator, "operserv/exception", 1, 5) + { + this->SetDesc(_("Modify the session-limit exception list")); + this->SetSyntax(_("ADD [\037+expiry\037] \037mask\037 \037limit\037 \037reason\037")); + this->SetSyntax(_("DEL {\037mask\037 | \037entry-num\037 | \037list\037}")); + this->SetSyntax(_("LIST [\037mask\037 | \037list\037]")); + this->SetSyntax(_("VIEW [\037mask\037 | \037list\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[0]; + + if (!session_limit) + source.Reply(_("Session limiting is disabled.")); + else if (cmd.equals_ci("ADD")) + return this->DoAdd(source, params); + else if (cmd.equals_ci("DEL")) + return this->DoDel(source, params); + else if (cmd.equals_ci("LIST")) + return this->DoList(source, params); + else if (cmd.equals_ci("VIEW")) + return this->DoView(source, params); + else + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows Services Operators to manipulate the list of hosts that\n" + "have specific session limits - allowing certain machines,\n" + "such as shell servers, to carry more than the default number\n" + "of clients at a time. Once a host reaches its session limit,\n" + "all clients attempting to connect from that host will be\n" + "killed. Before the user is killed, they are notified, of a\n" + "source of help regarding session limiting. The content of\n" + "this notice is a config setting.")); + source.Reply(" "); + source.Reply(_("\002EXCEPTION ADD\002 adds the given host mask to the exception list.\n" + "Note that \002nick!user@host\002 and \002user@host\002 masks are invalid!\n" + "Only real host masks, such as \002box.host.dom\002 and \002*.host.dom\002,\n" + "are allowed because sessions limiting does not take nick or\n" + "user names into account. \037limit\037 must be a number greater than\n" + "or equal to zero. This determines how many sessions this host\n" + "may carry at a time. A value of zero means the host has an\n" + "unlimited session limit. See the \002AKILL\002 help for details about\n" + "the format of the optional \037expiry\037 parameter.\n" + " \n" + "\002EXCEPTION DEL\002 removes the given mask from the exception list.\n" + " \n" + "\002EXCEPTION LIST\002 and \002EXCEPTION VIEW\002 show all current\n" + "sessions if the optional mask is given, the list is limited\n" + "to those sessions matching the mask. The difference is that\n" + "\002EXCEPTION VIEW\002 is more verbose, displaying the name of the\n" + "person who added the exception, its session limit, reason,\n" + "host mask and the expiry date and time.\n" + " \n" + "Note that a connecting client will \"use\" the first exception\n" + "their host matches.")); + return true; + } +}; + +class OSSession : public Module +{ + Serialize::Type exception_type; + MySessionService ss; + CommandOSSession commandossession; + CommandOSException commandosexception; + ServiceReference akills; + + public: + OSSession(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + exception_type("Exception", Exception::Unserialize), ss(this), commandossession(this), commandosexception(this), akills("XLineManager", "xlinemanager/sgline") + { + this->SetPermanent(true); + } + + void Prioritize() anope_override + { + ModuleManager::SetPriority(this, PRIORITY_FIRST); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *block = Config->GetModule(this); + + session_limit = block->Get("defaultsessionlimit"); + max_session_kill = block->Get("maxsessionkill"); + session_autokill_expiry = block->Get("sessionautokillexpiry"); + sle_reason = block->Get("sessionlimitexceeded"); + sle_detailsloc = block->Get("sessionlimitdetailsloc"); + + max_exception_limit = block->Get("maxsessionlimit"); + exception_expiry = block->Get("exceptionexpiry"); + + ipv4_cidr = block->Get("session_ipv4_cidr", "32"); + ipv6_cidr = block->Get("session_ipv6_cidr", "128"); + + if (ipv4_cidr > 32 || ipv6_cidr > 128) + throw ConfigException(this->name + ": session CIDR value out of range"); + } + + void OnUserConnect(User *u, bool &exempt) anope_override + { + if (u->Quitting() || !session_limit || exempt || !u->server || u->server->IsULined()) + return; + + cidr u_ip(u->ip, u->ip.ipv6() ? ipv6_cidr : ipv4_cidr); + if (!u_ip.valid()) + return; + + Session* &session = this->ss.FindOrCreateSession(u_ip); + + if (session) + { + bool kill = false; + if (session->count >= session_limit) + { + kill = true; + Exception *exception = this->ss.FindException(u); + if (exception) + { + kill = false; + if (exception->limit && session->count >= exception->limit) + kill = true; + } + } + + /* Previously on IRCds that send a QUIT (InspIRCD) when a user is killed, the session for a host was + * decremented in do_quit, which caused problems and fixed here + * + * Now, we create the user struture before calling this to fix some user tracking issues, + * so we must increment this here no matter what because it will either be + * decremented when the user is killed or quits - Adam + */ + ++session->count; + + if (kill && !exempt) + { + BotInfo *OperServ = Config->GetClient("OperServ"); + if (OperServ) + { + if (!sle_reason.empty()) + { + Anope::string message = sle_reason.replace_all_cs("%IP%", u->ip.addr()); + u->SendMessage(OperServ, message); + } + if (!sle_detailsloc.empty()) + u->SendMessage(OperServ, sle_detailsloc); + } + + ++session->hits; + + const Anope::string &akillmask = "*@" + session->addr.mask(); + if (max_session_kill && session->hits >= max_session_kill && akills && !akills->HasEntry(akillmask)) + { + XLine *x = new XLine(akillmask, OperServ ? OperServ->nick : "", Anope::CurTime + session_autokill_expiry, "Session limit exceeded", XLineManager::GenerateUID()); + akills->AddXLine(x); + akills->Send(NULL, x); + Log(OperServ, "akill/session") << "Added a temporary AKILL for \002" << akillmask << "\002 due to excessive connections"; + } + else + { + u->Kill(OperServ, "Session limit exceeded"); + } + } + } + else + { + session = new Session(u->ip, u->ip.ipv6() ? ipv6_cidr : ipv4_cidr); + } + } + + void OnUserQuit(User *u, const Anope::string &msg) anope_override + { + if (!session_limit || !u->server || u->server->IsULined()) + return; + + SessionService::SessionMap &sessions = this->ss.GetSessions(); + SessionService::SessionMap::iterator sit = this->ss.FindSessionIterator(u->ip); + + if (sit == sessions.end()) + return; + + Session *session = sit->second; + + if (session->count > 1) + { + --session->count; + return; + } + + delete session; + sessions.erase(sit); + } + + void OnExpireTick() anope_override + { + if (Anope::NoExpire) + return; + for (unsigned i = this->ss.GetExceptions().size(); i > 0; --i) + { + Exception *e = this->ss.GetExceptions()[i - 1]; + + if (!e->expires || e->expires > Anope::CurTime) + continue; + BotInfo *OperServ = Config->GetClient("OperServ"); + Log(OperServ, "expire/exception") << "Session exception for " << e->mask << " has expired."; + this->ss.DelException(e); + delete e; + } + } +}; + +MODULE_INIT(OSSession) diff --git a/modules/commands/os_set.cpp b/modules/commands/os_set.cpp new file mode 100644 index 0000000..8ee9ffb --- /dev/null +++ b/modules/commands/os_set.cpp @@ -0,0 +1,267 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSSet : public Command +{ + private: + void DoList(CommandSource &source) + { + Log(LOG_ADMIN, source, this) << "LIST"; + + Anope::string index; + + index = Anope::ReadOnly ? _("%s is enabled") : _("%s is disabled"); + source.Reply(index.c_str(), "READONLY"); + index = Anope::Debug ? _("%s is enabled") : _("%s is disabled"); + source.Reply(index.c_str(), "DEBUG"); + index = Anope::NoExpire ? _("%s is enabled") : _("%s is disabled"); + source.Reply(index.c_str(), "NOEXPIRE"); + + return; + } + + void DoSetReadOnly(CommandSource &source, const std::vector ¶ms) + { + const Anope::string &setting = params.size() > 1 ? params[1] : ""; + + if (setting.empty()) + { + this->OnSyntaxError(source, "READONLY"); + return; + } + + if (setting.equals_ci("ON")) + { + Anope::ReadOnly = true; + Log(LOG_ADMIN, source, this) << "READONLY ON"; + source.Reply(_("Services are now in \002read-only\002 mode.")); + } + else if (setting.equals_ci("OFF")) + { + Anope::ReadOnly = false; + Log(LOG_ADMIN, source, this) << "READONLY OFF"; + source.Reply(_("Services are now in \002read-write\002 mode.")); + } + else + source.Reply(_("Setting for READONLY must be \002ON\002 or \002OFF\002.")); + + return; + } + + void DoSetSuperAdmin(CommandSource &source, const std::vector ¶ms) + { + const Anope::string &setting = params.size() > 1 ? params[1] : ""; + + if (!source.GetUser()) + return; + + if (setting.empty()) + { + this->OnSyntaxError(source, "SUPERADMIN"); + return; + } + + /** + * Allow the user to turn super admin on/off + * + * Rob + **/ + bool super_admin = Config->GetModule(this->owner)->Get("superadmin"); + if (!super_admin) + source.Reply(_("Super admin can not be set because it is not enabled in the configuration.")); + else if (setting.equals_ci("ON")) + { + source.GetUser()->super_admin = true; + source.Reply(_("You are now a super admin.")); + Log(LOG_ADMIN, source, this) << "SUPERADMIN ON"; + } + else if (setting.equals_ci("OFF")) + { + source.GetUser()->super_admin = false; + source.Reply(_("You are no longer a super admin.")); + Log(LOG_ADMIN, source, this) << "SUPERADMIN OFF"; + } + else + source.Reply(_("Setting for super admin must be \002ON\002 or \002OFF\002.")); + + return; + } + + void DoSetDebug(CommandSource &source, const std::vector ¶ms) + { + const Anope::string &setting = params.size() > 1 ? params[1] : ""; + + if (setting.empty()) + { + this->OnSyntaxError(source, "DEBUG"); + return; + } + + if (setting.equals_ci("ON")) + { + Anope::Debug = 1; + Log(LOG_ADMIN, source, this) << "DEBUG ON"; + source.Reply(_("Services are now in \002debug\002 mode.")); + } + else if (setting.equals_ci("OFF") || setting == "0") + { + Log(LOG_ADMIN, source, this) << "DEBUG OFF"; + Anope::Debug = 0; + source.Reply(_("Services are now in \002non-debug\002 mode.")); + } + else + { + try + { + Anope::Debug = convertTo(setting); + Log(LOG_ADMIN, source, this) << "DEBUG " << Anope::Debug; + source.Reply(_("Services are now in \002debug\002 mode (level %d)."), Anope::Debug); + return; + } + catch (const ConvertException &) { } + + source.Reply(_("Setting for DEBUG must be \002ON\002, \002OFF\002, or a positive number.")); + } + + return; + } + + void DoSetNoExpire(CommandSource &source, const std::vector ¶ms) + { + const Anope::string &setting = params.size() > 1 ? params[1] : ""; + + if (setting.empty()) + { + this->OnSyntaxError(source, "NOEXPIRE"); + return; + } + + if (setting.equals_ci("ON")) + { + Anope::NoExpire = true; + Log(LOG_ADMIN, source, this) << "NOEXPIRE ON"; + source.Reply(_("Services are now in \002no expire\002 mode.")); + } + else if (setting.equals_ci("OFF")) + { + Anope::NoExpire = false; + Log(LOG_ADMIN, source, this) << "NOEXPIRE OFF"; + source.Reply(_("Services are now in \002expire\002 mode.")); + } + else + source.Reply(_("Setting for NOEXPIRE must be \002ON\002 or \002OFF\002.")); + + return; + } + public: + CommandOSSet(Module *creator) : Command(creator, "operserv/set", 1, 2) + { + this->SetDesc(_("Set various global Services options")); + this->SetSyntax(_("\037option\037 \037setting\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &option = params[0]; + + if (option.equals_ci("LIST")) + return this->DoList(source); + else if (option.equals_ci("READONLY")) + return this->DoSetReadOnly(source, params); + else if (option.equals_ci("DEBUG")) + return this->DoSetDebug(source, params); + else if (option.equals_ci("NOEXPIRE")) + return this->DoSetNoExpire(source, params); + else if (option.equals_ci("SUPERADMIN")) + return this->DoSetSuperAdmin(source, params); + else + this->OnSyntaxError(source, ""); + + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + if (subcommand.empty()) + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Sets various global Services options. Option names\n" + "currently defined are:\n" + " READONLY Set read-only or read-write mode\n" + " DEBUG Activate or deactivate debug mode\n" + " NOEXPIRE Activate or deactivate no expire mode\n" + " SUPERADMIN Activate or deactivate super admin mode\n" + " LIST List the options")); + } + else if (subcommand.equals_ci("LIST")) + source.Reply(_("Syntax: \002LIST\002\n" + " \n" + "Display the various %s settings."), source.service->nick.c_str()); + else if (subcommand.equals_ci("READONLY")) + source.Reply(_("Syntax: \002READONLY {ON | OFF}\002\n" + " \n" + "Sets read-only mode on or off. In read-only mode, normal\n" + "users will not be allowed to modify any Services data,\n" + "including channel and nickname access lists, etc. IRCops\n" + "with sufficient Services privileges will be able to modify\n" + "Services' AKILL, SQLINE, SNLINE and ignore lists, drop,\n" + "suspend or forbid nicknames and channels, and manage news,\n" + "oper info and DNS, but any such changes will not be saved\n" + "unless read-only mode is deactivated before Services are\n" + "terminated or restarted.\n" + " \n" + "This option is equivalent to the command-line option\n" + "\002--readonly\002.")); + else if (subcommand.equals_ci("DEBUG")) + source.Reply(_("Syntax: \002DEBUG {ON | OFF}\002\n" + " \n" + "Sets debug mode on or off.\n" + " \n" + "This option is equivalent to the command-line option\n" + "\002--debug\002.")); + else if (subcommand.equals_ci("NOEXPIRE")) + source.Reply(_("Syntax: \002NOEXPIRE {ON | OFF}\002\n" + " \n" + "Sets no expire mode on or off. In no expire mode, nicks,\n" + "channels, akills and exceptions won't expire until the\n" + "option is unset.\n" + " \n" + "This option is equivalent to the command-line option\n" + "\002--noexpire\002.")); + else if (subcommand.equals_ci("SUPERADMIN")) + source.Reply(_("Syntax: \002SUPERADMIN {ON | OFF}\002\n" + " \n" + "Setting this will grant you extra privileges such as the\n" + "ability to be \"founder\" on all channel's etc...\n" + " \n" + "This option is \002not\002 persistent, and should only be used when\n" + "needed, and set back to OFF when no longer needed.")); + else + return false; + return true; + } +}; + +class OSSet : public Module +{ + CommandOSSet commandosset; + + public: + OSSet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosset(this) + { + } +}; + +MODULE_INIT(OSSet) diff --git a/modules/commands/os_shutdown.cpp b/modules/commands/os_shutdown.cpp new file mode 100644 index 0000000..81573d6 --- /dev/null +++ b/modules/commands/os_shutdown.cpp @@ -0,0 +1,108 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSQuit : public Command +{ + public: + CommandOSQuit(Module *creator) : Command(creator, "operserv/quit", 0, 0) + { + this->SetDesc(_("Terminate Services WITHOUT saving")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + Log(LOG_ADMIN, source, this); + Anope::QuitReason = source.command + " command received from " + source.GetNick(); + Anope::Quitting = true; + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Causes Services to do an immediate shutdown; databases are\n" + "\002not\002 saved. This command should not be used unless\n" + "damage to the in-memory copies of the databases is feared\n" + "and they should not be saved.")); + return true; + } +}; + +class CommandOSRestart : public Command +{ + public: + CommandOSRestart(Module *creator) : Command(creator, "operserv/restart", 0, 0) + { + this->SetDesc(_("Save databases and restart Services")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + Log(LOG_ADMIN, source, this); + Anope::QuitReason = source.command + " command received from " + source.GetNick(); + Anope::Quitting = Anope::Restarting = true; + Anope::SaveDatabases(); + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(_("Causes Services to save all databases and then restart\n" + "(i.e. exit and immediately re-run the executable).")); + return true; + } +}; + +class CommandOSShutdown : public Command +{ + public: + CommandOSShutdown(Module *creator) : Command(creator, "operserv/shutdown", 0, 0) + { + this->SetDesc(_("Terminate services with save")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + Log(LOG_ADMIN, source, this); + Anope::QuitReason = source.command + " command received from " + source.GetNick(); + Anope::Quitting = true; + Anope::SaveDatabases(); + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Causes Services to save all databases and then shut down.")); + return true; + } +}; + +class OSShutdown : public Module +{ + CommandOSQuit commandosquit; + CommandOSRestart commandosrestart; + CommandOSShutdown commandosshutdown; + + public: + OSShutdown(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosquit(this), commandosrestart(this), commandosshutdown(this) + { + + } +}; + +MODULE_INIT(OSShutdown) diff --git a/modules/commands/os_stats.cpp b/modules/commands/os_stats.cpp new file mode 100644 index 0000000..7d411bd --- /dev/null +++ b/modules/commands/os_stats.cpp @@ -0,0 +1,276 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/os_session.h" + +struct Stats : Serializable +{ + static Stats *me; + + Stats() : Serializable("Stats") + { + me = this; + } + + void Serialize(Serialize::Data &data) const anope_override + { + data["maxusercnt"] << MaxUserCount; + data["maxusertime"] << MaxUserTime; + } + + static Serializable* Unserialize(Serializable *obj, Serialize::Data &data) + { + data["maxusercnt"] >> MaxUserCount; + data["maxusertime"] >> MaxUserTime; + return me; + } +}; + +Stats *Stats::me; + +/** + * Count servers connected to server s + * @param s The server to start counting from + * @return Amount of servers connected to server s + **/ +static int stats_count_servers(Server *s) +{ + if (!s) + return 0; + + int count = 1; + + if (!s->GetLinks().empty()) + for (unsigned i = 0, j = s->GetLinks().size(); i < j; ++i) + count += stats_count_servers(s->GetLinks()[i]); + + return count; +} + +class CommandOSStats : public Command +{ + ServiceReference akills, snlines, sqlines; + private: + void DoStatsAkill(CommandSource &source) + { + int timeout; + if (akills) + { + /* AKILLs */ + source.Reply(_("Current number of AKILLs: \002%d\002"), akills->GetCount()); + timeout = Config->GetModule("operserv")->Get("autokillexpiry", "30d") + 59; + if (timeout >= 172800) + source.Reply(_("Default AKILL expiry time: \002%d days\002"), timeout / 86400); + else if (timeout >= 86400) + source.Reply(_("Default AKILL expiry time: \0021 day\002")); + else if (timeout >= 7200) + source.Reply(_("Default AKILL expiry time: \002%d hours\002"), timeout / 3600); + else if (timeout >= 3600) + source.Reply(_("Default AKILL expiry time: \0021 hour\002")); + else if (timeout >= 120) + source.Reply(_("Default AKILL expiry time: \002%d minutes\002"), timeout / 60); + else if (timeout >= 60) + source.Reply(_("Default AKILL expiry time: \0021 minute\002")); + else + source.Reply(_("Default AKILL expiry time: \002No expiration\002")); + } + if (snlines) + { + /* SNLINEs */ + source.Reply(_("Current number of SNLINEs: \002%d\002"), snlines->GetCount()); + timeout = Config->GetModule("operserv")->Get("snlineexpiry", "30d") + 59; + if (timeout >= 172800) + source.Reply(_("Default SNLINE expiry time: \002%d days\002"), timeout / 86400); + else if (timeout >= 86400) + source.Reply(_("Default SNLINE expiry time: \0021 day\002")); + else if (timeout >= 7200) + source.Reply(_("Default SNLINE expiry time: \002%d hours\002"), timeout / 3600); + else if (timeout >= 3600) + source.Reply(_("Default SNLINE expiry time: \0021 hour\002")); + else if (timeout >= 120) + source.Reply(_("Default SNLINE expiry time: \002%d minutes\002"), timeout / 60); + else if (timeout >= 60) + source.Reply(_("Default SNLINE expiry time: \0021 minute\002")); + else + source.Reply(_("Default SNLINE expiry time: \002No expiration\002")); + } + if (sqlines) + { + /* SQLINEs */ + source.Reply(_("Current number of SQLINEs: \002%d\002"), sqlines->GetCount()); + timeout = Config->GetModule("operserv")->Get("sglineexpiry", "30d") + 59; + if (timeout >= 172800) + source.Reply(_("Default SQLINE expiry time: \002%d days\002"), timeout / 86400); + else if (timeout >= 86400) + source.Reply(_("Default SQLINE expiry time: \0021 day\002")); + else if (timeout >= 7200) + source.Reply(_("Default SQLINE expiry time: \002%d hours\002"), timeout / 3600); + else if (timeout >= 3600) + source.Reply(_("Default SQLINE expiry time: \0021 hour\002")); + else if (timeout >= 120) + source.Reply(_("Default SQLINE expiry time: \002%d minutes\002"), timeout / 60); + else if (timeout >= 60) + source.Reply(_("Default SQLINE expiry time: \0021 minute\002")); + else + source.Reply(_("Default SQLINE expiry time: \002No expiration\002")); + } + } + + void DoStatsReset(CommandSource &source) + { + MaxUserCount = UserListByNick.size(); + source.Reply(_("Statistics reset.")); + return; + } + + void DoStatsUptime(CommandSource &source) + { + time_t uptime = Anope::CurTime - Anope::StartTime; + source.Reply(_("Current users: \002%d\002 (\002%d\002 ops)"), UserListByNick.size(), OperCount); + source.Reply(_("Maximum users: \002%d\002 (%s)"), MaxUserCount, Anope::strftime(MaxUserTime, source.GetAccount()).c_str()); + source.Reply(_("Services up %s."), Anope::Duration(uptime, source.GetAccount()).c_str()); + + return; + } + + void DoStatsUplink(CommandSource &source) + { + Anope::string buf; + for (std::set::iterator it = Servers::Capab.begin(); it != Servers::Capab.end(); ++it) + buf += " " + *it; + if (!buf.empty()) + buf.erase(buf.begin()); + + source.Reply(_("Uplink server: %s"), Me->GetLinks().front()->GetName().c_str()); + source.Reply(_("Uplink capab: %s"), buf.c_str()); + source.Reply(_("Servers found: %d"), stats_count_servers(Me->GetLinks().front())); + return; + } + + template void GetHashStats(const T& map, size_t& entries, size_t& buckets, size_t& max_chain) + { + entries = map.size(), buckets = map.bucket_count(), max_chain = 0; + for (size_t i = 0; i < buckets; ++i) + if (map.bucket_size(i) > max_chain) + max_chain = map.bucket_size(i); + } + + void DoStatsHash(CommandSource &source) + { + size_t entries, buckets, max_chain; + + GetHashStats(UserListByNick, entries, buckets, max_chain); + source.Reply(_("Users (nick): %lu entries, %lu buckets, longest chain is %d"), entries, buckets, max_chain); + + if (!UserListByUID.empty()) + { + GetHashStats(UserListByUID, entries, buckets, max_chain); + source.Reply(_("Users (uid): %lu entries, %lu buckets, longest chain is %d"), entries, buckets, max_chain); + } + + GetHashStats(ChannelList, entries, buckets, max_chain); + source.Reply(_("Channels: %lu entries, %lu buckets, longest chain is %d"), entries, buckets, max_chain); + + GetHashStats(*RegisteredChannelList, entries, buckets, max_chain); + source.Reply(_("Registered channels: %lu entries, %lu buckets, longest chain is %d"), entries, buckets, max_chain); + + GetHashStats(*NickAliasList, entries, buckets, max_chain); + source.Reply(_("Registered nicknames: %lu entries, %lu buckets, longest chain is %d"), entries, buckets, max_chain); + + GetHashStats(*NickCoreList, entries, buckets, max_chain); + source.Reply(_("Registered nick groups: %lu entries, %lu buckets, longest chain is %d"), entries, buckets, max_chain); + + if (session_service) + { + GetHashStats(session_service->GetSessions(), entries, buckets, max_chain); + source.Reply(_("Sessions: %lu entries, %lu buckets, longest chain is %d"), entries, buckets, max_chain); + } + } + + public: + CommandOSStats(Module *creator) : Command(creator, "operserv/stats", 0, 1), + akills("XLineManager", "xlinemanager/sgline"), snlines("XLineManager", "xlinemanager/snline"), sqlines("XLineManager", "xlinemanager/sqline") + { + this->SetDesc(_("Show status of Services and network")); + this->SetSyntax("[AKILL | HASH | UPLINK | UPTIME | ALL | RESET]"); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + Anope::string extra = !params.empty() ? params[0] : ""; + + Log(LOG_ADMIN, source, this) << extra; + + if (extra.equals_ci("RESET")) + return this->DoStatsReset(source); + + if (extra.equals_ci("ALL") || extra.equals_ci("AKILL")) + this->DoStatsAkill(source); + + if (extra.equals_ci("ALL") || extra.equals_ci("HASH")) + this->DoStatsHash(source); + + if (extra.equals_ci("ALL") || extra.equals_ci("UPLINK")) + this->DoStatsUplink(source); + + if (extra.empty() || extra.equals_ci("ALL") || extra.equals_ci("UPTIME")) + this->DoStatsUptime(source); + + if (!extra.empty() && !extra.equals_ci("ALL") && !extra.equals_ci("AKILL") && !extra.equals_ci("HASH") && !extra.equals_ci("UPLINK") && !extra.equals_ci("UPTIME")) + source.Reply(_("Unknown STATS option: \002%s\002"), extra.c_str()); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Without any option, shows the current number of users online,\n" + "and the highest number of users online since Services was\n" + "started, and the length of time Services has been running.\n" + " \n" + "With the \002AKILL\002 option, displays the current size of the\n" + "AKILL list and the current default expiry time.\n" + " \n" + "The \002RESET\002 option currently resets the maximum user count\n" + "to the number of users currently present on the network.\n" + " \n" + "The \002UPLINK\002 option displays information about the current\n" + "server Anope uses as an uplink to the network.\n" + " \n" + "The \002HASH\002 option displays information about the hash maps.\n" + " \n" + "The \002ALL\002 option displays all of the above statistics.")); + return true; + } +}; + +class OSStats : public Module +{ + CommandOSStats commandosstats; + Serialize::Type stats_type; + Stats stats_saver; + + public: + OSStats(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosstats(this), stats_type("Stats", Stats::Unserialize) + { + + } + + void OnUserConnect(User *u, bool &exempt) anope_override + { + if (UserListByNick.size() == MaxUserCount && Anope::CurTime == MaxUserTime) + stats_saver.QueueUpdate(); + } +}; + +MODULE_INIT(OSStats) diff --git a/modules/commands/os_svs.cpp b/modules/commands/os_svs.cpp new file mode 100644 index 0000000..dfa1ec2 --- /dev/null +++ b/modules/commands/os_svs.cpp @@ -0,0 +1,178 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSSVSNick : public Command +{ + public: + CommandOSSVSNick(Module *creator) : Command(creator, "operserv/svsnick", 2, 2) + { + this->SetDesc(_("Forcefully change a user's nickname")); + this->SetSyntax(_("\037nick\037 \037newnick\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &nick = params[0]; + Anope::string newnick = params[1]; + User *u2; + + if (!IRCD->CanSVSNick) + { + source.Reply(_("Your IRCd does not support SVSNICK.")); + return; + } + + /* Truncate long nicknames to nicklen characters */ + unsigned nicklen = Config->GetBlock("networkinfo")->Get("nicklen"); + if (newnick.length() > nicklen) + { + source.Reply(_("Nick \002%s\002 was truncated to %d characters."), newnick.c_str(), nicklen, newnick.c_str()); + newnick = params[1].substr(0, nicklen); + } + + /* Check for valid characters */ + if (!IRCD->IsNickValid(newnick)) + { + source.Reply(_("Nick \002%s\002 is an illegal nickname and cannot be used."), newnick.c_str()); + return; + } + + /* Check for a nick in use or a forbidden/suspended nick */ + if (!(u2 = User::Find(nick, true))) + source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); + else if (!nick.equals_ci(newnick) && User::Find(newnick)) + source.Reply(_("Nick \002%s\002 is currently in use."), newnick.c_str()); + else + { + source.Reply(_("The nick \002%s\002 is now being changed to \002%s\002."), nick.c_str(), newnick.c_str()); + Log(LOG_ADMIN, source, this) << "to change " << nick << " to " << newnick; + IRCD->SendForceNickChange(u2, newnick, Anope::CurTime); + } + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Forcefully changes a user's nickname from \037nick\037 to \037newnick\037.")); + return true; + } +}; + +class CommandOSSVSJoin : public Command +{ + public: + CommandOSSVSJoin(Module *creator) : Command(creator, "operserv/svsjoin", 2, 2) + { + this->SetDesc(_("Forcefully join a user to a channel")); + this->SetSyntax(_("\037nick\037 \037channel\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!IRCD->CanSVSJoin) + { + source.Reply(_("Your IRCd does not support SVSJOIN.")); + return; + } + + User *target = User::Find(params[0], true); + Channel *c = Channel::Find(params[1]); + if (target == NULL) + source.Reply(NICK_X_NOT_IN_USE, params[0].c_str()); + else if (source.GetUser() != target && (target->IsProtected() || target->server == Me)) + source.Reply(ACCESS_DENIED); + else if (!IRCD->IsChannelValid(params[1])) + source.Reply(CHAN_X_INVALID, params[1].c_str()); + else if (c && c->FindUser(target)) + source.Reply(_("\002%s\002 is already in \002%s\002."), target->nick.c_str(), c->name.c_str()); + else + { + IRCD->SendSVSJoin(*source.service, target, params[1], ""); + Log(LOG_ADMIN, source, this) << "to force " << target->nick << " to join " << params[1]; + source.Reply(_("\002%s\002 has been joined to \002%s\002."), target->nick.c_str(), params[1].c_str()); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Forcefully join a user to a channel.")); + return true; + } +}; + +class CommandOSSVSPart : public Command +{ + public: + CommandOSSVSPart(Module *creator) : Command(creator, "operserv/svspart", 2, 3) + { + this->SetDesc(_("Forcefully part a user from a channel")); + this->SetSyntax(_("\037nick\037 \037channel\037 [\037reason\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!IRCD->CanSVSJoin) + { + source.Reply(_("Your IRCd does not support SVSPART.")); + return; + } + + User *target = User::Find(params[0], true); + Channel *c = Channel::Find(params[1]); + const Anope::string &reason = params.size() > 2 ? params[2] : ""; + if (target == NULL) + source.Reply(NICK_X_NOT_IN_USE, params[0].c_str()); + else if (source.GetUser() != target && (target->IsProtected() || target->server == Me)) + source.Reply(ACCESS_DENIED); + else if (!c) + source.Reply(CHAN_X_NOT_IN_USE, params[1].c_str()); + else if (!c->FindUser(target)) + source.Reply(_("\002%s\002 is not in \002%s\002."), target->nick.c_str(), c->name.c_str()); + else + { + IRCD->SendSVSPart(*source.service, target, params[1], reason); + if (!reason.empty()) + Log(LOG_ADMIN, source, this) << "to force " << target->nick << " to part " << c->name << " with reason " << reason; + else + Log(LOG_ADMIN, source, this) << "to force " << target->nick << " to part " << c->name; + source.Reply(_("\002%s\002 has been parted from \002%s\002."), target->nick.c_str(), c->name.c_str()); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Forcefully part a user from a channel.")); + return true; + } +}; + +class OSSVS : public Module +{ + CommandOSSVSNick commandossvsnick; + CommandOSSVSJoin commandossvsjoin; + CommandOSSVSPart commandossvspart; + + public: + OSSVS(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandossvsnick(this), commandossvsjoin(this), commandossvspart(this) + { + } +}; + +MODULE_INIT(OSSVS) diff --git a/modules/commands/os_sxline.cpp b/modules/commands/os_sxline.cpp new file mode 100644 index 0000000..3d54735 --- /dev/null +++ b/modules/commands/os_sxline.cpp @@ -0,0 +1,732 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class SXLineDelCallback : public NumberList +{ + XLineManager *xlm; + Command *command; + CommandSource &source; + unsigned deleted; + public: + SXLineDelCallback(XLineManager *x, Command *c, CommandSource &_source, const Anope::string &numlist) : NumberList(numlist, true), xlm(x), command(c), source(_source), deleted(0) + { + } + + ~SXLineDelCallback() + { + if (!deleted) + source.Reply(_("No matching entries on the %s list."), source.command.c_str()); + else if (deleted == 1) + source.Reply(_("Deleted 1 entry from the %s list."), source.command.c_str()); + else + source.Reply(_("Deleted %d entries from the %s list."), deleted, source.command.c_str()); + } + + void HandleNumber(unsigned number) anope_override + { + if (!number) + return; + + XLine *x = this->xlm->GetEntry(number - 1); + + if (!x) + return; + + Log(LOG_ADMIN, source, command) << "to remove " << x->mask << " from the list"; + + ++deleted; + DoDel(this->xlm, source, x); + } + + static void DoDel(XLineManager *xlm, CommandSource &source, XLine *x) + { + xlm->DelXLine(x); + } +}; + +class CommandOSSXLineBase : public Command +{ + private: + virtual XLineManager* xlm() = 0; + + virtual void OnAdd(CommandSource &source, const std::vector ¶ms) = 0; + + void OnDel(CommandSource &source, const std::vector ¶ms) + { + + if (!this->xlm() || this->xlm()->GetList().empty()) + { + source.Reply(_("%s list is empty."), source.command.c_str()); + return; + } + + const Anope::string &mask = params.size() > 1 ? params[1] : ""; + + if (mask.empty()) + { + this->OnSyntaxError(source, "DEL"); + return; + } + + if (isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) + { + SXLineDelCallback list(this->xlm(), this, source, mask); + list.Process(); + } + else + { + XLine *x = this->xlm()->HasEntry(mask); + + if (!x) + { + source.Reply(_("\002%s\002 not found on the %s list."), mask.c_str(), source.command.c_str()); + return; + } + + FOREACH_MOD(OnDelXLine, (source, x, this->xlm())); + + SXLineDelCallback::DoDel(this->xlm(), source, x); + source.Reply(_("\002%s\002 deleted from the %s list."), mask.c_str(), source.command.c_str()); + Log(LOG_ADMIN, source, this) << "to remove " << mask << " from the list"; + } + + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + return; + } + + void ProcessList(CommandSource &source, const std::vector ¶ms, ListFormatter &list) + { + if (!this->xlm() || this->xlm()->GetList().empty()) + { + source.Reply(_("%s list is empty."), source.command.c_str()); + return; + } + + const Anope::string &mask = params.size() > 1 ? params[1] : ""; + + if (!mask.empty() && isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) + { + class SXLineListCallback : public NumberList + { + XLineManager *xlm; + CommandSource &source; + ListFormatter &list; + public: + SXLineListCallback(XLineManager *x, CommandSource &_source, ListFormatter &_list, const Anope::string &numlist) : NumberList(numlist, false), xlm(x), source(_source), list(_list) + { + } + + void HandleNumber(unsigned number) anope_override + { + if (!number) + return; + + const XLine *x = this->xlm->GetEntry(number - 1); + + if (!x) + return; + + ListFormatter::ListEntry entry; + entry["Number"] = stringify(number); + entry["Mask"] = x->mask; + entry["By"] = x->by; + entry["Created"] = Anope::strftime(x->created, NULL, true); + entry["Expires"] = Anope::Expires(x->expires, source.nc); + entry["ID"] = x->id; + entry["Reason"] = x->reason; + list.AddEntry(entry); + } + } + sl_list(this->xlm(), source, list, mask); + sl_list.Process(); + } + else + { + for (unsigned i = 0, end = this->xlm()->GetCount(); i < end; ++i) + { + const XLine *x = this->xlm()->GetEntry(i); + + if (mask.empty() || mask.equals_ci(x->mask) || mask == x->id || Anope::Match(x->mask, mask, false, true)) + { + ListFormatter::ListEntry entry; + entry["Number"] = stringify(i + 1); + entry["Mask"] = x->mask; + entry["By"] = x->by; + entry["Created"] = Anope::strftime(x->created, NULL, true); + entry["Expires"] = Anope::Expires(x->expires, source.nc); + entry["ID"] = x->id; + entry["Reason"] = x->reason; + list.AddEntry(entry); + } + } + } + + if (list.IsEmpty()) + source.Reply(_("No matching entries on the %s list."), source.command.c_str()); + else + { + source.Reply(_("Current %s list:"), source.command.c_str()); + + std::vector replies; + list.Process(replies); + + for (unsigned i = 0; i < replies.size(); ++i) + source.Reply(replies[i]); + } + } + + void OnList(CommandSource &source, const std::vector ¶ms) + { + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Mask")).AddColumn(_("Reason")); + + this->ProcessList(source, params, list); + } + + void OnView(CommandSource &source, const std::vector ¶ms) + { + ListFormatter list(source.GetAccount()); + list.AddColumn(_("Number")).AddColumn(_("Mask")).AddColumn(_("By")).AddColumn(_("Created")).AddColumn(_("Expires")); + if (Config->GetModule("operserv")->Get("akillids")) + list.AddColumn(_("ID")); + list.AddColumn(_("Reason")); + + this->ProcessList(source, params, list); + } + + void OnClear(CommandSource &source) + { + FOREACH_MOD(OnDelXLine, (source, NULL, this->xlm())); + + for (unsigned i = this->xlm()->GetCount(); i > 0; --i) + { + XLine *x = this->xlm()->GetEntry(i - 1); + this->xlm()->DelXLine(x); + } + + Log(LOG_ADMIN, source, this) << "to CLEAR the list"; + source.Reply(_("The %s list has been cleared."), source.command.c_str()); + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + + return; + } + public: + CommandOSSXLineBase(Module *creator, const Anope::string &cmd) : Command(creator, cmd, 1, 4) + { + } + + const Anope::string GetDesc(CommandSource &source) const anope_override + { + return Anope::printf(Language::Translate(source.GetAccount(), _("Manipulate the %s list")), source.command.upper().c_str()); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &cmd = params[0]; + + if (cmd.equals_ci("ADD")) + return this->OnAdd(source, params); + else if (cmd.equals_ci("DEL")) + return this->OnDel(source, params); + else if (cmd.equals_ci("LIST")) + return this->OnList(source, params); + else if (cmd.equals_ci("VIEW")) + return this->OnView(source, params); + else if (cmd.equals_ci("CLEAR")) + return this->OnClear(source); + else + this->OnSyntaxError(source, ""); + + return; + } + + virtual bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override = 0; +}; + +class CommandOSSNLine : public CommandOSSXLineBase +{ + XLineManager *xlm() anope_override + { + return this->snlines; + } + + void OnAdd(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!this->xlm()) + return; + + unsigned last_param = 2; + Anope::string param, expiry; + + param = params.size() > 1 ? params[1] : ""; + if (!param.empty() && param[0] == '+') + { + expiry = param; + param = params.size() > 2 ? params[2] : ""; + last_param = 3; + } + + time_t expires = !expiry.empty() ? Anope::DoTime(expiry) : Config->GetModule("operserv")->Get("snlineexpiry", "30d"); + /* If the expiry given does not contain a final letter, it's in days, + * said the doc. Ah well. + */ + if (!expiry.empty() && isdigit(expiry[expiry.length() - 1])) + expires *= 86400; + /* Do not allow less than a minute expiry time */ + if (expires && expires < 60) + { + source.Reply(BAD_EXPIRY_TIME); + return; + } + else if (expires > 0) + expires += Anope::CurTime; + + if (param.empty()) + { + this->OnSyntaxError(source, "ADD"); + return; + } + + Anope::string rest = param; + if (params.size() > last_param) + rest += " " + params[last_param]; + + if (rest.find(':') == Anope::string::npos) + { + this->OnSyntaxError(source, "ADD"); + return; + } + + sepstream sep(rest, ':'); + Anope::string mask; + sep.GetToken(mask); + Anope::string reason = sep.GetRemaining(); + + if (mask.empty() || reason.empty()) + { + this->OnSyntaxError(source, "ADD"); + return; + } + + if (mask[0] == '/' && mask[mask.length() - 1] == '/') + { + const Anope::string ®exengine = Config->GetBlock("options")->Get("regexengine"); + + if (regexengine.empty()) + { + source.Reply(_("Regex is disabled.")); + return; + } + + ServiceReference provider("Regex", regexengine); + if (!provider) + { + source.Reply(_("Unable to find regex engine %s."), regexengine.c_str()); + return; + } + + try + { + Anope::string stripped_mask = mask.substr(1, mask.length() - 2); + delete provider->Compile(stripped_mask); + } + catch (const RegexException &ex) + { + source.Reply("%s", ex.GetReason().c_str()); + return; + } + } + + /* Clean up the last character of the mask if it is a space + * See bug #761 + */ + unsigned masklen = mask.length(); + if (mask[masklen - 1] == ' ') + mask.erase(masklen - 1); + + if (Config->GetModule("operserv")->Get("addakiller", "yes") && !source.GetNick().empty()) + reason = "[" + source.GetNick() + "] " + reason; + + if (mask.find_first_not_of("/.*?") == Anope::string::npos) + { + source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); + return; + } + + XLine *x = new XLine(mask, source.GetNick(), expires, reason); + if (Config->GetModule("operserv")->Get("akillids")) + x->id = XLineManager::GenerateUID(); + + unsigned int affected = 0; + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + if (this->xlm()->Check(it->second, x)) + ++affected; + float percent = static_cast(affected) / static_cast(UserListByNick.size()) * 100.0; + + if (percent > 95) + { + source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); + Log(LOG_ADMIN, source, this) << "tried to " << source.command << " " << percent << "% of the network (" << affected << " users)"; + delete x; + return; + } + + if (!this->xlm()->CanAdd(source, mask, expires, reason)) + return; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnAddXLine, MOD_RESULT, (source, x, this->xlm())); + if (MOD_RESULT == EVENT_STOP) + { + delete x; + return; + } + + this->xlm()->AddXLine(x); + + if (Config->GetModule("operserv")->Get("killonsnline", "yes")) + { + Anope::string rreason = "G-Lined: " + reason; + + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + { + User *user = it->second; + + if (!user->HasMode("OPER") && user->server != Me && this->xlm()->Check(user, x)) + user->Kill(Me, rreason); + } + + this->xlm()->Send(NULL, x); + } + + source.Reply(_("\002%s\002 added to the %s list."), mask.c_str(), source.command.c_str()); + Log(LOG_ADMIN, source, this) << "on " << mask << " (" << reason << "), expires in " << (expires ? Anope::Duration(expires - Anope::CurTime) : "never") << " [affects " << affected << " user(s) (" << percent << "%)]"; + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + } + + ServiceReference snlines; + public: + CommandOSSNLine(Module *creator) : CommandOSSXLineBase(creator, "operserv/snline"), snlines("XLineManager", "xlinemanager/snline") + { + this->SetSyntax(_("ADD [+\037expiry\037] \037mask\037:\037reason\037")); + this->SetSyntax(_("DEL {\037mask\037 | \037entry-num\037 | \037list\037 | \037id\037}")); + this->SetSyntax(_("LIST [\037mask\037 | \037list\037 | \037id\037]")); + this->SetSyntax(_("VIEW [\037mask\037 | \037list\037 | \037id\037]")); + this->SetSyntax("CLEAR"); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows Services Operators to manipulate the SNLINE list. If\n" + "a user with a realname matching an SNLINE mask attempts to\n" + "connect, Services will not allow it to pursue his IRC\n" + "session.")); + source.Reply(_(" \n" + "\002SNLINE ADD\002 adds the given realname mask to the SNLINE\n" + "list for the given reason (which \002must\002 be given).\n" + "\037expiry\037 is specified as an integer followed by one of \037d\037\n" + "(days), \037h\037 (hours), or \037m\037 (minutes). Combinations (such as\n" + "\0371h30m\037) are not permitted. If a unit specifier is not\n" + "included, the default is days (so \037+30\037 by itself means 30\n" + "days). To add an SNLINE which does not expire, use \037+0\037. If the\n" + "realname mask to be added starts with a \037+\037, an expiry time must\n" + "be given, even if it is the same as the default. The\n" + "current SNLINE default expiry time can be found with the\n" + "\002STATS AKILL\002 command.\n" + " \n" + "\002Note\002: because the realname mask may contain spaces, the\n" + "separator between it and the reason is a colon.")); + const Anope::string ®exengine = Config->GetBlock("options")->Get("regexengine"); + if (!regexengine.empty()) + { + source.Reply(" "); + source.Reply(_("Regex matches are also supported using the %s engine.\n" + "Enclose your mask in // if this is desired."), regexengine.c_str()); + } + source.Reply(_(" \n" + "The \002SNLINE DEL\002 command removes the given mask from the\n" + "SNLINE list if it is present. If a list of entry numbers is\n" + "given, those entries are deleted. (See the example for LIST\n" + "below.)\n" + " \n" + "The \002SNLINE LIST\002 command displays the SNLINE list.\n" + "If a wildcard mask is given, only those entries matching the\n" + "mask are displayed. If a list of entry numbers is given,\n" + "only those entries are shown; for example:\n" + " \002SNLINE LIST 2-5,7-9\002\n" + " Lists SNLINE entries numbered 2 through 5 and 7\n" + " through 9.\n" + " \n" + "\002SNLINE VIEW\002 is a more verbose version of \002SNLINE LIST\002, and\n" + "will show who added an SNLINE, the date it was added, and when\n" + "it expires, as well as the realname mask and reason.\n" + " \n" + "\002SNLINE CLEAR\002 clears all entries of the SNLINE list.")); + return true; + } +}; + +class CommandOSSQLine : public CommandOSSXLineBase +{ + XLineManager *xlm() anope_override + { + return this->sqlines; + } + + void OnAdd(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!this->xlm()) + return; + + unsigned last_param = 2; + Anope::string expiry, mask; + + mask = params.size() > 1 ? params[1] : ""; + if (!mask.empty() && mask[0] == '+') + { + expiry = mask; + mask = params.size() > 2 ? params[2] : ""; + last_param = 3; + } + + time_t expires = !expiry.empty() ? Anope::DoTime(expiry) : Config->GetModule("operserv")->Get("sqlineexpiry", "30d"); + /* If the expiry given does not contain a final letter, it's in days, + * said the doc. Ah well. + */ + if (!expiry.empty() && isdigit(expiry[expiry.length() - 1])) + expires *= 86400; + /* Do not allow less than a minute expiry time */ + if (expires && expires < 60) + { + source.Reply(BAD_EXPIRY_TIME); + return; + } + else if (expires > 0) + expires += Anope::CurTime; + + if (params.size() <= last_param) + { + this->OnSyntaxError(source, "ADD"); + return; + } + + Anope::string reason = params[last_param]; + if (last_param == 2 && params.size() > 3) + reason += " " + params[3]; + + if (mask.empty() || reason.empty()) + { + this->OnSyntaxError(source, "ADD"); + return; + } + + if (mask[0] == '/' && mask[mask.length() - 1] == '/') + { + const Anope::string ®exengine = Config->GetBlock("options")->Get("regexengine"); + + if (regexengine.empty()) + { + source.Reply(_("Regex is disabled.")); + return; + } + + ServiceReference provider("Regex", regexengine); + if (!provider) + { + source.Reply(_("Unable to find regex engine %s."), regexengine.c_str()); + return; + } + + try + { + Anope::string stripped_mask = mask.substr(1, mask.length() - 2); + delete provider->Compile(stripped_mask); + } + catch (const RegexException &ex) + { + source.Reply("%s", ex.GetReason().c_str()); + return; + } + } + + if (Config->GetModule("operserv")->Get("addakiller", "yes") && !source.GetNick().empty()) + reason = "[" + source.GetNick() + "] " + reason; + + if (mask.find_first_not_of("./?*") == Anope::string::npos) + { + source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); + return; + } + + XLine *x = new XLine(mask, source.GetNick(), expires, reason); + if (Config->GetModule("operserv")->Get("akillids")) + x->id = XLineManager::GenerateUID(); + + unsigned int affected = 0; + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + if (this->xlm()->Check(it->second, x)) + ++affected; + float percent = static_cast(affected) / static_cast(UserListByNick.size()) * 100.0; + + if (percent > 95) + { + source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); + Log(LOG_ADMIN, source, this) << "tried to SQLine " << percent << "% of the network (" << affected << " users)"; + delete x; + return; + } + + if (!this->sqlines->CanAdd(source, mask, expires, reason)) + return; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnAddXLine, MOD_RESULT, (source, x, this->xlm())); + if (MOD_RESULT == EVENT_STOP) + { + delete x; + return; + } + + this->xlm()->AddXLine(x); + + if (Config->GetModule("operserv")->Get("killonsqline", "yes")) + { + Anope::string rreason = "Q-Lined: " + reason; + + if (mask[0] == '#') + { + for (channel_map::const_iterator cit = ChannelList.begin(), cit_end = ChannelList.end(); cit != cit_end; ++cit) + { + Channel *c = cit->second; + + if (!Anope::Match(c->name, mask, false, true)) + continue; + + std::vector users; + for (Channel::ChanUserList::iterator it = c->users.begin(), it_end = c->users.end(); it != it_end; ++it) + { + ChanUserContainer *uc = it->second; + User *user = uc->user; + + if (!user->HasMode("OPER") && user->server != Me) + users.push_back(user); + } + + for (unsigned i = 0; i < users.size(); ++i) + c->Kick(NULL, users[i], "%s", reason.c_str()); + } + } + else + { + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + { + User *user = it->second; + + if (!user->HasMode("OPER") && user->server != Me && this->xlm()->Check(user, x)) + user->Kill(Me, rreason); + } + } + + this->xlm()->Send(NULL, x); + } + + source.Reply(_("\002%s\002 added to the %s list."), mask.c_str(), source.command.c_str()); + Log(LOG_ADMIN, source, this) << "on " << mask << " (" << reason << "), expires in " << (expires ? Anope::Duration(expires - Anope::CurTime) : "never") << " [affects " << affected << " user(s) (" << percent << "%)]"; + if (Anope::ReadOnly) + source.Reply(READ_ONLY_MODE); + } + + ServiceReference sqlines; + public: + CommandOSSQLine(Module *creator) : CommandOSSXLineBase(creator, "operserv/sqline"), sqlines("XLineManager", "xlinemanager/sqline") + { + this->SetSyntax(_("ADD [+\037expiry\037] \037mask\037 \037reason\037")); + this->SetSyntax(_("DEL {\037mask\037 | \037entry-num\037 | \037list\037 | \037id\037}")); + this->SetSyntax(_("LIST [\037mask\037 | \037list\037 | \037id\037]")); + this->SetSyntax(_("VIEW [\037mask\037 | \037list\037 | \037id\037]")); + this->SetSyntax("CLEAR"); + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Allows Services Operators to manipulate the SQLINE list. If\n" + "a user with a nick matching an SQLINE mask attempts to\n" + "connect, Services will not allow it to pursue his IRC\n" + "session.\n" + "If the first character of the mask is #, services will\n" + "prevent the use of matching channels. If the mask is a\n" + "regular expression, the expression will be matched against\n" + "channels too.")); + source.Reply(_(" \n" + "\002SQLINE ADD\002 adds the given (nick's) mask to the SQLINE\n" + "list for the given reason (which \002must\002 be given).\n" + "\037expiry\037 is specified as an integer followed by one of \037d\037\n" + "(days), \037h\037 (hours), or \037m\037 (minutes). Combinations (such as\n" + "\0371h30m\037) are not permitted. If a unit specifier is not\n" + "included, the default is days (so \037+30\037 by itself means 30\n" + "days). To add an SQLINE which does not expire, use \037+0\037.\n" + "If the mask to be added starts with a \037+\037, an expiry time\n" + "must be given, even if it is the same as the default. The\n" + "current SQLINE default expiry time can be found with the\n" + "\002STATS AKILL\002 command.")); + const Anope::string ®exengine = Config->GetBlock("options")->Get("regexengine"); + if (!regexengine.empty()) + { + source.Reply(" "); + source.Reply(_("Regex matches are also supported using the %s engine.\n" + "Enclose your mask in // if this is desired."), regexengine.c_str()); + } + source.Reply(_(" \n" + "The \002SQLINE DEL\002 command removes the given mask from the\n" + "SQLINE list if it is present. If a list of entry numbers is\n" + "given, those entries are deleted. (See the example for LIST\n" + "below.)\n" + " \n" + "The \002SQLINE LIST\002 command displays the SQLINE list.\n" + "If a wildcard mask is given, only those entries matching the\n" + "mask are displayed. If a list of entry numbers is given,\n" + "only those entries are shown; for example:\n" + " \002SQLINE LIST 2-5,7-9\002\n" + " Lists SQLINE entries numbered 2 through 5 and 7\n" + " through 9.\n" + " \n" + "\002SQLINE VIEW\002 is a more verbose version of \002SQLINE LIST\002, and\n" + "will show who added an SQLINE, the date it was added, and when\n" + "it expires, as well as the mask and reason.\n" + " \n" + "\002SQLINE CLEAR\002 clears all entries of the SQLINE list.")); + return true; + } +}; + +class OSSXLine : public Module +{ + CommandOSSNLine commandossnline; + CommandOSSQLine commandossqline; + + public: + OSSXLine(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandossnline(this), commandossqline(this) + { + } +}; + +MODULE_INIT(OSSXLine) diff --git a/modules/commands/os_update.cpp b/modules/commands/os_update.cpp new file mode 100644 index 0000000..183f012 --- /dev/null +++ b/modules/commands/os_update.cpp @@ -0,0 +1,52 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandOSUpdate : public Command +{ + public: + CommandOSUpdate(Module *creator) : Command(creator, "operserv/update", 0, 0) + { + this->SetDesc(_("Force the Services databases to be updated immediately")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + Log(LOG_ADMIN, source, this); + source.Reply(_("Updating databases.")); + Anope::SaveDatabases(); + return; + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Causes Services to update all database files as soon as you\n" + "send the command.")); + return true; + } +}; + +class OSUpdate : public Module +{ + CommandOSUpdate commandosupdate; + + public: + OSUpdate(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandosupdate(this) + { + + } +}; + +MODULE_INIT(OSUpdate) diff --git a/modules/cs_statusupdate.cpp b/modules/cs_statusupdate.cpp new file mode 100644 index 0000000..ade9828 --- /dev/null +++ b/modules/cs_statusupdate.cpp @@ -0,0 +1,65 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" + +class StatusUpdate : public Module +{ + public: + StatusUpdate(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR) + { + + } + + void OnAccessAdd(ChannelInfo *ci, CommandSource &, ChanAccess *access) anope_override + { + if (ci->c) + for (Channel::ChanUserList::iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end; ++it) + { + User *user = it->second->user; + + ChannelInfo *next; + if (user->server != Me && access->Matches(user, user->Account(), next)) + { + AccessGroup ag = ci->AccessFor(user); + + for (unsigned i = 0; i < ModeManager::GetStatusChannelModesByRank().size(); ++i) + { + ChannelModeStatus *cms = ModeManager::GetStatusChannelModesByRank()[i]; + if (!ag.HasPriv("AUTO" + cms->name)) + ci->c->RemoveMode(NULL, cms, user->GetUID()); + } + ci->c->SetCorrectModes(user, true); + } + } + } + + void OnAccessDel(ChannelInfo *ci, CommandSource &, ChanAccess *access) anope_override + { + if (ci->c) + for (Channel::ChanUserList::iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end; ++it) + { + User *user = it->second->user; + + ChannelInfo *next; + if (user->server != Me && access->Matches(user, user->Account(), next)) + { + AccessGroup ag = ci->AccessFor(user); + + for (unsigned i = 0; i < ModeManager::GetStatusChannelModesByRank().size(); ++i) + { + ChannelModeStatus *cms = ModeManager::GetStatusChannelModesByRank()[i]; + if (!ag.HasPriv("AUTO" + cms->name)) + ci->c->RemoveMode(NULL, cms, user->GetUID()); + } + } + } + } +}; + +MODULE_INIT(StatusUpdate) diff --git a/modules/database/db_flatfile.cpp b/modules/database/db_flatfile.cpp new file mode 100644 index 0000000..2d00162 --- /dev/null +++ b/modules/database/db_flatfile.cpp @@ -0,0 +1,411 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +#ifndef _WIN32 +#include +#endif + +class SaveData : public Serialize::Data +{ + public: + Anope::string last; + std::fstream *fs; + + SaveData() : fs(NULL) { } + + std::iostream& operator[](const Anope::string &key) anope_override + { + if (key != last) + { + *fs << "\nDATA " << key << " "; + last = key; + } + + return *fs; + } +}; + +class LoadData : public Serialize::Data +{ + public: + std::fstream *fs; + unsigned int id; + std::map data; + std::stringstream ss; + bool read; + + LoadData() : fs(NULL), id(0), read(false) { } + + std::iostream& operator[](const Anope::string &key) anope_override + { + if (!read) + { + for (Anope::string token; std::getline(*this->fs, token.str());) + { + if (token.find("ID ") == 0) + { + try + { + this->id = convertTo(token.substr(3)); + } + catch (const ConvertException &) { } + + continue; + } + else if (token.find("DATA ") != 0) + break; + + size_t sp = token.find(' ', 5); // Skip DATA + if (sp != Anope::string::npos) + data[token.substr(5, sp - 5)] = token.substr(sp + 1); + } + + read = true; + } + + ss.clear(); + this->ss << this->data[key]; + return this->ss; + } + + std::set KeySet() const anope_override + { + std::set keys; + for (std::map::const_iterator it = this->data.begin(), it_end = this->data.end(); it != it_end; ++it) + keys.insert(it->first); + return keys; + } + + size_t Hash() const anope_override + { + size_t hash = 0; + for (std::map::const_iterator it = this->data.begin(), it_end = this->data.end(); it != it_end; ++it) + if (!it->second.empty()) + hash ^= Anope::hash_cs()(it->second); + return hash; + } + + void Reset() + { + id = 0; + read = false; + data.clear(); + } +}; + +class DBFlatFile : public Module, public Pipe +{ + /* Day the last backup was on */ + int last_day; + /* Backup file names */ + std::map > backups; + bool loaded; + + int child_pid; + + void BackupDatabase() + { + tm *tm = localtime(&Anope::CurTime); + + if (tm->tm_mday != last_day) + { + last_day = tm->tm_mday; + + const std::vector &type_order = Serialize::Type::GetTypeOrder(); + + std::set dbs; + dbs.insert(Config->GetModule(this)->Get("database", "anope.db")); + + for (unsigned i = 0; i < type_order.size(); ++i) + { + Serialize::Type *stype = Serialize::Type::Find(type_order[i]); + + if (stype && stype->GetOwner()) + dbs.insert("module_" + stype->GetOwner()->name + ".db"); + } + + + for (std::set::const_iterator it = dbs.begin(), it_end = dbs.end(); it != it_end; ++it) + { + const Anope::string &oldname = Anope::DataDir + "/" + *it; + Anope::string newname = Anope::DataDir + "/backups/" + *it + "-" + stringify(tm->tm_year + 1900) + Anope::printf("-%02i-", tm->tm_mon + 1) + Anope::printf("%02i", tm->tm_mday); + + /* Backup already exists or no database to backup */ + if (Anope::IsFile(newname) || !Anope::IsFile(oldname)) + continue; + + Log(LOG_DEBUG) << "db_flatfile: Attempting to rename " << *it << " to " << newname; + if (rename(oldname.c_str(), newname.c_str())) + { + Anope::string err = Anope::LastError(); + Log(this) << "Unable to back up database " << *it << " (" << err << ")!"; + + if (!Config->GetModule(this)->Get("nobackupokay")) + { + Anope::Quitting = true; + Anope::QuitReason = "Unable to back up database " + *it + " (" + err + ")"; + } + + continue; + } + + backups[*it].push_back(newname); + + unsigned keepbackups = Config->GetModule(this)->Get("keepbackups"); + if (keepbackups > 0 && backups[*it].size() > keepbackups) + { + unlink(backups[*it].front().c_str()); + backups[*it].pop_front(); + } + } + } + } + + public: + DBFlatFile(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, DATABASE | VENDOR), last_day(0), loaded(false), child_pid(-1) + { + + } + +#ifndef _WIN32 + void OnRestart() anope_override + { + OnShutdown(); + } + + void OnShutdown() anope_override + { + if (child_pid > -1) + { + Log(this) << "Waiting for child to exit..."; + + int status; + waitpid(child_pid, &status, 0); + + Log(this) << "Done"; + } + } +#endif + + void OnNotify() anope_override + { + char buf[512]; + int i = this->Read(buf, sizeof(buf) - 1); + if (i <= 0) + return; + buf[i] = 0; + + child_pid = -1; + + if (!*buf) + { + Log(this) << "Finished saving databases"; + return; + } + + Log(this) << "Error saving databases: " << buf; + + if (!Config->GetModule(this)->Get("nobackupokay")) + Anope::Quitting = true; + } + + EventReturn OnLoadDatabase() anope_override + { + const std::vector &type_order = Serialize::Type::GetTypeOrder(); + std::set tried_dbs; + + const Anope::string &db_name = Anope::DataDir + "/" + Config->GetModule(this)->Get("database", "anope.db"); + + std::fstream fd(db_name.c_str(), std::ios_base::in | std::ios_base::binary); + if (!fd.is_open()) + { + Log(this) << "Unable to open " << db_name << " for reading!"; + return EVENT_STOP; + } + + std::map > positions; + + for (Anope::string buf; std::getline(fd, buf.str());) + if (buf.find("OBJECT ") == 0) + positions[buf.substr(7)].push_back(fd.tellg()); + + LoadData ld; + ld.fs = &fd; + + for (unsigned i = 0; i < type_order.size(); ++i) + { + Serialize::Type *stype = Serialize::Type::Find(type_order[i]); + if (!stype || stype->GetOwner()) + continue; + + std::vector &pos = positions[stype->GetName()]; + + for (unsigned j = 0; j < pos.size(); ++j) + { + fd.clear(); + fd.seekg(pos[j]); + + Serializable *obj = stype->Unserialize(NULL, ld); + if (obj != NULL) + obj->id = ld.id; + ld.Reset(); + } + } + + fd.close(); + + loaded = true; + return EVENT_STOP; + } + + + void OnSaveDatabase() anope_override + { + if (child_pid > -1) + { + Log(this) << "Database save is already in progress!"; + return; + } + + BackupDatabase(); + + int i = -1; +#ifndef _WIN32 + if (!Anope::Quitting && Config->GetModule(this)->Get("fork")) + { + i = fork(); + if (i > 0) + { + child_pid = i; + return; + } + else if (i < 0) + Log(this) << "Unable to fork for database save"; + } +#endif + + try + { + std::map databases; + + /* First open the databases of all of the registered types. This way, if we have a type with 0 objects, that database will be properly cleared */ + for (std::map::const_iterator it = Serialize::Type::GetTypes().begin(), it_end = Serialize::Type::GetTypes().end(); it != it_end; ++it) + { + Serialize::Type *s_type = it->second; + + if (databases[s_type->GetOwner()]) + continue; + + Anope::string db_name; + if (s_type->GetOwner()) + db_name = Anope::DataDir + "/module_" + s_type->GetOwner()->name + ".db"; + else + db_name = Anope::DataDir + "/" + Config->GetModule(this)->Get("database", "anope.db"); + + std::fstream *fs = databases[s_type->GetOwner()] = new std::fstream((db_name + ".tmp").c_str(), std::ios_base::out | std::ios_base::trunc | std::ios_base::binary); + + if (!fs->is_open()) + Log(this) << "Unable to open " << db_name << " for writing"; + } + + SaveData data; + const std::list &items = Serializable::GetItems(); + for (std::list::const_iterator it = items.begin(), it_end = items.end(); it != it_end; ++it) + { + Serializable *base = *it; + Serialize::Type *s_type = base->GetSerializableType(); + + data.fs = databases[s_type->GetOwner()]; + if (!data.fs || !data.fs->is_open()) + continue; + + *data.fs << "OBJECT " << s_type->GetName(); + if (base->id) + *data.fs << "\nID " << base->id; + base->Serialize(data); + *data.fs << "\nEND\n"; + } + + for (std::map::iterator it = databases.begin(), it_end = databases.end(); it != it_end; ++it) + { + std::fstream *f = it->second; + const Anope::string &db_name = Anope::DataDir + "/" + (it->first ? (it->first->name + ".db") : Config->GetModule(this)->Get("database", "anope.db")); + + if (!f->is_open() || !f->good()) + { + this->Write("Unable to write database " + db_name); + + f->close(); + } + else + { + f->close(); +#ifdef _WIN32 + /* Windows rename() fails if the file already exists. */ + remove(db_name.c_str()); +#endif + rename((db_name + ".tmp").c_str(), db_name.c_str()); + } + + delete f; + } + } + catch (...) + { + if (i) + throw; + } + + if (!i) + { + this->Notify(); + exit(0); + } + } + + /* Load just one type. Done if a module is reloaded during runtime */ + void OnSerializeTypeCreate(Serialize::Type *stype) anope_override + { + if (!loaded) + return; + + Anope::string db_name; + if (stype->GetOwner()) + db_name = Anope::DataDir + "/module_" + stype->GetOwner()->name + ".db"; + else + db_name = Anope::DataDir + "/" + Config->GetModule(this)->Get("database", "anope.db"); + + std::fstream fd(db_name.c_str(), std::ios_base::in | std::ios_base::binary); + if (!fd.is_open()) + { + Log(this) << "Unable to open " << db_name << " for reading!"; + return; + } + + LoadData ld; + ld.fs = &fd; + + for (Anope::string buf; std::getline(fd, buf.str());) + { + if (buf == "OBJECT " + stype->GetName()) + { + stype->Unserialize(NULL, ld); + ld.Reset(); + } + } + + fd.close(); + } +}; + +MODULE_INIT(DBFlatFile) diff --git a/modules/database/db_old.cpp b/modules/database/db_old.cpp new file mode 100644 index 0000000..8635945 --- /dev/null +++ b/modules/database/db_old.cpp @@ -0,0 +1,1360 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/os_session.h" +#include "modules/bs_kick.h" +#include "modules/cs_mode.h" +#include "modules/bs_badwords.h" +#include "modules/os_news.h" +#include "modules/suspend.h" +#include "modules/os_forbid.h" +#include "modules/cs_entrymsg.h" + +#define READ(x) \ +if (true) \ +{ \ + if ((x) < 0) \ + printf("Error, the database is broken, line %d, trying to continue... no guarantee.\n", __LINE__); \ +} \ +else \ + static_cast(0) + +#define getc_db(f) (fgetc((f)->fp)) +#define read_db(f, buf, len) (fread((buf), 1, (len), (f)->fp)) +#define read_buffer(buf, f) ((read_db((f), (buf), sizeof(buf)) == sizeof(buf)) ? 0 : -1) + +#define OLD_BI_PRIVATE 0x0001 + +#define OLD_NI_KILLPROTECT 0x00000001 /* Kill others who take this nick */ +#define OLD_NI_SECURE 0x00000002 /* Don't recognize unless IDENTIFY'd */ +#define OLD_NI_MSG 0x00000004 /* Use PRIVMSGs instead of NOTICEs */ +#define OLD_NI_MEMO_HARDMAX 0x00000008 /* Don't allow user to change memo limit */ +#define OLD_NI_MEMO_SIGNON 0x00000010 /* Notify of memos at signon and un-away */ +#define OLD_NI_MEMO_RECEIVE 0x00000020 /* Notify of new memos when sent */ +#define OLD_NI_PRIVATE 0x00000040 /* Don't show in LIST to non-servadmins */ +#define OLD_NI_HIDE_EMAIL 0x00000080 /* Don't show E-mail in INFO */ +#define OLD_NI_HIDE_MASK 0x00000100 /* Don't show last seen address in INFO */ +#define OLD_NI_HIDE_QUIT 0x00000200 /* Don't show last quit message in INFO */ +#define OLD_NI_KILL_QUICK 0x00000400 /* Kill in 20 seconds instead of 60 */ +#define OLD_NI_KILL_IMMED 0x00000800 /* Kill immediately instead of in 60 sec */ +#define OLD_NI_MEMO_MAIL 0x00010000 /* User gets email on memo */ +#define OLD_NI_HIDE_STATUS 0x00020000 /* Don't show services access status */ +#define OLD_NI_SUSPENDED 0x00040000 /* Nickname is suspended */ +#define OLD_NI_AUTOOP 0x00080000 /* Autoop nickname in channels */ + +#define OLD_NS_NO_EXPIRE 0x0004 /* nick won't expire */ +#define OLD_NS_VERBOTEN 0x0002 + +#define OLD_CI_KEEPTOPIC 0x00000001 +#define OLD_CI_SECUREOPS 0x00000002 +#define OLD_CI_PRIVATE 0x00000004 +#define OLD_CI_TOPICLOCK 0x00000008 +#define OLD_CI_RESTRICTED 0x00000010 +#define OLD_CI_PEACE 0x00000020 +#define OLD_CI_SECURE 0x00000040 +#define OLD_CI_VERBOTEN 0x00000080 +#define OLD_CI_ENCRYPTEDPW 0x00000100 +#define OLD_CI_NO_EXPIRE 0x00000200 +#define OLD_CI_MEMO_HARDMAX 0x00000400 +#define OLD_CI_OPNOTICE 0x00000800 +#define OLD_CI_SECUREFOUNDER 0x00001000 +#define OLD_CI_SIGNKICK 0x00002000 +#define OLD_CI_SIGNKICK_LEVEL 0x00004000 +#define OLD_CI_XOP 0x00008000 +#define OLD_CI_SUSPENDED 0x00010000 + +/* BotServ SET flags */ +#define OLD_BS_DONTKICKOPS 0x00000001 +#define OLD_BS_DONTKICKVOICES 0x00000002 +#define OLD_BS_FANTASY 0x00000004 +#define OLD_BS_SYMBIOSIS 0x00000008 +#define OLD_BS_GREET 0x00000010 +#define OLD_BS_NOBOT 0x00000020 + +/* BotServ Kickers flags */ +#define OLD_BS_KICK_BOLDS 0x80000000 +#define OLD_BS_KICK_COLORS 0x40000000 +#define OLD_BS_KICK_REVERSES 0x20000000 +#define OLD_BS_KICK_UNDERLINES 0x10000000 +#define OLD_BS_KICK_BADWORDS 0x08000000 +#define OLD_BS_KICK_CAPS 0x04000000 +#define OLD_BS_KICK_FLOOD 0x02000000 +#define OLD_BS_KICK_REPEAT 0x01000000 + +#define OLD_NEWS_LOGON 0 +#define OLD_NEWS_OPER 1 +#define OLD_NEWS_RANDOM 2 + +static struct mlock_info +{ + char c; + uint32_t m; +} mlock_infos[] = { + {'i', 0x00000001}, + {'m', 0x00000002}, + {'n', 0x00000004}, + {'p', 0x00000008}, + {'s', 0x00000010}, + {'t', 0x00000020}, + {'R', 0x00000100}, + {'r', 0x00000200}, + {'c', 0x00000400}, + {'A', 0x00000800}, + {'K', 0x00002000}, + {'O', 0x00008000}, + {'Q', 0x00010000}, + {'S', 0x00020000}, + {'G', 0x00100000}, + {'C', 0x00200000}, + {'u', 0x00400000}, + {'z', 0x00800000}, + {'N', 0x01000000}, + {'M', 0x04000000} +}; + +static Anope::string hashm; + +enum +{ + LANG_EN_US, /* United States English */ + LANG_JA_JIS, /* Japanese (JIS encoding) */ + LANG_JA_EUC, /* Japanese (EUC encoding) */ + LANG_JA_SJIS, /* Japanese (SJIS encoding) */ + LANG_ES, /* Spanish */ + LANG_PT, /* Portugese */ + LANG_FR, /* French */ + LANG_TR, /* Turkish */ + LANG_IT, /* Italian */ + LANG_DE, /* German */ + LANG_CAT, /* Catalan */ + LANG_GR, /* Greek */ + LANG_NL, /* Dutch */ + LANG_RU, /* Russian */ + LANG_HUN, /* Hungarian */ + LANG_PL /* Polish */ +}; + +static void process_mlock(ChannelInfo *ci, uint32_t lock, bool status, uint32_t *limit, Anope::string *key) +{ + ModeLocks *ml = ci->Require("modelocks"); + for (unsigned i = 0; i < (sizeof(mlock_infos) / sizeof(mlock_info)); ++i) + if (lock & mlock_infos[i].m) + { + ChannelMode *cm = ModeManager::FindChannelModeByChar(mlock_infos[i].c); + if (cm && ml) + { + if (limit && mlock_infos[i].c == 'l') + ml->SetMLock(cm, status, stringify(*limit)); + else if (key && mlock_infos[i].c == 'k') + ml->SetMLock(cm, status, *key); + else + ml->SetMLock(cm, status); + } + } +} + +static const char Base64[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"; +static const char Pad64 = '='; + +static void my_b64_encode(const Anope::string &src, Anope::string &target) +{ + size_t src_pos = 0, src_len = src.length(); + unsigned char input[3]; + + target.clear(); + + while (src_len - src_pos > 2) + { + input[0] = src[src_pos++]; + input[1] = src[src_pos++]; + input[2] = src[src_pos++]; + + target += Base64[input[0] >> 2]; + target += Base64[((input[0] & 0x03) << 4) + (input[1] >> 4)]; + target += Base64[((input[1] & 0x0f) << 2) + (input[2] >> 6)]; + target += Base64[input[2] & 0x3f]; + } + + /* Now we worry about padding */ + if (src_pos != src_len) + { + input[0] = input[1] = input[2] = 0; + for (size_t i = 0; i < src_len - src_pos; ++i) + input[i] = src[src_pos + i]; + + target += Base64[input[0] >> 2]; + target += Base64[((input[0] & 0x03) << 4) + (input[1] >> 4)]; + if (src_pos == src_len - 1) + target += Pad64; + else + target += Base64[((input[1] & 0x0f) << 2) + (input[2] >> 6)]; + target += Pad64; + } +} + +static Anope::string Hex(const char *data, size_t l) +{ + const char hextable[] = "0123456789abcdef"; + + std::string rv; + for (size_t i = 0; i < l; ++i) + { + unsigned char c = data[i]; + rv += hextable[c >> 4]; + rv += hextable[c & 0xF]; + } + return rv; +} + +static Anope::string GetLevelName(int level) +{ + switch (level) + { + case 0: + return "INVITE"; + case 1: + return "AKICK"; + case 2: + return "SET"; + case 3: + return "UNBAN"; + case 4: + return "AUTOOP"; + case 5: + return "AUTODEOP"; + case 6: + return "AUTOVOICE"; + case 7: + return "OP"; + case 8: + return "ACCESS_LIST"; + case 9: + return "CLEAR"; + case 10: + return "NOJOIN"; + case 11: + return "ACCESS_CHANGE"; + case 12: + return "MEMO"; + case 13: + return "ASSIGN"; + case 14: + return "BADWORDS"; + case 15: + return "NOKICK"; + case 16: + return "FANTASIA"; + case 17: + return "SAY"; + case 18: + return "GREET"; + case 19: + return "VOICEME"; + case 20: + return "VOICE"; + case 21: + return "GETKEY"; + case 22: + return "AUTOHALFOP"; + case 23: + return "AUTOPROTECT"; + case 24: + return "OPME"; + case 25: + return "HALFOPME"; + case 26: + return "HALFOP"; + case 27: + return "PROTECTME"; + case 28: + return "PROTECT"; + case 29: + return "KICKME"; + case 30: + return "KICK"; + case 31: + return "SIGNKICK"; + case 32: + return "BANME"; + case 33: + return "BAN"; + case 34: + return "TOPIC"; + case 35: + return "INFO"; + default: + return "INVALID"; + } +} + +static char *strscpy(char *d, const char *s, size_t len) +{ + char *d_orig = d; + + if (!len) + return d; + while (--len && (*d++ = *s++)); + *d = '\0'; + return d_orig; +} + +struct dbFILE +{ + int mode; /* 'r' for reading, 'w' for writing */ + FILE *fp; /* The normal file descriptor */ + char filename[1024]; /* Name of the database file */ +}; + +static dbFILE *open_db_read(const char *service, const char *filename, int version) +{ + dbFILE *f; + FILE *fp; + int myversion; + + f = new dbFILE; + strscpy(f->filename, (Anope::DataDir + "/" + filename).c_str(), sizeof(f->filename)); + f->mode = 'r'; + fp = fopen(f->filename, "rb"); + if (!fp) + { + Log() << "Can't read " << service << " database " << f->filename; + delete f; + return NULL; + } + f->fp = fp; + myversion = fgetc(fp) << 24 | fgetc(fp) << 16 | fgetc(fp) << 8 | fgetc(fp); + if (feof(fp)) + { + Log() << "Error reading version number on " << f->filename << ": End of file detected."; + delete f; + return NULL; + } + else if (myversion < version) + { + Log() << "Unsupported database version (" << myversion << ") on " << f->filename << "."; + delete f; + return NULL; + } + return f; +} + +void close_db(dbFILE *f) +{ + fclose(f->fp); + delete f; +} + +static int read_int16(int16_t *ret, dbFILE *f) +{ + int c1, c2; + + *ret = 0; + + c1 = fgetc(f->fp); + c2 = fgetc(f->fp); + if (c1 == EOF || c2 == EOF) + return -1; + *ret = c1 << 8 | c2; + return 0; +} + +static int read_uint16(uint16_t *ret, dbFILE *f) +{ + int c1, c2; + + *ret = 0; + + c1 = fgetc(f->fp); + c2 = fgetc(f->fp); + if (c1 == EOF || c2 == EOF) + return -1; + *ret = c1 << 8 | c2; + return 0; +} + +static int read_string(Anope::string &str, dbFILE *f) +{ + str.clear(); + uint16_t len; + + if (read_uint16(&len, f) < 0) + return -1; + if (len == 0) + return 0; + char *s = new char[len]; + if (len != fread(s, 1, len, f->fp)) + { + delete [] s; + return -1; + } + str = s; + delete [] s; + return 0; +} + +static int read_uint32(uint32_t *ret, dbFILE *f) +{ + int c1, c2, c3, c4; + + *ret = 0; + + c1 = fgetc(f->fp); + c2 = fgetc(f->fp); + c3 = fgetc(f->fp); + c4 = fgetc(f->fp); + if (c1 == EOF || c2 == EOF || c3 == EOF || c4 == EOF) + return -1; + *ret = c1 << 24 | c2 << 16 | c3 << 8 | c4; + return 0; +} + +int read_int32(int32_t *ret, dbFILE *f) +{ + int c1, c2, c3, c4; + + *ret = 0; + + c1 = fgetc(f->fp); + c2 = fgetc(f->fp); + c3 = fgetc(f->fp); + c4 = fgetc(f->fp); + if (c1 == EOF || c2 == EOF || c3 == EOF || c4 == EOF) + return -1; + *ret = c1 << 24 | c2 << 16 | c3 << 8 | c4; + return 0; +} + +static void LoadNicks() +{ + ServiceReference forbid("ForbidService", "forbid"); + dbFILE *f = open_db_read("NickServ", "nick.db", 14); + if (f == NULL) + return; + for (int i = 0; i < 1024; ++i) + for (int c; (c = getc_db(f)) == 1;) + { + Anope::string buffer; + + READ(read_string(buffer, f)); + NickCore *nc = new NickCore(buffer); + + const Anope::string settings[] = { "killprotect", "kill_quick", "ns_secure", "ns_private", "hide_email", + "hide_mask", "hide_quit", "memo_signon", "memo_receive", "autoop", "msg", "ns_keepmodes" }; + for (unsigned j = 0; j < sizeof(settings) / sizeof(Anope::string); ++j) + nc->Shrink(settings[j].upper()); + + char pwbuf[32]; + READ(read_buffer(pwbuf, f)); + if (hashm == "plain") + my_b64_encode(pwbuf, nc->pass); + else if (hashm == "md5" || hashm == "oldmd5") + nc->pass = Hex(pwbuf, 16); + else if (hashm == "sha1") + nc->pass = Hex(pwbuf, 20); + else + nc->pass = Hex(pwbuf, strlen(pwbuf)); + nc->pass = hashm + ":" + nc->pass; + + READ(read_string(buffer, f)); + nc->email = buffer; + + READ(read_string(buffer, f)); + if (!buffer.empty()) + nc->Extend("greet", buffer); + + uint32_t u32; + READ(read_uint32(&u32, f)); + //nc->icq = u32; + + READ(read_string(buffer, f)); + //nc->url = buffer; + + READ(read_uint32(&u32, f)); + if (u32 & OLD_NI_KILLPROTECT) + nc->Extend("KILLPROTECT"); + if (u32 & OLD_NI_SECURE) + nc->Extend("NS_SECURE"); + if (u32 & OLD_NI_MSG) + nc->Extend("MSG"); + if (u32 & OLD_NI_MEMO_HARDMAX) + nc->Extend("MEMO_HARDMAX"); + if (u32 & OLD_NI_MEMO_SIGNON) + nc->Extend("MEMO_SIGNON"); + if (u32 & OLD_NI_MEMO_RECEIVE) + nc->Extend("MEMO_RECEIVE"); + if (u32 & OLD_NI_PRIVATE) + nc->Extend("NS_PRIVATE"); + if (u32 & OLD_NI_HIDE_EMAIL) + nc->Extend("HIDE_EMAIL"); + if (u32 & OLD_NI_HIDE_MASK) + nc->Extend("HIDE_MASK"); + if (u32 & OLD_NI_HIDE_QUIT) + nc->Extend("HIDE_QUIT"); + if (u32 & OLD_NI_KILL_QUICK) + nc->Extend("KILL_QUICK"); + if (u32 & OLD_NI_KILL_IMMED) + nc->Extend("KILL_IMMED"); + if (u32 & OLD_NI_MEMO_MAIL) + nc->Extend("MEMO_MAIL"); + if (u32 & OLD_NI_HIDE_STATUS) + nc->Extend("HIDE_STATUS"); + if (u32 & OLD_NI_SUSPENDED) + { + SuspendInfo si; + si.what = nc->display; + si.when = si.expires = 0; + nc->Extend("NS_SUSPENDED", si); + } + if (!(u32 & OLD_NI_AUTOOP)) + nc->Extend("AUTOOP"); + + uint16_t u16; + READ(read_uint16(&u16, f)); + switch (u16) + { + case LANG_ES: + nc->language = "es_ES.UTF-8"; + break; + case LANG_PT: + nc->language = "pt_PT.UTF-8"; + break; + case LANG_FR: + nc->language = "fr_FR.UTF-8"; + break; + case LANG_TR: + nc->language = "tr_TR.UTF-8"; + break; + case LANG_IT: + nc->language = "it_IT.UTF-8"; + break; + case LANG_DE: + nc->language = "de_DE.UTF-8"; + break; + case LANG_CAT: + nc->language = "ca_ES.UTF-8"; // yes, iso639 defines catalan as CA + break; + case LANG_GR: + nc->language = "el_GR.UTF-8"; + break; + case LANG_NL: + nc->language = "nl_NL.UTF-8"; + break; + case LANG_RU: + nc->language = "ru_RU.UTF-8"; + break; + case LANG_HUN: + nc->language = "hu_HU.UTF-8"; + break; + case LANG_PL: + nc->language = "pl_PL.UTF-8"; + break; + case LANG_EN_US: + case LANG_JA_JIS: + case LANG_JA_EUC: + case LANG_JA_SJIS: // these seem to be unused + default: + nc->language = "en"; + } + + READ(read_uint16(&u16, f)); + for (uint16_t j = 0; j < u16; ++j) + { + READ(read_string(buffer, f)); + nc->access.push_back(buffer); + } + + int16_t i16; + READ(read_int16(&i16, f)); + READ(read_int16(&nc->memos.memomax, f)); + for (int16_t j = 0; j < i16; ++j) + { + Memo *m = new Memo; + READ(read_uint32(&u32, f)); + uint16_t flags; + READ(read_uint16(&flags, f)); + int32_t tmp32; + READ(read_int32(&tmp32, f)); + m->time = tmp32; + char sbuf[32]; + READ(read_buffer(sbuf, f)); + m->sender = sbuf; + READ(read_string(m->text, f)); + m->owner = nc->display; + nc->memos.memos->push_back(m); + m->mi = &nc->memos; + } + READ(read_uint16(&u16, f)); + READ(read_int16(&i16, f)); + + Log(LOG_DEBUG) << "Loaded NickCore " << nc->display; + } + + for (int i = 0; i < 1024; ++i) + for (int c; (c = getc_db(f)) == 1;) + { + Anope::string nick, last_usermask, last_realname, last_quit; + time_t time_registered, last_seen; + + READ(read_string(nick, f)); + READ(read_string(last_usermask, f)); + READ(read_string(last_realname, f)); + READ(read_string(last_quit, f)); + + int32_t tmp32; + READ(read_int32(&tmp32, f)); + time_registered = tmp32; + READ(read_int32(&tmp32, f)); + last_seen = tmp32; + + uint16_t tmpu16; + READ(read_uint16(&tmpu16, f)); + + Anope::string core; + READ(read_string(core, f)); + NickCore *nc = NickCore::Find(core); + if (nc == NULL) + { + Log() << "Skipping coreless nick " << nick << " with core " << core; + continue; + } + + if (tmpu16 & OLD_NS_VERBOTEN) + { + if (!forbid) + { + delete nc; + continue; + } + + if (nc->display.find_first_of("?*") != Anope::string::npos) + { + delete nc; + continue; + } + + ForbidData *d = forbid->CreateForbid(); + d->mask = nc->display; + d->creator = last_usermask; + d->reason = last_realname; + d->expires = 0; + d->created = 0; + d->type = FT_NICK; + delete nc; + forbid->AddForbid(d); + continue; + } + + NickAlias *na = new NickAlias(nick, nc); + na->last_usermask = last_usermask; + na->last_realname = last_realname; + na->last_quit = last_quit; + na->time_registered = time_registered; + na->last_seen = last_seen; + + if (tmpu16 & OLD_NS_NO_EXPIRE) + na->Extend("NS_NO_EXPIRE"); + + Log(LOG_DEBUG) << "Loaded NickAlias " << na->nick; + } + + close_db(f); /* End of section Ia */ +} + +static void LoadVHosts() +{ + dbFILE *f = open_db_read("HostServ", "hosts.db", 3); + if (f == NULL) + return; + + for (int c; (c = getc_db(f)) == 1;) + { + Anope::string nick, ident, host, creator; + int32_t vtime; + + READ(read_string(nick, f)); + READ(read_string(ident, f)); + READ(read_string(host, f)); + READ(read_string(creator, f)); + READ(read_int32(&vtime, f)); + + NickAlias *na = NickAlias::Find(nick); + if (na == NULL) + { + Log() << "Removing vhost for nonexistent nick " << nick; + continue; + } + + na->SetVhost(ident, host, creator, vtime); + + Log() << "Loaded vhost for " << na->nick; + } + + close_db(f); +} + +static void LoadBots() +{ + dbFILE *f = open_db_read("Botserv", "bot.db", 10); + if (f == NULL) + return; + + for (int c; (c = getc_db(f)) == 1;) + { + Anope::string nick, user, host, real; + int16_t flags, chancount; + int32_t created; + + READ(read_string(nick, f)); + READ(read_string(user, f)); + READ(read_string(host, f)); + READ(read_string(real, f)); + READ(read_int16(&flags, f)); + READ(read_int32(&created, f)); + READ(read_int16(&chancount, f)); + + BotInfo *bi = BotInfo::Find(nick, true); + if (!bi) + bi = new BotInfo(nick, user, host, real); + bi->created = created; + + if (flags & OLD_BI_PRIVATE) + bi->oper_only = true; + + Log(LOG_DEBUG) << "Loaded bot " << bi->nick; + } + + close_db(f); +} + +static void LoadChannels() +{ + ServiceReference forbid("ForbidService", "forbid"); + dbFILE *f = open_db_read("ChanServ", "chan.db", 16); + if (f == NULL) + return; + + for (int i = 0; i < 256; ++i) + for (int c; (c = getc_db(f)) == 1;) + { + Anope::string buffer; + char namebuf[64]; + READ(read_buffer(namebuf, f)); + ChannelInfo *ci = new ChannelInfo(namebuf); + + const Anope::string settings[] = { "keeptopic", "peace", "cs_private", "restricted", "cs_secure", "secureops", "securefounder", + "signkick", "signkick_level", "topiclock", "persist", "noautoop", "cs_keepmodes" }; + for (unsigned j = 0; j < sizeof(settings) / sizeof(Anope::string); ++j) + ci->Shrink(settings[j].upper()); + + READ(read_string(buffer, f)); + ci->SetFounder(NickCore::Find(buffer)); + + READ(read_string(buffer, f)); + ci->SetSuccessor(NickCore::Find(buffer)); + + char pwbuf[32]; + READ(read_buffer(pwbuf, f)); + + READ(read_string(ci->desc, f)); + READ(read_string(buffer, f)); + READ(read_string(buffer, f)); + + int32_t tmp32; + READ(read_int32(&tmp32, f)); + ci->time_registered = tmp32; + + READ(read_int32(&tmp32, f)); + ci->last_used = tmp32; + + READ(read_string(ci->last_topic, f)); + + READ(read_buffer(pwbuf, f)); + ci->last_topic_setter = pwbuf; + + READ(read_int32(&tmp32, f)); + ci->last_topic_time = tmp32; + + uint32_t tmpu32; + READ(read_uint32(&tmpu32, f)); + // Temporary flags cleanup + tmpu32 &= ~0x80000000; + if (tmpu32 & OLD_CI_KEEPTOPIC) + ci->Extend("KEEPTOPIC"); + if (tmpu32 & OLD_CI_SECUREOPS) + ci->Extend("SECUREOPS"); + if (tmpu32 & OLD_CI_PRIVATE) + ci->Extend("CS_PRIVATE"); + if (tmpu32 & OLD_CI_TOPICLOCK) + ci->Extend("TOPICLOCK"); + if (tmpu32 & OLD_CI_RESTRICTED) + ci->Extend("RESTRICTED"); + if (tmpu32 & OLD_CI_PEACE) + ci->Extend("PEACE"); + if (tmpu32 & OLD_CI_SECURE) + ci->Extend("CS_SECURE"); + if (tmpu32 & OLD_CI_NO_EXPIRE) + ci->Extend("CS_NO_EXPIRE"); + if (tmpu32 & OLD_CI_MEMO_HARDMAX) + ci->Extend("MEMO_HARDMAX"); + if (tmpu32 & OLD_CI_SECUREFOUNDER) + ci->Extend("SECUREFOUNDER"); + if (tmpu32 & OLD_CI_SIGNKICK) + ci->Extend("SIGNKICK"); + if (tmpu32 & OLD_CI_SIGNKICK_LEVEL) + ci->Extend("SIGNKICK_LEVEL"); + + Anope::string forbidby, forbidreason; + READ(read_string(forbidby, f)); + READ(read_string(forbidreason, f)); + if (tmpu32 & OLD_CI_SUSPENDED) + { + SuspendInfo si; + si.what = ci->name; + si.by = forbidby; + si.reason = forbidreason; + si.when = si.expires = 0; + ci->Extend("CS_SUSPENDED", si); + } + bool forbid_chan = tmpu32 & OLD_CI_VERBOTEN; + + int16_t tmp16; + READ(read_int16(&tmp16, f)); + ci->bantype = tmp16; + + READ(read_int16(&tmp16, f)); + if (tmp16 > 36) + tmp16 = 36; + for (int16_t j = 0; j < tmp16; ++j) + { + int16_t level; + READ(read_int16(&level, f)); + + if (level == ACCESS_INVALID) + level = ACCESS_FOUNDER; + + if (j == 10 && level < 0) // NOJOIN + ci->Shrink("RESTRICTED"); // If CSDefRestricted was enabled this can happen + + ci->SetLevel(GetLevelName(j), level); + } + + bool xop = tmpu32 & OLD_CI_XOP; + ServiceReference provider_access("AccessProvider", "access/access"), provider_xop("AccessProvider", "access/xop"); + uint16_t tmpu16; + READ(read_uint16(&tmpu16, f)); + for (uint16_t j = 0; j < tmpu16; ++j) + { + uint16_t in_use; + READ(read_uint16(&in_use, f)); + if (in_use) + { + ChanAccess *access = NULL; + + if (xop) + { + if (provider_xop) + access = provider_xop->Create(); + } + else + if (provider_access) + access = provider_access->Create(); + + if (access) + access->ci = ci; + + int16_t level; + READ(read_int16(&level, f)); + if (access) + { + if (xop) + { + switch (level) + { + case 3: + access->AccessUnserialize("VOP"); + break; + case 4: + access->AccessUnserialize("HOP"); + break; + case 5: + access->AccessUnserialize("AOP"); + break; + case 10: + access->AccessUnserialize("SOP"); + break; + } + } + else + access->AccessUnserialize(stringify(level)); + } + + Anope::string mask; + READ(read_string(mask, f)); + if (access) + access->SetMask(mask, ci); + + READ(read_int32(&tmp32, f)); + if (access) + { + access->last_seen = tmp32; + access->creator = "Unknown"; + access->created = Anope::CurTime; + + ci->AddAccess(access); + } + } + } + + READ(read_uint16(&tmpu16, f)); + for (uint16_t j = 0; j < tmpu16; ++j) + { + uint16_t flags; + READ(read_uint16(&flags, f)); + if (flags & 0x0001) + { + Anope::string mask, reason, creator; + READ(read_string(mask, f)); + READ(read_string(reason, f)); + READ(read_string(creator, f)); + READ(read_int32(&tmp32, f)); + + ci->AddAkick(creator, mask, reason, tmp32); + } + } + + READ(read_uint32(&tmpu32, f)); // mlock on + ci->Extend("mlock_on", tmpu32); + READ(read_uint32(&tmpu32, f)); // mlock off + ci->Extend("mlock_off", tmpu32); + READ(read_uint32(&tmpu32, f)); // mlock limit + ci->Extend("mlock_limit", tmpu32); + READ(read_string(buffer, f)); // key + ci->Extend("mlock_key", buffer); + READ(read_string(buffer, f)); // +f + READ(read_string(buffer, f)); // +L + + READ(read_int16(&tmp16, f)); + READ(read_int16(&ci->memos.memomax, f)); + for (int16_t j = 0; j < tmp16; ++j) + { + READ(read_uint32(&tmpu32, f)); + READ(read_uint16(&tmpu16, f)); + Memo *m = new Memo; + READ(read_int32(&tmp32, f)); + m->time = tmp32; + char sbuf[32]; + READ(read_buffer(sbuf, f)); + m->sender = sbuf; + READ(read_string(m->text, f)); + m->owner = ci->name; + ci->memos.memos->push_back(m); + m->mi = &ci->memos; + } + + READ(read_string(buffer, f)); + if (!buffer.empty()) + { + EntryMessageList *eml = ci->Require("entrymsg"); + if (eml) + { + EntryMsg *e = eml->Create(); + + e->chan = ci->name; + e->creator = "Unknown"; + e->message = buffer; + e->when = Anope::CurTime; + + (*eml)->push_back(e); + } + } + + READ(read_string(buffer, f)); + ci->bi = BotInfo::Find(buffer, true); + + READ(read_int32(&tmp32, f)); + if (tmp32 & OLD_BS_DONTKICKOPS) + ci->Extend("BS_DONTKICKOPS"); + if (tmp32 & OLD_BS_DONTKICKVOICES) + ci->Extend("BS_DONTKICKVOICES"); + if (tmp32 & OLD_BS_FANTASY) + ci->Extend("BS_FANTASY"); + if (tmp32 & OLD_BS_GREET) + ci->Extend("BS_GREET"); + if (tmp32 & OLD_BS_NOBOT) + ci->Extend("BS_NOBOT"); + + KickerData *kd = ci->Require("kickerdata"); + if (kd) + { + if (tmp32 & OLD_BS_KICK_BOLDS) + kd->bolds = true; + if (tmp32 & OLD_BS_KICK_COLORS) + kd->colors = true; + if (tmp32 & OLD_BS_KICK_REVERSES) + kd->reverses = true; + if (tmp32 & OLD_BS_KICK_UNDERLINES) + kd->underlines = true; + if (tmp32 & OLD_BS_KICK_BADWORDS) + kd->badwords = true; + if (tmp32 & OLD_BS_KICK_CAPS) + kd->caps = true; + if (tmp32 & OLD_BS_KICK_FLOOD) + kd->flood = true; + if (tmp32 & OLD_BS_KICK_REPEAT) + kd->repeat = true; + } + + READ(read_int16(&tmp16, f)); + for (int16_t j = 0; j < tmp16; ++j) + { + int16_t ttb; + READ(read_int16(&ttb, f)); + if (j < TTB_SIZE && kd) + kd->ttb[j] = ttb; + } + + READ(read_int16(&tmp16, f)); + if (kd) + kd->capsmin = tmp16; + READ(read_int16(&tmp16, f)); + if (kd) + kd->capspercent = tmp16; + READ(read_int16(&tmp16, f)); + if (kd) + kd->floodlines = tmp16; + READ(read_int16(&tmp16, f)); + if (kd) + kd->floodsecs = tmp16; + READ(read_int16(&tmp16, f)); + if (kd) + kd->repeattimes = tmp16; + + BadWords *bw = ci->Require("badwords"); + READ(read_uint16(&tmpu16, f)); + for (uint16_t j = 0; j < tmpu16; ++j) + { + uint16_t in_use; + READ(read_uint16(&in_use, f)); + if (in_use) + { + READ(read_string(buffer, f)); + uint16_t type; + READ(read_uint16(&type, f)); + + BadWordType bwtype = BW_ANY; + if (type == 1) + bwtype = BW_SINGLE; + else if (type == 2) + bwtype = BW_START; + else if (type == 3) + bwtype = BW_END; + + if (bw) + bw->AddBadWord(buffer, bwtype); + } + } + + if (forbid_chan) + { + if (!forbid) + { + delete ci; + continue; + } + + if (ci->name.find_first_of("?*") != Anope::string::npos) + { + delete ci; + continue; + } + + ForbidData *d = forbid->CreateForbid(); + d->mask = ci->name; + d->creator = forbidby; + d->reason = forbidreason; + d->expires = 0; + d->created = 0; + d->type = FT_CHAN; + delete ci; + forbid->AddForbid(d); + continue; + } + + Log(LOG_DEBUG) << "Loaded channel " << ci->name; + } + + close_db(f); +} + +static void LoadOper() +{ + dbFILE *f = open_db_read("OperServ", "oper.db", 13); + if (f == NULL) + return; + + XLineManager *akill, *sqline, *snline, *szline; + akill = sqline = snline = szline = NULL; + + for (std::list::iterator it = XLineManager::XLineManagers.begin(), it_end = XLineManager::XLineManagers.end(); it != it_end; ++it) + { + XLineManager *xl = *it; + if (xl->Type() == 'G') + akill = xl; + else if (xl->Type() == 'Q') + sqline = xl; + else if (xl->Type() == 'N') + snline = xl; + else if (xl->Type() == 'Z') + szline = xl; + } + + int32_t tmp32; + READ(read_int32(&tmp32, f)); + READ(read_int32(&tmp32, f)); + + int16_t capacity; + read_int16(&capacity, f); // AKill count + for (int16_t i = 0; i < capacity; ++i) + { + Anope::string user, host, by, reason; + int32_t seton, expires; + + READ(read_string(user, f)); + READ(read_string(host, f)); + READ(read_string(by, f)); + READ(read_string(reason, f)); + READ(read_int32(&seton, f)); + READ(read_int32(&expires, f)); + + if (!akill) + continue; + + XLine *x = new XLine(user + "@" + host, by, expires, reason, XLineManager::GenerateUID()); + x->created = seton; + akill->AddXLine(x); + } + + read_int16(&capacity, f); // SNLines + for (int16_t i = 0; i < capacity; ++i) + { + Anope::string mask, by, reason; + int32_t seton, expires; + + READ(read_string(mask, f)); + READ(read_string(by, f)); + READ(read_string(reason, f)); + READ(read_int32(&seton, f)); + READ(read_int32(&expires, f)); + + if (!snline) + continue; + + XLine *x = new XLine(mask, by, expires, reason, XLineManager::GenerateUID()); + x->created = seton; + snline->AddXLine(x); + } + + read_int16(&capacity, f); // SQLines + for (int16_t i = 0; i < capacity; ++i) + { + Anope::string mask, by, reason; + int32_t seton, expires; + + READ(read_string(mask, f)); + READ(read_string(by, f)); + READ(read_string(reason, f)); + READ(read_int32(&seton, f)); + READ(read_int32(&expires, f)); + + if (!sqline) + continue; + + XLine *x = new XLine(mask, by, expires, reason, XLineManager::GenerateUID()); + x->created = seton; + sqline->AddXLine(x); + } + + read_int16(&capacity, f); // SZLines + for (int16_t i = 0; i < capacity; ++i) + { + Anope::string mask, by, reason; + int32_t seton, expires; + + READ(read_string(mask, f)); + READ(read_string(by, f)); + READ(read_string(reason, f)); + READ(read_int32(&seton, f)); + READ(read_int32(&expires, f)); + + if (!szline) + continue; + + XLine *x = new XLine(mask, by, expires, reason, XLineManager::GenerateUID()); + x->created = seton; + szline->AddXLine(x); + } + + close_db(f); +} + +static void LoadExceptions() +{ + if (!session_service) + return; + + dbFILE *f = open_db_read("OperServ", "exception.db", 9); + if (f == NULL) + return; + + int16_t num; + READ(read_int16(&num, f)); + for (int i = 0; i < num; ++i) + { + Anope::string mask, reason; + int16_t limit; + char who[32]; + int32_t time, expires; + + READ(read_string(mask, f)); + READ(read_int16(&limit, f)); + READ(read_buffer(who, f)); + READ(read_string(reason, f)); + READ(read_int32(&time, f)); + READ(read_int32(&expires, f)); + + Exception *exception = session_service->CreateException(); + exception->mask = mask; + exception->limit = limit; + exception->who = who; + exception->time = time; + exception->expires = expires; + exception->reason = reason; + session_service->AddException(exception); + } + + close_db(f); +} + +static void LoadNews() +{ + if (!news_service) + return; + + dbFILE *f = open_db_read("OperServ", "news.db", 9); + + if (f == NULL) + return; + + int16_t n; + READ(read_int16(&n, f)); + + for (int16_t i = 0; i < n; i++) + { + int16_t type; + NewsItem *ni = news_service->CreateNewsItem(); + + READ(read_int16(&type, f)); + + switch (type) + { + case OLD_NEWS_LOGON: + ni->type = NEWS_LOGON; + break; + case OLD_NEWS_OPER: + ni->type = NEWS_OPER; + break; + case OLD_NEWS_RANDOM: + ni->type = NEWS_RANDOM; + break; + } + + int32_t unused; + READ(read_int32(&unused, f)); + + READ(read_string(ni->text, f)); + + char who[32]; + READ(read_buffer(who, f)); + ni->who = who; + + int32_t tmp; + READ(read_int32(&tmp, f)); + ni->time = tmp; + + news_service->AddNewsItem(ni); + } + + close_db(f); +} + +class DBOld : public Module +{ + PrimitiveExtensibleItem mlock_on, mlock_off, mlock_limit; + PrimitiveExtensibleItem mlock_key; + + public: + DBOld(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, DATABASE | VENDOR), + mlock_on(this, "mlock_on"), mlock_off(this, "mlock_off"), mlock_limit(this, "mlock_limit"), mlock_key(this, "mlock_key") + { + + + hashm = Config->GetModule(this)->Get("hash"); + + if (hashm != "md5" && hashm != "oldmd5" && hashm != "sha1" && hashm != "plain" && hashm != "sha256") + throw ModuleException("Invalid hash method"); + } + + EventReturn OnLoadDatabase() anope_override + { + LoadNicks(); + LoadVHosts(); + LoadBots(); + LoadChannels(); + LoadOper(); + LoadExceptions(); + LoadNews(); + + return EVENT_STOP; + } + + void OnUplinkSync(Server *s) anope_override + { + for (registered_channel_map::iterator it = RegisteredChannelList->begin(), it_end = RegisteredChannelList->end(); it != it_end; ++it) + { + ChannelInfo *ci = it->second; + uint32_t *limit = mlock_limit.Get(ci); + Anope::string *key = mlock_key.Get(ci); + + uint32_t *u = mlock_on.Get(ci); + if (u) + { + process_mlock(ci, *u, true, limit, key); + mlock_on.Unset(ci); + } + + u = mlock_off.Get(ci); + if (u) + { + process_mlock(ci, *u, false, limit, key); + mlock_off.Unset(ci); + } + + mlock_limit.Unset(ci); + mlock_key.Unset(ci); + + if (ci->c) + ci->c->CheckModes(); + } + } +}; + +MODULE_INIT(DBOld) diff --git a/modules/database/db_redis.cpp b/modules/database/db_redis.cpp new file mode 100644 index 0000000..2dc2004 --- /dev/null +++ b/modules/database/db_redis.cpp @@ -0,0 +1,668 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/redis.h" + +using namespace Redis; + +class DatabaseRedis; +static DatabaseRedis *me; + +class Data : public Serialize::Data +{ + public: + std::map data; + + ~Data() + { + for (std::map::iterator it = data.begin(), it_end = data.end(); it != it_end; ++it) + delete it->second; + } + + std::iostream& operator[](const Anope::string &key) anope_override + { + std::stringstream* &stream = data[key]; + if (!stream) + stream = new std::stringstream(); + return *stream; + } + + std::set KeySet() const anope_override + { + std::set keys; + for (std::map::const_iterator it = this->data.begin(), it_end = this->data.end(); it != it_end; ++it) + keys.insert(it->first); + return keys; + } + + size_t Hash() const anope_override + { + size_t hash = 0; + for (std::map::const_iterator it = this->data.begin(), it_end = this->data.end(); it != it_end; ++it) + if (!it->second->str().empty()) + hash ^= Anope::hash_cs()(it->second->str()); + return hash; + } +}; + +class TypeLoader : public Interface +{ + Anope::string type; + public: + TypeLoader(Module *creator, const Anope::string &t) : Interface(creator), type(t) { } + + void OnResult(const Reply &r) anope_override; +}; + +class ObjectLoader : public Interface +{ + Anope::string type; + int64_t id; + + public: + ObjectLoader(Module *creator, const Anope::string &t, int64_t i) : Interface(creator), type(t), id(i) { } + + void OnResult(const Reply &r) anope_override; +}; + +class IDInterface : public Interface +{ + Reference o; + public: + IDInterface(Module *creator, Serializable *obj) : Interface(creator), o(obj) { } + + void OnResult(const Reply &r) anope_override; +}; + +class Deleter : public Interface +{ + Anope::string type; + int64_t id; + public: + Deleter(Module *creator, const Anope::string &t, int64_t i) : Interface(creator), type(t), id(i) { } + + void OnResult(const Reply &r) anope_override; +}; + +class Updater : public Interface +{ + Anope::string type; + int64_t id; + public: + Updater(Module *creator, const Anope::string &t, int64_t i) : Interface(creator), type(t), id(i) { } + + void OnResult(const Reply &r) anope_override; +}; + +class ModifiedObject : public Interface +{ + Anope::string type; + int64_t id; + public: + ModifiedObject(Module *creator, const Anope::string &t, int64_t i) : Interface(creator), type(t), id(i) { } + + void OnResult(const Reply &r) anope_override; +}; + +class SubscriptionListener : public Interface +{ + public: + SubscriptionListener(Module *creator) : Interface(creator) { } + + void OnResult(const Reply &r) anope_override; +}; + +class DatabaseRedis : public Module, public Pipe +{ + SubscriptionListener sl; + std::set updated_items; + + public: + ServiceReference redis; + + DatabaseRedis(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, DATABASE | VENDOR), sl(this) + { + me = this; + + } + + /* Insert or update an object */ + void InsertObject(Serializable *obj) + { + Serialize::Type *t = obj->GetSerializableType(); + + /* If there is no id yet for this object, get one */ + if (!obj->id) + redis->SendCommand(new IDInterface(this, obj), "INCR id:" + t->GetName()); + else + { + Data data; + obj->Serialize(data); + + if (obj->IsCached(data)) + return; + + obj->UpdateCache(data); + + std::vector args; + args.push_back("HGETALL"); + args.push_back("hash:" + t->GetName() + ":" + stringify(obj->id)); + + /* Get object attrs to clear before updating */ + redis->SendCommand(new Updater(this, t->GetName(), obj->id), args); + } + } + + void OnNotify() anope_override + { + for (std::set::iterator it = this->updated_items.begin(), it_end = this->updated_items.end(); it != it_end; ++it) + { + Serializable *s = *it; + + this->InsertObject(s); + } + + this->updated_items.clear(); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *block = conf->GetModule(this); + this->redis = ServiceReference("Redis::Provider", block->Get("engine", "redis/main")); + } + + EventReturn OnLoadDatabase() anope_override + { + if (!redis) + { + Log(this) << "Unable to load database - unable to find redis provider"; + return EVENT_CONTINUE; + } + + const std::vector type_order = Serialize::Type::GetTypeOrder(); + for (unsigned i = 0; i < type_order.size(); ++i) + { + Serialize::Type *sb = Serialize::Type::Find(type_order[i]); + this->OnSerializeTypeCreate(sb); + } + + while (!redis->IsSocketDead() && redis->BlockAndProcess()); + + if (redis->IsSocketDead()) + { + Log(this) << "I/O error while loading redis database - is it online?"; + return EVENT_CONTINUE; + } + + redis->Subscribe(&this->sl, "__keyspace@*__:hash:*"); + + return EVENT_STOP; + } + + void OnSerializeTypeCreate(Serialize::Type *sb) anope_override + { + if (!redis) + return; + + std::vector args; + args.push_back("SMEMBERS"); + args.push_back("ids:" + sb->GetName()); + + redis->SendCommand(new TypeLoader(this, sb->GetName()), args); + } + + void OnSerializableConstruct(Serializable *obj) anope_override + { + this->updated_items.insert(obj); + this->Notify(); + } + + void OnSerializableDestruct(Serializable *obj) anope_override + { + Serialize::Type *t = obj->GetSerializableType(); + + if (t == NULL) + { + /* This is probably the module providing the type unloading. + * + * The types get registered after the extensible container is + * registered so that unserialization on module load can insert + * into the extensible container. So, the type destructs prior to + * the extensible container, which then triggers this + */ + return; + } + + std::vector args; + args.push_back("HGETALL"); + args.push_back("hash:" + t->GetName() + ":" + stringify(obj->id)); + + /* Get all of the attributes for this object */ + redis->SendCommand(new Deleter(this, t->GetName(), obj->id), args); + + this->updated_items.erase(obj); + t->objects.erase(obj->id); + this->Notify(); + } + + void OnSerializableUpdate(Serializable *obj) anope_override + { + this->updated_items.insert(obj); + this->Notify(); + } +}; + +void TypeLoader::OnResult(const Reply &r) +{ + if (r.type != Reply::MULTI_BULK || !me->redis) + { + delete this; + return; + } + + for (unsigned i = 0; i < r.multi_bulk.size(); ++i) + { + const Reply *reply = r.multi_bulk[i]; + + if (reply->type != Reply::BULK) + continue; + + int64_t id; + try + { + id = convertTo(reply->bulk); + } + catch (const ConvertException &) + { + continue; + } + + std::vector args; + args.push_back("HGETALL"); + args.push_back("hash:" + this->type + ":" + stringify(id)); + + me->redis->SendCommand(new ObjectLoader(me, this->type, id), args); + } + + delete this; +} + +void ObjectLoader::OnResult(const Reply &r) +{ + Serialize::Type *st = Serialize::Type::Find(this->type); + + if (r.type != Reply::MULTI_BULK || r.multi_bulk.empty() || !me->redis || !st) + { + delete this; + return; + } + + Data data; + + for (unsigned i = 0; i + 1 < r.multi_bulk.size(); i += 2) + { + const Reply *key = r.multi_bulk[i], + *value = r.multi_bulk[i + 1]; + + data[key->bulk] << value->bulk; + } + + Serializable* &obj = st->objects[this->id]; + obj = st->Unserialize(obj, data); + if (obj) + { + obj->id = this->id; + obj->UpdateCache(data); + } + + delete this; +} + +void IDInterface::OnResult(const Reply &r) +{ + if (!o || r.type != Reply::INT || !r.i) + { + delete this; + return; + } + + Serializable* &obj = o->GetSerializableType()->objects[r.i]; + if (obj) + /* This shouldn't be possible */ + obj->id = 0; + + o->id = r.i; + obj = o; + + /* Now that we have the id, insert this object for real */ + anope_dynamic_static_cast(this->owner)->InsertObject(o); + + delete this; +} + +void Deleter::OnResult(const Reply &r) +{ + if (r.type != Reply::MULTI_BULK || !me->redis || r.multi_bulk.empty()) + { + delete this; + return; + } + + /* Transaction start */ + me->redis->StartTransaction(); + + std::vector args; + args.push_back("DEL"); + args.push_back("hash:" + this->type + ":" + stringify(this->id)); + + /* Delete hash object */ + me->redis->SendCommand(NULL, args); + + args.clear(); + args.push_back("SREM"); + args.push_back("ids:" + this->type); + args.push_back(stringify(this->id)); + + /* Delete id from ids set */ + me->redis->SendCommand(NULL, args); + + for (unsigned i = 0; i + 1 < r.multi_bulk.size(); i += 2) + { + const Reply *key = r.multi_bulk[i], + *value = r.multi_bulk[i + 1]; + + args.clear(); + args.push_back("SREM"); + args.push_back("value:" + this->type + ":" + key->bulk + ":" + value->bulk); + args.push_back(stringify(this->id)); + + /* Delete value -> object id */ + me->redis->SendCommand(NULL, args); + } + + /* Transaction end */ + me->redis->CommitTransaction(); + + delete this; +} + +void Updater::OnResult(const Reply &r) +{ + Serialize::Type *st = Serialize::Type::Find(this->type); + + if (!st) + { + delete this; + return; + } + + Serializable *obj = st->objects[this->id]; + if (!obj) + { + delete this; + return; + } + + Data data; + obj->Serialize(data); + + /* Transaction start */ + me->redis->StartTransaction(); + + for (unsigned i = 0; i + 1 < r.multi_bulk.size(); i += 2) + { + const Reply *key = r.multi_bulk[i], + *value = r.multi_bulk[i + 1]; + + std::vector args; + args.push_back("SREM"); + args.push_back("value:" + this->type + ":" + key->bulk + ":" + value->bulk); + args.push_back(stringify(this->id)); + + /* Delete value -> object id */ + me->redis->SendCommand(NULL, args); + } + + /* Add object id to id set for this type */ + std::vector args; + args.push_back("SADD"); + args.push_back("ids:" + this->type); + args.push_back(stringify(obj->id)); + me->redis->SendCommand(NULL, args); + + args.clear(); + args.push_back("HMSET"); + args.push_back("hash:" + this->type + ":" + stringify(obj->id)); + + typedef std::map items; + for (items::iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + { + const Anope::string &key = it->first; + std::stringstream *value = it->second; + + args.push_back(key); + args.push_back(value->str()); + + std::vector args2; + + args2.push_back("SADD"); + args2.push_back("value:" + this->type + ":" + key + ":" + value->str()); + args2.push_back(stringify(obj->id)); + + /* Add to value -> object id set */ + me->redis->SendCommand(NULL, args2); + } + + ++obj->redis_ignore; + + /* Add object */ + me->redis->SendCommand(NULL, args); + + /* Transaction end */ + me->redis->CommitTransaction(); + + delete this; +} + +void SubscriptionListener::OnResult(const Reply &r) +{ + /* + * [May 15 13:59:35.645839 2013] Debug: pmessage + * [May 15 13:59:35.645866 2013] Debug: __keyspace@*__:anope:hash:* + * [May 15 13:59:35.645880 2013] Debug: __keyspace@0__:anope:hash:type:id + * [May 15 13:59:35.645893 2013] Debug: hset + */ + if (r.multi_bulk.size() != 4) + return; + + size_t sz = r.multi_bulk[2]->bulk.find(':'); + if (sz == Anope::string::npos) + return; + + const Anope::string &key = r.multi_bulk[2]->bulk.substr(sz + 1), + &op = r.multi_bulk[3]->bulk; + + sz = key.rfind(':'); + if (sz == Anope::string::npos) + return; + + const Anope::string &id = key.substr(sz + 1); + + size_t sz2 = key.rfind(':', sz - 1); + if (sz2 == Anope::string::npos) + return; + const Anope::string &type = key.substr(sz2 + 1, sz - sz2 - 1); + + Serialize::Type *s_type = Serialize::Type::Find(type); + + if (s_type == NULL) + return; + + uint64_t obj_id; + try + { + obj_id = convertTo(id); + } + catch (const ConvertException &) + { + return; + } + + if (op == "hset" || op == "hdel") + { + Serializable *s = s_type->objects[obj_id]; + + if (s && s->redis_ignore) + { + --s->redis_ignore; + Log(LOG_DEBUG) << "redis: notify: got modify for object id " << obj_id << " of type " << type << ", but I am ignoring it"; + } + else + { + Log(LOG_DEBUG) << "redis: notify: got modify for object id " << obj_id << " of type " << type; + + std::vector args; + args.push_back("HGETALL"); + args.push_back("hash:" + type + ":" + id); + + me->redis->SendCommand(new ModifiedObject(me, type, obj_id), args); + } + } + else if (op == "del") + { + Serializable* &s = s_type->objects[obj_id]; + if (s == NULL) + return; + + Log(LOG_DEBUG) << "redis: notify: deleting object id " << obj_id << " of type " << type; + + Data data; + + s->Serialize(data); + + /* Transaction start */ + me->redis->StartTransaction(); + + typedef std::map items; + for (items::iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + { + const Anope::string &k = it->first; + std::stringstream *value = it->second; + + std::vector args; + args.push_back("SREM"); + args.push_back("value:" + type + ":" + k + ":" + value->str()); + args.push_back(id); + + /* Delete value -> object id */ + me->redis->SendCommand(NULL, args); + } + + std::vector args; + args.push_back("SREM"); + args.push_back("ids:" + type); + args.push_back(stringify(s->id)); + + /* Delete object from id set */ + me->redis->SendCommand(NULL, args); + + /* Transaction end */ + me->redis->CommitTransaction(); + + delete s; + s = NULL; + } +} + +void ModifiedObject::OnResult(const Reply &r) +{ + Serialize::Type *st = Serialize::Type::Find(this->type); + + if (!st) + { + delete this; + return; + } + + Serializable* &obj = st->objects[this->id]; + + /* Transaction start */ + me->redis->StartTransaction(); + + /* Erase old object values */ + if (obj) + { + Data data; + + obj->Serialize(data); + + typedef std::map items; + for (items::iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + { + const Anope::string &key = it->first; + std::stringstream *value = it->second; + + std::vector args; + args.push_back("SREM"); + args.push_back("value:" + st->GetName() + ":" + key + ":" + value->str()); + args.push_back(stringify(this->id)); + + /* Delete value -> object id */ + me->redis->SendCommand(NULL, args); + } + } + + Data data; + + for (unsigned i = 0; i + 1 < r.multi_bulk.size(); i += 2) + { + const Reply *key = r.multi_bulk[i], + *value = r.multi_bulk[i + 1]; + + data[key->bulk] << value->bulk; + } + + obj = st->Unserialize(obj, data); + if (obj) + { + obj->id = this->id; + obj->UpdateCache(data); + + /* Insert new object values */ + typedef std::map items; + for (items::iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + { + const Anope::string &key = it->first; + std::stringstream *value = it->second; + + std::vector args; + args.push_back("SADD"); + args.push_back("value:" + st->GetName() + ":" + key + ":" + value->str()); + args.push_back(stringify(obj->id)); + + /* Add to value -> object id set */ + me->redis->SendCommand(NULL, args); + } + + std::vector args; + args.push_back("SADD"); + args.push_back("ids:" + st->GetName()); + args.push_back(stringify(obj->id)); + + /* Add to type -> id set */ + me->redis->SendCommand(NULL, args); + } + + /* Transaction end */ + me->redis->CommitTransaction(); + + delete this; +} + +MODULE_INIT(DatabaseRedis) diff --git a/modules/database/db_sql.cpp b/modules/database/db_sql.cpp new file mode 100644 index 0000000..fc0b0f2 --- /dev/null +++ b/modules/database/db_sql.cpp @@ -0,0 +1,268 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/sql.h" + +using namespace SQL; + +class SQLSQLInterface : public Interface +{ + public: + SQLSQLInterface(Module *o) : Interface(o) { } + + void OnResult(const Result &r) anope_override + { + Log(LOG_DEBUG) << "SQL successfully executed query: " << r.finished_query; + } + + void OnError(const Result &r) anope_override + { + if (!r.GetQuery().query.empty()) + Log(LOG_DEBUG) << "Error executing query " << r.finished_query << ": " << r.GetError(); + else + Log(LOG_DEBUG) << "Error executing query: " << r.GetError(); + } +}; + +class ResultSQLSQLInterface : public SQLSQLInterface +{ + Reference obj; + +public: + ResultSQLSQLInterface(Module *o, Serializable *ob) : SQLSQLInterface(o), obj(ob) { } + + void OnResult(const Result &r) anope_override + { + SQLSQLInterface::OnResult(r); + if (r.GetID() > 0 && this->obj) + this->obj->id = r.GetID(); + delete this; + } + + void OnError(const Result &r) anope_override + { + SQLSQLInterface::OnError(r); + delete this; + } +}; + +class DBSQL : public Module, public Pipe +{ + ServiceReference sql; + SQLSQLInterface sqlinterface; + Anope::string prefix; + bool import; + + std::set updated_items; + bool shutting_down; + bool loading_databases; + bool loaded; + bool imported; + + void RunBackground(const Query &q, Interface *iface = NULL) + { + if (!this->sql) + { + static time_t last_warn = 0; + if (last_warn + 300 < Anope::CurTime) + { + last_warn = Anope::CurTime; + Log(this) << "db_sql: Unable to execute query, is SQL configured correctly?"; + } + } + else if (!Anope::Quitting) + { + if (iface == NULL) + iface = &this->sqlinterface; + this->sql->Run(iface, q); + } + else + this->sql->RunQuery(q); + } + + public: + DBSQL(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, DATABASE | VENDOR), sql("", ""), sqlinterface(this), shutting_down(false), loading_databases(false), loaded(false), imported(false) + { + + + if (ModuleManager::FindModule("db_sql_live") != NULL) + throw ModuleException("db_sql can not be loaded after db_sql_live"); + } + + void OnNotify() anope_override + { + for (std::set::iterator it = this->updated_items.begin(), it_end = this->updated_items.end(); it != it_end; ++it) + { + Serializable *obj = *it; + + if (this->sql) + { + Data data; + obj->Serialize(data); + + if (obj->IsCached(data)) + continue; + + obj->UpdateCache(data); + + /* If we didn't load these objects and we don't want to import just update the cache and continue */ + if (!this->loaded && !this->imported && !this->import) + continue; + + Serialize::Type *s_type = obj->GetSerializableType(); + if (!s_type) + continue; + + std::vector create = this->sql->CreateTable(this->prefix + s_type->GetName(), data); + Query insert = this->sql->BuildInsert(this->prefix + s_type->GetName(), obj->id, data); + + if (this->imported) + { + for (unsigned i = 0; i < create.size(); ++i) + this->RunBackground(create[i]); + + this->RunBackground(insert, new ResultSQLSQLInterface(this, obj)); + } + else + { + for (unsigned i = 0; i < create.size(); ++i) + this->sql->RunQuery(create[i]); + + /* We are importing objects from another database module, so don't do asynchronous + * queries in case the core has to shut down, it will cut short the import + */ + Result r = this->sql->RunQuery(insert); + if (r.GetID() > 0) + obj->id = r.GetID(); + } + } + } + + this->updated_items.clear(); + this->imported = true; + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *block = conf->GetModule(this); + this->sql = ServiceReference("SQL::Provider", block->Get("engine")); + this->prefix = block->Get("prefix", "anope_db_"); + this->import = block->Get("import"); + } + + void OnShutdown() anope_override + { + this->shutting_down = true; + this->OnNotify(); + } + + void OnRestart() anope_override + { + this->OnShutdown(); + } + + EventReturn OnLoadDatabase() anope_override + { + if (!this->sql) + { + Log(this) << "Unable to load databases, is SQL configured correctly?"; + return EVENT_CONTINUE; + } + + this->loading_databases = true; + + const std::vector type_order = Serialize::Type::GetTypeOrder(); + for (unsigned i = 0; i < type_order.size(); ++i) + { + Serialize::Type *sb = Serialize::Type::Find(type_order[i]); + this->OnSerializeTypeCreate(sb); + } + + this->loading_databases = false; + this->loaded = true; + + return EVENT_STOP; + } + + void OnSerializableConstruct(Serializable *obj) anope_override + { + if (this->shutting_down || this->loading_databases) + return; + obj->UpdateTS(); + this->updated_items.insert(obj); + this->Notify(); + } + + void OnSerializableDestruct(Serializable *obj) anope_override + { + if (this->shutting_down) + return; + Serialize::Type *s_type = obj->GetSerializableType(); + if (s_type && obj->id > 0) + this->RunBackground("DELETE FROM `" + this->prefix + s_type->GetName() + "` WHERE `id` = " + stringify(obj->id)); + this->updated_items.erase(obj); + } + + void OnSerializableUpdate(Serializable *obj) anope_override + { + if (this->shutting_down || obj->IsTSCached()) + return; + if (obj->id == 0) + return; /* object is pending creation */ + obj->UpdateTS(); + this->updated_items.insert(obj); + this->Notify(); + } + + void OnSerializeTypeCreate(Serialize::Type *sb) anope_override + { + if (!this->loading_databases && !this->loaded) + return; + + Query query("SELECT * FROM `" + this->prefix + sb->GetName() + "`"); + Result res = this->sql->RunQuery(query); + + for (int j = 0; j < res.Rows(); ++j) + { + Data data; + + const std::map &row = res.Row(j); + for (std::map::const_iterator rit = row.begin(), rit_end = row.end(); rit != rit_end; ++rit) + data[rit->first] << rit->second; + + Serializable *obj = sb->Unserialize(NULL, data); + try + { + if (obj) + obj->id = convertTo(res.Get(j, "id")); + } + catch (const ConvertException &) + { + Log(this) << "Unable to convert id for object #" << j << " of type " << sb->GetName(); + } + + if (obj) + { + /* The Unserialize operation is destructive so rebuild the data for UpdateCache. + * Also the old data may contain columns that we don't use, so we reserialize the + * object to know for sure our cache is consistent + */ + + Data data2; + obj->Serialize(data2); + obj->UpdateCache(data2); /* We know this is the most up to date copy */ + } + } + } +}; + +MODULE_INIT(DBSQL) diff --git a/modules/database/db_sql_live.cpp b/modules/database/db_sql_live.cpp new file mode 100644 index 0000000..742bac3 --- /dev/null +++ b/modules/database/db_sql_live.cpp @@ -0,0 +1,264 @@ +/* + * + * (C) 2012-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/sql.h" + +using namespace SQL; + +class DBMySQL : public Module, public Pipe +{ + private: + Anope::string prefix; + ServiceReference SQL; + time_t lastwarn; + bool ro; + bool init; + std::set updated_items; + + bool CheckSQL() + { + if (SQL) + { + if (Anope::ReadOnly && this->ro) + { + Anope::ReadOnly = this->ro = false; + Log() << "Found SQL again, going out of readonly mode..."; + } + + return true; + } + else + { + if (Anope::CurTime - Config->GetBlock("options")->Get("updatetimeout", "5m") > lastwarn) + { + Log() << "Unable to locate SQL reference, going to readonly..."; + Anope::ReadOnly = this->ro = true; + this->lastwarn = Anope::CurTime; + } + + return false; + } + } + + bool CheckInit() + { + return init && SQL; + } + + void RunQuery(const Query &query) + { + /* Can this be threaded? */ + this->RunQueryResult(query); + } + + Result RunQueryResult(const Query &query) + { + if (this->CheckSQL()) + { + Result res = SQL->RunQuery(query); + if (!res.GetError().empty()) + Log(LOG_DEBUG) << "SQL-live got error " << res.GetError() << " for " + res.finished_query; + else + Log(LOG_DEBUG) << "SQL-live got " << res.Rows() << " rows for " << res.finished_query; + return res; + } + throw SQL::Exception("No SQL!"); + } + + public: + DBMySQL(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, DATABASE | VENDOR), SQL("", "") + { + this->lastwarn = 0; + this->ro = false; + this->init = false; + + + if (ModuleManager::FindFirstOf(DATABASE) != this) + throw ModuleException("If db_sql_live is loaded it must be the first database module loaded."); + } + + void OnNotify() anope_override + { + if (!this->CheckInit()) + return; + + for (std::set::iterator it = this->updated_items.begin(), it_end = this->updated_items.end(); it != it_end; ++it) + { + Serializable *obj = *it; + + if (obj && this->SQL) + { + Data data; + obj->Serialize(data); + + if (obj->IsCached(data)) + continue; + + obj->UpdateCache(data); + + Serialize::Type *s_type = obj->GetSerializableType(); + if (!s_type) + continue; + + std::vector create = this->SQL->CreateTable(this->prefix + s_type->GetName(), data); + for (unsigned i = 0; i < create.size(); ++i) + this->RunQueryResult(create[i]); + + Result res = this->RunQueryResult(this->SQL->BuildInsert(this->prefix + s_type->GetName(), obj->id, data)); + if (res.GetID() && obj->id != res.GetID()) + { + /* In this case obj is new, so place it into the object map */ + obj->id = res.GetID(); + s_type->objects[obj->id] = obj; + } + } + } + + this->updated_items.clear(); + } + + EventReturn OnLoadDatabase() anope_override + { + init = true; + return EVENT_STOP; + } + + void OnShutdown() anope_override + { + init = false; + } + + void OnRestart() anope_override + { + init = false; + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *block = conf->GetModule(this); + this->SQL = ServiceReference("SQL::Provider", block->Get("engine")); + this->prefix = block->Get("prefix", "anope_db_"); + } + + void OnSerializableConstruct(Serializable *obj) anope_override + { + if (!this->CheckInit()) + return; + obj->UpdateTS(); + this->updated_items.insert(obj); + this->Notify(); + } + + void OnSerializableDestruct(Serializable *obj) anope_override + { + if (!this->CheckInit()) + return; + Serialize::Type *s_type = obj->GetSerializableType(); + if (s_type) + { + if (obj->id > 0) + this->RunQuery("DELETE FROM `" + this->prefix + s_type->GetName() + "` WHERE `id` = " + stringify(obj->id)); + s_type->objects.erase(obj->id); + } + this->updated_items.erase(obj); + } + + void OnSerializeCheck(Serialize::Type *obj) anope_override + { + if (!this->CheckInit() || obj->GetTimestamp() == Anope::CurTime) + return; + + Query query("SELECT * FROM `" + this->prefix + obj->GetName() + "` WHERE (`timestamp` >= " + this->SQL->FromUnixtime(obj->GetTimestamp()) + " OR `timestamp` IS NULL)"); + + obj->UpdateTimestamp(); + + Result res = this->RunQueryResult(query); + + bool clear_null = false; + for (int i = 0; i < res.Rows(); ++i) + { + const std::map &row = res.Row(i); + + unsigned int id; + try + { + id = convertTo(res.Get(i, "id")); + } + catch (const ConvertException &) + { + Log(LOG_DEBUG) << "Unable to convert id from " << obj->GetName(); + continue; + } + + if (res.Get(i, "timestamp").empty()) + { + clear_null = true; + std::map::iterator it = obj->objects.find(id); + if (it != obj->objects.end()) + delete it->second; // This also removes this object from the map + } + else + { + Data data; + + for (std::map::const_iterator it = row.begin(), it_end = row.end(); it != it_end; ++it) + data[it->first] << it->second; + + Serializable *s = NULL; + std::map::iterator it = obj->objects.find(id); + if (it != obj->objects.end()) + s = it->second; + + Serializable *new_s = obj->Unserialize(s, data); + if (new_s) + { + // If s == new_s then s->id == new_s->id + if (s != new_s) + { + new_s->id = id; + obj->objects[id] = new_s; + + /* The Unserialize operation is destructive so rebuild the data for UpdateCache. + * Also the old data may contain columns that we don't use, so we reserialize the + * object to know for sure our cache is consistent + */ + + Data data2; + new_s->Serialize(data2); + new_s->UpdateCache(data2); /* We know this is the most up to date copy */ + } + } + else + { + if (!s) + this->RunQuery("UPDATE `" + prefix + obj->GetName() + "` SET `timestamp` = " + this->SQL->FromUnixtime(obj->GetTimestamp()) + " WHERE `id` = " + stringify(id)); + else + delete s; + } + } + } + + if (clear_null) + { + query = "DELETE FROM `" + this->prefix + obj->GetName() + "` WHERE `timestamp` IS NULL"; + this->RunQuery(query); + } + } + + void OnSerializableUpdate(Serializable *obj) anope_override + { + if (!this->CheckInit() || obj->IsTSCached()) + return; + obj->UpdateTS(); + this->updated_items.insert(obj); + this->Notify(); + } +}; + +MODULE_INIT(DBMySQL) diff --git a/modules/encryption/enc_bcrypt.cpp b/modules/encryption/enc_bcrypt.cpp new file mode 100644 index 0000000..6a0f463 --- /dev/null +++ b/modules/encryption/enc_bcrypt.cpp @@ -0,0 +1,964 @@ +/* Module for providing bcrypt hashing + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * This program is free but copyrighted software; see the file COPYING for + * details. + * + * Most of the code in this file is taken from + * https://www.openwall.com/crypt/crypt_blowfish-1.3.tar.gz +*/ + +/* + * The crypt_blowfish homepage is: + * + * http://www.openwall.com/crypt/ + * + * This code comes from John the Ripper password cracker, with reentrant + * and crypt(3) interfaces added, but optimizations specific to password + * cracking removed. + * + * Written by Solar Designer in 1998-2014. + * No copyright is claimed, and the software is hereby placed in the public + * domain. In case this attempt to disclaim copyright and place the software + * in the public domain is deemed null and void, then the software is + * Copyright (c) 1998-2014 Solar Designer and it is hereby released to the + * general public under the following terms: + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted. + * + * There's ABSOLUTELY NO WARRANTY, express or implied. + * + * It is my intent that you should be able to use this on your system, + * as part of a software package, or anywhere else to improve security, + * ensure compatibility, or for any other purpose. I would appreciate + * it if you give credit where it is due and keep your modifications in + * the public domain as well, but I don't require that in order to let + * you place this code and any modifications you make under a license + * of your choice. + * + * This implementation is fully compatible with OpenBSD's bcrypt.c for prefix + * "$2b$", originally by Niels Provos , and it uses + * some of his ideas. The password hashing algorithm was designed by David + * Mazieres . For information on the level of + * compatibility for bcrypt hash prefixes other than "$2b$", please refer to + * the comments in BF_set_key() below and to the included crypt(3) man page. + * + * There's a paper on the algorithm that explains its design decisions: + * + * http://www.usenix.org/events/usenix99/provos.html + * + * Some of the tricks in BF_ROUND might be inspired by Eric Young's + * Blowfish library (I can't be sure if I would think of something if I + * hadn't seen his code). + */ + +#include + +#ifdef __i386__ +#define BF_SCALE 1 +#elif defined(__x86_64__) || defined(__alpha__) || defined(__hppa__) +#define BF_SCALE 1 +#else +#define BF_SCALE 0 +#endif + +typedef unsigned int BF_word; +typedef signed int BF_word_signed; + +/* Number of Blowfish rounds, this is also hardcoded into a few places */ +#define BF_N 16 + +typedef BF_word BF_key[BF_N + 2]; + +typedef struct { + BF_word S[4][0x100]; + BF_key P; +} BF_ctx; + +/* + * Magic IV for 64 Blowfish encryptions that we do at the end. + * The string is "OrpheanBeholderScryDoubt" on big-endian. + */ +static BF_word BF_magic_w[6] = { + 0x4F727068, 0x65616E42, 0x65686F6C, + 0x64657253, 0x63727944, 0x6F756274 +}; + +/* + * P-box and S-box tables initialized with digits of Pi. + */ +static BF_ctx BF_init_state = { + { + { + 0xd1310ba6, 0x98dfb5ac, 0x2ffd72db, 0xd01adfb7, + 0xb8e1afed, 0x6a267e96, 0xba7c9045, 0xf12c7f99, + 0x24a19947, 0xb3916cf7, 0x0801f2e2, 0x858efc16, + 0x636920d8, 0x71574e69, 0xa458fea3, 0xf4933d7e, + 0x0d95748f, 0x728eb658, 0x718bcd58, 0x82154aee, + 0x7b54a41d, 0xc25a59b5, 0x9c30d539, 0x2af26013, + 0xc5d1b023, 0x286085f0, 0xca417918, 0xb8db38ef, + 0x8e79dcb0, 0x603a180e, 0x6c9e0e8b, 0xb01e8a3e, + 0xd71577c1, 0xbd314b27, 0x78af2fda, 0x55605c60, + 0xe65525f3, 0xaa55ab94, 0x57489862, 0x63e81440, + 0x55ca396a, 0x2aab10b6, 0xb4cc5c34, 0x1141e8ce, + 0xa15486af, 0x7c72e993, 0xb3ee1411, 0x636fbc2a, + 0x2ba9c55d, 0x741831f6, 0xce5c3e16, 0x9b87931e, + 0xafd6ba33, 0x6c24cf5c, 0x7a325381, 0x28958677, + 0x3b8f4898, 0x6b4bb9af, 0xc4bfe81b, 0x66282193, + 0x61d809cc, 0xfb21a991, 0x487cac60, 0x5dec8032, + 0xef845d5d, 0xe98575b1, 0xdc262302, 0xeb651b88, + 0x23893e81, 0xd396acc5, 0x0f6d6ff3, 0x83f44239, + 0x2e0b4482, 0xa4842004, 0x69c8f04a, 0x9e1f9b5e, + 0x21c66842, 0xf6e96c9a, 0x670c9c61, 0xabd388f0, + 0x6a51a0d2, 0xd8542f68, 0x960fa728, 0xab5133a3, + 0x6eef0b6c, 0x137a3be4, 0xba3bf050, 0x7efb2a98, + 0xa1f1651d, 0x39af0176, 0x66ca593e, 0x82430e88, + 0x8cee8619, 0x456f9fb4, 0x7d84a5c3, 0x3b8b5ebe, + 0xe06f75d8, 0x85c12073, 0x401a449f, 0x56c16aa6, + 0x4ed3aa62, 0x363f7706, 0x1bfedf72, 0x429b023d, + 0x37d0d724, 0xd00a1248, 0xdb0fead3, 0x49f1c09b, + 0x075372c9, 0x80991b7b, 0x25d479d8, 0xf6e8def7, + 0xe3fe501a, 0xb6794c3b, 0x976ce0bd, 0x04c006ba, + 0xc1a94fb6, 0x409f60c4, 0x5e5c9ec2, 0x196a2463, + 0x68fb6faf, 0x3e6c53b5, 0x1339b2eb, 0x3b52ec6f, + 0x6dfc511f, 0x9b30952c, 0xcc814544, 0xaf5ebd09, + 0xbee3d004, 0xde334afd, 0x660f2807, 0x192e4bb3, + 0xc0cba857, 0x45c8740f, 0xd20b5f39, 0xb9d3fbdb, + 0x5579c0bd, 0x1a60320a, 0xd6a100c6, 0x402c7279, + 0x679f25fe, 0xfb1fa3cc, 0x8ea5e9f8, 0xdb3222f8, + 0x3c7516df, 0xfd616b15, 0x2f501ec8, 0xad0552ab, + 0x323db5fa, 0xfd238760, 0x53317b48, 0x3e00df82, + 0x9e5c57bb, 0xca6f8ca0, 0x1a87562e, 0xdf1769db, + 0xd542a8f6, 0x287effc3, 0xac6732c6, 0x8c4f5573, + 0x695b27b0, 0xbbca58c8, 0xe1ffa35d, 0xb8f011a0, + 0x10fa3d98, 0xfd2183b8, 0x4afcb56c, 0x2dd1d35b, + 0x9a53e479, 0xb6f84565, 0xd28e49bc, 0x4bfb9790, + 0xe1ddf2da, 0xa4cb7e33, 0x62fb1341, 0xcee4c6e8, + 0xef20cada, 0x36774c01, 0xd07e9efe, 0x2bf11fb4, + 0x95dbda4d, 0xae909198, 0xeaad8e71, 0x6b93d5a0, + 0xd08ed1d0, 0xafc725e0, 0x8e3c5b2f, 0x8e7594b7, + 0x8ff6e2fb, 0xf2122b64, 0x8888b812, 0x900df01c, + 0x4fad5ea0, 0x688fc31c, 0xd1cff191, 0xb3a8c1ad, + 0x2f2f2218, 0xbe0e1777, 0xea752dfe, 0x8b021fa1, + 0xe5a0cc0f, 0xb56f74e8, 0x18acf3d6, 0xce89e299, + 0xb4a84fe0, 0xfd13e0b7, 0x7cc43b81, 0xd2ada8d9, + 0x165fa266, 0x80957705, 0x93cc7314, 0x211a1477, + 0xe6ad2065, 0x77b5fa86, 0xc75442f5, 0xfb9d35cf, + 0xebcdaf0c, 0x7b3e89a0, 0xd6411bd3, 0xae1e7e49, + 0x00250e2d, 0x2071b35e, 0x226800bb, 0x57b8e0af, + 0x2464369b, 0xf009b91e, 0x5563911d, 0x59dfa6aa, + 0x78c14389, 0xd95a537f, 0x207d5ba2, 0x02e5b9c5, + 0x83260376, 0x6295cfa9, 0x11c81968, 0x4e734a41, + 0xb3472dca, 0x7b14a94a, 0x1b510052, 0x9a532915, + 0xd60f573f, 0xbc9bc6e4, 0x2b60a476, 0x81e67400, + 0x08ba6fb5, 0x571be91f, 0xf296ec6b, 0x2a0dd915, + 0xb6636521, 0xe7b9f9b6, 0xff34052e, 0xc5855664, + 0x53b02d5d, 0xa99f8fa1, 0x08ba4799, 0x6e85076a + }, { + 0x4b7a70e9, 0xb5b32944, 0xdb75092e, 0xc4192623, + 0xad6ea6b0, 0x49a7df7d, 0x9cee60b8, 0x8fedb266, + 0xecaa8c71, 0x699a17ff, 0x5664526c, 0xc2b19ee1, + 0x193602a5, 0x75094c29, 0xa0591340, 0xe4183a3e, + 0x3f54989a, 0x5b429d65, 0x6b8fe4d6, 0x99f73fd6, + 0xa1d29c07, 0xefe830f5, 0x4d2d38e6, 0xf0255dc1, + 0x4cdd2086, 0x8470eb26, 0x6382e9c6, 0x021ecc5e, + 0x09686b3f, 0x3ebaefc9, 0x3c971814, 0x6b6a70a1, + 0x687f3584, 0x52a0e286, 0xb79c5305, 0xaa500737, + 0x3e07841c, 0x7fdeae5c, 0x8e7d44ec, 0x5716f2b8, + 0xb03ada37, 0xf0500c0d, 0xf01c1f04, 0x0200b3ff, + 0xae0cf51a, 0x3cb574b2, 0x25837a58, 0xdc0921bd, + 0xd19113f9, 0x7ca92ff6, 0x94324773, 0x22f54701, + 0x3ae5e581, 0x37c2dadc, 0xc8b57634, 0x9af3dda7, + 0xa9446146, 0x0fd0030e, 0xecc8c73e, 0xa4751e41, + 0xe238cd99, 0x3bea0e2f, 0x3280bba1, 0x183eb331, + 0x4e548b38, 0x4f6db908, 0x6f420d03, 0xf60a04bf, + 0x2cb81290, 0x24977c79, 0x5679b072, 0xbcaf89af, + 0xde9a771f, 0xd9930810, 0xb38bae12, 0xdccf3f2e, + 0x5512721f, 0x2e6b7124, 0x501adde6, 0x9f84cd87, + 0x7a584718, 0x7408da17, 0xbc9f9abc, 0xe94b7d8c, + 0xec7aec3a, 0xdb851dfa, 0x63094366, 0xc464c3d2, + 0xef1c1847, 0x3215d908, 0xdd433b37, 0x24c2ba16, + 0x12a14d43, 0x2a65c451, 0x50940002, 0x133ae4dd, + 0x71dff89e, 0x10314e55, 0x81ac77d6, 0x5f11199b, + 0x043556f1, 0xd7a3c76b, 0x3c11183b, 0x5924a509, + 0xf28fe6ed, 0x97f1fbfa, 0x9ebabf2c, 0x1e153c6e, + 0x86e34570, 0xeae96fb1, 0x860e5e0a, 0x5a3e2ab3, + 0x771fe71c, 0x4e3d06fa, 0x2965dcb9, 0x99e71d0f, + 0x803e89d6, 0x5266c825, 0x2e4cc978, 0x9c10b36a, + 0xc6150eba, 0x94e2ea78, 0xa5fc3c53, 0x1e0a2df4, + 0xf2f74ea7, 0x361d2b3d, 0x1939260f, 0x19c27960, + 0x5223a708, 0xf71312b6, 0xebadfe6e, 0xeac31f66, + 0xe3bc4595, 0xa67bc883, 0xb17f37d1, 0x018cff28, + 0xc332ddef, 0xbe6c5aa5, 0x65582185, 0x68ab9802, + 0xeecea50f, 0xdb2f953b, 0x2aef7dad, 0x5b6e2f84, + 0x1521b628, 0x29076170, 0xecdd4775, 0x619f1510, + 0x13cca830, 0xeb61bd96, 0x0334fe1e, 0xaa0363cf, + 0xb5735c90, 0x4c70a239, 0xd59e9e0b, 0xcbaade14, + 0xeecc86bc, 0x60622ca7, 0x9cab5cab, 0xb2f3846e, + 0x648b1eaf, 0x19bdf0ca, 0xa02369b9, 0x655abb50, + 0x40685a32, 0x3c2ab4b3, 0x319ee9d5, 0xc021b8f7, + 0x9b540b19, 0x875fa099, 0x95f7997e, 0x623d7da8, + 0xf837889a, 0x97e32d77, 0x11ed935f, 0x16681281, + 0x0e358829, 0xc7e61fd6, 0x96dedfa1, 0x7858ba99, + 0x57f584a5, 0x1b227263, 0x9b83c3ff, 0x1ac24696, + 0xcdb30aeb, 0x532e3054, 0x8fd948e4, 0x6dbc3128, + 0x58ebf2ef, 0x34c6ffea, 0xfe28ed61, 0xee7c3c73, + 0x5d4a14d9, 0xe864b7e3, 0x42105d14, 0x203e13e0, + 0x45eee2b6, 0xa3aaabea, 0xdb6c4f15, 0xfacb4fd0, + 0xc742f442, 0xef6abbb5, 0x654f3b1d, 0x41cd2105, + 0xd81e799e, 0x86854dc7, 0xe44b476a, 0x3d816250, + 0xcf62a1f2, 0x5b8d2646, 0xfc8883a0, 0xc1c7b6a3, + 0x7f1524c3, 0x69cb7492, 0x47848a0b, 0x5692b285, + 0x095bbf00, 0xad19489d, 0x1462b174, 0x23820e00, + 0x58428d2a, 0x0c55f5ea, 0x1dadf43e, 0x233f7061, + 0x3372f092, 0x8d937e41, 0xd65fecf1, 0x6c223bdb, + 0x7cde3759, 0xcbee7460, 0x4085f2a7, 0xce77326e, + 0xa6078084, 0x19f8509e, 0xe8efd855, 0x61d99735, + 0xa969a7aa, 0xc50c06c2, 0x5a04abfc, 0x800bcadc, + 0x9e447a2e, 0xc3453484, 0xfdd56705, 0x0e1e9ec9, + 0xdb73dbd3, 0x105588cd, 0x675fda79, 0xe3674340, + 0xc5c43465, 0x713e38d8, 0x3d28f89e, 0xf16dff20, + 0x153e21e7, 0x8fb03d4a, 0xe6e39f2b, 0xdb83adf7 + }, { + 0xe93d5a68, 0x948140f7, 0xf64c261c, 0x94692934, + 0x411520f7, 0x7602d4f7, 0xbcf46b2e, 0xd4a20068, + 0xd4082471, 0x3320f46a, 0x43b7d4b7, 0x500061af, + 0x1e39f62e, 0x97244546, 0x14214f74, 0xbf8b8840, + 0x4d95fc1d, 0x96b591af, 0x70f4ddd3, 0x66a02f45, + 0xbfbc09ec, 0x03bd9785, 0x7fac6dd0, 0x31cb8504, + 0x96eb27b3, 0x55fd3941, 0xda2547e6, 0xabca0a9a, + 0x28507825, 0x530429f4, 0x0a2c86da, 0xe9b66dfb, + 0x68dc1462, 0xd7486900, 0x680ec0a4, 0x27a18dee, + 0x4f3ffea2, 0xe887ad8c, 0xb58ce006, 0x7af4d6b6, + 0xaace1e7c, 0xd3375fec, 0xce78a399, 0x406b2a42, + 0x20fe9e35, 0xd9f385b9, 0xee39d7ab, 0x3b124e8b, + 0x1dc9faf7, 0x4b6d1856, 0x26a36631, 0xeae397b2, + 0x3a6efa74, 0xdd5b4332, 0x6841e7f7, 0xca7820fb, + 0xfb0af54e, 0xd8feb397, 0x454056ac, 0xba489527, + 0x55533a3a, 0x20838d87, 0xfe6ba9b7, 0xd096954b, + 0x55a867bc, 0xa1159a58, 0xcca92963, 0x99e1db33, + 0xa62a4a56, 0x3f3125f9, 0x5ef47e1c, 0x9029317c, + 0xfdf8e802, 0x04272f70, 0x80bb155c, 0x05282ce3, + 0x95c11548, 0xe4c66d22, 0x48c1133f, 0xc70f86dc, + 0x07f9c9ee, 0x41041f0f, 0x404779a4, 0x5d886e17, + 0x325f51eb, 0xd59bc0d1, 0xf2bcc18f, 0x41113564, + 0x257b7834, 0x602a9c60, 0xdff8e8a3, 0x1f636c1b, + 0x0e12b4c2, 0x02e1329e, 0xaf664fd1, 0xcad18115, + 0x6b2395e0, 0x333e92e1, 0x3b240b62, 0xeebeb922, + 0x85b2a20e, 0xe6ba0d99, 0xde720c8c, 0x2da2f728, + 0xd0127845, 0x95b794fd, 0x647d0862, 0xe7ccf5f0, + 0x5449a36f, 0x877d48fa, 0xc39dfd27, 0xf33e8d1e, + 0x0a476341, 0x992eff74, 0x3a6f6eab, 0xf4f8fd37, + 0xa812dc60, 0xa1ebddf8, 0x991be14c, 0xdb6e6b0d, + 0xc67b5510, 0x6d672c37, 0x2765d43b, 0xdcd0e804, + 0xf1290dc7, 0xcc00ffa3, 0xb5390f92, 0x690fed0b, + 0x667b9ffb, 0xcedb7d9c, 0xa091cf0b, 0xd9155ea3, + 0xbb132f88, 0x515bad24, 0x7b9479bf, 0x763bd6eb, + 0x37392eb3, 0xcc115979, 0x8026e297, 0xf42e312d, + 0x6842ada7, 0xc66a2b3b, 0x12754ccc, 0x782ef11c, + 0x6a124237, 0xb79251e7, 0x06a1bbe6, 0x4bfb6350, + 0x1a6b1018, 0x11caedfa, 0x3d25bdd8, 0xe2e1c3c9, + 0x44421659, 0x0a121386, 0xd90cec6e, 0xd5abea2a, + 0x64af674e, 0xda86a85f, 0xbebfe988, 0x64e4c3fe, + 0x9dbc8057, 0xf0f7c086, 0x60787bf8, 0x6003604d, + 0xd1fd8346, 0xf6381fb0, 0x7745ae04, 0xd736fccc, + 0x83426b33, 0xf01eab71, 0xb0804187, 0x3c005e5f, + 0x77a057be, 0xbde8ae24, 0x55464299, 0xbf582e61, + 0x4e58f48f, 0xf2ddfda2, 0xf474ef38, 0x8789bdc2, + 0x5366f9c3, 0xc8b38e74, 0xb475f255, 0x46fcd9b9, + 0x7aeb2661, 0x8b1ddf84, 0x846a0e79, 0x915f95e2, + 0x466e598e, 0x20b45770, 0x8cd55591, 0xc902de4c, + 0xb90bace1, 0xbb8205d0, 0x11a86248, 0x7574a99e, + 0xb77f19b6, 0xe0a9dc09, 0x662d09a1, 0xc4324633, + 0xe85a1f02, 0x09f0be8c, 0x4a99a025, 0x1d6efe10, + 0x1ab93d1d, 0x0ba5a4df, 0xa186f20f, 0x2868f169, + 0xdcb7da83, 0x573906fe, 0xa1e2ce9b, 0x4fcd7f52, + 0x50115e01, 0xa70683fa, 0xa002b5c4, 0x0de6d027, + 0x9af88c27, 0x773f8641, 0xc3604c06, 0x61a806b5, + 0xf0177a28, 0xc0f586e0, 0x006058aa, 0x30dc7d62, + 0x11e69ed7, 0x2338ea63, 0x53c2dd94, 0xc2c21634, + 0xbbcbee56, 0x90bcb6de, 0xebfc7da1, 0xce591d76, + 0x6f05e409, 0x4b7c0188, 0x39720a3d, 0x7c927c24, + 0x86e3725f, 0x724d9db9, 0x1ac15bb4, 0xd39eb8fc, + 0xed545578, 0x08fca5b5, 0xd83d7cd3, 0x4dad0fc4, + 0x1e50ef5e, 0xb161e6f8, 0xa28514d9, 0x6c51133c, + 0x6fd5c7e7, 0x56e14ec4, 0x362abfce, 0xddc6c837, + 0xd79a3234, 0x92638212, 0x670efa8e, 0x406000e0 + }, { + 0x3a39ce37, 0xd3faf5cf, 0xabc27737, 0x5ac52d1b, + 0x5cb0679e, 0x4fa33742, 0xd3822740, 0x99bc9bbe, + 0xd5118e9d, 0xbf0f7315, 0xd62d1c7e, 0xc700c47b, + 0xb78c1b6b, 0x21a19045, 0xb26eb1be, 0x6a366eb4, + 0x5748ab2f, 0xbc946e79, 0xc6a376d2, 0x6549c2c8, + 0x530ff8ee, 0x468dde7d, 0xd5730a1d, 0x4cd04dc6, + 0x2939bbdb, 0xa9ba4650, 0xac9526e8, 0xbe5ee304, + 0xa1fad5f0, 0x6a2d519a, 0x63ef8ce2, 0x9a86ee22, + 0xc089c2b8, 0x43242ef6, 0xa51e03aa, 0x9cf2d0a4, + 0x83c061ba, 0x9be96a4d, 0x8fe51550, 0xba645bd6, + 0x2826a2f9, 0xa73a3ae1, 0x4ba99586, 0xef5562e9, + 0xc72fefd3, 0xf752f7da, 0x3f046f69, 0x77fa0a59, + 0x80e4a915, 0x87b08601, 0x9b09e6ad, 0x3b3ee593, + 0xe990fd5a, 0x9e34d797, 0x2cf0b7d9, 0x022b8b51, + 0x96d5ac3a, 0x017da67d, 0xd1cf3ed6, 0x7c7d2d28, + 0x1f9f25cf, 0xadf2b89b, 0x5ad6b472, 0x5a88f54c, + 0xe029ac71, 0xe019a5e6, 0x47b0acfd, 0xed93fa9b, + 0xe8d3c48d, 0x283b57cc, 0xf8d56629, 0x79132e28, + 0x785f0191, 0xed756055, 0xf7960e44, 0xe3d35e8c, + 0x15056dd4, 0x88f46dba, 0x03a16125, 0x0564f0bd, + 0xc3eb9e15, 0x3c9057a2, 0x97271aec, 0xa93a072a, + 0x1b3f6d9b, 0x1e6321f5, 0xf59c66fb, 0x26dcf319, + 0x7533d928, 0xb155fdf5, 0x03563482, 0x8aba3cbb, + 0x28517711, 0xc20ad9f8, 0xabcc5167, 0xccad925f, + 0x4de81751, 0x3830dc8e, 0x379d5862, 0x9320f991, + 0xea7a90c2, 0xfb3e7bce, 0x5121ce64, 0x774fbe32, + 0xa8b6e37e, 0xc3293d46, 0x48de5369, 0x6413e680, + 0xa2ae0810, 0xdd6db224, 0x69852dfd, 0x09072166, + 0xb39a460a, 0x6445c0dd, 0x586cdecf, 0x1c20c8ae, + 0x5bbef7dd, 0x1b588d40, 0xccd2017f, 0x6bb4e3bb, + 0xdda26a7e, 0x3a59ff45, 0x3e350a44, 0xbcb4cdd5, + 0x72eacea8, 0xfa6484bb, 0x8d6612ae, 0xbf3c6f47, + 0xd29be463, 0x542f5d9e, 0xaec2771b, 0xf64e6370, + 0x740e0d8d, 0xe75b1357, 0xf8721671, 0xaf537d5d, + 0x4040cb08, 0x4eb4e2cc, 0x34d2466a, 0x0115af84, + 0xe1b00428, 0x95983a1d, 0x06b89fb4, 0xce6ea048, + 0x6f3f3b82, 0x3520ab82, 0x011a1d4b, 0x277227f8, + 0x611560b1, 0xe7933fdc, 0xbb3a792b, 0x344525bd, + 0xa08839e1, 0x51ce794b, 0x2f32c9b7, 0xa01fbac9, + 0xe01cc87e, 0xbcc7d1f6, 0xcf0111c3, 0xa1e8aac7, + 0x1a908749, 0xd44fbd9a, 0xd0dadecb, 0xd50ada38, + 0x0339c32a, 0xc6913667, 0x8df9317c, 0xe0b12b4f, + 0xf79e59b7, 0x43f5bb3a, 0xf2d519ff, 0x27d9459c, + 0xbf97222c, 0x15e6fc2a, 0x0f91fc71, 0x9b941525, + 0xfae59361, 0xceb69ceb, 0xc2a86459, 0x12baa8d1, + 0xb6c1075e, 0xe3056a0c, 0x10d25065, 0xcb03a442, + 0xe0ec6e0e, 0x1698db3b, 0x4c98a0be, 0x3278e964, + 0x9f1f9532, 0xe0d392df, 0xd3a0342b, 0x8971f21e, + 0x1b0a7441, 0x4ba3348c, 0xc5be7120, 0xc37632d8, + 0xdf359f8d, 0x9b992f2e, 0xe60b6f47, 0x0fe3f11d, + 0xe54cda54, 0x1edad891, 0xce6279cf, 0xcd3e7e6f, + 0x1618b166, 0xfd2c1d05, 0x848fd2c5, 0xf6fb2299, + 0xf523f357, 0xa6327623, 0x93a83531, 0x56cccd02, + 0xacf08162, 0x5a75ebb5, 0x6e163697, 0x88d273cc, + 0xde966292, 0x81b949d0, 0x4c50901b, 0x71c65614, + 0xe6c6c7bd, 0x327a140a, 0x45e1d006, 0xc3f27b9a, + 0xc9aa53fd, 0x62a80f00, 0xbb25bfe2, 0x35bdd2f6, + 0x71126905, 0xb2040222, 0xb6cbcf7c, 0xcd769c2b, + 0x53113ec0, 0x1640e3d3, 0x38abbd60, 0x2547adf0, + 0xba38209c, 0xf746ce76, 0x77afa1c5, 0x20756060, + 0x85cbfe4e, 0x8ae88dd8, 0x7aaaf9b0, 0x4cf9aa7e, + 0x1948c25c, 0x02fb8a8c, 0x01c36ae4, 0xd6ebe1f9, + 0x90d4f869, 0xa65cdea0, 0x3f09252d, 0xc208e69f, + 0xb74e6132, 0xce77e25b, 0x578fdfe3, 0x3ac372e6 + } + }, { + 0x243f6a88, 0x85a308d3, 0x13198a2e, 0x03707344, + 0xa4093822, 0x299f31d0, 0x082efa98, 0xec4e6c89, + 0x452821e6, 0x38d01377, 0xbe5466cf, 0x34e90c6c, + 0xc0ac29b7, 0xc97c50dd, 0x3f84d5b5, 0xb5470917, + 0x9216d5d9, 0x8979fb1b + } +}; + +static unsigned char BF_itoa64[64 + 1] = + "./ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789"; + +static unsigned char BF_atoi64[0x60] = { + 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 0, 1, + 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 64, 64, 64, 64, 64, + 64, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, + 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 64, 64, 64, 64, 64, + 64, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, + 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 64, 64, 64, 64, 64 +}; + +#define BF_safe_atoi64(dst, src) \ +{ \ + tmp = (unsigned char)(src); \ + if ((unsigned int)(tmp -= 0x20) >= 0x60) return -1; \ + tmp = BF_atoi64[tmp]; \ + if (tmp > 63) return -1; \ + (dst) = tmp; \ +} + +static int BF_decode(BF_word *dst, const char *src, int size) +{ + unsigned char *dptr = (unsigned char *)dst; + unsigned char *end = dptr + size; + const unsigned char *sptr = (const unsigned char *)src; + unsigned int tmp, c1, c2, c3, c4; + + do { + BF_safe_atoi64(c1, *sptr++); + BF_safe_atoi64(c2, *sptr++); + *dptr++ = (c1 << 2) | ((c2 & 0x30) >> 4); + if (dptr >= end) break; + + BF_safe_atoi64(c3, *sptr++); + *dptr++ = ((c2 & 0x0F) << 4) | ((c3 & 0x3C) >> 2); + if (dptr >= end) break; + + BF_safe_atoi64(c4, *sptr++); + *dptr++ = ((c3 & 0x03) << 6) | c4; + } while (dptr < end); + + return 0; +} + +static void BF_encode(char *dst, const BF_word *src, int size) +{ + const unsigned char *sptr = (const unsigned char *)src; + const unsigned char *end = sptr + size; + unsigned char *dptr = (unsigned char *)dst; + unsigned int c1, c2; + + do { + c1 = *sptr++; + *dptr++ = BF_itoa64[c1 >> 2]; + c1 = (c1 & 0x03) << 4; + if (sptr >= end) { + *dptr++ = BF_itoa64[c1]; + break; + } + + c2 = *sptr++; + c1 |= c2 >> 4; + *dptr++ = BF_itoa64[c1]; + c1 = (c2 & 0x0f) << 2; + if (sptr >= end) { + *dptr++ = BF_itoa64[c1]; + break; + } + + c2 = *sptr++; + c1 |= c2 >> 6; + *dptr++ = BF_itoa64[c1]; + *dptr++ = BF_itoa64[c2 & 0x3f]; + } while (sptr < end); +} + +static void BF_swap(BF_word *x, int count) +{ + static int endianness_check = 1; + char *is_little_endian = (char *)&endianness_check; + BF_word tmp; + + if (*is_little_endian) + do { + tmp = *x; + tmp = (tmp << 16) | (tmp >> 16); + *x++ = ((tmp & 0x00FF00FF) << 8) | ((tmp >> 8) & 0x00FF00FF); + } while (--count); +} + +#if BF_SCALE +/* Architectures which can shift addresses left by 2 bits with no extra cost */ +#define BF_ROUND(L, R, N) \ + tmp1 = L & 0xFF; \ + tmp2 = L >> 8; \ + tmp2 &= 0xFF; \ + tmp3 = L >> 16; \ + tmp3 &= 0xFF; \ + tmp4 = L >> 24; \ + tmp1 = data.ctx.S[3][tmp1]; \ + tmp2 = data.ctx.S[2][tmp2]; \ + tmp3 = data.ctx.S[1][tmp3]; \ + tmp3 += data.ctx.S[0][tmp4]; \ + tmp3 ^= tmp2; \ + R ^= data.ctx.P[N + 1]; \ + tmp3 += tmp1; \ + R ^= tmp3; +#else +/* Architectures with no complicated addressing modes supported */ +#define BF_INDEX(S, i) \ + (*((BF_word *)(((unsigned char *)S) + (i)))) +#define BF_ROUND(L, R, N) \ + tmp1 = L & 0xFF; \ + tmp1 <<= 2; \ + tmp2 = L >> 6; \ + tmp2 &= 0x3FC; \ + tmp3 = L >> 14; \ + tmp3 &= 0x3FC; \ + tmp4 = L >> 22; \ + tmp4 &= 0x3FC; \ + tmp1 = BF_INDEX(data.ctx.S[3], tmp1); \ + tmp2 = BF_INDEX(data.ctx.S[2], tmp2); \ + tmp3 = BF_INDEX(data.ctx.S[1], tmp3); \ + tmp3 += BF_INDEX(data.ctx.S[0], tmp4); \ + tmp3 ^= tmp2; \ + R ^= data.ctx.P[N + 1]; \ + tmp3 += tmp1; \ + R ^= tmp3; +#endif + +/* + * Encrypt one block, BF_N is hardcoded here. + */ +#define BF_ENCRYPT \ + L ^= data.ctx.P[0]; \ + BF_ROUND(L, R, 0); \ + BF_ROUND(R, L, 1); \ + BF_ROUND(L, R, 2); \ + BF_ROUND(R, L, 3); \ + BF_ROUND(L, R, 4); \ + BF_ROUND(R, L, 5); \ + BF_ROUND(L, R, 6); \ + BF_ROUND(R, L, 7); \ + BF_ROUND(L, R, 8); \ + BF_ROUND(R, L, 9); \ + BF_ROUND(L, R, 10); \ + BF_ROUND(R, L, 11); \ + BF_ROUND(L, R, 12); \ + BF_ROUND(R, L, 13); \ + BF_ROUND(L, R, 14); \ + BF_ROUND(R, L, 15); \ + tmp4 = R; \ + R = L; \ + L = tmp4 ^ data.ctx.P[BF_N + 1]; + +#define BF_body() \ + L = R = 0; \ + ptr = data.ctx.P; \ + do { \ + ptr += 2; \ + BF_ENCRYPT; \ + *(ptr - 2) = L; \ + *(ptr - 1) = R; \ + } while (ptr < &data.ctx.P[BF_N + 2]); \ +\ + ptr = data.ctx.S[0]; \ + do { \ + ptr += 2; \ + BF_ENCRYPT; \ + *(ptr - 2) = L; \ + *(ptr - 1) = R; \ + } while (ptr < &data.ctx.S[3][0xFF]); + +static void BF_set_key(const char *key, BF_key expanded, BF_key initial, + unsigned char flags) +{ + const char *ptr = key; + unsigned int bug, i, j; + BF_word safety, sign, diff, tmp[2]; + +/* + * There was a sign extension bug in older revisions of this function. While + * we would have liked to simply fix the bug and move on, we have to provide + * a backwards compatibility feature (essentially the bug) for some systems and + * a safety measure for some others. The latter is needed because for certain + * multiple inputs to the buggy algorithm there exist easily found inputs to + * the correct algorithm that produce the same hash. Thus, we optionally + * deviate from the correct algorithm just enough to avoid such collisions. + * While the bug itself affected the majority of passwords containing + * characters with the 8th bit set (although only a percentage of those in a + * collision-producing way), the anti-collision safety measure affects + * only a subset of passwords containing the '\xff' character (not even all of + * those passwords, just some of them). This character is not found in valid + * UTF-8 sequences and is rarely used in popular 8-bit character encodings. + * Thus, the safety measure is unlikely to cause much annoyance, and is a + * reasonable tradeoff to use when authenticating against existing hashes that + * are not reliably known to have been computed with the correct algorithm. + * + * We use an approach that tries to minimize side-channel leaks of password + * information - that is, we mostly use fixed-cost bitwise operations instead + * of branches or table lookups. (One conditional branch based on password + * length remains. It is not part of the bug aftermath, though, and is + * difficult and possibly unreasonable to avoid given the use of C strings by + * the caller, which results in similar timing leaks anyway.) + * + * For actual implementation, we set an array index in the variable "bug" + * (0 means no bug, 1 means sign extension bug emulation) and a flag in the + * variable "safety" (bit 16 is set when the safety measure is requested). + * Valid combinations of settings are: + * + * Prefix "$2a$": bug = 0, safety = 0x10000 + * Prefix "$2b$": bug = 0, safety = 0 + * Prefix "$2x$": bug = 1, safety = 0 + * Prefix "$2y$": bug = 0, safety = 0 + */ + bug = (unsigned int)flags & 1; + safety = ((BF_word)flags & 2) << 15; + + sign = diff = 0; + + for (i = 0; i < BF_N + 2; i++) { + tmp[0] = tmp[1] = 0; + for (j = 0; j < 4; j++) { + tmp[0] <<= 8; + tmp[0] |= (unsigned char)*ptr; /* correct */ + tmp[1] <<= 8; + tmp[1] |= (BF_word_signed)(signed char)*ptr; /* bug */ +/* + * Sign extension in the first char has no effect - nothing to overwrite yet, + * and those extra 24 bits will be fully shifted out of the 32-bit word. For + * chars 2, 3, 4 in each four-char block, we set bit 7 of "sign" if sign + * extension in tmp[1] occurs. Once this flag is set, it remains set. + */ + if (j) + sign |= tmp[1] & 0x80; + if (!*ptr) + ptr = key; + else + ptr++; + } + diff |= tmp[0] ^ tmp[1]; /* Non-zero on any differences */ + + expanded[i] = tmp[bug]; + initial[i] = BF_init_state.P[i] ^ tmp[bug]; + } + +/* + * At this point, "diff" is zero iff the correct and buggy algorithms produced + * exactly the same result. If so and if "sign" is non-zero, which indicates + * that there was a non-benign sign extension, this means that we have a + * collision between the correctly computed hash for this password and a set of + * passwords that could be supplied to the buggy algorithm. Our safety measure + * is meant to protect from such many-buggy to one-correct collisions, by + * deviating from the correct algorithm in such cases. Let's check for this. + */ + diff |= diff >> 16; /* still zero iff exact match */ + diff &= 0xffff; /* ditto */ + diff += 0xffff; /* bit 16 set iff "diff" was non-zero (on non-match) */ + sign <<= 9; /* move the non-benign sign extension flag to bit 16 */ + sign &= ~diff & safety; /* action needed? */ + +/* + * If we have determined that we need to deviate from the correct algorithm, + * flip bit 16 in initial expanded key. (The choice of 16 is arbitrary, but + * let's stick to it now. It came out of the approach we used above, and it's + * not any worse than any other choice we could make.) + * + * It is crucial that we don't do the same to the expanded key used in the main + * Eksblowfish loop. By doing it to only one of these two, we deviate from a + * state that could be directly specified by a password to the buggy algorithm + * (and to the fully correct one as well, but that's a side-effect). + */ + initial[0] ^= sign; +} + +static const unsigned char flags_by_subtype[26] = + {2, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 4, 0}; + +static char *BF_crypt(const char *key, const char *setting, + char *output, int size, + BF_word min) +{ + struct { + BF_ctx ctx; + BF_key expanded_key; + union { + BF_word salt[4]; + BF_word output[6]; + } binary; + } data; + BF_word L, R; + BF_word tmp1, tmp2, tmp3, tmp4; + BF_word *ptr; + BF_word count; + int i; + + if (size < 7 + 22 + 31 + 1) { + return NULL; + } + + if (setting[0] != '$' || + setting[1] != '2' || + setting[2] < 'a' || setting[2] > 'z' || + !flags_by_subtype[(unsigned int)(unsigned char)setting[2] - 'a'] || + setting[3] != '$' || + setting[4] < '0' || setting[4] > '3' || + setting[5] < '0' || setting[5] > '9' || + (setting[4] == '3' && setting[5] > '1') || + setting[6] != '$') { + return NULL; + } + + count = (BF_word)1 << ((setting[4] - '0') * 10 + (setting[5] - '0')); + if (count < min || BF_decode(data.binary.salt, &setting[7], 16)) { + return NULL; + } + BF_swap(data.binary.salt, 4); + + BF_set_key(key, data.expanded_key, data.ctx.P, + flags_by_subtype[(unsigned int)(unsigned char)setting[2] - 'a']); + + memcpy(data.ctx.S, BF_init_state.S, sizeof(data.ctx.S)); + + L = R = 0; + for (i = 0; i < BF_N + 2; i += 2) { + L ^= data.binary.salt[i & 2]; + R ^= data.binary.salt[(i & 2) + 1]; + BF_ENCRYPT; + data.ctx.P[i] = L; + data.ctx.P[i + 1] = R; + } + + ptr = data.ctx.S[0]; + do { + ptr += 4; + L ^= data.binary.salt[(BF_N + 2) & 3]; + R ^= data.binary.salt[(BF_N + 3) & 3]; + BF_ENCRYPT; + *(ptr - 4) = L; + *(ptr - 3) = R; + + L ^= data.binary.salt[(BF_N + 4) & 3]; + R ^= data.binary.salt[(BF_N + 5) & 3]; + BF_ENCRYPT; + *(ptr - 2) = L; + *(ptr - 1) = R; + } while (ptr < &data.ctx.S[3][0xFF]); + + do { + int done; + + for (i = 0; i < BF_N + 2; i += 2) { + data.ctx.P[i] ^= data.expanded_key[i]; + data.ctx.P[i + 1] ^= data.expanded_key[i + 1]; + } + + done = 0; + do { + BF_body(); + if (done) + break; + done = 1; + + tmp1 = data.binary.salt[0]; + tmp2 = data.binary.salt[1]; + tmp3 = data.binary.salt[2]; + tmp4 = data.binary.salt[3]; + for (i = 0; i < BF_N; i += 4) { + data.ctx.P[i] ^= tmp1; + data.ctx.P[i + 1] ^= tmp2; + data.ctx.P[i + 2] ^= tmp3; + data.ctx.P[i + 3] ^= tmp4; + } + data.ctx.P[16] ^= tmp1; + data.ctx.P[17] ^= tmp2; + } while (1); + } while (--count); + + for (i = 0; i < 6; i += 2) { + L = BF_magic_w[i]; + R = BF_magic_w[i + 1]; + + count = 64; + do { + BF_ENCRYPT; + } while (--count); + + data.binary.output[i] = L; + data.binary.output[i + 1] = R; + } + + memcpy(output, setting, 7 + 22 - 1); + output[7 + 22 - 1] = BF_itoa64[(int) + BF_atoi64[(int)setting[7 + 22 - 1] - 0x20] & 0x30]; + +/* This has to be bug-compatible with the original implementation, so + * only encode 23 of the 24 bytes. :-) */ + BF_swap(data.binary.output, 6); + BF_encode(&output[7 + 22], data.binary.output, 23); + output[7 + 22 + 31] = '\0'; + + return output; +} + +int _crypt_output_magic(const char *setting, char *output, int size) +{ + if (size < 3) + return -1; + + output[0] = '*'; + output[1] = '0'; + output[2] = '\0'; + + if (setting[0] == '*' && setting[1] == '0') + output[1] = '1'; + + return 0; +} + +/* + * Please preserve the runtime self-test. It serves two purposes at once: + * + * 1. We really can't afford the risk of producing incompatible hashes e.g. + * when there's something like gcc bug 26587 again, whereas an application or + * library integrating this code might not also integrate our external tests or + * it might not run them after every build. Even if it does, the miscompile + * might only occur on the production build, but not on a testing build (such + * as because of different optimization settings). It is painful to recover + * from incorrectly-computed hashes - merely fixing whatever broke is not + * enough. Thus, a proactive measure like this self-test is needed. + * + * 2. We don't want to leave sensitive data from our actual password hash + * computation on the stack or in registers. Previous revisions of the code + * would do explicit cleanups, but simply running the self-test after hash + * computation is more reliable. + * + * The performance cost of this quick self-test is around 0.6% at the "$2a$08" + * setting. + */ +char *_crypt_blowfish_rn(const char *key, const char *setting, + char *output, int size) +{ + _crypt_output_magic(setting, output, size); + return BF_crypt(key, setting, output, size, 16); +} + +char *_crypt_gensalt_blowfish_rn(const char *prefix, unsigned long count, + const char *input, int size, char *output, int output_size) +{ + if (size < 16 || output_size < 7 + 22 + 1 || + (count && (count < 4 || count > 31)) || + prefix[0] != '$' || prefix[1] != '2' || + (prefix[2] != 'a' && prefix[2] != 'b' && prefix[2] != 'y')) { + if (output_size > 0) output[0] = '\0'; + return NULL; + } + + if (!count) count = 5; + + output[0] = '$'; + output[1] = '2'; + output[2] = prefix[2]; + output[3] = '$'; + output[4] = '0' + count / 10; + output[5] = '0' + count % 10; + output[6] = '$'; + + BF_encode(&output[7], (const BF_word *)input, 16); + output[7 + 22] = '\0'; + + return output; +} + +// Start Anope-specific code + +#include "module.h" +#include "modules/encryption.h" + +class EBCRYPT : public Module +{ + unsigned int rounds; + + Anope::string Salt() + { + char entropy[16]; + for (unsigned int i = 0; i < sizeof(entropy); i++) + entropy[i] = static_cast(rand() % 0xFF); + + char salt[32]; + if (!_crypt_gensalt_blowfish_rn("$2a$", rounds, entropy, sizeof(entropy), salt, sizeof(salt))) + return ""; + return salt; + } + + Anope::string Generate(const Anope::string& data, const Anope::string& salt) + { + char hash[64]; + _crypt_blowfish_rn(data.c_str(), salt.c_str(), hash, sizeof(hash)); + return hash; + } + + bool Compare(const Anope::string& string, const Anope::string& hash) + { + Anope::string ret = Generate(string, hash); + if (ret.empty()) + return false; + + return (ret == hash); + } + + public: + EBCRYPT(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, ENCRYPTION | VENDOR), + rounds(10) + { + // Test a pre-calculated hash + bool test = Compare("Test!", "$2a$10$x9AQFAQScY0v9KF2suqkEOepsHFrG.CXHbIXI.1F28SfSUb56A/7K"); + + Anope::string salt; + Anope::string hash; + // Make sure it's working + if (!test || (salt = Salt()).empty() || (hash = Generate("Test!", salt)).empty() || !Compare("Test!", hash)) + throw ModuleException("BCrypt could not load!"); + } + + EventReturn OnEncrypt(const Anope::string &src, Anope::string &dest) anope_override + { + dest = "bcrypt:" + Generate(src, Salt()); + Log(LOG_DEBUG_2) << "(enc_bcrypt) hashed password from [" << src << "] to [" << dest << "]"; + return EVENT_ALLOW; + } + + void OnCheckAuthentication(User *, IdentifyRequest *req) anope_override + { + const NickAlias *na = NickAlias::Find(req->GetAccount()); + if (na == NULL) + return; + NickCore *nc = na->nc; + + size_t pos = nc->pass.find(':'); + if (pos == Anope::string::npos) + return; + Anope::string hash_method(nc->pass.begin(), nc->pass.begin() + pos); + if (hash_method != "bcrypt") + return; + + if (Compare(req->GetPassword(), nc->pass.substr(7))) + { + /* if we are NOT the first module in the list, + * we want to re-encrypt the pass with the new encryption + */ + + unsigned int hashrounds = 0; + try + { + size_t roundspos = nc->pass.find('$', 11); + if (roundspos == Anope::string::npos) + throw ConvertException("Could not find hashrounds"); + + hashrounds = convertTo(nc->pass.substr(11, roundspos - 11)); + } + catch (const ConvertException &) + { + Log(this) << "Could not get the round size of a hash. This is probably a bug. Hash: " << nc->pass; + } + + if (ModuleManager::FindFirstOf(ENCRYPTION) != this || (hashrounds && hashrounds != rounds)) + Anope::Encrypt(req->GetPassword(), nc->pass); + req->Success(this); + } + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *block = conf->GetModule(this); + rounds = block->Get("rounds", "10"); + + if (rounds == 0) + { + rounds = 10; + Log(this) << "Rounds can't be 0! Setting ignored."; + } + else if (rounds < 10) + { + Log(this) << "10 to 12 rounds is recommended."; + } + else if (rounds >= 32) + { + rounds = 10; + Log(this) << "The maximum number of rounds supported is 31. Ignoring setting and using 10."; + } + else if (rounds >= 14) + { + Log(this) << "Are you sure you want to use " << stringify(rounds) << " in your bcrypt settings? This is very CPU intensive! Recommended rounds is 10-12."; + } + } +}; + +MODULE_INIT(EBCRYPT) diff --git a/modules/encryption/enc_md5.cpp b/modules/encryption/enc_md5.cpp new file mode 100644 index 0000000..d16ee11 --- /dev/null +++ b/modules/encryption/enc_md5.cpp @@ -0,0 +1,395 @@ +/* Module for encryption using MD5. + * + * Modified for Anope. + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Taken from IRC Services and is copyright (c) 1996-2002 Andrew Church. + * E-mail: + * Parts written by Andrew Kempe and others. + * This program is free but copyrighted software; see the file COPYING for + * details. + */ + +#include "module.h" +#include "modules/encryption.h" + +/* Copyright (C) 1991-2, RSA Data Security, Inc. Created 1991. All +rights reserved. + +License to copy and use this software is granted provided that it +is identified as the "RSA Data Security, Inc. MD5 Message-Digest +Algorithm" in all material mentioning or referencing this software +or this function. + +License is also granted to make and use derivative works provided +that such works are identified as "derived from the RSA Data +Security, Inc. MD5 Message-Digest Algorithm" in all material +mentioning or referencing the derived work. + +RSA Data Security, Inc. makes no representations concerning either +the merchantability of this software or the suitability of this +software for any particular purpose. It is provided "as is" +without express or implied warranty of any kind. + +These notices must be retained in any copies of any part of this +documentation and/or software. + */ + +static unsigned char PADDING[64] = { + 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 +}; + +/* F, G, H and I are basic MD5 functions. + */ +inline static unsigned F(unsigned x, unsigned y, unsigned z) { return (x & y) | (~x & z); } +inline static unsigned G(unsigned x, unsigned y, unsigned z) { return (x & z) | (y & ~z); } +inline static unsigned H(unsigned x, unsigned y, unsigned z) { return x ^ y ^ z; } +inline static unsigned I(unsigned x, unsigned y, unsigned z) { return y ^ (x | ~z); } + +/* ROTATE_LEFT rotates x left n bits. + */ +inline static unsigned ROTATE_LEFT(unsigned x, unsigned n) { return (x << n) | (x >> (32 - n)); } + +/* FF, GG, HH, and II transformations for rounds 1, 2, 3, and 4. + * Rotation is separate from addition to prevent recomputation. + */ +inline static void FF(unsigned &a, unsigned b, unsigned c, unsigned d, unsigned x, unsigned s, unsigned ac) +{ + a += F(b, c, d) + x + ac; + a = ROTATE_LEFT(a, s); + a += b; +} +inline static void GG(unsigned &a, unsigned b, unsigned c, unsigned d, unsigned x, unsigned s, unsigned ac) +{ + a += G(b, c, d) + x + ac; + a = ROTATE_LEFT(a, s); + a += b; +} +inline static void HH(unsigned &a, unsigned b, unsigned c, unsigned d, unsigned x, unsigned s, unsigned ac) +{ + a += H(b, c, d) + x + ac; + a = ROTATE_LEFT(a, s); + a += b; +} +inline static void II(unsigned &a, unsigned b, unsigned c, unsigned d, unsigned x, unsigned s, unsigned ac) +{ + a += I(b, c, d) + x + ac; + a = ROTATE_LEFT(a, s); + a += b; +} + +static const uint32_t md5_iv[4] = +{ + 0x67452301, 0xefcdab89, 0x98badcfe, 0x10325476 +}; + +class MD5Context : public Encryption::Context +{ + unsigned state[4]; /* state (ABCD) */ + unsigned count[2]; /* number of bits, modulo 2^64 (lsb first) */ + unsigned char buffer[64]; /* input buffer */ + unsigned char digest[16]; /* final digest */ + + /* Constants for MD5Transform routine. + */ + enum + { + S11 = 7, + S12 = 12, + S13 = 17, + S14 = 22, + S21 = 5, + S22 = 9, + S23 = 14, + S24 = 20, + S31 = 4, + S32 = 11, + S33 = 16, + S34 = 23, + S41 = 6, + S42 = 10, + S43 = 15, + S44 = 21 + }; + + /* MD5 basic transformation. Transforms state based on block. + */ + void Transform(const unsigned char block[64]) + { + unsigned a = state[0], b = state[1], c = state[2], d = state[3], x[16]; + + Decode(x, block, 64); + + /* Round 1 */ + FF(a, b, c, d, x[0], S11, 0xd76aa478); /* 1 */ + FF(d, a, b, c, x[1], S12, 0xe8c7b756); /* 2 */ + FF(c, d, a, b, x[2], S13, 0x242070db); /* 3 */ + FF(b, c, d, a, x[3], S14, 0xc1bdceee); /* 4 */ + FF(a, b, c, d, x[4], S11, 0xf57c0faf); /* 5 */ + FF(d, a, b, c, x[5], S12, 0x4787c62a); /* 6 */ + FF(c, d, a, b, x[6], S13, 0xa8304613); /* 7 */ + FF(b, c, d, a, x[7], S14, 0xfd469501); /* 8 */ + FF(a, b, c, d, x[8], S11, 0x698098d8); /* 9 */ + FF(d, a, b, c, x[9], S12, 0x8b44f7af); /* 10 */ + FF(c, d, a, b, x[10], S13, 0xffff5bb1); /* 11 */ + FF(b, c, d, a, x[11], S14, 0x895cd7be); /* 12 */ + FF(a, b, c, d, x[12], S11, 0x6b901122); /* 13 */ + FF(d, a, b, c, x[13], S12, 0xfd987193); /* 14 */ + FF(c, d, a, b, x[14], S13, 0xa679438e); /* 15 */ + FF(b, c, d, a, x[15], S14, 0x49b40821); /* 16 */ + + /* Round 2 */ + GG(a, b, c, d, x[1], S21, 0xf61e2562); /* 17 */ + GG(d, a, b, c, x[6], S22, 0xc040b340); /* 18 */ + GG(c, d, a, b, x[11], S23, 0x265e5a51); /* 19 */ + GG(b, c, d, a, x[0], S24, 0xe9b6c7aa); /* 20 */ + GG(a, b, c, d, x[5], S21, 0xd62f105d); /* 21 */ + GG(d, a, b, c, x[10], S22, 0x2441453); /* 22 */ + GG(c, d, a, b, x[15], S23, 0xd8a1e681); /* 23 */ + GG(b, c, d, a, x[4], S24, 0xe7d3fbc8); /* 24 */ + GG(a, b, c, d, x[9], S21, 0x21e1cde6); /* 25 */ + GG(d, a, b, c, x[14], S22, 0xc33707d6); /* 26 */ + GG(c, d, a, b, x[3], S23, 0xf4d50d87); /* 27 */ + GG(b, c, d, a, x[8], S24, 0x455a14ed); /* 28 */ + GG(a, b, c, d, x[13], S21, 0xa9e3e905); /* 29 */ + GG(d, a, b, c, x[2], S22, 0xfcefa3f8); /* 30 */ + GG(c, d, a, b, x[7], S23, 0x676f02d9); /* 31 */ + GG(b, c, d, a, x[12], S24, 0x8d2a4c8a); /* 32 */ + + /* Round 3 */ + HH(a, b, c, d, x[5], S31, 0xfffa3942); /* 33 */ + HH(d, a, b, c, x[8], S32, 0x8771f681); /* 34 */ + HH(c, d, a, b, x[11], S33, 0x6d9d6122); /* 35 */ + HH(b, c, d, a, x[14], S34, 0xfde5380c); /* 36 */ + HH(a, b, c, d, x[1], S31, 0xa4beea44); /* 37 */ + HH(d, a, b, c, x[4], S32, 0x4bdecfa9); /* 38 */ + HH(c, d, a, b, x[7], S33, 0xf6bb4b60); /* 39 */ + HH(b, c, d, a, x[10], S34, 0xbebfbc70); /* 40 */ + HH(a, b, c, d, x[13], S31, 0x289b7ec6); /* 41 */ + HH(d, a, b, c, x[0], S32, 0xeaa127fa); /* 42 */ + HH(c, d, a, b, x[3], S33, 0xd4ef3085); /* 43 */ + HH(b, c, d, a, x[6], S34, 0x4881d05); /* 44 */ + HH(a, b, c, d, x[9], S31, 0xd9d4d039); /* 45 */ + HH(d, a, b, c, x[12], S32, 0xe6db99e5); /* 46 */ + HH(c, d, a, b, x[15], S33, 0x1fa27cf8); /* 47 */ + HH(b, c, d, a, x[2], S34, 0xc4ac5665); /* 48 */ + + /* Round 4 */ + II(a, b, c, d, x[0], S41, 0xf4292244); /* 49 */ + II(d, a, b, c, x[7], S42, 0x432aff97); /* 50 */ + II(c, d, a, b, x[14], S43, 0xab9423a7); /* 51 */ + II(b, c, d, a, x[5], S44, 0xfc93a039); /* 52 */ + II(a, b, c, d, x[12], S41, 0x655b59c3); /* 53 */ + II(d, a, b, c, x[3], S42, 0x8f0ccc92); /* 54 */ + II(c, d, a, b, x[10], S43, 0xffeff47d); /* 55 */ + II(b, c, d, a, x[1], S44, 0x85845dd1); /* 56 */ + II(a, b, c, d, x[8], S41, 0x6fa87e4f); /* 57 */ + II(d, a, b, c, x[15], S42, 0xfe2ce6e0); /* 58 */ + II(c, d, a, b, x[6], S43, 0xa3014314); /* 59 */ + II(b, c, d, a, x[13], S44, 0x4e0811a1); /* 60 */ + II(a, b, c, d, x[4], S41, 0xf7537e82); /* 61 */ + II(d, a, b, c, x[11], S42, 0xbd3af235); /* 62 */ + II(c, d, a, b, x[2], S43, 0x2ad7d2bb); /* 63 */ + II(b, c, d, a, x[9], S44, 0xeb86d391); /* 64 */ + + state[0] += a; + state[1] += b; + state[2] += c; + state[3] += d; + + /* Zeroize sensitive information. */ + memset(x, 0, sizeof(x)); + } + + /* Encodes input (unsigned) into output (unsigned char). Assumes len is + * a multiple of 4. + */ + void Encode(unsigned char *output, unsigned *input, unsigned len) + { + for (unsigned i = 0, j = 0; j < len; ++i, j += 4) + { + output[j] = static_cast(input[i] & 0xff); + output[j + 1] = static_cast((input[i] >> 8) & 0xff); + output[j + 2] = static_cast((input[i] >> 16) & 0xff); + output[j + 3] = static_cast((input[i] >> 24) & 0xff); + } + } + + /* Decodes input (unsigned char) into output (unsigned). Assumes len is + * a multiple of 4. + */ + void Decode(unsigned *output, const unsigned char *input, unsigned len) + { + for (unsigned i = 0, j = 0; j < len; ++i, j += 4) + output[i] = static_cast(input[j]) | (static_cast(input[j + 1]) << 8) | (static_cast(input[j + 2]) << 16) | (static_cast(input[j + 3]) << 24); + } + + public: + MD5Context(Encryption::IV *iv = NULL) + { + if (iv != NULL) + { + if (iv->second != 4) + throw CoreException("Invalid IV size"); + /* Load magic initialization constants. */ + for (int i = 0; i < 4; ++i) + this->state[i] = iv->first[i]; + } + else + for (int i = 0; i < 4; ++i) + this->state[i] = md5_iv[i]; + + this->count[0] = this->count[1] = 0; + memset(this->buffer, 0, sizeof(this->buffer)); + } + + /* MD5 block update operation. Continues an MD5 message-digest + * operation, processing another message block, and updating the + * context. + */ + void Update(const unsigned char *input, size_t len) anope_override + { + unsigned i, index, partLen; + + /* Compute number of bytes mod 64 */ + index = (this->count[0] >> 3) & 0x3F; + + /* Update number of bits */ + if ((this->count[0] += len << 3) < (len << 3)) + ++this->count[1]; + this->count[1] += len >> 29; + + partLen = 64 - index; + + /* Transform as many times as possible. */ + if (len >= partLen) + { + memcpy(&this->buffer[index], input, partLen); + this->Transform(this->buffer); + + for (i = partLen; i + 63 < len; i += 64) + this->Transform(&input[i]); + + index = 0; + } + else + i = 0; + + /* Buffer remaining input */ + memcpy(&this->buffer[index], &input[i], len - i); + } + + /* MD5 finalization. Ends an MD5 message-digest opera + * the message digest and zeroizing the context. + */ + void Finalize() anope_override + { + unsigned char bits[8]; + unsigned index, padLen; + + /* Save number of bits */ + this->Encode(bits, this->count, 8); + + /* Pad out to 56 mod 64. */ + index = (this->count[0] >> 3) & 0x3f; + padLen = index < 56 ? 56 - index : 120 - index; + this->Update(PADDING, padLen); + + /* Append length (before padding) */ + this->Update(bits, 8); + /* Store state in digest */ + this->Encode(digest, this->state, 16); + + /* Zeroize sensitive information. */ + memset(this->state, 0, sizeof(this->state)); + memset(this->count, 0, sizeof(this->count)); + memset(this->buffer, 0, sizeof(this->buffer)); + } + + Encryption::Hash GetFinalizedHash() anope_override + { + Encryption::Hash hash; + hash.first = this->digest; + hash.second = sizeof(this->digest); + return hash; + } +}; + +class MD5Provider : public Encryption::Provider +{ + public: + MD5Provider(Module *creator) : Encryption::Provider(creator, "md5") { } + + Encryption::Context *CreateContext(Encryption::IV *iv) anope_override + { + return new MD5Context(iv); + } + + Encryption::IV GetDefaultIV() anope_override + { + Encryption::IV iv; + iv.first = md5_iv; + iv.second = sizeof(md5_iv) / sizeof(uint32_t); + return iv; + } +}; + +class EMD5 : public Module +{ + MD5Provider md5provider; + + public: + EMD5(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, ENCRYPTION | VENDOR), + md5provider(this) + { + + } + + EventReturn OnEncrypt(const Anope::string &src, Anope::string &dest) anope_override + { + MD5Context context; + + context.Update(reinterpret_cast(src.c_str()), src.length()); + context.Finalize(); + + Encryption::Hash hash = context.GetFinalizedHash(); + + Anope::string buf = "md5:" + Anope::Hex(reinterpret_cast(hash.first), hash.second); + + Log(LOG_DEBUG_2) << "(enc_md5) hashed password from [" << src << "] to [" << buf << "]"; + dest = buf; + return EVENT_ALLOW; + } + + void OnCheckAuthentication(User *, IdentifyRequest *req) anope_override + { + const NickAlias *na = NickAlias::Find(req->GetAccount()); + if (na == NULL) + return; + NickCore *nc = na->nc; + + size_t pos = nc->pass.find(':'); + if (pos == Anope::string::npos) + return; + Anope::string hash_method(nc->pass.begin(), nc->pass.begin() + pos); + if (!hash_method.equals_cs("md5")) + return; + + Anope::string buf; + this->OnEncrypt(req->GetPassword(), buf); + if (nc->pass.equals_cs(buf)) + { + /* if we are NOT the first module in the list, + * we want to re-encrypt the pass with the new encryption + */ + if (ModuleManager::FindFirstOf(ENCRYPTION) != this) + Anope::Encrypt(req->GetPassword(), nc->pass); + req->Success(this); + } + } +}; + +MODULE_INIT(EMD5) diff --git a/modules/encryption/enc_none.cpp b/modules/encryption/enc_none.cpp new file mode 100644 index 0000000..943a39f --- /dev/null +++ b/modules/encryption/enc_none.cpp @@ -0,0 +1,69 @@ +/* Module for plain text encryption. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * This program is free but copyrighted software; see the file COPYING for + * details. + */ + +#include "module.h" + +class ENone : public Module +{ + public: + ENone(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, ENCRYPTION | VENDOR) + { + + } + + EventReturn OnEncrypt(const Anope::string &src, Anope::string &dest) anope_override + { + Anope::string buf = "plain:"; + Anope::string cpass; + Anope::B64Encode(src, cpass); + buf += cpass; + Log(LOG_DEBUG_2) << "(enc_none) hashed password from [" << src << "] to [" << buf << "]"; + dest = buf; + return EVENT_ALLOW; + } + + EventReturn OnDecrypt(const Anope::string &hashm, const Anope::string &src, Anope::string &dest) anope_override + { + if (!hashm.equals_cs("plain")) + return EVENT_CONTINUE; + size_t pos = src.find(':'); + Anope::string buf = src.substr(pos + 1); + Anope::B64Decode(buf, dest); + return EVENT_ALLOW; + } + + void OnCheckAuthentication(User *, IdentifyRequest *req) anope_override + { + const NickAlias *na = NickAlias::Find(req->GetAccount()); + if (na == NULL) + return; + NickCore *nc = na->nc; + + size_t pos = nc->pass.find(':'); + if (pos == Anope::string::npos) + return; + Anope::string hash_method(nc->pass.begin(), nc->pass.begin() + pos); + if (!hash_method.equals_cs("plain")) + return; + + Anope::string buf; + this->OnEncrypt(req->GetPassword(), buf); + if (nc->pass.equals_cs(buf)) + { + /* if we are NOT the first module in the list, + * we want to re-encrypt the pass with the new encryption + */ + if (ModuleManager::FindFirstOf(ENCRYPTION) != this) + Anope::Encrypt(req->GetPassword(), nc->pass); + req->Success(this); + } + } +}; + +MODULE_INIT(ENone) diff --git a/modules/encryption/enc_old.cpp b/modules/encryption/enc_old.cpp new file mode 100644 index 0000000..63289fa --- /dev/null +++ b/modules/encryption/enc_old.cpp @@ -0,0 +1,110 @@ +/* Include file for high-level encryption routines. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/encryption.h" + +static ServiceReference md5("Encryption::Provider", "md5"); + +class OldMD5Provider : public Encryption::Provider +{ + public: + OldMD5Provider(Module *creator) : Encryption::Provider(creator, "oldmd5") { } + + Encryption::Context *CreateContext(Encryption::IV *iv) anope_override + { + if (md5) + return md5->CreateContext(iv); + return NULL; + } + + Encryption::IV GetDefaultIV() anope_override + { + if (md5) + return md5->GetDefaultIV(); + return Encryption::IV(static_cast(NULL), 0); + } +}; + +class EOld : public Module +{ + OldMD5Provider oldmd5provider; + + inline static char XTOI(char c) { return c > 9 ? c - 'A' + 10 : c - '0'; } + + public: + EOld(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, ENCRYPTION | VENDOR), + oldmd5provider(this) + { + + ModuleManager::LoadModule("enc_md5", User::Find(creator, true)); + if (!md5) + throw ModuleException("Unable to find md5 reference"); + + } + + EventReturn OnEncrypt(const Anope::string &src, Anope::string &dest) anope_override + { + if (!md5) + return EVENT_CONTINUE; + + Encryption::Context *context = md5->CreateContext(); + context->Update(reinterpret_cast(src.c_str()), src.length()); + context->Finalize(); + + Encryption::Hash hash = context->GetFinalizedHash(); + + char digest[32], digest2[16]; + memset(digest, 0, sizeof(digest)); + if (hash.second > sizeof(digest)) + throw CoreException("Hash too large"); + memcpy(digest, hash.first, hash.second); + + for (int i = 0; i < 32; i += 2) + digest2[i / 2] = XTOI(digest[i]) << 4 | XTOI(digest[i + 1]); + + Anope::string buf = "oldmd5:" + Anope::Hex(digest2, sizeof(digest2)); + + Log(LOG_DEBUG_2) << "(enc_old) hashed password from [" << src << "] to [" << buf << "]"; + dest = buf; + delete context; + return EVENT_ALLOW; + } + + void OnCheckAuthentication(User *, IdentifyRequest *req) anope_override + { + const NickAlias *na = NickAlias::Find(req->GetAccount()); + if (na == NULL) + return; + NickCore *nc = na->nc; + + size_t pos = nc->pass.find(':'); + if (pos == Anope::string::npos) + return; + Anope::string hash_method(nc->pass.begin(), nc->pass.begin() + pos); + if (!hash_method.equals_cs("oldmd5")) + return; + + Anope::string buf; + this->OnEncrypt(req->GetPassword(), buf); + if (nc->pass.equals_cs(buf)) + { + /* if we are NOT the first module in the list, + * we want to re-encrypt the pass with the new encryption + */ + if (ModuleManager::FindFirstOf(ENCRYPTION) != this) + Anope::Encrypt(req->GetPassword(), nc->pass); + req->Success(this); + } + } +}; + +MODULE_INIT(EOld) diff --git a/modules/encryption/enc_sha1.cpp b/modules/encryption/enc_sha1.cpp new file mode 100644 index 0000000..d57929a --- /dev/null +++ b/modules/encryption/enc_sha1.cpp @@ -0,0 +1,252 @@ +/* + * + * Modified for Anope. + * (C) 2006-2022 Anope Team + * Contact us at team@anope.org + +SHA-1 in C +By Steve Reid +100% Public Domain + +Test Vectors (from FIPS PUB 180-1) +"abc" + A9993E36 4706816A BA3E2571 7850C26C 9CD0D89D +"abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq" + 84983E44 1C3BD26E BAAE4AA1 F95129E5 E54670F1 +A million repetitions of "a" + 34AA973C D4C4DAA4 F61EEB2B DBAD2731 6534016F +*/ + +/* #define LITTLE_ENDIAN * This should be #define'd if true. */ + +#include "module.h" +#include "modules/encryption.h" + +union CHAR64LONG16 +{ + unsigned char c[64]; + uint32_t l[16]; +}; + +inline static uint32_t rol(uint32_t value, uint32_t bits) { return (value << bits) | (value >> (32 - bits)); } + +/* blk0() and blk() perform the initial expand. */ +/* I got the idea of expanding during the round function from SSLeay */ +inline static uint32_t blk0(CHAR64LONG16 &block, uint32_t i) +{ +#ifdef LITTLE_ENDIAN + return block.l[i] = (rol(block.l[i], 24) & 0xFF00FF00) | (rol(block.l[i], 8) & 0x00FF00FF); +#else + return block.l[i]; +#endif +} +inline static uint32_t blk(CHAR64LONG16 &block, uint32_t i) { return block.l[i & 15] = rol(block.l[(i + 13) & 15] ^ block.l[(i + 8) & 15] ^ block.l[(i + 2) & 15] ^ block.l[i & 15],1); } + +/* (R0+R1), R2, R3, R4 are the different operations used in SHA1 */ +inline static void R0(CHAR64LONG16 &block, uint32_t v, uint32_t &w, uint32_t x, uint32_t y, uint32_t &z, uint32_t i) { z += ((w & (x ^ y)) ^ y) + blk0(block, i) + 0x5A827999 + rol(v, 5); w = rol(w, 30); } +inline static void R1(CHAR64LONG16 &block, uint32_t v, uint32_t &w, uint32_t x, uint32_t y, uint32_t &z, uint32_t i) { z += ((w & (x ^ y)) ^ y) + blk(block, i) + 0x5A827999 + rol(v, 5); w = rol(w, 30); } +inline static void R2(CHAR64LONG16 &block, uint32_t v, uint32_t &w, uint32_t x, uint32_t y, uint32_t &z, uint32_t i) { z += (w ^ x ^ y) + blk(block, i) + 0x6ED9EBA1 + rol(v, 5); w = rol(w, 30); } +inline static void R3(CHAR64LONG16 &block, uint32_t v, uint32_t &w, uint32_t x, uint32_t y, uint32_t &z, uint32_t i) { z += (((w | x) & y) | (w & x)) + blk(block, i) + 0x8F1BBCDC + rol(v, 5); w = rol(w, 30); } +inline static void R4(CHAR64LONG16 &block, uint32_t v, uint32_t &w, uint32_t x, uint32_t y, uint32_t &z, uint32_t i) { z += (w ^ x ^ y) + blk(block, i) + 0xCA62C1D6 + rol(v, 5); w = rol(w, 30); } + +static const uint32_t sha1_iv[5] = +{ + 0x67452301, 0xEFCDAB89, 0x98BADCFE, 0x10325476, 0xC3D2E1F0 +}; + +class SHA1Context : public Encryption::Context +{ + uint32_t state[5]; + uint32_t count[2]; + unsigned char buffer[64]; + unsigned char digest[20]; + + void Transform(const unsigned char buf[64]) + { + uint32_t a, b, c, d, e; + + CHAR64LONG16 block; + memcpy(block.c, buf, 64); + + /* Copy context->state[] to working vars */ + a = this->state[0]; + b = this->state[1]; + c = this->state[2]; + d = this->state[3]; + e = this->state[4]; + + /* 4 rounds of 20 operations each. Loop unrolled. */ + R0(block, a, b, c, d, e, 0); R0(block, e, a, b, c, d, 1); R0(block, d, e, a, b, c, 2); R0(block, c, d, e, a, b, 3); + R0(block, b, c, d, e, a, 4); R0(block, a, b, c, d, e, 5); R0(block, e, a, b, c, d, 6); R0(block, d, e, a, b, c, 7); + R0(block, c, d, e, a, b, 8); R0(block, b, c, d, e, a, 9); R0(block, a, b, c, d, e, 10); R0(block, e, a, b, c, d, 11); + R0(block, d, e, a, b, c, 12); R0(block, c, d, e, a, b, 13); R0(block, b, c, d, e, a, 14); R0(block, a, b, c, d, e, 15); + R1(block, e, a, b, c, d, 16); R1(block, d, e, a, b, c, 17); R1(block, c, d, e, a, b, 18); R1(block, b, c, d, e, a, 19); + R2(block, a, b, c, d, e, 20); R2(block, e, a, b, c, d, 21); R2(block, d, e, a, b, c, 22); R2(block, c, d, e, a, b, 23); + R2(block, b, c, d, e, a, 24); R2(block, a, b, c, d, e, 25); R2(block, e, a, b, c, d, 26); R2(block, d, e, a, b, c, 27); + R2(block, c, d, e, a, b, 28); R2(block, b, c, d, e, a, 29); R2(block, a, b, c, d, e, 30); R2(block, e, a, b, c, d, 31); + R2(block, d, e, a, b, c, 32); R2(block, c, d, e, a, b, 33); R2(block, b, c, d, e, a, 34); R2(block, a, b, c, d, e, 35); + R2(block, e, a, b, c, d, 36); R2(block, d, e, a, b, c, 37); R2(block, c, d, e, a, b, 38); R2(block, b, c, d, e, a, 39); + R3(block, a, b, c, d, e, 40); R3(block, e, a, b, c, d, 41); R3(block, d, e, a, b, c, 42); R3(block, c, d, e, a, b, 43); + R3(block, b, c, d, e, a, 44); R3(block, a, b, c, d, e, 45); R3(block, e, a, b, c, d, 46); R3(block, d, e, a, b, c, 47); + R3(block, c, d, e, a, b, 48); R3(block, b, c, d, e, a, 49); R3(block, a, b, c, d, e, 50); R3(block, e, a, b, c, d, 51); + R3(block, d, e, a, b, c, 52); R3(block, c, d, e, a, b, 53); R3(block, b, c, d, e, a, 54); R3(block, a, b, c, d, e, 55); + R3(block, e, a, b, c, d, 56); R3(block, d, e, a, b, c, 57); R3(block, c, d, e, a, b, 58); R3(block, b, c, d, e, a, 59); + R4(block, a, b, c, d, e, 60); R4(block, e, a, b, c, d, 61); R4(block, d, e, a, b, c, 62); R4(block, c, d, e, a, b, 63); + R4(block, b, c, d, e, a, 64); R4(block, a, b, c, d, e, 65); R4(block, e, a, b, c, d, 66); R4(block, d, e, a, b, c, 67); + R4(block, c, d, e, a, b, 68); R4(block, b, c, d, e, a, 69); R4(block, a, b, c, d, e, 70); R4(block, e, a, b, c, d, 71); + R4(block, d, e, a, b, c, 72); R4(block, c, d, e, a, b, 73); R4(block, b, c, d, e, a, 74); R4(block, a, b, c, d, e, 75); + R4(block, e, a, b, c, d, 76); R4(block, d, e, a, b, c, 77); R4(block, c, d, e, a, b, 78); R4(block, b, c, d, e, a, 79); + /* Add the working vars back into context.state[] */ + this->state[0] += a; + this->state[1] += b; + this->state[2] += c; + this->state[3] += d; + this->state[4] += e; + /* Wipe variables */ + a = b = c = d = e = 0; + } + + public: + SHA1Context(Encryption::IV *iv = NULL) + { + if (iv != NULL) + { + if (iv->second != 5) + throw CoreException("Invalid IV size"); + for (int i = 0; i < 5; ++i) + this->state[i] = iv->first[i]; + } + else + for (int i = 0; i < 5; ++i) + this->state[i] = sha1_iv[i]; + + this->count[0] = this->count[1] = 0; + memset(this->buffer, 0, sizeof(this->buffer)); + memset(this->digest, 0, sizeof(this->digest)); + } + + void Update(const unsigned char *data, size_t len) anope_override + { + uint32_t i, j; + + j = (this->count[0] >> 3) & 63; + if ((this->count[0] += len << 3) < (len << 3)) + ++this->count[1]; + this->count[1] += len >> 29; + if (j + len > 63) + { + memcpy(&this->buffer[j], data, (i = 64 - j)); + this->Transform(this->buffer); + for (; i + 63 < len; i += 64) + this->Transform(&data[i]); + j = 0; + } + else + i = 0; + memcpy(&this->buffer[j], &data[i], len - i); + } + + void Finalize() anope_override + { + uint32_t i; + unsigned char finalcount[8]; + + for (i = 0; i < 8; ++i) + finalcount[i] = static_cast((this->count[i >= 4 ? 0 : 1] >> ((3 - (i & 3)) * 8)) & 255); /* Endian independent */ + this->Update(reinterpret_cast("\200"), 1); + while ((this->count[0] & 504) != 448) + this->Update(reinterpret_cast("\0"), 1); + this->Update(finalcount, 8); /* Should cause a SHA1Transform() */ + for (i = 0; i < 20; ++i) + this->digest[i] = static_cast((this->state[i>>2] >> ((3 - (i & 3)) * 8)) & 255); + + /* Wipe variables */ + memset(this->buffer, 0, sizeof(this->buffer)); + memset(this->state, 0, sizeof(this->state)); + memset(this->count, 0, sizeof(this->count)); + memset(&finalcount, 0, sizeof(finalcount)); + + this->Transform(this->buffer); + } + + Encryption::Hash GetFinalizedHash() anope_override + { + Encryption::Hash hash; + hash.first = this->digest; + hash.second = sizeof(this->digest); + return hash; + } +}; + +class SHA1Provider : public Encryption::Provider +{ + public: + SHA1Provider(Module *creator) : Encryption::Provider(creator, "sha1") { } + + Encryption::Context *CreateContext(Encryption::IV *iv) anope_override + { + return new SHA1Context(iv); + } + + Encryption::IV GetDefaultIV() anope_override + { + Encryption::IV iv; + iv.first = sha1_iv; + iv.second = sizeof(sha1_iv) / sizeof(uint32_t); + return iv; + } +}; + +class ESHA1 : public Module +{ + SHA1Provider sha1provider; + + public: + ESHA1(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, ENCRYPTION | VENDOR), + sha1provider(this) + { + + } + + EventReturn OnEncrypt(const Anope::string &src, Anope::string &dest) anope_override + { + SHA1Context context; + + context.Update(reinterpret_cast(src.c_str()), src.length()); + context.Finalize(); + + Encryption::Hash hash = context.GetFinalizedHash(); + + Anope::string buf = "sha1:" + Anope::Hex(reinterpret_cast(hash.first), hash.second); + + Log(LOG_DEBUG_2) << "(enc_sha1) hashed password from [" << src << "] to [" << buf << "]"; + dest = buf; + return EVENT_ALLOW; + } + + void OnCheckAuthentication(User *, IdentifyRequest *req) anope_override + { + const NickAlias *na = NickAlias::Find(req->GetAccount()); + if (na == NULL) + return; + NickCore *nc = na->nc; + + size_t pos = nc->pass.find(':'); + if (pos == Anope::string::npos) + return; + Anope::string hash_method(nc->pass.begin(), nc->pass.begin() + pos); + if (!hash_method.equals_cs("sha1")) + return; + + Anope::string buf; + this->OnEncrypt(req->GetPassword(), buf); + if (nc->pass.equals_cs(buf)) + { + if (ModuleManager::FindFirstOf(ENCRYPTION) != this) + Anope::Encrypt(req->GetPassword(), nc->pass); + req->Success(this); + } + } +}; + +MODULE_INIT(ESHA1) diff --git a/modules/encryption/enc_sha256.cpp b/modules/encryption/enc_sha256.cpp new file mode 100644 index 0000000..9173ce7 --- /dev/null +++ b/modules/encryption/enc_sha256.cpp @@ -0,0 +1,334 @@ +/* This module generates and compares password hashes using SHA256 algorithms. + * + * If an intruder gets access to your system or uses a brute force attack, + * salt will not provide much value. + * IMPORTANT: DATA HASHES CANNOT BE "DECRYPTED" BACK TO PLAIN TEXT. + * + * Modified for Anope. + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Taken from InspIRCd (https://www.inspircd.org/), + * see https://wiki.inspircd.org/Credits + * + * This program is free but copyrighted software; see + * the file COPYING for details. + */ + +/* FIPS 180-2 SHA-224/256/384/512 implementation + * Last update: 05/23/2005 + * Issue date: 04/30/2005 + * + * Copyright (C) 2005 Olivier Gay + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of the project nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include "module.h" +#include "modules/encryption.h" + +static const unsigned SHA256_DIGEST_SIZE = 256 / 8; +static const unsigned SHA256_BLOCK_SIZE = 512 / 8; + +inline static uint32_t SHFR(uint32_t x, uint32_t n) { return x >> n; } +inline static uint32_t ROTR(uint32_t x, uint32_t n) { return (x >> n) | (x << ((sizeof(x) << 3) - n)); } +inline static uint32_t CH(uint32_t x, uint32_t y, uint32_t z) { return (x & y) ^ (~x & z); } +inline static uint32_t MAJ(uint32_t x, uint32_t y, uint32_t z) { return (x & y) ^ (x & z) ^ (y & z); } + +inline static uint32_t SHA256_F1(uint32_t x) { return ROTR(x, 2) ^ ROTR(x, 13) ^ ROTR(x, 22); } +inline static uint32_t SHA256_F2(uint32_t x) { return ROTR(x, 6) ^ ROTR(x, 11) ^ ROTR(x, 25); } +inline static uint32_t SHA256_F3(uint32_t x) { return ROTR(x, 7) ^ ROTR(x, 18) ^ SHFR(x, 3); } +inline static uint32_t SHA256_F4(uint32_t x) { return ROTR(x, 17) ^ ROTR(x, 19) ^ SHFR(x, 10); } + +inline static void UNPACK32(unsigned x, unsigned char *str) +{ + str[3] = static_cast(x); + str[2] = static_cast(x >> 8); + str[1] = static_cast(x >> 16); + str[0] = static_cast(x >> 24); +} + +inline static void PACK32(unsigned char *str, uint32_t &x) +{ + x = static_cast(str[3]) | static_cast(str[2]) << 8 | static_cast(str[1]) << 16 | static_cast(str[0]) << 24; +} + +/* Macros used for loops unrolling */ + +inline static void SHA256_SCR(uint32_t w[64], int i) +{ + w[i] = SHA256_F4(w[i - 2]) + w[i - 7] + SHA256_F3(w[i - 15]) + w[i - 16]; +} + +static const uint32_t sha256_h0[8] = +{ + 0x6a09e667, 0xbb67ae85, 0x3c6ef372, 0xa54ff53a, + 0x510e527f, 0x9b05688c, 0x1f83d9ab, 0x5be0cd19 +}; + +static const uint32_t sha256_k[64] = +{ + 0x428a2f98, 0x71374491, 0xb5c0fbcf, 0xe9b5dba5, + 0x3956c25b, 0x59f111f1, 0x923f82a4, 0xab1c5ed5, + 0xd807aa98, 0x12835b01, 0x243185be, 0x550c7dc3, + 0x72be5d74, 0x80deb1fe, 0x9bdc06a7, 0xc19bf174, + 0xe49b69c1, 0xefbe4786, 0x0fc19dc6, 0x240ca1cc, + 0x2de92c6f, 0x4a7484aa, 0x5cb0a9dc, 0x76f988da, + 0x983e5152, 0xa831c66d, 0xb00327c8, 0xbf597fc7, + 0xc6e00bf3, 0xd5a79147, 0x06ca6351, 0x14292967, + 0x27b70a85, 0x2e1b2138, 0x4d2c6dfc, 0x53380d13, + 0x650a7354, 0x766a0abb, 0x81c2c92e, 0x92722c85, + 0xa2bfe8a1, 0xa81a664b, 0xc24b8b70, 0xc76c51a3, + 0xd192e819, 0xd6990624, 0xf40e3585, 0x106aa070, + 0x19a4c116, 0x1e376c08, 0x2748774c, 0x34b0bcb5, + 0x391c0cb3, 0x4ed8aa4a, 0x5b9cca4f, 0x682e6ff3, + 0x748f82ee, 0x78a5636f, 0x84c87814, 0x8cc70208, + 0x90befffa, 0xa4506ceb, 0xbef9a3f7, 0xc67178f2 +}; + +/** An sha256 context + */ +class SHA256Context : public Encryption::Context +{ + void Transform(unsigned char *message, unsigned block_nb) + { + uint32_t w[64], wv[8]; + unsigned char *sub_block; + for (unsigned i = 1; i <= block_nb; ++i) + { + int j; + sub_block = message + ((i - 1) << 6); + + for (j = 0; j < 16; ++j) + PACK32(&sub_block[j << 2], w[j]); + for (j = 16; j < 64; ++j) + SHA256_SCR(w, j); + for (j = 0; j < 8; ++j) + wv[j] = this->h[j]; + for (j = 0; j < 64; ++j) + { + uint32_t t1 = wv[7] + SHA256_F2(wv[4]) + CH(wv[4], wv[5], wv[6]) + sha256_k[j] + w[j]; + uint32_t t2 = SHA256_F1(wv[0]) + MAJ(wv[0], wv[1], wv[2]); + wv[7] = wv[6]; + wv[6] = wv[5]; + wv[5] = wv[4]; + wv[4] = wv[3] + t1; + wv[3] = wv[2]; + wv[2] = wv[1]; + wv[1] = wv[0]; + wv[0] = t1 + t2; + } + for (j = 0; j < 8; ++j) + this->h[j] += wv[j]; + } + } + + unsigned tot_len; + unsigned len; + unsigned char block[2 * SHA256_BLOCK_SIZE]; + uint32_t h[8]; + unsigned char digest[SHA256_DIGEST_SIZE]; + + public: + SHA256Context(Encryption::IV *iv) + { + if (iv != NULL) + { + if (iv->second != 8) + throw CoreException("Invalid IV size"); + for (int i = 0; i < 8; ++i) + this->h[i] = iv->first[i]; + } + else + for (int i = 0; i < 8; ++i) + this->h[i] = sha256_h0[i]; + + this->tot_len = 0; + this->len = 0; + memset(this->block, 0, sizeof(this->block)); + memset(this->digest, 0, sizeof(this->digest)); + } + + void Update(const unsigned char *message, size_t mlen) anope_override + { + unsigned tmp_len = SHA256_BLOCK_SIZE - this->len, rem_len = mlen < tmp_len ? mlen : tmp_len; + + memcpy(&this->block[this->len], message, rem_len); + if (this->len + mlen < SHA256_BLOCK_SIZE) + { + this->len += mlen; + return; + } + unsigned new_len = mlen - rem_len, block_nb = new_len / SHA256_BLOCK_SIZE; + unsigned char *shifted_message = new unsigned char[mlen - rem_len]; + memcpy(shifted_message, message + rem_len, mlen - rem_len); + this->Transform(this->block, 1); + this->Transform(shifted_message, block_nb); + rem_len = new_len % SHA256_BLOCK_SIZE; + memcpy(this->block, &shifted_message[block_nb << 6], rem_len); + delete [] shifted_message; + this->len = rem_len; + this->tot_len += (block_nb + 1) << 6; + } + + void Finalize() anope_override + { + unsigned block_nb = 1 + ((SHA256_BLOCK_SIZE - 9) < (this->len % SHA256_BLOCK_SIZE)); + unsigned len_b = (this->tot_len + this->len) << 3; + unsigned pm_len = block_nb << 6; + memset(this->block + this->len, 0, pm_len - this->len); + this->block[this->len] = 0x80; + UNPACK32(len_b, this->block + pm_len - 4); + this->Transform(this->block, block_nb); + for (int i = 0 ; i < 8; ++i) + UNPACK32(this->h[i], &this->digest[i << 2]); + } + + Encryption::Hash GetFinalizedHash() anope_override + { + Encryption::Hash hash; + hash.first = this->digest; + hash.second = SHA256_DIGEST_SIZE; + return hash; + } +}; + +class SHA256Provider : public Encryption::Provider +{ + public: + SHA256Provider(Module *creator) : Encryption::Provider(creator, "sha256") { } + + Encryption::Context *CreateContext(Encryption::IV *iv) anope_override + { + return new SHA256Context(iv); + } + + Encryption::IV GetDefaultIV() anope_override + { + Encryption::IV iv; + iv.first = sha256_h0; + iv.second = sizeof(sha256_h0) / sizeof(uint32_t); + return iv; + } +}; + +class ESHA256 : public Module +{ + SHA256Provider sha256provider; + + unsigned iv[8]; + bool use_iv; + + /* initializes the IV with a new random value */ + void NewRandomIV() + { + for (int i = 0; i < 8; ++i) + iv[i] = static_cast(rand()); + } + + /* returns the IV as base64-encrypted string */ + Anope::string GetIVString() + { + char buf[33]; + for (int i = 0; i < 8; ++i) + UNPACK32(iv[i], reinterpret_cast(&buf[i << 2])); + buf[32] = '\0'; + return Anope::Hex(buf, 32); + } + + /* splits the appended IV from the password string so it can be used for the next encryption */ + /* password format: :: */ + void GetIVFromPass(const Anope::string &password) + { + size_t pos = password.find(':'); + Anope::string buf = password.substr(password.find(':', pos + 1) + 1, password.length()); + char buf2[33]; + Anope::Unhex(buf, buf2, sizeof(buf2)); + for (int i = 0 ; i < 8; ++i) + PACK32(reinterpret_cast(&buf2[i << 2]), iv[i]); + } + + public: + ESHA256(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, ENCRYPTION | VENDOR), + sha256provider(this) + { + + + use_iv = false; + } + + EventReturn OnEncrypt(const Anope::string &src, Anope::string &dest) anope_override + { + if (!use_iv) + NewRandomIV(); + else + use_iv = false; + + Encryption::IV initialization(this->iv, 8); + SHA256Context ctx(&initialization); + ctx.Update(reinterpret_cast(src.c_str()), src.length()); + ctx.Finalize(); + + Encryption::Hash hash = ctx.GetFinalizedHash(); + + std::stringstream buf; + buf << "sha256:" << Anope::Hex(reinterpret_cast(hash.first), hash.second) << ":" << GetIVString(); + Log(LOG_DEBUG_2) << "(enc_sha256) hashed password from [" << src << "] to [" << buf.str() << " ]"; + dest = buf.str(); + return EVENT_ALLOW; + } + + void OnCheckAuthentication(User *, IdentifyRequest *req) anope_override + { + const NickAlias *na = NickAlias::Find(req->GetAccount()); + if (na == NULL) + return; + NickCore *nc = na->nc; + + size_t pos = nc->pass.find(':'); + if (pos == Anope::string::npos) + return; + Anope::string hash_method(nc->pass.begin(), nc->pass.begin() + pos); + if (!hash_method.equals_cs("sha256")) + return; + + GetIVFromPass(nc->pass); + use_iv = true; + Anope::string buf; + this->OnEncrypt(req->GetPassword(), buf); + if (nc->pass.equals_cs(buf)) + { + /* if we are NOT the first module in the list, + * we want to re-encrypt the pass with the new encryption + */ + if (ModuleManager::FindFirstOf(ENCRYPTION) != this) + Anope::Encrypt(req->GetPassword(), nc->pass); + req->Success(this); + } + } +}; + +MODULE_INIT(ESHA256) diff --git a/modules/extra/CMakeLists.txt b/modules/extra/CMakeLists.txt new file mode 100644 index 0000000..6c50f86 --- /dev/null +++ b/modules/extra/CMakeLists.txt @@ -0,0 +1,3 @@ +# This file is here to prevent the building of the extras directory. +# Users who want to build the contents of this directory should copy +# or symlink files out of it. diff --git a/modules/extra/m_ldap.cpp b/modules/extra/m_ldap.cpp new file mode 100644 index 0000000..43ef058 --- /dev/null +++ b/modules/extra/m_ldap.cpp @@ -0,0 +1,626 @@ +/* + * + * (C) 2011-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +/* RequiredLibraries: ldap_r|ldap,lber */ +/* RequiredWindowsLibraries: libldap_r|libldap,liblber */ + +#include "module.h" +#include "modules/ldap.h" +#include + +#if defined LDAP_API_FEATURE_X_OPENLDAP_REENTRANT && !LDAP_API_FEATURE_X_OPENLDAP_REENTRANT +# error Anope requires OpenLDAP to be built as reentrant. +#endif + + +class LDAPService; +static Pipe *me; + +class LDAPRequest +{ + public: + LDAPService *service; + LDAPInterface *inter; + LDAPMessage *message; /* message returned by ldap_ */ + LDAPResult *result; /* final result */ + struct timeval tv; + QueryType type; + + LDAPRequest(LDAPService *s, LDAPInterface *i) + : service(s) + , inter(i) + , message(NULL) + , result(NULL) + { + type = QUERY_UNKNOWN; + tv.tv_sec = 0; + tv.tv_usec = 100000; + } + + virtual ~LDAPRequest() + { + delete result; + if (inter != NULL) + inter->OnDelete(); + if (message != NULL) + ldap_msgfree(message); + } + + virtual int run() = 0; +}; + +class LDAPBind : public LDAPRequest +{ + Anope::string who, pass; + + public: + LDAPBind(LDAPService *s, LDAPInterface *i, const Anope::string &w, const Anope::string &p) + : LDAPRequest(s, i) + , who(w) + , pass(p) + { + type = QUERY_BIND; + } + + int run() anope_override; +}; + +class LDAPSearch : public LDAPRequest +{ + Anope::string base; + Anope::string filter; + + public: + LDAPSearch(LDAPService *s, LDAPInterface *i, const Anope::string &b, const Anope::string &f) + : LDAPRequest(s, i) + , base(b) + , filter(f) + { + type = QUERY_SEARCH; + } + + int run() anope_override; +}; + +class LDAPAdd : public LDAPRequest +{ + Anope::string dn; + LDAPMods attributes; + + public: + LDAPAdd(LDAPService *s, LDAPInterface *i, const Anope::string &d, const LDAPMods &attr) + : LDAPRequest(s, i) + , dn(d) + , attributes(attr) + { + type = QUERY_ADD; + } + + int run() anope_override; +}; + +class LDAPDel : public LDAPRequest +{ + Anope::string dn; + + public: + LDAPDel(LDAPService *s, LDAPInterface *i, const Anope::string &d) + : LDAPRequest(s, i) + , dn(d) + { + type = QUERY_DELETE; + } + + int run() anope_override; +}; + +class LDAPModify : public LDAPRequest +{ + Anope::string base; + LDAPMods attributes; + + public: + LDAPModify(LDAPService *s, LDAPInterface *i, const Anope::string &b, const LDAPMods &attr) + : LDAPRequest(s, i) + , base(b) + , attributes(attr) + { + type = QUERY_MODIFY; + } + + int run() anope_override; +}; + +class LDAPService : public LDAPProvider, public Thread, public Condition +{ + Anope::string server; + Anope::string admin_binddn; + Anope::string admin_pass; + + LDAP *con; + + time_t last_connect; + + public: + static LDAPMod **BuildMods(const LDAPMods &attributes) + { + LDAPMod **mods = new LDAPMod*[attributes.size() + 1]; + memset(mods, 0, sizeof(LDAPMod*) * (attributes.size() + 1)); + for (unsigned x = 0; x < attributes.size(); ++x) + { + const LDAPModification &l = attributes[x]; + mods[x] = new LDAPMod(); + + if (l.op == LDAPModification::LDAP_ADD) + mods[x]->mod_op = LDAP_MOD_ADD; + else if (l.op == LDAPModification::LDAP_DEL) + mods[x]->mod_op = LDAP_MOD_DELETE; + else if (l.op == LDAPModification::LDAP_REPLACE) + mods[x]->mod_op = LDAP_MOD_REPLACE; + else if (l.op != 0) + throw LDAPException("Unknown LDAP operation"); + mods[x]->mod_type = strdup(l.name.c_str()); + mods[x]->mod_values = new char*[l.values.size() + 1]; + memset(mods[x]->mod_values, 0, sizeof(char *) * (l.values.size() + 1)); + for (unsigned j = 0, c = 0; j < l.values.size(); ++j) + if (!l.values[j].empty()) + mods[x]->mod_values[c++] = strdup(l.values[j].c_str()); + } + return mods; + } + + static void FreeMods(LDAPMod **mods) + { + for (int i = 0; mods[i] != NULL; ++i) + { + free(mods[i]->mod_type); + for (int j = 0; mods[i]->mod_values[j] != NULL; ++j) + free(mods[i]->mod_values[j]); + delete [] mods[i]->mod_values; + } + delete [] mods; + } + + private: + void Connect() + { + int i = ldap_initialize(&this->con, this->server.c_str()); + if (i != LDAP_SUCCESS) + throw LDAPException("Unable to connect to LDAP service " + this->name + ": " + ldap_err2string(i)); + + const int version = LDAP_VERSION3; + i = ldap_set_option(this->con, LDAP_OPT_PROTOCOL_VERSION, &version); + if (i != LDAP_OPT_SUCCESS) + throw LDAPException("Unable to set protocol version for " + this->name + ": " + ldap_err2string(i)); + + const struct timeval tv = { 0, 0 }; + i = ldap_set_option(this->con, LDAP_OPT_NETWORK_TIMEOUT, &tv); + if (i != LDAP_OPT_SUCCESS) + throw LDAPException("Unable to set timeout for " + this->name + ": " + ldap_err2string(i)); + } + + void Reconnect() + { + /* Only try one connect a minute. It is an expensive blocking operation */ + if (last_connect > Anope::CurTime - 60) + throw LDAPException("Unable to connect to LDAP service " + this->name + ": reconnecting too fast"); + last_connect = Anope::CurTime; + + ldap_unbind_ext(this->con, NULL, NULL); + + Connect(); + } + + void QueueRequest(LDAPRequest *r) + { + this->Lock(); + this->queries.push_back(r); + this->Wakeup(); + this->Unlock(); + } + + public: + typedef std::vector query_queue; + query_queue queries, results; + Mutex process_mutex; /* held when processing requests not in either queue */ + + LDAPService(Module *o, const Anope::string &n, const Anope::string &s, const Anope::string &b, const Anope::string &p) : LDAPProvider(o, n), server(s), admin_binddn(b), admin_pass(p), last_connect(0) + { + Connect(); + } + + ~LDAPService() + { + /* At this point the thread has stopped so we don't need to hold process_mutex */ + + this->Lock(); + + for (unsigned int i = 0; i < this->queries.size(); ++i) + { + LDAPRequest *req = this->queries[i]; + + /* queries have no results yet */ + req->result = new LDAPResult(); + req->result->type = req->type; + req->result->error = "LDAP Interface is going away"; + if (req->inter) + req->inter->OnError(*req->result); + + delete req; + } + this->queries.clear(); + + for (unsigned int i = 0; i < this->results.size(); ++i) + { + LDAPRequest *req = this->results[i]; + + /* even though this may have already finished successfully we return that it didn't */ + req->result->error = "LDAP Interface is going away"; + if (req->inter) + req->inter->OnError(*req->result); + + delete req; + } + + this->Unlock(); + + ldap_unbind_ext(this->con, NULL, NULL); + } + + void BindAsAdmin(LDAPInterface *i) anope_override + { + this->Bind(i, this->admin_binddn, this->admin_pass); + } + + void Bind(LDAPInterface *i, const Anope::string &who, const Anope::string &pass) anope_override + { + LDAPBind *b = new LDAPBind(this, i, who, pass); + QueueRequest(b); + } + + void Search(LDAPInterface *i, const Anope::string &base, const Anope::string &filter) anope_override + { + if (i == NULL) + throw LDAPException("No interface"); + + LDAPSearch *s = new LDAPSearch(this, i, base, filter); + QueueRequest(s); + } + + void Add(LDAPInterface *i, const Anope::string &dn, LDAPMods &attributes) anope_override + { + LDAPAdd *add = new LDAPAdd(this, i, dn, attributes); + QueueRequest(add); + } + + void Del(LDAPInterface *i, const Anope::string &dn) anope_override + { + LDAPDel *del = new LDAPDel(this, i, dn); + QueueRequest(del); + } + + void Modify(LDAPInterface *i, const Anope::string &base, LDAPMods &attributes) anope_override + { + LDAPModify *mod = new LDAPModify(this, i, base, attributes); + QueueRequest(mod); + } + + private: + void BuildReply(int res, LDAPRequest *req) + { + LDAPResult *ldap_result = req->result = new LDAPResult(); + req->result->type = req->type; + + if (res != LDAP_SUCCESS) + { + ldap_result->error = ldap_err2string(res); + return; + } + + if (req->message == NULL) + { + return; + } + + /* a search result */ + + for (LDAPMessage *cur = ldap_first_message(this->con, req->message); cur; cur = ldap_next_message(this->con, cur)) + { + LDAPAttributes attributes; + + char *dn = ldap_get_dn(this->con, cur); + if (dn != NULL) + { + attributes["dn"].push_back(dn); + ldap_memfree(dn); + dn = NULL; + } + + BerElement *ber = NULL; + + for (char *attr = ldap_first_attribute(this->con, cur, &ber); attr; attr = ldap_next_attribute(this->con, cur, ber)) + { + berval **vals = ldap_get_values_len(this->con, cur, attr); + int count = ldap_count_values_len(vals); + + std::vector attrs; + for (int j = 0; j < count; ++j) + attrs.push_back(vals[j]->bv_val); + attributes[attr] = attrs; + + ldap_value_free_len(vals); + ldap_memfree(attr); + } + + if (ber != NULL) + ber_free(ber, 0); + + ldap_result->messages.push_back(attributes); + } + } + + void SendRequests() + { + process_mutex.Lock(); + + query_queue q; + this->Lock(); + queries.swap(q); + this->Unlock(); + + if (q.empty()) + { + process_mutex.Unlock(); + return; + } + + for (unsigned int i = 0; i < q.size(); ++i) + { + LDAPRequest *req = q[i]; + int ret = req->run(); + + if (ret == LDAP_SERVER_DOWN || ret == LDAP_TIMEOUT) + { + /* try again */ + try + { + Reconnect(); + } + catch (const LDAPException &) + { + } + + ret = req->run(); + } + + BuildReply(ret, req); + + this->Lock(); + results.push_back(req); + this->Unlock(); + } + + me->Notify(); + + process_mutex.Unlock(); + } + + public: + void Run() anope_override + { + while (!this->GetExitState()) + { + this->Lock(); + /* Queries can be non empty if one is pushed during SendRequests() */ + if (queries.empty()) + this->Wait(); + this->Unlock(); + + SendRequests(); + } + } + + LDAP* GetConnection() + { + return con; + } +}; + +class ModuleLDAP : public Module, public Pipe +{ + std::map LDAPServices; + + public: + + ModuleLDAP(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR) + { + me = this; + } + + ~ModuleLDAP() + { + for (std::map::iterator it = this->LDAPServices.begin(); it != this->LDAPServices.end(); ++it) + { + it->second->SetExitState(); + it->second->Wakeup(); + it->second->Join(); + delete it->second; + } + LDAPServices.clear(); + } + + void OnReload(Configuration::Conf *config) anope_override + { + Configuration::Block *conf = config->GetModule(this); + + for (std::map::iterator it = this->LDAPServices.begin(); it != this->LDAPServices.end();) + { + const Anope::string &cname = it->first; + LDAPService *s = it->second; + int i; + + ++it; + + for (i = 0; i < conf->CountBlock("ldap"); ++i) + if (conf->GetBlock("ldap", i)->Get("name", "ldap/main") == cname) + break; + + if (i == conf->CountBlock("ldap")) + { + Log(LOG_NORMAL, "ldap") << "LDAP: Removing server connection " << cname; + + s->SetExitState(); + s->Wakeup(); + s->Join(); + delete s; + this->LDAPServices.erase(cname); + } + } + + for (int i = 0; i < conf->CountBlock("ldap"); ++i) + { + Configuration::Block *ldap = conf->GetBlock("ldap", i); + + const Anope::string &connname = ldap->Get("name", "ldap/main"); + + if (this->LDAPServices.find(connname) == this->LDAPServices.end()) + { + const Anope::string &server = ldap->Get("server", "127.0.0.1"); + const Anope::string &admin_binddn = ldap->Get("admin_binddn"); + const Anope::string &admin_password = ldap->Get("admin_password"); + + try + { + LDAPService *ss = new LDAPService(this, connname, server, admin_binddn, admin_password); + ss->Start(); + this->LDAPServices.insert(std::make_pair(connname, ss)); + + Log(LOG_NORMAL, "ldap") << "LDAP: Successfully initialized server " << connname << " (" << server << ")"; + } + catch (const LDAPException &ex) + { + Log(LOG_NORMAL, "ldap") << "LDAP: " << ex.GetReason(); + } + } + } + } + + void OnModuleUnload(User *, Module *m) anope_override + { + for (std::map::iterator it = this->LDAPServices.begin(); it != this->LDAPServices.end(); ++it) + { + LDAPService *s = it->second; + + s->process_mutex.Lock(); + s->Lock(); + + for (unsigned int i = s->queries.size(); i > 0; --i) + { + LDAPRequest *req = s->queries[i - 1]; + LDAPInterface *li = req->inter; + + if (li && li->owner == m) + { + s->queries.erase(s->queries.begin() + i - 1); + delete req; + } + } + for (unsigned int i = s->results.size(); i > 0; --i) + { + LDAPRequest *req = s->results[i - 1]; + LDAPInterface *li = req->inter; + + if (li && li->owner == m) + { + s->results.erase(s->results.begin() + i - 1); + delete req; + } + } + + s->Unlock(); + s->process_mutex.Unlock(); + } + } + + void OnNotify() anope_override + { + for (std::map::iterator it = this->LDAPServices.begin(); it != this->LDAPServices.end(); ++it) + { + LDAPService *s = it->second; + + LDAPService::query_queue results; + s->Lock(); + results.swap(s->results); + s->Unlock(); + + for (unsigned int i = 0; i < results.size(); ++i) + { + LDAPRequest *req = results[i]; + LDAPInterface *li = req->inter; + LDAPResult *r = req->result; + + if (li != NULL) + { + if (!r->getError().empty()) + { + Log(this) << "Error running LDAP query: " << r->getError(); + li->OnError(*r); + } + else + li->OnResult(*r); + } + + delete req; + } + } + } +}; + +int LDAPBind::run() +{ + berval cred; + cred.bv_val = strdup(pass.c_str()); + cred.bv_len = pass.length(); + + int i = ldap_sasl_bind_s(service->GetConnection(), who.c_str(), LDAP_SASL_SIMPLE, &cred, NULL, NULL, NULL); + + free(cred.bv_val); + + return i; +} + +int LDAPSearch::run() +{ + return ldap_search_ext_s(service->GetConnection(), base.c_str(), LDAP_SCOPE_SUBTREE, filter.c_str(), NULL, 0, NULL, NULL, &tv, 0, &message); +} + +int LDAPAdd::run() +{ + LDAPMod **mods = LDAPService::BuildMods(attributes); + int i = ldap_add_ext_s(service->GetConnection(), dn.c_str(), mods, NULL, NULL); + LDAPService::FreeMods(mods); + return i; +} + +int LDAPDel::run() +{ + return ldap_delete_ext_s(service->GetConnection(), dn.c_str(), NULL, NULL); +} + +int LDAPModify::run() +{ + LDAPMod **mods = LDAPService::BuildMods(attributes); + int i = ldap_modify_ext_s(service->GetConnection(), base.c_str(), mods, NULL, NULL); + LDAPService::FreeMods(mods); + return i; +} + +MODULE_INIT(ModuleLDAP) diff --git a/modules/extra/m_ldap_authentication.cpp b/modules/extra/m_ldap_authentication.cpp new file mode 100644 index 0000000..4fd5436 --- /dev/null +++ b/modules/extra/m_ldap_authentication.cpp @@ -0,0 +1,304 @@ +/* + * + * (C) 2011-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/ldap.h" + +static Module *me; + +static Anope::string basedn; +static Anope::string search_filter; +static Anope::string object_class; +static Anope::string email_attribute; +static Anope::string username_attribute; + +struct IdentifyInfo +{ + Reference user; + IdentifyRequest *req; + ServiceReference lprov; + bool admin_bind; + Anope::string dn; + + IdentifyInfo(User *u, IdentifyRequest *r, ServiceReference &lp) : user(u), req(r), lprov(lp), admin_bind(true) + { + req->Hold(me); + } + + ~IdentifyInfo() + { + req->Release(me); + } +}; + +class IdentifyInterface : public LDAPInterface +{ + IdentifyInfo *ii; + + public: + IdentifyInterface(Module *m, IdentifyInfo *i) : LDAPInterface(m), ii(i) { } + + ~IdentifyInterface() + { + delete ii; + } + + void OnDelete() anope_override + { + delete this; + } + + void OnResult(const LDAPResult &r) anope_override + { + if (!ii->lprov) + return; + + switch (r.type) + { + case QUERY_SEARCH: + { + if (!r.empty()) + { + try + { + const LDAPAttributes &attr = r.get(0); + ii->dn = attr.get("dn"); + Log(LOG_DEBUG) << "m_ldap_authenticationn: binding as " << ii->dn; + + ii->lprov->Bind(new IdentifyInterface(this->owner, ii), ii->dn, ii->req->GetPassword()); + ii = NULL; + } + catch (const LDAPException &ex) + { + Log(this->owner) << "Error binding after search: " << ex.GetReason(); + } + } + break; + } + case QUERY_BIND: + { + if (ii->admin_bind) + { + Anope::string sf = search_filter.replace_all_cs("%account", ii->req->GetAccount()).replace_all_cs("%object_class", object_class); + try + { + Log(LOG_DEBUG) << "m_ldap_authentication: searching for " << sf; + ii->lprov->Search(new IdentifyInterface(this->owner, ii), basedn, sf); + ii->admin_bind = false; + ii = NULL; + } + catch (const LDAPException &ex) + { + Log(this->owner) << "Unable to search for " << sf << ": " << ex.GetReason(); + } + } + else + { + NickAlias *na = NickAlias::Find(ii->req->GetAccount()); + if (na == NULL) + { + na = new NickAlias(ii->req->GetAccount(), new NickCore(ii->req->GetAccount())); + na->last_realname = ii->user ? ii->user->realname : ii->req->GetAccount(); + FOREACH_MOD(OnNickRegister, (ii->user, na, ii->req->GetPassword())); + BotInfo *NickServ = Config->GetClient("NickServ"); + if (ii->user && NickServ) + ii->user->SendMessage(NickServ, _("Your account \002%s\002 has been successfully created."), na->nick.c_str()); + } + // encrypt and store the password in the nickcore + Anope::Encrypt(ii->req->GetPassword(), na->nc->pass); + + na->nc->Extend("m_ldap_authentication_dn", ii->dn); + ii->req->Success(me); + } + break; + } + default: + break; + } + } + + void OnError(const LDAPResult &r) anope_override + { + } +}; + +class OnIdentifyInterface : public LDAPInterface +{ + Anope::string uid; + + public: + OnIdentifyInterface(Module *m, const Anope::string &i) : LDAPInterface(m), uid(i) { } + + void OnDelete() anope_override + { + delete this; + } + + void OnResult(const LDAPResult &r) anope_override + { + User *u = User::Find(uid); + + if (!u || !u->Account() || r.empty()) + return; + + try + { + const LDAPAttributes &attr = r.get(0); + Anope::string email = attr.get(email_attribute); + + if (!email.equals_ci(u->Account()->email)) + { + u->Account()->email = email; + BotInfo *NickServ = Config->GetClient("NickServ"); + if (NickServ) + u->SendMessage(NickServ, _("Your email has been updated to \002%s\002"), email.c_str()); + Log(this->owner) << "Updated email address for " << u->nick << " (" << u->Account()->display << ") to " << email; + } + } + catch (const LDAPException &ex) + { + Log(this->owner) << ex.GetReason(); + } + } + + void OnError(const LDAPResult &r) anope_override + { + Log(this->owner) << r.error; + } +}; + +class OnRegisterInterface : public LDAPInterface +{ + public: + OnRegisterInterface(Module *m) : LDAPInterface(m) { } + + void OnResult(const LDAPResult &r) anope_override + { + Log(this->owner) << "Successfully added newly created account to LDAP"; + } + + void OnError(const LDAPResult &r) anope_override + { + Log(this->owner) << "Error adding newly created account to LDAP: " << r.getError(); + } +}; + +class ModuleLDAPAuthentication : public Module +{ + ServiceReference ldap; + OnRegisterInterface orinterface; + + PrimitiveExtensibleItem dn; + + Anope::string password_attribute; + Anope::string disable_register_reason; + Anope::string disable_email_reason; + public: + ModuleLDAPAuthentication(const Anope::string &modname, const Anope::string &creator) : + Module(modname, creator, EXTRA | VENDOR), ldap("LDAPProvider", "ldap/main"), orinterface(this), + dn(this, "m_ldap_authentication_dn") + { + me = this; + } + + void Prioritize() anope_override + { + ModuleManager::SetPriority(this, PRIORITY_FIRST); + } + + void OnReload(Configuration::Conf *config) anope_override + { + Configuration::Block *conf = Config->GetModule(this); + + basedn = conf->Get("basedn"); + search_filter = conf->Get("search_filter"); + object_class = conf->Get("object_class"); + username_attribute = conf->Get("username_attribute"); + this->password_attribute = conf->Get("password_attribute"); + email_attribute = conf->Get("email_attribute"); + this->disable_register_reason = conf->Get("disable_register_reason"); + this->disable_email_reason = conf->Get("disable_email_reason"); + + if (!email_attribute.empty()) + /* Don't complain to users about how they need to update their email, we will do it for them */ + config->GetModule("nickserv")->Set("forceemail", "false"); + } + + EventReturn OnPreCommand(CommandSource &source, Command *command, std::vector ¶ms) anope_override + { + if (!this->disable_register_reason.empty()) + { + if (command->name == "nickserv/register" || command->name == "nickserv/group") + { + source.Reply(this->disable_register_reason); + return EVENT_STOP; + } + } + + if (!email_attribute.empty() && !this->disable_email_reason.empty() && command->name == "nickserv/set/email") + { + source.Reply(this->disable_email_reason); + return EVENT_STOP; + } + + return EVENT_CONTINUE; + } + + void OnCheckAuthentication(User *u, IdentifyRequest *req) anope_override + { + if (!this->ldap) + return; + + IdentifyInfo *ii = new IdentifyInfo(u, req, this->ldap); + this->ldap->BindAsAdmin(new IdentifyInterface(this, ii)); + } + + void OnNickIdentify(User *u) anope_override + { + if (email_attribute.empty() || !this->ldap) + return; + + Anope::string *d = dn.Get(u->Account()); + if (!d || d->empty()) + return; + + this->ldap->Search(new OnIdentifyInterface(this, u->GetUID()), *d, "(" + email_attribute + "=*)"); + } + + void OnNickRegister(User *, NickAlias *na, const Anope::string &pass) anope_override + { + if (!this->disable_register_reason.empty() || !this->ldap) + return; + + this->ldap->BindAsAdmin(NULL); + + LDAPMods attributes; + attributes.resize(4); + + attributes[0].name = "objectClass"; + attributes[0].values.push_back("top"); + attributes[0].values.push_back(object_class); + + attributes[1].name = username_attribute; + attributes[1].values.push_back(na->nick); + + if (!na->nc->email.empty()) + { + attributes[2].name = email_attribute; + attributes[2].values.push_back(na->nc->email); + } + + attributes[3].name = this->password_attribute; + attributes[3].values.push_back(pass); + + Anope::string new_dn = username_attribute + "=" + na->nick + "," + basedn; + this->ldap->Add(&this->orinterface, new_dn, attributes); + } +}; + +MODULE_INIT(ModuleLDAPAuthentication) diff --git a/modules/extra/m_ldap_oper.cpp b/modules/extra/m_ldap_oper.cpp new file mode 100644 index 0000000..2c4b760 --- /dev/null +++ b/modules/extra/m_ldap_oper.cpp @@ -0,0 +1,138 @@ +/* + * + * (C) 2011-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/ldap.h" + +static std::set my_opers; +static Anope::string opertype_attribute; + +class IdentifyInterface : public LDAPInterface +{ + Reference u; + + public: + IdentifyInterface(Module *m, User *user) : LDAPInterface(m), u(user) + { + } + + void OnResult(const LDAPResult &r) anope_override + { + if (!u || !u->Account()) + return; + + NickCore *nc = u->Account(); + + try + { + const LDAPAttributes &attr = r.get(0); + + const Anope::string &opertype = attr.get(opertype_attribute); + + OperType *ot = OperType::Find(opertype); + if (ot != NULL && (nc->o == NULL || ot != nc->o->ot)) + { + Oper *o = nc->o; + if (o != NULL && my_opers.count(o) > 0) + { + my_opers.erase(o); + delete o; + } + o = new Oper(u->nick, ot); + my_opers.insert(o); + nc->o = o; + Log(this->owner) << "Tied " << u->nick << " (" << nc->display << ") to opertype " << ot->GetName(); + } + } + catch (const LDAPException &ex) + { + if (nc->o != NULL) + { + if (my_opers.count(nc->o) > 0) + { + my_opers.erase(nc->o); + delete nc->o; + } + nc->o = NULL; + + Log(this->owner) << "Removed services operator from " << u->nick << " (" << nc->display << ")"; + } + } + } + + void OnError(const LDAPResult &r) anope_override + { + } + + void OnDelete() anope_override + { + delete this; + } +}; + +class LDAPOper : public Module +{ + ServiceReference ldap; + + Anope::string binddn; + Anope::string password; + Anope::string basedn; + Anope::string filter; + public: + LDAPOper(const Anope::string &modname, const Anope::string &creator) : + Module(modname, creator, EXTRA | VENDOR), ldap("LDAPProvider", "ldap/main") + { + + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *config = Config->GetModule(this); + + this->binddn = config->Get("binddn"); + this->password = config->Get("password"); + this->basedn = config->Get("basedn"); + this->filter = config->Get("filter"); + opertype_attribute = config->Get("opertype_attribute"); + + for (std::set::iterator it = my_opers.begin(), it_end = my_opers.end(); it != it_end; ++it) + delete *it; + my_opers.clear(); + } + + void OnNickIdentify(User *u) anope_override + { + try + { + if (!this->ldap) + throw LDAPException("No LDAP interface. Is m_ldap loaded and configured correctly?"); + else if (this->basedn.empty() || this->filter.empty() || opertype_attribute.empty()) + throw LDAPException("Could not search LDAP for opertype settings, invalid configuration."); + + if (!this->binddn.empty()) + this->ldap->Bind(NULL, this->binddn.replace_all_cs("%a", u->Account()->display), this->password.c_str()); + this->ldap->Search(new IdentifyInterface(this, u), this->basedn, this->filter.replace_all_cs("%a", u->Account()->display)); + } + catch (const LDAPException &ex) + { + Log() << ex.GetReason(); + } + } + + void OnDelCore(NickCore *nc) anope_override + { + if (nc->o != NULL && my_opers.count(nc->o) > 0) + { + my_opers.erase(nc->o); + delete nc->o; + nc->o = NULL; + } + } +}; + +MODULE_INIT(LDAPOper) diff --git a/modules/extra/m_mysql.cpp b/modules/extra/m_mysql.cpp new file mode 100644 index 0000000..c94a443 --- /dev/null +++ b/modules/extra/m_mysql.cpp @@ -0,0 +1,555 @@ +/* + * + * (C) 2010-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +/* RequiredLibraries: mysqlclient */ +/* RequiredWindowsLibraries: libmysql */ + +#include "module.h" +#include "modules/sql.h" +#define NO_CLIENT_LONG_LONG +#ifdef WIN32 +# include +#else +# include +#endif + +using namespace SQL; + +/** Non blocking threaded MySQL API, based loosely from InspIRCd's m_mysql.cpp + * + * This module spawns a single thread that is used to execute blocking MySQL queries. + * When a module requests a query to be executed it is added to a list for the thread + * (which never stops looping and sleeping) to pick up and execute, the result of which + * is inserted in to another queue to be picked up by the main thread. The main thread + * uses Pipe to become notified through the socket engine when there are results waiting + * to be sent back to the modules requesting the query + */ + +class MySQLService; + +/** A query request + */ +struct QueryRequest +{ + /* The connection to the database */ + MySQLService *service; + /* The interface to use once we have the result to send the data back */ + Interface *sqlinterface; + /* The actual query */ + Query query; + + QueryRequest(MySQLService *s, Interface *i, const Query &q) : service(s), sqlinterface(i), query(q) { } +}; + +/** A query result */ +struct QueryResult +{ + /* The interface to send the data back on */ + Interface *sqlinterface; + /* The result */ + Result result; + + QueryResult(Interface *i, Result &r) : sqlinterface(i), result(r) { } +}; + +/** A MySQL result + */ +class MySQLResult : public Result +{ + MYSQL_RES *res; + + public: + MySQLResult(unsigned int i, const Query &q, const Anope::string &fq, MYSQL_RES *r) : Result(i, q, fq), res(r) + { + unsigned num_fields = res ? mysql_num_fields(res) : 0; + + /* It is not thread safe to log anything here using Log(this->owner) now :( */ + + if (!num_fields) + return; + + for (MYSQL_ROW row; (row = mysql_fetch_row(res));) + { + MYSQL_FIELD *fields = mysql_fetch_fields(res); + + if (fields) + { + std::map items; + + for (unsigned field_count = 0; field_count < num_fields; ++field_count) + { + Anope::string column = (fields[field_count].name ? fields[field_count].name : ""); + Anope::string data = (row[field_count] ? row[field_count] : ""); + + items[column] = data; + } + + this->entries.push_back(items); + } + } + } + + MySQLResult(const Query &q, const Anope::string &fq, const Anope::string &err) : Result(0, q, fq, err), res(NULL) + { + } + + ~MySQLResult() + { + if (this->res) + mysql_free_result(this->res); + } +}; + +/** A MySQL connection, there can be multiple + */ +class MySQLService : public Provider +{ + std::map > active_schema; + + Anope::string database; + Anope::string server; + Anope::string user; + Anope::string password; + int port; + + MYSQL *sql; + + /** Escape a query. + * Note the mutex must be held! + */ + Anope::string Escape(const Anope::string &query); + + public: + /* Locked by the SQL thread when a query is pending on this database, + * prevents us from deleting a connection while a query is executing + * in the thread + */ + Mutex Lock; + + MySQLService(Module *o, const Anope::string &n, const Anope::string &d, const Anope::string &s, const Anope::string &u, const Anope::string &p, int po); + + ~MySQLService(); + + void Run(Interface *i, const Query &query) anope_override; + + Result RunQuery(const Query &query) anope_override; + + std::vector CreateTable(const Anope::string &table, const Data &data) anope_override; + + Query BuildInsert(const Anope::string &table, unsigned int id, Data &data) anope_override; + + Query GetTables(const Anope::string &prefix) anope_override; + + void Connect(); + + bool CheckConnection(); + + Anope::string BuildQuery(const Query &q); + + Anope::string FromUnixtime(time_t); +}; + +/** The SQL thread used to execute queries + */ +class DispatcherThread : public Thread, public Condition +{ + public: + DispatcherThread() : Thread() { } + + void Run() anope_override; +}; + +class ModuleSQL; +static ModuleSQL *me; +class ModuleSQL : public Module, public Pipe +{ + /* SQL connections */ + std::map MySQLServices; + public: + /* Pending query requests */ + std::deque QueryRequests; + /* Pending finished requests with results */ + std::deque FinishedRequests; + /* The thread used to execute queries */ + DispatcherThread *DThread; + + ModuleSQL(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR) + { + me = this; + + + DThread = new DispatcherThread(); + DThread->Start(); + } + + ~ModuleSQL() + { + for (std::map::iterator it = this->MySQLServices.begin(); it != this->MySQLServices.end(); ++it) + delete it->second; + MySQLServices.clear(); + + DThread->SetExitState(); + DThread->Wakeup(); + DThread->Join(); + delete DThread; + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *config = conf->GetModule(this); + + for (std::map::iterator it = this->MySQLServices.begin(); it != this->MySQLServices.end();) + { + const Anope::string &cname = it->first; + MySQLService *s = it->second; + int i; + + ++it; + + for (i = 0; i < config->CountBlock("mysql"); ++i) + if (config->GetBlock("mysql", i)->Get("name", "mysql/main") == cname) + break; + + if (i == config->CountBlock("mysql")) + { + Log(LOG_NORMAL, "mysql") << "MySQL: Removing server connection " << cname; + + delete s; + this->MySQLServices.erase(cname); + } + } + + for (int i = 0; i < config->CountBlock("mysql"); ++i) + { + Configuration::Block *block = config->GetBlock("mysql", i); + const Anope::string &connname = block->Get("name", "mysql/main"); + + if (this->MySQLServices.find(connname) == this->MySQLServices.end()) + { + const Anope::string &database = block->Get("database", "anope"); + const Anope::string &server = block->Get("server", "127.0.0.1"); + const Anope::string &user = block->Get("username", "anope"); + const Anope::string &password = block->Get("password"); + int port = block->Get("port", "3306"); + + try + { + MySQLService *ss = new MySQLService(this, connname, database, server, user, password, port); + this->MySQLServices.insert(std::make_pair(connname, ss)); + + Log(LOG_NORMAL, "mysql") << "MySQL: Successfully connected to server " << connname << " (" << server << ")"; + } + catch (const SQL::Exception &ex) + { + Log(LOG_NORMAL, "mysql") << "MySQL: " << ex.GetReason(); + } + } + } + } + + void OnModuleUnload(User *, Module *m) anope_override + { + this->DThread->Lock(); + + for (unsigned i = this->QueryRequests.size(); i > 0; --i) + { + QueryRequest &r = this->QueryRequests[i - 1]; + + if (r.sqlinterface && r.sqlinterface->owner == m) + { + if (i == 1) + { + r.service->Lock.Lock(); + r.service->Lock.Unlock(); + } + + this->QueryRequests.erase(this->QueryRequests.begin() + i - 1); + } + } + + this->DThread->Unlock(); + + this->OnNotify(); + } + + void OnNotify() anope_override + { + this->DThread->Lock(); + std::deque finishedRequests = this->FinishedRequests; + this->FinishedRequests.clear(); + this->DThread->Unlock(); + + for (std::deque::const_iterator it = finishedRequests.begin(), it_end = finishedRequests.end(); it != it_end; ++it) + { + const QueryResult &qr = *it; + + if (!qr.sqlinterface) + throw SQL::Exception("NULL qr.sqlinterface in MySQLPipe::OnNotify() ?"); + + if (qr.result.GetError().empty()) + qr.sqlinterface->OnResult(qr.result); + else + qr.sqlinterface->OnError(qr.result); + } + } +}; + +MySQLService::MySQLService(Module *o, const Anope::string &n, const Anope::string &d, const Anope::string &s, const Anope::string &u, const Anope::string &p, int po) +: Provider(o, n), database(d), server(s), user(u), password(p), port(po), sql(NULL) +{ + Connect(); +} + +MySQLService::~MySQLService() +{ + me->DThread->Lock(); + this->Lock.Lock(); + mysql_close(this->sql); + this->sql = NULL; + + for (unsigned i = me->QueryRequests.size(); i > 0; --i) + { + QueryRequest &r = me->QueryRequests[i - 1]; + + if (r.service == this) + { + if (r.sqlinterface) + r.sqlinterface->OnError(Result(0, r.query, "SQL Interface is going away")); + me->QueryRequests.erase(me->QueryRequests.begin() + i - 1); + } + } + this->Lock.Unlock(); + me->DThread->Unlock(); +} + +void MySQLService::Run(Interface *i, const Query &query) +{ + me->DThread->Lock(); + me->QueryRequests.push_back(QueryRequest(this, i, query)); + me->DThread->Unlock(); + me->DThread->Wakeup(); +} + +Result MySQLService::RunQuery(const Query &query) +{ + this->Lock.Lock(); + + Anope::string real_query = this->BuildQuery(query); + + if (this->CheckConnection() && !mysql_real_query(this->sql, real_query.c_str(), real_query.length())) + { + MYSQL_RES *res = mysql_store_result(this->sql); + unsigned int id = mysql_insert_id(this->sql); + + /* because we enabled CLIENT_MULTI_RESULTS in our options + * a multiple statement or a procedure call can return + * multiple result sets. + * we must process them all before the next query. + */ + + while (!mysql_next_result(this->sql)) + mysql_free_result(mysql_store_result(this->sql)); + + this->Lock.Unlock(); + return MySQLResult(id, query, real_query, res); + } + else + { + Anope::string error = mysql_error(this->sql); + this->Lock.Unlock(); + return MySQLResult(query, real_query, error); + } +} + +std::vector MySQLService::CreateTable(const Anope::string &table, const Data &data) +{ + std::vector queries; + std::set &known_cols = this->active_schema[table]; + + if (known_cols.empty()) + { + Log(LOG_DEBUG) << "m_mysql: Fetching columns for " << table; + + Result columns = this->RunQuery("SHOW COLUMNS FROM `" + table + "`"); + for (int i = 0; i < columns.Rows(); ++i) + { + const Anope::string &column = columns.Get(i, "Field"); + + Log(LOG_DEBUG) << "m_mysql: Column #" << i << " for " << table << ": " << column; + known_cols.insert(column); + } + } + + if (known_cols.empty()) + { + Anope::string query_text = "CREATE TABLE `" + table + "` (`id` int(10) unsigned NOT NULL AUTO_INCREMENT," + " `timestamp` timestamp NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP"; + for (Data::Map::const_iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + { + known_cols.insert(it->first); + + query_text += ", `" + it->first + "` "; + if (data.GetType(it->first) == Serialize::Data::DT_INT) + query_text += "int(11)"; + else + query_text += "text"; + } + query_text += ", PRIMARY KEY (`id`), KEY `timestamp_idx` (`timestamp`))"; + queries.push_back(query_text); + } + else + for (Data::Map::const_iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + { + if (known_cols.count(it->first) > 0) + continue; + + known_cols.insert(it->first); + + Anope::string query_text = "ALTER TABLE `" + table + "` ADD `" + it->first + "` "; + if (data.GetType(it->first) == Serialize::Data::DT_INT) + query_text += "int(11)"; + else + query_text += "text"; + + queries.push_back(query_text); + } + + return queries; +} + +Query MySQLService::BuildInsert(const Anope::string &table, unsigned int id, Data &data) +{ + /* Empty columns not present in the data set */ + const std::set &known_cols = this->active_schema[table]; + for (std::set::iterator it = known_cols.begin(), it_end = known_cols.end(); it != it_end; ++it) + if (*it != "id" && *it != "timestamp" && data.data.count(*it) == 0) + data[*it] << ""; + + Anope::string query_text = "INSERT INTO `" + table + "` (`id`"; + for (Data::Map::const_iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + query_text += ",`" + it->first + "`"; + query_text += ") VALUES (" + stringify(id); + for (Data::Map::const_iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + query_text += ",@" + it->first + "@"; + query_text += ") ON DUPLICATE KEY UPDATE "; + for (Data::Map::const_iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + query_text += "`" + it->first + "`=VALUES(`" + it->first + "`),"; + query_text.erase(query_text.end() - 1); + + Query query(query_text); + for (Data::Map::const_iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + { + Anope::string buf; + *it->second >> buf; + + bool escape = true; + if (buf.empty()) + { + buf = "NULL"; + escape = false; + } + + query.SetValue(it->first, buf, escape); + } + + return query; +} + +Query MySQLService::GetTables(const Anope::string &prefix) +{ + return Query("SHOW TABLES LIKE '" + prefix + "%';"); +} + +void MySQLService::Connect() +{ + this->sql = mysql_init(this->sql); + + const unsigned int timeout = 1; + mysql_options(this->sql, MYSQL_OPT_CONNECT_TIMEOUT, reinterpret_cast(&timeout)); + + bool connect = mysql_real_connect(this->sql, this->server.c_str(), this->user.c_str(), this->password.c_str(), this->database.c_str(), this->port, NULL, CLIENT_MULTI_RESULTS); + + if (!connect) + throw SQL::Exception("Unable to connect to MySQL service " + this->name + ": " + mysql_error(this->sql)); + + Log(LOG_DEBUG) << "Successfully connected to MySQL service " << this->name << " at " << this->server << ":" << this->port; +} + + +bool MySQLService::CheckConnection() +{ + if (!this->sql || mysql_ping(this->sql)) + { + try + { + this->Connect(); + } + catch (const SQL::Exception &) + { + return false; + } + } + + return true; +} + +Anope::string MySQLService::Escape(const Anope::string &query) +{ + std::vector buffer(query.length() * 2 + 1); + mysql_real_escape_string(this->sql, &buffer[0], query.c_str(), query.length()); + return &buffer[0]; +} + +Anope::string MySQLService::BuildQuery(const Query &q) +{ + Anope::string real_query = q.query; + + for (std::map::const_iterator it = q.parameters.begin(), it_end = q.parameters.end(); it != it_end; ++it) + real_query = real_query.replace_all_cs("@" + it->first + "@", (it->second.escape ? ("'" + this->Escape(it->second.data) + "'") : it->second.data)); + + return real_query; +} + +Anope::string MySQLService::FromUnixtime(time_t t) +{ + return "FROM_UNIXTIME(" + stringify(t) + ")"; +} + +void DispatcherThread::Run() +{ + this->Lock(); + + while (!this->GetExitState()) + { + if (!me->QueryRequests.empty()) + { + QueryRequest &r = me->QueryRequests.front(); + this->Unlock(); + + Result sresult = r.service->RunQuery(r.query); + + this->Lock(); + if (!me->QueryRequests.empty() && me->QueryRequests.front().query == r.query) + { + if (r.sqlinterface) + me->FinishedRequests.push_back(QueryResult(r.sqlinterface, sresult)); + me->QueryRequests.pop_front(); + } + } + else + { + if (!me->FinishedRequests.empty()) + me->Notify(); + this->Wait(); + } + } + + this->Unlock(); +} + +MODULE_INIT(ModuleSQL) diff --git a/modules/extra/m_regex_pcre.cpp b/modules/extra/m_regex_pcre.cpp new file mode 100644 index 0000000..e52c164 --- /dev/null +++ b/modules/extra/m_regex_pcre.cpp @@ -0,0 +1,83 @@ +/* + * + * (C) 2012-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +/* RequiredLibraries: pcre */ +/* RequiredWindowsLibraries: libpcre */ + +#include "module.h" +#include + +class PCRERegex : public Regex +{ + pcre *regex; + + public: + PCRERegex(const Anope::string &expr) : Regex(expr) + { + const char *error; + int erroffset; + this->regex = pcre_compile(expr.c_str(), PCRE_CASELESS, &error, &erroffset, NULL); + if (!this->regex) + throw RegexException("Error in regex " + expr + " at offset " + stringify(erroffset) + ": " + error); + } + + ~PCRERegex() + { + pcre_free(this->regex); + } + + bool Matches(const Anope::string &str) + { + return pcre_exec(this->regex, NULL, str.c_str(), str.length(), 0, 0, NULL, 0) > -1; + } +}; + +class PCRERegexProvider : public RegexProvider +{ + public: + PCRERegexProvider(Module *creator) : RegexProvider(creator, "regex/pcre") { } + + Regex *Compile(const Anope::string &expression) anope_override + { + return new PCRERegex(expression); + } +}; + +class ModuleRegexPCRE : public Module +{ + PCRERegexProvider pcre_regex_provider; + + public: + ModuleRegexPCRE(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR), + pcre_regex_provider(this) + { + this->SetPermanent(true); + } + + ~ModuleRegexPCRE() + { + for (std::list::iterator it = XLineManager::XLineManagers.begin(); it != XLineManager::XLineManagers.end(); ++it) + { + XLineManager *xlm = *it; + const std::vector &xlines = xlm->GetList(); + + for (unsigned int i = 0; i < xlines.size(); ++i) + { + XLine *x = xlines[i]; + + if (x->regex && dynamic_cast(x->regex)) + { + delete x->regex; + x->regex = NULL; + } + } + } + } +}; + +MODULE_INIT(ModuleRegexPCRE) diff --git a/modules/extra/m_regex_pcre2.cpp b/modules/extra/m_regex_pcre2.cpp new file mode 100644 index 0000000..1351d81 --- /dev/null +++ b/modules/extra/m_regex_pcre2.cpp @@ -0,0 +1,93 @@ +/* + * + * (C) 2012-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +/* RequiredLibraries: pcre2-8 */ +/* RequiredWindowsLibraries: libpcre2-8 */ + +#include "module.h" + +#define PCRE2_CODE_UNIT_WIDTH 8 +#include + +class PCRERegex : public Regex +{ + pcre2_code *regex; + + public: + PCRERegex(const Anope::string &expr) : Regex(expr) + { + int errcode; + PCRE2_SIZE erroffset; + this->regex = pcre2_compile(reinterpret_cast(expr.c_str()), expr.length(), PCRE2_CASELESS, &errcode, &erroffset, NULL); + + if (!this->regex) + { + PCRE2_UCHAR error[128]; + pcre2_get_error_message(errcode, error, sizeof error); + throw RegexException("Error in regex " + expr + " at offset " + stringify(erroffset) + ": " + reinterpret_cast(error)); + } + } + + ~PCRERegex() + { + pcre2_code_free(this->regex); + } + + bool Matches(const Anope::string &str) + { + pcre2_match_data *unused = pcre2_match_data_create_from_pattern(this->regex, NULL); + int result = pcre2_match(regex, reinterpret_cast(str.c_str()), str.length(), 0, 0, unused, NULL); + pcre2_match_data_free(unused); + return result >= 0; + } +}; + +class PCRERegexProvider : public RegexProvider +{ + public: + PCRERegexProvider(Module *creator) : RegexProvider(creator, "regex/pcre") { } + + Regex *Compile(const Anope::string &expression) anope_override + { + return new PCRERegex(expression); + } +}; + +class ModuleRegexPCRE : public Module +{ + PCRERegexProvider pcre_regex_provider; + + public: + ModuleRegexPCRE(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR), + pcre_regex_provider(this) + { + this->SetPermanent(true); + } + + ~ModuleRegexPCRE() + { + for (std::list::iterator it = XLineManager::XLineManagers.begin(); it != XLineManager::XLineManagers.end(); ++it) + { + XLineManager *xlm = *it; + const std::vector &xlines = xlm->GetList(); + + for (unsigned int i = 0; i < xlines.size(); ++i) + { + XLine *x = xlines[i]; + + if (x->regex && dynamic_cast(x->regex)) + { + delete x->regex; + x->regex = NULL; + } + } + } + } +}; + +MODULE_INIT(ModuleRegexPCRE) diff --git a/modules/extra/m_regex_posix.cpp b/modules/extra/m_regex_posix.cpp new file mode 100644 index 0000000..e955f67 --- /dev/null +++ b/modules/extra/m_regex_posix.cpp @@ -0,0 +1,84 @@ +/* + * + * (C) 2012-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include +#include + +class POSIXRegex : public Regex +{ + regex_t regbuf; + + public: + POSIXRegex(const Anope::string &expr) : Regex(expr) + { + int err = regcomp(&this->regbuf, expr.c_str(), REG_EXTENDED | REG_NOSUB | REG_ICASE); + if (err) + { + char buf[BUFSIZE]; + regerror(err, &this->regbuf, buf, sizeof(buf)); + regfree(&this->regbuf); + throw RegexException("Error in regex " + expr + ": " + buf); + } + } + + ~POSIXRegex() + { + regfree(&this->regbuf); + } + + bool Matches(const Anope::string &str) + { + return regexec(&this->regbuf, str.c_str(), 0, NULL, 0) == 0; + } +}; + +class POSIXRegexProvider : public RegexProvider +{ + public: + POSIXRegexProvider(Module *creator) : RegexProvider(creator, "regex/posix") { } + + Regex *Compile(const Anope::string &expression) anope_override + { + return new POSIXRegex(expression); + } +}; + +class ModuleRegexPOSIX : public Module +{ + POSIXRegexProvider posix_regex_provider; + + public: + ModuleRegexPOSIX(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR), + posix_regex_provider(this) + { + this->SetPermanent(true); + } + + ~ModuleRegexPOSIX() + { + for (std::list::iterator it = XLineManager::XLineManagers.begin(); it != XLineManager::XLineManagers.end(); ++it) + { + XLineManager *xlm = *it; + const std::vector &xlines = xlm->GetList(); + + for (unsigned int i = 0; i < xlines.size(); ++i) + { + XLine *x = xlines[i]; + + if (x->regex && dynamic_cast(x->regex)) + { + delete x->regex; + x->regex = NULL; + } + } + } + } +}; + +MODULE_INIT(ModuleRegexPOSIX) diff --git a/modules/extra/m_regex_tre.cpp b/modules/extra/m_regex_tre.cpp new file mode 100644 index 0000000..1df73db --- /dev/null +++ b/modules/extra/m_regex_tre.cpp @@ -0,0 +1,85 @@ +/* + * + * (C) 2012-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +/* RequiredLibraries: tre */ + +#include "module.h" +#include + +class TRERegex : public Regex +{ + regex_t regbuf; + + public: + TRERegex(const Anope::string &expr) : Regex(expr) + { + int err = regcomp(&this->regbuf, expr.c_str(), REG_EXTENDED | REG_NOSUB); + if (err) + { + char buf[BUFSIZE]; + regerror(err, &this->regbuf, buf, sizeof(buf)); + regfree(&this->regbuf); + throw RegexException("Error in regex " + expr + ": " + buf); + } + } + + ~TRERegex() + { + regfree(&this->regbuf); + } + + bool Matches(const Anope::string &str) + { + return regexec(&this->regbuf, str.c_str(), 0, NULL, 0) == 0; + } +}; + +class TRERegexProvider : public RegexProvider +{ + public: + TRERegexProvider(Module *creator) : RegexProvider(creator, "regex/tre") { } + + Regex *Compile(const Anope::string &expression) anope_override + { + return new TRERegex(expression); + } +}; + +class ModuleRegexTRE : public Module +{ + TRERegexProvider tre_regex_provider; + + public: + ModuleRegexTRE(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR), + tre_regex_provider(this) + { + this->SetPermanent(true); + } + + ~ModuleRegexTRE() + { + for (std::list::iterator it = XLineManager::XLineManagers.begin(); it != XLineManager::XLineManagers.end(); ++it) + { + XLineManager *xlm = *it; + const std::vector &xlines = xlm->GetList(); + + for (unsigned int i = 0; i < xlines.size(); ++i) + { + XLine *x = xlines[i]; + + if (x->regex && dynamic_cast(x->regex)) + { + delete x->regex; + x->regex = NULL; + } + } + } + } +}; + +MODULE_INIT(ModuleRegexTRE) diff --git a/modules/extra/m_sql_authentication.cpp b/modules/extra/m_sql_authentication.cpp new file mode 100644 index 0000000..a19931b --- /dev/null +++ b/modules/extra/m_sql_authentication.cpp @@ -0,0 +1,148 @@ +/* + * + * (C) 2012-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/sql.h" + +static Module *me; + +class SQLAuthenticationResult : public SQL::Interface +{ + Reference user; + IdentifyRequest *req; + + public: + SQLAuthenticationResult(User *u, IdentifyRequest *r) : SQL::Interface(me), user(u), req(r) + { + req->Hold(me); + } + + ~SQLAuthenticationResult() + { + req->Release(me); + } + + void OnResult(const SQL::Result &r) anope_override + { + if (r.Rows() == 0) + { + Log(LOG_DEBUG) << "m_sql_authentication: Unsuccessful authentication for " << req->GetAccount(); + delete this; + return; + } + + Log(LOG_DEBUG) << "m_sql_authentication: Successful authentication for " << req->GetAccount(); + + Anope::string email; + try + { + email = r.Get(0, "email"); + } + catch (const SQL::Exception &) { } + + NickAlias *na = NickAlias::Find(req->GetAccount()); + BotInfo *NickServ = Config->GetClient("NickServ"); + if (na == NULL) + { + na = new NickAlias(req->GetAccount(), new NickCore(req->GetAccount())); + FOREACH_MOD(OnNickRegister, (user, na, "")); + if (user && NickServ) + user->SendMessage(NickServ, _("Your account \002%s\002 has been successfully created."), na->nick.c_str()); + } + + if (!email.empty() && email != na->nc->email) + { + na->nc->email = email; + if (user && NickServ) + user->SendMessage(NickServ, _("Your email has been updated to \002%s\002."), email.c_str()); + } + + req->Success(me); + delete this; + } + + void OnError(const SQL::Result &r) anope_override + { + Log(this->owner) << "m_sql_authentication: Error executing query " << r.GetQuery().query << ": " << r.GetError(); + delete this; + } +}; + +class ModuleSQLAuthentication : public Module +{ + Anope::string engine; + Anope::string query; + Anope::string disable_reason, disable_email_reason; + + ServiceReference SQL; + + public: + ModuleSQLAuthentication(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR) + { + me = this; + + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *config = conf->GetModule(this); + this->engine = config->Get("engine"); + this->query = config->Get("query"); + this->disable_reason = config->Get("disable_reason"); + this->disable_email_reason = config->Get("disable_email_reason"); + + this->SQL = ServiceReference("SQL::Provider", this->engine); + } + + EventReturn OnPreCommand(CommandSource &source, Command *command, std::vector ¶ms) anope_override + { + if (!this->disable_reason.empty() && (command->name == "nickserv/register" || command->name == "nickserv/group")) + { + source.Reply(this->disable_reason); + return EVENT_STOP; + } + + if (!this->disable_email_reason.empty() && command->name == "nickserv/set/email") + { + source.Reply(this->disable_email_reason); + return EVENT_STOP; + } + + return EVENT_CONTINUE; + } + + void OnCheckAuthentication(User *u, IdentifyRequest *req) anope_override + { + if (!this->SQL) + { + Log(this) << "Unable to find SQL engine"; + return; + } + + SQL::Query q(this->query); + q.SetValue("a", req->GetAccount()); + q.SetValue("p", req->GetPassword()); + if (u) + { + q.SetValue("n", u->nick); + q.SetValue("i", u->ip.addr()); + } + else + { + q.SetValue("n", ""); + q.SetValue("i", ""); + } + + + this->SQL->Run(new SQLAuthenticationResult(u, req), q); + + Log(LOG_DEBUG) << "m_sql_authentication: Checking authentication for " << req->GetAccount(); + } +}; + +MODULE_INIT(ModuleSQLAuthentication) diff --git a/modules/extra/m_sql_log.cpp b/modules/extra/m_sql_log.cpp new file mode 100644 index 0000000..15d071e --- /dev/null +++ b/modules/extra/m_sql_log.cpp @@ -0,0 +1,108 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/sql.h" + +class SQLLog : public Module +{ + std::set inited; + Anope::string table; + + public: + SQLLog(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR | EXTRA) + { + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *config = conf->GetModule(this); + this->table = config->Get("table", "logs"); + } + + void OnLogMessage(LogInfo *li, const Log *l, const Anope::string &msg) anope_override + { + Anope::string ref_name; + ServiceReference SQL; + + for (unsigned i = 0; i < li->targets.size(); ++i) + { + const Anope::string &target = li->targets[i]; + size_t sz = target.find("sql_log:"); + if (!sz) + { + ref_name = target.substr(8); + SQL = ServiceReference("SQL::Provider", ref_name); + break; + } + } + + if (!SQL) + return; + + if (!inited.count(ref_name)) + { + inited.insert(ref_name); + + SQL::Query create("CREATE TABLE IF NOT EXISTS `" + table + "` (" + "`date` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP," + "`type` varchar(64) NOT NULL," + "`user` varchar(64) NOT NULL," + "`acc` varchar(64) NOT NULL," + "`command` varchar(64) NOT NULL," + "`channel` varchar(64) NOT NULL," + "`msg` text NOT NULL" + ")"); + + SQL->Run(NULL, create); + } + + SQL::Query insert("INSERT INTO `" + table + "` (`type`,`user`,`acc`,`command`,`channel`,`msg`)" + "VALUES (@type@, @user@, @acc@, @command@, @channel@, @msg@)"); + + switch (l->type) + { + case LOG_ADMIN: + insert.SetValue("type", "ADMIN"); + break; + case LOG_OVERRIDE: + insert.SetValue("type", "OVERRIDE"); + break; + case LOG_COMMAND: + insert.SetValue("type", "COMMAND"); + break; + case LOG_SERVER: + insert.SetValue("type", "SERVER"); + break; + case LOG_CHANNEL: + insert.SetValue("type", "CHANNEL"); + break; + case LOG_USER: + insert.SetValue("type", "USER"); + break; + case LOG_MODULE: + insert.SetValue("type", "MODULE"); + break; + case LOG_NORMAL: + insert.SetValue("type", "NORMAL"); + break; + default: + return; + } + + insert.SetValue("user", l->u ? l->u->nick : ""); + insert.SetValue("acc", l->nc ? l->nc->display : ""); + insert.SetValue("command", l->c ? l->c->name : ""); + insert.SetValue("channel", l->ci ? l->ci->name : ""); + insert.SetValue("msg", msg); + + SQL->Run(NULL, insert); + } +}; + +MODULE_INIT(SQLLog) diff --git a/modules/extra/m_sql_oper.cpp b/modules/extra/m_sql_oper.cpp new file mode 100644 index 0000000..925cd21 --- /dev/null +++ b/modules/extra/m_sql_oper.cpp @@ -0,0 +1,180 @@ +/* + * + * (C) 2012-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/sql.h" + +struct SQLOper : Oper +{ + SQLOper(const Anope::string &n, OperType *o) : Oper(n, o) { } +}; + +class SQLOperResult : public SQL::Interface +{ + Reference user; + + struct SQLOperResultDeleter + { + SQLOperResult *res; + SQLOperResultDeleter(SQLOperResult *r) : res(r) { } + ~SQLOperResultDeleter() { delete res; } + }; + + void Deoper() + { + if (user->Account() && user->Account()->o && dynamic_cast(user->Account()->o)) + { + delete user->Account()->o; + user->Account()->o = NULL; + + Log(this->owner) << "m_sql_oper: Removed services operator from " << user->nick << " (" << user->Account()->display << ")"; + + BotInfo *OperServ = Config->GetClient("OperServ"); + user->RemoveMode(OperServ, "OPER"); // Probably not set, just incase + } + } + + public: + SQLOperResult(Module *m, User *u) : SQL::Interface(m), user(u) { } + + void OnResult(const SQL::Result &r) anope_override + { + SQLOperResultDeleter d(this); + + if (!user || !user->Account()) + return; + + if (r.Rows() == 0) + { + Log(LOG_DEBUG) << "m_sql_oper: Got 0 rows for " << user->nick; + Deoper(); + return; + } + + Anope::string opertype; + try + { + opertype = r.Get(0, "opertype"); + } + catch (const SQL::Exception &) + { + Log(this->owner) << "Expected column named \"opertype\" but one was not found"; + return; + } + + Log(LOG_DEBUG) << "m_sql_oper: Got result for " << user->nick << ", opertype " << opertype; + + Anope::string modes; + try + { + modes = r.Get(0, "modes"); + } + catch (const SQL::Exception &) + { + // Common case here is an exception, but this probably doesn't get this far often + } + + BotInfo *OperServ = Config->GetClient("OperServ"); + if (opertype.empty()) + { + Deoper(); + return; + } + + OperType *ot = OperType::Find(opertype); + if (ot == NULL) + { + Log(this->owner) << "m_sql_oper: Oper " << user->nick << " has type " << opertype << ", but this opertype does not exist?"; + return; + } + + if (user->Account()->o && !dynamic_cast(user->Account()->o)) + { + Log(this->owner) << "Oper " << user->Account()->display << " has type " << opertype << ", but is already configured as an oper of type " << user->Account()->o->ot->GetName(); + return; + } + + if (!user->Account()->o || user->Account()->o->ot != ot) + { + Log(this->owner) << "m_sql_oper: Tieing oper " << user->nick << " to type " << opertype; + + delete user->Account()->o; + user->Account()->o = new SQLOper(user->Account()->display, ot); + } + + if (!user->HasMode("OPER")) + { + IRCD->SendOper(user); + + if (!modes.empty()) + user->SetModes(OperServ, "%s", modes.c_str()); + } + } + + void OnError(const SQL::Result &r) anope_override + { + SQLOperResultDeleter d(this); + Log(this->owner) << "m_sql_oper: Error executing query " << r.GetQuery().query << ": " << r.GetError(); + } +}; + +class ModuleSQLOper : public Module +{ + Anope::string engine; + Anope::string query; + + ServiceReference SQL; + + public: + ModuleSQLOper(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR) + { + } + + ~ModuleSQLOper() + { + for (nickcore_map::const_iterator it = NickCoreList->begin(), it_end = NickCoreList->end(); it != it_end; ++it) + { + NickCore *nc = it->second; + + if (nc->o && dynamic_cast(nc->o)) + { + delete nc->o; + nc->o = NULL; + } + } + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *config = conf->GetModule(this); + + this->engine = config->Get("engine"); + this->query = config->Get("query"); + + this->SQL = ServiceReference("SQL::Provider", this->engine); + } + + void OnNickIdentify(User *u) anope_override + { + if (!this->SQL) + { + Log() << "Unable to find SQL engine"; + return; + } + + SQL::Query q(this->query); + q.SetValue("a", u->Account()->display); + q.SetValue("i", u->ip.addr()); + + this->SQL->Run(new SQLOperResult(this, u), q); + + Log(LOG_DEBUG) << "m_sql_oper: Checking authentication for " << u->Account()->display; + } +}; + +MODULE_INIT(ModuleSQLOper) diff --git a/modules/extra/m_sqlite.cpp b/modules/extra/m_sqlite.cpp new file mode 100644 index 0000000..5e28d5a --- /dev/null +++ b/modules/extra/m_sqlite.cpp @@ -0,0 +1,334 @@ +/* + * + * (C) 2011-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +/* RequiredLibraries: sqlite3 */ +/* RequiredWindowsLibraries: sqlite3 */ + +#include "module.h" +#include "modules/sql.h" +#include + +using namespace SQL; + +/* SQLite3 API, based from InspIRCd */ + +/** A SQLite result + */ +class SQLiteResult : public Result +{ + public: + SQLiteResult(unsigned int i, const Query &q, const Anope::string &fq) : Result(i, q, fq) + { + } + + SQLiteResult(const Query &q, const Anope::string &fq, const Anope::string &err) : Result(0, q, fq, err) + { + } + + void AddRow(const std::map &data) + { + this->entries.push_back(data); + } +}; + +/** A SQLite database, there can be multiple + */ +class SQLiteService : public Provider +{ + std::map > active_schema; + + Anope::string database; + + sqlite3 *sql; + + Anope::string Escape(const Anope::string &query); + + public: + SQLiteService(Module *o, const Anope::string &n, const Anope::string &d); + + ~SQLiteService(); + + void Run(Interface *i, const Query &query) anope_override; + + Result RunQuery(const Query &query); + + std::vector CreateTable(const Anope::string &table, const Data &data) anope_override; + + Query BuildInsert(const Anope::string &table, unsigned int id, Data &data); + + Query GetTables(const Anope::string &prefix); + + Anope::string BuildQuery(const Query &q); + + Anope::string FromUnixtime(time_t); +}; + +class ModuleSQLite : public Module +{ + /* SQL connections */ + std::map SQLiteServices; + public: + ModuleSQLite(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR) + { + } + + ~ModuleSQLite() + { + for (std::map::iterator it = this->SQLiteServices.begin(); it != this->SQLiteServices.end(); ++it) + delete it->second; + SQLiteServices.clear(); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *config = conf->GetModule(this); + + for (std::map::iterator it = this->SQLiteServices.begin(); it != this->SQLiteServices.end();) + { + const Anope::string &cname = it->first; + SQLiteService *s = it->second; + int i, num; + ++it; + + for (i = 0, num = config->CountBlock("sqlite"); i < num; ++i) + if (config->GetBlock("sqlite", i)->Get("name", "sqlite/main") == cname) + break; + + if (i == num) + { + Log(LOG_NORMAL, "sqlite") << "SQLite: Removing server connection " << cname; + + delete s; + this->SQLiteServices.erase(cname); + } + } + + for (int i = 0; i < config->CountBlock("sqlite"); ++i) + { + Configuration::Block *block = config->GetBlock("sqlite", i); + Anope::string connname = block->Get("name", "sqlite/main"); + + if (this->SQLiteServices.find(connname) == this->SQLiteServices.end()) + { + Anope::string database = Anope::DataDir + "/" + block->Get("database", "anope"); + + try + { + SQLiteService *ss = new SQLiteService(this, connname, database); + this->SQLiteServices[connname] = ss; + + Log(LOG_NORMAL, "sqlite") << "SQLite: Successfully added database " << database; + } + catch (const SQL::Exception &ex) + { + Log(LOG_NORMAL, "sqlite") << "SQLite: " << ex.GetReason(); + } + } + } + } +}; + +SQLiteService::SQLiteService(Module *o, const Anope::string &n, const Anope::string &d) +: Provider(o, n), database(d), sql(NULL) +{ + int db = sqlite3_open_v2(database.c_str(), &this->sql, SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE, 0); + if (db != SQLITE_OK) + { + Anope::string exstr = "Unable to open SQLite database " + database; + if (this->sql) + { + exstr += ": "; + exstr += sqlite3_errmsg(this->sql); + sqlite3_close(this->sql); + } + throw SQL::Exception(exstr); + } +} + +SQLiteService::~SQLiteService() +{ + sqlite3_interrupt(this->sql); + sqlite3_close(this->sql); +} + +void SQLiteService::Run(Interface *i, const Query &query) +{ + Result res = this->RunQuery(query); + if (!res.GetError().empty()) + i->OnError(res); + else + i->OnResult(res); +} + +Result SQLiteService::RunQuery(const Query &query) +{ + Anope::string real_query = this->BuildQuery(query); + sqlite3_stmt *stmt; + int err = sqlite3_prepare_v2(this->sql, real_query.c_str(), real_query.length(), &stmt, NULL); + if (err != SQLITE_OK) + return SQLiteResult(query, real_query, sqlite3_errmsg(this->sql)); + + std::vector columns; + int cols = sqlite3_column_count(stmt); + columns.resize(cols); + for (int i = 0; i < cols; ++i) + columns[i] = sqlite3_column_name(stmt, i); + + SQLiteResult result(0, query, real_query); + + while ((err = sqlite3_step(stmt)) == SQLITE_ROW) + { + std::map items; + for (int i = 0; i < cols; ++i) + { + const char *data = reinterpret_cast(sqlite3_column_text(stmt, i)); + if (data && *data) + items[columns[i]] = data; + } + result.AddRow(items); + } + + result.id = sqlite3_last_insert_rowid(this->sql); + + sqlite3_finalize(stmt); + + if (err != SQLITE_DONE) + return SQLiteResult(query, real_query, sqlite3_errmsg(this->sql)); + + return result; +} + +std::vector SQLiteService::CreateTable(const Anope::string &table, const Data &data) +{ + std::vector queries; + std::set &known_cols = this->active_schema[table]; + + if (known_cols.empty()) + { + Log(LOG_DEBUG) << "m_sqlite: Fetching columns for " << table; + + Result columns = this->RunQuery("PRAGMA table_info(" + table + ")"); + for (int i = 0; i < columns.Rows(); ++i) + { + const Anope::string &column = columns.Get(i, "name"); + + Log(LOG_DEBUG) << "m_sqlite: Column #" << i << " for " << table << ": " << column; + known_cols.insert(column); + } + } + + if (known_cols.empty()) + { + Anope::string query_text = "CREATE TABLE `" + table + "` (`id` INTEGER PRIMARY KEY, `timestamp` timestamp DEFAULT CURRENT_TIMESTAMP"; + + for (Data::Map::const_iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + { + known_cols.insert(it->first); + + query_text += ", `" + it->first + "` "; + if (data.GetType(it->first) == Serialize::Data::DT_INT) + query_text += "int(11)"; + else + query_text += "text"; + } + + query_text += ")"; + + queries.push_back(query_text); + + query_text = "CREATE UNIQUE INDEX `" + table + "_id_idx` ON `" + table + "` (`id`)"; + queries.push_back(query_text); + + query_text = "CREATE INDEX `" + table + "_timestamp_idx` ON `" + table + "` (`timestamp`)"; + queries.push_back(query_text); + + query_text = "CREATE TRIGGER `" + table + "_trigger` AFTER UPDATE ON `" + table + "` FOR EACH ROW BEGIN UPDATE `" + table + "` SET `timestamp` = CURRENT_TIMESTAMP WHERE `id` = `old.id`; end;"; + queries.push_back(query_text); + } + else + for (Data::Map::const_iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + { + if (known_cols.count(it->first) > 0) + continue; + + known_cols.insert(it->first); + + Anope::string query_text = "ALTER TABLE `" + table + "` ADD `" + it->first + "` "; + if (data.GetType(it->first) == Serialize::Data::DT_INT) + query_text += "int(11)"; + else + query_text += "text"; + + queries.push_back(query_text); + } + + return queries; +} + +Query SQLiteService::BuildInsert(const Anope::string &table, unsigned int id, Data &data) +{ + /* Empty columns not present in the data set */ + const std::set &known_cols = this->active_schema[table]; + for (std::set::iterator it = known_cols.begin(), it_end = known_cols.end(); it != it_end; ++it) + if (*it != "id" && *it != "timestamp" && data.data.count(*it) == 0) + data[*it] << ""; + + Anope::string query_text = "REPLACE INTO `" + table + "` ("; + if (id > 0) + query_text += "`id`,"; + for (Data::Map::const_iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + query_text += "`" + it->first + "`,"; + query_text.erase(query_text.length() - 1); + query_text += ") VALUES ("; + if (id > 0) + query_text += stringify(id) + ","; + for (Data::Map::const_iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + query_text += "@" + it->first + "@,"; + query_text.erase(query_text.length() - 1); + query_text += ")"; + + Query query(query_text); + for (Data::Map::const_iterator it = data.data.begin(), it_end = data.data.end(); it != it_end; ++it) + { + Anope::string buf; + *it->second >> buf; + query.SetValue(it->first, buf); + } + + return query; +} + +Query SQLiteService::GetTables(const Anope::string &prefix) +{ + return Query("SELECT name FROM sqlite_master WHERE type='table' AND name LIKE '" + prefix + "%';"); +} + +Anope::string SQLiteService::Escape(const Anope::string &query) +{ + char *e = sqlite3_mprintf("%q", query.c_str()); + Anope::string buffer = e; + sqlite3_free(e); + return buffer; +} + +Anope::string SQLiteService::BuildQuery(const Query &q) +{ + Anope::string real_query = q.query; + + for (std::map::const_iterator it = q.parameters.begin(), it_end = q.parameters.end(); it != it_end; ++it) + real_query = real_query.replace_all_cs("@" + it->first + "@", (it->second.escape ? ("'" + this->Escape(it->second.data) + "'") : it->second.data)); + + return real_query; +} + +Anope::string SQLiteService::FromUnixtime(time_t t) +{ + return "datetime('" + stringify(t) + "', 'unixepoch')"; +} + +MODULE_INIT(ModuleSQLite) diff --git a/modules/extra/m_ssl_gnutls.cpp b/modules/extra/m_ssl_gnutls.cpp new file mode 100644 index 0000000..1e834fc --- /dev/null +++ b/modules/extra/m_ssl_gnutls.cpp @@ -0,0 +1,656 @@ +/* + * + * (C) 2014 Attila Molnar + * (C) 2014-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +/* RequiredLibraries: gnutls */ +/* RequiredWindowsLibraries: libgnutls-30 */ + +#include "module.h" +#include "modules/ssl.h" + +#include +#include +#include + +class GnuTLSModule; +static GnuTLSModule *me; + +namespace GnuTLS { class X509CertCredentials; } + +class MySSLService : public SSLService +{ + public: + MySSLService(Module *o, const Anope::string &n); + + /** Initialize a socket to use SSL + * @param s The socket + */ + void Init(Socket *s) anope_override; +}; + +class SSLSocketIO : public SocketIO +{ + public: + gnutls_session_t sess; + GnuTLS::X509CertCredentials* mycreds; + + /** Constructor + */ + SSLSocketIO(); + + /** Really receive something from the buffer + * @param s The socket + * @param buf The buf to read to + * @param sz How much to read + * @return Number of bytes received + */ + int Recv(Socket *s, char *buf, size_t sz) anope_override; + + /** Write something to the socket + * @param s The socket + * @param buf The data to write + * @param size The length of the data + */ + int Send(Socket *s, const char *buf, size_t sz) anope_override; + + /** Accept a connection from a socket + * @param s The socket + * @return The new socket + */ + ClientSocket *Accept(ListenSocket *s) anope_override; + + /** Finished accepting a connection from a socket + * @param s The socket + * @return SF_ACCEPTED if accepted, SF_ACCEPTING if still in process, SF_DEAD on error + */ + SocketFlag FinishAccept(ClientSocket *cs) anope_override; + + /** Connect the socket + * @param s THe socket + * @param target IP to connect to + * @param port to connect to + */ + void Connect(ConnectionSocket *s, const Anope::string &target, int port) anope_override; + + /** Called to potentially finish a pending connection + * @param s The socket + * @return SF_CONNECTED on success, SF_CONNECTING if still pending, and SF_DEAD on error. + */ + SocketFlag FinishConnect(ConnectionSocket *s) anope_override; + + /** Called when the socket is destructing + */ + void Destroy() anope_override; +}; + +namespace GnuTLS +{ + class Init + { + public: + Init() { gnutls_global_init(); } + ~Init() { gnutls_global_deinit(); } + }; + + /** Used to create a gnutls_datum_t* from an Anope::string + */ + class Datum + { + gnutls_datum_t datum; + + public: + Datum(const Anope::string &dat) + { + datum.data = reinterpret_cast(const_cast(dat.data())); + datum.size = static_cast(dat.length()); + } + + const gnutls_datum_t *get() const { return &datum; } + }; + + class DHParams + { + gnutls_dh_params_t dh_params; + + public: + DHParams() : dh_params(NULL) { } + + void Import(const Anope::string &dhstr) + { + if (dh_params != NULL) + { + gnutls_dh_params_deinit(dh_params); + dh_params = NULL; + } + + int ret = gnutls_dh_params_init(&dh_params); + if (ret < 0) + throw ConfigException("Unable to initialize DH parameters"); + + ret = gnutls_dh_params_import_pkcs3(dh_params, Datum(dhstr).get(), GNUTLS_X509_FMT_PEM); + if (ret < 0) + { + gnutls_dh_params_deinit(dh_params); + dh_params = NULL; + throw ConfigException("Unable to import DH parameters"); + } + } + + ~DHParams() + { + if (dh_params) + gnutls_dh_params_deinit(dh_params); + } + + gnutls_dh_params_t get() const { return dh_params; } + }; + + class X509Key + { + /** Ensure that the key is deinited in case the constructor of X509Key throws + */ + class RAIIKey + { + public: + gnutls_x509_privkey_t key; + + RAIIKey() + { + int ret = gnutls_x509_privkey_init(&key); + if (ret < 0) + throw ConfigException("gnutls_x509_privkey_init() failed"); + } + + ~RAIIKey() + { + gnutls_x509_privkey_deinit(key); + } + } key; + + public: + /** Import */ + X509Key(const Anope::string &keystr) + { + int ret = gnutls_x509_privkey_import(key.key, Datum(keystr).get(), GNUTLS_X509_FMT_PEM); + if (ret < 0) + throw ConfigException("Error loading private key: " + Anope::string(gnutls_strerror(ret))); + } + + gnutls_x509_privkey_t& get() { return key.key; } + }; + + class X509CertList + { + std::vector certs; + + public: + /** Import */ + X509CertList(const Anope::string &certstr) + { + unsigned int certcount = 3; + certs.resize(certcount); + Datum datum(certstr); + + int ret = gnutls_x509_crt_list_import(raw(), &certcount, datum.get(), GNUTLS_X509_FMT_PEM, GNUTLS_X509_CRT_LIST_IMPORT_FAIL_IF_EXCEED); + if (ret == GNUTLS_E_SHORT_MEMORY_BUFFER) + { + // the buffer wasn't big enough to hold all certs but gnutls changed certcount to the number of available certs, + // try again with a bigger buffer + certs.resize(certcount); + ret = gnutls_x509_crt_list_import(raw(), &certcount, datum.get(), GNUTLS_X509_FMT_PEM, GNUTLS_X509_CRT_LIST_IMPORT_FAIL_IF_EXCEED); + } + + if (ret < 0) + throw ConfigException("Unable to load certificates" + Anope::string(gnutls_strerror(ret))); + + // Resize the vector to the actual number of certs because we rely on its size being correct + // when deallocating the certs + certs.resize(certcount); + } + + ~X509CertList() + { + for (std::vector::iterator i = certs.begin(); i != certs.end(); ++i) + gnutls_x509_crt_deinit(*i); + } + + gnutls_x509_crt_t* raw() { return &certs[0]; } + unsigned int size() const { return certs.size(); } + }; + + class X509CertCredentials + { + unsigned int refcount; + gnutls_certificate_credentials_t cred; + DHParams dh; + + static Anope::string LoadFile(const Anope::string &filename) + { + std::ifstream ifs(filename.c_str()); + const Anope::string ret((std::istreambuf_iterator(ifs)), std::istreambuf_iterator()); + return ret; + } + + #if (GNUTLS_VERSION_MAJOR < 2 || (GNUTLS_VERSION_MAJOR == 2 && GNUTLS_VERSION_MINOR < 12)) + static int cert_callback(gnutls_session_t sess, const gnutls_datum_t* req_ca_rdn, int nreqs, const gnutls_pk_algorithm_t* sign_algos, int sign_algos_length, gnutls_retr_st* st); + #else + static int cert_callback(gnutls_session_t sess, const gnutls_datum_t* req_ca_rdn, int nreqs, const gnutls_pk_algorithm_t* sign_algos, int sign_algos_length, gnutls_retr2_st* st); + #endif + + public: + X509CertList certs; + X509Key key; + + X509CertCredentials(const Anope::string &certfile, const Anope::string &keyfile) + : refcount(0), certs(LoadFile(certfile)), key(LoadFile(keyfile)) + { + if (gnutls_certificate_allocate_credentials(&cred) < 0) + throw ConfigException("Cannot allocate certificate credentials"); + + int ret = gnutls_certificate_set_x509_key(cred, certs.raw(), certs.size(), key.get()); + if (ret < 0) + { + gnutls_certificate_free_credentials(cred); + throw ConfigException("Unable to set cert/key pair"); + } + + #if (GNUTLS_VERSION_MAJOR < 2 || (GNUTLS_VERSION_MAJOR == 2 && GNUTLS_VERSION_MINOR < 12)) + gnutls_certificate_client_set_retrieve_function(cred, cert_callback); + #else + gnutls_certificate_set_retrieve_function(cred, cert_callback); + #endif + } + + ~X509CertCredentials() + { + gnutls_certificate_free_credentials(cred); + } + + void SetupSession(gnutls_session_t sess) + { + gnutls_credentials_set(sess, GNUTLS_CRD_CERTIFICATE, cred); + gnutls_set_default_priority(sess); + } + + void SetDH(const Anope::string &dhfile) + { + const Anope::string dhdata = LoadFile(dhfile); + dh.Import(dhdata); + gnutls_certificate_set_dh_params(cred, dh.get()); + } + + bool HasDH() const + { + return (dh.get() != NULL); + } + + void incrref() { refcount++; } + void decrref() { if (!--refcount) delete this; } + }; +} + +class GnuTLSModule : public Module +{ + GnuTLS::Init libinit; + + public: + GnuTLS::X509CertCredentials *cred; + MySSLService service; + + GnuTLSModule(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR), cred(NULL), service(this, "ssl") + { + me = this; + this->SetPermanent(true); + } + + ~GnuTLSModule() + { + for (std::map::const_iterator it = SocketEngine::Sockets.begin(), it_end = SocketEngine::Sockets.end(); it != it_end;) + { + Socket *s = it->second; + ++it; + + if (dynamic_cast(s->io)) + delete s; + } + + if (cred) + cred->decrref(); + } + + static void CheckFile(const Anope::string &filename) + { + if (!Anope::IsFile(filename.c_str())) + { + Log() << "File does not exist: " << filename; + throw ConfigException("Error loading certificate/private key"); + } + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *config = conf->GetModule(this); + + const Anope::string certfile = config->Get("cert", "data/anope.crt"); + const Anope::string keyfile = config->Get("key", "data/anope.key"); + const Anope::string dhfile = config->Get("dh", "data/dhparams.pem"); + + CheckFile(certfile); + CheckFile(keyfile); + + GnuTLS::X509CertCredentials *newcred = new GnuTLS::X509CertCredentials(certfile, keyfile); + + // DH params is not mandatory + if (Anope::IsFile(dhfile.c_str())) + { + try + { + newcred->SetDH(dhfile); + } + catch (...) + { + delete newcred; + throw; + } + Log(LOG_DEBUG) << "m_ssl_gnutls: Successfully loaded DH parameters from " << dhfile; + } + + if (cred) + cred->decrref(); + cred = newcred; + cred->incrref(); + + Log(LOG_DEBUG) << "m_ssl_gnutls: Successfully loaded certificate " << certfile << " and private key " << keyfile; + } + + void OnPreServerConnect() anope_override + { + Configuration::Block *config = Config->GetBlock("uplink", Anope::CurrentUplink); + + if (config->Get("ssl")) + { + this->service.Init(UplinkSock); + } + } +}; + +MySSLService::MySSLService(Module *o, const Anope::string &n) : SSLService(o, n) +{ +} + +void MySSLService::Init(Socket *s) +{ + if (s->io != &NormalSocketIO) + throw CoreException("Socket initializing SSL twice"); + + s->io = new SSLSocketIO(); +} + +int SSLSocketIO::Recv(Socket *s, char *buf, size_t sz) +{ + int ret = gnutls_record_recv(this->sess, buf, sz); + + if (ret > 0) + TotalRead += ret; + else if (ret < 0) + { + switch (ret) + { + case GNUTLS_E_AGAIN: + case GNUTLS_E_INTERRUPTED: + SocketEngine::SetLastError(EAGAIN); + break; + default: + if (s == UplinkSock) + { + // Log and fake an errno because this is a fatal error on the uplink socket + Log() << "SSL error: " << gnutls_strerror(ret); + } + SocketEngine::SetLastError(ECONNRESET); + } + } + + return ret; +} + +int SSLSocketIO::Send(Socket *s, const char *buf, size_t sz) +{ + int ret = gnutls_record_send(this->sess, buf, sz); + + if (ret > 0) + TotalWritten += ret; + else + { + switch (ret) + { + case 0: + case GNUTLS_E_AGAIN: + case GNUTLS_E_INTERRUPTED: + SocketEngine::SetLastError(EAGAIN); + break; + default: + if (s == UplinkSock) + { + // Log and fake an errno because this is a fatal error on the uplink socket + Log() << "SSL error: " << gnutls_strerror(ret); + } + SocketEngine::SetLastError(ECONNRESET); + } + } + + return ret; +} + +ClientSocket *SSLSocketIO::Accept(ListenSocket *s) +{ + if (s->io == &NormalSocketIO) + throw SocketException("Attempting to accept on uninitialized socket with SSL"); + + sockaddrs conaddr; + + socklen_t size = sizeof(conaddr); + int newsock = accept(s->GetFD(), &conaddr.sa, &size); + +#ifndef INVALID_SOCKET + const int INVALID_SOCKET = -1; +#endif + + if (newsock < 0 || newsock == INVALID_SOCKET) + throw SocketException("Unable to accept connection: " + Anope::LastError()); + + ClientSocket *newsocket = s->OnAccept(newsock, conaddr); + me->service.Init(newsocket); + SSLSocketIO *io = anope_dynamic_static_cast(newsocket->io); + + if (gnutls_init(&io->sess, GNUTLS_SERVER) != GNUTLS_E_SUCCESS) + throw SocketException("Unable to initialize SSL socket"); + + me->cred->SetupSession(io->sess); + gnutls_transport_set_ptr(io->sess, reinterpret_cast(newsock)); + + newsocket->flags[SF_ACCEPTING] = true; + this->FinishAccept(newsocket); + + return newsocket; +} + +SocketFlag SSLSocketIO::FinishAccept(ClientSocket *cs) +{ + if (cs->io == &NormalSocketIO) + throw SocketException("Attempting to finish connect uninitialized socket with SSL"); + else if (cs->flags[SF_ACCEPTED]) + return SF_ACCEPTED; + else if (!cs->flags[SF_ACCEPTING]) + throw SocketException("SSLSocketIO::FinishAccept called for a socket not accepted nor accepting?"); + + SSLSocketIO *io = anope_dynamic_static_cast(cs->io); + + int ret = gnutls_handshake(io->sess); + if (ret < 0) + { + if (ret == GNUTLS_E_AGAIN || ret == GNUTLS_E_INTERRUPTED) + { + // gnutls_handshake() wants to read or write again; + // if gnutls_record_get_direction() returns 0 it wants to read, otherwise it wants to write. + if (gnutls_record_get_direction(io->sess) == 0) + { + SocketEngine::Change(cs, false, SF_WRITABLE); + SocketEngine::Change(cs, true, SF_READABLE); + } + else + { + SocketEngine::Change(cs, true, SF_WRITABLE); + SocketEngine::Change(cs, false, SF_READABLE); + } + return SF_ACCEPTING; + } + else + { + cs->OnError(Anope::string(gnutls_strerror(ret))); + cs->flags[SF_DEAD] = true; + cs->flags[SF_ACCEPTING] = false; + return SF_DEAD; + } + } + else + { + cs->flags[SF_ACCEPTED] = true; + cs->flags[SF_ACCEPTING] = false; + SocketEngine::Change(cs, false, SF_WRITABLE); + SocketEngine::Change(cs, true, SF_READABLE); + cs->OnAccept(); + return SF_ACCEPTED; + } +} + +void SSLSocketIO::Connect(ConnectionSocket *s, const Anope::string &target, int port) +{ + if (s->io == &NormalSocketIO) + throw SocketException("Attempting to connect uninitialized socket with SSL"); + + s->flags[SF_CONNECTING] = s->flags[SF_CONNECTED] = false; + + s->conaddr.pton(s->IsIPv6() ? AF_INET6 : AF_INET, target, port); + int c = connect(s->GetFD(), &s->conaddr.sa, s->conaddr.size()); + if (c == -1) + { + if (Anope::LastErrorCode() != EINPROGRESS) + { + s->OnError(Anope::LastError()); + s->flags[SF_DEAD] = true; + return; + } + else + { + SocketEngine::Change(s, true, SF_WRITABLE); + s->flags[SF_CONNECTING] = true; + return; + } + } + else + { + s->flags[SF_CONNECTING] = true; + this->FinishConnect(s); + } +} + +SocketFlag SSLSocketIO::FinishConnect(ConnectionSocket *s) +{ + if (s->io == &NormalSocketIO) + throw SocketException("Attempting to finish connect uninitialized socket with SSL"); + else if (s->flags[SF_CONNECTED]) + return SF_CONNECTED; + else if (!s->flags[SF_CONNECTING]) + throw SocketException("SSLSocketIO::FinishConnect called for a socket not connected nor connecting?"); + + SSLSocketIO *io = anope_dynamic_static_cast(s->io); + + if (io->sess == NULL) + { + if (gnutls_init(&io->sess, GNUTLS_CLIENT) != GNUTLS_E_SUCCESS) + throw SocketException("Unable to initialize SSL socket"); + me->cred->SetupSession(io->sess); + gnutls_transport_set_ptr(io->sess, reinterpret_cast(s->GetFD())); + } + + int ret = gnutls_handshake(io->sess); + if (ret < 0) + { + if (ret == GNUTLS_E_AGAIN || ret == GNUTLS_E_INTERRUPTED) + { + // gnutls_handshake() wants to read or write again; + // if gnutls_record_get_direction() returns 0 it wants to read, otherwise it wants to write. + if (gnutls_record_get_direction(io->sess) == 0) + { + SocketEngine::Change(s, false, SF_WRITABLE); + SocketEngine::Change(s, true, SF_READABLE); + } + else + { + SocketEngine::Change(s, true, SF_WRITABLE); + SocketEngine::Change(s, false, SF_READABLE); + } + + return SF_CONNECTING; + } + else + { + s->OnError(Anope::string(gnutls_strerror(ret))); + s->flags[SF_CONNECTING] = false; + s->flags[SF_DEAD] = true; + return SF_DEAD; + } + } + else + { + s->flags[SF_CONNECTING] = false; + s->flags[SF_CONNECTED] = true; + SocketEngine::Change(s, false, SF_WRITABLE); + SocketEngine::Change(s, true, SF_READABLE); + s->OnConnect(); + return SF_CONNECTED; + } +} + +void SSLSocketIO::Destroy() +{ + if (this->sess) + { + gnutls_bye(this->sess, GNUTLS_SHUT_WR); + gnutls_deinit(this->sess); + } + + mycreds->decrref(); + + delete this; +} + +SSLSocketIO::SSLSocketIO() : sess(NULL), mycreds(me->cred) +{ + mycreds->incrref(); +} + +#if (GNUTLS_VERSION_MAJOR < 2 || (GNUTLS_VERSION_MAJOR == 2 && GNUTLS_VERSION_MINOR < 12)) +int GnuTLS::X509CertCredentials::cert_callback(gnutls_session_t sess, const gnutls_datum_t* req_ca_rdn, int nreqs, const gnutls_pk_algorithm_t* sign_algos, int sign_algos_length, gnutls_retr_st* st) +{ + st->type = GNUTLS_CRT_X509; +#else +int GnuTLS::X509CertCredentials::cert_callback(gnutls_session_t sess, const gnutls_datum_t* req_ca_rdn, int nreqs, const gnutls_pk_algorithm_t* sign_algos, int sign_algos_length, gnutls_retr2_st* st) +{ + st->cert_type = GNUTLS_CRT_X509; + st->key_type = GNUTLS_PRIVKEY_X509; +#endif + st->ncerts = me->cred->certs.size(); + st->cert.x509 = me->cred->certs.raw(); + st->key.x509 = me->cred->key.get(); + st->deinit_all = 0; + + return 0; +} + +MODULE_INIT(GnuTLSModule) diff --git a/modules/extra/m_ssl_openssl.cpp b/modules/extra/m_ssl_openssl.cpp new file mode 100644 index 0000000..59b9492 --- /dev/null +++ b/modules/extra/m_ssl_openssl.cpp @@ -0,0 +1,422 @@ +/* + * + * (C) 2010-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +/* RequiredLibraries: ssl,crypto */ +/* RequiredWindowsLibraries: ssleay32,libeay32 */ + +#include "module.h" +#include "modules/ssl.h" + +#define OPENSSL_NO_SHA512 +#include +#include +#include +#include +#include + +static SSL_CTX *server_ctx, *client_ctx; + +class MySSLService : public SSLService +{ + public: + MySSLService(Module *o, const Anope::string &n); + + /** Initialize a socket to use SSL + * @param s The socket + */ + void Init(Socket *s) anope_override; +}; + +class SSLSocketIO : public SocketIO +{ + public: + /* The SSL socket for this socket */ + SSL *sslsock; + + /** Constructor + */ + SSLSocketIO(); + + /** Really receive something from the buffer + * @param s The socket + * @param buf The buf to read to + * @param sz How much to read + * @return Number of bytes received + */ + int Recv(Socket *s, char *buf, size_t sz) anope_override; + + /** Write something to the socket + * @param s The socket + * @param buf The data to write + * @param size The length of the data + */ + int Send(Socket *s, const char *buf, size_t sz) anope_override; + + /** Accept a connection from a socket + * @param s The socket + * @return The new socket + */ + ClientSocket *Accept(ListenSocket *s) anope_override; + + /** Finished accepting a connection from a socket + * @param s The socket + * @return SF_ACCEPTED if accepted, SF_ACCEPTING if still in process, SF_DEAD on error + */ + SocketFlag FinishAccept(ClientSocket *cs) anope_override; + + /** Connect the socket + * @param s THe socket + * @param target IP to connect to + * @param port to connect to + */ + void Connect(ConnectionSocket *s, const Anope::string &target, int port) anope_override; + + /** Called to potentially finish a pending connection + * @param s The socket + * @return SF_CONNECTED on success, SF_CONNECTING if still pending, and SF_DEAD on error. + */ + SocketFlag FinishConnect(ConnectionSocket *s) anope_override; + + /** Called when the socket is destructing + */ + void Destroy() anope_override; +}; + +class SSLModule; +static SSLModule *me; +class SSLModule : public Module +{ + Anope::string certfile, keyfile; + + public: + MySSLService service; + + SSLModule(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR), service(this, "ssl") + { + me = this; + + this->SetPermanent(true); + + SSL_library_init(); + SSL_load_error_strings(); + + client_ctx = SSL_CTX_new(SSLv23_client_method()); + server_ctx = SSL_CTX_new(SSLv23_server_method()); + + if (!client_ctx || !server_ctx) + throw ModuleException("Error initializing SSL CTX"); + + long opts = SSL_OP_NO_SSLv2 | SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION | SSL_OP_CIPHER_SERVER_PREFERENCE; + SSL_CTX_set_options(client_ctx, opts); + SSL_CTX_set_options(server_ctx, opts); + + SSL_CTX_set_mode(client_ctx, SSL_MODE_ENABLE_PARTIAL_WRITE | SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER); + SSL_CTX_set_mode(server_ctx, SSL_MODE_ENABLE_PARTIAL_WRITE | SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER); + + Anope::string context_name = "Anope"; + SSL_CTX_set_session_id_context(client_ctx, reinterpret_cast(context_name.c_str()), context_name.length()); + SSL_CTX_set_session_id_context(server_ctx, reinterpret_cast(context_name.c_str()), context_name.length()); + } + + ~SSLModule() + { + for (std::map::const_iterator it = SocketEngine::Sockets.begin(), it_end = SocketEngine::Sockets.end(); it != it_end;) + { + Socket *s = it->second; + ++it; + + if (dynamic_cast(s->io)) + delete s; + } + + SSL_CTX_free(client_ctx); + SSL_CTX_free(server_ctx); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *config = conf->GetModule(this); + + this->certfile = config->Get("cert", "data/anope.crt"); + this->keyfile = config->Get("key", "data/anope.key"); + + if (Anope::IsFile(this->certfile.c_str())) + { + if (!SSL_CTX_use_certificate_chain_file(client_ctx, this->certfile.c_str()) || !SSL_CTX_use_certificate_chain_file(server_ctx, this->certfile.c_str())) + throw ConfigException("Error loading certificate"); + else + Log(LOG_DEBUG) << "m_ssl_openssl: Successfully loaded certificate " << this->certfile; + } + else + Log() << "Unable to open certificate " << this->certfile; + + if (Anope::IsFile(this->keyfile.c_str())) + { + if (!SSL_CTX_use_PrivateKey_file(client_ctx, this->keyfile.c_str(), SSL_FILETYPE_PEM) || !SSL_CTX_use_PrivateKey_file(server_ctx, this->keyfile.c_str(), SSL_FILETYPE_PEM)) + throw ConfigException("Error loading private key"); + else + Log(LOG_DEBUG) << "m_ssl_openssl: Successfully loaded private key " << this->keyfile; + } + else + { + if (Anope::IsFile(this->certfile.c_str())) + throw ConfigException("Error loading private key " + this->keyfile + " - file not found"); + else + Log() << "Unable to open private key " << this->keyfile; + } + + // Allow disabling SSLv3 + if (!config->Get("sslv3").empty()) + { + if (config->Get("sslv3")) + { + SSL_CTX_clear_options(client_ctx, SSL_OP_NO_SSLv3); + SSL_CTX_clear_options(server_ctx, SSL_OP_NO_SSLv3); + } + else + { + SSL_CTX_set_options(client_ctx, SSL_OP_NO_SSLv3); + SSL_CTX_set_options(server_ctx, SSL_OP_NO_SSLv3); + } + } + } + + void OnPreServerConnect() anope_override + { + Configuration::Block *config = Config->GetBlock("uplink", Anope::CurrentUplink); + + if (config->Get("ssl")) + { + this->service.Init(UplinkSock); + } + } +}; + +MySSLService::MySSLService(Module *o, const Anope::string &n) : SSLService(o, n) +{ +} + +void MySSLService::Init(Socket *s) +{ + if (s->io != &NormalSocketIO) + throw CoreException("Socket initializing SSL twice"); + + s->io = new SSLSocketIO(); +} + +SSLSocketIO::SSLSocketIO() +{ + this->sslsock = NULL; +} + +int SSLSocketIO::Recv(Socket *s, char *buf, size_t sz) +{ + int i = SSL_read(this->sslsock, buf, sz); + if (i > 0) + TotalRead += i; + else if (i < 0) + { + int err = SSL_get_error(this->sslsock, i); + switch (err) + { + case SSL_ERROR_WANT_READ: + case SSL_ERROR_WANT_WRITE: + SocketEngine::SetLastError(EAGAIN); + } + } + + return i; +} + +int SSLSocketIO::Send(Socket *s, const char *buf, size_t sz) +{ + int i = SSL_write(this->sslsock, buf, sz); + if (i > 0) + TotalWritten += i; + else if (i < 0) + { + int err = SSL_get_error(this->sslsock, i); + switch (err) + { + case SSL_ERROR_WANT_READ: + case SSL_ERROR_WANT_WRITE: + SocketEngine::SetLastError(EAGAIN); + } + } + return i; +} + +ClientSocket *SSLSocketIO::Accept(ListenSocket *s) +{ + if (s->io == &NormalSocketIO) + throw SocketException("Attempting to accept on uninitialized socket with SSL"); + + sockaddrs conaddr; + + socklen_t size = sizeof(conaddr); + int newsock = accept(s->GetFD(), &conaddr.sa, &size); + +#ifndef INVALID_SOCKET + const int INVALID_SOCKET = -1; +#endif + + if (newsock < 0 || newsock == INVALID_SOCKET) + throw SocketException("Unable to accept connection: " + Anope::LastError()); + + ClientSocket *newsocket = s->OnAccept(newsock, conaddr); + me->service.Init(newsocket); + SSLSocketIO *io = anope_dynamic_static_cast(newsocket->io); + + io->sslsock = SSL_new(server_ctx); + if (!io->sslsock) + throw SocketException("Unable to initialize SSL socket"); + + SSL_set_accept_state(io->sslsock); + + if (!SSL_set_fd(io->sslsock, newsocket->GetFD())) + throw SocketException("Unable to set SSL fd"); + + newsocket->flags[SF_ACCEPTING] = true; + this->FinishAccept(newsocket); + + return newsocket; +} + +SocketFlag SSLSocketIO::FinishAccept(ClientSocket *cs) +{ + if (cs->io == &NormalSocketIO) + throw SocketException("Attempting to finish connect uninitialized socket with SSL"); + else if (cs->flags[SF_ACCEPTED]) + return SF_ACCEPTED; + else if (!cs->flags[SF_ACCEPTING]) + throw SocketException("SSLSocketIO::FinishAccept called for a socket not accepted nor accepting?"); + + SSLSocketIO *io = anope_dynamic_static_cast(cs->io); + + int ret = SSL_accept(io->sslsock); + if (ret <= 0) + { + int error = SSL_get_error(io->sslsock, ret); + if (ret == -1 && (error == SSL_ERROR_WANT_READ || error == SSL_ERROR_WANT_WRITE)) + { + SocketEngine::Change(cs, error == SSL_ERROR_WANT_WRITE, SF_WRITABLE); + SocketEngine::Change(cs, error == SSL_ERROR_WANT_READ, SF_READABLE); + return SF_ACCEPTING; + } + else + { + cs->OnError(ERR_error_string(ERR_get_error(), NULL)); + cs->flags[SF_DEAD] = true; + cs->flags[SF_ACCEPTING] = false; + return SF_DEAD; + } + } + else + { + cs->flags[SF_ACCEPTED] = true; + cs->flags[SF_ACCEPTING] = false; + SocketEngine::Change(cs, false, SF_WRITABLE); + SocketEngine::Change(cs, true, SF_READABLE); + cs->OnAccept(); + return SF_ACCEPTED; + } +} + +void SSLSocketIO::Connect(ConnectionSocket *s, const Anope::string &target, int port) +{ + if (s->io == &NormalSocketIO) + throw SocketException("Attempting to connect uninitialized socket with SSL"); + + s->flags[SF_CONNECTING] = s->flags[SF_CONNECTED] = false; + + s->conaddr.pton(s->IsIPv6() ? AF_INET6 : AF_INET, target, port); + int c = connect(s->GetFD(), &s->conaddr.sa, s->conaddr.size()); + if (c == -1) + { + if (Anope::LastErrorCode() != EINPROGRESS) + { + s->OnError(Anope::LastError()); + s->flags[SF_DEAD] = true; + return; + } + else + { + SocketEngine::Change(s, true, SF_WRITABLE); + s->flags[SF_CONNECTING] = true; + return; + } + } + else + { + s->flags[SF_CONNECTING] = true; + this->FinishConnect(s); + } +} + +SocketFlag SSLSocketIO::FinishConnect(ConnectionSocket *s) +{ + if (s->io == &NormalSocketIO) + throw SocketException("Attempting to finish connect uninitialized socket with SSL"); + else if (s->flags[SF_CONNECTED]) + return SF_CONNECTED; + else if (!s->flags[SF_CONNECTING]) + throw SocketException("SSLSocketIO::FinishConnect called for a socket not connected nor connecting?"); + + SSLSocketIO *io = anope_dynamic_static_cast(s->io); + + if (io->sslsock == NULL) + { + io->sslsock = SSL_new(client_ctx); + if (!io->sslsock) + throw SocketException("Unable to initialize SSL socket"); + + if (!SSL_set_fd(io->sslsock, s->GetFD())) + throw SocketException("Unable to set SSL fd"); + } + + int ret = SSL_connect(io->sslsock); + if (ret <= 0) + { + int error = SSL_get_error(io->sslsock, ret); + if (ret == -1 && (error == SSL_ERROR_WANT_READ || error == SSL_ERROR_WANT_WRITE)) + { + SocketEngine::Change(s, error == SSL_ERROR_WANT_WRITE, SF_WRITABLE); + SocketEngine::Change(s, error == SSL_ERROR_WANT_READ, SF_READABLE); + return SF_CONNECTING; + } + else + { + s->OnError(ERR_error_string(ERR_get_error(), NULL)); + s->flags[SF_CONNECTING] = false; + s->flags[SF_DEAD] = true; + return SF_DEAD; + } + } + else + { + s->flags[SF_CONNECTING] = false; + s->flags[SF_CONNECTED] = true; + SocketEngine::Change(s, false, SF_WRITABLE); + SocketEngine::Change(s, true, SF_READABLE); + s->OnConnect(); + return SF_CONNECTED; + } +} + +void SSLSocketIO::Destroy() +{ + if (this->sslsock) + { + SSL_shutdown(this->sslsock); + SSL_free(this->sslsock); + } + + delete this; +} + +MODULE_INIT(SSLModule) diff --git a/modules/extra/stats/cs_fantasy_stats.cpp b/modules/extra/stats/cs_fantasy_stats.cpp new file mode 100644 index 0000000..0b7dda7 --- /dev/null +++ b/modules/extra/stats/cs_fantasy_stats.cpp @@ -0,0 +1,176 @@ +/* Chanstats core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/sql.h" + +class MySQLInterface : public SQL::Interface +{ + public: + MySQLInterface(Module *o) : SQL::Interface(o) { } + + void OnResult(const SQL::Result &r) anope_override + { + } + + void OnError(const SQL::Result &r) anope_override + { + if (!r.GetQuery().query.empty()) + Log(LOG_DEBUG) << "Chanstats: Error executing query " << r.finished_query << ": " << r.GetError(); + else + Log(LOG_DEBUG) << "Chanstats: Error executing query: " << r.GetError(); + } +}; + + +class CommandCSStats : public Command +{ + public: + CommandCSStats(Module *creator) : Command (creator, "chanserv/stats", 0, 2) + { + this->SetDesc(_("Displays your Channel Stats")); + this->SetSyntax(_("[\037channel\037] [\037nick\037]")); + } + + void Execute(CommandSource &source, const std::vector ¶ms); +}; + +class CommandCSGStats : public Command +{ + public: + CommandCSGStats(Module *creator) : Command (creator, "chanserv/gstats", 0, 2) + { + this->SetDesc(_("Displays your Global Stats")); + this->SetSyntax(_("\037nick\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms); +}; + + +class CSStats; +static CSStats *me; +class CSStats : public Module +{ + CommandCSStats commandcsstats; + CommandCSGStats commandcsgstats; + ServiceReference sql; + MySQLInterface sqlinterface; + Anope::string prefix; + public: + CSStats(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcsstats(this), commandcsgstats(this), sql("", ""), sqlinterface(this) + { + me = this; + + } + + void OnReload(Configuration::Conf *conf) anope_override + { + prefix = conf->GetModule("m_chanstats")->Get("prefix", "anope_"); + this->sql = ServiceReference("SQL::Provider", conf->GetModule("m_chanstats")->Get("engine")); + } + + SQL::Result RunQuery(const SQL::Query &query) + { + if (!this->sql) + throw SQL::Exception("Unable to locate SQL reference, is m_mysql loaded and configured correctly?"); + + SQL::Result res = this->sql->RunQuery(query); + if (!res.GetError().empty()) + throw SQL::Exception(res.GetError()); + return res; + } + + void DoStats(CommandSource &source, const bool is_global, const std::vector ¶ms) + { + Anope::string display, channel; + + /* + * possible parameters are: + * stats [channel] [nick] + * stats [channel] + * stats [nick] + * stats + */ + + switch (params.size()) + { + case 2: + channel = params[0]; + display = params[1]; + break; + case 1: + if (params[0][0] == '#') + channel = params[0]; + else + { + if (NickAlias *na = NickAlias::Find(params[0])) + display = na->nc->display; + else + { + source.Reply(_("%s not found."), params[0].c_str()); + return; + } + } + break; + } + + if (display.empty()) + display = source.nc->display; + + try + { + SQL::Query query; + query = "SELECT letters, words, line, smileys_happy+smileys_sad+smileys_other as smileys," + "actions FROM `" + prefix + "chanstats` " + "WHERE `nick` = @nick@ AND `chan` = @channel@ AND `type` = 'total';"; + if (is_global || channel.empty()) + query.SetValue("channel", ""); + else + query.SetValue("channel", channel); + query.SetValue("nick", display); + SQL::Result res = this->RunQuery(query); + + if (res.Rows() > 0) + { + if (is_global) + source.Reply(_("Network stats for %s:"), display.c_str()); + else + source.Reply(_("Channel stats for %s on %s:"), display.c_str(), channel.c_str()); + + source.Reply(_("letters: %s, words: %s, lines: %s, smileys: %s, actions: %s"), + res.Get(0, "letters").c_str(), res.Get(0, "words").c_str(), + res.Get(0, "line").c_str(), res.Get(0, "smileys").c_str(), + res.Get(0, "actions").c_str()); + } + else + source.Reply(_("No stats for %s."), display.c_str()); + } + catch (const SQL::Exception &ex) + { + Log(LOG_DEBUG) << ex.GetReason(); + } + + } +}; + +void CommandCSStats::Execute(CommandSource &source, const std::vector ¶ms) +{ + me->DoStats(source, false, params); +} + +void CommandCSGStats::Execute(CommandSource &source, const std::vector ¶ms) +{ + me->DoStats(source, true, params); +} + +MODULE_INIT(CSStats) diff --git a/modules/extra/stats/cs_fantasy_top.cpp b/modules/extra/stats/cs_fantasy_top.cpp new file mode 100644 index 0000000..88a10a3 --- /dev/null +++ b/modules/extra/stats/cs_fantasy_top.cpp @@ -0,0 +1,188 @@ +/* Chanstats core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/sql.h" + +class MySQLInterface : public SQL::Interface +{ + public: + MySQLInterface(Module *o) : SQL::Interface(o) { } + + void OnResult(const SQL::Result &r) anope_override + { + } + + void OnError(const SQL::Result &r) anope_override + { + if (!r.GetQuery().query.empty()) + Log(LOG_DEBUG) << "Chanstats: Error executing query " << r.finished_query << ": " << r.GetError(); + else + Log(LOG_DEBUG) << "Chanstats: Error executing query: " << r.GetError(); + } +}; + +class CommandCSTop : public Command +{ + public: + CommandCSTop(Module *creator) : Command (creator, "chanserv/top", 0, 2) + { + this->SetDesc(_("Displays the top 3 users of a channel")); + this->SetSyntax(_("\037channel\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms); +}; + +class CommandCSTop10 : public Command +{ + public: + CommandCSTop10(Module *creator) : Command (creator, "chanserv/top10", 0, 2) + { + this->SetDesc(_("Displays the top 10 users of a channel")); + this->SetSyntax(_("\037channel\037")); + } + + void Execute(CommandSource &source, const std::vector ¶ms); +}; + +class CommandCSGTop : public Command +{ + public: + CommandCSGTop(Module *creator) : Command (creator, "chanserv/gtop", 0, 1) + { + this->SetDesc(_("Displays the top 3 users of the network")); + } + + void Execute(CommandSource &source, const std::vector ¶ms); +}; + +class CommandCSGTop10 : public Command +{ + public: + CommandCSGTop10(Module *creator) : Command (creator, "chanserv/gtop10", 0, 1) + { + this->SetDesc(_("Displays the top 10 users of the network")); + } + + void Execute(CommandSource &source, const std::vector ¶ms); +}; + + +class CSTop; +static CSTop *me; +class CSTop : public Module +{ + CommandCSTop commandcstop; + CommandCSGTop commandcsgtop; + CommandCSTop10 commandcstop10; + CommandCSGTop10 commandcsgtop10; + ServiceReference sql; + MySQLInterface sqlinterface; + Anope::string prefix; + + public: + CSTop(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + commandcstop(this), commandcsgtop(this), commandcstop10(this), commandcsgtop10(this), sql("", ""), + sqlinterface(this) + { + me = this; + + } + + void OnReload(Configuration::Conf *conf) anope_override + { + prefix = conf->GetModule("m_chanstats")->Get("prefix", "anope_"); + this->sql = ServiceReference("SQL::Provider", conf->GetModule("m_chanstats")->Get("engine")); + } + + SQL::Result RunQuery(const SQL::Query &query) + { + if (!this->sql) + throw SQL::Exception("Unable to locate SQL reference, is m_mysql loaded and configured correctly?"); + + SQL::Result res = sql->RunQuery(query); + if (!res.GetError().empty()) + throw SQL::Exception(res.GetError()); + return res; + } + + void DoTop(CommandSource &source, const std::vector ¶ms, bool is_global, int limit = 1) + { + + Anope::string channel; + if (!params.empty()) + channel = params[0]; + else if (source.c && source.c->ci) + channel = source.c->ci->name; + + if (!is_global && channel.empty()) + is_global = true; + + try + { + SQL::Query query; + query = "SELECT nick, letters, words, line, actions," + "smileys_happy+smileys_sad+smileys_other as smileys " + "FROM `" + prefix + "chanstats` " + "WHERE `nick` != '' AND `chan` = @channel@ AND `type` = 'total' " + "ORDER BY `letters` DESC LIMIT @limit@;"; + query.SetValue("limit", limit, false); + + if (is_global) + query.SetValue("channel", ""); + else + query.SetValue("channel", channel.c_str()); + + SQL::Result res = this->RunQuery(query); + + if (res.Rows() > 0) + { + source.Reply(_("Top %i of %s"), limit, (is_global ? "Network" : channel.c_str())); + for (int i = 0; i < res.Rows(); ++i) + { + source.Reply(_("%2lu \002%-16s\002 letters: %s, words: %s, lines: %s, smileys: %s, actions: %s"), + i+1, res.Get(i, "nick").c_str(), res.Get(i, "letters").c_str(), + res.Get(i, "words").c_str(), res.Get(i, "line").c_str(), + res.Get(i, "smileys").c_str(), res.Get(i, "actions").c_str()); + } + } + else + source.Reply(_("No stats for %s."), is_global ? "Network" : channel.c_str()); + } + catch (const SQL::Exception &ex) + { + Log(LOG_DEBUG) << ex.GetReason(); + } + } +}; + +void CommandCSTop::Execute(CommandSource &source, const std::vector ¶ms) +{ + me->DoTop(source, params, false, 3); +} + +void CommandCSTop10::Execute(CommandSource &source, const std::vector ¶ms) +{ + me->DoTop(source, params, false, 10); +} + +void CommandCSGTop::Execute(CommandSource &source, const std::vector ¶ms) +{ + me->DoTop(source, params, true, 3); +} + +void CommandCSGTop10::Execute(CommandSource &source, const std::vector ¶ms) +{ + me->DoTop(source, params, true, 10); +} + +MODULE_INIT(CSTop) diff --git a/modules/extra/stats/irc2sql/CMakeLists.txt b/modules/extra/stats/irc2sql/CMakeLists.txt new file mode 100644 index 0000000..781f0ef --- /dev/null +++ b/modules/extra/stats/irc2sql/CMakeLists.txt @@ -0,0 +1 @@ +build_subdir(${CMAKE_CURRENT_SOURCE_DIR}) diff --git a/modules/extra/stats/irc2sql/irc2sql.cpp b/modules/extra/stats/irc2sql/irc2sql.cpp new file mode 100644 index 0000000..6c14ec0 --- /dev/null +++ b/modules/extra/stats/irc2sql/irc2sql.cpp @@ -0,0 +1,327 @@ +/* + * + * (C) 2013-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "irc2sql.h" + +void IRC2SQL::OnShutdown() +{ + // TODO: test if we really have to use blocking query here + // (sometimes m_mysql get unloaded before the other thread executed all queries) + if (this->sql) + SQL::Result r = this->sql->RunQuery(SQL::Query("CALL " + prefix + "OnShutdown()")); + quitting = true; +} + +void IRC2SQL::OnReload(Configuration::Conf *conf) +{ + Configuration::Block *block = Config->GetModule(this); + prefix = block->Get("prefix", "anope_"); + GeoIPDB = block->Get("geoip_database"); + ctcpuser = block->Get("ctcpuser", "no"); + ctcpeob = block->Get("ctcpeob", "yes"); + Anope::string engine = block->Get("engine"); + this->sql = ServiceReference("SQL::Provider", engine); + if (sql) + this->CheckTables(); + else + Log() << "IRC2SQL: no database connection to " << engine; + + const Anope::string &snick = block->Get("client"); + if (snick.empty()) + throw ConfigException(Module::name + ": must be defined"); + StatServ = BotInfo::Find(snick, true); + if (!StatServ) + throw ConfigException(Module::name + ": no bot named " + snick); + + if (firstrun) + { + firstrun = false; + + for (Anope::map::const_iterator it = Servers::ByName.begin(); it != Servers::ByName.end(); ++it) + { + this->OnNewServer(it->second); + } + + for (channel_map::const_iterator it = ChannelList.begin(), it_end = ChannelList.end(); it != it_end; ++it) + { + this->OnChannelCreate(it->second); + } + + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + { + User *u = it->second; + bool exempt = false; + this->OnUserConnect(u, exempt); + for (User::ChanUserList::const_iterator cit = u->chans.begin(), cit_end = u->chans.end(); cit != cit_end; ++cit) + { + this->OnJoinChannel(u, cit->second->chan); + } + } + } + +} + +void IRC2SQL::OnNewServer(Server *server) +{ + query = "INSERT DELAYED INTO `" + prefix + "server` (name, hops, comment, link_time, online, ulined) " + "VALUES (@name@, @hops@, @comment@, now(), 'Y', @ulined@) " + "ON DUPLICATE KEY UPDATE name=VALUES(name), hops=VALUES(hops), comment=VALUES(comment), " + "link_time=VALUES(link_time), online=VALUES(online), ulined=VALUES(ulined)"; + query.SetValue("name", server->GetName()); + query.SetValue("hops", server->GetHops()); + query.SetValue("comment", server->GetDescription()); + query.SetValue("ulined", server->IsULined() ? "Y" : "N"); + this->RunQuery(query); +} + +void IRC2SQL::OnServerQuit(Server *server) +{ + if (quitting) + return; + + query = "CALL " + prefix + "ServerQuit(@name@)"; + query.SetValue("name", server->GetName()); + this->RunQuery(query); +} + +void IRC2SQL::OnUserConnect(User *u, bool &exempt) +{ + if (!introduced_myself) + { + this->OnNewServer(Me); + introduced_myself = true; + } + + query = "CALL " + prefix + "UserConnect(@nick@,@host@,@vhost@,@chost@,@realname@,@ip@,@ident@,@vident@," + "@account@,@secure@,@fingerprint@,@signon@,@server@,@uuid@,@modes@,@oper@)"; + query.SetValue("nick", u->nick); + query.SetValue("host", u->host); + query.SetValue("vhost", u->vhost); + query.SetValue("chost", u->chost); + query.SetValue("realname", u->realname); + query.SetValue("ip", u->ip.addr()); + query.SetValue("ident", u->GetIdent()); + query.SetValue("vident", u->GetVIdent()); + query.SetValue("secure", u->HasMode("SSL") || u->HasExt("ssl") ? "Y" : "N"); + query.SetValue("account", u->Account() ? u->Account()->display : ""); + query.SetValue("fingerprint", u->fingerprint); + query.SetValue("signon", u->signon); + query.SetValue("server", u->server->GetName()); + query.SetValue("uuid", u->GetUID()); + query.SetValue("modes", u->GetModes()); + query.SetValue("oper", u->HasMode("OPER") ? "Y" : "N"); + this->RunQuery(query); + + if (ctcpuser && (Me->IsSynced() || ctcpeob) && u->server != Me) + IRCD->SendPrivmsg(StatServ, u->GetUID(), "\1VERSION\1"); + +} + +void IRC2SQL::OnUserQuit(User *u, const Anope::string &msg) +{ + if (quitting || u->server->IsQuitting()) + return; + + query = "CALL " + prefix + "UserQuit(@nick@)"; + query.SetValue("nick", u->nick); + this->RunQuery(query); +} + +void IRC2SQL::OnUserNickChange(User *u, const Anope::string &oldnick) +{ + query = "UPDATE `" + prefix + "user` SET nick=@newnick@ WHERE nick=@oldnick@"; + query.SetValue("newnick", u->nick); + query.SetValue("oldnick", oldnick); + this->RunQuery(query); +} + +void IRC2SQL::OnUserAway(User *u, const Anope::string &message) +{ + query = "UPDATE `" + prefix + "user` SET away=@away@, awaymsg=@awaymsg@ WHERE nick=@nick@"; + query.SetValue("away", (!message.empty()) ? "Y" : "N"); + query.SetValue("awaymsg", message); + query.SetValue("nick", u->nick); + this->RunQuery(query); +} + +void IRC2SQL::OnFingerprint(User *u) +{ + query = "UPDATE `" + prefix + "user` SET secure=@secure@, fingerprint=@fingerprint@ WHERE nick=@nick@"; + query.SetValue("secure", u->HasMode("SSL") || u->HasExt("ssl") ? "Y" : "N"); + query.SetValue("fingerprint", u->fingerprint); + query.SetValue("nick", u->nick); + this->RunQuery(query); +} + +void IRC2SQL::OnUserModeSet(const MessageSource &setter, User *u, const Anope::string &mname) +{ + query = "UPDATE `" + prefix + "user` SET modes=@modes@, oper=@oper@ WHERE nick=@nick@"; + query.SetValue("nick", u->nick); + query.SetValue("modes", u->GetModes()); + query.SetValue("oper", u->HasMode("OPER") ? "Y" : "N"); + this->RunQuery(query); +} + +void IRC2SQL::OnUserModeUnset(const MessageSource &setter, User *u, const Anope::string &mname) +{ + this->OnUserModeSet(setter, u, mname); +} + +void IRC2SQL::OnUserLogin(User *u) +{ + query = "UPDATE `" + prefix + "user` SET account=@account@ WHERE nick=@nick@"; + query.SetValue("nick", u->nick); + query.SetValue("account", u->Account() ? u->Account()->display : ""); + this->RunQuery(query); +} + +void IRC2SQL::OnNickLogout(User *u) +{ + this->OnUserLogin(u); +} + +void IRC2SQL::OnSetDisplayedHost(User *u) +{ + query = "UPDATE `" + prefix + "user` " + "SET vhost=@vhost@ " + "WHERE nick=@nick@"; + query.SetValue("vhost", u->GetDisplayedHost()); + query.SetValue("nick", u->nick); + this->RunQuery(query); +} + +void IRC2SQL::OnChannelCreate(Channel *c) +{ + query = "INSERT INTO `" + prefix + "chan` (channel, topic, topicauthor, topictime, modes) " + "VALUES (@channel@,@topic@,@topicauthor@,@topictime@,@modes@) " + "ON DUPLICATE KEY UPDATE channel=VALUES(channel), topic=VALUES(topic)," + "topicauthor=VALUES(topicauthor), topictime=VALUES(topictime), modes=VALUES(modes)"; + query.SetValue("channel", c->name); + query.SetValue("topic", c->topic); + query.SetValue("topicauthor", c->topic_setter); + if (c->topic_ts > 0) + query.SetValue("topictime", c->topic_ts); + else + query.SetValue("topictime", "NULL", false); + query.SetValue("modes", c->GetModes(true,true)); + this->RunQuery(query); +} + +void IRC2SQL::OnChannelDelete(Channel *c) +{ + query = "DELETE FROM `" + prefix + "chan` WHERE channel=@channel@"; + query.SetValue("channel", c->name); + this->RunQuery(query); +} + +void IRC2SQL::OnJoinChannel(User *u, Channel *c) +{ + Anope::string modes; + ChanUserContainer *cu = u->FindChannel(c); + if (cu) + modes = cu->status.Modes(); + + query = "CALL " + prefix + "JoinUser(@nick@,@channel@,@modes@)"; + query.SetValue("nick", u->nick); + query.SetValue("channel", c->name); + query.SetValue("modes", modes); + this->RunQuery(query); +} + +EventReturn IRC2SQL::OnChannelModeSet(Channel *c, MessageSource &setter, ChannelMode *mode, const Anope::string ¶m) +{ + if (mode->type == MODE_STATUS) + { + User *u = User::Find(param); + if (u == NULL) + return EVENT_CONTINUE; + + ChanUserContainer *cc = u->FindChannel(c); + if (cc == NULL) + return EVENT_CONTINUE; + + query = "UPDATE `" + prefix + "user` AS u, `" + prefix + "ison` AS i, `" + prefix + "chan` AS c" + " SET i.modes=@modes@" + " WHERE u.nick=@nick@ AND c.channel=@channel@" + " AND u.nickid = i.nickid AND c.chanid = i.chanid"; + query.SetValue("nick", u->nick); + query.SetValue("modes", cc->status.Modes()); + query.SetValue("channel", c->name); + this->RunQuery(query); + } + else + { + query = "UPDATE `" + prefix + "chan` SET modes=@modes@ WHERE channel=@channel@"; + query.SetValue("channel", c->name); + query.SetValue("modes", c->GetModes(true,true)); + this->RunQuery(query); + } + return EVENT_CONTINUE; +} + +EventReturn IRC2SQL::OnChannelModeUnset(Channel *c, MessageSource &setter, ChannelMode *mode, const Anope::string ¶m) +{ + this->OnChannelModeSet(c, setter, mode, param); + return EVENT_CONTINUE; +} + +void IRC2SQL::OnLeaveChannel(User *u, Channel *c) +{ + if (quitting) + return; + /* + * user is quitting, we already received a OnUserQuit() + * at this point the user is already removed from SQL and all channels + */ + if (u->Quitting()) + return; + query = "CALL " + prefix + "PartUser(@nick@,@channel@)"; + query.SetValue("nick", u->nick); + query.SetValue("channel", c->name); + this->RunQuery(query); +} + +void IRC2SQL::OnTopicUpdated(User *source, Channel *c, const Anope::string &user, const Anope::string &topic) +{ + query = "UPDATE `" + prefix + "chan` " + "SET topic=@topic@, topicauthor=@author@, topictime=FROM_UNIXTIME(@time@) " + "WHERE channel=@channel@"; + query.SetValue("topic", c->topic); + query.SetValue("author", c->topic_setter); + query.SetValue("time", c->topic_ts); + query.SetValue("channel", c->name); + this->RunQuery(query); +} + +void IRC2SQL::OnBotNotice(User *u, BotInfo *bi, Anope::string &message) +{ + Anope::string versionstr; + if (bi != StatServ) + return; + if (message[0] == '\1' && message[message.length() - 1] == '\1') + { + if (message.substr(0, 9).equals_ci("\1VERSION ")) + { + if (u->HasExt("CTCPVERSION")) + return; + u->Extend("CTCPVERSION"); + + versionstr = Anope::NormalizeBuffer(message.substr(9, message.length() - 10)); + if (versionstr.empty()) + return; + query = "UPDATE `" + prefix + "user` " + "SET version=@version@ " + "WHERE nick=@nick@"; + query.SetValue("version", versionstr); + query.SetValue("nick", u->nick); + this->RunQuery(query); + } + } +} + +MODULE_INIT(IRC2SQL) diff --git a/modules/extra/stats/irc2sql/irc2sql.h b/modules/extra/stats/irc2sql/irc2sql.h new file mode 100644 index 0000000..bb385c6 --- /dev/null +++ b/modules/extra/stats/irc2sql/irc2sql.h @@ -0,0 +1,84 @@ +/* + * + * (C) 2013-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/sql.h" + +class MySQLInterface : public SQL::Interface +{ + public: + MySQLInterface(Module *o) : SQL::Interface(o) { } + + void OnResult(const SQL::Result &r) anope_override + { + } + + void OnError(const SQL::Result &r) anope_override + { + if (!r.GetQuery().query.empty()) + Log(LOG_DEBUG) << "m_irc2sql: Error executing query " << r.finished_query << ": " << r.GetError(); + else + Log(LOG_DEBUG) << "m_irc2sql: Error executing query: " << r.GetError(); + } +}; + +class IRC2SQL : public Module +{ + ServiceReference sql; + MySQLInterface sqlinterface; + SQL::Query query; + std::vector TableList, ProcedureList, EventList; + Anope::string prefix, GeoIPDB; + bool quitting, introduced_myself, ctcpuser, ctcpeob, firstrun; + BotInfo *StatServ; + PrimitiveExtensibleItem versionreply; + + void RunQuery(const SQL::Query &q); + void GetTables(); + + bool HasTable(const Anope::string &table); + bool HasProcedure(const Anope::string &table); + bool HasEvent(const Anope::string &table); + + void CheckTables(); + + public: + IRC2SQL(const Anope::string &modname, const Anope::string &creator) : + Module(modname, creator, EXTRA | VENDOR), sql("", ""), sqlinterface(this), versionreply(this, "CTCPVERSION") + { + firstrun = true; + quitting = false; + introduced_myself = false; + } + + void OnShutdown() anope_override; + void OnReload(Configuration::Conf *config) anope_override; + void OnNewServer(Server *server) anope_override; + void OnServerQuit(Server *server) anope_override; + void OnUserConnect(User *u, bool &exempt) anope_override; + void OnUserQuit(User *u, const Anope::string &msg) anope_override; + void OnUserNickChange(User *u, const Anope::string &oldnick) anope_override; + void OnUserAway(User *u, const Anope::string &message) anope_override; + void OnFingerprint(User *u) anope_override; + void OnUserModeSet(const MessageSource &setter, User *u, const Anope::string &mname) anope_override; + void OnUserModeUnset(const MessageSource &setter, User *u, const Anope::string &mname) anope_override; + void OnUserLogin(User *u) anope_override; + void OnNickLogout(User *u) anope_override; + void OnSetDisplayedHost(User *u) anope_override; + + void OnChannelCreate(Channel *c) anope_override; + void OnChannelDelete(Channel *c) anope_override; + void OnLeaveChannel(User *u, Channel *c) anope_override; + void OnJoinChannel(User *u, Channel *c) anope_override; + EventReturn OnChannelModeSet(Channel *c, MessageSource &setter, ChannelMode *mode, const Anope::string ¶m) anope_override; + EventReturn OnChannelModeUnset(Channel *c, MessageSource &setter, ChannelMode *mode, const Anope::string ¶m) anope_override; + + void OnTopicUpdated(User *source, Channel *c, const Anope::string &user, const Anope::string &topic) anope_override; + + void OnBotNotice(User *u, BotInfo *bi, Anope::string &message) anope_override; +}; diff --git a/modules/extra/stats/irc2sql/tables.cpp b/modules/extra/stats/irc2sql/tables.cpp new file mode 100644 index 0000000..45fa301 --- /dev/null +++ b/modules/extra/stats/irc2sql/tables.cpp @@ -0,0 +1,343 @@ +/* + * + * (C) 2013-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "irc2sql.h" + +void IRC2SQL::CheckTables() +{ + Anope::string geoquery(""); + + if (firstrun) + { + /* + * reset some tables to make sure they are really empty + */ + this->sql->RunQuery("TRUNCATE TABLE " + prefix + "user"); + this->sql->RunQuery("TRUNCATE TABLE " + prefix + "chan"); + this->sql->RunQuery("TRUNCATE TABLE " + prefix + "ison"); + this->sql->RunQuery("UPDATE `" + prefix + "server` SET currentusers=0, online='N'"); + } + + this->GetTables(); + + if (GeoIPDB.equals_ci("country")) + { + if (!this->HasTable(prefix + "geoip_country")) + { + query = "CREATE TABLE `" + prefix + "geoip_country` (" + "`start` INT UNSIGNED NOT NULL," + "`end` INT UNSIGNED NOT NULL," + "`countrycode` varchar(2)," + "`countryname` varchar(50)," + "PRIMARY KEY `end` (`end`)," + "KEY `start` (`start`)" + ") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"; + this->RunQuery(query); + } + } + else if (GeoIPDB.equals_ci("city")) + { + if (!this->HasTable(prefix + "geoip_city_blocks")) + { + query = "CREATE TABLE `" + prefix + "geoip_city_blocks` (" + "`start` INT UNSIGNED NOT NULL," + "`end` INT UNSIGNED NOT NULL," + "`locId` INT UNSIGNED NOT NULL," + "PRIMARY KEY `end` (`end`)," + "KEY `start` (`start`)" + ") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"; + this->RunQuery(query); + } + if (!this->HasTable(prefix + "geoip_city_location")) + { + query = "CREATE TABLE `" + prefix + "geoip_city_location` (" + "`locId` INT UNSIGNED NOT NULL," + "`country` CHAR(2) NOT NULL," + "`region` CHAR(2) NOT NULL," + "`city` VARCHAR(50)," + "`latitude` FLOAT," + "`longitude` FLOAT," + "`areaCode` INT," + "PRIMARY KEY (`locId`)" + ") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"; + this->RunQuery(query); + } + if (!this->HasTable(prefix + "geoip_city_region")) + { query = "CREATE TABLE `" + prefix + "geoip_city_region` (" + "`country` CHAR(2) NOT NULL," + "`region` CHAR(2) NOT NULL," + "`regionname` VARCHAR(100) NOT NULL," + "PRIMARY KEY (`country`,`region`)" + ") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"; + this->RunQuery(query); + } + } + if (!this->HasTable(prefix + "server")) + { + query = "CREATE TABLE `" + prefix + "server` (" + "`id` int(11) UNSIGNED NOT NULL AUTO_INCREMENT," + "`name` varchar(64) NOT NULL," + "`hops` tinyint(3) NOT NULL," + "`comment` varchar(255) NOT NULL," + "`link_time` datetime DEFAULT NULL," + "`split_time` datetime DEFAULT NULL," + "`version` varchar(127) DEFAULT NULL," + "`currentusers` int(15) DEFAULT 0," + "`online` enum('Y','N') NOT NULL DEFAULT 'Y'," + "`ulined` enum('Y','N') NOT NULL DEFAULT 'N'," + "PRIMARY KEY (`id`)," + "UNIQUE KEY `name` (`name`)" + ") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"; + this->RunQuery(query); + } + if (!this->HasTable(prefix + "chan")) + { + query = "CREATE TABLE `" + prefix + "chan` (" + "`chanid` int(11) UNSIGNED NOT NULL AUTO_INCREMENT," + "`channel` varchar(255) NOT NULL," + "`topic` varchar(512) DEFAULT NULL," + "`topicauthor` varchar(255) DEFAULT NULL," + "`topictime` datetime DEFAULT NULL," + "`modes` varchar(512) DEFAULT NULL," + "PRIMARY KEY (`chanid`)," + "UNIQUE KEY `channel`(`channel`)" + ") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"; + this->RunQuery(query); + } + if (!this->HasTable(prefix + "user")) + { + query = "CREATE TABLE `" + prefix + "user` (" + "`nickid` int(11) UNSIGNED NOT NULL AUTO_INCREMENT," + "`nick` varchar(255) NOT NULL DEFAULT ''," + "`host` varchar(255) NOT NULL DEFAULT ''," + "`vhost` varchar(255) NOT NULL DEFAULT ''," + "`chost` varchar(255) NOT NULL DEFAULT ''," + "`realname` varchar(255) NOT NULL DEFAULT ''," + "`ip` varchar(255) NOT NULL DEFAULT ''," + "`ident` varchar(32) NOT NULL DEFAULT ''," + "`vident` varchar(32) NOT NULL DEFAULT ''," + "`modes` varchar(255) NOT NULL DEFAULT ''," + "`account` varchar(255) NOT NULL DEFAULT ''," + "`secure` enum('Y','N') NOT NULL DEFAULT 'N'," + "`fingerprint` varchar(128) NOT NULL DEFAULT ''," + "`signon` datetime DEFAULT NULL," + "`server` varchar(255) NOT NULL DEFAULT ''," + "`servid` int(11) UNSIGNED NOT NULL DEFAULT '0'," + "`uuid` varchar(32) NOT NULL DEFAULT ''," + "`oper` enum('Y','N') NOT NULL DEFAULT 'N'," + "`away` enum('Y','N') NOT NULL DEFAULT 'N'," + "`awaymsg` varchar(255) NOT NULL DEFAULT ''," + "`version` varchar(255) NOT NULL DEFAULT ''," + "`geocode` varchar(16) NOT NULL DEFAULT ''," + "`geocountry` varchar(64) NOT NULL DEFAULT ''," + "`georegion` varchar(100) NOT NULL DEFAULT ''," + "`geocity` varchar(128) NOT NULL DEFAULT ''," + "`locId` INT UNSIGNED," + "PRIMARY KEY (`nickid`)," + "UNIQUE KEY `nick` (`nick`)," + "KEY `servid` (`servid`)" + ") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"; + this->RunQuery(query); + } + if (!this->HasTable(prefix + "ison")) + { + query = "CREATE TABLE `" + prefix + "ison` (" + "`nickid` int(11) unsigned NOT NULL default '0'," + "`chanid` int(11) unsigned NOT NULL default '0'," + "`modes` varchar(255) NOT NULL default ''," + "PRIMARY KEY (`nickid`,`chanid`)," + "KEY `modes` (`modes`)" + ") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"; + this->RunQuery(query); + } + if (!this->HasTable(prefix + "maxusers")) + { + query = "CREATE TABLE `" + prefix + "maxusers` (" + "`name` VARCHAR(255) NOT NULL," + "`maxusers` INT(15) NOT NULL," + "`maxtime` DATETIME NOT NULL," + "`lastused` DATETIME NOT NULL," + "UNIQUE KEY `name` (`name`)" + ") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"; + this->RunQuery(query); + } + if (this->HasProcedure(prefix + "UserConnect")) + this->RunQuery(SQL::Query("DROP PROCEDURE " + prefix + "UserConnect")); + + if (GeoIPDB.equals_ci("country")) + geoquery = "UPDATE `" + prefix + "user` AS u " + "JOIN ( SELECT `countrycode`, `countryname` " + "FROM `" + prefix + "geoip_country` " + "WHERE INET_ATON(ip_) <= `end` " + "AND `start` <= INET_ATON(ip_) " + "ORDER BY `end` ASC LIMIT 1 ) as c " + "SET u.geocode = c.countrycode, u.geocountry = c.countryname " + "WHERE u.nick = nick_; "; + else if (GeoIPDB.equals_ci("city")) + geoquery = "UPDATE `" + prefix + "user` as u " + "JOIN ( SELECT * FROM `" + prefix + "geoip_city_location` " + "WHERE `locID` = ( SELECT `locID` " + "FROM `" + prefix + "geoip_city_blocks` " + "WHERE INET_ATON(ip_) <= `end` " + "AND `start` <= INET_ATON(ip_) " + "ORDER BY `end` ASC LIMIT 1 ) " + ") as l " + "SET u.geocode = l.country, " + "u.geocity = l.city, " + "u.locID = l.locID, " + "u.georegion = ( SELECT `regionname` " + "FROM `" + prefix + "geoip_city_region` " + "WHERE `country` = l.country " + "AND `region` = l.region )" + "WHERE u.nick = nick_;"; + + query = "CREATE PROCEDURE `" + prefix + "UserConnect`" + "(nick_ varchar(255), host_ varchar(255), vhost_ varchar(255), " + "chost_ varchar(255), realname_ varchar(255), ip_ varchar(255), " + "ident_ varchar(255), vident_ varchar(255), account_ varchar(255), " + "secure_ enum('Y','N'), fingerprint_ varchar(255), signon_ int(15), " + "server_ varchar(255), uuid_ varchar(32), modes_ varchar(255), " + "oper_ enum('Y','N')) " + "BEGIN " + "DECLARE cur int(15);" + "DECLARE max int(15);" + "INSERT INTO `" + prefix + "user` " + "(nick, host, vhost, chost, realname, ip, ident, vident, account, " + "secure, fingerprint, signon, server, uuid, modes, oper) " + "VALUES (nick_, host_, vhost_, chost_, realname_, ip_, ident_, vident_, " + "account_, secure_, fingerprint_, FROM_UNIXTIME(signon_), server_, " + "uuid_, modes_, oper_) " + "ON DUPLICATE KEY UPDATE host=VALUES(host), vhost=VALUES(vhost), " + "chost=VALUES(chost), realname=VALUES(realname), ip=VALUES(ip), " + "ident=VALUES(ident), vident=VALUES(vident), account=VALUES(account), " + "secure=VALUES(secure), fingerprint=VALUES(fingerprint), signon=VALUES(signon), " + "server=VALUES(server), uuid=VALUES(uuid), modes=VALUES(modes), " + "oper=VALUES(oper);" + "UPDATE `" + prefix + "user` as `u`, `" + prefix + "server` as `s`" + "SET u.servid = s.id, " + "s.currentusers = s.currentusers + 1 " + "WHERE s.name = server_ AND u.nick = nick_;" + "SELECT `currentusers` INTO cur FROM `" + prefix + "server` WHERE name=server_;" + "SELECT `maxusers` INTO max FROM `" + prefix + "maxusers` WHERE name=server_;" + "IF found_rows() AND cur <= max THEN " + "UPDATE `" + prefix + "maxusers` SET lastused=now() WHERE name=server_;" + "ELSE " + "INSERT INTO `" + prefix + "maxusers` (name, maxusers, maxtime, lastused) " + "VALUES ( server_, cur, now(), now() ) " + "ON DUPLICATE KEY UPDATE " + "name=VALUES(name), maxusers=VALUES(maxusers)," + "maxtime=VALUES(maxtime), lastused=VALUES(lastused);" + "END IF;" + + geoquery + + "END"; + this->RunQuery(query); + + if (this->HasProcedure(prefix + "ServerQuit")) + this->RunQuery(SQL::Query("DROP PROCEDURE " + prefix + "ServerQuit")); + query = "CREATE PROCEDURE " + prefix + "ServerQuit(sname_ varchar(255)) " + "BEGIN " + /* 1. + * remove all users on the splitting server from the ison table + */ + "DELETE i FROM `" + prefix + "ison` AS i " + "INNER JOIN `" + prefix + "server` AS s " + "INNER JOIN `" + prefix + "user` AS u " + "WHERE i.nickid = u.nickid " + "AND u.servid = s.id " + "AND s.name = sname_;" + + /* 2. + * remove all users on the splitting server from the user table + */ + "DELETE u FROM `" + prefix + "user` AS u " + "INNER JOIN `" + prefix + "server` AS s " + "WHERE s.id = u.servid " + "AND s.name = sname_;" + + /* 3. + * on the splitting server, set usercount = 0, split_time = now(), online = 'N' + */ + "UPDATE `" + prefix + "server` SET currentusers = 0, split_time = now(), online = 'N' " + "WHERE name = sname_;" + "END;"; // end of the procedure + this->RunQuery(query); + + + if (this->HasProcedure(prefix + "UserQuit")) + this->RunQuery(SQL::Query("DROP PROCEDURE " + prefix + "UserQuit")); + query = "CREATE PROCEDURE `" + prefix + "UserQuit`" + "(nick_ varchar(255)) " + "BEGIN " + /* decrease usercount on the server where the user was on */ + "UPDATE `" + prefix + "user` AS `u`, `" + prefix + "server` AS `s` " + "SET s.currentusers = s.currentusers - 1 " + "WHERE u.nick=nick_ AND u.servid = s.id; " + /* remove from all channels where the user was on */ + "DELETE i FROM `" + prefix + "ison` AS i " + "INNER JOIN `" + prefix + "user` as u " + "WHERE u.nick = nick_ " + "AND i.nickid = u.nickid;" + /* remove the user from the user table */ + "DELETE FROM `" + prefix + "user` WHERE nick = nick_; " + "END"; + this->RunQuery(query); + + if (this->HasProcedure(prefix + "ShutDown")) + this->RunQuery(SQL::Query("DROP PROCEDURE " + prefix + "ShutDown")); + query = "CREATE PROCEDURE `" + prefix + "ShutDown`()" + "BEGIN " + "UPDATE `" + prefix + "server` " + "SET currentusers=0, online='N', split_time=now();" + "TRUNCATE TABLE `" + prefix + "user`;" + "TRUNCATE TABLE `" + prefix + "chan`;" + "TRUNCATE TABLE `" + prefix + "ison`;" + "END"; + this->RunQuery(query); + + if (this->HasProcedure(prefix + "JoinUser")) + this->RunQuery(SQL::Query("DROP PROCEDURE " + prefix + "JoinUser")); + query = "CREATE PROCEDURE `"+ prefix + "JoinUser`" + "(nick_ varchar(255), channel_ varchar(255), modes_ varchar(255)) " + "BEGIN " + "DECLARE cur int(15);" + "DECLARE max int(15);" + "INSERT INTO `" + prefix + "ison` (nickid, chanid, modes) " + "SELECT u.nickid, c.chanid, modes_ " + "FROM " + prefix + "user AS u, " + prefix + "chan AS c " + "WHERE u.nick=nick_ AND c.channel=channel_;" + "SELECT count(i.chanid) INTO cur " + "FROM `" + prefix + "chan` AS c, " + prefix + "ison AS i " + "WHERE i.chanid = c.chanid AND c.channel=channel_;" + "SELECT `maxusers` INTO max FROM `" + prefix + "maxusers` WHERE name=channel_;" + "IF found_rows() AND cur <= max THEN " + "UPDATE `" + prefix + "maxusers` SET lastused=now() WHERE name=channel_;" + "ELSE " + "INSERT INTO `" + prefix + "maxusers` (name, maxusers, maxtime, lastused) " + "VALUES ( channel_, cur, now(), now() ) " + "ON DUPLICATE KEY UPDATE " + "name=VALUES(name), maxusers=VALUES(maxusers)," + "maxtime=VALUES(maxtime), lastused=VALUES(lastused);" + "END IF;" + "END"; + this->RunQuery(query); + + if (this->HasProcedure(prefix + "PartUser")) + this->RunQuery(SQL::Query("DROP PROCEDURE " + prefix + "PartUser")); + query = "CREATE PROCEDURE `" + prefix + "PartUser`" + "(nick_ varchar(255), channel_ varchar(255)) " + "BEGIN " + "DELETE i FROM `" + prefix + "ison` AS i " + "INNER JOIN `" + prefix + "user` AS u " + "INNER JOIN `" + prefix + "chan` AS c " + "WHERE i.nickid = u.nickid " + "AND u.nick = nick_ " + "AND i.chanid = c.chanid " + "AND c.channel = channel_;" + "END"; + this->RunQuery(query); +} diff --git a/modules/extra/stats/irc2sql/utils.cpp b/modules/extra/stats/irc2sql/utils.cpp new file mode 100644 index 0000000..888fc0c --- /dev/null +++ b/modules/extra/stats/irc2sql/utils.cpp @@ -0,0 +1,68 @@ +/* + * + * (C) 2013-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "irc2sql.h" + +void IRC2SQL::RunQuery(const SQL::Query &q) +{ + if (sql) + sql->Run(&sqlinterface, q); +} + +void IRC2SQL::GetTables() +{ + TableList.clear(); + ProcedureList.clear(); + EventList.clear(); + if (!sql) + return; + + SQL::Result r = this->sql->RunQuery(this->sql->GetTables(prefix)); + for (int i = 0; i < r.Rows(); ++i) + { + const std::map &map = r.Row(i); + for (std::map::const_iterator it = map.begin(); it != map.end(); ++it) + TableList.push_back(it->second); + } + query = "SHOW PROCEDURE STATUS WHERE `Db` = Database();"; + r = this->sql->RunQuery(query); + for (int i = 0; i < r.Rows(); ++i) + { + ProcedureList.push_back(r.Get(i, "Name")); + } + query = "SHOW EVENTS WHERE `Db` = Database();"; + r = this->sql->RunQuery(query); + for (int i = 0; i < r.Rows(); ++i) + { + EventList.push_back(r.Get(i, "Name")); + } +} + +bool IRC2SQL::HasTable(const Anope::string &table) +{ + for (std::vector::const_iterator it = TableList.begin(); it != TableList.end(); ++it) + if (*it == table) + return true; + return false; +} + +bool IRC2SQL::HasProcedure(const Anope::string &table) +{ + for (std::vector::const_iterator it = ProcedureList.begin(); it != ProcedureList.end(); ++it) + if (*it == table) + return true; + return false; +} + +bool IRC2SQL::HasEvent(const Anope::string &table) +{ + for (std::vector::const_iterator it = EventList.begin(); it != EventList.end(); ++it) + if (*it == table) + return true; + return false; +} diff --git a/modules/extra/stats/m_chanstats.cpp b/modules/extra/stats/m_chanstats.cpp new file mode 100644 index 0000000..60ecd6b --- /dev/null +++ b/modules/extra/stats/m_chanstats.cpp @@ -0,0 +1,655 @@ +/* + * + * (C) 2012-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/sql.h" + +class CommandCSSetChanstats : public Command +{ + public: + CommandCSSetChanstats(Module *creator) : Command(creator, "chanserv/set/chanstats", 2, 2) + { + this->SetDesc(_("Turn chanstats statistics on or off")); + this->SetSyntax(_("\037channel\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci = ChannelInfo::Find(params[0]); + if (!ci) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetChannelOption, MOD_RESULT, (source, this, ci, params[1])); + if (MOD_RESULT == EVENT_STOP) + return; + + if (MOD_RESULT != EVENT_ALLOW && !source.AccessFor(ci).HasPriv("SET") && source.permission.empty() && !source.HasPriv("chanserv/administration")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (params[1].equals_ci("ON")) + { + ci->Extend("CS_STATS"); + source.Reply(_("Chanstats statistics are now enabled for this channel.")); + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to enable chanstats"; + } + else if (params[1].equals_ci("OFF")) + { + Log(source.AccessFor(ci).HasPriv("SET") ? LOG_COMMAND : LOG_OVERRIDE, source, this, ci) << "to disable chanstats"; + ci->Shrink("CS_STATS"); + source.Reply(_("Chanstats statistics are now disabled for this channel.")); + } + else + this->OnSyntaxError(source, ""); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Turns chanstats statistics ON or OFF.")); + return true; + } +}; + +class CommandNSSetChanstats : public Command +{ + public: + CommandNSSetChanstats(Module *creator, const Anope::string &sname = "nickserv/set/chanstats", size_t min = 1 ) : Command(creator, sname, min, min + 1) + { + this->SetDesc(_("Turn chanstats statistics on or off")); + this->SetSyntax("{ON | OFF}"); + } + void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m, bool saset = false) + { + NickAlias *na = NickAlias::Find(user); + if (!na) + { + source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, na->nc, param)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (param.equals_ci("ON")) + { + Log(na->nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to enable chanstats for " << na->nc->display; + na->nc->Extend("NS_STATS"); + if (saset) + source.Reply(_("Chanstats statistics are now enabled for %s"), na->nc->display.c_str()); + else + source.Reply(_("Chanstats statistics are now enabled for your nick.")); + } + else if (param.equals_ci("OFF")) + { + Log(na->nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to disable chanstats for " << na->nc->display; + na->nc->Shrink("NS_STATS"); + if (saset) + source.Reply(_("Chanstats statistics are now disabled for %s"), na->nc->display.c_str()); + else + source.Reply(_("Chanstats statistics are now disabled for your nick.")); + } + else + this->OnSyntaxError(source, "CHANSTATS"); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, source.nc->display, params[0]); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Turns chanstats statistics ON or OFF.")); + return true; + } +}; + +class CommandNSSASetChanstats : public CommandNSSetChanstats +{ + public: + CommandNSSASetChanstats(Module *creator) : CommandNSSetChanstats(creator, "nickserv/saset/chanstats", 2) + { + this->ClearSyntax(); + this->SetSyntax(_("\037nickname\037 {ON | OFF}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + this->Run(source, params[0], params[1], true); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(" "); + source.Reply(_("Turns chanstats channel statistics ON or OFF for this user.")); + return true; + } +}; + +class MySQLInterface : public SQL::Interface +{ + public: + MySQLInterface(Module *o) : SQL::Interface(o) { } + + void OnResult(const SQL::Result &r) anope_override + { + } + + void OnError(const SQL::Result &r) anope_override + { + if (!r.GetQuery().query.empty()) + Log(LOG_DEBUG) << "Chanstats: Error executing query " << r.finished_query << ": " << r.GetError(); + else + Log(LOG_DEBUG) << "Chanstats: Error executing query: " << r.GetError(); + } +}; + +class MChanstats : public Module +{ + SerializableExtensibleItem cs_stats, ns_stats; + + CommandCSSetChanstats commandcssetchanstats; + + CommandNSSetChanstats commandnssetchanstats; + CommandNSSASetChanstats commandnssasetchanstats; + + ServiceReference sql; + MySQLInterface sqlinterface; + SQL::Query query; + Anope::string SmileysHappy, SmileysSad, SmileysOther, prefix; + std::vector TableList, ProcedureList, EventList; + bool NSDefChanstats, CSDefChanstats; + + void RunQuery(const SQL::Query &q) + { + if (sql) + sql->Run(&sqlinterface, q); + } + + size_t CountWords(const Anope::string &msg) + { + size_t words = 0; + for (size_t pos = 0; pos != Anope::string::npos; pos = msg.find(" ", pos+1)) + words++; + return words; + } + size_t CountSmileys(const Anope::string &msg, const Anope::string &smileylist) + { + size_t smileys = 0; + spacesepstream sep(smileylist); + Anope::string buf; + + while (sep.GetToken(buf) && !buf.empty()) + { + for (size_t pos = msg.find(buf, 0); pos != Anope::string::npos; pos = msg.find(buf, pos+1)) + smileys++; + } + return smileys; + } + + const Anope::string GetDisplay(User *u) + { + if (u && u->Account() && ns_stats.HasExt(u->Account())) + return u->Account()->display; + else + return ""; + } + + void GetTables() + { + TableList.clear(); + ProcedureList.clear(); + EventList.clear(); + if (!sql) + return; + + SQL::Result r = this->sql->RunQuery(this->sql->GetTables(prefix)); + for (int i = 0; i < r.Rows(); ++i) + { + const std::map &map = r.Row(i); + for (std::map::const_iterator it = map.begin(); it != map.end(); ++it) + TableList.push_back(it->second); + } + query = "SHOW PROCEDURE STATUS WHERE `Db` = Database();"; + r = this->sql->RunQuery(query); + for (int i = 0; i < r.Rows(); ++i) + { + ProcedureList.push_back(r.Get(i, "Name")); + } + query = "SHOW EVENTS WHERE `Db` = Database();"; + r = this->sql->RunQuery(query); + for (int i = 0; i < r.Rows(); ++i) + { + EventList.push_back(r.Get(i, "Name")); + } + } + + bool HasTable(const Anope::string &table) + { + for (std::vector::const_iterator it = TableList.begin(); it != TableList.end(); ++it) + if (*it == table) + return true; + return false; + } + + bool HasProcedure(const Anope::string &table) + { + for (std::vector::const_iterator it = ProcedureList.begin(); it != ProcedureList.end(); ++it) + if (*it == table) + return true; + return false; + } + + bool HasEvent(const Anope::string &table) + { + for (std::vector::const_iterator it = EventList.begin(); it != EventList.end(); ++it) + if (*it == table) + return true; + return false; + } + + + void CheckTables() + { + this->GetTables(); + if (!this->HasTable(prefix +"chanstats")) + { + query = "CREATE TABLE `" + prefix + "chanstats` (" + "`id` int(11) NOT NULL AUTO_INCREMENT," + "`chan` varchar(64) NOT NULL DEFAULT ''," + "`nick` varchar(64) NOT NULL DEFAULT ''," + "`type` ENUM('total', 'monthly', 'weekly', 'daily') NOT NULL," + "`letters` int(10) unsigned NOT NULL DEFAULT '0'," + "`words` int(10) unsigned NOT NULL DEFAULT '0'," + "`line` int(10) unsigned NOT NULL DEFAULT '0'," + "`actions` int(10) unsigned NOT NULL DEFAULT '0'," + "`smileys_happy` int(10) unsigned NOT NULL DEFAULT '0'," + "`smileys_sad` int(10) unsigned NOT NULL DEFAULT '0'," + "`smileys_other` int(10) unsigned NOT NULL DEFAULT '0'," + "`kicks` int(10) unsigned NOT NULL DEFAULT '0'," + "`kicked` int(10) unsigned NOT NULL DEFAULT '0'," + "`modes` int(10) unsigned NOT NULL DEFAULT '0'," + "`topics` int(10) unsigned NOT NULL DEFAULT '0'," + "`time0` int(10) unsigned NOT NULL default '0'," + "`time1` int(10) unsigned NOT NULL default '0'," + "`time2` int(10) unsigned NOT NULL default '0'," + "`time3` int(10) unsigned NOT NULL default '0'," + "`time4` int(10) unsigned NOT NULL default '0'," + "`time5` int(10) unsigned NOT NULL default '0'," + "`time6` int(10) unsigned NOT NULL default '0'," + "`time7` int(10) unsigned NOT NULL default '0'," + "`time8` int(10) unsigned NOT NULL default '0'," + "`time9` int(10) unsigned NOT NULL default '0'," + "`time10` int(10) unsigned NOT NULL default '0'," + "`time11` int(10) unsigned NOT NULL default '0'," + "`time12` int(10) unsigned NOT NULL default '0'," + "`time13` int(10) unsigned NOT NULL default '0'," + "`time14` int(10) unsigned NOT NULL default '0'," + "`time15` int(10) unsigned NOT NULL default '0'," + "`time16` int(10) unsigned NOT NULL default '0'," + "`time17` int(10) unsigned NOT NULL default '0'," + "`time18` int(10) unsigned NOT NULL default '0'," + "`time19` int(10) unsigned NOT NULL default '0'," + "`time20` int(10) unsigned NOT NULL default '0'," + "`time21` int(10) unsigned NOT NULL default '0'," + "`time22` int(10) unsigned NOT NULL default '0'," + "`time23` int(10) unsigned NOT NULL default '0'," + "PRIMARY KEY (`id`)," + "UNIQUE KEY `chan` (`chan`,`nick`,`type`)," + "KEY `nick` (`nick`)," + "KEY `chan_` (`chan`)," + "KEY `type` (`type`)" + ") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"; + this->RunQuery(query); + } + /* There is no CREATE OR REPLACE PROCEDURE in MySQL */ + if (this->HasProcedure(prefix + "chanstats_proc_update")) + { + query = "DROP PROCEDURE " + prefix + "chanstats_proc_update"; + this->RunQuery(query); + } + query = "CREATE PROCEDURE `" + prefix + "chanstats_proc_update`" + "(chan_ VARCHAR(255), nick_ VARCHAR(255), line_ INT(10), letters_ INT(10)," + "words_ INT(10), actions_ INT(10), sm_h_ INT(10), sm_s_ INT(10), sm_o_ INT(10)," + "kicks_ INT(10), kicked_ INT(10), modes_ INT(10), topics_ INT(10))" + "BEGIN " + "DECLARE time_ VARCHAR(20);" + "SET time_ = CONCAT('time', hour(now()));" + "INSERT IGNORE INTO `" + prefix + "chanstats` (`nick`,`chan`, `type`) VALUES " + "('', chan_, 'total'), ('', chan_, 'monthly')," + "('', chan_, 'weekly'), ('', chan_, 'daily');" + "IF nick_ != '' THEN " + "INSERT IGNORE INTO `" + prefix + "chanstats` (`nick`,`chan`, `type`) VALUES " + "(nick_, chan_, 'total'), (nick_, chan_, 'monthly')," + "(nick_, chan_, 'weekly'),(nick_, chan_, 'daily')," + "(nick_, '', 'total'), (nick_, '', 'monthly')," + "(nick_, '', 'weekly'), (nick_, '', 'daily');" + "END IF;" + "SET @update_query = CONCAT('UPDATE `" + prefix + "chanstats` SET line=line+', line_, '," + "letters=letters+', letters_, ' , words=words+', words_, ', actions=actions+', actions_, ', " + "smileys_happy=smileys_happy+', sm_h_, ', smileys_sad=smileys_sad+', sm_s_, ', " + "smileys_other=smileys_other+', sm_o_, ', kicks=kicks+', kicks_, ', kicked=kicked+', kicked_, ', " + "modes=modes+', modes_, ', topics=topics+', topics_, ', ', time_ , '=', time_, '+', line_ ,' " + "WHERE (nick='''' OR nick=''', nick_, ''') AND (chan='''' OR chan=''', chan_, ''')');" + "PREPARE update_query FROM @update_query;" + "EXECUTE update_query;" + "DEALLOCATE PREPARE update_query;" + "END"; + this->RunQuery(query); + + if (this->HasProcedure(prefix + "chanstats_proc_chgdisplay")) + { + query = "DROP PROCEDURE " + prefix + "chanstats_proc_chgdisplay;"; + this->RunQuery(query); + } + query = "CREATE PROCEDURE `" + prefix + "chanstats_proc_chgdisplay`" + "(old_nick varchar(255), new_nick varchar(255))" + "BEGIN " + "DECLARE res_count int(10) unsigned;" + "SELECT COUNT(nick) INTO res_count FROM `" + prefix + "chanstats` WHERE nick = new_nick;" + "IF res_count = 0 THEN " + "UPDATE `" + prefix + "chanstats` SET `nick` = new_nick WHERE `nick` = old_nick;" + "ELSE " + "my_cursor: BEGIN " + "DECLARE no_more_rows BOOLEAN DEFAULT FALSE;" + "DECLARE chan_ VARCHAR(255);" + "DECLARE type_ ENUM('total', 'monthly', 'weekly', 'daily');" + "DECLARE letters_, words_, line_, actions_, smileys_happy_," + "smileys_sad_, smileys_other_, kicks_, kicked_, modes_, topics_," + "time0_, time1_, time2_, time3_, time4_, time5_, time6_, time7_, time8_, time9_," + "time10_, time11_, time12_, time13_, time14_, time15_, time16_, time17_, time18_," + "time19_, time20_, time21_, time22_, time23_ INT(10) unsigned;" + "DECLARE stats_cursor CURSOR FOR " + "SELECT chan, type, letters, words, line, actions, smileys_happy," + "smileys_sad, smileys_other, kicks, kicked, modes, topics, time0, time1," + "time2, time3, time4, time5, time6, time7, time8, time9, time10, time11," + "time12, time13, time14, time15, time16, time17, time18, time19, time20," + "time21, time22, time23 " + "FROM `" + prefix + "chanstats` " + "WHERE `nick` = old_nick;" + "DECLARE CONTINUE HANDLER FOR NOT FOUND " + "SET no_more_rows = TRUE;" + "OPEN stats_cursor;" + "the_loop: LOOP " + "FETCH stats_cursor " + "INTO chan_, type_, letters_, words_, line_, actions_, smileys_happy_," + "smileys_sad_, smileys_other_, kicks_, kicked_, modes_, topics_," + "time0_, time1_, time2_, time3_, time4_, time5_, time6_, time7_, time8_," + "time9_, time10_, time11_, time12_, time13_, time14_, time15_, time16_," + "time17_, time18_, time19_, time20_, time21_, time22_, time23_;" + "IF no_more_rows THEN " + "CLOSE stats_cursor;" + "LEAVE the_loop;" + "END IF;" + "INSERT INTO `" + prefix + "chanstats` " + "(chan, nick, type, letters, words, line, actions, smileys_happy, " + "smileys_sad, smileys_other, kicks, kicked, modes, topics, time0, time1, " + "time2, time3, time4, time5, time6, time7, time8, time9, time10, time11," + "time12, time13, time14, time15, time16, time17, time18, time19, time20," + "time21, time22, time23)" + "VALUES (chan_, new_nick, type_, letters_, words_, line_, actions_, smileys_happy_," + "smileys_sad_, smileys_other_, kicks_, kicked_, modes_, topics_," + "time0_, time1_, time2_, time3_, time4_, time5_, time6_, time7_, time8_, " + "time9_, time10_, time11_, time12_, time13_, time14_, time15_, time16_, " + "time17_, time18_, time19_, time20_, time21_, time22_, time23_)" + "ON DUPLICATE KEY UPDATE letters=letters+VALUES(letters), words=words+VALUES(words)," + "line=line+VALUES(line), actions=actions+VALUES(actions)," + "smileys_happy=smileys_happy+VALUES(smileys_happy)," + "smileys_sad=smileys_sad+VALUES(smileys_sad)," + "smileys_other=smileys_other+VALUES(smileys_other)," + "kicks=kicks+VALUES(kicks), kicked=kicked+VALUES(kicked)," + "modes=modes+VALUES(modes), topics=topics+VALUES(topics)," + "time1=time1+VALUES(time1), time2=time2+VALUES(time2), time3=time3+VALUES(time3)," + "time4=time4+VALUES(time4), time5=time5+VALUES(time5), time6=time6+VALUES(time6)," + "time7=time7+VALUES(time7), time8=time8+VALUES(time8), time9=time9+VALUES(time9)," + "time10=time10+VALUES(time10), time11=time11+VALUES(time11), time12=time12+VALUES(time12)," + "time13=time13+VALUES(time13), time14=time14+VALUES(time14), time15=time15+VALUES(time15)," + "time16=time16+VALUES(time16), time17=time17+VALUES(time17), time18=time18+VALUES(time18)," + "time19=time19+VALUES(time19), time20=time20+VALUES(time20), time21=time21+VALUES(time21)," + "time22=time22+VALUES(time22), time23=time23+VALUES(time23);" + "END LOOP;" + "DELETE FROM `" + prefix + "chanstats` WHERE `nick` = old_nick;" + "END my_cursor;" + "END IF;" + "END;"; + this->RunQuery(query); + + /* don't prepend any database prefix to events so we can always delete/change old events */ + if (this->HasEvent("chanstats_event_cleanup_daily")) + { + query = "DROP EVENT chanstats_event_cleanup_daily"; + this->RunQuery(query); + } + query = "CREATE EVENT `chanstats_event_cleanup_daily` " + "ON SCHEDULE EVERY 1 DAY STARTS CURRENT_DATE " + "DO UPDATE `" + prefix + "chanstats` SET letters=0, words=0, line=0, actions=0, smileys_happy=0," + "smileys_sad=0, smileys_other=0, kicks=0, modes=0, topics=0, time0=0, time1=0, time2=0," + "time3=0, time4=0, time5=0, time6=0, time7=0, time8=0, time9=0, time10=0, time11=0," + "time12=0, time13=0, time14=0, time15=0, time16=0, time17=0, time18=0, time19=0," + "time20=0, time21=0, time22=0, time23=0 " + "WHERE type='daily';"; + this->RunQuery(query); + + if (this->HasEvent("chanstats_event_cleanup_weekly")) + { + query = "DROP EVENT `chanstats_event_cleanup_weekly`"; + this->RunQuery(query); + } + query = "CREATE EVENT `chanstats_event_cleanup_weekly` " + "ON SCHEDULE EVERY 1 WEEK STARTS ADDDATE(CURDATE(), INTERVAL 1-DAYOFWEEK(CURDATE()) DAY) " + "DO UPDATE `" + prefix + "chanstats` SET letters=0, words=0, line=0, actions=0, smileys_happy=0," + "smileys_sad=0, smileys_other=0, kicks=0, modes=0, topics=0, time0=0, time1=0, time2=0," + "time3=0, time4=0, time5=0, time6=0, time7=0, time8=0, time9=0, time10=0, time11=0," + "time12=0, time13=0, time14=0, time15=0, time16=0, time17=0, time18=0, time19=0," + "time20=0, time21=0, time22=0, time23=0 " + "WHERE type='weekly';"; + this->RunQuery(query); + + if (this->HasEvent("chanstats_event_cleanup_monthly")) + { + query = "DROP EVENT `chanstats_event_cleanup_monthly`;"; + this->RunQuery(query); + } + query = "CREATE EVENT `chanstats_event_cleanup_monthly` " + "ON SCHEDULE EVERY 1 MONTH STARTS LAST_DAY(CURRENT_TIMESTAMP) + INTERVAL 1 DAY " + "DO BEGIN " + "UPDATE `" + prefix + "chanstats` SET letters=0, words=0, line=0, actions=0, smileys_happy=0," + "smileys_sad=0, smileys_other=0, kicks=0, modes=0, topics=0, time0=0, time1=0, time2=0," + "time3=0, time4=0, time5=0, time6=0, time7=0, time8=0, time9=0, time10=0, time11=0," + "time12=0, time13=0, time14=0, time15=0, time16=0, time17=0, time18=0, time19=0, " + "time20=0, time21=0, time22=0, time23=0 " + "WHERE type='monthly';" + "OPTIMIZE TABLE `" + prefix + "chanstats`;" + "END;"; + this->RunQuery(query); + } + + + public: + MChanstats(const Anope::string &modname, const Anope::string &creator) : + Module(modname, creator, EXTRA | VENDOR), + cs_stats(this, "CS_STATS"), ns_stats(this, "NS_STATS"), + commandcssetchanstats(this), commandnssetchanstats(this), commandnssasetchanstats(this), + sqlinterface(this) + { + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *block = conf->GetModule(this); + prefix = block->Get("prefix", "anope_"); + SmileysHappy = block->Get("SmileysHappy"); + SmileysSad = block->Get("SmileysSad"); + SmileysOther = block->Get("SmileysOther"); + NSDefChanstats = block->Get("ns_def_chanstats"); + CSDefChanstats = block->Get("cs_def_chanstats"); + Anope::string engine = block->Get("engine"); + this->sql = ServiceReference("SQL::Provider", engine); + if (sql) + this->CheckTables(); + else + Log(this) << "no database connection to " << engine; + } + + void OnChanInfo(CommandSource &source, ChannelInfo *ci, InfoFormatter &info, bool show_all) anope_override + { + if (!show_all) + return; + if (cs_stats.HasExt(ci)) + info.AddOption(_("Chanstats")); + } + + void OnNickInfo(CommandSource &source, NickAlias *na, InfoFormatter &info, bool show_hidden) anope_override + { + if (!show_hidden) + return; + if (ns_stats.HasExt(na->nc)) + info.AddOption(_("Chanstats")); + } + + void OnTopicUpdated(User *source, Channel *c, const Anope::string &user, const Anope::string &topic) anope_override + { + if (!source || !source->Account() || !c->ci || !cs_stats.HasExt(c->ci)) + return; + query = "CALL " + prefix + "chanstats_proc_update(@channel@, @nick@, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1);"; + query.SetValue("channel", c->name); + query.SetValue("nick", GetDisplay(source)); + this->RunQuery(query); + } + + EventReturn OnChannelModeSet(Channel *c, MessageSource &setter, ChannelMode *mode, const Anope::string ¶m) anope_override + { + this->OnModeChange(c, setter.GetUser()); + return EVENT_CONTINUE; + } + + EventReturn OnChannelModeUnset(Channel *c, MessageSource &setter, ChannelMode *, const Anope::string ¶m) anope_override + { + this->OnModeChange(c, setter.GetUser()); + return EVENT_CONTINUE; + } + + private: + void OnModeChange(Channel *c, User *u) + { + if (!u || !u->Account() || !c->ci || !cs_stats.HasExt(c->ci)) + return; + + query = "CALL " + prefix + "chanstats_proc_update(@channel@, @nick@, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0);"; + query.SetValue("channel", c->name); + query.SetValue("nick", GetDisplay(u)); + this->RunQuery(query); + } + + public: + void OnPreUserKicked(const MessageSource &source, ChanUserContainer *cu, const Anope::string &kickmsg) anope_override + { + if (!cu->chan->ci || !cs_stats.HasExt(cu->chan->ci)) + return; + + query = "CALL " + prefix + "chanstats_proc_update(@channel@, @nick@, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0);"; + query.SetValue("channel", cu->chan->name); + query.SetValue("nick", GetDisplay(cu->user)); + this->RunQuery(query); + + query = "CALL " + prefix + "chanstats_proc_update(@channel@, @nick@, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0);"; + query.SetValue("channel", cu->chan->name); + query.SetValue("nick", GetDisplay(source.GetUser())); + this->RunQuery(query); + } + + void OnPrivmsg(User *u, Channel *c, Anope::string &msg) anope_override + { + if (!c->ci || !cs_stats.HasExt(c->ci)) + return; + + size_t letters = msg.length(); + size_t words = this->CountWords(msg); + + size_t action = 0; + if (msg.find("\01ACTION")!=Anope::string::npos) + { + action = 1; + letters = letters - 7; + words--; + } + + // count smileys + size_t smileys_happy = CountSmileys(msg, SmileysHappy); + size_t smileys_sad = CountSmileys(msg, SmileysSad); + size_t smileys_other = CountSmileys(msg, SmileysOther); + + // do not count smileys as words + size_t smileys = smileys_happy + smileys_sad + smileys_other; + if (smileys > words) + words = 0; + else + words = words - smileys; + + query = "CALL " + prefix + "chanstats_proc_update(@channel@, @nick@, 1, @letters@, @words@, @action@, " + "@smileys_happy@, @smileys_sad@, @smileys_other@, '0', '0', '0', '0');"; + query.SetValue("channel", c->name); + query.SetValue("nick", GetDisplay(u)); + query.SetValue("letters", letters); + query.SetValue("words", words); + query.SetValue("action", action); + query.SetValue("smileys_happy", smileys_happy); + query.SetValue("smileys_sad", smileys_sad); + query.SetValue("smileys_other", smileys_other); + this->RunQuery(query); + } + + void OnDelCore(NickCore *nc) anope_override + { + query = "DELETE FROM `" + prefix + "chanstats` WHERE `nick` = @nick@;"; + query.SetValue("nick", nc->display); + this->RunQuery(query); + } + + void OnChangeCoreDisplay(NickCore *nc, const Anope::string &newdisplay) anope_override + { + query = "CALL " + prefix + "chanstats_proc_chgdisplay(@old_display@, @new_display@);"; + query.SetValue("old_display", nc->display); + query.SetValue("new_display", newdisplay); + this->RunQuery(query); + } + + void OnDelChan(ChannelInfo *ci) anope_override + { + query = "DELETE FROM `" + prefix + "chanstats` WHERE `chan` = @channel@;"; + query.SetValue("channel", ci->name); + this->RunQuery(query); + } + + void OnChanRegistered(ChannelInfo *ci) + { + if (CSDefChanstats) + ci->Extend("CS_STATS"); + } + + void OnNickRegister(User *user, NickAlias *na, const Anope::string &) + { + if (NSDefChanstats) + na->nc->Extend("NS_STATS"); + } +}; + +MODULE_INIT(MChanstats) diff --git a/modules/fantasy.cpp b/modules/fantasy.cpp new file mode 100644 index 0000000..1c57790 --- /dev/null +++ b/modules/fantasy.cpp @@ -0,0 +1,218 @@ +/* Fantasy functionality + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class CommandBSSetFantasy : public Command +{ + public: + CommandBSSetFantasy(Module *creator, const Anope::string &sname = "botserv/set/fantasy") : Command(creator, sname, 2, 2) + { + this->SetDesc(_("Enable fantaisist commands")); + this->SetSyntax(_("\037channel\037 {\037ON|OFF\037}")); + } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + ChannelInfo *ci = ChannelInfo::Find(params[0]); + const Anope::string &value = params[1]; + + if (ci == NULL) + { + source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); + return; + } + + if (!source.HasPriv("botserv/administration") && !source.AccessFor(ci).HasPriv("SET")) + { + source.Reply(ACCESS_DENIED); + return; + } + + if (Anope::ReadOnly) + { + source.Reply(_("Sorry, bot option setting is temporarily disabled.")); + return; + } + + if (value.equals_ci("ON")) + { + bool override = !source.AccessFor(ci).HasPriv("SET"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to enable fantasy"; + + ci->Extend("BS_FANTASY"); + source.Reply(_("Fantasy mode is now \002on\002 on channel %s."), ci->name.c_str()); + } + else if (value.equals_ci("OFF")) + { + bool override = !source.AccessFor(ci).HasPriv("SET"); + Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "to disable fantasy"; + + ci->Shrink("BS_FANTASY"); + source.Reply(_("Fantasy mode is now \002off\002 on channel %s."), ci->name.c_str()); + } + else + this->OnSyntaxError(source, source.command); + } + + bool OnHelp(CommandSource &source, const Anope::string &) anope_override + { + this->SendSyntax(source); + source.Reply(_(" \n" + "Enables or disables \002fantasy\002 mode on a channel.\n" + "When it is enabled, users will be able to use\n" + "fantasy commands on a channel when prefixed\n" + "with one of the following fantasy characters: \002%s\002\n" + " \n" + "Note that users wanting to use fantaisist\n" + "commands MUST have enough access for both\n" + "the FANTASIA and the command they are executing."), + Config->GetModule(this->owner)->Get("fantasycharacter", "!").c_str()); + return true; + } +}; + +class Fantasy : public Module +{ + SerializableExtensibleItem fantasy; + + CommandBSSetFantasy commandbssetfantasy; + + public: + Fantasy(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + fantasy(this, "BS_FANTASY"), commandbssetfantasy(this) + { + } + + void OnPrivmsg(User *u, Channel *c, Anope::string &msg) anope_override + { + if (!u || !c || !c->ci || !c->ci->bi || msg.empty() || msg[0] == '\1') + return; + + if (Config->GetClient("BotServ") && !fantasy.HasExt(c->ci)) + return; + + std::vector params; + spacesepstream(msg).GetTokens(params); + + if (params.empty()) + return; + + Anope::string normalized_param0 = Anope::NormalizeBuffer(params[0]); + Anope::string fantasy_chars = Config->GetModule(this)->Get("fantasycharacter", "!"); + + if (!normalized_param0.find(c->ci->bi->nick)) + { + params.erase(params.begin()); + } + else if (!normalized_param0.find_first_of(fantasy_chars)) + { + size_t sz = params[0].find_first_of(fantasy_chars); + if (sz == Anope::string::npos) + return; /* normalized_param0 is a subset of params[0] so this can't happen */ + + params[0].erase(0, sz + 1); + } + else + { + return; + } + + if (params.empty()) + return; + + CommandInfo::map::const_iterator it = Config->Fantasy.end(); + unsigned count = 0; + for (unsigned max = params.size(); it == Config->Fantasy.end() && max > 0; --max) + { + Anope::string full_command; + for (unsigned i = 0; i < max; ++i) + full_command += " " + params[i]; + full_command.erase(full_command.begin()); + + ++count; + it = Config->Fantasy.find(Anope::NormalizeBuffer(full_command)); + } + + if (it == Config->Fantasy.end()) + return; + + const CommandInfo &info = it->second; + ServiceReference cmd("Command", info.name); + if (!cmd) + { + Log(LOG_DEBUG) << "Fantasy command " << it->first << " exists for nonexistent service " << info.name << "!"; + return; + } + + for (unsigned i = 0, j = params.size() - (count - 1); i < j; ++i) + params.erase(params.begin()); + + /* Some commands take the channel as a first parameter */ + if (info.prepend_channel) + params.insert(params.begin(), c->name); + + while (cmd->max_params > 0 && params.size() > cmd->max_params) + { + params[cmd->max_params - 1] += " " + params[cmd->max_params]; + params.erase(params.begin() + cmd->max_params); + } + + // Command requires registered users only + if (!cmd->AllowUnregistered() && !u->Account()) + return; + + if (params.size() < cmd->min_params) + return; + + CommandSource source(u->nick, u, u->Account(), u, c->ci->bi); + source.c = c; + source.command = it->first; + source.permission = info.permission; + + AccessGroup ag = c->ci->AccessFor(u); + bool has_fantasia = ag.HasPriv("FANTASIA") || source.HasPriv("botserv/fantasy"); + + EventReturn MOD_RESULT; + if (has_fantasia) + { + FOREACH_RESULT(OnBotFantasy, MOD_RESULT, (source, cmd, c->ci, params)); + } + else + { + FOREACH_RESULT(OnBotNoFantasyAccess, MOD_RESULT, (source, cmd, c->ci, params)); + } + + if (MOD_RESULT == EVENT_STOP || !has_fantasia) + return; + + if (MOD_RESULT != EVENT_ALLOW && !info.permission.empty() && !source.HasCommand(info.permission)) + return; + + FOREACH_RESULT(OnPreCommand, MOD_RESULT, (source, cmd, params)); + if (MOD_RESULT == EVENT_STOP) + return; + + Reference nc_reference(u->Account()); + cmd->Execute(source, params); + if (!nc_reference) + source.nc = NULL; + FOREACH_MOD(OnPostCommand, (source, cmd, params)); + } + + void OnBotInfo(CommandSource &source, BotInfo *bi, ChannelInfo *ci, InfoFormatter &info) anope_override + { + if (fantasy.HasExt(ci)) + info.AddOption(_("Fantasy")); + } +}; + +MODULE_INIT(Fantasy) diff --git a/modules/m_dns.cpp b/modules/m_dns.cpp new file mode 100644 index 0000000..db700d0 --- /dev/null +++ b/modules/m_dns.cpp @@ -0,0 +1,1125 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/dns.h" + +using namespace DNS; + +namespace +{ + Anope::string admin, nameservers; + int refresh; + time_t timeout; +} + +/** A full packet sent or received to/from the nameserver + */ +class Packet : public Query +{ + static bool IsValidName(const Anope::string &name) + { + return name.find_first_not_of("0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ.-") == Anope::string::npos; + } + + void PackName(unsigned char *output, unsigned short output_size, unsigned short &pos, const Anope::string &name) + { + if (pos + name.length() + 2 > output_size) + throw SocketException("Unable to pack name"); + + Log(LOG_DEBUG_2) << "Resolver: PackName packing " << name; + + sepstream sep(name, '.'); + Anope::string token; + + while (sep.GetToken(token)) + { + output[pos++] = token.length(); + memcpy(&output[pos], token.c_str(), token.length()); + pos += token.length(); + } + + output[pos++] = 0; + } + + Anope::string UnpackName(const unsigned char *input, unsigned short input_size, unsigned short &pos) + { + Anope::string name; + unsigned short pos_ptr = pos, lowest_ptr = input_size; + bool compressed = false; + + if (pos_ptr >= input_size) + throw SocketException("Unable to unpack name - no input"); + + while (input[pos_ptr] > 0) + { + unsigned short offset = input[pos_ptr]; + + if (offset & POINTER) + { + if ((offset & POINTER) != POINTER) + throw SocketException("Unable to unpack name - bogus compression header"); + if (pos_ptr + 1 >= input_size) + throw SocketException("Unable to unpack name - bogus compression header"); + + /* Place pos at the second byte of the first (farthest) compression pointer */ + if (compressed == false) + { + ++pos; + compressed = true; + } + + pos_ptr = (offset & LABEL) << 8 | input[pos_ptr + 1]; + + /* Pointers can only go back */ + if (pos_ptr >= lowest_ptr) + throw SocketException("Unable to unpack name - bogus compression pointer"); + lowest_ptr = pos_ptr; + } + else + { + if (pos_ptr + offset + 1 >= input_size) + throw SocketException("Unable to unpack name - offset too large"); + if (!name.empty()) + name += "."; + for (unsigned i = 1; i <= offset; ++i) + name += input[pos_ptr + i]; + + pos_ptr += offset + 1; + if (compressed == false) + /* Move up pos */ + pos = pos_ptr; + } + } + + /* +1 pos either to one byte after the compression pointer or one byte after the ending \0 */ + ++pos; + + /* Empty names are valid (root domain) */ + + Log(LOG_DEBUG_2) << "Resolver: UnpackName successfully unpacked " << name; + + return name; + } + + Question UnpackQuestion(const unsigned char *input, unsigned short input_size, unsigned short &pos) + { + Question question; + + question.name = this->UnpackName(input, input_size, pos); + + if (pos + 4 > input_size) + throw SocketException("Unable to unpack question"); + + if (!IsValidName(question.name)) + throw SocketException("Invalid question name"); + + question.type = static_cast(input[pos] << 8 | input[pos + 1]); + pos += 2; + + question.qclass = input[pos] << 8 | input[pos + 1]; + pos += 2; + + return question; + } + + ResourceRecord UnpackResourceRecord(const unsigned char *input, unsigned short input_size, unsigned short &pos) + { + ResourceRecord record = static_cast(this->UnpackQuestion(input, input_size, pos)); + + if (pos + 6 > input_size) + throw SocketException("Unable to unpack resource record"); + + record.ttl = (input[pos] << 24) | (input[pos + 1] << 16) | (input[pos + 2] << 8) | input[pos + 3]; + pos += 4; + + //record.rdlength = input[pos] << 8 | input[pos + 1]; + pos += 2; + + switch (record.type) + { + case QUERY_A: + { + if (pos + 4 > input_size) + throw SocketException("Unable to unpack resource record"); + + in_addr a; + a.s_addr = input[pos] | (input[pos + 1] << 8) | (input[pos + 2] << 16) | (input[pos + 3] << 24); + pos += 4; + + sockaddrs addrs; + addrs.ntop(AF_INET, &a); + if (!addrs.valid()) + throw SocketException("Invalid IP"); + + record.rdata = addrs.addr(); + break; + } + case QUERY_AAAA: + { + if (pos + 16 > input_size) + throw SocketException("Unable to unpack resource record"); + + in6_addr a; + for (int j = 0; j < 16; ++j) + a.s6_addr[j] = input[pos + j]; + pos += 16; + + sockaddrs addrs; + addrs.ntop(AF_INET6, &a); + if (!addrs.valid()) + throw SocketException("Invalid IP"); + + record.rdata = addrs.addr(); + break; + } + case QUERY_CNAME: + case QUERY_PTR: + { + record.rdata = this->UnpackName(input, input_size, pos); + + if (!IsValidName(record.rdata)) + throw SocketException("Invalid cname/ptr record data"); + + break; + } + default: + break; + } + + Log(LOG_DEBUG_2) << "Resolver: " << record.name << " -> " << record.rdata; + + return record; + } + + public: + static const int POINTER = 0xC0; + static const int LABEL = 0x3F; + static const int HEADER_LENGTH = 12; + + Manager *manager; + /* Source or destination of the packet */ + sockaddrs addr; + /* ID for this packet */ + unsigned short id; + /* Flags on the packet */ + unsigned short flags; + + Packet(Manager *m, sockaddrs *a) : manager(m), id(0), flags(0) + { + if (a) + addr = *a; + } + + void Fill(const unsigned char *input, const unsigned short len) + { + if (len < HEADER_LENGTH) + throw SocketException("Unable to fill packet"); + + unsigned short packet_pos = 0; + + this->id = (input[packet_pos] << 8) | input[packet_pos + 1]; + packet_pos += 2; + + this->flags = (input[packet_pos] << 8) | input[packet_pos + 1]; + packet_pos += 2; + + unsigned short qdcount = (input[packet_pos] << 8) | input[packet_pos + 1]; + packet_pos += 2; + + unsigned short ancount = (input[packet_pos] << 8) | input[packet_pos + 1]; + packet_pos += 2; + + unsigned short nscount = (input[packet_pos] << 8) | input[packet_pos + 1]; + packet_pos += 2; + + unsigned short arcount = (input[packet_pos] << 8) | input[packet_pos + 1]; + packet_pos += 2; + + Log(LOG_DEBUG_2) << "Resolver: qdcount: " << qdcount << " ancount: " << ancount << " nscount: " << nscount << " arcount: " << arcount; + + for (unsigned i = 0; i < qdcount; ++i) + this->questions.push_back(this->UnpackQuestion(input, len, packet_pos)); + + for (unsigned i = 0; i < ancount; ++i) + this->answers.push_back(this->UnpackResourceRecord(input, len, packet_pos)); + + try + { + for (unsigned i = 0; i < nscount; ++i) + this->authorities.push_back(this->UnpackResourceRecord(input, len, packet_pos)); + + for (unsigned i = 0; i < arcount; ++i) + this->additional.push_back(this->UnpackResourceRecord(input, len, packet_pos)); + } + catch (const SocketException &ex) + { + Log(LOG_DEBUG_2) << "Unable to parse ns/ar records: " << ex.GetReason(); + } + } + + unsigned short Pack(unsigned char *output, unsigned short output_size) + { + if (output_size < HEADER_LENGTH) + throw SocketException("Unable to pack packet"); + + unsigned short pos = 0; + + output[pos++] = this->id >> 8; + output[pos++] = this->id & 0xFF; + output[pos++] = this->flags >> 8; + output[pos++] = this->flags & 0xFF; + output[pos++] = this->questions.size() >> 8; + output[pos++] = this->questions.size() & 0xFF; + output[pos++] = this->answers.size() >> 8; + output[pos++] = this->answers.size() & 0xFF; + output[pos++] = this->authorities.size() >> 8; + output[pos++] = this->authorities.size() & 0xFF; + output[pos++] = this->additional.size() >> 8; + output[pos++] = this->additional.size() & 0xFF; + + for (unsigned i = 0; i < this->questions.size(); ++i) + { + Question &q = this->questions[i]; + + if (q.type == QUERY_PTR) + { + sockaddrs ip(q.name); + if (!ip.valid()) + throw SocketException("Invalid IP"); + + switch (ip.family()) + { + case AF_INET6: + q.name = ip.reverse() + ".ip6.arpa"; + break; + case AF_INET: + q.name = ip.reverse() + ".in-addr.arpa"; + break; + default: + throw SocketException("Unsupported IP Family"); + } + } + + this->PackName(output, output_size, pos, q.name); + + if (pos + 4 >= output_size) + throw SocketException("Unable to pack packet"); + + short s = htons(q.type); + memcpy(&output[pos], &s, 2); + pos += 2; + + s = htons(q.qclass); + memcpy(&output[pos], &s, 2); + pos += 2; + } + + std::vector types[] = { this->answers, this->authorities, this->additional }; + for (int i = 0; i < 3; ++i) + for (unsigned j = 0; j < types[i].size(); ++j) + { + ResourceRecord &rr = types[i][j]; + + this->PackName(output, output_size, pos, rr.name); + + if (pos + 8 >= output_size) + throw SocketException("Unable to pack packet"); + + short s = htons(rr.type); + memcpy(&output[pos], &s, 2); + pos += 2; + + s = htons(rr.qclass); + memcpy(&output[pos], &s, 2); + pos += 2; + + long l = htonl(rr.ttl); + memcpy(&output[pos], &l, 4); + pos += 4; + + switch (rr.type) + { + case QUERY_A: + { + if (pos + 6 > output_size) + throw SocketException("Unable to pack packet"); + + sockaddrs a(rr.rdata); + if (!a.valid()) + throw SocketException("Invalid IP"); + + s = htons(4); + memcpy(&output[pos], &s, 2); + pos += 2; + + memcpy(&output[pos], &a.sa4.sin_addr, 4); + pos += 4; + break; + } + case QUERY_AAAA: + { + if (pos + 18 > output_size) + throw SocketException("Unable to pack packet"); + + sockaddrs a(rr.rdata); + if (!a.valid()) + throw SocketException("Invalid IP"); + + s = htons(16); + memcpy(&output[pos], &s, 2); + pos += 2; + + memcpy(&output[pos], &a.sa6.sin6_addr, 16); + pos += 16; + break; + } + case QUERY_NS: + case QUERY_CNAME: + case QUERY_PTR: + { + if (pos + 2 >= output_size) + throw SocketException("Unable to pack packet"); + + unsigned short packet_pos_save = pos; + pos += 2; + + this->PackName(output, output_size, pos, rr.rdata); + + s = htons(pos - packet_pos_save - 2); + memcpy(&output[packet_pos_save], &s, 2); + break; + } + case QUERY_SOA: + { + if (pos + 2 >= output_size) + throw SocketException("Unable to pack packet"); + + unsigned short packet_pos_save = pos; + pos += 2; + + std::vector ns; + spacesepstream(nameservers).GetTokens(ns); + this->PackName(output, output_size, pos, !ns.empty() ? ns[0] : ""); + this->PackName(output, output_size, pos, admin.replace_all_cs('@', '.')); + + if (pos + 20 >= output_size) + throw SocketException("Unable to pack SOA"); + + l = htonl(manager->GetSerial()); + memcpy(&output[pos], &l, 4); + pos += 4; + + l = htonl(refresh); // Refresh + memcpy(&output[pos], &l, 4); + pos += 4; + + l = htonl(refresh); // Retry + memcpy(&output[pos], &l, 4); + pos += 4; + + l = htonl(604800); // Expire + memcpy(&output[pos], &l, 4); + pos += 4; + + l = htonl(0); // Minimum + memcpy(&output[pos], &l, 4); + pos += 4; + + s = htons(pos - packet_pos_save - 2); + memcpy(&output[packet_pos_save], &s, 2); + + break; + } + default: + break; + } + } + + return pos; + } +}; + +namespace DNS +{ + class ReplySocket : public virtual Socket + { + public: + virtual ~ReplySocket() { } + virtual void Reply(Packet *p) = 0; + }; +} + +/* Listens for TCP requests */ +class TCPSocket : public ListenSocket +{ + Manager *manager; + + public: + /* A TCP client */ + class Client : public ClientSocket, public Timer, public ReplySocket + { + Manager *manager; + Packet *packet; + unsigned char packet_buffer[524]; + int length; + + public: + Client(Manager *m, TCPSocket *l, int fd, const sockaddrs &addr) : Socket(fd, l->IsIPv6()), ClientSocket(l, addr), Timer(5), + manager(m), packet(NULL), length(0) + { + Log(LOG_DEBUG_2) << "Resolver: New client from " << addr.addr(); + } + + ~Client() + { + Log(LOG_DEBUG_2) << "Resolver: Exiting client from " << clientaddr.addr(); + delete packet; + } + + /* Times out after a few seconds */ + void Tick(time_t) anope_override { } + + void Reply(Packet *p) anope_override + { + delete packet; + packet = p; + SocketEngine::Change(this, true, SF_WRITABLE); + } + + bool ProcessRead() anope_override + { + Log(LOG_DEBUG_2) << "Resolver: Reading from DNS TCP socket"; + + int i = recv(this->GetFD(), reinterpret_cast(packet_buffer) + length, sizeof(packet_buffer) - length, 0); + if (i <= 0) + return false; + + length += i; + + unsigned short want_len = packet_buffer[0] << 8 | packet_buffer[1]; + if (length >= want_len + 2) + { + int len = length - 2; + length -= want_len + 2; + return this->manager->HandlePacket(this, packet_buffer + 2, len, NULL); + } + return true; + } + + bool ProcessWrite() anope_override + { + Log(LOG_DEBUG_2) << "Resolver: Writing to DNS TCP socket"; + + if (packet != NULL) + { + try + { + unsigned char buffer[65535]; + unsigned short len = packet->Pack(buffer + 2, sizeof(buffer) - 2); + + short s = htons(len); + memcpy(buffer, &s, 2); + len += 2; + + send(this->GetFD(), reinterpret_cast(buffer), len, 0); + } + catch (const SocketException &) { } + + delete packet; + packet = NULL; + } + + SocketEngine::Change(this, false, SF_WRITABLE); + return true; /* Do not return false here, bind is unhappy we close the connection so soon after sending */ + } + }; + + TCPSocket(Manager *m, const Anope::string &ip, int port) : Socket(-1, ip.find(':') != Anope::string::npos), ListenSocket(ip, port, ip.find(':') != Anope::string::npos), manager(m) { } + + ClientSocket *OnAccept(int fd, const sockaddrs &addr) anope_override + { + return new Client(this->manager, this, fd, addr); + } +}; + +/* Listens for UDP requests */ +class UDPSocket : public ReplySocket +{ + Manager *manager; + std::deque packets; + + public: + UDPSocket(Manager *m, const Anope::string &ip, int port) : Socket(-1, ip.find(':') != Anope::string::npos, SOCK_DGRAM), manager(m) { } + + ~UDPSocket() + { + for (unsigned i = 0; i < packets.size(); ++i) + delete packets[i]; + } + + void Reply(Packet *p) anope_override + { + packets.push_back(p); + SocketEngine::Change(this, true, SF_WRITABLE); + } + + std::deque& GetPackets() { return packets; } + + bool ProcessRead() anope_override + { + Log(LOG_DEBUG_2) << "Resolver: Reading from DNS UDP socket"; + + unsigned char packet_buffer[524]; + sockaddrs from_server; + socklen_t x = sizeof(from_server); + int length = recvfrom(this->GetFD(), reinterpret_cast(&packet_buffer), sizeof(packet_buffer), 0, &from_server.sa, &x); + return this->manager->HandlePacket(this, packet_buffer, length, &from_server); + } + + bool ProcessWrite() anope_override + { + Log(LOG_DEBUG_2) << "Resolver: Writing to DNS UDP socket"; + + Packet *r = !packets.empty() ? packets.front() : NULL; + if (r != NULL) + { + try + { + unsigned char buffer[524]; + unsigned short len = r->Pack(buffer, sizeof(buffer)); + + sendto(this->GetFD(), reinterpret_cast(buffer), len, 0, &r->addr.sa, r->addr.size()); + } + catch (const SocketException &) { } + + delete r; + packets.pop_front(); + } + + if (packets.empty()) + SocketEngine::Change(this, false, SF_WRITABLE); + + return true; + } +}; + +class NotifySocket : public Socket +{ + Packet *packet; + public: + NotifySocket(bool v6, Packet *p) : Socket(-1, v6, SOCK_DGRAM), packet(p) + { + SocketEngine::Change(this, false, SF_READABLE); + SocketEngine::Change(this, true, SF_WRITABLE); + } + + bool ProcessWrite() anope_override + { + if (!packet) + return false; + + Log(LOG_DEBUG_2) << "Resolver: Notifying slave " << packet->addr.addr(); + + try + { + unsigned char buffer[524]; + unsigned short len = packet->Pack(buffer, sizeof(buffer)); + + sendto(this->GetFD(), reinterpret_cast(buffer), len, 0, &packet->addr.sa, packet->addr.size()); + } + catch (const SocketException &) { } + + delete packet; + packet = NULL; + + return false; + } +}; + +class MyManager : public Manager, public Timer +{ + uint32_t serial; + + typedef TR1NS::unordered_map cache_map; + cache_map cache; + + TCPSocket *tcpsock; + UDPSocket *udpsock; + + bool listen; + sockaddrs addrs; + + std::vector > notify; + public: + std::map requests; + + MyManager(Module *creator) : Manager(creator), Timer(300, Anope::CurTime, true), serial(Anope::CurTime), tcpsock(NULL), udpsock(NULL), + listen(false), cur_id(rand()) + { + } + + ~MyManager() + { + delete udpsock; + delete tcpsock; + + for (std::map::iterator it = this->requests.begin(), it_end = this->requests.end(); it != it_end;) + { + Request *request = it->second; + ++it; + + Query rr(*request); + rr.error = ERROR_UNKNOWN; + request->OnError(&rr); + + delete request; + } + this->requests.clear(); + + this->cache.clear(); + } + + void SetIPPort(const Anope::string &nameserver, const Anope::string &ip, unsigned short port, std::vector > n) + { + delete udpsock; + delete tcpsock; + + udpsock = NULL; + tcpsock = NULL; + + try + { + this->addrs.pton(nameserver.find(':') != Anope::string::npos ? AF_INET6 : AF_INET, nameserver, 53); + + udpsock = new UDPSocket(this, ip, port); + + if (!ip.empty()) + { + udpsock->Bind(ip, port); + tcpsock = new TCPSocket(this, ip, port); + listen = true; + } + } + catch (const SocketException &ex) + { + Log() << "Unable to bind dns to " << ip << ":" << port << ": " << ex.GetReason(); + } + + notify = n; + } + + private: + unsigned short cur_id; + + unsigned short GetID() + { + if (this->udpsock->GetPackets().size() == 65535) + throw SocketException("DNS queue full"); + + do + cur_id = (cur_id + 1) & 0xFFFF; + while (!cur_id || this->requests.count(cur_id)); + + return cur_id; + } + + public: + void Process(Request *req) anope_override + { + Log(LOG_DEBUG_2) << "Resolver: Processing request to lookup " << req->name << ", of type " << req->type; + + if (req->use_cache && this->CheckCache(req)) + { + Log(LOG_DEBUG_2) << "Resolver: Using cached result"; + delete req; + return; + } + + if (!this->udpsock) + throw SocketException("No dns socket"); + + req->id = GetID(); + this->requests[req->id] = req; + + req->SetSecs(timeout); + + Packet *p = new Packet(this, &this->addrs); + p->flags = QUERYFLAGS_RD; + p->id = req->id; + p->questions.push_back(*req); + + this->udpsock->Reply(p); + } + + void RemoveRequest(Request *req) anope_override + { + this->requests.erase(req->id); + } + + bool HandlePacket(ReplySocket *s, const unsigned char *const packet_buffer, int length, sockaddrs *from) anope_override + { + if (length < Packet::HEADER_LENGTH) + return true; + + Packet recv_packet(this, from); + + try + { + recv_packet.Fill(packet_buffer, length); + } + catch (const SocketException &ex) + { + Log(LOG_DEBUG_2) << ex.GetReason(); + return true; + } + + if (!(recv_packet.flags & QUERYFLAGS_QR)) + { + if (!listen) + return true; + else if (recv_packet.questions.empty()) + { + Log(LOG_DEBUG_2) << "Resolver: Received a question with no questions?"; + return true; + } + + Packet *packet = new Packet(recv_packet); + packet->flags |= QUERYFLAGS_QR; /* This is a response */ + packet->flags |= QUERYFLAGS_AA; /* And we are authoritative */ + + packet->answers.clear(); + packet->authorities.clear(); + packet->additional.clear(); + + for (unsigned i = 0; i < recv_packet.questions.size(); ++i) + { + const Question& q = recv_packet.questions[i]; + + if (q.type == QUERY_AXFR || q.type == QUERY_SOA) + { + ResourceRecord rr(q.name, QUERY_SOA); + packet->answers.push_back(rr); + + if (q.type == QUERY_AXFR) + { + Anope::string token; + spacesepstream sep(nameservers); + while (sep.GetToken(token)) + { + ResourceRecord rr2(q.name, QUERY_NS); + rr2.rdata = token; + packet->answers.push_back(rr2); + } + } + break; + } + } + + FOREACH_MOD(OnDnsRequest, (recv_packet, packet)); + + for (unsigned i = 0; i < recv_packet.questions.size(); ++i) + { + const Question& q = recv_packet.questions[i]; + + if (q.type == QUERY_AXFR) + { + ResourceRecord rr(q.name, QUERY_SOA); + packet->answers.push_back(rr); + break; + } + } + + if (packet->answers.empty() && packet->authorities.empty() && packet->additional.empty() && packet->error == ERROR_NONE) + packet->error = ERROR_REFUSED; // usually safe, won't cause an NXDOMAIN to get cached + + s->Reply(packet); + return true; + } + + if (from == NULL) + { + Log(LOG_DEBUG_2) << "Resolver: Received an answer over TCP. This is not supported."; + return true; + } + else if (this->addrs != *from) + { + Log(LOG_DEBUG_2) << "Resolver: Received an answer from the wrong nameserver, Bad NAT or DNS forging attempt? '" << this->addrs.addr() << "' != '" << from->addr() << "'"; + return true; + } + + std::map::iterator it = this->requests.find(recv_packet.id); + if (it == this->requests.end()) + { + Log(LOG_DEBUG_2) << "Resolver: Received an answer for something we didn't request"; + return true; + } + Request *request = it->second; + + if (recv_packet.flags & QUERYFLAGS_OPCODE) + { + Log(LOG_DEBUG_2) << "Resolver: Received a nonstandard query"; + recv_packet.error = ERROR_NONSTANDARD_QUERY; + request->OnError(&recv_packet); + } + else if (recv_packet.flags & QUERYFLAGS_RCODE) + { + Error error = ERROR_UNKNOWN; + + switch (recv_packet.flags & QUERYFLAGS_RCODE) + { + case 1: + Log(LOG_DEBUG_2) << "Resolver: format error"; + error = ERROR_FORMAT_ERROR; + break; + case 2: + Log(LOG_DEBUG_2) << "Resolver: server error"; + error = ERROR_SERVER_FAILURE; + break; + case 3: + Log(LOG_DEBUG_2) << "Resolver: domain not found"; + error = ERROR_DOMAIN_NOT_FOUND; + break; + case 4: + Log(LOG_DEBUG_2) << "Resolver: not implemented"; + error = ERROR_NOT_IMPLEMENTED; + break; + case 5: + Log(LOG_DEBUG_2) << "Resolver: refused"; + error = ERROR_REFUSED; + break; + default: + break; + } + + recv_packet.error = error; + request->OnError(&recv_packet); + } + else if (recv_packet.questions.empty() || recv_packet.answers.empty()) + { + Log(LOG_DEBUG_2) << "Resolver: No resource records returned"; + recv_packet.error = ERROR_NO_RECORDS; + request->OnError(&recv_packet); + } + else + { + Log(LOG_DEBUG_2) << "Resolver: Lookup complete for " << request->name; + request->OnLookupComplete(&recv_packet); + this->AddCache(recv_packet); + } + + delete request; + return true; + } + + void UpdateSerial() anope_override + { + serial = Anope::CurTime; + } + + void Notify(const Anope::string &zone) anope_override + { + /* notify slaves of the update */ + for (unsigned i = 0; i < notify.size(); ++i) + { + const Anope::string &ip = notify[i].first; + short port = notify[i].second; + + sockaddrs addr; + addr.pton(ip.find(':') != Anope::string::npos ? AF_INET6 : AF_INET, ip, port); + if (!addr.valid()) + return; + + Packet *packet = new Packet(this, &addr); + packet->flags = QUERYFLAGS_AA | QUERYFLAGS_OPCODE_NOTIFY; + try + { + packet->id = GetID(); + } + catch (const SocketException &) + { + delete packet; + continue; + } + + packet->questions.push_back(Question(zone, QUERY_SOA)); + + new NotifySocket(ip.find(':') != Anope::string::npos, packet); + } + } + + uint32_t GetSerial() const anope_override + { + return serial; + } + + void Tick(time_t now) anope_override + { + Log(LOG_DEBUG_2) << "Resolver: Purging DNS cache"; + + for (cache_map::iterator it = this->cache.begin(), it_next; it != this->cache.end(); it = it_next) + { + const Query &q = it->second; + const ResourceRecord &req = q.answers[0]; + it_next = it; + ++it_next; + + if (req.created + static_cast(req.ttl) < now) + this->cache.erase(it); + } + } + + private: + /** Add a record to the dns cache + * @param r The record + */ + void AddCache(Query &r) + { + const ResourceRecord &rr = r.answers[0]; + Log(LOG_DEBUG_3) << "Resolver cache: added cache for " << rr.name << " -> " << rr.rdata << ", ttl: " << rr.ttl; + this->cache[r.questions[0]] = r; + } + + /** Check the DNS cache to see if request can be handled by a cached result + * @return true if a cached result was found. + */ + bool CheckCache(Request *request) + { + cache_map::iterator it = this->cache.find(*request); + if (it != this->cache.end()) + { + Query &record = it->second; + Log(LOG_DEBUG_3) << "Resolver: Using cached result for " << request->name; + request->OnLookupComplete(&record); + return true; + } + + return false; + } + +}; + +class ModuleDNS : public Module +{ + MyManager manager; + + Anope::string nameserver; + Anope::string ip; + int port; + + std::vector > notify; + + public: + ModuleDNS(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR), manager(this) + { + + } + + ~ModuleDNS() + { + for (std::map::const_iterator it = SocketEngine::Sockets.begin(), it_end = SocketEngine::Sockets.end(); it != it_end;) + { + Socket *s = it->second; + ++it; + + if (dynamic_cast(s) || dynamic_cast(s)) + delete s; + } + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *block = conf->GetModule(this); + + nameserver = block->Get("nameserver", "127.0.0.1"); + timeout = block->Get("timeout", "5"); + ip = block->Get("ip", "0.0.0.0"); + port = block->Get("port", "53"); + admin = block->Get("admin", "admin@example.com"); + nameservers = block->Get("nameservers", "ns1.example.com"); + refresh = block->Get("refresh", "3600"); + + for (int i = 0; i < block->CountBlock("notify"); ++i) + { + Configuration::Block *n = block->GetBlock("notify", i); + Anope::string nip = n->Get("ip"); + short nport = n->Get("port"); + + notify.push_back(std::make_pair(nip, nport)); + } + + if (Anope::IsFile(nameserver)) + { + std::ifstream f(nameserver.c_str()); + bool success = false; + + if (f.is_open()) + { + for (Anope::string server; std::getline(f, server.str());) + { + if (server.find("nameserver") == 0) + { + size_t i = server.find_first_of("123456789"); + if (i != Anope::string::npos) + { + if (server.substr(i).is_pos_number_only()) + { + nameserver = server.substr(i); + Log(LOG_DEBUG) << "Nameserver set to " << nameserver; + success = true; + break; + } + } + } + } + + f.close(); + } + + if (!success) + { + Log() << "Unable to find nameserver, defaulting to 127.0.0.1"; + nameserver = "127.0.0.1"; + } + } + + try + { + this->manager.SetIPPort(nameserver, ip, port, notify); + } + catch (const SocketException &ex) + { + throw ModuleException(ex.GetReason()); + } + } + + void OnModuleUnload(User *u, Module *m) anope_override + { + for (std::map::iterator it = this->manager.requests.begin(), it_end = this->manager.requests.end(); it != it_end;) + { + unsigned short id = it->first; + Request *req = it->second; + ++it; + + if (req->creator == m) + { + Query rr(*req); + rr.error = ERROR_UNLOADED; + req->OnError(&rr); + + delete req; + this->manager.requests.erase(id); + } + } + } +}; + +MODULE_INIT(ModuleDNS) diff --git a/modules/m_dnsbl.cpp b/modules/m_dnsbl.cpp new file mode 100644 index 0000000..f3a49ac --- /dev/null +++ b/modules/m_dnsbl.cpp @@ -0,0 +1,198 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/dns.h" + +using namespace DNS; + +static ServiceReference akills("XLineManager", "xlinemanager/sgline"); +static ServiceReference dnsmanager("DNS::Manager", "dns/manager"); + +struct Blacklist +{ + struct Reply + { + int code; + Anope::string reason; + bool allow_account; + + Reply() : code(0), allow_account(false) { } + }; + + Anope::string name; + time_t bantime; + Anope::string reason; + std::vector replies; + + Blacklist() : bantime(0) { } + + Reply *Find(int code) + { + for (unsigned int i = 0; i < replies.size(); ++i) + if (replies[i].code == code) + return &replies[i]; + return NULL; + } +}; + +class DNSBLResolver : public Request +{ + Reference user; + Blacklist blacklist; + bool add_to_akill; + + public: + DNSBLResolver(Module *c, User *u, const Blacklist &b, const Anope::string &host, bool add_akill) : Request(dnsmanager, c, host, QUERY_A, true), user(u), blacklist(b), add_to_akill(add_akill) { } + + void OnLookupComplete(const Query *record) anope_override + { + if (!user || user->Quitting()) + return; + + const ResourceRecord &ans_record = record->answers[0]; + // Replies should be in 127.0.0.0/8 + if (ans_record.rdata.find("127.") != 0) + return; + + sockaddrs sresult; + sresult.pton(AF_INET, ans_record.rdata); + int result = sresult.sa4.sin_addr.s_addr >> 24; + + Blacklist::Reply *reply = blacklist.Find(result); + if (!blacklist.replies.empty() && !reply) + return; + + if (reply && reply->allow_account && user->Account()) + return; + + Anope::string reason = this->blacklist.reason, addr = user->ip.addr(); + reason = reason.replace_all_cs("%n", user->nick); + reason = reason.replace_all_cs("%u", user->GetIdent()); + reason = reason.replace_all_cs("%g", user->realname); + reason = reason.replace_all_cs("%h", user->host); + reason = reason.replace_all_cs("%i", addr); + reason = reason.replace_all_cs("%r", reply ? reply->reason : ""); + reason = reason.replace_all_cs("%N", Config->GetBlock("networkinfo")->Get("networkname")); + + BotInfo *OperServ = Config->GetClient("OperServ"); + Log(creator, "dnsbl", OperServ) << user->GetMask() << " (" << addr << ") appears in " << this->blacklist.name; + XLine *x = new XLine("*@" + addr, OperServ ? OperServ->nick : "m_dnsbl", Anope::CurTime + this->blacklist.bantime, reason, XLineManager::GenerateUID()); + if (this->add_to_akill && akills) + { + akills->AddXLine(x); + akills->Send(NULL, x); + } + else + { + IRCD->SendAkill(NULL, x); + delete x; + } + } +}; + +class ModuleDNSBL : public Module +{ + std::vector blacklists; + std::set exempts; + bool check_on_connect; + bool check_on_netburst; + bool add_to_akill; + + public: + ModuleDNSBL(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR | EXTRA) + { + + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *block = conf->GetModule(this); + this->check_on_connect = block->Get("check_on_connect"); + this->check_on_netburst = block->Get("check_on_netburst"); + this->add_to_akill = block->Get("add_to_akill", "yes"); + + this->blacklists.clear(); + for (int i = 0; i < block->CountBlock("blacklist"); ++i) + { + Configuration::Block *bl = block->GetBlock("blacklist", i); + Blacklist blacklist; + + blacklist.name = bl->Get("name"); + if (blacklist.name.empty()) + continue; + blacklist.bantime = bl->Get("time", "4h"); + blacklist.reason = bl->Get("reason"); + + for (int j = 0; j < bl->CountBlock("reply"); ++j) + { + Configuration::Block *reply = bl->GetBlock("reply", j); + Blacklist::Reply r; + + r.code = reply->Get("code"); + r.reason = reply->Get("reason"); + r.allow_account = reply->Get("allow_account"); + + blacklist.replies.push_back(r); + } + + this->blacklists.push_back(blacklist); + } + + this->exempts.clear(); + for (int i = 0; i < block->CountBlock("exempt"); ++i) + { + Configuration::Block *bl = block->GetBlock("exempt", i); + this->exempts.insert(bl->Get("ip")); + } + } + + void OnUserConnect(User *user, bool &exempt) anope_override + { + if (exempt || user->Quitting() || (!this->check_on_connect && !Me->IsSynced()) || !dnsmanager) + return; + + if (!this->check_on_netburst && !user->server->IsSynced()) + return; + + if (!user->ip.valid()) + /* User doesn't have a valid IP (spoof/etc) */ + return; + + if (this->blacklists.empty()) + return; + + if (this->exempts.count(user->ip.addr())) + { + Log(LOG_DEBUG) << "User " << user->nick << " is exempt from dnsbl check - ip: " << user->ip.addr(); + return; + } + + Anope::string reverse = user->ip.reverse(); + + for (unsigned i = 0; i < this->blacklists.size(); ++i) + { + const Blacklist &b = this->blacklists[i]; + + Anope::string dnsbl_host = reverse + "." + b.name; + DNSBLResolver *res = NULL; + try + { + res = new DNSBLResolver(this, user, b, dnsbl_host, this->add_to_akill); + dnsmanager->Process(res); + } + catch (const SocketException &ex) + { + delete res; + Log(this) << ex.GetReason(); + } + } + } +}; + +MODULE_INIT(ModuleDNSBL) diff --git a/modules/m_helpchan.cpp b/modules/m_helpchan.cpp new file mode 100644 index 0000000..4794f9a --- /dev/null +++ b/modules/m_helpchan.cpp @@ -0,0 +1,32 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" + +class HelpChannel : public Module +{ + public: + HelpChannel(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR) + { + } + + EventReturn OnChannelModeSet(Channel *c, MessageSource &, ChannelMode *mode, const Anope::string ¶m) anope_override + { + if (mode->name == "OP" && c && c->ci && c->name.equals_ci(Config->GetModule(this)->Get("helpchannel"))) + { + User *u = User::Find(param); + + if (u && c->ci->AccessFor(u).HasPriv("OPME")) + u->SetMode(Config->GetClient("OperServ"), "HELPOP"); + } + + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(HelpChannel) diff --git a/modules/m_httpd.cpp b/modules/m_httpd.cpp new file mode 100644 index 0000000..7cf672f --- /dev/null +++ b/modules/m_httpd.cpp @@ -0,0 +1,472 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/httpd.h" +#include "modules/ssl.h" + +static Anope::string BuildDate() +{ + char timebuf[64]; + struct tm *tm = localtime(&Anope::CurTime); + strftime(timebuf, sizeof(timebuf), "%a, %d %b %Y %H:%M:%S %Z", tm); + return timebuf; +} + +static Anope::string GetStatusFromCode(HTTPError err) +{ + switch (err) + { + case HTTP_ERROR_OK: + return "200 OK"; + case HTTP_FOUND: + return "302 Found"; + case HTTP_BAD_REQUEST: + return "400 Bad Request"; + case HTTP_PAGE_NOT_FOUND: + return "404 Not Found"; + case HTTP_NOT_SUPPORTED: + return "505 HTTP Version Not Supported"; + } + + return "501 Not Implemented"; +} + +class MyHTTPClient : public HTTPClient +{ + HTTPProvider *provider; + HTTPMessage message; + bool header_done, served; + Anope::string page_name; + Reference page; + Anope::string ip; + + unsigned content_length; + + enum + { + ACTION_NONE, + ACTION_GET, + ACTION_POST + } action; + + void Serve() + { + if (this->served) + return; + this->served = true; + + if (!this->page) + { + this->SendError(HTTP_PAGE_NOT_FOUND, "Page not found"); + return; + } + + if (std::find(this->provider->ext_ips.begin(), this->provider->ext_ips.end(), this->ip) != this->provider->ext_ips.end()) + { + for (unsigned i = 0; i < this->provider->ext_headers.size(); ++i) + { + const Anope::string &token = this->provider->ext_headers[i]; + + if (this->message.headers.count(token)) + { + this->ip = this->message.headers[token]; + Log(LOG_DEBUG, "httpd") << "m_httpd: IP for connection " << this->GetFD() << " changed to " << this->ip; + break; + } + } + } + + Log(LOG_DEBUG, "httpd") << "m_httpd: Serving page " << this->page_name << " to " << this->ip; + + HTTPReply reply; + reply.content_type = this->page->GetContentType(); + + if (this->page->OnRequest(this->provider, this->page_name, this, this->message, reply)) + this->SendReply(&reply); + } + + public: + time_t created; + + MyHTTPClient(HTTPProvider *l, int f, const sockaddrs &a) : Socket(f, l->IsIPv6()), HTTPClient(l, f, a), provider(l), header_done(false), served(false), ip(a.addr()), content_length(0), action(ACTION_NONE), created(Anope::CurTime) + { + Log(LOG_DEBUG, "httpd") << "Accepted connection " << f << " from " << a.addr(); + } + + ~MyHTTPClient() + { + Log(LOG_DEBUG, "httpd") << "Closing connection " << this->GetFD() << " from " << this->ip; + } + + /* Close connection once all data is written */ + bool ProcessWrite() anope_override + { + return !BinarySocket::ProcessWrite() || this->write_buffer.empty() ? false : true; + } + + const Anope::string GetIP() anope_override + { + return this->ip; + } + + bool Read(const char *buffer, size_t l) anope_override + { + message.content.append(buffer, l); + + for (size_t nl; !this->header_done && (nl = message.content.find('\n')) != Anope::string::npos;) + { + Anope::string token = message.content.substr(0, nl).trim(); + message.content = message.content.substr(nl + 1); + + if (token.empty()) + this->header_done = true; + else + this->Read(token); + } + + if (!this->header_done) + return true; + + if (this->message.content.length() >= this->content_length) + { + sepstream sep(this->message.content, '&'); + Anope::string token; + + while (sep.GetToken(token)) + { + size_t sz = token.find('='); + if (sz == Anope::string::npos || !sz || sz + 1 >= token.length()) + continue; + this->message.post_data[token.substr(0, sz)] = HTTPUtils::URLDecode(token.substr(sz + 1)); + Log(LOG_DEBUG_2) << "HTTP POST from " << this->clientaddr.addr() << ": " << token.substr(0, sz) << ": " << this->message.post_data[token.substr(0, sz)]; + } + + this->Serve(); + } + + return true; + } + + bool Read(const Anope::string &buf) + { + Log(LOG_DEBUG_2) << "HTTP from " << this->clientaddr.addr() << ": " << buf; + + if (this->action == ACTION_NONE) + { + std::vector params; + spacesepstream(buf).GetTokens(params); + + if (params.empty() || (params[0] != "GET" && params[0] != "POST")) + { + this->SendError(HTTP_BAD_REQUEST, "Unknown operation"); + return true; + } + + if (params.size() != 3) + { + this->SendError(HTTP_BAD_REQUEST, "Invalid parameters"); + return true; + } + + if (params[0] == "GET") + this->action = ACTION_GET; + else if (params[0] == "POST") + this->action = ACTION_POST; + + Anope::string targ = params[1]; + size_t q = targ.find('?'); + if (q != Anope::string::npos) + { + sepstream sep(targ.substr(q + 1), '&'); + targ = targ.substr(0, q); + + Anope::string token; + while (sep.GetToken(token)) + { + size_t sz = token.find('='); + if (sz == Anope::string::npos || !sz || sz + 1 >= token.length()) + continue; + this->message.get_data[token.substr(0, sz)] = HTTPUtils::URLDecode(token.substr(sz + 1)); + } + } + + this->page = this->provider->FindPage(targ); + this->page_name = targ; + } + else if (buf.find_ci("Cookie: ") == 0) + { + spacesepstream sep(buf.substr(8)); + Anope::string token; + + while (sep.GetToken(token)) + { + size_t sz = token.find('='); + if (sz == Anope::string::npos || !sz || sz + 1 >= token.length()) + continue; + size_t end = token.length() - (sz + 1); + if (!sep.StreamEnd()) + --end; // Remove trailing ; + this->message.cookies[token.substr(0, sz)] = token.substr(sz + 1, end); + } + } + else if (buf.find_ci("Content-Length: ") == 0) + { + try + { + this->content_length = convertTo(buf.substr(16)); + } + catch (const ConvertException &ex) { } + } + else if (buf.find(':') != Anope::string::npos) + { + size_t sz = buf.find(':'); + if (sz + 2 < buf.length()) + this->message.headers[buf.substr(0, sz)] = buf.substr(sz + 2); + } + + return true; + } + + void SendError(HTTPError err, const Anope::string &msg) anope_override + { + HTTPReply h; + + h.error = err; + + h.Write(msg); + + this->SendReply(&h); + } + + void SendReply(HTTPReply *msg) anope_override + { + this->WriteClient("HTTP/1.1 " + GetStatusFromCode(msg->error)); + this->WriteClient("Date: " + BuildDate()); + this->WriteClient("Server: Anope-" + Anope::VersionShort()); + if (msg->content_type.empty()) + this->WriteClient("Content-Type: text/html"); + else + this->WriteClient("Content-Type: " + msg->content_type); + this->WriteClient("Content-Length: " + stringify(msg->length)); + + for (unsigned i = 0; i < msg->cookies.size(); ++i) + { + Anope::string buf = "Set-Cookie:"; + + for (HTTPReply::cookie::iterator it = msg->cookies[i].begin(), it_end = msg->cookies[i].end(); it != it_end; ++it) + buf += " " + it->first + "=" + it->second + ";"; + + buf.erase(buf.length() - 1); + + this->WriteClient(buf); + } + + typedef std::map map; + for (map::iterator it = msg->headers.begin(), it_end = msg->headers.end(); it != it_end; ++it) + this->WriteClient(it->first + ": " + it->second); + + this->WriteClient("Connection: Close"); + this->WriteClient(""); + + for (unsigned i = 0; i < msg->out.size(); ++i) + { + HTTPReply::Data* d = msg->out[i]; + + this->Write(d->buf, d->len); + + delete d; + } + + msg->out.clear(); + } +}; + +class MyHTTPProvider : public HTTPProvider, public Timer +{ + int timeout; + std::map pages; + std::list > clients; + + public: + MyHTTPProvider(Module *c, const Anope::string &n, const Anope::string &i, const unsigned short p, const int t, bool s) : Socket(-1, i.find(':') != Anope::string::npos), HTTPProvider(c, n, i, p, s), Timer(c, 10, Anope::CurTime, true), timeout(t) { } + + void Tick(time_t) anope_override + { + while (!this->clients.empty()) + { + Reference& c = this->clients.front(); + if (c && c->created + this->timeout >= Anope::CurTime) + break; + + delete c; + this->clients.pop_front(); + } + } + + ClientSocket* OnAccept(int fd, const sockaddrs &addr) anope_override + { + MyHTTPClient *c = new MyHTTPClient(this, fd, addr); + this->clients.push_back(c); + return c; + } + + bool RegisterPage(HTTPPage *page) anope_override + { + return this->pages.insert(std::make_pair(page->GetURL(), page)).second; + } + + void UnregisterPage(HTTPPage *page) anope_override + { + this->pages.erase(page->GetURL()); + } + + HTTPPage* FindPage(const Anope::string &pname) anope_override + { + if (this->pages.count(pname) == 0) + return NULL; + return this->pages[pname]; + } +}; + +class HTTPD : public Module +{ + ServiceReference sslref; + std::map providers; + public: + HTTPD(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR), sslref("SSLService", "ssl") + { + + } + + ~HTTPD() + { + for (std::map::const_iterator it = SocketEngine::Sockets.begin(), it_end = SocketEngine::Sockets.end(); it != it_end;) + { + Socket *s = it->second; + ++it; + + if (dynamic_cast(s) || dynamic_cast(s)) + delete s; + } + + this->providers.clear(); + } + + void OnReload(Configuration::Conf *config) anope_override + { + Configuration::Block *conf = config->GetModule(this); + std::set existing; + + for (int i = 0; i < conf->CountBlock("httpd"); ++i) + { + Configuration::Block *block = conf->GetBlock("httpd", i); + + + const Anope::string &hname = block->Get("name", "httpd/main"); + existing.insert(hname); + + Anope::string ip = block->Get("ip"); + int port = block->Get("port", "8080"); + int timeout = block->Get("timeout", "30"); + bool ssl = block->Get("ssl", "no"); + Anope::string ext_ip = block->Get("extforward_ip"); + Anope::string ext_header = block->Get("extforward_header"); + + if (ip.empty()) + { + Log(this) << "You must configure a bind IP for HTTP server " << hname; + continue; + } + else if (port <= 0 || port > 65535) + { + Log(this) << "You must configure a (valid) listen port for HTTP server " << hname; + continue; + } + + MyHTTPProvider *p; + if (this->providers.count(hname) == 0) + { + try + { + p = new MyHTTPProvider(this, hname, ip, port, timeout, ssl); + if (ssl && sslref) + sslref->Init(p); + } + catch (const SocketException &ex) + { + Log(this) << "Unable to create HTTP server " << hname << ": " << ex.GetReason(); + continue; + } + this->providers[hname] = p; + + Log(this) << "Created HTTP server " << hname; + } + else + { + p = this->providers[hname]; + + if (p->GetIP() != ip || p->GetPort() != port) + { + delete p; + this->providers.erase(hname); + + Log(this) << "Changing HTTP server " << hname << " to " << ip << ":" << port; + + try + { + p = new MyHTTPProvider(this, hname, ip, port, timeout, ssl); + if (ssl && sslref) + sslref->Init(p); + } + catch (const SocketException &ex) + { + Log(this) << "Unable to create HTTP server " << hname << ": " << ex.GetReason(); + continue; + } + + this->providers[hname] = p; + } + } + + + spacesepstream(ext_ip).GetTokens(p->ext_ips); + spacesepstream(ext_header).GetTokens(p->ext_headers); + } + + for (std::map::iterator it = this->providers.begin(), it_end = this->providers.end(); it != it_end;) + { + HTTPProvider *p = it->second; + ++it; + + if (existing.count(p->name) == 0) + { + Log(this) << "Removing HTTP server " << p->name; + this->providers.erase(p->name); + delete p; + } + } + } + + void OnModuleLoad(User *u, Module *m) anope_override + { + for (std::map::iterator it = this->providers.begin(), it_end = this->providers.end(); it != it_end; ++it) + { + MyHTTPProvider *p = it->second; + + if (p->IsSSL() && sslref) + try + { + sslref->Init(p); + } + catch (const CoreException &) { } // Throws on reinitialization + } + } +}; + +MODULE_INIT(HTTPD) diff --git a/modules/m_proxyscan.cpp b/modules/m_proxyscan.cpp new file mode 100644 index 0000000..766c30f --- /dev/null +++ b/modules/m_proxyscan.cpp @@ -0,0 +1,378 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" + +struct ProxyCheck +{ + std::set types; + std::vector ports; + time_t duration; + Anope::string reason; +}; + +static Anope::string ProxyCheckString; +static Anope::string target_ip; +static unsigned short target_port; +static bool add_to_akill; + +class ProxyCallbackListener : public ListenSocket +{ + class ProxyCallbackClient : public ClientSocket, public BufferedSocket + { + public: + ProxyCallbackClient(ListenSocket *l, int f, const sockaddrs &a) : Socket(f, l->IsIPv6()), ClientSocket(l, a), BufferedSocket() + { + } + + void OnAccept() anope_override + { + this->Write(ProxyCheckString); + } + + bool ProcessWrite() anope_override + { + return !BufferedSocket::ProcessWrite() || this->write_buffer.empty() ? false : true; + } + }; + + public: + ProxyCallbackListener(const Anope::string &b, int p) : Socket(-1, b.find(':') != Anope::string::npos), ListenSocket(b, p, false) + { + } + + ClientSocket *OnAccept(int fd, const sockaddrs &addr) anope_override + { + return new ProxyCallbackClient(this, fd, addr); + } +}; + +class ProxyConnect : public ConnectionSocket +{ + static ServiceReference akills; + + public: + static std::set proxies; + + ProxyCheck proxy; + unsigned short port; + time_t created; + + ProxyConnect(ProxyCheck &p, unsigned short po) : Socket(-1), ConnectionSocket(), proxy(p), + port(po), created(Anope::CurTime) + { + proxies.insert(this); + } + + ~ProxyConnect() + { + proxies.erase(this); + } + + virtual void OnConnect() anope_override = 0; + virtual const Anope::string GetType() const = 0; + + protected: + void Ban() + { + Anope::string reason = this->proxy.reason; + + reason = reason.replace_all_cs("%t", this->GetType()); + reason = reason.replace_all_cs("%i", this->conaddr.addr()); + reason = reason.replace_all_cs("%p", stringify(this->conaddr.port())); + + BotInfo *OperServ = Config->GetClient("OperServ"); + Log(OperServ) << "PROXYSCAN: Open " << this->GetType() << " proxy found on " << this->conaddr.addr() << ":" << this->conaddr.port() << " (" << reason << ")"; + XLine *x = new XLine("*@" + this->conaddr.addr(), OperServ ? OperServ->nick : "", Anope::CurTime + this->proxy.duration, reason, XLineManager::GenerateUID()); + if (add_to_akill && akills) + { + akills->AddXLine(x); + akills->Send(NULL, x); + } + else + { + if (IRCD->CanSZLine) + IRCD->SendSZLine(NULL, x); + else + IRCD->SendAkill(NULL, x); + delete x; + } + } +}; +ServiceReference ProxyConnect::akills("XLineManager", "xlinemanager/sgline"); +std::set ProxyConnect::proxies; + +class HTTPProxyConnect : public ProxyConnect, public BufferedSocket +{ + public: + HTTPProxyConnect(ProxyCheck &p, unsigned short po) : Socket(-1), ProxyConnect(p, po), BufferedSocket() + { + } + + void OnConnect() anope_override + { + this->Write("CONNECT %s:%d HTTP/1.0", target_ip.c_str(), target_port); + this->Write("Content-Length: 0"); + this->Write("Connection: close"); + this->Write(""); + } + + const Anope::string GetType() const anope_override + { + return "HTTP"; + } + + bool ProcessRead() anope_override + { + bool b = BufferedSocket::ProcessRead(); + if (this->GetLine() == ProxyCheckString) + { + this->Ban(); + return false; + } + return b; + } +}; + +class SOCKS5ProxyConnect : public ProxyConnect, public BinarySocket +{ + public: + SOCKS5ProxyConnect(ProxyCheck &p, unsigned short po) : Socket(-1), ProxyConnect(p, po), BinarySocket() + { + } + + void OnConnect() anope_override + { + sockaddrs target_addr; + char buf[4 + sizeof(target_addr.sa4.sin_addr.s_addr) + sizeof(target_addr.sa4.sin_port)]; + int ptr = 0; + target_addr.pton(AF_INET, target_ip, target_port); + if (!target_addr.valid()) + return; + + buf[ptr++] = 5; // Version + buf[ptr++] = 1; // # of methods + buf[ptr++] = 0; // No authentication + + this->Write(buf, ptr); + + ptr = 1; + buf[ptr++] = 1; // Connect + buf[ptr++] = 0; // Reserved + buf[ptr++] = 1; // IPv4 + memcpy(buf + ptr, &target_addr.sa4.sin_addr.s_addr, sizeof(target_addr.sa4.sin_addr.s_addr)); + ptr += sizeof(target_addr.sa4.sin_addr.s_addr); + memcpy(buf + ptr, &target_addr.sa4.sin_port, sizeof(target_addr.sa4.sin_port)); + ptr += sizeof(target_addr.sa4.sin_port); + + this->Write(buf, ptr); + } + + const Anope::string GetType() const anope_override + { + return "SOCKS5"; + } + + bool Read(const char *buffer, size_t l) anope_override + { + if (l >= ProxyCheckString.length() && !strncmp(buffer, ProxyCheckString.c_str(), ProxyCheckString.length())) + { + this->Ban(); + return false; + } + return true; + } +}; + +class ModuleProxyScan : public Module +{ + Anope::string listen_ip; + unsigned short listen_port; + Anope::string con_notice, con_source; + std::vector proxyscans; + + ProxyCallbackListener *listener; + + class ConnectionTimeout : public Timer + { + public: + ConnectionTimeout(Module *c, long timeout) : Timer(c, timeout, Anope::CurTime, true) + { + } + + void Tick(time_t) anope_override + { + for (std::set::iterator it = ProxyConnect::proxies.begin(), it_end = ProxyConnect::proxies.end(); it != it_end;) + { + ProxyConnect *p = *it; + ++it; + + if (p->created + this->GetSecs() < Anope::CurTime) + delete p; + } + } + } connectionTimeout; + + public: + ModuleProxyScan(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR), + connectionTimeout(this, 5) + { + + + this->listener = NULL; + } + + ~ModuleProxyScan() + { + for (std::set::iterator it = ProxyConnect::proxies.begin(), it_end = ProxyConnect::proxies.end(); it != it_end;) + { + ProxyConnect *p = *it; + ++it; + delete p; + } + + for (std::map::const_iterator it = SocketEngine::Sockets.begin(), it_end = SocketEngine::Sockets.end(); it != it_end;) + { + Socket *s = it->second; + ++it; + + ClientSocket *cs = dynamic_cast(s); + if (cs != NULL && cs->ls == this->listener) + delete s; + } + + delete this->listener; + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *config = Config->GetModule(this); + + Anope::string s_target_ip = config->Get("target_ip"); + if (s_target_ip.empty()) + throw ConfigException(this->name + " target_ip may not be empty"); + + int s_target_port = config->Get("target_port", "-1"); + if (s_target_port <= 0) + throw ConfigException(this->name + " target_port may not be empty and must be a positive number"); + + Anope::string s_listen_ip = config->Get("listen_ip"); + if (s_listen_ip.empty()) + throw ConfigException(this->name + " listen_ip may not be empty"); + + int s_listen_port = config->Get("listen_port", "-1"); + if (s_listen_port <= 0) + throw ConfigException(this->name + " listen_port may not be empty and must be a positive number"); + + target_ip = s_target_ip; + target_port = s_target_port; + this->listen_ip = s_listen_ip; + this->listen_port = s_listen_port; + this->con_notice = config->Get("connect_notice"); + this->con_source = config->Get("connect_source"); + add_to_akill = config->Get("add_to_akill", "true"); + this->connectionTimeout.SetSecs(config->Get("timeout", "5s")); + + ProxyCheckString = Config->GetBlock("networkinfo")->Get("networkname") + " proxy check"; + delete this->listener; + this->listener = NULL; + try + { + this->listener = new ProxyCallbackListener(this->listen_ip, this->listen_port); + } + catch (const SocketException &ex) + { + throw ConfigException("m_proxyscan: " + ex.GetReason()); + } + + this->proxyscans.clear(); + for (int i = 0; i < config->CountBlock("proxyscan"); ++i) + { + Configuration::Block *block = config->GetBlock("proxyscan", i); + ProxyCheck p; + Anope::string token; + + commasepstream sep(block->Get("type")); + while (sep.GetToken(token)) + { + if (!token.equals_ci("HTTP") && !token.equals_ci("SOCKS5")) + continue; + p.types.insert(token); + } + if (p.types.empty()) + continue; + + commasepstream sep2(block->Get("port")); + while (sep2.GetToken(token)) + { + try + { + unsigned short port = convertTo(token); + p.ports.push_back(port); + } + catch (const ConvertException &) { } + } + if (p.ports.empty()) + continue; + + p.duration = block->Get("time", "4h"); + p.reason = block->Get("reason"); + if (p.reason.empty()) + continue; + + this->proxyscans.push_back(p); + } + } + + void OnUserConnect(User *user, bool &exempt) anope_override + { + if (exempt || user->Quitting() || !Me->IsSynced() || !user->server->IsSynced()) + return; + + /* At this time we only support IPv4 */ + if (!user->ip.valid() || user->ip.sa.sa_family != AF_INET) + /* User doesn't have a valid IPv4 IP (ipv6/spoof/etc) */ + return; + + if (!this->con_notice.empty() && !this->con_source.empty()) + { + BotInfo *bi = BotInfo::Find(this->con_source, true); + if (bi) + user->SendMessage(bi, this->con_notice); + } + + for (unsigned i = this->proxyscans.size(); i > 0; --i) + { + ProxyCheck &p = this->proxyscans[i - 1]; + + for (std::set::iterator it = p.types.begin(), it_end = p.types.end(); it != it_end; ++it) + { + for (unsigned k = 0; k < p.ports.size(); ++k) + { + try + { + ProxyConnect *con = NULL; + if (it->equals_ci("HTTP")) + con = new HTTPProxyConnect(p, p.ports[k]); + else if (it->equals_ci("SOCKS5")) + con = new SOCKS5ProxyConnect(p, p.ports[k]); + else + continue; + con->Connect(user->ip.addr(), p.ports[k]); + } + catch (const SocketException &ex) + { + Log(LOG_DEBUG) << "m_proxyscan: " << ex.GetReason(); + } + } + } + } + } +}; + +MODULE_INIT(ModuleProxyScan) diff --git a/modules/m_redis.cpp b/modules/m_redis.cpp new file mode 100644 index 0000000..630d246 --- /dev/null +++ b/modules/m_redis.cpp @@ -0,0 +1,625 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/redis.h" + +using namespace Redis; + +class MyRedisService; + +class RedisSocket : public BinarySocket, public ConnectionSocket +{ + size_t ParseReply(Reply &r, const char *buf, size_t l); + public: + MyRedisService *provider; + std::deque interfaces; + std::map subinterfaces; + + RedisSocket(MyRedisService *pro, bool v6) : Socket(-1, v6), provider(pro) { } + + ~RedisSocket(); + + void OnConnect() anope_override; + void OnError(const Anope::string &error) anope_override; + + bool Read(const char *buffer, size_t l) anope_override; +}; + +class Transaction : public Interface +{ + public: + std::deque interfaces; + + Transaction(Module *creator) : Interface(creator) { } + + ~Transaction() + { + for (unsigned i = 0; i < interfaces.size(); ++i) + { + Interface *inter = interfaces[i]; + + if (!inter) + continue; + + inter->OnError("Interface going away"); + } + } + + void OnResult(const Reply &r) anope_override + { + /* This is a multi bulk reply of the results of the queued commands + * in this transaction + */ + + Log(LOG_DEBUG_2) << "redis: transaction complete with " << r.multi_bulk.size() << " results"; + + for (unsigned i = 0; i < r.multi_bulk.size(); ++i) + { + const Reply *reply = r.multi_bulk[i]; + + if (interfaces.empty()) + break; + + Interface *inter = interfaces.front(); + interfaces.pop_front(); + + if (inter) + inter->OnResult(*reply); + } + } +}; + +class MyRedisService : public Provider +{ + public: + Anope::string host; + int port; + unsigned db; + + RedisSocket *sock, *sub; + + Transaction ti; + bool in_transaction; + + MyRedisService(Module *c, const Anope::string &n, const Anope::string &h, int p, unsigned d) : Provider(c, n), host(h), port(p), db(d), sock(NULL), sub(NULL), + ti(c), in_transaction(false) + { + sock = new RedisSocket(this, host.find(':') != Anope::string::npos); + sock->Connect(host, port); + + sub = new RedisSocket(this, host.find(':') != Anope::string::npos); + sub->Connect(host, port); + } + + ~MyRedisService() + { + if (sock) + { + sock->flags[SF_DEAD] = true; + sock->provider = NULL; + } + + if (sub) + { + sub->flags[SF_DEAD] = true; + sub->provider = NULL; + } + } + + private: + inline void Pack(std::vector &buffer, const char *buf, size_t sz = 0) + { + if (!sz) + sz = strlen(buf); + + size_t old_size = buffer.size(); + buffer.resize(old_size + sz); + std::copy(buf, buf + sz, buffer.begin() + old_size); + } + + void Send(RedisSocket *s, Interface *i, const std::vector > &args) + { + std::vector buffer; + + Pack(buffer, "*"); + Pack(buffer, stringify(args.size()).c_str()); + Pack(buffer, "\r\n"); + + for (unsigned j = 0; j < args.size(); ++j) + { + const std::pair &pair = args[j]; + + Pack(buffer, "$"); + Pack(buffer, stringify(pair.second).c_str()); + Pack(buffer, "\r\n"); + + Pack(buffer, pair.first, pair.second); + Pack(buffer, "\r\n"); + } + + if (buffer.empty()) + return; + + s->Write(&buffer[0], buffer.size()); + if (in_transaction) + { + ti.interfaces.push_back(i); + s->interfaces.push_back(NULL); // For the +Queued response + } + else + s->interfaces.push_back(i); + } + + public: + bool IsSocketDead() anope_override + { + return this->sock && this->sock->flags[SF_DEAD]; + } + + void SendCommand(RedisSocket *s, Interface *i, const std::vector &cmds) + { + std::vector > args; + for (unsigned j = 0; j < cmds.size(); ++j) + args.push_back(std::make_pair(cmds[j].c_str(), cmds[j].length())); + this->Send(s, i, args); + } + + void SendCommand(RedisSocket *s, Interface *i, const Anope::string &str) + { + std::vector args; + spacesepstream(str).GetTokens(args); + this->SendCommand(s, i, args); + } + + void Send(Interface *i, const std::vector > &args) + { + if (!sock) + { + sock = new RedisSocket(this, host.find(':') != Anope::string::npos); + sock->Connect(host, port); + } + + this->Send(sock, i, args); + } + + void SendCommand(Interface *i, const std::vector &cmds) anope_override + { + std::vector > args; + for (unsigned j = 0; j < cmds.size(); ++j) + args.push_back(std::make_pair(cmds[j].c_str(), cmds[j].length())); + this->Send(i, args); + } + + void SendCommand(Interface *i, const Anope::string &str) anope_override + { + std::vector args; + spacesepstream(str).GetTokens(args); + this->SendCommand(i, args); + } + + public: + bool BlockAndProcess() anope_override + { + if (!this->sock->ProcessWrite()) + this->sock->flags[SF_DEAD] = true; + this->sock->SetBlocking(true); + if (!this->sock->ProcessRead()) + this->sock->flags[SF_DEAD] = true; + this->sock->SetBlocking(false); + return !this->sock->interfaces.empty(); + } + + void Subscribe(Interface *i, const Anope::string &pattern) anope_override + { + if (sub == NULL) + { + sub = new RedisSocket(this, host.find(':') != Anope::string::npos); + sub->Connect(host, port); + } + + std::vector args; + args.push_back("PSUBSCRIBE"); + args.push_back(pattern); + this->SendCommand(sub, NULL, args); + + sub->subinterfaces[pattern] = i; + } + + void Unsubscribe(const Anope::string &pattern) anope_override + { + if (sub) + sub->subinterfaces.erase(pattern); + } + + void StartTransaction() anope_override + { + if (in_transaction) + throw CoreException(); + + this->SendCommand(NULL, "MULTI"); + in_transaction = true; + } + + void CommitTransaction() anope_override + { + /* The result of the transaction comes back to the reply of EXEC as a multi bulk. + * The reply to the individual commands that make up the transaction when executed + * is a simple +QUEUED + */ + in_transaction = false; + this->SendCommand(&this->ti, "EXEC"); + } +}; + +RedisSocket::~RedisSocket() +{ + if (provider) + { + if (provider->sock == this) + provider->sock = NULL; + else if (provider->sub == this) + provider->sub = NULL; + } + + for (unsigned i = 0; i < interfaces.size(); ++i) + { + Interface *inter = interfaces[i]; + + if (!inter) + continue; + + inter->OnError("Interface going away"); + } +} + +void RedisSocket::OnConnect() +{ + Log() << "redis: Successfully connected to " << provider->name << (this == this->provider->sub ? " (sub)" : ""); + + this->provider->SendCommand(NULL, "CLIENT SETNAME Anope"); + this->provider->SendCommand(NULL, "SELECT " + stringify(provider->db)); + + if (this != this->provider->sub) + { + this->provider->SendCommand(this, NULL, "CONFIG SET notify-keyspace-events KA"); + } +} + +void RedisSocket::OnError(const Anope::string &error) +{ + Log() << "redis: Error on " << provider->name << (this == this->provider->sub ? " (sub)" : "") << ": " << error; +} + +size_t RedisSocket::ParseReply(Reply &r, const char *buffer, size_t l) +{ + size_t used = 0; + + if (!l) + return used; + + if (r.type == Reply::MULTI_BULK) + goto multi_bulk_cont; + + switch (*buffer) + { + case '+': + { + Anope::string reason(buffer, 1, l - 1); + size_t nl = reason.find("\r\n"); + Log(LOG_DEBUG_2) << "redis: status ok: " << reason.substr(0, nl); + if (nl != Anope::string::npos) + { + r.type = Reply::OK; + used = 1 + nl + 2; + } + break; + } + case '-': + { + Anope::string reason(buffer, 1, l - 1); + size_t nl = reason.find("\r\n"); + Log(LOG_DEBUG) << "redis: status error: " << reason.substr(0, nl); + if (nl != Anope::string::npos) + { + r.type = Reply::NOT_OK; + used = 1 + nl + 2; + } + break; + } + case ':': + { + Anope::string ibuf(buffer, 1, l - 1); + size_t nl = ibuf.find("\r\n"); + if (nl != Anope::string::npos) + { + try + { + r.i = convertTo(ibuf.substr(0, nl)); + } + catch (const ConvertException &) { } + + r.type = Reply::INT; + used = 1 + nl + 2; + } + break; + } + case '$': + { + Anope::string reply(buffer + 1, l - 1); + /* This assumes one bulk can always fit in our recv buffer */ + size_t nl = reply.find("\r\n"); + if (nl != Anope::string::npos) + { + int len; + try + { + len = convertTo(reply.substr(0, nl)); + if (len >= 0) + { + if (1 + nl + 2 + len + 2 <= l) + { + used = 1 + nl + 2 + len + 2; + r.bulk = reply.substr(nl + 2, len); + r.type = Reply::BULK; + } + } + else + { + used = 1 + nl + 2 + 2; + r.type = Reply::BULK; + } + } + catch (const ConvertException &) { } + } + break; + } + multi_bulk_cont: + case '*': + { + if (r.type != Reply::MULTI_BULK) + { + Anope::string reply(buffer + 1, l - 1); + size_t nl = reply.find("\r\n"); + if (nl != Anope::string::npos) + { + r.type = Reply::MULTI_BULK; + try + { + r.multi_bulk_size = convertTo(reply.substr(0, nl)); + } + catch (const ConvertException &) { } + + used = 1 + nl + 2; + } + else + break; + } + else if (r.multi_bulk_size >= 0 && r.multi_bulk.size() == static_cast(r.multi_bulk_size)) + { + /* This multi bulk is already complete, so check the sub bulks */ + for (unsigned i = 0; i < r.multi_bulk.size(); ++i) + if (r.multi_bulk[i]->type == Reply::MULTI_BULK) + ParseReply(*r.multi_bulk[i], buffer + used, l - used); + break; + } + + for (int i = r.multi_bulk.size(); i < r.multi_bulk_size; ++i) + { + Reply *reply = new Reply(); + size_t u = ParseReply(*reply, buffer + used, l - used); + if (!u) + { + Log(LOG_DEBUG) << "redis: ran out of data to parse"; + delete reply; + break; + } + r.multi_bulk.push_back(reply); + used += u; + } + break; + } + default: + Log(LOG_DEBUG) << "redis: unknown reply " << *buffer; + } + + return used; +} + +bool RedisSocket::Read(const char *buffer, size_t l) +{ + static std::vector save; + std::vector copy; + + if (!save.empty()) + { + std::copy(buffer, buffer + l, std::back_inserter(save)); + + copy = save; + + buffer = ©[0]; + l = copy.size(); + } + + while (l) + { + static Reply r; + + size_t used = this->ParseReply(r, buffer, l); + if (!used) + { + Log(LOG_DEBUG) << "redis: used == 0 ?"; + r.Clear(); + break; + } + else if (used > l) + { + Log(LOG_DEBUG) << "redis: used > l ?"; + r.Clear(); + break; + } + + /* Full result is not here yet */ + if (r.type == Reply::MULTI_BULK && static_cast(r.multi_bulk_size) != r.multi_bulk.size()) + { + buffer += used; + l -= used; + break; + } + + if (this == provider->sub) + { + if (r.multi_bulk.size() == 4) + { + /* pmessage + * pattern subscribed to + * __keyevent@0__:set + * key + */ + std::map::iterator it = this->subinterfaces.find(r.multi_bulk[1]->bulk); + if (it != this->subinterfaces.end()) + it->second->OnResult(r); + } + } + else + { + if (this->interfaces.empty()) + { + Log(LOG_DEBUG) << "redis: no interfaces?"; + } + else + { + Interface *i = this->interfaces.front(); + this->interfaces.pop_front(); + + if (i) + { + if (r.type != Reply::NOT_OK) + i->OnResult(r); + else + i->OnError(r.bulk); + } + } + } + + buffer += used; + l -= used; + + r.Clear(); + } + + if (l) + { + save.resize(l); + std::copy(buffer, buffer + l, save.begin()); + } + else + std::vector().swap(save); + + return true; +} + + +class ModuleRedis : public Module +{ + std::map services; + + public: + ModuleRedis(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR) + { + } + + ~ModuleRedis() + { + for (std::map::iterator it = services.begin(); it != services.end(); ++it) + { + MyRedisService *p = it->second; + + delete p->sock; + p->sock = NULL; + delete p->sub; + p->sub = NULL; + + delete p; + } + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Configuration::Block *block = conf->GetModule(this); + std::vector new_services; + + for (int i = 0; i < block->CountBlock("redis"); ++i) + { + Configuration::Block *redis = block->GetBlock("redis", i); + + const Anope::string &n = redis->Get("name"), + &ip = redis->Get("ip"); + int port = redis->Get("port"); + unsigned db = redis->Get("db"); + + delete services[n]; + services[n] = new MyRedisService(this, n, ip, port, db); + new_services.push_back(n); + } + + for (std::map::iterator it = services.begin(); it != services.end();) + { + Provider *p = it->second; + ++it; + + if (std::find(new_services.begin(), new_services.end(), p->name) == new_services.end()) + delete it->second; + } + } + + void OnModuleUnload(User *, Module *m) anope_override + { + for (std::map::iterator it = services.begin(); it != services.end(); ++it) + { + MyRedisService *p = it->second; + + if (p->sock) + for (unsigned i = p->sock->interfaces.size(); i > 0; --i) + { + Interface *inter = p->sock->interfaces[i - 1]; + + if (inter && inter->owner == m) + { + inter->OnError(m->name + " being unloaded"); + p->sock->interfaces.erase(p->sock->interfaces.begin() + i - 1); + } + } + + if (p->sub) + for (unsigned i = p->sub->interfaces.size(); i > 0; --i) + { + Interface *inter = p->sub->interfaces[i - 1]; + + if (inter && inter->owner == m) + { + inter->OnError(m->name + " being unloaded"); + p->sub->interfaces.erase(p->sub->interfaces.begin() + i - 1); + } + } + + for (unsigned i = p->ti.interfaces.size(); i > 0; --i) + { + Interface *inter = p->ti.interfaces[i - 1]; + + if (inter && inter->owner == m) + { + inter->OnError(m->name + " being unloaded"); + p->ti.interfaces.erase(p->ti.interfaces.begin() + i - 1); + } + } + } + } +}; + +MODULE_INIT(ModuleRedis) diff --git a/modules/m_rewrite.cpp b/modules/m_rewrite.cpp new file mode 100644 index 0000000..306a080 --- /dev/null +++ b/modules/m_rewrite.cpp @@ -0,0 +1,187 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" + +struct Rewrite +{ + Anope::string client, source_message, target_message, desc; + + bool Matches(const std::vector &message) + { + std::vector sm; + spacesepstream(this->source_message).GetTokens(sm); + + for (unsigned i = 0; i < sm.size(); ++i) + if (i >= message.size() || (sm[i] != "$" && !sm[i].equals_ci(message[i]))) + return false; + + return true; + } + + Anope::string Process(CommandSource &source, const std::vector ¶ms) + { + spacesepstream sep(this->target_message); + Anope::string token, message; + + while (sep.GetToken(token)) + { + if (token[0] != '$') + message += " " + token; + else if (token == "$me") + message += " " + source.GetNick(); + else + { + int num = -1, end = -1; + try + { + Anope::string num_str = token.substr(1); + size_t hy = num_str.find('-'); + if (hy == Anope::string::npos) + { + num = convertTo(num_str); + end = num + 1; + } + else + { + num = convertTo(num_str.substr(0, hy)); + if (hy == num_str.length() - 1) + end = params.size(); + else + end = convertTo(num_str.substr(hy + 1)) + 1; + } + } + catch (const ConvertException &) + { + continue; + } + + for (int i = num; i < end && static_cast(i) < params.size(); ++i) + message += " " + params[i]; + } + } + + message.trim(); + return message; + } + + static std::vector rewrites; + + static Rewrite *Find(const Anope::string &client, const Anope::string &cmd) + { + for (unsigned i = 0; i < rewrites.size(); ++i) + { + Rewrite &r = rewrites[i]; + + if ((client.empty() || r.client.equals_ci(client)) && (r.source_message.equals_ci(cmd) || r.source_message.find_ci(cmd + " ") == 0)) + return &r; + } + + return NULL; + } + + static Rewrite *Match(const Anope::string &client, const std::vector ¶ms) + { + for (unsigned i = 0; i < rewrites.size(); ++i) + { + Rewrite &r = rewrites[i]; + + if ((client.empty() || r.client.equals_ci(client)) && r.Matches(params)) + return &r; + } + + return NULL; + } +}; + +std::vector Rewrite::rewrites; + +class RewriteCommand : public Command +{ + public: + RewriteCommand(Module *creator) : Command(creator, "rewrite", 0, 0) { } + + void Execute(CommandSource &source, const std::vector ¶ms) anope_override + { + std::vector full_params = params; + full_params.insert(full_params.begin(), source.command); + + Rewrite *r = Rewrite::Match(!source.c ? source.service->nick : "", full_params); + if (r != NULL) + { + Anope::string new_message = r->Process(source, full_params); + Log(LOG_DEBUG) << "m_rewrite: Rewrote '" << source.command << (!params.empty() ? " " + params[0] : "") << "' to '" << new_message << "' using '" << r->source_message << "'"; + source.service = BotInfo::Find(r->client, true); + if (!source.service) + return; + Command::Run(source, new_message); + } + else + Log() << "m_rewrite: Unable to rewrite '" << source.command << (!params.empty() ? " " + params[0] : "") << "'"; + } + + void OnServHelp(CommandSource &source) anope_override + { + Rewrite *r = Rewrite::Find(!source.c ? source.service->nick : "", source.command); + if (r != NULL && !r->desc.empty()) + { + this->SetDesc(r->desc); + Command::OnServHelp(source); + } + } + + bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override + { + Rewrite *r = Rewrite::Find(!source.c ? source.service->nick : "", source.command); + if (r != NULL && !r->desc.empty()) + { + source.Reply(r->desc); + size_t sz = r->target_message.find(' '); + source.Reply(_("This command is an alias to the command %s."), sz != Anope::string::npos ? r->target_message.substr(0, sz).c_str() : r->target_message.c_str()); + return true; + } + return false; + } +}; + +class ModuleRewrite : public Module +{ + RewriteCommand cmdrewrite; + + public: + ModuleRewrite(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR | EXTRA), cmdrewrite(this) + { + } + + void OnReload(Configuration::Conf *conf) anope_override + { + Rewrite::rewrites.clear(); + + for (int i = 0; i < conf->CountBlock("command"); ++i) + { + Configuration::Block *block = conf->GetBlock("command", i); + + if (!block->Get("rewrite")) + continue; + + Rewrite rw; + + rw.client = block->Get("service"); + rw.source_message = block->Get("rewrite_source"); + rw.target_message = block->Get("rewrite_target"); + rw.desc = block->Get("rewrite_description"); + + if (rw.client.empty() || rw.source_message.empty() || rw.target_message.empty()) + continue; + + Rewrite::rewrites.push_back(rw); + } + } +}; + +MODULE_INIT(ModuleRewrite) diff --git a/modules/m_sasl.cpp b/modules/m_sasl.cpp new file mode 100644 index 0000000..26c5cab --- /dev/null +++ b/modules/m_sasl.cpp @@ -0,0 +1,357 @@ +/* + * + * (C) 2014-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/sasl.h" +#include "modules/ns_cert.h" + +using namespace SASL; + +class Plain : public Mechanism +{ + public: + Plain(Module *o) : Mechanism(o, "PLAIN") { } + + void ProcessMessage(Session *sess, const SASL::Message &m) anope_override + { + if (m.type == "S") + { + sasl->SendMessage(sess, "C", "+"); + } + else if (m.type == "C") + { + Anope::string decoded; + Anope::B64Decode(m.data, decoded); + + size_t p = decoded.find('\0'); + if (p == Anope::string::npos) + { + sasl->Fail(sess); + delete sess; + return; + } + decoded = decoded.substr(p + 1); + + p = decoded.find('\0'); + if (p == Anope::string::npos) + { + sasl->Fail(sess); + delete sess; + return; + } + + Anope::string acc = decoded.substr(0, p), + pass = decoded.substr(p + 1); + + if (acc.empty() || pass.empty() || !IRCD->IsNickValid(acc) || pass.find_first_of("\r\n") != Anope::string::npos) + { + sasl->Fail(sess); + delete sess; + return; + } + + SASL::IdentifyRequest *req = new SASL::IdentifyRequest(this->owner, m.source, acc, pass, sess->hostname, sess->ip); + FOREACH_MOD(OnCheckAuthentication, (NULL, req)); + req->Dispatch(); + } + } +}; + +class External : public Mechanism +{ + ServiceReference certs; + + struct Session : SASL::Session + { + Anope::string cert; + + Session(Mechanism *m, const Anope::string &u) : SASL::Session(m, u) { } + }; + + public: + External(Module *o) : Mechanism(o, "EXTERNAL"), certs("CertService", "certs") + { + if (!IRCD || !IRCD->CanCertFP) + throw ModuleException("No CertFP"); + } + + Session* CreateSession(const Anope::string &uid) anope_override + { + return new Session(this, uid); + } + + void ProcessMessage(SASL::Session *sess, const SASL::Message &m) anope_override + { + Session *mysess = anope_dynamic_static_cast(sess); + + if (m.type == "S") + { + mysess->cert = m.ext; + + sasl->SendMessage(sess, "C", "+"); + } + else if (m.type == "C") + { + if (!certs || mysess->cert.empty()) + { + sasl->Fail(sess); + delete sess; + return; + } + + Anope::string user = "A user"; + if (!mysess->hostname.empty() && !mysess->ip.empty()) + user = mysess->hostname + " (" + mysess->ip + ")"; + + NickCore *nc = certs->FindAccountFromCert(mysess->cert); + if (!nc || nc->HasExt("NS_SUSPENDED") || nc->HasExt("UNCONFIRMED")) + { + Log(this->owner, "sasl", Config->GetClient("NickServ")) << user << " failed to identify using certificate " << mysess->cert << " using SASL EXTERNAL"; + sasl->Fail(sess); + delete sess; + return; + } + + Log(this->owner, "sasl", Config->GetClient("NickServ")) << user << " identified to account " << nc->display << " using SASL EXTERNAL"; + sasl->Succeed(sess, nc); + delete sess; + } + } +}; + +class SASLService : public SASL::Service, public Timer +{ + std::map sessions; + + public: + SASLService(Module *o) : SASL::Service(o), Timer(o, 60, Anope::CurTime, true) { } + + ~SASLService() + { + for (std::map::iterator it = sessions.begin(); it != sessions.end(); it++) + delete it->second; + } + + void ProcessMessage(const SASL::Message &m) anope_override + { + if (m.target != "*") + { + Server *s = Server::Find(m.target); + if (s != Me) + { + User *u = User::Find(m.target); + if (!u || u->server != Me) + return; + } + } + + Session* session = GetSession(m.source); + + if (m.type == "S") + { + ServiceReference mech("SASL::Mechanism", m.data); + if (!mech) + { + Session tmp(NULL, m.source); + + sasl->SendMechs(&tmp); + sasl->Fail(&tmp); + return; + } + + Anope::string hostname, ip; + if (session) + { + // Copy over host/ip to mech-specific session + hostname = session->hostname; + ip = session->ip; + delete session; + } + + session = mech->CreateSession(m.source); + if (session) + { + session->hostname = hostname; + session->ip = ip; + + sessions[m.source] = session; + } + } + else if (m.type == "D") + { + delete session; + return; + } + else if (m.type == "H") + { + if (!session) + { + session = new Session(NULL, m.source); + sessions[m.source] = session; + } + session->hostname = m.data; + session->ip = m.ext; + } + + if (session && session->mech) + session->mech->ProcessMessage(session, m); + } + + Anope::string GetAgent() anope_override + { + Anope::string agent = Config->GetModule(Service::owner)->Get("agent", "NickServ"); + BotInfo *bi = Config->GetClient(agent); + if (bi) + agent = bi->GetUID(); + return agent; + } + + Session* GetSession(const Anope::string &uid) anope_override + { + std::map::iterator it = sessions.find(uid); + if (it != sessions.end()) + return it->second; + return NULL; + } + + void RemoveSession(Session *sess) anope_override + { + sessions.erase(sess->uid); + } + + void DeleteSessions(Mechanism *mech, bool da) anope_override + { + for (std::map::iterator it = sessions.begin(); it != sessions.end();) + { + std::map::iterator del = it++; + if (*del->second->mech == mech) + { + if (da) + this->SendMessage(del->second, "D", "A"); + delete del->second; + } + } + } + + void SendMessage(Session *session, const Anope::string &mtype, const Anope::string &data) anope_override + { + SASL::Message msg; + msg.source = this->GetAgent(); + msg.target = session->uid; + msg.type = mtype; + msg.data = data; + + IRCD->SendSASLMessage(msg); + } + + void Succeed(Session *session, NickCore *nc) anope_override + { + // If the user is already introduced then we log them in now. + // Otherwise, we send an SVSLOGIN to log them in later. + User *user = User::Find(session->uid); + NickAlias *na = NickAlias::Find(nc->display); + if (user) + { + user->Identify(na); + } + else + { + IRCD->SendSVSLogin(session->uid, nc->display, na->GetVhostIdent(), na->GetVhostHost()); + } + this->SendMessage(session, "D", "S"); + } + + void Fail(Session *session) anope_override + { + this->SendMessage(session, "D", "F"); + } + + void SendMechs(Session *session) anope_override + { + std::vector mechs = Service::GetServiceKeys("SASL::Mechanism"); + Anope::string buf; + for (unsigned j = 0; j < mechs.size(); ++j) + buf += "," + mechs[j]; + + this->SendMessage(session, "M", buf.empty() ? "" : buf.substr(1)); + } + + void Tick(time_t) anope_override + { + for (std::map::iterator it = sessions.begin(); it != sessions.end();) + { + Anope::string key = it->first; + Session *s = it->second; + ++it; + + if (!s || s->created + 60 < Anope::CurTime) + { + delete s; + sessions.erase(key); + } + } + } +}; + +class ModuleSASL : public Module +{ + SASLService sasl; + + Plain plain; + External *external; + + std::vector mechs; + + void CheckMechs() + { + std::vector newmechs = ::Service::GetServiceKeys("SASL::Mechanism"); + if (newmechs == mechs) + return; + + mechs = newmechs; + + // If we are connected to the network then broadcast the mechlist. + if (Me && Me->IsSynced()) + IRCD->SendSASLMechanisms(mechs); + } + + public: + ModuleSASL(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), + sasl(this), plain(this), external(NULL) + { + try + { + external = new External(this); + CheckMechs(); + } + catch (ModuleException &) { } + } + + ~ModuleSASL() + { + delete external; + } + + void OnModuleLoad(User *, Module *) anope_override + { + CheckMechs(); + } + + void OnModuleUnload(User *, Module *) anope_override + { + CheckMechs(); + } + + void OnPreUplinkSync(Server *) anope_override + { + // We have not yet sent a mechanism list so always do it here. + IRCD->SendSASLMechanisms(mechs); + } +}; + +MODULE_INIT(ModuleSASL) diff --git a/modules/m_xmlrpc.cpp b/modules/m_xmlrpc.cpp new file mode 100644 index 0000000..885d8aa --- /dev/null +++ b/modules/m_xmlrpc.cpp @@ -0,0 +1,228 @@ +/* + * + * (C) 2010-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/xmlrpc.h" +#include "modules/httpd.h" + +static struct special_chars +{ + Anope::string character; + Anope::string replace; + + special_chars(const Anope::string &c, const Anope::string &r) : character(c), replace(r) { } +} +special[] = { + special_chars("&", "&"), + special_chars("\"", """), + special_chars("<", "<"), + special_chars(">", "&qt;"), + special_chars("'", "'"), + special_chars("\n", " "), + special_chars("\002", ""), // bold + special_chars("\003", ""), // color + special_chars("\035", ""), // italics + special_chars("\037", ""), // underline + special_chars("\026", ""), // reverses + special_chars("", "") +}; + +class MyXMLRPCServiceInterface : public XMLRPCServiceInterface, public HTTPPage +{ + std::deque events; + + public: + MyXMLRPCServiceInterface(Module *creator, const Anope::string &sname) : XMLRPCServiceInterface(creator, sname), HTTPPage("/xmlrpc", "text/xml") { } + + void Register(XMLRPCEvent *event) anope_override + { + this->events.push_back(event); + } + + void Unregister(XMLRPCEvent *event) anope_override + { + std::deque::iterator it = std::find(this->events.begin(), this->events.end(), event); + + if (it != this->events.end()) + this->events.erase(it); + } + + Anope::string Sanitize(const Anope::string &string) anope_override + { + Anope::string ret = string; + for (int i = 0; special[i].character.empty() == false; ++i) + ret = ret.replace_all_cs(special[i].character, special[i].replace); + return ret; + } + + static Anope::string Unescape(const Anope::string &string) + { + Anope::string ret = string; + for (int i = 0; special[i].character.empty() == false; ++i) + if (!special[i].replace.empty()) + ret = ret.replace_all_cs(special[i].replace, special[i].character); + + for (size_t i, last = 0; (i = string.find("&#", last)) != Anope::string::npos;) + { + last = i + 1; + + size_t end = string.find(';', i); + if (end == Anope::string::npos) + break; + + Anope::string ch = string.substr(i + 2, end - (i + 2)); + + if (ch.empty()) + continue; + + long l; + if (!ch.empty() && ch[0] == 'x') + l = strtol(ch.substr(1).c_str(), NULL, 16); + else + l = strtol(ch.c_str(), NULL, 10); + + if (l > 0 && l < 256) + ret = ret.replace_all_cs("&#" + ch + ";", Anope::string(l)); + } + + return ret; + } + + private: + static bool GetData(Anope::string &content, Anope::string &tag, Anope::string &data) + { + if (content.empty()) + return false; + + Anope::string prev, cur; + bool istag; + + do + { + prev = cur; + cur.clear(); + + size_t len = 0; + istag = false; + + if (content[0] == '<') + { + len = content.find_first_of('>'); + istag = true; + } + else if (content[0] != '>') + { + len = content.find_first_of('<'); + } + + // len must advance + if (len == Anope::string::npos || len == 0) + break; + + if (istag) + { + cur = content.substr(1, len - 1); + content.erase(0, len + 1); + while (!content.empty() && content[0] == ' ') + content.erase(content.begin()); + } + else + { + cur = content.substr(0, len); + content.erase(0, len); + } + } + while (istag && !content.empty()); + + tag = Unescape(prev); + data = Unescape(cur); + return !istag && !data.empty(); + } + + public: + bool OnRequest(HTTPProvider *provider, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply) anope_override + { + Anope::string content = message.content, tname, data; + XMLRPCRequest request(reply); + + while (GetData(content, tname, data)) + { + Log(LOG_DEBUG) << "m_xmlrpc: Tag name: " << tname << ", data: " << data; + if (tname == "methodName") + request.name = data; + else if (tname == "name" && data == "id") + { + GetData(content, tname, data); + request.id = data; + } + else if (tname == "string") + request.data.push_back(data); + } + + for (unsigned i = 0; i < this->events.size(); ++i) + { + XMLRPCEvent *e = this->events[i]; + + if (!e->Run(this, client, request)) + return false; + else if (!request.get_replies().empty()) + { + this->Reply(request); + return true; + } + } + + reply.error = HTTP_PAGE_NOT_FOUND; + reply.Write("Unrecognized query"); + return true; + } + + void Reply(XMLRPCRequest &request) anope_override + { + if (!request.id.empty()) + request.reply("id", request.id); + + Anope::string r = "\n\n\n\n\n\n"; + for (std::map::const_iterator it = request.get_replies().begin(); it != request.get_replies().end(); ++it) + r += "\n" + it->first + "\n\n" + this->Sanitize(it->second) + "\n\n\n"; + r += "\n\n\n\n"; + + request.r.Write(r); + } +}; + +class ModuleXMLRPC : public Module +{ + ServiceReference httpref; + public: + MyXMLRPCServiceInterface xmlrpcinterface; + + ModuleXMLRPC(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR), + xmlrpcinterface(this, "xmlrpc") + { + + } + + ~ModuleXMLRPC() + { + if (httpref) + httpref->UnregisterPage(&xmlrpcinterface); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + if (httpref) + httpref->UnregisterPage(&xmlrpcinterface); + this->httpref = ServiceReference("HTTPProvider", conf->GetModule(this)->Get("server", "httpd/main")); + if (!httpref) + throw ConfigException("Unable to find http reference, is m_httpd loaded?"); + httpref->RegisterPage(&xmlrpcinterface); + } +}; + +MODULE_INIT(ModuleXMLRPC) diff --git a/modules/m_xmlrpc_main.cpp b/modules/m_xmlrpc_main.cpp new file mode 100644 index 0000000..7046c6c --- /dev/null +++ b/modules/m_xmlrpc_main.cpp @@ -0,0 +1,310 @@ +/* + * + * (C) 2010-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/xmlrpc.h" + +static Module *me; + +class XMLRPCIdentifyRequest : public IdentifyRequest +{ + XMLRPCRequest request; + HTTPReply repl; /* Request holds a reference to the HTTPReply, because we might exist long enough to invalidate it + we'll copy it here then reset the reference before we use it */ + Reference client; + Reference xinterface; + + public: + XMLRPCIdentifyRequest(Module *m, XMLRPCRequest& req, HTTPClient *c, XMLRPCServiceInterface* iface, const Anope::string &acc, const Anope::string &pass) : IdentifyRequest(m, acc, pass), request(req), repl(request.r), client(c), xinterface(iface) { } + + void OnSuccess() anope_override + { + if (!xinterface || !client) + return; + + request.r = this->repl; + + request.reply("result", "Success"); + request.reply("account", GetAccount()); + + xinterface->Reply(request); + client->SendReply(&request.r); + } + + void OnFail() anope_override + { + if (!xinterface || !client) + return; + + request.r = this->repl; + + request.reply("error", "Invalid password"); + + xinterface->Reply(request); + client->SendReply(&request.r); + } +}; + +class MyXMLRPCEvent : public XMLRPCEvent +{ + public: + bool Run(XMLRPCServiceInterface *iface, HTTPClient *client, XMLRPCRequest &request) anope_override + { + if (request.name == "command") + this->DoCommand(iface, client, request); + else if (request.name == "checkAuthentication") + return this->DoCheckAuthentication(iface, client, request); + else if (request.name == "stats") + this->DoStats(iface, client, request); + else if (request.name == "channel") + this->DoChannel(iface, client, request); + else if (request.name == "user") + this->DoUser(iface, client, request); + else if (request.name == "opers") + this->DoOperType(iface, client, request); + else if (request.name == "notice") + this->DoNotice(iface, client, request); + + return true; + } + + private: + void DoCommand(XMLRPCServiceInterface *iface, HTTPClient *client, XMLRPCRequest &request) + { + Anope::string service = request.data.size() > 0 ? request.data[0] : ""; + Anope::string user = request.data.size() > 1 ? request.data[1] : ""; + Anope::string command = request.data.size() > 2 ? request.data[2] : ""; + + if (service.empty() || user.empty() || command.empty()) + request.reply("error", "Invalid parameters"); + else + { + BotInfo *bi = BotInfo::Find(service, true); + if (!bi) + request.reply("error", "Invalid service"); + else + { + request.reply("result", "Success"); + + NickAlias *na = NickAlias::Find(user); + + Anope::string out; + + struct XMLRPCommandReply : CommandReply + { + Anope::string &str; + + XMLRPCommandReply(Anope::string &s) : str(s) { } + + void SendMessage(BotInfo *, const Anope::string &msg) anope_override + { + str += msg + "\n"; + }; + } + reply(out); + + User *u = User::Find(user, true); + CommandSource source(user, u, na ? *na->nc : NULL, &reply, bi); + Command::Run(source, command); + + if (!out.empty()) + request.reply("return", iface->Sanitize(out)); + } + } + } + + bool DoCheckAuthentication(XMLRPCServiceInterface *iface, HTTPClient *client, XMLRPCRequest &request) + { + Anope::string username = request.data.size() > 0 ? request.data[0] : ""; + Anope::string password = request.data.size() > 1 ? request.data[1] : ""; + + if (username.empty() || password.empty()) + request.reply("error", "Invalid parameters"); + else + { + XMLRPCIdentifyRequest *req = new XMLRPCIdentifyRequest(me, request, client, iface, username, password); + FOREACH_MOD(OnCheckAuthentication, (NULL, req)); + req->Dispatch(); + return false; + } + + return true; + } + + void DoStats(XMLRPCServiceInterface *iface, HTTPClient *client, XMLRPCRequest &request) + { + request.reply("uptime", stringify(Anope::CurTime - Anope::StartTime)); + request.reply("uplinkname", Me->GetLinks().front()->GetName()); + { + Anope::string buf; + for (std::set::iterator it = Servers::Capab.begin(); it != Servers::Capab.end(); ++it) + buf += " " + *it; + if (!buf.empty()) + buf.erase(buf.begin()); + request.reply("uplinkcapab", buf); + } + request.reply("usercount", stringify(UserListByNick.size())); + request.reply("maxusercount", stringify(MaxUserCount)); + request.reply("channelcount", stringify(ChannelList.size())); + } + + void DoChannel(XMLRPCServiceInterface *iface, HTTPClient *client, XMLRPCRequest &request) + { + if (request.data.empty()) + return; + + Channel *c = Channel::Find(request.data[0]); + + request.reply("name", iface->Sanitize(c ? c->name : request.data[0])); + + if (c) + { + request.reply("bancount", stringify(c->HasMode("BAN"))); + int count = 0; + std::vector v = c->GetModeList("BAN"); + for (unsigned int i = 0; i < v.size(); ++i) + request.reply("ban" + stringify(++count), iface->Sanitize(v[i])); + + request.reply("exceptcount", stringify(c->HasMode("EXCEPT"))); + count = 0; + v = c->GetModeList("EXCEPT"); + for (unsigned int i = 0; i < v.size(); ++i) + request.reply("except" + stringify(++count), iface->Sanitize(v[i])); + + request.reply("invitecount", stringify(c->HasMode("INVITEOVERRIDE"))); + count = 0; + v = c->GetModeList("INVITEOVERRIDE"); + for (unsigned int i = 0; i < v.size(); ++i) + request.reply("invite" + stringify(++count), iface->Sanitize(v[i])); + + Anope::string users; + for (Channel::ChanUserList::const_iterator it = c->users.begin(); it != c->users.end(); ++it) + { + ChanUserContainer *uc = it->second; + users += uc->status.BuildModePrefixList() + uc->user->nick + " "; + } + if (!users.empty()) + { + users.erase(users.length() - 1); + request.reply("users", iface->Sanitize(users)); + } + + if (!c->topic.empty()) + request.reply("topic", iface->Sanitize(c->topic)); + + if (!c->topic_setter.empty()) + request.reply("topicsetter", iface->Sanitize(c->topic_setter)); + + request.reply("topictime", stringify(c->topic_time)); + request.reply("topicts", stringify(c->topic_ts)); + } + } + + void DoUser(XMLRPCServiceInterface *iface, HTTPClient *client, XMLRPCRequest &request) + { + if (request.data.empty()) + return; + + User *u = User::Find(request.data[0]); + + request.reply("nick", iface->Sanitize(u ? u->nick : request.data[0])); + + if (u) + { + request.reply("ident", iface->Sanitize(u->GetIdent())); + request.reply("vident", iface->Sanitize(u->GetVIdent())); + request.reply("host", iface->Sanitize(u->host)); + if (!u->vhost.empty()) + request.reply("vhost", iface->Sanitize(u->vhost)); + if (!u->chost.empty()) + request.reply("chost", iface->Sanitize(u->chost)); + request.reply("ip", u->ip.addr()); + request.reply("timestamp", stringify(u->timestamp)); + request.reply("signon", stringify(u->signon)); + if (u->Account()) + { + request.reply("account", iface->Sanitize(u->Account()->display)); + if (u->Account()->o) + request.reply("opertype", iface->Sanitize(u->Account()->o->ot->GetName())); + } + + Anope::string channels; + for (User::ChanUserList::const_iterator it = u->chans.begin(); it != u->chans.end(); ++it) + { + ChanUserContainer *cc = it->second; + channels += cc->status.BuildModePrefixList() + cc->chan->name + " "; + } + if (!channels.empty()) + { + channels.erase(channels.length() - 1); + request.reply("channels", channels); + } + } + } + + void DoOperType(XMLRPCServiceInterface *iface, HTTPClient *client, XMLRPCRequest &request) + { + for (unsigned i = 0; i < Config->MyOperTypes.size(); ++i) + { + OperType *ot = Config->MyOperTypes[i]; + Anope::string perms; + + std::list privs = ot->GetPrivs(); + for (std::list::const_iterator it2 = privs.begin(), it2_end = privs.end(); it2 != it2_end; ++it2) + perms += " " + *it2; + + std::list commands = ot->GetCommands(); + for (std::list::const_iterator it2 = commands.begin(), it2_end = commands.end(); it2 != it2_end; ++it2) + perms += " " + *it2; + request.reply(ot->GetName(), perms); + } + } + + void DoNotice(XMLRPCServiceInterface *iface, HTTPClient *client, XMLRPCRequest &request) + { + Anope::string from = request.data.size() > 0 ? request.data[0] : ""; + Anope::string to = request.data.size() > 1 ? request.data[1] : ""; + Anope::string message = request.data.size() > 2 ? request.data[2] : ""; + + BotInfo *bi = BotInfo::Find(from, true); + User *u = User::Find(to, true); + + if (!bi || !u || message.empty()) + return; + + u->SendMessage(bi, message); + + request.reply("result", "Success"); + } +}; + +class ModuleXMLRPCMain : public Module +{ + ServiceReference xmlrpc; + + MyXMLRPCEvent stats; + + public: + ModuleXMLRPCMain(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR), xmlrpc("XMLRPCServiceInterface", "xmlrpc") + { + me = this; + + if (!xmlrpc) + throw ModuleException("Unable to find xmlrpc reference, is m_xmlrpc loaded?"); + + xmlrpc->Register(&stats); + } + + ~ModuleXMLRPCMain() + { + if (xmlrpc) + xmlrpc->Unregister(&stats); + } +}; + +MODULE_INIT(ModuleXMLRPCMain) diff --git a/modules/ns_maxemail.cpp b/modules/ns_maxemail.cpp new file mode 100644 index 0000000..9327ea8 --- /dev/null +++ b/modules/ns_maxemail.cpp @@ -0,0 +1,114 @@ +/* ns_maxemail.cpp - Limit the amount of times an email address + * can be used for a NickServ account. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Included in the Anope module pack since Anope 1.7.9 + * Anope Coder: GeniusDex + * + * Please read COPYING and README for further details. + */ + +#include "module.h" + +class NSMaxEmail : public Module +{ + bool clean; + + /* strip dots from username, and remove anything after the first + */ + Anope::string CleanMail(const Anope::string &email) + { + size_t host = email.find('@'); + if (host == Anope::string::npos) + return email; + + Anope::string username = email.substr(0, host); + username = username.replace_all_cs(".", ""); + + size_t sz = username.find('+'); + if (sz != Anope::string::npos) + username = username.substr(0, sz); + + Anope::string cleaned = username + email.substr(host); + Log(LOG_DEBUG) << "cleaned " << email << " to " << cleaned; + return cleaned; + } + + bool CheckLimitReached(CommandSource &source, const Anope::string &email) + { + int NSEmailMax = Config->GetModule(this)->Get("maxemails"); + + if (NSEmailMax < 1 || email.empty()) + return false; + + if (this->CountEmail(email, source.nc) < NSEmailMax) + return false; + + if (NSEmailMax == 1) + source.Reply(_("The email address \002%s\002 has reached its usage limit of 1 user."), email.c_str()); + else + source.Reply(_("The email address \002%s\002 has reached its usage limit of %d users."), email.c_str(), NSEmailMax); + + return true; + } + + int CountEmail(const Anope::string &email, NickCore *unc) + { + int count = 0; + + if (email.empty()) + return 0; + + Anope::string cleanemail = clean ? CleanMail(email) : email; + + for (nickcore_map::const_iterator it = NickCoreList->begin(), it_end = NickCoreList->end(); it != it_end; ++it) + { + const NickCore *nc = it->second; + + Anope::string cleannc = clean ? CleanMail(nc->email) : nc->email; + + if (unc != nc && cleanemail.equals_ci(cleannc)) + ++count; + } + + return count; + } + + public: + NSMaxEmail(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR) + , clean(false) + { + } + + void OnReload(Configuration::Conf *conf) anope_override + { + clean = conf->GetModule(this)->Get("remove_aliases", "true"); + } + + EventReturn OnPreCommand(CommandSource &source, Command *command, std::vector ¶ms) anope_override + { + if (source.IsOper()) + return EVENT_CONTINUE; + + if (command->name == "nickserv/register") + { + if (this->CheckLimitReached(source, params.size() > 1 ? params[1] : "")) + return EVENT_STOP; + } + else if (command->name == "nickserv/set/email") + { + if (this->CheckLimitReached(source, params.size() > 0 ? params[0] : "")) + return EVENT_STOP; + } + else if (command->name == "nickserv/ungroup" && source.GetAccount()) + { + if (this->CheckLimitReached(source, source.GetAccount()->email)) + return EVENT_STOP; + } + + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(NSMaxEmail) diff --git a/modules/protocol/bahamut.cpp b/modules/protocol/bahamut.cpp new file mode 100644 index 0000000..6d14dab --- /dev/null +++ b/modules/protocol/bahamut.cpp @@ -0,0 +1,570 @@ +/* Bahamut functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class ChannelModeFlood : public ChannelModeParam +{ + public: + ChannelModeFlood(char modeChar, bool minusNoArg) : ChannelModeParam("FLOOD", modeChar, minusNoArg) { } + + bool IsValid(Anope::string &value) const anope_override + { + try + { + Anope::string rest; + if (!value.empty() && value[0] != ':' && convertTo(value[0] == '*' ? value.substr(1) : value, rest, false) > 0 && rest[0] == ':' && rest.length() > 1 && convertTo(rest.substr(1), rest, false) > 0 && rest.empty()) + return true; + } + catch (const ConvertException &) { } + + return false; + } +}; + +class BahamutIRCdProto : public IRCDProto +{ + public: + BahamutIRCdProto(Module *creator) : IRCDProto(creator, "Bahamut 1.8.x") + { + DefaultPseudoclientModes = "+"; + CanSVSNick = true; + CanSNLine = true; + CanSQLine = true; + CanSQLineChannel = true; + CanSZLine = true; + CanSVSHold = true; + MaxModes = 60; + } + + void SendModeInternal(const MessageSource &source, const Channel *dest, const Anope::string &buf) anope_override + { + if (Servers::Capab.count("TSMODE") > 0) + { + UplinkSocket::Message(source) << "MODE " << dest->name << " " << dest->creation_time << " " << buf; + } + else + IRCDProto::SendModeInternal(source, dest, buf); + } + + void SendModeInternal(const MessageSource &source, User *u, const Anope::string &buf) anope_override + { + UplinkSocket::Message(source) << "SVSMODE " << u->nick << " " << u->timestamp << " " << buf; + } + + void SendGlobalNotice(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "NOTICE $" << dest->GetName() << " :" << msg; + } + + void SendGlobalPrivmsg(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "PRIVMSG $" << dest->GetName() << " :" << msg; + } + + /* SVSHOLD - set */ + void SendSVSHold(const Anope::string &nick, time_t time) anope_override + { + UplinkSocket::Message(Me) << "SVSHOLD " << nick << " " << time << " :Being held for registered user"; + } + + /* SVSHOLD - release */ + void SendSVSHoldDel(const Anope::string &nick) anope_override + { + UplinkSocket::Message(Me) << "SVSHOLD " << nick << " 0"; + } + + /* SQLINE */ + void SendSQLine(User *, const XLine *x) anope_override + { + UplinkSocket::Message() << "SQLINE " << x->mask << " :" << x->GetReason(); + } + + /* UNSLINE */ + void SendSGLineDel(const XLine *x) anope_override + { + UplinkSocket::Message() << "UNSGLINE 0 :" << x->mask; + } + + /* UNSZLINE */ + void SendSZLineDel(const XLine *x) anope_override + { + /* this will likely fail so its only here for legacy */ + UplinkSocket::Message() << "UNSZLINE 0 " << x->GetHost(); + /* this is how we are supposed to deal with it */ + UplinkSocket::Message() << "RAKILL " << x->GetHost() << " *"; + } + + /* SZLINE */ + void SendSZLine(User *, const XLine *x) anope_override + { + // Calculate the time left before this would expire, capping it at 2 days + time_t timeleft = x->expires - Anope::CurTime; + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + /* this will likely fail so its only here for legacy */ + UplinkSocket::Message() << "SZLINE " << x->GetHost() << " :" << x->GetReason(); + /* this is how we are supposed to deal with it */ + UplinkSocket::Message() << "AKILL " << x->GetHost() << " * " << timeleft << " " << x->by << " " << Anope::CurTime << " :" << x->GetReason(); + } + + /* SVSNOOP */ + void SendSVSNOOP(const Server *server, bool set) anope_override + { + UplinkSocket::Message() << "SVSNOOP " << server->GetName() << " " << (set ? "+" : "-"); + } + + /* SGLINE */ + void SendSGLine(User *, const XLine *x) anope_override + { + UplinkSocket::Message() << "SGLINE " << x->mask.length() << " :" << x->mask << ":" << x->GetReason(); + } + + /* RAKILL */ + void SendAkillDel(const XLine *x) anope_override + { + if (x->IsRegex() || x->HasNickOrReal()) + return; + + /* ZLine if we can instead */ + if (x->GetUser() == "*") + { + cidr a(x->GetHost()); + if (a.valid()) + { + IRCD->SendSZLineDel(x); + return; + } + } + + UplinkSocket::Message() << "RAKILL " << x->GetHost() << " " << x->GetUser(); + } + + /* TOPIC */ + void SendTopic(const MessageSource &source, Channel *c) anope_override + { + UplinkSocket::Message(source) << "TOPIC " << c->name << " " << c->topic_setter << " " << c->topic_ts << " :" << c->topic; + } + + /* UNSQLINE */ + void SendSQLineDel(const XLine *x) anope_override + { + UplinkSocket::Message() << "UNSQLINE " << x->mask; + } + + /* JOIN - SJOIN */ + void SendJoin(User *user, Channel *c, const ChannelStatus *status) anope_override + { + UplinkSocket::Message(user) << "SJOIN " << c->creation_time << " " << c->name; + if (status) + { + /* First save the channel status incase uc->Status == status */ + ChannelStatus cs = *status; + /* If the user is internally on the channel with flags, kill them so that + * the stacker will allow this. + */ + ChanUserContainer *uc = c->FindUser(user); + if (uc != NULL) + uc->status.Clear(); + + BotInfo *setter = BotInfo::Find(user->GetUID()); + for (size_t i = 0; i < cs.Modes().length(); ++i) + c->SetMode(setter, ModeManager::FindChannelModeByChar(cs.Modes()[i]), user->GetUID(), false); + + if (uc != NULL) + uc->status = cs; + } + } + + void SendAkill(User *u, XLine *x) anope_override + { + if (x->IsRegex() || x->HasNickOrReal()) + { + if (!u) + { + /* No user (this akill was just added), and contains nick and/or realname. Find users that match and ban them */ + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + if (x->manager->Check(it->second, x)) + this->SendAkill(it->second, x); + return; + } + + const XLine *old = x; + + if (old->manager->HasEntry("*@" + u->host)) + return; + + /* We can't akill x as it has a nick and/or realname included, so create a new akill for *@host */ + x = new XLine("*@" + u->host, old->by, old->expires, old->reason, old->id); + old->manager->AddXLine(x); + + Log(Config->GetClient("OperServ"), "akill") << "AKILL: Added an akill for " << x->mask << " because " << u->GetMask() << "#" << u->realname << " matches " << old->mask; + } + + /* ZLine if we can instead */ + if (x->GetUser() == "*") + { + cidr a(x->GetHost()); + if (a.valid()) + { + IRCD->SendSZLine(u, x); + return; + } + } + + // Calculate the time left before this would expire, capping it at 2 days + time_t timeleft = x->expires - Anope::CurTime; + if (timeleft > 172800) + timeleft = 172800; + UplinkSocket::Message() << "AKILL " << x->GetHost() << " " << x->GetUser() << " " << timeleft << " " << x->by << " " << Anope::CurTime << " :" << x->GetReason(); + } + + /* + Note: if the stamp is null 0, the below usage is correct of Bahamut + */ + void SendSVSKillInternal(const MessageSource &source, User *user, const Anope::string &buf) anope_override + { + UplinkSocket::Message(source) << "SVSKILL " << user->nick << " :" << buf; + } + + void SendBOB() anope_override + { + UplinkSocket::Message() << "BURST"; + } + + void SendEOB() anope_override + { + UplinkSocket::Message() << "BURST 0"; + } + + void SendClientIntroduction(User *u) anope_override + { + Anope::string modes = "+" + u->GetModes(); + UplinkSocket::Message() << "NICK " << u->nick << " 1 " << u->timestamp << " " << modes << " " << u->GetIdent() << " " << u->host << " " << u->server->GetName() << " 0 0 :" << u->realname; + } + + /* SERVER */ + void SendServer(const Server *server) anope_override + { + UplinkSocket::Message() << "SERVER " << server->GetName() << " " << server->GetHops() << " :" << server->GetDescription(); + } + + void SendConnect() anope_override + { + UplinkSocket::Message() << "PASS " << Config->Uplinks[Anope::CurrentUplink].password << " :TS"; + UplinkSocket::Message() << "CAPAB SSJOIN NOQUIT BURST UNCONNECT NICKIP TSMODE TS3"; + SendServer(Me); + /* + * SVINFO + * parv[0] = sender prefix + * parv[1] = TS_CURRENT for the server + * parv[2] = TS_MIN for the server + * parv[3] = server is standalone or connected to non-TS only + * parv[4] = server's idea of UTC time + */ + UplinkSocket::Message() << "SVINFO 3 1 0 :" << Anope::CurTime; + this->SendBOB(); + } + + void SendChannel(Channel *c) anope_override + { + Anope::string modes = c->GetModes(true, true); + if (modes.empty()) + modes = "+"; + UplinkSocket::Message() << "SJOIN " << c->creation_time << " " << c->name << " " << modes << " :"; + } + + void SendLogin(User *u, NickAlias *) anope_override + { + IRCD->SendMode(Config->GetClient("NickServ"), u, "+d %d", u->signon); + } + + void SendLogout(User *u) anope_override + { + IRCD->SendMode(Config->GetClient("NickServ"), u, "+d 1"); + } +}; + +struct IRCDMessageBurst : IRCDMessage +{ + IRCDMessageBurst(Module *creator) : IRCDMessage(creator, "BURST", 0) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + /* If we found a server with the given source, that one just + * finished bursting. If there was no source, then our uplink + * server finished bursting. -GD + */ + Server *s = source.GetServer(); + if (!s) + s = Me->GetLinks().front(); + if (s) + s->Sync(true); + } +}; + +struct IRCDMessageMode : IRCDMessage +{ + IRCDMessageMode(Module *creator, const Anope::string &sname) : IRCDMessage(creator, sname, 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params.size() > 2 && IRCD->IsChannelValid(params[0])) + { + Channel *c = Channel::Find(params[0]); + time_t ts = 0; + + try + { + ts = convertTo(params[1]); + } + catch (const ConvertException &) { } + + Anope::string modes = params[2]; + for (unsigned int i = 3; i < params.size(); ++i) + modes += " " + params[i]; + + if (c) + c->SetModesInternal(source, modes, ts); + } + else + { + User *u = User::Find(params[0]); + if (u) + u->SetModesInternal(source, "%s", params[1].c_str()); + } + } +}; + +/* + ** NICK - new + ** source = NULL + ** parv[0] = nickname + ** parv[1] = hopcount + ** parv[2] = timestamp + ** parv[3] = modes + ** parv[4] = username + ** parv[5] = hostname + ** parv[6] = server + ** parv[7] = servicestamp + ** parv[8] = IP + ** parv[9] = info + ** NICK - change + ** source = oldnick + ** parv[0] = new nickname + ** parv[1] = hopcount + */ +struct IRCDMessageNick : IRCDMessage +{ + IRCDMessageNick(Module *creator) : IRCDMessage(creator, "NICK", 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params.size() == 10) + { + Server *s = Server::Find(params[6]); + if (s == NULL) + { + Log(LOG_DEBUG) << "User " << params[0] << " introduced from nonexistent server " << params[6] << "?"; + return; + } + + NickAlias *na = NULL; + time_t signon = params[2].is_pos_number_only() ? convertTo(params[2]) : 0, + stamp = params[7].is_pos_number_only() ? convertTo(params[7]) : 0; + if (signon && signon == stamp) + na = NickAlias::Find(params[0]); + + User::OnIntroduce(params[0], params[4], params[5], "", params[8], s, params[9], signon, params[3], "", na ? *na->nc : NULL); + } + else + { + User *u = source.GetUser(); + + if (u) + u->ChangeNick(params[0]); + } + } +}; + +struct IRCDMessageServer : IRCDMessage +{ + IRCDMessageServer(Module *creator) : IRCDMessage(creator, "SERVER", 3) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + unsigned int hops = Anope::string(params[1]).is_pos_number_only() ? convertTo(params[1]) : 0; + new Server(source.GetServer() == NULL ? Me : source.GetServer(), params[0], hops, params[2]); + } +}; + +struct IRCDMessageSJoin : IRCDMessage +{ + IRCDMessageSJoin(Module *creator) : IRCDMessage(creator, "SJOIN", 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Anope::string modes; + if (params.size() >= 4) + for (unsigned i = 2; i < params.size(); ++i) + modes += " " + params[i]; + if (!modes.empty()) + modes.erase(modes.begin()); + + std::list users; + + /* For some reason, bahamut will send a SJOIN from the user joining a channel + * if the channel already existed + */ + if (source.GetUser()) + { + Message::Join::SJoinUser sju; + sju.second = source.GetUser(); + users.push_back(sju); + } + else + { + spacesepstream sep(params[params.size() - 1]); + Anope::string buf; + + while (sep.GetToken(buf)) + { + Message::Join::SJoinUser sju; + + /* Get prefixes from the nick */ + for (char ch; (ch = ModeManager::GetStatusChar(buf[0]));) + { + buf.erase(buf.begin()); + sju.first.AddMode(ch); + } + + sju.second = User::Find(buf); + if (!sju.second) + { + Log(LOG_DEBUG) << "SJOIN for nonexistent user " << buf << " on " << params[1]; + continue; + } + + users.push_back(sju); + } + } + + time_t ts = Anope::string(params[0]).is_pos_number_only() ? convertTo(params[0]) : Anope::CurTime; + Message::Join::SJoin(source, params[1], ts, modes, users); + } +}; + +struct IRCDMessageTopic : IRCDMessage +{ + IRCDMessageTopic(Module *creator) : IRCDMessage(creator, "TOPIC", 4) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Channel *c = Channel::Find(params[0]); + if (c) + c->ChangeTopicInternal(source.GetUser(), params[1], params[3], Anope::string(params[2]).is_pos_number_only() ? convertTo(params[2]) : Anope::CurTime); + } +}; + +class ProtoBahamut : public Module +{ + BahamutIRCdProto ircd_proto; + + /* Core message handlers */ + Message::Away message_away; + Message::Capab message_capab; + Message::Error message_error; + Message::Invite message_invite; + Message::Join message_join; + Message::Kick message_kick; + Message::Kill message_kill; + Message::MOTD message_motd; + Message::Notice message_notice; + Message::Part message_part; + Message::Ping message_ping; + Message::Privmsg message_privmsg; + Message::Quit message_quit; + Message::SQuit message_squit; + Message::Stats message_stats; + Message::Time message_time; + Message::Version message_version; + Message::Whois message_whois; + + /* Our message handlers */ + IRCDMessageBurst message_burst; + IRCDMessageMode message_mode, message_svsmode; + IRCDMessageNick message_nick; + IRCDMessageServer message_server; + IRCDMessageSJoin message_sjoin; + IRCDMessageTopic message_topic; + + void AddModes() + { + /* Add user modes */ + ModeManager::AddUserMode(new UserModeOperOnly("SERV_ADMIN", 'A')); + ModeManager::AddUserMode(new UserMode("REGPRIV", 'R')); + ModeManager::AddUserMode(new UserModeOperOnly("ADMIN", 'a')); + ModeManager::AddUserMode(new UserMode("INVIS", 'i')); + ModeManager::AddUserMode(new UserModeOperOnly("OPER", 'o')); + ModeManager::AddUserMode(new UserModeNoone("REGISTERED", 'r')); + ModeManager::AddUserMode(new UserModeOperOnly("SNOMASK", 's')); + ModeManager::AddUserMode(new UserModeOperOnly("WALLOPS", 'w')); + ModeManager::AddUserMode(new UserMode("DEAF", 'd')); + + /* b/e/I */ + ModeManager::AddChannelMode(new ChannelModeList("BAN", 'b')); + + /* v/h/o/a/q */ + ModeManager::AddChannelMode(new ChannelModeStatus("VOICE", 'v', '+', 0)); + ModeManager::AddChannelMode(new ChannelModeStatus("HALFOP", 'h', '%', 1)); + ModeManager::AddChannelMode(new ChannelModeStatus("OP", 'o', '@', 1)); + + /* Add channel modes */ + ModeManager::AddChannelMode(new ChannelMode("BLOCKCOLOR", 'c')); + ModeManager::AddChannelMode(new ChannelMode("INVITE", 'i')); + ModeManager::AddChannelMode(new ChannelModeFlood('f', false)); + ModeManager::AddChannelMode(new ChannelModeKey('k')); + ModeManager::AddChannelMode(new ChannelModeParam("LIMIT", 'l', true)); + ModeManager::AddChannelMode(new ChannelMode("MODERATED", 'm')); + ModeManager::AddChannelMode(new ChannelMode("NOEXTERNAL", 'n')); + ModeManager::AddChannelMode(new ChannelMode("PRIVATE", 'p')); + ModeManager::AddChannelMode(new ChannelModeNoone("REGISTERED", 'r')); + ModeManager::AddChannelMode(new ChannelMode("SECRET", 's')); + ModeManager::AddChannelMode(new ChannelMode("TOPIC", 't')); + ModeManager::AddChannelMode(new ChannelMode("REGMODERATED", 'M')); + ModeManager::AddChannelMode(new ChannelModeOperOnly("OPERONLY", 'O')); + ModeManager::AddChannelMode(new ChannelMode("REGISTEREDONLY", 'R')); + } + + public: + ProtoBahamut(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PROTOCOL | VENDOR), + ircd_proto(this), + message_away(this), message_capab(this), message_error(this), message_invite(this), + message_join(this), message_kick(this), message_kill(this), message_motd(this), message_notice(this), + message_part(this), message_ping(this), message_privmsg(this), message_quit(this), + message_squit(this), message_stats(this), message_time(this), message_version(this), message_whois(this), + + message_burst(this), message_mode(this, "MODE"), message_svsmode(this, "SVSMODE"), + message_nick(this), message_server(this), message_sjoin(this), message_topic(this) + { + + this->AddModes(); + + } + + void OnUserNickChange(User *u, const Anope::string &) anope_override + { + u->RemoveModeInternal(Me, ModeManager::FindUserModeByName("REGISTERED")); + IRCD->SendLogout(u); + } +}; + +MODULE_INIT(ProtoBahamut) diff --git a/modules/protocol/charybdis.cpp b/modules/protocol/charybdis.cpp new file mode 100644 index 0000000..7e58951 --- /dev/null +++ b/modules/protocol/charybdis.cpp @@ -0,0 +1,427 @@ +/* Charybdis IRCD functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/cs_mode.h" +#include "modules/sasl.h" + +static Anope::string UplinkSID; + +static ServiceReference ratbox("IRCDProto", "ratbox"); + +class ChannelModeLargeBan : public ChannelMode +{ + public: + ChannelModeLargeBan(const Anope::string &mname, char modeChar) : ChannelMode(mname, modeChar) { } + + bool CanSet(User *u) const anope_override + { + return u && u->HasMode("OPER"); + } +}; + + +class CharybdisProto : public IRCDProto +{ + public: + + CharybdisProto(Module *creator) : IRCDProto(creator, "Charybdis 3.4+") + { + DefaultPseudoclientModes = "+oiS"; + CanCertFP = true; + CanSNLine = true; + CanSQLine = true; + CanSQLineChannel = true; + CanSZLine = true; + CanSVSNick = true; + CanSVSHold = true; + CanSetVHost = true; + RequiresID = true; + MaxModes = 4; + } + + void SendSVSKillInternal(const MessageSource &source, User *targ, const Anope::string &reason) anope_override { ratbox->SendSVSKillInternal(source, targ, reason); } + void SendGlobalNotice(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override { ratbox->SendGlobalNotice(bi, dest, msg); } + void SendGlobalPrivmsg(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override { ratbox->SendGlobalPrivmsg(bi, dest, msg); } + void SendGlobopsInternal(const MessageSource &source, const Anope::string &buf) anope_override { ratbox->SendGlobopsInternal(source, buf); } + void SendSGLine(User *u, const XLine *x) anope_override { ratbox->SendSGLine(u, x); } + void SendSGLineDel(const XLine *x) anope_override { ratbox->SendSGLineDel(x); } + void SendAkill(User *u, XLine *x) anope_override { ratbox->SendAkill(u, x); } + void SendAkillDel(const XLine *x) anope_override { ratbox->SendAkillDel(x); } + void SendSQLine(User *u, const XLine *x) anope_override { ratbox->SendSQLine(u, x); } + void SendSQLineDel(const XLine *x) anope_override { ratbox->SendSQLineDel(x); } + void SendJoin(User *user, Channel *c, const ChannelStatus *status) anope_override { ratbox->SendJoin(user, c, status); } + void SendServer(const Server *server) anope_override { ratbox->SendServer(server); } + void SendChannel(Channel *c) anope_override { ratbox->SendChannel(c); } + void SendTopic(const MessageSource &source, Channel *c) anope_override { ratbox->SendTopic(source, c); } + bool IsIdentValid(const Anope::string &ident) anope_override { return ratbox->IsIdentValid(ident); } + void SendLogin(User *u, NickAlias *na) anope_override { ratbox->SendLogin(u, na); } + void SendLogout(User *u) anope_override { ratbox->SendLogout(u); } + + void SendSASLMechanisms(std::vector &mechanisms) anope_override + { + Anope::string mechlist; + + for (unsigned i = 0; i < mechanisms.size(); ++i) + { + mechlist += "," + mechanisms[i]; + } + + UplinkSocket::Message(Me) << "ENCAP * MECHLIST :" << (mechanisms.empty() ? "" : mechlist.substr(1)); + } + + void SendConnect() anope_override + { + UplinkSocket::Message() << "PASS " << Config->Uplinks[Anope::CurrentUplink].password << " TS 6 :" << Me->GetSID(); + /* + * Received: CAPAB :BAN CHW CLUSTER ENCAP EOPMOD EUID EX IE KLN + * KNOCK MLOCK QS RSFNC SAVE SERVICES TB UNKLN + * + * BAN - Can do BAN message + * CHW - Can do channel wall @# + * CLUSTER - Supports umode +l, can send LOCOPS (encap only) + * ENCAP - Can do ENCAP message + * EOPMOD - Can do channel wall =# (for cmode +z) + * EUID - Can do EUID (its similar to UID but includes the ENCAP REALHOST and ENCAP LOGIN information) + * EX - Can do channel +e exemptions + * GLN - Can set G:Lines + * IE - Can do invite exceptions + * KLN - Can set K:Lines (encap only) + * KNOCK - Supports KNOCK + * MLOCK - Supports MLOCK + * RSFNC - Forces a nickname change and propagates it (encap only) + * SERVICES - Support channel mode +r (only registered users may join) + * SAVE - Resolve a nick collision by changing a nickname to the UID. + * TB - Supports topic burst + * UNKLN - Can do UNKLINE (encap only) + * QS - Can handle quit storm removal + */ + UplinkSocket::Message() << "CAPAB :BAN CHW CLUSTER ENCAP EOPMOD EUID EX IE KLN KNOCK MLOCK QS RSFNC SERVICES TB UNKLN"; + + /* Make myself known to myself in the serverlist */ + SendServer(Me); + + /* + * Received: SVINFO 6 6 0 :1353235537 + * arg[0] = current TS version + * arg[1] = minimum required TS version + * arg[2] = '0' + * arg[3] = server's idea of UTC time + */ + UplinkSocket::Message() << "SVINFO 6 6 0 :" << Anope::CurTime; + } + + void SendClientIntroduction(User *u) anope_override + { + Anope::string modes = "+" + u->GetModes(); + UplinkSocket::Message(Me) << "EUID " << u->nick << " 1 " << u->timestamp << " " << modes << " " << u->GetIdent() << " " << u->host << " 0 " << u->GetUID() << " * * :" << u->realname; + } + + void SendForceNickChange(User *u, const Anope::string &newnick, time_t when) anope_override + { + UplinkSocket::Message(Me) << "ENCAP " << u->server->GetName() << " RSFNC " << u->GetUID() + << " " << newnick << " " << when << " " << u->timestamp; + } + + void SendSVSHold(const Anope::string &nick, time_t delay) anope_override + { + UplinkSocket::Message(Me) << "ENCAP * NICKDELAY " << delay << " " << nick; + } + + void SendSVSHoldDel(const Anope::string &nick) anope_override + { + UplinkSocket::Message(Me) << "ENCAP * NICKDELAY 0 " << nick; + } + + void SendVhost(User *u, const Anope::string &ident, const Anope::string &host) anope_override + { + UplinkSocket::Message(Me) << "ENCAP * CHGHOST " << u->GetUID() << " :" << host; + } + + void SendVhostDel(User *u) anope_override + { + this->SendVhost(u, "", u->host); + } + + void SendSASLMessage(const SASL::Message &message) anope_override + { + Server *s = Server::Find(message.target.substr(0, 3)); + UplinkSocket::Message(Me) << "ENCAP " << (s ? s->GetName() : message.target.substr(0, 3)) << " SASL " << message.source << " " << message.target << " " << message.type << " " << message.data << (message.ext.empty() ? "" : (" " + message.ext)); + } + + void SendSVSLogin(const Anope::string &uid, const Anope::string &acc, const Anope::string &vident, const Anope::string &vhost) anope_override + { + Server *s = Server::Find(uid.substr(0, 3)); + UplinkSocket::Message(Me) << "ENCAP " << (s ? s->GetName() : uid.substr(0, 3)) << " SVSLOGIN " << uid << " * " << (!vident.empty() ? vident : '*') << " " << (!vhost.empty() ? vhost : '*') << " " << acc; + } +}; + + +struct IRCDMessageEncap : IRCDMessage +{ + IRCDMessageEncap(Module *creator) : IRCDMessage(creator, "ENCAP", 3) + { + SetFlag(IRCDMESSAGE_SOFT_LIMIT); + } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + // In a burst, states that the source user is logged in as the account. + if (params[1] == "LOGIN" || params[1] == "SU") + { + User *u = source.GetUser(); + NickCore *nc = NickCore::Find(params[2]); + + if (!u || !nc) + return; + + u->Login(nc); + } + // Received: :42XAAAAAE ENCAP * CERTFP :3f122a9cc7811dbad3566bf2cec3009007c0868f + else if (params[1] == "CERTFP") + { + User *u = source.GetUser(); + if (!u) + return; + + u->fingerprint = params[2]; + + FOREACH_MOD(OnFingerprint, (u)); + } + /* + * Received: :42X ENCAP * SASL 42XAAAAAH * S PLAIN + * Received: :42X ENCAP * SASL 42XAAAAAC * D A + * + * Part of a SASL authentication exchange. The mode is 'C' to send some data + * (base64 encoded), or 'S' to end the exchange (data indicates type of + * termination: 'A' for abort, 'F' for authentication failure, 'S' for + * authentication success). + * + * Charybdis only accepts messages from SASL agents; these must have umode +S + */ + else if (params[1] == "SASL" && SASL::sasl && params.size() >= 6) + { + SASL::Message m; + m.source = params[2]; + m.target = params[3]; + m.type = params[4]; + m.data = params[5]; + m.ext = params.size() > 6 ? params[6] : ""; + + SASL::sasl->ProcessMessage(m); + } + } +}; + +struct IRCDMessageEUID : IRCDMessage +{ + IRCDMessageEUID(Module *creator) : IRCDMessage(creator, "EUID", 11) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + /* + * :42X EUID DukePyrolator 1 1353240577 +Zi ~jens erft-5d80b00b.pool.mediaWays.net 93.128.176.11 42XAAAAAD * * :jens + * : EUID + : + * 0 1 2 3 4 5 6 7 8 9 10 + * + * Introduces a user. The hostname field is now always the visible host. + * The realhost field is * if the real host is equal to the visible host. + * The account field is * if the login is not set. + * Note that even if both new fields are *, an EUID command still carries more + * information than a UID command (namely that real host is visible host and the + * user is not logged in with services). Hence a NICK or UID command received + * from a remote server should not be sent in EUID form to other servers. + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + NickAlias *na = NULL; + if (params[9] != "*") + na = NickAlias::Find(params[9]); + + User::OnIntroduce(params[0], params[4], (params[8] != "*" ? params[8] : params[5]), params[5], params[6], source.GetServer(), params[10], params[2].is_pos_number_only() ? convertTo(params[2]) : Anope::CurTime, params[3], params[7], na ? *na->nc : NULL); + } +}; + +// we can't use this function from ratbox because we set a local variable here +struct IRCDMessageServer : IRCDMessage +{ + IRCDMessageServer(Module *creator) : IRCDMessage(creator, "SERVER", 3) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + // SERVER dev.anope.de 1 :charybdis test server + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + // Servers other then our immediate uplink are introduced via SID + if (params[1] != "1") + return; + new Server(source.GetServer() == NULL ? Me : source.GetServer(), params[0], 1, params[2], UplinkSID); + IRCD->SendPing(Me->GetName(), params[0]); + } +}; + +// we can't use this function from ratbox because we set a local variable here +struct IRCDMessagePass : IRCDMessage +{ + IRCDMessagePass(Module *creator) : IRCDMessage(creator, "PASS", 4) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + // UplinkSID is used in IRCDMessageServer + UplinkSID = params[3]; + } +}; + +class ProtoCharybdis : public Module +{ + Module *m_ratbox; + + CharybdisProto ircd_proto; + + /* Core message handlers */ + Message::Away message_away; + Message::Capab message_capab; + Message::Error message_error; + Message::Invite message_invite; + Message::Kick message_kick; + Message::Kill message_kill; + Message::Mode message_mode; + Message::MOTD message_motd; + Message::Notice message_notice; + Message::Part message_part; + Message::Ping message_ping; + Message::Privmsg message_privmsg; + Message::Quit message_quit; + Message::SQuit message_squit; + Message::Stats message_stats; + Message::Time message_time; + Message::Topic message_topic; + Message::Version message_version; + Message::Whois message_whois; + + /* Ratbox Message Handlers */ + ServiceAlias message_bmask, message_join, message_nick, message_pong, message_sid, message_sjoin, + message_tb, message_tmode, message_uid; + + /* Our message handlers */ + IRCDMessageEncap message_encap; + IRCDMessageEUID message_euid; + IRCDMessagePass message_pass; + IRCDMessageServer message_server; + + bool use_server_side_mlock; + + void AddModes() + { + /* Add user modes */ + ModeManager::AddUserMode(new UserMode("NOFORWARD", 'Q')); + ModeManager::AddUserMode(new UserMode("REGPRIV", 'R')); + ModeManager::AddUserMode(new UserModeOperOnly("OPERWALLS", 'z')); + ModeManager::AddUserMode(new UserModeNoone("SSL", 'Z')); + + /* b/e/I */ + ModeManager::AddChannelMode(new ChannelModeList("QUIET", 'q')); + + /* Add channel modes */ + ModeManager::AddChannelMode(new ChannelMode("BLOCKCOLOR", 'c')); + ModeManager::AddChannelMode(new ChannelMode("NOCTCP", 'C')); + ModeManager::AddChannelMode(new ChannelModeParam("REDIRECT", 'f')); + ModeManager::AddChannelMode(new ChannelMode("ALLOWFORWARD", 'F')); + ModeManager::AddChannelMode(new ChannelMode("ALLINVITE", 'g')); + ModeManager::AddChannelMode(new ChannelModeParam("JOINFLOOD", 'j')); + ModeManager::AddChannelMode(new ChannelModeLargeBan("LBAN", 'L')); + ModeManager::AddChannelMode(new ChannelMode("PERM", 'P')); + ModeManager::AddChannelMode(new ChannelMode("NOFORWARD", 'Q')); + ModeManager::AddChannelMode(new ChannelMode("OPMODERATED", 'z')); + } + + public: + ProtoCharybdis(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PROTOCOL | VENDOR), + ircd_proto(this), + message_away(this), message_capab(this), message_error(this), message_invite(this), message_kick(this), + message_kill(this), message_mode(this), message_motd(this), message_notice(this), message_part(this), + message_ping(this), message_privmsg(this), message_quit(this), message_squit(this), message_stats(this), + message_time(this), message_topic(this), message_version(this), message_whois(this), + + message_bmask("IRCDMessage", "charybdis/bmask", "ratbox/bmask"), + message_join("IRCDMessage", "charybdis/join", "ratbox/join"), + message_nick("IRCDMessage", "charybdis/nick", "ratbox/nick"), + message_pong("IRCDMessage", "charybdis/pong", "ratbox/pong"), + message_sid("IRCDMessage", "charybdis/sid", "ratbox/sid"), + message_sjoin("IRCDMessage", "charybdis/sjoin", "ratbox/sjoin"), + message_tb("IRCDMessage", "charybdis/tb", "ratbox/tb"), + message_tmode("IRCDMessage", "charybdis/tmode", "ratbox/tmode"), + message_uid("IRCDMessage", "charybdis/uid", "ratbox/uid"), + + message_encap(this), message_euid(this), message_pass(this), message_server(this) + + { + + + if (ModuleManager::LoadModule("ratbox", User::Find(creator)) != MOD_ERR_OK) + throw ModuleException("Unable to load ratbox"); + m_ratbox = ModuleManager::FindModule("ratbox"); + if (!m_ratbox) + throw ModuleException("Unable to find ratbox"); + if (!ratbox) + throw ModuleException("No protocol interface for ratbox"); + + this->AddModes(); + } + + ~ProtoCharybdis() + { + m_ratbox = ModuleManager::FindModule("ratbox"); + ModuleManager::UnloadModule(m_ratbox, NULL); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + use_server_side_mlock = conf->GetModule(this)->Get("use_server_side_mlock"); + } + + void OnChannelSync(Channel *c) anope_override + { + if (!c->ci) + return; + + ModeLocks *modelocks = c->ci->GetExt("modelocks"); + if (use_server_side_mlock && modelocks && Servers::Capab.count("MLOCK") > 0) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", ""); + UplinkSocket::Message(Me) << "MLOCK " << static_cast(c->creation_time) << " " << c->ci->name << " " << modes; + } + } + + EventReturn OnMLock(ChannelInfo *ci, ModeLock *lock) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + ChannelMode *cm = ModeManager::FindChannelModeByName(lock->name); + if (use_server_side_mlock && cm && ci->c && modelocks && (cm->type == MODE_REGULAR || cm->type == MODE_PARAM) && Servers::Capab.count("MLOCK") > 0) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", "") + cm->mchar; + UplinkSocket::Message(Me) << "MLOCK " << static_cast(ci->c->creation_time) << " " << ci->name << " " << modes; + } + + return EVENT_CONTINUE; + } + + EventReturn OnUnMLock(ChannelInfo *ci, ModeLock *lock) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + ChannelMode *cm = ModeManager::FindChannelModeByName(lock->name); + if (use_server_side_mlock && cm && modelocks && ci->c && (cm->type == MODE_REGULAR || cm->type == MODE_PARAM) && Servers::Capab.count("MLOCK") > 0) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", "").replace_all_cs(cm->mchar, ""); + UplinkSocket::Message(Me) << "MLOCK " << static_cast(ci->c->creation_time) << " " << ci->name << " " << modes; + } + + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(ProtoCharybdis) diff --git a/modules/protocol/hybrid.cpp b/modules/protocol/hybrid.cpp new file mode 100644 index 0000000..232c9e9 --- /dev/null +++ b/modules/protocol/hybrid.cpp @@ -0,0 +1,875 @@ +/* ircd-hybrid protocol module. Minimum supported version of ircd-hybrid is 8.2.23. + * + * (C) 2003-2022 Anope Team + * (C) 2012-2022 ircd-hybrid development team + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/cs_mode.h" + +static Anope::string UplinkSID; +static bool UseSVSAccount = false; // Temporary backwards compatibility hack until old proto is deprecated + +class HybridProto : public IRCDProto +{ + void SendSVSKillInternal(const MessageSource &source, User *u, const Anope::string &buf) anope_override + { + IRCDProto::SendSVSKillInternal(source, u, buf); + u->KillInternal(source, buf); + } + + public: + HybridProto(Module *creator) : IRCDProto(creator, "ircd-hybrid 8.2.23+") + { + DefaultPseudoclientModes = "+oi"; + CanSVSNick = true; + CanSVSHold = true; + CanSVSJoin = true; + CanSNLine = true; + CanSQLine = true; + CanSQLineChannel = true; + CanSZLine = true; + CanCertFP = true; + CanSetVHost = true; + RequiresID = true; + MaxModes = 6; + } + + void SendInvite(const MessageSource &source, const Channel *c, User *u) anope_override + { + UplinkSocket::Message(source) << "INVITE " << u->GetUID() << " " << c->name << " " << c->creation_time; + } + + void SendGlobalNotice(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "NOTICE $$" << dest->GetName() << " :" << msg; + } + + void SendGlobalPrivmsg(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "PRIVMSG $$" << dest->GetName() << " :" << msg; + } + + void SendSQLine(User *, const XLine *x) anope_override + { + UplinkSocket::Message(Me) << "RESV * " << (x->expires ? x->expires - Anope::CurTime : 0) << " " << x->mask << " :" << x->reason; + } + + void SendSGLineDel(const XLine *x) anope_override + { + UplinkSocket::Message(Me) << "UNXLINE * " << x->mask; + } + + void SendSGLine(User *, const XLine *x) anope_override + { + UplinkSocket::Message(Me) << "XLINE * " << x->mask << " " << (x->expires ? x->expires - Anope::CurTime : 0) << " :" << x->GetReason(); + } + + void SendSZLineDel(const XLine *x) anope_override + { + UplinkSocket::Message(Me) << "UNDLINE * " << x->GetHost(); + } + + void SendSZLine(User *, const XLine *x) anope_override + { + /* Calculate the time left before this would expire, capping it at 2 days */ + time_t timeleft = x->expires - Anope::CurTime; + + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + + UplinkSocket::Message(Me) << "DLINE * " << timeleft << " " << x->GetHost() << " :" << x->GetReason(); + } + + void SendAkillDel(const XLine *x) anope_override + { + if (x->IsRegex() || x->HasNickOrReal()) + return; + + UplinkSocket::Message(Me) << "UNKLINE * " << x->GetUser() << " " << x->GetHost(); + } + + void SendSQLineDel(const XLine *x) anope_override + { + UplinkSocket::Message(Me) << "UNRESV * " << x->mask; + } + + void SendJoin(User *u, Channel *c, const ChannelStatus *status) anope_override + { + UplinkSocket::Message(Me) << "SJOIN " << c->creation_time << " " << c->name << " +" << c->GetModes(true, true) << " :" << u->GetUID(); + + /* + * Note that we can send this with the SJOIN but choose not to + * because the mode stacker will handle this and probably will + * merge these modes with +nrt and other mlocked modes. + */ + if (status) + { + /* First save the channel status in case uc->status == status */ + ChannelStatus cs = *status; + + /* + * If the user is internally on the channel with flags, kill them so that + * the stacker will allow this. + */ + ChanUserContainer *uc = c->FindUser(u); + if (uc) + uc->status.Clear(); + + BotInfo *setter = BotInfo::Find(u->GetUID()); + for (size_t i = 0; i < cs.Modes().length(); ++i) + c->SetMode(setter, ModeManager::FindChannelModeByChar(cs.Modes()[i]), u->GetUID(), false); + + if (uc) + uc->status = cs; + } + } + + void SendAkill(User *u, XLine *x) anope_override + { + if (x->IsRegex() || x->HasNickOrReal()) + { + if (!u) + { + /* + * No user (this akill was just added), and contains nick and/or realname. + * Find users that match and ban them. + */ + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + if (x->manager->Check(it->second, x)) + this->SendAkill(it->second, x); + + return; + } + + const XLine *old = x; + + if (old->manager->HasEntry("*@" + u->host)) + return; + + /* We can't akill x as it has a nick and/or realname included, so create a new akill for *@host */ + XLine *xline = new XLine("*@" + u->host, old->by, old->expires, old->reason, old->id); + + old->manager->AddXLine(xline); + x = xline; + + Log(Config->GetClient("OperServ"), "akill") << "AKILL: Added an akill for " << x->mask << " because " << u->GetMask() << "#" + << u->realname << " matches " << old->mask; + } + + /* Calculate the time left before this would expire, capping it at 2 days */ + time_t timeleft = x->expires - Anope::CurTime; + + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + + UplinkSocket::Message(Me) << "KLINE * " << timeleft << " " << x->GetUser() << " " << x->GetHost() << " :" << x->GetReason(); + } + + void SendServer(const Server *server) anope_override + { + if (server == Me) + UplinkSocket::Message() << "SERVER " << server->GetName() << " " << server->GetHops() + 1 << " " << server->GetSID() << " +" << " :" << server->GetDescription(); + else + UplinkSocket::Message(Me) << "SID " << server->GetName() << " " << server->GetHops() + 1 << " " << server->GetSID() << " +" << " :" << server->GetDescription(); + } + + void SendConnect() anope_override + { + UplinkSocket::Message() << "PASS " << Config->Uplinks[Anope::CurrentUplink].password; + + /* + * TBURST - Supports topic burst + * ENCAP - Supports ENCAP + * EOB - Supports End Of Burst message + * RHOST - Supports UID message with realhost information + * MLOCK - Supports MLOCK + */ + UplinkSocket::Message() << "CAPAB :ENCAP TBURST EOB RHOST MLOCK"; + + SendServer(Me); + + UplinkSocket::Message(Me) << "SVINFO 6 6 0 :" << Anope::CurTime; + } + + void SendClientIntroduction(User *u) anope_override + { + Anope::string modes = "+" + u->GetModes(); + + UplinkSocket::Message(Me) << "UID " << u->nick << " 1 " << u->timestamp << " " << modes << " " << u->GetIdent() << " " + << u->host << " " << u->host << " 0.0.0.0 " << u->GetUID() << " * :" << u->realname; + } + + void SendEOB() anope_override + { + UplinkSocket::Message(Me) << "EOB"; + } + + void SendModeInternal(const MessageSource &source, User *u, const Anope::string &buf) anope_override + { + UplinkSocket::Message(source) << "SVSMODE " << u->GetUID() << " " << u->timestamp << " " << buf; + } + + void SendLogin(User *u, NickAlias *na) anope_override + { + if (UseSVSAccount == false) + IRCD->SendMode(Config->GetClient("NickServ"), u, "+d %s", na->nc->display.c_str()); + else + UplinkSocket::Message(Me) << "SVSACCOUNT " << u->GetUID() << " " << u->timestamp << " " << na->nc->display; + } + + void SendLogout(User *u) anope_override + { + if (UseSVSAccount == false) + IRCD->SendMode(Config->GetClient("NickServ"), u, "+d *"); + else + UplinkSocket::Message(Me) << "SVSACCOUNT " << u->GetUID() << " " << u->timestamp << " *"; + } + + void SendChannel(Channel *c) anope_override + { + Anope::string modes = "+" + c->GetModes(true, true); + UplinkSocket::Message(Me) << "SJOIN " << c->creation_time << " " << c->name << " " << modes << " :"; + } + + void SendTopic(const MessageSource &source, Channel *c) anope_override + { + UplinkSocket::Message(source) << "TBURST " << c->creation_time << " " << c->name << " " << c->topic_ts << " " << c->topic_setter << " :" << c->topic; + } + + void SendForceNickChange(User *u, const Anope::string &newnick, time_t when) anope_override + { + UplinkSocket::Message(Me) << "SVSNICK " << u->GetUID() << " " << u->timestamp << " " << newnick << " " << when; + } + + void SendSVSJoin(const MessageSource &source, User *u, const Anope::string &chan, const Anope::string &) anope_override + { + UplinkSocket::Message(source) << "SVSJOIN " << u->GetUID() << " " << chan; + } + + void SendSVSPart(const MessageSource &source, User *u, const Anope::string &chan, const Anope::string ¶m) anope_override + { + if (!param.empty()) + UplinkSocket::Message(source) << "SVSPART " << u->GetUID() << " " << chan << " :" << param; + else + UplinkSocket::Message(source) << "SVSPART " << u->GetUID() << " " << chan; + } + + void SendSVSHold(const Anope::string &nick, time_t t) anope_override + { + XLine x(nick, Me->GetName(), Anope::CurTime + t, "Being held for registered user"); + this->SendSQLine(NULL, &x); + } + + void SendSVSHoldDel(const Anope::string &nick) anope_override + { + XLine x(nick); + this->SendSQLineDel(&x); + } + + void SendVhost(User *u, const Anope::string &ident, const Anope::string &host) anope_override + { + UplinkSocket::Message(Me) << "SVSHOST " << u->GetUID() << " " << u->timestamp << " " << host; + } + + void SendVhostDel(User *u) anope_override + { + UplinkSocket::Message(Me) << "SVSHOST " << u->GetUID() << " " << u->timestamp << " " << u->host; + } + + bool IsExtbanValid(const Anope::string &mask) anope_override + { + return mask.length() >= 4 && mask[0] == '$' && mask[2] == ':'; + } + + bool IsIdentValid(const Anope::string &ident) anope_override + { + if (ident.empty() || ident.length() > Config->GetBlock("networkinfo")->Get("userlen")) + return false; + + /* + * If the user name begins with a tilde (~), make sure there is at least + * one succeeding character. + */ + unsigned i = ident[0] == '~'; + if (i >= ident.length()) + return false; + + /* User names may not start with a '-', '_', or '.'. */ + const char &a = ident[i]; + if (a == '-' || a == '_' || a == '.') + return false; + + for (i = 0; i < ident.length(); ++i) + { + const char &c = ident[i]; + + /* A tilde can only be used as the first character of a user name. */ + if (c == '~' && i == 0) + continue; + + if ((c >= 'A' && c <= 'Z') || + (c >= 'a' && c <= 'z') || + (c >= '0' && c <= '9') || c == '-' || c == '_' || c == '.') + continue; + + return false; + } + + return true; + } +}; + +struct IRCDMessageBMask : IRCDMessage +{ + IRCDMessageBMask(Module *creator) : IRCDMessage(creator, "BMASK", 4) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + /* 0 1 2 3 */ + /* :0MC BMASK 1350157102 #channel b :*!*@*.test.com */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Channel *c = Channel::Find(params[1]); + ChannelMode *mode = ModeManager::FindChannelModeByChar(params[2][0]); + + if (c && mode) + { + spacesepstream bans(params[3]); + Anope::string token; + + while (bans.GetToken(token)) + c->SetModeInternal(source, mode, token); + } + } +}; + +struct IRCDMessageCapab : Message::Capab +{ + IRCDMessageCapab(Module *creator) : Message::Capab(creator, "CAPAB") { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* 0 */ + /* CAPAB :TBURST EOB MLOCK */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + spacesepstream sep(params[0]); + Anope::string capab; + + while (sep.GetToken(capab)) + { + if (capab.find("HOP") != Anope::string::npos || capab.find("RHOST") != Anope::string::npos) + ModeManager::AddChannelMode(new ChannelModeStatus("HALFOP", 'h', '%', 1)); + if (capab.find("AOP") != Anope::string::npos) + ModeManager::AddChannelMode(new ChannelModeStatus("PROTECT", 'a', '&', 3)); + if (capab.find("QOP") != Anope::string::npos) + ModeManager::AddChannelMode(new ChannelModeStatus("OWNER", 'q', '~', 4)); + } + + Message::Capab::Run(source, params); + } +}; + +struct IRCDMessageCertFP: IRCDMessage +{ + IRCDMessageCertFP(Module *creator) : IRCDMessage(creator, "CERTFP", 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + /* 0 */ + /* :0MCAAAAAB CERTFP 4C62287BA6776A89CD4F8FF10A62FFB35E79319F51AF6C62C674984974FCCB1D */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + + u->fingerprint = params[0]; + FOREACH_MOD(OnFingerprint, (u)); + } +}; + +struct IRCDMessageEOB : IRCDMessage +{ + IRCDMessageEOB(Module *creator) : IRCDMessage(creator, "EOB", 0) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetServer()->Sync(true); + } +}; + +struct IRCDMessageJoin : Message::Join +{ + IRCDMessageJoin(Module *creator) : Message::Join(creator, "JOIN") { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params.size() < 2) + return; + + std::vector p = params; + p.erase(p.begin()); + + Message::Join::Run(source, p); + } +}; + +struct IRCDMessageMetadata : IRCDMessage +{ + IRCDMessageMetadata(Module *creator) : IRCDMessage(creator, "METADATA", 3) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + /* 0 1 2 3 */ + /* :0MC METADATA client 0MCAAAAAB certfp :4C62287BA6776A89CD4F8FF10A62FFB35E79319F51AF6C62C674984974FCCB1D */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params[0].equals_cs("client")) + { + User *u = User::Find(params[1]); + if (!u) + { + Log(LOG_DEBUG) << "METADATA for nonexistent user " << params[1]; + return; + } + + if (params[2].equals_cs("certfp")) + { + u->fingerprint = params[3]; + FOREACH_MOD(OnFingerprint, (u)); + } + } + } +}; + +struct IRCDMessageMLock : IRCDMessage +{ + IRCDMessageMLock(Module *creator) : IRCDMessage(creator, "MLOCK", 4) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + /* 0 1 2 3 */ + /* :0MC MLOCK 1350157102 #channel 1350158923 :nt */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Channel *c = Channel::Find(params[1]); + + if (c && c->ci) + { + ModeLocks *modelocks = c->ci->GetExt("modelocks"); + Anope::string modes; + + if (modelocks) + modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", ""); + + // Mode lock string is not what we say it is? + if (modes != params[3]) + UplinkSocket::Message(Me) << "MLOCK " << c->creation_time << " " << c->name << " " << Anope::CurTime << " :" << modes; + } + } +}; + +struct IRCDMessageNick : IRCDMessage +{ + IRCDMessageNick(Module *creator) : IRCDMessage(creator, "NICK", 2) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + /* 0 1 */ + /* :0MCAAAAAB NICK newnick 1350157102 */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetUser()->ChangeNick(params[0], convertTo(params[1])); + } +}; + +struct IRCDMessagePass : IRCDMessage +{ + IRCDMessagePass(Module *creator) : IRCDMessage(creator, "PASS", 1) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* 0 */ + /* PASS password */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params.size() == 4) + UplinkSID = params[3]; + } +}; + +struct IRCDMessagePong : IRCDMessage +{ + IRCDMessagePong(Module *creator) : IRCDMessage(creator, "PONG", 0) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetServer()->Sync(false); + } +}; + +struct IRCDMessageServer : IRCDMessage +{ + IRCDMessageServer(Module *creator) : IRCDMessage(creator, "SERVER", 3) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* 0 1 2 3 4 */ + /* SERVER hades.arpa 1 4XY + :ircd-hybrid test server */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + /* Servers other than our immediate uplink are introduced via SID */ + if (params[1] != "1") + return; + + if (params.size() == 5) + { + UplinkSID = params[2]; + UseSVSAccount = true; + } + + new Server(source.GetServer() == NULL ? Me : source.GetServer(), params[0], 1, params.back(), UplinkSID); + + IRCD->SendPing(Me->GetName(), params[0]); + } +}; + +struct IRCDMessageSID : IRCDMessage +{ + IRCDMessageSID(Module *creator) : IRCDMessage(creator, "SID", 5) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* 0 1 2 3 4 */ + /* :0MC SID hades.arpa 2 4XY + :ircd-hybrid test server */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + unsigned int hops = params[1].is_pos_number_only() ? convertTo(params[1]) : 0; + new Server(source.GetServer() == NULL ? Me : source.GetServer(), params[0], hops, params.back(), params[2]); + + IRCD->SendPing(Me->GetName(), params[0]); + } +}; + +struct IRCDMessageSJoin : IRCDMessage +{ + IRCDMessageSJoin(Module *creator) : IRCDMessage(creator, "SJOIN", 4) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* 0 1 2 3 */ + /* :0MC SJOIN 1654877335 #nether +nt :@0MCAAAAAB +0MCAAAAAC */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Anope::string modes; + + for (unsigned i = 2; i < params.size() - 1; ++i) + modes += " " + params[i]; + + if (!modes.empty()) + modes.erase(modes.begin()); + + std::list users; + + spacesepstream sep(params[params.size() - 1]); + Anope::string buf; + + while (sep.GetToken(buf)) + { + Message::Join::SJoinUser sju; + + /* Get prefixes from the nick */ + for (char ch; (ch = ModeManager::GetStatusChar(buf[0])); ) + { + buf.erase(buf.begin()); + sju.first.AddMode(ch); + } + + sju.second = User::Find(buf); + if (!sju.second) + { + Log(LOG_DEBUG) << "SJOIN for nonexistent user " << buf << " on " << params[1]; + continue; + } + + users.push_back(sju); + } + + time_t ts = Anope::string(params[0]).is_pos_number_only() ? convertTo(params[0]) : Anope::CurTime; + Message::Join::SJoin(source, params[1], ts, modes, users); + } +}; + +struct IRCDMessageSVSMode : IRCDMessage +{ + IRCDMessageSVSMode(Module *creator) : IRCDMessage(creator, "SVSMODE", 3) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* 0 1 2 */ + /* :0MC SVSMODE 0MCAAAAAB 1350157102 +r */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = User::Find(params[0]); + + if (!u) + return; + + if (!params[1].is_pos_number_only() || convertTo(params[1]) != u->timestamp) + return; + + u->SetModesInternal(source, "%s", params[2].c_str()); + } +}; + +struct IRCDMessageTBurst : IRCDMessage +{ + IRCDMessageTBurst(Module *creator) : IRCDMessage(creator, "TBURST", 5) { } + + /* 0 1 2 3 4 */ + /* :0MC TBURST 1654867975 #nether 1654877335 Steve!~steve@the.mines :Join the ghast nation */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Anope::string setter; + sepstream(params[3], '!').GetToken(setter, 0); + time_t topic_time = Anope::string(params[2]).is_pos_number_only() ? convertTo(params[2]) : Anope::CurTime; + Channel *c = Channel::Find(params[1]); + + if (c) + c->ChangeTopicInternal(NULL, setter, params[4], topic_time); + } +}; + +struct IRCDMessageTMode : IRCDMessage +{ + IRCDMessageTMode(Module *creator) : IRCDMessage(creator, "TMODE", 3) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* 0 1 2 */ + /* :0MC TMODE 1654867975 #nether +ntR */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + time_t ts = 0; + + try + { + ts = convertTo(params[0]); + } + catch (const ConvertException &) { } + + Channel *c = Channel::Find(params[1]); + Anope::string modes = params[2]; + + for (unsigned i = 3; i < params.size(); ++i) + modes += " " + params[i]; + + if (c) + c->SetModesInternal(source, modes, ts); + } +}; + +struct IRCDMessageUID : IRCDMessage +{ + IRCDMessageUID(Module *creator) : IRCDMessage(creator, "UID", 11) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* 0 1 2 3 4 5 6 7 8 9 10 */ + /* :0MC UID Steve 1 1350157102 +oi ~steve virtual.host real.host 10.0.0.1 0MCAAAAAB Steve :Mining all the time */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + NickAlias *na = NULL; + + if (params[9] != "*") + na = NickAlias::Find(params[9]); + + /* Source is always the server */ + User::OnIntroduce(params[0], params[4], params[6], params[5], params[7], source.GetServer(), params[10], + params[2].is_pos_number_only() ? convertTo(params[2]) : 0, + params[3], params[8], na ? *na->nc : NULL); + } +}; + +class ProtoHybrid : public Module +{ + HybridProto ircd_proto; + + /* Core message handlers */ + Message::Away message_away; + Message::Error message_error; + Message::Invite message_invite; + Message::Kick message_kick; + Message::Kill message_kill; + Message::Mode message_mode; + Message::MOTD message_motd; + Message::Notice message_notice; + Message::Part message_part; + Message::Ping message_ping; + Message::Privmsg message_privmsg; + Message::Quit message_quit; + Message::SQuit message_squit; + Message::Stats message_stats; + Message::Time message_time; + Message::Topic message_topic; + Message::Version message_version; + Message::Whois message_whois; + + /* Our message handlers */ + IRCDMessageBMask message_bmask; + IRCDMessageCapab message_capab; + IRCDMessageCertFP message_certfp; + IRCDMessageEOB message_eob; + IRCDMessageJoin message_join; + IRCDMessageMetadata message_metadata; + IRCDMessageMLock message_mlock; + IRCDMessageNick message_nick; + IRCDMessagePass message_pass; + IRCDMessagePong message_pong; + IRCDMessageServer message_server; + IRCDMessageSID message_sid; + IRCDMessageSJoin message_sjoin; + IRCDMessageSVSMode message_svsmode; + IRCDMessageTBurst message_tburst; + IRCDMessageTMode message_tmode; + IRCDMessageUID message_uid; + + bool use_server_side_mlock; + + void AddModes() + { + /* Add user modes */ + ModeManager::AddUserMode(new UserModeOperOnly("ADMIN", 'a')); + ModeManager::AddUserMode(new UserMode("CALLERID", 'g')); + ModeManager::AddUserMode(new UserMode("INVIS", 'i')); + ModeManager::AddUserMode(new UserModeOperOnly("LOCOPS", 'l')); + ModeManager::AddUserMode(new UserModeOperOnly("OPER", 'o')); + ModeManager::AddUserMode(new UserMode("HIDECHANS", 'p')); + ModeManager::AddUserMode(new UserMode("HIDEIDLE", 'q')); + ModeManager::AddUserMode(new UserModeNoone("REGISTERED", 'r')); + ModeManager::AddUserMode(new UserModeOperOnly("SNOMASK", 's')); + ModeManager::AddUserMode(new UserMode("WALLOPS", 'w')); + ModeManager::AddUserMode(new UserMode("BOT", 'B')); + ModeManager::AddUserMode(new UserMode("DEAF", 'D')); + ModeManager::AddUserMode(new UserMode("SOFTCALLERID", 'G')); + ModeManager::AddUserMode(new UserModeOperOnly("HIDEOPER", 'H')); + ModeManager::AddUserMode(new UserMode("REGPRIV", 'R')); + ModeManager::AddUserMode(new UserModeNoone("SSL", 'S')); + ModeManager::AddUserMode(new UserModeNoone("WEBIRC", 'W')); + ModeManager::AddUserMode(new UserMode("SECUREONLY", 'Z')); + + /* b/e/I */ + ModeManager::AddChannelMode(new ChannelModeList("BAN", 'b')); + ModeManager::AddChannelMode(new ChannelModeList("EXCEPT", 'e')); + ModeManager::AddChannelMode(new ChannelModeList("INVITEOVERRIDE", 'I')); + + /* v/o */ + ModeManager::AddChannelMode(new ChannelModeStatus("VOICE", 'v', '+', 0)); + ModeManager::AddChannelMode(new ChannelModeStatus("OP", 'o', '@', 2)); + + /* l/k */ + ModeManager::AddChannelMode(new ChannelModeParam("LIMIT", 'l', true)); + ModeManager::AddChannelMode(new ChannelModeKey('k')); + + /* Add channel modes */ + ModeManager::AddChannelMode(new ChannelMode("BLOCKCOLOR", 'c')); + ModeManager::AddChannelMode(new ChannelMode("INVITE", 'i')); + ModeManager::AddChannelMode(new ChannelMode("MODERATED", 'm')); + ModeManager::AddChannelMode(new ChannelMode("NOEXTERNAL", 'n')); + ModeManager::AddChannelMode(new ChannelMode("PRIVATE", 'p')); + ModeManager::AddChannelMode(new ChannelModeNoone("REGISTERED", 'r')); + ModeManager::AddChannelMode(new ChannelMode("SECRET", 's')); + ModeManager::AddChannelMode(new ChannelMode("TOPIC", 't')); + ModeManager::AddChannelMode(new ChannelMode("NOCTCP", 'C')); + ModeManager::AddChannelMode(new ChannelMode("NOKNOCK", 'K')); + ModeManager::AddChannelMode(new ChannelModeOperOnly("LBAN", 'L')); + ModeManager::AddChannelMode(new ChannelMode("REGMODERATED", 'M')); + ModeManager::AddChannelMode(new ChannelMode("NONICK", 'N')); + ModeManager::AddChannelMode(new ChannelModeOperOnly("OPERONLY", 'O')); + ModeManager::AddChannelMode(new ChannelMode("NOKICK", 'Q')); + ModeManager::AddChannelMode(new ChannelMode("REGISTEREDONLY", 'R')); + ModeManager::AddChannelMode(new ChannelMode("SSL", 'S')); + ModeManager::AddChannelMode(new ChannelMode("NONOTICE", 'T')); + ModeManager::AddChannelMode(new ChannelMode("NOINVITE", 'V')); + ModeManager::AddChannelMode(new ChannelModeNoone("ISSECURE", 'Z')); + } + + public: + ProtoHybrid(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PROTOCOL | VENDOR), + ircd_proto(this), + message_away(this), + message_error(this), + message_invite(this), + message_kick(this), + message_kill(this), + message_mode(this), + message_motd(this), + message_notice(this), + message_part(this), + message_ping(this), + message_privmsg(this), + message_quit(this), + message_squit(this), + message_stats(this), + message_time(this), + message_topic(this), + message_version(this), + message_whois(this), + message_bmask(this), + message_capab(this), + message_certfp(this), + message_eob(this), + message_join(this), + message_metadata(this), + message_mlock(this), + message_nick(this), + message_pass(this), + message_pong(this), + message_server(this), + message_sid(this), + message_sjoin(this), + message_svsmode(this), + message_tburst(this), + message_tmode(this), + message_uid(this) + { + if (Config->GetModule(this)) + this->AddModes(); + } + + void OnUserNickChange(User *u, const Anope::string &) anope_override + { + u->RemoveModeInternal(Me, ModeManager::FindUserModeByName("REGISTERED")); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + use_server_side_mlock = conf->GetModule(this)->Get("use_server_side_mlock"); + } + + void OnChannelSync(Channel *c) anope_override + { + if (!c->ci) + return; + + ModeLocks *modelocks = c->ci->GetExt("modelocks"); + if (use_server_side_mlock && modelocks && Servers::Capab.count("MLOCK")) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", ""); + UplinkSocket::Message(Me) << "MLOCK " << c->creation_time << " " << c->ci->name << " " << Anope::CurTime << " :" << modes; + } + } + + void OnDelChan(ChannelInfo *ci) anope_override + { + if (use_server_side_mlock && ci->c && Servers::Capab.count("MLOCK")) + UplinkSocket::Message(Me) << "MLOCK " << ci->c->creation_time << " " << ci->name << " " << Anope::CurTime << " :"; + } + + EventReturn OnMLock(ChannelInfo *ci, ModeLock *lock) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + ChannelMode *cm = ModeManager::FindChannelModeByName(lock->name); + if (use_server_side_mlock && cm && ci->c && modelocks && (cm->type == MODE_REGULAR || cm->type == MODE_PARAM) && Servers::Capab.count("MLOCK")) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", "") + cm->mchar; + UplinkSocket::Message(Me) << "MLOCK " << ci->c->creation_time << " " << ci->name << " " << Anope::CurTime << " :" << modes; + } + + return EVENT_CONTINUE; + } + + EventReturn OnUnMLock(ChannelInfo *ci, ModeLock *lock) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + ChannelMode *cm = ModeManager::FindChannelModeByName(lock->name); + if (use_server_side_mlock && cm && modelocks && ci->c && (cm->type == MODE_REGULAR || cm->type == MODE_PARAM) && Servers::Capab.count("MLOCK")) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", "").replace_all_cs(cm->mchar, ""); + UplinkSocket::Message(Me) << "MLOCK " << ci->c->creation_time << " " << ci->name << " " << Anope::CurTime << " :" << modes; + } + + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(ProtoHybrid) diff --git a/modules/protocol/inspircd12.cpp b/modules/protocol/inspircd12.cpp new file mode 100644 index 0000000..60b46e7 --- /dev/null +++ b/modules/protocol/inspircd12.cpp @@ -0,0 +1,1400 @@ +/* inspircd 1.2 functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/sasl.h" + +struct SASLUser +{ + Anope::string uid; + Anope::string acc; + time_t created; +}; + +static std::list saslusers; + +static Anope::string rsquit_server, rsquit_id; + +class ChannelModeFlood : public ChannelModeParam +{ + public: + ChannelModeFlood(char modeChar, bool minusNoArg) : ChannelModeParam("FLOOD", modeChar, minusNoArg) { } + + bool IsValid(Anope::string &value) const anope_override + { + try + { + Anope::string rest; + if (!value.empty() && value[0] != ':' && convertTo(value[0] == '*' ? value.substr(1) : value, rest, false) > 0 && rest[0] == ':' && rest.length() > 1 && convertTo(rest.substr(1), rest, false) > 0 && rest.empty()) + return true; + } + catch (const ConvertException &) { } + + return false; + } +}; + +class InspIRCd12Proto : public IRCDProto +{ + private: + void SendSVSKillInternal(const MessageSource &source, User *user, const Anope::string &buf) anope_override + { + IRCDProto::SendSVSKillInternal(source, user, buf); + user->KillInternal(source, buf); + } + + void SendChgIdentInternal(const Anope::string &nick, const Anope::string &vIdent) + { + if (!Servers::Capab.count("CHGIDENT")) + Log() << "CHGIDENT not loaded!"; + else + UplinkSocket::Message(Me) << "CHGIDENT " << nick << " " << vIdent; + } + + void SendChgHostInternal(const Anope::string &nick, const Anope::string &vhost) + { + if (!Servers::Capab.count("CHGHOST")) + Log() << "CHGHOST not loaded!"; + else + UplinkSocket::Message(Me) << "CHGHOST " << nick << " " << vhost; + } + + void SendAddLine(const Anope::string &xtype, const Anope::string &mask, time_t duration, const Anope::string &addedby, const Anope::string &reason) + { + UplinkSocket::Message(Me) << "ADDLINE " << xtype << " " << mask << " " << addedby << " " << Anope::CurTime << " " << duration << " :" << reason; + } + + void SendDelLine(const Anope::string &xtype, const Anope::string &mask) + { + UplinkSocket::Message(Me) << "DELLINE " << xtype << " " << mask; + } + + public: + InspIRCd12Proto(Module *creator) : IRCDProto(creator, "InspIRCd 1.2") + { + DefaultPseudoclientModes = "+I"; + CanSVSNick = true; + CanSVSJoin = true; + CanSetVHost = true; + CanSetVIdent = true; + CanSQLine = true; + CanSZLine = true; + CanSVSHold = true; + CanCertFP = true; + RequiresID = true; + MaxModes = 20; + } + + void SendGlobalNotice(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "NOTICE $" << dest->GetName() << " :" << msg; + } + + void SendGlobalPrivmsg(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "PRIVMSG $" << dest->GetName() << " :" << msg; + } + + void SendAkillDel(const XLine *x) anope_override + { + /* InspIRCd may support regex bans + * Mask is expected in format: 'n!u@h\sr' and spaces as '\s' + * We remove the '//' and replace '#' and any ' ' with '\s' + */ + if (x->IsRegex() && Servers::Capab.count("RLINE")) + { + Anope::string mask = x->mask; + if (mask.length() >= 2 && mask[0] == '/' && mask[mask.length() - 1] == '/') + mask = mask.substr(1, mask.length() - 2); + size_t h = mask.find('#'); + if (h != Anope::string::npos) + { + mask = mask.replace(h, 1, "\\s"); + mask = mask.replace_all_cs(" ", "\\s"); + } + SendDelLine("R", mask); + return; + } + else if (x->IsRegex() || x->HasNickOrReal()) + return; + + /* ZLine if we can instead */ + if (x->GetUser() == "*") + { + cidr addr(x->GetHost()); + if (addr.valid()) + { + IRCD->SendSZLineDel(x); + return; + } + } + + SendDelLine("G", x->GetUser() + "@" + x->GetHost()); + } + + void SendTopic(const MessageSource &source, Channel *c) anope_override + { + if (Servers::Capab.count("SVSTOPIC")) + { + UplinkSocket::Message(c->ci->WhoSends()) << "SVSTOPIC " << c->name << " " << c->topic_ts << " " << c->topic_setter << " :" << c->topic; + } + else + { + /* If the last time a topic was set is after the TS we want for this topic we must bump this topic's timestamp to now */ + time_t ts = c->topic_ts; + if (c->topic_time > ts) + ts = Anope::CurTime; + /* But don't modify c->topic_ts, it should remain set to the real TS we want as ci->last_topic_time pulls from it */ + UplinkSocket::Message(source) << "FTOPIC " << c->name << " " << ts << " " << c->topic_setter << " :" << c->topic; + } + } + + void SendVhostDel(User *u) anope_override + { + UserMode *um = ModeManager::FindUserModeByName("CLOAK"); + + if (um && !u->HasMode(um->name)) + // Just set +x if we can + u->SetMode(NULL, um); + else + // Try to restore cloaked host + this->SendChgHostInternal(u->nick, u->chost); + } + + void SendAkill(User *u, XLine *x) anope_override + { + // Calculate the time left before this would expire, capping it at 2 days + time_t timeleft = x->expires - Anope::CurTime; + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + + /* InspIRCd may support regex bans, if they do we can send this and forget about it + * Mask is expected in format: 'n!u@h\sr' and spaces as '\s' + * We remove the '//' and replace '#' and any ' ' with '\s' + */ + if (x->IsRegex() && Servers::Capab.count("RLINE")) + { + Anope::string mask = x->mask; + if (mask.length() >= 2 && mask[0] == '/' && mask[mask.length() - 1] == '/') + mask = mask.substr(1, mask.length() - 2); + size_t h = mask.find('#'); + if (h != Anope::string::npos) + { + mask = mask.replace(h, 1, "\\s"); + mask = mask.replace_all_cs(" ", "\\s"); + } + SendAddLine("R", mask, timeleft, x->by, x->GetReason()); + return; + } + else if (x->IsRegex() || x->HasNickOrReal()) + { + if (!u) + { + /* No user (this akill was just added), and contains nick and/or realname. Find users that match and ban them */ + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + if (x->manager->Check(it->second, x)) + this->SendAkill(it->second, x); + return; + } + + const XLine *old = x; + + if (old->manager->HasEntry("*@" + u->host)) + return; + + /* We can't akill x as it has a nick and/or realname included, so create a new akill for *@host */ + x = new XLine("*@" + u->host, old->by, old->expires, old->reason, old->id); + old->manager->AddXLine(x); + + Log(Config->GetClient("OperServ"), "akill") << "AKILL: Added an akill for " << x->mask << " because " << u->GetMask() << "#" << u->realname << " matches " << old->mask; + } + + /* ZLine if we can instead */ + if (x->GetUser() == "*") + { + cidr addr(x->GetHost()); + if (addr.valid()) + { + IRCD->SendSZLine(u, x); + return; + } + } + + SendAddLine("G", x->GetUser() + "@" + x->GetHost(), timeleft, x->by, x->GetReason()); + } + + void SendNumericInternal(int numeric, const Anope::string &dest, const Anope::string &buf) anope_override + { + User *u = User::Find(dest); + UplinkSocket::Message() << "PUSH " << dest << " ::" << Me->GetName() << " " << numeric << " " << (u ? u->nick : dest) << " " << buf; + } + + void SendModeInternal(const MessageSource &source, const Channel *dest, const Anope::string &buf) anope_override + { + UplinkSocket::Message(source) << "FMODE " << dest->name << " " << dest->creation_time << " " << buf; + } + + void SendClientIntroduction(User *u) anope_override + { + Anope::string modes = "+" + u->GetModes(); + UplinkSocket::Message(Me) << "UID " << u->GetUID() << " " << u->timestamp << " " << u->nick << " " << u->host << " " << u->host << " " << u->GetIdent() << " 0.0.0.0 " << u->timestamp << " " << modes << " :" << u->realname; + if (modes.find('o') != Anope::string::npos) + UplinkSocket::Message(u) << "OPERTYPE :service"; + } + + /* SERVER services-dev.chatspike.net password 0 :Description here */ + void SendServer(const Server *server) anope_override + { + /* if rsquit is set then we are waiting on a squit */ + if (rsquit_id.empty() && rsquit_server.empty()) + UplinkSocket::Message() << "SERVER " << server->GetName() << " " << Config->Uplinks[Anope::CurrentUplink].password << " " << server->GetHops() << " " << server->GetSID() << " :" << server->GetDescription(); + } + + void SendSquit(Server *s, const Anope::string &message) anope_override + { + if (s != Me) + { + rsquit_id = s->GetSID(); + rsquit_server = s->GetName(); + UplinkSocket::Message() << "RSQUIT " << s->GetName() << " :" << message; + } + else + UplinkSocket::Message() << "SQUIT " << s->GetName() << " :" << message; + } + + /* JOIN */ + void SendJoin(User *user, Channel *c, const ChannelStatus *status) anope_override + { + UplinkSocket::Message(Me) << "FJOIN " << c->name << " " << c->creation_time << " +" << c->GetModes(true, true) << " :," << user->GetUID(); + /* Note that we can send this with the FJOIN but choose not to + * because the mode stacker will handle this and probably will + * merge these modes with +nrt and other mlocked modes + */ + if (status) + { + /* First save the channel status incase uc->Status == status */ + ChannelStatus cs = *status; + /* If the user is internally on the channel with flags, kill them so that + * the stacker will allow this. + */ + ChanUserContainer *uc = c->FindUser(user); + if (uc != NULL) + uc->status.Clear(); + + BotInfo *setter = BotInfo::Find(user->GetUID()); + for (size_t i = 0; i < cs.Modes().length(); ++i) + c->SetMode(setter, ModeManager::FindChannelModeByChar(cs.Modes()[i]), user->GetUID(), false); + + if (uc != NULL) + uc->status = cs; + } + } + + /* UNSQLINE */ + void SendSQLineDel(const XLine *x) anope_override + { + SendDelLine("Q", x->mask); + } + + /* SQLINE */ + void SendSQLine(User *, const XLine *x) anope_override + { + // Calculate the time left before this would expire, capping it at 2 days + time_t timeleft = x->expires - Anope::CurTime; + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + SendAddLine("Q", x->mask, timeleft, x->by, x->GetReason()); + } + + void SendVhost(User *u, const Anope::string &vIdent, const Anope::string &vhost) anope_override + { + if (!vIdent.empty()) + this->SendChgIdentInternal(u->nick, vIdent); + if (!vhost.empty()) + this->SendChgHostInternal(u->nick, vhost); + } + + void SendConnect() anope_override + { + SendServer(Me); + } + + /* SVSHOLD - set */ + void SendSVSHold(const Anope::string &nick, time_t t) anope_override + { + UplinkSocket::Message(Config->GetClient("NickServ")) << "SVSHOLD " << nick << " " << t << " :Being held for registered user"; + } + + /* SVSHOLD - release */ + void SendSVSHoldDel(const Anope::string &nick) anope_override + { + UplinkSocket::Message(Config->GetClient("NickServ")) << "SVSHOLD " << nick; + } + + /* UNSZLINE */ + void SendSZLineDel(const XLine *x) anope_override + { + SendDelLine("Z", x->GetHost()); + } + + /* SZLINE */ + void SendSZLine(User *, const XLine *x) anope_override + { + // Calculate the time left before this would expire, capping it at 2 days + time_t timeleft = x->expires - Anope::CurTime; + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + SendAddLine("Z", x->GetHost(), timeleft, x->by, x->GetReason()); + } + + void SendSVSJoin(const MessageSource &source, User *u, const Anope::string &chan, const Anope::string &) anope_override + { + UplinkSocket::Message(source) << "SVSJOIN " << u->GetUID() << " " << chan; + } + + void SendSVSPart(const MessageSource &source, User *u, const Anope::string &chan, const Anope::string ¶m) anope_override + { + if (!param.empty()) + UplinkSocket::Message(source) << "SVSPART " << u->GetUID() << " " << chan << " :" << param; + else + UplinkSocket::Message(source) << "SVSPART " << u->GetUID() << " " << chan; + } + + void SendSWhois(const MessageSource &, const Anope::string &who, const Anope::string &mask) anope_override + { + User *u = User::Find(who); + + UplinkSocket::Message(Me) << "METADATA " << u->GetUID() << " swhois :" << mask; + } + + void SendBOB() anope_override + { + UplinkSocket::Message(Me) << "BURST " << Anope::CurTime; + Module *enc = ModuleManager::FindFirstOf(ENCRYPTION); + UplinkSocket::Message(Me) << "VERSION :Anope-" << Anope::Version() << " " << Me->GetName() << " :" << IRCD->GetProtocolName() << " - (" << (enc ? enc->name : "none") << ") -- " << Anope::VersionBuildString(); + } + + void SendEOB() anope_override + { + UplinkSocket::Message(Me) << "ENDBURST"; + } + + void SendGlobopsInternal(const MessageSource &source, const Anope::string &buf) anope_override + { + if (Servers::Capab.count("GLOBOPS")) + UplinkSocket::Message(source) << "SNONOTICE g :" << buf; + else + UplinkSocket::Message(source) << "SNONOTICE A :" << buf; + } + + void SendLogin(User *u, NickAlias *na) anope_override + { + /* InspIRCd uses an account to bypass chmode +R, not umode +r, so we can't send this here */ + if (na->nc->HasExt("UNCONFIRMED")) + return; + + UplinkSocket::Message(Me) << "METADATA " << u->GetUID() << " accountname :" << na->nc->display; + } + + void SendLogout(User *u) anope_override + { + UplinkSocket::Message(Me) << "METADATA " << u->GetUID() << " accountname :"; + } + + void SendChannel(Channel *c) anope_override + { + UplinkSocket::Message(Me) << "FJOIN " << c->name << " " << c->creation_time << " +" << c->GetModes(true, true) << " :"; + } + + void SendOper(User *u) anope_override + { + } + + void SendSASLMessage(const SASL::Message &message) anope_override + { + UplinkSocket::Message(Me) << "ENCAP " << message.target.substr(0, 3) << " SASL " << message.source << " " << message.target << " " << message.type << " " << message.data << (message.ext.empty() ? "" : (" " + message.ext)); + } + + void SendSVSLogin(const Anope::string &uid, const Anope::string &acc, const Anope::string &vident, const Anope::string &vhost) anope_override + { + UplinkSocket::Message(Me) << "METADATA " << uid << " accountname :" << acc; + + if (!vident.empty()) + UplinkSocket::Message(Me) << "ENCAP " << uid.substr(0, 3) << " CHGIDENT " << uid << " " << vident; + if (!vhost.empty()) + UplinkSocket::Message(Me) << "ENCAP " << uid.substr(0, 3) << " CHGHOST " << uid << " " << vhost; + + SASLUser su; + su.uid = uid; + su.acc = acc; + su.created = Anope::CurTime; + + for (std::list::iterator it = saslusers.begin(); it != saslusers.end();) + { + SASLUser &u = *it; + + if (u.created + 30 < Anope::CurTime || u.uid == uid) + it = saslusers.erase(it); + else + ++it; + } + + saslusers.push_back(su); + } + + bool IsExtbanValid(const Anope::string &mask) anope_override + { + return mask.length() >= 3 && mask[1] == ':'; + } + + bool IsIdentValid(const Anope::string &ident) anope_override + { + if (ident.empty() || ident.length() > Config->GetBlock("networkinfo")->Get("userlen")) + return false; + + for (unsigned i = 0; i < ident.length(); ++i) + { + const char &c = ident[i]; + + if (c >= 'A' && c <= '}') + continue; + + if ((c >= '0' && c <= '9') || c == '-' || c == '.') + continue; + + return false; + } + + return true; + } +}; + +class InspIRCdExtBan : public ChannelModeList +{ + public: + InspIRCdExtBan(const Anope::string &mname, char modeChar) : ChannelModeList(mname, modeChar) { } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + + if (mask.find("m:") == 0 || mask.find("N:") == 0) + { + Anope::string real_mask = mask.substr(2); + + Entry en(this->name, real_mask); + if (en.Matches(u)) + return true; + } + else if (mask.find("j:") == 0) + { + Anope::string real_mask = mask.substr(2); + + Channel *c = Channel::Find(real_mask); + if (c != NULL && c->FindUser(u) != NULL) + return true; + } + else if (mask.find("M:") == 0 || mask.find("R:") == 0) + { + Anope::string real_mask = mask.substr(2); + + if (u->IsIdentified() && real_mask.equals_ci(u->Account()->display)) + return true; + } + else if (mask.find("r:") == 0) + { + Anope::string real_mask = mask.substr(2); + + if (Anope::Match(u->realname, real_mask)) + return true; + } + else if (mask.find("s:") == 0) + { + Anope::string real_mask = mask.substr(2); + + if (Anope::Match(u->server->GetName(), real_mask)) + return true; + } + + return false; + } +}; + +struct IRCDMessageCapab : Message::Capab +{ + IRCDMessageCapab(Module *creator) : Message::Capab(creator, "CAPAB") { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params[0].equals_cs("START")) + { + /* reset CAPAB */ + Servers::Capab.clear(); + Servers::Capab.insert("NOQUIT"); + IRCD->CanSVSHold = false; + } + else if (params[0].equals_cs("MODULES") && params.size() > 1) + { + if (params[1].find("m_globops.so") != Anope::string::npos) + Servers::Capab.insert("GLOBOPS"); + if (params[1].find("m_services_account.so") != Anope::string::npos) + Servers::Capab.insert("SERVICES"); + if (params[1].find("m_svshold.so") != Anope::string::npos) + IRCD->CanSVSHold = true; + if (params[1].find("m_chghost.so") != Anope::string::npos) + Servers::Capab.insert("CHGHOST"); + if (params[1].find("m_chgident.so") != Anope::string::npos) + Servers::Capab.insert("CHGIDENT"); + if (params[1].find("m_hidechans.so") != Anope::string::npos) + Servers::Capab.insert("HIDECHANS"); + if (params[1].find("m_servprotect.so") != Anope::string::npos) + IRCD->DefaultPseudoclientModes = "+Ik"; + if (params[1].find("m_rline.so") != Anope::string::npos) + Servers::Capab.insert("RLINE"); + } + else if (params[0].equals_cs("CAPABILITIES") && params.size() > 1) + { + spacesepstream ssep(params[1]); + Anope::string capab; + while (ssep.GetToken(capab)) + { + if (capab.find("CHANMODES") != Anope::string::npos) + { + Anope::string modes(capab.begin() + 10, capab.end()); + commasepstream sep(modes); + Anope::string modebuf; + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'b': + ModeManager::AddChannelMode(new InspIRCdExtBan("BAN", 'b')); + continue; + case 'e': + ModeManager::AddChannelMode(new InspIRCdExtBan("EXCEPT", 'e')); + continue; + case 'I': + ModeManager::AddChannelMode(new InspIRCdExtBan("INVITEOVERRIDE", 'I')); + continue; + /* InspIRCd sends q and a here if they have no prefixes */ + case 'q': + ModeManager::AddChannelMode(new ChannelModeStatus("OWNER", 'q', '@', 4)); + continue; + case 'a': + ModeManager::AddChannelMode(new ChannelModeStatus("PROTECT" , 'a', '@', 3)); + continue; + default: + ModeManager::AddChannelMode(new ChannelModeList("", modebuf[t])); + } + } + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'k': + ModeManager::AddChannelMode(new ChannelModeKey('k')); + continue; + default: + ModeManager::AddChannelMode(new ChannelModeParam("", modebuf[t])); + } + } + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'F': + ModeManager::AddChannelMode(new ChannelModeParam("NICKFLOOD", 'F', true)); + continue; + case 'J': + ModeManager::AddChannelMode(new ChannelModeParam("NOREJOIN", 'J', true)); + continue; + case 'L': + ModeManager::AddChannelMode(new ChannelModeParam("REDIRECT", 'L', true)); + continue; + case 'f': + ModeManager::AddChannelMode(new ChannelModeFlood('f', true)); + continue; + case 'j': + ModeManager::AddChannelMode(new ChannelModeParam("JOINFLOOD", 'j', true)); + continue; + case 'l': + ModeManager::AddChannelMode(new ChannelModeParam("LIMIT", 'l', true)); + continue; + default: + ModeManager::AddChannelMode(new ChannelModeParam("", modebuf[t], true)); + } + } + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'A': + ModeManager::AddChannelMode(new ChannelMode("ALLINVITE", 'A')); + continue; + case 'B': + ModeManager::AddChannelMode(new ChannelMode("BLOCKCAPS", 'B')); + continue; + case 'C': + ModeManager::AddChannelMode(new ChannelMode("NOCTCP", 'C')); + continue; + case 'D': + ModeManager::AddChannelMode(new ChannelMode("DELAYEDJOIN", 'D')); + continue; + case 'G': + ModeManager::AddChannelMode(new ChannelMode("CENSOR", 'G')); + continue; + case 'K': + ModeManager::AddChannelMode(new ChannelMode("NOKNOCK", 'K')); + continue; + case 'M': + ModeManager::AddChannelMode(new ChannelMode("REGMODERATED", 'M')); + continue; + case 'N': + ModeManager::AddChannelMode(new ChannelMode("NONICK", 'N')); + continue; + case 'O': + ModeManager::AddChannelMode(new ChannelModeOperOnly("OPERONLY", 'O')); + continue; + case 'P': + ModeManager::AddChannelMode(new ChannelMode("PERM", 'P')); + continue; + case 'Q': + ModeManager::AddChannelMode(new ChannelMode("NOKICK", 'Q')); + continue; + case 'R': + ModeManager::AddChannelMode(new ChannelMode("REGISTEREDONLY", 'R')); + continue; + case 'S': + ModeManager::AddChannelMode(new ChannelMode("STRIPCOLOR", 'S')); + continue; + case 'T': + ModeManager::AddChannelMode(new ChannelMode("NONOTICE", 'T')); + continue; + case 'c': + ModeManager::AddChannelMode(new ChannelMode("BLOCKCOLOR", 'c')); + continue; + case 'i': + ModeManager::AddChannelMode(new ChannelMode("INVITE", 'i')); + continue; + case 'm': + ModeManager::AddChannelMode(new ChannelMode("MODERATED", 'm')); + continue; + case 'n': + ModeManager::AddChannelMode(new ChannelMode("NOEXTERNAL", 'n')); + continue; + case 'p': + ModeManager::AddChannelMode(new ChannelMode("PRIVATE", 'p')); + continue; + case 'r': + ModeManager::AddChannelMode(new ChannelModeNoone("REGISTERED", 'r')); + continue; + case 's': + ModeManager::AddChannelMode(new ChannelMode("SECRET", 's')); + continue; + case 't': + ModeManager::AddChannelMode(new ChannelMode("TOPIC", 't')); + continue; + case 'u': + ModeManager::AddChannelMode(new ChannelMode("AUDITORIUM", 'u')); + continue; + case 'z': + ModeManager::AddChannelMode(new ChannelMode("SSL", 'z')); + continue; + default: + ModeManager::AddChannelMode(new ChannelMode("", modebuf[t])); + } + } + } + else if (capab.find("USERMODES") != Anope::string::npos) + { + Anope::string modes(capab.begin() + 10, capab.end()); + commasepstream sep(modes); + Anope::string modebuf; + + while (sep.GetToken(modebuf)) + { + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'h': + ModeManager::AddUserMode(new UserModeOperOnly("HELPOP", 'h')); + continue; + case 'B': + ModeManager::AddUserMode(new UserMode("BOT", 'B')); + continue; + case 'G': + ModeManager::AddUserMode(new UserMode("CENSOR", 'G')); + continue; + case 'H': + ModeManager::AddUserMode(new UserModeOperOnly("HIDEOPER", 'H')); + continue; + case 'I': + ModeManager::AddUserMode(new UserMode("PRIV", 'I')); + continue; + case 'Q': + ModeManager::AddUserMode(new UserModeOperOnly("HIDDEN", 'Q')); + continue; + case 'R': + ModeManager::AddUserMode(new UserMode("REGPRIV", 'R')); + continue; + case 'S': + ModeManager::AddUserMode(new UserMode("STRIPCOLOR", 'S')); + continue; + case 'W': + ModeManager::AddUserMode(new UserMode("WHOIS", 'W')); + continue; + case 'c': + ModeManager::AddUserMode(new UserMode("COMMONCHANS", 'c')); + continue; + case 'g': + ModeManager::AddUserMode(new UserMode("CALLERID", 'g')); + continue; + case 'i': + ModeManager::AddUserMode(new UserMode("INVIS", 'i')); + continue; + case 'k': + ModeManager::AddUserMode(new UserModeNoone("PROTECTED", 'k')); + continue; + case 'o': + ModeManager::AddUserMode(new UserModeOperOnly("OPER", 'o')); + continue; + case 'r': + ModeManager::AddUserMode(new UserModeNoone("REGISTERED", 'r')); + continue; + case 'w': + ModeManager::AddUserMode(new UserMode("WALLOPS", 'w')); + continue; + case 'x': + ModeManager::AddUserMode(new UserMode("CLOAK", 'x')); + continue; + case 'd': + ModeManager::AddUserMode(new UserMode("DEAF", 'd')); + continue; + default: + ModeManager::AddUserMode(new UserMode("", modebuf[t])); + } + } + } + } + else if (capab.find("PREFIX=(") != Anope::string::npos) + { + Anope::string modes(capab.begin() + 8, capab.begin() + capab.find(')')); + Anope::string chars(capab.begin() + capab.find(')') + 1, capab.end()); + unsigned short level = modes.length() - 1; + + for (size_t t = 0, end = modes.length(); t < end; ++t) + { + switch (modes[t]) + { + case 'q': + ModeManager::AddChannelMode(new ChannelModeStatus("OWNER", 'q', chars[t], level--)); + continue; + case 'a': + ModeManager::AddChannelMode(new ChannelModeStatus("PROTECT", 'a', chars[t], level--)); + continue; + case 'o': + ModeManager::AddChannelMode(new ChannelModeStatus("OP", 'o', chars[t], level--)); + continue; + case 'h': + ModeManager::AddChannelMode(new ChannelModeStatus("HALFOP", 'h', chars[t], level--)); + continue; + case 'v': + ModeManager::AddChannelMode(new ChannelModeStatus("VOICE", 'v', chars[t], level--)); + continue; + default: + ModeManager::AddChannelMode(new ChannelModeStatus("", modes[t], chars[t], level--)); + } + } + + ModeManager::RebuildStatusModes(); + } + else if (capab.find("MAXMODES=") != Anope::string::npos) + { + Anope::string maxmodes(capab.begin() + 9, capab.end()); + IRCD->MaxModes = maxmodes.is_pos_number_only() ? convertTo(maxmodes) : 3; + } + } + } + else if (params[0].equals_cs("END")) + { + if (!Servers::Capab.count("GLOBOPS")) + { + UplinkSocket::Message() << "ERROR :m_globops is not loaded. This is required by Anope"; + Anope::QuitReason = "Remote server does not have the m_globops module loaded, and this is required."; + Anope::Quitting = true; + return; + } + if (!Servers::Capab.count("SERVICES")) + { + UplinkSocket::Message() << "ERROR :m_services_account.so is not loaded. This is required by Anope"; + Anope::QuitReason = "ERROR: Remote server does not have the m_services_account module loaded, and this is required."; + Anope::Quitting = true; + return; + } + if (!Servers::Capab.count("HIDECHANS")) + { + UplinkSocket::Message() << "ERROR :m_hidechans.so is not loaded. This is required by Anope"; + Anope::QuitReason = "ERROR: Remote server does not have the m_hidechans module loaded, and this is required."; + Anope::Quitting = true; + return; + } + if (!IRCD->CanSVSHold) + Log() << "SVSHOLD missing, Usage disabled until module is loaded."; + if (!Servers::Capab.count("CHGHOST")) + Log() << "CHGHOST missing, Usage disabled until module is loaded."; + if (!Servers::Capab.count("CHGIDENT")) + Log() << "CHGIDENT missing, Usage disabled until module is loaded."; + } + + Message::Capab::Run(source, params); + } +}; + +struct IRCDMessageChgIdent : IRCDMessage +{ + IRCDMessageChgIdent(Module *creator) : IRCDMessage(creator, "CHGIDENT", 2) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = User::Find(params[0]); + if (u) + u->SetIdent(params[1]); + } +}; + +struct IRCDMessageChgName : IRCDMessage +{ + IRCDMessageChgName(Module *creator, const Anope::string &n) : IRCDMessage(creator, n, 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetUser()->SetRealname(params[0]); + } +}; + +struct IRCDMessageEncap : IRCDMessage +{ + IRCDMessageEncap(Module *creator) : IRCDMessage(creator, "ENCAP", 4) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (!Anope::Match(Me->GetSID(), params[0]) && !Anope::Match(Me->GetName(), params[0])) + return; + + if (SASL::sasl && params[1] == "SASL" && params.size() >= 6) + { + SASL::Message m; + m.source = params[2]; + m.target = params[3]; + m.type = params[4]; + m.data = params[5]; + m.ext = params.size() > 6 ? params[6] : ""; + + SASL::sasl->ProcessMessage(m); + } + } +}; + +struct IRCDMessageEndburst : IRCDMessage +{ + IRCDMessageEndburst(Module *creator) : IRCDMessage(creator, "ENDBURST", 0) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Server *s = source.GetServer(); + + Log(LOG_DEBUG) << "Processed ENDBURST for " << s->GetName(); + + s->Sync(true); + } +}; + +struct IRCDMessageFHost : IRCDMessage +{ + IRCDMessageFHost(Module *creator, const Anope::string &n) : IRCDMessage(creator, n, 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetUser()->SetDisplayedHost(params[0]); + } +}; + +struct IRCDMessageFJoin : IRCDMessage +{ + IRCDMessageFJoin(Module *creator) : IRCDMessage(creator, "FJOIN", 2) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Anope::string modes; + if (params.size() >= 3) + { + for (unsigned i = 2; i < params.size() - 1; ++i) + modes += " " + params[i]; + if (!modes.empty()) + modes.erase(modes.begin()); + } + + std::list users; + + spacesepstream sep(params[params.size() - 1]); + Anope::string buf; + while (sep.GetToken(buf)) + { + Message::Join::SJoinUser sju; + + /* Loop through prefixes and find modes for them */ + for (char c; (c = buf[0]) != ',' && c;) + { + buf.erase(buf.begin()); + sju.first.AddMode(c); + } + /* Erase the , */ + if (!buf.empty()) + buf.erase(buf.begin()); + + sju.second = User::Find(buf); + if (!sju.second) + { + Log(LOG_DEBUG) << "FJOIN for nonexistent user " << buf << " on " << params[0]; + continue; + } + + users.push_back(sju); + } + + time_t ts = Anope::string(params[1]).is_pos_number_only() ? convertTo(params[1]) : Anope::CurTime; + Message::Join::SJoin(source, params[0], ts, modes, users); + } +}; + +struct IRCDMessageFMode : IRCDMessage +{ + IRCDMessageFMode(Module *creator) : IRCDMessage(creator, "FMODE", 3) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + /* :source FMODE #test 12345678 +nto foo */ + + Anope::string modes = params[2]; + for (unsigned n = 3; n < params.size(); ++n) + modes += " " + params[n]; + + Channel *c = Channel::Find(params[0]); + time_t ts; + + try + { + ts = convertTo(params[1]); + } + catch (const ConvertException &) + { + ts = 0; + } + + if (c) + c->SetModesInternal(source, modes, ts); + } +}; + +struct IRCDMessageFTopic : IRCDMessage +{ + IRCDMessageFTopic(Module *creator) : IRCDMessage(creator, "FTOPIC", 4) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + /* :source FTOPIC channel topicts setby :topic */ + + Channel *c = Channel::Find(params[0]); + if (c) + c->ChangeTopicInternal(NULL, params[2], params[3], Anope::string(params[1]).is_pos_number_only() ? convertTo(params[1]) : Anope::CurTime); + } +}; + +struct IRCDMessageIdle : IRCDMessage +{ + IRCDMessageIdle(Module *creator) : IRCDMessage(creator, "IDLE", 1) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + BotInfo *bi = BotInfo::Find(params[0]); + if (bi) + UplinkSocket::Message(bi) << "IDLE " << source.GetSource() << " " << Anope::StartTime << " " << (Anope::CurTime - bi->lastmsg); + else + { + User *u = User::Find(params[0]); + if (u && u->server == Me) + UplinkSocket::Message(u) << "IDLE " << source.GetSource() << " " << Anope::StartTime << " 0"; + } + } +}; + +/* + * source = numeric of the sending server + * params[0] = uuid + * params[1] = metadata name + * params[2] = data + */ +struct IRCDMessageMetadata : IRCDMessage +{ + IRCDMessageMetadata(Module *creator) : IRCDMessage(creator, "METADATA", 3) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (isdigit(params[0][0])) + { + if (params[1].equals_cs("accountname")) + { + User *u = User::Find(params[0]); + NickCore *nc = NickCore::Find(params[2]); + if (u && nc) + u->Login(nc); + } + + /* + * possible incoming ssl_cert messages: + * Received: :409 METADATA 409AAAAAA ssl_cert :vTrSe c38070ce96e41cc144ed6590a68d45a6 <...> <...> + * Received: :409 METADATA 409AAAAAC ssl_cert :vTrSE Could not get peer certificate: error:00000000:lib(0):func(0):reason(0) + */ + else if (params[1].equals_cs("ssl_cert")) + { + User *u = User::Find(params[0]); + if (!u) + return; + u->Extend("ssl"); + Anope::string data = params[2].c_str(); + size_t pos1 = data.find(' ') + 1; + size_t pos2 = data.find(' ', pos1); + if ((pos2 - pos1) >= 32) // inspircd supports md5 and sha1 fingerprint hashes -> size 32 or 40 bytes. + { + u->fingerprint = data.substr(pos1, pos2 - pos1); + } + FOREACH_MOD(OnFingerprint, (u)); + } + } + else if (params[0][0] == '#') + { + } + else if (params[0] == "*") + { + // Wed Oct 3 15:40:27 2012: S[14] O :20D METADATA * modules :-m_svstopic.so + + if (params[1].equals_cs("modules") && !params[2].empty()) + { + // only interested when it comes from our uplink + Server* server = source.GetServer(); + if (!server || server->GetUplink() != Me) + return; + + bool plus = (params[2][0] == '+'); + if (!plus && params[2][0] != '-') + return; + + bool required = false; + Anope::string capab, module = params[2].substr(1); + + if (module.equals_cs("m_services_account.so")) + required = true; + else if (module.equals_cs("m_hidechans.so")) + required = true; + else if (module.equals_cs("m_chghost.so")) + capab = "CHGHOST"; + else if (module.equals_cs("m_chgident.so")) + capab = "CHGIDENT"; + else if (module.equals_cs("m_svshold.so")) + capab = "SVSHOLD"; + else if (module.equals_cs("m_rline.so")) + capab = "RLINE"; + else if (module.equals_cs("m_topiclock.so")) + capab = "TOPICLOCK"; + else + return; + + if (required) + { + if (!plus) + Log() << "Warning: InspIRCd unloaded module " << module << ", Anope won't function correctly without it"; + } + else + { + if (plus) + Servers::Capab.insert(capab); + else + Servers::Capab.erase(capab); + + Log() << "InspIRCd " << (plus ? "loaded" : "unloaded") << " module " << module << ", adjusted functionality"; + } + + } + } + } +}; + +struct IRCDMessageMode : IRCDMessage +{ + IRCDMessageMode(Module *creator) : IRCDMessage(creator, "MODE", 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (IRCD->IsChannelValid(params[0])) + { + Channel *c = Channel::Find(params[0]); + + Anope::string modes = params[1]; + for (unsigned n = 2; n < params.size(); ++n) + modes += " " + params[n]; + + if (c) + c->SetModesInternal(source, modes); + } + else + { + /* InspIRCd lets opers change another + users modes, we have to kludge this + as it slightly breaks RFC1459 + */ + User *u = User::Find(params[0]); + if (u) + u->SetModesInternal(source, "%s", params[1].c_str()); + } + } +}; + +struct IRCDMessageNick : IRCDMessage +{ + IRCDMessageNick(Module *creator) : IRCDMessage(creator, "NICK", 2) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetUser()->ChangeNick(params[0]); + } +}; + +struct IRCDMessageOperType : IRCDMessage +{ + IRCDMessageOperType(Module *creator) : IRCDMessage(creator, "OPERTYPE", 0) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + /* opertype is equivalent to mode +o because servers + don't do this directly */ + User *u = source.GetUser(); + if (!u->HasMode("OPER")) + u->SetModesInternal(source, "+o"); + } +}; + +struct IRCDMessageRSQuit : IRCDMessage +{ + IRCDMessageRSQuit(Module *creator) : IRCDMessage(creator, "RSQUIT", 1) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Server *s = Server::Find(params[0]); + const Anope::string &reason = params.size() > 1 ? params[1] : ""; + if (!s) + return; + + UplinkSocket::Message(Me) << "SQUIT " << s->GetSID() << " :" << reason; + s->Delete(s->GetName() + " " + s->GetUplink()->GetName()); + } +}; + +struct IRCDMessageSetIdent : IRCDMessage +{ + IRCDMessageSetIdent(Module *creator) : IRCDMessage(creator, "SETIDENT", 0) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetUser()->SetIdent(params[0]); + } +}; + +struct IRCDMessageServer : IRCDMessage +{ + IRCDMessageServer(Module *creator) : IRCDMessage(creator, "SERVER", 5) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + /* + * [Nov 04 00:08:46.308435 2009] debug: Received: SERVER irc.inspircd.com pass 0 964 :Testnet Central! + * 0: name + * 1: pass + * 2: hops + * 3: numeric + * 4: desc + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + unsigned int hops = Anope::string(params[2]).is_pos_number_only() ? convertTo(params[2]) : 0; + new Server(source.GetServer() == NULL ? Me : source.GetServer(), params[0], hops, params[4], params[3]); + } +}; + +struct IRCDMessageSQuit : Message::SQuit +{ + IRCDMessageSQuit(Module *creator) : Message::SQuit(creator) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params[0] == rsquit_id || params[0] == rsquit_server) + { + /* squit for a recently squit server, introduce the juped server now */ + Server *s = Server::Find(rsquit_server); + + rsquit_id.clear(); + rsquit_server.clear(); + + if (s && s->IsJuped()) + IRCD->SendServer(s); + } + else + Message::SQuit::Run(source, params); + } +}; + +struct IRCDMessageTime : IRCDMessage +{ + IRCDMessageTime(Module *creator) : IRCDMessage(creator, "TIME", 2) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + UplinkSocket::Message(Me) << "TIME " << source.GetSource() << " " << params[1] << " " << Anope::CurTime; + } +}; + +struct IRCDMessageUID : IRCDMessage +{ + IRCDMessageUID(Module *creator) : IRCDMessage(creator, "UID", 8) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* + * [Nov 03 22:09:58.176252 2009] debug: Received: :964 UID 964AAAAAC 1225746297 w00t2 localhost testnet.user w00t 127.0.0.1 1225746302 +iosw +ACGJKLNOQcdfgjklnoqtx :Robin Burchell + * 0: uid + * 1: ts + * 2: nick + * 3: host + * 4: dhost + * 5: ident + * 6: ip + * 7: signon + * 8+: modes and params -- IMPORTANT, some modes (e.g. +s) may have parameters. So don't assume a fixed position of realname! + * last: realname + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + time_t ts = convertTo(params[1]); + + Anope::string modes = params[8]; + for (unsigned i = 9; i < params.size() - 1; ++i) + modes += " " + params[i]; + + NickAlias *na = NULL; + if (SASL::sasl) + for (std::list::iterator it = saslusers.begin(); it != saslusers.end();) + { + SASLUser &u = *it; + + if (u.created + 30 < Anope::CurTime) + it = saslusers.erase(it); + else if (u.uid == params[0]) + { + na = NickAlias::Find(u.acc); + it = saslusers.erase(it); + } + else + ++it; + } + + User *u = User::OnIntroduce(params[2], params[5], params[3], params[4], params[6], source.GetServer(), params[params.size() - 1], ts, modes, params[0], na ? *na->nc : NULL); + if (u) + u->signon = convertTo(params[7]); + } +}; + +class ProtoInspIRCd12 : public Module +{ + InspIRCd12Proto ircd_proto; + ExtensibleItem ssl; + + /* Core message handlers */ + Message::Away message_away; + Message::Error message_error; + Message::Invite message_invite; + Message::Join message_join; + Message::Kick message_kick; + Message::Kill message_kill; + Message::MOTD message_motd; + Message::Notice message_notice; + Message::Part message_part; + Message::Ping message_ping; + Message::Privmsg message_privmsg; + Message::Quit message_quit; + Message::Stats message_stats; + Message::Topic message_topic; + + /* Our message handlers */ + IRCDMessageChgIdent message_chgident; + IRCDMessageChgName message_setname, message_chgname; + IRCDMessageCapab message_capab; + IRCDMessageEncap message_encap; + IRCDMessageEndburst message_endburst; + IRCDMessageFHost message_fhost, message_sethost; + IRCDMessageFJoin message_fjoin; + IRCDMessageFMode message_fmode; + IRCDMessageFTopic message_ftopic; + IRCDMessageIdle message_idle; + IRCDMessageMetadata message_metadata; + IRCDMessageMode message_mode; + IRCDMessageNick message_nick; + IRCDMessageOperType message_opertype; + IRCDMessageRSQuit message_rsquit; + IRCDMessageSetIdent message_setident; + IRCDMessageServer message_server; + IRCDMessageSQuit message_squit; + IRCDMessageTime message_time; + IRCDMessageUID message_uid; + + public: + ProtoInspIRCd12(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PROTOCOL | VENDOR), + ircd_proto(this), ssl(this, "ssl"), + message_away(this), message_error(this), message_invite(this), message_join(this), message_kick(this), message_kill(this), + message_motd(this), message_notice(this), message_part(this), message_ping(this), message_privmsg(this), message_quit(this), + message_stats(this), message_topic(this), + + message_chgident(this), message_setname(this, "SETNAME"), message_chgname(this, "FNAME"), message_capab(this), message_encap(this), + message_endburst(this), + message_fhost(this, "FHOST"), message_sethost(this, "SETHOST"), message_fjoin(this), message_fmode(this), message_ftopic(this), + message_idle(this), message_metadata(this), message_mode(this), message_nick(this), message_opertype(this), message_rsquit(this), + message_setident(this), message_server(this), message_squit(this), message_time(this), message_uid(this) + { + Servers::Capab.insert("NOQUIT"); + } + + void OnUserNickChange(User *u, const Anope::string &) anope_override + { + /* InspIRCd 1.2 doesn't set -r on nick change, remove -r here. Note that if we have to set +r later + * this will cancel out this -r, resulting in no mode changes. + * + * Do not set -r if we don't have a NickServ loaded - DP + */ + BotInfo *NickServ = Config->GetClient("NickServ"); + if (NickServ) + u->RemoveMode(NickServ, "REGISTERED"); + } +}; + +MODULE_INIT(ProtoInspIRCd12) diff --git a/modules/protocol/inspircd20.cpp b/modules/protocol/inspircd20.cpp new file mode 100644 index 0000000..2ccb94f --- /dev/null +++ b/modules/protocol/inspircd20.cpp @@ -0,0 +1,1106 @@ +/* InspIRCd 2.0 functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/cs_mode.h" + +static unsigned int spanningtree_proto_ver = 0; + +static ServiceReference insp12("IRCDProto", "inspircd12"); + +class InspIRCd20Proto : public IRCDProto +{ + public: + InspIRCd20Proto(Module *creator) : IRCDProto(creator, "InspIRCd 2.0") + { + DefaultPseudoclientModes = "+I"; + CanSVSNick = true; + CanSVSJoin = true; + CanSetVHost = true; + CanSetVIdent = true; + CanSQLine = true; + CanSZLine = true; + CanSVSHold = true; + CanCertFP = true; + RequiresID = true; + MaxModes = 20; + } + + void SendConnect() anope_override + { + UplinkSocket::Message() << "CAPAB START 1202"; + UplinkSocket::Message() << "CAPAB CAPABILITIES :PROTOCOL=1202"; + UplinkSocket::Message() << "CAPAB END"; + insp12->SendConnect(); + } + + void SendSASLMechanisms(std::vector &mechanisms) anope_override + { + Anope::string mechlist; + for (unsigned i = 0; i < mechanisms.size(); ++i) + mechlist += "," + mechanisms[i]; + + UplinkSocket::Message(Me) << "METADATA * saslmechlist :" << (mechanisms.empty() ? "" : mechlist.substr(1)); + } + + void SendSVSKillInternal(const MessageSource &source, User *user, const Anope::string &buf) anope_override { insp12->SendSVSKillInternal(source, user, buf); } + void SendGlobalNotice(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override { insp12->SendGlobalNotice(bi, dest, msg); } + void SendGlobalPrivmsg(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override { insp12->SendGlobalPrivmsg(bi, dest, msg); } + void SendAkillDel(const XLine *x) anope_override { insp12->SendAkillDel(x); } + void SendTopic(const MessageSource &whosets, Channel *c) anope_override { insp12->SendTopic(whosets, c); }; + void SendVhostDel(User *u) anope_override { insp12->SendVhostDel(u); } + void SendAkill(User *u, XLine *x) anope_override { insp12->SendAkill(u, x); } + void SendNumericInternal(int numeric, const Anope::string &dest, const Anope::string &buf) anope_override { insp12->SendNumericInternal(numeric, dest, buf); } + void SendModeInternal(const MessageSource &source, const Channel *dest, const Anope::string &buf) anope_override { insp12->SendModeInternal(source, dest, buf); } + void SendClientIntroduction(User *u) anope_override { insp12->SendClientIntroduction(u); } + void SendServer(const Server *server) anope_override { insp12->SendServer(server); } + void SendSquit(Server *s, const Anope::string &message) anope_override { insp12->SendSquit(s, message); } + void SendJoin(User *user, Channel *c, const ChannelStatus *status) anope_override { insp12->SendJoin(user, c, status); } + void SendSQLineDel(const XLine *x) anope_override { insp12->SendSQLineDel(x); } + void SendSQLine(User *u, const XLine *x) anope_override { insp12->SendSQLine(u, x); } + void SendVhost(User *u, const Anope::string &vident, const Anope::string &vhost) anope_override { insp12->SendVhost(u, vident, vhost); } + void SendSVSHold(const Anope::string &nick, time_t t) anope_override { insp12->SendSVSHold(nick, t); } + void SendSVSHoldDel(const Anope::string &nick) anope_override { insp12->SendSVSHoldDel(nick); } + void SendSZLineDel(const XLine *x) anope_override { insp12->SendSZLineDel(x); } + void SendSZLine(User *u, const XLine *x) anope_override { insp12->SendSZLine(u, x); } + void SendSVSJoin(const MessageSource &source, User *u, const Anope::string &chan, const Anope::string &other) anope_override { insp12->SendSVSJoin(source, u, chan, other); } + void SendSVSPart(const MessageSource &source, User *u, const Anope::string &chan, const Anope::string ¶m) anope_override { insp12->SendSVSPart(source, u, chan, param); } + void SendSWhois(const MessageSource &bi, const Anope::string &who, const Anope::string &mask) anope_override { insp12->SendSWhois(bi, who, mask); } + void SendBOB() anope_override { insp12->SendBOB(); } + void SendEOB() anope_override { insp12->SendEOB(); } + void SendGlobopsInternal(const MessageSource &source, const Anope::string &buf) { insp12->SendGlobopsInternal(source, buf); } + void SendLogin(User *u, NickAlias *na) anope_override { insp12->SendLogin(u, na); } + void SendLogout(User *u) anope_override { insp12->SendLogout(u); } + void SendChannel(Channel *c) anope_override { insp12->SendChannel(c); } + void SendSASLMessage(const SASL::Message &message) anope_override { insp12->SendSASLMessage(message); } + void SendSVSLogin(const Anope::string &uid, const Anope::string &acc, const Anope::string &vident, const Anope::string &vhost) anope_override { insp12->SendSVSLogin(uid, acc, vident, vhost); } + bool IsExtbanValid(const Anope::string &mask) anope_override { return insp12->IsExtbanValid(mask); } + bool IsIdentValid(const Anope::string &ident) anope_override { return insp12->IsIdentValid(ident); } +}; + +class InspIRCdAutoOpMode : public ChannelModeList +{ + public: + InspIRCdAutoOpMode(char mode) : ChannelModeList("AUTOOP", mode) + { + } + + bool IsValid(Anope::string &mask) const anope_override + { + // We can not validate this because we don't know about the + // privileges of the setter so just reject attempts to set it. + return false; + } +}; + +class InspIRCdExtBan : public ChannelModeVirtual +{ + char ext; + + public: + InspIRCdExtBan(const Anope::string &mname, const Anope::string &basename, char extban) : ChannelModeVirtual(mname, basename) + , ext(extban) + { + } + + ChannelMode *Wrap(Anope::string ¶m) anope_override + { + param = Anope::string(ext) + ":" + param; + return ChannelModeVirtual::Wrap(param); + } + + ChannelMode *Unwrap(ChannelMode *cm, Anope::string ¶m) anope_override + { + if (cm->type != MODE_LIST || param.length() < 3 || param[0] != ext || param[1] != ':') + return cm; + + param = param.substr(2); + return this; + } +}; + +namespace InspIRCdExtban +{ + class EntryMatcher : public InspIRCdExtBan + { + public: + EntryMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(3); + + return Entry(this->name, real_mask).Matches(u); + } + }; + + class ChannelMatcher : public InspIRCdExtBan + { + public: + ChannelMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + + Anope::string channel = mask.substr(3); + + ChannelMode *cm = NULL; + if (channel[0] != '#') + { + char modeChar = ModeManager::GetStatusChar(channel[0]); + channel.erase(channel.begin()); + cm = ModeManager::FindChannelModeByChar(modeChar); + if (cm != NULL && cm->type != MODE_STATUS) + cm = NULL; + } + + Channel *c = Channel::Find(channel); + if (c != NULL) + { + ChanUserContainer *uc = c->FindUser(u); + if (uc != NULL) + if (cm == NULL || uc->status.HasMode(cm->mchar)) + return true; + } + + return false; + } + }; + + class AccountMatcher : public InspIRCdExtBan + { + public: + AccountMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(2); + + return u->IsIdentified() && real_mask.equals_ci(u->Account()->display); + } + }; + + class RealnameMatcher : public InspIRCdExtBan + { + public: + RealnameMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(2); + return Anope::Match(u->realname, real_mask); + } + }; + + class ServerMatcher : public InspIRCdExtBan + { + public: + ServerMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(2); + return Anope::Match(u->server->GetName(), real_mask); + } + }; + + class FingerprintMatcher : public InspIRCdExtBan + { + public: + FingerprintMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(2); + return !u->fingerprint.empty() && Anope::Match(u->fingerprint, real_mask); + } + }; + + class UnidentifiedMatcher : public InspIRCdExtBan + { + public: + UnidentifiedMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(2); + return !u->Account() && Entry("BAN", real_mask).Matches(u); + } + }; +} + +class ColonDelimitedParamMode : public ChannelModeParam +{ + public: + ColonDelimitedParamMode(const Anope::string &modename, char modeChar) : ChannelModeParam(modename, modeChar, true) { } + + bool IsValid(Anope::string &value) const anope_override + { + return IsValid(value, false); + } + + bool IsValid(const Anope::string &value, bool historymode) const + { + if (value.empty()) + return false; // empty param is never valid + + Anope::string::size_type pos = value.find(':'); + if ((pos == Anope::string::npos) || (pos == 0)) + return false; // no ':' or it's the first char, both are invalid + + Anope::string rest; + try + { + if (convertTo(value, rest, false) <= 0) + return false; // negative numbers and zero are invalid + + rest = rest.substr(1); + int n; + if (historymode) + { + // For the history mode, the part after the ':' is a duration and it + // can be in the user friendly "1d3h20m" format, make sure we accept that + n = Anope::DoTime(rest); + } + else + n = convertTo(rest); + + if (n <= 0) + return false; + } + catch (const ConvertException &e) + { + // conversion error, invalid + return false; + } + + return true; + } +}; + +class SimpleNumberParamMode : public ChannelModeParam +{ + public: + SimpleNumberParamMode(const Anope::string &modename, char modeChar) : ChannelModeParam(modename, modeChar, true) { } + + bool IsValid(Anope::string &value) const anope_override + { + if (value.empty()) + return false; // empty param is never valid + + try + { + if (convertTo(value) <= 0) + return false; + } + catch (const ConvertException &e) + { + // conversion error, invalid + return false; + } + + return true; + } +}; + +class ChannelModeFlood : public ColonDelimitedParamMode +{ + public: + ChannelModeFlood(char modeChar) : ColonDelimitedParamMode("FLOOD", modeChar) { } + + bool IsValid(Anope::string &value) const anope_override + { + // The parameter of this mode is a bit different, it may begin with a '*', + // ignore it if that's the case + Anope::string v = value[0] == '*' ? value.substr(1) : value; + return ((!value.empty()) && (ColonDelimitedParamMode::IsValid(v))); + } +}; + +class ChannelModeHistory : public ColonDelimitedParamMode +{ + public: + ChannelModeHistory(char modeChar) : ColonDelimitedParamMode("HISTORY", modeChar) { } + + bool IsValid(Anope::string &value) const anope_override + { + return (ColonDelimitedParamMode::IsValid(value, true)); + } +}; + +class ChannelModeRedirect : public ChannelModeParam +{ + public: + ChannelModeRedirect(char modeChar) : ChannelModeParam("REDIRECT", modeChar, true) { } + + bool IsValid(Anope::string &value) const anope_override + { + // The parameter of this mode is a channel, and channel names start with '#' + return ((!value.empty()) && (value[0] == '#')); + } +}; + +struct IRCDMessageAway : Message::Away +{ + IRCDMessageAway(Module *creator) : Message::Away(creator, "AWAY") { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + std::vector newparams(params); + if (newparams.size() > 1) + newparams.erase(newparams.begin()); + + Message::Away::Run(source, newparams); + } +}; + +struct IRCDMessageCapab : Message::Capab +{ + std::map chmodes, umodes; + + IRCDMessageCapab(Module *creator) : Message::Capab(creator, "CAPAB") { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params[0].equals_cs("START")) + { + if (params.size() >= 2) + spanningtree_proto_ver = (Anope::string(params[1]).is_pos_number_only() ? convertTo(params[1]) : 0); + + if (spanningtree_proto_ver < 1202) + { + UplinkSocket::Message() << "ERROR :Protocol mismatch, no or invalid protocol version given in CAPAB START"; + Anope::QuitReason = "Protocol mismatch, no or invalid protocol version given in CAPAB START"; + Anope::Quitting = true; + return; + } + + /* reset CAPAB */ + chmodes.clear(); + umodes.clear(); + Servers::Capab.insert("SERVERS"); + Servers::Capab.insert("TOPICLOCK"); + IRCD->CanSVSHold = false; + IRCD->DefaultPseudoclientModes = "+I"; + } + else if (params[0].equals_cs("CHANMODES") && params.size() > 1) + { + spacesepstream ssep(params[1]); + Anope::string capab; + + while (ssep.GetToken(capab)) + { + Anope::string modename = capab.substr(0, capab.find('=')); + Anope::string modechar = capab.substr(capab.find('=') + 1); + ChannelMode *cm = NULL; + + if (modename.equals_cs("admin")) + cm = new ChannelModeStatus("PROTECT", modechar.length() > 1 ? modechar[1] : modechar[0], modechar.length() > 1 ? modechar[0] : 0, 3); + else if (modename.equals_cs("allowinvite")) + { + cm = new ChannelMode("ALLINVITE", modechar[0]); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("INVITEBAN", "BAN", 'A')); + } + else if (modename.equals_cs("auditorium")) + cm = new ChannelMode("AUDITORIUM", modechar[0]); + else if (modename.equals_cs("autoop")) + cm = new InspIRCdAutoOpMode(modechar[0]); + else if (modename.equals_cs("ban")) + cm = new ChannelModeList("BAN", modechar[0]); + else if (modename.equals_cs("banexception")) + cm = new ChannelModeList("EXCEPT", modechar[0]); + else if (modename.equals_cs("blockcaps")) + { + cm = new ChannelMode("BLOCKCAPS", modechar[0]); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("BLOCKCAPSBAN", "BAN", 'B')); + } + else if (modename.equals_cs("blockcolor")) + { + cm = new ChannelMode("BLOCKCOLOR", modechar[0]); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("BLOCKCOLORBAN", "BAN", 'c')); + } + else if (modename.equals_cs("c_registered")) + cm = new ChannelModeNoone("REGISTERED", modechar[0]); + else if (modename.equals_cs("censor")) + cm = new ChannelMode("CENSOR", modechar[0]); + else if (modename.equals_cs("delayjoin")) + cm = new ChannelMode("DELAYEDJOIN", modechar[0]); + else if (modename.equals_cs("delaymsg")) + cm = new SimpleNumberParamMode("DELAYMSG", modechar[0]); + else if (modename.equals_cs("filter")) + cm = new ChannelModeList("FILTER", modechar[0]); + else if (modename.equals_cs("flood")) + cm = new ChannelModeFlood(modechar[0]); + else if (modename.equals_cs("founder")) + cm = new ChannelModeStatus("OWNER", modechar.length() > 1 ? modechar[1] : modechar[0], modechar.length() > 1 ? modechar[0] : 0, 4); + else if (modename.equals_cs("halfop")) + cm = new ChannelModeStatus("HALFOP", modechar.length() > 1 ? modechar[1] : modechar[0], modechar.length() > 1 ? modechar[0] : 0, 1); + else if (modename.equals_cs("history")) + cm = new ChannelModeHistory(modechar[0]); + else if (modename.equals_cs("invex")) + cm = new ChannelModeList("INVITEOVERRIDE", modechar[0]); + else if (modename.equals_cs("inviteonly")) + cm = new ChannelMode("INVITE", modechar[0]); + else if (modename.equals_cs("joinflood")) + cm = new ColonDelimitedParamMode("JOINFLOOD", modechar[0]); + else if (modename.equals_cs("key")) + cm = new ChannelModeKey(modechar[0]); + else if (modename.equals_cs("kicknorejoin")) + cm = new SimpleNumberParamMode("NOREJOIN", modechar[0]); + else if (modename.equals_cs("limit")) + cm = new ChannelModeParam("LIMIT", modechar[0], true); + else if (modename.equals_cs("moderated")) + cm = new ChannelMode("MODERATED", modechar[0]); + else if (modename.equals_cs("nickflood")) + cm = new ColonDelimitedParamMode("NICKFLOOD", modechar[0]); + else if (modename.equals_cs("noctcp")) + { + cm = new ChannelMode("NOCTCP", modechar[0]); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("NOCTCPBAN", "BAN", 'C')); + } + else if (modename.equals_cs("noextmsg")) + cm = new ChannelMode("NOEXTERNAL", modechar[0]); + else if (modename.equals_cs("nokick")) + { + cm = new ChannelMode("NOKICK", modechar[0]); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("NOKICKBAN", "BAN", 'Q')); + } + else if (modename.equals_cs("noknock")) + cm = new ChannelMode("NOKNOCK", modechar[0]); + else if (modename.equals_cs("nonick")) + { + cm = new ChannelMode("NONICK", modechar[0]); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("NONICKBAN", "BAN", 'N')); + } + else if (modename.equals_cs("nonotice")) + { + cm = new ChannelMode("NONOTICE", modechar[0]); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("NONOTICEBAN", "BAN", 'T')); + } + else if (modename.equals_cs("official-join")) + cm = new ChannelModeStatus("OFFICIALJOIN", modechar.length() > 1 ? modechar[1] : modechar[0], modechar.length() > 1 ? modechar[0] : 0, 2); + else if (modename.equals_cs("op")) + cm = new ChannelModeStatus("OP", modechar.length() > 1 ? modechar[1] : modechar[0], modechar.length() > 1 ? modechar[0] : 0, 2); + else if (modename.equals_cs("operonly")) + cm = new ChannelModeOperOnly("OPERONLY", modechar[0]); + else if (modename.equals_cs("operprefix")) + cm = new ChannelModeStatus("OPERPREFIX", modechar.length() > 1 ? modechar[1] : modechar[0], modechar.length() > 1 ? modechar[0] : 0, 2); + else if (modename.equals_cs("permanent")) + cm = new ChannelMode("PERM", modechar[0]); + else if (modename.equals_cs("private")) + cm = new ChannelMode("PRIVATE", modechar[0]); + else if (modename.equals_cs("redirect")) + cm = new ChannelModeRedirect(modechar[0]); + else if (modename.equals_cs("reginvite")) + cm = new ChannelMode("REGISTEREDONLY", modechar[0]); + else if (modename.equals_cs("regmoderated")) + cm = new ChannelMode("REGMODERATED", modechar[0]); + else if (modename.equals_cs("secret")) + cm = new ChannelMode("SECRET", modechar[0]); + else if (modename.equals_cs("sslonly")) + { + cm = new ChannelMode("SSL", modechar[0]); + ModeManager::AddChannelMode(new InspIRCdExtban::FingerprintMatcher("SSLBAN", "BAN", 'z')); + } + else if (modename.equals_cs("stripcolor")) + { + cm = new ChannelMode("STRIPCOLOR", modechar[0]); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("STRIPCOLORBAN", "BAN", 'S')); + } + else if (modename.equals_cs("topiclock")) + cm = new ChannelMode("TOPIC", modechar[0]); + else if (modename.equals_cs("voice")) + cm = new ChannelModeStatus("VOICE", modechar.length() > 1 ? modechar[1] : modechar[0], modechar.length() > 1 ? modechar[0] : 0, 0); + /* Unknown status mode, (customprefix) - add it */ + else if (modechar.length() == 2) + cm = new ChannelModeStatus(modename.upper(), modechar[1], modechar[0], -1); + /* Unknown non status mode, add it to our list for later */ + else + chmodes[modechar[0]] = modename.upper(); + + if (cm) + ModeManager::AddChannelMode(cm); + } + } + if (params[0].equals_cs("USERMODES") && params.size() > 1) + { + spacesepstream ssep(params[1]); + Anope::string capab; + + while (ssep.GetToken(capab)) + { + Anope::string modename = capab.substr(0, capab.find('=')); + Anope::string modechar = capab.substr(capab.find('=') + 1); + UserMode *um = NULL; + + if (modename.equals_cs("bot")) + { + um = new UserMode("BOT", modechar[0]); + IRCD->DefaultPseudoclientModes += modechar; + } + else if (modename.equals_cs("callerid")) + um = new UserMode("CALLERID", modechar[0]); + else if (modename.equals_cs("cloak")) + um = new UserMode("CLOAK", modechar[0]); + else if (modename.equals_cs("deaf")) + um = new UserMode("DEAF", modechar[0]); + else if (modename.equals_cs("deaf_commonchan")) + um = new UserMode("COMMONCHANS", modechar[0]); + else if (modename.equals_cs("helpop")) + um = new UserModeOperOnly("HELPOP", modechar[0]); + else if (modename.equals_cs("hidechans")) + um = new UserMode("PRIV", modechar[0]); + else if (modename.equals_cs("hideoper")) + um = new UserModeOperOnly("HIDEOPER", modechar[0]); + else if (modename.equals_cs("invisible")) + um = new UserMode("INVIS", modechar[0]); + else if (modename.equals_cs("invis-oper")) + um = new UserModeOperOnly("INVISIBLE_OPER", modechar[0]); + else if (modename.equals_cs("oper")) + um = new UserModeOperOnly("OPER", modechar[0]); + else if (modename.equals_cs("regdeaf")) + um = new UserMode("REGPRIV", modechar[0]); + else if (modename.equals_cs("servprotect")) + { + um = new UserModeNoone("PROTECTED", modechar[0]); + IRCD->DefaultPseudoclientModes += modechar; + } + else if (modename.equals_cs("showwhois")) + um = new UserMode("WHOIS", modechar[0]); + else if (modename.equals_cs("u_censor")) + um = new UserMode("CENSOR", modechar[0]); + else if (modename.equals_cs("u_registered")) + um = new UserModeNoone("REGISTERED", modechar[0]); + else if (modename.equals_cs("u_stripcolor")) + um = new UserMode("STRIPCOLOR", modechar[0]); + else if (modename.equals_cs("wallops")) + um = new UserMode("WALLOPS", modechar[0]); + else + umodes[modechar[0]] = modename.upper(); + + if (um) + ModeManager::AddUserMode(um); + } + } + else if (params[0].equals_cs("MODULES") && params.size() > 1) + { + spacesepstream ssep(params[1]); + Anope::string module; + + while (ssep.GetToken(module)) + { + if (module.equals_cs("m_svshold.so")) + IRCD->CanSVSHold = true; + else if (module.find("m_rline.so") == 0) + { + Servers::Capab.insert("RLINE"); + const Anope::string ®exengine = Config->GetBlock("options")->Get("regexengine"); + if (!regexengine.empty() && module.length() > 11 && regexengine != module.substr(11)) + Log() << "Warning: InspIRCd is using regex engine " << module.substr(11) << ", but we have " << regexengine << ". This may cause inconsistencies."; + } + else if (module.equals_cs("m_topiclock.so")) + Servers::Capab.insert("TOPICLOCK"); + } + } + else if (params[0].equals_cs("MODSUPPORT") && params.size() > 1) + { + spacesepstream ssep(params[1]); + Anope::string module; + + while (ssep.GetToken(module)) + { + if (module.equals_cs("m_services_account.so")) + { + Servers::Capab.insert("SERVICES"); + ModeManager::AddChannelMode(new InspIRCdExtban::AccountMatcher("ACCOUNTBAN", "BAN", 'R')); + ModeManager::AddChannelMode(new InspIRCdExtban::UnidentifiedMatcher("UNREGISTEREDBAN", "BAN", 'U')); + } + else if (module.equals_cs("m_chghost.so")) + Servers::Capab.insert("CHGHOST"); + else if (module.equals_cs("m_chgident.so")) + Servers::Capab.insert("CHGIDENT"); + else if (module == "m_channelban.so") + ModeManager::AddChannelMode(new InspIRCdExtban::ChannelMatcher("CHANNELBAN", "BAN", 'j')); + else if (module == "m_gecosban.so") + ModeManager::AddChannelMode(new InspIRCdExtban::RealnameMatcher("REALNAMEBAN", "BAN", 'r')); + else if (module == "m_nopartmessage.so") + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("PARTMESSAGEBAN", "BAN", 'p')); + else if (module == "m_serverban.so") + ModeManager::AddChannelMode(new InspIRCdExtban::ServerMatcher("SERVERBAN", "BAN", 's')); + else if (module == "m_muteban.so") + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("QUIET", "BAN", 'm')); + } + } + else if (params[0].equals_cs("CAPABILITIES") && params.size() > 1) + { + spacesepstream ssep(params[1]); + Anope::string capab; + while (ssep.GetToken(capab)) + { + if (capab.find("CHANMODES") != Anope::string::npos) + { + Anope::string modes(capab.begin() + 10, capab.end()); + commasepstream sep(modes, true); + Anope::string modebuf; + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + if (ModeManager::FindChannelModeByChar(modebuf[t])) + continue; + ModeManager::AddChannelMode(new ChannelModeList(chmodes[modebuf[t]], modebuf[t])); + } + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + if (ModeManager::FindChannelModeByChar(modebuf[t])) + continue; + ModeManager::AddChannelMode(new ChannelModeParam(chmodes[modebuf[t]], modebuf[t])); + } + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + if (ModeManager::FindChannelModeByChar(modebuf[t])) + continue; + ModeManager::AddChannelMode(new ChannelModeParam(chmodes[modebuf[t]], modebuf[t], true)); + } + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + if (ModeManager::FindChannelModeByChar(modebuf[t])) + continue; + ModeManager::AddChannelMode(new ChannelMode(chmodes[modebuf[t]], modebuf[t])); + } + } + else if (capab.find("USERMODES") != Anope::string::npos) + { + Anope::string modes(capab.begin() + 10, capab.end()); + commasepstream sep(modes, true); + Anope::string modebuf; + + sep.GetToken(modebuf); + sep.GetToken(modebuf); + + if (sep.GetToken(modebuf)) + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + ModeManager::AddUserMode(new UserModeParam(umodes[modebuf[t]], modebuf[t])); + + if (sep.GetToken(modebuf)) + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + ModeManager::AddUserMode(new UserMode(umodes[modebuf[t]], modebuf[t])); + } + else if (capab.find("MAXMODES=") != Anope::string::npos) + { + Anope::string maxmodes(capab.begin() + 9, capab.end()); + IRCD->MaxModes = maxmodes.is_pos_number_only() ? convertTo(maxmodes) : 3; + } + else if (capab.find("PREFIX=") != Anope::string::npos) + { + Anope::string modes(capab.begin() + 8, capab.begin() + capab.find(')')); + Anope::string chars(capab.begin() + capab.find(')') + 1, capab.end()); + short level = modes.length() - 1; + + for (size_t t = 0, end = modes.length(); t < end; ++t) + { + ChannelMode *cm = ModeManager::FindChannelModeByChar(modes[t]); + if (cm == NULL || cm->type != MODE_STATUS) + { + Log() << "CAPAB PREFIX gave unknown channel status mode " << modes[t]; + continue; + } + + ChannelModeStatus *cms = anope_dynamic_static_cast(cm); + cms->level = level--; + + Log(LOG_DEBUG) << cms->name << " is now level " << cms->level; + } + + ModeManager::RebuildStatusModes(); + } + else if (capab == "GLOBOPS=1") + Servers::Capab.insert("GLOBOPS"); + } + } + else if (params[0].equals_cs("END")) + { + if (!Servers::Capab.count("SERVICES")) + { + UplinkSocket::Message() << "ERROR :m_services_account.so is not loaded. This is required by Anope"; + Anope::QuitReason = "ERROR: Remote server does not have the m_services_account module loaded, and this is required."; + Anope::Quitting = true; + return; + } + if (!ModeManager::FindUserModeByName("PRIV")) + { + UplinkSocket::Message() << "ERROR :m_hidechans.so is not loaded. This is required by Anope"; + Anope::QuitReason = "ERROR: Remote server does not have the m_hidechans module loaded, and this is required."; + Anope::Quitting = true; + return; + } + if (!IRCD->CanSVSHold) + Log() << "SVSHOLD missing, Usage disabled until module is loaded."; + if (!Servers::Capab.count("CHGHOST")) + Log() << "CHGHOST missing, Usage disabled until module is loaded."; + if (!Servers::Capab.count("CHGIDENT")) + Log() << "CHGIDENT missing, Usage disabled until module is loaded."; + + chmodes.clear(); + umodes.clear(); + } + + Message::Capab::Run(source, params); + } +}; + +struct IRCDMessageEncap : IRCDMessage +{ + ServiceReference insp12_encap; + + IRCDMessageEncap(Module *creator) : IRCDMessage(creator, "ENCAP", 4), insp12_encap("IRCDMessage", "inspircd12/encap") { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (!Anope::Match(Me->GetSID(), params[0]) && !Anope::Match(Me->GetName(), params[0])) + return; + + if (params[1] == "CHGIDENT") + { + User *u = User::Find(params[2]); + if (!u || u->server != Me) + return; + + u->SetIdent(params[3]); + UplinkSocket::Message(u) << "FIDENT :" << params[3]; + } + else if (params[1] == "CHGHOST") + { + User *u = User::Find(params[2]); + if (!u || u->server != Me) + return; + + u->SetDisplayedHost(params[3]); + UplinkSocket::Message(u) << "FHOST :" << params[3]; + } + else if (params[1] == "CHGNAME") + { + User *u = User::Find(params[2]); + if (!u || u->server != Me) + return; + + u->SetRealname(params[3]); + UplinkSocket::Message(u) << "FNAME :" << params[3]; + } + + if (insp12_encap) + insp12_encap->Run(source, params); + } +}; + +struct IRCDMessageFHost : IRCDMessage +{ + IRCDMessageFHost(Module *creator) : IRCDMessage(creator, "FHOST", 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + if (u->HasMode("CLOAK")) + u->RemoveModeInternal(source, ModeManager::FindUserModeByName("CLOAK")); + u->SetDisplayedHost(params[0]); + } +}; + +struct IRCDMessageFIdent : IRCDMessage +{ + IRCDMessageFIdent(Module *creator) : IRCDMessage(creator, "FIDENT", 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetUser()->SetIdent(params[0]); + } +}; + +struct IRCDMessageSave : IRCDMessage +{ + time_t last_collide; + + IRCDMessageSave(Module *creator) : IRCDMessage(creator, "SAVE", 2), last_collide(0) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *targ = User::Find(params[0]); + time_t ts; + + try + { + ts = convertTo(params[1]); + } + catch (const ConvertException &) + { + return; + } + + if (!targ || targ->timestamp != ts) + return; + + BotInfo *bi; + if (targ->server == Me && (bi = dynamic_cast(targ))) + { + if (last_collide == Anope::CurTime) + { + Anope::QuitReason = "Nick collision fight on " + targ->nick; + Anope::Quitting = true; + return; + } + + IRCD->SendKill(Me, targ->nick, "Nick collision"); + IRCD->SendNickChange(targ, targ->nick); + last_collide = Anope::CurTime; + } + else + targ->ChangeNick(targ->GetUID()); + } +}; + +class IRCDMessageMetadata : IRCDMessage +{ + ServiceReference insp12_metadata; + const bool &do_topiclock; + const bool &do_mlock; + + public: + IRCDMessageMetadata(Module *creator, const bool &handle_topiclock, const bool &handle_mlock) : IRCDMessage(creator, "METADATA", 3), insp12_metadata("IRCDMessage", "inspircd12/metadata"), do_topiclock(handle_topiclock), do_mlock(handle_mlock) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + // We deliberately ignore non-bursting servers to avoid pseudoserver fights + if ((params[0][0] == '#') && (!source.GetServer()->IsSynced())) + { + Channel *c = Channel::Find(params[0]); + if (c && c->ci) + { + if ((do_mlock) && (params[1] == "mlock")) + { + ModeLocks *modelocks = c->ci->GetExt("modelocks"); + Anope::string modes; + if (modelocks) + modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", ""); + + // Mode lock string is not what we say it is? + if (modes != params[2]) + UplinkSocket::Message(Me) << "METADATA " << c->name << " mlock :" << modes; + } + else if ((do_topiclock) && (params[1] == "topiclock")) + { + bool mystate = c->ci->HasExt("TOPICLOCK"); + bool serverstate = (params[2] == "1"); + if (mystate != serverstate) + UplinkSocket::Message(Me) << "METADATA " << c->name << " topiclock :" << (mystate ? "1" : ""); + } + } + } + + if (insp12_metadata) + insp12_metadata->Run(source, params); + } +}; + +class ProtoInspIRCd20 : public Module +{ + Module *m_insp12; + + InspIRCd20Proto ircd_proto; + + /* Core message handlers */ + Message::Error message_error; + Message::Invite message_invite; + Message::Join message_join; + Message::Kick message_kick; + Message::Kill message_kill; + Message::MOTD message_motd; + Message::Notice message_notice; + Message::Part message_part; + Message::Ping message_ping; + Message::Privmsg message_privmsg; + Message::Quit message_quit; + Message::Stats message_stats; + Message::Topic message_topic; + + /* InspIRCd 1.2 message handlers */ + ServiceAlias message_endburst, message_fjoin, message_fmode, + message_ftopic, message_idle, message_mode, + message_nick, message_opertype, message_rsquit, message_server, + message_squit, message_time, message_uid; + + /* Our message handlers */ + IRCDMessageAway message_away; + IRCDMessageCapab message_capab; + IRCDMessageEncap message_encap; + IRCDMessageFHost message_fhost; + IRCDMessageFIdent message_fident; + IRCDMessageMetadata message_metadata; + IRCDMessageSave message_save; + + bool use_server_side_topiclock, use_server_side_mlock; + + void SendChannelMetadata(Channel *c, const Anope::string &metadataname, const Anope::string &value) + { + UplinkSocket::Message(Me) << "METADATA " << c->name << " " << metadataname << " :" << value; + } + + public: + ProtoInspIRCd20(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PROTOCOL | VENDOR), + ircd_proto(this), + message_error(this), message_invite(this), message_join(this), message_kick(this), message_kill(this), + message_motd(this), message_notice(this), message_part(this), message_ping(this), message_privmsg(this), + message_quit(this), message_stats(this), message_topic(this), + + message_endburst("IRCDMessage", "inspircd20/endburst", "inspircd12/endburst"), + message_fjoin("IRCDMessage", "inspircd20/fjoin", "inspircd12/fjoin"), + message_fmode("IRCDMessage", "inspircd20/fmode", "inspircd12/fmode"), + message_ftopic("IRCDMessage", "inspircd20/ftopic", "inspircd12/ftopic"), + message_idle("IRCDMessage", "inspircd20/idle", "inspircd12/idle"), + message_mode("IRCDMessage", "inspircd20/mode", "inspircd12/mode"), + message_nick("IRCDMessage", "inspircd20/nick", "inspircd12/nick"), + message_opertype("IRCDMessage", "inspircd20/opertype", "inspircd12/opertype"), + message_rsquit("IRCDMessage", "inspircd20/rsquit", "inspircd12/rsquit"), + message_server("IRCDMessage", "inspircd20/server", "inspircd12/server"), + message_squit("IRCDMessage", "inspircd20/squit", "inspircd12/squit"), + message_time("IRCDMessage", "inspircd20/time", "inspircd12/time"), + message_uid("IRCDMessage", "inspircd20/uid", "inspircd12/uid"), + + message_away(this), message_capab(this), message_encap(this), message_fhost(this), message_fident(this), + message_metadata(this, use_server_side_topiclock, use_server_side_mlock), message_save(this) + { + + if (ModuleManager::LoadModule("inspircd12", User::Find(creator)) != MOD_ERR_OK) + throw ModuleException("Unable to load inspircd12"); + m_insp12 = ModuleManager::FindModule("inspircd12"); + if (!m_insp12) + throw ModuleException("Unable to find inspircd12"); + if (!insp12) + throw ModuleException("No protocol interface for insp12"); + ModuleManager::DetachAll(m_insp12); + + } + + ~ProtoInspIRCd20() + { + m_insp12 = ModuleManager::FindModule("inspircd12"); + ModuleManager::UnloadModule(m_insp12, NULL); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + use_server_side_topiclock = conf->GetModule(this)->Get("use_server_side_topiclock"); + use_server_side_mlock = conf->GetModule(this)->Get("use_server_side_mlock"); + } + + void OnUserNickChange(User *u, const Anope::string &) anope_override + { + u->RemoveModeInternal(Me, ModeManager::FindUserModeByName("REGISTERED")); + } + + void OnChannelSync(Channel *c) anope_override + { + if (c->ci) + this->OnChanRegistered(c->ci); + } + + void OnChanRegistered(ChannelInfo *ci) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + if (use_server_side_mlock && ci->c && modelocks && !modelocks->GetMLockAsString(false).empty()) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", ""); + SendChannelMetadata(ci->c, "mlock", modes); + } + + if (use_server_side_topiclock && Servers::Capab.count("TOPICLOCK") && ci->c) + { + if (ci->HasExt("TOPICLOCK")) + SendChannelMetadata(ci->c, "topiclock", "1"); + } + } + + void OnDelChan(ChannelInfo *ci) anope_override + { + if (use_server_side_mlock && ci->c) + SendChannelMetadata(ci->c, "mlock", ""); + + if (use_server_side_topiclock && Servers::Capab.count("TOPICLOCK") && ci->c) + SendChannelMetadata(ci->c, "topiclock", ""); + } + + EventReturn OnMLock(ChannelInfo *ci, ModeLock *lock) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + ChannelMode *cm = ModeManager::FindChannelModeByName(lock->name); + if (use_server_side_mlock && cm && ci->c && modelocks && (cm->type == MODE_REGULAR || cm->type == MODE_PARAM)) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", "") + cm->mchar; + SendChannelMetadata(ci->c, "mlock", modes); + } + + return EVENT_CONTINUE; + } + + EventReturn OnUnMLock(ChannelInfo *ci, ModeLock *lock) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + ChannelMode *cm = ModeManager::FindChannelModeByName(lock->name); + if (use_server_side_mlock && cm && ci->c && modelocks && (cm->type == MODE_REGULAR || cm->type == MODE_PARAM)) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", "").replace_all_cs(cm->mchar, ""); + SendChannelMetadata(ci->c, "mlock", modes); + } + + return EVENT_CONTINUE; + } + + EventReturn OnSetChannelOption(CommandSource &source, Command *cmd, ChannelInfo *ci, const Anope::string &setting) anope_override + { + if (cmd->name == "chanserv/topic" && ci->c) + { + if (setting == "topiclock on") + SendChannelMetadata(ci->c, "topiclock", "1"); + else if (setting == "topiclock off") + SendChannelMetadata(ci->c, "topiclock", "0"); + } + + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(ProtoInspIRCd20) diff --git a/modules/protocol/inspircd3.cpp b/modules/protocol/inspircd3.cpp new file mode 100644 index 0000000..e370db4 --- /dev/null +++ b/modules/protocol/inspircd3.cpp @@ -0,0 +1,1987 @@ +/* InspIRCd 3.0 functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/cs_mode.h" +#include "modules/sasl.h" + +typedef std::map ListLimits; + +struct SASLUser +{ + Anope::string uid; + Anope::string acc; + time_t created; +}; + +static std::list saslusers; + +static Anope::string rsquit_server, rsquit_id; + +class InspIRCd3Proto : public IRCDProto +{ + private: + void SendChgIdentInternal(const Anope::string &nick, const Anope::string &vIdent) + { + if (!Servers::Capab.count("CHGIDENT")) + Log() << "CHGIDENT not loaded!"; + else + UplinkSocket::Message(Me) << "CHGIDENT " << nick << " " << vIdent; + } + + void SendChgHostInternal(const Anope::string &nick, const Anope::string &vhost) + { + if (!Servers::Capab.count("CHGHOST")) + Log() << "CHGHOST not loaded!"; + else + UplinkSocket::Message(Me) << "CHGHOST " << nick << " " << vhost; + } + + void SendAddLine(const Anope::string &xtype, const Anope::string &mask, time_t duration, const Anope::string &addedby, const Anope::string &reason) + { + UplinkSocket::Message(Me) << "ADDLINE " << xtype << " " << mask << " " << addedby << " " << Anope::CurTime << " " << duration << " :" << reason; + } + + void SendDelLine(const Anope::string &xtype, const Anope::string &mask) + { + UplinkSocket::Message(Me) << "DELLINE " << xtype << " " << mask; + } + + public: + PrimitiveExtensibleItem maxlist; + + InspIRCd3Proto(Module *creator) : IRCDProto(creator, "InspIRCd 3"), maxlist(creator, "maxlist") + { + DefaultPseudoclientModes = "+oI"; + CanSVSNick = true; + CanSVSJoin = true; + CanSetVHost = true; + CanSetVIdent = true; + CanSQLine = true; + CanSQLineChannel = true; + CanSZLine = true; + CanSVSHold = true; + CanCertFP = true; + RequiresID = true; + MaxModes = 20; + MaxLine = 4096; + } + + unsigned GetMaxListFor(Channel *c, ChannelMode *cm) anope_override + { + ListLimits *limits = maxlist.Get(c); + if (limits) + { + ListLimits::const_iterator limit = limits->find(cm->mchar); + if (limit != limits->end()) + return limit->second; + } + + // Fall back to the config limit if we can't find the mode. + return IRCDProto::GetMaxListFor(c, cm); + } + + void SendConnect() anope_override + { + UplinkSocket::Message() << "CAPAB START 1205"; + UplinkSocket::Message() << "CAPAB CAPABILITIES :CASEMAPPING=" << Config->GetBlock("options")->Get("casemap", "ascii"); + UplinkSocket::Message() << "CAPAB END"; + UplinkSocket::Message() << "SERVER " << Me->GetName() << " " << Config->Uplinks[Anope::CurrentUplink].password << " 0 " << Me->GetSID() << " :" << Me->GetDescription(); + } + + void SendSASLMechanisms(std::vector &mechanisms) anope_override + { + Anope::string mechlist; + for (unsigned i = 0; i < mechanisms.size(); ++i) + mechlist += "," + mechanisms[i]; + + UplinkSocket::Message(Me) << "METADATA * saslmechlist :" << (mechanisms.empty() ? "" : mechlist.substr(1)); + } + + void SendSVSKillInternal(const MessageSource &source, User *user, const Anope::string &buf) anope_override + { + IRCDProto::SendSVSKillInternal(source, user, buf); + user->KillInternal(source, buf); + } + + void SendGlobalNotice(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "NOTICE $" << dest->GetName() << " :" << msg; + } + + void SendGlobalPrivmsg(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "PRIVMSG $" << dest->GetName() << " :" << msg; + } + + void SendPong(const Anope::string &servname, const Anope::string &who) anope_override + { + Server *serv = servname.empty() ? NULL : Server::Find(servname); + if (!serv) + serv = Me; + + UplinkSocket::Message(serv) << "PONG " << who; + } + + void SendAkillDel(const XLine *x) anope_override + { + { + /* InspIRCd may support regex bans + * Mask is expected in format: 'n!u@h\sr' and spaces as '\s' + * We remove the '//' and replace '#' and any ' ' with '\s' + */ + if (x->IsRegex() && Servers::Capab.count("RLINE")) + { + Anope::string mask = x->mask; + if (mask.length() >= 2 && mask[0] == '/' && mask[mask.length() - 1] == '/') + mask = mask.substr(1, mask.length() - 2); + size_t h = mask.find('#'); + if (h != Anope::string::npos) + { + mask = mask.replace(h, 1, "\\s"); + mask = mask.replace_all_cs(" ", "\\s"); + } + SendDelLine("R", mask); + return; + } + else if (x->IsRegex() || x->HasNickOrReal()) + return; + + /* ZLine if we can instead */ + if (x->GetUser() == "*") + { + cidr addr(x->GetHost()); + if (addr.valid()) + { + IRCD->SendSZLineDel(x); + return; + } + } + + SendDelLine("G", x->GetUser() + "@" + x->GetHost()); + } + } + + void SendInvite(const MessageSource &source, const Channel *c, User *u) anope_override + { + UplinkSocket::Message(source) << "INVITE " << u->GetUID() << " " << c->name << " " << c->creation_time; + } + + void SendTopic(const MessageSource &source, Channel *c) anope_override + { + if (Servers::Capab.count("SVSTOPIC")) + { + UplinkSocket::Message(c->ci->WhoSends()) << "SVSTOPIC " << c->name << " " << c->topic_ts << " " << c->topic_setter << " :" << c->topic; + } + else + { + /* If the last time a topic was set is after the TS we want for this topic we must bump this topic's timestamp to now */ + time_t ts = c->topic_ts; + if (c->topic_time > ts) + ts = Anope::CurTime; + /* But don't modify c->topic_ts, it should remain set to the real TS we want as ci->last_topic_time pulls from it */ + UplinkSocket::Message(source) << "FTOPIC " << c->name << " " << c->creation_time << " " << ts << " " << c->topic_setter << " :" << c->topic; + } + } + + void SendVhostDel(User *u) anope_override + { + UserMode *um = ModeManager::FindUserModeByName("CLOAK"); + + if (um && !u->HasMode(um->name)) + // Just set +x if we can + u->SetMode(NULL, um); + else + // Try to restore cloaked host + this->SendChgHostInternal(u->nick, u->chost); + } + + void SendAkill(User *u, XLine *x) anope_override + { + // Calculate the time left before this would expire, capping it at 2 days + time_t timeleft = x->expires - Anope::CurTime; + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + + /* InspIRCd may support regex bans, if they do we can send this and forget about it + * Mask is expected in format: 'n!u@h\sr' and spaces as '\s' + * We remove the '//' and replace '#' and any ' ' with '\s' + */ + if (x->IsRegex() && Servers::Capab.count("RLINE")) + { + Anope::string mask = x->mask; + if (mask.length() >= 2 && mask[0] == '/' && mask[mask.length() - 1] == '/') + mask = mask.substr(1, mask.length() - 2); + size_t h = mask.find('#'); + if (h != Anope::string::npos) + { + mask = mask.replace(h, 1, "\\s"); + mask = mask.replace_all_cs(" ", "\\s"); + } + SendAddLine("R", mask, timeleft, x->by, x->GetReason()); + return; + } + else if (x->IsRegex() || x->HasNickOrReal()) + { + if (!u) + { + /* No user (this akill was just added), and contains nick and/or realname. Find users that match and ban them */ + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + if (x->manager->Check(it->second, x)) + this->SendAkill(it->second, x); + return; + } + + const XLine *old = x; + + if (old->manager->HasEntry("*@" + u->host)) + return; + + /* We can't akill x as it has a nick and/or realname included, so create a new akill for *@host */ + x = new XLine("*@" + u->host, old->by, old->expires, old->reason, old->id); + old->manager->AddXLine(x); + + Log(Config->GetClient("OperServ"), "akill") << "AKILL: Added an akill for " << x->mask << " because " << u->GetMask() << "#" << u->realname << " matches " << old->mask; + } + + /* ZLine if we can instead */ + if (x->GetUser() == "*") + { + cidr addr(x->GetHost()); + if (addr.valid()) + { + IRCD->SendSZLine(u, x); + return; + } + } + + SendAddLine("G", x->GetUser() + "@" + x->GetHost(), timeleft, x->by, x->GetReason()); + } + + void SendNumericInternal(int numeric, const Anope::string &dest, const Anope::string &buf) anope_override + { + UplinkSocket::Message() << "NUM " << Me->GetSID() << " " << dest << " " << numeric << " " << buf; + } + + void SendModeInternal(const MessageSource &source, const Channel *dest, const Anope::string &buf) anope_override + { + UplinkSocket::Message(source) << "FMODE " << dest->name << " " << dest->creation_time << " " << buf; + } + + void SendClientIntroduction(User *u) anope_override + { + Anope::string modes = "+" + u->GetModes(); + UplinkSocket::Message(Me) << "UID " << u->GetUID() << " " << u->timestamp << " " << u->nick << " " << u->host << " " << u->host << " " << u->GetIdent() << " 0.0.0.0 " << u->timestamp << " " << modes << " :" << u->realname; + if (modes.find('o') != Anope::string::npos) + UplinkSocket::Message(u) << "OPERTYPE :service"; + } + + void SendServer(const Server *server) anope_override + { + /* if rsquit is set then we are waiting on a squit */ + if (rsquit_id.empty() && rsquit_server.empty()) + UplinkSocket::Message() << "SERVER " << server->GetName() << " " << server->GetSID() << " :" << server->GetDescription(); + } + + void SendSquit(Server *s, const Anope::string &message) anope_override + { + if (s != Me) + { + rsquit_id = s->GetSID(); + rsquit_server = s->GetName(); + UplinkSocket::Message() << "RSQUIT " << s->GetName() << " :" << message; + } + else + UplinkSocket::Message() << "SQUIT " << s->GetName() << " :" << message; + } + + void SendJoin(User *user, Channel *c, const ChannelStatus *status) anope_override + { + UplinkSocket::Message(Me) << "FJOIN " << c->name << " " << c->creation_time << " +" << c->GetModes(true, true) << " :," << user->GetUID(); + /* Note that we can send this with the FJOIN but choose not to + * because the mode stacker will handle this and probably will + * merge these modes with +nrt and other mlocked modes + */ + if (status) + { + /* First save the channel status incase uc->Status == status */ + ChannelStatus cs = *status; + /* If the user is internally on the channel with flags, kill them so that + * the stacker will allow this. + */ + ChanUserContainer *uc = c->FindUser(user); + if (uc != NULL) + uc->status.Clear(); + + BotInfo *setter = BotInfo::Find(user->GetUID()); + for (size_t i = 0; i < cs.Modes().length(); ++i) + c->SetMode(setter, ModeManager::FindChannelModeByChar(cs.Modes()[i]), user->GetUID(), false); + + if (uc != NULL) + uc->status = cs; + } + } + + void SendSQLineDel(const XLine *x) anope_override + { + if (IRCD->CanSQLineChannel && (x->mask[0] == '#')) + SendDelLine("CBAN", x->mask); + else + SendDelLine("Q", x->mask); + } + + void SendSQLine(User *u, const XLine *x) anope_override + { + // Calculate the time left before this would expire, capping it at 2 days + time_t timeleft = x->expires - Anope::CurTime; + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + + if (IRCD->CanSQLineChannel && (x->mask[0] == '#')) + SendAddLine("CBAN", x->mask, timeleft, x->by, x->GetReason()); + else + SendAddLine("Q", x->mask, timeleft, x->by, x->GetReason()); + } + + void SendVhost(User *u, const Anope::string &vIdent, const Anope::string &vhost) anope_override + { + if (!vIdent.empty()) + this->SendChgIdentInternal(u->nick, vIdent); + if (!vhost.empty()) + this->SendChgHostInternal(u->nick, vhost); + } + + void SendSVSHold(const Anope::string &nick, time_t t) anope_override + { + UplinkSocket::Message(Config->GetClient("NickServ")) << "SVSHOLD " << nick << " " << t << " :Being held for registered user"; + } + + void SendSVSHoldDel(const Anope::string &nick) anope_override + { + UplinkSocket::Message(Config->GetClient("NickServ")) << "SVSHOLD " << nick; + } + + void SendSZLineDel(const XLine *x) anope_override + { + SendDelLine("Z", x->GetHost()); + } + + void SendSZLine(User *u, const XLine *x) anope_override + { + // Calculate the time left before this would expire, capping it at 2 days + time_t timeleft = x->expires - Anope::CurTime; + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + SendAddLine("Z", x->GetHost(), timeleft, x->by, x->GetReason()); + } + + void SendSVSJoin(const MessageSource &source, User *u, const Anope::string &chan, const Anope::string &other) anope_override + { + UplinkSocket::Message(source) << "SVSJOIN " << u->GetUID() << " " << chan; + } + + void SendSVSPart(const MessageSource &source, User *u, const Anope::string &chan, const Anope::string ¶m) anope_override + { + if (!param.empty()) + UplinkSocket::Message(source) << "SVSPART " << u->GetUID() << " " << chan << " :" << param; + else + UplinkSocket::Message(source) << "SVSPART " << u->GetUID() << " " << chan; + } + + void SendSWhois(const MessageSource &bi, const Anope::string &who, const Anope::string &mask) anope_override + { + User *u = User::Find(who); + + UplinkSocket::Message(Me) << "METADATA " << u->GetUID() << " swhois :" << mask; + } + + void SendBOB() anope_override + { + UplinkSocket::Message(Me) << "BURST " << Anope::CurTime; + Module *enc = ModuleManager::FindFirstOf(ENCRYPTION); + UplinkSocket::Message(Me) << "SINFO version :Anope-" << Anope::Version() << " " << Me->GetName() << " :" << IRCD->GetProtocolName() << " - (" << (enc ? enc->name : "none") << ") -- " << Anope::VersionBuildString(); + UplinkSocket::Message(Me) << "SINFO fullversion :Anope-" << Anope::Version() << " " << Me->GetName() << " :[" << Me->GetSID() << "] " << IRCD->GetProtocolName() << " - (" << (enc ? enc->name : "none") << ") -- " << Anope::VersionBuildString(); + UplinkSocket::Message(Me) << "SINFO rawversion :Anope-" << Anope::VersionShort(); + } + + void SendEOB() anope_override + { + UplinkSocket::Message(Me) << "ENDBURST"; + } + + void SendGlobopsInternal(const MessageSource &source, const Anope::string &buf) anope_override + { + if (Servers::Capab.count("GLOBOPS")) + UplinkSocket::Message(source) << "SNONOTICE g :" << buf; + else + UplinkSocket::Message(source) << "SNONOTICE A :" << buf; + } + + void SendLogin(User *u, NickAlias *na) anope_override + { + /* InspIRCd uses an account to bypass chmode +R, not umode +r, so we can't send this here */ + if (na->nc->HasExt("UNCONFIRMED")) + return; + + UplinkSocket::Message(Me) << "METADATA " << u->GetUID() << " accountid :" << na->nc->GetId(); + UplinkSocket::Message(Me) << "METADATA " << u->GetUID() << " accountname :" << na->nc->display; + } + + void SendLogout(User *u) anope_override + { + UplinkSocket::Message(Me) << "METADATA " << u->GetUID() << " accountid :"; + UplinkSocket::Message(Me) << "METADATA " << u->GetUID() << " accountname :"; + } + + void SendChannel(Channel *c) anope_override + { + UplinkSocket::Message(Me) << "FJOIN " << c->name << " " << c->creation_time << " +" << c->GetModes(true, true) << " :"; + } + + void SendSASLMessage(const SASL::Message &message) anope_override + { + UplinkSocket::Message(Me) << "ENCAP " << message.target.substr(0, 3) << " SASL " << message.source << " " << message.target << " " << message.type << " " << message.data << (message.ext.empty() ? "" : (" " + message.ext)); + } + + void SendSVSLogin(const Anope::string &uid, const Anope::string &acc, const Anope::string &vident, const Anope::string &vhost) anope_override + { + // TODO: in 2.1 this function should take a NickAlias instead of strings. + NickCore *nc = NickCore::Find(acc); + if (!nc) + return; + + UplinkSocket::Message(Me) << "METADATA " << uid << " accountid :" << nc->GetId(); + UplinkSocket::Message(Me) << "METADATA " << uid << " accountname :" << acc; + + if (!vident.empty()) + UplinkSocket::Message(Me) << "ENCAP " << uid.substr(0, 3) << " CHGIDENT " << uid << " " << vident; + if (!vhost.empty()) + UplinkSocket::Message(Me) << "ENCAP " << uid.substr(0, 3) << " CHGHOST " << uid << " " << vhost; + + SASLUser su; + su.uid = uid; + su.acc = acc; + su.created = Anope::CurTime; + + for (std::list::iterator it = saslusers.begin(); it != saslusers.end();) + { + SASLUser &u = *it; + + if (u.created + 30 < Anope::CurTime || u.uid == uid) + it = saslusers.erase(it); + else + ++it; + } + + saslusers.push_back(su); + } + + bool IsExtbanValid(const Anope::string &mask) anope_override + { + return mask.length() >= 3 && mask[1] == ':'; + } + + bool IsIdentValid(const Anope::string &ident) anope_override + { + if (ident.empty() || ident.length() > Config->GetBlock("networkinfo")->Get("userlen")) + return false; + + for (unsigned i = 0; i < ident.length(); ++i) + { + const char &c = ident[i]; + + if (c >= 'A' && c <= '}') + continue; + + if ((c >= '0' && c <= '9') || c == '-' || c == '.') + continue; + + return false; + } + + return true; + } +}; + +class InspIRCdAutoOpMode : public ChannelModeList +{ + public: + InspIRCdAutoOpMode(char mode) : ChannelModeList("AUTOOP", mode) + { + } + + bool IsValid(Anope::string &mask) const anope_override + { + // We can not validate this because we don't know about the + // privileges of the setter so just reject attempts to set it. + return false; + } +}; + +class InspIRCdExtBan : public ChannelModeVirtual +{ + char ext; + + public: + InspIRCdExtBan(const Anope::string &mname, const Anope::string &basename, char extban) : ChannelModeVirtual(mname, basename) + , ext(extban) + { + } + + ChannelMode *Wrap(Anope::string ¶m) anope_override + { + param = Anope::string(ext) + ":" + param; + return ChannelModeVirtual::Wrap(param); + } + + ChannelMode *Unwrap(ChannelMode *cm, Anope::string ¶m) anope_override + { + if (cm->type != MODE_LIST || param.length() < 3 || param[0] != ext || param[1] != ':') + return cm; + + param = param.substr(2); + return this; + } +}; + +namespace InspIRCdExtban +{ + class EntryMatcher : public InspIRCdExtBan + { + public: + EntryMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(3); + + return Entry(this->name, real_mask).Matches(u); + } + }; + + class ChannelMatcher : public InspIRCdExtBan + { + public: + ChannelMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + + Anope::string channel = mask.substr(3); + + ChannelMode *cm = NULL; + if (channel[0] != '#') + { + char modeChar = ModeManager::GetStatusChar(channel[0]); + channel.erase(channel.begin()); + cm = ModeManager::FindChannelModeByChar(modeChar); + if (cm != NULL && cm->type != MODE_STATUS) + cm = NULL; + } + + Channel *c = Channel::Find(channel); + if (c != NULL) + { + ChanUserContainer *uc = c->FindUser(u); + if (uc != NULL) + if (cm == NULL || uc->status.HasMode(cm->mchar)) + return true; + } + + return false; + } + }; + + class AccountMatcher : public InspIRCdExtBan + { + public: + AccountMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(2); + + return u->IsIdentified() && real_mask.equals_ci(u->Account()->display); + } + }; + + class RealnameMatcher : public InspIRCdExtBan + { + public: + RealnameMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(2); + return Anope::Match(u->realname, real_mask); + } + }; + + class ServerMatcher : public InspIRCdExtBan + { + public: + ServerMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(2); + return Anope::Match(u->server->GetName(), real_mask); + } + }; + + class FingerprintMatcher : public InspIRCdExtBan + { + public: + FingerprintMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(2); + return !u->fingerprint.empty() && Anope::Match(u->fingerprint, real_mask); + } + }; + + class UnidentifiedMatcher : public InspIRCdExtBan + { + public: + UnidentifiedMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : InspIRCdExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(2); + return !u->Account() && Entry("BAN", real_mask).Matches(u); + } + }; +} + +class ColonDelimitedParamMode : public ChannelModeParam +{ + public: + ColonDelimitedParamMode(const Anope::string &modename, char modeChar) : ChannelModeParam(modename, modeChar, true) { } + + bool IsValid(Anope::string &value) const anope_override + { + return IsValid(value, false); + } + + bool IsValid(const Anope::string &value, bool historymode) const + { + if (value.empty()) + return false; // empty param is never valid + + Anope::string::size_type pos = value.find(':'); + if ((pos == Anope::string::npos) || (pos == 0)) + return false; // no ':' or it's the first char, both are invalid + + Anope::string rest; + try + { + if (convertTo(value, rest, false) <= 0) + return false; // negative numbers and zero are invalid + + rest = rest.substr(1); + int n; + if (historymode) + { + // For the history mode, the part after the ':' is a duration and it + // can be in the user friendly "1d3h20m" format, make sure we accept that + n = Anope::DoTime(rest); + } + else + n = convertTo(rest); + + if (n <= 0) + return false; + } + catch (const ConvertException &e) + { + // conversion error, invalid + return false; + } + + return true; + } +}; + +class SimpleNumberParamMode : public ChannelModeParam +{ + public: + SimpleNumberParamMode(const Anope::string &modename, char modeChar) : ChannelModeParam(modename, modeChar, true) { } + + bool IsValid(Anope::string &value) const anope_override + { + if (value.empty()) + return false; // empty param is never valid + + try + { + if (convertTo(value) <= 0) + return false; + } + catch (const ConvertException &e) + { + // conversion error, invalid + return false; + } + + return true; + } +}; + +class ChannelModeFlood : public ColonDelimitedParamMode +{ + public: + ChannelModeFlood(char modeChar) : ColonDelimitedParamMode("FLOOD", modeChar) { } + + bool IsValid(Anope::string &value) const anope_override + { + // The parameter of this mode is a bit different, it may begin with a '*', + // ignore it if that's the case + Anope::string v = value[0] == '*' ? value.substr(1) : value; + return ((!value.empty()) && (ColonDelimitedParamMode::IsValid(v))); + } +}; + +class ChannelModeHistory : public ColonDelimitedParamMode +{ + public: + ChannelModeHistory(char modeChar) : ColonDelimitedParamMode("HISTORY", modeChar) { } + + bool IsValid(Anope::string &value) const anope_override + { + return (ColonDelimitedParamMode::IsValid(value, true)); + } +}; + +class ChannelModeRedirect : public ChannelModeParam +{ + public: + ChannelModeRedirect(char modeChar) : ChannelModeParam("REDIRECT", modeChar, true) { } + + bool IsValid(Anope::string &value) const anope_override + { + // The parameter of this mode is a channel, and channel names start with '#' + return ((!value.empty()) && (value[0] == '#')); + } +}; + +struct IRCDMessageAway : Message::Away +{ + IRCDMessageAway(Module *creator) : Message::Away(creator, "AWAY") { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + std::vector newparams(params); + if (newparams.size() > 1) + newparams.erase(newparams.begin()); + + Message::Away::Run(source, newparams); + } +}; + +struct IRCDMessageCapab : Message::Capab +{ + struct ModeInfo + { + // The letter assigned to the mode (e.g. o). + char letter; + + // If a prefix mode then the rank of the prefix. + unsigned level; + + // The name of the mode. + Anope::string name; + + // If a prefix mode then the symbol associated with the prefix. + char symbol; + + // The type of mode. + Anope::string type; + + ModeInfo() : letter(0), level(0), symbol(0) { } + }; + + static bool ParseMode(const Anope::string& token, ModeInfo& mode) + { + // list:ban=b param-set:limit=l param:key=k prefix:30000:op=@o simple:noextmsg=n + // A C A C A C A B C A C + Anope::string::size_type a = token.find(':'); + if (a == Anope::string::npos) + return false; + + // If the mode is a prefix mode then it also has a rank. + mode.type = token.substr(0, a); + if (mode.type == "prefix") + { + Anope::string::size_type b = token.find(':', a + 1); + if (b == Anope::string::npos) + return false; + + const Anope::string modelevel = token.substr(a + 1, b - a - 1); + mode.level = modelevel.is_pos_number_only() ? convertTo(modelevel) : 0; + a = b; + } + + Anope::string::size_type c = token.find('=', a + 1); + if (c == Anope::string::npos) + return false; + + mode.name = token.substr(a + 1, c - a - 1); + switch (token.length() - c) + { + case 2: + mode.letter = token[c + 1]; + break; + case 3: + mode.symbol = token[c + 1]; + mode.letter = token[c + 2]; + break; + default: + return false; + } + + Log(LOG_DEBUG) << "Parsed mode: " << "type=" << mode.type << " name=" << mode.name << " level=" + << mode.level << " symbol=" << mode.symbol << " letter=" << mode.letter; + return true; + } + + IRCDMessageCapab(Module *creator) : Message::Capab(creator, "CAPAB") { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params[0].equals_cs("START")) + { + unsigned int spanningtree_proto_ver = 0; + if (params.size() >= 2) + spanningtree_proto_ver = params[1].is_pos_number_only() ? convertTo(params[1]) : 0; + + if (spanningtree_proto_ver < 1205) + { + UplinkSocket::Message() << "ERROR :Protocol mismatch, no or invalid protocol version given in CAPAB START"; + Anope::QuitReason = "Protocol mismatch, no or invalid protocol version given in CAPAB START"; + Anope::Quitting = true; + return; + } + + /* reset CAPAB */ + Servers::Capab.insert("SERVERS"); + Servers::Capab.insert("TOPICLOCK"); + IRCD->CanSQLineChannel = false; + IRCD->CanSVSHold = false; + IRCD->DefaultPseudoclientModes = "+oI"; + } + else if (params[0].equals_cs("CHANMODES") && params.size() > 1) + { + spacesepstream ssep(params[1]); + Anope::string capab; + + while (ssep.GetToken(capab)) + { + ModeInfo mode; + if (!ParseMode(capab, mode)) + continue; + + ChannelMode *cm = NULL; + if (mode.name.equals_cs("admin")) + cm = new ChannelModeStatus("PROTECT", mode.letter, mode.symbol, mode.level); + else if (mode.name.equals_cs("allowinvite")) + { + cm = new ChannelMode("ALLINVITE", mode.letter); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("INVITEBAN", "BAN", 'A')); + } + else if (mode.name.equals_cs("auditorium")) + cm = new ChannelMode("AUDITORIUM", mode.letter); + else if (mode.name.equals_cs("autoop")) + cm = new InspIRCdAutoOpMode(mode.letter); + else if (mode.name.equals_cs("ban")) + cm = new ChannelModeList("BAN", mode.letter); + else if (mode.name.equals_cs("banexception")) + cm = new ChannelModeList("EXCEPT", mode.letter); + else if (mode.name.equals_cs("blockcaps")) + { + cm = new ChannelMode("BLOCKCAPS", mode.letter); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("BLOCKCAPSBAN", "BAN", 'B')); + } + else if (mode.name.equals_cs("blockcolor")) + { + cm = new ChannelMode("BLOCKCOLOR", mode.letter); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("BLOCKCOLORBAN", "BAN", 'c')); + } + else if (mode.name.equals_cs("c_registered")) + cm = new ChannelModeNoone("REGISTERED", mode.letter); + else if (mode.name.equals_cs("censor")) + cm = new ChannelMode("CENSOR", mode.letter); + else if (mode.name.equals_cs("delayjoin")) + cm = new ChannelMode("DELAYEDJOIN", mode.letter); + else if (mode.name.equals_cs("delaymsg")) + cm = new SimpleNumberParamMode("DELAYMSG", mode.letter); + else if (mode.name.equals_cs("filter")) + cm = new ChannelModeList("FILTER", mode.letter); + else if (mode.name.equals_cs("flood")) + cm = new ChannelModeFlood(mode.letter); + else if (mode.name.equals_cs("founder")) + cm = new ChannelModeStatus("OWNER", mode.letter, mode.symbol, mode.level); + else if (mode.name.equals_cs("halfop")) + cm = new ChannelModeStatus("HALFOP", mode.letter, mode.symbol, mode.level); + else if (mode.name.equals_cs("history")) + cm = new ChannelModeHistory(mode.letter); + else if (mode.name.equals_cs("invex")) + cm = new ChannelModeList("INVITEOVERRIDE", mode.letter); + else if (mode.name.equals_cs("inviteonly")) + cm = new ChannelMode("INVITE", mode.letter); + else if (mode.name.equals_cs("joinflood")) + cm = new ColonDelimitedParamMode("JOINFLOOD", mode.letter); + else if (mode.name.equals_cs("key")) + cm = new ChannelModeKey(mode.letter); + else if (mode.name.equals_cs("kicknorejoin")) + cm = new SimpleNumberParamMode("NOREJOIN", mode.letter); + else if (mode.name.equals_cs("limit")) + cm = new ChannelModeParam("LIMIT", mode.letter, true); + else if (mode.name.equals_cs("moderated")) + cm = new ChannelMode("MODERATED", mode.letter); + else if (mode.name.equals_cs("nickflood")) + cm = new ColonDelimitedParamMode("NICKFLOOD", mode.letter); + else if (mode.name.equals_cs("noctcp")) + { + cm = new ChannelMode("NOCTCP", mode.letter); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("NOCTCPBAN", "BAN", 'C')); + } + else if (mode.name.equals_cs("noextmsg")) + cm = new ChannelMode("NOEXTERNAL", mode.letter); + else if (mode.name.equals_cs("nokick")) + { + cm = new ChannelMode("NOKICK", mode.letter); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("NOKICKBAN", "BAN", 'Q')); + } + else if (mode.name.equals_cs("noknock")) + cm = new ChannelMode("NOKNOCK", mode.letter); + else if (mode.name.equals_cs("nonick")) + { + cm = new ChannelMode("NONICK", mode.letter); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("NONICKBAN", "BAN", 'N')); + } + else if (mode.name.equals_cs("nonotice")) + { + cm = new ChannelMode("NONOTICE", mode.letter); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("NONOTICEBAN", "BAN", 'T')); + } + else if (mode.name.equals_cs("official-join")) + cm = new ChannelModeStatus("OFFICIALJOIN", mode.letter, mode.symbol, mode.level); + else if (mode.name.equals_cs("op")) + cm = new ChannelModeStatus("OP", mode.letter, mode.symbol, mode.level); + else if (mode.name.equals_cs("operonly")) + cm = new ChannelModeOperOnly("OPERONLY", mode.letter); + else if (mode.name.equals_cs("operprefix")) + cm = new ChannelModeStatus("OPERPREFIX", mode.letter, mode.symbol, mode.level); + else if (mode.name.equals_cs("permanent")) + cm = new ChannelMode("PERM", mode.letter); + else if (mode.name.equals_cs("private")) + cm = new ChannelMode("PRIVATE", mode.letter); + else if (mode.name.equals_cs("redirect")) + cm = new ChannelModeRedirect(mode.letter); + else if (mode.name.equals_cs("reginvite")) + cm = new ChannelMode("REGISTEREDONLY", mode.letter); + else if (mode.name.equals_cs("regmoderated")) + cm = new ChannelMode("REGMODERATED", mode.letter); + else if (mode.name.equals_cs("secret")) + cm = new ChannelMode("SECRET", mode.letter); + else if (mode.name.equals_cs("sslonly")) + { + cm = new ChannelMode("SSL", mode.letter); + ModeManager::AddChannelMode(new InspIRCdExtban::FingerprintMatcher("SSLBAN", "BAN", 'z')); + } + else if (mode.name.equals_cs("stripcolor")) + { + cm = new ChannelMode("STRIPCOLOR", mode.letter); + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("STRIPCOLORBAN", "BAN", 'S')); + } + else if (mode.name.equals_cs("topiclock")) + cm = new ChannelMode("TOPIC", mode.letter); + else if (mode.name.equals_cs("voice")) + cm = new ChannelModeStatus("VOICE", mode.letter, mode.symbol, mode.level); + + // Handle unknown modes. + else if (mode.type.equals_cs("list")) + cm = new ChannelModeList(mode.name.upper(), mode.letter); + else if (mode.type.equals_cs("param-set")) + cm = new ChannelModeParam(mode.name.upper(), mode.letter, true); + else if (mode.type.equals_cs("param")) + cm = new ChannelModeParam(mode.name.upper(), mode.letter, false); + else if (mode.type.equals_cs("prefix")) + cm = new ChannelModeStatus(mode.name.upper(), mode.letter, mode.symbol, mode.level); + else if (mode.type.equals_cs("simple")) + cm = new ChannelMode(mode.name.upper(), mode.letter); + else + Log(LOG_DEBUG) << "Unknown channel mode: " << capab; + + if (cm) + ModeManager::AddChannelMode(cm); + } + } + if (params[0].equals_cs("USERMODES") && params.size() > 1) + { + spacesepstream ssep(params[1]); + Anope::string capab; + + while (ssep.GetToken(capab)) + { + ModeInfo mode; + if (!ParseMode(capab, mode)) + continue; + + UserMode *um = NULL; + if (mode.name.equals_cs("bot")) + { + um = new UserMode("BOT", mode.letter); + IRCD->DefaultPseudoclientModes += mode.letter; + } + else if (mode.name.equals_cs("callerid")) + um = new UserMode("CALLERID", mode.letter); + else if (mode.name.equals_cs("cloak")) + um = new UserMode("CLOAK", mode.letter); + else if (mode.name.equals_cs("deaf")) + um = new UserMode("DEAF", mode.letter); + else if (mode.name.equals_cs("deaf_commonchan")) + um = new UserMode("COMMONCHANS", mode.letter); + else if (mode.name.equals_cs("helpop")) + um = new UserModeOperOnly("HELPOP", mode.letter); + else if (mode.name.equals_cs("hidechans")) + um = new UserMode("PRIV", mode.letter); + else if (mode.name.equals_cs("hideoper")) + um = new UserModeOperOnly("HIDEOPER", mode.letter); + else if (mode.name.equals_cs("invisible")) + um = new UserMode("INVIS", mode.letter); + else if (mode.name.equals_cs("invis-oper")) + um = new UserModeOperOnly("INVISIBLE_OPER", mode.letter); + else if (mode.name.equals_cs("oper")) + um = new UserModeOperOnly("OPER", mode.letter); + else if (mode.name.equals_cs("regdeaf")) + um = new UserMode("REGPRIV", mode.letter); + else if (mode.name.equals_cs("servprotect")) + { + um = new UserModeNoone("PROTECTED", mode.letter); + IRCD->DefaultPseudoclientModes += mode.letter; + } + else if (mode.name.equals_cs("showwhois")) + um = new UserMode("WHOIS", mode.letter); + else if (mode.name.equals_cs("u_censor")) + um = new UserMode("CENSOR", mode.letter); + else if (mode.name.equals_cs("u_registered")) + um = new UserModeNoone("REGISTERED", mode.letter); + else if (mode.name.equals_cs("u_stripcolor")) + um = new UserMode("STRIPCOLOR", mode.letter); + else if (mode.name.equals_cs("wallops")) + um = new UserMode("WALLOPS", mode.letter); + + // Handle unknown modes. + else if (mode.type.equals_cs("param-set")) + um = new UserModeParam(mode.name.upper(), mode.letter); + else if (mode.type.equals_cs("simple")) + um = new UserMode(mode.name.upper(), mode.letter); + else + Log(LOG_DEBUG) << "Unknown user mode: " << capab; + + if (um) + ModeManager::AddUserMode(um); + } + } + else if (params[0].equals_cs("MODULES") && params.size() > 1) + { + spacesepstream ssep(params[1]); + Anope::string module; + + while (ssep.GetToken(module)) + { + if (module.equals_cs("m_svshold.so")) + IRCD->CanSVSHold = true; + else if (module.find("m_rline.so") == 0) + { + Servers::Capab.insert("RLINE"); + const Anope::string ®exengine = Config->GetBlock("options")->Get("regexengine"); + if (!regexengine.empty() && module.length() > 11 && regexengine != module.substr(11)) + Log() << "Warning: InspIRCd is using regex engine " << module.substr(11) << ", but we have " << regexengine << ". This may cause inconsistencies."; + } + else if (module.equals_cs("m_topiclock.so")) + Servers::Capab.insert("TOPICLOCK"); + else if (module.equals_cs("m_cban.so=glob")) + IRCD->CanSQLineChannel = true; + } + } + else if (params[0].equals_cs("MODSUPPORT") && params.size() > 1) + { + spacesepstream ssep(params[1]); + Anope::string module; + + while (ssep.GetToken(module)) + { + if (module.equals_cs("m_services_account.so")) + { + Servers::Capab.insert("SERVICES"); + ModeManager::AddChannelMode(new InspIRCdExtban::AccountMatcher("ACCOUNTBAN", "BAN", 'R')); + ModeManager::AddChannelMode(new InspIRCdExtban::UnidentifiedMatcher("UNREGISTEREDBAN", "BAN", 'U')); + } + else if (module.equals_cs("m_chghost.so")) + Servers::Capab.insert("CHGHOST"); + else if (module.equals_cs("m_chgident.so")) + Servers::Capab.insert("CHGIDENT"); + else if (module == "m_channelban.so") + ModeManager::AddChannelMode(new InspIRCdExtban::ChannelMatcher("CHANNELBAN", "BAN", 'j')); + else if (module == "m_gecosban.so") + ModeManager::AddChannelMode(new InspIRCdExtban::RealnameMatcher("REALNAMEBAN", "BAN", 'r')); + else if (module == "m_nopartmessage.so") + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("PARTMESSAGEBAN", "BAN", 'p')); + else if (module == "m_serverban.so") + ModeManager::AddChannelMode(new InspIRCdExtban::ServerMatcher("SERVERBAN", "BAN", 's')); + else if (module == "m_muteban.so") + ModeManager::AddChannelMode(new InspIRCdExtban::EntryMatcher("QUIET", "BAN", 'm')); + } + } + else if (params[0].equals_cs("CAPABILITIES") && params.size() > 1) + { + spacesepstream ssep(params[1]); + Anope::string capab; + while (ssep.GetToken(capab)) + { + if (capab.find("MAXMODES=") != Anope::string::npos) + { + Anope::string maxmodes(capab.begin() + 9, capab.end()); + IRCD->MaxModes = maxmodes.is_pos_number_only() ? convertTo(maxmodes) : 3; + } + else if (capab == "GLOBOPS=1") + Servers::Capab.insert("GLOBOPS"); + } + } + else if (params[0].equals_cs("END")) + { + if (!Servers::Capab.count("SERVICES")) + { + UplinkSocket::Message() << "ERROR :The services_account module is not loaded. This is required by Anope"; + Anope::QuitReason = "ERROR: Remote server does not have the services_account module loaded, and this is required."; + Anope::Quitting = true; + return; + } + if (!ModeManager::FindUserModeByName("PRIV")) + { + UplinkSocket::Message() << "ERROR :The hidechans module is not loaded. This is required by Anope"; + Anope::QuitReason = "ERROR: Remote server does not have the hidechans module loaded, and this is required."; + Anope::Quitting = true; + return; + } + if (!IRCD->CanSVSHold) + Log() << "SVSHOLD missing, Usage disabled until module is loaded."; + if (!Servers::Capab.count("CHGHOST")) + Log() << "CHGHOST missing, Usage disabled until module is loaded."; + if (!Servers::Capab.count("CHGIDENT")) + Log() << "CHGIDENT missing, Usage disabled until module is loaded."; + } + + Message::Capab::Run(source, params); + } +}; + +struct IRCDMessageEncap : IRCDMessage +{ + IRCDMessageEncap(Module *creator) : IRCDMessage(creator, "ENCAP", 4) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (!Anope::Match(Me->GetSID(), params[0]) && !Anope::Match(Me->GetName(), params[0])) + return; + + if (params[1] == "CHGIDENT") + { + User *u = User::Find(params[2]); + if (!u || u->server != Me) + return; + + u->SetIdent(params[3]); + UplinkSocket::Message(u) << "FIDENT :" << params[3]; + } + else if (params[1] == "CHGHOST") + { + User *u = User::Find(params[2]); + if (!u || u->server != Me) + return; + + u->SetDisplayedHost(params[3]); + UplinkSocket::Message(u) << "FHOST :" << params[3]; + } + else if (params[1] == "CHGNAME") + { + User *u = User::Find(params[2]); + if (!u || u->server != Me) + return; + + u->SetRealname(params[3]); + UplinkSocket::Message(u) << "FNAME :" << params[3]; + } + else if (SASL::sasl && params[1] == "SASL" && params.size() >= 6) + { + SASL::Message m; + m.source = params[2]; + m.target = params[3]; + m.type = params[4]; + m.data = params[5]; + m.ext = params.size() > 6 ? params[6] : ""; + + SASL::sasl->ProcessMessage(m); + } + } +}; + +struct IRCDMessageFHost : IRCDMessage +{ + IRCDMessageFHost(Module *creator) : IRCDMessage(creator, "FHOST", 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + if (u->HasMode("CLOAK")) + u->RemoveModeInternal(source, ModeManager::FindUserModeByName("CLOAK")); + u->SetDisplayedHost(params[0]); + } +}; + +struct IRCDMessageFIdent : IRCDMessage +{ + IRCDMessageFIdent(Module *creator) : IRCDMessage(creator, "FIDENT", 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetUser()->SetIdent(params[0]); + } +}; + +struct IRCDMessageKick : IRCDMessage +{ + IRCDMessageKick(Module *creator) : IRCDMessage(creator, "KICK", 3) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + // Received: :715AAAAAA KICK #chan 715AAAAAD :reason + // Received: :715AAAAAA KICK #chan 628AAAAAA 4 :reason + Channel *c = Channel::Find(params[0]); + if (!c) + return; + + const Anope::string &reason = params.size() > 3 ? params[3] : params[2]; + c->KickInternal(source, params[1], reason); + } +}; + +struct IRCDMessageSave : IRCDMessage +{ + time_t last_collide; + + IRCDMessageSave(Module *creator) : IRCDMessage(creator, "SAVE", 2), last_collide(0) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *targ = User::Find(params[0]); + time_t ts; + + try + { + ts = convertTo(params[1]); + } + catch (const ConvertException &) + { + return; + } + + if (!targ || targ->timestamp != ts) + return; + + BotInfo *bi; + if (targ->server == Me && (bi = dynamic_cast(targ))) + { + if (last_collide == Anope::CurTime) + { + Anope::QuitReason = "Nick collision fight on " + targ->nick; + Anope::Quitting = true; + return; + } + + IRCD->SendKill(Me, targ->nick, "Nick collision"); + IRCD->SendNickChange(targ, targ->nick); + last_collide = Anope::CurTime; + } + else + targ->ChangeNick(targ->GetUID()); + } +}; + +class IRCDMessageMetadata : IRCDMessage +{ + const bool &do_topiclock; + const bool &do_mlock; + PrimitiveExtensibleItem &maxlist; + + public: + IRCDMessageMetadata(Module *creator, const bool &handle_topiclock, const bool &handle_mlock, PrimitiveExtensibleItem &listlimits) : IRCDMessage(creator, "METADATA", 3), do_topiclock(handle_topiclock), do_mlock(handle_mlock), maxlist(listlimits) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + // We deliberately ignore non-bursting servers to avoid pseudoserver fights + // Channel METADATA has an additional parameter: the channel TS + // Received: :715 METADATA #chan 1572026333 mlock :nt + if ((params[0][0] == '#') && (params.size() > 3) && (!source.GetServer()->IsSynced())) + { + Channel *c = Channel::Find(params[0]); + if (c) + { + if ((c->ci) && (do_mlock) && (params[2] == "mlock")) + { + ModeLocks *modelocks = c->ci->GetExt("modelocks"); + Anope::string modes; + if (modelocks) + modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", ""); + + // Mode lock string is not what we say it is? + if (modes != params[3]) + UplinkSocket::Message(Me) << "METADATA " << c->name << " " << c->creation_time << " mlock :" << modes; + } + else if ((c->ci) && (do_topiclock) && (params[2] == "topiclock")) + { + bool mystate = c->ci->HasExt("TOPICLOCK"); + bool serverstate = (params[3] == "1"); + if (mystate != serverstate) + UplinkSocket::Message(Me) << "METADATA " << c->name << " " << c->creation_time << " topiclock :" << (mystate ? "1" : ""); + } + else if (params[2] == "maxlist") + { + ListLimits limits; + spacesepstream limitstream(params[3]); + Anope::string modechr, modelimit; + while (limitstream.GetToken(modechr) && limitstream.GetToken(modelimit)) + { + limits.insert(std::make_pair(modechr[0], convertTo(modelimit))); + } + maxlist.Set(c, limits); + } + } + } + else if (isdigit(params[0][0])) + { + if (params[1].equals_cs("accountname")) + { + User *u = User::Find(params[0]); + NickCore *nc = NickCore::Find(params[2]); + if (u && nc) + u->Login(nc); + } + + /* + * possible incoming ssl_cert messages: + * Received: :409 METADATA 409AAAAAA ssl_cert :vTrSe c38070ce96e41cc144ed6590a68d45a6 <...> <...> + * Received: :409 METADATA 409AAAAAC ssl_cert :vTrSE Could not get peer certificate: error:00000000:lib(0):func(0):reason(0) + */ + else if (params[1].equals_cs("ssl_cert")) + { + User *u = User::Find(params[0]); + if (!u) + return; + u->Extend("ssl"); + Anope::string data = params[2].c_str(); + size_t pos1 = data.find(' ') + 1; + size_t pos2 = data.find(' ', pos1); + if ((pos2 - pos1) >= 32) // inspircd supports md5 and sha1 fingerprint hashes -> size 32 or 40 bytes. + { + u->fingerprint = data.substr(pos1, pos2 - pos1); + } + FOREACH_MOD(OnFingerprint, (u)); + } + } + else if (params[0] == "*") + { + // Wed Oct 3 15:40:27 2012: S[14] O :20D METADATA * modules :-m_svstopic.so + + if (params[1].equals_cs("modules") && !params[2].empty()) + { + // only interested when it comes from our uplink + Server* server = source.GetServer(); + if (!server || server->GetUplink() != Me) + return; + + bool plus = (params[2][0] == '+'); + if (!plus && params[2][0] != '-') + return; + + bool required = false; + Anope::string capab, module = params[2].substr(1); + + if (module.equals_cs("m_services_account.so")) + required = true; + else if (module.equals_cs("m_hidechans.so")) + required = true; + else if (module.equals_cs("m_chghost.so")) + capab = "CHGHOST"; + else if (module.equals_cs("m_chgident.so")) + capab = "CHGIDENT"; + else if (module.equals_cs("m_svshold.so")) + capab = "SVSHOLD"; + else if (module.equals_cs("m_rline.so")) + capab = "RLINE"; + else if (module.equals_cs("m_topiclock.so")) + capab = "TOPICLOCK"; + else + return; + + if (required) + { + if (!plus) + Log() << "Warning: InspIRCd unloaded module " << module << ", Anope won't function correctly without it"; + } + else + { + if (plus) + Servers::Capab.insert(capab); + else + Servers::Capab.erase(capab); + + Log() << "InspIRCd " << (plus ? "loaded" : "unloaded") << " module " << module << ", adjusted functionality"; + } + + } + } + } +}; + +struct IRCDMessageEndburst : IRCDMessage +{ + IRCDMessageEndburst(Module *creator) : IRCDMessage(creator, "ENDBURST", 0) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Server *s = source.GetServer(); + + Log(LOG_DEBUG) << "Processed ENDBURST for " << s->GetName(); + + s->Sync(true); + } +}; + +struct IRCDMessageFJoin : IRCDMessage +{ + IRCDMessageFJoin(Module *creator) : IRCDMessage(creator, "FJOIN", 2) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Anope::string modes; + if (params.size() >= 3) + { + for (unsigned i = 2; i < params.size() - 1; ++i) + modes += " " + params[i]; + if (!modes.empty()) + modes.erase(modes.begin()); + } + + std::list users; + + spacesepstream sep(params[params.size() - 1]); + Anope::string buf; + while (sep.GetToken(buf)) + { + Message::Join::SJoinUser sju; + + /* Loop through prefixes and find modes for them */ + for (char c; (c = buf[0]) != ',' && c;) + { + buf.erase(buf.begin()); + sju.first.AddMode(c); + } + /* Erase the , */ + if (!buf.empty()) + buf.erase(buf.begin()); + + /* Erase the :membid */ + if (!buf.empty()) + { + Anope::string::size_type membid = buf.find(':'); + if (membid != Anope::string::npos) + buf.erase(membid, Anope::string::npos); + } + + sju.second = User::Find(buf); + if (!sju.second) + { + Log(LOG_DEBUG) << "FJOIN for nonexistent user " << buf << " on " << params[0]; + continue; + } + + users.push_back(sju); + } + + time_t ts = Anope::string(params[1]).is_pos_number_only() ? convertTo(params[1]) : Anope::CurTime; + Message::Join::SJoin(source, params[0], ts, modes, users); + } +}; + +struct IRCDMessageFMode : IRCDMessage +{ + IRCDMessageFMode(Module *creator) : IRCDMessage(creator, "FMODE", 3) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + /* :source FMODE #test 12345678 +nto foo */ + + Anope::string modes = params[2]; + for (unsigned n = 3; n < params.size(); ++n) + modes += " " + params[n]; + + Channel *c = Channel::Find(params[0]); + time_t ts; + + try + { + ts = convertTo(params[1]); + } + catch (const ConvertException &) + { + ts = 0; + } + + if (c) + c->SetModesInternal(source, modes, ts); + } +}; + +struct IRCDMessageFTopic : IRCDMessage +{ + IRCDMessageFTopic(Module *creator) : IRCDMessage(creator, "FTOPIC", 4) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + // :source FTOPIC channel ts topicts :topic + // :source FTOPIC channel ts topicts setby :topic (burst or RESYNC) + + const Anope::string &setby = params.size() > 4 ? params[3] : source.GetName(); + const Anope::string &topic = params.size() > 4 ? params[4] : params[3]; + + Channel *c = Channel::Find(params[0]); + if (c) + c->ChangeTopicInternal(NULL, setby, topic, params[2].is_pos_number_only() ? convertTo(params[2]) : Anope::CurTime); + } +}; + +struct IRCDMessageIdle : IRCDMessage +{ + IRCDMessageIdle(Module *creator) : IRCDMessage(creator, "IDLE", 1) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + BotInfo *bi = BotInfo::Find(params[0]); + if (bi) + UplinkSocket::Message(bi) << "IDLE " << source.GetSource() << " " << Anope::StartTime << " " << (Anope::CurTime - bi->lastmsg); + else + { + User *u = User::Find(params[0]); + if (u && u->server == Me) + UplinkSocket::Message(u) << "IDLE " << source.GetSource() << " " << Anope::StartTime << " 0"; + } + } +}; + +struct IRCDMessageIJoin : IRCDMessage +{ + IRCDMessageIJoin(Module *creator) : IRCDMessage(creator, "IJOIN", 2) { SetFlag(IRCDMESSAGE_REQUIRE_USER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + // : IJOIN [ []] + Channel *c = Channel::Find(params[0]); + if (!c) + { + // When receiving an IJOIN, first check if the target channel exists. If it does not exist, + // ignore the join (that is, do not create the channel) and send a RESYNC back to the source. + UplinkSocket::Message(Me) << "RESYNC :" << params[0]; + return; + } + + // If the channel does exist then join the user, and in case any prefix modes were sent (found in + // the 3rd parameter), compare the TS of the channel to the TS in the IJOIN (2nd parameter). If + // the timestamps match, set the modes on the user, otherwise ignore the modes. + Message::Join::SJoinUser user; + user.second = source.GetUser(); + + time_t chants = Anope::CurTime; + if (params.size() >= 4) + { + chants = params[2].is_pos_number_only() ? convertTo(params[2]) : 0; + for (unsigned i = 0; i < params[3].length(); ++i) + user.first.AddMode(params[3][i]); + } + + std::list users; + users.push_back(user); + Message::Join::SJoin(source, params[0], chants, "", users); + } +}; + +struct IRCDMessageMode : IRCDMessage +{ + IRCDMessageMode(Module *creator) : IRCDMessage(creator, "MODE", 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (IRCD->IsChannelValid(params[0])) + { + Channel *c = Channel::Find(params[0]); + + Anope::string modes = params[1]; + for (unsigned n = 2; n < params.size(); ++n) + modes += " " + params[n]; + + if (c) + c->SetModesInternal(source, modes); + } + else + { + /* InspIRCd lets opers change another + users modes, we have to kludge this + as it slightly breaks RFC1459 + */ + User *u = User::Find(params[0]); + if (u) + u->SetModesInternal(source, "%s", params[1].c_str()); + } + } +}; + +struct IRCDMessageNick : IRCDMessage +{ + IRCDMessageNick(Module *creator) : IRCDMessage(creator, "NICK", 2) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetUser()->ChangeNick(params[0]); + } +}; + +struct IRCDMessageOperType : IRCDMessage +{ + IRCDMessageOperType(Module *creator) : IRCDMessage(creator, "OPERTYPE", 0) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + /* opertype is equivalent to mode +o because servers + don't do this directly */ + User *u = source.GetUser(); + if (!u->HasMode("OPER")) + u->SetModesInternal(source, "+o"); + } +}; + +struct IRCDMessagePing : IRCDMessage +{ + IRCDMessagePing(Module *creator) : IRCDMessage(creator, "PING", 1) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params[0] == Me->GetSID()) + IRCD->SendPong(params[0], source.GetServer()->GetSID()); + } +}; + +struct IRCDMessageRSQuit : IRCDMessage +{ + IRCDMessageRSQuit(Module *creator) : IRCDMessage(creator, "RSQUIT", 1) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Server *s = Server::Find(params[0]); + const Anope::string &reason = params.size() > 1 ? params[1] : ""; + if (!s) + return; + + UplinkSocket::Message(Me) << "SQUIT " << s->GetSID() << " :" << reason; + s->Delete(s->GetName() + " " + s->GetUplink()->GetName()); + } +}; + +struct IRCDMessageServer : IRCDMessage +{ + IRCDMessageServer(Module *creator) : IRCDMessage(creator, "SERVER", 3) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (!source.GetServer() && params.size() == 5) + { + /* + * SERVER testnet.inspircd.org hunter7 0 123 :InspIRCd Test Network + * 0: name + * 1: pass + * 2: hops + * 3: numeric + * 4: desc + */ + unsigned int hops = Anope::string(params[2]).is_pos_number_only() ? convertTo(params[2]) : 0; + new Server(Me, params[0], hops, params[4], params[3]); + } + else if (source.GetServer()) + { + /* + * SERVER testnet.inspircd.org 123 burst=1234 hidden=0 :InspIRCd Test Network + * 0: name + * 1: numeric + * 2 to N-1: various key=value pairs. + * N: desc + */ + new Server(source.GetServer(), params[0], 1, params.back(), params[1]); + } + } +}; + +struct IRCDMessageSQuit : Message::SQuit +{ + IRCDMessageSQuit(Module *creator) : Message::SQuit(creator) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params[0] == rsquit_id || params[0] == rsquit_server) + { + /* squit for a recently squit server, introduce the juped server now */ + Server *s = Server::Find(rsquit_server); + + rsquit_id.clear(); + rsquit_server.clear(); + + if (s && s->IsJuped()) + IRCD->SendServer(s); + } + else + Message::SQuit::Run(source, params); + } +}; + +struct IRCDMessageTime : IRCDMessage +{ + IRCDMessageTime(Module *creator) : IRCDMessage(creator, "TIME", 2) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + UplinkSocket::Message(Me) << "TIME " << source.GetSource() << " " << params[1] << " " << Anope::CurTime; + } +}; + +struct IRCDMessageUID : IRCDMessage +{ + IRCDMessageUID(Module *creator) : IRCDMessage(creator, "UID", 8) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* + * [Nov 03 22:09:58.176252 2009] debug: Received: :964 UID 964AAAAAC 1225746297 w00t2 localhost testnet.user w00t 127.0.0.1 1225746302 +iosw +ACGJKLNOQcdfgjklnoqtx :Robin Burchell + * 0: uid + * 1: ts + * 2: nick + * 3: host + * 4: dhost + * 5: ident + * 6: ip + * 7: signon + * 8+: modes and params -- IMPORTANT, some modes (e.g. +s) may have parameters. So don't assume a fixed position of realname! + * last: realname + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + time_t ts = convertTo(params[1]); + + Anope::string modes = params[8]; + for (unsigned i = 9; i < params.size() - 1; ++i) + modes += " " + params[i]; + + NickAlias *na = NULL; + if (SASL::sasl) + for (std::list::iterator it = saslusers.begin(); it != saslusers.end();) + { + SASLUser &u = *it; + + if (u.created + 30 < Anope::CurTime) + it = saslusers.erase(it); + else if (u.uid == params[0]) + { + na = NickAlias::Find(u.acc); + it = saslusers.erase(it); + } + else + ++it; + } + + User *u = User::OnIntroduce(params[2], params[5], params[3], params[4], params[6], source.GetServer(), params[params.size() - 1], ts, modes, params[0], na ? *na->nc : NULL); + if (u) + u->signon = convertTo(params[7]); + } +}; + +class ProtoInspIRCd3 : public Module +{ + InspIRCd3Proto ircd_proto; + ExtensibleItem ssl; + + /* Core message handlers */ + Message::Error message_error; + Message::Invite message_invite; + Message::Kill message_kill; + Message::MOTD message_motd; + Message::Notice message_notice; + Message::Part message_part; + Message::Privmsg message_privmsg; + Message::Quit message_quit; + Message::Stats message_stats; + + /* Our message handlers */ + IRCDMessageAway message_away; + IRCDMessageCapab message_capab; + IRCDMessageEncap message_encap; + IRCDMessageEndburst message_endburst; + IRCDMessageFHost message_fhost; + IRCDMessageFIdent message_fident; + IRCDMessageFJoin message_fjoin; + IRCDMessageFMode message_fmode; + IRCDMessageFTopic message_ftopic; + IRCDMessageIdle message_idle; + IRCDMessageIJoin message_ijoin; + IRCDMessageKick message_kick; + IRCDMessageMetadata message_metadata; + IRCDMessageMode message_mode; + IRCDMessageNick message_nick; + IRCDMessageOperType message_opertype; + IRCDMessagePing message_ping; + IRCDMessageRSQuit message_rsquit; + IRCDMessageSave message_save; + IRCDMessageServer message_server; + IRCDMessageSQuit message_squit; + IRCDMessageTime message_time; + IRCDMessageUID message_uid; + + bool use_server_side_topiclock, use_server_side_mlock; + + void SendChannelMetadata(Channel *c, const Anope::string &metadataname, const Anope::string &value) + { + UplinkSocket::Message(Me) << "METADATA " << c->name << " " << c->creation_time << " " << metadataname << " :" << value; + } + + public: + ProtoInspIRCd3(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PROTOCOL | VENDOR), + ircd_proto(this), ssl(this, "ssl"), + message_error(this), message_invite(this), message_kill(this), message_motd(this), message_notice(this), + message_part(this), message_privmsg(this), message_quit(this), message_stats(this), + message_away(this), message_capab(this), message_encap(this), message_endburst(this), message_fhost(this), + message_fident(this), message_fjoin(this), message_fmode(this), message_ftopic(this), message_idle(this), + message_ijoin(this), message_kick(this), message_metadata(this, use_server_side_topiclock, use_server_side_mlock, ircd_proto.maxlist), + message_mode(this), message_nick(this), message_opertype(this), message_ping(this), message_rsquit(this), + message_save(this), message_server(this), message_squit(this), message_time(this), message_uid(this) + { + } + + void OnReload(Configuration::Conf *conf) anope_override + { + use_server_side_topiclock = conf->GetModule(this)->Get("use_server_side_topiclock"); + use_server_side_mlock = conf->GetModule(this)->Get("use_server_side_mlock"); + } + + void OnUserNickChange(User *u, const Anope::string &) anope_override + { + u->RemoveModeInternal(Me, ModeManager::FindUserModeByName("REGISTERED")); + } + + void OnChannelSync(Channel *c) anope_override + { + if (c->ci) + this->OnChanRegistered(c->ci); + } + + void OnChanRegistered(ChannelInfo *ci) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + if (use_server_side_mlock && ci->c && modelocks && !modelocks->GetMLockAsString(false).empty()) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", ""); + SendChannelMetadata(ci->c, "mlock", modes); + } + + if (use_server_side_topiclock && Servers::Capab.count("TOPICLOCK") && ci->c) + { + if (ci->HasExt("TOPICLOCK")) + SendChannelMetadata(ci->c, "topiclock", "1"); + } + } + + void OnDelChan(ChannelInfo *ci) anope_override + { + if (use_server_side_mlock && ci->c) + SendChannelMetadata(ci->c, "mlock", ""); + + if (use_server_side_topiclock && Servers::Capab.count("TOPICLOCK") && ci->c) + SendChannelMetadata(ci->c, "topiclock", ""); + } + + EventReturn OnMLock(ChannelInfo *ci, ModeLock *lock) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + ChannelMode *cm = ModeManager::FindChannelModeByName(lock->name); + if (use_server_side_mlock && cm && ci->c && modelocks && (cm->type == MODE_REGULAR || cm->type == MODE_PARAM)) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", "") + cm->mchar; + SendChannelMetadata(ci->c, "mlock", modes); + } + + return EVENT_CONTINUE; + } + + EventReturn OnUnMLock(ChannelInfo *ci, ModeLock *lock) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + ChannelMode *cm = ModeManager::FindChannelModeByName(lock->name); + if (use_server_side_mlock && cm && ci->c && modelocks && (cm->type == MODE_REGULAR || cm->type == MODE_PARAM)) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", "").replace_all_cs(cm->mchar, ""); + SendChannelMetadata(ci->c, "mlock", modes); + } + + return EVENT_CONTINUE; + } + + EventReturn OnSetChannelOption(CommandSource &source, Command *cmd, ChannelInfo *ci, const Anope::string &setting) anope_override + { + if (cmd->name == "chanserv/topic" && ci->c) + { + if (setting == "topiclock on") + SendChannelMetadata(ci->c, "topiclock", "1"); + else if (setting == "topiclock off") + SendChannelMetadata(ci->c, "topiclock", "0"); + } + + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(ProtoInspIRCd3) diff --git a/modules/protocol/ngircd.cpp b/modules/protocol/ngircd.cpp new file mode 100644 index 0000000..731ac9c --- /dev/null +++ b/modules/protocol/ngircd.cpp @@ -0,0 +1,679 @@ +/* ngIRCd Protocol module for Anope IRC Services + * + * (C) 2011-2012, 2014 Alexander Barton + * (C) 2011-2022 Anope Team + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class ngIRCdProto : public IRCDProto +{ + void SendSVSKillInternal(const MessageSource &source, User *user, const Anope::string &buf) anope_override + { + IRCDProto::SendSVSKillInternal(source, user, buf); + user->KillInternal(source, buf); + } + + public: + ngIRCdProto(Module *creator) : IRCDProto(creator, "ngIRCd") + { + DefaultPseudoclientModes = "+oi"; + CanCertFP = true; + CanSVSNick = true; + CanSetVHost = true; + CanSetVIdent = true; + MaxModes = 5; + } + + void SendAkill(User *u, XLine *x) anope_override + { + // Calculate the time left before this would expire, capping it at 2 days + time_t timeleft = x->expires - Anope::CurTime; + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + UplinkSocket::Message(Me) << "GLINE " << x->mask << " " << timeleft << " :" << x->GetReason() << " (" << x->by << ")"; + } + + void SendAkillDel(const XLine *x) anope_override + { + UplinkSocket::Message(Me) << "GLINE " << x->mask; + } + + void SendChannel(Channel *c) anope_override + { + UplinkSocket::Message(Me) << "CHANINFO " << c->name << " +" << c->GetModes(true, true); + } + + // Received: :dev.anope.de NICK DukeP 1 ~DukePyro p57ABF9C9.dip.t-dialin.net 1 +i :DukePyrolator + void SendClientIntroduction(User *u) anope_override + { + Anope::string modes = "+" + u->GetModes(); + UplinkSocket::Message(Me) << "NICK " << u->nick << " 1 " << u->GetIdent() << " " << u->host << " 1 " << modes << " :" << u->realname; + } + + void SendConnect() anope_override + { + UplinkSocket::Message() << "PASS " << Config->Uplinks[Anope::CurrentUplink].password << " 0210-IRC+ Anope|" << Anope::VersionShort() << ":CLHMSo P"; + /* Make myself known to myself in the serverlist */ + SendServer(Me); + /* finish the enhanced server handshake and register the connection */ + this->SendNumeric(376, "*", ":End of MOTD command"); + } + + void SendForceNickChange(User *u, const Anope::string &newnick, time_t when) anope_override + { + UplinkSocket::Message(Me) << "SVSNICK " << u->nick << " " << newnick; + } + + void SendGlobalNotice(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "NOTICE $" << dest->GetName() << " :" << msg; + } + + void SendGlobalPrivmsg(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "PRIVMSG $" << dest->GetName() << " :" << msg; + } + + void SendGlobopsInternal(const MessageSource &source, const Anope::string &buf) anope_override + { + UplinkSocket::Message(source) << "WALLOPS :" << buf; + } + + void SendJoin(User *user, Channel *c, const ChannelStatus *status) anope_override + { + UplinkSocket::Message(user) << "JOIN " << c->name; + if (status) + { + /* First save the channel status incase uc->Status == status */ + ChannelStatus cs = *status; + /* If the user is internally on the channel with flags, kill them so that + * the stacker will allow this. + */ + ChanUserContainer *uc = c->FindUser(user); + if (uc != NULL) + uc->status.Clear(); + + BotInfo *setter = BotInfo::Find(user->GetUID()); + for (size_t i = 0; i < cs.Modes().length(); ++i) + c->SetMode(setter, ModeManager::FindChannelModeByChar(cs.Modes()[i]), user->GetUID(), false); + + if (uc != NULL) + uc->status = cs; + } + } + + void SendLogin(User *u, NickAlias *na) anope_override + { + UplinkSocket::Message(Me) << "METADATA " << u->GetUID() << " accountname :" << na->nc->display; + } + + void SendLogout(User *u) anope_override + { + UplinkSocket::Message(Me) << "METADATA " << u->GetUID() << " accountname :"; + } + + /* SERVER name hop descript */ + void SendServer(const Server *server) anope_override + { + UplinkSocket::Message() << "SERVER " << server->GetName() << " " << server->GetHops() << " :" << server->GetDescription(); + } + + void SendVhost(User *u, const Anope::string &vIdent, const Anope::string &vhost) anope_override + { + if (!vIdent.empty()) + UplinkSocket::Message(Me) << "METADATA " << u->nick << " user :" << vIdent; + + UplinkSocket::Message(Me) << "METADATA " << u->nick << " cloakhost :" << vhost; + if (!u->HasMode("CLOAK")) + { + u->SetMode(Config->GetClient("HostServ"), "CLOAK"); + ModeManager::ProcessModes(); + } + } + + void SendVhostDel(User *u) anope_override + { + this->SendVhost(u, u->GetIdent(), ""); + } + + Anope::string Format(const Anope::string &source, const Anope::string &message) anope_override + { + return IRCDProto::Format(source.empty() ? Me->GetSID() : source, message); + } +}; + +struct IRCDMessage005 : IRCDMessage +{ + IRCDMessage005(Module *creator) : IRCDMessage(creator, "005", 1) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + // Please see for details. + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + size_t pos; + Anope::string parameter, data; + for (unsigned i = 0, end = params.size(); i < end; ++i) + { + pos = params[i].find('='); + if (pos != Anope::string::npos) + { + parameter = params[i].substr(0, pos); + data = params[i].substr(pos+1, params[i].length()); + if (parameter == "MODES") + { + unsigned maxmodes = convertTo(data); + IRCD->MaxModes = maxmodes; + } + else if (parameter == "NICKLEN") + { + unsigned newlen = convertTo(data), len = Config->GetBlock("networkinfo")->Get("nicklen"); + if (len != newlen) + { + Log() << "Warning: NICKLEN is " << newlen << " but networkinfo:nicklen is " << len; + } + } + } + } + } +}; + +struct IRCDMessage376 : IRCDMessage +{ + IRCDMessage376(Module *creator) : IRCDMessage(creator, "376", 2) { } + + /* + * :ngircd.dev.anope.de 376 services.anope.de :End of MOTD command + * + * we do nothing here, this function exists only to + * avoid the "unknown message from server" message. + * + */ + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + } +}; + +struct IRCDMessageChaninfo : IRCDMessage +{ + IRCDMessageChaninfo(Module *creator) : IRCDMessage(creator, "CHANINFO", 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + /* + * CHANINFO is used by servers to inform each other about a channel: its + * modes, channel key, user limits and its topic. The parameter combination + * and is optional, as well as the parameter, so that + * there are three possible forms of this command: + * + * CHANINFO + + * CHANINFO + : + * CHANINFO + : + * + * The parameter must be ignored if a channel has no key (the parameter + * doesn't list the "k" channel mode). In this case should + * contain "*" because the parameter is required by the CHANINFO syntax + * and therefore can't be omitted. The parameter must be ignored when + * a channel has no user limit (the parameter doesn't list the "l" + * channel mode). In this case should be "0". + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + bool created; + Channel *c = Channel::FindOrCreate(params[0], created); + + Anope::string modes = params[1]; + + if (params.size() == 3) + { + c->ChangeTopicInternal(NULL, source.GetName(), params[2], Anope::CurTime); + } + else if (params.size() == 5) + { + for (size_t i = 0, end = params[1].length(); i < end; ++i) + { + switch(params[1][i]) + { + case 'k': + modes += " " + params[2]; + continue; + case 'l': + modes += " " + params[3]; + continue; + } + } + c->ChangeTopicInternal(NULL, source.GetName(), params[4], Anope::CurTime); + } + + c->SetModesInternal(source, modes); + } +}; + +struct IRCDMessageJoin : Message::Join +{ + IRCDMessageJoin(Module *creator) : Message::Join(creator, "JOIN") { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + /* + * <@po||ux> DukeP: RFC 2813, 4.2.1: the JOIN command on server-server links + * separates the modes ("o") with ASCII 7, not space. And you can't see ASCII 7. + * + * if a user joins a new channel, the ircd sends \7 + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *user = source.GetUser(); + size_t pos = params[0].find('\7'); + Anope::string channel, modes; + + if (pos != Anope::string::npos) + { + channel = params[0].substr(0, pos); + modes = '+' + params[0].substr(pos+1, params[0].length()) + " " + user->nick; + } + else + { + channel = params[0]; + } + + std::vector new_params; + new_params.push_back(channel); + + Message::Join::Run(source, new_params); + + if (!modes.empty()) + { + Channel *c = Channel::Find(channel); + if (c) + c->SetModesInternal(source, modes); + } + } +}; + +struct IRCDMessageMetadata : IRCDMessage +{ + IRCDMessageMetadata(Module *creator) : IRCDMessage(creator, "METADATA", 3) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + /* + * Received: :ngircd.dev.anope.de METADATA DukePyrolator host :anope-e2ee5c7d + * + * params[0] = nick of the user + * params[1] = command + * params[2] = data + * + * following commands are supported: + * - "accountname": the account name of a client (can't be empty) + * - "certfp": the certificate fingerprint of a client (can't be empty) + * - "cloakhost" : the cloaked hostname of a client + * - "host": the hostname of a client (can't be empty) + * - "info": info text ("real name") of a client + * - "user": the user name (ident) of a client (can't be empty) + */ + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = User::Find(params[0]); + if (!u) + { + Log(LOG_DEBUG) << "received METADATA for nonexistent user " << params[0]; + return; + } + if (params[1].equals_cs("accountname")) + { + NickCore *nc = NickCore::Find(params[2]); + if (nc) + u->Login(nc); + } + else if (params[1].equals_cs("certfp")) + { + u->fingerprint = params[2]; + FOREACH_MOD(OnFingerprint, (u)); + } + else if (params[1].equals_cs("cloakhost")) + { + if (!params[2].empty()) + u->SetDisplayedHost(params[2]); + } + else if (params[1].equals_cs("host")) + { + u->SetCloakedHost(params[2]); + } + else if (params[1].equals_cs("info")) + { + u->SetRealname(params[2]); + } + else if (params[1].equals_cs("user")) + { + u->SetVIdent(params[2]); + } + } +}; + +struct IRCDMessageMode : IRCDMessage +{ + IRCDMessageMode(Module *creator) : IRCDMessage(creator, "MODE", 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* + * Received: :DukeP MODE #anope +b *!*@*.aol.com + * Received: :DukeP MODE #anope +h DukeP + * params[0] = channel or nick + * params[1] = modes + * params[n] = parameters + */ + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Anope::string modes = params[1]; + + for (size_t i = 2; i < params.size(); ++i) + modes += " " + params[i]; + + if (IRCD->IsChannelValid(params[0])) + { + Channel *c = Channel::Find(params[0]); + + if (c) + c->SetModesInternal(source, modes); + } + else + { + User *u = User::Find(params[0]); + + if (u) + u->SetModesInternal(source, "%s", params[1].c_str()); + } + } +}; + +struct IRCDMessageNick : IRCDMessage +{ + IRCDMessageNick(Module *creator) : IRCDMessage(creator, "NICK", 1) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* + * NICK - NEW + * Received: :dev.anope.de NICK DukeP_ 1 ~DukePyro ip-2-201-236-154.web.vodafone.de 1 + :DukePyrolator + * Parameters: : + * source = server + * params[0] = nick + * params[1] = hopcount + * params[2] = username/ident + * params[3] = host + * params[4] = servertoken + * params[5] = modes + * params[6] = info + * + * NICK - change + * Received: :DukeP_ NICK :test2 + * source = oldnick + * params[0] = newnick + * + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params.size() == 1) + { + User *u = source.GetUser(); + + // we have a nickchange + if (u) + u->ChangeNick(params[0]); + } + else if (params.size() == 7) + { + // a new user is connecting to the network + Server *s = Server::Find(params[4]); + if (s == NULL) + { + Log(LOG_DEBUG) << "User " << params[0] << " introduced from nonexistent server " << params[4] << "?"; + return; + } + User::OnIntroduce(params[0], params[2], params[3], "", "", s, params[6], Anope::CurTime, params[5], "", NULL); + Log(LOG_DEBUG) << "Registered nick \"" << params[0] << "\" on server " << s->GetName() << "."; + } + else + { + Log(LOG_DEBUG) << "Received NICK with invalid number of parameters. source = " << source.GetName() << "params[0] = " << params[0] << "params.size() = " << params.size(); + } + } +}; + +struct IRCDMessageNJoin : IRCDMessage +{ + IRCDMessageNJoin(Module *creator) : IRCDMessage(creator, "NJOIN",2) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); }; + + /* + * RFC 2813, 4.2.2: Njoin Message: + * The NJOIN message is used between servers only. + * It is used when two servers connect to each other to exchange + * the list of channel members for each channel. + * + * Even though the same function can be performed by using a succession + * of JOIN, this message SHOULD be used instead as it is more efficient. + * + * Received: :dev.anope.de NJOIN #test :DukeP2,@DukeP,%test,+test2 + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + std::list users; + + commasepstream sep(params[1]); + Anope::string buf; + while (sep.GetToken(buf)) + { + + Message::Join::SJoinUser sju; + + /* Get prefixes from the nick */ + for (char ch; (ch = ModeManager::GetStatusChar(buf[0]));) + { + buf.erase(buf.begin()); + sju.first.AddMode(ch); + } + + sju.second = User::Find(buf); + if (!sju.second) + { + Log(LOG_DEBUG) << "NJOIN for nonexistent user " << buf << " on " << params[0]; + continue; + } + users.push_back(sju); + } + + Message::Join::SJoin(source, params[0], 0, "", users); + } +}; + +struct IRCDMessagePong : IRCDMessage +{ + IRCDMessagePong(Module *creator) : IRCDMessage(creator, "PONG", 0) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + /* + * ngIRCd does not send an EOB, so we send a PING immediately + * when receiving a new server and then finish sync once we + * get a pong back from that server. + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (!source.GetServer()->IsSynced()) + source.GetServer()->Sync(false); + } +}; + +struct IRCDMessageServer : IRCDMessage +{ + IRCDMessageServer(Module *creator) : IRCDMessage(creator, "SERVER", 3) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* + * New directly linked server: + * + * SERVER tolsun.oulu.fi 1 :Experimental server + * New server tolsun.oulu.fi introducing itself + * and attempting to register. + * + * params[0] = servername + * params[1] = hop count + * params[2] = server description + * + * New remote server in the network: + * + * :tolsun.oulu.fi SERVER csd.bu.edu 5 34 :BU Central Server + * Server tolsun.oulu.fi is our uplink for csd.bu.edu + * which is 5 hops away. The token "34" will be used + * by tolsun.oulu.fi when introducing new users or + * services connected to csd.bu.edu. + * + * params[0] = servername + * params[1] = hop count + * params[2] = server numeric + * params[3] = server description + */ + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params.size() == 3) + { + // our uplink is introducing itself + new Server(Me, params[0], 1, params[2], "1"); + } + else + { + // our uplink is introducing a new server + unsigned int hops = params[1].is_pos_number_only() ? convertTo(params[1]) : 0; + new Server(source.GetServer(), params[0], hops, params[3], params[2]); + } + /* + * ngIRCd does not send an EOB, so we send a PING immediately + * when receiving a new server and then finish sync once we + * get a pong back from that server. + */ + IRCD->SendPing(Me->GetName(), params[0]); + } +}; + +struct IRCDMessageTopic : IRCDMessage +{ + IRCDMessageTopic(Module *creator) : IRCDMessage(creator, "TOPIC", 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + // Received: :DukeP TOPIC #anope :test + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Channel *c = Channel::Find(params[0]); + if (!c) + { + Log(LOG_DEBUG) << "TOPIC for nonexistent channel " << params[0]; + return; + } + c->ChangeTopicInternal(source.GetUser(), source.GetName(), params[1], Anope::CurTime); + } +}; + + + +class ProtongIRCd : public Module +{ + ngIRCdProto ircd_proto; + + /* Core message handlers */ + Message::Capab message_capab; + Message::Error message_error; + Message::Invite message_invite; + Message::Kick message_kick; + Message::Kill message_kill; + Message::MOTD message_motd; + Message::Notice message_notice; + Message::Part message_part; + Message::Ping message_ping; + Message::Privmsg message_privmsg, message_squery; + Message::Quit message_quit; + Message::SQuit message_squit; + Message::Stats message_stats; + Message::Time message_time; + Message::Version message_version; + Message::Whois message_whois; + + /* Our message handlers */ + IRCDMessage005 message_005; + IRCDMessage376 message_376; + IRCDMessageChaninfo message_chaninfo; + IRCDMessageJoin message_join; + IRCDMessageMetadata message_metadata; + IRCDMessageMode message_mode; + IRCDMessageNick message_nick; + IRCDMessageNJoin message_njoin; + IRCDMessagePong message_pong; + IRCDMessageServer message_server; + IRCDMessageTopic message_topic; + + void AddModes() + { + /* Add user modes */ + ModeManager::AddUserMode(new UserMode("NOCTCP", 'b')); + ModeManager::AddUserMode(new UserMode("BOT", 'B')); + ModeManager::AddUserMode(new UserMode("COMMONCHANS", 'C')); + ModeManager::AddUserMode(new UserMode("INVIS", 'i')); + ModeManager::AddUserMode(new UserModeOperOnly("OPER", 'o')); + ModeManager::AddUserMode(new UserModeOperOnly("PROTECTED", 'q')); + ModeManager::AddUserMode(new UserModeOperOnly("RESTRICTED", 'r')); + ModeManager::AddUserMode(new UserModeNoone("REGISTERED", 'R')); + ModeManager::AddUserMode(new UserModeOperOnly("SNOMASK", 's')); + ModeManager::AddUserMode(new UserMode("WALLOPS", 'w')); + ModeManager::AddUserMode(new UserMode("CLOAK", 'x')); + + /* Add modes for ban, exception, and invite lists */ + ModeManager::AddChannelMode(new ChannelModeList("BAN", 'b')); + ModeManager::AddChannelMode(new ChannelModeList("EXCEPT", 'e')); + ModeManager::AddChannelMode(new ChannelModeList("INVITEOVERRIDE", 'I')); + + /* Add channel user modes */ + ModeManager::AddChannelMode(new ChannelModeStatus("VOICE", 'v', '+', 0)); + ModeManager::AddChannelMode(new ChannelModeStatus("HALFOP", 'h', '%', 1)); + ModeManager::AddChannelMode(new ChannelModeStatus("OP", 'o', '@', 2)); + ModeManager::AddChannelMode(new ChannelModeStatus("PROTECT", 'a', '&', 3)); + ModeManager::AddChannelMode(new ChannelModeStatus("OWNER", 'q', '~', 4)); + + /* Add channel modes */ + ModeManager::AddChannelMode(new ChannelMode("INVITE", 'i')); + ModeManager::AddChannelMode(new ChannelModeKey('k')); + ModeManager::AddChannelMode(new ChannelModeParam("LIMIT", 'l', true)); + ModeManager::AddChannelMode(new ChannelMode("MODERATED", 'm')); + ModeManager::AddChannelMode(new ChannelMode("REGMODERATED", 'M')); + ModeManager::AddChannelMode(new ChannelMode("NOEXTERNAL", 'n')); + ModeManager::AddChannelMode(new ChannelMode("OPERONLY", 'O')); + ModeManager::AddChannelMode(new ChannelMode("PERM", 'P')); + ModeManager::AddChannelMode(new ChannelMode("NOKICK", 'Q')); + ModeManager::AddChannelMode(new ChannelModeNoone("REGISTERED", 'r')); + ModeManager::AddChannelMode(new ChannelMode("REGISTEREDONLY", 'R')); + ModeManager::AddChannelMode(new ChannelMode("SECRET", 's')); + ModeManager::AddChannelMode(new ChannelMode("TOPIC", 't')); + ModeManager::AddChannelMode(new ChannelMode("NOINVITE", 'V')); + ModeManager::AddChannelMode(new ChannelMode("SSL", 'z')); + } + + public: + ProtongIRCd(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PROTOCOL | VENDOR), + ircd_proto(this), + message_capab(this), message_error(this), message_invite(this), message_kick(this), message_kill(this), + message_motd(this), message_notice(this), message_part(this), message_ping(this), message_privmsg(this), + message_squery(this, "SQUERY"), message_quit(this), message_squit(this), message_stats(this), message_time(this), + message_version(this), message_whois(this), + + message_005(this), message_376(this), message_chaninfo(this), message_join(this), message_metadata(this), + message_mode(this), message_nick(this), message_njoin(this), message_pong(this), message_server(this), + message_topic(this) + { + + Servers::Capab.insert("QS"); + + this->AddModes(); + + } + + void OnUserNickChange(User *u, const Anope::string &) anope_override + { + u->RemoveMode(Config->GetClient("NickServ"), "REGISTERED"); + } +}; + +MODULE_INIT(ProtongIRCd) diff --git a/modules/protocol/plexus.cpp b/modules/protocol/plexus.cpp new file mode 100644 index 0000000..1eb25cd --- /dev/null +++ b/modules/protocol/plexus.cpp @@ -0,0 +1,451 @@ +/* Plexus 3+ IRCD functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/sasl.h" + +static Anope::string UplinkSID; + +static ServiceReference hybrid("IRCDProto", "hybrid"); + +class PlexusProto : public IRCDProto +{ + public: + PlexusProto(Module *creator) : IRCDProto(creator, "hybrid-7.2.3+plexus-3.0.1") + { + DefaultPseudoclientModes = "+iU"; + CanSVSNick = true; + CanSVSJoin = true; + CanSetVHost = true; + CanSetVIdent = true; + CanSNLine = true; + CanSQLine = true; + CanSQLineChannel = true; + CanSVSHold = true; + CanCertFP = true; + RequiresID = true; + MaxModes = 4; + } + + void SendSVSKillInternal(const MessageSource &source, User *targ, const Anope::string &reason) anope_override { hybrid->SendSVSKillInternal(source, targ, reason); } + void SendGlobalNotice(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override { hybrid->SendGlobalNotice(bi, dest, msg); } + void SendGlobalPrivmsg(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override { hybrid->SendGlobalPrivmsg(bi, dest, msg); } + void SendSQLine(User *u, const XLine *x) anope_override { hybrid->SendSQLine(u, x); } + void SendSQLineDel(const XLine *x) anope_override { hybrid->SendSQLineDel(x); } + void SendSGLineDel(const XLine *x) anope_override { hybrid->SendSGLineDel(x); } + void SendSGLine(User *u, const XLine *x) anope_override { hybrid->SendSGLine(u, x); } + void SendAkillDel(const XLine *x) anope_override { hybrid->SendAkillDel(x); } + void SendAkill(User *u, XLine *x) anope_override { hybrid->SendAkill(u, x); } + void SendServer(const Server *server) anope_override { hybrid->SendServer(server); } + void SendChannel(Channel *c) anope_override { hybrid->SendChannel(c); } + void SendSVSHold(const Anope::string &nick, time_t t) anope_override { hybrid->SendSVSHold(nick, t); } + void SendSVSHoldDel(const Anope::string &nick) anope_override { hybrid->SendSVSHoldDel(nick); } + + void SendGlobopsInternal(const MessageSource &source, const Anope::string &buf) anope_override + { + UplinkSocket::Message(source) << "OPERWALL :" << buf; + } + + void SendJoin(User *user, Channel *c, const ChannelStatus *status) anope_override + { + UplinkSocket::Message(Me) << "SJOIN " << c->creation_time << " " << c->name << " +" << c->GetModes(true, true) << " :" << user->GetUID(); + if (status) + { + /* First save the channel status incase uc->Status == status */ + ChannelStatus cs = *status; + /* If the user is internally on the channel with flags, kill them so that + * the stacker will allow this. + */ + ChanUserContainer *uc = c->FindUser(user); + if (uc != NULL) + uc->status.Clear(); + + BotInfo *setter = BotInfo::Find(user->GetUID()); + for (size_t i = 0; i < cs.Modes().length(); ++i) + c->SetMode(setter, ModeManager::FindChannelModeByChar(cs.Modes()[i]), user->GetUID(), false); + + if (uc != NULL) + uc->status = cs; + } + } + + void SendForceNickChange(User *u, const Anope::string &newnick, time_t when) anope_override + { + UplinkSocket::Message(Me) << "ENCAP " << u->server->GetName() << " SVSNICK " << u->GetUID() << " " << u->timestamp << " " << newnick << " " << when; + } + + void SendVhost(User *u, const Anope::string &ident, const Anope::string &host) anope_override + { + if (!ident.empty()) + UplinkSocket::Message(Me) << "ENCAP * CHGIDENT " << u->GetUID() << " " << ident; + UplinkSocket::Message(Me) << "ENCAP * CHGHOST " << u->GetUID() << " " << host; + u->SetMode(Config->GetClient("HostServ"), "CLOAK"); + } + + void SendVhostDel(User *u) anope_override + { + u->RemoveMode(Config->GetClient("HostServ"), "CLOAK"); + } + + void SendConnect() anope_override + { + UplinkSocket::Message() << "PASS " << Config->Uplinks[Anope::CurrentUplink].password << " TS 6 :" << Me->GetSID(); + /* CAPAB + * QS - Can handle quit storm removal + * EX - Can do channel +e exemptions + * CHW - Can do channel wall @# + * LL - Can do lazy links + * IE - Can do invite exceptions + * EOB - Can do EOB message + * KLN - Can do KLINE message + * GLN - Can do GLINE message + * HUB - This server is a HUB + * AOPS - Can do anon ops (+a) + * UID - Can do UIDs + * ZIP - Can do ZIPlinks + * ENC - Can do ENCrypted links + * KNOCK - Supports KNOCK + * TBURST - Supports TBURST + * PARA - Supports invite broadcasting for +p + * ENCAP - Supports encapsulation of protocol messages + * SVS - Supports services protocol extensions + */ + UplinkSocket::Message() << "CAPAB :QS EX CHW IE EOB KLN UNKLN GLN HUB KNOCK TBURST PARA ENCAP SVS"; + /* Make myself known to myself in the serverlist */ + SendServer(Me); + /* + * SVINFO + * parv[0] = sender prefix + * parv[1] = TS_CURRENT for the server + * parv[2] = TS_MIN for the server + * parv[3] = server is standalone or connected to non-TS only + * parv[4] = server's idea of UTC time + */ + UplinkSocket::Message() << "SVINFO 6 5 0 :" << Anope::CurTime; + } + + void SendClientIntroduction(User *u) anope_override + { + Anope::string modes = "+" + u->GetModes(); + UplinkSocket::Message(Me) << "UID " << u->nick << " 1 " << u->timestamp << " " << modes << " " << u->GetIdent() << " " << u->host << " 255.255.255.255 " << u->GetUID() << " 0 " << u->host << " :" << u->realname; + } + + void SendModeInternal(const MessageSource &source, User *u, const Anope::string &buf) anope_override + { + UplinkSocket::Message(source) << "ENCAP * SVSMODE " << u->GetUID() << " " << u->timestamp << " " << buf; + } + + void SendLogin(User *u, NickAlias *na) anope_override + { + UplinkSocket::Message(Me) << "ENCAP * SU " << u->GetUID() << " " << na->nc->display; + } + + void SendLogout(User *u) anope_override + { + UplinkSocket::Message(Me) << "ENCAP * SU " << u->GetUID(); + } + + void SendTopic(const MessageSource &source, Channel *c) anope_override + { + UplinkSocket::Message(source) << "ENCAP * TOPIC " << c->name << " " << c->topic_setter << " " << c->topic_ts << " :" << c->topic; + } + + void SendSVSJoin(const MessageSource &source, User *user, const Anope::string &chan, const Anope::string ¶m) anope_override + { + UplinkSocket::Message(source) << "ENCAP " << user->server->GetName() << " SVSJOIN " << user->GetUID() << " " << chan; + } + + void SendSVSPart(const MessageSource &source, User *user, const Anope::string &chan, const Anope::string ¶m) anope_override + { + UplinkSocket::Message(source) << "ENCAP " << user->server->GetName() << " SVSPART " << user->GetUID() << " " << chan; + } + + void SendSASLMessage(const SASL::Message &message) anope_override + { + Server *s = Server::Find(message.target.substr(0, 3)); + UplinkSocket::Message(Me) << "ENCAP " << (s ? s->GetName() : message.target.substr(0, 3)) << " SASL " << message.source << " " << message.target << " " << message.type << " " << message.data << (message.ext.empty() ? "" : (" " + message.ext)); + } + + void SendSVSLogin(const Anope::string &uid, const Anope::string &acc, const Anope::string &vident, const Anope::string &vhost) anope_override + { + Server *s = Server::Find(uid.substr(0, 3)); + UplinkSocket::Message(Me) << "ENCAP " << (s ? s->GetName() : uid.substr(0, 3)) << " SVSLOGIN " << uid << " * * " + << (vhost.empty() ? "*" : vhost) << " " << acc; + } + + void SendSVSNOOP(const Server *server, bool set) anope_override + { + UplinkSocket::Message() << "ENCAP " << server->GetName() << " SVSNOOP " << (set ? "+" : "-"); + } +}; + +struct IRCDMessageEncap : IRCDMessage +{ + IRCDMessageEncap(Module *creator) : IRCDMessage(creator, "ENCAP", 4) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + /* + * Received: :dev.anope.de ENCAP * SU DukePyrolator DukePyrolator + * params[0] = * + * params[1] = SU + * params[2] = nickname + * params[3] = account + */ + if (params[1].equals_cs("SU")) + { + User *u = User::Find(params[2]); + NickCore *nc = NickCore::Find(params[3]); + if (u && nc) + { + u->Login(nc); + } + } + + /* + * Received: :dev.anope.de ENCAP * CERTFP DukePyrolator :3F122A9CC7811DBAD3566BF2CEC3009007C0868F + * params[0] = * + * params[1] = CERTFP + * params[2] = nickname + * params[3] = fingerprint + */ + else if (params[1].equals_cs("CERTFP")) + { + User *u = User::Find(params[2]); + if (u) + { + u->fingerprint = params[3]; + FOREACH_MOD(OnFingerprint, (u)); + } + } + + else if (params[1] == "SASL" && SASL::sasl && params.size() >= 6) + { + SASL::Message m; + m.source = params[2]; + m.target = params[3]; + m.type = params[4]; + m.data = params[5]; + m.ext = params.size() > 6 ? params[6] : ""; + + SASL::sasl->ProcessMessage(m); + } + + return; + } +}; + +struct IRCDMessagePass : IRCDMessage +{ + IRCDMessagePass(Module *creator) : IRCDMessage(creator, "PASS", 4) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + UplinkSID = params[3]; + } +}; + +struct IRCDMessageServer : IRCDMessage +{ + IRCDMessageServer(Module *creator) : IRCDMessage(creator, "SERVER", 3) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + /* 0 1 2 */ + /* SERVER hades.arpa 1 :ircd-hybrid test server */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + /* Servers other than our immediate uplink are introduced via SID */ + if (params[1] != "1") + return; + + new Server(source.GetServer() == NULL ? Me : source.GetServer(), params[0], 1, params[2], UplinkSID); + } +}; + +struct IRCDMessageUID : IRCDMessage +{ + IRCDMessageUID(Module *creator) : IRCDMessage(creator, "UID", 11) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + /* + params[0] = nick + params[1] = hop + params[2] = ts + params[3] = modes + params[4] = user + params[5] = host + params[6] = IP + params[7] = UID + params[8] = services stamp + params[9] = realhost + params[10] = info + */ + // :42X UID Adam 1 1348535644 +aow Adam 192.168.0.5 192.168.0.5 42XAAAAAB 0 192.168.0.5 :Adam + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + /* An IP of 0 means the user is spoofed */ + Anope::string ip = params[6]; + if (ip == "0") + ip.clear(); + + time_t ts; + try + { + ts = convertTo(params[2]); + } + catch (const ConvertException &) + { + ts = Anope::CurTime; + } + + NickAlias *na = NULL; + try + { + if (params[8].is_pos_number_only() && convertTo(params[8]) == ts) + na = NickAlias::Find(params[0]); + } + catch (const ConvertException &) { } + if (params[8] != "0" && !na) + na = NickAlias::Find(params[8]); + + User::OnIntroduce(params[0], params[4], params[9], params[5], ip, source.GetServer(), params[10], ts, params[3], params[7], na ? *na->nc : NULL); + } +}; + +class ProtoPlexus : public Module +{ + Module *m_hybrid; + + PlexusProto ircd_proto; + + /* Core message handlers */ + Message::Away message_away; + Message::Capab message_capab; + Message::Error message_error; + Message::Invite message_invite; + Message::Kick message_kick; + Message::Kill message_kill; + Message::Mode message_mode; + Message::MOTD message_motd; + Message::Notice message_notice; + Message::Part message_part; + Message::Ping message_ping; + Message::Privmsg message_privmsg; + Message::Quit message_quit; + Message::SQuit message_squit; + Message::Stats message_stats; + Message::Time message_time; + Message::Topic message_topic; + Message::Version message_version; + Message::Whois message_whois; + + /* Hybrid message handlers */ + ServiceAlias message_bmask, message_eob, message_join, message_nick, message_sid, message_sjoin, + message_tburst, message_tmode; + + /* Our message handlers */ + IRCDMessageEncap message_encap; + IRCDMessagePass message_pass; + IRCDMessageServer message_server; + IRCDMessageUID message_uid; + + void AddModes() + { + /* Add user modes */ + ModeManager::AddUserMode(new UserModeOperOnly("ADMIN", 'a')); + ModeManager::AddUserMode(new UserMode("NOCTCP", 'C')); + ModeManager::AddUserMode(new UserMode("DEAF", 'D')); + ModeManager::AddUserMode(new UserMode("SOFTCALLERID", 'G')); + ModeManager::AddUserMode(new UserMode("CALLERID", 'g')); + ModeManager::AddUserMode(new UserMode("INVIS", 'i')); + ModeManager::AddUserMode(new UserModeOperOnly("LOCOPS", 'l')); + ModeManager::AddUserMode(new UserModeOperOnly("OPER", 'o')); + ModeManager::AddUserMode(new UserModeOperOnly("NETADMIN", 'N')); + ModeManager::AddUserMode(new UserMode("PRIV", 'p')); + ModeManager::AddUserMode(new UserModeOperOnly("ROUTING", 'q')); + ModeManager::AddUserMode(new UserModeNoone("REGISTERED", 'r')); + ModeManager::AddUserMode(new UserMode("REGPRIV", 'R')); + ModeManager::AddUserMode(new UserModeOperOnly("SNOMASK", 's')); + ModeManager::AddUserMode(new UserModeNoone("SSL", 'S')); + ModeManager::AddUserMode(new UserModeNoone("PROTECTED", 'U')); + ModeManager::AddUserMode(new UserMode("WALLOPS", 'w')); + ModeManager::AddUserMode(new UserModeNoone("WEBIRC", 'W')); + ModeManager::AddUserMode(new UserMode("CLOAK", 'x')); + ModeManager::AddUserMode(new UserModeOperOnly("OPERWALLS", 'z')); + + /* b/e/I */ + ModeManager::AddChannelMode(new ChannelModeList("BAN", 'b')); + ModeManager::AddChannelMode(new ChannelModeList("EXCEPT", 'e')); + ModeManager::AddChannelMode(new ChannelModeList("INVITEOVERRIDE", 'I')); + + /* v/h/o/a/q */ + ModeManager::AddChannelMode(new ChannelModeStatus("VOICE", 'v', '+', 0)); + ModeManager::AddChannelMode(new ChannelModeStatus("HALFOP", 'h', '%', 1)); + ModeManager::AddChannelMode(new ChannelModeStatus("OP", 'o', '@', 2)); + ModeManager::AddChannelMode(new ChannelModeStatus("PROTECT", 'a', '&', 3)); + ModeManager::AddChannelMode(new ChannelModeStatus("OWNER", 'q', '~', 4)); + + /* l/k */ + ModeManager::AddChannelMode(new ChannelModeParam("LIMIT", 'l', true)); + ModeManager::AddChannelMode(new ChannelModeKey('k')); + + /* Add channel modes */ + ModeManager::AddChannelMode(new ChannelMode("BANDWIDTH", 'B')); + ModeManager::AddChannelMode(new ChannelMode("NOCTCP", 'C')); + ModeManager::AddChannelMode(new ChannelMode("BLOCKCOLOR", 'c')); + ModeManager::AddChannelMode(new ChannelMode("INVITE", 'i')); + ModeManager::AddChannelMode(new ChannelMode("MODERATED", 'm')); + ModeManager::AddChannelMode(new ChannelMode("REGMODERATED", 'M')); + ModeManager::AddChannelMode(new ChannelMode("NOEXTERNAL", 'n')); + ModeManager::AddChannelMode(new ChannelMode("NONOTICE", 'N')); + ModeManager::AddChannelMode(new ChannelMode("PRIVATE", 'p')); + ModeManager::AddChannelMode(new ChannelMode("SECRET", 's')); + ModeManager::AddChannelMode(new ChannelMode("TOPIC", 't')); + ModeManager::AddChannelMode(new ChannelModeOperOnly("OPERONLY", 'O')); + ModeManager::AddChannelMode(new ChannelMode("REGISTEREDONLY", 'R')); + ModeManager::AddChannelMode(new ChannelMode("SSL", 'S')); + ModeManager::AddChannelMode(new ChannelMode("PERM", 'z')); + } + + public: + ProtoPlexus(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PROTOCOL | VENDOR), + ircd_proto(this), + message_away(this), message_capab(this), message_error(this), message_invite(this), message_kick(this), message_kill(this), + message_mode(this), message_motd(this), message_notice(this), message_part(this), message_ping(this), message_privmsg(this), + message_quit(this), message_squit(this), message_stats(this), message_time(this), message_topic(this), message_version(this), + message_whois(this), + + message_bmask("IRCDMessage", "plexus/bmask", "hybrid/bmask"), message_eob("IRCDMessage", "plexus/eob", "hybrid/eob"), + message_join("IRCDMessage", "plexus/join", "hybrid/join"), message_nick("IRCDMessage", "plexus/nick", "hybrid/nick"), + message_sid("IRCDMessage", "plexus/sid", "hybrid/sid"), + message_sjoin("IRCDMessage", "plexus/sjoin", "hybrid/sjoin"), message_tburst("IRCDMessage", "plexus/tburst", "hybrid/tburst"), + message_tmode("IRCDMessage", "plexus/tmode", "hybrid/tmode"), + + message_encap(this), message_pass(this), message_server(this), message_uid(this) + { + + if (ModuleManager::LoadModule("hybrid", User::Find(creator)) != MOD_ERR_OK) + throw ModuleException("Unable to load hybrid"); + m_hybrid = ModuleManager::FindModule("hybrid"); + if (!m_hybrid) + throw ModuleException("Unable to find hybrid"); + if (!hybrid) + throw ModuleException("No protocol interface for hybrid"); + + this->AddModes(); + } + + ~ProtoPlexus() + { + m_hybrid = ModuleManager::FindModule("hybrid"); + ModuleManager::UnloadModule(m_hybrid, NULL); + } +}; + +MODULE_INIT(ProtoPlexus) diff --git a/modules/protocol/ratbox.cpp b/modules/protocol/ratbox.cpp new file mode 100644 index 0000000..b9ff469 --- /dev/null +++ b/modules/protocol/ratbox.cpp @@ -0,0 +1,373 @@ +/* Ratbox IRCD functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +static Anope::string UplinkSID; + +static ServiceReference hybrid("IRCDProto", "hybrid"); + +class RatboxProto : public IRCDProto +{ + BotInfo *FindIntroduced() + { + BotInfo *bi = Config->GetClient("OperServ"); + + if (bi && bi->introduced) + return bi; + + for (botinfo_map::iterator it = BotListByNick->begin(), it_end = BotListByNick->end(); it != it_end; ++it) + if (it->second->introduced) + return it->second; + + return NULL; + } + + public: + RatboxProto(Module *creator) : IRCDProto(creator, "Ratbox 3.0+") + { + DefaultPseudoclientModes = "+oiS"; + CanSNLine = true; + CanSQLine = true; + CanSQLineChannel = true; + CanSZLine = true; + RequiresID = true; + MaxModes = 4; + } + + void SendSVSKillInternal(const MessageSource &source, User *targ, const Anope::string &reason) anope_override { hybrid->SendSVSKillInternal(source, targ, reason); } + void SendGlobalNotice(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override { hybrid->SendGlobalNotice(bi, dest, msg); } + void SendGlobalPrivmsg(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override { hybrid->SendGlobalPrivmsg(bi, dest, msg); } + void SendSGLine(User *u, const XLine *x) anope_override { hybrid->SendSGLine(u, x); } + void SendSGLineDel(const XLine *x) anope_override { hybrid->SendSGLineDel(x); } + void SendAkill(User *u, XLine *x) anope_override { hybrid->SendAkill(u, x); } + void SendAkillDel(const XLine *x) anope_override { hybrid->SendAkillDel(x); } + void SendJoin(User *user, Channel *c, const ChannelStatus *status) anope_override { hybrid->SendJoin(user, c, status); } + void SendServer(const Server *server) anope_override { hybrid->SendServer(server); } + void SendModeInternal(const MessageSource &source, User *u, const Anope::string &buf) anope_override { hybrid->SendModeInternal(source, u, buf); } + void SendChannel(Channel *c) anope_override { hybrid->SendChannel(c); } + bool IsIdentValid(const Anope::string &ident) anope_override { return hybrid->IsIdentValid(ident); } + + void SendGlobopsInternal(const MessageSource &source, const Anope::string &buf) anope_override + { + UplinkSocket::Message(source) << "OPERWALL :" << buf; + } + + void SendSQLine(User *, const XLine *x) anope_override + { + /* Calculate the time left before this would expire, capping it at 2 days */ + time_t timeleft = x->expires - Anope::CurTime; + + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + + UplinkSocket::Message(FindIntroduced()) << "ENCAP * RESV " << timeleft << " " << x->mask << " 0 :" << x->GetReason(); + } + + void SendSQLineDel(const XLine *x) anope_override + { + UplinkSocket::Message(Config->GetClient("OperServ")) << "ENCAP * UNRESV " << x->mask; + } + + void SendConnect() anope_override + { + UplinkSocket::Message() << "PASS " << Config->Uplinks[Anope::CurrentUplink].password << " TS 6 :" << Me->GetSID(); + /* + QS - Can handle quit storm removal + EX - Can do channel +e exemptions + CHW - Can do channel wall @# + IE - Can do invite exceptions + GLN - Can do GLINE message + KNOCK - supports KNOCK + TB - supports topic burst + ENCAP - supports ENCAP + */ + UplinkSocket::Message() << "CAPAB :QS EX CHW IE GLN TB ENCAP"; + /* Make myself known to myself in the serverlist */ + SendServer(Me); + /* + * SVINFO + * parv[0] = sender prefix + * parv[1] = TS_CURRENT for the server + * parv[2] = TS_MIN for the server + * parv[3] = server is standalone or connected to non-TS only + * parv[4] = server's idea of UTC time + */ + UplinkSocket::Message() << "SVINFO 6 3 0 :" << Anope::CurTime; + } + + void SendClientIntroduction(User *u) anope_override + { + Anope::string modes = "+" + u->GetModes(); + UplinkSocket::Message(Me) << "UID " << u->nick << " 1 " << u->timestamp << " " << modes << " " << u->GetIdent() << " " << u->host << " 0 " << u->GetUID() << " :" << u->realname; + } + + void SendLogin(User *u, NickAlias *na) anope_override + { + if (na->nc->HasExt("UNCONFIRMED")) + return; + + UplinkSocket::Message(Me) << "ENCAP * SU " << u->GetUID() << " " << na->nc->display; + } + + void SendLogout(User *u) anope_override + { + UplinkSocket::Message(Me) << "ENCAP * SU " << u->GetUID(); + } + + void SendTopic(const MessageSource &source, Channel *c) anope_override + { + BotInfo *bi = source.GetBot(); + bool needjoin = c->FindUser(bi) == NULL; + + if (needjoin) + { + ChannelStatus status; + + status.AddMode('o'); + bi->Join(c, &status); + } + + IRCDProto::SendTopic(source, c); + + if (needjoin) + bi->Part(c); + } +}; + +struct IRCDMessageEncap : IRCDMessage +{ + IRCDMessageEncap(Module *creator) : IRCDMessage(creator, "ENCAP", 3) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + // Debug: Received: :00BAAAAAB ENCAP * LOGIN Adam + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params[1] == "LOGIN" || params[1] == "SU") + { + User *u = source.GetUser(); + + NickCore *nc = NickCore::Find(params[2]); + if (!nc) + return; + u->Login(nc); + + /* Sometimes a user connects, we send them the usual "this nickname is registered" mess (if + * their server isn't syncing) and then we receive this.. so tell them about it. + */ + if (u->server->IsSynced()) + u->SendMessage(Config->GetClient("NickServ"), _("You have been logged in as \002%s\002."), nc->display.c_str()); + } + } +}; + +struct IRCDMessageJoin : Message::Join +{ + IRCDMessageJoin(Module *creator) : Message::Join(creator, "JOIN") { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params.size() == 1 && params[0] == "0") + return Message::Join::Run(source, params); + + if (params.size() < 2) + return; + + std::vector p = params; + p.erase(p.begin()); + + return Message::Join::Run(source, p); + } +}; + +struct IRCDMessagePass : IRCDMessage +{ + IRCDMessagePass(Module *creator) : IRCDMessage(creator, "PASS", 4) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + UplinkSID = params[3]; + } +}; + +struct IRCDMessageServer : IRCDMessage +{ + IRCDMessageServer(Module *creator) : IRCDMessage(creator, "SERVER", 3) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + // SERVER hades.arpa 1 :ircd-ratbox test server + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + // Servers other then our immediate uplink are introduced via SID + if (params[1] != "1") + return; + new Server(source.GetServer() == NULL ? Me : source.GetServer(), params[0], 1, params[2], UplinkSID); + IRCD->SendPing(Me->GetName(), params[0]); + } +}; + +struct IRCDMessageTBurst : IRCDMessage +{ + IRCDMessageTBurst(Module *creator) : IRCDMessage(creator, "TB", 3) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* + * params[0] = channel + * params[1] = ts + * params[2] = topic OR who set the topic + * params[3] = topic if params[2] isn't the topic + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + time_t topic_time = Anope::string(params[1]).is_pos_number_only() ? convertTo(params[1]) : Anope::CurTime; + Channel *c = Channel::Find(params[0]); + + if (!c) + return; + + const Anope::string &setter = params.size() == 4 ? params[2] : "", + topic = params.size() == 4 ? params[3] : params[2]; + + c->ChangeTopicInternal(NULL, setter, topic, topic_time); + } +}; + +struct IRCDMessageUID : IRCDMessage +{ + IRCDMessageUID(Module *creator) : IRCDMessage(creator, "UID", 9) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + // :42X UID Adam 1 1348535644 +aow Adam 192.168.0.5 192.168.0.5 42XAAAAAB :Adam + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + /* Source is always the server */ + User::OnIntroduce(params[0], params[4], params[5], "", params[6], source.GetServer(), params[8], params[2].is_pos_number_only() ? convertTo(params[2]) : 0, params[3], params[7], NULL); + } +}; + +class ProtoRatbox : public Module +{ + Module *m_hybrid; + + RatboxProto ircd_proto; + + /* Core message handlers */ + Message::Away message_away; + Message::Capab message_capab; + Message::Error message_error; + Message::Invite message_invite; + Message::Kick message_kick; + Message::Kill message_kill; + Message::Mode message_mode; + Message::MOTD message_motd; + Message::Notice message_notice; + Message::Part message_part; + Message::Ping message_ping; + Message::Privmsg message_privmsg; + Message::Quit message_quit; + Message::SQuit message_squit; + Message::Stats message_stats; + Message::Time message_time; + Message::Topic message_topic; + Message::Version message_version; + Message::Whois message_whois; + + /* Hybrid message handlers */ + ServiceAlias message_bmask, message_nick, message_pong, message_sid, + message_sjoin, message_tmode; + + /* Our message handlers */ + IRCDMessageEncap message_encap; + IRCDMessageJoin message_join; + IRCDMessagePass message_pass; + IRCDMessageServer message_server; + IRCDMessageTBurst message_tburst; + IRCDMessageUID message_uid; + + void AddModes() + { + /* user modes */ + ModeManager::AddUserMode(new UserModeOperOnly("ADMIN", 'a')); + ModeManager::AddUserMode(new UserModeOperOnly("BOT", 'b')); + // c/C = con + // d = debug? + ModeManager::AddUserMode(new UserMode("DEAF", 'D')); + // f = full? + ModeManager::AddUserMode(new UserMode("CALLERID", 'g')); + ModeManager::AddUserMode(new UserMode("INVIS", 'i')); + // k = skill? + ModeManager::AddUserMode(new UserModeOperOnly("LOCOPS", 'l')); + // n = nchange + ModeManager::AddUserMode(new UserModeOperOnly("OPER", 'o')); + // r = rej + ModeManager::AddUserMode(new UserModeOperOnly("SNOMASK", 's')); + ModeManager::AddUserMode(new UserModeNoone("PROTECTED", 'S')); + // u = unauth? + ModeManager::AddUserMode(new UserMode("WALLOPS", 'w')); + // x = external? + // y = spy? + ModeManager::AddUserMode(new UserModeOperOnly("OPERWALLS", 'z')); + // Z = spy? + + /* b/e/I */ + ModeManager::AddChannelMode(new ChannelModeList("BAN", 'b')); + ModeManager::AddChannelMode(new ChannelModeList("EXCEPT", 'e')); + ModeManager::AddChannelMode(new ChannelModeList("INVITEOVERRIDE", 'I')); + + /* v/h/o/a/q */ + ModeManager::AddChannelMode(new ChannelModeStatus("VOICE", 'v', '+', 0)); + ModeManager::AddChannelMode(new ChannelModeStatus("OP", 'o', '@', 1)); + + /* l/k */ + ModeManager::AddChannelMode(new ChannelModeParam("LIMIT", 'l', true)); + ModeManager::AddChannelMode(new ChannelModeKey('k')); + + /* channel modes */ + ModeManager::AddChannelMode(new ChannelMode("INVITE", 'i')); + ModeManager::AddChannelMode(new ChannelMode("MODERATED", 'm')); + ModeManager::AddChannelMode(new ChannelMode("NOEXTERNAL", 'n')); + ModeManager::AddChannelMode(new ChannelMode("PRIVATE", 'p')); + ModeManager::AddChannelMode(new ChannelMode("REGISTEREDONLY", 'r')); + ModeManager::AddChannelMode(new ChannelMode("SECRET", 's')); + ModeManager::AddChannelMode(new ChannelMode("TOPIC", 't')); + ModeManager::AddChannelMode(new ChannelMode("SSL", 'S')); + } + + public: + ProtoRatbox(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PROTOCOL | VENDOR), + ircd_proto(this), + message_away(this), message_capab(this), message_error(this), message_invite(this), message_kick(this), + message_kill(this), message_mode(this), message_motd(this), message_notice(this), message_part(this), + message_ping(this), message_privmsg(this), message_quit(this), message_squit(this), message_stats(this), + message_time(this), message_topic(this), message_version(this), message_whois(this), + + message_bmask("IRCDMessage", "ratbox/bmask", "hybrid/bmask"), message_nick("IRCDMessage", "ratbox/nick", "hybrid/nick"), + message_pong("IRCDMessage", "ratbox/pong", "hybrid/pong"), message_sid("IRCDMessage", "ratbox/sid", "hybrid/sid"), + message_sjoin("IRCDMessage", "ratbox/sjoin", "hybrid/sjoin"), message_tmode("IRCDMessage", "ratbox/tmode", "hybrid/tmode"), + + message_encap(this), message_join(this), message_pass(this), message_server(this), message_tburst(this), message_uid(this) + { + + if (ModuleManager::LoadModule("hybrid", User::Find(creator)) != MOD_ERR_OK) + throw ModuleException("Unable to load hybrid"); + m_hybrid = ModuleManager::FindModule("hybrid"); + if (!m_hybrid) + throw ModuleException("Unable to find hybrid"); + if (!hybrid) + throw ModuleException("No protocol interface for hybrid"); + + this->AddModes(); + } + + ~ProtoRatbox() + { + m_hybrid = ModuleManager::FindModule("hybrid"); + ModuleManager::UnloadModule(m_hybrid, NULL); + } +}; + +MODULE_INIT(ProtoRatbox) diff --git a/modules/protocol/unreal.cpp b/modules/protocol/unreal.cpp new file mode 100644 index 0000000..ed6cdac --- /dev/null +++ b/modules/protocol/unreal.cpp @@ -0,0 +1,1340 @@ +/* Unreal IRCD 3.2.x functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/cs_mode.h" +#include "modules/sasl.h" + +class UnrealIRCdProto : public IRCDProto +{ + public: + UnrealIRCdProto(Module *creator) : IRCDProto(creator, "UnrealIRCd 3.2.x") + { + DefaultPseudoclientModes = "+Soiq"; + CanSVSNick = true; + CanSVSJoin = true; + CanSetVHost = true; + CanSetVIdent = true; + CanSNLine = true; + CanSQLine = true; + CanSZLine = true; + CanSVSHold = true; + CanSVSO = true; + MaxModes = 12; + } + + private: + /* SVSNOOP */ + void SendSVSNOOP(const Server *server, bool set) anope_override + { + UplinkSocket::Message() << "SVSNOOP " << server->GetName() << " " << (set ? "+" : "-"); + } + + void SendAkillDel(const XLine *x) anope_override + { + if (x->IsRegex() || x->HasNickOrReal()) + return; + + /* ZLine if we can instead */ + if (x->GetUser() == "*") + { + cidr a(x->GetHost()); + if (a.valid()) + { + IRCD->SendSZLineDel(x); + return; + } + } + + UplinkSocket::Message() << "TKL - G " << x->GetUser() << " " << x->GetHost() << " " << x->by; + } + + void SendTopic(const MessageSource &source, Channel *c) anope_override + { + UplinkSocket::Message(source) << "TOPIC " << c->name << " " << c->topic_setter << " " << c->topic_ts << " :" << c->topic; + } + + void SendGlobalNotice(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "NOTICE $" << dest->GetName() << " :" << msg; + } + + void SendGlobalPrivmsg(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "PRIVMSG $" << dest->GetName() << " :" << msg; + } + + void SendVhostDel(User *u) anope_override + { + BotInfo *HostServ = Config->GetClient("HostServ"); + u->RemoveMode(HostServ, "CLOAK"); + u->RemoveMode(HostServ, "VHOST"); + ModeManager::ProcessModes(); + u->SetMode(HostServ, "CLOAK"); + } + + void SendAkill(User *u, XLine *x) anope_override + { + if (x->IsRegex() || x->HasNickOrReal()) + { + if (!u) + { + /* No user (this akill was just added), and contains nick and/or realname. Find users that match and ban them */ + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + if (x->manager->Check(it->second, x)) + this->SendAkill(it->second, x); + return; + } + + const XLine *old = x; + + if (old->manager->HasEntry("*@" + u->host)) + return; + + /* We can't akill x as it has a nick and/or realname included, so create a new akill for *@host */ + XLine *xline = new XLine("*@" + u->host, old->by, old->expires, old->reason, old->id); + old->manager->AddXLine(xline); + x = xline; + + Log(Config->GetClient("OperServ"), "akill") << "AKILL: Added an akill for " << x->mask << " because " << u->GetMask() << "#" << u->realname << " matches " << old->mask; + } + + /* ZLine if we can instead */ + if (x->GetUser() == "*") + { + cidr a(x->GetHost()); + if (a.valid()) + { + IRCD->SendSZLine(u, x); + return; + } + } + + // Calculate the time left before this would expire, capping it at 2 days + time_t timeleft = x->expires - Anope::CurTime; + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + UplinkSocket::Message() << "TKL + G " << x->GetUser() << " " << x->GetHost() << " " << x->by << " " << Anope::CurTime + timeleft << " " << x->created << " :" << x->GetReason(); + } + + void SendSVSKillInternal(const MessageSource &source, User *user, const Anope::string &buf) anope_override + { + UplinkSocket::Message(source) << "SVSKILL " << user->nick << " :" << buf; + user->KillInternal(source, buf); + } + + void SendModeInternal(const MessageSource &source, User *u, const Anope::string &buf) anope_override + { + UplinkSocket::Message(source) << "SVS2MODE " << u->nick <<" " << buf; + } + + void SendClientIntroduction(User *u) anope_override + { + Anope::string modes = "+" + u->GetModes(); + UplinkSocket::Message() << "NICK " << u->nick << " 1 " << u->timestamp << " " << u->GetIdent() << " " << u->host << " " << u->server->GetName() << " 0 " << modes << " " << u->host << " * :" << u->realname; + } + + /* SERVER name hop descript */ + /* Unreal 3.2 actually sends some info about itself in the descript area */ + void SendServer(const Server *server) anope_override + { + if (!server->GetSID().empty() && server == Me) + UplinkSocket::Message() << "SERVER " << server->GetName() << " " << server->GetHops() << " :U0-*-" << server->GetSID() << " " << server->GetDescription(); + else + UplinkSocket::Message() << "SERVER " << server->GetName() << " " << server->GetHops() << " :" << server->GetDescription(); + } + + /* JOIN */ + void SendJoin(User *user, Channel *c, const ChannelStatus *status) anope_override + { + UplinkSocket::Message(Me) << "SJOIN " << c->creation_time << " " << c->name << " :" << user->nick; + if (status) + { + /* First save the channel status incase uc->Status == status */ + ChannelStatus cs = *status; + /* If the user is internally on the channel with flags, kill them so that + * the stacker will allow this. + */ + ChanUserContainer *uc = c->FindUser(user); + if (uc != NULL) + uc->status.Clear(); + + BotInfo *setter = BotInfo::Find(user->GetUID()); + for (size_t i = 0; i < cs.Modes().length(); ++i) + c->SetMode(setter, ModeManager::FindChannelModeByChar(cs.Modes()[i]), user->GetUID(), false); + + if (uc != NULL) + uc->status = cs; + } + } + + /* unsqline + */ + void SendSQLineDel(const XLine *x) anope_override + { + UplinkSocket::Message() << "UNSQLINE " << x->mask; + } + + /* SQLINE */ + /* + ** - Unreal will translate this to TKL for us + ** + */ + void SendSQLine(User *, const XLine *x) anope_override + { + UplinkSocket::Message() << "SQLINE " << x->mask << " :" << x->GetReason(); + } + + /* + ** svso + ** parv[0] = sender prefix + ** parv[1] = nick + ** parv[2] = options + */ + void SendSVSO(BotInfo *source, const Anope::string &nick, const Anope::string &flag) anope_override + { + UplinkSocket::Message(source) << "SVSO " << nick << " " << flag; + } + + /* Functions that use serval cmd functions */ + + void SendVhost(User *u, const Anope::string &vIdent, const Anope::string &vhost) anope_override + { + if (!vIdent.empty()) + UplinkSocket::Message(Me) << "CHGIDENT " << u->nick << " " << vIdent; + if (!vhost.empty()) + UplinkSocket::Message(Me) << "CHGHOST " << u->nick << " " << vhost; + } + + void SendConnect() anope_override + { + /* + NICKv2 = Nick Version 2 + VHP = Sends hidden host + UMODE2 = sends UMODE2 on user modes + NICKIP = Sends IP on NICK + TOKEN = Use tokens to talk + SJ3 = Supports SJOIN + NOQUIT = No Quit + TKLEXT = Extended TKL we don't use it but best to have it + SJB64 = Base64 encoded time stamps + ESVID = Allows storing account names as services stamp + MLOCK = Supports the MLOCK server command + VL = Version Info + NS = Config->Numeric Server + */ + Anope::string protoctl = "NICKv2 VHP UMODE2 NICKIP SJOIN SJOIN2 SJ3 NOQUIT TKLEXT ESVID MLOCK VL"; + if (!Me->GetSID().empty()) + protoctl += " VL"; + UplinkSocket::Message() << "PROTOCTL " << protoctl; + UplinkSocket::Message() << "PASS :" << Config->Uplinks[Anope::CurrentUplink].password; + SendServer(Me); + } + + /* SVSHOLD - set */ + void SendSVSHold(const Anope::string &nick, time_t t) anope_override + { + UplinkSocket::Message() << "TKL + Q H " << nick << " " << Me->GetName() << " " << Anope::CurTime + t << " " << Anope::CurTime << " :Being held for registered user"; + } + + /* SVSHOLD - release */ + void SendSVSHoldDel(const Anope::string &nick) anope_override + { + UplinkSocket::Message() << "TKL - Q * " << nick << " " << Me->GetName(); + } + + /* UNSGLINE */ + /* + * SVSNLINE - :realname mask + */ + void SendSGLineDel(const XLine *x) anope_override + { + UplinkSocket::Message() << "SVSNLINE - :" << x->mask; + } + + /* UNSZLINE */ + void SendSZLineDel(const XLine *x) anope_override + { + UplinkSocket::Message() << "TKL - Z * " << x->GetHost() << " " << x->by; + } + + /* SZLINE */ + void SendSZLine(User *, const XLine *x) anope_override + { + // Calculate the time left before this would expire, capping it at 2 days + time_t timeleft = x->expires - Anope::CurTime; + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + UplinkSocket::Message() << "TKL + Z * " << x->GetHost() << " " << x->by << " " << Anope::CurTime + timeleft << " " << x->created << " :" << x->GetReason(); + } + + /* SGLINE */ + /* + * SVSNLINE + reason_where_is_space :realname mask with spaces + */ + void SendSGLine(User *, const XLine *x) anope_override + { + Anope::string edited_reason = x->GetReason(); + edited_reason = edited_reason.replace_all_cs(" ", "_"); + UplinkSocket::Message() << "SVSNLINE + " << edited_reason << " :" << x->mask; + } + + /* svsjoin + parv[0] - sender + parv[1] - nick to make join + parv[2] - channel to join + parv[3] - (optional) channel key(s) + */ + /* In older Unreal SVSJOIN and SVSNLINE tokens were mixed so SVSJOIN and SVSNLINE are broken + when coming from a none TOKEN'd server + */ + void SendSVSJoin(const MessageSource &source, User *user, const Anope::string &chan, const Anope::string ¶m) anope_override + { + if (!param.empty()) + UplinkSocket::Message(source) << "SVSJOIN " << user->GetUID() << " " << chan << " :" << param; + else + UplinkSocket::Message(source) << "SVSJOIN " << user->GetUID() << " " << chan; + } + + void SendSVSPart(const MessageSource &source, User *user, const Anope::string &chan, const Anope::string ¶m) anope_override + { + if (!param.empty()) + UplinkSocket::Message(source) << "SVSPART " << user->GetUID() << " " << chan << " :" << param; + else + UplinkSocket::Message(source) << "SVSPART " << user->GetUID() << " " << chan; + } + + void SendSWhois(const MessageSource &source, const Anope::string &who, const Anope::string &mask) anope_override + { + UplinkSocket::Message(source) << "SWHOIS " << who << " :" << mask; + } + + void SendEOB() anope_override + { + UplinkSocket::Message(Me) << "EOS"; + } + + bool IsNickValid(const Anope::string &nick) anope_override + { + if (nick.equals_ci("ircd") || nick.equals_ci("irc")) + return false; + + return IRCDProto::IsNickValid(nick); + } + + bool IsChannelValid(const Anope::string &chan) anope_override + { + if (chan.find(':') != Anope::string::npos) + return false; + + return IRCDProto::IsChannelValid(chan); + } + + bool IsExtbanValid(const Anope::string &mask) anope_override + { + return mask.length() >= 4 && mask[0] == '~' && mask[2] == ':'; + } + + void SendLogin(User *u, NickAlias *na) anope_override + { + /* 3.2.10.4+ treats users logged in with accounts as fully registered, even if -r, so we can not set this here. Just use the timestamp. */ + if (Servers::Capab.count("ESVID") > 0 && !na->nc->HasExt("UNCONFIRMED")) + IRCD->SendMode(Config->GetClient("NickServ"), u, "+d %s", na->nc->display.c_str()); + else + IRCD->SendMode(Config->GetClient("NickServ"), u, "+d %d", u->signon); + } + + void SendLogout(User *u) anope_override + { + IRCD->SendMode(Config->GetClient("NickServ"), u, "+d 0"); + } + + void SendChannel(Channel *c) anope_override + { + /* Unreal does not support updating a channels TS without actually joining a user, + * so we will join and part us now + */ + BotInfo *bi = c->ci->WhoSends(); + if (!bi) + ; + else if (c->FindUser(bi) == NULL) + { + bi->Join(c); + bi->Part(c); + } + else + { + bi->Part(c); + bi->Join(c); + } + } + + void SendSASLMessage(const SASL::Message &message) anope_override + { + size_t p = message.target.find('!'); + if (p == Anope::string::npos) + return; + + UplinkSocket::Message(BotInfo::Find(message.source)) << "SASL " << message.target.substr(0, p) << " " << message.target << " " << message.type << " " << message.data << (message.ext.empty() ? "" : " " + message.ext); + } + + void SendSVSLogin(const Anope::string &uid, const Anope::string &acc, const Anope::string &vident, const Anope::string &vhost) anope_override + { + size_t p = uid.find('!'); + if (p == Anope::string::npos) + return; + UplinkSocket::Message(Me) << "SVSLOGIN " << uid.substr(0, p) << " " << uid << " " << acc; + } + + bool IsIdentValid(const Anope::string &ident) anope_override + { + if (ident.empty() || ident.length() > Config->GetBlock("networkinfo")->Get("userlen")) + return false; + + for (unsigned i = 0; i < ident.length(); ++i) + { + const char &c = ident[i]; + + if ((c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || (c >= '0' && c <= '9') || c == '.' || c == '-') + continue; + + if (c == '-' || c == '.' || c == '_') + continue; + + return false; + } + + return true; + } +}; + +class UnrealExtBan : public ChannelModeVirtual +{ + char ext; + + public: + UnrealExtBan(const Anope::string &mname, const Anope::string &basename, char extban) : ChannelModeVirtual(mname, basename) + , ext(extban) + { + } + + ChannelMode *Wrap(Anope::string ¶m) anope_override + { + param = "~" + Anope::string(ext) + ":" + param; + return ChannelModeVirtual::Wrap(param); + } + + ChannelMode *Unwrap(ChannelMode *cm, Anope::string ¶m) anope_override + { + if (cm->type != MODE_LIST || param.length() < 4 || param[0] != '~' || param[1] != ext || param[2] != ':') + return cm; + + param = param.substr(3); + return this; + } +}; + +namespace UnrealExtban +{ + class ChannelMatcher : public UnrealExtBan + { + public: + ChannelMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string channel = mask.substr(3); + + ChannelMode *cm = NULL; + if (channel[0] != '#') + { + char modeChar = ModeManager::GetStatusChar(channel[0]); + channel.erase(channel.begin()); + cm = ModeManager::FindChannelModeByChar(modeChar); + if (cm != NULL && cm->type != MODE_STATUS) + cm = NULL; + } + + Channel *c = Channel::Find(channel); + if (c != NULL) + { + ChanUserContainer *uc = c->FindUser(u); + if (uc != NULL) + if (cm == NULL || uc->status.HasMode(cm->mchar)) + return true; + } + + return false; + } + }; + + class EntryMatcher : public UnrealExtBan + { + public: + EntryMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(3); + + return Entry(this->name, real_mask).Matches(u); + } + }; + + class RealnameMatcher : public UnrealExtBan + { + public: + RealnameMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(3); + + return Anope::Match(u->realname, real_mask); + } + }; + + class RegisteredMatcher : public UnrealExtBan + { + public: + RegisteredMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + return u->HasMode("REGISTERED") && mask.equals_ci(u->nick); + } + }; + + class AccountMatcher : public UnrealExtBan + { + public: + AccountMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(3); + + return u->Account() && Anope::Match(u->Account()->display, real_mask); + } + }; +} + +class ChannelModeFlood : public ChannelModeParam +{ + public: + ChannelModeFlood(char modeChar, bool minusNoArg) : ChannelModeParam("FLOOD", modeChar, minusNoArg) { } + + /* Borrowed part of this check from UnrealIRCd */ + bool IsValid(Anope::string &value) const anope_override + { + if (value.empty()) + return false; + try + { + Anope::string rest; + if (value[0] != ':' && convertTo(value[0] == '*' ? value.substr(1) : value, rest, false) > 0 && rest[0] == ':' && rest.length() > 1 && convertTo(rest.substr(1), rest, false) > 0 && rest.empty()) + return true; + } + catch (const ConvertException &) { } + + /* '['<1 letter>[optional: '#'+1 letter],[next..]']'':' */ + size_t end_bracket = value.find(']', 1); + if (end_bracket == Anope::string::npos) + return false; + Anope::string xbuf = value.substr(0, end_bracket); + if (value[end_bracket + 1] != ':') + return false; + commasepstream args(xbuf.substr(1)); + Anope::string arg; + while (args.GetToken(arg)) + { + /* <1 letter>[optional: '#'+1 letter] */ + size_t p = 0; + while (p < arg.length() && isdigit(arg[p])) + ++p; + if (p == arg.length() || !(arg[p] == 'c' || arg[p] == 'j' || arg[p] == 'k' || arg[p] == 'm' || arg[p] == 'n' || arg[p] == 't')) + continue; /* continue instead of break for forward compatibility. */ + try + { + int v = arg.substr(0, p).is_number_only() ? convertTo(arg.substr(0, p)) : 0; + if (v < 1 || v > 999) + return false; + } + catch (const ConvertException &) + { + return false; + } + } + + return true; + } +}; + +class ChannelModeUnrealSSL : public ChannelMode +{ + public: + ChannelModeUnrealSSL(const Anope::string &n, char c) : ChannelMode(n, c) + { + } + + bool CanSet(User *u) const anope_override + { + return false; + } +}; + +struct IRCDMessageCapab : Message::Capab +{ + IRCDMessageCapab(Module *creator) : Message::Capab(creator, "PROTOCTL") { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + for (unsigned i = 0; i < params.size(); ++i) + { + Anope::string capab = params[i]; + + if (capab.find("CHANMODES") != Anope::string::npos) + { + Anope::string modes(capab.begin() + 10, capab.end()); + commasepstream sep(modes); + Anope::string modebuf; + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'b': + ModeManager::AddChannelMode(new ChannelModeList("BAN", 'b')); + + ModeManager::AddChannelMode(new UnrealExtban::ChannelMatcher("CHANNELBAN", "BAN", 'c')); + ModeManager::AddChannelMode(new UnrealExtban::EntryMatcher("JOINBAN", "BAN", 'j')); + ModeManager::AddChannelMode(new UnrealExtban::EntryMatcher("NONICKBAN", "BAN", 'n')); + ModeManager::AddChannelMode(new UnrealExtban::EntryMatcher("QUIET", "BAN", 'q')); + ModeManager::AddChannelMode(new UnrealExtban::RealnameMatcher("REALNAMEBAN", "BAN", 'r')); + ModeManager::AddChannelMode(new UnrealExtban::RegisteredMatcher("REGISTEREDBAN", "BAN", 'R')); + ModeManager::AddChannelMode(new UnrealExtban::AccountMatcher("ACCOUNTBAN", "BAN", 'a')); + continue; + case 'e': + ModeManager::AddChannelMode(new ChannelModeList("EXCEPT", 'e')); + continue; + case 'I': + ModeManager::AddChannelMode(new ChannelModeList("INVITEOVERRIDE", 'I')); + continue; + default: + ModeManager::AddChannelMode(new ChannelModeList("", modebuf[t])); + } + } + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'k': + ModeManager::AddChannelMode(new ChannelModeKey('k')); + continue; + case 'f': + ModeManager::AddChannelMode(new ChannelModeFlood('f', false)); + continue; + case 'L': + ModeManager::AddChannelMode(new ChannelModeParam("REDIRECT", 'L')); + continue; + default: + ModeManager::AddChannelMode(new ChannelModeParam("", modebuf[t])); + } + } + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'l': + ModeManager::AddChannelMode(new ChannelModeParam("LIMIT", 'l', true)); + continue; + case 'j': + ModeManager::AddChannelMode(new ChannelModeParam("JOINFLOOD", 'j', true)); + continue; + default: + ModeManager::AddChannelMode(new ChannelModeParam("", modebuf[t], true)); + } + } + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'p': + ModeManager::AddChannelMode(new ChannelMode("PRIVATE", 'p')); + continue; + case 's': + ModeManager::AddChannelMode(new ChannelMode("SECRET", 's')); + continue; + case 'm': + ModeManager::AddChannelMode(new ChannelMode("MODERATED", 'm')); + continue; + case 'n': + ModeManager::AddChannelMode(new ChannelMode("NOEXTERNAL", 'n')); + continue; + case 't': + ModeManager::AddChannelMode(new ChannelMode("TOPIC", 't')); + continue; + case 'i': + ModeManager::AddChannelMode(new ChannelMode("INVITE", 'i')); + continue; + case 'r': + ModeManager::AddChannelMode(new ChannelModeNoone("REGISTERED", 'r')); + continue; + case 'R': + ModeManager::AddChannelMode(new ChannelMode("REGISTEREDONLY", 'R')); + continue; + case 'c': + ModeManager::AddChannelMode(new ChannelMode("BLOCKCOLOR", 'c')); + continue; + case 'O': + ModeManager::AddChannelMode(new ChannelModeOperOnly("OPERONLY", 'O')); + continue; + case 'A': + ModeManager::AddChannelMode(new ChannelModeOperOnly("ADMINONLY", 'A')); + continue; + case 'Q': + ModeManager::AddChannelMode(new ChannelMode("NOKICK", 'Q')); + continue; + case 'K': + ModeManager::AddChannelMode(new ChannelMode("NOKNOCK", 'K')); + continue; + case 'V': + ModeManager::AddChannelMode(new ChannelMode("NOINVITE", 'V')); + continue; + case 'C': + ModeManager::AddChannelMode(new ChannelMode("NOCTCP", 'C')); + continue; + case 'u': + ModeManager::AddChannelMode(new ChannelMode("AUDITORIUM", 'u')); + continue; + case 'z': + ModeManager::AddChannelMode(new ChannelMode("SSL", 'z')); + continue; + case 'N': + ModeManager::AddChannelMode(new ChannelMode("NONICK", 'N')); + continue; + case 'S': + ModeManager::AddChannelMode(new ChannelMode("STRIPCOLOR", 'S')); + continue; + case 'M': + ModeManager::AddChannelMode(new ChannelMode("REGMODERATED", 'M')); + continue; + case 'T': + ModeManager::AddChannelMode(new ChannelMode("NONOTICE", 'T')); + continue; + case 'G': + ModeManager::AddChannelMode(new ChannelMode("CENSOR", 'G')); + continue; + case 'Z': + ModeManager::AddChannelMode(new ChannelModeUnrealSSL("", 'Z')); + continue; + default: + ModeManager::AddChannelMode(new ChannelMode("", modebuf[t])); + } + } + } + } + + Message::Capab::Run(source, params); + } +}; + +struct IRCDMessageChgHost : IRCDMessage +{ + IRCDMessageChgHost(Module *creator) : IRCDMessage(creator, "CHGHOST", 2) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = User::Find(params[0]); + if (u) + u->SetDisplayedHost(params[1]); + } +}; + +struct IRCDMessageChgIdent : IRCDMessage +{ + IRCDMessageChgIdent(Module *creator) : IRCDMessage(creator, "CHGIDENT", 2) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = User::Find(params[0]); + if (u) + u->SetVIdent(params[1]); + } +}; + +struct IRCDMessageChgName : IRCDMessage +{ + IRCDMessageChgName(Module *creator) : IRCDMessage(creator, "CHGNAME", 2) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = User::Find(params[0]); + if (u) + u->SetRealname(params[1]); + } +}; + +struct IRCDMessageMode : IRCDMessage +{ + IRCDMessageMode(Module *creator, const Anope::string &mname) : IRCDMessage(creator, mname, 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + bool server_source = source.GetServer() != NULL; + Anope::string modes = params[1]; + for (unsigned i = 2; i < params.size() - (server_source ? 1 : 0); ++i) + modes += " " + params[i]; + + if (IRCD->IsChannelValid(params[0])) + { + Channel *c = Channel::Find(params[0]); + time_t ts = 0; + + try + { + if (server_source) + ts = convertTo(params[params.size() - 1]); + } + catch (const ConvertException &) { } + + if (c) + c->SetModesInternal(source, modes, ts); + } + else + { + User *u = User::Find(params[0]); + if (u) + u->SetModesInternal(source, "%s", params[1].c_str()); + } + } +}; + +/* netinfo + * argv[0] = max global count + * argv[1] = time of end sync + * argv[2] = unreal protocol using (numeric) + * argv[3] = cloak-crc (> u2302) + * argv[4] = free(**) + * argv[5] = free(**) + * argv[6] = free(**) + * argv[7] = ircnet + */ +struct IRCDMessageNetInfo : IRCDMessage +{ + IRCDMessageNetInfo(Module *creator) : IRCDMessage(creator, "NETINFO", 8) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + UplinkSocket::Message() << "NETINFO " << MaxUserCount << " " << Anope::CurTime << " " << convertTo(params[2]) << " " << params[3] << " 0 0 0 :" << params[7]; + } +}; + +struct IRCDMessageNick : IRCDMessage +{ + IRCDMessageNick(Module *creator) : IRCDMessage(creator, "NICK", 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* + ** NICK - new + ** source = NULL + ** parv[0] = nickname + ** parv[1] = hopcount + ** parv[2] = timestamp + ** parv[3] = username + ** parv[4] = hostname + ** parv[5] = servername + ** parv[6] = servicestamp + ** parv[7] = umodes + ** parv[8] = virthost, * if none + ** parv[9] = ip + ** parv[10] = info + ** + ** NICK - change + ** source = oldnick + ** parv[0] = new nickname + ** parv[1] = hopcount + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params.size() == 11) + { + Anope::string ip; + if (params[9] != "*") + { + Anope::string decoded_ip; + Anope::B64Decode(params[9], decoded_ip); + + sockaddrs ip_addr; + ip_addr.ntop(params[9].length() == 8 ? AF_INET : AF_INET6, decoded_ip.c_str()); + ip = ip_addr.addr(); + } + + Anope::string vhost = params[8]; + if (vhost.equals_cs("*")) + vhost.clear(); + + time_t user_ts = params[2].is_pos_number_only() ? convertTo(params[2]) : Anope::CurTime; + + Server *s = Server::Find(params[5]); + if (s == NULL) + { + Log(LOG_DEBUG) << "User " << params[0] << " introduced from nonexistent server " << params[5] << "?"; + return; + } + + NickAlias *na = NULL; + + if (params[6] == "0") + ; + else if (params[6].is_pos_number_only()) + { + if (convertTo(params[6]) == user_ts) + na = NickAlias::Find(params[0]); + } + else + { + na = NickAlias::Find(params[6]); + } + + User::OnIntroduce(params[0], params[3], params[4], vhost, ip, s, params[10], user_ts, params[7], "", na ? *na->nc : NULL); + } + else + { + User *u = source.GetUser(); + if (u) + u->ChangeNick(params[0]); + } + } +}; + +/** This is here because: + * + * If we had three servers, A, B & C linked like so: A<->B<->C + * If Anope is linked to A and B splits from A and then reconnects + * B introduces itself, introduces C, sends EOS for C, introduces Bs clients + * introduces Cs clients, sends EOS for B. This causes all of Cs clients to be introduced + * with their server "not syncing". We now send a PING immediately when receiving a new server + * and then finish sync once we get a pong back from that server. + */ +struct IRCDMessagePong : IRCDMessage +{ + IRCDMessagePong(Module *creator) : IRCDMessage(creator, "PONG", 0) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (!source.GetServer()->IsSynced()) + source.GetServer()->Sync(false); + } +}; + +struct IRCDMessageSASL : IRCDMessage +{ + IRCDMessageSASL(Module *creator) : IRCDMessage(creator, "SASL", 4) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + size_t p = params[1].find('!'); + if (!SASL::sasl || p == Anope::string::npos) + return; + + SASL::Message m; + m.source = params[1]; + m.target = params[0]; + m.type = params[2]; + m.data = params[3]; + m.ext = params.size() > 4 ? params[4] : ""; + + SASL::sasl->ProcessMessage(m); + } +}; + +struct IRCDMessageSDesc : IRCDMessage +{ + IRCDMessageSDesc(Module *creator) : IRCDMessage(creator, "SDESC", 1) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetServer()->SetDescription(params[0]); + } +}; + +struct IRCDMessageSetHost : IRCDMessage +{ + IRCDMessageSetHost(Module *creator) : IRCDMessage(creator, "SETHOST", 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + + /* When a user sets +x we receive the new host and then the mode change */ + if (u->HasMode("CLOAK")) + u->SetDisplayedHost(params[0]); + else + u->SetCloakedHost(params[0]); + } +}; + +struct IRCDMessageSetIdent : IRCDMessage +{ + IRCDMessageSetIdent(Module *creator) : IRCDMessage(creator, "SETIDENT", 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + u->SetVIdent(params[0]); + } +}; + +struct IRCDMessageSetName : IRCDMessage +{ + IRCDMessageSetName(Module *creator) : IRCDMessage(creator, "SETNAME", 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + u->SetRealname(params[0]); + } +}; + +struct IRCDMessageServer : IRCDMessage +{ + IRCDMessageServer(Module *creator) : IRCDMessage(creator, "SERVER", 3) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + unsigned int hops = Anope::string(params[1]).is_pos_number_only() ? convertTo(params[1]) : 0; + + if (params[1].equals_cs("1")) + { + Anope::string desc; + spacesepstream(params[2]).GetTokenRemainder(desc, 1); + + new Server(source.GetServer() == NULL ? Me : source.GetServer(), params[0], hops, desc); + } + else + new Server(source.GetServer(), params[0], hops, params[2]); + + IRCD->SendPing(Me->GetName(), params[0]); + } +}; + +struct IRCDMessageSJoin : IRCDMessage +{ + IRCDMessageSJoin(Module *creator) : IRCDMessage(creator, "SJOIN", 3) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Anope::string modes; + if (params.size() >= 4) + for (unsigned i = 2; i < params.size() - 1; ++i) + modes += " " + params[i]; + if (!modes.empty()) + modes.erase(modes.begin()); + + std::list bans, excepts, invites; + std::list users; + + spacesepstream sep(params[params.size() - 1]); + Anope::string buf; + while (sep.GetToken(buf)) + { + /* Ban */ + if (buf[0] == '&') + { + buf.erase(buf.begin()); + bans.push_back(buf); + } + /* Except */ + else if (buf[0] == '"') + { + buf.erase(buf.begin()); + excepts.push_back(buf); + } + /* Invex */ + else if (buf[0] == '\'') + { + buf.erase(buf.begin()); + invites.push_back(buf); + } + else + { + Message::Join::SJoinUser sju; + + /* Get prefixes from the nick */ + for (char ch; (ch = ModeManager::GetStatusChar(buf[0]));) + { + sju.first.AddMode(ch); + buf.erase(buf.begin()); + } + + sju.second = User::Find(buf); + if (!sju.second) + { + Log(LOG_DEBUG) << "SJOIN for nonexistent user " << buf << " on " << params[1]; + continue; + } + + users.push_back(sju); + } + } + + time_t ts = Anope::string(params[0]).is_pos_number_only() ? convertTo(params[0]) : Anope::CurTime; + Message::Join::SJoin(source, params[1], ts, modes, users); + + if (!bans.empty() || !excepts.empty() || !invites.empty()) + { + Channel *c = Channel::Find(params[1]); + + if (!c || c->creation_time != ts) + return; + + ChannelMode *ban = ModeManager::FindChannelModeByName("BAN"), + *except = ModeManager::FindChannelModeByName("EXCEPT"), + *invex = ModeManager::FindChannelModeByName("INVITEOVERRIDE"); + + if (ban) + for (std::list::iterator it = bans.begin(), it_end = bans.end(); it != it_end; ++it) + c->SetModeInternal(source, ban, *it); + if (except) + for (std::list::iterator it = excepts.begin(), it_end = excepts.end(); it != it_end; ++it) + c->SetModeInternal(source, except, *it); + if (invex) + for (std::list::iterator it = invites.begin(), it_end = invites.end(); it != it_end; ++it) + c->SetModeInternal(source, invex, *it); + } + } +}; + +struct IRCDMessageTopic : IRCDMessage +{ + IRCDMessageTopic(Module *creator) : IRCDMessage(creator, "TOPIC", 4) { } + + /* + ** source = sender prefix + ** parv[0] = channel name + ** parv[1] = topic nickname + ** parv[2] = topic time + ** parv[3] = topic text + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Channel *c = Channel::Find(params[0]); + if (c) + c->ChangeTopicInternal(source.GetUser(), params[1], params[3], Anope::string(params[2]).is_pos_number_only() ? convertTo(params[2]) : Anope::CurTime); + } +}; + + +struct IRCDMessageUmode2 : IRCDMessage +{ + IRCDMessageUmode2(Module *creator) : IRCDMessage(creator, "UMODE2", 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetUser()->SetModesInternal(source, "%s", params[0].c_str()); + } +}; + +class ProtoUnreal : public Module +{ + UnrealIRCdProto ircd_proto; + + /* Core message handlers */ + Message::Away message_away; + Message::Error message_error; + Message::Invite message_invite; + Message::Join message_join; + Message::Kick message_kick; + Message::Kill message_kill, message_svskill; + Message::MOTD message_motd; + Message::Notice message_notice; + Message::Part message_part; + Message::Ping message_ping; + Message::Privmsg message_privmsg; + Message::Quit message_quit; + Message::SQuit message_squit; + Message::Stats message_stats; + Message::Time message_time; + Message::Version message_version; + Message::Whois message_whois; + + /* Our message handlers */ + IRCDMessageCapab message_capab; + IRCDMessageChgHost message_chghost; + IRCDMessageChgIdent message_chgident; + IRCDMessageChgName message_chgname; + IRCDMessageMode message_mode, message_svsmode, message_svs2mode; + IRCDMessageNetInfo message_netinfo; + IRCDMessageNick message_nick; + IRCDMessagePong message_pong; + IRCDMessageSASL message_sasl; + IRCDMessageSDesc message_sdesc; + IRCDMessageSetHost message_sethost; + IRCDMessageSetIdent message_setident; + IRCDMessageSetName message_setname; + IRCDMessageServer message_server; + IRCDMessageSJoin message_sjoin; + IRCDMessageTopic message_topic; + IRCDMessageUmode2 message_umode2; + + bool use_server_side_mlock; + + void AddModes() + { + ModeManager::AddChannelMode(new ChannelModeStatus("VOICE", 'v', '+', 0)); + ModeManager::AddChannelMode(new ChannelModeStatus("HALFOP", 'h', '%', 1)); + ModeManager::AddChannelMode(new ChannelModeStatus("OP", 'o', '@', 2)); + /* Unreal sends +q as * and +a as ~ */ + ModeManager::AddChannelMode(new ChannelModeStatus("PROTECT", 'a', '~', 3)); + ModeManager::AddChannelMode(new ChannelModeStatus("OWNER", 'q', '*', 4)); + + /* Add user modes */ + ModeManager::AddUserMode(new UserModeOperOnly("SERV_ADMIN", 'A')); + ModeManager::AddUserMode(new UserMode("BOT", 'B')); + ModeManager::AddUserMode(new UserModeOperOnly("CO_ADMIN", 'C')); + ModeManager::AddUserMode(new UserMode("CENSOR", 'G')); + ModeManager::AddUserMode(new UserModeOperOnly("HIDEOPER", 'H')); + ModeManager::AddUserMode(new UserModeOperOnly("HIDEIDLE", 'I')); + ModeManager::AddUserMode(new UserModeOperOnly("NETADMIN", 'N')); + ModeManager::AddUserMode(new UserMode("REGPRIV", 'R')); + ModeManager::AddUserMode(new UserModeOperOnly("PROTECTED", 'S')); + ModeManager::AddUserMode(new UserMode("NOCTCP", 'T')); + ModeManager::AddUserMode(new UserMode("WEBTV", 'V')); + ModeManager::AddUserMode(new UserModeOperOnly("WHOIS", 'W')); + ModeManager::AddUserMode(new UserModeOperOnly("ADMIN", 'a')); + ModeManager::AddUserMode(new UserMode("DEAF", 'd')); + ModeManager::AddUserMode(new UserModeOperOnly("GLOBOPS", 'g')); + ModeManager::AddUserMode(new UserModeOperOnly("HELPOP", 'h')); + ModeManager::AddUserMode(new UserMode("INVIS", 'i')); + ModeManager::AddUserMode(new UserModeOperOnly("OPER", 'o')); + ModeManager::AddUserMode(new UserMode("PRIV", 'p')); + ModeManager::AddUserMode(new UserModeOperOnly("GOD", 'q')); + ModeManager::AddUserMode(new UserModeNoone("REGISTERED", 'r')); + ModeManager::AddUserMode(new UserModeOperOnly("SNOMASK", 's')); + ModeManager::AddUserMode(new UserModeNoone("VHOST", 't')); + ModeManager::AddUserMode(new UserMode("WALLOPS", 'w')); + ModeManager::AddUserMode(new UserMode("CLOAK", 'x')); + ModeManager::AddUserMode(new UserModeNoone("SSL", 'z')); + } + + public: + ProtoUnreal(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PROTOCOL | VENDOR), + ircd_proto(this), + message_away(this), message_error(this), message_invite(this), message_join(this), message_kick(this), + message_kill(this), message_svskill(this, "SVSKILL"), message_motd(this), message_notice(this), message_part(this), message_ping(this), + message_privmsg(this), message_quit(this), message_squit(this), message_stats(this), message_time(this), + message_version(this), message_whois(this), + + message_capab(this), message_chghost(this), message_chgident(this), message_chgname(this), message_mode(this, "MODE"), + message_svsmode(this, "SVSMODE"), message_svs2mode(this, "SVS2MODE"), message_netinfo(this), message_nick(this), message_pong(this), + message_sasl(this), message_sdesc(this), message_sethost(this), message_setident(this), message_setname(this), message_server(this), + message_sjoin(this), message_topic(this), message_umode2(this) + { + + this->AddModes(); + } + + void Prioritize() anope_override + { + ModuleManager::SetPriority(this, PRIORITY_FIRST); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + use_server_side_mlock = conf->GetModule(this)->Get("use_server_side_mlock"); + } + + void OnUserNickChange(User *u, const Anope::string &) anope_override + { + u->RemoveModeInternal(Me, ModeManager::FindUserModeByName("REGISTERED")); + if (Servers::Capab.count("ESVID") == 0) + IRCD->SendLogout(u); + } + + void OnChannelSync(Channel *c) anope_override + { + if (!c->ci) + return; + + ModeLocks *modelocks = c->ci->GetExt("modelocks"); + if (use_server_side_mlock && Servers::Capab.count("MLOCK") > 0 && modelocks) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", ""); + UplinkSocket::Message(Me) << "MLOCK " << static_cast(c->creation_time) << " " << c->ci->name << " " << modes; + } + } + + void OnChanRegistered(ChannelInfo *ci) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + if (!ci->c || !use_server_side_mlock || !modelocks || !Servers::Capab.count("MLOCK")) + return; + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", ""); + UplinkSocket::Message(Me) << "MLOCK " << static_cast(ci->c->creation_time) << " " << ci->name << " " << modes; + } + + void OnDelChan(ChannelInfo *ci) anope_override + { + if (!ci->c || !use_server_side_mlock || !Servers::Capab.count("MLOCK")) + return; + UplinkSocket::Message(Me) << "MLOCK " << static_cast(ci->c->creation_time) << " " << ci->name << " :"; + } + + EventReturn OnMLock(ChannelInfo *ci, ModeLock *lock) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + ChannelMode *cm = ModeManager::FindChannelModeByName(lock->name); + if (use_server_side_mlock && cm && modelocks && ci->c && (cm->type == MODE_REGULAR || cm->type == MODE_PARAM) && Servers::Capab.count("MLOCK") > 0) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", "") + cm->mchar; + UplinkSocket::Message(Me) << "MLOCK " << static_cast(ci->c->creation_time) << " " << ci->name << " " << modes; + } + + return EVENT_CONTINUE; + } + + EventReturn OnUnMLock(ChannelInfo *ci, ModeLock *lock) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + ChannelMode *cm = ModeManager::FindChannelModeByName(lock->name); + if (use_server_side_mlock && cm && modelocks && ci->c && (cm->type == MODE_REGULAR || cm->type == MODE_PARAM) && Servers::Capab.count("MLOCK") > 0) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", "").replace_all_cs(cm->mchar, ""); + UplinkSocket::Message(Me) << "MLOCK " << static_cast(ci->c->creation_time) << " " << ci->name << " " << modes; + } + + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(ProtoUnreal) diff --git a/modules/protocol/unreal4.cpp b/modules/protocol/unreal4.cpp new file mode 100644 index 0000000..6626158 --- /dev/null +++ b/modules/protocol/unreal4.cpp @@ -0,0 +1,1741 @@ +/* Unreal IRCD 4 functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/cs_mode.h" +#include "modules/sasl.h" + +typedef Anope::map ModData; +static Anope::string UplinkSID; + +class UnrealIRCdProto : public IRCDProto +{ + public: + PrimitiveExtensibleItem ClientModData; + PrimitiveExtensibleItem ChannelModData; + + UnrealIRCdProto(Module *creator) : IRCDProto(creator, "UnrealIRCd 4+"), ClientModData(creator, "ClientModData"), ChannelModData(creator, "ChannelModData") + { + DefaultPseudoclientModes = "+BioqS"; + CanSVSNick = true; + CanSVSJoin = true; + CanSetVHost = true; + CanSetVIdent = true; + CanSNLine = true; + CanSQLine = true; + CanSZLine = true; + CanSVSHold = true; + CanCertFP = true; + RequiresID = true; + MaxModes = 12; + } + + private: + /* SVSNOOP */ + void SendSVSNOOP(const Server *server, bool set) anope_override + { + UplinkSocket::Message() << "SVSNOOP " << server->GetSID() << " " << (set ? "+" : "-"); + } + + void SendAkillDel(const XLine *x) anope_override + { + if (x->IsRegex() || x->HasNickOrReal()) + return; + + /* ZLine if we can instead */ + if (x->GetUser() == "*") + { + cidr a(x->GetHost()); + if (a.valid()) + { + IRCD->SendSZLineDel(x); + return; + } + } + + UplinkSocket::Message() << "TKL - G " << x->GetUser() << " " << x->GetHost() << " " << x->by; + } + + void SendTopic(const MessageSource &source, Channel *c) anope_override + { + UplinkSocket::Message(source) << "TOPIC " << c->name << " " << c->topic_setter << " " << c->topic_ts << " :" << c->topic; + } + + void SendGlobalNotice(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "NOTICE $" << dest->GetName() << " :" << msg; + } + + void SendGlobalPrivmsg(BotInfo *bi, const Server *dest, const Anope::string &msg) anope_override + { + UplinkSocket::Message(bi) << "PRIVMSG $" << dest->GetName() << " :" << msg; + } + + void SendVhostDel(User *u) anope_override + { + BotInfo *HostServ = Config->GetClient("HostServ"); + u->RemoveMode(HostServ, "VHOST"); + } + + void SendAkill(User *u, XLine *x) anope_override + { + if (x->IsRegex() || x->HasNickOrReal()) + { + if (!u) + { + /* No user (this akill was just added), and contains nick and/or realname. Find users that match and ban them */ + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + if (x->manager->Check(it->second, x)) + this->SendAkill(it->second, x); + return; + } + + const XLine *old = x; + + if (old->manager->HasEntry("*@" + u->host)) + return; + + /* We can't akill x as it has a nick and/or realname included, so create a new akill for *@host */ + XLine *xline = new XLine("*@" + u->host, old->by, old->expires, old->reason, old->id); + old->manager->AddXLine(xline); + x = xline; + + Log(Config->GetClient("OperServ"), "akill") << "AKILL: Added an akill for " << x->mask << " because " << u->GetMask() << "#" << u->realname << " matches " << old->mask; + } + + /* ZLine if we can instead */ + if (x->GetUser() == "*") + { + cidr a(x->GetHost()); + if (a.valid()) + { + IRCD->SendSZLine(u, x); + return; + } + } + + // Calculate the time left before this would expire, capping it at 2 days + time_t timeleft = x->expires - Anope::CurTime; + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + UplinkSocket::Message() << "TKL + G " << x->GetUser() << " " << x->GetHost() << " " << x->by << " " << Anope::CurTime + timeleft << " " << x->created << " :" << x->GetReason(); + } + + void SendSVSKillInternal(const MessageSource &source, User *user, const Anope::string &buf) anope_override + { + UplinkSocket::Message(source) << "SVSKILL " << user->GetUID() << " :" << buf; + user->KillInternal(source, buf); + } + + void SendModeInternal(const MessageSource &source, User *u, const Anope::string &buf) anope_override + { + UplinkSocket::Message(source) << "SVS2MODE " << u->GetUID() <<" " << buf; + } + + void SendClientIntroduction(User *u) anope_override + { + Anope::string modes = "+" + u->GetModes(); + UplinkSocket::Message(u->server) << "UID " << u->nick << " 1 " << u->timestamp << " " << u->GetIdent() << " " << u->host << " " + << u->GetUID() << " * " << modes << " " << (!u->vhost.empty() ? u->vhost : "*") << " " + << (!u->chost.empty() ? u->chost : "*") << " " << "*" << " :" << u->realname; + } + + void SendServer(const Server *server) anope_override + { + if (server == Me) + UplinkSocket::Message() << "SERVER " << server->GetName() << " " << server->GetHops() + 1 << " :" << server->GetDescription(); + else + UplinkSocket::Message(Me) << "SID " << server->GetName() << " " << server->GetHops() + 1 << " " << server->GetSID() << " :" << server->GetDescription(); + } + + /* JOIN */ + void SendJoin(User *user, Channel *c, const ChannelStatus *status) anope_override + { + UplinkSocket::Message(Me) << "SJOIN " << c->creation_time << " " << c->name + << " +" << c->GetModes(true, true) << " :" << user->GetUID(); + if (status) + { + /* First save the channel status incase uc->Status == status */ + ChannelStatus cs = *status; + /* If the user is internally on the channel with flags, kill them so that + * the stacker will allow this. + */ + ChanUserContainer *uc = c->FindUser(user); + if (uc != NULL) + uc->status.Clear(); + + BotInfo *setter = BotInfo::Find(user->GetUID()); + for (size_t i = 0; i < cs.Modes().length(); ++i) + c->SetMode(setter, ModeManager::FindChannelModeByChar(cs.Modes()[i]), user->GetUID(), false); + + if (uc != NULL) + uc->status = cs; + } + } + + /* unsqline + */ + void SendSQLineDel(const XLine *x) anope_override + { + UplinkSocket::Message() << "UNSQLINE " << x->mask; + } + + /* SQLINE */ + /* + ** - Unreal will translate this to TKL for us + ** + */ + void SendSQLine(User *, const XLine *x) anope_override + { + UplinkSocket::Message() << "SQLINE " << x->mask << " :" << x->GetReason(); + } + + /* Functions that use serval cmd functions */ + + void SendVhost(User *u, const Anope::string &vIdent, const Anope::string &vhost) anope_override + { + if (!vIdent.empty()) + UplinkSocket::Message(Me) << "CHGIDENT " << u->GetUID() << " " << vIdent; + if (!vhost.empty()) + UplinkSocket::Message(Me) << "CHGHOST " << u->GetUID() << " " << vhost; + // Internally unreal sets +xt on chghost + BotInfo *bi = Config->GetClient("HostServ"); + u->SetMode(bi, "CLOAK"); + u->SetMode(bi, "VHOST"); + } + + void SendConnect() anope_override + { + /* + NICKv2 = Nick Version 2 + VHP = Sends hidden host + UMODE2 = sends UMODE2 on user modes + NICKIP = Sends IP on NICK + SJ3 = Supports SJOIN + NOQUIT = No Quit + TKLEXT = Extended TKL we don't use it but best to have it + MLOCK = Supports the MLOCK server command + VL = Version Info + SID = SID/UID mode + */ + UplinkSocket::Message() << "PASS :" << Config->Uplinks[Anope::CurrentUplink].password; + UplinkSocket::Message() << "PROTOCTL " << "NICKv2 VHP UMODE2 NICKIP SJOIN SJOIN2 SJ3 NOQUIT TKLEXT MLOCK SID MTAGS"; + UplinkSocket::Message() << "PROTOCTL " << "EAUTH=" << Me->GetName() << ",,,Anope-" << Anope::VersionShort(); + UplinkSocket::Message() << "PROTOCTL " << "SID=" << Me->GetSID(); + SendServer(Me); + } + + void SendSASLMechanisms(std::vector &mechanisms) anope_override + { + Anope::string mechlist; + for (unsigned i = 0; i < mechanisms.size(); ++i) + mechlist += "," + mechanisms[i]; + + UplinkSocket::Message() << "MD client " << Me->GetName() << " saslmechlist :" << (mechanisms.empty() ? "" : mechlist.substr(1)); + } + + /* SVSHOLD - set */ + void SendSVSHold(const Anope::string &nick, time_t t) anope_override + { + UplinkSocket::Message() << "TKL + Q H " << nick << " " << Me->GetName() << " " << Anope::CurTime + t << " " << Anope::CurTime << " :Being held for registered user"; + } + + /* SVSHOLD - release */ + void SendSVSHoldDel(const Anope::string &nick) anope_override + { + UplinkSocket::Message() << "TKL - Q * " << nick << " " << Me->GetName(); + } + + /* UNSGLINE */ + /* + * SVSNLINE - :realname mask + */ + void SendSGLineDel(const XLine *x) anope_override + { + UplinkSocket::Message() << "SVSNLINE - :" << x->mask; + } + + /* UNSZLINE */ + void SendSZLineDel(const XLine *x) anope_override + { + UplinkSocket::Message() << "TKL - Z * " << x->GetHost() << " " << x->by; + } + + /* SZLINE */ + void SendSZLine(User *, const XLine *x) anope_override + { + // Calculate the time left before this would expire, capping it at 2 days + time_t timeleft = x->expires - Anope::CurTime; + if (timeleft > 172800 || !x->expires) + timeleft = 172800; + UplinkSocket::Message() << "TKL + Z * " << x->GetHost() << " " << x->by << " " << Anope::CurTime + timeleft << " " << x->created << " :" << x->GetReason(); + } + + /* SGLINE */ + /* + * SVSNLINE + reason_where_is_space :realname mask with spaces + */ + void SendSGLine(User *, const XLine *x) anope_override + { + Anope::string edited_reason = x->GetReason(); + edited_reason = edited_reason.replace_all_cs(" ", "_"); + UplinkSocket::Message() << "SVSNLINE + " << edited_reason << " :" << x->mask; + } + + /* svsjoin + parv[0] - sender + parv[1] - nick to make join + parv[2] - channel to join + parv[3] - (optional) channel key(s) + */ + /* In older Unreal SVSJOIN and SVSNLINE tokens were mixed so SVSJOIN and SVSNLINE are broken + when coming from a none TOKEN'd server + */ + void SendSVSJoin(const MessageSource &source, User *user, const Anope::string &chan, const Anope::string ¶m) anope_override + { + if (!param.empty()) + UplinkSocket::Message() << "SVSJOIN " << user->GetUID() << " " << chan << " :" << param; + else + UplinkSocket::Message() << "SVSJOIN " << user->GetUID() << " " << chan; + } + + void SendSVSPart(const MessageSource &source, User *user, const Anope::string &chan, const Anope::string ¶m) anope_override + { + if (!param.empty()) + UplinkSocket::Message() << "SVSPART " << user->GetUID() << " " << chan << " :" << param; + else + UplinkSocket::Message() << "SVSPART " << user->GetUID() << " " << chan; + } + + void SendGlobopsInternal(const MessageSource &source, const Anope::string &buf) anope_override + { + UplinkSocket::Message(Me) << "SENDUMODE o :from " << source.GetName() << ": " << buf; + } + + void SendSWhois(const MessageSource &source, const Anope::string &who, const Anope::string &mask) anope_override + { + UplinkSocket::Message() << "SWHOIS " << who << " :" << mask; + } + + void SendEOB() anope_override + { + UplinkSocket::Message(Me) << "EOS"; + } + + bool IsNickValid(const Anope::string &nick) anope_override + { + if (nick.equals_ci("ircd") || nick.equals_ci("irc")) + return false; + + return IRCDProto::IsNickValid(nick); + } + + bool IsChannelValid(const Anope::string &chan) anope_override + { + if (chan.find(':') != Anope::string::npos) + return false; + + return IRCDProto::IsChannelValid(chan); + } + + bool IsExtbanValid(const Anope::string &mask) anope_override + { + return mask.length() >= 4 && mask[0] == '~' && mask[2] == ':'; + } + + void SendLogin(User *u, NickAlias *na) anope_override + { + /* 3.2.10.4+ treats users logged in with accounts as fully registered, even if -r, so we can not set this here. Just use the timestamp. */ + if (Servers::Capab.count("ESVID") > 0 && !na->nc->HasExt("UNCONFIRMED")) + IRCD->SendMode(Config->GetClient("NickServ"), u, "+d %s", na->nc->display.c_str()); + else + IRCD->SendMode(Config->GetClient("NickServ"), u, "+d %d", u->signon); + } + + void SendLogout(User *u) anope_override + { + IRCD->SendMode(Config->GetClient("NickServ"), u, "+d 0"); + } + + void SendChannel(Channel *c) anope_override + { + UplinkSocket::Message(Me) << "SJOIN " << c->creation_time << " " << c->name + << " +" << c->GetModes(true, true) << " :"; + } + + void SendSASLMessage(const SASL::Message &message) anope_override + { + size_t p = message.target.find('!'); + Anope::string distmask; + + if (p == Anope::string::npos) + { + Server *s = Server::Find(message.target.substr(0, 3)); + if (!s) + return; + distmask = s->GetName(); + } + else + { + distmask = message.target.substr(0, p); + } + + UplinkSocket::Message(BotInfo::Find(message.source)) << "SASL " << distmask << " " << message.target << " " << message.type << " " << message.data << (message.ext.empty() ? "" : " " + message.ext); + } + + void SendSVSLogin(const Anope::string &uid, const Anope::string &acc, const Anope::string &vident, const Anope::string &vhost) anope_override + { + size_t p = uid.find('!'); + Anope::string distmask; + + if (p == Anope::string::npos) + { + Server *s = Server::Find(uid.substr(0, 3)); + if (!s) + return; + distmask = s->GetName(); + } + else + { + distmask = uid.substr(0, p); + } + UplinkSocket::Message(Me) << "SVSLOGIN " << distmask << " " << uid << " " << acc; + } + + bool IsIdentValid(const Anope::string &ident) anope_override + { + if (ident.empty() || ident.length() > Config->GetBlock("networkinfo")->Get("userlen")) + return false; + + for (unsigned i = 0; i < ident.length(); ++i) + { + const char &c = ident[i]; + + if ((c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || (c >= '0' && c <= '9') || c == '.' || c == '-') + continue; + + if (c == '-' || c == '.' || c == '_') + continue; + + return false; + } + + return true; + } +}; + +class UnrealExtBan : public ChannelModeVirtual +{ + char ext; + + public: + UnrealExtBan(const Anope::string &mname, const Anope::string &basename, char extban) : ChannelModeVirtual(mname, basename) + , ext(extban) + { + } + + ChannelMode *Wrap(Anope::string ¶m) anope_override + { + param = "~" + Anope::string(ext) + ":" + param; + return ChannelModeVirtual::Wrap(param); + } + + ChannelMode *Unwrap(ChannelMode *cm, Anope::string ¶m) anope_override + { + if (cm->type != MODE_LIST || param.length() < 4 || param[0] != '~' || param[1] != ext || param[2] != ':') + return cm; + + param = param.substr(3); + return this; + } +}; + +namespace UnrealExtban +{ + class ChannelMatcher : public UnrealExtBan + { + public: + ChannelMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string channel = mask.substr(3); + + ChannelMode *cm = NULL; + if (channel[0] != '#') + { + char modeChar = ModeManager::GetStatusChar(channel[0]); + channel.erase(channel.begin()); + cm = ModeManager::FindChannelModeByChar(modeChar); + if (cm != NULL && cm->type != MODE_STATUS) + cm = NULL; + } + + Channel *c = Channel::Find(channel); + if (c != NULL) + { + ChanUserContainer *uc = c->FindUser(u); + if (uc != NULL) + if (cm == NULL || uc->status.HasMode(cm->mchar)) + return true; + } + + return false; + } + }; + + class EntryMatcher : public UnrealExtBan + { + public: + EntryMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(3); + + return Entry(this->name, real_mask).Matches(u); + } + }; + + class RealnameMatcher : public UnrealExtBan + { + public: + RealnameMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(3); + + return Anope::Match(u->realname, real_mask); + } + }; + + class RegisteredMatcher : public UnrealExtBan + { + public: + RegisteredMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + return u->HasMode("REGISTERED") && mask.equals_ci(u->nick); + } + }; + + class AccountMatcher : public UnrealExtBan + { + public: + AccountMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(3); + + if (real_mask == "0" && !u->Account()) /* ~a:0 is special and matches all unauthenticated users */ + return true; + + return u->Account() && Anope::Match(u->Account()->display, real_mask); + } + }; + + class FingerprintMatcher : public UnrealExtBan + { + public: + FingerprintMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(3); + return !u->fingerprint.empty() && Anope::Match(u->fingerprint, real_mask); + } + }; + + class OperclassMatcher : public UnrealExtBan + { + public: + OperclassMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(3); + ModData *moddata = u->GetExt("ClientModData"); + return moddata != NULL && moddata->find("operclass") != moddata->end() && Anope::Match((*moddata)["operclass"], real_mask); + } + }; + + class TimedBanMatcher : public UnrealExtBan + { + public: + TimedBanMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + /* strip down the time (~t:1234:) and call other matchers */ + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(3); + real_mask = real_mask.substr(real_mask.find(":") + 1); + return Entry("BAN", real_mask).Matches(u); + } + }; + + class CountryMatcher : public UnrealExtBan + { + public: + CountryMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c) + { + } + + bool Matches(User *u, const Entry *e) anope_override + { + const Anope::string &mask = e->GetMask(); + Anope::string real_mask = mask.substr(3); + ModData *moddata = u->GetExt("ClientModData"); + if (moddata == NULL || moddata->find("geoip") == moddata->end()) + return false; + + sepstream sep((*moddata)["geoip"], '|');/* "cc=PL|cd=Poland" */ + Anope::string tokenbuf; + while (sep.GetToken(tokenbuf)) + { + if (tokenbuf.rfind("cc=", 0) == 0) + return (tokenbuf.substr(3, 2) == real_mask); + } + return false; + } + }; + +} + +class ChannelModeFlood : public ChannelModeParam +{ + public: + ChannelModeFlood(char modeChar, bool minusNoArg) : ChannelModeParam("FLOOD", modeChar, minusNoArg) { } + + /* Borrowed part of this check from UnrealIRCd */ + bool IsValid(Anope::string &value) const anope_override + { + if (value.empty()) + return false; + try + { + Anope::string rest; + if (value[0] != ':' && convertTo(value[0] == '*' ? value.substr(1) : value, rest, false) > 0 && rest[0] == ':' && rest.length() > 1 && convertTo(rest.substr(1), rest, false) > 0 && rest.empty()) + return true; + } + catch (const ConvertException &) { } + + /* '['<1 letter>[optional: '#'+1 letter],[next..]']'':' */ + size_t end_bracket = value.find(']', 1); + if (end_bracket == Anope::string::npos) + return false; + Anope::string xbuf = value.substr(0, end_bracket); + if (value[end_bracket + 1] != ':') + return false; + commasepstream args(xbuf.substr(1)); + Anope::string arg; + while (args.GetToken(arg)) + { + /* <1 letter>[optional: '#'+1 letter] */ + size_t p = 0; + while (p < arg.length() && isdigit(arg[p])) + ++p; + if (p == arg.length() || !(arg[p] == 'c' || arg[p] == 'j' || arg[p] == 'k' || arg[p] == 'm' || arg[p] == 'n' || arg[p] == 't')) + continue; /* continue instead of break for forward compatibility. */ + try + { + int v = arg.substr(0, p).is_number_only() ? convertTo(arg.substr(0, p)) : 0; + if (v < 1 || v > 999) + return false; + } + catch (const ConvertException &) + { + return false; + } + } + + return true; + } +}; + +class ChannelModeHistory : public ChannelModeParam /* stolen from inspircd3's ColonDelimitedParamMode */ +{ + public: + ChannelModeHistory(char modeChar) : ChannelModeParam("HISTORY", modeChar, true) { } + + bool IsValid(Anope::string &value) const anope_override + { + if (value.empty()) + return false; // empty param is never valid + + Anope::string::size_type pos = value.find(':'); + if ((pos == Anope::string::npos) || (pos == 0)) + return false; // no ':' or it's the first char, both are invalid + + Anope::string rest; + try + { + if (convertTo(value, rest, false) <= 0) + return false; // negative numbers and zero are invalid + + rest = rest.substr(1); + int n; + // The part after the ':' is a duration and it + // can be in the user friendly "1d3h20m" format, make sure we accept that + n = Anope::DoTime(rest); + + if (n <= 0) + return false; + } + catch (const ConvertException &e) + { + // conversion error, invalid + return false; + } + + return true; + } +}; + +class ChannelModeUnrealSSL : public ChannelMode +{ + public: + ChannelModeUnrealSSL(const Anope::string &n, char c) : ChannelMode(n, c) + { + } + + bool CanSet(User *u) const anope_override + { + return false; + } +}; + +struct IRCDMessageCapab : Message::Capab +{ + IRCDMessageCapab(Module *creator) : Message::Capab(creator, "PROTOCTL") { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + for (unsigned i = 0; i < params.size(); ++i) + { + Anope::string capab = params[i]; + + if (capab.find("USERMODES=") != Anope::string::npos) + { + Anope::string modebuf(capab.begin() + 10, capab.end()); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'B': + ModeManager::AddUserMode(new UserMode("BOT", 'B')); + continue; + case 'G': + ModeManager::AddUserMode(new UserMode("CENSOR", 'G')); + continue; + case 'H': + ModeManager::AddUserMode(new UserModeOperOnly("HIDEOPER", 'H')); + continue; + case 'I': + ModeManager::AddUserMode(new UserModeOperOnly("HIDEIDLE", 'I')); + continue; + case 'R': + ModeManager::AddUserMode(new UserMode("REGPRIV", 'R')); + continue; + case 'S': + ModeManager::AddUserMode(new UserModeOperOnly("PROTECTED", 'S')); + continue; + case 'T': + ModeManager::AddUserMode(new UserMode("NOCTCP", 'T')); + continue; + case 'W': + ModeManager::AddUserMode(new UserModeOperOnly("WHOIS", 'W')); + continue; + case 'd': + ModeManager::AddUserMode(new UserMode("DEAF", 'd')); + continue; + case 'D': + ModeManager::AddUserMode(new UserMode("PRIVDEAF", 'D')); + continue; + case 'i': + ModeManager::AddUserMode(new UserMode("INVIS", 'i')); + continue; + case 'o': + ModeManager::AddUserMode(new UserModeOperOnly("OPER", 'o')); + continue; + case 'p': + ModeManager::AddUserMode(new UserMode("PRIV", 'p')); + continue; + case 'q': + ModeManager::AddUserMode(new UserModeOperOnly("GOD", 'q')); + continue; + case 'r': + ModeManager::AddUserMode(new UserModeNoone("REGISTERED", 'r')); + continue; + case 's': + ModeManager::AddUserMode(new UserModeOperOnly("SNOMASK", 's')); + continue; + case 't': + ModeManager::AddUserMode(new UserModeNoone("VHOST", 't')); + continue; + case 'w': + ModeManager::AddUserMode(new UserMode("WALLOPS", 'w')); + continue; + case 'x': + ModeManager::AddUserMode(new UserMode("CLOAK", 'x')); + continue; + case 'z': + ModeManager::AddUserMode(new UserModeNoone("SSL", 'z')); + continue; + case 'Z': + ModeManager::AddUserMode(new UserMode("SSLPRIV", 'Z')); + continue; + default: + ModeManager::AddUserMode(new UserMode("", modebuf[t])); + } + } + } + else if (capab.find("CHANMODES=") != Anope::string::npos) + { + Anope::string modes(capab.begin() + 10, capab.end()); + commasepstream sep(modes); + Anope::string modebuf; + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'b': + ModeManager::AddChannelMode(new ChannelModeList("BAN", 'b')); + + ModeManager::AddChannelMode(new UnrealExtban::ChannelMatcher("CHANNELBAN", "BAN", 'c')); + ModeManager::AddChannelMode(new UnrealExtban::EntryMatcher("JOINBAN", "BAN", 'j')); + ModeManager::AddChannelMode(new UnrealExtban::EntryMatcher("NONICKBAN", "BAN", 'n')); + ModeManager::AddChannelMode(new UnrealExtban::EntryMatcher("QUIET", "BAN", 'q')); + ModeManager::AddChannelMode(new UnrealExtban::RealnameMatcher("REALNAMEBAN", "BAN", 'r')); + ModeManager::AddChannelMode(new UnrealExtban::RegisteredMatcher("REGISTEREDBAN", "BAN", 'R')); + ModeManager::AddChannelMode(new UnrealExtban::AccountMatcher("ACCOUNTBAN", "BAN", 'a')); + ModeManager::AddChannelMode(new UnrealExtban::FingerprintMatcher("SSLBAN", "BAN", 'S')); + ModeManager::AddChannelMode(new UnrealExtban::TimedBanMatcher("TIMEDBAN", "BAN", 't')); + ModeManager::AddChannelMode(new UnrealExtban::OperclassMatcher("OPERCLASSBAN", "BAN", 'O')); + ModeManager::AddChannelMode(new UnrealExtban::CountryMatcher("COUNTRYBAN", "BAN", 'C')); + continue; + case 'e': + ModeManager::AddChannelMode(new ChannelModeList("EXCEPT", 'e')); + continue; + case 'I': + ModeManager::AddChannelMode(new ChannelModeList("INVITEOVERRIDE", 'I')); + continue; + default: + ModeManager::AddChannelMode(new ChannelModeList("", modebuf[t])); + } + } + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'k': + ModeManager::AddChannelMode(new ChannelModeKey('k')); + continue; + case 'f': + ModeManager::AddChannelMode(new ChannelModeFlood('f', false)); + continue; + case 'L': + ModeManager::AddChannelMode(new ChannelModeParam("REDIRECT", 'L')); + continue; + default: + ModeManager::AddChannelMode(new ChannelModeParam("", modebuf[t])); + } + } + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'l': + ModeManager::AddChannelMode(new ChannelModeParam("LIMIT", 'l', true)); + continue; + case 'H': + ModeManager::AddChannelMode(new ChannelModeHistory('H')); + continue; + default: + ModeManager::AddChannelMode(new ChannelModeParam("", modebuf[t], true)); + } + } + + sep.GetToken(modebuf); + for (size_t t = 0, end = modebuf.length(); t < end; ++t) + { + switch (modebuf[t]) + { + case 'p': + ModeManager::AddChannelMode(new ChannelMode("PRIVATE", 'p')); + continue; + case 's': + ModeManager::AddChannelMode(new ChannelMode("SECRET", 's')); + continue; + case 'm': + ModeManager::AddChannelMode(new ChannelMode("MODERATED", 'm')); + continue; + case 'n': + ModeManager::AddChannelMode(new ChannelMode("NOEXTERNAL", 'n')); + continue; + case 't': + ModeManager::AddChannelMode(new ChannelMode("TOPIC", 't')); + continue; + case 'i': + ModeManager::AddChannelMode(new ChannelMode("INVITE", 'i')); + continue; + case 'r': + ModeManager::AddChannelMode(new ChannelModeNoone("REGISTERED", 'r')); + continue; + case 'R': + ModeManager::AddChannelMode(new ChannelMode("REGISTEREDONLY", 'R')); + continue; + case 'c': + ModeManager::AddChannelMode(new ChannelMode("BLOCKCOLOR", 'c')); + continue; + case 'O': + ModeManager::AddChannelMode(new ChannelModeOperOnly("OPERONLY", 'O')); + continue; + case 'Q': + ModeManager::AddChannelMode(new ChannelMode("NOKICK", 'Q')); + continue; + case 'K': + ModeManager::AddChannelMode(new ChannelMode("NOKNOCK", 'K')); + continue; + case 'V': + ModeManager::AddChannelMode(new ChannelMode("NOINVITE", 'V')); + continue; + case 'C': + ModeManager::AddChannelMode(new ChannelMode("NOCTCP", 'C')); + continue; + case 'z': + ModeManager::AddChannelMode(new ChannelMode("SSL", 'z')); + continue; + case 'N': + ModeManager::AddChannelMode(new ChannelMode("NONICK", 'N')); + continue; + case 'S': + ModeManager::AddChannelMode(new ChannelMode("STRIPCOLOR", 'S')); + continue; + case 'M': + ModeManager::AddChannelMode(new ChannelMode("REGMODERATED", 'M')); + continue; + case 'T': + ModeManager::AddChannelMode(new ChannelMode("NONOTICE", 'T')); + continue; + case 'G': + ModeManager::AddChannelMode(new ChannelMode("CENSOR", 'G')); + continue; + case 'Z': + ModeManager::AddChannelMode(new ChannelModeUnrealSSL("ALLSSL", 'Z')); + continue; + case 'd': + // post delayed. means that channel is -D but invisible users still exist. + continue; + case 'D': + ModeManager::AddChannelMode(new ChannelMode("DELAYEDJOIN", 'D')); + continue; + case 'P': + ModeManager::AddChannelMode(new ChannelModeOperOnly("PERM", 'P')); + continue; + default: + ModeManager::AddChannelMode(new ChannelMode("", modebuf[t])); + } + } + } + else if (!capab.find("SID=")) + { + UplinkSID = capab.substr(4); + } + else if (!capab.find("PREFIX=")) /* PREFIX=(qaohv)~&@%+ */ + { + Anope::string modes(capab.begin() + 7, capab.end()); + reverse(modes.begin(), modes.end()); /* +%@&!)vhoaq( */ + std::size_t mode_count = modes.find(')'); + Anope::string mode_prefixes = modes.substr(0, mode_count); + Anope::string mode_chars = modes.substr(mode_count+1, mode_count); + + for (size_t t = 0, end = mode_chars.length(); t < end; ++t) + { + Anope::string mode_name; + switch (mode_chars[t]) + { + + case 'v': + mode_name = "VOICE"; + break; + case 'h': + mode_name = "HALFOP"; + break; + case 'o': + mode_name = "OP"; + break; + case 'a': + mode_name = "PROTECT"; + break; + case 'q': + mode_name = "OWNER"; + break; + default: + mode_name = ""; + break; + } + ModeManager::AddChannelMode(new ChannelModeStatus(mode_name, mode_chars[t], mode_prefixes[t], t)); + } + } + } + + Message::Capab::Run(source, params); + } +}; + +struct IRCDMessageChgHost : IRCDMessage +{ + IRCDMessageChgHost(Module *creator) : IRCDMessage(creator, "CHGHOST", 2) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = User::Find(params[0]); + if (u) + u->SetDisplayedHost(params[1]); + } +}; + +struct IRCDMessageChgIdent : IRCDMessage +{ + IRCDMessageChgIdent(Module *creator) : IRCDMessage(creator, "CHGIDENT", 2) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = User::Find(params[0]); + if (u) + u->SetVIdent(params[1]); + } +}; + +struct IRCDMessageChgName : IRCDMessage +{ + IRCDMessageChgName(Module *creator) : IRCDMessage(creator, "CHGNAME", 2) { } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = User::Find(params[0]); + if (u) + u->SetRealname(params[1]); + } +}; + +struct IRCDMessageMD : IRCDMessage +{ + PrimitiveExtensibleItem &ClientModData; + PrimitiveExtensibleItem &ChannelModData; + + IRCDMessageMD(Module *creator, PrimitiveExtensibleItem &clmoddata, PrimitiveExtensibleItem &chmoddata) : IRCDMessage(creator, "MD", 3), ClientModData(clmoddata), ChannelModData(chmoddata) + { + SetFlag(IRCDMESSAGE_SOFT_LIMIT); + } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + const Anope::string &mdtype = params[0], + &obj = params[1], + &var = params[2], + &value = params.size() > 3 ? params[3] : ""; + + if (mdtype == "client") /* can be a server too! */ + { + User *u = User::Find(obj); + + if (u == NULL) + return; + + ModData &clientmd = *ClientModData.Require(u); + + if (value.empty()) + { + clientmd.erase(var); + Log(LOG_DEBUG) << "Erased client moddata " << var << " from " << u->nick; + } + else + { + clientmd[var] = value; + Log(LOG_DEBUG) << "Set client moddata " << var << "=\"" << value << "\" to " << u->nick; + } + if (var == "certfp" && !value.empty()) + { + u->Extend("ssl"); + u->fingerprint = value; + FOREACH_MOD(OnFingerprint, (u)); + } + } + else if (mdtype == "channel") + { + Channel *c = Channel::Find(obj); + + if (c == NULL) + return; + + ModData &channelmd = *ChannelModData.Require(c); + + if (value.empty()) + { + channelmd.erase(var); + Log(LOG_DEBUG) << "Erased channel moddata " << var << " from " << c->name; + } + else + { + channelmd[var] = value; + Log(LOG_DEBUG) << "Set channel moddata " << var << "=\"" << value << "\" to " << c->name; + } + } + } +}; + +struct IRCDMessageMode : IRCDMessage +{ + IRCDMessageMode(Module *creator, const Anope::string &mname) : IRCDMessage(creator, mname, 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + bool server_source = source.GetServer() != NULL; + Anope::string modes = params[1]; + for (unsigned i = 2; i < params.size() - (server_source ? 1 : 0); ++i) + modes += " " + params[i]; + + if (IRCD->IsChannelValid(params[0])) + { + Channel *c = Channel::Find(params[0]); + time_t ts = 0; + + try + { + if (server_source) + ts = convertTo(params[params.size() - 1]); + } + catch (const ConvertException &) { } + + if (c) + c->SetModesInternal(source, modes, ts); + } + else + { + User *u = User::Find(params[0]); + if (u) + u->SetModesInternal(source, "%s", params[1].c_str()); + } + } +}; + +/* netinfo + * argv[0] = max global count + * argv[1] = time of end sync + * argv[2] = unreal protocol using (numeric) + * argv[3] = cloak-crc (> u2302) + * argv[4] = free(**) + * argv[5] = free(**) + * argv[6] = free(**) + * argv[7] = ircnet + */ +struct IRCDMessageNetInfo : IRCDMessage +{ + IRCDMessageNetInfo(Module *creator) : IRCDMessage(creator, "NETINFO", 8) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + UplinkSocket::Message() << "NETINFO " << MaxUserCount << " " << Anope::CurTime << " " << convertTo(params[2]) << " " << params[3] << " 0 0 0 :" << params[7]; + } +}; + +struct IRCDMessageNick : IRCDMessage +{ + IRCDMessageNick(Module *creator) : IRCDMessage(creator, "NICK", 2) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + /* + ** NICK - new + ** source = NULL + ** parv[0] = nickname + ** parv[1] = hopcount + ** parv[2] = timestamp + ** parv[3] = username + ** parv[4] = hostname + ** parv[5] = servername + ** parv[6] = servicestamp + ** parv[7] = umodes + ** parv[8] = virthost, * if none + ** parv[9] = ip + ** parv[10] = info + ** + ** NICK - change + ** source = oldnick + ** parv[0] = new nickname + ** parv[1] = hopcount + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (params.size() == 11) + { + Anope::string ip; + if (params[9] != "*") + { + Anope::string decoded_ip; + Anope::B64Decode(params[9], decoded_ip); + + sockaddrs ip_addr; + ip_addr.ntop(params[9].length() == 8 ? AF_INET : AF_INET6, decoded_ip.c_str()); + ip = ip_addr.addr(); + } + + Anope::string vhost = params[8]; + if (vhost.equals_cs("*")) + vhost.clear(); + + time_t user_ts = params[2].is_pos_number_only() ? convertTo(params[2]) : Anope::CurTime; + + Server *s = Server::Find(params[5]); + if (s == NULL) + { + Log(LOG_DEBUG) << "User " << params[0] << " introduced from nonexistent server " << params[5] << "?"; + return; + } + + NickAlias *na = NULL; + + if (params[6] == "0") + ; + else if (params[6].is_pos_number_only()) + { + if (convertTo(params[6]) == user_ts) + na = NickAlias::Find(params[0]); + } + else + { + na = NickAlias::Find(params[6]); + } + + User::OnIntroduce(params[0], params[3], params[4], vhost, ip, s, params[10], user_ts, params[7], "", na ? *na->nc : NULL); + } + else + { + User *u = source.GetUser(); + if (u) + u->ChangeNick(params[0]); + } + } +}; + +/** This is here because: + * + * If we had three servers, A, B & C linked like so: A<->B<->C + * If Anope is linked to A and B splits from A and then reconnects + * B introduces itself, introduces C, sends EOS for C, introduces Bs clients + * introduces Cs clients, sends EOS for B. This causes all of Cs clients to be introduced + * with their server "not syncing". We now send a PING immediately when receiving a new server + * and then finish sync once we get a pong back from that server. + */ +struct IRCDMessagePong : IRCDMessage +{ + IRCDMessagePong(Module *creator) : IRCDMessage(creator, "PONG", 0) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (!source.GetServer()->IsSynced()) + source.GetServer()->Sync(false); + } +}; + +struct IRCDMessageSASL : IRCDMessage +{ + IRCDMessageSASL(Module *creator) : IRCDMessage(creator, "SASL", 4) { SetFlag(IRCDMESSAGE_SOFT_LIMIT); SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + if (!SASL::sasl) + return; + + SASL::Message m; + m.source = params[1]; + m.target = params[0]; + m.type = params[2]; + m.data = params[3]; + m.ext = params.size() > 4 ? params[4] : ""; + + SASL::sasl->ProcessMessage(m); + } +}; + +struct IRCDMessageSDesc : IRCDMessage +{ + IRCDMessageSDesc(Module *creator) : IRCDMessage(creator, "SDESC", 1) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetServer()->SetDescription(params[0]); + } +}; + +struct IRCDMessageSetHost : IRCDMessage +{ + IRCDMessageSetHost(Module *creator) : IRCDMessage(creator, "SETHOST", 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + + /* When a user sets +x we receive the new host and then the mode change */ + if (u->HasMode("CLOAK")) + u->SetDisplayedHost(params[0]); + else + u->SetCloakedHost(params[0]); + } +}; + +struct IRCDMessageSetIdent : IRCDMessage +{ + IRCDMessageSetIdent(Module *creator) : IRCDMessage(creator, "SETIDENT", 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + u->SetVIdent(params[0]); + } +}; + +struct IRCDMessageSetName : IRCDMessage +{ + IRCDMessageSetName(Module *creator) : IRCDMessage(creator, "SETNAME", 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + User *u = source.GetUser(); + u->SetRealname(params[0]); + } +}; + +struct IRCDMessageServer : IRCDMessage +{ + IRCDMessageServer(Module *creator) : IRCDMessage(creator, "SERVER", 3) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + unsigned int hops = Anope::string(params[1]).is_pos_number_only() ? convertTo(params[1]) : 0; + + if (params[1].equals_cs("1")) + { + Anope::string desc; + spacesepstream(params[2]).GetTokenRemainder(desc, 1); + + new Server(source.GetServer() == NULL ? Me : source.GetServer(), params[0], hops, desc, UplinkSID); + } + else + new Server(source.GetServer(), params[0], hops, params[2]); + + IRCD->SendPing(Me->GetName(), params[0]); + } +}; + +struct IRCDMessageSID : IRCDMessage +{ + IRCDMessageSID(Module *creator) : IRCDMessage(creator, "SID", 4) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + unsigned int hops = Anope::string(params[1]).is_pos_number_only() ? convertTo(params[1]) : 0; + + new Server(source.GetServer(), params[0], hops, params[3], params[2]); + + IRCD->SendPing(Me->GetName(), params[0]); + } +}; + +static char UnrealSjoinPrefixToModeChar(char sjoin_prefix) +{ + switch(sjoin_prefix) + { + case '*': + return ModeManager::GetStatusChar('~'); + case '~': + return ModeManager::GetStatusChar('&'); + default: + return ModeManager::GetStatusChar(sjoin_prefix); /* remaining are regular */ + } +} + +struct IRCDMessageSJoin : IRCDMessage +{ + IRCDMessageSJoin(Module *creator) : IRCDMessage(creator, "SJOIN", 3) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); SetFlag(IRCDMESSAGE_SOFT_LIMIT); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Anope::string modes; + if (params.size() >= 4) + for (unsigned i = 2; i < params.size() - 1; ++i) + modes += " " + params[i]; + if (!modes.empty()) + modes.erase(modes.begin()); + + std::list bans, excepts, invites; + std::list users; + + spacesepstream sep(params[params.size() - 1]); + Anope::string buf; + while (sep.GetToken(buf)) + { + /* Ban */ + if (buf[0] == '&') + { + buf.erase(buf.begin()); + bans.push_back(buf); + } + /* Except */ + else if (buf[0] == '"') + { + buf.erase(buf.begin()); + excepts.push_back(buf); + } + /* Invex */ + else if (buf[0] == '\'') + { + buf.erase(buf.begin()); + invites.push_back(buf); + } + else + { + Message::Join::SJoinUser sju; + + /* Get prefixes from the nick */ + for (char ch; (ch = UnrealSjoinPrefixToModeChar(buf[0]));) + { + sju.first.AddMode(ch); + buf.erase(buf.begin()); + } + + sju.second = User::Find(buf); + if (!sju.second) + { + Log(LOG_DEBUG) << "SJOIN for nonexistent user " << buf << " on " << params[1]; + continue; + } + + users.push_back(sju); + } + } + + time_t ts = Anope::string(params[0]).is_pos_number_only() ? convertTo(params[0]) : Anope::CurTime; + Message::Join::SJoin(source, params[1], ts, modes, users); + + if (!bans.empty() || !excepts.empty() || !invites.empty()) + { + Channel *c = Channel::Find(params[1]); + + if (!c || c->creation_time != ts) + return; + + ChannelMode *ban = ModeManager::FindChannelModeByName("BAN"), + *except = ModeManager::FindChannelModeByName("EXCEPT"), + *invex = ModeManager::FindChannelModeByName("INVITEOVERRIDE"); + + if (ban) + for (std::list::iterator it = bans.begin(), it_end = bans.end(); it != it_end; ++it) + c->SetModeInternal(source, ban, *it); + if (except) + for (std::list::iterator it = excepts.begin(), it_end = excepts.end(); it != it_end; ++it) + c->SetModeInternal(source, except, *it); + if (invex) + for (std::list::iterator it = invites.begin(), it_end = invites.end(); it != it_end; ++it) + c->SetModeInternal(source, invex, *it); + } + } +}; + +struct IRCDMessageTopic : IRCDMessage +{ + IRCDMessageTopic(Module *creator) : IRCDMessage(creator, "TOPIC", 4) { } + + /* + ** source = sender prefix + ** parv[0] = channel name + ** parv[1] = topic nickname + ** parv[2] = topic time + ** parv[3] = topic text + */ + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Channel *c = Channel::Find(params[0]); + if (c) + c->ChangeTopicInternal(source.GetUser(), params[1], params[3], Anope::string(params[2]).is_pos_number_only() ? convertTo(params[2]) : Anope::CurTime); + } +}; + +/* + * parv[0] = nickname + * parv[1] = hopcount + * parv[2] = timestamp + * parv[3] = username + * parv[4] = hostname + * parv[5] = UID + * parv[6] = servicestamp + * parv[7] = umodes + * parv[8] = virthost, * if none + * parv[9] = cloaked host, * if none + * parv[10] = ip + * parv[11] = info + */ +struct IRCDMessageUID : IRCDMessage +{ + IRCDMessageUID(Module *creator) : IRCDMessage(creator, "UID", 12) { SetFlag(IRCDMESSAGE_REQUIRE_SERVER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + Anope::string + nickname = params[0], + hopcount = params[1], + timestamp = params[2], + username = params[3], + hostname = params[4], + uid = params[5], + account = params[6], + umodes = params[7], + vhost = params[8], + chost = params[9], + ip = params[10], + info = params[11]; + + if (ip != "*") + { + Anope::string decoded_ip; + Anope::B64Decode(ip, decoded_ip); + + sockaddrs ip_addr; + ip_addr.ntop(ip.length() == 8 ? AF_INET : AF_INET6, decoded_ip.c_str()); + ip = ip_addr.addr(); + } + + if (vhost == "*") + vhost.clear(); + + if (chost == "*") + chost.clear(); + + time_t user_ts; + try + { + user_ts = convertTo(timestamp); + } + catch (const ConvertException &) + { + user_ts = Anope::CurTime; + } + + NickAlias *na = NULL; + + if (account == "0") + { + ; + } + else if (account.is_pos_number_only()) + { + if (convertTo(account) == user_ts) + na = NickAlias::Find(nickname); + } + else + { + na = NickAlias::Find(account); + } + + User *u = User::OnIntroduce(nickname, username, hostname, vhost, ip, source.GetServer(), info, user_ts, umodes, uid, na ? *na->nc : NULL); + + if (u && !chost.empty() && chost != u->GetCloakedHost()) + u->SetCloakedHost(chost); + } +}; + +struct IRCDMessageUmode2 : IRCDMessage +{ + IRCDMessageUmode2(Module *creator) : IRCDMessage(creator, "UMODE2", 1) { SetFlag(IRCDMESSAGE_REQUIRE_USER); } + + void Run(MessageSource &source, const std::vector ¶ms) anope_override + { + source.GetUser()->SetModesInternal(source, "%s", params[0].c_str()); + } +}; + +class ProtoUnreal : public Module +{ + UnrealIRCdProto ircd_proto; + + /* Core message handlers */ + Message::Away message_away; + Message::Error message_error; + Message::Invite message_invite; + Message::Join message_join; + Message::Kick message_kick; + Message::Kill message_kill, message_svskill; + Message::MOTD message_motd; + Message::Notice message_notice; + Message::Part message_part; + Message::Ping message_ping; + Message::Privmsg message_privmsg; + Message::Quit message_quit; + Message::SQuit message_squit; + Message::Stats message_stats; + Message::Time message_time; + Message::Version message_version; + Message::Whois message_whois; + + /* Our message handlers */ + IRCDMessageCapab message_capab; + IRCDMessageChgHost message_chghost; + IRCDMessageChgIdent message_chgident; + IRCDMessageChgName message_chgname; + IRCDMessageMD message_md; + IRCDMessageMode message_mode, message_svsmode, message_svs2mode; + IRCDMessageNetInfo message_netinfo; + IRCDMessageNick message_nick; + IRCDMessagePong message_pong; + IRCDMessageSASL message_sasl; + IRCDMessageSDesc message_sdesc; + IRCDMessageSetHost message_sethost; + IRCDMessageSetIdent message_setident; + IRCDMessageSetName message_setname; + IRCDMessageServer message_server; + IRCDMessageSID message_sid; + IRCDMessageSJoin message_sjoin; + IRCDMessageTopic message_topic; + IRCDMessageUID message_uid; + IRCDMessageUmode2 message_umode2; + + bool use_server_side_mlock; + + public: + ProtoUnreal(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PROTOCOL | VENDOR), + ircd_proto(this), + message_away(this), message_error(this), message_invite(this), message_join(this), message_kick(this), + message_kill(this), message_svskill(this, "SVSKILL"), message_motd(this), message_notice(this), message_part(this), message_ping(this), + message_privmsg(this), message_quit(this), message_squit(this), message_stats(this), message_time(this), + message_version(this), message_whois(this), + + message_capab(this), message_chghost(this), message_chgident(this), message_chgname(this), + message_md(this, ircd_proto.ClientModData, ircd_proto.ChannelModData),message_mode(this, "MODE"), + message_svsmode(this, "SVSMODE"), message_svs2mode(this, "SVS2MODE"), message_netinfo(this), message_nick(this), message_pong(this), + message_sasl(this), message_sdesc(this), message_sethost(this), message_setident(this), message_setname(this), message_server(this), + message_sid(this), message_sjoin(this), message_topic(this), message_uid(this), message_umode2(this) + { + + } + + void Prioritize() anope_override + { + ModuleManager::SetPriority(this, PRIORITY_FIRST); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + use_server_side_mlock = conf->GetModule(this)->Get("use_server_side_mlock"); + } + + void OnUserNickChange(User *u, const Anope::string &) anope_override + { + u->RemoveModeInternal(Me, ModeManager::FindUserModeByName("REGISTERED")); + if (Servers::Capab.count("ESVID") == 0) + IRCD->SendLogout(u); + } + + void OnChannelSync(Channel *c) anope_override + { + if (!c->ci) + return; + + ModeLocks *modelocks = c->ci->GetExt("modelocks"); + if (use_server_side_mlock && Servers::Capab.count("MLOCK") > 0 && modelocks) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", ""); + UplinkSocket::Message(Me) << "MLOCK " << static_cast(c->creation_time) << " " << c->ci->name << " " << modes; + } + } + + void OnChanRegistered(ChannelInfo *ci) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + if (!ci->c || !use_server_side_mlock || !modelocks || !Servers::Capab.count("MLOCK")) + return; + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", ""); + UplinkSocket::Message(Me) << "MLOCK " << static_cast(ci->c->creation_time) << " " << ci->name << " " << modes; + } + + void OnDelChan(ChannelInfo *ci) anope_override + { + if (!ci->c || !use_server_side_mlock || !Servers::Capab.count("MLOCK")) + return; + UplinkSocket::Message(Me) << "MLOCK " << static_cast(ci->c->creation_time) << " " << ci->name << " :"; + } + + EventReturn OnMLock(ChannelInfo *ci, ModeLock *lock) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + ChannelMode *cm = ModeManager::FindChannelModeByName(lock->name); + if (use_server_side_mlock && cm && modelocks && ci->c && (cm->type == MODE_REGULAR || cm->type == MODE_PARAM) && Servers::Capab.count("MLOCK") > 0) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", "") + cm->mchar; + UplinkSocket::Message(Me) << "MLOCK " << static_cast(ci->c->creation_time) << " " << ci->name << " " << modes; + } + + return EVENT_CONTINUE; + } + + EventReturn OnUnMLock(ChannelInfo *ci, ModeLock *lock) anope_override + { + ModeLocks *modelocks = ci->GetExt("modelocks"); + ChannelMode *cm = ModeManager::FindChannelModeByName(lock->name); + if (use_server_side_mlock && cm && modelocks && ci->c && (cm->type == MODE_REGULAR || cm->type == MODE_PARAM) && Servers::Capab.count("MLOCK") > 0) + { + Anope::string modes = modelocks->GetMLockAsString(false).replace_all_cs("+", "").replace_all_cs("-", "").replace_all_cs(cm->mchar, ""); + UplinkSocket::Message(Me) << "MLOCK " << static_cast(ci->c->creation_time) << " " << ci->name << " " << modes; + } + + return EVENT_CONTINUE; + } + + void OnChannelUnban(User *u, ChannelInfo *ci) anope_override + { + UplinkSocket::Message(ci->WhoSends()) << "SVS2MODE " << ci->c->name << " -b " << u->GetUID(); + /* Unreal will remove all matching bans for us regardless of our internal matching. + Don't use Message(Me) here as certain Unreal versions will always respond with TS-less MODE message. */ + } +}; + +MODULE_INIT(ProtoUnreal) diff --git a/modules/pseudoclients/botserv.cpp b/modules/pseudoclients/botserv.cpp new file mode 100644 index 0000000..608f58f --- /dev/null +++ b/modules/pseudoclients/botserv.cpp @@ -0,0 +1,214 @@ +/* BotServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class BotServCore : public Module +{ + Reference BotServ; + ExtensibleRef persist, inhabit; + + public: + BotServCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PSEUDOCLIENT | VENDOR), + persist("PERSIST"), inhabit("inhabit") + { + } + + void OnReload(Configuration::Conf *conf) anope_override + { + const Anope::string &bsnick = conf->GetModule(this)->Get("client"); + BotServ = BotInfo::Find(bsnick, true); + } + + void OnSetCorrectModes(User *user, Channel *chan, AccessGroup &access, bool &give_modes, bool &take_modes) anope_override + { + /* Do not allow removing bot modes on our service bots */ + if (chan->ci && chan->ci->bi == user) + { + const Anope::string &botmodes = Config->GetModule(this)->Get("botmodes"); + for (unsigned i = 0; i < botmodes.length(); ++i) + chan->SetMode(chan->ci->bi, ModeManager::FindChannelModeByChar(botmodes[i]), chan->ci->bi->GetUID()); + } + } + + void OnBotAssign(User *sender, ChannelInfo *ci, BotInfo *bi) anope_override + { + if (ci->c && ci->c->users.size() >= Config->GetModule(this)->Get("minusers")) + { + ChannelStatus status(Config->GetModule(this)->Get("botmodes")); + bi->Join(ci->c, &status); + } + } + + void OnJoinChannel(User *user, Channel *c) anope_override + { + if (!Config || !IRCD) + return; + + BotInfo *bi = user->server == Me ? dynamic_cast(user) : NULL; + if (bi && Config->GetModule(this)->Get("smartjoin")) + { + std::vector bans = c->GetModeList("BAN"); + + /* We check for bans */ + for (unsigned int i = 0; i < bans.size(); ++i) + { + Entry ban("BAN", bans[i]); + if (ban.Matches(user)) + c->RemoveMode(NULL, "BAN", ban.GetMask()); + } + + Anope::string Limit; + unsigned limit = 0; + try + { + if (c->GetParam("LIMIT", Limit)) + limit = convertTo(Limit); + } + catch (const ConvertException &) { } + + /* Should we be invited? */ + if (c->HasMode("INVITE") || (limit && c->users.size() >= limit)) + { + ChannelMode *cm = ModeManager::FindChannelModeByName("OP"); + char symbol = cm ? anope_dynamic_static_cast(cm)->symbol : 0; + IRCD->SendNotice(bi, (symbol ? Anope::string(symbol) : "") + c->name, "%s invited %s into the channel.", user->nick.c_str(), user->nick.c_str()); + } + + ModeManager::ProcessModes(); + } + + if (user->server != Me && c->ci && c->ci->bi) + { + /** + * We let the bot join even if it was an ignored user, as if we don't, + * and the ignored user doesn't just leave, the bot will never + * make it into the channel, leaving the channel botless even for + * legit users - Rob + **/ + /* This is before the user has joined the channel, so check usercount + 1 */ + if (c->users.size() + 1 >= Config->GetModule(this)->Get("minusers") && !c->FindUser(c->ci->bi)) + { + ChannelStatus status(Config->GetModule(this)->Get("botmodes")); + c->ci->bi->Join(c, &status); + } + } + } + + void OnLeaveChannel(User *u, Channel *c) anope_override + { + /* Channel is persistent, it shouldn't be deleted and the service bot should stay */ + if (c->ci && persist && persist->HasExt(c->ci)) + return; + + /* Channel is syncing from a netburst, don't destroy it as more users are probably wanting to join immediately + * We also don't part the bot here either, if necessary we will part it after the sync + */ + if (c->syncing) + return; + + /* Additionally, do not delete this channel if ChanServ/a BotServ bot is inhabiting it */ + if (inhabit && inhabit->HasExt(c)) + return; + + /* This is called prior to removing the user from the channel, so c->users.size() - 1 should be safe */ + if (c->ci && c->ci->bi && u != *c->ci->bi && c->users.size() - 1 <= Config->GetModule(this)->Get("minusers") && c->FindUser(c->ci->bi)) + c->ci->bi->Part(c->ci->c); + } + + EventReturn OnPreHelp(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!params.empty()) + return EVENT_CONTINUE; + + if (source.c) + { + source.Reply(_("\002%s\002 allows you to execute \"fantasy\" commands in the channel.\n" + "Fantasy commands are commands that can be executed from messaging a\n" + "channel, and provide a more convenient way to execute commands. Commands that\n" + "require a channel as a parameter will automatically have that parameter\n" + "given.\n"), source.service->nick.c_str()); + const Anope::string &fantasycharacters = Config->GetModule("fantasy")->Get("fantasycharacter", "!"); + if (!fantasycharacters.empty()) + source.Reply(_(" \n" + "Fantasy commands may be prefixed with one of the following characters: %s\n"), fantasycharacters.c_str()); + source.Reply(_(" \n" + "Available commands are:")); + } + else if (*source.service == BotServ) + { + source.Reply(_("\002%s\002 allows you to have a bot on your own channel.\n" + "It has been created for users that can't host or\n" + "configure a bot, or for use on networks that don't\n" + "allow user bots. Available commands are listed\n" + "below; to use them, type \002%s%s \037command\037\002. For\n" + "more information on a specific command, type\n" + "\002%s%s %s \037command\037\002.\n"), + BotServ->nick.c_str(), Config->StrictPrivmsg.c_str(), BotServ->nick.c_str(), + Config->StrictPrivmsg.c_str(), BotServ->nick.c_str(), source.command.c_str()); + } + + return EVENT_CONTINUE; + } + + void OnPostHelp(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!params.empty() || source.c || source.service != *BotServ) + return; + + source.Reply(_(" \n" + "Bot will join a channel whenever there is at least\n" + "\002%d\002 user(s) on it."), Config->GetModule(this)->Get("minusers")); + const Anope::string &fantasycharacters = Config->GetModule("fantasy")->Get("fantasycharacter", "!"); + if (!fantasycharacters.empty()) + source.Reply(_("Additionally, if fantasy is enabled fantasy commands\n" + "can be executed by prefixing the command name with\n" + "one of the following characters: %s"), fantasycharacters.c_str()); + } + + EventReturn OnChannelModeSet(Channel *c, MessageSource &source, ChannelMode *mode, const Anope::string ¶m) anope_override + { + if (source.GetUser() && !source.GetBot() && Config->GetModule(this)->Get("smartjoin") && mode->name == "BAN" && c->ci && c->ci->bi && c->FindUser(c->ci->bi)) + { + BotInfo *bi = c->ci->bi; + + Entry ban("BAN", param); + if (ban.Matches(bi)) + c->RemoveMode(bi, "BAN", param); + } + + return EVENT_CONTINUE; + } + + void OnCreateChan(ChannelInfo *ci) anope_override + { + /* Set default bot flags */ + spacesepstream sep(Config->GetModule(this)->Get("defaults", "greet fantasy")); + for (Anope::string token; sep.GetToken(token);) + ci->Extend("BS_" + token.upper()); + } + + void OnUserKicked(const MessageSource &source, User *target, const Anope::string &channel, ChannelStatus &status, const Anope::string &kickmsg) anope_override + { + BotInfo *bi = BotInfo::Find(target->GetUID()); + if (bi) + /* Bots get rejoined */ + bi->Join(channel, &status); + } + + void OnCreateBot(BotInfo *bi) anope_override + { + if (bi->botmodes.empty()) + bi->botmodes = Config->GetModule(this)->Get("botumodes"); + } +}; + +MODULE_INIT(BotServCore) diff --git a/modules/pseudoclients/chanserv.cpp b/modules/pseudoclients/chanserv.cpp new file mode 100644 index 0000000..f2a1e77 --- /dev/null +++ b/modules/pseudoclients/chanserv.cpp @@ -0,0 +1,480 @@ +/* ChanServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" +#include "modules/cs_mode.h" + +inline static Anope::string BotModes() +{ + return Config->GetModule("botserv")->Get("botmodes", + Config->GetModule("chanserv")->Get("botmodes", "o") + ); +} + +class ChanServCore : public Module, public ChanServService +{ + Reference ChanServ; + std::vector defaults; + ExtensibleItem inhabit; + ExtensibleRef persist; + bool always_lower; + + public: + ChanServCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PSEUDOCLIENT | VENDOR), + ChanServService(this), inhabit(this, "inhabit"), persist("PERSIST"), always_lower(false) + { + } + + void Hold(Channel *c) anope_override + { + /** A timer used to keep the BotServ bot/ChanServ in the channel + * after kicking the last user in a channel + */ + class ChanServTimer : public Timer + { + Reference &ChanServ; + ExtensibleItem &inhabit; + Reference c; + + public: + /** Constructor + * @param chan The channel + */ + ChanServTimer(Reference &cs, ExtensibleItem &i, Module *m, Channel *chan) : Timer(m, Config->GetModule(m)->Get("inhabit", "15s")), ChanServ(cs), inhabit(i), c(chan) + { + if (!ChanServ || !c) + return; + inhabit.Set(c, true); + if (!c->ci || !c->ci->bi) + ChanServ->Join(c); + else if (!c->FindUser(c->ci->bi)) + c->ci->bi->Join(c); + + /* Set +ntsi to prevent rejoin */ + c->SetMode(NULL, "NOEXTERNAL"); + c->SetMode(NULL, "TOPIC"); + c->SetMode(NULL, "SECRET"); + c->SetMode(NULL, "INVITE"); + } + + /** Called when the delay is up + * @param The current time + */ + void Tick(time_t) anope_override + { + if (!c) + return; + + /* In the event we don't part */ + c->RemoveMode(NULL, "SECRET"); + c->RemoveMode(NULL, "INVITE"); + + inhabit.Unset(c); /* now we're done changing modes, unset inhabit */ + + if (!c->ci || !c->ci->bi) + { + if (ChanServ) + ChanServ->Part(c); + } + /* If someone has rejoined this channel in the meantime, don't part the bot */ + else if (c->users.size() <= 1) + c->ci->bi->Part(c); + } + }; + + if (inhabit.HasExt(c)) + return; + + new ChanServTimer(ChanServ, inhabit, this->owner, c); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + const Anope::string &channick = conf->GetModule(this)->Get("client"); + + if (channick.empty()) + throw ConfigException(Module::name + ": must be defined"); + + BotInfo *bi = BotInfo::Find(channick, true); + if (!bi) + throw ConfigException(Module::name + ": no bot named " + channick); + + ChanServ = bi; + + spacesepstream(conf->GetModule(this)->Get("defaults", "greet fantasy")).GetTokens(defaults); + if (defaults.empty()) + { + defaults.push_back("KEEPTOPIC"); + defaults.push_back("CS_SECURE"); + defaults.push_back("SECUREFOUNDER"); + defaults.push_back("SIGNKICK"); + } + else if (defaults[0].equals_ci("none")) + defaults.clear(); + + always_lower = conf->GetModule(this)->Get("always_lower_ts"); + } + + void OnBotDelete(BotInfo *bi) anope_override + { + if (bi == ChanServ) + ChanServ = NULL; + } + + EventReturn OnBotPrivmsg(User *u, BotInfo *bi, Anope::string &message) anope_override + { + if (bi == ChanServ && Config->GetModule(this)->Get("opersonly") && !u->HasMode("OPER")) + { + u->SendMessage(bi, ACCESS_DENIED); + return EVENT_STOP; + } + + return EVENT_CONTINUE; + } + + void OnDelCore(NickCore *nc) anope_override + { + std::deque chans; + nc->GetChannelReferences(chans); + int max_reg = Config->GetModule(this)->Get("maxregistered"); + + for (unsigned i = 0; i < chans.size(); ++i) + { + ChannelInfo *ci = chans[i]; + + if (ci->GetFounder() == nc) + { + NickCore *newowner = NULL; + if (ci->GetSuccessor() && ci->GetSuccessor() != nc && (ci->GetSuccessor()->IsServicesOper() || !max_reg || ci->GetSuccessor()->channelcount < max_reg)) + newowner = ci->GetSuccessor(); + else + { + const ChanAccess *highest = NULL; + for (unsigned j = 0; j < ci->GetAccessCount(); ++j) + { + const ChanAccess *ca = ci->GetAccess(j); + NickCore *anc = ca->GetAccount(); + + if (!anc || (!anc->IsServicesOper() && max_reg && anc->channelcount >= max_reg) || (anc == nc)) + continue; + if (!highest || *ca > *highest) + highest = ca; + } + if (highest) + newowner = highest->GetAccount(); + } + + if (newowner) + { + Log(LOG_NORMAL, "chanserv/drop", ChanServ) << "Transferring foundership of " << ci->name << " from deleted nick " << nc->display << " to " << newowner->display; + ci->SetFounder(newowner); + ci->SetSuccessor(NULL); + } + else + { + Log(LOG_NORMAL, "chanserv/drop", ChanServ) << "Deleting channel " << ci->name << " owned by deleted nick " << nc->display; + + delete ci; + continue; + } + } + + if (ci->GetSuccessor() == nc) + ci->SetSuccessor(NULL); + + for (unsigned j = 0; j < ci->GetAccessCount(); ++j) + { + const ChanAccess *ca = ci->GetAccess(j); + + if (ca->GetAccount() == nc) + { + delete ci->EraseAccess(j); + break; + } + } + + for (unsigned j = 0; j < ci->GetAkickCount(); ++j) + { + const AutoKick *akick = ci->GetAkick(j); + if (akick->nc == nc) + { + ci->EraseAkick(j); + break; + } + } + } + } + + void OnDelChan(ChannelInfo *ci) anope_override + { + /* remove access entries that are this channel */ + + std::deque chans; + ci->GetChannelReferences(chans); + + for (unsigned i = 0; i < chans.size(); ++i) + { + ChannelInfo *c = ChannelInfo::Find(chans[i]); + if (!c) + continue; + + for (unsigned j = 0; j < c->GetAccessCount(); ++j) + { + ChanAccess *a = c->GetAccess(j); + + if (a->Mask().equals_ci(ci->name)) + { + delete a; + break; + } + } + } + + if (ci->c) + { + ci->c->RemoveMode(ci->WhoSends(), "REGISTERED", "", false); + + const Anope::string &require = Config->GetModule(this)->Get("require"); + if (!require.empty()) + ci->c->SetModes(ci->WhoSends(), false, "-%s", require.c_str()); + } + } + + EventReturn OnPreHelp(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!params.empty() || source.c || source.service != *ChanServ) + return EVENT_CONTINUE; + source.Reply(_("\002%s\002 allows you to register and control various\n" + "aspects of channels. %s can often prevent\n" + "malicious users from \"taking over\" channels by limiting\n" + "who is allowed channel operator privileges. Available\n" + "commands are listed below; to use them, type\n" + "\002%s%s \037command\037\002. For more information on a\n" + "specific command, type \002%s%s HELP \037command\037\002.\n"), + ChanServ->nick.c_str(), ChanServ->nick.c_str(), Config->StrictPrivmsg.c_str(), ChanServ->nick.c_str(), Config->StrictPrivmsg.c_str(), ChanServ->nick.c_str(), ChanServ->nick.c_str(), source.command.c_str()); + return EVENT_CONTINUE; + } + + void OnPostHelp(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!params.empty() || source.c || source.service != *ChanServ) + return; + time_t chanserv_expire = Config->GetModule(this)->Get("expire", "14d"); + if (chanserv_expire >= 86400) + source.Reply(_(" \n" + "Note that any channel which is not used for %d days\n" + "(i.e. which no user on the channel's access list enters\n" + "for that period of time) will be automatically dropped."), chanserv_expire / 86400); + if (source.IsServicesOper()) + source.Reply(_(" \n" + "Services Operators can also, depending on their access drop\n" + "any channel, view (and modify) the access, levels and akick\n" + "lists and settings for any channel.")); + } + + void OnCheckModes(Reference &c) anope_override + { + if (!c) + return; + + if (c->ci) + c->SetMode(c->ci->WhoSends(), "REGISTERED", "", false); + else + c->RemoveMode(c->ci->WhoSends(), "REGISTERED", "", false); + + const Anope::string &require = Config->GetModule(this)->Get("require"); + if (!require.empty()) + { + if (c->ci) + c->SetModes(c->ci->WhoSends(), false, "+%s", require.c_str()); + else + c->SetModes(c->ci->WhoSends(), false, "-%s", require.c_str()); + } + } + + void OnCreateChan(ChannelInfo *ci) anope_override + { + /* Set default chan flags */ + for (unsigned i = 0; i < defaults.size(); ++i) + ci->Extend(defaults[i].upper()); + } + + EventReturn OnCanSet(User *u, const ChannelMode *cm) anope_override + { + if (Config->GetModule(this)->Get("nomlock").find(cm->mchar) != Anope::string::npos + || Config->GetModule(this)->Get("require").find(cm->mchar) != Anope::string::npos) + return EVENT_STOP; + return EVENT_CONTINUE; + } + + void OnChannelSync(Channel *c) anope_override + { + bool perm = c->HasMode("PERM") || (c->ci && persist && persist->HasExt(c->ci)); + if (!perm && !c->botchannel && (c->users.empty() || (c->users.size() == 1 && c->users.begin()->second->user->server == Me))) + { + this->Hold(c); + } + } + + void OnLog(Log *l) anope_override + { + if (l->type == LOG_CHANNEL) + l->bi = ChanServ; + } + + void OnExpireTick() anope_override + { + time_t chanserv_expire = Config->GetModule(this)->Get("expire", "14d"); + + if (!chanserv_expire || Anope::NoExpire || Anope::ReadOnly) + return; + + for (registered_channel_map::const_iterator it = RegisteredChannelList->begin(), it_end = RegisteredChannelList->end(); it != it_end; ) + { + ChannelInfo *ci = it->second; + ++it; + + bool expire = false; + + if (Anope::CurTime - ci->last_used >= chanserv_expire) + { + if (ci->c) + { + time_t last_used = ci->last_used; + for (Channel::ChanUserList::const_iterator cit = ci->c->users.begin(), cit_end = ci->c->users.end(); cit != cit_end && last_used == ci->last_used; ++cit) + ci->AccessFor(cit->second->user); + expire = last_used == ci->last_used; + } + else + expire = true; + } + + FOREACH_MOD(OnPreChanExpire, (ci, expire)); + + if (expire) + { + Log(LOG_NORMAL, "chanserv/expire", ChanServ) << "Expiring channel " << ci->name << " (founder: " << (ci->GetFounder() ? ci->GetFounder()->display : "(none)") << ")"; + FOREACH_MOD(OnChanExpire, (ci)); + delete ci; + } + } + } + + EventReturn OnCheckDelete(Channel *c) anope_override + { + /* Do not delete this channel if ChanServ/a BotServ bot is inhabiting it */ + if (inhabit.HasExt(c)) + return EVENT_STOP; + + return EVENT_CONTINUE; + } + + void OnPostInit() anope_override + { + if (!persist) + return; + + ChannelMode *perm = ModeManager::FindChannelModeByName("PERM"); + + /* Find all persistent channels and create them, as we are about to finish burst to our uplink */ + for (registered_channel_map::iterator it = RegisteredChannelList->begin(), it_end = RegisteredChannelList->end(); it != it_end; ++it) + { + ChannelInfo *ci = it->second; + if (!persist->HasExt(ci)) + continue; + + bool c; + ci->c = Channel::FindOrCreate(ci->name, c, ci->time_registered); + ci->c->syncing |= created; + + if (perm) + { + ci->c->SetMode(NULL, perm); + } + else + { + if (!ci->bi) + ci->WhoSends()->Assign(NULL, ci); + if (ci->c->FindUser(ci->bi) == NULL) + { + ChannelStatus status(BotModes()); + ci->bi->Join(ci->c, &status); + } + } + } + + } + + void OnChanRegistered(ChannelInfo *ci) anope_override + { + if (!persist || !ci->c) + return; + /* Mark the channel as persistent */ + if (ci->c->HasMode("PERM")) + persist->Set(ci); + /* Persist may be in def cflags, set it here */ + else if (persist->HasExt(ci)) + ci->c->SetMode(NULL, "PERM"); + } + + void OnJoinChannel(User *u, Channel *c) anope_override + { + if (always_lower && c->ci && c->creation_time > c->ci->time_registered) + { + Log(LOG_DEBUG) << "Changing TS of " << c->name << " from " << c->creation_time << " to " << c->ci->time_registered; + c->creation_time = c->ci->time_registered; + IRCD->SendChannel(c); + c->Reset(); + } + } + + EventReturn OnChannelModeSet(Channel *c, MessageSource &setter, ChannelMode *mode, const Anope::string ¶m) anope_override + { + if (!always_lower && Anope::CurTime == c->creation_time && c->ci && setter.GetUser() && !setter.GetUser()->server->IsULined()) + { + ChanUserContainer *cu = c->FindUser(setter.GetUser()); + ChannelMode *cm = ModeManager::FindChannelModeByName("OP"); + if (cu && cm && !cu->status.HasMode(cm->mchar)) + { + /* Our -o and their mode change crossing, bounce their mode */ + c->RemoveMode(c->ci->WhoSends(), mode, param); + /* We don't set mlocks until after the join has finished processing, it will stack with this change, + * so there isn't much for the user to remove except -nt etc which is likely locked anyway. + */ + } + } + + return EVENT_CONTINUE; + } + + void OnChanInfo(CommandSource &source, ChannelInfo *ci, InfoFormatter &info, bool show_all) anope_override + { + if (!show_all) + return; + + time_t chanserv_expire = Config->GetModule(this)->Get("expire", "14d"); + if (!ci->HasExt("CS_NO_EXPIRE") && chanserv_expire && !Anope::NoExpire && ci->last_used != Anope::CurTime) + info[_("Expires")] = Anope::strftime(ci->last_used + chanserv_expire, source.GetAccount()); + } + + void OnSetCorrectModes(User *user, Channel *chan, AccessGroup &access, bool &give_modes, bool &take_modes) anope_override + { + if (always_lower) + // Since we always lower the TS, the other side will remove the modes if the channel ts lowers, so we don't + // have to worry about it + take_modes = false; + else if (ModeManager::FindChannelModeByName("REGISTERED")) + // Otherwise if the registered channel mode exists, we should remove modes if the channel is not +r + take_modes = !chan->HasMode("REGISTERED"); + } +}; + +MODULE_INIT(ChanServCore) diff --git a/modules/pseudoclients/global.cpp b/modules/pseudoclients/global.cpp new file mode 100644 index 0000000..e960396 --- /dev/null +++ b/modules/pseudoclients/global.cpp @@ -0,0 +1,100 @@ +/* Global core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class GlobalCore : public Module, public GlobalService +{ + Reference Global; + + void ServerGlobal(BotInfo *sender, Server *s, const Anope::string &message) + { + if (s != Me && !s->IsJuped()) + s->Notice(sender, message); + for (unsigned i = 0, j = s->GetLinks().size(); i < j; ++i) + this->ServerGlobal(sender, s->GetLinks()[i], message); + } + + public: + GlobalCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PSEUDOCLIENT | VENDOR), + GlobalService(this) + { + } + + Reference GetDefaultSender() anope_override + { + return Global; + } + + void SendGlobal(BotInfo *sender, const Anope::string &source, const Anope::string &message) anope_override + { + if (Me->GetLinks().empty()) + return; + if (!sender) + sender = Global; + if (!sender) + return; + + Anope::string rmessage; + + if (!source.empty() && !Config->GetModule("global")->Get("anonymousglobal")) + rmessage = "[" + source + "] " + message; + else + rmessage = message; + + this->ServerGlobal(sender, Servers::GetUplink(), rmessage); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + const Anope::string &glnick = conf->GetModule(this)->Get("client"); + + if (glnick.empty()) + throw ConfigException(Module::name + ": must be defined"); + + BotInfo *bi = BotInfo::Find(glnick, true); + if (!bi) + throw ConfigException(Module::name + ": no bot named " + glnick); + + Global = bi; + } + + void OnRestart() anope_override + { + const Anope::string &gl = Config->GetModule(this)->Get("globaloncycledown"); + if (!gl.empty()) + this->SendGlobal(Global, "", gl); + } + + void OnShutdown() anope_override + { + const Anope::string &gl = Config->GetModule(this)->Get("globaloncycledown"); + if (!gl.empty()) + this->SendGlobal(Global, "", gl); + } + + void OnNewServer(Server *s) anope_override + { + const Anope::string &gl = Config->GetModule(this)->Get("globaloncycleup"); + if (!gl.empty() && !Me->IsSynced()) + s->Notice(Global, gl); + } + + EventReturn OnPreHelp(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!params.empty() || source.c || source.service != *Global) + return EVENT_CONTINUE; + source.Reply(_("%s commands:"), Global->nick.c_str()); + return EVENT_CONTINUE; + } +}; + +MODULE_INIT(GlobalCore) diff --git a/modules/pseudoclients/hostserv.cpp b/modules/pseudoclients/hostserv.cpp new file mode 100644 index 0000000..8714b5f --- /dev/null +++ b/modules/pseudoclients/hostserv.cpp @@ -0,0 +1,130 @@ +/* HostServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class HostServCore : public Module +{ + Reference HostServ; + public: + HostServCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PSEUDOCLIENT | VENDOR) + { + if (!IRCD || !IRCD->CanSetVHost) + throw ModuleException("Your IRCd does not support vhosts"); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + const Anope::string &hsnick = conf->GetModule(this)->Get("client"); + + if (hsnick.empty()) + throw ConfigException(Module::name + ": must be defined"); + + BotInfo *bi = BotInfo::Find(hsnick, true); + if (!bi) + throw ConfigException(Module::name + ": no bot named " + hsnick); + + HostServ = bi; + } + + void OnUserLogin(User *u) anope_override + { + if (!IRCD->CanSetVHost) + return; + + const NickAlias *na = NickAlias::Find(u->nick); + if (!na || na->nc != u->Account() || !na->HasVhost()) + na = NickAlias::Find(u->Account()->display); + if (!na || !na->HasVhost()) + return; + + if (u->vhost.empty() || !u->vhost.equals_cs(na->GetVhostHost()) || (!na->GetVhostIdent().empty() && !u->GetVIdent().equals_cs(na->GetVhostIdent()))) + { + IRCD->SendVhost(u, na->GetVhostIdent(), na->GetVhostHost()); + + u->vhost = na->GetVhostHost(); + u->UpdateHost(); + + if (IRCD->CanSetVIdent && !na->GetVhostIdent().empty()) + u->SetVIdent(na->GetVhostIdent()); + + if (HostServ) + { + if (!na->GetVhostIdent().empty()) + u->SendMessage(HostServ, _("Your vhost of \002%s\002@\002%s\002 is now activated."), na->GetVhostIdent().c_str(), na->GetVhostHost().c_str()); + else + u->SendMessage(HostServ, _("Your vhost of \002%s\002 is now activated."), na->GetVhostHost().c_str()); + } + } + } + + void OnNickDrop(CommandSource &source, NickAlias *na) anope_override + { + if (na->HasVhost()) + { + FOREACH_MOD(OnDeleteVhost, (na)); + na->RemoveVhost(); + } + } + + void OnNickUpdate(User *u) anope_override + { + this->OnUserLogin(u); + } + + EventReturn OnPreHelp(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!params.empty() || source.c || source.service != *HostServ) + return EVENT_CONTINUE; + source.Reply(_("%s commands:"), HostServ->nick.c_str()); + return EVENT_CONTINUE; + } + + void OnSetVhost(NickAlias *na) anope_override + { + if (Config->GetModule(this)->Get("activate_on_set")) + { + User *u = User::Find(na->nick); + + if (u && u->Account() == na->nc) + { + IRCD->SendVhost(u, na->GetVhostIdent(), na->GetVhostHost()); + + u->vhost = na->GetVhostHost(); + u->UpdateHost(); + + if (IRCD->CanSetVIdent && !na->GetVhostIdent().empty()) + u->SetVIdent(na->GetVhostIdent()); + + if (HostServ) + { + if (!na->GetVhostIdent().empty()) + u->SendMessage(HostServ, _("Your vhost of \002%s\002@\002%s\002 is now activated."), na->GetVhostIdent().c_str(), na->GetVhostHost().c_str()); + else + u->SendMessage(HostServ, _("Your vhost of \002%s\002 is now activated."), na->GetVhostHost().c_str()); + } + } + } + } + + void OnDeleteVhost(NickAlias *na) anope_override + { + if (Config->GetModule(this)->Get("activate_on_set")) + { + User *u = User::Find(na->nick); + + if (u && u->Account() == na->nc) + IRCD->SendVhostDel(u); + } + } +}; + +MODULE_INIT(HostServCore) diff --git a/modules/pseudoclients/memoserv.cpp b/modules/pseudoclients/memoserv.cpp new file mode 100644 index 0000000..258ee8f --- /dev/null +++ b/modules/pseudoclients/memoserv.cpp @@ -0,0 +1,233 @@ +/* MemoServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class MemoServCore : public Module, public MemoServService +{ + Reference MemoServ; + + bool SendMemoMail(NickCore *nc, MemoInfo *mi, Memo *m) + { + Anope::string subject = Language::Translate(nc, Config->GetBlock("mail")->Get("memo_subject").c_str()), + message = Language::Translate(Config->GetBlock("mail")->Get("memo_message").c_str()); + + subject = subject.replace_all_cs("%n", nc->display); + subject = subject.replace_all_cs("%s", m->sender); + subject = subject.replace_all_cs("%d", stringify(mi->GetIndex(m) + 1)); + subject = subject.replace_all_cs("%t", m->text); + subject = subject.replace_all_cs("%N", Config->GetBlock("networkinfo")->Get("networkname")); + + message = message.replace_all_cs("%n", nc->display); + message = message.replace_all_cs("%s", m->sender); + message = message.replace_all_cs("%d", stringify(mi->GetIndex(m) + 1)); + message = message.replace_all_cs("%t", m->text); + message = message.replace_all_cs("%N", Config->GetBlock("networkinfo")->Get("networkname")); + + return Mail::Send(nc, subject, message); + } + + public: + MemoServCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PSEUDOCLIENT | VENDOR), + MemoServService(this) + { + } + + MemoResult Send(const Anope::string &source, const Anope::string &target, const Anope::string &message, bool force) anope_override + { + bool ischan; + MemoInfo *mi = MemoInfo::GetMemoInfo(target, ischan); + + if (mi == NULL) + return MEMO_INVALID_TARGET; + + Anope::string sender_display = source; + + User *sender = User::Find(source, true); + if (sender != NULL) + { + if (!sender->HasPriv("memoserv/no-limit") && !force) + { + time_t send_delay = Config->GetModule("memoserv")->Get("senddelay"); + if (send_delay > 0 && sender->lastmemosend + send_delay > Anope::CurTime) + return MEMO_TOO_FAST; + else if (!mi->memomax) + return MEMO_TARGET_FULL; + else if (mi->memomax > 0 && mi->memos->size() >= static_cast(mi->memomax)) + return MEMO_TARGET_FULL; + else if (mi->HasIgnore(sender)) + return MEMO_SUCCESS; + } + + NickCore *acc = sender->Account(); + if (acc != NULL) + { + sender_display = acc->display; + } + } + + if (sender != NULL) + sender->lastmemosend = Anope::CurTime; + + Memo *m = new Memo(); + m->mi = mi; + mi->memos->push_back(m); + m->owner = target; + m->sender = sender_display; + m->time = Anope::CurTime; + m->text = message; + m->unread = true; + + FOREACH_MOD(OnMemoSend, (source, target, mi, m)); + + if (ischan) + { + ChannelInfo *ci = ChannelInfo::Find(target); + + if (ci->c) + { + for (Channel::ChanUserList::iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end; ++it) + { + ChanUserContainer *cu = it->second; + + if (ci->AccessFor(cu->user).HasPriv("MEMO")) + { + if (cu->user->Account() && cu->user->Account()->HasExt("MEMO_RECEIVE")) + cu->user->SendMessage(MemoServ, MEMO_NEW_X_MEMO_ARRIVED, ci->name.c_str(), Config->StrictPrivmsg.c_str(), MemoServ->nick.c_str(), ci->name.c_str(), mi->memos->size()); + } + } + } + } + else + { + NickCore *nc = NickAlias::Find(target)->nc; + + if (nc->HasExt("MEMO_RECEIVE")) + { + for (unsigned i = 0; i < nc->aliases->size(); ++i) + { + const NickAlias *na = nc->aliases->at(i); + User *user = User::Find(na->nick, true); + if (user && user->IsIdentified()) + user->SendMessage(MemoServ, MEMO_NEW_MEMO_ARRIVED, source.c_str(), Config->StrictPrivmsg.c_str(), MemoServ->nick.c_str(), mi->memos->size()); + } + } + + /* let's get out the mail if set in the nickcore - certus */ + if (nc->HasExt("MEMO_MAIL")) + SendMemoMail(nc, mi, m); + } + + return MEMO_SUCCESS; + } + + void Check(User *u) anope_override + { + const NickCore *nc = u->Account(); + if (!nc) + return; + + unsigned i = 0, end = nc->memos.memos->size(), newcnt = 0; + for (; i < end; ++i) + if (nc->memos.GetMemo(i)->unread) + ++newcnt; + if (newcnt > 0) + u->SendMessage(MemoServ, newcnt == 1 ? _("You have 1 new memo.") : _("You have %d new memos."), newcnt); + if (nc->memos.memomax > 0 && nc->memos.memos->size() >= static_cast(nc->memos.memomax)) + { + if (nc->memos.memos->size() > static_cast(nc->memos.memomax)) + u->SendMessage(MemoServ, _("You are over your maximum number of memos (%d). You will be unable to receive any new memos until you delete some of your current ones."), nc->memos.memomax); + else + u->SendMessage(MemoServ, _("You have reached your maximum number of memos (%d). You will be unable to receive any new memos until you delete some of your current ones."), nc->memos.memomax); + } + } + + void OnReload(Configuration::Conf *conf) anope_override + { + const Anope::string &msnick = conf->GetModule(this)->Get("client"); + + if (msnick.empty()) + throw ConfigException(Module::name + ": must be defined"); + + BotInfo *bi = BotInfo::Find(msnick, true); + if (!bi) + throw ConfigException(Module::name + ": no bot named " + msnick); + + MemoServ = bi; + } + + void OnNickCoreCreate(NickCore *nc) anope_override + { + nc->memos.memomax = Config->GetModule(this)->Get("maxmemos"); + } + + void OnCreateChan(ChannelInfo *ci) anope_override + { + ci->memos.memomax = Config->GetModule(this)->Get("maxmemos"); + } + + void OnBotDelete(BotInfo *bi) anope_override + { + if (bi == MemoServ) + MemoServ = NULL; + } + + void OnNickIdentify(User *u) anope_override + { + this->Check(u); + } + + void OnJoinChannel(User *u, Channel *c) anope_override + { + if (c->ci && !c->ci->memos.memos->empty() && c->ci->AccessFor(u).HasPriv("MEMO")) + { + if (c->ci->memos.memos->size() == 1) + u->SendMessage(MemoServ, _("There is \002%d\002 memo on channel %s."), c->ci->memos.memos->size(), c->ci->name.c_str()); + else + u->SendMessage(MemoServ, _("There are \002%d\002 memos on channel %s."), c->ci->memos.memos->size(), c->ci->name.c_str()); + } + } + + void OnUserAway(User *u, const Anope::string &message) anope_override + { + if (message.empty()) + this->Check(u); + } + + void OnNickUpdate(User *u) anope_override + { + this->Check(u); + } + + EventReturn OnPreHelp(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!params.empty() || source.c || source.service != *MemoServ) + return EVENT_CONTINUE; + source.Reply(_("\002%s\002 is a utility allowing IRC users to send short\n" + "messages to other IRC users, whether they are online at\n" + "the time or not, or to channels(*). Both the sender's\n" + "nickname and the target nickname or channel must be\n" + "registered in order to send a memo.\n" + "%s's commands include:"), MemoServ->nick.c_str(), MemoServ->nick.c_str()); + return EVENT_CONTINUE; + } + + void OnPostHelp(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!params.empty() || source.c || source.service != *MemoServ) + return; + source.Reply(_(" \n" + "Type \002%s%s HELP \037command\037\002 for help on any of the\n" + "above commands."), Config->StrictPrivmsg.c_str(), MemoServ->nick.c_str()); + } +}; + +MODULE_INIT(MemoServCore) diff --git a/modules/pseudoclients/nickserv.cpp b/modules/pseudoclients/nickserv.cpp new file mode 100644 index 0000000..b7a1a60 --- /dev/null +++ b/modules/pseudoclients/nickserv.cpp @@ -0,0 +1,567 @@ +/* NickServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class NickServCollide; +static std::set collides; + +/** Timer for colliding nicks to force people off of nicknames + */ +class NickServCollide : public Timer +{ + NickServService *service; + Reference u; + time_t ts; + Reference na; + + public: + NickServCollide(Module *me, NickServService *nss, User *user, NickAlias *nick, time_t delay) : Timer(me, delay), service(nss), u(user), ts(user->timestamp), na(nick) + { + collides.insert(this); + } + + ~NickServCollide() + { + collides.erase(this); + } + + User *GetUser() + { + return u; + } + + NickAlias *GetNick() + { + return na; + } + + void Tick(time_t t) anope_override + { + if (!u || !na) + return; + /* If they identified or don't exist anymore, don't kill them. */ + if (u->Account() == na->nc || u->timestamp > ts) + return; + + service->Collide(u, na); + } +}; + +/** Timer for removing HELD status from nicks. + */ +class NickServHeld : public Timer +{ + Reference na; + Anope::string nick; + public: + NickServHeld(Module *me, NickAlias *n, long l) : Timer(me, l), na(n), nick(na->nick) + { + n->Extend("HELD"); + } + + void Tick(time_t) + { + if (na) + na->Shrink("HELD"); + } +}; + +class NickServRelease; +static Anope::map NickServReleases; + +/** Timer for releasing nicks to be available for use + */ +class NickServRelease : public User, public Timer +{ + Anope::string nick; + + public: + NickServRelease(Module *me, NickAlias *na, time_t delay) : User(na->nick, Config->GetModule("nickserv")->Get("enforceruser", "user"), + Config->GetModule("nickserv")->Get("enforcerhost", Me->GetName()), "", "", Me, "Services Enforcer", Anope::CurTime, "", IRCD->UID_Retrieve(), NULL), Timer(me, delay), nick(na->nick) + { + /* Erase the current release timer and use the new one */ + Anope::map::iterator nit = NickServReleases.find(this->nick); + if (nit != NickServReleases.end()) + { + IRCD->SendQuit(nit->second, ""); + delete nit->second; + } + + NickServReleases.insert(std::make_pair(this->nick, this)); + + IRCD->SendClientIntroduction(this); + } + + ~NickServRelease() + { + IRCD->SendQuit(this, ""); + NickServReleases.erase(this->nick); + } + + void Tick(time_t t) anope_override { } +}; + +class NickServCore : public Module, public NickServService +{ + Reference NickServ; + std::vector defaults; + ExtensibleItem held, collided; + + void OnCancel(User *u, NickAlias *na) + { + if (collided.HasExt(na)) + { + collided.Unset(na); + + new NickServHeld(this, na, Config->GetModule("nickserv")->Get("releasetimeout", "1m")); + + if (IRCD->CanSVSHold) + IRCD->SendSVSHold(na->nick, Config->GetModule("nickserv")->Get("releasetimeout", "1m")); + else + new NickServRelease(this, na, Config->GetModule("nickserv")->Get("releasetimeout", "1m")); + } + } + + public: + NickServCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PSEUDOCLIENT | VENDOR), + NickServService(this), held(this, "HELD"), collided(this, "COLLIDED") + { + } + + ~NickServCore() + { + OnShutdown(); + } + + void OnShutdown() anope_override + { + /* On shutdown, restart, or mod unload, remove all of our holds for nicks (svshold or qlines) + * because some IRCds do not allow us to have these automatically expire + */ + for (nickalias_map::const_iterator it = NickAliasList->begin(); it != NickAliasList->end(); ++it) + this->Release(it->second); + } + + void OnRestart() anope_override + { + OnShutdown(); + } + + void Validate(User *u) anope_override + { + NickAlias *na = NickAlias::Find(u->nick); + if (!na) + return; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnNickValidate, MOD_RESULT, (u, na)); + if (MOD_RESULT == EVENT_STOP) + { + this->Collide(u, na); + return; + } + else if (MOD_RESULT == EVENT_ALLOW) + return; + + if (!na->nc->HasExt("NS_SECURE") && u->IsRecognized()) + { + na->last_seen = Anope::CurTime; + na->last_usermask = u->GetIdent() + "@" + u->GetDisplayedHost(); + na->last_realname = u->realname; + return; + } + + if (Config->GetModule("nickserv")->Get("nonicknameownership")) + return; + + bool on_access = u->IsRecognized(false); + + if (on_access || !na->nc->HasExt("KILL_IMMED")) + { + if (na->nc->HasExt("NS_SECURE")) + u->SendMessage(NickServ, NICK_IS_SECURE, Config->StrictPrivmsg.c_str(), NickServ->nick.c_str()); + else + u->SendMessage(NickServ, NICK_IS_REGISTERED, Config->StrictPrivmsg.c_str(), NickServ->nick.c_str()); + } + if (na->nc->HasExt("KILLPROTECT") && !on_access) + { + if (na->nc->HasExt("KILL_IMMED")) + { + u->SendMessage(NickServ, FORCENICKCHANGE_NOW); + this->Collide(u, na); + } + else if (na->nc->HasExt("KILL_QUICK")) + { + time_t killquick = Config->GetModule("nickserv")->Get("killquick", "20s"); + u->SendMessage(NickServ, _("If you do not change within %s, I will change your nick."), Anope::Duration(killquick, u->Account()).c_str()); + new NickServCollide(this, this, u, na, killquick); + } + else + { + time_t kill = Config->GetModule("nickserv")->Get("kill", "60s"); + u->SendMessage(NickServ, _("If you do not change within %s, I will change your nick."), Anope::Duration(kill, u->Account()).c_str()); + new NickServCollide(this, this, u, na, kill); + } + } + + } + + void OnUserLogin(User *u) anope_override + { + NickAlias *na = NickAlias::Find(u->nick); + if (na && *na->nc == u->Account() && !Config->GetModule("nickserv")->Get("nonicknameownership") && !na->nc->HasExt("UNCONFIRMED")) + u->SetMode(NickServ, "REGISTERED"); + + const Anope::string &modesonid = Config->GetModule(this)->Get("modesonid"); + if (!modesonid.empty()) + u->SetModes(NickServ, "%s", modesonid.c_str()); + } + + void Collide(User *u, NickAlias *na) anope_override + { + if (na) + collided.Set(na); + + if (IRCD->CanSVSNick) + { + unsigned nicklen = Config->GetBlock("networkinfo")->Get("nicklen"); + const Anope::string &guestprefix = Config->GetModule("nickserv")->Get("guestnickprefix", "Guest"); + + Anope::string guestnick; + + int i = 0; + do + { + guestnick = guestprefix + stringify(static_cast(rand())); + if (guestnick.length() > nicklen) + guestnick = guestnick.substr(0, nicklen); + } + while (User::Find(guestnick) && i++ < 10); + + if (i == 11) + u->Kill(*NickServ, "Services nickname-enforcer kill"); + else + { + u->SendMessage(*NickServ, _("Your nickname is now being changed to \002%s\002"), guestnick.c_str()); + IRCD->SendForceNickChange(u, guestnick, Anope::CurTime); + } + } + else + u->Kill(*NickServ, "Services nickname-enforcer kill"); + } + + void Release(NickAlias *na) anope_override + { + if (held.HasExt(na)) + { + if (IRCD->CanSVSHold) + IRCD->SendSVSHoldDel(na->nick); + else + { + User *u = User::Find(na->nick); + if (u && u->server == Me) + { + u->Quit(); + } + } + + held.Unset(na); + } + collided.Unset(na); /* clear pending collide */ + } + + void OnReload(Configuration::Conf *conf) anope_override + { + const Anope::string &nsnick = conf->GetModule(this)->Get("client"); + + if (nsnick.empty()) + throw ConfigException(Module::name + ": must be defined"); + + BotInfo *bi = BotInfo::Find(nsnick, true); + if (!bi) + throw ConfigException(Module::name + ": no bot named " + nsnick); + + NickServ = bi; + + spacesepstream(conf->GetModule(this)->Get("defaults", "ns_secure memo_signon memo_receive")).GetTokens(defaults); + if (defaults.empty()) + { + defaults.push_back("NS_SECURE"); + defaults.push_back("MEMO_SIGNON"); + defaults.push_back("MEMO_RECEIVE"); + } + else if (defaults[0].equals_ci("none")) + defaults.clear(); + } + + void OnDelNick(NickAlias *na) anope_override + { + User *u = User::Find(na->nick); + if (u && u->Account() == na->nc) + { + IRCD->SendLogout(u); + u->RemoveMode(NickServ, "REGISTERED"); + u->Logout(); + } + } + + void OnDelCore(NickCore *nc) anope_override + { + Log(NickServ, "nick") << "Deleting nickname group " << nc->display; + + /* Clean up this nick core from any users online */ + for (std::list::iterator it = nc->users.begin(); it != nc->users.end();) + { + User *user = *it++; + IRCD->SendLogout(user); + user->RemoveMode(NickServ, "REGISTERED"); + user->Logout(); + FOREACH_MOD(OnNickLogout, (user)); + } + nc->users.clear(); + } + + void OnChangeCoreDisplay(NickCore *nc, const Anope::string &newdisplay) anope_override + { + Log(LOG_NORMAL, "nick", NickServ) << "Changing " << nc->display << " nickname group display to " << newdisplay; + } + + void OnNickIdentify(User *u) anope_override + { + Configuration::Block *block = Config->GetModule(this); + + if (block->Get("modeonid", "yes")) + + for (User::ChanUserList::iterator it = u->chans.begin(), it_end = u->chans.end(); it != it_end; ++it) + { + ChanUserContainer *cc = it->second; + Channel *c = cc->chan; + if (c) + c->SetCorrectModes(u, true); + } + + const Anope::string &modesonid = block->Get("modesonid"); + if (!modesonid.empty()) + u->SetModes(NickServ, "%s", modesonid.c_str()); + + if (block->Get("forceemail", "yes") && u->Account()->email.empty()) + { + u->SendMessage(NickServ, _("You must now supply an e-mail for your nick.\n" + "This e-mail will allow you to retrieve your password in\n" + "case you forget it.")); + u->SendMessage(NickServ, _("Type \002%s%s SET EMAIL \037e-mail\037\002 in order to set your e-mail.\n" + "Your privacy is respected; this e-mail won't be given to\n" + "any third-party person."), Config->StrictPrivmsg.c_str(), NickServ->nick.c_str()); + } + + for (std::set::iterator it = collides.begin(); it != collides.end(); ++it) + { + NickServCollide *c = *it; + if (c->GetUser() == u && c->GetNick() && c->GetNick()->nc == u->Account()) + { + delete c; + break; + } + } + } + + void OnNickGroup(User *u, NickAlias *target) anope_override + { + if (!target->nc->HasExt("UNCONFIRMED")) + u->SetMode(NickServ, "REGISTERED"); + } + + void OnNickUpdate(User *u) anope_override + { + for (User::ChanUserList::iterator it = u->chans.begin(), it_end = u->chans.end(); it != it_end; ++it) + { + ChanUserContainer *cc = it->second; + Channel *c = cc->chan; + if (c) + c->SetCorrectModes(u, true); + } + } + + void OnUserConnect(User *u, bool &exempt) anope_override + { + if (u->Quitting() || !u->server->IsSynced() || u->server->IsULined()) + return; + + const NickAlias *na = NickAlias::Find(u->nick); + + const Anope::string &unregistered_notice = Config->GetModule(this)->Get("unregistered_notice"); + if (!Config->GetModule("nickserv")->Get("nonicknameownership") && !unregistered_notice.empty() && !na && !u->Account()) + u->SendMessage(NickServ, unregistered_notice.replace_all_cs("%n", u->nick)); + else if (na && !u->IsIdentified(true)) + this->Validate(u); + } + + void OnPostUserLogoff(User *u) anope_override + { + NickAlias *na = NickAlias::Find(u->nick); + if (na) + OnCancel(u, na); + } + + void OnServerSync(Server *s) anope_override + { + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + { + User *u = it->second; + + if (u->server == s) + { + if (u->HasMode("REGISTERED") && !u->IsIdentified(true)) + u->RemoveMode(NickServ, "REGISTERED"); + if (!u->IsIdentified()) + this->Validate(u); + } + } + } + + void OnUserNickChange(User *u, const Anope::string &oldnick) anope_override + { + NickAlias *old_na = NickAlias::Find(oldnick), *na = NickAlias::Find(u->nick); + /* If the new nick isn't registered or it's registered and not yours */ + if (!na || na->nc != u->Account()) + { + /* Remove +r, but keep an account associated with the user */ + u->RemoveMode(NickServ, "REGISTERED"); + + this->Validate(u); + } + else + { + /* Reset +r and re-send account (even though it really should be set at this point) */ + IRCD->SendLogin(u, na); + if (!Config->GetModule("nickserv")->Get("nonicknameownership") && na->nc == u->Account() && !na->nc->HasExt("UNCONFIRMED")) + u->SetMode(NickServ, "REGISTERED"); + Log(u, "", NickServ) << u->GetMask() << " automatically identified for group " << u->Account()->display; + } + + if (!u->nick.equals_ci(oldnick) && old_na) + OnCancel(u, old_na); + } + + void OnUserModeSet(const MessageSource &setter, User *u, const Anope::string &mname) anope_override + { + if (u->server->IsSynced() && mname == "REGISTERED" && !u->IsIdentified(true)) + u->RemoveMode(NickServ, mname); + } + + EventReturn OnPreHelp(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!params.empty() || source.c || source.service != *NickServ) + return EVENT_CONTINUE; + if (!Config->GetModule("nickserv")->Get("nonicknameownership")) + source.Reply(_("\002%s\002 allows you to register a nickname and\n" + "prevent others from using it. The following\n" + "commands allow for registration and maintenance of\n" + "nicknames; to use them, type \002%s%s \037command\037\002.\n" + "For more information on a specific command, type\n" + "\002%s%s %s \037command\037\002.\n"), NickServ->nick.c_str(), Config->StrictPrivmsg.c_str(), NickServ->nick.c_str(), Config->StrictPrivmsg.c_str(), NickServ->nick.c_str(), source.command.c_str()); + else + source.Reply(_("\002%s\002 allows you to register an account.\n" + "The following commands allow for registration and maintenance of\n" + "accounts; to use them, type \002%s%s \037command\037\002.\n" + "For more information on a specific command, type\n" + "\002%s%s %s \037command\037\002.\n"), NickServ->nick.c_str(), Config->StrictPrivmsg.c_str(), NickServ->nick.c_str(), Config->StrictPrivmsg.c_str(), NickServ->nick.c_str(), source.command.c_str()); + return EVENT_CONTINUE; + } + + void OnPostHelp(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!params.empty() || source.c || source.service != *NickServ) + return; + if (source.IsServicesOper()) + source.Reply(_(" \n" + "Services Operators can also drop any nickname without needing\n" + "to identify for the nick, and may view the access list for\n" + "any nickname.")); + time_t nickserv_expire = Config->GetModule(this)->Get("expire", "21d"); + if (nickserv_expire >= 86400) + source.Reply(_(" \n" + "Accounts that are not used anymore are subject to\n" + "the automatic expiration, i.e. they will be deleted\n" + "after %d days if not used."), nickserv_expire / 86400); + } + + void OnNickCoreCreate(NickCore *nc) anope_override + { + /* Set default flags */ + for (unsigned i = 0; i < defaults.size(); ++i) + nc->Extend(defaults[i].upper()); + } + + void OnUserQuit(User *u, const Anope::string &msg) anope_override + { + if (u->server && !u->server->GetQuitReason().empty() && Config->GetModule(this)->Get("hidenetsplitquit")) + return; + + /* Update last quit and last seen for the user */ + NickAlias *na = NickAlias::Find(u->nick); + if (na && !na->nc->HasExt("NS_SUSPENDED") && (u->IsRecognized() || u->IsIdentified(true))) + { + na->last_seen = Anope::CurTime; + na->last_quit = msg; + } + } + + void OnExpireTick() anope_override + { + if (Anope::NoExpire || Anope::ReadOnly) + return; + + time_t nickserv_expire = Config->GetModule(this)->Get("expire", "21d"); + + for (nickalias_map::const_iterator it = NickAliasList->begin(), it_end = NickAliasList->end(); it != it_end; ) + { + NickAlias *na = it->second; + ++it; + + User *u = User::Find(na->nick, true); + if (u && (u->IsIdentified(true) || u->IsRecognized())) + na->last_seen = Anope::CurTime; + + bool expire = false; + + if (nickserv_expire && Anope::CurTime - na->last_seen >= nickserv_expire) + expire = true; + + FOREACH_MOD(OnPreNickExpire, (na, expire)); + + if (expire) + { + Log(LOG_NORMAL, "nickserv/expire", NickServ) << "Expiring nickname " << na->nick << " (group: " << na->nc->display << ") (e-mail: " << (na->nc->email.empty() ? "none" : na->nc->email) << ")"; + FOREACH_MOD(OnNickExpire, (na)); + delete na; + } + } + } + + void OnNickInfo(CommandSource &source, NickAlias *na, InfoFormatter &info, bool show_hidden) anope_override + { + if (!na->nc->HasExt("UNCONFIRMED")) + { + time_t nickserv_expire = Config->GetModule(this)->Get("expire", "21d"); + if (!na->HasExt("NS_NO_EXPIRE") && nickserv_expire && !Anope::NoExpire && (source.HasPriv("nickserv/auspex") || na->last_seen != Anope::CurTime)) + info[_("Expires")] = Anope::strftime(na->last_seen + nickserv_expire, source.GetAccount()); + } + else + { + time_t unconfirmed_expire = Config->GetModule("ns_register")->Get("unconfirmedexpire", "1d"); + info[_("Expires")] = Anope::strftime(na->time_registered + unconfirmed_expire, source.GetAccount()); + } + } +}; + +MODULE_INIT(NickServCore) diff --git a/modules/pseudoclients/operserv.cpp b/modules/pseudoclients/operserv.cpp new file mode 100644 index 0000000..ca1489f --- /dev/null +++ b/modules/pseudoclients/operserv.cpp @@ -0,0 +1,298 @@ +/* OperServ core functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "module.h" + +class SGLineManager : public XLineManager +{ + public: + SGLineManager(Module *creator) : XLineManager(creator, "xlinemanager/sgline", 'G') { } + + void OnMatch(User *u, XLine *x) anope_override + { + this->Send(u, x); + } + + void OnExpire(const XLine *x) anope_override + { + Log(Config->GetClient("OperServ"), "expire/akill") << "AKILL on \002" << x->mask << "\002 has expired"; + } + + void Send(User *u, XLine *x) anope_override + { + IRCD->SendAkill(u, x); + } + + void SendDel(XLine *x) anope_override + { + IRCD->SendAkillDel(x); + } + + bool Check(User *u, const XLine *x) anope_override + { + if (x->regex) + { + Anope::string uh = u->GetIdent() + "@" + u->host, nuhr = u->nick + "!" + uh + "#" + u->realname; + return x->regex->Matches(uh) || x->regex->Matches(nuhr); + } + + if (!x->GetNick().empty() && !Anope::Match(u->nick, x->GetNick())) + return false; + + if (!x->GetUser().empty() && !Anope::Match(u->GetIdent(), x->GetUser())) + return false; + + if (!x->GetReal().empty() && !Anope::Match(u->realname, x->GetReal())) + return false; + + if (x->c && x->c->match(u->ip)) + return true; + + if (x->GetHost().empty() || Anope::Match(u->host, x->GetHost()) || Anope::Match(u->ip.addr(), x->GetHost())) + return true; + + return false; + } +}; + +class SQLineManager : public XLineManager +{ + ServiceReference nickserv; + + public: + SQLineManager(Module *creator) : XLineManager(creator, "xlinemanager/sqline", 'Q'), nickserv("NickServService", "NickServ") { } + + void OnMatch(User *u, XLine *x) anope_override + { + this->Send(u, x); + } + + void OnExpire(const XLine *x) anope_override + { + Log(Config->GetClient("OperServ"), "expire/sqline") << "SQLINE on \002" << x->mask << "\002 has expired"; + } + + void Send(User *u, XLine *x) anope_override + { + if (!IRCD->CanSQLine) + { + if (!u) + ; + else if (nickserv) + nickserv->Collide(u, NULL); + else + u->Kill(Config->GetClient("OperServ"), "Q-Lined: " + x->reason); + } + else if (x->IsRegex()) + { + if (u) + u->Kill(Config->GetClient("OperServ"), "Q-Lined: " + x->reason); + } + else if (x->mask[0] != '#' || IRCD->CanSQLineChannel) + { + IRCD->SendSQLine(u, x); + /* If it is an oper, assume they're walking it, otherwise kill for good measure */ + if (u && !u->HasMode("OPER")) + u->Kill(Config->GetClient("OperServ"), "Q-Lined: " + x->reason); + } + } + + void SendDel(XLine *x) anope_override + { + if (!IRCD->CanSQLine || x->IsRegex()) + ; + else if (x->mask[0] != '#' || IRCD->CanSQLineChannel) + IRCD->SendSQLineDel(x); + } + + bool Check(User *u, const XLine *x) anope_override + { + if (x->regex) + return x->regex->Matches(u->nick); + return Anope::Match(u->nick, x->mask); + } + + XLine *CheckChannel(Channel *c) + { + for (std::vector::const_iterator it = this->GetList().begin(), it_end = this->GetList().end(); it != it_end; ++it) + { + XLine *x = *it; + + if (x->regex) + { + if (x->regex->Matches(c->name)) + return x; + } + else + { + if (x->mask.empty() || x->mask[0] != '#') + continue; + + if (Anope::Match(c->name, x->mask, false, true)) + return x; + } + } + return NULL; + } +}; + +class SNLineManager : public XLineManager +{ + public: + SNLineManager(Module *creator) : XLineManager(creator, "xlinemanager/snline", 'N') { } + + void OnMatch(User *u, XLine *x) anope_override + { + this->Send(u, x); + } + + void OnExpire(const XLine *x) anope_override + { + Log(Config->GetClient("OperServ"), "expire/snline") << "SNLINE on \002" << x->mask << "\002 has expired"; + } + + void Send(User *u, XLine *x) anope_override + { + if (IRCD->CanSNLine && !x->IsRegex()) + IRCD->SendSGLine(u, x); + + if (u) + u->Kill(Config->GetClient("OperServ"), "SNLined: " + x->reason); + } + + void SendDel(XLine *x) anope_override + { + if (IRCD->CanSNLine && !x->IsRegex()) + IRCD->SendSGLineDel(x); + } + + bool Check(User *u, const XLine *x) anope_override + { + if (x->regex) + return x->regex->Matches(u->realname); + return Anope::Match(u->realname, x->mask, false, true); + } +}; + +class OperServCore : public Module +{ + Reference OperServ; + SGLineManager sglines; + SQLineManager sqlines; + SNLineManager snlines; + + public: + OperServCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, PSEUDOCLIENT | VENDOR), + sglines(this), sqlines(this), snlines(this) + { + + /* Yes, these are in this order for a reason. Most violent->least violent. */ + XLineManager::RegisterXLineManager(&sglines); + XLineManager::RegisterXLineManager(&sqlines); + XLineManager::RegisterXLineManager(&snlines); + } + + ~OperServCore() + { + this->sglines.Clear(); + this->sqlines.Clear(); + this->snlines.Clear(); + + XLineManager::UnregisterXLineManager(&sglines); + XLineManager::UnregisterXLineManager(&sqlines); + XLineManager::UnregisterXLineManager(&snlines); + } + + void OnReload(Configuration::Conf *conf) anope_override + { + const Anope::string &osnick = conf->GetModule(this)->Get("client"); + + if (osnick.empty()) + throw ConfigException(this->name + ": must be defined"); + + BotInfo *bi = BotInfo::Find(osnick, true); + if (!bi) + throw ConfigException(this->name + ": no bot named " + osnick); + + OperServ = bi; + } + + EventReturn OnBotPrivmsg(User *u, BotInfo *bi, Anope::string &message) anope_override + { + if (bi == OperServ && !u->HasMode("OPER") && Config->GetModule(this)->Get("opersonly")) + { + u->SendMessage(bi, ACCESS_DENIED); + Log(bi, "bados") << "Denied access to " << bi->nick << " from " << u->GetMask() << " (non-oper)"; + return EVENT_STOP; + } + + return EVENT_CONTINUE; + } + + void OnServerQuit(Server *server) anope_override + { + if (server->IsJuped()) + Log(server, "squit", OperServ) << "Received SQUIT for juped server " << server->GetName(); + } + + void OnUserModeSet(const MessageSource &setter, User *u, const Anope::string &mname) anope_override + { + if (mname == "OPER") + Log(u, "oper", OperServ) << "is now an IRC operator."; + } + + void OnUserModeUnset(const MessageSource &setter, User *u, const Anope::string &mname) anope_override + { + if (mname == "OPER") + Log(u, "oper", OperServ) << "is no longer an IRC operator"; + } + + void OnUserConnect(User *u, bool &exempt) anope_override + { + if (!u->Quitting() && !exempt) + XLineManager::CheckAll(u); + } + + void OnUserNickChange(User *u, const Anope::string &oldnick) anope_override + { + if (!u->HasMode("OPER")) + this->sqlines.CheckAllXLines(u); + } + + EventReturn OnCheckKick(User *u, Channel *c, Anope::string &mask, Anope::string &reason) anope_override + { + XLine *x = this->sqlines.CheckChannel(c); + if (x) + { + this->sqlines.OnMatch(u, x); + reason = x->reason; + return EVENT_STOP; + } + + return EVENT_CONTINUE; + } + + EventReturn OnPreHelp(CommandSource &source, const std::vector ¶ms) anope_override + { + if (!params.empty() || source.c || source.service != *OperServ) + return EVENT_CONTINUE; + source.Reply(_("%s commands:"), OperServ->nick.c_str()); + return EVENT_CONTINUE; + } + + void OnLog(Log *l) anope_override + { + if (l->type == LOG_SERVER) + l->bi = OperServ; + } +}; + +MODULE_INIT(OperServCore) diff --git a/modules/third/README b/modules/third/README new file mode 100644 index 0000000..f960fba --- /dev/null +++ b/modules/third/README @@ -0,0 +1,2 @@ +Third party modules, eg, modules not shipped with Anope are to be placed here. +After doing so, run ./Config, make, make install and with some luck your module will work! diff --git a/modules/third/language/CMakeLists.txt b/modules/third/language/CMakeLists.txt new file mode 100644 index 0000000..85278f5 --- /dev/null +++ b/modules/third/language/CMakeLists.txt @@ -0,0 +1,38 @@ +# Only do this if gettext is installed +if(GETTEXT_FOUND) + # Get all of the .po files + file(GLOB LANG_SRCS_PO RELATIVE ${CMAKE_CURRENT_SOURCE_DIR} "*.*.po") + sort_list(LANG_SRCS_PO) + + foreach(LANG_PO ${LANG_SRCS_PO}) + # Get the domain for this language file + string(LENGTH ${LANG_PO} LANG_PO_LENGTH) + math(EXPR DOMAIN_LENGTH "${LANG_PO_LENGTH} - 9") + string(SUBSTRING ${LANG_PO} 0 ${DOMAIN_LENGTH} LANG_DOMAIN) + + # Get the language for this language file + math(EXPR DOMAIN_LENGTH "${LANG_PO_LENGTH} - 8") + string(SUBSTRING ${LANG_PO} ${DOMAIN_LENGTH} 5 LANG_LANG) + + # Get the .mo file name + string(REGEX REPLACE "\\.po$" ".mo" LANG_MO ${LANG_PO}) + # Add the .mo file to a list for use later with add_custom_target + set(LANG_SRCS_MO ${LANG_SRCS_MO} ${CMAKE_CURRENT_BINARY_DIR}/${LANG_MO}) + # Run msgfmt on the language file, depends on the .po file + add_custom_command(OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/${LANG_MO} + COMMAND ${GETTEXT_MSGFMT_EXECUTABLE} -c ${CMAKE_CURRENT_SOURCE_DIR}/${LANG_PO} -o ${CMAKE_CURRENT_BINARY_DIR}/${LANG_MO} + MAIN_DEPENDENCY ${LANG_PO} + ) + # Add to cpack ignored files if not on Windows. + if(NOT WIN32) + add_to_cpack_ignored_files("${LANG_MO}") + endif(NOT WIN32) + + # Install the new language file + install(CODE "FILE(MAKE_DIRECTORY ${LOCALE_DIR}/${LANG_LANG}/LC_MESSAGES/)") + install(FILES ${CMAKE_CURRENT_BINARY_DIR}/${LANG_MO} DESTINATION ${LOCALE_DIR}/${LANG_LANG}/LC_MESSAGES RENAME ${LANG_DOMAIN}.mo PERMISSIONS ${PERMS}) + endforeach(LANG_PO) + + # Generate languages, depends on the mo files + add_custom_target(module_language DEPENDS ${LANG_SRCS_MO}) +endif(GETTEXT_FOUND) diff --git a/modules/third/language/README b/modules/third/language/README new file mode 100644 index 0000000..c86eeef --- /dev/null +++ b/modules/third/language/README @@ -0,0 +1 @@ +Language files for third party modules are to go here. diff --git a/modules/third/language/update.sh b/modules/third/language/update.sh new file mode 100755 index 0000000..1f16ea9 --- /dev/null +++ b/modules/third/language/update.sh @@ -0,0 +1,14 @@ +#!/bin/bash + +for f in `ls ../*.cpp` +do + BASE=`basename $f | cut -d'.' -f1` + xgettext -C -s -d $BASE -o $BASE.pot --from-code=utf-8 --keyword --keyword=_ $f +done + +for f in `ls *.po` +do + msgmerge -v -s -U $f `basename $f | cut -d'.' -f1`.pot +done + +rm -f *~ diff --git a/modules/webcpanel/CMakeLists.txt b/modules/webcpanel/CMakeLists.txt new file mode 100644 index 0000000..ea5a03b --- /dev/null +++ b/modules/webcpanel/CMakeLists.txt @@ -0,0 +1,5 @@ +build_subdir(${CMAKE_CURRENT_SOURCE_DIR}) + +install(DIRECTORY templates + DESTINATION "${DB_DIR}/modules/webcpanel" +) diff --git a/modules/webcpanel/pages/chanserv/access.cpp b/modules/webcpanel/pages/chanserv/access.cpp new file mode 100644 index 0000000..1b0991c --- /dev/null +++ b/modules/webcpanel/pages/chanserv/access.cpp @@ -0,0 +1,127 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" +#include "utils.h" + +WebCPanel::ChanServ::Access::Access(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage(cat, u) +{ +} + +bool WebCPanel::ChanServ::Access::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + TemplateFileServer Page("chanserv/access.html"); + const Anope::string &chname = message.get_data["channel"]; + + BuildChanList(na, replacements); + + if (chname.empty()) + { + Page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + + ChannelInfo *ci = ChannelInfo::Find(chname); + + if (!ci) + { + replacements["MESSAGES"] = "Channel not registered."; + Page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + + AccessGroup u_access = ci->AccessFor(na->nc); + bool has_priv = na->nc->IsServicesOper() && na->nc->o->ot->HasPriv("chanserv/access/modify"); + + if (!u_access.HasPriv("ACCESS_LIST") && !has_priv) + { + replacements["MESSAGES"] = "Access denied."; + Page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + + replacements["ACCESS_LIST"] = "YES"; + + if (u_access.HasPriv("ACCESS_CHANGE") || has_priv) + { + if (message.get_data["del"].empty() == false && message.get_data["mask"].empty() == false) + { + std::vector params; + params.push_back(ci->name); + params.push_back("DEL"); + params.push_back(message.get_data["mask"]); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "ChanServ", "chanserv/access", params, replacements); + } + else if (message.post_data["mask"].empty() == false && message.post_data["access"].empty() == false && message.post_data["provider"].empty() == false) + { + const Anope::string &provider = message.post_data["provider"]; + + if (provider == "chanserv/access") + { + std::vector params; + params.push_back(ci->name); + params.push_back("ADD"); + params.push_back(message.post_data["mask"]); + params.push_back(message.post_data["access"]); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "ChanServ", "chanserv/access", params, replacements); + } + else if (provider == "chanserv/xop") + { + std::vector params; + params.push_back(ci->name); + params.push_back("ADD"); + params.push_back(message.post_data["mask"]); + + WebPanel::RunCommandWithName(client, na->nc, "ChanServ", "chanserv/xop", message.post_data["access"], params, replacements); + } + else if (provider == "chanserv/flags") + { + std::vector params; + params.push_back(ci->name); + params.push_back("MODIFY"); + params.push_back(message.post_data["mask"]); + params.push_back(message.post_data["access"]); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "ChanServ", "chanserv/flags", params, replacements); + } + } + } + + /* command might have invalidated u_access */ + u_access = ci->AccessFor(na->nc); + + replacements["ESCAPED_CHANNEL"] = HTTPUtils::URLEncode(chname); + replacements["ACCESS_CHANGE"] = u_access.HasPriv("ACCESS_CHANGE") ? "YES" : "NO"; + + for (unsigned i = 0; i < ci->GetAccessCount(); ++i) + { + ChanAccess *access = ci->GetAccess(i); + + replacements["MASKS"] = access->Mask(); + replacements["ACCESSES"] = access->AccessSerialize(); + replacements["CREATORS"] = access->creator; + } + + if (Service::FindService("Command", "chanserv/access")) + replacements["PROVIDERS"] = "chanserv/access"; + if (Service::FindService("Command", "chanserv/xop")) + replacements["PROVIDERS"] = "chanserv/xop"; + if (Service::FindService("Command", "chanserv/flags")) + replacements["PROVIDERS"] = "chanserv/flags"; + + Page.Serve(server, page_name, client, message, reply, replacements); + return true; +} + +std::set WebCPanel::ChanServ::Access::GetData() +{ + std::set v; + v.insert("channel"); + return v; +} diff --git a/modules/webcpanel/pages/chanserv/access.h b/modules/webcpanel/pages/chanserv/access.h new file mode 100644 index 0000000..57b67ae --- /dev/null +++ b/modules/webcpanel/pages/chanserv/access.h @@ -0,0 +1,26 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace ChanServ +{ + +class Access : public WebPanelProtectedPage +{ + public: + Access(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; + + std::set GetData() anope_override; +}; + +} + +} diff --git a/modules/webcpanel/pages/chanserv/akick.cpp b/modules/webcpanel/pages/chanserv/akick.cpp new file mode 100644 index 0000000..648e912 --- /dev/null +++ b/modules/webcpanel/pages/chanserv/akick.cpp @@ -0,0 +1,93 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" +#include "utils.h" + +WebCPanel::ChanServ::Akick::Akick(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage(cat, u) +{ +} + +bool WebCPanel::ChanServ::Akick::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + const Anope::string &chname = message.get_data["channel"]; + TemplateFileServer Page("chanserv/akick.html"); + + BuildChanList(na, replacements); + + if (chname.empty()) + { + Page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + + ChannelInfo *ci = ChannelInfo::Find(chname); + + if (!ci) + { + replacements["MESSAGES"] = "Channel not registered"; + Page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + + AccessGroup u_access = ci->AccessFor(na->nc); + bool has_priv = na->nc->IsServicesOper() && na->nc->o->ot->HasPriv("chanserv/access/modify"); + + if (!u_access.HasPriv("AKICK") && !has_priv) + { + replacements["MESSAGES"] = "Permission denied."; + Page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + + replacements["AKICK"] = "YES"; + + if (message.get_data["del"].empty() == false && message.get_data["mask"].empty() == false) + { + std::vector params; + params.push_back(ci->name); + params.push_back("DEL"); + params.push_back(message.get_data["mask"]); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "ChanServ", "chanserv/akick", params, replacements); + } + else if (message.post_data["mask"].empty() == false) + { + std::vector params; + params.push_back(ci->name); + params.push_back("ADD"); + params.push_back(message.post_data["mask"]); + if (message.post_data["reason"].empty() == false) + params.push_back(message.post_data["reason"]); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "ChanServ", "chanserv/akick", params, replacements); + } + + replacements["ESCAPED_CHANNEL"] = HTTPUtils::URLEncode(chname); + + for (unsigned i = 0; i < ci->GetAkickCount(); ++i) + { + AutoKick *akick = ci->GetAkick(i); + + if (akick->nc) + replacements["MASKS"] = akick->nc->display; + else + replacements["MASKS"] = akick->mask; + replacements["CREATORS"] = akick->creator; + replacements["REASONS"] = akick->reason; + } + + Page.Serve(server, page_name, client, message, reply, replacements); + return true; +} + +std::set WebCPanel::ChanServ::Akick::GetData() +{ + std::set v; + v.insert("channel"); + return v; +} diff --git a/modules/webcpanel/pages/chanserv/akick.h b/modules/webcpanel/pages/chanserv/akick.h new file mode 100644 index 0000000..735c184 --- /dev/null +++ b/modules/webcpanel/pages/chanserv/akick.h @@ -0,0 +1,26 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace ChanServ +{ + +class Akick : public WebPanelProtectedPage +{ + public: + Akick(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; + + std::set GetData() anope_override; +}; + +} + +} diff --git a/modules/webcpanel/pages/chanserv/drop.cpp b/modules/webcpanel/pages/chanserv/drop.cpp new file mode 100644 index 0000000..ab295d1 --- /dev/null +++ b/modules/webcpanel/pages/chanserv/drop.cpp @@ -0,0 +1,58 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" +#include "utils.h" + +WebCPanel::ChanServ::Drop::Drop(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage (cat, u) +{ +} + + +bool WebCPanel::ChanServ::Drop::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + + if (message.post_data.count("channel") > 0 && message.post_data.count("confChan") > 0) + { + if (message.post_data["channel"] == message.post_data["confChan"]) + { + std::vector params; + const Anope::string &channel = HTTPUtils::URLDecode(message.post_data["channel"]); + params.push_back(channel); + params.push_back(channel); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "ChanServ", "chanserv/drop", params, replacements); + } + else + replacements["MESSAGES"] = "Invalid Confirmation"; + } + + std::deque queue; + na->nc->GetChannelReferences(queue); + for (unsigned i = 0; i < queue.size(); ++i) + { + ChannelInfo *ci = queue[i]; + if ((ci->HasExt("SECUREFOUNDER") ? ci->AccessFor(na->nc).founder : ci->AccessFor(na->nc).HasPriv("FOUNDER")) || (na->nc->IsServicesOper() && na->nc->o->ot->HasCommand("chanserv/drop"))) + { + replacements["CHANNEL_NAMES"] = ci->name; + replacements["ESCAPED_CHANNEL_NAMES"] = HTTPUtils::URLEncode(ci->name); + } + } + + if (message.get_data.count("channel") > 0) + { + const Anope::string &chname = message.get_data["channel"]; + + replacements["CHANNEL_DROP"] = chname; + replacements["ESCAPED_CHANNEL"] = HTTPUtils::URLEncode(chname); + } + + TemplateFileServer page("chanserv/drop.html"); + page.Serve(server, page_name, client, message, reply, replacements); + return true; + +} diff --git a/modules/webcpanel/pages/chanserv/drop.h b/modules/webcpanel/pages/chanserv/drop.h new file mode 100644 index 0000000..519b179 --- /dev/null +++ b/modules/webcpanel/pages/chanserv/drop.h @@ -0,0 +1,25 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + + namespace ChanServ + { + + class Drop : public WebPanelProtectedPage + { + public: + Drop(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; + + }; + + } + +} diff --git a/modules/webcpanel/pages/chanserv/info.cpp b/modules/webcpanel/pages/chanserv/info.cpp new file mode 100644 index 0000000..1b89f7e --- /dev/null +++ b/modules/webcpanel/pages/chanserv/info.cpp @@ -0,0 +1,27 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" +#include "utils.h" + +WebCPanel::ChanServ::Info::Info(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage(cat, u) +{ +} + +bool WebCPanel::ChanServ::Info::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + const Anope::string &chname = message.get_data["channel"]; + + if (!chname.empty()) + replacements["ESCAPED_CHANNEL"] = HTTPUtils::URLEncode(chname); + + BuildChanList(na, replacements); + + TemplateFileServer page("chanserv/main.html"); + page.Serve(server, page_name, client, message, reply, replacements); + return true; +} diff --git a/modules/webcpanel/pages/chanserv/info.h b/modules/webcpanel/pages/chanserv/info.h new file mode 100644 index 0000000..c2535bc --- /dev/null +++ b/modules/webcpanel/pages/chanserv/info.h @@ -0,0 +1,24 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace ChanServ +{ + +class Info : public WebPanelProtectedPage +{ + public: + Info(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; +}; + +} + +} diff --git a/modules/webcpanel/pages/chanserv/modes.cpp b/modules/webcpanel/pages/chanserv/modes.cpp new file mode 100644 index 0000000..4f3ed03 --- /dev/null +++ b/modules/webcpanel/pages/chanserv/modes.cpp @@ -0,0 +1,111 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" +#include "utils.h" + +WebCPanel::ChanServ::Modes::Modes(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage(cat, u) +{ +} + +bool WebCPanel::ChanServ::Modes::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + const Anope::string &chname = message.get_data["channel"]; + const Anope::string &mode = message.get_data["m"]; + TemplateFileServer Page("chanserv/modes.html"); + + BuildChanList(na, replacements); + + if (chname.empty()) + { + Page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + + replacements["ESCAPED_CHANNEL"] = HTTPUtils::URLEncode(chname); + ChannelInfo *ci = ChannelInfo::Find(chname); + + if (!ci) + { + Page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + + Channel *c = Channel::Find(chname); + + if (!c) + { + replacements["MESSAGES"] = Anope::printf(CHAN_X_NOT_IN_USE, chname.c_str()); + Page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + + AccessGroup u_access = ci->AccessFor(na->nc); + bool has_priv = na->nc->IsServicesOper() && na->nc->o->ot->HasPriv("chanserv/administration"); + + if (!u_access.HasPriv("MODE") && !has_priv) + { + replacements["MESSAGES"] = "Access denied."; + Page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + + replacements["MODE"] = "YES"; + + /* build a list with the names of all listmodes */ + for (unsigned i = 0; i < ModeManager::GetChannelModes().size(); ++i) + { + ChannelMode *cm = ModeManager::GetChannelModes()[i]; + + if (cm->type == MODE_LIST && cm->mchar) + replacements["LISTMODES"] = cm->mchar; + } + + if (mode.empty()) + { + Page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + replacements["ESCAPED_MODE"] = HTTPUtils::URLEncode(mode); + + ChannelMode *cm = ModeManager::FindChannelModeByChar(mode[0]); + if (cm) + { + if (message.get_data["del"].empty() == false && message.get_data["mask"].empty() == false) + { + std::vector params; + params.push_back(ci->name); + params.push_back("SET"); + params.push_back("-" + Anope::string(cm->mchar)); + params.push_back(message.get_data["mask"]); + WebPanel::RunCommand(client, na->nc->display, na->nc, "ChanServ", "chanserv/mode", params, replacements); + } + else if (message.post_data["mask"].empty() == false) + { + std::vector params; + params.push_back(ci->name); + params.push_back("SET"); + params.push_back("+" + Anope::string(cm->mchar)); + params.push_back(message.post_data["mask"]); + WebPanel::RunCommand(client, na->nc->display, na->nc, "ChanServ", "chanserv/mode", params, replacements); + } + + std::vector v = c->GetModeList(cm->name); + for (unsigned int i = 0; i < v.size(); ++i) + replacements["MASKS"] = v[i]; + } + + Page.Serve(server, page_name, client, message, reply, replacements); + return true; +} + +std::set WebCPanel::ChanServ::Modes::GetData() +{ + std::set v; + v.insert("channel"); + return v; +} diff --git a/modules/webcpanel/pages/chanserv/modes.h b/modules/webcpanel/pages/chanserv/modes.h new file mode 100644 index 0000000..842098f --- /dev/null +++ b/modules/webcpanel/pages/chanserv/modes.h @@ -0,0 +1,26 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace ChanServ +{ + +class Modes : public WebPanelProtectedPage +{ + public: + Modes(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; + + std::set GetData() anope_override; +}; + +} + +} diff --git a/modules/webcpanel/pages/chanserv/set.cpp b/modules/webcpanel/pages/chanserv/set.cpp new file mode 100644 index 0000000..4fe81b1 --- /dev/null +++ b/modules/webcpanel/pages/chanserv/set.cpp @@ -0,0 +1,154 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" +#include "utils.h" + +WebCPanel::ChanServ::Set::Set(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage(cat, u) +{ +} + +bool WebCPanel::ChanServ::Set::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + const Anope::string &chname = message.get_data["channel"]; + bool can_set = false; + TemplateFileServer page("chanserv/set.html"); + + BuildChanList(na, replacements); + + if (chname.empty()) + { + page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + + ChannelInfo *ci = ChannelInfo::Find(chname); + + if (!ci) + { + page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + + replacements["OKAY"]; + + if (ci->AccessFor(na->nc).HasPriv("SET")) + { + replacements["CAN_SET"]; + can_set = true; + } + + if (can_set && message.post_data.empty() == false) + { + if (ci->HasExt("KEEPTOPIC") != message.post_data.count("keeptopic")) + { + if (!ci->HasExt("KEEPTOPIC")) + ci->Extend("KEEPTOPIC"); + else + ci->Shrink("KEEPTOPIC"); + replacements["MESSAGES"] = "Secure updated"; + } + if (ci->HasExt("PEACE") != message.post_data.count("peace")) + { + if (!ci->HasExt("PEACE")) + ci->Extend("PEACE"); + else + ci->Shrink("PEACE"); + replacements["MESSAGES"] = "Peace updated"; + } + if (ci->HasExt("CS_PRIVATE") != message.post_data.count("private")) + { + if (!ci->HasExt("CS_PRIVATE")) + ci->Extend("CS_PRIVATE"); + else + ci->Shrink("CS_PRIVATE"); + replacements["MESSAGES"] = "Private updated"; + } + if (ci->HasExt("RESTRICTED") != message.post_data.count("restricted")) + { + if (!ci->HasExt("RESTRICTED")) + ci->Extend("RESTRICTED"); + else + ci->Shrink("RESTRICTED"); + replacements["MESSAGES"] = "Restricted updated"; + } + if (ci->HasExt("CS_SECURE") != message.post_data.count("secure")) + { + if (!ci->HasExt("CS_SECURE")) + ci->Extend("CS_SECURE"); + else + ci->Shrink("CS_SECURE"); + replacements["MESSAGES"] = "Secure updated"; + } + if (ci->HasExt("SECUREOPS") != message.post_data.count("secureops")) + { + if (!ci->HasExt("SECUREOPS")) + ci->Extend("SECUREOPS"); + else + ci->Shrink("SECUREOPS"); + replacements["MESSAGES"] = "Secureops updated"; + } + if (ci->HasExt("TOPICLOCK") != message.post_data.count("topiclock")) + { + if (!ci->HasExt("TOPICLOCK")) + ci->Extend("TOPICLOCK"); + else + ci->Shrink("TOPICLOCK"); + replacements["MESSAGES"] = "Topiclock updated"; + } + } + + replacements["CHANNEL"] = ci->name; + replacements["CHANNEL_ESCAPED"] = HTTPUtils::URLEncode(ci->name); + if (ci->GetFounder()) + replacements["FOUNDER"] = ci->GetFounder()->display; + if (ci->GetSuccessor()) + replacements["SUCCESSOR"] = ci->GetSuccessor()->display; + replacements["TIME_REGISTERED"] = Anope::strftime(ci->time_registered, na->nc); + replacements["LAST_USED"] = Anope::strftime(ci->last_used, na->nc); + replacements["ESCAPED_CHANNEL"] = HTTPUtils::URLEncode(chname); + + if (!ci->last_topic.empty()) + { + replacements["LAST_TOPIC"] = ci->last_topic; + replacements["LAST_TOPIC_SETTER"] = ci->last_topic_setter; + } + + if (can_set) + { + if (ci->HasExt("KEEPTOPIC")) + replacements["KEEPTOPIC"]; + + if (ci->HasExt("PEACE")) + replacements["PEACE"]; + + if (ci->HasExt("CS_PRIVATE")) + replacements["PRIVATE"]; + + if (ci->HasExt("RESTRICTED")) + replacements["RESTRICTED"]; + + if (ci->HasExt("CS_SECURE")) + replacements["SECURE"]; + + if (ci->HasExt("SECUREOPS")) + replacements["SECUREOPS"]; + + if (ci->HasExt("TOPICLOCK")) + replacements["TOPICLOCK"]; + } + + page.Serve(server, page_name, client, message, reply, replacements); + return true; +} + +std::set WebCPanel::ChanServ::Set::GetData() +{ + std::set v; + v.insert("channel"); + return v; +} diff --git a/modules/webcpanel/pages/chanserv/set.h b/modules/webcpanel/pages/chanserv/set.h new file mode 100644 index 0000000..90001b6 --- /dev/null +++ b/modules/webcpanel/pages/chanserv/set.h @@ -0,0 +1,26 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace ChanServ +{ + +class Set : public WebPanelProtectedPage +{ + public: + Set(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; + + std::set GetData() anope_override; +}; + +} + +} diff --git a/modules/webcpanel/pages/chanserv/utils.cpp b/modules/webcpanel/pages/chanserv/utils.cpp new file mode 100644 index 0000000..e6ab3d8 --- /dev/null +++ b/modules/webcpanel/pages/chanserv/utils.cpp @@ -0,0 +1,44 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" + +namespace +{ + bool ChannelSort(ChannelInfo *ci1, ChannelInfo *ci2) + { + return ci::less()(ci1->name, ci2->name); + } +} + +namespace WebCPanel +{ + +namespace ChanServ +{ + +void BuildChanList(NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + std::deque queue; + na->nc->GetChannelReferences(queue); + std::sort(queue.begin(), queue.end(), ChannelSort); + + for (unsigned i = 0; i < queue.size(); ++i) + { + ChannelInfo *ci = queue[i]; + + if (na->nc != ci->GetFounder() && ci->AccessFor(na->nc).empty()) + continue; + + replacements["CHANNEL_NAMES"] = ci->name; + replacements["ESCAPED_CHANNEL_NAMES"] = HTTPUtils::URLEncode(ci->name); + } +} + +} + +} diff --git a/modules/webcpanel/pages/chanserv/utils.h b/modules/webcpanel/pages/chanserv/utils.h new file mode 100644 index 0000000..6e323e9 --- /dev/null +++ b/modules/webcpanel/pages/chanserv/utils.h @@ -0,0 +1,18 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace ChanServ +{ + +extern void BuildChanList(NickAlias *, TemplateFileServer::Replacements &); + +} + +} diff --git a/modules/webcpanel/pages/confirm.cpp b/modules/webcpanel/pages/confirm.cpp new file mode 100644 index 0000000..da91b1b --- /dev/null +++ b/modules/webcpanel/pages/confirm.cpp @@ -0,0 +1,31 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../webcpanel.h" + +bool WebCPanel::Confirm::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply) +{ + TemplateFileServer::Replacements replacements; + const Anope::string &user = message.post_data["username"], &pass = message.post_data["password"], &email = message.post_data["email"]; + + replacements["TITLE"] = page_title; + + if (!user.empty() && !pass.empty()) + { + std::vector params; + params.push_back(pass); + if (!email.empty()) + params.push_back(email); + + WebPanel::RunCommand(client, user, NULL, "NickServ", "nickserv/register", params, replacements); + } + + TemplateFileServer page("confirm.html"); + + page.Serve(server, page_name, client, message, reply, replacements); + return true; +} diff --git a/modules/webcpanel/pages/confirm.h b/modules/webcpanel/pages/confirm.h new file mode 100644 index 0000000..8a8926f --- /dev/null +++ b/modules/webcpanel/pages/confirm.h @@ -0,0 +1,21 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "modules/httpd.h" + +namespace WebCPanel +{ + +class Confirm : public WebPanelPage +{ + public: + Confirm(const Anope::string &u) : WebPanelPage(u) { } + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &) anope_override; +}; + +} diff --git a/modules/webcpanel/pages/hostserv/request.cpp b/modules/webcpanel/pages/hostserv/request.cpp new file mode 100644 index 0000000..013e865 --- /dev/null +++ b/modules/webcpanel/pages/hostserv/request.cpp @@ -0,0 +1,36 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" + +WebCPanel::HostServ::Request::Request(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage (cat, u) +{ +} + +bool WebCPanel::HostServ::Request::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + if (message.post_data.count("req") > 0) + { + std::vector params; + params.push_back(HTTPUtils::URLDecode(message.post_data["req"])); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "HostServ", "hostserv/request", params, replacements, "CMDR"); + } + + if (na->HasVhost()) + { + if (na->GetVhostIdent().empty() == false) + replacements["VHOST"] = na->GetVhostIdent() + "@" + na->GetVhostHost(); + else + replacements["VHOST"] = na->GetVhostHost(); + } + if (ServiceReference("Command", "hostserv/request")) + replacements["CAN_REQUEST"] = "YES"; + TemplateFileServer page("hostserv/request.html"); + page.Serve(server, page_name, client, message, reply, replacements); + return true; +} diff --git a/modules/webcpanel/pages/hostserv/request.h b/modules/webcpanel/pages/hostserv/request.h new file mode 100644 index 0000000..3a16d5c --- /dev/null +++ b/modules/webcpanel/pages/hostserv/request.h @@ -0,0 +1,24 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace HostServ +{ + +class Request : public WebPanelProtectedPage +{ + public: + Request(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; +}; + +} + +} diff --git a/modules/webcpanel/pages/index.cpp b/modules/webcpanel/pages/index.cpp new file mode 100644 index 0000000..8afe330 --- /dev/null +++ b/modules/webcpanel/pages/index.cpp @@ -0,0 +1,137 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../webcpanel.h" + +class WebpanelRequest : public IdentifyRequest +{ + HTTPReply reply; + HTTPMessage message; + Reference server; + Anope::string page_name; + Reference client; + TemplateFileServer::Replacements replacements; + + public: + WebpanelRequest(Module *o, HTTPReply &r, HTTPMessage &m, HTTPProvider *s, const Anope::string &p_n, HTTPClient *c, TemplateFileServer::Replacements &re, const Anope::string &user, const Anope::string &pass) : IdentifyRequest(o, user, pass), reply(r), message(m), server(s), page_name(p_n), client(c), replacements(re) { } + + void OnSuccess() anope_override + { + if (!client || !server) + return; + NickAlias *na = NickAlias::Find(this->GetAccount()); + if (!na) + { + this->OnFail(); + return; + } + + if (na->nc->HasExt("NS_SUSPENDED")) + { + this->OnFail(); + return; + } + + // Rate limit logins to 1/sec + time_t *last_login = na->nc->GetExt("webcpanel_last_login"); + if (last_login != NULL && Anope::CurTime == *last_login) + { + this->OnFail(); + return; + } + + Anope::string id; + for (int i = 0; i < 64; ++i) + { + char c; + do + c = 48 + (rand() % 75); + while (!isalnum(c)); + id += c; + } + + na->Extend("webcpanel_id", id); + na->Extend("webcpanel_ip", client->GetIP()); + na->nc->Extend("webcpanel_last_login", Anope::CurTime); + + { + HTTPReply::cookie c; + c.push_back(std::make_pair("account", na->nick)); + c.push_back(std::make_pair("Path", "/")); + reply.cookies.push_back(c); + } + + { + HTTPReply::cookie c; + c.push_back(std::make_pair("id", id)); + c.push_back(std::make_pair("Path", "/")); + reply.cookies.push_back(c); + } + + reply.error = HTTP_FOUND; + reply.headers["Location"] = Anope::string("http") + (server->IsSSL() ? "s" : "") + "://" + message.headers["Host"] + "/nickserv/info"; + + client->SendReply(&reply); + } + + void OnFail() anope_override + { + if (!client || !server) + return; + replacements["INVALID_LOGIN"] = "Invalid username or password"; + TemplateFileServer page("login.html"); + page.Serve(server, page_name, client, message, reply, replacements); + + client->SendReply(&reply); + } +}; + +bool WebCPanel::Index::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply) +{ + TemplateFileServer::Replacements replacements; + const Anope::string &user = message.post_data["username"], &pass = message.post_data["password"]; + + replacements["TITLE"] = page_title; + + if (!user.empty() && !pass.empty()) + { + // Rate limit check. + Anope::string ip = client->clientaddr.addr(); + + Anope::hash_map::iterator it = last_login_attempt.find(ip); + if (it != last_login_attempt.end()) + { + time_t last_time = it->second; + + if (last_time == Anope::CurTime) + { + replacements["INVALID_LOGIN"] = "Rate limited"; + TemplateFileServer page("login.html"); + page.Serve(server, page_name, client, message, reply, replacements); + return true; + } + } + + // don't let ip hash grow too long + if (Anope::CurTime > last_clear + FLUSH_TIME) + { + last_login_attempt.clear(); + last_clear = Anope::CurTime; + } + + last_login_attempt[ip] = Anope::CurTime; + + WebpanelRequest *req = new WebpanelRequest(me, reply, message, server, page_name, client, replacements, user, pass); + FOREACH_MOD(OnCheckAuthentication, (NULL, req)); + req->Dispatch(); + return false; + } + + TemplateFileServer page("login.html"); + page.Serve(server, page_name, client, message, reply, replacements); + return true; +} diff --git a/modules/webcpanel/pages/index.h b/modules/webcpanel/pages/index.h new file mode 100644 index 0000000..b62cc05 --- /dev/null +++ b/modules/webcpanel/pages/index.h @@ -0,0 +1,26 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "modules/httpd.h" + +namespace WebCPanel +{ + +class Index : public WebPanelPage +{ + static const int FLUSH_TIME = 60; + + Anope::hash_map last_login_attempt; + time_t last_clear; + + public: + Index(const Anope::string &u) : WebPanelPage(u), last_clear(0) { } + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &) anope_override; +}; + +} diff --git a/modules/webcpanel/pages/logout.cpp b/modules/webcpanel/pages/logout.cpp new file mode 100644 index 0000000..931537a --- /dev/null +++ b/modules/webcpanel/pages/logout.cpp @@ -0,0 +1,22 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../webcpanel.h" + +WebCPanel::Logout::Logout(const Anope::string &u) : WebPanelProtectedPage("", u) +{ +} + +bool WebCPanel::Logout::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + na->Shrink("webcpanel_id"); + na->Shrink("webcpanel_ip"); + + reply.error = HTTP_FOUND; + reply.headers["Location"] = Anope::string("http") + (server->IsSSL() ? "s" : "") + "://" + message.headers["Host"] + "/"; + return true; +} diff --git a/modules/webcpanel/pages/logout.h b/modules/webcpanel/pages/logout.h new file mode 100644 index 0000000..cca0fc6 --- /dev/null +++ b/modules/webcpanel/pages/logout.h @@ -0,0 +1,19 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +class Logout : public WebPanelProtectedPage +{ + public: + Logout(const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; +}; + +} diff --git a/modules/webcpanel/pages/memoserv/memos.cpp b/modules/webcpanel/pages/memoserv/memos.cpp new file mode 100644 index 0000000..090f6af --- /dev/null +++ b/modules/webcpanel/pages/memoserv/memos.cpp @@ -0,0 +1,114 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" + +WebCPanel::MemoServ::Memos::Memos(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage(cat, u) +{ +} + +bool WebCPanel::MemoServ::Memos::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + const Anope::string &chname = message.get_data["channel"]; + ChannelInfo *ci; + const MemoInfo *mi; + Memo *m; + + for (registered_channel_map::const_iterator it = RegisteredChannelList->begin(), it_end = RegisteredChannelList->end(); it != it_end; ++it) + { + ci = it->second; + + if (ci->AccessFor(na->nc).HasPriv("MEMO")) + { + replacements["CHANNEL_NAMES"] = ci->name; + replacements["ESCAPED_CHANNEL_NAMES"] = HTTPUtils::URLEncode(ci->name); + } + } + + if (chname.empty()) + { + replacements["MESSAGES"] = "No Channel specified, displaying the memos for your Nick"; + mi = &na->nc->memos; + } + else + { + ci = ChannelInfo::Find(chname); + if (ci) + { + replacements["MESSAGES"] = "Displaying the memos for " + chname + "."; + mi = &ci->memos; + + replacements["CHANNEL_NAME"] = ci->name; + replacements["ESCAPED_CHANNEL_NAME"] = HTTPUtils::URLEncode(ci->name); + } + else + { + replacements["MESSAGES"] = "Channel " + chname + " not found, displaying the memos for your nick"; + mi = &na->nc->memos; + } + } + if (message.post_data.count("receiver") > 0 && message.post_data.count("message") > 0) + { + std::vector params; + params.push_back(HTTPUtils::URLDecode(message.post_data["receiver"])); + params.push_back(HTTPUtils::URLDecode(message.post_data["message"])); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "MemoServ", "memoserv/send", params, replacements, "CMDR"); + } + if (message.get_data.count("del") > 0 && message.get_data.count("number") > 0) + { + std::vector params; + if (!chname.empty()) + params.push_back(chname); + params.push_back(message.get_data["number"]); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "MemoServ", "memoserv/del", params, replacements, "CMDR"); + } + if (message.get_data.count("read") > 0 && message.get_data.count("number") > 0) + { + std::vector params; + int number = -1; + + try + { + number = convertTo(message.get_data["number"]); + } + catch (const ConvertException &ex) + { + replacements["MESSAGES"] = "ERROR - invalid parameter for NUMBER"; + } + + if (number > 0) + { + m = mi->GetMemo(number-1); + + if (!m) + replacements["MESSAGES"] = "ERROR - invalid memo number."; + else if (message.get_data["read"] == "1") + m->unread = false; + else if (message.get_data["read"] == "2") + m->unread = true; + } + } + + for (unsigned i = 0; i < mi->memos->size(); ++i) + { + m = mi->GetMemo(i); + replacements["NUMBER"] = stringify(i+1); + replacements["SENDER"] = m->sender; + replacements["TIME"] = Anope::strftime(m->time); + replacements["TEXT"] = m->text; + if (m->unread) + replacements["UNREAD"] = "YES"; + else + replacements["UNREAD"] = "NO"; + } + + TemplateFileServer page("memoserv/memos.html"); + page.Serve(server, page_name, client, message, reply, replacements); + return true; +} diff --git a/modules/webcpanel/pages/memoserv/memos.h b/modules/webcpanel/pages/memoserv/memos.h new file mode 100644 index 0000000..8bafb30 --- /dev/null +++ b/modules/webcpanel/pages/memoserv/memos.h @@ -0,0 +1,24 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace MemoServ +{ + +class Memos : public WebPanelProtectedPage +{ + public: + Memos(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; +}; + +} + +} diff --git a/modules/webcpanel/pages/nickserv/access.cpp b/modules/webcpanel/pages/nickserv/access.cpp new file mode 100644 index 0000000..ac98152 --- /dev/null +++ b/modules/webcpanel/pages/nickserv/access.cpp @@ -0,0 +1,39 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" + +WebCPanel::NickServ::Access::Access(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage(cat, u) +{ +} + +bool WebCPanel::NickServ::Access::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + if (message.post_data.count("access") > 0) + { + std::vector params; + params.push_back("ADD"); + params.push_back(message.post_data["access"]); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "NickServ", "nickserv/access", params, replacements); + } + else if (message.get_data.count("del") > 0 && message.get_data.count("mask") > 0) + { + std::vector params; + params.push_back("DEL"); + params.push_back(message.get_data["mask"]); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "NickServ", "nickserv/access", params, replacements); + } + + for (unsigned i = 0; i < na->nc->access.size(); ++i) + replacements["ACCESS"] = na->nc->access[i]; + + TemplateFileServer page("nickserv/access.html"); + page.Serve(server, page_name, client, message, reply, replacements); + return true; +} diff --git a/modules/webcpanel/pages/nickserv/access.h b/modules/webcpanel/pages/nickserv/access.h new file mode 100644 index 0000000..c6f0f4e --- /dev/null +++ b/modules/webcpanel/pages/nickserv/access.h @@ -0,0 +1,24 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace NickServ +{ + +class Access : public WebPanelProtectedPage +{ + public: + Access(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; +}; + +} + +} diff --git a/modules/webcpanel/pages/nickserv/alist.cpp b/modules/webcpanel/pages/nickserv/alist.cpp new file mode 100644 index 0000000..bc3bf0b --- /dev/null +++ b/modules/webcpanel/pages/nickserv/alist.cpp @@ -0,0 +1,57 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" + +static bool ChannelSort(ChannelInfo *ci1, ChannelInfo *ci2) +{ + return ci::less()(ci1->name, ci2->name); +} + +WebCPanel::NickServ::Alist::Alist(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage(cat, u) +{ +} + +bool WebCPanel::NickServ::Alist::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + std::deque queue; + na->nc->GetChannelReferences(queue); + std::sort(queue.begin(), queue.end(), ChannelSort); + + int chan_count = 0; + + for (unsigned q = 0; q < queue.size(); ++q) + { + ChannelInfo *ci = queue[q]; + + if (ci->GetFounder() == na->nc) + { + ++chan_count; + + replacements["NUMBERS"] = stringify(chan_count); + replacements["CHANNELS"] = (ci->HasExt("CS_NO_EXPIRE") ? "!" : "") + ci->name; + replacements["ACCESSES"] = "Founder"; + continue; + } + + AccessGroup access = ci->AccessFor(na->nc); + if (access.empty()) + continue; + + ++chan_count; + + replacements["NUMBERS"] = stringify(chan_count); + replacements["CHANNELS"] = (ci->HasExt("CS_NO_EXPIRE") ? "!" : "") + ci->name; + + const ChanAccess *highest = access.Highest(); + replacements["ACCESSES"] = highest ? highest->AccessSerialize() : ""; + } + + TemplateFileServer page("nickserv/alist.html"); + page.Serve(server, page_name, client, message, reply, replacements); + return true; +} diff --git a/modules/webcpanel/pages/nickserv/alist.h b/modules/webcpanel/pages/nickserv/alist.h new file mode 100644 index 0000000..abc7dcb --- /dev/null +++ b/modules/webcpanel/pages/nickserv/alist.h @@ -0,0 +1,24 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace NickServ +{ + +class Alist : public WebPanelProtectedPage +{ + public: + Alist(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; +}; + +} + +} diff --git a/modules/webcpanel/pages/nickserv/cert.cpp b/modules/webcpanel/pages/nickserv/cert.cpp new file mode 100644 index 0000000..218b879 --- /dev/null +++ b/modules/webcpanel/pages/nickserv/cert.cpp @@ -0,0 +1,42 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" +#include "modules/ns_cert.h" + +WebCPanel::NickServ::Cert::Cert(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage(cat, u) +{ +} + +bool WebCPanel::NickServ::Cert::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + if (message.post_data.count("certfp") > 0) + { + std::vector params; + params.push_back("ADD"); + params.push_back(message.post_data["certfp"]); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "NickServ", "nickserv/cert", params, replacements); + } + else if (message.get_data.count("del") > 0 && message.get_data.count("mask") > 0) + { + std::vector params; + params.push_back("DEL"); + params.push_back(message.get_data["mask"]); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "NickServ", "nickserv/cert", params, replacements); + } + + NSCertList *cl = na->nc->GetExt("certificates"); + if (cl) + for (unsigned i = 0; i < cl->GetCertCount(); ++i) + replacements["CERTS"] = cl->GetCert(i); + + TemplateFileServer page("nickserv/cert.html"); + page.Serve(server, page_name, client, message, reply, replacements); + return true; +} diff --git a/modules/webcpanel/pages/nickserv/cert.h b/modules/webcpanel/pages/nickserv/cert.h new file mode 100644 index 0000000..e8c2623 --- /dev/null +++ b/modules/webcpanel/pages/nickserv/cert.h @@ -0,0 +1,24 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace NickServ +{ + +class Cert : public WebPanelProtectedPage +{ + public: + Cert(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; +}; + +} + +} diff --git a/modules/webcpanel/pages/nickserv/confirm.cpp b/modules/webcpanel/pages/nickserv/confirm.cpp new file mode 100644 index 0000000..00d2196 --- /dev/null +++ b/modules/webcpanel/pages/nickserv/confirm.cpp @@ -0,0 +1,26 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" + +WebCPanel::NickServ::Confirm::Confirm(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage(cat, u) +{ +} + +bool WebCPanel::NickServ::Confirm::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + + std::vector params; + params.push_back(message.post_data["code"]); + + WebPanel::RunCommand(client, na->nc->display, na->nc, "NickServ", "nickserv/confirm", params, replacements); + + TemplateFileServer page("nickserv/confirm.html"); + + page.Serve(server, page_name, client, message, reply, replacements); + return true; +} diff --git a/modules/webcpanel/pages/nickserv/confirm.h b/modules/webcpanel/pages/nickserv/confirm.h new file mode 100644 index 0000000..6b0744a --- /dev/null +++ b/modules/webcpanel/pages/nickserv/confirm.h @@ -0,0 +1,24 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace NickServ +{ + +class Confirm : public WebPanelProtectedPage +{ + public: + Confirm(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; +}; + +} + +} diff --git a/modules/webcpanel/pages/nickserv/info.cpp b/modules/webcpanel/pages/nickserv/info.cpp new file mode 100644 index 0000000..c03320c --- /dev/null +++ b/modules/webcpanel/pages/nickserv/info.cpp @@ -0,0 +1,117 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" + +WebCPanel::NickServ::Info::Info(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage(cat, u) +{ +} + +bool WebCPanel::NickServ::Info::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + if (message.post_data.empty() == false) + { + if (message.post_data.count("email") > 0) + { + if (message.post_data["email"] != na->nc->email) + { + if (!message.post_data["email"].empty() && !Mail::Validate(message.post_data["email"])) + replacements["ERRORS"] = "Invalid email"; + else + { + na->nc->email = message.post_data["email"]; + replacements["MESSAGES"] = "Email updated"; + } + } + } + if (message.post_data.count("greet") > 0) + { + Anope::string *greet = na->nc->GetExt("greet"); + const Anope::string &post_greet = HTTPUtils::URLDecode(message.post_data["greet"].replace_all_cs("+", " ")); + + if (post_greet.empty()) + na->nc->Shrink("greet"); + else if (!greet || post_greet != *greet) + na->nc->Extend("greet", post_greet); + + replacements["MESSAGES"] = "Greet updated"; + } + if (na->nc->HasExt("AUTOOP") != message.post_data.count("autoop")) + { + if (!na->nc->HasExt("AUTOOP")) + na->nc->Extend("AUTOOP"); + else + na->nc->Shrink("AUTOOP"); + replacements["MESSAGES"] = "Autoop updated"; + } + if (na->nc->HasExt("NS_PRIVATE") != message.post_data.count("private")) + { + if (!na->nc->HasExt("NS_PRIVATE")) + na->nc->Extend("NS_PRIVATE"); + else + na->nc->Shrink("NS_PRIVATE"); + replacements["MESSAGES"] = "Private updated"; + } + if (na->nc->HasExt("NS_SECURE") != message.post_data.count("secure")) + { + if (!na->nc->HasExt("NS_SECURE")) + na->nc->Extend("NS_SECURE"); + else + na->nc->Shrink("NS_SECURE"); + replacements["MESSAGES"] = "Secure updated"; + } + if (message.post_data["kill"] == "on" && !na->nc->HasExt("KILLPROTECT")) + { + na->nc->Extend("KILLPROTECT"); + na->nc->Shrink("KILL_QUICK"); + replacements["MESSAGES"] = "Kill updated"; + } + else if (message.post_data["kill"] == "quick" && !na->nc->HasExt("KILL_QUICK")) + { + na->nc->Extend("KILLPROTECT"); + na->nc->Extend("KILL_QUICK"); + replacements["MESSAGES"] = "Kill updated"; + } + else if (message.post_data["kill"] == "off" && (na->nc->HasExt("KILLPROTECT") || na->nc->HasExt("KILL_QUICK"))) + { + na->nc->Shrink("KILLPROTECT"); + na->nc->Shrink("KILL_QUICK"); + replacements["MESSAGES"] = "Kill updated"; + } + } + + replacements["DISPLAY"] = na->nc->display; + if (na->nc->email.empty() == false) + replacements["EMAIL"] = na->nc->email; + replacements["TIME_REGISTERED"] = Anope::strftime(na->time_registered, na->nc); + if (na->HasVhost()) + { + if (na->GetVhostIdent().empty() == false) + replacements["VHOST"] = na->GetVhostIdent() + "@" + na->GetVhostHost(); + else + replacements["VHOST"] = na->GetVhostHost(); + } + Anope::string *greet = na->nc->GetExt("greet"); + if (greet) + replacements["GREET"] = *greet; + if (na->nc->HasExt("AUTOOP")) + replacements["AUTOOP"]; + if (na->nc->HasExt("NS_PRIVATE")) + replacements["PRIVATE"]; + if (na->nc->HasExt("NS_SECURE")) + replacements["SECURE"]; + if (na->nc->HasExt("KILLPROTECT")) + replacements["KILL_ON"]; + if (na->nc->HasExt("KILL_QUICK")) + replacements["KILL_QUICK"]; + if (!na->nc->HasExt("KILLPROTECT") && !na->nc->HasExt("KILL_QUICK")) + replacements["KILL_OFF"]; + + TemplateFileServer page("nickserv/info.html"); + page.Serve(server, page_name, client, message, reply, replacements); + return true; +} diff --git a/modules/webcpanel/pages/nickserv/info.h b/modules/webcpanel/pages/nickserv/info.h new file mode 100644 index 0000000..59df1ea --- /dev/null +++ b/modules/webcpanel/pages/nickserv/info.h @@ -0,0 +1,24 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace NickServ +{ + +class Info : public WebPanelProtectedPage +{ + public: + Info(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; +}; + +} + +} diff --git a/modules/webcpanel/pages/operserv/akill.cpp b/modules/webcpanel/pages/operserv/akill.cpp new file mode 100644 index 0000000..c148315 --- /dev/null +++ b/modules/webcpanel/pages/operserv/akill.cpp @@ -0,0 +1,63 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../../webcpanel.h" + +WebCPanel::OperServ::Akill::Akill(const Anope::string &cat, const Anope::string &u) : WebPanelProtectedPage(cat, u) +{ +} + +bool WebCPanel::OperServ::Akill::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, NickAlias *na, TemplateFileServer::Replacements &replacements) +{ + + static ServiceReference akills("XLineManager","xlinemanager/sgline"); + + if (!na->nc->o || !na->nc->o->ot->HasCommand("operserv/akill")) + { + replacements["NOACCESS"]; + } + else + { + if (akills->GetCount() == 0) + replacements["AKILLS"] = "No Akills to display."; + + if (message.post_data.count("mask") > 0 && message.post_data.count("expiry") > 0 && message.post_data.count("reason") > 0) + { + std::vector params; + std::stringstream cmdstr; + params.push_back("ADD"); + cmdstr << "+" << HTTPUtils::URLDecode(message.post_data["expiry"]); + cmdstr << " " << HTTPUtils::URLDecode(message.post_data["mask"]); + cmdstr << " " << HTTPUtils::URLDecode(message.post_data["reason"]); + params.push_back(cmdstr.str()); + WebPanel::RunCommand(client, na->nc->display, na->nc, "OperServ", "operserv/akill", params, replacements); + } + + if (message.get_data["del"] == "1" && message.get_data.count("number") > 0) + { + std::vector params; + params.push_back("DEL"); + params.push_back(HTTPUtils::URLDecode(message.get_data["number"])); + WebPanel::RunCommand(client, na->nc->display, na->nc, "OperServ", "operserv/akill", params, replacements); + } + + for (unsigned i = 0, end = akills->GetCount(); i < end; ++i) + { + const XLine *x = akills->GetEntry(i); + replacements["NUMBER"] = stringify(i + 1); + replacements["HOST"] = x->mask; + replacements["SETTER"] = x->by; + replacements["TIME"] = Anope::strftime(x->created, NULL, true); + replacements["EXPIRE"] = Anope::Expires(x->expires, na->nc); + replacements["REASON"] = x->reason; + } + } + + TemplateFileServer page("operserv/akill.html"); + page.Serve(server, page_name, client, message, reply, replacements); + return true; +} diff --git a/modules/webcpanel/pages/operserv/akill.h b/modules/webcpanel/pages/operserv/akill.h new file mode 100644 index 0000000..ca1d330 --- /dev/null +++ b/modules/webcpanel/pages/operserv/akill.h @@ -0,0 +1,24 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +namespace WebCPanel +{ + +namespace OperServ +{ + +class Akill : public WebPanelProtectedPage +{ + public: + Akill(const Anope::string &cat, const Anope::string &u); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) anope_override; +}; + +} + +} diff --git a/modules/webcpanel/pages/register.cpp b/modules/webcpanel/pages/register.cpp new file mode 100644 index 0000000..29b37d6 --- /dev/null +++ b/modules/webcpanel/pages/register.cpp @@ -0,0 +1,23 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "../webcpanel.h" + +bool WebCPanel::Register::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply) +{ + TemplateFileServer::Replacements replacements; + + replacements["TITLE"] = page_title; + + if (Config->GetModule("nickserv")->Get("forceemail", "yes")) + replacements["FORCE_EMAIL"] = "yes"; + + TemplateFileServer page("register.html"); + + page.Serve(server, page_name, client, message, reply, replacements); + return true; +} diff --git a/modules/webcpanel/pages/register.h b/modules/webcpanel/pages/register.h new file mode 100644 index 0000000..d20c7ea --- /dev/null +++ b/modules/webcpanel/pages/register.h @@ -0,0 +1,21 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "modules/httpd.h" + +namespace WebCPanel +{ + +class Register : public WebPanelPage +{ + public: + Register(const Anope::string &u) : WebPanelPage(u) { } + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &) anope_override; +}; + +} diff --git a/modules/webcpanel/static_fileserver.cpp b/modules/webcpanel/static_fileserver.cpp new file mode 100644 index 0000000..d54144a --- /dev/null +++ b/modules/webcpanel/static_fileserver.cpp @@ -0,0 +1,41 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "webcpanel.h" +#include +#include + +#include +#include +#include + +StaticFileServer::StaticFileServer(const Anope::string &f_n, const Anope::string &u, const Anope::string &c_t) : HTTPPage(u, c_t), file_name(f_n) +{ +} + +bool StaticFileServer::OnRequest(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply) +{ + int fd = open((template_base + "/" + this->file_name).c_str(), O_RDONLY); + if (fd < 0) + { + Log(LOG_NORMAL, "httpd") << "Error serving file " << page_name << " (" << (template_base + "/" + this->file_name) << "): " << strerror(errno); + + client->SendError(HTTP_PAGE_NOT_FOUND, "Page not found"); + return true; + } + + reply.content_type = this->GetContentType(); + reply.headers["Cache-Control"] = "public"; + + int i; + char buffer[BUFSIZE]; + while ((i = read(fd, buffer, sizeof(buffer))) > 0) + reply.Write(buffer, i); + + close(fd); + return true; +} diff --git a/modules/webcpanel/static_fileserver.h b/modules/webcpanel/static_fileserver.h new file mode 100644 index 0000000..60f0c0c --- /dev/null +++ b/modules/webcpanel/static_fileserver.h @@ -0,0 +1,18 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "modules/httpd.h" + +/* A basic file server. Used for serving static content on disk. */ +class StaticFileServer : public HTTPPage +{ + Anope::string file_name; + public: + StaticFileServer(const Anope::string &f_n, const Anope::string &u, const Anope::string &c_t); + + bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &) anope_override; +}; diff --git a/modules/webcpanel/template_fileserver.cpp b/modules/webcpanel/template_fileserver.cpp new file mode 100644 index 0000000..5a96db2 --- /dev/null +++ b/modules/webcpanel/template_fileserver.cpp @@ -0,0 +1,267 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "webcpanel.h" +#include +#include +#include + +#include +#include +#include + +struct ForLoop +{ + static std::vector Stack; + + size_t start; /* Index of start of this loop */ + std::vector vars; /* User defined variables */ + typedef std::pair range; + std::vector ranges; /* iterator ranges for each variable */ + + ForLoop(size_t s, TemplateFileServer::Replacements &r, const std::vector &v, const std::vector &r_names) : start(s), vars(v) + { + for (unsigned i = 0; i < r_names.size(); ++i) + ranges.push_back(r.equal_range(r_names[i])); + } + + void increment(const TemplateFileServer::Replacements &r) + { + for (unsigned i = 0; i < ranges.size(); ++i) + { + range &ra = ranges[i]; + + if (ra.first != r.end() && ra.first != ra.second) + ++ra.first; + } + } + + bool finished(const TemplateFileServer::Replacements &r) const + { + for (unsigned i = 0; i < ranges.size(); ++i) + { + const range &ra = ranges[i]; + + if (ra.first != r.end() && ra.first != ra.second) + return false; + } + + return true; + } +}; +std::vector ForLoop::Stack; + +std::stack IfStack; + +static Anope::string FindReplacement(const TemplateFileServer::Replacements &r, const Anope::string &key) +{ + /* Search first through for loop stack then global replacements */ + for (unsigned i = ForLoop::Stack.size(); i > 0; --i) + { + ForLoop &fl = ForLoop::Stack[i - 1]; + + for (unsigned j = 0; j < fl.vars.size(); ++j) + { + const Anope::string &var_name = fl.vars[j]; + + if (key == var_name) + { + const ForLoop::range &range = fl.ranges[j]; + + if (range.first != r.end() && range.first != range.second) + { + return range.first->second; + } + } + } + } + + TemplateFileServer::Replacements::const_iterator it = r.find(key); + if (it != r.end()) + return it->second; + return ""; +} + +TemplateFileServer::TemplateFileServer(const Anope::string &f_n) : file_name(f_n) +{ +} + +void TemplateFileServer::Serve(HTTPProvider *server, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply, Replacements &r) +{ + int fd = open((template_base + "/" + this->file_name).c_str(), O_RDONLY); + if (fd < 0) + { + Log(LOG_NORMAL, "httpd") << "Error serving file " << page_name << " (" << (template_base + "/" + this->file_name) << "): " << strerror(errno); + + client->SendError(HTTP_PAGE_NOT_FOUND, "Page not found"); + return; + } + + Anope::string buf; + + int i; + char buffer[BUFSIZE]; + while ((i = read(fd, buffer, sizeof(buffer) - 1)) > 0) + { + buffer[i] = 0; + buf += buffer; + } + + close(fd); + + Anope::string finished; + + bool escaped = false; + for (unsigned j = 0; j < buf.length(); ++j) + { + if (buf[j] == '\\' && j + 1 < buf.length() && (buf[j + 1] == '{' || buf[j + 1] == '}')) + escaped = true; + else if (buf[j] == '{' && !escaped) + { + size_t f = buf.substr(j).find('}'); + if (f == Anope::string::npos) + break; + const Anope::string &content = buf.substr(j + 1, f - 1); + + if (content.find("IF ") == 0) + { + std::vector tokens; + spacesepstream(content).GetTokens(tokens); + + if (tokens.size() == 4 && tokens[1] == "EQ") + { + Anope::string first = FindReplacement(r, tokens[2]), second = FindReplacement(r, tokens[3]); + if (first.empty()) + first = tokens[2]; + if (second.empty()) + second = tokens[3]; + + bool stackok = IfStack.empty() || IfStack.top(); + IfStack.push(stackok && first == second); + } + else if (tokens.size() == 3 && tokens[1] == "EXISTS") + { + bool stackok = IfStack.empty() || IfStack.top(); + IfStack.push(stackok && r.count(tokens[2]) > 0); + } + else + Log() << "Invalid IF in web template " << this->file_name; + } + else if (content == "ELSE") + { + if (IfStack.empty()) + Log() << "Invalid ELSE with no stack in web template" << this->file_name; + else + { + bool old = IfStack.top(); + IfStack.pop(); // Pop off previous if() + bool stackok = IfStack.empty() || IfStack.top(); + IfStack.push(stackok && !old); // Push back the opposite of what was popped + } + } + else if (content == "END IF") + { + if (IfStack.empty()) + Log() << "END IF with empty stack?"; + else + IfStack.pop(); + } + else if (content.find("FOR ") == 0) + { + std::vector tokens; + spacesepstream(content).GetTokens(tokens); + + if (tokens.size() != 4 || tokens[2] != "IN") + Log() << "Invalid FOR in web template " << this->file_name; + else + { + std::vector temp_variables, real_variables; + commasepstream(tokens[1]).GetTokens(temp_variables); + commasepstream(tokens[3]).GetTokens(real_variables); + + if (temp_variables.size() != real_variables.size()) + Log() << "Invalid FOR in web template " << this->file_name << " variable mismatch"; + else + ForLoop::Stack.push_back(ForLoop(j + f, r, temp_variables, real_variables)); + } + } + else if (content == "END FOR") + { + if (ForLoop::Stack.empty()) + Log() << "END FOR with empty stack?"; + else + { + ForLoop &fl = ForLoop::Stack.back(); + if (fl.finished(r)) + ForLoop::Stack.pop_back(); + else + { + fl.increment(r); + if (fl.finished(r)) + ForLoop::Stack.pop_back(); + else + { + j = fl.start; // Move pointer back to start of the loop + continue; // To prevent skipping over this block which doesn't exist anymore + } + } + } + } + else if (content.find("INCLUDE ") == 0) + { + std::vector tokens; + spacesepstream(content).GetTokens(tokens); + + if (tokens.size() != 2) + Log() << "Invalid INCLUDE in web template " << this->file_name; + else + { + if (!finished.empty()) + { + reply.Write(finished); // Write out what we have currently so we insert this files contents here + finished.clear(); + } + + TemplateFileServer tfs(tokens[1]); + tfs.Serve(server, page_name, client, message, reply, r); + } + } + else + { + // If the if stack is empty or we are in a true statement + bool ifok = IfStack.empty() || IfStack.top(); + bool forok = ForLoop::Stack.empty() || !ForLoop::Stack.back().finished(r); + + if (ifok && forok) + { + Anope::string replacement = FindReplacement(r, content.substr(0, f - 1)); + + // htmlescape all text replaced onto the page + replacement = HTTPUtils::Escape(replacement); + + finished += replacement; + } + } + + j += f; // Skip over this whole block + } + else + { + escaped = false; + + // If the if stack is empty or we are in a true statement + bool ifok = IfStack.empty() || IfStack.top(); + bool forok = ForLoop::Stack.empty() || !ForLoop::Stack.back().finished(r); + + if (ifok && forok) + finished += buf[j]; + } + } + + if (!finished.empty()) + reply.Write(finished); +} diff --git a/modules/webcpanel/template_fileserver.h b/modules/webcpanel/template_fileserver.h new file mode 100644 index 0000000..f7ad3f7 --- /dev/null +++ b/modules/webcpanel/template_fileserver.h @@ -0,0 +1,26 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "modules/httpd.h" + +/* A basic file server. Used for serving non-static non-binary content on disk. */ +class TemplateFileServer +{ + Anope::string file_name; + public: + struct Replacements : std::multimap + { + Anope::string& operator[](const Anope::string &key) + { + return insert(std::make_pair(key, ""))->second; + } + }; + + TemplateFileServer(const Anope::string &f_n); + + void Serve(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, Replacements &); +}; diff --git a/modules/webcpanel/templates/default/chanserv/access.html b/modules/webcpanel/templates/default/chanserv/access.html new file mode 100644 index 0000000..c50434f --- /dev/null +++ b/modules/webcpanel/templates/default/chanserv/access.html @@ -0,0 +1,77 @@ +{INCLUDE header.html} +{INCLUDE chanserv/chanlist.html} +
Access List
+
+ {FOR M IN MESSAGES} +
+ {M}
+
+ {END FOR} + + {IF EQ ACCESS_LIST YES} + {IF EXISTS ACCESSES} + + + + + + + + + + + {FOR MASK,ACCESS,CREATOR IN MASKS,ACCESSES,CREATORS} + + + + + {IF EQ ACCESS_CHANGE YES} + + {ELSE} + + {END IF} + + {END FOR} + +
MaskAccessCreator
{MASK}{ACCESS}{CREATOR}Delete
+ {ELSE} + Access list is empty. + {END IF} + +
+ + {IF EQ ACCESS_CHANGE YES} +

Add an access entry

+
+
+ +
+ +
+
+
+ +
+ +
+
+
+ +
+ +
+
+
+
+ +
+
+
+ {END IF} + {END IF} +
+{INCLUDE footer.html} diff --git a/modules/webcpanel/templates/default/chanserv/akick.html b/modules/webcpanel/templates/default/chanserv/akick.html new file mode 100644 index 0000000..ddfea54 --- /dev/null +++ b/modules/webcpanel/templates/default/chanserv/akick.html @@ -0,0 +1,61 @@ +{INCLUDE header.html} +{INCLUDE chanserv/chanlist.html} +
Akick List
+
+ {FOR M IN MESSAGES} +
+ {M}
+
+ {END FOR} + + {IF EQ AKICK YES} + {IF EXISTS MASKS} + + + + + + + + + + + {FOR MASK,REASON,CREATOR IN MASKS,REASONS,CREATORS} + + + + + + + {END FOR} + +
MaskReasonCreator
{MASK}{REASON}{CREATOR}Delete
+ {ELSE} + Akick list is empty. + {END IF} + +
+ +

Add an akick entry

+
+
+ +
+ +
+
+
+ +
+ +
+
+
+
+ +
+
+
+ {END IF} +
+{INCLUDE footer.html} diff --git a/modules/webcpanel/templates/default/chanserv/chanlist.html b/modules/webcpanel/templates/default/chanserv/chanlist.html new file mode 100644 index 0000000..8f00f02 --- /dev/null +++ b/modules/webcpanel/templates/default/chanserv/chanlist.html @@ -0,0 +1,17 @@ +
Channels you have access in
+
+ {IF EXISTS CHANNEL_NAMES} +
+

Choose a channel to access it's Settings, Access or Akick pages.

+ {FOR CH,ECH IN CHANNEL_NAMES,ESCAPED_CHANNEL_NAMES} + {IF EQ PAGE_NAME /chanserv/info} + {CH} + {ELSE} + {CH} + {END IF} + {END FOR} +
+ {ELSE} + You don't have access in any channels.
+ {END IF} +
diff --git a/modules/webcpanel/templates/default/chanserv/drop.html b/modules/webcpanel/templates/default/chanserv/drop.html new file mode 100644 index 0000000..c28eb05 --- /dev/null +++ b/modules/webcpanel/templates/default/chanserv/drop.html @@ -0,0 +1,32 @@ +{INCLUDE header.html} +{INCLUDE chanserv/chanlist.html} +
Channels you can drop
+
+ {FOR M IN MESSAGES} +
+ {M}
+
+ {END FOR} + + {IF EXISTS CHANNEL_DROP} +
+

Drop Channel {CHANNEL_DROP}?

+
+ + +
+ +
+ +
+
+
+
+ +
+
+
+
+ {END IF} +
+{INCLUDE footer.html} \ No newline at end of file diff --git a/modules/webcpanel/templates/default/chanserv/main.html b/modules/webcpanel/templates/default/chanserv/main.html new file mode 100644 index 0000000..e77626f --- /dev/null +++ b/modules/webcpanel/templates/default/chanserv/main.html @@ -0,0 +1,3 @@ +{INCLUDE header.html} +{INCLUDE chanserv/chanlist.html} +{INCLUDE footer.html} diff --git a/modules/webcpanel/templates/default/chanserv/modes.html b/modules/webcpanel/templates/default/chanserv/modes.html new file mode 100644 index 0000000..3c7fe7a --- /dev/null +++ b/modules/webcpanel/templates/default/chanserv/modes.html @@ -0,0 +1,56 @@ +{INCLUDE header.html} +{INCLUDE chanserv/chanlist.html} +
Channel Mode List
+
+ {FOR M IN MESSAGES} +
+ {M}
+
+ {END FOR} + + {IF EQ MODE YES} + {FOR LM IN LISTMODES} + +{LM} + {END FOR} +
+ + {IF EXISTS MASKS} + + + + + + + + + {FOR MASK IN MASKS} + + + + + {END FOR} + +
Mask
{MASK}Delete
+ {ELSE} + Nothing to display. + {END IF} + +
+ +

Set a new mode

+
+
+ +
+ +
+
+
+
+ +
+
+
+ {END IF} +
+{INCLUDE footer.html} diff --git a/modules/webcpanel/templates/default/chanserv/set.html b/modules/webcpanel/templates/default/chanserv/set.html new file mode 100644 index 0000000..9437ca7 --- /dev/null +++ b/modules/webcpanel/templates/default/chanserv/set.html @@ -0,0 +1,93 @@ +{INCLUDE header.html} +{INCLUDE chanserv/chanlist.html} +
Channel Information
+
+ {FOR M IN MESSAGES} +
+ {M}
+
+ {END FOR} + + {IF EXISTS OKAY} + {IF EXISTS CAN_SET} +
+ {END IF} + + + + + + {IF EXISTS FOUNDER} + + + + + {END IF} + {IF EXISTS SUCCESSOR} + + + + + {END IF} + + + + + + + + + {IF EXISTS LAST_TOPIC} + + + + + + + + + {END IF} + {IF EXISTS CAN_SET} + + + + + + + + + + + + + + + + + + + + + + + + + + + + + {IF EXISTS CAN_SET} + + + + + {END IF} + {END IF} +
Channel Name{CHANNEL}
Founder{FOUNDER}
Successor{SUCCESSOR}
Time registered{TIME_REGISTERED}
Last used{LAST_USED}
Last topic{LAST_TOPIC}
Set by{LAST_TOPIC_SETTER}
Keep topic
Peace
Private
Restricted
Secure
Secure Ops
Topic Lock
+ + {IF EXISTS CAN_SET} +
+ {END IF} + {END IF} +
+{INCLUDE footer.html} diff --git a/modules/webcpanel/templates/default/confirm.html b/modules/webcpanel/templates/default/confirm.html new file mode 100644 index 0000000..11aa668 --- /dev/null +++ b/modules/webcpanel/templates/default/confirm.html @@ -0,0 +1,51 @@ + + + + + + + + + + + + + {TITLE} + + +
+
+
+ + + + Back Home + +

Register

+ + {IF EXISTS MESSAGES} +
+ {FOR M IN MESSAGES} + {M}
+ {END FOR} +
+ {END IF} + + Retry +
+
+ +
+
+
+ +
+
+
+ + + + + diff --git a/modules/webcpanel/templates/default/cubes.png b/modules/webcpanel/templates/default/cubes.png new file mode 100644 index 0000000000000000000000000000000000000000..d75208db7da913970c6612617de1e365b6f4b6a5 GIT binary patch literal 723 zcmV;^0xbQBP)b-r>0000UP)t-s^Yioc z^z`lR?eg;S@bK{L?CkFD?(gsK@$vEX_4NpY!%6@E0&q!0K~#9!?U#XW>o5pKuff6a z|35rYhtgzo>ZFt2n-oi1mCQZ9+<}dOayUTccraBgQgNAqDk1_@p{B6s>lp@C05vWK ztTca^(2_6_G~sjC8g!6V$Cq!n7ZVasaKKR_=e8U}PrnHa{GLDIE#e=cz$k zV1^8{mp#EBlactylK}(pl|=bX%{6H}V8BzeMhV(M?Z?C|!@5e&YA!av2Nj^$cHc1n zF&r`q&?NUlX!vw?Uq@&MT|65yCIRr-8Ks#sml=i9$?J@aQ}H*^R-W0>DCDqm)ppM)Y++ak5Uv9k<#r_6|Zfa0tUXr=5XqA|n?23L}XajQ3G z=?P?pd%W3oeUh_l5${Yjg|tKr4DXk!sO6KREq(f;n-9+ z9QMcjACd)$_e)G zgbvGew(4E`@qXGUtbb;Lo!-~MmE67+fYWC~TC+%F zH{Gr<&=Z_yxB^$?yWVYbc!rD%A(fhvSGHZPouSIfCLDNh(Pcvf{c(* z837_8;0u|Vp{W@nDpRNA<@^9;D1@I==eL52yq)tr&nxiC)dhd;_PU>QpL74txz8uQ zKrj9`Vg&f>iqd|-002XHvk33-7WwzBC843n2?)U2g$rSenuf2^=AbGk4gV@wfF1c6 z_~+tuR4kl_RdZsI8yJ9!{Cs?sm4*C}U^H%6hNBgw_%bB{xj{k52@FI7%L>9murxdr zb*l?dl{+7wTVqhWY6VjPaFFT&RBG_>8i zh3zX=u+2c!tjt5vw5eDY9gQtnsi@3M!KJfj(Q@SqR;8q%FftNtZEeU44#r~MH(FY- zZqXuaNS}+H97Fw=OVLzb!oCGyWl|EBTdg=$_Awgv>_Ow#HhlJeH0stAU|U`~%0EoP zp7rZd8XbvGW25ljBS&!M+&L6a4@YrS6pkM}2s^)3Sx|sR)^ELW11An0Li6Rz*tj4W z^*eW>n0-Cn*a%xp47PFZN|;_|8|zYMqiJI)$5_lUet@ku8cT~+ zUt5TqY;zOaKY!{J%I3!5llXX?J8=S~GpFMk=j(Hh`Rm+V5l+cXp zXRzCrg$?r)@ol*c|1Ql&>&=@e3=hMuvNCKbD#96lr*8Xp96fLV*RNf}t=3kQXC%Qk zYZeM3B5-)uE-Ynw?czo3DftLrq^9DNm`JRMn~DE$Y->}jSecxRva~dm#KyulBLc^2 zYq4)dF3Q=bHOcX)t*YW$Ou@#yJe0)6p}Hs&x7d%Ct5>lmJsq34e(N$barMFlY{<^W zsrq{El`!o4G#3X~<)a`x9Gkh$%M%i~c7@-2*AchBqC&5;w$mSW4K9c^F9+3P? zt!1ucR-}hz?z+9)yN%R=7U~h6ruGOw($l9WcyH3Qp5TYP)f4<5S`M_c|I5h3)_&L3sZ+gZRB>0Bj7&XgbUYqBpM41$&X%r&pN9PlzGyRar!Z(lb1CI7%_7$Z@vM@#c zU7IAasyL$5i6qDAA2?>F-5u?@IUy>M<|>u+*5hPJ=H$#~E9{!+5|5$Xj%kKlY~;_op_I+DM|(VsrT5SknxNPl@Yb@LH$j4sI&cd{yLst z=DSIgwR?$1@bTS%djgrfsXV&Cdo$Xd-tbc7q4~eP-u$SBFgOh}Z6YX@VPz2feKRs8{#}rT#pDb)Mn88bkaF%?#~wE?wPC~f1zy8{(bpmBO!aw$ z@!x^m{OnPI|9l7y?Tj-yPqxl$@NJKJKlCv7x=r+}i($I%75NzB_(x^dh?JhrL}~U0q!C zj~rb2b9bK~^(DH;NKNN2t8}@3&=JPJf$a88kl#Xf`!fb@Gij?yTbyX4$vbGJ$y-ed zgSP3^%C9lsCXX_0HED}U8-+duR0?%#r&i%zfKJrm`TvpX{_y(_zbe72gWrw9b37M> Wa=dz+31-}O&M%9532kIGrr!Z3+e7pK literal 0 HcmV?d00001 diff --git a/modules/webcpanel/templates/default/footer.html b/modules/webcpanel/templates/default/footer.html new file mode 100644 index 0000000..6b1bc3f --- /dev/null +++ b/modules/webcpanel/templates/default/footer.html @@ -0,0 +1,14 @@ +
+ + + +
+
+ +
+
+ + + diff --git a/modules/webcpanel/templates/default/header.html b/modules/webcpanel/templates/default/header.html new file mode 100644 index 0000000..0ccf477 --- /dev/null +++ b/modules/webcpanel/templates/default/header.html @@ -0,0 +1,64 @@ + + + + + + + + + + + + + + + + + + {TITLE} + + +
+ + +
+
+ +
+ +
+
diff --git a/modules/webcpanel/templates/default/hostserv/request.html b/modules/webcpanel/templates/default/hostserv/request.html new file mode 100644 index 0000000..f557244 --- /dev/null +++ b/modules/webcpanel/templates/default/hostserv/request.html @@ -0,0 +1,45 @@ +{INCLUDE header.html} +
vHost Information
+
+ {FOR M IN MESSAGES} +
+ {M}
+
+ {END FOR} + + + + + + + + + {IF EXISTS CAN_REQUEST} + + + + + + + + {ELSE} + + + + {END IF} + +
Your current vHost: + {IF EXISTS VHOST} + {VHOST} + {ELSE} + None + {END IF} +
+ {IF EXISTS VHOST} + Request a new vHost + {ELSE} + Request a vHost + {END IF} +
vHost requests are disabled on this network.
+
+{INCLUDE footer.html} diff --git a/modules/webcpanel/templates/default/login.html b/modules/webcpanel/templates/default/login.html new file mode 100644 index 0000000..2b735cf --- /dev/null +++ b/modules/webcpanel/templates/default/login.html @@ -0,0 +1,55 @@ + + + + + + + + + + + + + {TITLE} + + +
+
+
+ + + + +

Login to continue

+ + {IF EXISTS INVALID_LOGIN} +
+ {INVALID_LOGIN} +
+ {END IF} + + +
+
+ +
+
+
+ +
+
+
+ + + + + diff --git a/modules/webcpanel/templates/default/logo.png b/modules/webcpanel/templates/default/logo.png new file mode 100644 index 0000000000000000000000000000000000000000..f7c2ff92a6e3064da02bce89ee9eb59384ba2592 GIT binary patch literal 19247 zcmX`T1ymeO7cGi=a0%}2?(Uut+}+*X3GTrmd^iMmcN^Rx_z*0(yWP(J-o3rnzyLGT z)zzoY*?XT|M1N6{{e(n-1OWl@NnTD$4FUo(33#4_00(@f0SS8p-(cJ%{t&6K4w+Cs(VS zb0Go<2r>wHDRFi0+|xWSe?6=2wtUJlLC>z;EWW|4md5o`eC2r_hXUqVp4n^U-B1hY zeGVABwm7HK;CvM%n^ep?UC%=s5jj^fzT*#A5HrMZ^~zx+Egv*@6t#DT*^|NlL)F7<^z2hD6V zL$HetWNHba3q|PVFieW!&GH;9)vO$5mAaZCAt7C;h97~YW@fgDq3z*XpmKuS#fTQP z`;;lA{v))8OMs;AgX|W$7*}^x5EtJWu~LAM3w%H4Ge&kMOqm7Au$MjM2!J7qph|pg zTZ{ht&$)=*28v2F$cwEG>yg5llT2xR0Eu!DsxxHMH^A^k-AM)*;{ld4WJ-RoA8Hbs zKZ#t5TfA;H4INh|ILSCvLbAA)ydNe~!ARryA-{nlhE2%a+H_c?}IK_v2W1Z#TPyT1}pEgqLL{Qdvv|jWC9B4 zr=$6IIJhInv*OC;u=8b=XTRq?eNTu-=F0}dd@IybR2*z ztYUH+dP9uQkVA(5xpRB5&8}S7cr#xL12a;a+9V7M8$k%si-=yCxa-%~>Wn3f!|sP` zlZ8(;r7B&m`C?%J>*LPVJm*~SJ)x9Gb^L*T_mic-m=7z*k&#Rn?9~nj(}q1#~8!>hYb0x?0;`HlYkof$Sj;pC=9<$4(i8cT#- zT(YO9PA$kF*oKjxImD!c4LNQIiE)|Wdu*uqRr5c8ju>h*SK0+OKfQJWr)-tq`rl}c z_5U}$Q+KR2!^Ny)V(34(60@YN6a_U#$MH`Iojsl_eFL^?Y5i1z*jgaW zhm8{4DX=EyByAj)~904j;lbPC~zR+WX&b`^w`CN`( z5?ZAPLpq9%j_!97v)Be=B2H@!4ZDG6sE-&1GsQ}0M;0;Ou6xaGAG-wQK(wMfnWah> zrUX-1$X1}rSx_Rm6?`X!6mYQ+Sy1Kz$Y`QP)JRc}3T?=QPGLulKgxG`Jxl}? zmlI2i7Bvk^JDQNv6#7hE-VLp!Wij(pA2P`90$G5C7Ny0(!x6fU?rKbOz3TS=} z#GnZ-OcLB!IWrIDi*DV4r(G-jQ&KT>GHPiK1B31j(0>N23HKwG5X)6MeX2nnu?C$j zb*}qDptG2@iC{T?vd@Gp^Hr|p3vwyxxor0Qb|4(_L_WIcIk=2uTQV9n>l5s zqChNtOQij@XC-zF%K0zJ7*}vxj3zA(C)T>cK?++Mmr1TEt6HY*tYu%nZC1+NoljnV zPD(nWNV5_F8JUJ_vA)pXXd8WLi5Y^bn1-*~g6OkE$=4!8wT|P2q#wx&Zf6<-vdA1r z!Q?;&QRo(#u@J`ox3=*zyhec$=s{M$)eqaHV`2ZPua@mYOhlojr%Wql{B*jmHSW+_ zO-5yYtA~K3b`!yRn#8>lfvn6^=DV;j^GEFf9h)fJ#W*V4ZArhn#%$|4Vsd621@yr2 zO{aq;w#bQS$iAT&O$WuF^l_$QJ?-Cof~Ujp>`ry3M@pzvDvri~wol+f%r0=s$;%J7 z9qKgOk_dWM!4wa*V>$IqM0`8+eptdJU|BY<*S2nR9yS~>0*>(gFZ8y_Ij@=$(;VbQT%hdk+ zjHFZ)6hFYmpS(7kV@N+9F?bw*95}W)>&!{$vx%;cH9d?0cR+y(n3@*^c+!7s5*@sI zKbmq_rhNQe#@f!h`K`CNETiL>;rdHeRlCq5c*?Q%?D)8-u<)m1Ms`#b0yPay=;I@u zW=(Fa!afrxCui!@eXFR1T+~SE(ni38Eh?$VOx>K+U<3h&Ce!t<7w=89d>kd0&|*)9 z99$g^-Opdb^mKGeEM|FsNuf+-x1>gMc}pJ`D;HduefJUVjuk+w89Hz(=pilTew znGr!qNFd<-d<4C?)ZCftHl1rt;(tk_Su^P@fJb`q7%(zC^=DZR&+YFQ9FN1=q#i2h zW|?RZfjBx$3dejozt`CNW!YDlDByzOBGqVsWW5b>PU6$+eTFp8aj5)Usx(Nm<#VOX zgqy4yV9VIL)$uuaWJG0PFf2McYu|k;8f!`D?G`dlW^AKatrAF;@vHWh*2c31*s_|M z0*NBN8Hx@=KNAv2dLFuijCu65lNvMQ_TN_|CTTcr;}8ENSir0Phd7U(ks_z>3Y85e z>%A}&imT>?yM>eoYItpqA~rVB>@ms&fD~fx(xMhMpBQGX-*gSNlPZ5Fmyx%~9s_rb zKA0I!vqVi*Q4lvaicF681w-wdnL&c6cU_9rPktCNXKS|D6-$i#l;H82Zts!?;mUK3CLsNIaW<*pL$|JLp%m$yrN% z)@iNr6m%>Pnk|jzUNMwLhq0s`LI)DDzXHY1*XaTG2B5YXd-|iStaZwuN<*MQsj9A) zzD8+U$w8AmTs2Tez_$B}R+GYDKRb^F;o$BW-iu7ytx=psjDMd1dakt{7zTo5xLjgE3b$jg9 zoaJ`+=b409lc_U8zM#U;5k(JdynKuE4VWBHvzem>E$^KOv!)h9=;9Q5cDFy(YXd_t zpeS(L7P&>g(Z%0VuO|vi=}sP;7VZ|lEAsEi6TBU?^Mf@pxs zYLRwEwGodD;-p<12EiHalAg4773EPnm`u9$so`A%yuPb#RTJlt0ELA~rkiI1Sx4Bm zIjV>i%&Kj4*enp%Qb+bMD|K&bf!p&DxX}(yyx*Y=z-1l7X8v_M2qE^I243><1FF%8q&yXDHK zK{s#bMhw3PIkBDzQlUv;uoif@pADmbzZI*IwhfyrUc!GbU&5!^CPg>iKuW5Ms(9MG zbvGE~quYE-v_Vf3rQcN#yyW7nCuH3ZD`^~2*&dbm@ zXS~Q_cdJ!j|82iFvaR|AC|l%{kv#tA)Tex4jJ08YoZ~dWLbP~AxMu%&JvZJ zli>{ISAB=Ujlh+i0FUp{BQA_$dmC}k{a-#H#Fy1hrlvN#o{!~8f?o5naeMZ;TFR`F z3dk!2?ES}yR_&xlN7roiHPjac^Hh~`9X2N(6}$Yfh#IW~?@20H+?FK-ve(ehd^7FW zno#o24FjJhR1253rl)vWDJTY-HK}4K`b~CMGWQCX%SY4O#tzoi4PP+hLB6Sv8Ro>xn1|b;>$mmNr=0BNvbaoG<<4mreia` zVL&a}rJ|BrP4H@V|KfI!nK8lQd=J7ON6Y_n{kfpQ*8>h>XQ#hPuQh4L-%_ymahUe$ zdFA4;rc)CWW5>EjQ7(;DopvB|MnMWFIo@7oR_It5Q0vtMlj_d-OZ-Cn)*jz$A@k8L zIdX!_pt`>Iw&Qzi0JHyy>UsZ5eFPMwFQlQu5UN1NL;v%4u{VtPe>A1>SRo`;5pPcQ5}P@Tm< zP5lqNO=NQ;f0j3CzvyWex?8kf8`{4{c6`YBf$hLqy;=mUB}SBqCg+a#NCjidOzyE{W-^Wty>-p`wrd8XgBO5=C$2LtX z?^*FqR6NW4&o=L`{8jo{;$M;ozJ}YKZK`Kzx*SdNx4OYazzAmM$RuHs zUV!UINleeyzV1LeFDS>#sifmo)!Ax%AHBJ|I|FX@d)%KCECU)nI4HdQj5v86J~8cl z6sJ5e*M%47vT8jeNB~g?$j6qtk&|dP9^b3Kbw@|D6>C-zhg7R`-4hv&O)H32EZ8BGvcxB{F&(K>ZiU*GH;O&BTeS^0#~! zuS}y-gKcd(LifKVfhg(QpVCK%Iqwb1n`nm-7b{UKm@7v_M0Cv(c2d>R$s2rmRG;y? zqh%3c{g#pYhm;2ztGRM}Cow)Q)xLTf{2a!O2m}lod6td8xD=A42+|^iWnxiYG`zcr zAt&)A_l&hJJ97~v6E1RmhHZtgmP0HE6DH(j1wJ~#(|^sN*;XViE#936;F9&rb_ZQ9 z&QSopgW$0TQL(d+pZ!isB7^Uh$i;)i%om6R{a)p9Q<0TrEh%Z{*^XdbuF9G@Yqi3_ z#FSD{K%u9vpUlE?Sg6`lGc>e&=~XD9;2CR|PZwShtStb_KFLvSUnU_^kTqH>kR_uA zLN`P%B%ueag0WJ&%a*`Q%A;&ez1TB zb?@>)V2rAE@6VC+eer#L1x|vnSzz!x@L`mJt0hD7U=7h}-q6&5KwYGyR40;xGQ|$W zN_7Svd+o{YhZ+}55(vE(rrpUb0tQCHHt%04fHZ)4NYk0y+WH~@z!MI8E)48q&zDkPPCO0CjO3!$}}mlYLYw;Q`Vd0Sjw>wwYq%UWb} zdXhM-&s%9z3k(5hIp%ySXsgXq!fyLN5C)lF9plSxsIf8f<#!{`J;6k44>$u8@pE&p zm@Y!?ox#TsCMHmT>8W@n`XjJt_=2(Fm}DvAV6KBnU+Q}F1%O(gGfHG9)}aFpBN3#eCmF%@jwz4yMvn|6y|6w*Q|N$KV<9~r&=X!);uxTaIA-ggIu!)syA1xk-=Vzw1>;4aRW>~rB6rUCjhB6hO-X|HU@XL#jz}6|!c>vE1 z?=0l{pBN-`=_;)jq;eVl8noxYA|~z+dL0eeaE)y&U0w5y7yW1t$D;j(|Cvoqi}yJ5 zez+`&{b1~)c}0cdxx_co&eW9Rak*7wvQSzcbu`D0fWP~LZvP_p&*PStJ+6 z+djc@C{`x3+oD4kfvu60vMgV;A9;*k){JIP9w5=NF(uS)B6zR4_NEGkQDjR%!08Y4)012EUt>H}_=q*u~(QM&{HXYCWYH~E9E9)$Yfui8m3m|zk6g=8`+((yPm-Dfd~c|5Bx zMjjC+yKH{_L;Z(t`-I+&AqBfQb9dVRo-~7;8x*DdW|4kUM@${|Cp%oPa$!*hR2alJV;f!35@$D+U8G zqze>zzuy{lo`b}FMzlT5iJ8ertO?R$$867G5VfKMZz6HbS1yi5Bio7UO)kIMqkb^6 zMtbkr=`4J=VHA^TN}901^FGYGVbW%ce0!Nu`$m~%@~bk(=XS0$k3f92MyoO^Hb+`N z_aSQDDqmPhV@U&oLyMK#M_hndYu(z(zM!aLiTwH3n=SI2aKJwSr{$VMoV-5~rZfte-z2 z#gIbIJ6o*Bvm=%9fQxf2E+tm95;*KhIxR}cxQ{JDs)AW z!SeK{(zUdqAw)8g0kVS2=Q-ucI+SZND`PT7Ppkfk(rZm26y^TYtk+b%*8F8s@w;{y}tZu8;ps4ykE>D8JA(NCp6dCM}Kz2{J_# zeA#O;Zi>Wjt9)tknY# zM953Ye4kt345kyE)~BJ0S<7U zOVy6*25lBU=jzUKpoy*>83drsO3@A_b=!P8@wBI6;ZJ`2!C%$=h6^JeF=k#+Dr2}c z+idrisg#hv{!h%<%7PYCbijHOKJTpe{Edh%9;}>`-f>$E$Y4o1ew|fn6f3o8mwTyB z*GskU5g$+a!bE(|3DYVzXoYn1o0~IfjMcdU9uX^sg2P_DFHBBdF4;Rf(RXDo)e&7m zlnqszAA4LU^@vHp1(E!xKf;}g5x*~w`~>h?XO`jvqx45M&4dGW@GJk&xMAccKLWaS*;^?+u*Jpu_br7o4Pf)pf*KX-%}wc zyfh3Qj&lnc8uV5r=)`(l;(MUZ=!Fs$kNJzQNO$Q{{F5j|qUH%ntcT%3F6V)q$A4Az zzsq4Jir&m^F4Hw+bgwumfrvL;i74gyWV<1AY>}gnJNVouq)G6=ZAtb}mt4RRdv@L}IGWfCD6XazQ_m zqoWkkU+wMdG(rcH$~06$aY>ixEO|ABtzJpITYSnuz43cUcX@l3gVhTeYL}lhs{d_q zvR40&<_Bq-NVIeHdUJ7gkdq)H)hwf|dm!{j4Ks_FbhlXJGkj#5noDx!(jDqfdnBqx zN^){vsq*ei7Zt6bE|2a>&X{+QEqTwgs7%uC?|89!XVk|g%Iznk4dkR|-8}L#01JL` zUlOJ&E*1oAky=M5CG40wu#?$gwwwJe5U|CIChD4oRA z*AL$3X&#j;0{+rj!{U(k0V(!-a^(C|I4~pan}NdZT}7;Hh0pM zynf{htwxO4+zcQRP#^QVke>#(?MdZaLV!TyO$+ES0K9d(f#*r}II&F}C@Qiw26chC4wUEmqBeqd?*O9HD2%VXLJ{FEqLXNQyW5)$pAWh>p zQcl=%-60E?@I8S5H3h?xvIYpEzht3U7Q;cQML9`iFH(QOE+{)8AlA|Y%4kvR3qc_Q z;!y&#f#l#IpnAjt8aE0nL8P$Rl-BC%ZY8SAfzqd?r6M0jjIWKLttL->l}nt~s=dda zL6lnsnzou6k^6JuK}odDKUW>wAAx9RXVdAyQLByGN!{V$O=C7;f>TLuZoRqy?m0Qw z= z!}IpYP&+t8rK3A}lMy6zKN!eDQ!6YS!JH?ZSbT!dh28ZLZRUsDhlLsw!s(h`5#11o zNb_~}S-f@;oVc-|SXKeJOF&3B-@s4@RL}iwad$ofp`!$5%WX+fqWv8{^-hfg6{ z1!~f`9h4~P!VlVjyx&MEL33j2eV)bhdyqu{l@0}XLii%~1WvxmF)YYCfQ)iw{0aKD z74BL`bcT0;RR2eGKKrB`R=OYn2u*mh5D}5dJ?8Wm2|fX2Rh>vg*-e>pP*Ns8BGSbf zRIuGTW`4li>yy{I#ZXox*`s=~(e9g_BU?03h-DhBn)iF*z3Q)AB*zUi^JY`C&-=QP zvWI;^PNM~}JbuN6-cG?1K1ULsqK(aEPXXR{jKkat0Y2_-I+lyzjJP?6LGWK%}q%Vu`khg98l zv$ss0|6Xn}lb3hFCW99Kw#4SNM)pv8uK5oxqVDFBawIp?C}5mZrZ4uDLDiLRpj*Ui zT4hG zBcd+X1-?-X41~5XZ%G3vHlZgliL&;`?85$2v;olQJ;JA26n_x#MBGr3naO~&g52EsEaPX`Pap|9j{jds^ltjqEadazfZT7iW zwdG3am-z#O#53()_14)s@!5CamxZ^4V?nPVWcOq})($<{%2c~FAp0r;^jBQ8<}j8) zFz3q3aK;_d_0yv+K>y3;IkAROl&Y4KDIJ?9@M*;W@d77O)r5$P!_SlNVWTl-DklR_ zNpw26BIf4_bWgI0YIK?vY*k9sDzv-!@EcbpTwGx1uIjBr_uddB1|)&5k}ObwltxT| zhGp@)MEqIT>gkir#w!2w0}eK3oB}hgtvboz$ef>^dz00aOtq)FzzOT3F%bvArKQX# z)ejAo1?-ZvU^NmvU0{6pky0uCW$=F--U$}BOd(ilFN|h||2$TPOXrnX-Wz7k#*q$? z`1ONVAT0lb_*$VpY0wd@X!R?Tmo)?cnD&PUlhFrZr22|Z7ZCFD?BNlx1!@(baRskT zv!O|>oYPDcYa%YwdhIS-cpyPg>=JRdbt5K)gnT7u(PfG%{EIi*ylOsTPAk@R=R?XU z2Iu?ougGLKW+22PP?CF~A|A=JH10Tw?LAYq*m}V6AHY$9tKEKkR!{#&V8yL#uc&SoJ1QG<2Bs{oW3uh@#~&2oW)A@i6MvSnobrm3kI z5YQ>9`3NW}SH9hgKIlMy5HllJPEH%4IW5DcOIy)@jYvo5x0zx(3aaltIg3HIL_qf* zD<@EZ9nYvNr-$?)Q0@icn!Jy@5K<5oOEBxSb6=1@-GBNLRPg;7nY-9x+U#l#2WxAa zOV+VAA?MO4weYhsv-5`PjgM(@UtwkM4MMRi9-L_PekG!v&|_h{QVRq|h$Xmc^F#^= zrz82T(P9ot*eKm18V;J6=>yN0*qQ4w)$xh};TTOn_>Y%fr*FEt6BVtAWHH7(@-&0X z9W)147QP;?iFbKz3>(&}D%1Lrm^5cvdT$hBHO>427iMO{7lQo!+4&!@SU=L2osZQ& zX=uc^NTl2kQB8y1c^c|PrW|t%_b<#bVdPB29b*BZ6K4h%_l;VNAmFngKGaag8;BfF zo-WQ<3R6v3ZcS^O$|E3Ga}oj4^+*ZFpqiMfSRnwkPN?_S-jNn)S)%#(J&f0rlM{%1 zJP~(Y4t%{oW0WjWt9RMOMR|ggWKq+|nnSYpj1q^&XusQAh zr2E$0aM!hcG4D&Y=GD{8g)@>OEC7hVX)MXPx$(};VF0|g&bXf_vO_zR>=GQ-$`%wz zVPkVeMI$o@C>(P|8P*kc6oc`&uGQVK#|<~`tpXxXyxcxDUx3x1T~85@MO)000p0zk z&(hg9kk)g%;{q(+Pm<6@ceSpr2ld7wPGivp1>#JGxu?dVu_{TV`fOoYRkB6;W>Q7lOJo03~+AeStzj(XJf; zJF5Ps$XQtl0b+1)aj$O|7tR3OkSQ|5)^l~`LKAY1{YE~-Z6`B$Jvb=&yC(n^C_HQO z$VX@AJFZW#kqmA3;gNnpncYXF(maq*U-Wd8)lcm)=ks2&y#M)b*4&m_9vIU4pwZ%H zl#C1wBLmd0fA0+u{;0qv>+i!YK5mCB0f1B$&>4dAUzkc#C1XXLUl*9t%_|`ES&MMu zIlMB^;-2Ql_BS5FIt4@G8t`eC#U%4IFlt#|?x1ZCJ@odb=D*qF5%Ms3eqNcMpHdCH z#vDyB7%*=Ex~^g)G1A3Mxf4~HblKS*Pj43wmy?`7*QvH$WO@3@33QLM|F&A%7zunE zs~3*cM@npJ(k2PGWqIEfJ%4!a1~m76fC>{Q2xoaQ%TS^J`EI(&L6iKx9x6$FTt2VlL%d@;5xsL5|OsZ?O-Kwa5$WxoPVtE6?& zO_Fw~Vp3_O#B-#jRf9RuGrWd(Fl;I z$3Hk(?Wf-{fea_-?|_@PLZi9S5%V9I43$J^RPdthJ$GfP84x+BKSwG>70QKi&rk}@ z^K*Gl=dSJ@Y)u2S7oDH~y7DIQwy3qid8d2?z()M_7Y4r)w2X;vb8%Q=D4Gv{0cz%e zxOaHCb=${#bHjsi;+VN7-3bW^{tkD$D-#P07+-6*6vKq}{hgAbmdfi(+0qcs%7^WAE zJ{^mQqLvmbd$dc{mM5n;`7|>cz`9I^t1E$a0w6g}0wMtF;Y@DDj;yF}NKA|XPGpE%p*n3;fc)WRZJr};uU*XE7{%G&fV2D;LA z0az=79RN%nGAAl+c5F)5@>unWWO^(wckX%JNAp%Db02-W(ZVMnz>&GC=*g))ja8ZHj3E9Z;LZ07_sAc8X>C@58>wk+}`|zHZc-44*^U4Db4vtFTd*0tW zr}<4`1`uF001AVq}rPbC}C4fNi_0q{7^ zJaUggdVke`W`;u(+zqE@7GzrIbv&gFfN8FNaiIBpz2PSNIP>BEeZ|PD%4TJOQw%T( znKTY$Q5Rv4f<84A4%EZCNQ7dOTa)ncBP3z~szpf&cgs-U)xUiC{?bc&(DSkk^i}q5 z?s9lp_w9^2jnXgqe6Begjbj(eB}EHz*ky9* zUKsP|Hi@(+n*+=gko^0TC!>@?RX;#Pyjhk^0AhKoAAv|gPnIOOq~?bPXs9LFFzaR+ z7k4jxoT!pb9N^g^vRE_fNe#{{Iijxcm93jf5^KOct1fL|i%MYQWZ%y*5>9JFj!c};eI3&ZRs9pd#?BYrcHXa7iS<4=YLRSaT7ZUY zI+1SS|1?2ryi&t#&9xOvzp~tNRVJGDyRfRp=;H8lhvEG)vfKZzQdRIrR-&@XB|q!F zZ{)Z4i6&e!P_K<@vC5B)twUFC@*oTlR3PQ!_3ejn^|W(i86+SNz;34ylW`1Kr+IX=%xoGMlXn`>59J5Wnv&ZspPJ~)@vxa}5X=P6OG-yDiHXI% zywD_}!wk8T6KLpvF_QP!mzT*D9axF34`*?56A60$<5NdRr=D`8yLN(Q~~I zT88}lU}Spc>V3eA@Wp7mKb?8PdoMX&#iMZp0|!S&UH!9K<$kmYSN7u|={?`0w#0x0 z1_pb_Uq}js&HTGqrm@;7X@%z{B!}gXqpl(c7vim4m!bhbL2GKyDKqjt5BfkUfi4#St-|^${ zmqykt!p&me-yqlXlz}rq*c+Pe{x_E%#-5fLHwa(`u_N&c_b+~(ZqVhY_Vhy!17mI^ zhXjAm%IZ53{v-R8!z-xOo)Cj%21H|(9E5$KGXc`B!%&QTZUWpk($ZFBmWm@uoCVxhp_PhG!h z;xG4uUDTome>*}Tdw(^2wqDYqlp{S8NLaMLS;0IZ=QMnz7rbqVQS(TwW+HB+4P_ld z3TZUtwPONBa&tuxfyi+`_o#aBRAcC9%m64@eAl*!+=ndWx>7t&hU38UCogj$eV!En zx>tZz?Eo;rX+=BeU;I5-e1AY^rdV&a@EIJ)kj26QyA{rPawFP33_J@{CE*w zT;dm8Vq_%r`4gRC?Qpm8G@IXbJ&vf7M-YDibcX>~Y>V`g^vJYjpeN1A#oExwOKYRK z0j^udFtpnu17AMKDz#?37@i#SwaAy|I${*6UGdK{suE-{V_gP1$HS*v>~ ziN#GmAPCZuzK@T?$$}sf(H{o?_ww>hMh0s8?L6#X7mSZj%E5yBP*vS|XOSNONrhi4 z0Sw`>cepL@d|7TJi7ovvE4+f?XRZd2M}fjW0rVs?hxjsfx{Q}3(wW_TSQuEc(^{*o zo|qYl{Ye7?BwwFbYF!?kjonTGzncB(A8nRl^V{0t!p4etyED{b%38?Iw~nZMV1doa zd3x|GwSCKPhOOD4h)8u9@rB-2RuTc$jh)OfuPaB=34}u*JV0NCwKz2p5NcxR1%3oM zcB#wS9tf=_7zc4O3Z#VJQmq~5&;uhAevpGjt<|@orluYtkE8&25NqI-Ba4w^K}$>C z^t9pkNM$Cy^zjA@8`Mys6C*V9Uw`Is^2)2a4vG zDTF>u=)M3f(8||LvYO%nLOE(8h>Bx7<>AF_+(W(QB;IYNqF=v~jXs_|etQ3*4!m#7 zI68Gl`RSKM*g1Hl4JOuG7OD$uJzc1=gOaL_nmrqnA@ zORhJ?Xf!PZtu`ch2=WLZparj9u~)6vV<=yiCoNd37niA4>7>#sqfn)8Ikd(D+O}nz z-=B@S`Fie7fe@n?i|am$2l@|U(dDlU$^4FanpU5Us3)&>E1IIW>+V0cAi9nZD;R_0 z0gY1jO{g{$jc-%q?pf#?;2+92_WD*{-KAve+fb!+A!b|~@p`P45}{n8Ha9yv2Ecy` zz=C2hnSY^&3iyM_f?jgWE3`e`Pyrth6$AjNIE2i9+%^4dV9Q&Sb`wtcS^*RJb3YcZ z44vRuSEkHv87yRc z?ytIX21^zKIcp;%?{S9tKtpwUC`;*M6k#;!XUbq#+&9Sekf3K5heRMr`~+0($gJ?1 zI8Acbd`+uIrc1`+*TgGR@tAwR$w&@5B**~+(WGtiRaV~MJ=$_1&FK!}RuvsX&?`<> z(-JQhChkC&1+sj0{zycsl}(M!9$H4yhK zKA~WiQOmbx!|&c6T2;7t`=kr#bL^Orb}pSgwX~2F77jR=%vd&Nb^Nl$t#(Bgh|UI+YP;t+4>yy)&OKm6~m6 zS3T9`IJZxPz~4Ur$=DFy6EYE^rwOZCd>rq|4p1p{Sk3l1;=1x#<#1q&ik0H)4OB;0a`NP@>2JlKJzjRB;4&o7k%uPl~*A-vshSK zk_Ggm!9iRBK|gE9bIaWk>Y<^yQpkUuBh{d14ssK6`!+8^hUSkqA;8=6TVWnr=xS(` z_?|7jET3g((~H$RPpjzb&EqbqTlUHIzNTTo9gNkCK%{ZyqOD`M6JvitkB2MqDIplB zDI+ac%+QX@CpU1L`lbJYF{-EQVCZ)oSdvTws41QbYA81AYM_P{1Xquu*Av14JFf*0 zoueTiB>X_Hp5m&)t+Yzv;Bn`o=g9Io zYyNh+)(m^e#0LTF+W=|z%=VK~M)sU^=hBND%nIPq3*DJWd($bw*fkuei+p8NLU&?z z2#Q&>r-3hCleJPvsJDD!7U3mEf}vEsH!w@+yTR*=il(k zs&}WOJ0Hv-(+4^w~V!p85d;lN7jRExuz%*;M zE%U5J>VflJ*y&E%``7w|!@4ZF?kG}-pU^1HhKFF_<>oa1nWQpjhS4uwfQ?!aE~-Ki zLRxC?CTY@>5a=3QryJQfU9EQSI%@SQP1-!Gq*xkJ+Uj|QbX*93z!iC3RUXHs)ERiF z8Z>&}m2=QRxYFt5Q7ckyOusZ(1ML+x#iqhKRez$yoFhK-AymR3;}?pNLODQ5L?B&V zhUqn0q$xg*u9w6vg@T)pPbAmfx(*QE%z}m`xYJ)w6QdcV`YH7BqzfRMfB7FS?>96Y z<_C0|sw5fvnD2Ef4Bw#HPr2A2(J|2b$<=B5RU`lEh-|U&d5yz6WBn)$E{9~R^u93D zbMtpS$2$|oWBi`kN|wS*R)hZaQw0o5Eba}VU~BDXICo zug!xLNLis`No3k<=n;&#>XDT2k}4Z+GZY!BRa^dKJbTh(o=L@`Y()XcTbIb*U*6jP{t<+v%pUB^EZJ^<#(_~8zD1SWF6_wS4;&ue&saiRFV(#*2z>wN;D>QasXLNr?wQFq7J2l2t_DdecX7D=|v#^CF^yre_k(U)WqJ@$?Fb|6vGadr^4(s{tx3_ zUk!_Z94QDFw!$fvPB$=Wab{>x<|!fy9g0kQh!m;;7IZU=gNDu|LLWsHr$j@hFtr7< zgccJsvAx;OyzXb1KCO&Zc|QvG0>{^LL0psD{r6g?9IW)a${8?t)!D8q+xvi38hB~|Jt>>{ zL#jj#|8($xDih@p?N zLO;^*OyWD;unNk{<*L;xK4LPytKrJ0EAxiJiceB+y<#~*U$k4zC6Qg%CO<$4?b+&w zdk4UKD)%miYVT#_b%38z8uDYKK465nH+2Zh?>6TgqhHbyNbk60E-!tOszc(y3Ru8a zJ*{!p`Q_Px>m1ioCbIyV!ewhYB~=P`VZ^W4M@L;UL8_#{hLZ;6^QI~Y<13N95n1#h zS*Ah;qGUl>@r`Kiaw+s7Rmcd}1Mix)Q*lU>vdyY9vOrl2j4jRz7;*F=dvR>HkiPP9 zM8*b;Dc;qs*nvbCZ-d#)HK|nJIuKO?~iEUW)wA+Cf2+kmc4 ziYNTY?~hAnj71?SCoz)0p;sa$SQU%MXAGI_|^9Ky6USa#~Q!y4z6o1DVZlymctkZIqPZST&@7?g1K{S6hB7<40y3Hc@K5i5S`4h-gWZ+I@_a7qH&5 z@BW>i{Rq+R^dyzVCbd2u4vw(V9dz>%f`}=F>|stH&c8>s1j?R-uDwPVrnsq;E~%b^ zjtKqi!(D91D771xoTSz0Kal+#iaR40hGnBOg=3p0QBn@dI?ief{$u<0*vqS0R?eM0 z2ci`B|2FNx5X*oi-sH#HwfC{__6A+p#l|q+^HtmJ5Tb4U+^-jXoz9zxmmc0v z>qCN&>VZ9A#l^`WMVBs+3da*|5w2WYAi}!uI==I<1Ztv{+*;H(oBbZU?p)EY{W}>C zZbwSg&;bj_JHTc>T;M~jV(zu{zu0lb8zUF^8Ylj^cbnDb8XRfGm~xYUt&tF)c-ZCi|W!=*AGlLcFWns zdZp(aK--(1Q{5x!!{uZxS3-+>)e>vE6T*z>vnHLFu#60b#VH&mY`BQJQW13<>Xf=G z_uSuqc7nbaNzmzohZTQqS3qaQ!O=SP+4)kU7g@P2;Z;?_%tOIl;qoiloC6i8JrNIv z!eXlhSo+=iwFp=dSwjji>14rQb6_2QGl-G+cb`tk4o0(hNnq~EZL?}eF7Hh4yPWhs{mpOY}W z61>t|m_Db!0Q%CamZNIYL9q-~^aM}g zg`4){L-KwpA?QDe@b;h(QeN7eYQ5HMlC|_V?R@mCa5^D~0n+5Pfwdcr5sVn>0eFnX z$}=Nd_P;s18^;<%e&ejDpD-1+ymwQaN{TT~b9V>6|ARP{QcKXD&@A4ZcS)oJ%sE@$sgc|9FxbnWZQ9Wh~c;G^R1=Jukl6fayo&cgl4&g47+^O(5vGK*b=~d9Ec(d`nBK0I z&|00~?$b;6l)IR-xU z6bq1~2qN9wX6W7+-u2~wH?)SlZ&+a-y-tomg{{*ioo?5igA|!F!d={*Bcw0i5I0Cf z&^=3dt3KSK2IMIIbo9)M6N9<&%wgD@4nM(J-I4G6l{1y@BnDq5C*OpI1z(9WEFMnX zpXtJ!!x%nnBT39mS5M4%lOE2P1##)urY~_~6>j!1_Ki1WB9l zdjCg*+o7x3+&WI}f0(i`2*>FCt$!RK`v~Okati-k6UzliqGR;l{8`uN+|Ne!a{SHq zMP2`%0f98N2JaoZ^Zm5&KcvhjByh;t#4!L=W+*phz zNUpnXk@)HV74k}Yv^YyighhAGdL#V;_y!ICPXNgWHu#@+7&x4tzdH%o25bdx!}^0& zfT8|DPQCpei`OnEWufO*xe8N*HFD)~qz5B_^mbw&0{+j#Ws>kIF8?-Ci3xxd)WIj7 z-(T^lXc;;hq)`jQ2w8%t%2lIY&q!p9A2F%P5k#JUzPS9K2*O`QmE~+##Bf8*_23*- ze9LZV_XC@k`P`;hWzjrTR8rpVbV6-2-S!y1VQz%8ue#^**;F6 zT2xa0Y3IXY=gw_8|8gEbW*EY2Ma5;6f++mfET~Qm2odL_ECX|d_@$o}M}!BUvbgq< zOqu{0L9fqi2A;LPunLshtgo%W_#`J+)-}Qe9&TZKzi;Bw*kNn&OgfA8qo%@Binph)*_YJ=> z5D`3L#+EJbOACJt3dgO^+kUE?l>SFsb-9;S3DrEY5B|| z3%d_^)8z(wyL-sqw1&{|=~3-iK_YMM+To)8<^O|Vv&G;1kCL)myj5oX{`axG@kaRV zeIWxs6a~JHdsD8@PyccdEaG(p!HDDE&zPHqcxHGo>^}ps{zMQ&;Wwhdh~P~Y;!O_& zf01+Tz4xx|FDfa29g&^($3-!4+2><9doX*~@-5{jfFA*&cBkxq{-UgE!+xd>94h;c z6&_upMfI6a>{#K_uQ25TWGs4pUI*~LOJUE?-@O9Ksc8!p?diP6@x6!1x^*=%bK<6M zb2A)45MLB6f;AdOyySVb?V97FsQQh&^TWaDgN%Z$W|c}5WECf~+V#IxRC4bB5KVUi z*&r+ft_g4%kryA@p6!$v<_~sm&)NU4!{_6TL&m!;g0NK(NJkV?fnG!|3o70^dm!i8 z?|)xj{WC!&o)=B-e?}t&i5jm0QBYBhNwCeO8n!rOo5!mbuRK_$wr#4G(wvkU%t@XRZsN%cVlAzPHpltYMI z76svrM4>}oy9ANvLGWyP6D*B#raE^pd)|u86}O1+0YMNmMM;t)ify5LgreGK10U^ZtU= z1+vEe`1Ou%j_*B8cUz~+>l73e6#RiAKxR04ecowcEwIo2xN&fZ)BBH7fBwqUY)nBx z;f6;MAU6PdeO@PU4^oc=TVjYPid;Nh$=M@kFq_R&wm$_0g&Pw^fZQPH^?4S(KJPn7 z9UrgTpKGbT%E>q1WuUj;^~DMb3JT*u5g<1hdVStY|G&NaXKgBq!#MsG#J3>0_ySx- z9K=oB+yr;wAxNfs4S{1CX`ODv#$|47au?FP5ZTus~*9M7j!`1~!ZHcijzI za|;Z5{XD@WRh|V>0}<&iJFogK73W_EUufUC&)Zks$qOavA1siXh)A!26Tpq)d^8%d z{NNF*51)E8yrezZpF4p5pNRAgINxYA7lG@*fuGmjth}WE;S&cBAIg?bQnk1PsiBC} z1Wp2D$M^O&-m}tP&J#*f#DjpL6GtR2>$G0EkF8f#bl7+*u@5g9V~rB2ou93f#_}Mbh-MKr|*IeFV+` zmnj?#FG;`iI}rULB7FxgH5$z}a3psgNz=(4i2f=f-2$%U&LL?!?eo2VNm3c^KqN_} zSRj(5QY;WjQYjXQB&ie&M3PjB1tLi*#R8EemGT4o)w4D^Yb|jA0000Memos List
+ +{INCLUDE footer.html} diff --git a/modules/webcpanel/templates/default/nickserv/access.html b/modules/webcpanel/templates/default/nickserv/access.html new file mode 100644 index 0000000..6387da8 --- /dev/null +++ b/modules/webcpanel/templates/default/nickserv/access.html @@ -0,0 +1,42 @@ +{INCLUDE header.html} +
Nick access list
+
+ {FOR M IN MESSAGES} +
+ {M}
+
+ {END FOR} + + {IF EXISTS ACCESS} + + + {FOR A IN ACCESS} + + + + + {END FOR} + +
{A}Delete
+ {ELSE} + Your access list is empty. + {END IF} + +
+ +

Add an access entry

+
+
+ +
+ +
+
+
+
+ +
+
+
+
+{INCLUDE footer.html} diff --git a/modules/webcpanel/templates/default/nickserv/alist.html b/modules/webcpanel/templates/default/nickserv/alist.html new file mode 100644 index 0000000..f3b2e01 --- /dev/null +++ b/modules/webcpanel/templates/default/nickserv/alist.html @@ -0,0 +1,23 @@ +{INCLUDE header.html} +
Channel access list
+
+ + + + + + + + + + {FOR N,C,A IN NUMBERS,CHANNELS,ACCESSES} + + + + + + {END FOR} + +
NumberChannelAccess
{N}{C}{A}
+
+{INCLUDE footer.html} diff --git a/modules/webcpanel/templates/default/nickserv/cert.html b/modules/webcpanel/templates/default/nickserv/cert.html new file mode 100644 index 0000000..6d41a44 --- /dev/null +++ b/modules/webcpanel/templates/default/nickserv/cert.html @@ -0,0 +1,42 @@ +{INCLUDE header.html} +
Your certificate fingerprints
+
+ {FOR M IN MESSAGES} +
+ {M}
+
+ {END FOR} + + {IF EXISTS CERTS} + + + {FOR CERT IN CERTS} + + + + + {END FOR} + +
{CERT}Delete
+ {ELSE} + Certificates list is empty. + {END IF} + +
+ +

Add a certificate fingerprint

+
+
+ +
+ +
+
+
+
+ +
+
+
+
+{INCLUDE footer.html} diff --git a/modules/webcpanel/templates/default/nickserv/confirm.html b/modules/webcpanel/templates/default/nickserv/confirm.html new file mode 100644 index 0000000..66dbe34 --- /dev/null +++ b/modules/webcpanel/templates/default/nickserv/confirm.html @@ -0,0 +1,29 @@ +{INCLUDE header.html} +
Confirm your Email
+
+ {FOR M IN MESSAGES} +
+ {M}
+
+ {END FOR} + + You can CONFIRM your registration by entering your confirmation code below. + +
+ +

Confirm your account

+
+
+ +
+ +
+
+
+
+ +
+
+
+
+{INCLUDE footer.html} diff --git a/modules/webcpanel/templates/default/nickserv/info.html b/modules/webcpanel/templates/default/nickserv/info.html new file mode 100644 index 0000000..667c8b3 --- /dev/null +++ b/modules/webcpanel/templates/default/nickserv/info.html @@ -0,0 +1,72 @@ +{INCLUDE header.html} +
Your account information
+
+ {FOR M IN ERRORS} +
+ {M}
+
+ {END FOR} + + {FOR M IN MESSAGES} +
+ {M}
+
+ {END FOR} + +
+ + + + + + + {IF EXISTS EMAIL} + + + + + {END IF} + + + + + {IF EXISTS VHOST} + + + + + {END IF} + + + + + + + + + + + + + + + + + + + + + +
Account:{DISPLAY}
E-mail:{EMAIL}
Time registered:{TIME_REGISTERED}
Vhost:{VHOST}
Greet:
Auto op:
Private:
Secure:
Kill: + +
+
+ +
+
+
+{INCLUDE footer.html} diff --git a/modules/webcpanel/templates/default/operserv/akill.html b/modules/webcpanel/templates/default/operserv/akill.html new file mode 100644 index 0000000..ffc73f8 --- /dev/null +++ b/modules/webcpanel/templates/default/operserv/akill.html @@ -0,0 +1,77 @@ +{INCLUDE header.html} +
Akill List
+
+ {IF EXISTS NOACCESS} +

Access denied.

+ {ELSE} + + {FOR M IN MESSAGES} +
+ {M}
+
+ {END FOR} + + + + {IF EXISTS AKILLS} + {AKILLS} + {ELSE} + + + + + + + + + + + + {FOR N,H,S,T,E,R IN NUMBER,HOST,SETTER,TIME,EXPIRE,REASON} + + + + + + + + {END FOR} + +
NumberHostmask (hover: Reason)Expires (hover: Set Date)Setter
{N}{H}{E}{S}Delete
+ {END IF} + +
+ +

Add a new Akill

+
+
+ +
+ +
+
+
+ +
+ +
+
+
+ +
+ +
+
+
+
+ +
+
+
+ {END IF} +
+{INCLUDE footer.html} diff --git a/modules/webcpanel/templates/default/register.html b/modules/webcpanel/templates/default/register.html new file mode 100644 index 0000000..c601db8 --- /dev/null +++ b/modules/webcpanel/templates/default/register.html @@ -0,0 +1,65 @@ + + + + + + + + + + + + + {TITLE} + + +
+
+
+ + + + Back Home + +

Register

+ + {IF EXISTS MESSAGES} +
+ {MESSAGES} +
+ {END IF} + + +
+
+ +
+
+
+ +
+
+
+ + + + + diff --git a/modules/webcpanel/templates/default/style.css b/modules/webcpanel/templates/default/style.css new file mode 100644 index 0000000..e425c3d --- /dev/null +++ b/modules/webcpanel/templates/default/style.css @@ -0,0 +1,166 @@ +@import url(//fonts.googleapis.com/css?family=Open+Sans:300,400); +@import url(//fonts.googleapis.com/css?family=Port+Lligat+Slab); + +*, html, body, h1, h2, h3, h4, div, p, span, a, button { + font-family: 'Open Sans', sans-serif; +} +body { + background-color: #eee; + background-image: url('/static/cubes.png'); +} + +/* RANDOM STUFF */ +#frontPages { + padding-top: 20px; +} + +h2 { + margin: 0 0 10px 0; +} +h4 { + margin-top: 30px; +} +.popover { + max-width: 450px; + -webkit-box-shadow: 0 1px 10px rgba(0, 0, 0, 0.8); + box-shadow: 0 1px 10px rgba(0, 0, 0, 0.8); +} + +.label { + font-size: 13px; + font-weight: normal; +} + +.label-info { + background-color: #4EA4EE; +} + +.label-info[href]:hover, .label-info[href]:focus { + background-color: #428BCA; +} + +/* LOGIN FORM */ +.form-signin .form-signin-heading, .form-signin .checkbox { + margin-bottom: 10px; +} +.form-signin .checkbox { + font-weight: normal; +} +.form-signin .form-control { + position: relative; + font-size: 16px; + height: auto; + padding: 10px; + -webkit-box-sizing: border-box; + -moz-box-sizing: border-box; + box-sizing: border-box; +} +.form-signin .form-control:focus { + z-index: 2; +} +/* FOOTER */ +.footer { + margin-top: 20px; +} + +/* Control Panel */ +.panel-default .panel-heading { + font-size: 24px; +} +#loggedIn { + margin: 15px 15px 0 0; +} + +#navPanel { + margin: 0; + padding: 0; +} +.table thead > tr:first-child > th, .table tbody > tr:first-child > th, .table tfoot > tr:first-child > th, .table thead > tr:first-child > td, .table tbody > tr:first-child > td, .table tfoot > tr:first-child > td { + vertical-align: top; + border-top: 0; +} +#tableInfo td { + vertical-align: middle; +} +#tableInfo td:first-child { + font-weight: bold; + padding-right: 10px; + text-align: right; + width: 25%; +} + +#tableInfoNorm td { + vertical-align: middle; +} +#tableInfoNorm td:first-child { + font-weight: bold; + padding-right: 10px; +} + +#tableInfoMemos td { + vertical-align: top; +} +#tableInfoMemos td:first-child { + font-weight: bold; + padding-right: 10px; +} +#tableInfoMemos th small { + font-weight: normal; +} + +#tableNSAccess td { + vertical-align: middle; +} +#tableNSAccess td:first-child { + padding-right: 10px; + text-align: left; +} +#tableNSAccess td:last-child { + padding-right: 10px; + text-align: right; +} +#tableNSAccess th small { + font-weight: normal; +} + +#channelList li { + margin-top: 10px; +} + +/* NAVBAR */ +.navbar, .well { + background-color: white; +} + +.navbar { + -webkit-box-shadow: 0 8px 6px -8px black; + -moz-box-shadow: 0 8px 6px -8px black; + box-shadow: 0 8px 6px -8px black; +} +.navbar-brand { + font-size: 25px; +} +.navbar-brand, .navbar-brand small { + font-family: 'Port Lligat Slab', serif; +} + +.navbar-default .nav { + margin-bottom: -1px; +} + +.navbar-default .nav > li > a { + color: #428BCA; +} + +.navbar-default .nav > li > a:hover, .navbar-default .nav > li > a:focus { + color: #428BCA; + border-top: 3px solid #0082D9; + margin-top: -3px; +} + +.navbar-default .nav > li.active > a, .navbar-default .nav > li.active > a:hover, .navbar-default .nav > li.active > a:focus { + color: #428BCA; + background-color: transparent; + background-color: rgba(66, 139, 202, 0.1); + border-bottom-color: transparent; +} diff --git a/modules/webcpanel/webcpanel.cpp b/modules/webcpanel/webcpanel.cpp new file mode 100644 index 0000000..9b46fe6 --- /dev/null +++ b/modules/webcpanel/webcpanel.cpp @@ -0,0 +1,324 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "webcpanel.h" + +Module *me; +Anope::string provider_name, template_name, template_base, page_title; + +class ModuleWebCPanel : public Module +{ + ServiceReference provider; + Panel panel; + PrimitiveExtensibleItem id, ip; + PrimitiveExtensibleItem last_login; + + StaticFileServer style_css, logo_png, cubes_png, favicon_ico; + + WebCPanel::Index index; + WebCPanel::Logout logout; + WebCPanel::Register _register; + WebCPanel::Confirm confirm; + + WebCPanel::NickServ::Info nickserv_info; + WebCPanel::NickServ::Cert nickserv_cert; + WebCPanel::NickServ::Access nickserv_access; + WebCPanel::NickServ::Alist nickserv_alist; + WebCPanel::NickServ::Confirm nickserv_confirm; + + WebCPanel::ChanServ::Info chanserv_info; + WebCPanel::ChanServ::Set chanserv_set; + WebCPanel::ChanServ::Access chanserv_access; + WebCPanel::ChanServ::Akick chanserv_akick; + WebCPanel::ChanServ::Modes chanserv_modes; + WebCPanel::ChanServ::Drop chanserv_drop; + + WebCPanel::MemoServ::Memos memoserv_memos; + + WebCPanel::HostServ::Request hostserv_request; + + WebCPanel::OperServ::Akill operserv_akill; + + + public: + ModuleWebCPanel(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, EXTRA | VENDOR), + panel(this, "webcpanel"), + id(this, "webcpanel_id"), ip(this, "webcpanel_ip"), last_login(this, "webcpanel_last_login"), + style_css("style.css", "/static/style.css", "text/css"), logo_png("logo.png", "/static/logo.png", "image/png"), cubes_png("cubes.png", "/static/cubes.png", "image/png"), favicon_ico("favicon.ico", "/favicon.ico", "image/x-icon"), + index("/"), logout("/logout"), _register("/register"), confirm("/confirm"), + nickserv_info("NickServ", "/nickserv/info"), nickserv_cert("NickServ", "/nickserv/cert"), nickserv_access("NickServ", "/nickserv/access"), nickserv_alist("NickServ", "/nickserv/alist"), nickserv_confirm("NickServ", "/nickserv/confirm"), + chanserv_info("ChanServ", "/chanserv/info"), chanserv_set("ChanServ", "/chanserv/set"), chanserv_access("ChanServ", "/chanserv/access"), chanserv_akick("ChanServ", "/chanserv/akick"), + chanserv_modes("ChanServ", "/chanserv/modes"), chanserv_drop("ChanServ", "/chanserv/drop"), memoserv_memos("MemoServ", "/memoserv/memos"), hostserv_request("HostServ", "/hostserv/request"), + operserv_akill("OperServ", "/operserv/akill") + { + + me = this; + + Configuration::Block *block = Config->GetModule(this); + provider_name = block->Get("server", "httpd/main"); + template_name = block->Get("template", "default"); + template_base = Anope::DataDir + "/modules/webcpanel/templates/" + template_name; + page_title = block->Get("title", "Anope IRC Services"); + + provider = ServiceReference("HTTPProvider", provider_name); + if (!provider) + throw ModuleException("Unable to find HTTPD provider. Is m_httpd loaded?"); + + provider->RegisterPage(&this->style_css); + provider->RegisterPage(&this->logo_png); + provider->RegisterPage(&this->cubes_png); + provider->RegisterPage(&this->favicon_ico); + + provider->RegisterPage(&this->index); + provider->RegisterPage(&this->logout); + provider->RegisterPage(&this->_register); + provider->RegisterPage(&this->confirm); + + BotInfo *NickServ = Config->GetClient("NickServ"); + if (NickServ) + { + Section s; + s.name = NickServ->nick; + + SubSection ss; + ss.name = "Information"; + ss.url = "/nickserv/info"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->nickserv_info); + + if (IRCD && IRCD->CanCertFP) + { + ss.name = "SSL Certificates"; + ss.url = "/nickserv/cert"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->nickserv_cert); + } + + ss.name = "Access"; + ss.url = "/nickserv/access"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->nickserv_access); + + ss.name = "AList"; + ss.url = "/nickserv/alist"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->nickserv_alist); + + ss.name = "Confirm"; + ss.url = "/nickserv/confirm"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->nickserv_confirm); + + panel.sections.push_back(s); + } + + BotInfo *ChanServ = Config->GetClient("ChanServ"); + if (ChanServ) + { + Section s; + s.name = ChanServ->nick; + + SubSection ss; + ss.name = "Channels"; + ss.url = "/chanserv/info"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->chanserv_info); + + ss.name = "Settings"; + ss.url = "/chanserv/set"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->chanserv_set); + + ss.name = "Access"; + ss.url = "/chanserv/access"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->chanserv_access); + + ss.name = "Akick"; + ss.url = "/chanserv/akick"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->chanserv_akick); + + ss.name = "Modes"; + ss.url = "/chanserv/modes"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->chanserv_modes); + + ss.name = "Drop"; + ss.url = "/chanserv/drop"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->chanserv_drop); + + panel.sections.push_back(s); + } + + BotInfo *MemoServ = Config->GetClient("MemoServ"); + if (MemoServ) + { + Section s; + s.name = MemoServ->nick; + + SubSection ss; + ss.name = "Memos"; + ss.url = "/memoserv/memos"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->memoserv_memos); + + panel.sections.push_back(s); + } + + BotInfo *HostServ = Config->GetClient("HostServ"); + if (HostServ) + { + Section s; + s.name = HostServ->nick; + + SubSection ss; + ss.name = "vHost Request"; + ss.url = "/hostserv/request"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->hostserv_request); + + panel.sections.push_back(s); + } + + BotInfo *OperServ = Config->GetClient("OperServ"); + if (OperServ) + { + Section s; + s.name = OperServ->nick; + + SubSection ss; + ss.name = "Akill"; + ss.url = "/operserv/akill"; + s.subsections.push_back(ss); + provider->RegisterPage(&this->operserv_akill); + + panel.sections.push_back(s); + } + } + + ~ModuleWebCPanel() + { + if (provider) + { + provider->UnregisterPage(&this->style_css); + provider->UnregisterPage(&this->logo_png); + provider->UnregisterPage(&this->cubes_png); + provider->UnregisterPage(&this->favicon_ico); + + provider->UnregisterPage(&this->index); + provider->UnregisterPage(&this->logout); + provider->UnregisterPage(&this->_register); + provider->UnregisterPage(&this->confirm); + + provider->UnregisterPage(&this->nickserv_info); + provider->UnregisterPage(&this->nickserv_cert); + provider->UnregisterPage(&this->nickserv_access); + provider->UnregisterPage(&this->nickserv_alist); + provider->UnregisterPage(&this->nickserv_confirm); + + provider->UnregisterPage(&this->chanserv_info); + provider->UnregisterPage(&this->chanserv_set); + provider->UnregisterPage(&this->chanserv_access); + provider->UnregisterPage(&this->chanserv_akick); + provider->UnregisterPage(&this->chanserv_modes); + provider->UnregisterPage(&this->chanserv_drop); + + provider->UnregisterPage(&this->memoserv_memos); + + provider->UnregisterPage(&this->hostserv_request); + + provider->UnregisterPage(&this->operserv_akill); + } + } +}; + +namespace WebPanel +{ + void RunCommand(HTTPClient *client, const Anope::string &user, NickCore *nc, const Anope::string &service, const Anope::string &c, std::vector ¶ms, TemplateFileServer::Replacements &r, const Anope::string &key) + { + ServiceReference cmd("Command", c); + if (!cmd) + { + r[key] = "Unable to find command " + c; + return; + } + + if (params.size() < cmd->min_params) + return; + + BotInfo *bi = Config->GetClient(service); + if (!bi) + { + if (BotListByNick->empty()) + return; + bi = BotListByNick->begin()->second; // Pick one... + } + + struct MyComandReply : CommandReply + { + TemplateFileServer::Replacements &re; + const Anope::string &k; + + MyComandReply(TemplateFileServer::Replacements &_r, const Anope::string &_k) : re(_r), k(_k) { } + + void SendMessage(BotInfo *source, const Anope::string &msg) anope_override + { + re[k] = msg; + } + } + my_reply(r, key); + + CommandSource source(user, NULL, nc, &my_reply, bi); + source.ip = client->GetIP(); + + CommandInfo info; + info.name = c; + + cmd->Run(source, "", info, params); + } + + void RunCommandWithName(HTTPClient *client, NickCore *nc, const Anope::string &service, const Anope::string &c, const Anope::string &cmdname, std::vector ¶ms, TemplateFileServer::Replacements &r, const Anope::string &key) + { + ServiceReference cmd("Command", c); + if (!cmd) + { + r[key] = "Unable to find command " + c; + return; + } + + BotInfo *bi = Config->GetClient(service); + if (!bi) + return; + + CommandInfo *info = bi->GetCommand(cmdname); + if (!info) + return; + + struct MyComandReply : CommandReply + { + TemplateFileServer::Replacements &re; + const Anope::string &k; + + MyComandReply(TemplateFileServer::Replacements &_r, const Anope::string &_k) : re(_r), k(_k) { } + + void SendMessage(BotInfo *source, const Anope::string &msg) anope_override + { + re[k] = msg; + } + } + my_reply(r, key); + + CommandSource source(nc->display, NULL, nc, &my_reply, bi); + source.ip = client->GetIP(); + + cmd->Run(source, cmdname, *info, params); + } +} + +MODULE_INIT(ModuleWebCPanel) diff --git a/modules/webcpanel/webcpanel.h b/modules/webcpanel/webcpanel.h new file mode 100644 index 0000000..0313be2 --- /dev/null +++ b/modules/webcpanel/webcpanel.h @@ -0,0 +1,182 @@ +/* + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "module.h" +#include "modules/httpd.h" + +#include "static_fileserver.h" +#include "template_fileserver.h" + +extern Module *me; + +extern Anope::string provider_name, template_name, template_base, page_title; + +struct SubSection +{ + Anope::string name; + Anope::string url; +}; + +struct Section +{ + Anope::string name; + std::vector subsections; +}; + +/* An interface for this webpanel used by other modules */ +class Panel : public Section, public Service +{ + public: + Panel(Module *c, const Anope::string &n) : Service(c, "Panel", n) { } + + std::vector
sections; + + NickAlias *GetNickFromSession(HTTPClient *client, HTTPMessage &msg) + { + if (!client) + return NULL; + + const Anope::string &acc = msg.cookies["account"], &id = msg.cookies["id"]; + + if (acc.empty() || id.empty()) + return NULL; + + NickAlias *na = NickAlias::Find(acc); + if (na == NULL) + return NULL; + + Anope::string *n_id = na->GetExt("webcpanel_id"), *n_ip = na->GetExt("webcpanel_ip"); + if (n_id == NULL || n_ip == NULL) + return NULL; + else if (id != *n_id) + return NULL; + else if (client->GetIP() != *n_ip) + return NULL; + else + return na; + } +}; + +class WebPanelPage : public HTTPPage +{ + public: + WebPanelPage(const Anope::string &u, const Anope::string &ct = "text/html") : HTTPPage(u, ct) + { + } + + virtual bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &) = 0; +}; + +class WebPanelProtectedPage : public WebPanelPage +{ + Anope::string category; + + public: + WebPanelProtectedPage(const Anope::string &cat, const Anope::string &u, const Anope::string &ct = "text/html") : WebPanelPage(u, ct), category(cat) + { + } + + bool OnRequest(HTTPProvider *provider, const Anope::string &page_name, HTTPClient *client, HTTPMessage &message, HTTPReply &reply) anope_override anope_final + { + ServiceReference panel("Panel", "webcpanel"); + NickAlias *na; + + if (!panel || !(na = panel->GetNickFromSession(client, message))) + { + reply.error = HTTP_FOUND; + reply.headers["Location"] = Anope::string("http") + (provider->IsSSL() ? "s" : "") + "://" + message.headers["Host"] + "/"; + return true; // Access denied + } + + TemplateFileServer::Replacements replacements; + + replacements["TITLE"] = page_title; + replacements["ACCOUNT"] = na->nc->display; + replacements["PAGE_NAME"] = page_name; + replacements["CATEGORY"] = category; + if (na->nc->IsServicesOper()) + replacements["IS_OPER"]; + + Anope::string sections, get; + + for (std::map::iterator it = message.get_data.begin(), it_end = message.get_data.end(); it != it_end; ++it) + if (this->GetData().count(it->first) > 0) + get += "&" + it->first + "=" + HTTPUtils::URLEncode(it->second); + if (get.empty() == false) + get = "?" + get.substr(1); + + Section *ns = NULL; + for (unsigned i = 0; i < panel->sections.size(); ++i) + { + Section& s = panel->sections[i]; + if (s.name == this->category) + ns = &s; + replacements["CATEGORY_URLS"] = s.subsections[0].url; + replacements["CATEGORY_NAMES"] = s.name; + } + + if (ns) + { + sections = ""; + for (unsigned i = 0; i < ns->subsections.size(); ++i) + { + SubSection& ss = ns->subsections[i]; + replacements["SUBCATEGORY_URLS"] = ss.url; + replacements["SUBCATEGORY_GETS"] = get; + replacements["SUBCATEGORY_NAMES"] = ss.name; + } + } + + return this->OnRequest(provider, page_name, client, message, reply, na, replacements); + } + + virtual bool OnRequest(HTTPProvider *, const Anope::string &, HTTPClient *, HTTPMessage &, HTTPReply &, NickAlias *, TemplateFileServer::Replacements &) = 0; + + /* What get data should be appended to links in the navbar */ + virtual std::set GetData() { return std::set(); } +}; + +namespace WebPanel +{ + /** Run a command + * @param client HTTP client command is being issued for + * @param User name to run command as, probably nc->display unless nc == NULL + * @param nc Nick core to run command from + * @param service Service for source.owner and source.service + * @param c Command to run (as a service name) + * @param params Command parameters + * @param r Replacements, reply from command goes back here into key + * @param key The key to put the replies into r + */ + extern void RunCommand(HTTPClient *client, const Anope::string &user, NickCore *nc, const Anope::string &service, const Anope::string &c, std::vector ¶ms, TemplateFileServer::Replacements &r, const Anope::string &key = "MESSAGES"); + + extern void RunCommandWithName(HTTPClient *client, NickCore *nc, const Anope::string &service, const Anope::string &c, const Anope::string &cmdname, std::vector ¶ms, TemplateFileServer::Replacements &r, const Anope::string &key = "MESSAGES"); +} + +#include "pages/index.h" +#include "pages/logout.h" +#include "pages/register.h" +#include "pages/confirm.h" + +#include "pages/nickserv/info.h" +#include "pages/nickserv/cert.h" +#include "pages/nickserv/access.h" +#include "pages/nickserv/alist.h" +#include "pages/nickserv/confirm.h" + +#include "pages/chanserv/info.h" +#include "pages/chanserv/set.h" +#include "pages/chanserv/access.h" +#include "pages/chanserv/akick.h" +#include "pages/chanserv/modes.h" +#include "pages/chanserv/drop.h" + +#include "pages/memoserv/memos.h" + +#include "pages/hostserv/request.h" + +#include "pages/operserv/akill.h" diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt new file mode 100644 index 0000000..b390d16 --- /dev/null +++ b/src/CMakeLists.txt @@ -0,0 +1,116 @@ +# Find all the *.cpp files within the current source directory, and sort the list +file(GLOB SRC_SRCS RELATIVE ${CMAKE_CURRENT_SOURCE_DIR} "*.cpp") + +if(WIN32) + append_to_list(SRC_SRCS win32/dir/dir.cpp) + append_to_list(SRC_SRCS win32/socket.cpp) + append_to_list(SRC_SRCS win32/windows.cpp) + append_to_list(SRC_SRCS win32/dl/dl.cpp) + append_to_list(SRC_SRCS win32/pipe/pipe.cpp) + append_to_list(SRC_SRCS win32/pthread/pthread.cpp) + append_to_list(SRC_SRCS win32/sigaction/sigaction.cpp) +endif(WIN32) + +if(HAVE_EPOLL) + append_to_list(SRC_SRCS socketengines/socketengine_epoll.cpp) +else(HAVE_EPOLL) + if(HAVE_KQUEUE) + append_to_list(SRC_SRCS socketengines/socketengine_kqueue.cpp) + else(HAVE_KQUEUE) + if(HAVE_POLL) + append_to_list(SRC_SRCS socketengines/socketengine_poll.cpp) + else(HAVE_POLL) + append_to_list(SRC_SRCS socketengines/socketengine_select.cpp) + endif(HAVE_POLL) + endif(HAVE_KQUEUE) +endif(HAVE_EPOLL) + +sort_list(SRC_SRCS) + +# Set all the files to use C++ as well as set their compile flags (use the module-specific compile flags, though) +set_source_files_properties(${SRC_SRCS} PROPERTIES LANGUAGE CXX COMPILE_FLAGS "${CXXFLAGS}") + +# Create an empty list to store extra include directories +set(EXTRA_INCLUDES) +# Iterate through all the source files +foreach(SRC ${SRC_SRCS}) + # Temporary variable for the current source's include directories + set(TEMP_INCLUDES) + # Calculate the header file dependencies for the given source file + calculate_depends(${SRC} TEMP_INCLUDES) + # If there were some extra include directories, add them to the list + if(TEMP_INCLUDES) + append_to_list(EXTRA_INCLUDES ${TEMP_INCLUDES}) + endif(TEMP_INCLUDES) +endforeach(SRC) +# If there were extra include directories, remove the duplicates and add the directories to the include path +if(EXTRA_INCLUDES) + remove_list_duplicates(EXTRA_INCLUDES) + include_directories(${EXTRA_INCLUDES}) +endif(EXTRA_INCLUDES) + +# Under Windows, we also include a resource file to the build +if(WIN32) + # Make sure that the resource file is seen as an RC file to be compiled with a resource compiler, not a C++ compiler + set_source_files_properties(${CMAKE_CURRENT_BINARY_DIR}/win32/win32.rc LANGUAGE RC) + # Add the resource file to the list of sources + append_to_list(SRC_SRCS ${CMAKE_CURRENT_BINARY_DIR}/win32/win32.rc) + # For MinGW, we have to change the compile flags + if(MINGW) + set(RC_CFLAGS "-DMINGW -Ocoff -I${Anope_SOURCE_DIR}/include") + # If any sort of debugging is being enabled, add a _DEBUG define to the flags for the resource compiler + if(CMAKE_BUILD_TYPE STREQUAL "DEBUG" OR CMAKE_BUILD_TYPE STREQUAL "RELWITHDEBINFO") + set(RC_CFLAGS "${RC_CFLAGS} -D_DEBUG") + endif(CMAKE_BUILD_TYPE STREQUAL "DEBUG" OR CMAKE_BUILD_TYPE STREQUAL "RELWITHDEBINFO") + set_source_files_properties(${CMAKE_CURRENT_BINARY_DIR}/win32/win32.rc COMPILE_FLAGS "${RC_CFLAGS}") + # For anything else, assumingly Visual Studio at this point, use a different set of compile flags + else(MINGW) + set_source_files_properties(${CMAKE_CURRENT_BINARY_DIR}/win32/win32.rc COMPILE_FLAGS "/i\"${Anope_SOURCE_DIR}/include\"") + endif(MINGW) +endif(WIN32) + +# If compiling with Visual Studio, create a static library out of win32/win32_memory.cpp to be included with everything else, needed to override its override of new/delete operators +if(MSVC) + set_source_files_properties(win32/win32_memory.cpp PROPERTIES LANGUAGE CXX COMPILE_FLAGS "${CXXFLAGS}") + add_library(win32_memory STATIC win32/win32_memory.cpp) + set(WIN32_MEMORY win32_memory) + set(EXTRA_LDFLAGS "/OPT:NOREF") # https://sourceware.org/bugzilla/show_bug.cgi?id=12633 +else(MSVC) + set(WIN32_MEMORY) +endif(MSVC) + +# Generate the Anope executable and set it's linker flags, also set it to export it's symbols even though it's not a module +add_executable(${PROGRAM_NAME} ${SRC_SRCS}) +set_target_properties(${PROGRAM_NAME} PROPERTIES LINKER_LANGUAGE CXX LINK_FLAGS "${LDFLAGS} ${EXTRA_LDFLAGS}" ENABLE_EXPORTS ON INSTALL_RPATH_USE_LINK_PATH ON BUILD_WITH_INSTALL_RPATH ON) +# On Windows, also link Anope to the wsock32 and Ws2_32 library, as well as set the version +if(WIN32) + target_link_libraries(${PROGRAM_NAME} wsock32 Ws2_32 ${LINK_LIBS} ${GETTEXT_LIBRARIES} ${WIN32_MEMORY}) + set_target_properties(${PROGRAM_NAME} PROPERTIES VERSION "${VERSION_DOTTED}") +else(WIN32) + target_link_libraries(${PROGRAM_NAME} ${LINK_LIBS} ${GETTEXT_LIBRARIES}) +endif(WIN32) +# Building the Anope executable requires the version.h header to be generated +add_dependencies(${PROGRAM_NAME} headers) +# Also require the language files if we have gettext +if(GETTEXT_FOUND) + add_dependencies(${PROGRAM_NAME} language) +endif(GETTEXT_FOUND) + +# Get the filename of the Anope executable as it is in on this system +get_target_property(SERVICES_BINARY ${PROGRAM_NAME} LOCATION) +get_filename_component(SERVICES_BINARY ${SERVICES_BINARY} NAME) +# Add the Anope executable to the list of files for CPack to ignore +add_to_cpack_ignored_files("${SERVICES_BINARY}$" TRUE) + +# Generate sysconf.h from the earlier configuration +configure_file(${Anope_SOURCE_DIR}/include/sysconf.h.cmake ${Anope_BINARY_DIR}/include/sysconf.h) + +# Go into the following directories and run their CMakeLists.txt as well +if(NOT DISABLE_TOOLS) + add_subdirectory(tools) +endif(NOT DISABLE_TOOLS) + +# Set Anope to be installed to the bin directory +install(TARGETS ${PROGRAM_NAME} + DESTINATION ${BIN_DIR} +) diff --git a/src/access.cpp b/src/access.cpp new file mode 100644 index 0000000..cfb4152 --- /dev/null +++ b/src/access.cpp @@ -0,0 +1,475 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "service.h" +#include "access.h" +#include "regchannel.h" +#include "users.h" +#include "account.h" +#include "protocol.h" + +static struct +{ + Anope::string name; + Anope::string desc; +} descriptions[] = { + {"ACCESS_CHANGE", _("Allowed to modify the access list")}, + {"ACCESS_LIST", _("Allowed to view the access list")}, + {"AKICK", _("Allowed to use the AKICK command")}, + {"ASSIGN", _("Allowed to assign/unassign a bot")}, + {"AUTOHALFOP", _("Automatic halfop upon join")}, + {"AUTOOP", _("Automatic channel operator status upon join")}, + {"AUTOOWNER", _("Automatic owner upon join")}, + {"AUTOPROTECT", _("Automatic protect upon join")}, + {"AUTOVOICE", _("Automatic voice on join")}, + {"BADWORDS", _("Allowed to modify channel badwords list")}, + {"BAN", _("Allowed to ban users")}, + {"FANTASIA", _("Allowed to use fantasy commands")}, + {"FOUNDER", _("Allowed to issue commands restricted to channel founders")}, + {"GETKEY", _("Allowed to use GETKEY command")}, + {"GREET", _("Greet message displayed on join")}, + {"HALFOP", _("Allowed to (de)halfop users")}, + {"HALFOPME", _("Allowed to (de)halfop him/herself")}, + {"INFO", _("Allowed to get full INFO output")}, + {"INVITE", _("Allowed to use the INVITE command")}, + {"KICK", _("Allowed to use the KICK command")}, + {"MEMO", _("Allowed to read channel memos")}, + {"MODE", _("Allowed to use the MODE command")}, + {"NOKICK", _("Prevents users being kicked by Services")}, + {"OP", _("Allowed to (de)op users")}, + {"OPME", _("Allowed to (de)op him/herself")}, + {"OWNER", _("Allowed to (de)owner users")}, + {"OWNERME", _("Allowed to (de)owner him/herself")}, + {"PROTECT", _("Allowed to (de)protect users")}, + {"PROTECTME", _("Allowed to (de)protect him/herself")}, + {"SAY", _("Allowed to use SAY and ACT commands")}, + {"SET", _("Allowed to set channel settings")}, + {"SIGNKICK", _("No signed kick when SIGNKICK LEVEL is used")}, + {"TOPIC", _("Allowed to change channel topics")}, + {"UNBAN", _("Allowed to unban users")}, + {"VOICE", _("Allowed to (de)voice users")}, + {"VOICEME", _("Allowed to (de)voice him/herself")} +}; + +Privilege::Privilege(const Anope::string &n, const Anope::string &d, int r) : name(n), desc(d), rank(r) +{ + if (this->desc.empty()) + for (unsigned j = 0; j < sizeof(descriptions) / sizeof(*descriptions); ++j) + if (descriptions[j].name.equals_ci(name)) + this->desc = descriptions[j].desc; +} + +bool Privilege::operator==(const Privilege &other) const +{ + return this->name.equals_ci(other.name); +} + +std::vector PrivilegeManager::Privileges; + +void PrivilegeManager::AddPrivilege(Privilege p) +{ + unsigned i; + for (i = 0; i < Privileges.size(); ++i) + { + Privilege &priv = Privileges[i]; + + if (priv.rank > p.rank) + break; + } + + Privileges.insert(Privileges.begin() + i, p); +} + +void PrivilegeManager::RemovePrivilege(Privilege &p) +{ + std::vector::iterator it = std::find(Privileges.begin(), Privileges.end(), p); + if (it != Privileges.end()) + Privileges.erase(it); + + for (registered_channel_map::const_iterator cit = RegisteredChannelList->begin(), cit_end = RegisteredChannelList->end(); cit != cit_end; ++cit) + { + cit->second->QueueUpdate(); + cit->second->RemoveLevel(p.name); + } +} + +Privilege *PrivilegeManager::FindPrivilege(const Anope::string &name) +{ + for (unsigned i = Privileges.size(); i > 0; --i) + if (Privileges[i - 1].name.equals_ci(name)) + return &Privileges[i - 1]; + return NULL; +} + +std::vector &PrivilegeManager::GetPrivileges() +{ + return Privileges; +} + +void PrivilegeManager::ClearPrivileges() +{ + Privileges.clear(); +} + +AccessProvider::AccessProvider(Module *o, const Anope::string &n) : Service(o, "AccessProvider", n) +{ + Providers.push_back(this); +} + +AccessProvider::~AccessProvider() +{ + std::list::iterator it = std::find(Providers.begin(), Providers.end(), this); + if (it != Providers.end()) + Providers.erase(it); +} + +std::list AccessProvider::Providers; + +const std::list& AccessProvider::GetProviders() +{ + return Providers; +} + +ChanAccess::ChanAccess(AccessProvider *p) : Serializable("ChanAccess"), provider(p) +{ +} + +ChanAccess::~ChanAccess() +{ + if (this->ci) + { + std::vector::iterator it = std::find(this->ci->access->begin(), this->ci->access->end(), this); + if (it != this->ci->access->end()) + this->ci->access->erase(it); + + if (*nc != NULL) + nc->RemoveChannelReference(this->ci); + else + { + ChannelInfo *c = ChannelInfo::Find(this->mask); + if (c) + c->RemoveChannelReference(this->ci->name); + } + } +} + +void ChanAccess::SetMask(const Anope::string &m, ChannelInfo *c) +{ + if (*nc != NULL) + nc->RemoveChannelReference(this->ci); + else if (!this->mask.empty()) + { + ChannelInfo *targc = ChannelInfo::Find(this->mask); + if (targc) + targc->RemoveChannelReference(this->ci->name); + } + + ci = c; + mask.clear(); + nc = NULL; + + const NickAlias *na = NickAlias::Find(m); + if (na != NULL) + { + nc = na->nc; + nc->AddChannelReference(ci); + } + else + { + mask = m; + + ChannelInfo *targci = ChannelInfo::Find(mask); + if (targci != NULL) + targci->AddChannelReference(ci->name); + } +} + +const Anope::string &ChanAccess::Mask() const +{ + if (nc) + return nc->display; + else + return mask; +} + +NickCore *ChanAccess::GetAccount() const +{ + return nc; +} + +void ChanAccess::Serialize(Serialize::Data &data) const +{ + data["provider"] << this->provider->name; + data["ci"] << this->ci->name; + data["mask"] << this->Mask(); + data["creator"] << this->creator; + data.SetType("last_seen", Serialize::Data::DT_INT); data["last_seen"] << this->last_seen; + data.SetType("created", Serialize::Data::DT_INT); data["created"] << this->created; + data["data"] << this->AccessSerialize(); +} + +Serializable* ChanAccess::Unserialize(Serializable *obj, Serialize::Data &data) +{ + Anope::string provider, chan; + + data["provider"] >> provider; + data["ci"] >> chan; + + ServiceReference aprovider("AccessProvider", provider); + ChannelInfo *ci = ChannelInfo::Find(chan); + if (!aprovider || !ci) + return NULL; + + ChanAccess *access; + if (obj) + access = anope_dynamic_static_cast(obj); + else + access = aprovider->Create(); + access->ci = ci; + Anope::string m; + data["mask"] >> m; + access->SetMask(m, ci); + data["creator"] >> access->creator; + data["last_seen"] >> access->last_seen; + data["created"] >> access->created; + + Anope::string adata; + data["data"] >> adata; + access->AccessUnserialize(adata); + + if (!obj) + ci->AddAccess(access); + return access; +} + +bool ChanAccess::Matches(const User *u, const NickCore *acc, ChannelInfo* &next) const +{ + next = NULL; + + if (this->nc) + return this->nc == acc; + + if (u) + { + bool is_mask = this->mask.find_first_of("!@?*") != Anope::string::npos; + if (is_mask && Anope::Match(u->nick, this->mask)) + return true; + else if (Anope::Match(u->GetDisplayedMask(), this->mask)) + return true; + } + + if (acc) + { + for (unsigned i = 0; i < acc->aliases->size(); ++i) + { + const NickAlias *na = acc->aliases->at(i); + if (Anope::Match(na->nick, this->mask)) + return true; + } + } + + if (IRCD->IsChannelValid(this->mask)) + { + next = ChannelInfo::Find(this->mask); + } + + return false; +} + +bool ChanAccess::operator>(const ChanAccess &other) const +{ + const std::vector &privs = PrivilegeManager::GetPrivileges(); + for (unsigned i = privs.size(); i > 0; --i) + { + bool this_p = this->HasPriv(privs[i - 1].name), + other_p = other.HasPriv(privs[i - 1].name); + + if (!this_p && !other_p) + continue; + + return this_p && !other_p; + } + + return false; +} + +bool ChanAccess::operator<(const ChanAccess &other) const +{ + const std::vector &privs = PrivilegeManager::GetPrivileges(); + for (unsigned i = privs.size(); i > 0; --i) + { + bool this_p = this->HasPriv(privs[i - 1].name), + other_p = other.HasPriv(privs[i - 1].name); + + if (!this_p && !other_p) + continue; + + return !this_p && other_p; + } + + return false; +} + +bool ChanAccess::operator>=(const ChanAccess &other) const +{ + return !(*this < other); +} + +bool ChanAccess::operator<=(const ChanAccess &other) const +{ + return !(*this > other); +} + +AccessGroup::AccessGroup() +{ + this->ci = NULL; + this->nc = NULL; + this->super_admin = this->founder = false; +} + +static bool HasPriv(const ChanAccess::Path &path, const Anope::string &name) +{ + if (path.empty()) + return false; + + for (unsigned int i = 0; i < path.size(); ++i) + { + ChanAccess *access = path[i]; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnCheckPriv, MOD_RESULT, (access, name)); + + if (MOD_RESULT != EVENT_ALLOW && !access->HasPriv(name)) + return false; + } + + return true; +} + +bool AccessGroup::HasPriv(const Anope::string &name) const +{ + if (this->super_admin) + return true; + else if (!ci || ci->GetLevel(name) == ACCESS_INVALID) + return false; + + /* Privileges prefixed with auto are understood to be given + * automatically. Sometimes founders want to not automatically + * obtain privileges, so we will let them */ + bool auto_mode = !name.find("AUTO"); + + /* Only grant founder privilege if this isn't an auto mode or if they don't match any entries in this group */ + if ((!auto_mode || paths.empty()) && this->founder) + return true; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnGroupCheckPriv, MOD_RESULT, (this, name)); + if (MOD_RESULT != EVENT_CONTINUE) + return MOD_RESULT == EVENT_ALLOW; + + for (unsigned int i = paths.size(); i > 0; --i) + { + const ChanAccess::Path &path = paths[i - 1]; + + if (::HasPriv(path, name)) + return true; + } + + return false; +} + +static ChanAccess *HighestInPath(const ChanAccess::Path &path) +{ + ChanAccess *highest = NULL; + + for (unsigned int i = 0; i < path.size(); ++i) + if (highest == NULL || *path[i] > *highest) + highest = path[i]; + + return highest; +} + +const ChanAccess *AccessGroup::Highest() const +{ + ChanAccess *highest = NULL; + + for (unsigned int i = 0; i < paths.size(); ++i) + { + ChanAccess *hip = HighestInPath(paths[i]); + + if (highest == NULL || *hip > *highest) + highest = hip; + } + + return highest; +} + +bool AccessGroup::operator>(const AccessGroup &other) const +{ + if (other.super_admin) + return false; + else if (this->super_admin) + return true; + else if (other.founder) + return false; + else if (this->founder) + return true; + + const std::vector &privs = PrivilegeManager::GetPrivileges(); + for (unsigned i = privs.size(); i > 0; --i) + { + bool this_p = this->HasPriv(privs[i - 1].name), + other_p = other.HasPriv(privs[i - 1].name); + + if (!this_p && !other_p) + continue; + + return this_p && !other_p; + } + + return false; +} + +bool AccessGroup::operator<(const AccessGroup &other) const +{ + if (this->super_admin) + return false; + else if (other.super_admin) + return true; + else if (this->founder) + return false; + else if (other.founder) + return true; + + const std::vector &privs = PrivilegeManager::GetPrivileges(); + for (unsigned i = privs.size(); i > 0; --i) + { + bool this_p = this->HasPriv(privs[i - 1].name), + other_p = other.HasPriv(privs[i - 1].name); + + if (!this_p && !other_p) + continue; + + return !this_p && other_p; + } + + return false; +} + +bool AccessGroup::operator>=(const AccessGroup &other) const +{ + return !(*this < other); +} + +bool AccessGroup::operator<=(const AccessGroup &other) const +{ + return !(*this > other); +} diff --git a/src/account.cpp b/src/account.cpp new file mode 100644 index 0000000..af85579 --- /dev/null +++ b/src/account.cpp @@ -0,0 +1,91 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "account.h" +#include "modules.h" +#include "users.h" +#include "protocol.h" +#include "regchannel.h" + +std::set IdentifyRequest::Requests; + +IdentifyRequest::IdentifyRequest(Module *o, const Anope::string &acc, const Anope::string &pass) : owner(o), account(acc), password(pass), dispatched(false), success(false) +{ + Requests.insert(this); +} + +IdentifyRequest::~IdentifyRequest() +{ + Requests.erase(this); +} + +void IdentifyRequest::Hold(Module *m) +{ + holds.insert(m); +} + +void IdentifyRequest::Release(Module *m) +{ + holds.erase(m); + if (holds.empty() && dispatched) + { + if (!success) + this->OnFail(); + delete this; + } +} + +void IdentifyRequest::Success(Module *m) +{ + if (!success) + { + this->OnSuccess(); + success = true; + } +} + +void IdentifyRequest::Dispatch() +{ + if (holds.empty()) + { + if (!success) + this->OnFail(); + delete this; + } + else + dispatched = true; +} + +void IdentifyRequest::ModuleUnload(Module *m) +{ + for (std::set::iterator it = Requests.begin(), it_end = Requests.end(); it != it_end;) + { + IdentifyRequest *ir = *it; + ++it; + + ir->holds.erase(m); + if (ir->holds.empty() && ir->dispatched) + { + if (!ir->success) + ir->OnFail(); + delete ir; + continue; + } + + if (ir->owner == m) + { + if (!ir->success) + ir->OnFail(); + delete ir; + } + } +} diff --git a/src/base.cpp b/src/base.cpp new file mode 100644 index 0000000..824187e --- /dev/null +++ b/src/base.cpp @@ -0,0 +1,48 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "services.h" +#include "anope.h" +#include "service.h" + +std::map > Service::Services; +std::map > Service::Aliases; + +Base::Base() : references(NULL) +{ +} + +Base::~Base() +{ + if (this->references != NULL) + { + for (std::set::iterator it = this->references->begin(), it_end = this->references->end(); it != it_end; ++it) + (*it)->Invalidate(); + delete this->references; + } +} + +void Base::AddReference(ReferenceBase *r) +{ + if (this->references == NULL) + this->references = new std::set(); + this->references->insert(r); +} + +void Base::DelReference(ReferenceBase *r) +{ + if (this->references != NULL) + { + this->references->erase(r); + if (this->references->empty()) + { + delete this->references; + this->references = NULL; + } + } +} diff --git a/src/base64.cpp b/src/base64.cpp new file mode 100644 index 0000000..5c0171b --- /dev/null +++ b/src/base64.cpp @@ -0,0 +1,163 @@ +/* base64 routines. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "anope.h" + +static const Anope::string Base64 = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"; +static const char Pad64 = '='; + +/* (From RFC1521 and draft-ietf-dnssec-secext-03.txt) + The following encoding technique is taken from RFC 1521 by Borenstein + and Freed. It is reproduced here in a slightly edited form for + convenience. + + A 65-character subset of US-ASCII is used, enabling 6 bits to be + represented per printable character. (The extra 65th character, "=", + is used to signify a special processing function.) + + The encoding process represents 24-bit groups of input bits as output + strings of 4 encoded characters. Proceeding from left to right, a + 24-bit input group is formed by concatenating 3 8-bit input groups. + These 24 bits are then treated as 4 concatenated 6-bit groups, each + of which is translated into a single digit in the base64 alphabet. + + Each 6-bit group is used as an index into an array of 64 printable + characters. The character referenced by the index is placed in the + output string. + + Table 1: The Base64 Alphabet + + Value Encoding Value Encoding Value Encoding Value Encoding + 0 A 17 R 34 i 51 z + 1 B 18 S 35 j 52 0 + 2 C 19 T 36 k 53 1 + 3 D 20 U 37 l 54 2 + 4 E 21 V 38 m 55 3 + 5 F 22 W 39 n 56 4 + 6 G 23 X 40 o 57 5 + 7 H 24 Y 41 p 58 6 + 8 I 25 Z 42 q 59 7 + 9 J 26 a 43 r 60 8 + 10 K 27 b 44 s 61 9 + 11 L 28 c 45 t 62 + + 12 M 29 d 46 u 63 / + 13 N 30 e 47 v + 14 O 31 f 48 w (pad) = + 15 P 32 g 49 x + 16 Q 33 h 50 y + + Special processing is performed if fewer than 24 bits are available + at the end of the data being encoded. A full encoding quantum is + always completed at the end of a quantity. When fewer than 24 input + bits are available in an input group, zero bits are added (on the + right) to form an integral number of 6-bit groups. Padding at the + end of the data is performed using the '=' character. + + Since all base64 input is an integral number of octets, only the + ------------------------------------------------- + following cases can arise: + + (1) the final quantum of encoding input is an integral + multiple of 24 bits; here, the final unit of encoded + output will be an integral multiple of 4 characters + with no "=" padding, + (2) the final quantum of encoding input is exactly 8 bits; + here, the final unit of encoded output will be two + characters followed by two "=" padding characters, or + (3) the final quantum of encoding input is exactly 16 bits; + here, the final unit of encoded output will be three + characters followed by one "=" padding character. + */ + +void Anope::B64Encode(const Anope::string &src, Anope::string &target) +{ + size_t src_pos = 0, src_len = src.length(); + unsigned char input[3] = { '\0', '\0', '\0' }; + + target.clear(); + + while (src_len - src_pos > 2) + { + input[0] = src[src_pos++]; + input[1] = src[src_pos++]; + input[2] = src[src_pos++]; + + target += Base64[input[0] >> 2]; + target += Base64[((input[0] & 0x03) << 4) + (input[1] >> 4)]; + target += Base64[((input[1] & 0x0f) << 2) + (input[2] >> 6)]; + target += Base64[input[2] & 0x3f]; + } + + /* Now we worry about padding */ + if (src_pos != src_len) + { + input[0] = input[1] = input[2] = 0; + for (size_t i = 0; i < src_len - src_pos; ++i) + input[i] = src[src_pos + i]; + + target += Base64[input[0] >> 2]; + target += Base64[((input[0] & 0x03) << 4) + (input[1] >> 4)]; + if (src_pos == src_len - 1) + target += Pad64; + else + target += Base64[((input[1] & 0x0f) << 2) + (input[2] >> 6)]; + target += Pad64; + } +} + +/* skips all whitespace anywhere. + converts characters, four at a time, starting at (or after) + src from base - 64 numbers into three 8 bit bytes in the target area. + */ + +void Anope::B64Decode(const Anope::string &src, Anope::string &target) +{ + target.clear(); + + unsigned state = 0; + Anope::string::const_iterator ch = src.begin(), end = src.end(); + for (; ch != end; ++ch) + { + if (isspace(*ch)) /* Skip whitespace anywhere */ + continue; + + if (*ch == Pad64) + break; + + size_t pos = Base64.find(*ch); + if (pos == Anope::string::npos) /* A non-base64 character */ + return; + + switch (state) + { + case 0: + target += pos << 2; + state = 1; + break; + case 1: + target[target.length() - 1] |= pos >> 4; + target += (pos & 0x0f) << 4; + state = 2; + break; + case 2: + target[target.length() - 1] |= pos >> 2; + target += (pos & 0x03) << 6; + state = 3; + break; + case 3: + target[target.length() - 1] |= pos; + state = 0; + } + } + if (!target.empty() && !target[target.length() - 1]) + target.erase(target.length() - 1); +} diff --git a/src/bots.cpp b/src/bots.cpp new file mode 100644 index 0000000..0ea337e --- /dev/null +++ b/src/bots.cpp @@ -0,0 +1,277 @@ +/* + * + * (C) 2008-2011 Robin Burchell + * (C) 2008-2022 Anope Team + * + * Please read COPYING and README for further details. + */ + +#include "services.h" +#include "anope.h" +#include "bots.h" +#include "servers.h" +#include "protocol.h" +#include "xline.h" +#include "regchannel.h" +#include "channels.h" +#include "config.h" +#include "language.h" +#include "serialize.h" + +Serialize::Checker BotListByNick("BotInfo"), BotListByUID("BotInfo"); + +BotInfo::BotInfo(const Anope::string &nnick, const Anope::string &nuser, const Anope::string &nhost, const Anope::string &nreal, const Anope::string &bmodes) : User(nnick, nuser, nhost, "", "", Me, nreal, Anope::CurTime, "", IRCD ? IRCD->UID_Retrieve() : "", NULL), Serializable("BotInfo"), channels("ChannelInfo"), botmodes(bmodes) +{ + this->lastmsg = this->created = Anope::CurTime; + this->introduced = false; + this->oper_only = this->conf = false; + + (*BotListByNick)[this->nick] = this; + if (!this->uid.empty()) + (*BotListByUID)[this->uid] = this; + + FOREACH_MOD(OnCreateBot, (this)); + + // If we're synchronised with the uplink already, send the bot. + if (Me && Me->IsSynced()) + { + Anope::string tmodes = !this->botmodes.empty() ? ("+" + this->botmodes) : IRCD->DefaultPseudoclientModes; + if (!tmodes.empty()) + this->SetModesInternal(this, tmodes.c_str()); + + XLine x(this->nick, "Reserved for services"); + IRCD->SendSQLine(NULL, &x); + IRCD->SendClientIntroduction(this); + this->introduced = true; + } +} + +BotInfo::~BotInfo() +{ + UnsetExtensibles(); + + FOREACH_MOD(OnDelBot, (this)); + + // If we're synchronised with the uplink already, send the bot. + if (Me && Me->IsSynced()) + { + IRCD->SendQuit(this, ""); + FOREACH_MOD(OnUserQuit, (this, "")); + this->introduced = false; + XLine x(this->nick); + IRCD->SendSQLineDel(&x); + } + + for (std::set::iterator it = this->channels->begin(), it_end = this->channels->end(); it != it_end;) + { + ChannelInfo *ci = *it++; + this->UnAssign(NULL, ci); + } + + BotListByNick->erase(this->nick); + if (!this->uid.empty()) + BotListByUID->erase(this->uid); +} + +void BotInfo::Serialize(Serialize::Data &data) const +{ + data["nick"] << this->nick; + data["user"] << this->ident; + data["host"] << this->host; + data["realname"] << this->realname; + data["created"] << this->created; + data["oper_only"] << this->oper_only; + + Extensible::ExtensibleSerialize(this, this, data); +} + +Serializable* BotInfo::Unserialize(Serializable *obj, Serialize::Data &data) +{ + Anope::string nick, user, host, realname, flags; + + data["nick"] >> nick; + data["user"] >> user; + data["host"] >> host; + data["realname"] >> realname; + + BotInfo *bi; + if (obj) + bi = anope_dynamic_static_cast(obj); + else if (!(bi = BotInfo::Find(nick, true))) + bi = new BotInfo(nick, user, host, realname); + + data["created"] >> bi->created; + data["oper_only"] >> bi->oper_only; + + Extensible::ExtensibleUnserialize(bi, bi, data); + + return bi; +} + +void BotInfo::GenerateUID() +{ + if (this->introduced) + throw CoreException("Changing bot UID when it is introduced?"); + + if (!this->uid.empty()) + { + BotListByUID->erase(this->uid); + UserListByUID.erase(this->uid); + } + + this->uid = IRCD->UID_Retrieve(); + (*BotListByUID)[this->uid] = this; + UserListByUID[this->uid] = this; +} + +void BotInfo::OnKill() +{ + this->introduced = false; + this->GenerateUID(); + IRCD->SendClientIntroduction(this); + this->introduced = true; + + for (User::ChanUserList::const_iterator cit = this->chans.begin(), cit_end = this->chans.end(); cit != cit_end; ++cit) + IRCD->SendJoin(this, cit->second->chan, &cit->second->status); +} + +void BotInfo::SetNewNick(const Anope::string &newnick) +{ + UserListByNick.erase(this->nick); + BotListByNick->erase(this->nick); + + this->nick = newnick; + + UserListByNick[this->nick] = this; + (*BotListByNick)[this->nick] = this; +} + +const std::set &BotInfo::GetChannels() const +{ + return this->channels; +} + +void BotInfo::Assign(User *u, ChannelInfo *ci) +{ + EventReturn MOD_RESULT; + FOREACH_RESULT(OnPreBotAssign, MOD_RESULT, (u, ci, this)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (ci->bi) + ci->bi->UnAssign(u, ci); + + ci->bi = this; + this->channels->insert(ci); + + FOREACH_MOD(OnBotAssign, (u, ci, this)); +} + +void BotInfo::UnAssign(User *u, ChannelInfo *ci) +{ + EventReturn MOD_RESULT; + FOREACH_RESULT(OnBotUnAssign, MOD_RESULT, (u, ci)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (ci->c && ci->c->FindUser(ci->bi)) + { + if (u) + ci->bi->Part(ci->c, "UNASSIGN from " + u->nick); + else + ci->bi->Part(ci->c); + } + + ci->bi = NULL; + this->channels->erase(ci); +} + +unsigned BotInfo::GetChannelCount() const +{ + return this->channels->size(); +} + +void BotInfo::Join(Channel *c, ChannelStatus *status) +{ + if (c->FindUser(this) != NULL) + return; + + c->JoinUser(this, status); + if (IRCD) + IRCD->SendJoin(this, c, status); + + FOREACH_MOD(OnJoinChannel, (this, c)); +} + +void BotInfo::Join(const Anope::string &chname, ChannelStatus *status) +{ + bool c; + return this->Join(Channel::FindOrCreate(chname, c), status); +} + +void BotInfo::Part(Channel *c, const Anope::string &reason) +{ + if (c->FindUser(this) == NULL) + return; + + FOREACH_MOD(OnPrePartChannel, (this, c)); + + IRCD->SendPart(this, c, "%s", !reason.empty() ? reason.c_str() : ""); + + c->DeleteUser(this); + + FOREACH_MOD(OnPartChannel, (this, c, c->name, reason)); +} + +void BotInfo::OnMessage(User *u, const Anope::string &message) +{ + if (this->commands.empty()) + return; + + CommandSource source(u->nick, u, u->Account(), u, this); + Command::Run(source, message); +} + +CommandInfo& BotInfo::SetCommand(const Anope::string &cname, const Anope::string &sname, const Anope::string &permission) +{ + CommandInfo ci; + ci.name = sname; + ci.permission = permission; + this->commands[cname] = ci; + return this->commands[cname]; +} + +CommandInfo *BotInfo::GetCommand(const Anope::string &cname) +{ + CommandInfo::map::iterator it = this->commands.find(cname); + if (it != this->commands.end()) + return &it->second; + return NULL; +} + +BotInfo* BotInfo::Find(const Anope::string &nick, bool nick_only) +{ + if (!nick_only && IRCD != NULL && IRCD->RequiresID) + { + botinfo_map::iterator it = BotListByUID->find(nick); + if (it != BotListByUID->end()) + { + BotInfo *bi = it->second; + bi->QueueUpdate(); + return bi; + } + + if (IRCD->AmbiguousID) + return NULL; + } + + botinfo_map::iterator it = BotListByNick->find(nick); + if (it != BotListByNick->end()) + { + BotInfo *bi = it->second; + bi->QueueUpdate(); + return bi; + } + + return NULL; +} diff --git a/src/channels.cpp b/src/channels.cpp new file mode 100644 index 0000000..d17cea7 --- /dev/null +++ b/src/channels.cpp @@ -0,0 +1,961 @@ +/* Channel-handling routines. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "channels.h" +#include "regchannel.h" +#include "logger.h" +#include "modules.h" +#include "users.h" +#include "bots.h" +#include "servers.h" +#include "protocol.h" +#include "users.h" +#include "config.h" +#include "access.h" +#include "sockets.h" +#include "language.h" +#include "uplink.h" + +channel_map ChannelList; +std::vector Channel::deleting; + +Channel::Channel(const Anope::string &nname, time_t ts) +{ + if (nname.empty()) + throw CoreException("A channel without a name ?"); + + this->name = nname; + + this->creation_time = ts; + this->syncing = this->botchannel = false; + this->server_modetime = this->chanserv_modetime = 0; + this->server_modecount = this->chanserv_modecount = this->bouncy_modes = this->topic_ts = this->topic_time = 0; + + this->ci = ChannelInfo::Find(this->name); + if (this->ci) + this->ci->c = this; + + if (Me && Me->IsSynced()) + Log(NULL, this, "create"); + + FOREACH_MOD(OnChannelCreate, (this)); +} + +Channel::~Channel() +{ + UnsetExtensibles(); + + FOREACH_MOD(OnChannelDelete, (this)); + + ModeManager::StackerDel(this); + + if (Me && Me->IsSynced()) + Log(NULL, this, "destroy"); + + if (this->ci) + this->ci->c = NULL; + + ChannelList.erase(this->name); +} + +void Channel::Reset() +{ + this->modes.clear(); + + for (ChanUserList::const_iterator it = this->users.begin(), it_end = this->users.end(); it != it_end; ++it) + { + ChanUserContainer *uc = it->second; + + ChannelStatus f = uc->status; + uc->status.Clear(); + + /* reset modes for my clients */ + if (uc->user->server == Me) + { + for (size_t i = 0; i < f.Modes().length(); ++i) + this->SetMode(NULL, ModeManager::FindChannelModeByChar(f.Modes()[i]), uc->user->GetUID(), false); + /* Modes might not exist yet, so be sure the status is really reset */ + uc->status = f; + } + } + + for (ChanUserList::const_iterator it = this->users.begin(), it_end = this->users.end(); it != it_end; ++it) + this->SetCorrectModes(it->second->user, true); + + // If the channel is syncing now, do not force a sync due to Reset(), as we are probably iterating over users in Message::SJoin + // A sync will come soon + if (!syncing) + this->Sync(); +} + +void Channel::Sync() +{ + syncing = false; + FOREACH_MOD(OnChannelSync, (this)); + CheckModes(); +} + +void Channel::CheckModes() +{ + if (this->bouncy_modes || this->syncing) + return; + + /* Check for mode bouncing */ + if (this->chanserv_modetime == Anope::CurTime && this->server_modetime == Anope::CurTime && this->server_modecount >= 3 && this->chanserv_modecount >= 3) + { + Log() << "Warning: unable to set modes on channel " << this->name << ". Are your servers' U:lines configured correctly?"; + this->bouncy_modes = 1; + return; + } + + Reference ref = this; + FOREACH_MOD(OnCheckModes, (ref)); +} + +bool Channel::CheckDelete() +{ + /* Channel is syncing from a netburst, don't destroy it as more users are probably wanting to join immediately + * We also don't part the bot here either, if necessary we will part it after the sync + */ + if (this->syncing) + return false; + + /* Permanent channels never get deleted */ + if (this->HasMode("PERM")) + return false; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnCheckDelete, MOD_RESULT, (this)); + + return MOD_RESULT != EVENT_STOP && this->users.empty(); +} + +ChanUserContainer* Channel::JoinUser(User *user, const ChannelStatus *status) +{ + if (user->server && user->server->IsSynced()) + Log(user, this, "join"); + + ChanUserContainer *cuc = new ChanUserContainer(user, this); + user->chans[this] = cuc; + this->users[user] = cuc; + if (status) + cuc->status = *status; + + return cuc; +} + +void Channel::DeleteUser(User *user) +{ + if (user->server && user->server->IsSynced() && !user->Quitting()) + Log(user, this, "leave"); + + FOREACH_MOD(OnLeaveChannel, (user, this)); + + ChanUserContainer *cu = user->FindChannel(this); + if (!this->users.erase(user)) + Log(LOG_DEBUG) << "Channel::DeleteUser() tried to delete nonexistent user " << user->nick << " from channel " << this->name; + + if (!user->chans.erase(this)) + Log(LOG_DEBUG) << "Channel::DeleteUser() tried to delete nonexistent channel " << this->name << " from " << user->nick << "'s channel list"; + delete cu; + + QueueForDeletion(); +} + +ChanUserContainer *Channel::FindUser(User *u) const +{ + ChanUserList::const_iterator it = this->users.find(u); + if (it != this->users.end()) + return it->second; + return NULL; +} + +bool Channel::HasUserStatus(User *u, ChannelModeStatus *cms) +{ + /* Usually its more efficient to search the users channels than the channels users */ + ChanUserContainer *cc = u->FindChannel(this); + if (cc) + { + if (cms) + return cc->status.HasMode(cms->mchar); + else + return cc->status.Empty(); + } + + return false; +} + +bool Channel::HasUserStatus(User *u, const Anope::string &mname) +{ + return HasUserStatus(u, anope_dynamic_static_cast(ModeManager::FindChannelModeByName(mname))); +} + +size_t Channel::HasMode(const Anope::string &mname, const Anope::string ¶m) +{ + if (param.empty()) + return modes.count(mname); + std::vector v = this->GetModeList(mname); + for (unsigned int i = 0; i < v.size(); ++i) + if (v[i].equals_ci(param)) + return 1; + return 0; +} + +Anope::string Channel::GetModes(bool complete, bool plus) +{ + Anope::string res, params; + + for (std::multimap::const_iterator it = this->modes.begin(), it_end = this->modes.end(); it != it_end; ++it) + { + ChannelMode *cm = ModeManager::FindChannelModeByName(it->first); + if (!cm || cm->type == MODE_LIST) + continue; + + res += cm->mchar; + + if (complete && !it->second.empty()) + { + ChannelModeParam *cmp = NULL; + if (cm->type == MODE_PARAM) + cmp = anope_dynamic_static_cast(cm); + + if (plus || !cmp || !cmp->minus_no_arg) + params += " " + it->second; + } + } + + return res + params; +} + +const Channel::ModeList &Channel::GetModes() const +{ + return this->modes; +} + +template +struct second +{ + S operator()(const std::pair &p) + { + return p.second; + } +}; + +std::vector Channel::GetModeList(const Anope::string &mname) +{ + std::vector r; + std::transform(modes.lower_bound(mname), modes.upper_bound(mname), std::back_inserter(r), second()); + return r; +} + +void Channel::SetModeInternal(MessageSource &setter, ChannelMode *ocm, const Anope::string &oparam, bool enforce_mlock) +{ + if (!ocm) + return; + + Anope::string param = oparam; + ChannelMode *cm = ocm->Unwrap(param); + + EventReturn MOD_RESULT; + + /* Setting v/h/o/a/q etc */ + if (cm->type == MODE_STATUS) + { + if (param.empty()) + { + Log() << "Channel::SetModeInternal() mode " << cm->mchar << " with no parameter for channel " << this->name; + return; + } + + User *u = User::Find(param); + + if (!u) + { + Log(LOG_DEBUG) << "MODE " << this->name << " +" << cm->mchar << " for nonexistent user " << param; + return; + } + + Log(LOG_DEBUG) << "Setting +" << cm->mchar << " on " << this->name << " for " << u->nick; + + /* Set the status on the user */ + ChanUserContainer *cc = u->FindChannel(this); + if (cc) + cc->status.AddMode(cm->mchar); + + FOREACH_RESULT(OnChannelModeSet, MOD_RESULT, (this, setter, cm, param)); + + /* Enforce secureops, etc */ + if (enforce_mlock && MOD_RESULT != EVENT_STOP) + this->SetCorrectModes(u, false); + return; + } + + if (cm->type != MODE_LIST) + this->modes.erase(cm->name); + else if (this->HasMode(cm->name, param)) + return; + + this->modes.insert(std::make_pair(cm->name, param)); + + if (param.empty() && cm->type != MODE_REGULAR) + { + Log() << "Channel::SetModeInternal() mode " << cm->mchar << " for " << this->name << " with no paramater, but is a param mode"; + return; + } + + if (cm->type == MODE_LIST) + { + ChannelModeList *cml = anope_dynamic_static_cast(cm); + cml->OnAdd(this, param); + } + + FOREACH_RESULT(OnChannelModeSet, MOD_RESULT, (this, setter, cm, param)); + + /* Check if we should enforce mlock */ + if (!enforce_mlock || MOD_RESULT == EVENT_STOP) + return; + + this->CheckModes(); +} + +void Channel::RemoveModeInternal(MessageSource &setter, ChannelMode *ocm, const Anope::string &oparam, bool enforce_mlock) +{ + if (!ocm) + return; + + Anope::string param = oparam; + ChannelMode *cm = ocm->Unwrap(param); + + EventReturn MOD_RESULT; + + /* Setting v/h/o/a/q etc */ + if (cm->type == MODE_STATUS) + { + if (param.empty()) + { + Log() << "Channel::RemoveModeInternal() mode " << cm->mchar << " with no parameter for channel " << this->name; + return; + } + + BotInfo *bi = BotInfo::Find(param); + User *u = bi ? bi : User::Find(param); + + if (!u) + { + Log(LOG_DEBUG) << "Channel::RemoveModeInternal() MODE " << this->name << "-" << cm->mchar << " for nonexistent user " << param; + return; + } + + Log(LOG_DEBUG) << "Setting -" << cm->mchar << " on " << this->name << " for " << u->nick; + + /* Remove the status on the user */ + ChanUserContainer *cc = u->FindChannel(this); + if (cc) + cc->status.DelMode(cm->mchar); + + FOREACH_RESULT(OnChannelModeUnset, MOD_RESULT, (this, setter, cm, param)); + + if (enforce_mlock && MOD_RESULT != EVENT_STOP) + this->SetCorrectModes(u, false); + + return; + } + + if (cm->type == MODE_LIST) + { + for (Channel::ModeList::iterator it = modes.lower_bound(cm->name), it_end = modes.upper_bound(cm->name); it != it_end; ++it) + if (param.equals_ci(it->second)) + { + this->modes.erase(it); + break; + } + } + else + this->modes.erase(cm->name); + + if (cm->type == MODE_LIST) + { + ChannelModeList *cml = anope_dynamic_static_cast(cm); + cml->OnDel(this, param); + } + + FOREACH_RESULT(OnChannelModeUnset, MOD_RESULT, (this, setter, cm, param)); + + if (cm->name == "PERM") + { + if (this->CheckDelete()) + { + delete this; + return; + } + } + + /* Check for mlock */ + if (!enforce_mlock || MOD_RESULT == EVENT_STOP) + return; + + this->CheckModes(); +} + +void Channel::SetMode(BotInfo *bi, ChannelMode *cm, const Anope::string ¶m, bool enforce_mlock) +{ + Anope::string wparam = param; + if (!cm) + return; + /* Don't set modes already set */ + if (cm->type == MODE_REGULAR && HasMode(cm->name)) + return; + else if (cm->type == MODE_PARAM) + { + ChannelModeParam *cmp = anope_dynamic_static_cast(cm); + if (!cmp->IsValid(wparam)) + return; + + Anope::string cparam; + if (GetParam(cm->name, cparam) && cparam.equals_cs(wparam)) + return; + } + else if (cm->type == MODE_STATUS) + { + User *u = User::Find(param); + if (!u || HasUserStatus(u, anope_dynamic_static_cast(cm))) + return; + } + else if (cm->type == MODE_LIST) + { + ChannelModeList *cml = anope_dynamic_static_cast(cm); + + if (!cml->IsValid(wparam)) + return; + + if (this->HasMode(cm->name, wparam)) + return; + } + + if (Me->IsSynced()) + { + if (this->chanserv_modetime != Anope::CurTime) + { + this->chanserv_modecount = 0; + this->chanserv_modetime = Anope::CurTime; + } + + this->chanserv_modecount++; + } + + ChannelMode *wcm = cm->Wrap(wparam); + + ModeManager::StackerAdd(bi, this, wcm, true, wparam); + MessageSource ms(bi); + SetModeInternal(ms, wcm, wparam, enforce_mlock); +} + +void Channel::SetMode(BotInfo *bi, const Anope::string &mname, const Anope::string ¶m, bool enforce_mlock) +{ + SetMode(bi, ModeManager::FindChannelModeByName(mname), param, enforce_mlock); +} + +void Channel::RemoveMode(BotInfo *bi, ChannelMode *cm, const Anope::string &wparam, bool enforce_mlock) +{ + if (!cm) + return; + + /* Don't unset modes that arent set */ + if ((cm->type == MODE_REGULAR || cm->type == MODE_PARAM) && !HasMode(cm->name)) + return; + + /* Unwrap to be sure we have the internal representation */ + Anope::string param = wparam; + cm = cm->Unwrap(param); + + /* Don't unset status that aren't set */ + if (cm->type == MODE_STATUS) + { + User *u = User::Find(param); + if (!u || !HasUserStatus(u, anope_dynamic_static_cast(cm))) + return; + } + else if (cm->type == MODE_LIST) + { + if (!this->HasMode(cm->name, param)) + return; + } + + /* Get the param to send, if we need it */ + if (cm->type == MODE_PARAM) + { + param.clear(); + ChannelModeParam *cmp = anope_dynamic_static_cast(cm); + if (!cmp->minus_no_arg) + this->GetParam(cmp->name, param); + } + + if (Me->IsSynced()) + { + if (this->chanserv_modetime != Anope::CurTime) + { + this->chanserv_modecount = 0; + this->chanserv_modetime = Anope::CurTime; + } + + this->chanserv_modecount++; + } + + /* Wrap to get ircd representation */ + ChannelMode *wcm = cm->Wrap(param); + + ModeManager::StackerAdd(bi, this, wcm, false, param); + MessageSource ms(bi); + RemoveModeInternal(ms, wcm, param, enforce_mlock); +} + +void Channel::RemoveMode(BotInfo *bi, const Anope::string &mname, const Anope::string ¶m, bool enforce_mlock) +{ + RemoveMode(bi, ModeManager::FindChannelModeByName(mname), param, enforce_mlock); +} + +bool Channel::GetParam(const Anope::string &mname, Anope::string &target) const +{ + std::multimap::const_iterator it = this->modes.find(mname); + + target.clear(); + + if (it != this->modes.end()) + { + target = it->second; + return true; + } + + return false; +} + +void Channel::SetModes(BotInfo *bi, bool enforce_mlock, const char *cmodes, ...) +{ + char buf[BUFSIZE] = ""; + va_list args; + Anope::string modebuf, sbuf; + int add = -1; + va_start(args, cmodes); + vsnprintf(buf, BUFSIZE - 1, cmodes, args); + va_end(args); + + Reference this_reference(this); + + spacesepstream sep(buf); + sep.GetToken(modebuf); + for (unsigned i = 0, end = modebuf.length(); this_reference && i < end; ++i) + { + ChannelMode *cm; + + switch (modebuf[i]) + { + case '+': + add = 1; + continue; + case '-': + add = 0; + continue; + default: + if (add == -1) + continue; + cm = ModeManager::FindChannelModeByChar(modebuf[i]); + if (!cm) + continue; + } + + if (add) + { + if (cm->type != MODE_REGULAR && sep.GetToken(sbuf)) + { + if (cm->type == MODE_STATUS) + { + User *targ = User::Find(sbuf); + if (targ != NULL) + sbuf = targ->GetUID(); + } + this->SetMode(bi, cm, sbuf, enforce_mlock); + } + else + this->SetMode(bi, cm, "", enforce_mlock); + } + else if (!add) + { + if (cm->type != MODE_REGULAR && sep.GetToken(sbuf)) + { + if (cm->type == MODE_STATUS) + { + User *targ = User::Find(sbuf); + if (targ != NULL) + sbuf = targ->GetUID(); + } + this->RemoveMode(bi, cm, sbuf, enforce_mlock); + } + else + this->RemoveMode(bi, cm, "", enforce_mlock); + } + } +} + +void Channel::SetModesInternal(MessageSource &source, const Anope::string &mode, time_t ts, bool enforce_mlock) +{ + if (!ts) + ; + else if (ts > this->creation_time) + { + Log(LOG_DEBUG) << "Dropping mode " << mode << " on " << this->name << ", " << ts << " > " << this->creation_time; + return; + } + else if (ts < this->creation_time) + { + Log(LOG_DEBUG) << "Changing TS of " << this->name << " from " << this->creation_time << " to " << ts; + this->creation_time = ts; + this->Reset(); + } + + User *setter = source.GetUser(); + /* Removing channel modes *may* delete this channel */ + Reference this_reference(this); + + spacesepstream sep_modes(mode); + Anope::string m; + + sep_modes.GetToken(m); + + Anope::string modestring; + Anope::string paramstring; + int add = -1; + bool changed = false; + for (unsigned int i = 0, end = m.length(); i < end && this_reference; ++i) + { + ChannelMode *cm; + + switch (m[i]) + { + case '+': + modestring += '+'; + add = 1; + continue; + case '-': + modestring += '-'; + add = 0; + continue; + default: + if (add == -1) + continue; + cm = ModeManager::FindChannelModeByChar(m[i]); + if (!cm) + { + Log(LOG_DEBUG) << "Channel::SetModeInternal: Unknown mode char " << m[i]; + continue; + } + modestring += cm->mchar; + } + + if (cm->type == MODE_REGULAR) + { + /* something changed if we are adding a mode we don't have, or removing one we have */ + changed |= !!add != this->HasMode(cm->name); + if (add) + this->SetModeInternal(source, cm, "", false); + else + this->RemoveModeInternal(source, cm, "", false); + continue; + } + else if (cm->type == MODE_PARAM) + { + ChannelModeParam *cmp = anope_dynamic_static_cast(cm); + + if (!add && cmp->minus_no_arg) + { + this->RemoveModeInternal(source, cm, "", false); + continue; + } + } + Anope::string token; + if (sep_modes.GetToken(token)) + { + User *u = NULL; + if (cm->type == MODE_STATUS && (u = User::Find(token))) + paramstring += " " + u->nick; + else + paramstring += " " + token; + + changed |= !!add != this->HasMode(cm->name, token); + /* CheckModes below doesn't check secureops (+ the module event) */ + if (add) + this->SetModeInternal(source, cm, token, enforce_mlock); + else + this->RemoveModeInternal(source, cm, token, enforce_mlock); + } + else + Log() << "warning: Channel::SetModesInternal() received more modes requiring params than params, modes: " << mode; + } + + if (!this_reference) + return; + + if (changed && source.GetServer() && source.GetServer()->IsSynced()) + { + if (Anope::CurTime != this->server_modetime) + { + this->server_modecount = 0; + this->server_modetime = Anope::CurTime; + } + + ++this->server_modecount; + } + + if (setter) + Log(setter, this, "mode") << modestring << paramstring; + else + Log(LOG_DEBUG) << source.GetName() << " is setting " << this->name << " to " << modestring << paramstring; + + if (enforce_mlock) + this->CheckModes(); +} + +bool Channel::MatchesList(User *u, const Anope::string &mode) +{ + if (!this->HasMode(mode)) + return false; + + std::vector v = this->GetModeList(mode); + for (unsigned i = 0; i < v.size(); ++i) + { + Entry e(mode, v[i]); + if (e.Matches(u)) + return true; + } + + return false; +} + +void Channel::KickInternal(const MessageSource &source, const Anope::string &nick, const Anope::string &reason) +{ + User *sender = source.GetUser(); + User *target = User::Find(nick); + if (!target) + { + Log(LOG_DEBUG) << "Channel::KickInternal got a nonexistent user " << nick << " on " << this->name << ": " << reason; + return; + } + + if (sender) + Log(sender, this, "kick") << "kicked " << target->nick << " (" << reason << ")"; + else + Log(target, this, "kick") << "was kicked by " << source.GetName() << " (" << reason << ")"; + + Anope::string chname = this->name; + + ChanUserContainer *cu = target->FindChannel(this); + if (cu == NULL) + { + Log(LOG_DEBUG) << "Channel::KickInternal got kick for user " << target->nick << " from " << source.GetSource() << " who isn't on channel " << this->name; + return; + } + + ChannelStatus status = cu->status; + + FOREACH_MOD(OnPreUserKicked, (source, cu, reason)); + this->DeleteUser(target); + FOREACH_MOD(OnUserKicked, (source, target, this->name, status, reason)); +} + +bool Channel::Kick(BotInfo *bi, User *u, const char *reason, ...) +{ + va_list args; + char buf[BUFSIZE] = ""; + va_start(args, reason); + vsnprintf(buf, BUFSIZE - 1, reason, args); + va_end(args); + + /* Do not kick protected clients or Ulines */ + if (u->IsProtected()) + return false; + + if (bi == NULL) + bi = this->ci->WhoSends(); + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnBotKick, MOD_RESULT, (bi, this, u, buf)); + if (MOD_RESULT == EVENT_STOP) + return false; + IRCD->SendKick(bi, this, u, "%s", buf); + this->KickInternal(bi, u->nick, buf); + return true; +} + +void Channel::ChangeTopicInternal(User *u, const Anope::string &user, const Anope::string &newtopic, time_t ts) +{ + this->topic = newtopic; + this->topic_setter = u ? u->nick : user; + this->topic_ts = ts; + this->topic_time = Anope::CurTime; + + Log(LOG_DEBUG) << "Topic of " << this->name << " changed by " << this->topic_setter << " to " << newtopic; + + FOREACH_MOD(OnTopicUpdated, (u, this, user, this->topic)); +} + +void Channel::ChangeTopic(const Anope::string &user, const Anope::string &newtopic, time_t ts) +{ + this->topic = newtopic; + this->topic_setter = user; + this->topic_ts = ts; + + IRCD->SendTopic(this->ci->WhoSends(), this); + + /* Now that the topic is set update the time set. This is *after* we set it so the protocol modules are able to tell the old last set time */ + this->topic_time = Anope::CurTime; + + FOREACH_MOD(OnTopicUpdated, (NULL, this, user, this->topic)); +} + +void Channel::SetCorrectModes(User *user, bool give_modes) +{ + if (user == NULL) + return; + + if (!this->ci) + return; + + Log(LOG_DEBUG) << "Setting correct user modes for " << user->nick << " on " << this->name << " (" << (give_modes ? "" : "not ") << "giving modes)"; + + AccessGroup u_access = ci->AccessFor(user); + + /* Initially only take modes if the channel is being created by a non netmerge */ + bool take_modes = this->syncing && user->server->IsSynced(); + + FOREACH_MOD(OnSetCorrectModes, (user, this, u_access, give_modes, take_modes)); + + /* Never take modes from ulines */ + if (user->server->IsULined()) + take_modes = false; + + /* whether or not we are giving modes */ + bool giving = give_modes; + /* whether or not we have given a mode */ + bool given = false; + for (unsigned i = 0; i < ModeManager::GetStatusChannelModesByRank().size(); ++i) + { + ChannelModeStatus *cm = ModeManager::GetStatusChannelModesByRank()[i]; + bool has_priv = u_access.HasPriv("AUTO" + cm->name); + + if (give_modes && has_priv) + { + /* Always give op. If we have already given one mode, don't give more until it has a symbol */ + if (cm->name == "OP" || !given || (giving && cm->symbol)) + { + this->SetMode(NULL, cm, user->GetUID(), false); + /* Now if this contains a symbol don't give any more modes, to prevent setting +qaohv etc on users */ + giving = !cm->symbol; + given = true; + } + } + /* modes that have no privileges assigned shouldn't be removed (like operprefix, ojoin) */ + else if (take_modes && !has_priv && ci->GetLevel(cm->name + "ME") != ACCESS_INVALID && !u_access.HasPriv(cm->name + "ME")) + { + /* Only remove modes if they are > voice */ + if (cm->name == "VOICE") + take_modes = false; + else + this->RemoveMode(NULL, cm, user->GetUID(), false); + } + } +} + +bool Channel::Unban(User *u, const Anope::string &mode, bool full) +{ + if (!this->HasMode(mode)) + return false; + + bool ret = false; + + std::vector v = this->GetModeList(mode); + for (unsigned int i = 0; i < v.size(); ++i) + { + Entry ban(mode, v[i]); + if (ban.Matches(u, full)) + { + this->RemoveMode(NULL, mode, ban.GetMask()); + ret = true; + } + } + + return ret; +} + +bool Channel::CheckKick(User *user) +{ + if (user->super_admin) + return false; + + /* We don't enforce services restrictions on clients on ulined services + * as this will likely lead to kick/rejoin floods. ~ Viper */ + if (user->IsProtected()) + return false; + + Anope::string mask, reason; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnCheckKick, MOD_RESULT, (user, this, mask, reason)); + if (MOD_RESULT != EVENT_STOP) + return false; + + if (mask.empty()) + mask = this->ci->GetIdealBan(user); + if (reason.empty()) + reason = Language::Translate(user->Account(), CHAN_NOT_ALLOWED_TO_JOIN); + + Log(LOG_DEBUG) << "Autokicking " << user->nick << " (" << mask << ") from " << this->name; + + this->SetMode(NULL, "BAN", mask); + this->Kick(NULL, user, "%s", reason.c_str()); + + return true; +} + +Channel* Channel::Find(const Anope::string &name) +{ + channel_map::const_iterator it = ChannelList.find(name); + + if (it != ChannelList.end()) + return it->second; + return NULL; +} + +Channel *Channel::FindOrCreate(const Anope::string &name, bool &created, time_t ts) +{ + Channel* &chan = ChannelList[name]; + created = chan == NULL; + if (!chan) + chan = new Channel(name, ts); + return chan; +} + +void Channel::QueueForDeletion() +{ + if (std::find(deleting.begin(), deleting.end(), this) == deleting.end()) + deleting.push_back(this); +} + +void Channel::DeleteChannels() +{ + for (unsigned int i = 0; i < deleting.size(); ++i) + { + Channel *c = deleting[i]; + + if (c->CheckDelete()) + delete c; + } + deleting.clear(); +} diff --git a/src/command.cpp b/src/command.cpp new file mode 100644 index 0000000..6e4fa1a --- /dev/null +++ b/src/command.cpp @@ -0,0 +1,314 @@ +/* + * + * (C) 2008-2011 Robin Burchell + * (C) 2008-2022 Anope Team + * + * Please read COPYING and README for further details. + */ + +#include "services.h" +#include "commands.h" +#include "users.h" +#include "language.h" +#include "config.h" +#include "bots.h" +#include "opertype.h" +#include "access.h" +#include "regchannel.h" +#include "channels.h" + +CommandSource::CommandSource(const Anope::string &n, User *user, NickCore *core, CommandReply *r, BotInfo *bi) : nick(n), u(user), nc(core), reply(r), + c(NULL), service(bi) +{ +} + +const Anope::string &CommandSource::GetNick() const +{ + return this->nick; +} + +User *CommandSource::GetUser() +{ + return this->u; +} + +NickCore *CommandSource::GetAccount() +{ + return this->nc; +} + +AccessGroup CommandSource::AccessFor(ChannelInfo *ci) +{ + if (this->u) + return ci->AccessFor(this->u); + else if (this->nc) + return ci->AccessFor(this->nc); + else + return AccessGroup(); +} + +bool CommandSource::IsFounder(ChannelInfo *ci) +{ + if (this->u) + return ::IsFounder(this->u, ci); + else if (this->nc) + return *this->nc == ci->GetFounder(); + return false; +} + +bool CommandSource::HasCommand(const Anope::string &cmd) +{ + if (this->u) + return this->u->HasCommand(cmd); + else if (this->nc && this->nc->o) + return this->nc->o->ot->HasCommand(cmd); + return false; +} + +bool CommandSource::HasPriv(const Anope::string &cmd) +{ + if (this->u) + return this->u->HasPriv(cmd); + else if (this->nc && this->nc->o) + return this->nc->o->ot->HasPriv(cmd); + return false; +} + +bool CommandSource::IsServicesOper() +{ + if (this->u) + return this->u->IsServicesOper(); + else if (this->nc) + return this->nc->IsServicesOper(); + return false; +} + +bool CommandSource::IsOper() +{ + if (this->u) + return this->u->HasMode("OPER"); + else if (this->nc) + return this->nc->IsServicesOper(); + return false; +} + +void CommandSource::Reply(const char *message, ...) +{ + va_list args; + char buf[4096]; // Messages can be really big. + + const char *translated_message = Language::Translate(this->nc, message); + + va_start(args, message); + vsnprintf(buf, sizeof(buf), translated_message, args); + + this->Reply(Anope::string(buf)); + + va_end(args); +} + +void CommandSource::Reply(const Anope::string &message) +{ + const char *translated_message = Language::Translate(this->nc, message.c_str()); + + sepstream sep(translated_message, '\n', true); + Anope::string tok; + while (sep.GetToken(tok)) + this->reply->SendMessage(this->service, tok); +} + +Command::Command(Module *o, const Anope::string &sname, size_t minparams, size_t maxparams) : Service(o, "Command", sname), max_params(maxparams), min_params(minparams), module(o) +{ + allow_unregistered = require_user = false; +} + +Command::~Command() +{ +} + +void Command::SetDesc(const Anope::string &d) +{ + this->desc = d; +} + +void Command::ClearSyntax() +{ + this->syntax.clear(); +} + +void Command::SetSyntax(const Anope::string &s) +{ + this->syntax.push_back(s); +} + +void Command::SendSyntax(CommandSource &source) +{ + Anope::string s = Language::Translate(source.GetAccount(), _("Syntax")); + if (!this->syntax.empty()) + { + source.Reply("%s: \002%s %s\002", s.c_str(), source.command.c_str(), Language::Translate(source.GetAccount(), this->syntax[0].c_str())); + Anope::string spaces(s.length(), ' '); + for (unsigned i = 1, j = this->syntax.size(); i < j; ++i) + source.Reply("%s \002%s %s\002", spaces.c_str(), source.command.c_str(), Language::Translate(source.GetAccount(), this->syntax[i].c_str())); + } + else + source.Reply("%s: \002%s\002", s.c_str(), source.command.c_str()); +} + +bool Command::AllowUnregistered() const +{ + return this->allow_unregistered; +} + +void Command::AllowUnregistered(bool b) +{ + this->allow_unregistered = b; +} + +bool Command::RequireUser() const +{ + return this->require_user; +} + +void Command::RequireUser(bool b) +{ + this->require_user = b; +} + +const Anope::string Command::GetDesc(CommandSource &) const +{ + return this->desc; +} + +void Command::OnServHelp(CommandSource &source) +{ + source.Reply(" %-14s %s", source.command.c_str(), Language::Translate(source.nc, this->GetDesc(source).c_str())); +} + +bool Command::OnHelp(CommandSource &source, const Anope::string &subcommand) { return false; } + +void Command::OnSyntaxError(CommandSource &source, const Anope::string &subcommand) +{ + this->SendSyntax(source); + bool has_help = source.service->commands.find("HELP") != source.service->commands.end(); + if (has_help) + source.Reply(MORE_INFO, Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), source.command.c_str()); +} + +void Command::Run(CommandSource &source, const Anope::string &message) +{ + std::vector params; + spacesepstream(message).GetTokens(params); + bool has_help = source.service->commands.find("HELP") != source.service->commands.end(); + + CommandInfo::map::const_iterator it = source.service->commands.end(); + unsigned count = 0; + for (unsigned max = params.size(); it == source.service->commands.end() && max > 0; --max) + { + Anope::string full_command; + for (unsigned i = 0; i < max; ++i) + full_command += " " + params[i]; + full_command.erase(full_command.begin()); + + ++count; + it = source.service->commands.find(full_command); + } + + if (it == source.service->commands.end()) + { + if (has_help) + source.Reply(_("Unknown command \002%s\002. \"%s%s HELP\" for help."), message.c_str(), Config->StrictPrivmsg.c_str(), source.service->nick.c_str()); + else + source.Reply(_("Unknown command \002%s\002."), message.c_str()); + return; + } + + const CommandInfo &info = it->second; + ServiceReference c("Command", info.name); + if (!c) + { + if (has_help) + source.Reply(_("Unknown command \002%s\002. \"%s%s HELP\" for help."), message.c_str(), Config->StrictPrivmsg.c_str(), source.service->nick.c_str()); + else + source.Reply(_("Unknown command \002%s\002."), message.c_str()); + Log(source.service) << "Command " << it->first << " exists on me, but its service " << info.name << " was not found!"; + return; + } + + for (unsigned i = 0, j = params.size() - (count - 1); i < j; ++i) + params.erase(params.begin()); + + while (c->max_params > 0 && params.size() > c->max_params) + { + params[c->max_params - 1] += " " + params[c->max_params]; + params.erase(params.begin() + c->max_params); + } + + c->Run(source, it->first, info, params); +} + +void Command::Run(CommandSource &source, const Anope::string &cmdname, const CommandInfo &info, std::vector ¶ms) +{ + if (this->RequireUser() && !source.GetUser()) + return; + + // Command requires registered users only + if (!this->AllowUnregistered() && !source.nc) + { + source.Reply(NICK_IDENTIFY_REQUIRED); + if (source.GetUser()) + Log(LOG_NORMAL, "access_denied_unreg", source.service) << "Access denied for unregistered user " << source.GetUser()->GetMask() << " with command " << cmdname; + return; + } + + source.command = cmdname; + source.permission = info.permission; + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnPreCommand, MOD_RESULT, (source, this, params)); + if (MOD_RESULT == EVENT_STOP) + return; + + if (params.size() < this->min_params) + { + this->OnSyntaxError(source, !params.empty() ? params[params.size() - 1] : ""); + return; + } + + // If the command requires a permission, and they aren't registered or don't have the required perm, DENIED + if (!info.permission.empty() && !source.HasCommand(info.permission)) + { + source.Reply(ACCESS_DENIED); + if (source.GetUser()) + Log(LOG_NORMAL, "access_denied", source.service) << "Access denied for user " << source.GetUser()->GetMask() << " with command " << cmdname; + return; + } + + this->Execute(source, params); + FOREACH_MOD(OnPostCommand, (source, this, params)); +} + +bool Command::FindCommandFromService(const Anope::string &command_service, BotInfo* &bot, Anope::string &name) +{ + bot = NULL; + + for (botinfo_map::iterator it = BotListByNick->begin(), it_end = BotListByNick->end(); it != it_end; ++it) + { + BotInfo *bi = it->second; + + for (CommandInfo::map::const_iterator cit = bi->commands.begin(), cit_end = bi->commands.end(); cit != cit_end; ++cit) + { + const Anope::string &c_name = cit->first; + const CommandInfo &info = cit->second; + + if (info.name != command_service) + continue; + + bot = bi; + name = c_name; + return true; + } + } + + return false; +} diff --git a/src/config.cpp b/src/config.cpp new file mode 100644 index 0000000..f1d237a --- /dev/null +++ b/src/config.cpp @@ -0,0 +1,947 @@ +/* Configuration file handling. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "config.h" +#include "bots.h" +#include "access.h" +#include "opertype.h" +#include "channels.h" +#include "hashcomp.h" + +using namespace Configuration; + +File ServicesConf("services.conf", false); // Services configuration file name +Conf *Config = NULL; + +Block::Block(const Anope::string &n) : name(n), linenum(-1) +{ +} + +const Anope::string &Block::GetName() const +{ + return name; +} + +int Block::CountBlock(const Anope::string &bname) +{ + if (!this) + return 0; + + return blocks.count(bname); +} + +Block* Block::GetBlock(const Anope::string &bname, int num) +{ + if (!this) + return NULL; + + std::pair it = blocks.equal_range(bname); + + for (int i = 0; it.first != it.second; ++it.first, ++i) + if (i == num) + return &it.first->second; + return NULL; +} + +bool Block::Set(const Anope::string &tag, const Anope::string &value) +{ + if (!this) + return false; + + items[tag] = value; + return true; +} + +const Block::item_map* Block::GetItems() const +{ + if (this) + return &items; + else + return NULL; +} + +template<> const Anope::string Block::Get(const Anope::string &tag, const Anope::string& def) const +{ + if (!this) + return def; + + Anope::map::const_iterator it = items.find(tag); + if (it != items.end()) + return it->second; + + return def; +} + +template<> time_t Block::Get(const Anope::string &tag, const Anope::string &def) const +{ + return Anope::DoTime(Get(tag, def)); +} + +template<> bool Block::Get(const Anope::string &tag, const Anope::string &def) const +{ + const Anope::string &str = Get(tag, def); + return !str.empty() && !str.equals_ci("no") && !str.equals_ci("off") && !str.equals_ci("false") && !str.equals_ci("0"); +} + +static void ValidateNotEmpty(const Anope::string &block, const Anope::string &name, const Anope::string &value) +{ + if (value.empty()) + throw ConfigException("The value for <" + block + ":" + name + "> cannot be empty!"); +} + +static void ValidateNoSpaces(const Anope::string &block, const Anope::string &name, const Anope::string &value) +{ + if (value.find(' ') != Anope::string::npos) + throw ConfigException("The value for <" + block + ":" + name + "> may not contain spaces!"); +} + +static void ValidateNotEmptyOrSpaces(const Anope::string &block, const Anope::string &name, const Anope::string &value) +{ + ValidateNotEmpty(block, name, value); + ValidateNoSpaces(block, name, value); +} + +template static void ValidateNotZero(const Anope::string &block, const Anope::string &name, T value) +{ + if (!value) + throw ConfigException("The value for <" + block + ":" + name + "> cannot be zero!"); +} + +Conf::Conf() : Block("") +{ + ReadTimeout = 0; + UsePrivmsg = DefPrivmsg = false; + + this->LoadConf(ServicesConf); + + for (int i = 0; i < this->CountBlock("include"); ++i) + { + Block *include = this->GetBlock("include", i); + + const Anope::string &type = include->Get("type"), + &file = include->Get("name"); + + File f(file, type == "executable"); + this->LoadConf(f); + } + + FOREACH_MOD(OnReload, (this)); + + /* Check for modified values that aren't allowed to be modified */ + if (Config) + { + struct + { + Anope::string block; + Anope::string name; + } noreload[] = { + {"serverinfo", "name"}, + {"serverinfo", "description"}, + {"serverinfo", "localhost"}, + {"serverinfo", "id"}, + {"serverinfo", "pid"}, + {"networkinfo", "nicklen"}, + {"networkinfo", "userlen"}, + {"networkinfo", "hostlen"}, + {"networkinfo", "chanlen"}, + }; + + for (unsigned i = 0; i < sizeof(noreload) / sizeof(noreload[0]); ++i) + if (this->GetBlock(noreload[i].block)->Get(noreload[i].name) != Config->GetBlock(noreload[i].block)->Get(noreload[i].name)) + throw ConfigException("<" + noreload[i].block + ":" + noreload[i].name + "> can not be modified once set"); + } + + Block *serverinfo = this->GetBlock("serverinfo"), *options = this->GetBlock("options"), + *mail = this->GetBlock("mail"), *networkinfo = this->GetBlock("networkinfo"); + + const Anope::string &servername = serverinfo->Get("name"); + + ValidateNotEmptyOrSpaces("serverinfo", "name", servername); + + if (servername.find(' ') != Anope::string::npos || servername.find('.') == Anope::string::npos) + throw ConfigException("serverinfo:name is not a valid server name"); + + ValidateNotEmpty("serverinfo", "description", serverinfo->Get("description")); + ValidateNotEmpty("serverinfo", "pid", serverinfo->Get("pid")); + ValidateNotEmpty("serverinfo", "motd", serverinfo->Get("motd")); + + ValidateNotZero("options", "readtimeout", options->Get("readtimeout")); + ValidateNotZero("options", "warningtimeout", options->Get("warningtimeout")); + + ValidateNotZero("networkinfo", "nicklen", networkinfo->Get("nicklen")); + ValidateNotZero("networkinfo", "userlen", networkinfo->Get("userlen")); + ValidateNotZero("networkinfo", "hostlen", networkinfo->Get("hostlen")); + ValidateNotZero("networkinfo", "chanlen", networkinfo->Get("chanlen")); + + spacesepstream(options->Get("ulineservers")).GetTokens(this->Ulines); + + if (mail->Get("usemail")) + { + Anope::string check[] = { "sendmailpath", "sendfrom", "registration_subject", "registration_message", "emailchange_subject", "emailchange_message", "memo_subject", "memo_message" }; + for (unsigned i = 0; i < sizeof(check) / sizeof(Anope::string); ++i) + ValidateNotEmpty("mail", check[i], mail->Get(check[i])); + } + + this->ReadTimeout = options->Get("readtimeout"); + this->UsePrivmsg = options->Get("useprivmsg"); + this->UseStrictPrivmsg = options->Get("usestrictprivmsg"); + this->StrictPrivmsg = !UseStrictPrivmsg ? "/msg " : "/"; + { + std::vector defaults; + spacesepstream(this->GetModule("nickserv")->Get("defaults")).GetTokens(defaults); + this->DefPrivmsg = std::find(defaults.begin(), defaults.end(), "msg") != defaults.end(); + } + this->DefLanguage = options->Get("defaultlanguage"); + this->TimeoutCheck = options->Get("timeoutcheck"); + this->NickChars = networkinfo->Get("nick_chars"); + + for (int i = 0; i < this->CountBlock("uplink"); ++i) + { + Block *uplink = this->GetBlock("uplink", i); + + const Anope::string &host = uplink->Get("host"); + bool ipv6 = uplink->Get("ipv6"); + int port = uplink->Get("port"); + const Anope::string &password = uplink->Get("password"); + + ValidateNotEmptyOrSpaces("uplink", "host", host); + ValidateNotZero("uplink", "port", port); + ValidateNotEmptyOrSpaces("uplink", "password", password); + + if (password.find(' ') != Anope::string::npos || password[0] == ':') + throw ConfigException("uplink:password is not valid"); + + this->Uplinks.push_back(Uplink(host, port, password, ipv6)); + } + + for (int i = 0; i < this->CountBlock("module"); ++i) + { + Block *module = this->GetBlock("module", i); + + const Anope::string &modname = module->Get("name"); + + ValidateNotEmptyOrSpaces("module", "name", modname); + + this->ModulesAutoLoad.push_back(modname); + } + + for (int i = 0; i < this->CountBlock("opertype"); ++i) + { + Block *opertype = this->GetBlock("opertype", i); + + const Anope::string &oname = opertype->Get("name"), + &modes = opertype->Get("modes"), + &inherits = opertype->Get("inherits"), + &commands = opertype->Get("commands"), + &privs = opertype->Get("privs"); + + ValidateNotEmpty("opertype", "name", oname); + + OperType *ot = new OperType(oname); + ot->modes = modes; + + spacesepstream cmdstr(commands); + for (Anope::string str; cmdstr.GetToken(str);) + ot->AddCommand(str); + + spacesepstream privstr(privs); + for (Anope::string str; privstr.GetToken(str);) + ot->AddPriv(str); + + commasepstream inheritstr(inherits); + for (Anope::string str; inheritstr.GetToken(str);) + { + /* Strip leading ' ' after , */ + if (str.length() > 1 && str[0] == ' ') + str.erase(str.begin()); + for (unsigned j = 0; j < this->MyOperTypes.size(); ++j) + { + OperType *ot2 = this->MyOperTypes[j]; + + if (ot2->GetName().equals_ci(str)) + { + Log() << "Inheriting commands and privs from " << ot2->GetName() << " to " << ot->GetName(); + ot->Inherits(ot2); + break; + } + } + } + + this->MyOperTypes.push_back(ot); + } + + for (int i = 0; i < this->CountBlock("oper"); ++i) + { + Block *oper = this->GetBlock("oper", i); + + const Anope::string &nname = oper->Get("name"), + &type = oper->Get("type"), + &password = oper->Get("password"), + &certfp = oper->Get("certfp"), + &host = oper->Get("host"), + &vhost = oper->Get("vhost"); + bool require_oper = oper->Get("require_oper"); + + ValidateNotEmptyOrSpaces("oper", "name", nname); + ValidateNotEmpty("oper", "type", type); + + OperType *ot = NULL; + for (unsigned j = 0; j < this->MyOperTypes.size(); ++j) + if (this->MyOperTypes[j]->GetName() == type) + ot = this->MyOperTypes[j]; + if (ot == NULL) + throw ConfigException("Oper block for " + nname + " has invalid oper type " + type); + + Oper *o = new Oper(nname, ot); + o->require_oper = require_oper; + o->password = password; + o->certfp = certfp; + spacesepstream(host).GetTokens(o->hosts); + o->vhost = vhost; + + this->Opers.push_back(o); + } + + for (botinfo_map::const_iterator it = BotListByNick->begin(), it_end = BotListByNick->end(); it != it_end; ++it) + it->second->conf = false; + for (int i = 0; i < this->CountBlock("service"); ++i) + { + Block *service = this->GetBlock("service", i); + + const Anope::string &nick = service->Get("nick"), + &user = service->Get("user"), + &host = service->Get("host"), + &gecos = service->Get("gecos"), + &modes = service->Get("modes"), + &channels = service->Get("channels"); + + ValidateNotEmptyOrSpaces("service", "nick", nick); + ValidateNotEmptyOrSpaces("service", "user", user); + ValidateNotEmptyOrSpaces("service", "host", host); + ValidateNotEmpty("service", "gecos", gecos); + ValidateNoSpaces("service", "channels", channels); + + BotInfo *bi = BotInfo::Find(nick, true); + if (!bi) + bi = new BotInfo(nick, user, host, gecos, modes); + bi->conf = true; + + std::vector oldchannels = bi->botchannels; + bi->botchannels.clear(); + commasepstream sep(channels); + for (Anope::string token; sep.GetToken(token);) + { + bi->botchannels.push_back(token); + size_t ch = token.find('#'); + Anope::string chname, want_modes; + if (ch == Anope::string::npos) + chname = token; + else + { + want_modes = token.substr(0, ch); + chname = token.substr(ch); + } + bi->Join(chname); + Channel *c = Channel::Find(chname); + if (!c) + continue; // Can't happen + + c->botchannel = true; + + /* Remove all existing modes */ + ChanUserContainer *cu = c->FindUser(bi); + if (cu != NULL) + for (size_t j = 0; j < cu->status.Modes().length(); ++j) + c->RemoveMode(bi, ModeManager::FindChannelModeByChar(cu->status.Modes()[j]), bi->GetUID()); + /* Set the new modes */ + for (unsigned j = 0; j < want_modes.length(); ++j) + { + ChannelMode *cm = ModeManager::FindChannelModeByChar(want_modes[j]); + if (cm == NULL) + cm = ModeManager::FindChannelModeByChar(ModeManager::GetStatusChar(want_modes[j])); + if (cm && cm->type == MODE_STATUS) + c->SetMode(bi, cm, bi->GetUID()); + } + } + for (unsigned k = 0; k < oldchannels.size(); ++k) + { + size_t ch = oldchannels[k].find('#'); + Anope::string chname = oldchannels[k].substr(ch != Anope::string::npos ? ch : 0); + + bool found = false; + for (unsigned j = 0; j < bi->botchannels.size(); ++j) + { + ch = bi->botchannels[j].find('#'); + Anope::string ochname = bi->botchannels[j].substr(ch != Anope::string::npos ? ch : 0); + + if (chname.equals_ci(ochname)) + found = true; + } + + if (found) + continue; + + Channel *c = Channel::Find(chname); + if (c) + { + c->botchannel = false; + bi->Part(c); + } + } + } + + for (int i = 0; i < this->CountBlock("log"); ++i) + { + Block *log = this->GetBlock("log", i); + + int logage = log->Get("logage"); + bool rawio = log->Get("rawio"); + bool debug = log->Get("debug"); + + LogInfo l(logage, rawio, debug); + + l.bot = BotInfo::Find(log->Get("bot", "Global"), true); + spacesepstream(log->Get("target")).GetTokens(l.targets); + spacesepstream(log->Get("source")).GetTokens(l.sources); + spacesepstream(log->Get("admin")).GetTokens(l.admin); + spacesepstream(log->Get("override")).GetTokens(l.override); + spacesepstream(log->Get("commands")).GetTokens(l.commands); + spacesepstream(log->Get("servers")).GetTokens(l.servers); + spacesepstream(log->Get("channels")).GetTokens(l.channels); + spacesepstream(log->Get("users")).GetTokens(l.users); + spacesepstream(log->Get("other")).GetTokens(l.normal); + + this->LogInfos.push_back(l); + } + + for (botinfo_map::const_iterator it = BotListByNick->begin(), it_end = BotListByNick->end(); it != it_end; ++it) + it->second->commands.clear(); + for (int i = 0; i < this->CountBlock("command"); ++i) + { + Block *command = this->GetBlock("command", i); + + const Anope::string &service = command->Get("service"), + &nname = command->Get("name"), + &cmd = command->Get("command"), + &permission = command->Get("permission"), + &group = command->Get("group"); + bool hide = command->Get("hide"); + + ValidateNotEmptyOrSpaces("command", "service", service); + ValidateNotEmpty("command", "name", nname); + ValidateNotEmptyOrSpaces("command", "command", cmd); + + BotInfo *bi = this->GetClient(service); + if (!bi) + continue; + + CommandInfo &ci = bi->SetCommand(nname, cmd, permission); + ci.group = group; + ci.hide = hide; + } + + PrivilegeManager::ClearPrivileges(); + for (int i = 0; i < this->CountBlock("privilege"); ++i) + { + Block *privilege = this->GetBlock("privilege", i); + + const Anope::string &nname = privilege->Get("name"), + &desc = privilege->Get("desc"); + int rank = privilege->Get("rank"); + + PrivilegeManager::AddPrivilege(Privilege(nname, desc, rank)); + } + + for (int i = 0; i < this->CountBlock("fantasy"); ++i) + { + Block *fantasy = this->GetBlock("fantasy", i); + + const Anope::string &nname = fantasy->Get("name"), + &service = fantasy->Get("command"), + &permission = fantasy->Get("permission"), + &group = fantasy->Get("group"); + bool hide = fantasy->Get("hide"), + prepend_channel = fantasy->Get("prepend_channel", "yes"); + + ValidateNotEmptyOrSpaces("fantasy", "name", nname); + ValidateNotEmptyOrSpaces("fantasy", "command", service); + + CommandInfo &c = this->Fantasy[nname]; + c.name = service; + c.permission = permission; + c.group = group; + c.hide = hide; + c.prepend_channel = prepend_channel; + } + + for (int i = 0; i < this->CountBlock("command_group"); ++i) + { + Block *command_group = this->GetBlock("command_group", i); + + const Anope::string &nname = command_group->Get("name"), + &description = command_group->Get("description"); + + CommandGroup gr; + gr.name = nname; + gr.description = description; + + this->CommandGroups.push_back(gr); + } + + /* Below here can't throw */ + + if (Config) + /* Clear existing conf opers */ + for (nickcore_map::const_iterator it = NickCoreList->begin(), it_end = NickCoreList->end(); it != it_end; ++it) + { + NickCore *nc = it->second; + if (nc->o && std::find(Config->Opers.begin(), Config->Opers.end(), nc->o) != Config->Opers.end()) + nc->o = NULL; + } + /* Apply new opers */ + for (unsigned i = 0; i < this->Opers.size(); ++i) + { + Oper *o = this->Opers[i]; + + NickAlias *na = NickAlias::Find(o->name); + if (!na) + continue; + + if (!na->nc || na->nc->o) + { + // If the account is already an oper it might mean two oper blocks for the same nick, or + // something else has configured them as an oper (like a module) + continue; + } + + na->nc->o = o; + Log() << "Tied oper " << na->nc->display << " to type " << o->ot->GetName(); + } + + if (options->Get("casemap", "ascii") == "ascii") + Anope::casemap = std::locale(std::locale(), new Anope::ascii_ctype()); + else if (options->Get("casemap") == "rfc1459") + Anope::casemap = std::locale(std::locale(), new Anope::rfc1459_ctype()); + else + { + try + { + Anope::casemap = std::locale(options->Get("casemap").c_str()); + } + catch (const std::runtime_error &) + { + Log() << "Unknown casemap " << options->Get("casemap") << " - casemap not changed"; + } + } + Anope::CaseMapRebuild(); + + /* Check the user keys */ + if (!options->Get("seed")) + Log() << "Configuration option options:seed should be set. It's for YOUR safety! Remember that!"; +} + +Conf::~Conf() +{ + for (unsigned i = 0; i < MyOperTypes.size(); ++i) + delete MyOperTypes[i]; + for (unsigned i = 0; i < Opers.size(); ++i) + delete Opers[i]; +} + +void Conf::Post(Conf *old) +{ + /* Apply module changes */ + for (unsigned i = 0; i < old->ModulesAutoLoad.size(); ++i) + if (std::find(this->ModulesAutoLoad.begin(), this->ModulesAutoLoad.end(), old->ModulesAutoLoad[i]) == this->ModulesAutoLoad.end()) + ModuleManager::UnloadModule(ModuleManager::FindModule(old->ModulesAutoLoad[i]), NULL); + for (unsigned i = 0; i < this->ModulesAutoLoad.size(); ++i) + if (std::find(old->ModulesAutoLoad.begin(), old->ModulesAutoLoad.end(), this->ModulesAutoLoad[i]) == old->ModulesAutoLoad.end()) + ModuleManager::LoadModule(this->ModulesAutoLoad[i], NULL); + + /* Apply opertype changes, as non-conf opers still point to the old oper types */ + for (unsigned i = Oper::opers.size(); i > 0; --i) + { + Oper *o = Oper::opers[i - 1]; + + /* Oper's type is in the old config, so update it */ + if (std::find(old->MyOperTypes.begin(), old->MyOperTypes.end(), o->ot) != old->MyOperTypes.end()) + { + OperType *ot = o->ot; + o->ot = NULL; + + for (unsigned j = 0; j < MyOperTypes.size(); ++j) + if (ot->GetName() == MyOperTypes[j]->GetName()) + o->ot = MyOperTypes[j]; + + if (o->ot == NULL) + { + /* Oper block has lost type */ + std::vector::iterator it = std::find(old->Opers.begin(), old->Opers.end(), o); + if (it != old->Opers.end()) + old->Opers.erase(it); + + it = std::find(this->Opers.begin(), this->Opers.end(), o); + if (it != this->Opers.end()) + this->Opers.erase(it); + + delete o; + } + } + } +} + +Block *Conf::GetModule(Module *m) +{ + if (!m) + return NULL; + + return GetModule(m->name); +} + +Block *Conf::GetModule(const Anope::string &mname) +{ + std::map::iterator it = modules.find(mname); + if (it != modules.end()) + return it->second; + + Block* &block = modules[mname]; + + /* Search for the block */ + for (std::pair iters = blocks.equal_range("module"); iters.first != iters.second; ++iters.first) + { + Block *b = &iters.first->second; + + if (b->Get("name") == mname) + { + block = b; + break; + } + } + + return GetModule(mname); +} + +BotInfo *Conf::GetClient(const Anope::string &cname) +{ + Anope::map::iterator it = bots.find(cname); + if (it != bots.end()) + return BotInfo::Find(!it->second.empty() ? it->second : cname, true); + + Block *block = GetModule(cname.lower()); + const Anope::string &client = block->Get("client"); + bots[cname] = client; + return GetClient(cname); +} + +Block *Conf::GetCommand(CommandSource &source) +{ + const Anope::string &block_name = source.c ? "fantasy" : "command"; + + for (std::pair iters = blocks.equal_range(block_name); iters.first != iters.second; ++iters.first) + { + Block *b = &iters.first->second; + + if (b->Get("name") == source.command) + return b; + } + + return NULL; +} + +File::File(const Anope::string &n, bool e) : name(n), executable(e), fp(NULL) +{ +} + +File::~File() +{ + this->Close(); +} + +const Anope::string &File::GetName() const +{ + return this->name; +} + +Anope::string File::GetPath() const +{ + return (this->executable ? "" : Anope::ConfigDir + "/") + this->name; +} + +bool File::IsOpen() const +{ + return this->fp != NULL; +} + +bool File::Open() +{ + this->Close(); + this->fp = (this->executable ? popen(this->name.c_str(), "r") : fopen((Anope::ConfigDir + "/" + this->name).c_str(), "r")); + return this->fp != NULL; +} + +void File::Close() +{ + if (this->fp != NULL) + { + if (this->executable) + pclose(this->fp); + else + fclose(this->fp); + this->fp = NULL; + } +} + +bool File::End() const +{ + return !this->IsOpen() || feof(this->fp); +} + +Anope::string File::Read() +{ + Anope::string ret; + char buf[BUFSIZE]; + while (fgets(buf, sizeof(buf), this->fp) != NULL) + { + char *nl = strchr(buf, '\n'); + if (nl != NULL) + *nl = 0; + else if (!this->End()) + { + ret += buf; + continue; + } + + ret = buf; + break; + } + + return ret; +} + +void Conf::LoadConf(File &file) +{ + if (file.GetName().empty()) + return; + + if (!file.Open()) + throw ConfigException("File " + file.GetPath() + " could not be opened."); + + Anope::string itemname, wordbuffer; + std::stack block_stack; + int linenumber = 0; + bool in_word = false, in_quote = false, in_comment = false; + + Log(LOG_DEBUG) << "Start to read conf " << file.GetPath(); + // Start reading characters... + while (!file.End()) + { + Anope::string line = file.Read(); + ++linenumber; + + /* If this line is completely empty and we are in a quote, just append a newline */ + if (line.empty() && in_quote) + wordbuffer += "\n"; + + for (unsigned c = 0, len = line.length(); c < len; ++c) + { + char ch = line[c]; + if (in_quote) + { + /* Strip leading white spaces from multi line quotes */ + if (c == 0) + { + while (c < len && isspace(line[c])) + ++c; + ch = line[c]; + } + + /* Allow \" in quotes */ + if (ch == '\\' && c + 1 < len && line[c + 1] == '"') + wordbuffer += line[++c]; + else if (ch == '"') + in_quote = in_word = false; + else if (ch) + wordbuffer += ch; + } + else if (in_comment) + { + if (ch == '*' && c + 1 < len && line[c + 1] == '/') + { + in_comment = false; + ++c; + // We might be at an eol, so continue on and process it + } + else + continue; + } + else if (ch == '#' || (ch == '/' && c + 1 < len && line[c + 1] == '/')) + c = len - 1; // Line comment, ignore the rest of the line (much like this one!) + else if (ch == '/' && c + 1 < len && line[c + 1] == '*') + { + // Multiline (or less than one line) comment + in_comment = true; + ++c; + continue; + } + else if (!in_word && (ch == '(' || ch == '_' || ch == ')')) + ; + else if (ch == '"') + { + // Quotes are valid only in the value position + if (block_stack.empty() || itemname.empty()) + { + file.Close(); + throw ConfigException("Unexpected quoted string: " + file.GetName() + ":" + stringify(linenumber)); + } + if (in_word || !wordbuffer.empty()) + { + file.Close(); + throw ConfigException("Unexpected quoted string (prior unhandled words): " + file.GetName() + ":" + stringify(linenumber)); + } + in_quote = in_word = true; + } + else if (ch == '=') + { + if (block_stack.empty()) + { + file.Close(); + throw ConfigException("Config item outside of section (or stray '='): " + file.GetName() + ":" + stringify(linenumber)); + } + + if (!itemname.empty() || wordbuffer.empty()) + { + file.Close(); + throw ConfigException("Stray '=' sign or item without value: " + file.GetName() + ":" + stringify(linenumber)); + } + + in_word = false; + itemname = wordbuffer; + wordbuffer.clear(); + } + else if (ch == '{') + { + if (wordbuffer.empty()) + { + block_stack.push(NULL); + // Commented or unnamed section + continue; + } + + if (!block_stack.empty() && !block_stack.top()) + { + // Named block inside of a commented block + in_word = false; + wordbuffer.clear(); + block_stack.push(NULL); + continue; + } + + Block *b = block_stack.empty() ? this : block_stack.top(); + block_map::iterator it = b->blocks.insert(std::make_pair(wordbuffer, Configuration::Block(wordbuffer))); + b = &it->second; + b->linenum = linenumber; + block_stack.push(b); + + in_word = false; + wordbuffer.clear(); + continue; + } + else if (ch == ' ' || ch == '\r' || ch == '\t') + { + // Terminate word + in_word = false; + } + else if (ch == ';' || ch == '}') + ; + else + { + if (!in_word && !wordbuffer.empty()) + { + file.Close(); + throw ConfigException("Unexpected word: " + file.GetName() + ":" + stringify(linenumber)); + } + wordbuffer += ch; + in_word = true; + } + + if (ch == ';' || ch == '}' || c + 1 >= len) + { + bool eol = c + 1 >= len; + + if (!eol && in_quote) + // Allow ; and } in quoted strings + continue; + + if (in_quote) + { + // Quotes can span multiple lines; all we need to do is go to the next line without clearing things + wordbuffer += "\n"; + continue; + } + + in_word = false; + if (!itemname.empty()) + { + if (block_stack.empty()) + { + file.Close(); + throw ConfigException("Stray ';' outside of block: " + file.GetName() + ":" + stringify(linenumber)); + } + + Block *b = block_stack.top(); + + if (b) + Log(LOG_DEBUG) << "ln " << linenumber << " EOL: s='" << b->name << "' '" << itemname << "' set to '" << wordbuffer << "'"; + + /* Check defines */ + for (int i = 0; i < this->CountBlock("define"); ++i) + { + Block *define = this->GetBlock("define", i); + + const Anope::string &dname = define->Get("name"); + + if (dname == wordbuffer && define != b) + wordbuffer = define->Get("value"); + } + + if (b) + b->items[itemname] = wordbuffer; + + wordbuffer.clear(); + itemname.clear(); + } + + if (ch == '}') + { + if (block_stack.empty()) + { + file.Close(); + throw ConfigException("Stray '}': " + file.GetName() + ":" + stringify(linenumber)); + } + + block_stack.pop(); + } + } + } + } + + file.Close(); + + if (in_comment) + throw ConfigException("Unterminated multiline comment at end of file: " + file.GetName()); + if (in_quote) + throw ConfigException("Unterminated quote at end of file: " + file.GetName()); + if (!itemname.empty() || !wordbuffer.empty()) + throw ConfigException("Unexpected garbage at end of file: " + file.GetName()); + if (!block_stack.empty()) + throw ConfigException("Unterminated block at end of file: " + file.GetName() + ". Block was opened on line " + stringify(block_stack.top()->linenum)); +} diff --git a/src/extensible.cpp b/src/extensible.cpp new file mode 100644 index 0000000..796c7cd --- /dev/null +++ b/src/extensible.cpp @@ -0,0 +1,71 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "extensible.h" + +static std::set extensible_items; + +ExtensibleBase::ExtensibleBase(Module *m, const Anope::string &n) : Service(m, "Extensible", n) +{ + extensible_items.insert(this); +} + +ExtensibleBase::~ExtensibleBase() +{ + extensible_items.erase(this); +} + +Extensible::~Extensible() +{ + UnsetExtensibles(); +} + +void Extensible::UnsetExtensibles() +{ + while (!extension_items.empty()) + (*extension_items.begin())->Unset(this); +} + +bool Extensible::HasExt(const Anope::string &name) const +{ + ExtensibleRef ref(name); + if (ref) + return ref->HasExt(this); + + Log(LOG_DEBUG) << "HasExt for nonexistent type " << name << " on " << static_cast(this); + return false; +} + +void Extensible::ExtensibleSerialize(const Extensible *e, const Serializable *s, Serialize::Data &data) +{ + for (std::set::iterator it = e->extension_items.begin(); it != e->extension_items.end(); ++it) + { + ExtensibleBase *eb = *it; + eb->ExtensibleSerialize(e, s, data); + } +} + +void Extensible::ExtensibleUnserialize(Extensible *e, Serializable *s, Serialize::Data &data) +{ + for (std::set::iterator it = extensible_items.begin(); it != extensible_items.end(); ++it) + { + ExtensibleBase *eb = *it; + eb->ExtensibleUnserialize(e, s, data); + } +} + +template<> +bool* Extensible::Extend(const Anope::string &name, const bool &what) +{ + ExtensibleRef ref(name); + if (ref) + return ref->Set(this); + + Log(LOG_DEBUG) << "Extend for nonexistent type " << name << " on " << static_cast(this); + return NULL; +} diff --git a/src/hashcomp.cpp b/src/hashcomp.cpp new file mode 100644 index 0000000..e839de4 --- /dev/null +++ b/src/hashcomp.cpp @@ -0,0 +1,163 @@ +/* + * + * (C) 2002-2011 InspIRCd Development Team + * (C) 2008-2022 Anope Team + * + * Please read COPYING and README for further details. + */ + +#include "services.h" +#include "hashcomp.h" +#include "anope.h" + +/* Case map in use by Anope */ +std::locale Anope::casemap = std::locale(std::locale(), new Anope::ascii_ctype()); +/* Cache of the above case map, forced upper */ +static unsigned char case_map_upper[256], case_map_lower[256]; + +/* called whenever Anope::casemap is modified to rebuild the casemap cache */ +void Anope::CaseMapRebuild() +{ + const std::ctype &ct = std::use_facet >(Anope::casemap); + + for (unsigned i = 0; i < sizeof(case_map_upper); ++i) + { + case_map_upper[i] = ct.toupper(i); + case_map_lower[i] = ct.tolower(i); + } +} + +unsigned char Anope::tolower(unsigned char c) +{ + return case_map_lower[c]; +} + +unsigned char Anope::toupper(unsigned char c) +{ + return case_map_upper[c]; +} + +/* + * + * This is an implementation of a special string class, ci::string, + * which is a case-insensitive equivalent to std::string. + * + */ + +bool ci::ci_char_traits::eq(char c1st, char c2nd) +{ + return case_map_upper[static_cast(c1st)] == case_map_upper[static_cast(c2nd)]; +} + +bool ci::ci_char_traits::ne(char c1st, char c2nd) +{ + return !eq(c1st, c2nd); +} + +bool ci::ci_char_traits::lt(char c1st, char c2nd) +{ + return case_map_upper[static_cast(c1st)] < case_map_upper[static_cast(c2nd)]; +} + +int ci::ci_char_traits::compare(const char *str1, const char *str2, size_t n) +{ + for (unsigned i = 0; i < n; ++i) + { + unsigned char c1 = case_map_upper[static_cast(*str1)], + c2 = case_map_upper[static_cast(*str2)]; + + if (c1 > c2) + return 1; + else if (c1 < c2) + return -1; + else if (!c1 || !c2) + return 0; + + ++str1; + ++str2; + } + return 0; +} + +const char *ci::ci_char_traits::find(const char *s1, int n, char c) +{ + while (n-- > 0 && case_map_upper[static_cast(*s1)] != case_map_upper[static_cast(c)]) + ++s1; + return n >= 0 ? s1 : NULL; +} + +bool ci::less::operator()(const Anope::string &s1, const Anope::string &s2) const +{ + return s1.ci_str().compare(s2.ci_str()) < 0; +} + +sepstream::sepstream(const Anope::string &source, char separator, bool ae) : tokens(source), sep(separator), pos(0), allow_empty(ae) +{ +} + +bool sepstream::GetToken(Anope::string &token) +{ + if (this->StreamEnd()) + { + token.clear(); + return false; + } + + if (!this->allow_empty) + { + this->pos = this->tokens.find_first_not_of(this->sep, this->pos); + if (this->pos == std::string::npos) + { + this->pos = this->tokens.length() + 1; + token.clear(); + return false; + } + } + + size_t p = this->tokens.find(this->sep, this->pos); + if (p == std::string::npos) + p = this->tokens.length(); + + token = this->tokens.substr(this->pos, p - this->pos); + this->pos = p + 1; + + return true; +} + +bool sepstream::GetToken(Anope::string &token, int num) +{ + int i; + for (i = 0; i < num + 1 && this->GetToken(token); ++i); + return i == num + 1; +} + +int sepstream::NumTokens() +{ + int i; + Anope::string token; + for (i = 0; this->GetToken(token); ++i); + return i; +} + +bool sepstream::GetTokenRemainder(Anope::string &token, int num) +{ + if (this->GetToken(token, num)) + { + if (!this->StreamEnd()) + token += sep + this->GetRemaining(); + + return true; + } + + return false; +} + +const Anope::string sepstream::GetRemaining() +{ + return !this->StreamEnd() ? this->tokens.substr(this->pos) : ""; +} + +bool sepstream::StreamEnd() +{ + return this->pos > this->tokens.length(); +} diff --git a/src/init.cpp b/src/init.cpp new file mode 100644 index 0000000..e3866ab --- /dev/null +++ b/src/init.cpp @@ -0,0 +1,567 @@ +/* Initialization and related routines. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "config.h" +#include "users.h" +#include "protocol.h" +#include "bots.h" +#include "xline.h" +#include "socketengine.h" +#include "servers.h" +#include "language.h" + +#ifndef _WIN32 +#include +#include + +#include +#include +#include +#include +#endif + +Anope::string Anope::ConfigDir = "conf", Anope::DataDir = "data", Anope::ModuleDir = "lib", Anope::LocaleDir = "locale", Anope::LogDir = "logs"; + +/* Vector of pairs of command line arguments and their params */ +static std::vector > CommandLineArguments; + +/** Called on startup to organize our starting arguments in a better way + * and check for errors + * @param ac number of args + * @param av args + */ +static void ParseCommandLineArguments(int ac, char **av) +{ + for (int i = 1; i < ac; ++i) + { + Anope::string option = av[i]; + Anope::string param; + while (!option.empty() && option[0] == '-') + option.erase(option.begin()); + size_t t = option.find('='); + if (t != Anope::string::npos) + { + param = option.substr(t + 1); + option.erase(t); + } + + if (option.empty()) + continue; + + CommandLineArguments.push_back(std::make_pair(option, param)); + } +} + +/** Check if an argument was given on startup and its parameter + * @param name The argument name + * @param shortname A shorter name, eg --debug and -d + * @param param A string to put the param, if any, of the argument + * @return true if name/shortname was found, false if not + */ +static bool GetCommandLineArgument(const Anope::string &name, char shortname, Anope::string ¶m) +{ + param.clear(); + + for (std::vector >::iterator it = CommandLineArguments.begin(), it_end = CommandLineArguments.end(); it != it_end; ++it) + { + if (it->first.equals_ci(name) || (it->first.length() == 1 && it->first[0] == shortname)) + { + param = it->second; + return true; + } + } + + return false; +} + +/** Check if an argument was given on startup + * @param name The argument name + * @param shortname A shorter name, eg --debug and -d + * @return true if name/shortname was found, false if not + */ +static bool GetCommandLineArgument(const Anope::string &name, char shortname = 0) +{ + Anope::string Unused; + return GetCommandLineArgument(name, shortname, Unused); +} + +bool Anope::AtTerm() +{ + return isatty(fileno(stdout)) && isatty(fileno(stdin)) && isatty(fileno(stderr)); +} + +static void setuidgid(); + +void Anope::Fork() +{ +#ifndef _WIN32 + kill(getppid(), SIGUSR2); + + if (!freopen("/dev/null", "r", stdin)) + Log() << "Unable to redirect stdin to /dev/null: " << Anope::LastError(); + if (!freopen("/dev/null", "w", stdout)) + Log() << "Unable to redirect stdout to /dev/null: " << Anope::LastError(); + if (!freopen("/dev/null", "w", stderr)) + Log() << "Unable to redirect stderr to /dev/null: " << Anope::LastError(); + + setpgid(0, 0); + + setuidgid(); +#else + FreeConsole(); +#endif +} + +void Anope::HandleSignal() +{ + switch (Signal) + { + case SIGHUP: + { + Anope::SaveDatabases(); + + try + { + Configuration::Conf *new_config = new Configuration::Conf(); + Configuration::Conf *old = Config; + Config = new_config; + Config->Post(old); + delete old; + } + catch (const ConfigException &ex) + { + Log() << "Error reloading configuration file: " << ex.GetReason(); + } + break; + } + case SIGTERM: + case SIGINT: +#ifndef _WIN32 + Log() << "Received " << strsignal(Signal) << " signal (" << Signal << "), exiting."; + Anope::QuitReason = Anope::string("Services terminating via signal ") + strsignal(Signal) + " (" + stringify(Signal) + ")"; +#else + Log() << "Received signal " << Signal << ", exiting."; + Anope::QuitReason = Anope::string("Services terminating via signal ") + stringify(Signal); +#endif + Anope::Quitting = true; + Anope::SaveDatabases(); + break; + } + + Signal = 0; +} + +#ifndef _WIN32 +static void parent_signal_handler(int signal) +{ + if (signal == SIGUSR2) + { + Anope::Quitting = true; + } + else if (signal == SIGCHLD) + { + Anope::ReturnValue = -1; + Anope::Quitting = true; + int status = 0; + wait(&status); + if (WIFEXITED(status)) + Anope::ReturnValue = WEXITSTATUS(status); + } +} +#endif + +static void SignalHandler(int sig) +{ + Anope::Signal = sig; +} + +static void InitSignals() +{ + struct sigaction sa; + + sa.sa_flags = 0; + sigemptyset(&sa.sa_mask); + + sa.sa_handler = SignalHandler; + + sigaction(SIGHUP, &sa, NULL); + + sigaction(SIGTERM, &sa, NULL); + sigaction(SIGINT, &sa, NULL); + + sa.sa_handler = SIG_IGN; + +#ifndef _WIN32 + sigaction(SIGCHLD, &sa, NULL); +#endif + sigaction(SIGPIPE, &sa, NULL); +} + +/* Remove our PID file. Done at exit. */ + +static void remove_pidfile() +{ + remove(Config->GetBlock("serverinfo")->Get("pid").c_str()); +} + +/* Create our PID file and write the PID to it. */ + +static void write_pidfile() +{ + FILE *pidfile = fopen(Config->GetBlock("serverinfo")->Get("pid").c_str(), "w"); + if (pidfile) + { +#ifdef _WIN32 + fprintf(pidfile, "%d\n", static_cast(GetCurrentProcessId())); +#else + fprintf(pidfile, "%d\n", static_cast(getpid())); +#endif + fclose(pidfile); + atexit(remove_pidfile); + } + else + throw CoreException("Can not write to PID file " + Config->GetBlock("serverinfo")->Get("pid")); +} + +static void setuidgid() +{ +#ifndef _WIN32 + Configuration::Block *options = Config->GetBlock("options"); + uid_t uid = -1; + gid_t gid = -1; + + if (!options->Get("user").empty()) + { + errno = 0; + struct passwd *u = getpwnam(options->Get("user").c_str()); + if (u == NULL) + Log() << "Unable to setuid to " << options->Get("user") << ": " << Anope::LastError(); + else + uid = u->pw_uid; + } + if (!options->Get("group").empty()) + { + errno = 0; + struct group *g = getgrnam(options->Get("group").c_str()); + if (g == NULL) + Log() << "Unable to setgid to " << options->Get("group") << ": " << Anope::LastError(); + else + gid = g->gr_gid; + } + + for (unsigned i = 0; i < Config->LogInfos.size(); ++i) + { + LogInfo& li = Config->LogInfos[i]; + + for (unsigned j = 0; j < li.logfiles.size(); ++j) + { + LogFile* lf = li.logfiles[j]; + + errno = 0; + if (chown(lf->filename.c_str(), uid, gid) != 0) + Log() << "Unable to change the ownership of " << lf->filename << " to " << uid << "/" << gid << ": " << Anope::LastError(); + } + } + + if (static_cast(gid) != -1) + { + if (setgid(gid) == -1) + Log() << "Unable to setgid to " << options->Get("group") << ": " << Anope::LastError(); + else + Log() << "Successfully set group to " << options->Get("group"); + } + if (static_cast(uid) != -1) + { + if (setuid(uid) == -1) + Log() << "Unable to setuid to " << options->Get("user") << ": " << Anope::LastError(); + else + Log() << "Successfully set user to " << options->Get("user"); + } +#endif +} + +void Anope::Init(int ac, char **av) +{ + /* Set file creation mask and group ID. */ +#if defined(DEFUMASK) && HAVE_UMASK + umask(DEFUMASK); +#endif + + Serialize::RegisterTypes(); + + /* Parse command line arguments */ + ParseCommandLineArguments(ac, av); + + if (GetCommandLineArgument("version", 'v')) + { + Log(LOG_TERMINAL) << "Anope-" << Anope::Version() << " -- " << Anope::VersionBuildString(); + throw CoreException(); + } + + if (GetCommandLineArgument("help", 'h')) + { + Log(LOG_TERMINAL) << "Anope-" << Anope::Version() << " -- " << Anope::VersionBuildString(); + Log(LOG_TERMINAL) << "Anope IRC Services (https://www.anope.org/)"; + Log(LOG_TERMINAL) << "Usage ./" << Anope::ServicesBin << " [options] ..."; + Log(LOG_TERMINAL) << "-c, --config=filename.conf"; + Log(LOG_TERMINAL) << " --confdir=conf file directory"; + Log(LOG_TERMINAL) << " --dbdir=database directory"; + Log(LOG_TERMINAL) << "-d, --debug[=level]"; + Log(LOG_TERMINAL) << "-h, --help"; + Log(LOG_TERMINAL) << " --localedir=locale directory"; + Log(LOG_TERMINAL) << " --logdir=logs directory"; + Log(LOG_TERMINAL) << " --modulesdir=modules directory"; + Log(LOG_TERMINAL) << "-e, --noexpire"; + Log(LOG_TERMINAL) << "-n, --nofork"; + Log(LOG_TERMINAL) << " --nothird"; + Log(LOG_TERMINAL) << " --protocoldebug"; + Log(LOG_TERMINAL) << "-r, --readonly"; + Log(LOG_TERMINAL) << "-s, --support"; + Log(LOG_TERMINAL) << "-v, --version"; + Log(LOG_TERMINAL) << ""; + Log(LOG_TERMINAL) << "Further support is available from https://www.anope.org/"; + Log(LOG_TERMINAL) << "Or visit us on IRC at irc.anope.org #anope"; + throw CoreException(); + } + + if (GetCommandLineArgument("nofork", 'n')) + Anope::NoFork = true; + + if (GetCommandLineArgument("support", 's')) + { + Anope::NoFork = Anope::NoThird = true; + ++Anope::Debug; + } + + if (GetCommandLineArgument("readonly", 'r')) + Anope::ReadOnly = true; + + if (GetCommandLineArgument("nothird")) + Anope::NoThird = true; + + if (GetCommandLineArgument("noexpire", 'e')) + Anope::NoExpire = true; + + if (GetCommandLineArgument("protocoldebug")) + Anope::ProtocolDebug = true; + + Anope::string arg; + if (GetCommandLineArgument("debug", 'd', arg)) + { + if (!arg.empty()) + { + int level = arg.is_number_only() ? convertTo(arg) : -1; + if (level > 0) + Anope::Debug = level; + else + throw CoreException("Invalid option given to --debug"); + } + else + ++Anope::Debug; + } + + if (GetCommandLineArgument("config", 'c', arg)) + { + if (arg.empty()) + throw CoreException("The --config option requires a file name"); + ServicesConf = Configuration::File(arg, false); + } + + if (GetCommandLineArgument("confdir", 0, arg)) + { + if (arg.empty()) + throw CoreException("The --confdir option requires a path"); + Anope::ConfigDir = arg; + } + + if (GetCommandLineArgument("dbdir", 0, arg)) + { + if (arg.empty()) + throw CoreException("The --dbdir option requires a path"); + Anope::DataDir = arg; + } + + if (GetCommandLineArgument("localedir", 0, arg)) + { + if (arg.empty()) + throw CoreException("The --localedir option requires a path"); + Anope::LocaleDir = arg; + } + + if (GetCommandLineArgument("modulesdir", 0, arg)) + { + if (arg.empty()) + throw CoreException("The --modulesdir option requires a path"); + Anope::ModuleDir = arg; + } + + if (GetCommandLineArgument("logdir", 0, arg)) + { + if (arg.empty()) + throw CoreException("The --logdir option requires a path"); + Anope::LogDir = arg; + } + + /* Chdir to Services data directory. */ + if (chdir(Anope::ServicesDir.c_str()) < 0) + { + throw CoreException("Unable to chdir to " + Anope::ServicesDir + ": " + Anope::LastError()); + } + + Log(LOG_TERMINAL) << "Anope " << Anope::Version() << ", " << Anope::VersionBuildString(); + +#ifdef _WIN32 + if (!SupportedWindowsVersion()) + throw CoreException(GetWindowsVersion() + " is not a supported version of Windows"); +#else + /* If we're root, issue a warning now */ + if (!getuid() && !getgid()) + { + /* If we are configured to setuid later, don't issue a warning */ + Configuration::Block *options = Config->GetBlock("options"); + if (options->Get("user").empty()) + { + std::cerr << "WARNING: You are currently running Anope as the root superuser. Anope does not" << std::endl; + std::cerr << " require root privileges to run, and it is discouraged that you run Anope" << std::endl; + std::cerr << " as the root superuser." << std::endl; + sleep(3); + } + } +#endif + +#ifdef _WIN32 + Log(LOG_TERMINAL) << "Using configuration file " << Anope::ConfigDir << "\\" << ServicesConf.GetName(); +#else + Log(LOG_TERMINAL) << "Using configuration file " << Anope::ConfigDir << "/" << ServicesConf.GetName(); + + /* Fork to background */ + if (!Anope::NoFork) + { + /* Install these before fork() - it is possible for the child to + * connect and kill() the parent before it is able to install the + * handler. + */ + struct sigaction sa, old_sigusr2, old_sigchld; + + sa.sa_flags = 0; + sigemptyset(&sa.sa_mask); + sa.sa_handler = parent_signal_handler; + + sigaction(SIGUSR2, &sa, &old_sigusr2); + sigaction(SIGCHLD, &sa, &old_sigchld); + + int i = fork(); + if (i > 0) + { + sigset_t mask; + + sigemptyset(&mask); + sigsuspend(&mask); + + exit(Anope::ReturnValue); + } + else if (i == -1) + { + Log() << "Error, unable to fork: " << Anope::LastError(); + Anope::NoFork = true; + } + + /* Child doesn't need these */ + sigaction(SIGUSR2, &old_sigusr2, NULL); + sigaction(SIGCHLD, &old_sigchld, NULL); + } + +#endif + + /* Initialize the socket engine. Note that some engines can not survive a fork(), so this must be here. */ + SocketEngine::Init(); + + /* Read configuration file; exit if there are problems. */ + try + { + Config = new Configuration::Conf(); + } + catch (const ConfigException &ex) + { + Log(LOG_TERMINAL) << ex.GetReason(); + Log(LOG_TERMINAL) << "*** Support resources: Read through the services.conf self-contained"; + Log(LOG_TERMINAL) << "*** documentation. Read the documentation files found in the 'docs'"; + Log(LOG_TERMINAL) << "*** folder. Visit our portal located at https://www.anope.org/. Join"; + Log(LOG_TERMINAL) << "*** our support channel on /server irc.anope.org channel #anope."; + throw CoreException("Configuration file failed to validate"); + } + + /* Create me */ + Configuration::Block *block = Config->GetBlock("serverinfo"); + Me = new Server(NULL, block->Get("name"), 0, block->Get("description"), block->Get("id")); + for (botinfo_map::const_iterator it = BotListByNick->begin(), it_end = BotListByNick->end(); it != it_end; ++it) + { + it->second->server = Me; + ++Me->users; + } + + /* Announce ourselves to the logfile. */ + Log() << "Anope " << Anope::Version() << " starting up" << (Anope::Debug || Anope::ReadOnly ? " (options:" : "") << (Anope::Debug ? " debug" : "") << (Anope::ReadOnly ? " readonly" : "") << (Anope::Debug || Anope::ReadOnly ? ")" : ""); + + InitSignals(); + + /* Initialize multi-language support */ + Language::InitLanguages(); + + /* Initialize random number generator */ + block = Config->GetBlock("options"); + srand(block->Get("seed") ^ time(NULL)); + + /* load modules */ + Log() << "Loading modules..."; + for (int i = 0; i < Config->CountBlock("module"); ++i) + ModuleManager::LoadModule(Config->GetBlock("module", i)->Get("name"), NULL); + +#ifndef _WIN32 + /* We won't background later, so we should setuid now */ + if (Anope::NoFork) + setuidgid(); +#endif + + Module *protocol = ModuleManager::FindFirstOf(PROTOCOL); + if (protocol == NULL) + throw CoreException("You must load a protocol module!"); + + /* Write our PID to the PID file. */ + write_pidfile(); + + Log() << "Using IRCd protocol " << protocol->name; + + /* Auto assign sid if applicable */ + if (IRCD->RequiresID) + { + Anope::string sid = IRCD->SID_Retrieve(); + if (Me->GetSID() == Me->GetName()) + Me->SetSID(sid); + for (botinfo_map::iterator it = BotListByNick->begin(), it_end = BotListByNick->end(); it != it_end; ++it) + it->second->GenerateUID(); + } + + /* Load up databases */ + Log() << "Loading databases..."; + EventReturn MOD_RESULT; + FOREACH_RESULT(OnLoadDatabase, MOD_RESULT, ()); + static_cast(MOD_RESULT); + Log() << "Databases loaded"; + + FOREACH_MOD(OnPostInit, ()); + + for (channel_map::const_iterator it = ChannelList.begin(), it_end = ChannelList.end(); it != it_end; ++it) + it->second->Sync(); + + Serialize::CheckTypes(); +} diff --git a/src/language.cpp b/src/language.cpp new file mode 100644 index 0000000..8c39941 --- /dev/null +++ b/src/language.cpp @@ -0,0 +1,127 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "modules.h" +#include "commands.h" +#include "config.h" +#include "language.h" + +#if GETTEXT_FOUND +# include +#endif + +std::vector Language::Languages; +std::vector Language::Domains; + +void Language::InitLanguages() +{ +#if GETTEXT_FOUND + Log(LOG_DEBUG) << "Initializing Languages..."; + + Languages.clear(); + + if (!bindtextdomain("anope", Anope::LocaleDir.c_str())) + Log() << "Error calling bindtextdomain, " << Anope::LastError(); + else + Log(LOG_DEBUG) << "Successfully bound anope to " << Anope::LocaleDir; + + setlocale(LC_ALL, ""); + + spacesepstream sep(Config->GetBlock("options")->Get("languages")); + Anope::string language; + while (sep.GetToken(language)) + { + const Anope::string &lang_name = Translate(language.c_str(), _("English")); + if (lang_name == "English") + { + Log() << "Unable to use language " << language; + continue; + } + + Log(LOG_DEBUG) << "Found language " << language; + Languages.push_back(language); + } +#else + Log() << "Unable to initialize languages, gettext is not installed"; +#endif +} + +const char *Language::Translate(const char *string) +{ + return Translate("", string); +} + +const char *Language::Translate(User *u, const char *string) +{ + if (u && u->Account()) + return Translate(u->Account(), string); + else + return Translate("", string); +} + +const char *Language::Translate(const NickCore *nc, const char *string) +{ + return Translate(nc ? nc->language.c_str() : "", string); +} + +#if GETTEXT_FOUND + +#if defined(__GLIBC__) && defined(__USE_GNU_GETTEXT) +extern "C" int _nl_msg_cat_cntr; +#endif + +const char *Language::Translate(const char *lang, const char *string) +{ + if (!string || !*string) + return ""; + + if (!lang || !*lang) + lang = Config->DefLanguage.c_str(); + +#if defined(__GLIBC__) && defined(__USE_GNU_GETTEXT) + ++_nl_msg_cat_cntr; +#endif + +#ifdef _WIN32 + SetThreadLocale(MAKELCID(MAKELANGID(WindowsGetLanguage(lang), SUBLANG_DEFAULT), SORT_DEFAULT)); +#else + /* First, set LANG and LANGUAGE env variables. + * Some systems (Debian) don't care about this, so we must setlocale LC_ALL as well. + * BUT if this call fails because the LANGUAGE env variable is set, setlocale resets + * the locale to "C", which short circuits gettext and causes it to fail on systems that + * use the LANGUAGE env variable. We must reset the locale to en_US (or, anything not + * C or POSIX) then. + */ + setenv("LANG", lang, 1); + setenv("LANGUAGE", lang, 1); + if (setlocale(LC_ALL, lang) == NULL) + setlocale(LC_ALL, "en_US"); +#endif + const char *translated_string = dgettext("anope", string); + for (unsigned i = 0; translated_string == string && i < Domains.size(); ++i) + translated_string = dgettext(Domains[i].c_str(), string); +#ifdef _WIN32 + SetThreadLocale(MAKELCID(MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), SORT_DEFAULT)); +#else + unsetenv("LANGUAGE"); + unsetenv("LANG"); + setlocale(LC_ALL, ""); +#endif + + return translated_string; +} +#else +const char *Language::Translate(const char *lang, const char *string) +{ + return string != NULL ? string : ""; +} +#endif diff --git a/src/logger.cpp b/src/logger.cpp new file mode 100644 index 0000000..937fb4d --- /dev/null +++ b/src/logger.cpp @@ -0,0 +1,418 @@ +/* Logging routines. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "modules.h" +#include "commands.h" +#include "channels.h" +#include "users.h" +#include "logger.h" +#include "config.h" +#include "bots.h" +#include "servers.h" +#include "uplink.h" +#include "protocol.h" + +#ifndef _WIN32 +#include +#include +#endif + +static Anope::string GetTimeStamp() +{ + char tbuf[256]; + time_t t; + + if (time(&t) < 0) + t = Anope::CurTime; + + tm tm = *localtime(&t); + if (Anope::Debug) + { + char *s; + struct timeval tv; + gettimeofday(&tv, NULL); + strftime(tbuf, sizeof(tbuf) - 1, "[%b %d %H:%M:%S", &tm); + s = tbuf + strlen(tbuf); + s += snprintf(s, sizeof(tbuf) - (s - tbuf), ".%06d", static_cast(tv.tv_usec)); + strftime(s, sizeof(tbuf) - (s - tbuf) - 1, " %Y]", &tm); + } + else + strftime(tbuf, sizeof(tbuf) - 1, "[%b %d %H:%M:%S %Y]", &tm); + + return tbuf; +} + +static inline Anope::string CreateLogName(const Anope::string &file, time_t t = Anope::CurTime) +{ + char timestamp[32]; + tm *tm = localtime(&t); + strftime(timestamp, sizeof(timestamp), "%Y%m%d", tm); + + return Anope::LogDir + "/" + file + "." + timestamp; +} + +LogFile::LogFile(const Anope::string &name) : filename(name), stream(name.c_str(), std::ios_base::out | std::ios_base::app) +{ +} + +LogFile::~LogFile() +{ + this->stream.close(); +} + +const Anope::string &LogFile::GetName() const +{ + return this->filename; +} + +Log::Log(LogType t, const Anope::string &cat, BotInfo *b) : bi(b), u(NULL), nc(NULL), c(NULL), source(NULL), chan(NULL), ci(NULL), s(NULL), m(NULL), type(t), category(cat) +{ +} + +Log::Log(LogType t, CommandSource &src, Command *_c, ChannelInfo *_ci) : u(src.GetUser()), nc(src.nc), c(_c), source(&src), chan(NULL), ci(_ci), s(NULL), m(NULL), type(t) +{ + if (!c) + throw CoreException("Invalid pointers passed to Log::Log"); + + if (type != LOG_COMMAND && type != LOG_OVERRIDE && type != LOG_ADMIN) + throw CoreException("This constructor does not support this log type"); + + size_t sl = c->name.find('/'); + this->bi = NULL; + if (sl != Anope::string::npos) + this->bi = BotInfo::Find(c->name.substr(0, sl), true); + this->category = c->name; +} + +Log::Log(User *_u, Channel *ch, const Anope::string &cat) : bi(NULL), u(_u), nc(NULL), c(NULL), source(NULL), chan(ch), ci(chan ? *chan->ci : NULL), s(NULL), m(NULL), type(LOG_CHANNEL), category(cat) +{ + if (!chan) + throw CoreException("Invalid pointers passed to Log::Log"); +} + +Log::Log(User *_u, const Anope::string &cat, BotInfo *_bi) : bi(_bi), u(_u), nc(NULL), c(NULL), source(NULL), chan(NULL), ci(NULL), s(NULL), m(NULL), type(LOG_USER), category(cat) +{ + if (!u) + throw CoreException("Invalid pointers passed to Log::Log"); +} + +Log::Log(Server *serv, const Anope::string &cat, BotInfo *_bi) : bi(_bi), u(NULL), nc(NULL), c(NULL), source(NULL), chan(NULL), ci(NULL), s(serv), m(NULL), type(LOG_SERVER), category(cat) +{ + if (!s) + throw CoreException("Invalid pointer passed to Log::Log"); +} + +Log::Log(BotInfo *b, const Anope::string &cat) : bi(b), u(NULL), nc(NULL), c(NULL), source(NULL), chan(NULL), ci(NULL), s(NULL), m(NULL), type(LOG_NORMAL), category(cat) +{ +} + +Log::Log(Module *mod, const Anope::string &cat, BotInfo *_bi) : bi(_bi), u(NULL), nc(NULL), c(NULL), source(NULL), chan(NULL), ci(NULL), s(NULL), m(mod), type(LOG_MODULE), category(cat) +{ +} + +Log::~Log() +{ + if (Anope::NoFork && Anope::Debug && this->type >= LOG_NORMAL && this->type <= LOG_DEBUG + Anope::Debug - 1) + std::cout << GetTimeStamp() << " Debug: " << this->BuildPrefix() << this->buf.str() << std::endl; + else if (Anope::NoFork && this->type <= LOG_TERMINAL) + std::cout << GetTimeStamp() << " " << this->BuildPrefix() << this->buf.str() << std::endl; + else if (this->type == LOG_TERMINAL) + std::cout << this->BuildPrefix() << this->buf.str() << std::endl; + + FOREACH_MOD(OnLog, (this)); + + if (Config) + for (unsigned i = 0; i < Config->LogInfos.size(); ++i) + if (Config->LogInfos[i].HasType(this->type, this->category)) + Config->LogInfos[i].ProcessMessage(this); +} + +Anope::string Log::FormatSource() const +{ + if (u) + if (nc) + return this->u->GetMask() + " (" + this->nc->display + ")"; + else + return this->u->GetMask(); + else if (nc) + return nc->display; + else if (source) + { + Anope::string nickbuf = source->GetNick(); + if (!nickbuf.empty() && !source->ip.empty()) + nickbuf += " (" + source->ip + ")"; + return nickbuf; + } + return ""; +} + +Anope::string Log::FormatCommand() const +{ + Anope::string buffer = FormatSource() + " used " + (source != NULL && !source->command.empty() ? source->command : this->c->name) + " "; + if (this->ci) + buffer += "on " + this->ci->name + " "; + + return buffer; +} + +Anope::string Log::BuildPrefix() const +{ + Anope::string buffer; + + switch (this->type) + { + case LOG_ADMIN: + { + if (!this->c) + break; + buffer += "ADMIN: " + FormatCommand(); + break; + } + case LOG_OVERRIDE: + { + if (!this->c) + break; + buffer += "OVERRIDE: " + FormatCommand(); + break; + } + case LOG_COMMAND: + { + if (!this->c) + break; + buffer += "COMMAND: " + FormatCommand(); + break; + } + case LOG_CHANNEL: + { + if (!this->chan) + break; + buffer += "CHANNEL: "; + Anope::string src = FormatSource(); + if (!src.empty()) + buffer += src + " "; + buffer += this->category + " " + this->chan->name + " "; + break; + } + case LOG_USER: + { + if (this->u) + buffer += "USERS: " + FormatSource() + " "; + break; + } + case LOG_SERVER: + { + if (this->s) + buffer += "SERVER: " + this->s->GetName() + " (" + this->s->GetDescription() + ") "; + break; + } + case LOG_MODULE: + { + if (this->m) + buffer += this->m->name.upper() + ": "; + break; + } + default: + break; + } + + return buffer; +} + +LogInfo::LogInfo(int la, bool rio, bool ldebug) : bot(NULL), last_day(0), log_age(la), raw_io(rio), debug(ldebug) +{ +} + +LogInfo::~LogInfo() +{ + for (unsigned i = 0; i < this->logfiles.size(); ++i) + delete this->logfiles[i]; + this->logfiles.clear(); +} + +bool LogInfo::HasType(LogType ltype, const Anope::string &type) const +{ + const std::vector *list = NULL; + switch (ltype) + { + case LOG_ADMIN: + list = &this->admin; + break; + case LOG_OVERRIDE: + list = &this->override; + break; + case LOG_COMMAND: + list = &this->commands; + break; + case LOG_SERVER: + list = &this->servers; + break; + case LOG_CHANNEL: + list = &this->channels; + break; + case LOG_USER: + list = &this->users; + break; + case LOG_TERMINAL: + return true; + case LOG_RAWIO: + return (Anope::Debug || this->debug) ? true : this->raw_io; + case LOG_DEBUG: + return Anope::Debug ? true : this->debug; + case LOG_DEBUG_2: + case LOG_DEBUG_3: + case LOG_DEBUG_4: + break; + case LOG_MODULE: + case LOG_NORMAL: + default: + list = &this->normal; + break; + } + + if (list == NULL) + return false; + + for (unsigned i = 0; i < list->size(); ++i) + { + Anope::string cat = list->at(i); + bool inverse = false; + if (cat[0] == '~') + { + cat.erase(cat.begin()); + inverse = true; + } + if (Anope::Match(type, cat)) + { + return !inverse; + } + } + + return false; +} + +void LogInfo::OpenLogFiles() +{ + for (unsigned i = 0; i < this->logfiles.size(); ++i) + delete this->logfiles[i]; + this->logfiles.clear(); + + for (unsigned i = 0; i < this->targets.size(); ++i) + { + const Anope::string &target = this->targets[i]; + + if (target.empty() || target[0] == '#' || target == "globops" || target.find(":") != Anope::string::npos) + continue; + + LogFile *lf = new LogFile(CreateLogName(target)); + if (!lf->stream.is_open()) + { + Log() << "Unable to open logfile " << lf->GetName(); + delete lf; + } + else + this->logfiles.push_back(lf); + } +} + +void LogInfo::ProcessMessage(const Log *l) +{ + if (!this->sources.empty()) + { + bool log = false; + for (unsigned i = 0; i < this->sources.size() && !log; ++i) + { + const Anope::string &src = this->sources[i]; + + if (l->bi && src == l->bi->nick) + log = true; + else if (l->u && src == l->u->nick) + log = true; + else if (l->nc && src == l->nc->display) + log = true; + else if (l->ci && src == l->ci->name) + log = true; + else if (l->m && src == l->m->name) + log = true; + else if (l->s && src == l->s->GetName()) + log = true; + } + if (!log) + return; + } + + const Anope::string &buffer = l->BuildPrefix() + l->buf.str(); + + FOREACH_MOD(OnLogMessage, (this, l, buffer)); + + for (unsigned i = 0; i < this->targets.size(); ++i) + { + const Anope::string &target = this->targets[i]; + + if (!target.empty() && target[0] == '#') + { + if (UplinkSock && l->type <= LOG_NORMAL && Me && Me->IsSynced()) + { + Channel *c = Channel::Find(target); + if (!c) + continue; + + BotInfo *bi = l->bi; + if (!bi) + bi = this->bot; + if (!bi) + bi = c->ci->WhoSends(); + if (bi) + IRCD->SendPrivmsg(bi, c->name, "%s", buffer.c_str()); + } + } + else if (target == "globops") + { + if (UplinkSock && l->type <= LOG_NORMAL && Me && Me->IsSynced()) + { + BotInfo *bi = l->bi; + if (!bi) + bi = this->bot; + if (bi) + IRCD->SendGlobops(bi, "%s", buffer.c_str()); + } + } + } + + tm *tm = localtime(&Anope::CurTime); + if (tm->tm_mday != this->last_day) + { + this->last_day = tm->tm_mday; + this->OpenLogFiles(); + + if (this->log_age) + for (unsigned i = 0; i < this->targets.size(); ++i) + { + const Anope::string &target = this->targets[i]; + + if (target.empty() || target[0] == '#' || target == "globops" || target.find(":") != Anope::string::npos) + continue; + + Anope::string oldlog = CreateLogName(target, Anope::CurTime - 86400 * this->log_age); + if (IsFile(oldlog)) + { + unlink(oldlog.c_str()); + Log(LOG_DEBUG) << "Deleted old logfile " << oldlog; + } + } + } + + for (unsigned i = 0; i < this->logfiles.size(); ++i) + { + LogFile *lf = this->logfiles[i]; + lf->stream << GetTimeStamp() << " " << buffer << std::endl; + } +} diff --git a/src/mail.cpp b/src/mail.cpp new file mode 100644 index 0000000..ee947c0 --- /dev/null +++ b/src/mail.cpp @@ -0,0 +1,164 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "mail.h" +#include "config.h" + +Mail::Message::Message(const Anope::string &sf, const Anope::string &mailto, const Anope::string &a, const Anope::string &s, const Anope::string &m) : Thread(), sendmail_path(Config->GetBlock("mail")->Get("sendmailpath")), send_from(sf), mail_to(mailto), addr(a), subject(s), message(m), dont_quote_addresses(Config->GetBlock("mail")->Get("dontquoteaddresses")), success(false) +{ +} + +Mail::Message::~Message() +{ + if (success) + Log(LOG_NORMAL, "mail") << "Successfully delivered mail for " << mail_to << " (" << addr << ")"; + else + Log(LOG_NORMAL, "mail") << "Error delivering mail for " << mail_to << " (" << addr << ")"; +} + +void Mail::Message::Run() +{ + FILE *pipe = popen(sendmail_path.c_str(), "w"); + + if (!pipe) + { + SetExitState(); + return; + } + + fprintf(pipe, "From: %s\n", send_from.c_str()); + if (this->dont_quote_addresses) + fprintf(pipe, "To: %s <%s>\n", mail_to.c_str(), addr.c_str()); + else + fprintf(pipe, "To: \"%s\" <%s>\n", mail_to.c_str(), addr.c_str()); + fprintf(pipe, "Subject: %s\n", subject.c_str()); + fprintf(pipe, "Content-Type: text/plain; charset=UTF-8;\n"); + fprintf(pipe, "Content-Transfer-Encoding: 8bit\n"); + fprintf(pipe, "\n"); + fprintf(pipe, "%s", message.c_str()); + fprintf(pipe, "\n.\n"); + + pclose(pipe); + + success = true; + SetExitState(); +} + +bool Mail::Send(User *u, NickCore *nc, BotInfo *service, const Anope::string &subject, const Anope::string &message) +{ + if (!nc || !service || subject.empty() || message.empty()) + return false; + + Configuration::Block *b = Config->GetBlock("mail"); + + if (!u) + { + if (!b->Get("usemail") || b->Get("sendfrom").empty()) + return false; + else if (nc->email.empty()) + return false; + + nc->lastmail = Anope::CurTime; + Thread *t = new Mail::Message(b->Get("sendfrom"), nc->display, nc->email, subject, message); + t->Start(); + return true; + } + else + { + if (!b->Get("usemail") || b->Get("sendfrom").empty()) + u->SendMessage(service, _("Services have been configured to not send mail.")); + else if (Anope::CurTime - u->lastmail < b->Get("delay")) + u->SendMessage(service, _("Please wait \002%d\002 seconds and retry."), b->Get("delay") - (Anope::CurTime - u->lastmail)); + else if (nc->email.empty()) + u->SendMessage(service, _("E-mail for \002%s\002 is invalid."), nc->display.c_str()); + else + { + u->lastmail = nc->lastmail = Anope::CurTime; + Thread *t = new Mail::Message(b->Get("sendfrom"), nc->display, nc->email, subject, message); + t->Start(); + return true; + } + + return false; + } +} + +bool Mail::Send(NickCore *nc, const Anope::string &subject, const Anope::string &message) +{ + Configuration::Block *b = Config->GetBlock("mail"); + if (!b->Get("usemail") || b->Get("sendfrom").empty() || !nc || nc->email.empty() || subject.empty() || message.empty()) + return false; + + nc->lastmail = Anope::CurTime; + Thread *t = new Mail::Message(b->Get("sendfrom"), nc->display, nc->email, subject, message); + t->Start(); + + return true; +} + +/** + * Checks whether we have a valid, common e-mail address. + * This is NOT entirely RFC compliant, and won't be so, because I said + * *common* cases. ;) It is very unlikely that e-mail addresses that + * are really being used will fail the check. + * + * @param email Email to Validate + * @return bool + */ +bool Mail::Validate(const Anope::string &email) +{ + bool has_period = false; + + static char specials[] = {'(', ')', '<', '>', '@', ',', ';', ':', '\\', '\"', '[', ']', ' '}; + + if (email.empty()) + return false; + Anope::string copy = email; + + size_t at = copy.find('@'); + if (at == Anope::string::npos) + return false; + Anope::string domain = copy.substr(at + 1); + copy = copy.substr(0, at); + + /* Don't accept empty copy or domain. */ + if (copy.empty() || domain.empty()) + return false; + + /* Check for forbidden characters in the name */ + for (unsigned i = 0, end = copy.length(); i < end; ++i) + { + if (copy[i] <= 31 || copy[i] >= 127) + return false; + for (unsigned int j = 0; j < 13; ++j) + if (copy[i] == specials[j]) + return false; + } + + /* Check for forbidden characters in the domain */ + for (unsigned i = 0, end = domain.length(); i < end; ++i) + { + if (domain[i] <= 31 || domain[i] >= 127) + return false; + for (unsigned int j = 0; j < 13; ++j) + if (domain[i] == specials[j]) + return false; + if (domain[i] == '.') + { + if (!i || i == end - 1) + return false; + has_period = true; + } + } + + return has_period; +} diff --git a/src/main.cpp b/src/main.cpp new file mode 100644 index 0000000..660e145 --- /dev/null +++ b/src/main.cpp @@ -0,0 +1,218 @@ +/* Services -- main source file. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "timers.h" +#include "config.h" +#include "bots.h" +#include "socketengine.h" +#include "uplink.h" + +#ifndef _WIN32 +#include +#else +#include +#endif + +/* Command-line options: */ +int Anope::Debug = 0; +bool Anope::ReadOnly = false, Anope::NoFork = false, Anope::NoThird = false, Anope::NoExpire = false, Anope::ProtocolDebug = false; +Anope::string Anope::ServicesDir; +Anope::string Anope::ServicesBin; + +int Anope::ReturnValue = 0; +sig_atomic_t Anope::Signal = 0; +bool Anope::Quitting = false; +bool Anope::Restarting = false; +Anope::string Anope::QuitReason; + +static Anope::string BinaryDir; /* Full path to services bin directory */ + +time_t Anope::StartTime = time(NULL); +time_t Anope::CurTime = time(NULL); + +int Anope::CurrentUplink = -1; + +class UpdateTimer : public Timer +{ + public: + UpdateTimer(time_t timeout) : Timer(timeout, Anope::CurTime, true) { } + + void Tick(time_t) anope_override + { + Anope::SaveDatabases(); + } +}; + +class ExpireTimer : public Timer +{ + public: + ExpireTimer(time_t timeout) : Timer(timeout, Anope::CurTime, true) { } + + void Tick(time_t) anope_override + { + FOREACH_MOD(OnExpireTick, ()); + } +}; + +void Anope::SaveDatabases() +{ + if (Anope::ReadOnly) + return; + + Log(LOG_DEBUG) << "Saving databases"; + FOREACH_MOD(OnSaveDatabase, ()); +} + +/** The following comes from InspIRCd to get the full path of the Anope executable + */ +static Anope::string GetFullProgDir(const Anope::string &argv0) +{ + char buffer[PATH_MAX]; +#ifdef _WIN32 + /* Windows has specific API calls to get the EXE path that never fail. + * For once, Windows has something of use, compared to the POSIX code + * for this, this is positively neato. + */ + if (GetModuleFileName(NULL, buffer, PATH_MAX)) + { + Anope::string fullpath = buffer; + Anope::string::size_type n = fullpath.rfind("\\"); + Anope::ServicesBin = fullpath.substr(n + 1, fullpath.length()); + return fullpath.substr(0, n); + } +#else + // Get the current working directory + if (getcwd(buffer, PATH_MAX)) + { + Anope::string remainder = argv0; + + Anope::ServicesBin = remainder; + Anope::string::size_type n = Anope::ServicesBin.rfind("/"); + Anope::string fullpath; + if (Anope::ServicesBin[0] == '/') + fullpath = Anope::ServicesBin.substr(0, n); + else + fullpath = Anope::string(buffer) + "/" + Anope::ServicesBin.substr(0, n); + Anope::ServicesBin = Anope::ServicesBin.substr(n + 1, remainder.length()); + return fullpath; + } +#endif + return "/"; +} + +/* Main routine. (What does it look like? :-) ) */ + +int main(int ac, char **av, char **envp) +{ + /* String comparisons won't work until we build the case map cache, so do it first */ + Anope::CaseMapRebuild(); + + BinaryDir = GetFullProgDir(av[0]); + if (BinaryDir[BinaryDir.length() - 1] == '.') + BinaryDir = BinaryDir.substr(0, BinaryDir.length() - 2); + +#ifdef _WIN32 + Anope::string::size_type n = BinaryDir.rfind('\\'); +#else + Anope::string::size_type n = BinaryDir.rfind('/'); +#endif + Anope::ServicesDir = BinaryDir.substr(0, n); + +#ifdef _WIN32 + /* Clean out the module runtime directory prior to running, just in case files were left behind during a previous run */ + ModuleManager::CleanupRuntimeDirectory(); + + OnStartup(); +#endif + + try + { + /* General initialization first */ + Anope::Init(ac, av); + } + catch (const CoreException &ex) + { + Log() << ex.GetReason(); + return -1; + } + + try + { + Uplink::Connect(); + } + catch (const SocketException &ex) + { + Log(LOG_TERMINAL) << "Unable to connect to uplink #" << (Anope::CurrentUplink + 1) << " (" << Config->Uplinks[Anope::CurrentUplink].host << ":" << Config->Uplinks[Anope::CurrentUplink].port << "): " << ex.GetReason(); + } + + /* Set up timers */ + time_t last_check = Anope::CurTime; + UpdateTimer updateTimer(Config->GetBlock("options")->Get("updatetimeout", "5m")); + ExpireTimer expireTimer(Config->GetBlock("options")->Get("expiretimeout", "30m")); + + /*** Main loop. ***/ + while (!Anope::Quitting) + { + Log(LOG_DEBUG_2) << "Top of main loop"; + + /* Process timers */ + if (Anope::CurTime - last_check >= Config->TimeoutCheck) + { + TimerManager::TickTimers(Anope::CurTime); + last_check = Anope::CurTime; + } + + /* Process the socket engine */ + SocketEngine::Process(); + + if (Anope::Signal) + Anope::HandleSignal(); + } + + if (Anope::Restarting) + { + FOREACH_MOD(OnRestart, ()); + } + else + { + FOREACH_MOD(OnShutdown, ()); + } + + if (Anope::QuitReason.empty()) + Anope::QuitReason = "Terminating, reason unknown"; + Log() << Anope::QuitReason; + + delete UplinkSock; + + ModuleManager::UnloadAll(); + SocketEngine::Shutdown(); + for (Module *m; (m = ModuleManager::FindFirstOf(PROTOCOL)) != NULL;) + ModuleManager::UnloadModule(m, NULL); + +#ifdef _WIN32 + ModuleManager::CleanupRuntimeDirectory(); + + OnShutdown(); +#endif + + if (Anope::Restarting) + { + chdir(BinaryDir.c_str()); + Anope::string sbin = "./" + Anope::ServicesBin; + av[0] = const_cast(sbin.c_str()); + execve(Anope::ServicesBin.c_str(), av, envp); + Log() << "Restart failed"; + Anope::ReturnValue = -1; + } + + return Anope::ReturnValue; +} diff --git a/src/memos.cpp b/src/memos.cpp new file mode 100644 index 0000000..20d2ce8 --- /dev/null +++ b/src/memos.cpp @@ -0,0 +1,140 @@ +/* MemoServ functions. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "modules.h" +#include "service.h" +#include "memo.h" +#include "users.h" +#include "account.h" +#include "regchannel.h" + +Memo::Memo() : Serializable("Memo") +{ + mi = NULL; + unread = receipt = false; +} + +Memo::~Memo() +{ + if (mi) + { + std::vector::iterator it = std::find(mi->memos->begin(), mi->memos->end(), this); + + if (it != mi->memos->end()) + mi->memos->erase(it); + } +} + +void Memo::Serialize(Serialize::Data &data) const +{ + data["owner"] << this->owner; + data.SetType("time", Serialize::Data::DT_INT); data["time"] << this->time; + data["sender"] << this->sender; + data["text"] << this->text; + data["unread"] << this->unread; + data["receipt"] << this->receipt; +} + +Serializable* Memo::Unserialize(Serializable *obj, Serialize::Data &data) +{ + Anope::string owner; + + data["owner"] >> owner; + + bool ischan; + MemoInfo *mi = MemoInfo::GetMemoInfo(owner, ischan); + if (!mi) + return NULL; + + Memo *m; + if (obj) + m = anope_dynamic_static_cast(obj); + else + { + m = new Memo(); + m->mi = mi; + } + + m->owner = owner; + data["time"] >> m->time; + data["sender"] >> m->sender; + data["text"] >> m->text; + data["unread"] >> m->unread; + data["receipt"] >> m->receipt; + + if (obj == NULL) + mi->memos->push_back(m); + return m; +} + +MemoInfo::MemoInfo() : memomax(0), memos("Memo") +{ +} + +Memo *MemoInfo::GetMemo(unsigned index) const +{ + if (index >= this->memos->size()) + return NULL; + Memo *m = (*memos)[index]; + m->QueueUpdate(); + return m; +} + +unsigned MemoInfo::GetIndex(Memo *m) const +{ + for (unsigned i = 0; i < this->memos->size(); ++i) + if (this->GetMemo(i) == m) + return i; + return -1; +} + +void MemoInfo::Del(unsigned index) +{ + if (index >= this->memos->size()) + return; + + Memo *m = this->GetMemo(index); + + std::vector::iterator it = std::find(memos->begin(), memos->end(), m); + if (it != memos->end()) + memos->erase(it); + + delete m; +} + +bool MemoInfo::HasIgnore(User *u) +{ + for (unsigned i = 0; i < this->ignores.size(); ++i) + if (u->nick.equals_ci(this->ignores[i]) || (u->Account() && u->Account()->display.equals_ci(this->ignores[i])) || Anope::Match(u->GetMask(), Anope::string(this->ignores[i]))) + return true; + return false; +} + +MemoInfo *MemoInfo::GetMemoInfo(const Anope::string &target, bool &ischan) +{ + if (!target.empty() && target[0] == '#') + { + ischan = true; + ChannelInfo *ci = ChannelInfo::Find(target); + if (ci != NULL) + return &ci->memos; + } + else + { + ischan = false; + NickAlias *na = NickAlias::Find(target); + if (na != NULL) + return &na->nc->memos; + } + + return NULL; +} diff --git a/src/messages.cpp b/src/messages.cpp new file mode 100644 index 0000000..0d0882b --- /dev/null +++ b/src/messages.cpp @@ -0,0 +1,502 @@ +/* Common message handlers + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "modules.h" +#include "users.h" +#include "protocol.h" +#include "config.h" +#include "uplink.h" +#include "opertype.h" +#include "messages.h" +#include "servers.h" +#include "channels.h" + +using namespace Message; + +void Away::Run(MessageSource &source, const std::vector ¶ms) +{ + const Anope::string &msg = !params.empty() ? params[0] : ""; + + FOREACH_MOD(OnUserAway, (source.GetUser(), msg)); + if (!msg.empty()) + Log(source.GetUser(), "away") << "is now away: " << msg; + else + Log(source.GetUser(), "away") << "is no longer away"; +} + +void Capab::Run(MessageSource &source, const std::vector ¶ms) +{ + if (params.size() == 1) + { + spacesepstream sep(params[0]); + Anope::string token; + while (sep.GetToken(token)) + Servers::Capab.insert(token); + } + else + for (unsigned i = 0; i < params.size(); ++i) + Servers::Capab.insert(params[i]); +} + +void Error::Run(MessageSource &source, const std::vector ¶ms) +{ + Log(LOG_TERMINAL) << "ERROR: " << params[0]; + Anope::QuitReason = "Received ERROR from uplink: " + params[0]; + Anope::Quitting = true; +} + +void Invite::Run(MessageSource &source, const std::vector ¶ms) +{ + User *targ = User::Find(params[0]); + Channel *c = Channel::Find(params[1]); + + if (!targ || targ->server != Me || !c || c->FindUser(targ)) + return; + + FOREACH_MOD(OnInvite, (source.GetUser(), c, targ)); +} + +void Join::Run(MessageSource &source, const std::vector ¶ms) +{ + User *user = source.GetUser(); + const Anope::string &channels = params[0]; + + Anope::string channel; + commasepstream sep(channels); + + while (sep.GetToken(channel)) + { + /* Special case for /join 0 */ + if (channel == "0") + { + for (User::ChanUserList::iterator it = user->chans.begin(), it_end = user->chans.end(); it != it_end; ) + { + ChanUserContainer *cc = it->second; + Channel *c = cc->chan; + ++it; + + FOREACH_MOD(OnPrePartChannel, (user, c)); + cc->chan->DeleteUser(user); + FOREACH_MOD(OnPartChannel, (user, c, c->name, "")); + } + continue; + } + + std::list users; + users.push_back(std::make_pair(ChannelStatus(), user)); + + Channel *chan = Channel::Find(channel); + SJoin(source, channel, chan ? chan->creation_time : Anope::CurTime, "", users); + } +} + +void Join::SJoin(MessageSource &source, const Anope::string &chan, time_t ts, const Anope::string &modes, const std::list &users) +{ + bool created; + Channel *c = Channel::FindOrCreate(chan, created, ts ? ts : Anope::CurTime); + bool keep_their_modes = true; + + if (created) + c->syncing = true; + /* Some IRCds do not include a TS */ + else if (!ts) + ; + /* Our creation time is newer than what the server gave us, so reset the channel to the older time */ + else if (c->creation_time > ts) + { + c->creation_time = ts; + c->Reset(); + } + /* Their TS is newer, don't accept any modes from them */ + else if (ts > c->creation_time) + keep_their_modes = false; + + /* Update the modes for the channel */ + if (keep_their_modes && !modes.empty()) + /* If we are syncing, mlock is checked later in Channel::Sync. It is important to not check it here + * so that Channel::SetCorrectModes can correctly detect the presence of channel mode +r. + */ + c->SetModesInternal(source, modes, ts, !c->syncing); + + for (std::list::const_iterator it = users.begin(), it_end = users.end(); it != it_end; ++it) + { + const ChannelStatus &status = it->first; + User *u = it->second; + keep_their_modes = ts <= c->creation_time; // OnJoinChannel can call modules which can modify this channel's ts + + if (c->FindUser(u)) + continue; + + /* Add the user to the channel */ + c->JoinUser(u, keep_their_modes ? &status : NULL); + + /* Check if the user is allowed to join */ + if (c->CheckKick(u)) + continue; + + /* Set whatever modes the user should have, and remove any that + * they aren't allowed to have (secureops etc). + */ + c->SetCorrectModes(u, true); + + FOREACH_MOD(OnJoinChannel, (u, c)); + } + + /* Channel is done syncing */ + if (c->syncing) + { + /* Sync the channel (mode lock, topic, etc) */ + /* the channel is synced when the netmerge is complete */ + Server *src = source.GetServer() ? source.GetServer() : Me; + if (src && src->IsSynced()) + { + c->Sync(); + + if (c->CheckDelete()) + c->QueueForDeletion(); + } + } +} + +void Kick::Run(MessageSource &source, const std::vector ¶ms) +{ + const Anope::string &channel = params[0]; + const Anope::string &users = params[1]; + const Anope::string &reason = params.size() > 2 ? params[2] : ""; + + Channel *c = Channel::Find(channel); + if (!c) + return; + + Anope::string user; + commasepstream sep(users); + + while (sep.GetToken(user)) + c->KickInternal(source, user, reason); +} + +void Kill::Run(MessageSource &source, const std::vector ¶ms) +{ + User *u = User::Find(params[0]); + BotInfo *bi; + + if (!u) + return; + + /* Recover if someone kills us. */ + if (u->server == Me && (bi = dynamic_cast(u))) + { + static time_t last_time = 0; + + if (last_time == Anope::CurTime) + { + Anope::QuitReason = "Kill loop detected. Are Services U:Lined?"; + Anope::Quitting = true; + return; + } + last_time = Anope::CurTime; + + bi->OnKill(); + } + else + u->KillInternal(source, params[1]); +} + +void Message::Mode::Run(MessageSource &source, const std::vector ¶ms) +{ + Anope::string buf; + for (unsigned i = 1; i < params.size(); ++i) + buf += " " + params[i]; + + if (IRCD->IsChannelValid(params[0])) + { + Channel *c = Channel::Find(params[0]); + + if (c) + c->SetModesInternal(source, buf.substr(1), 0); + } + else + { + User *u = User::Find(params[0]); + + if (u) + u->SetModesInternal(source, "%s", buf.substr(1).c_str()); + } +} + +/* XXX We should cache the file somewhere not open/read/close it on every request */ +void MOTD::Run(MessageSource &source, const std::vector ¶ms) +{ + Server *s = Server::Find(params[0]); + if (s != Me) + return; + + FILE *f = fopen(Config->GetBlock("serverinfo")->Get("motd").c_str(), "r"); + if (f) + { + IRCD->SendNumeric(375, source.GetSource(), ":- %s Message of the Day", s->GetName().c_str()); + char buf[BUFSIZE]; + while (fgets(buf, sizeof(buf), f)) + { + buf[strlen(buf) - 1] = 0; + IRCD->SendNumeric(372, source.GetSource(), ":- %s", buf); + } + fclose(f); + IRCD->SendNumeric(376, source.GetSource(), ":End of /MOTD command."); + } + else + IRCD->SendNumeric(422, source.GetSource(), ":- MOTD file not found! Please contact your IRC administrator."); +} + +void Notice::Run(MessageSource &source, const std::vector ¶ms) +{ + Anope::string message = params[1]; + + User *u = source.GetUser(); + + /* ignore channel notices */ + if (!IRCD->IsChannelValid(params[0])) + { + BotInfo *bi = BotInfo::Find(params[0]); + if (!bi) + return; + FOREACH_MOD(OnBotNotice, (u, bi, message)); + } +} + +void Part::Run(MessageSource &source, const std::vector ¶ms) +{ + User *u = source.GetUser(); + const Anope::string &reason = params.size() > 1 ? params[1] : ""; + + Anope::string channel; + commasepstream sep(params[0]); + + while (sep.GetToken(channel)) + { + Channel *c = Channel::Find(channel); + + if (!c || !u->FindChannel(c)) + continue; + + Log(u, c, "part") << "Reason: " << (!reason.empty() ? reason : "No reason"); + FOREACH_MOD(OnPrePartChannel, (u, c)); + c->DeleteUser(u); + FOREACH_MOD(OnPartChannel, (u, c, c->name, !reason.empty() ? reason : "")); + } +} + +void Ping::Run(MessageSource &source, const std::vector ¶ms) +{ + IRCD->SendPong(params.size() > 1 ? params[1] : Me->GetSID(), params[0]); +} + +void Privmsg::Run(MessageSource &source, const std::vector ¶ms) +{ + const Anope::string &receiver = params[0]; + Anope::string message = params[1]; + + User *u = source.GetUser(); + + if (IRCD->IsChannelValid(receiver)) + { + Channel *c = Channel::Find(receiver); + if (c) + { + FOREACH_MOD(OnPrivmsg, (u, c, message)); + } + } + else + { + /* If a server is specified (nick@server format), make sure it matches + * us, and strip it off. */ + Anope::string botname = receiver; + size_t s = receiver.find('@'); + bool nick_only = false; + if (s != Anope::string::npos) + { + Anope::string servername(receiver.begin() + s + 1, receiver.end()); + botname = botname.substr(0, s); + nick_only = true; + if (!servername.equals_ci(Me->GetName())) + return; + } + else if (!IRCD->RequiresID && Config->UseStrictPrivmsg) + { + BotInfo *bi = BotInfo::Find(receiver); + if (!bi) + return; + Log(LOG_DEBUG) << "Ignored PRIVMSG without @ from " << u->nick; + u->SendMessage(bi, _("\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead."), bi->nick.c_str(), bi->nick.c_str(), Me->GetName().c_str(), bi->nick.c_str()); + return; + } + + BotInfo *bi = BotInfo::Find(botname, nick_only); + + if (bi) + { + if (message[0] == '\1' && message[message.length() - 1] == '\1') + { + if (message.substr(0, 6).equals_ci("\1PING ")) + { + Anope::string buf = message; + buf.erase(buf.begin()); + buf.erase(buf.end() - 1); + IRCD->SendCTCP(bi, u->nick, "%s", buf.c_str()); + } + else if (message.substr(0, 9).equals_ci("\1VERSION\1")) + { + Module *enc = ModuleManager::FindFirstOf(ENCRYPTION); + IRCD->SendCTCP(bi, u->nick, "VERSION Anope-%s %s :%s - (%s) -- %s", Anope::Version().c_str(), Me->GetName().c_str(), IRCD->GetProtocolName().c_str(), enc ? enc->name.c_str() : "(none)", Anope::VersionBuildString().c_str()); + } + return; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnBotPrivmsg, MOD_RESULT, (u, bi, message)); + if (MOD_RESULT == EVENT_STOP) + return; + + bi->OnMessage(u, message); + } + } + + return; +} + +void Quit::Run(MessageSource &source, const std::vector ¶ms) +{ + const Anope::string &reason = params[0]; + User *user = source.GetUser(); + + Log(user, "quit") << "quit (Reason: " << (!reason.empty() ? reason : "no reason") << ")"; + + user->Quit(reason); +} + +void SQuit::Run(MessageSource &source, const std::vector ¶ms) +{ + Server *s = Server::Find(params[0]); + + if (!s) + { + Log(LOG_DEBUG) << "SQUIT for nonexistent server " << params[0]; + return; + } + + if (s == Me) + { + if (Me->GetLinks().empty()) + return; + + s = Me->GetLinks().front(); + } + + s->Delete(s->GetName() + " " + s->GetUplink()->GetName()); +} + +void Stats::Run(MessageSource &source, const std::vector ¶ms) +{ + User *u = source.GetUser(); + + switch (params[0][0]) + { + case 'l': + if (u->HasMode("OPER")) + { + IRCD->SendNumeric(211, source.GetSource(), "Server SendBuf SentBytes SentMsgs RecvBuf RecvBytes RecvMsgs ConnTime"); + IRCD->SendNumeric(211, source.GetSource(), "%s %d %d %d %d %d %d %ld", Config->Uplinks[Anope::CurrentUplink].host.c_str(), UplinkSock->WriteBufferLen(), TotalWritten, -1, UplinkSock->ReadBufferLen(), TotalRead, -1, static_cast(Anope::CurTime - Anope::StartTime)); + } + + IRCD->SendNumeric(219, source.GetSource(), "%c :End of /STATS report.", params[0][0]); + break; + case 'o': + case 'O': + /* Check whether the user is an operator */ + if (!u->HasMode("OPER") && Config->GetBlock("options")->Get("hidestatso")) + IRCD->SendNumeric(219, source.GetSource(), "%c :End of /STATS report.", params[0][0]); + else + { + for (unsigned i = 0; i < Oper::opers.size(); ++i) + { + Oper *o = Oper::opers[i]; + + const NickAlias *na = NickAlias::Find(o->name); + if (na) + IRCD->SendNumeric(243, source.GetSource(), "O * * %s %s 0", o->name.c_str(), o->ot->GetName().replace_all_cs(" ", "_").c_str()); + } + + IRCD->SendNumeric(219, source.GetSource(), "%c :End of /STATS report.", params[0][0]); + } + + break; + case 'u': + { + long uptime = static_cast(Anope::CurTime - Anope::StartTime); + IRCD->SendNumeric(242, source.GetSource(), ":Services up %d day%s, %02d:%02d:%02d", uptime / 86400, uptime / 86400 == 1 ? "" : "s", (uptime / 3600) % 24, (uptime / 60) % 60, uptime % 60); + IRCD->SendNumeric(250, source.GetSource(), ":Current users: %d (%d ops); maximum %d", UserListByNick.size(), OperCount, MaxUserCount); + IRCD->SendNumeric(219, source.GetSource(), "%c :End of /STATS report.", params[0][0]); + break; + } /* case 'u' */ + + default: + IRCD->SendNumeric(219, source.GetSource(), "%c :End of /STATS report.", params[0][0]); + } + + return; +} + +void Time::Run(MessageSource &source, const std::vector ¶ms) +{ + time_t t; + time(&t); + struct tm *tm = localtime(&t); + char buf[64]; + strftime(buf, sizeof(buf), "%a %b %d %H:%M:%S %Y %Z", tm); + IRCD->SendNumeric(391, source.GetSource(), "%s :%s", Me->GetName().c_str(), buf); + return; +} + +void Topic::Run(MessageSource &source, const std::vector ¶ms) +{ + Channel *c = Channel::Find(params[0]); + if (c) + c->ChangeTopicInternal(source.GetUser(), source.GetSource(), params[1], Anope::CurTime); + + return; +} + +void Version::Run(MessageSource &source, const std::vector ¶ms) +{ + Module *enc = ModuleManager::FindFirstOf(ENCRYPTION); + IRCD->SendNumeric(351, source.GetSource(), "Anope-%s %s :%s -(%s) -- %s", Anope::Version().c_str(), Me->GetName().c_str(), IRCD->GetProtocolName().c_str(), enc ? enc->name.c_str() : "(none)", Anope::VersionBuildString().c_str()); +} + +void Whois::Run(MessageSource &source, const std::vector ¶ms) +{ + User *u = User::Find(params[0]); + + if (u && u->server == Me) + { + const BotInfo *bi = BotInfo::Find(u->GetUID()); + IRCD->SendNumeric(311, source.GetSource(), "%s %s %s * :%s", u->nick.c_str(), u->GetIdent().c_str(), u->host.c_str(), u->realname.c_str()); + if (bi) + IRCD->SendNumeric(307, source.GetSource(), "%s :is a registered nick", bi->nick.c_str()); + IRCD->SendNumeric(312, source.GetSource(), "%s %s :%s", u->nick.c_str(), Me->GetName().c_str(), Config->GetBlock("serverinfo")->Get("description").c_str()); + if (bi) + IRCD->SendNumeric(317, source.GetSource(), "%s %ld %ld :seconds idle, signon time", bi->nick.c_str(), static_cast(Anope::CurTime - bi->lastmsg), static_cast(bi->signon)); + IRCD->SendNumeric(313, source.GetSource(), "%s :is a Network Service", u->nick.c_str()); + IRCD->SendNumeric(318, source.GetSource(), "%s :End of /WHOIS list.", u->nick.c_str()); + } + else + IRCD->SendNumeric(401, source.GetSource(), "%s :No such user.", params[0].c_str()); +} diff --git a/src/misc.cpp b/src/misc.cpp new file mode 100644 index 0000000..99d5106 --- /dev/null +++ b/src/misc.cpp @@ -0,0 +1,765 @@ +/* Miscellaneous routines. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "build.h" +#include "modules.h" +#include "lists.h" +#include "config.h" +#include "bots.h" +#include "language.h" +#include "regexpr.h" +#include "sockets.h" + +#include +#include +#include +#ifndef _WIN32 +#include +#include +#endif + +NumberList::NumberList(const Anope::string &list, bool descending) : is_valid(true), desc(descending) +{ + Anope::string error; + commasepstream sep(list); + Anope::string token; + + sep.GetToken(token); + if (token.empty()) + token = list; + do + { + size_t t = token.find('-'); + + if (t == Anope::string::npos) + { + try + { + unsigned num = convertTo(token, error, false); + if (error.empty()) + numbers.insert(num); + } + catch (const ConvertException &) + { + error = "1"; + } + + if (!error.empty()) + { + if (!this->InvalidRange(list)) + { + is_valid = false; + return; + } + } + } + else + { + Anope::string error2; + try + { + unsigned num1 = convertTo(token.substr(0, t), error, false); + unsigned num2 = convertTo(token.substr(t + 1), error2, false); + if (error.empty() && error2.empty()) + for (unsigned i = num1; i <= num2; ++i) + numbers.insert(i); + } + catch (const ConvertException &) + { + error = "1"; + } + + if (!error.empty() || !error2.empty()) + { + if (!this->InvalidRange(list)) + { + is_valid = false; + return; + } + } + } + } while (sep.GetToken(token)); +} + +NumberList::~NumberList() +{ +} + +void NumberList::Process() +{ + if (!is_valid) + return; + + if (this->desc) + { + for (std::set::reverse_iterator it = numbers.rbegin(), it_end = numbers.rend(); it != it_end; ++it) + this->HandleNumber(*it); + } + else + { + for (std::set::iterator it = numbers.begin(), it_end = numbers.end(); it != it_end; ++it) + this->HandleNumber(*it); + } +} + +void NumberList::HandleNumber(unsigned) +{ +} + +bool NumberList::InvalidRange(const Anope::string &) +{ + return true; +} + +ListFormatter::ListFormatter(NickCore *acc) : nc(acc) +{ +} + +ListFormatter &ListFormatter::AddColumn(const Anope::string &name) +{ + this->columns.push_back(name); + return *this; +} + +void ListFormatter::AddEntry(const ListEntry &entry) +{ + this->entries.push_back(entry); +} + +bool ListFormatter::IsEmpty() const +{ + return this->entries.empty(); +} + +void ListFormatter::Process(std::vector &buffer) +{ + std::vector tcolumns; + std::map lengths; + std::set breaks; + for (unsigned i = 0; i < this->columns.size(); ++i) + { + tcolumns.push_back(Language::Translate(this->nc, this->columns[i].c_str())); + lengths[this->columns[i]] = tcolumns[i].length(); + } + for (unsigned i = 0; i < this->entries.size(); ++i) + { + ListEntry &e = this->entries[i]; + for (unsigned j = 0; j < this->columns.size(); ++j) + if (e[this->columns[j]].length() > lengths[this->columns[j]]) + lengths[this->columns[j]] = e[this->columns[j]].length(); + } + unsigned length = 0; + for (std::map::iterator it = lengths.begin(), it_end = lengths.end(); it != it_end; ++it) + { + /* Break lines at 80 chars */ + if (length > 80) + { + breaks.insert(it->first); + length = 0; + } + else + length += it->second; + } + + /* Only put a list header if more than 1 column */ + if (this->columns.size() > 1) + { + Anope::string s; + for (unsigned i = 0; i < this->columns.size(); ++i) + { + if (breaks.count(this->columns[i])) + { + buffer.push_back(s); + s = " "; + } + else if (!s.empty()) + s += " "; + s += tcolumns[i]; + if (i + 1 != this->columns.size()) + for (unsigned j = tcolumns[i].length(); j < lengths[this->columns[i]]; ++j) + s += " "; + } + buffer.push_back(s); + } + + for (unsigned i = 0; i < this->entries.size(); ++i) + { + ListEntry &e = this->entries[i]; + + Anope::string s; + for (unsigned j = 0; j < this->columns.size(); ++j) + { + if (breaks.count(this->columns[j])) + { + buffer.push_back(s); + s = " "; + } + else if (!s.empty()) + s += " "; + s += e[this->columns[j]]; + if (j + 1 != this->columns.size()) + for (unsigned k = e[this->columns[j]].length(); k < lengths[this->columns[j]]; ++k) + s += " "; + } + buffer.push_back(s); + } +} + +InfoFormatter::InfoFormatter(NickCore *acc) : nc(acc), longest(0) +{ +} + +void InfoFormatter::Process(std::vector &buffer) +{ + buffer.clear(); + + for (std::vector >::iterator it = this->replies.begin(), it_end = this->replies.end(); it != it_end; ++it) + { + Anope::string s; + for (unsigned i = it->first.length(); i < this->longest; ++i) + s += " "; + s += it->first + ": " + Language::Translate(this->nc, it->second.c_str()); + + buffer.push_back(s); + } +} + +Anope::string& InfoFormatter::operator[](const Anope::string &key) +{ + Anope::string tkey = Language::Translate(this->nc, key.c_str()); + if (tkey.length() > this->longest) + this->longest = tkey.length(); + this->replies.push_back(std::make_pair(tkey, "")); + return this->replies.back().second; +} + +void InfoFormatter::AddOption(const Anope::string &opt) +{ + Anope::string options = Language::Translate(this->nc, "Options"); + Anope::string *optstr = NULL; + for (std::vector >::iterator it = this->replies.begin(), it_end = this->replies.end(); it != it_end; ++it) + { + if (it->first == options) + { + optstr = &it->second; + break; + } + } + if (!optstr) + optstr = &(*this)[_("Options")]; + + if (!optstr->empty()) + *optstr += ", "; + *optstr += Language::Translate(nc, opt.c_str()); +} + +bool Anope::IsFile(const Anope::string &filename) +{ + struct stat fileinfo; + if (!stat(filename.c_str(), &fileinfo)) + return true; + + return false; +} + +time_t Anope::DoTime(const Anope::string &s) +{ + if (s.empty()) + return 0; + + int amount = 0; + Anope::string end; + + try + { + amount = convertTo(s, end, false); + if (!end.empty()) + { + switch (end[0]) + { + case 's': + return amount; + case 'm': + return amount * 60; + case 'h': + return amount * 3600; + case 'd': + return amount * 86400; + case 'w': + return amount * 86400 * 7; + case 'y': + return amount * 86400 * 365; + default: + break; + } + } + } + catch (const ConvertException &) + { + amount = -1; + } + + return amount; +} + +Anope::string Anope::Duration(time_t t, const NickCore *nc) +{ + /* We first calculate everything */ + time_t years = t / 31536000; + time_t days = (t / 86400) % 365; + time_t hours = (t / 3600) % 24; + time_t minutes = (t / 60) % 60; + time_t seconds = (t) % 60; + + if (!years && !days && !hours && !minutes) + return stringify(seconds) + " " + (seconds != 1 ? Language::Translate(nc, _("seconds")) : Language::Translate(nc, _("second"))); + else + { + bool need_comma = false; + Anope::string buffer; + if (years) + { + buffer = stringify(years) + " " + (years != 1 ? Language::Translate(nc, _("years")) : Language::Translate(nc, _("year"))); + need_comma = true; + } + if (days) + { + buffer += need_comma ? ", " : ""; + buffer += stringify(days) + " " + (days != 1 ? Language::Translate(nc, _("days")) : Language::Translate(nc, _("day"))); + need_comma = true; + } + if (hours) + { + buffer += need_comma ? ", " : ""; + buffer += stringify(hours) + " " + (hours != 1 ? Language::Translate(nc, _("hours")) : Language::Translate(nc, _("hour"))); + need_comma = true; + } + if (minutes) + { + buffer += need_comma ? ", " : ""; + buffer += stringify(minutes) + " " + (minutes != 1 ? Language::Translate(nc, _("minutes")) : Language::Translate(nc, _("minute"))); + } + return buffer; + } +} + +Anope::string Anope::strftime(time_t t, const NickCore *nc, bool short_output) +{ + tm tm = *localtime(&t); + char buf[BUFSIZE]; + strftime(buf, sizeof(buf), Language::Translate(nc, _("%b %d %H:%M:%S %Y %Z")), &tm); + if (short_output) + return buf; + if (t < Anope::CurTime) + return Anope::string(buf) + " " + Anope::printf(Language::Translate(nc, _("(%s ago)")), Duration(Anope::CurTime - t, nc).c_str(), nc); + else if (t > Anope::CurTime) + return Anope::string(buf) + " " + Anope::printf(Language::Translate(nc, _("(%s from now)")), Duration(t - Anope::CurTime, nc).c_str(), nc); + else + return Anope::string(buf) + " " + Language::Translate(nc, _("(now)")); +} + +Anope::string Anope::Expires(time_t expires, const NickCore *nc) +{ + if (!expires) + return Language::Translate(nc, NO_EXPIRE); + else if (expires <= Anope::CurTime) + return Language::Translate(nc, _("expires momentarily")); + else + { + char buf[256]; + time_t diff = expires - Anope::CurTime + 59; + + if (diff >= 86400) + { + int days = diff / 86400; + snprintf(buf, sizeof(buf), Language::Translate(nc, days == 1 ? _("expires in %d day") : _("expires in %d days")), days); + } + else + { + if (diff <= 3600) + { + int minutes = diff / 60; + snprintf(buf, sizeof(buf), Language::Translate(nc, minutes == 1 ? _("expires in %d minute") : _("expires in %d minutes")), minutes); + } + else + { + int hours = diff / 3600, minutes; + diff -= hours * 3600; + minutes = diff / 60; + snprintf(buf, sizeof(buf), Language::Translate(nc, hours == 1 && minutes == 1 ? _("expires in %d hour, %d minute") : (hours == 1 && minutes != 1 ? _("expires in %d hour, %d minutes") : (hours != 1 && minutes == 1 ? _("expires in %d hours, %d minute") : _("expires in %d hours, %d minutes")))), hours, minutes); + } + } + + return buf; + } +} + +bool Anope::Match(const Anope::string &str, const Anope::string &mask, bool case_sensitive, bool use_regex) +{ + size_t s = 0, m = 0, str_len = str.length(), mask_len = mask.length(); + + if (use_regex && mask_len >= 2 && mask[0] == '/' && mask[mask.length() - 1] == '/') + { + Anope::string stripped_mask = mask.substr(1, mask_len - 2); + // This is often called with the same mask multiple times in a row, so cache it + static Regex *r = NULL; + + if (r == NULL || r->GetExpression() != stripped_mask) + { + ServiceReference provider("Regex", Config->GetBlock("options")->Get("regexengine")); + if (provider) + { + try + { + delete r; + r = NULL; + // This may throw + r = provider->Compile(stripped_mask); + } + catch (const RegexException &ex) + { + Log(LOG_DEBUG) << ex.GetReason(); + } + } + else + { + delete r; + r = NULL; + } + } + + if (r != NULL && r->Matches(str)) + return true; + + // Fall through to non regex match + } + + while (s < str_len && m < mask_len && mask[m] != '*') + { + char string = str[s], wild = mask[m]; + if (case_sensitive) + { + if (wild != string && wild != '?') + return false; + } + else + { + if (Anope::tolower(wild) != Anope::tolower(string) && wild != '?') + return false; + } + + ++m; + ++s; + } + + size_t sp = Anope::string::npos, mp = Anope::string::npos; + while (s < str_len) + { + char string = str[s], wild = mask[m]; + if (wild == '*') + { + if (++m == mask_len) + return 1; + + mp = m; + sp = s + 1; + } + else if (case_sensitive) + { + if (wild == string || wild == '?') + { + ++m; + ++s; + } + else + { + m = mp; + s = sp++; + } + } + else + { + if (Anope::tolower(wild) == Anope::tolower(string) || wild == '?') + { + ++m; + ++s; + } + else + { + m = mp; + s = sp++; + } + } + } + + if (m < mask_len && mask[m] == '*') + ++m; + + return m == mask_len; +} + +void Anope::Encrypt(const Anope::string &src, Anope::string &dest) +{ + EventReturn MOD_RESULT; + FOREACH_RESULT(OnEncrypt, MOD_RESULT, (src, dest)); + static_cast(MOD_RESULT); +} + +bool Anope::Decrypt(const Anope::string &src, Anope::string &dest) +{ + size_t pos = src.find(':'); + if (pos == Anope::string::npos) + { + Log() << "Error: Anope::Decrypt() called with invalid password string (" << src << ")"; + return false; + } + Anope::string hashm(src.begin(), src.begin() + pos); + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnDecrypt, MOD_RESULT, (hashm, src, dest)); + if (MOD_RESULT == EVENT_ALLOW) + return true; + + return false; +} + +Anope::string Anope::printf(const char *fmt, ...) +{ + va_list args; + char buf[1024]; + va_start(args, fmt); + vsnprintf(buf, sizeof(buf), fmt, args); + va_end(args); + return buf; +} + +Anope::string Anope::Hex(const Anope::string &data) +{ + const char hextable[] = "0123456789abcdef"; + + size_t l = data.length(); + Anope::string rv; + for (size_t i = 0; i < l; ++i) + { + unsigned char c = data[i]; + rv += hextable[c >> 4]; + rv += hextable[c & 0xF]; + } + return rv; +} + +Anope::string Anope::Hex(const char *data, unsigned len) +{ + const char hextable[] = "0123456789abcdef"; + + Anope::string rv; + for (size_t i = 0; i < len; ++i) + { + unsigned char c = data[i]; + rv += hextable[c >> 4]; + rv += hextable[c & 0xF]; + } + return rv; +} + +void Anope::Unhex(const Anope::string &src, Anope::string &dest) +{ + size_t len = src.length(); + Anope::string rv; + for (size_t i = 0; i + 1 < len; i += 2) + { + char h = Anope::tolower(src[i]), l = Anope::tolower(src[i + 1]); + unsigned char byte = (h >= 'a' ? h - 'a' + 10 : h - '0') << 4; + byte += (l >= 'a' ? l - 'a' + 10 : l - '0'); + rv += byte; + } + dest = rv; +} + +void Anope::Unhex(const Anope::string &src, char *dest, size_t sz) +{ + Anope::string d; + Anope::Unhex(src, d); + + memcpy(dest, d.c_str(), std::min(d.length() + 1, sz)); +} + +int Anope::LastErrorCode() +{ +#ifndef _WIN32 + return errno; +#else + return GetLastError(); +#endif +} + +const Anope::string Anope::LastError() +{ +#ifndef _WIN32 + return strerror(errno); +#else + char errbuf[513]; + DWORD err = GetLastError(); + if (!err) + return ""; + FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, NULL, err, 0, errbuf, 512, NULL); + return errbuf; +#endif +} + +Anope::string Anope::Version() +{ +#ifdef VERSION_GIT + return stringify(VERSION_MAJOR) + "." + stringify(VERSION_MINOR) + "." + stringify(VERSION_PATCH) + VERSION_EXTRA + " (" + VERSION_GIT + ")"; +#else + return stringify(VERSION_MAJOR) + "." + stringify(VERSION_MINOR) + "." + stringify(VERSION_PATCH) + VERSION_EXTRA; +#endif +} + +Anope::string Anope::VersionShort() +{ + return stringify(VERSION_MAJOR) + "." + stringify(VERSION_MINOR) + "." + stringify(VERSION_PATCH); +} + +Anope::string Anope::VersionBuildString() +{ +#ifdef REPRODUCIBLE_BUILD + Anope::string s = "build #" + stringify(BUILD); +#else + Anope::string s = "build #" + stringify(BUILD) + ", compiled " + Anope::compiled; +#endif + Anope::string flags; + +#ifdef DEBUG_BUILD + flags += "D"; +#endif +#ifdef VERSION_GIT + flags += "G"; +#endif +#ifdef _WIN32 + flags += "W"; +#endif + + if (!flags.empty()) + s += ", flags " + flags; + + return s; +} + +int Anope::VersionMajor() { return VERSION_MAJOR; } +int Anope::VersionMinor() { return VERSION_MINOR; } +int Anope::VersionPatch() { return VERSION_PATCH; } + +Anope::string Anope::NormalizeBuffer(const Anope::string &buf) +{ + Anope::string newbuf; + + for (unsigned i = 0, end = buf.length(); i < end; ++i) + { + switch (buf[i]) + { + /* ctrl char */ + case 1: + /* Bold ctrl char */ + case 2: + break; + /* Color ctrl char */ + case 3: + /* If the next character is a digit, its also removed */ + if (isdigit(buf[i + 1])) + { + ++i; + + /* not the best way to remove colors + * which are two digit but no worse then + * how the Unreal does with +S - TSL + */ + if (isdigit(buf[i + 1])) + ++i; + + /* Check for background color code + * and remove it as well + */ + if (buf[i + 1] == ',') + { + ++i; + + if (isdigit(buf[i + 1])) + ++i; + /* not the best way to remove colors + * which are two digit but no worse then + * how the Unreal does with +S - TSL + */ + if (isdigit(buf[i + 1])) + ++i; + } + } + + break; + /* line feed char */ + case 10: + /* carriage returns char */ + case 13: + /* Reverse ctrl char */ + case 22: + /* Italic ctrl char */ + case 29: + /* Underline ctrl char */ + case 31: + break; + /* A valid char gets copied into the new buffer */ + default: + newbuf += buf[i]; + } + } + + return newbuf; +} + +Anope::string Anope::Resolve(const Anope::string &host, int type) +{ + Anope::string result = host; + + addrinfo hints; + memset(&hints, 0, sizeof(hints)); + hints.ai_family = type; + + Log(LOG_DEBUG_2) << "Resolver: BlockingQuery: Looking up " << host; + + addrinfo *addrresult = NULL; + if (getaddrinfo(host.c_str(), NULL, &hints, &addrresult) == 0) + { + sockaddrs addr; + memcpy(static_cast(&addr), addrresult->ai_addr, addrresult->ai_addrlen); + result = addr.addr(); + Log(LOG_DEBUG_2) << "Resolver: " << host << " -> " << result; + + freeaddrinfo(addrresult); + } + + return result; +} + +Anope::string Anope::Random(size_t len) +{ + char chars[] = { + 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', + 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', + 'z', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', + 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', + 'Z', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9' + }; + Anope::string buf; + for (size_t i = 0; i < len; ++i) + buf.append(chars[rand() % sizeof(chars)]); + return buf; +} diff --git a/src/modes.cpp b/src/modes.cpp new file mode 100644 index 0000000..2153fd3 --- /dev/null +++ b/src/modes.cpp @@ -0,0 +1,896 @@ +/* Mode support + * + * (C) 2008-2011 Adam + * (C) 2008-2022 Anope Team + * + * Please read COPYING and README for further details. + */ + +#include "services.h" +#include "modules.h" +#include "config.h" +#include "sockets.h" +#include "protocol.h" +#include "channels.h" +#include "uplink.h" + +struct StackerInfo; + +/* List of pairs of user/channels and their stacker info */ +static std::map UserStackerObjects; +static std::map ChannelStackerObjects; + +/* Array of all modes Anope knows about.*/ +static std::vector ChannelModes; +static std::vector UserModes; + +/* Modes are in this array are at position + * modechar. Additionally, status modes are in this array (again) at statuschar. + */ +static std::vector ChannelModesIdx; +static std::vector UserModesIdx; + +static std::map ChannelModesByName; +static std::map UserModesByName; + +/* Sorted by status */ +static std::vector ChannelModesByStatus; + +/* Number of generic modes we support */ +unsigned ModeManager::GenericChannelModes = 0, ModeManager::GenericUserModes = 0; + +struct StackerInfo +{ + /* Modes to be added */ + std::list > AddModes; + /* Modes to be deleted */ + std::list > DelModes; + /* Bot this is sent from */ + BotInfo *bi; + + StackerInfo() : bi(NULL) { } + + /** Add a mode to this object + * @param mode The mode + * @param set true if setting, false if unsetting + * @param param The param for the mode + */ + void AddMode(Mode *mode, bool set, const Anope::string ¶m); +}; + +ChannelStatus::ChannelStatus() +{ +} + +ChannelStatus::ChannelStatus(const Anope::string &m) : modes(m) +{ +} + +void ChannelStatus::AddMode(char c) +{ + if (modes.find(c) == Anope::string::npos) + modes.append(c); +} + +void ChannelStatus::DelMode(char c) +{ + modes = modes.replace_all_cs(c, ""); +} + +bool ChannelStatus::HasMode(char c) const +{ + return modes.find(c) != Anope::string::npos; +} + +bool ChannelStatus::Empty() const +{ + return modes.empty(); +} + +void ChannelStatus::Clear() +{ + modes.clear(); +} + +const Anope::string &ChannelStatus::Modes() const +{ + return modes; +} + +Anope::string ChannelStatus::BuildModePrefixList() const +{ + Anope::string ret; + + for (size_t i = 0; i < modes.length(); ++i) + { + ChannelMode *cm = ModeManager::FindChannelModeByChar(modes[i]); + if (cm != NULL && cm->type == MODE_STATUS) + { + ChannelModeStatus *cms = anope_dynamic_static_cast(cm); + ret += cms->symbol; + } + } + + return ret; +} + +Mode::Mode(const Anope::string &mname, ModeClass mcl, char mch, ModeType mt) : name(mname), mclass(mcl), mchar(mch), type(mt) +{ +} + +Mode::~Mode() +{ +} + +bool Mode::CanSet(User *u) const +{ + return true; +} + +UserMode::UserMode(const Anope::string &un, char mch) : Mode(un, MC_USER, mch, MODE_REGULAR) +{ +} + +UserModeParam::UserModeParam(const Anope::string &un, char mch) : UserMode(un, mch) +{ + this->type = MODE_PARAM; +} + +ChannelMode::ChannelMode(const Anope::string &cm, char mch) : Mode(cm, MC_CHANNEL, mch, MODE_REGULAR) +{ +} + +bool ChannelMode::CanSet(User *u) const +{ + EventReturn MOD_RESULT; + FOREACH_RESULT(OnCanSet, MOD_RESULT, (u, this)); + return MOD_RESULT != EVENT_STOP; +} + +ChannelMode *ChannelMode::Wrap(Anope::string ¶m) +{ + return this; +} + +ChannelMode *ChannelMode::Unwrap(Anope::string ¶m) +{ + for (unsigned i = 0; i < listeners.size(); ++i) + { + ChannelMode *cm = listeners[i]->Unwrap(this, param); + if (cm != this) + return cm; + } + + return this; +} + +ChannelMode *ChannelMode::Unwrap(ChannelMode *, Anope::string ¶m) +{ + throw CoreException("Unwrap in channel mode"); +} + +ChannelModeList::ChannelModeList(const Anope::string &cm, char mch) : ChannelMode(cm, mch) +{ + this->type = MODE_LIST; +} + +bool ChannelModeList::IsValid(Anope::string &mask) const +{ + if (name == "BAN" || name == "EXCEPT" || name == "INVITEOVERRIDE") + mask = IRCD->NormalizeMask(mask); + return true; +} + +ChannelModeParam::ChannelModeParam(const Anope::string &cm, char mch, bool ma) : ChannelMode(cm, mch), minus_no_arg(ma) +{ + this->type = MODE_PARAM; +} + +ChannelModeStatus::ChannelModeStatus(const Anope::string &mname, char modeChar, char msymbol, unsigned mlevel) : ChannelMode(mname, modeChar), symbol(msymbol), level(mlevel) +{ + this->type = MODE_STATUS; +} + +template +ChannelModeVirtual::ChannelModeVirtual(const Anope::string &mname, const Anope::string &basename) : T(mname, 0) + , base(basename) +{ + basech = ModeManager::FindChannelModeByName(base); + if (basech) + basech->listeners.push_back(this); +} + +template +ChannelModeVirtual::~ChannelModeVirtual() +{ + if (basech) + { + std::vector::iterator it = std::find(basech->listeners.begin(), basech->listeners.end(), this); + if (it != basech->listeners.end()) + basech->listeners.erase(it); + } +} + +template +void ChannelModeVirtual::Check() +{ + if (basech == NULL) + { + basech = ModeManager::FindChannelModeByName(base); + if (basech) + basech->listeners.push_back(this); + } +} + +template +ChannelMode *ChannelModeVirtual::Wrap(Anope::string ¶m) +{ + return basech; +} + +template class ChannelModeVirtual; +template class ChannelModeVirtual; + +bool UserModeOperOnly::CanSet(User *u) const +{ + return u && u->HasMode("OPER"); +} + +bool UserModeNoone::CanSet(User *u) const +{ + return false; +} + +bool ChannelModeKey::IsValid(Anope::string &value) const +{ + if (!value.empty() && value.find(':') == Anope::string::npos && value.find(',') == Anope::string::npos) + return true; + + return false; +} + +bool ChannelModeOperOnly::CanSet(User *u) const +{ + return u && u->HasMode("OPER"); +} + +bool ChannelModeNoone::CanSet(User *u) const +{ + return false; +} + +void StackerInfo::AddMode(Mode *mode, bool set, const Anope::string ¶m) +{ + bool is_param = mode->type == MODE_PARAM; + + std::list > *list, *otherlist; + if (set) + { + list = &AddModes; + otherlist = &DelModes; + } + else + { + list = &DelModes; + otherlist = &AddModes; + } + + /* Loop through the list and find if this mode is already on here */ + std::list >::iterator it, it_end; + for (it = list->begin(), it_end = list->end(); it != it_end; ++it) + { + /* The param must match too (can have multiple status or list modes), but + * if it is a param mode it can match no matter what the param is + */ + if (it->first == mode && (is_param || param.equals_cs(it->second))) + { + list->erase(it); + /* It can only be on this list once */ + break; + } + } + /* If the mode is on the other list, remove it from there (eg, we don't want +o-o Adam Adam) */ + for (it = otherlist->begin(), it_end = otherlist->end(); it != it_end; ++it) + { + /* The param must match too (can have multiple status or list modes), but + * if it is a param mode it can match no matter what the param is + */ + if (it->first == mode && (is_param || param.equals_cs(it->second))) + { + otherlist->erase(it); + return; + /* Note that we return here because this is like setting + and - on the same mode within the same + * cycle, no change is made. This causes no problems with something like - + and -, because after the + * second mode change the list is empty, and the third mode change starts fresh. + */ + } + } + + /* Add this mode and its param to our list */ + list->push_back(std::make_pair(mode, param)); +} + +static class ModePipe : public Pipe +{ + public: + void OnNotify() + { + ModeManager::ProcessModes(); + } +} *modePipe; + +/** Get the stacker info for an item, if one doesn't exist it is created + * @param Item The user/channel etc + * @return The stacker info + */ +template +static StackerInfo *GetInfo(List &l, Object *o) +{ + typename List::const_iterator it = l.find(o); + if (it != l.end()) + return it->second; + + StackerInfo *s = new StackerInfo(); + l[o] = s; + return s; +} + +/** Build a list of mode strings to send to the IRCd from the mode stacker + * @param info The stacker info for a channel or user + * @return a list of strings + */ +static std::list BuildModeStrings(StackerInfo *info) +{ + std::list ret; + std::list >::iterator it, it_end; + Anope::string buf = "+", parambuf; + unsigned NModes = 0; + + for (it = info->AddModes.begin(), it_end = info->AddModes.end(); it != it_end; ++it) + { + if (++NModes > IRCD->MaxModes || (buf.length() + parambuf.length() > IRCD->MaxLine - 100)) // Leave room for command, channel, etc + { + ret.push_back(buf + parambuf); + buf = "+"; + parambuf.clear(); + NModes = 1; + } + + buf += it->first->mchar; + + if (!it->second.empty()) + parambuf += " " + it->second; + } + + if (buf[buf.length() - 1] == '+') + buf.erase(buf.length() - 1); + + buf += "-"; + for (it = info->DelModes.begin(), it_end = info->DelModes.end(); it != it_end; ++it) + { + if (++NModes > IRCD->MaxModes || (buf.length() + parambuf.length() > IRCD->MaxLine - 100)) // Leave room for command, channel, etc + { + ret.push_back(buf + parambuf); + buf = "-"; + parambuf.clear(); + NModes = 1; + } + + buf += it->first->mchar; + + if (!it->second.empty()) + parambuf += " " + it->second; + } + + if (buf[buf.length() - 1] == '-') + buf.erase(buf.length() - 1); + + if (!buf.empty()) + ret.push_back(buf + parambuf); + + return ret; +} + +bool ModeManager::AddUserMode(UserMode *um) +{ + if (ModeManager::FindUserModeByChar(um->mchar) != NULL) + return false; + if (ModeManager::FindUserModeByName(um->name) != NULL) + return false; + + if (um->name.empty()) + { + um->name = stringify(++GenericUserModes); + Log() << "ModeManager: Added generic support for user mode " << um->mchar; + } + + unsigned want = um->mchar; + if (want >= UserModesIdx.size()) + UserModesIdx.resize(want + 1); + UserModesIdx[want] = um; + + UserModesByName[um->name] = um; + + UserModes.push_back(um); + + FOREACH_MOD(OnUserModeAdd, (um)); + + return true; +} + +bool ModeManager::AddChannelMode(ChannelMode *cm) +{ + if (cm->mchar && ModeManager::FindChannelModeByChar(cm->mchar) != NULL) + return false; + if (ModeManager::FindChannelModeByName(cm->name) != NULL) + return false; + + if (cm->name.empty()) + { + cm->name = stringify(++GenericChannelModes); + Log() << "ModeManager: Added generic support for channel mode " << cm->mchar; + } + + if (cm->mchar) + { + unsigned want = cm->mchar; + if (want >= ChannelModesIdx.size()) + ChannelModesIdx.resize(want + 1); + ChannelModesIdx[want] = cm; + } + + if (cm->type == MODE_STATUS) + { + ChannelModeStatus *cms = anope_dynamic_static_cast(cm); + unsigned want = cms->symbol; + if (want >= ChannelModesIdx.size()) + ChannelModesIdx.resize(want + 1); + ChannelModesIdx[want] = cms; + + RebuildStatusModes(); + } + + ChannelModesByName[cm->name] = cm; + + ChannelModes.push_back(cm); + + FOREACH_MOD(OnChannelModeAdd, (cm)); + + for (unsigned int i = 0; i < ChannelModes.size(); ++i) + ChannelModes[i]->Check(); + + return true; +} + +void ModeManager::RemoveUserMode(UserMode *um) +{ + if (!um) + return; + + unsigned want = um->mchar; + if (want >= UserModesIdx.size()) + return; + + if (UserModesIdx[want] != um) + return; + + UserModesIdx[want] = NULL; + + UserModesByName.erase(um->name); + + std::vector::iterator it = std::find(UserModes.begin(), UserModes.end(), um); + if (it != UserModes.end()) + UserModes.erase(it); + + StackerDel(um); +} + +void ModeManager::RemoveChannelMode(ChannelMode *cm) +{ + if (!cm) + return; + + if (cm->mchar) + { + unsigned want = cm->mchar; + if (want >= ChannelModesIdx.size()) + return; + + if (ChannelModesIdx[want] != cm) + return; + + ChannelModesIdx[want] = NULL; + } + + if (cm->type == MODE_STATUS) + { + ChannelModeStatus *cms = anope_dynamic_static_cast(cm); + unsigned want = cms->symbol; + + if (want >= ChannelModesIdx.size()) + return; + + if (ChannelModesIdx[want] != cm) + return; + + ChannelModesIdx[want] = NULL; + + RebuildStatusModes(); + } + + ChannelModesByName.erase(cm->name); + + std::vector::iterator it = std::find(ChannelModes.begin(), ChannelModes.end(), cm); + if (it != ChannelModes.end()) + ChannelModes.erase(it); + + StackerDel(cm); +} + +ChannelMode *ModeManager::FindChannelModeByChar(char mode) +{ + unsigned want = mode; + if (want >= ChannelModesIdx.size()) + return NULL; + + return ChannelModesIdx[want]; +} + +UserMode *ModeManager::FindUserModeByChar(char mode) +{ + unsigned want = mode; + if (want >= UserModesIdx.size()) + return NULL; + + return UserModesIdx[want]; +} + +ChannelMode *ModeManager::FindChannelModeByName(const Anope::string &name) +{ + std::map::iterator it = ChannelModesByName.find(name); + if (it != ChannelModesByName.end()) + return it->second; + return NULL; +} + +UserMode *ModeManager::FindUserModeByName(const Anope::string &name) +{ + std::map::iterator it = UserModesByName.find(name); + if (it != UserModesByName.end()) + return it->second; + return NULL; +} + +char ModeManager::GetStatusChar(char value) +{ + unsigned want = value; + if (want >= ChannelModesIdx.size()) + return 0; + + ChannelMode *cm = ChannelModesIdx[want]; + if (cm == NULL || cm->type != MODE_STATUS || cm->mchar == value) + return 0; + + return cm->mchar; +} + +const std::vector &ModeManager::GetChannelModes() +{ + return ChannelModes; +} + +const std::vector &ModeManager::GetUserModes() +{ + return UserModes; +} + +const std::vector &ModeManager::GetStatusChannelModesByRank() +{ + return ChannelModesByStatus; +} + +static struct StatusSort +{ + bool operator()(ChannelModeStatus *cm1, ChannelModeStatus *cm2) const + { + return cm1->level > cm2->level; + } +} statuscmp; + +void ModeManager::RebuildStatusModes() +{ + ChannelModesByStatus.clear(); + for (unsigned j = 0; j < ChannelModesIdx.size(); ++j) + { + ChannelMode *cm = ChannelModesIdx[j]; + + if (cm && cm->type == MODE_STATUS && std::find(ChannelModesByStatus.begin(), ChannelModesByStatus.end(), cm) == ChannelModesByStatus.end()) + ChannelModesByStatus.push_back(anope_dynamic_static_cast(cm)); + } + std::sort(ChannelModesByStatus.begin(), ChannelModesByStatus.end(), statuscmp); +} + +void ModeManager::StackerAdd(BotInfo *bi, Channel *c, ChannelMode *cm, bool Set, const Anope::string &Param) +{ + StackerInfo *s = GetInfo(ChannelStackerObjects, c); + s->AddMode(cm, Set, Param); + if (bi) + s->bi = bi; + else + s->bi = c->ci->WhoSends(); + + if (!modePipe) + modePipe = new ModePipe(); + modePipe->Notify(); +} + +void ModeManager::StackerAdd(BotInfo *bi, User *u, UserMode *um, bool Set, const Anope::string &Param) +{ + StackerInfo *s = GetInfo(UserStackerObjects, u); + s->AddMode(um, Set, Param); + if (bi) + s->bi = bi; + + if (!modePipe) + modePipe = new ModePipe(); + modePipe->Notify(); +} + +void ModeManager::ProcessModes() +{ + if (!UserStackerObjects.empty()) + { + for (std::map::const_iterator it = UserStackerObjects.begin(), it_end = UserStackerObjects.end(); it != it_end; ++it) + { + User *u = it->first; + StackerInfo *s = it->second; + + std::list ModeStrings = BuildModeStrings(s); + for (std::list::iterator lit = ModeStrings.begin(), lit_end = ModeStrings.end(); lit != lit_end; ++lit) + IRCD->SendMode(s->bi, u, "%s", lit->c_str()); + delete it->second; + } + UserStackerObjects.clear(); + } + + if (!ChannelStackerObjects.empty()) + { + for (std::map::const_iterator it = ChannelStackerObjects.begin(), it_end = ChannelStackerObjects.end(); it != it_end; ++it) + { + Channel *c = it->first; + StackerInfo *s = it->second; + + std::list ModeStrings = BuildModeStrings(s); + for (std::list::iterator lit = ModeStrings.begin(), lit_end = ModeStrings.end(); lit != lit_end; ++lit) + IRCD->SendMode(s->bi, c, "%s", lit->c_str()); + delete it->second; + } + ChannelStackerObjects.clear(); + } +} + +template +static void StackerDel(std::map &map, T *obj) +{ + typename std::map::iterator it = map.find(obj); + if (it != map.end()) + { + StackerInfo *si = it->second; + std::list ModeStrings = BuildModeStrings(si); + for (std::list::iterator lit = ModeStrings.begin(), lit_end = ModeStrings.end(); lit != lit_end; ++lit) + IRCD->SendMode(si->bi, obj, "%s", lit->c_str()); + + delete si; + map.erase(it); + } +} + +void ModeManager::StackerDel(User *u) +{ + ::StackerDel(UserStackerObjects, u); +} + +void ModeManager::StackerDel(Channel *c) +{ + ::StackerDel(ChannelStackerObjects, c); +} + +void ModeManager::StackerDel(Mode *m) +{ + for (std::map::const_iterator it = UserStackerObjects.begin(), it_end = UserStackerObjects.end(); it != it_end;) + { + StackerInfo *si = it->second; + ++it; + + for (std::list >::iterator it2 = si->AddModes.begin(), it2_end = si->AddModes.end(); it2 != it2_end;) + { + if (it2->first == m) + it2 = si->AddModes.erase(it2); + else + ++it2; + } + + for (std::list >::iterator it2 = si->DelModes.begin(), it2_end = si->DelModes.end(); it2 != it2_end;) + { + if (it2->first == m) + it2 = si->DelModes.erase(it2); + else + ++it2; + } + } + + for (std::map::const_iterator it = ChannelStackerObjects.begin(), it_end = ChannelStackerObjects.end(); it != it_end;) + { + StackerInfo *si = it->second; + ++it; + + for (std::list >::iterator it2 = si->AddModes.begin(), it2_end = si->AddModes.end(); it2 != it2_end;) + { + if (it2->first == m) + it2 = si->AddModes.erase(it2); + else + ++it2; + } + + for (std::list >::iterator it2 = si->DelModes.begin(), it2_end = si->DelModes.end(); it2 != it2_end;) + { + if (it2->first == m) + it2 = si->DelModes.erase(it2); + else + ++it2; + } + } +} + +Entry::Entry(const Anope::string &m, const Anope::string &fh) : name(m), mask(fh), cidr_len(0), family(0) +{ + Anope::string n, u, h; + + size_t at = fh.find('@'); + if (at != Anope::string::npos) + { + this->host = fh.substr(at + 1); + + const Anope::string &nu = fh.substr(0, at); + + size_t ex = nu.find('!'); + if (ex != Anope::string::npos) + { + this->user = nu.substr(ex + 1); + this->nick = nu.substr(0, ex); + } + else + this->user = nu; + } + else + { + if (fh.find('.') != Anope::string::npos || fh.find(':') != Anope::string::npos) + this->host = fh; + else + this->nick = fh; + } + + at = this->host.find('#'); + if (at != Anope::string::npos) + { + this->real = this->host.substr(at + 1); + this->host = this->host.substr(0, at); + } + + /* If the mask is all *'s it will match anything, so just clear it */ + if (this->nick.find_first_not_of("*") == Anope::string::npos) + this->nick.clear(); + + if (this->user.find_first_not_of("*") == Anope::string::npos) + this->user.clear(); + + if (this->host.find_first_not_of("*") == Anope::string::npos) + this->host.clear(); + else + { + /* Host might be a CIDR range */ + size_t sl = this->host.find_last_of('/'); + if (sl != Anope::string::npos) + { + const Anope::string &cidr_ip = this->host.substr(0, sl), + &cidr_range = this->host.substr(sl + 1); + + sockaddrs addr(cidr_ip); + + try + { + if (addr.valid() && cidr_range.is_pos_number_only()) + { + this->cidr_len = convertTo(cidr_range); + + /* If we got here, cidr_len is a valid number. */ + + this->host = cidr_ip; + this->family = addr.family(); + + Log(LOG_DEBUG) << "Ban " << mask << " has cidr " << this->cidr_len; + } + } + catch (const ConvertException &) { } + } + } + + if (this->real.find_first_not_of("*") == Anope::string::npos) + this->real.clear(); +} + +const Anope::string Entry::GetMask() const +{ + return this->mask; +} + +const Anope::string Entry::GetNUHMask() const +{ + Anope::string n = nick.empty() ? "*" : nick, + u = user.empty() ? "*" : user, + h = host.empty() ? "*" : host, + r = real.empty() ? "" : "#" + real, + c; + switch (family) + { + case AF_INET: + if (cidr_len <= 32) + c = "/" + stringify(cidr_len); + break; + case AF_INET6: + if (cidr_len <= 128) + c = "/" + stringify(cidr_len); + break; + } + + return n + "!" + u + "@" + h + c + r; +} + +bool Entry::Matches(User *u, bool full) const +{ + /* First check if this mode has defined any matches (usually for extbans). */ + if (IRCD->IsExtbanValid(this->mask)) + { + ChannelMode *cm = ModeManager::FindChannelModeByName(this->name); + if (cm != NULL && cm->type == MODE_LIST) + { + ChannelModeList *cml = anope_dynamic_static_cast(cm); + if (cml->Matches(u, this)) + return true; + } + } + + /* If the user's displayed host is their real host, then we can do a full match without + * having to worry about exposing a user's IP + */ + full |= u->GetDisplayedHost() == u->host; + + bool ret = true; + + if (!this->nick.empty() && !Anope::Match(u->nick, this->nick)) + ret = false; + + if (!this->user.empty() && !Anope::Match(u->GetVIdent(), this->user) && (!full || !Anope::Match(u->GetIdent(), this->user))) + ret = false; + + if (this->cidr_len && full) + { + try + { + if (!cidr(this->host, this->cidr_len).match(u->ip)) + ret = false; + } + catch (const SocketException &) + { + ret = false; + } + } + else if (!this->host.empty() && !Anope::Match(u->GetDisplayedHost(), this->host) && !Anope::Match(u->GetCloakedHost(), this->host) && + (!full || (!Anope::Match(u->host, this->host) && !Anope::Match(u->ip.addr(), this->host)))) + ret = false; + + if (!this->real.empty() && !Anope::Match(u->realname, this->real)) + ret = false; + + return ret; +} diff --git a/src/module.cpp b/src/module.cpp new file mode 100644 index 0000000..2881c4e --- /dev/null +++ b/src/module.cpp @@ -0,0 +1,129 @@ +/* Modular support + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "services.h" +#include "modules.h" +#include "language.h" +#include "account.h" + +#ifdef GETTEXT_FOUND +# include +#endif + +Module::Module(const Anope::string &modname, const Anope::string &, ModType modtype) : name(modname), type(modtype) +{ + this->handle = NULL; + this->permanent = false; + this->created = Anope::CurTime; + this->SetVersion(Anope::Version()); + + if (type & VENDOR) + this->SetAuthor("Anope"); + else + { + /* Not vendor implies third */ + type |= THIRD; + this->SetAuthor("Unknown"); + } + + if (ModuleManager::FindModule(this->name)) + throw CoreException("Module already exists!"); + + if (Anope::NoThird && type & THIRD) + throw ModuleException("Third party modules may not be loaded"); + + ModuleManager::Modules.push_back(this); + +#if GETTEXT_FOUND + for (unsigned i = 0; i < Language::Languages.size(); ++i) + { + /* Remove .UTF-8 or any other suffix */ + Anope::string lang; + sepstream(Language::Languages[i], '.').GetToken(lang); + + if (Anope::IsFile(Anope::LocaleDir + "/" + lang + "/LC_MESSAGES/" + modname + ".mo")) + { + if (!bindtextdomain(this->name.c_str(), Anope::LocaleDir.c_str())) + Log() << "Error calling bindtextdomain, " << Anope::LastError(); + else + { + Log() << "Found language file " << lang << " for " << modname; + Language::Domains.push_back(modname); + } + break; + } + } +#endif +} + +Module::~Module() +{ + UnsetExtensibles(); + + /* Detach all event hooks for this module */ + ModuleManager::DetachAll(this); + IdentifyRequest::ModuleUnload(this); + /* Clear any active timers this module has */ + TimerManager::DeleteTimersFor(this); + + std::list::iterator it = std::find(ModuleManager::Modules.begin(), ModuleManager::Modules.end(), this); + if (it != ModuleManager::Modules.end()) + ModuleManager::Modules.erase(it); + +#if GETTEXT_FOUND + std::vector::iterator dit = std::find(Language::Domains.begin(), Language::Domains.end(), this->name); + if (dit != Language::Domains.end()) + Language::Domains.erase(dit); +#endif +} + +void Module::SetPermanent(bool state) +{ + this->permanent = state; +} + +bool Module::GetPermanent() const +{ + return this->permanent; +} + +void Module::SetVersion(const Anope::string &nversion) +{ + this->version = nversion; +} + +void Module::SetAuthor(const Anope::string &nauthor) +{ + this->author = nauthor; +} + +void Module::Prioritize() +{ +} + +ModuleVersion::ModuleVersion(const ModuleVersionC &ver) +{ + version_major = ver.version_major; + version_minor = ver.version_minor; + version_patch = ver.version_patch; +} + +int ModuleVersion::GetMajor() const +{ + return this->version_major; +} + +int ModuleVersion::GetMinor() const +{ + return this->version_minor; +} + +int ModuleVersion::GetPatch() const +{ + return this->version_patch; +} diff --git a/src/modulemanager.cpp b/src/modulemanager.cpp new file mode 100644 index 0000000..3317a6f --- /dev/null +++ b/src/modulemanager.cpp @@ -0,0 +1,526 @@ +/* Modular support + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "services.h" +#include "modules.h" +#include "users.h" +#include "regchannel.h" +#include "config.h" + +#include +#include +#ifndef _WIN32 +#include +#include +#include +#endif + +std::list ModuleManager::Modules; +std::vector ModuleManager::EventHandlers[I_SIZE]; + +#ifdef _WIN32 +void ModuleManager::CleanupRuntimeDirectory() +{ + Anope::string dirbuf = Anope::DataDir + "/runtime"; + + Log(LOG_DEBUG) << "Cleaning out Module run time directory (" << dirbuf << ") - this may take a moment, please wait"; + + DIR *dirp = opendir(dirbuf.c_str()); + if (!dirp) + { + Log(LOG_DEBUG) << "Cannot open directory (" << dirbuf << ")"; + return; + } + + for (dirent *dp; (dp = readdir(dirp));) + { + if (!dp->d_ino) + continue; + if (Anope::string(dp->d_name).equals_cs(".") || Anope::string(dp->d_name).equals_cs("..")) + continue; + Anope::string filebuf = dirbuf + "/" + dp->d_name; + unlink(filebuf.c_str()); + } + + closedir(dirp); +} + +/** + * Copy the module from the modules folder to the runtime folder. + * This will prevent module updates while the modules is loaded from + * triggering a segfault, as the actual file in use will be in the + * runtime folder. + * @param name the name of the module to copy + * @param output the destination to copy the module to + * @return MOD_ERR_OK on success + */ +static ModuleReturn moduleCopyFile(const Anope::string &name, Anope::string &output) +{ + Anope::string input = Anope::ModuleDir + "/modules/" + name + ".so"; + + struct stat s; + if (stat(input.c_str(), &s) == -1) + return MOD_ERR_NOEXIST; + else if (!S_ISREG(s.st_mode)) + return MOD_ERR_NOEXIST; + + std::ifstream source(input.c_str(), std::ios_base::in | std::ios_base::binary); + if (!source.is_open()) + return MOD_ERR_NOEXIST; + + char *tmp_output = strdup(output.c_str()); + int target_fd = mkstemp(tmp_output); + if (target_fd == -1 || close(target_fd) == -1) + { + free(tmp_output); + source.close(); + return MOD_ERR_FILE_IO; + } + output = tmp_output; + free(tmp_output); + + Log(LOG_DEBUG_2) << "Runtime module location: " << output; + + std::ofstream target(output.c_str(), std::ios_base::in | std::ios_base::binary); + if (!target.is_open()) + { + source.close(); + return MOD_ERR_FILE_IO; + } + + int want = s.st_size; + char buffer[1024]; + while (want > 0 && !source.fail() && !target.fail()) + { + source.read(buffer, std::min(want, static_cast(sizeof(buffer)))); + int read_len = source.gcount(); + + target.write(buffer, read_len); + want -= read_len; + } + + source.close(); + target.close(); + + return !source.fail() && !target.fail() ? MOD_ERR_OK : MOD_ERR_FILE_IO; +} +#endif + +/* This code was found online at https://web.archive.org/web/20180318184211/https://www.linuxjournal.com/article/3687#comment-26593 + * + * This function will take a pointer from either dlsym or GetProcAddress and cast it in + * a way that won't cause C++ warnings/errors to come up. + */ +template static TYPE function_cast(void *symbol) +{ + union + { + void *symbol; + TYPE function; + } cast; + cast.symbol = symbol; + return cast.function; +} + +ModuleReturn ModuleManager::LoadModule(const Anope::string &modname, User *u) +{ + if (modname.empty()) + return MOD_ERR_PARAMS; + + if (FindModule(modname)) + return MOD_ERR_EXISTS; + + Log(LOG_DEBUG) << "Trying to load module: " << modname; + +#ifdef _WIN32 + /* Generate the filename for the temporary copy of the module */ + Anope::string pbuf = Anope::DataDir + "/runtime/" + modname + ".so.XXXXXX"; + + /* Don't skip return value checking! -GD */ + ModuleReturn ret = moduleCopyFile(modname, pbuf); + if (ret != MOD_ERR_OK) + { + if (ret == MOD_ERR_NOEXIST) + Log(LOG_TERMINAL) << "Error while loading " << modname << " (file does not exist)"; + else if (ret == MOD_ERR_FILE_IO) + Log(LOG_TERMINAL) << "Error while loading " << modname << " (file IO error, check file permissions and diskspace)"; + return ret; + } +#else + Anope::string pbuf = Anope::ModuleDir + "/modules/" + modname + ".so"; +#endif + + dlerror(); + void *handle = dlopen(pbuf.c_str(), RTLD_NOW); + const char *err = dlerror(); + if (!handle) + { + if (err && *err) + Log() << err; + return MOD_ERR_NOLOAD; + } + + try + { + ModuleVersion v = GetVersion(handle); + + if (v.GetMajor() < Anope::VersionMajor() || (v.GetMajor() == Anope::VersionMajor() && v.GetMinor() < Anope::VersionMinor())) + { + Log() << "Module " << modname << " is compiled against an older version of Anope " << v.GetMajor() << "." << v.GetMinor() << ", this is " << Anope::VersionShort(); + dlclose(handle); + return MOD_ERR_VERSION; + } + else if (v.GetMajor() > Anope::VersionMajor() || (v.GetMajor() == Anope::VersionMajor() && v.GetMinor() > Anope::VersionMinor())) + { + Log() << "Module " << modname << " is compiled against a newer version of Anope " << v.GetMajor() << "." << v.GetMinor() << ", this is " << Anope::VersionShort(); + dlclose(handle); + return MOD_ERR_VERSION; + } + else if (v.GetPatch() < Anope::VersionPatch()) + { + Log() << "Module " << modname << " is compiled against an older version of Anope, " << v.GetMajor() << "." << v.GetMinor() << "." << v.GetPatch() << ", this is " << Anope::VersionShort(); + dlclose(handle); + return MOD_ERR_VERSION; + } + else if (v.GetPatch() > Anope::VersionPatch()) + { + Log() << "Module " << modname << " is compiled against a newer version of Anope, " << v.GetMajor() << "." << v.GetMinor() << "." << v.GetPatch() << ", this is " << Anope::VersionShort(); + dlclose(handle); + return MOD_ERR_VERSION; + } + else + { + Log(LOG_DEBUG_2) << "Module " << modname << " is compiled against current version of Anope " << Anope::VersionShort(); + } + } + catch (const ModuleException &ex) + { + /* this error has already been logged */ + dlclose(handle); + return MOD_ERR_NOLOAD; + } + + dlerror(); + Module *(*func)(const Anope::string &, const Anope::string &) = function_cast(dlsym(handle, "AnopeInit")); + err = dlerror(); + if (!func) + { + Log() << "No init function found, not an Anope module"; + if (err && *err) + Log(LOG_DEBUG) << err; + dlclose(handle); + return MOD_ERR_NOLOAD; + } + + /* Create module. */ + Anope::string nick; + if (u) + nick = u->nick; + + Module *m; + + ModuleReturn moderr = MOD_ERR_OK; + try + { + m = func(modname, nick); + } + catch (const ModuleException &ex) + { + Log() << "Error while loading " << modname << ": " << ex.GetReason(); + moderr = MOD_ERR_EXCEPTION; + } + + if (moderr != MOD_ERR_OK) + { + if (dlclose(handle)) + Log() << dlerror(); + return moderr; + } + + m->filename = pbuf; + m->handle = handle; + + /* Initialize config */ + try + { + m->OnReload(Config); + } + catch (const ModuleException &ex) + { + Log() << "Module " << modname << " couldn't load:" << ex.GetReason(); + moderr = MOD_ERR_EXCEPTION; + } + catch (const ConfigException &ex) + { + Log() << "Module " << modname << " couldn't load due to configuration problems: " << ex.GetReason(); + moderr = MOD_ERR_EXCEPTION; + } + catch (const NotImplementedException &ex) + { + } + + if (moderr != MOD_ERR_OK) + { + DeleteModule(m); + return moderr; + } + + Log(LOG_DEBUG) << "Module " << modname << " loaded."; + + /* Attach module to all events */ + for (unsigned i = 0; i < I_SIZE; ++i) + EventHandlers[i].push_back(m); + + m->Prioritize(); + + FOREACH_MOD(OnModuleLoad, (u, m)); + + return MOD_ERR_OK; +} + +ModuleVersion ModuleManager::GetVersion(void *handle) +{ + dlerror(); + ModuleVersionC (*func)() = function_cast(dlsym(handle, "AnopeVersion"));; + if (!func) + { + Log() << "No version function found, not an Anope module"; + + const char *err = dlerror(); + if (err && *err) + Log(LOG_DEBUG) << err; + + throw ModuleException("No version"); + } + + return func(); +} + +ModuleReturn ModuleManager::UnloadModule(Module *m, User *u) +{ + if (!m) + return MOD_ERR_PARAMS; + + FOREACH_MOD(OnModuleUnload, (u, m)); + + return DeleteModule(m); +} + +Module *ModuleManager::FindModule(const Anope::string &name) +{ + for (std::list::const_iterator it = Modules.begin(), it_end = Modules.end(); it != it_end; ++it) + { + Module *m = *it; + + if (m->name.equals_ci(name)) + return m; + } + + return NULL; +} + +Module *ModuleManager::FindFirstOf(ModType type) +{ + for (std::list::const_iterator it = Modules.begin(), it_end = Modules.end(); it != it_end; ++it) + { + Module *m = *it; + + if (m->type & type) + return m; + } + + return NULL; +} + +void ModuleManager::RequireVersion(int major, int minor, int patch) +{ + if (Anope::VersionMajor() > major) + return; + else if (Anope::VersionMajor() == major) + { + if (minor == -1) + return; + else if (Anope::VersionMinor() > minor) + return; + else if (Anope::VersionMinor() == minor) + { + if (patch == -1) + return; + else if (Anope::VersionPatch() > patch) + return; + else if (Anope::VersionPatch() == patch) + return; + } + } + + throw ModuleException("This module requires version " + stringify(major) + "." + stringify(minor) + "." + stringify(patch) + " - this is " + Anope::VersionShort()); +} + +ModuleReturn ModuleManager::DeleteModule(Module *m) +{ + if (!m || !m->handle) + return MOD_ERR_PARAMS; + + void *handle = m->handle; + Anope::string filename = m->filename; + + Log(LOG_DEBUG) << "Unloading module " << m->name; + + dlerror(); + void (*destroy_func)(Module *m) = function_cast(dlsym(m->handle, "AnopeFini")); + const char *err = dlerror(); + if (!destroy_func || (err && *err)) + { + Log() << "No destroy function found for " << m->name << ", chancing delete..."; + delete m; /* we just have to chance they haven't overwrote the delete operator then... */ + } + else + destroy_func(m); /* Let the module delete it self, just in case */ + + if (dlclose(handle)) + Log() << dlerror(); + +#ifdef _WIN32 + if (!filename.empty()) + unlink(filename.c_str()); +#endif + + return MOD_ERR_OK; +} + +void ModuleManager::DetachAll(Module *mod) +{ + for (unsigned i = 0; i < I_SIZE; ++i) + { + std::vector &mods = EventHandlers[i]; + std::vector::iterator it2 = std::find(mods.begin(), mods.end(), mod); + if (it2 != mods.end()) + mods.erase(it2); + } +} + +bool ModuleManager::SetPriority(Module *mod, Priority s) +{ + for (unsigned i = 0; i < I_SIZE; ++i) + SetPriority(mod, static_cast(i), s); + + return true; +} + +bool ModuleManager::SetPriority(Module *mod, Implementation i, Priority s, Module **modules, size_t sz) +{ + /** To change the priority of a module, we first find its position in the vector, + * then we find the position of the other modules in the vector that this module + * wants to be before/after. We pick off either the first or last of these depending + * on which they want, and we make sure our module is *at least* before or after + * the first or last of this subset, depending again on the type of priority. + */ + + /* Locate our module. This is O(n) but it only occurs on module load so we're + * not too bothered about it + */ + size_t source = 0; + bool found = false; + for (size_t x = 0, end = EventHandlers[i].size(); x != end; ++x) + if (EventHandlers[i][x] == mod) + { + source = x; + found = true; + break; + } + + /* Eh? this module doesn't exist, probably trying to set priority on an event + * they're not attached to. + */ + if (!found) + return false; + + size_t swap_pos = 0; + bool swap = true; + switch (s) + { + /* Dummy value */ + case PRIORITY_DONTCARE: + swap = false; + break; + /* Module wants to be first, sod everything else */ + case PRIORITY_FIRST: + swap_pos = 0; + break; + /* Module is submissive and wants to be last... awww. */ + case PRIORITY_LAST: + if (EventHandlers[i].empty()) + swap_pos = 0; + else + swap_pos = EventHandlers[i].size() - 1; + break; + /* Place this module after a set of other modules */ + case PRIORITY_AFTER: + /* Find the latest possible position */ + swap_pos = 0; + swap = false; + for (size_t x = 0, end = EventHandlers[i].size(); x != end; ++x) + for (size_t n = 0; n < sz; ++n) + if (modules[n] && EventHandlers[i][x] == modules[n] && x >= swap_pos && source <= swap_pos) + { + swap_pos = x; + swap = true; + } + break; + /* Place this module before a set of other modules */ + case PRIORITY_BEFORE: + swap_pos = EventHandlers[i].size() - 1; + swap = false; + for (size_t x = 0, end = EventHandlers[i].size(); x != end; ++x) + for (size_t n = 0; n < sz; ++n) + if (modules[n] && EventHandlers[i][x] == modules[n] && x <= swap_pos && source >= swap_pos) + { + swap = true; + swap_pos = x; + } + } + + /* Do we need to swap? */ + if (swap && swap_pos != source) + { + /* Suggestion from Phoenix, "shuffle" the modules to better retain call order */ + int increment = 1; + + if (source > swap_pos) + increment = -1; + + for (unsigned j = source; j != swap_pos; j += increment) + { + if (j + increment > EventHandlers[i].size() - 1 || (!j && increment == -1)) + continue; + + std::swap(EventHandlers[i][j], EventHandlers[i][j + increment]); + } + } + + return true; +} + +void ModuleManager::UnloadAll() +{ + std::vector modules; + for (size_t i = 1, j = 0; i != MT_END; j |= i, i <<= 1) + for (std::list::iterator it = Modules.begin(), it_end = Modules.end(); it != it_end; ++it) + { + Module *m = *it; + if ((m->type & j) == m->type) + modules.push_back(m->name); + } + + for (unsigned i = 0; i < modules.size(); ++i) + { + Module *m = FindModule(modules[i]); + if (m != NULL) + UnloadModule(m, NULL); + } +} diff --git a/src/nickalias.cpp b/src/nickalias.cpp new file mode 100644 index 0000000..81ad8f1 --- /dev/null +++ b/src/nickalias.cpp @@ -0,0 +1,216 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "account.h" +#include "modules.h" +#include "opertype.h" +#include "protocol.h" +#include "users.h" +#include "servers.h" +#include "config.h" + +Serialize::Checker NickAliasList("NickAlias"); + +NickAlias::NickAlias(const Anope::string &nickname, NickCore* nickcore) : Serializable("NickAlias") +{ + if (nickname.empty()) + throw CoreException("Empty nick passed to NickAlias constructor"); + else if (!nickcore) + throw CoreException("Empty nickcore passed to NickAlias constructor"); + + this->time_registered = this->last_seen = Anope::CurTime; + this->nick = nickname; + this->nc = nickcore; + nickcore->aliases->push_back(this); + + size_t old = NickAliasList->size(); + (*NickAliasList)[this->nick] = this; + if (old == NickAliasList->size()) + Log(LOG_DEBUG) << "Duplicate nick " << nickname << " in nickalias table"; + + if (this->nc->o == NULL) + { + Oper *o = Oper::Find(this->nick); + if (o == NULL) + o = Oper::Find(this->nc->display); + nickcore->o = o; + if (this->nc->o != NULL) + Log() << "Tied oper " << this->nc->display << " to type " << this->nc->o->ot->GetName(); + } +} + +NickAlias::~NickAlias() +{ + FOREACH_MOD(OnDelNick, (this)); + + UnsetExtensibles(); + + /* Accept nicks that have no core, because of database load functions */ + if (this->nc) + { + /* Next: see if our core is still useful. */ + std::vector::iterator it = std::find(this->nc->aliases->begin(), this->nc->aliases->end(), this); + if (it != this->nc->aliases->end()) + this->nc->aliases->erase(it); + if (this->nc->aliases->empty()) + { + delete this->nc; + this->nc = NULL; + } + else + { + /* Display updating stuff */ + if (this->nick.equals_ci(this->nc->display)) + this->nc->SetDisplay(this->nc->aliases->front()); + } + } + + /* Remove us from the aliases list */ + NickAliasList->erase(this->nick); +} + +void NickAlias::SetVhost(const Anope::string &ident, const Anope::string &host, const Anope::string &creator, time_t created) +{ + this->vhost_ident = ident; + this->vhost_host = host; + this->vhost_creator = creator; + this->vhost_created = created; +} + +void NickAlias::RemoveVhost() +{ + this->vhost_ident.clear(); + this->vhost_host.clear(); + this->vhost_creator.clear(); + this->vhost_created = 0; +} + +bool NickAlias::HasVhost() const +{ + return !this->vhost_host.empty(); +} + +const Anope::string &NickAlias::GetVhostIdent() const +{ + return this->vhost_ident; +} + +const Anope::string &NickAlias::GetVhostHost() const +{ + return this->vhost_host; +} + +const Anope::string &NickAlias::GetVhostCreator() const +{ + return this->vhost_creator; +} + +time_t NickAlias::GetVhostCreated() const +{ + return this->vhost_created; +} + +NickAlias *NickAlias::Find(const Anope::string &nick) +{ + nickalias_map::const_iterator it = NickAliasList->find(nick); + if (it != NickAliasList->end()) + { + it->second->QueueUpdate(); + return it->second; + } + + return NULL; +} + +void NickAlias::Serialize(Serialize::Data &data) const +{ + data["nick"] << this->nick; + data["last_quit"] << this->last_quit; + data["last_realname"] << this->last_realname; + data["last_usermask"] << this->last_usermask; + data["last_realhost"] << this->last_realhost; + data.SetType("time_registered", Serialize::Data::DT_INT); data["time_registered"] << this->time_registered; + data.SetType("last_seen", Serialize::Data::DT_INT); data["last_seen"] << this->last_seen; + data["nc"] << this->nc->display; + + if (this->HasVhost()) + { + data["vhost_ident"] << this->GetVhostIdent(); + data["vhost_host"] << this->GetVhostHost(); + data["vhost_creator"] << this->GetVhostCreator(); + data["vhost_time"] << this->GetVhostCreated(); + } + + Extensible::ExtensibleSerialize(this, this, data); +} + +Serializable* NickAlias::Unserialize(Serializable *obj, Serialize::Data &data) +{ + Anope::string snc, snick; + + data["nc"] >> snc; + data["nick"] >> snick; + + NickCore *core = NickCore::Find(snc); + if (core == NULL) + return NULL; + + NickAlias *na; + if (obj) + na = anope_dynamic_static_cast(obj); + else + na = new NickAlias(snick, core); + + if (na->nc != core) + { + std::vector::iterator it = std::find(na->nc->aliases->begin(), na->nc->aliases->end(), na); + if (it != na->nc->aliases->end()) + na->nc->aliases->erase(it); + + if (na->nc->aliases->empty()) + delete na->nc; + else if (na->nick.equals_ci(na->nc->display)) + na->nc->SetDisplay(na->nc->aliases->front()); + + na->nc = core; + core->aliases->push_back(na); + } + + data["last_quit"] >> na->last_quit; + data["last_realname"] >> na->last_realname; + data["last_usermask"] >> na->last_usermask; + data["last_realhost"] >> na->last_realhost; + data["time_registered"] >> na->time_registered; + data["last_seen"] >> na->last_seen; + + Anope::string vhost_ident, vhost_host, vhost_creator; + time_t vhost_time; + + data["vhost_ident"] >> vhost_ident; + data["vhost_host"] >> vhost_host; + data["vhost_creator"] >> vhost_creator; + data["vhost_time"] >> vhost_time; + + na->SetVhost(vhost_ident, vhost_host, vhost_creator, vhost_time); + + Extensible::ExtensibleUnserialize(na, na, data); + + /* compat */ + bool b; + b = false; + data["extensible:NO_EXPIRE"] >> b; + if (b) + na->Extend("NS_NO_EXPIRE"); + /* end compat */ + + return na; +} diff --git a/src/nickcore.cpp b/src/nickcore.cpp new file mode 100644 index 0000000..65ebd93 --- /dev/null +++ b/src/nickcore.cpp @@ -0,0 +1,318 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "modules.h" +#include "account.h" +#include "config.h" +#include + +Serialize::Checker NickCoreList("NickCore"); +nickcoreid_map NickCoreIdList; + +NickCore::NickCore(const Anope::string &coredisplay, uint64_t coreid) : Serializable("NickCore"), chanaccess("ChannelInfo"), aliases("NickAlias") +{ + if (coredisplay.empty()) + throw CoreException("Empty display passed to NickCore constructor"); + + this->o = NULL; + this->channelcount = 0; + this->lastmail = 0; + + this->display = coredisplay; + this->id = coreid; + + size_t old = NickCoreList->size(); + (*NickCoreList)[this->display] = this; + if (old == NickCoreList->size()) + Log(LOG_DEBUG) << "Duplicate account " << coredisplay << " in nickcore table?"; + + if (this->id) + NickCoreIdList[this->id] = this; + + FOREACH_MOD(OnNickCoreCreate, (this)); +} + +NickCore::~NickCore() +{ + FOREACH_MOD(OnDelCore, (this)); + + UnsetExtensibles(); + + if (!this->chanaccess->empty()) + Log(LOG_DEBUG) << "Non-empty chanaccess list in destructor!"; + + for (std::list::iterator it = this->users.begin(); it != this->users.end();) + { + User *user = *it++; + user->Logout(); + } + this->users.clear(); + + NickCoreList->erase(this->display); + if (this->id) + NickCoreIdList.erase(this->id); + + this->ClearAccess(); + + if (!this->memos.memos->empty()) + { + for (unsigned i = 0, end = this->memos.memos->size(); i < end; ++i) + delete this->memos.GetMemo(i); + this->memos.memos->clear(); + } +} + +void NickCore::Serialize(Serialize::Data &data) const +{ + data["display"] << this->display; + data["uniqueid"] << this->id; + data["pass"] << this->pass; + data["email"] << this->email; + data["language"] << this->language; + for (unsigned i = 0; i < this->access.size(); ++i) + data["access"] << this->access[i] << " "; + data["memomax"] << this->memos.memomax; + for (unsigned i = 0; i < this->memos.ignores.size(); ++i) + data["memoignores"] << this->memos.ignores[i] << " "; + Extensible::ExtensibleSerialize(this, this, data); +} + +Serializable* NickCore::Unserialize(Serializable *obj, Serialize::Data &data) +{ + NickCore *nc; + + Anope::string sdisplay; + data["display"] >> sdisplay; + + uint64_t sid = 0; + data["uniqueid"] >> sid; + + if (obj) + nc = anope_dynamic_static_cast(obj); + else + nc = new NickCore(sdisplay, sid); + + data["pass"] >> nc->pass; + data["email"] >> nc->email; + data["language"] >> nc->language; + { + Anope::string buf; + data["access"] >> buf; + spacesepstream sep(buf); + nc->access.clear(); + while (sep.GetToken(buf)) + nc->access.push_back(buf); + } + data["memomax"] >> nc->memos.memomax; + { + Anope::string buf; + data["memoignores"] >> buf; + spacesepstream sep(buf); + nc->memos.ignores.clear(); + while (sep.GetToken(buf)) + nc->memos.ignores.push_back(buf); + } + + Extensible::ExtensibleUnserialize(nc, nc, data); + + /* compat */ + bool b; + b = false; + data["extensible:SECURE"] >> b; + if (b) + nc->Extend("NS_SECURE"); + b = false; + data["extensible:PRIVATE"] >> b; + if (b) + nc->Extend("NS_PRIVATE"); + b = false; + data["extensible:AUTOOP"] >> b; + if (b) + nc->Extend("AUTOOP"); + b = false; + data["extensible:HIDE_EMAIL"] >> b; + if (b) + nc->Extend("HIDE_EMAIL"); + b = false; + data["extensible:HIDE_QUIT"] >> b; + if (b) + nc->Extend("HIDE_QUIT"); + b = false; + data["extensible:MEMO_RECEIVE"] >> b; + if (b) + nc->Extend("MEMO_RECEIVE"); + b = false; + data["extensible:MEMO_SIGNON"] >> b; + if (b) + nc->Extend("MEMO_SIGNON"); + b = false; + data["extensible:KILLPROTECT"] >> b; + if (b) + nc->Extend("KILLPROTECT"); + /* end compat */ + + return nc; +} + +void NickCore::SetDisplay(const NickAlias *na) +{ + if (na->nc != this || na->nick == this->display) + return; + + FOREACH_MOD(OnChangeCoreDisplay, (this, na->nick)); + + /* this affects the serialized aliases */ + for (unsigned i = 0; i < aliases->size(); ++i) + aliases->at(i)->QueueUpdate(); + + /* Remove the core from the list */ + NickCoreList->erase(this->display); + + this->display = na->nick; + + (*NickCoreList)[this->display] = this; +} + +bool NickCore::IsServicesOper() const +{ + return this->o != NULL; +} + +void NickCore::AddAccess(const Anope::string &entry) +{ + this->access.push_back(entry); + FOREACH_MOD(OnNickAddAccess, (this, entry)); +} + +Anope::string NickCore::GetAccess(unsigned entry) const +{ + if (this->access.empty() || entry >= this->access.size()) + return ""; + return this->access[entry]; +} + +unsigned NickCore::GetAccessCount() const +{ + return this->access.size(); +} + +bool NickCore::FindAccess(const Anope::string &entry) +{ + for (unsigned i = 0, end = this->access.size(); i < end; ++i) + if (this->access[i] == entry) + return true; + + return false; +} + +void NickCore::EraseAccess(const Anope::string &entry) +{ + for (unsigned i = 0, end = this->access.size(); i < end; ++i) + if (this->access[i] == entry) + { + FOREACH_MOD(OnNickEraseAccess, (this, entry)); + this->access.erase(this->access.begin() + i); + break; + } +} + +void NickCore::ClearAccess() +{ + FOREACH_MOD(OnNickClearAccess, (this)); + this->access.clear(); +} + +bool NickCore::IsOnAccess(const User *u) const +{ + Anope::string buf = u->GetIdent() + "@" + u->host, buf2, buf3; + if (!u->vhost.empty()) + buf2 = u->GetIdent() + "@" + u->vhost; + if (!u->GetCloakedHost().empty()) + buf3 = u->GetIdent() + "@" + u->GetCloakedHost(); + + for (unsigned i = 0, end = this->access.size(); i < end; ++i) + { + Anope::string a = this->GetAccess(i); + if (Anope::Match(buf, a) || (!buf2.empty() && Anope::Match(buf2, a)) || (!buf3.empty() && Anope::Match(buf3, a))) + return true; + } + return false; +} + +void NickCore::AddChannelReference(ChannelInfo *ci) +{ + ++(*this->chanaccess)[ci]; +} + +void NickCore::RemoveChannelReference(ChannelInfo *ci) +{ + int& i = (*this->chanaccess)[ci]; + if (--i <= 0) + this->chanaccess->erase(ci); +} + +void NickCore::GetChannelReferences(std::deque &queue) +{ + queue.clear(); + for (std::map::iterator it = this->chanaccess->begin(), it_end = this->chanaccess->end(); it != it_end; ++it) + queue.push_back(it->first); +} + +NickCore* NickCore::Find(const Anope::string &nick) +{ + nickcore_map::const_iterator it = NickCoreList->find(nick); + if (it != NickCoreList->end()) + { + it->second->QueueUpdate(); + return it->second; + } + + return NULL; +} + +uint64_t NickCore::GetId() +{ + if (this->id) + return this->id; + + NickAlias *na = NickAlias::Find(this->display); + if (!na) + { + Log(LOG_DEBUG) << "Unable to find the display NickAlias for NickCore: " << this->display; + return 0; + } + + Anope::string secretid = this->display + "\0" + stringify(na->time_registered); + + // Generate the account id. This should almost always only have one + // iteration but in the rare case that we generate a duplicate id we try + // again with a new key. + while (!this->id) + { + // Generate a random key for SipHash. + char key[16]; + for (size_t i = 0; i < sizeof(key); ++i) + key[i] = rand() % CHAR_MAX; + + uint64_t newid = Anope::SipHash24(secretid.c_str(), secretid.length(), key); + nickcoreid_map::const_iterator it = NickCoreIdList.find(newid); + if (it == NickCoreIdList.end()) + { + this->id = newid; + NickCoreIdList[this->id] = this; + this->QueueUpdate(); + break; + } + } + + return this->id; +} diff --git a/src/opertype.cpp b/src/opertype.cpp new file mode 100644 index 0000000..139b790 --- /dev/null +++ b/src/opertype.cpp @@ -0,0 +1,147 @@ +/* + * + * (C) 2008-2011 Robin Burchell + * (C) 2008-2022 Anope Team + * + * Please read COPYING and README for further details. + */ + +#include "services.h" +#include "anope.h" +#include "opertype.h" +#include "config.h" + +std::vector Oper::opers; + +Oper::Oper(const Anope::string &n, OperType *o) : name(n), ot(o), require_oper(true) +{ + opers.push_back(this); +} + +Oper::~Oper() +{ + std::vector::iterator it = std::find(opers.begin(), opers.end(), this); + if (it != opers.end()) + opers.erase(it); +} + +Oper *Oper::Find(const Anope::string &name) +{ + for (unsigned i = 0; i < opers.size(); ++i) + { + Oper *o = opers[i]; + + if (o->name.equals_ci(name)) + return o; + } + + return NULL; +} + +OperType *OperType::Find(const Anope::string &name) +{ + for (unsigned i = 0; i < Config->MyOperTypes.size(); ++i) + { + OperType *ot = Config->MyOperTypes[i]; + + if (ot->GetName() == name) + return ot; + } + + return NULL; +} + +OperType::OperType(const Anope::string &nname) : name(nname) +{ +} + +bool OperType::HasCommand(const Anope::string &cmdstr) const +{ + for (std::list::const_iterator it = this->commands.begin(), it_end = this->commands.end(); it != it_end; ++it) + { + const Anope::string &s = *it; + + if (!s.find('~') && Anope::Match(cmdstr, s.substr(1))) + return false; + else if (Anope::Match(cmdstr, s)) + return true; + } + for (std::set::const_iterator iit = this->inheritances.begin(), iit_end = this->inheritances.end(); iit != iit_end; ++iit) + { + OperType *ot = *iit; + + if (ot->HasCommand(cmdstr)) + return true; + } + + return false; +} + +bool OperType::HasPriv(const Anope::string &privstr) const +{ + for (std::list::const_iterator it = this->privs.begin(), it_end = this->privs.end(); it != it_end; ++it) + { + const Anope::string &s = *it; + + if (!s.find('~') && Anope::Match(privstr, s.substr(1))) + return false; + else if (Anope::Match(privstr, s)) + return true; + } + for (std::set::const_iterator iit = this->inheritances.begin(), iit_end = this->inheritances.end(); iit != iit_end; ++iit) + { + OperType *ot = *iit; + + if (ot->HasPriv(privstr)) + return true; + } + + return false; +} + +void OperType::AddCommand(const Anope::string &cmdstr) +{ + this->commands.push_back(cmdstr); +} + +void OperType::AddPriv(const Anope::string &privstr) +{ + this->privs.push_back(privstr); +} + +const Anope::string &OperType::GetName() const +{ + return this->name; +} + +void OperType::Inherits(OperType *ot) +{ + if (ot != this) + this->inheritances.insert(ot); +} + +const std::list OperType::GetCommands() const +{ + std::list cmd_list = this->commands; + for (std::set::const_iterator it = this->inheritances.begin(), it_end = this->inheritances.end(); it != it_end; ++it) + { + OperType *ot = *it; + std::list cmds = ot->GetCommands(); + for (std::list::const_iterator it2 = cmds.begin(), it2_end = cmds.end(); it2 != it2_end; ++it2) + cmd_list.push_back(*it2); + } + return cmd_list; +} + +const std::list OperType::GetPrivs() const +{ + std::list priv_list = this->privs; + for (std::set::const_iterator it = this->inheritances.begin(), it_end = this->inheritances.end(); it != it_end; ++it) + { + OperType *ot = *it; + std::list priv = ot->GetPrivs(); + for (std::list::const_iterator it2 = priv.begin(), it2_end = priv.end(); it2 != it2_end; ++it2) + priv_list.push_back(*it2); + } + return priv_list; +} diff --git a/src/pipeengine.cpp b/src/pipeengine.cpp new file mode 100644 index 0000000..c38cbb6 --- /dev/null +++ b/src/pipeengine.cpp @@ -0,0 +1,80 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "sockets.h" +#include "socketengine.h" + +#ifndef _WIN32 +#include +#endif + +Pipe::Pipe() : Socket(-1), write_pipe(-1) +{ + int fds[2]; + if (pipe(fds)) + throw CoreException("Could not create pipe: " + Anope::LastError()); + int sflags = fcntl(fds[0], F_GETFL, 0); + fcntl(fds[0], F_SETFL, sflags | O_NONBLOCK); + sflags = fcntl(fds[1], F_GETFL, 0); + fcntl(fds[1], F_SETFL, sflags | O_NONBLOCK); + + SocketEngine::Change(this, false, SF_READABLE); + SocketEngine::Change(this, false, SF_WRITABLE); + anope_close(this->sock); + this->io->Destroy(); + SocketEngine::Sockets.erase(this->sock); + + this->sock = fds[0]; + this->write_pipe = fds[1]; + + SocketEngine::Sockets[this->sock] = this; + SocketEngine::Change(this, true, SF_READABLE); +} + +Pipe::~Pipe() +{ + if (this->write_pipe >= 0) + anope_close(this->write_pipe); +} + +bool Pipe::ProcessRead() +{ + this->OnNotify(); + + char dummy[512]; + while (read(this->GetFD(), dummy, 512) == 512); + return true; +} + +void Pipe::Write(const char *data, size_t sz) +{ + write(this->write_pipe, data, sz); +} + +int Pipe::Read(char *data, size_t sz) +{ + return read(this->GetFD(), data, sz); +} + +bool Pipe::SetWriteBlocking(bool state) +{ + int f = fcntl(this->write_pipe, F_GETFL, 0); + if (state) + return !fcntl(this->write_pipe, F_SETFL, f & ~O_NONBLOCK); + else + return !fcntl(this->write_pipe, F_SETFL, f | O_NONBLOCK); +} + +void Pipe::Notify() +{ + this->Write("\0", 1); +} diff --git a/src/process.cpp b/src/process.cpp new file mode 100644 index 0000000..de7dc8e --- /dev/null +++ b/src/process.cpp @@ -0,0 +1,182 @@ +/* Main processing code for Services. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "modules.h" +#include "protocol.h" +#include "servers.h" +#include "users.h" +#include "regchannel.h" + +void Anope::Process(const Anope::string &buffer) +{ + /* If debugging, log the buffer */ + Log(LOG_RAWIO) << "Received: " << buffer; + + if (buffer.empty()) + return; + + Anope::map tags; + Anope::string source, command; + std::vector params; + + if (!IRCD->Parse(buffer, tags, source, command, params)) + return; + + if (Anope::ProtocolDebug) + { + if (tags.empty()) + Log() << "No tags"; + else + for (Anope::map::const_iterator it = tags.begin(); it != tags.end(); ++it) + Log() << "tags " << it->first << ": " << it->second; + + Log() << "Source : " << (source.empty() ? "No source" : source); + Log() << "Command: " << command; + + if (params.empty()) + Log() << "No params"; + else + for (unsigned i = 0; i < params.size(); ++i) + Log() << "params " << i << ": " << params[i]; + } + + static const Anope::string proto_name = ModuleManager::FindFirstOf(PROTOCOL) ? ModuleManager::FindFirstOf(PROTOCOL)->name : ""; + + MessageSource src(source); + + EventReturn MOD_RESULT; + FOREACH_RESULT(OnMessage, MOD_RESULT, (src, command, params)); + if (MOD_RESULT == EVENT_STOP) + return; + + ServiceReference m("IRCDMessage", proto_name + "/" + command.lower()); + if (!m) + { + Log(LOG_DEBUG) << "unknown message from server (" << buffer << ")"; + return; + } + + if (m->HasFlag(IRCDMESSAGE_SOFT_LIMIT) ? (params.size() < m->GetParamCount()) : (params.size() != m->GetParamCount())) + Log(LOG_DEBUG) << "invalid parameters for " << command << ": " << params.size() << " != " << m->GetParamCount(); + else if (m->HasFlag(IRCDMESSAGE_REQUIRE_USER) && !src.GetUser()) + Log(LOG_DEBUG) << "unexpected non-user source " << source << " for " << command; + else if (m->HasFlag(IRCDMESSAGE_REQUIRE_SERVER) && !source.empty() && !src.GetServer()) + Log(LOG_DEBUG) << "unexpected non-server source " << source << " for " << command; + else + m->Run(src, params, tags); +} + +bool IRCDProto::Parse(const Anope::string &buffer, Anope::map &tags, Anope::string &source, Anope::string &command, std::vector ¶ms) +{ + MessageTokenizer tokens(buffer); + + // This will always exist because of the check in Anope::Process. + Anope::string token; + tokens.GetMiddle(token); + + if (token[0] == '@') + { + // The line begins with message tags. + sepstream tagstream(token.substr(1), ';'); + while (tagstream.GetToken(token)) + { + const Anope::string::size_type valsep = token.find('='); + if (valsep == Anope::string::npos) + { + // Tag has no value. + tags[token]; + } + else + { + // Tag has a value + tags[token.substr(0, valsep)] = token.substr(valsep + 1); + } + } + + if (!tokens.GetMiddle(token)) + return false; + } + + if (token[0] == ':') + { + source = token.substr(1); + if (!tokens.GetMiddle(token)) + return false; + } + + // Store the command name. + command = token; + + // Retrieve all of the parameters. + while (tokens.GetTrailing(token)) + params.push_back(token); + + return true; +} + +Anope::string IRCDProto::Format(const Anope::string &source, const Anope::string &message) +{ + if (!source.empty()) + return ":" + source + " " + message; + else + return message; +} + +MessageTokenizer::MessageTokenizer(const Anope::string &msg) + : message(msg) + , position(0) +{ +} + +bool MessageTokenizer::GetMiddle(Anope::string &token) +{ + // If we are past the end of the string we can't do anything. + if (position >= message.length()) + { + token.clear(); + return false; + } + + // If we can't find another separator this is the last token in the message. + Anope::string::size_type separator = message.find(' ', position); + if (separator == Anope::string::npos) + { + token = message.substr(position); + position = message.length(); + return true; + } + + token = message.substr(position, separator - position); + position = message.find_first_not_of(' ', separator); + return true; +} + +bool MessageTokenizer::GetTrailing(Anope::string &token) +{ + // If we are past the end of the string we can't do anything. + if (position >= message.length()) + { + token.clear(); + return false; + } + + // If this is true then we have a token! + if (message[position] == ':') + { + token = message.substr(position + 1); + position = message.length(); + return true; + } + + // There is no token so it must be a token. + return GetMiddle(token); +} diff --git a/src/protocol.cpp b/src/protocol.cpp new file mode 100644 index 0000000..19a0a82 --- /dev/null +++ b/src/protocol.cpp @@ -0,0 +1,516 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "modules.h" +#include "protocol.h" +#include "users.h" +#include "servers.h" +#include "config.h" +#include "uplink.h" +#include "bots.h" +#include "channels.h" + +IRCDProto *IRCD = NULL; + +IRCDProto::IRCDProto(Module *creator, const Anope::string &p) : Service(creator, "IRCDProto", creator->name), proto_name(p) +{ + DefaultPseudoclientModes = "+io"; + CanSVSNick = CanSVSJoin = CanSetVHost = CanSetVIdent = CanSNLine = CanSQLine = CanSQLineChannel + = CanSZLine = CanSVSHold = CanSVSO = CanCertFP = RequiresID = AmbiguousID = false; + MaxModes = 3; + MaxLine = 512; + + if (IRCD == NULL) + IRCD = this; +} + +IRCDProto::~IRCDProto() +{ + if (IRCD == this) + IRCD = NULL; +} + +const Anope::string &IRCDProto::GetProtocolName() +{ + return this->proto_name; +} + +static inline char nextID(int pos, Anope::string &buf) +{ + char &c = buf[pos]; + if (c == 'Z') + c = '0'; + else if (c != '9') + ++c; + else if (pos) + c = 'A'; + else + c = '0'; + return c; +} + +Anope::string IRCDProto::UID_Retrieve() +{ + if (!IRCD || !IRCD->RequiresID) + return ""; + + static Anope::string current_uid = "AAAAAA"; + + do + { + int current_len = current_uid.length() - 1; + while (current_len >= 0 && nextID(current_len--, current_uid) == 'A'); + } + while (User::Find(Me->GetSID() + current_uid) != NULL); + + return Me->GetSID() + current_uid; +} + +Anope::string IRCDProto::SID_Retrieve() +{ + if (!IRCD || !IRCD->RequiresID) + return ""; + + static Anope::string current_sid = Config->GetBlock("serverinfo")->Get("id"); + if (current_sid.empty()) + current_sid = "00A"; + + do + { + int current_len = current_sid.length() - 1; + while (current_len >= 0 && nextID(current_len--, current_sid) == 'A'); + } + while (Server::Find(current_sid) != NULL); + + return current_sid; +} + +void IRCDProto::SendKill(const MessageSource &source, const Anope::string &target, const Anope::string &reason) +{ + UplinkSocket::Message(source) << "KILL " << target << " :" << reason; +} + +void IRCDProto::SendSVSKillInternal(const MessageSource &source, User *user, const Anope::string &buf) +{ + UplinkSocket::Message(source) << "KILL " << user->GetUID() << " :" << buf; +} + +void IRCDProto::SendModeInternal(const MessageSource &source, const Channel *dest, const Anope::string &buf) +{ + UplinkSocket::Message(source) << "MODE " << dest->name << " " << buf; +} + +void IRCDProto::SendModeInternal(const MessageSource &source, User *dest, const Anope::string &buf) +{ + UplinkSocket::Message(source) << "MODE " << dest->GetUID() << " " << buf; +} + +void IRCDProto::SendKickInternal(const MessageSource &source, const Channel *c, User *u, const Anope::string &r) +{ + if (!r.empty()) + UplinkSocket::Message(source) << "KICK " << c->name << " " << u->GetUID() << " :" << r; + else + UplinkSocket::Message(source) << "KICK " << c->name << " " << u->GetUID(); +} + +void IRCDProto::SendNoticeInternal(const MessageSource &source, const Anope::string &dest, const Anope::string &msg) +{ + UplinkSocket::Message(source) << "NOTICE " << dest << " :" << msg; +} + +void IRCDProto::SendPrivmsgInternal(const MessageSource &source, const Anope::string &dest, const Anope::string &buf) +{ + UplinkSocket::Message(source) << "PRIVMSG " << dest << " :" << buf; +} + +void IRCDProto::SendQuitInternal(User *u, const Anope::string &buf) +{ + if (!buf.empty()) + UplinkSocket::Message(u) << "QUIT :" << buf; + else + UplinkSocket::Message(u) << "QUIT"; +} + +void IRCDProto::SendPartInternal(User *u, const Channel *chan, const Anope::string &buf) +{ + if (!buf.empty()) + UplinkSocket::Message(u) << "PART " << chan->name << " :" << buf; + else + UplinkSocket::Message(u) << "PART " << chan->name; +} + +void IRCDProto::SendGlobopsInternal(const MessageSource &source, const Anope::string &buf) +{ + UplinkSocket::Message(source) << "GLOBOPS :" << buf; +} + +void IRCDProto::SendCTCPInternal(const MessageSource &source, const Anope::string &dest, const Anope::string &buf) +{ + Anope::string s = Anope::NormalizeBuffer(buf); + this->SendNoticeInternal(source, dest, "\1" + s + "\1"); +} + +void IRCDProto::SendNumericInternal(int numeric, const Anope::string &dest, const Anope::string &buf) +{ + Anope::string n = stringify(numeric); + if (numeric < 10) + n = "0" + n; + if (numeric < 100) + n = "0" + n; + UplinkSocket::Message(Me) << n << " " << dest << " " << buf; +} + +void IRCDProto::SendTopic(const MessageSource &source, Channel *c) +{ + UplinkSocket::Message(source) << "TOPIC " << c->name << " :" << c->topic; +} + +void IRCDProto::SendSVSKill(const MessageSource &source, User *user, const char *fmt, ...) +{ + if (!user || !fmt) + return; + + va_list args; + char buf[BUFSIZE] = ""; + va_start(args, fmt); + vsnprintf(buf, BUFSIZE - 1, fmt, args); + va_end(args); + SendSVSKillInternal(source, user, buf); +} + +void IRCDProto::SendMode(const MessageSource &source, const Channel *dest, const char *fmt, ...) +{ + va_list args; + char buf[BUFSIZE] = ""; + va_start(args, fmt); + vsnprintf(buf, BUFSIZE - 1, fmt, args); + va_end(args); + SendModeInternal(source, dest, buf); +} + +void IRCDProto::SendMode(const MessageSource &source, User *u, const char *fmt, ...) +{ + va_list args; + char buf[BUFSIZE] = ""; + va_start(args, fmt); + vsnprintf(buf, BUFSIZE - 1, fmt, args); + va_end(args); + SendModeInternal(source, u, buf); +} + +void IRCDProto::SendKick(const MessageSource &source, const Channel *chan, User *user, const char *fmt, ...) +{ + if (!chan || !user) + return; + + va_list args; + char buf[BUFSIZE] = ""; + va_start(args, fmt); + vsnprintf(buf, BUFSIZE - 1, fmt, args); + va_end(args); + SendKickInternal(source, chan, user, buf); +} + +void IRCDProto::SendNotice(const MessageSource &source, const Anope::string &dest, const char *fmt, ...) +{ + va_list args; + char buf[BUFSIZE] = ""; + va_start(args, fmt); + vsnprintf(buf, BUFSIZE - 1, fmt, args); + va_end(args); + SendNoticeInternal(source, dest, buf); +} + +void IRCDProto::SendAction(const MessageSource &source, const Anope::string &dest, const char *fmt, ...) +{ + va_list args; + char buf[BUFSIZE] = ""; + va_start(args, fmt); + vsnprintf(buf, BUFSIZE - 1, fmt, args); + va_end(args); + Anope::string actionbuf = Anope::string("\1ACTION ") + buf + '\1'; + SendPrivmsgInternal(source, dest, actionbuf); +} + +void IRCDProto::SendPrivmsg(const MessageSource &source, const Anope::string &dest, const char *fmt, ...) +{ + va_list args; + char buf[BUFSIZE] = ""; + va_start(args, fmt); + vsnprintf(buf, BUFSIZE - 1, fmt, args); + va_end(args); + SendPrivmsgInternal(source, dest, buf); +} + +void IRCDProto::SendQuit(User *u, const char *fmt, ...) +{ + va_list args; + char buf[BUFSIZE] = ""; + va_start(args, fmt); + vsnprintf(buf, BUFSIZE - 1, fmt, args); + va_end(args); + SendQuitInternal(u, buf); +} + +void IRCDProto::SendPing(const Anope::string &servname, const Anope::string &who) +{ + if (servname.empty()) + UplinkSocket::Message(Me) << "PING " << who; + else + UplinkSocket::Message(Me) << "PING " << servname << " " << who; +} + +/** + * Send a PONG reply to a received PING. + * servname should be left NULL to send a one param reply. + * @param servname Daemon or client that is responding to the PING. + * @param who Origin of the PING and destination of the PONG message. + **/ +void IRCDProto::SendPong(const Anope::string &servname, const Anope::string &who) +{ + if (servname.empty()) + UplinkSocket::Message(Me) << "PONG " << who; + else + UplinkSocket::Message(Me) << "PONG " << servname << " " << who; +} + +void IRCDProto::SendInvite(const MessageSource &source, const Channel *c, User *u) +{ + UplinkSocket::Message(source) << "INVITE " << u->GetUID() << " " << c->name; +} + +void IRCDProto::SendPart(User *user, const Channel *chan, const char *fmt, ...) +{ + if (fmt) + { + va_list args; + char buf[BUFSIZE] = ""; + va_start(args, fmt); + vsnprintf(buf, BUFSIZE - 1, fmt, args); + va_end(args); + SendPartInternal(user, chan, buf); + } + else + SendPartInternal(user, chan, ""); +} + +void IRCDProto::SendGlobops(const MessageSource &source, const char *fmt, ...) +{ + va_list args; + char buf[BUFSIZE] = ""; + va_start(args, fmt); + vsnprintf(buf, BUFSIZE - 1, fmt, args); + va_end(args); + SendGlobopsInternal(source, buf); +} + +void IRCDProto::SendSquit(Server *s, const Anope::string &message) +{ + UplinkSocket::Message() << "SQUIT " << s->GetSID() << " :" << message; +} + +void IRCDProto::SendNickChange(User *u, const Anope::string &newnick) +{ + UplinkSocket::Message(u) << "NICK " << newnick << " " << Anope::CurTime; +} + +void IRCDProto::SendForceNickChange(User *u, const Anope::string &newnick, time_t when) +{ + UplinkSocket::Message() << "SVSNICK " << u->GetUID() << " " << newnick << " " << when; +} + +void IRCDProto::SendCTCP(const MessageSource &source, const Anope::string &dest, const char *fmt, ...) +{ + va_list args; + char buf[BUFSIZE] = ""; + va_start(args, fmt); + vsnprintf(buf, BUFSIZE - 1, fmt, args); + va_end(args); + SendCTCPInternal(source, dest, buf); +} + +void IRCDProto::SendNumeric(int numeric, const Anope::string &dest, const char *fmt, ...) +{ + va_list args; + char buf[BUFSIZE] = ""; + va_start(args, fmt); + vsnprintf(buf, BUFSIZE - 1, fmt, args); + va_end(args); + SendNumericInternal(numeric, dest, buf); +} + +bool IRCDProto::IsNickValid(const Anope::string &nick) +{ + /** + * RFC: definition of a valid nick + * nickname = ( letter / special ) ( letter / digit / special / "-" ) + * letter = A-Z / a-z + * digit = 0-9 + * special = [, ], \, `, _, ^, {, |, } + **/ + + if (nick.empty()) + return false; + + Anope::string special = "[]\\`_^{|}"; + + for (unsigned i = 0; i < nick.length(); ++i) + if (!(nick[i] >= 'A' && nick[i] <= 'Z') && !(nick[i] >= 'a' && nick[i] <= 'z') + && special.find(nick[i]) == Anope::string::npos + && (Config && Config->NickChars.find(nick[i]) == Anope::string::npos) + && (!i || (!(nick[i] >= '0' && nick[i] <= '9') && nick[i] != '-'))) + return false; + + return true; +} + +bool IRCDProto::IsChannelValid(const Anope::string &chan) +{ + if (chan.empty() || chan[0] != '#' || chan.length() > Config->GetBlock("networkinfo")->Get("chanlen")) + return false; + + if (chan.find_first_of(" ,") != Anope::string::npos) + return false; + + return true; +} + +bool IRCDProto::IsIdentValid(const Anope::string &ident) +{ + if (ident.empty() || ident.length() > Config->GetBlock("networkinfo")->Get("userlen")) + return false; + + for (unsigned i = 0; i < ident.length(); ++i) + { + const char &c = ident[i]; + + if ((c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || (c >= '0' && c <= '9') || c == '.' || c == '-') + continue; + + return false; + } + + return true; +} + +bool IRCDProto::IsHostValid(const Anope::string &host) +{ + if (host.empty() || host.length() > Config->GetBlock("networkinfo")->Get("hostlen")) + return false; + + const Anope::string &vhostdisablebe = Config->GetBlock("networkinfo")->Get("disallow_start_or_end"), + vhostchars = Config->GetBlock("networkinfo")->Get("vhost_chars"); + + if (vhostdisablebe.find_first_of(host[0]) != Anope::string::npos) + return false; + else if (vhostdisablebe.find_first_of(host[host.length() - 1]) != Anope::string::npos) + return false; + + int dots = 0; + for (unsigned i = 0; i < host.length(); ++i) + { + if (host[i] == '.') + ++dots; + if (vhostchars.find_first_of(host[i]) == Anope::string::npos) + return false; + } + + return dots > 0 || Config->GetBlock("networkinfo")->Get("allow_undotted_vhosts"); +} + +void IRCDProto::SendOper(User *u) +{ + SendNumericInternal(381, u->GetUID(), ":You are now an IRC operator (set by services)"); + u->SetMode(NULL, "OPER"); +} + +unsigned IRCDProto::GetMaxListFor(Channel *c) +{ + return c->HasMode("LBAN") ? 0 : Config->GetBlock("networkinfo")->Get("modelistsize"); +} + +unsigned IRCDProto::GetMaxListFor(Channel *c, ChannelMode *cm) +{ + return GetMaxListFor(c); +} + +Anope::string IRCDProto::NormalizeMask(const Anope::string &mask) +{ + if (IsExtbanValid(mask)) + return mask; + return Entry("", mask).GetNUHMask(); +} + +MessageSource::MessageSource(const Anope::string &src) : source(src), u(NULL), s(NULL) +{ + /* no source for incoming message is our uplink */ + if (src.empty()) + this->s = Servers::GetUplink(); + else if (IRCD->RequiresID || src.find('.') != Anope::string::npos) + this->s = Server::Find(src); + if (this->s == NULL) + this->u = User::Find(src); +} + +MessageSource::MessageSource(User *_u) : source(_u ? _u->nick : ""), u(_u), s(NULL) +{ +} + +MessageSource::MessageSource(Server *_s) : source(_s ? _s->GetName() : ""), u(NULL), s(_s) +{ +} + +const Anope::string &MessageSource::GetName() const +{ + if (this->s) + return this->s->GetName(); + else if (this->u) + return this->u->nick; + else + return this->source; +} + +const Anope::string &MessageSource::GetSource() const +{ + return this->source; +} + +User *MessageSource::GetUser() const +{ + return this->u; +} + +BotInfo *MessageSource::GetBot() const +{ + return BotInfo::Find(this->GetName(), true); +} + +Server *MessageSource::GetServer() const +{ + return this->s; +} + +IRCDMessage::IRCDMessage(Module *o, const Anope::string &n, unsigned p) : Service(o, "IRCDMessage", o->name + "/" + n.lower()), name(n), param_count(p) +{ +} + +unsigned IRCDMessage::GetParamCount() const +{ + return this->param_count; +} + +void IRCDMessage::Run(MessageSource &source, const std::vector ¶ms, const Anope::map &tags) +{ + // Most IRCds don't support message tags yet so use the tagless variant. + Run(source, params); +} + diff --git a/src/regchannel.cpp b/src/regchannel.cpp new file mode 100644 index 0000000..c571d74 --- /dev/null +++ b/src/regchannel.cpp @@ -0,0 +1,694 @@ +/* Registered channel functions + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "modules.h" +#include "regchannel.h" +#include "account.h" +#include "access.h" +#include "channels.h" +#include "config.h" +#include "bots.h" +#include "servers.h" + +Serialize::Checker RegisteredChannelList("ChannelInfo"); + +AutoKick::AutoKick() : Serializable("AutoKick") +{ +} + +AutoKick::~AutoKick() +{ + if (this->ci) + { + std::vector::iterator it = std::find(this->ci->akick->begin(), this->ci->akick->end(), this); + if (it != this->ci->akick->end()) + this->ci->akick->erase(it); + + if (nc) + nc->RemoveChannelReference(this->ci); + } +} + +void AutoKick::Serialize(Serialize::Data &data) const +{ + data["ci"] << this->ci->name; + if (this->nc) + data["nc"] << this->nc->display; + else + data["mask"] << this->mask; + data["reason"] << this->reason; + data["creator"] << this->creator; + data.SetType("addtime", Serialize::Data::DT_INT); data["addtime"] << this->addtime; + data.SetType("last_used", Serialize::Data::DT_INT); data["last_used"] << this->last_used; +} + +Serializable* AutoKick::Unserialize(Serializable *obj, Serialize::Data &data) +{ + Anope::string sci, snc; + + data["ci"] >> sci; + data["nc"] >> snc; + + ChannelInfo *ci = ChannelInfo::Find(sci); + if (!ci) + return NULL; + + AutoKick *ak; + NickCore *nc = NickCore::Find(snc); + if (obj) + { + ak = anope_dynamic_static_cast(obj); + data["creator"] >> ak->creator; + data["reason"] >> ak->reason; + ak->nc = NickCore::Find(snc); + data["mask"] >> ak->mask; + data["addtime"] >> ak->addtime; + data["last_used"] >> ak->last_used; + } + else + { + time_t addtime, lastused; + data["addtime"] >> addtime; + data["last_used"] >> lastused; + + Anope::string screator, sreason, smask; + + data["creator"] >> screator; + data["reason"] >> sreason; + data["mask"] >> smask; + + if (nc) + ak = ci->AddAkick(screator, nc, sreason, addtime, lastused); + else + ak = ci->AddAkick(screator, smask, sreason, addtime, lastused); + } + + return ak; +} + +ChannelInfo::ChannelInfo(const Anope::string &chname) : Serializable("ChannelInfo"), + access("ChanAccess"), akick("AutoKick") +{ + if (chname.empty()) + throw CoreException("Empty channel passed to ChannelInfo constructor"); + + this->founder = NULL; + this->successor = NULL; + this->c = Channel::Find(chname); + if (this->c) + this->c->ci = this; + this->banexpire = 0; + this->bi = NULL; + this->last_topic_time = 0; + + this->name = chname; + + this->bantype = 2; + this->memos.memomax = 0; + this->last_used = this->time_registered = Anope::CurTime; + + size_t old = RegisteredChannelList->size(); + (*RegisteredChannelList)[this->name] = this; + if (old == RegisteredChannelList->size()) + Log(LOG_DEBUG) << "Duplicate channel " << this->name << " in registered channel table?"; + + FOREACH_MOD(OnCreateChan, (this)); +} + +ChannelInfo::ChannelInfo(const ChannelInfo &ci) : Serializable("ChannelInfo"), + access("ChanAccess"), akick("AutoKick") +{ + *this = ci; + + if (this->founder) + ++this->founder->channelcount; + + this->access->clear(); + this->akick->clear(); + + FOREACH_MOD(OnCreateChan, (this)); +} + +ChannelInfo::~ChannelInfo() +{ + FOREACH_MOD(OnDelChan, (this)); + + UnsetExtensibles(); + + Log(LOG_DEBUG) << "Deleting channel " << this->name; + + if (this->c) + { + if (this->bi && this->c->FindUser(this->bi)) + this->bi->Part(this->c); + + /* Parting the service bot can cause the channel to go away */ + + if (this->c) + { + if (this->c && this->c->CheckDelete()) + this->c->QueueForDeletion(); + + this->c = NULL; + } + } + + RegisteredChannelList->erase(this->name); + + this->SetFounder(NULL); + this->SetSuccessor(NULL); + + this->ClearAccess(); + this->ClearAkick(); + + if (!this->memos.memos->empty()) + { + for (unsigned i = 0, end = this->memos.memos->size(); i < end; ++i) + delete this->memos.GetMemo(i); + this->memos.memos->clear(); + } +} + +void ChannelInfo::Serialize(Serialize::Data &data) const +{ + data["name"] << this->name; + if (this->founder) + data["founder"] << this->founder->display; + if (this->successor) + data["successor"] << this->successor->display; + data["description"] << this->desc; + data.SetType("time_registered", Serialize::Data::DT_INT); data["time_registered"] << this->time_registered; + data.SetType("last_used", Serialize::Data::DT_INT); data["last_used"] << this->last_used; + data["last_topic"] << this->last_topic; + data["last_topic_setter"] << this->last_topic_setter; + data.SetType("last_topic_time", Serialize::Data::DT_INT); data["last_topic_time"] << this->last_topic_time; + data.SetType("bantype", Serialize::Data::DT_INT); data["bantype"] << this->bantype; + { + Anope::string levels_buffer; + for (Anope::map::const_iterator it = this->levels.begin(), it_end = this->levels.end(); it != it_end; ++it) + levels_buffer += it->first + " " + stringify(it->second) + " "; + data["levels"] << levels_buffer; + } + if (this->bi) + data["bi"] << this->bi->nick; + data.SetType("banexpire", Serialize::Data::DT_INT); data["banexpire"] << this->banexpire; + data["memomax"] << this->memos.memomax; + for (unsigned i = 0; i < this->memos.ignores.size(); ++i) + data["memoignores"] << this->memos.ignores[i] << " "; + + Extensible::ExtensibleSerialize(this, this, data); +} + +Serializable* ChannelInfo::Unserialize(Serializable *obj, Serialize::Data &data) +{ + Anope::string sname, sfounder, ssuccessor, slevels, sbi; + + data["name"] >> sname; + data["founder"] >> sfounder; + data["successor"] >> ssuccessor; + data["levels"] >> slevels; + data["bi"] >> sbi; + + ChannelInfo *ci; + if (obj) + ci = anope_dynamic_static_cast(obj); + else + ci = new ChannelInfo(sname); + + ci->SetFounder(NickCore::Find(sfounder)); + ci->SetSuccessor(NickCore::Find(ssuccessor)); + + data["description"] >> ci->desc; + data["time_registered"] >> ci->time_registered; + data["last_used"] >> ci->last_used; + data["last_topic"] >> ci->last_topic; + data["last_topic_setter"] >> ci->last_topic_setter; + data["last_topic_time"] >> ci->last_topic_time; + data["bantype"] >> ci->bantype; + { + std::vector v; + spacesepstream(slevels).GetTokens(v); + for (unsigned i = 0; i + 1 < v.size(); i += 2) + try + { + ci->levels[v[i]] = convertTo(v[i + 1]); + } + catch (const ConvertException &) { } + } + BotInfo *bi = BotInfo::Find(sbi, true); + if (*ci->bi != bi) + { + if (bi) + bi->Assign(NULL, ci); + else if (ci->bi) + ci->bi->UnAssign(NULL, ci); + } + data["banexpire"] >> ci->banexpire; + data["memomax"] >> ci->memos.memomax; + { + Anope::string buf; + data["memoignores"] >> buf; + spacesepstream sep(buf); + ci->memos.ignores.clear(); + while (sep.GetToken(buf)) + ci->memos.ignores.push_back(buf); + } + + Extensible::ExtensibleUnserialize(ci, ci, data); + + /* compat */ + bool b; + b = false; + data["extensible:SECURE"] >> b; + if (b) + ci->Extend("CS_SECURE"); + b = false; + data["extensible:PRIVATE"] >> b; + if (b) + ci->Extend("CS_PRIVATE"); + b = false; + data["extensible:NO_EXPIRE"] >> b; + if (b) + ci->Extend("CS_NO_EXPIRE"); + b = false; + data["extensible:FANTASY"] >> b; + if (b) + ci->Extend("BS_FANTASY"); + b = false; + data["extensible:GREET"] >> b; + if (b) + ci->Extend("BS_GREET"); + b = false; + data["extensible:PEACE"] >> b; + if (b) + ci->Extend("PEACE"); + b = false; + data["extensible:SECUREFOUNDER"] >> b; + if (b) + ci->Extend("SECUREFOUNDER"); + b = false; + data["extensible:RESTRICTED"] >> b; + if (b) + ci->Extend("RESTRICTED"); + b = false; + data["extensible:KEEPTOPIC"] >> b; + if (b) + ci->Extend("KEEPTOPIC"); + b = false; + data["extensible:SIGNKICK"] >> b; + if (b) + ci->Extend("SIGNKICK"); + b = false; + data["extensible:SIGNKICK_LEVEL"] >> b; + if (b) + ci->Extend("SIGNKICK_LEVEL"); + /* end compat */ + + return ci; +} + + +void ChannelInfo::SetFounder(NickCore *nc) +{ + if (this->founder) + { + --this->founder->channelcount; + this->founder->RemoveChannelReference(this); + } + + this->founder = nc; + + if (this->founder) + { + ++this->founder->channelcount; + this->founder->AddChannelReference(this); + } +} + +NickCore *ChannelInfo::GetFounder() const +{ + return this->founder; +} + +void ChannelInfo::SetSuccessor(NickCore *nc) +{ + if (this->successor) + this->successor->RemoveChannelReference(this); + this->successor = nc; + if (this->successor) + this->successor->AddChannelReference(this); +} + +NickCore *ChannelInfo::GetSuccessor() const +{ + return this->successor; +} + +BotInfo *ChannelInfo::WhoSends() const +{ + if (this && this->bi) + return this->bi; + + BotInfo *ChanServ = Config->GetClient("ChanServ"); + if (ChanServ) + return ChanServ; + + if (!BotListByNick->empty()) + return BotListByNick->begin()->second; + + return NULL; +} + +void ChannelInfo::AddAccess(ChanAccess *taccess) +{ + this->access->push_back(taccess); +} + +ChanAccess *ChannelInfo::GetAccess(unsigned index) const +{ + if (this->access->empty() || index >= this->access->size()) + return NULL; + + ChanAccess *acc = (*this->access)[index]; + acc->QueueUpdate(); + return acc; +} + +static void FindMatchesRecurse(ChannelInfo *ci, const User *u, const NickCore *account, unsigned int depth, std::vector &paths, ChanAccess::Path &path) +{ + if (depth > ChanAccess::MAX_DEPTH) + return; + + for (unsigned int i = 0; i < ci->GetAccessCount(); ++i) + { + ChanAccess *a = ci->GetAccess(i); + ChannelInfo *next = NULL; + + if (a->Matches(u, account, next)) + { + ChanAccess::Path next_path = path; + next_path.push_back(a); + + paths.push_back(next_path); + } + else if (next) + { + ChanAccess::Path next_path = path; + next_path.push_back(a); + + FindMatchesRecurse(next, u, account, depth + 1, paths, next_path); + } + } +} + +static void FindMatches(AccessGroup &group, ChannelInfo *ci, const User *u, const NickCore *account) +{ + ChanAccess::Path path; + FindMatchesRecurse(ci, u, account, 0, group.paths, path); +} + +AccessGroup ChannelInfo::AccessFor(const User *u, bool updateLastUsed) +{ + AccessGroup group; + + if (u == NULL) + return group; + + const NickCore *nc = u->Account(); + if (nc == NULL && !this->HasExt("NS_SECURE") && u->IsRecognized()) + { + const NickAlias *na = NickAlias::Find(u->nick); + if (na != NULL) + nc = na->nc; + } + + group.super_admin = u->super_admin; + group.founder = IsFounder(u, this); + group.ci = this; + group.nc = nc; + + FindMatches(group, this, u, u->Account()); + + if (group.founder || !group.paths.empty()) + { + if (updateLastUsed) + this->last_used = Anope::CurTime; + + for (unsigned i = 0; i < group.paths.size(); ++i) + { + ChanAccess::Path &p = group.paths[i]; + + for (unsigned int j = 0; j < p.size(); ++j) + p[j]->last_seen = Anope::CurTime; + } + } + + return group; +} + +AccessGroup ChannelInfo::AccessFor(const NickCore *nc, bool updateLastUsed) +{ + AccessGroup group; + + group.founder = (this->founder && this->founder == nc); + group.ci = this; + group.nc = nc; + + FindMatches(group, this, NULL, nc); + + if (group.founder || !group.paths.empty()) + if (updateLastUsed) + this->last_used = Anope::CurTime; + + /* don't update access last seen here, this isn't the user requesting access */ + + return group; +} + +unsigned ChannelInfo::GetAccessCount() const +{ + return this->access->size(); +} + +static unsigned int GetDeepAccessCount(const ChannelInfo *ci, std::set &seen, unsigned int depth) +{ + if (depth > ChanAccess::MAX_DEPTH || seen.count(ci)) + return 0; + seen.insert(ci); + + unsigned int total = 0; + + for (unsigned int i = 0; i < ci->GetAccessCount(); ++i) + { + ChanAccess::Path path; + ChanAccess *a = ci->GetAccess(i); + ChannelInfo *next = NULL; + + a->Matches(NULL, NULL, next); + ++total; + + if (next) + total += GetDeepAccessCount(ci, seen, depth + 1); + } + + return total; +} + +unsigned ChannelInfo::GetDeepAccessCount() const +{ + std::set seen; + return ::GetDeepAccessCount(this, seen, 0); +} + +ChanAccess *ChannelInfo::EraseAccess(unsigned index) +{ + if (this->access->empty() || index >= this->access->size()) + return NULL; + + ChanAccess *ca = this->access->at(index); + this->access->erase(this->access->begin() + index); + return ca; +} + +void ChannelInfo::ClearAccess() +{ + for (unsigned i = this->access->size(); i > 0; --i) + delete this->GetAccess(i - 1); +} + +AutoKick *ChannelInfo::AddAkick(const Anope::string &user, NickCore *akicknc, const Anope::string &reason, time_t t, time_t lu) +{ + AutoKick *autokick = new AutoKick(); + autokick->ci = this; + autokick->nc = akicknc; + autokick->reason = reason; + autokick->creator = user; + autokick->addtime = t; + autokick->last_used = lu; + + this->akick->push_back(autokick); + + akicknc->AddChannelReference(this); + + return autokick; +} + +AutoKick *ChannelInfo::AddAkick(const Anope::string &user, const Anope::string &mask, const Anope::string &reason, time_t t, time_t lu) +{ + AutoKick *autokick = new AutoKick(); + autokick->ci = this; + autokick->mask = mask; + autokick->nc = NULL; + autokick->reason = reason; + autokick->creator = user; + autokick->addtime = t; + autokick->last_used = lu; + + this->akick->push_back(autokick); + + return autokick; +} + +AutoKick *ChannelInfo::GetAkick(unsigned index) const +{ + if (this->akick->empty() || index >= this->akick->size()) + return NULL; + + AutoKick *ak = (*this->akick)[index]; + ak->QueueUpdate(); + return ak; +} + +unsigned ChannelInfo::GetAkickCount() const +{ + return this->akick->size(); +} + +void ChannelInfo::EraseAkick(unsigned index) +{ + if (this->akick->empty() || index >= this->akick->size()) + return; + + delete this->GetAkick(index); +} + +void ChannelInfo::ClearAkick() +{ + while (!this->akick->empty()) + delete this->akick->back(); +} + +const Anope::map &ChannelInfo::GetLevelEntries() +{ + return this->levels; +} + +int16_t ChannelInfo::GetLevel(const Anope::string &priv) const +{ + if (PrivilegeManager::FindPrivilege(priv) == NULL) + { + Log(LOG_DEBUG) << "Unknown privilege " + priv; + return ACCESS_INVALID; + } + + Anope::map::const_iterator it = this->levels.find(priv); + if (it == this->levels.end()) + return 0; + return it->second; +} + +void ChannelInfo::SetLevel(const Anope::string &priv, int16_t level) +{ + if (PrivilegeManager::FindPrivilege(priv) == NULL) + { + Log(LOG_DEBUG) << "Unknown privilege " + priv; + return; + } + + this->levels[priv] = level; +} + +void ChannelInfo::RemoveLevel(const Anope::string &priv) +{ + this->levels.erase(priv); +} + +void ChannelInfo::ClearLevels() +{ + this->levels.clear(); +} + +Anope::string ChannelInfo::GetIdealBan(User *u) const +{ + int bt = this ? this->bantype : -1; + switch (bt) + { + case 0: + return "*!" + u->GetVIdent() + "@" + u->GetDisplayedHost(); + case 1: + if (u->GetVIdent()[0] == '~') + return "*!*" + u->GetVIdent() + "@" + u->GetDisplayedHost(); + else + return "*!" + u->GetVIdent() + "@" + u->GetDisplayedHost(); + case 3: + return "*!" + u->Mask(); + case 2: + default: + return "*!*@" + u->GetDisplayedHost(); + } +} + +ChannelInfo* ChannelInfo::Find(const Anope::string &name) +{ + registered_channel_map::const_iterator it = RegisteredChannelList->find(name); + if (it != RegisteredChannelList->end()) + { + it->second->QueueUpdate(); + return it->second; + } + + return NULL; +} + +bool IsFounder(const User *user, const ChannelInfo *ci) +{ + if (!user || !ci) + return false; + + if (user->super_admin) + return true; + + if (user->Account() && user->Account() == ci->GetFounder()) + return true; + + return false; +} + + +void ChannelInfo::AddChannelReference(const Anope::string &what) +{ + ++references[what]; +} + +void ChannelInfo::RemoveChannelReference(const Anope::string &what) +{ + int &i = references[what]; + if (--i <= 0) + references.erase(what); +} + +void ChannelInfo::GetChannelReferences(std::deque &chans) +{ + chans.clear(); + for (Anope::map::iterator it = references.begin(); it != references.end(); ++it) + chans.push_back(it->first); +} diff --git a/src/serialize.cpp b/src/serialize.cpp new file mode 100644 index 0000000..caca587 --- /dev/null +++ b/src/serialize.cpp @@ -0,0 +1,177 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "anope.h" +#include "serialize.h" +#include "modules.h" +#include "account.h" +#include "bots.h" +#include "regchannel.h" +#include "xline.h" +#include "access.h" + +using namespace Serialize; + +std::vector Type::TypeOrder; +std::map Serialize::Type::Types; +std::list *Serializable::SerializableItems; + +void Serialize::RegisterTypes() +{ + static Type nc("NickCore", NickCore::Unserialize), na("NickAlias", NickAlias::Unserialize), bi("BotInfo", BotInfo::Unserialize), + ci("ChannelInfo", ChannelInfo::Unserialize), access("ChanAccess", ChanAccess::Unserialize), + akick("AutoKick", AutoKick::Unserialize), memo("Memo", Memo::Unserialize), xline("XLine", XLine::Unserialize); +} + +void Serialize::CheckTypes() +{ + for (std::map::const_iterator it = Serialize::Type::GetTypes().begin(), it_end = Serialize::Type::GetTypes().end(); it != it_end; ++it) + { + Serialize::Type *t = it->second; + t->Check(); + } +} + +Serializable::Serializable(const Anope::string &serialize_type) : last_commit(0), last_commit_time(0), id(0), redis_ignore(0) +{ + if (SerializableItems == NULL) + SerializableItems = new std::list(); + SerializableItems->push_back(this); + + this->s_type = Type::Find(serialize_type); + + this->s_iter = SerializableItems->end(); + --this->s_iter; + + FOREACH_MOD(OnSerializableConstruct, (this)); +} + +Serializable::Serializable(const Serializable &other) : last_commit(0), last_commit_time(0), id(0), redis_ignore(0) +{ + SerializableItems->push_back(this); + this->s_iter = SerializableItems->end(); + --this->s_iter; + + this->s_type = other.s_type; + + FOREACH_MOD(OnSerializableConstruct, (this)); +} + +Serializable::~Serializable() +{ + FOREACH_MOD(OnSerializableDestruct, (this)); + + SerializableItems->erase(this->s_iter); +} + +Serializable &Serializable::operator=(const Serializable &) +{ + return *this; +} + +void Serializable::QueueUpdate() +{ + /* Schedule updater */ + FOREACH_MOD(OnSerializableUpdate, (this)); + + /* Check for modifications now - this can delete this object! */ + FOREACH_MOD(OnSerializeCheck, (this->GetSerializableType())); +} + +bool Serializable::IsCached(Serialize::Data &data) +{ + return this->last_commit == data.Hash(); +} + +void Serializable::UpdateCache(Serialize::Data &data) +{ + this->last_commit = data.Hash(); +} + +bool Serializable::IsTSCached() +{ + return this->last_commit_time == Anope::CurTime; +} + +void Serializable::UpdateTS() +{ + this->last_commit_time = Anope::CurTime; +} + +const std::list &Serializable::GetItems() +{ + return *SerializableItems; +} + +Type::Type(const Anope::string &n, unserialize_func f, Module *o) : name(n), unserialize(f), owner(o), timestamp(0) +{ + TypeOrder.push_back(this->name); + Types[this->name] = this; + + FOREACH_MOD(OnSerializeTypeCreate, (this)); +} + +Type::~Type() +{ + /* null the type of existing serializable objects of this type */ + if (Serializable::SerializableItems != NULL) + for (std::list::iterator it = Serializable::SerializableItems->begin(); it != Serializable::SerializableItems->end(); ++it) + { + Serializable *s = *it; + + if (s->s_type == this) + s->s_type = NULL; + } + + std::vector::iterator it = std::find(TypeOrder.begin(), TypeOrder.end(), this->name); + if (it != TypeOrder.end()) + TypeOrder.erase(it); + Types.erase(this->name); +} + +Serializable *Type::Unserialize(Serializable *obj, Serialize::Data &data) +{ + return this->unserialize(obj, data); +} + +void Type::Check() +{ + FOREACH_MOD(OnSerializeCheck, (this)); +} + +time_t Type::GetTimestamp() const +{ + return this->timestamp; +} + +void Type::UpdateTimestamp() +{ + this->timestamp = Anope::CurTime; +} + +Type *Serialize::Type::Find(const Anope::string &name) +{ + std::map::iterator it = Types.find(name); + if (it != Types.end()) + return it->second; + return NULL; +} + +const std::vector &Type::GetTypeOrder() +{ + return TypeOrder; +} + +const std::map& Type::GetTypes() +{ + return Types; +} diff --git a/src/servers.cpp b/src/servers.cpp new file mode 100644 index 0000000..db8cfce --- /dev/null +++ b/src/servers.cpp @@ -0,0 +1,360 @@ +/* Routines to maintain a list of connected servers + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "modules.h" +#include "xline.h" +#include "servers.h" +#include "bots.h" +#include "regchannel.h" +#include "protocol.h" +#include "config.h" +#include "channels.h" + +/* Anope */ +Server *Me = NULL; + +Anope::map Servers::ByName; +Anope::map Servers::ByID; + +std::set Servers::Capab; + +Server::Server(Server *up, const Anope::string &sname, unsigned shops, const Anope::string &desc, const Anope::string &ssid, bool jupe) : name(sname), hops(shops), description(desc), sid(ssid), uplink(up), users(0) +{ + syncing = true; + juped = jupe; + quitting = false; + + Servers::ByName[sname] = this; + if (!ssid.empty()) + Servers::ByID[ssid] = this; + + Log(this, "connect") << "has connected to the network (uplinked to " << (this->uplink ? this->uplink->GetName() : "no uplink") << ")"; + + /* Add this server to our uplinks leaf list */ + if (this->uplink) + { + this->uplink->AddLink(this); + + /* Check to be sure this isn't a juped server */ + if (Me == this->uplink && !juped) + { + /* Now do mode related stuff as we know what modes exist .. */ + for (botinfo_map::iterator it = BotListByNick->begin(), it_end = BotListByNick->end(); it != it_end; ++it) + { + BotInfo *bi = it->second; + Anope::string modes = !bi->botmodes.empty() ? ("+" + bi->botmodes) : IRCD->DefaultPseudoclientModes; + + bi->SetModesInternal(bi, modes.c_str()); + for (unsigned i = 0; i < bi->botchannels.size(); ++i) + { + size_t h = bi->botchannels[i].find('#'); + if (h == Anope::string::npos) + continue; + Anope::string chname = bi->botchannels[i].substr(h); + Channel *c = Channel::Find(chname); + if (c && c->FindUser(bi)) + { + Anope::string want_modes = bi->botchannels[i].substr(0, h); + for (unsigned j = 0; j < want_modes.length(); ++j) + { + ChannelMode *cm = ModeManager::FindChannelModeByChar(want_modes[j]); + if (cm == NULL) + cm = ModeManager::FindChannelModeByChar(ModeManager::GetStatusChar(want_modes[j])); + if (cm && cm->type == MODE_STATUS) + { + MessageSource ms = bi; + c->SetModeInternal(ms, cm, bi->nick); + } + } + } + } + } + + IRCD->SendBOB(); + + for (unsigned i = 0; i < Me->GetLinks().size(); ++i) + { + Server *s = Me->GetLinks()[i]; + + if (s->juped) + IRCD->SendServer(s); + } + + /* We make the bots go online */ + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + { + User *u = it->second; + + BotInfo *bi = BotInfo::Find(u->GetUID()); + if (bi) + { + XLine x(bi->nick, "Reserved for services"); + IRCD->SendSQLine(NULL, &x); + } + + IRCD->SendClientIntroduction(u); + if (bi) + bi->introduced = true; + } + + for (channel_map::const_iterator it = ChannelList.begin(), it_end = ChannelList.end(); it != it_end; ++it) + { + Channel *c = it->second; + + if (c->users.empty()) + IRCD->SendChannel(c); + else + for (Channel::ChanUserList::const_iterator cit = c->users.begin(), cit_end = c->users.end(); cit != cit_end; ++cit) + IRCD->SendJoin(cit->second->user, c, &cit->second->status); + + for (Channel::ModeList::const_iterator it2 = c->GetModes().begin(); it2 != c->GetModes().end(); ++it2) + { + ChannelMode *cm = ModeManager::FindChannelModeByName(it2->first); + if (!cm || cm->type != MODE_LIST) + continue; + ModeManager::StackerAdd(c->ci->WhoSends(), c, cm, true, it2->second); + } + + if (!c->topic.empty() && !c->topic_setter.empty()) + IRCD->SendTopic(c->ci->WhoSends(), c); + + c->syncing = true; + } + } + } + + FOREACH_MOD(OnNewServer, (this)); +} + +Server::~Server() +{ + Log(this, "quit") << "quit from " << (this->uplink ? this->uplink->GetName() : "no uplink") << " for " << this->quit_reason; + + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + { + User *u = it->second; + + if (u->server == this) + { + u->Quit(this->quit_reason); + u->server = NULL; + } + } + + Log(LOG_DEBUG) << "Finished removing all users for " << this->GetName(); + + if (this->uplink) + this->uplink->DelLink(this); + + for (unsigned i = this->links.size(); i > 0; --i) + this->links[i - 1]->Delete(this->quit_reason); + + Servers::ByName.erase(this->name); + if (!this->sid.empty()) + Servers::ByID.erase(this->sid); +} + +void Server::Delete(const Anope::string &reason) +{ + this->quit_reason = reason; + this->quitting = true; + FOREACH_MOD(OnServerQuit, (this)); + delete this; +} + +const Anope::string &Server::GetName() const +{ + return this->name; +} + +unsigned Server::GetHops() const +{ + return this->hops; +} + +void Server::SetDescription(const Anope::string &desc) +{ + this->description = desc; +} + +const Anope::string &Server::GetDescription() const +{ + return this->description; +} + +void Server::SetSID(const Anope::string &nsid) +{ + if (!this->sid.empty()) + throw CoreException("Server already has an id?"); + this->sid = nsid; + Servers::ByID[nsid] = this; +} + +const Anope::string &Server::GetSID() const +{ + if (!this->sid.empty() && IRCD->RequiresID) + return this->sid; + else + return this->name; +} + +const Anope::string &Server::GetQuitReason() const +{ + return this->quit_reason; +} + +const std::vector &Server::GetLinks() const +{ + return this->links; +} + +Server *Server::GetUplink() +{ + return this->uplink; +} + +void Server::AddLink(Server *s) +{ + this->links.push_back(s); + + Log(this, "connect") << "introduced " << s->GetName(); +} + +void Server::DelLink(Server *s) +{ + if (this->links.empty()) + throw CoreException("Server::DelLink called on " + this->GetName() + " for " + s->GetName() + " but we have no links?"); + + for (unsigned i = 0, j = this->links.size(); i < j; ++i) + { + if (this->links[i] == s) + { + this->links.erase(this->links.begin() + i); + break; + } + } + + Log(this, "quit") << "quit " << s->GetName(); +} + +void Server::Sync(bool sync_links) +{ + if (this->IsSynced()) + return; + + syncing = false; + + Log(this, "sync") << "is done syncing"; + + FOREACH_MOD(OnServerSync, (this)); + + if (sync_links && !this->links.empty()) + { + for (unsigned i = 0, j = this->links.size(); i < j; ++i) + this->links[i]->Sync(true); + } + + bool me = this->GetUplink() && this->GetUplink() == Me; + + if (me) + { + FOREACH_MOD(OnPreUplinkSync, (this)); + } + + for (channel_map::const_iterator it = ChannelList.begin(), it_end = ChannelList.end(); it != it_end;) + { + Channel *c = it->second; + ++it; + + if (c->syncing) + c->Sync(); + } + + if (me) + { + IRCD->SendEOB(); + Me->Sync(false); + + FOREACH_MOD(OnUplinkSync, (this)); + + if (!Anope::NoFork) + { + Log(LOG_TERMINAL) << "Successfully linked, launching into background..."; + Anope::Fork(); + } + } +} + +bool Server::IsSynced() const +{ + return !syncing; +} + +void Server::Unsync() +{ + syncing = true; +} + +bool Server::IsULined() const +{ + if (this == Me) + return true; + + for (unsigned i = 0; i < Config->Ulines.size(); ++i) + if (Config->Ulines[i].equals_ci(this->GetName())) + return true; + return false; +} + +bool Server::IsJuped() const +{ + return juped; +} + +bool Server::IsQuitting() const +{ + return quitting; +} + +void Server::Notice(BotInfo *source, const Anope::string &message) +{ + if (Config->UsePrivmsg && Config->DefPrivmsg) + IRCD->SendGlobalPrivmsg(source, this, message); + else + IRCD->SendGlobalNotice(source, this, message); +} + +Server *Server::Find(const Anope::string &name, bool name_only) +{ + Anope::map::iterator it; + + if (!name_only) + { + it = Servers::ByID.find(name); + if (it != Servers::ByID.end()) + return it->second; + } + + it = Servers::ByName.find(name); + if (it != Servers::ByName.end()) + return it->second; + + return NULL; +} + +Server* Servers::GetUplink() +{ + for (unsigned i = 0; Me && i < Me->GetLinks().size(); ++i) + if (!Me->GetLinks()[i]->IsJuped()) + return Me->GetLinks()[i]; + return NULL; +} diff --git a/src/siphash.cpp b/src/siphash.cpp new file mode 100644 index 0000000..6a34d4d --- /dev/null +++ b/src/siphash.cpp @@ -0,0 +1,139 @@ +/* SipHash-2-4 routines. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +/* + Copyright (c) 2013 Marek Majkowski + Permission is hereby granted, free of charge, to any person obtaining a copy + of this software and associated documentation files (the "Software"), to deal + in the Software without restriction, including without limitation the rights + to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + copies of the Software, and to permit persons to whom the Software is + furnished to do so, subject to the following conditions: + The above copyright notice and this permission notice shall be included in + all copies or substantial portions of the Software. + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + THE SOFTWARE. + + Original location: + https://github.com/majek/csiphash/ + Solution inspired by code from: + Samuel Neves (supercop/crypto_auth/siphash24/little) + djb (supercop/crypto_auth/siphash24/little2) + Jean-Philippe Aumasson (https://131002.net/siphash/siphash24.c) +*/ + +#include "services.h" +#include "anope.h" + +// WARNING: This ifdef maze could be a lot simpler but unfortunately +// that will cause find_includes to be unable to parse it. + +#ifdef __APPLE__ +# include +# define _le64toh(x) OSSwapLittleToHostInt64(x) +#endif + +#ifdef __FreeBSD__ +# include +# define _le64toh(x) le64toh(x) +#endif + +#ifdef __linux__ +# include +#endif + +#ifdef __NetBSD__ +# include +# define _le64toh(x) le64toh(x) +#endif + +#ifdef __OpenBSD__ +# include +# define _le64toh(x) le64toh(x) +#endif + +// Windows is always little endian. +#ifdef _WIN32 +# define _le64toh(x) ((uint64_t)(x)) +#endif + +// Attempt to work on unenumerated platforms. +#if defined(le64toh) && !defined(_le64toh) +# define _le64toh le64toh +#endif + +// We can't do anything about this. +#ifndef _le64toh +# error Please define _le64toh for your platform! +#endif + +#define ROTATE(x, b) (uint64_t)( ((x) << (b)) | ( (x) >> (64 - (b))) ) + +#define HALF_ROUND(a,b,c,d,s,t) \ + a += b; c += d; \ + b = ROTATE(b, s) ^ a; \ + d = ROTATE(d, t) ^ c; \ + a = ROTATE(a, 32); + +#define DOUBLE_ROUND(v0,v1,v2,v3) \ + HALF_ROUND(v0,v1,v2,v3,13,16); \ + HALF_ROUND(v2,v1,v0,v3,17,21); \ + HALF_ROUND(v0,v1,v2,v3,13,16); \ + HALF_ROUND(v2,v1,v0,v3,17,21); + + +uint64_t Anope::SipHash24(const void *src, unsigned long src_sz, const char key[16]) +{ + const uint64_t *_key = (uint64_t *)key; + uint64_t k0 = _le64toh(_key[0]); + uint64_t k1 = _le64toh(_key[1]); + uint64_t b = (uint64_t)src_sz << 56; + const uint64_t *in = (uint64_t*)src; + + uint64_t v0 = k0 ^ 0x736f6d6570736575ULL; + uint64_t v1 = k1 ^ 0x646f72616e646f6dULL; + uint64_t v2 = k0 ^ 0x6c7967656e657261ULL; + uint64_t v3 = k1 ^ 0x7465646279746573ULL; + + while (src_sz >= 8) + { + uint64_t mi = _le64toh(*in); + in += 1; src_sz -= 8; + v3 ^= mi; + DOUBLE_ROUND(v0,v1,v2,v3); + v0 ^= mi; + } + + uint64_t t = 0; uint8_t *pt = (uint8_t *)&t; uint8_t *m = (uint8_t *)in; + switch (src_sz) + { + case 7: pt[6] = m[6]; + case 6: pt[5] = m[5]; + case 5: pt[4] = m[4]; + case 4: *((uint32_t*)&pt[0]) = *((uint32_t*)&m[0]); break; + case 3: pt[2] = m[2]; + case 2: pt[1] = m[1]; + case 1: pt[0] = m[0]; + } + b |= _le64toh(t); + + v3 ^= b; + DOUBLE_ROUND(v0,v1,v2,v3); + v0 ^= b; v2 ^= 0xff; + DOUBLE_ROUND(v0,v1,v2,v3); + DOUBLE_ROUND(v0,v1,v2,v3); + return (v0 ^ v1) ^ (v2 ^ v3); +} diff --git a/src/socket_clients.cpp b/src/socket_clients.cpp new file mode 100644 index 0000000..e8665df --- /dev/null +++ b/src/socket_clients.cpp @@ -0,0 +1,98 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "anope.h" +#include "logger.h" +#include "sockets.h" + +#include + +void ConnectionSocket::Connect(const Anope::string &TargetHost, int Port) +{ + this->io->Connect(this, TargetHost, Port); +} + +bool ConnectionSocket::Process() +{ + try + { + if (this->flags[SF_CONNECTED]) + return true; + else if (this->flags[SF_CONNECTING]) + this->flags[this->io->FinishConnect(this)] = true; + else + this->flags[SF_DEAD] = true; + } + catch (const SocketException &ex) + { + Log() << ex.GetReason(); + } + return false; +} + +void ConnectionSocket::ProcessError() +{ + int optval = 0; + socklen_t optlen = sizeof(optval); + getsockopt(this->GetFD(), SOL_SOCKET, SO_ERROR, reinterpret_cast(&optval), &optlen); + errno = optval; + this->OnError(optval ? Anope::LastError() : ""); +} + +void ConnectionSocket::OnConnect() +{ +} + +void ConnectionSocket::OnError(const Anope::string &error) +{ + Log(LOG_DEBUG) << "Socket error: " << error; +} + +ClientSocket::ClientSocket(ListenSocket *l, const sockaddrs &addr) : ls(l), clientaddr(addr) +{ +} + +bool ClientSocket::Process() +{ + try + { + if (this->flags[SF_ACCEPTED]) + return true; + else if (this->flags[SF_ACCEPTING]) + this->flags[this->io->FinishAccept(this)] = true; + else + this->flags[SF_DEAD] = true; + } + catch (const SocketException &ex) + { + Log() << ex.GetReason(); + } + return false; +} + +void ClientSocket::ProcessError() +{ + int optval = 0; + socklen_t optlen = sizeof(optval); + getsockopt(this->GetFD(), SOL_SOCKET, SO_ERROR, reinterpret_cast(&optval), &optlen); + errno = optval; + this->OnError(optval ? Anope::LastError() : ""); +} + +void ClientSocket::OnAccept() +{ +} + +void ClientSocket::OnError(const Anope::string &error) +{ + Log(LOG_DEBUG) << "Socket error: " << error; +} diff --git a/src/socket_transport.cpp b/src/socket_transport.cpp new file mode 100644 index 0000000..abee187 --- /dev/null +++ b/src/socket_transport.cpp @@ -0,0 +1,198 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "sockets.h" +#include "socketengine.h" + +BufferedSocket::BufferedSocket() +{ +} + +BufferedSocket::~BufferedSocket() +{ +} + +bool BufferedSocket::ProcessRead() +{ + char tbuffer[NET_BUFSIZE]; + + this->recv_len = 0; + + int len = this->io->Recv(this, tbuffer, sizeof(tbuffer) - 1); + if (len == 0) + return false; + if (len < 0) + return SocketEngine::IgnoreErrno(); + + tbuffer[len] = 0; + this->read_buffer.append(tbuffer); + this->recv_len = len; + + return true; +} + +bool BufferedSocket::ProcessWrite() +{ + int count = this->io->Send(this, this->write_buffer); + if (count == 0) + return false; + if (count < 0) + return SocketEngine::IgnoreErrno(); + + this->write_buffer = this->write_buffer.substr(count); + if (this->write_buffer.empty()) + SocketEngine::Change(this, false, SF_WRITABLE); + + return true; +} + +const Anope::string BufferedSocket::GetLine() +{ + size_t s = this->read_buffer.find('\n'); + if (s == Anope::string::npos) + return ""; + Anope::string str = this->read_buffer.substr(0, s + 1); + this->read_buffer.erase(0, s + 1); + this->read_buffer.ltrim("\r\n"); + return str.trim("\r\n"); +} + +void BufferedSocket::Write(const char *buffer, size_t l) +{ + this->write_buffer += buffer + Anope::string("\r\n"); + SocketEngine::Change(this, true, SF_WRITABLE); +} + +void BufferedSocket::Write(const char *message, ...) +{ + va_list vi; + char tbuffer[BUFSIZE]; + + if (!message) + return; + + va_start(vi, message); + int len = vsnprintf(tbuffer, sizeof(tbuffer), message, vi); + va_end(vi); + + this->Write(tbuffer, std::min(len, static_cast(sizeof(tbuffer)))); +} + +void BufferedSocket::Write(const Anope::string &message) +{ + this->Write(message.c_str(), message.length()); +} + +int BufferedSocket::ReadBufferLen() const +{ + return recv_len; +} + +int BufferedSocket::WriteBufferLen() const +{ + return this->write_buffer.length(); +} + + +BinarySocket::DataBlock::DataBlock(const char *b, size_t l) +{ + this->orig = this->buf = new char[l]; + memcpy(this->buf, b, l); + this->len = l; +} + +BinarySocket::DataBlock::~DataBlock() +{ + delete [] this->orig; +} + +BinarySocket::BinarySocket() +{ +} + +BinarySocket::~BinarySocket() +{ +} + +bool BinarySocket::ProcessRead() +{ + char tbuffer[NET_BUFSIZE]; + + int len = this->io->Recv(this, tbuffer, sizeof(tbuffer)); + if (len <= 0) + return false; + + return this->Read(tbuffer, len); +} + +bool BinarySocket::ProcessWrite() +{ + if (this->write_buffer.empty()) + { + SocketEngine::Change(this, false, SF_WRITABLE); + return true; + } + + DataBlock *d = this->write_buffer.front(); + + int len = this->io->Send(this, d->buf, d->len); + if (len <= -1) + return false; + else if (static_cast(len) == d->len) + { + delete d; + this->write_buffer.pop_front(); + } + else + { + d->buf += len; + d->len -= len; + } + + if (this->write_buffer.empty()) + SocketEngine::Change(this, false, SF_WRITABLE); + + return true; +} + +void BinarySocket::Write(const char *buffer, size_t l) +{ + if (l == 0) + return; + this->write_buffer.push_back(new DataBlock(buffer, l)); + SocketEngine::Change(this, true, SF_WRITABLE); +} + +void BinarySocket::Write(const char *message, ...) +{ + va_list vi; + char tbuffer[BUFSIZE]; + + if (!message) + return; + + va_start(vi, message); + int len = vsnprintf(tbuffer, sizeof(tbuffer), message, vi); + va_end(vi); + + this->Write(tbuffer, std::min(len, static_cast(sizeof(tbuffer)))); +} + +void BinarySocket::Write(const Anope::string &message) +{ + this->Write(message.c_str(), message.length()); +} + +bool BinarySocket::Read(const char *buffer, size_t l) +{ + return true; +} diff --git a/src/socketengines/socketengine_epoll.cpp b/src/socketengines/socketengine_epoll.cpp new file mode 100644 index 0000000..bf17b09 --- /dev/null +++ b/src/socketengines/socketengine_epoll.cpp @@ -0,0 +1,121 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "anope.h" +#include "sockets.h" +#include "socketengine.h" +#include "config.h" + +#include +#include +#include + +static int EngineHandle; +static std::vector events; + +void SocketEngine::Init() +{ + EngineHandle = epoll_create(4); + + if (EngineHandle == -1) + throw SocketException("Could not initialize epoll socket engine: " + Anope::LastError()); + + events.resize(DefaultSize); +} + +void SocketEngine::Shutdown() +{ + while (!Sockets.empty()) + delete Sockets.begin()->second; +} + +void SocketEngine::Change(Socket *s, bool set, SocketFlag flag) +{ + if (set == s->flags[flag]) + return; + + bool before_registered = s->flags[SF_READABLE] || s->flags[SF_WRITABLE]; + + s->flags[flag] = set; + + bool now_registered = s->flags[SF_READABLE] || s->flags[SF_WRITABLE]; + + epoll_event ev; + + memset(&ev, 0, sizeof(ev)); + + ev.events = (s->flags[SF_READABLE] ? EPOLLIN : 0) | (s->flags[SF_WRITABLE] ? EPOLLOUT : 0); + ev.data.fd = s->GetFD(); + + int mod; + if (!before_registered && now_registered) + mod = EPOLL_CTL_ADD; + else if (before_registered && !now_registered) + mod = EPOLL_CTL_DEL; + else if (before_registered && now_registered) + mod = EPOLL_CTL_MOD; + else + return; + + if (epoll_ctl(EngineHandle, mod, ev.data.fd, &ev) == -1) + throw SocketException("Unable to epoll_ctl() fd " + stringify(ev.data.fd) + " to epoll: " + Anope::LastError()); +} + +void SocketEngine::Process() +{ + if (Sockets.size() > events.size()) + events.resize(events.size() * 2); + + int total = epoll_wait(EngineHandle, &events.front(), events.size(), Config->ReadTimeout * 1000); + Anope::CurTime = time(NULL); + + /* EINTR can be given if the read timeout expires */ + if (total == -1) + { + if (errno != EINTR) + Log() << "SockEngine::Process(): error: " << Anope::LastError(); + return; + } + + for (int i = 0; i < total; ++i) + { + epoll_event &ev = events[i]; + + std::map::iterator it = Sockets.find(ev.data.fd); + if (it == Sockets.end()) + continue; + Socket *s = it->second; + + if (ev.events & (EPOLLHUP | EPOLLERR)) + { + s->ProcessError(); + delete s; + continue; + } + + if (!s->Process()) + { + if (s->flags[SF_DEAD]) + delete s; + continue; + } + + if ((ev.events & EPOLLIN) && !s->ProcessRead()) + s->flags[SF_DEAD] = true; + + if ((ev.events & EPOLLOUT) && !s->ProcessWrite()) + s->flags[SF_DEAD] = true; + + if (s->flags[SF_DEAD]) + delete s; + } +} diff --git a/src/socketengines/socketengine_kqueue.cpp b/src/socketengines/socketengine_kqueue.cpp new file mode 100644 index 0000000..6b3350d --- /dev/null +++ b/src/socketengines/socketengine_kqueue.cpp @@ -0,0 +1,123 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "anope.h" +#include "sockets.h" +#include "socketengine.h" +#include "logger.h" +#include "config.h" + +#include +#include +#include +#include + +static int kq_fd; +static std::vector change_events, event_events; +static unsigned change_count; + +static inline struct kevent *GetChangeEvent() +{ + if (change_count == change_events.size()) + change_events.resize(change_count * 2); + + return &change_events[change_count++]; +} + +void SocketEngine::Init() +{ + kq_fd = kqueue(); + + if (kq_fd < 0) + throw SocketException("Unable to create kqueue engine: " + Anope::LastError()); + + change_events.resize(DefaultSize); + event_events.resize(DefaultSize); +} + +void SocketEngine::Shutdown() +{ + while (!Sockets.empty()) + delete Sockets.begin()->second; +} + +void SocketEngine::Change(Socket *s, bool set, SocketFlag flag) +{ + if (set == s->flags[flag]) + return; + + s->flags[flag] = set; + + int mod; + if (flag == SF_READABLE) + mod = EVFILT_READ; + else if (flag == SF_WRITABLE) + mod = EVFILT_WRITE; + else + return; + + struct kevent *event = GetChangeEvent(); + EV_SET(event, s->GetFD(), mod, set ? EV_ADD : EV_DELETE, 0, 0, NULL); +} + +void SocketEngine::Process() +{ + if (Sockets.size() > event_events.size()) + event_events.resize(event_events.size() * 2); + + static timespec kq_timespec = { Config->ReadTimeout, 0 }; + int total = kevent(kq_fd, &change_events.front(), change_count, &event_events.front(), event_events.size(), &kq_timespec); + change_count = 0; + Anope::CurTime = time(NULL); + + /* EINTR can be given if the read timeout expires */ + if (total == -1) + { + if (errno != EINTR) + Log() << "SockEngine::Process(): error: " << Anope::LastError(); + return; + } + + for (int i = 0; i < total; ++i) + { + struct kevent &event = event_events[i]; + if (event.flags & EV_ERROR) + continue; + + std::map::iterator it = Sockets.find(event.ident); + if (it == Sockets.end()) + continue; + Socket *s = it->second; + + if (event.flags & EV_EOF) + { + s->ProcessError(); + delete s; + continue; + } + + if (!s->Process()) + { + if (s->flags[SF_DEAD]) + delete s; + continue; + } + + if (event.filter == EVFILT_READ && !s->ProcessRead()) + s->flags[SF_DEAD] = true; + else if (event.filter == EVFILT_WRITE && !s->ProcessWrite()) + s->flags[SF_DEAD] = true; + + if (s->flags[SF_DEAD]) + delete s; + } +} diff --git a/src/socketengines/socketengine_poll.cpp b/src/socketengines/socketengine_poll.cpp new file mode 100644 index 0000000..bf03096 --- /dev/null +++ b/src/socketengines/socketengine_poll.cpp @@ -0,0 +1,148 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "anope.h" +#include "sockets.h" +#include "socketengine.h" +#include "config.h" + +#include + +#ifndef _WIN32 +# include +# include +# include +# include +# include +# ifndef POLLRDHUP +# define POLLRDHUP 0 +# endif +#else +# define poll WSAPoll +# define POLLRDHUP POLLHUP +#endif + +static std::vector events; +static std::map socket_positions; + +void SocketEngine::Init() +{ + events.resize(DefaultSize); +} + +void SocketEngine::Shutdown() +{ + while (!Sockets.empty()) + delete Sockets.begin()->second; +} + +void SocketEngine::Change(Socket *s, bool set, SocketFlag flag) +{ + if (set == s->flags[flag]) + return; + + bool before_registered = s->flags[SF_READABLE] || s->flags[SF_WRITABLE]; + + s->flags[flag] = set; + + bool now_registered = s->flags[SF_READABLE] || s->flags[SF_WRITABLE]; + + if (!before_registered && now_registered) + { + pollfd ev; + memset(&ev, 0, sizeof(ev)); + + ev.fd = s->GetFD(); + ev.events = (s->flags[SF_READABLE] ? POLLIN : 0) | (s->flags[SF_WRITABLE] ? POLLOUT : 0); + + socket_positions[ev.fd] = events.size(); + events.push_back(ev); + } + else if (before_registered && !now_registered) + { + std::map::iterator pos = socket_positions.find(s->GetFD()); + if (pos == socket_positions.end()) + throw SocketException("Unable to remove fd " + stringify(s->GetFD()) + " from poll, it does not exist?"); + + if (pos->second != events.size() - 1) + { + pollfd &ev = events[pos->second], + &last_ev = events[events.size() - 1]; + + ev = last_ev; + + socket_positions[ev.fd] = pos->second; + } + + socket_positions.erase(pos); + events.pop_back(); + } + else if (before_registered && now_registered) + { + std::map::iterator pos = socket_positions.find(s->GetFD()); + if (pos == socket_positions.end()) + throw SocketException("Unable to modify fd " + stringify(s->GetFD()) + " in poll, it does not exist?"); + + pollfd &ev = events[pos->second]; + ev.events = (s->flags[SF_READABLE] ? POLLIN : 0) | (s->flags[SF_WRITABLE] ? POLLOUT : 0); + } +} + +void SocketEngine::Process() +{ + int total = poll(&events.front(), events.size(), Config->ReadTimeout * 1000); + Anope::CurTime = time(NULL); + + /* EINTR can be given if the read timeout expires */ + if (total < 0) + { + if (errno != EINTR) + Log() << "SockEngine::Process(): error: " << Anope::LastError(); + return; + } + + for (unsigned i = 0, processed = 0; i < events.size() && processed != static_cast(total); ++i) + { + pollfd *ev = &events[i]; + + if (ev->revents != 0) + ++processed; + + std::map::iterator it = Sockets.find(ev->fd); + if (it == Sockets.end()) + continue; + Socket *s = it->second; + + if (ev->revents & (POLLERR | POLLRDHUP)) + { + s->ProcessError(); + delete s; + continue; + } + + if (!s->Process()) + { + if (s->flags[SF_DEAD]) + delete s; + continue; + } + + if ((ev->revents & POLLIN) && !s->ProcessRead()) + s->flags[SF_DEAD] = true; + + if ((ev->revents & POLLOUT) && !s->ProcessWrite()) + s->flags[SF_DEAD] = true; + + if (s->flags[SF_DEAD]) + delete s; + } +} diff --git a/src/socketengines/socketengine_select.cpp b/src/socketengines/socketengine_select.cpp new file mode 100644 index 0000000..6146659 --- /dev/null +++ b/src/socketengines/socketengine_select.cpp @@ -0,0 +1,148 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "anope.h" +#include "sockets.h" +#include "socketengine.h" +#include "logger.h" +#include "config.h" + +#ifdef _AIX +# undef FD_ZERO +# define FD_ZERO(p) memset((p), 0, sizeof(*(p))) +#endif /* _AIX */ + +static int MaxFD; +static unsigned FDCount; +static fd_set ReadFDs; +static fd_set WriteFDs; + +void SocketEngine::Init() +{ + FD_ZERO(&ReadFDs); + FD_ZERO(&WriteFDs); +} + +void SocketEngine::Shutdown() +{ + while (!Sockets.empty()) + delete Sockets.begin()->second; +} + +void SocketEngine::Change(Socket *s, bool set, SocketFlag flag) +{ + if (set == s->flags[flag]) + return; + + bool before_registered = s->flags[SF_READABLE] || s->flags[SF_WRITABLE]; + + s->flags[flag] = set; + + bool now_registered = s->flags[SF_READABLE] || s->flags[SF_WRITABLE]; + + if (!before_registered && now_registered) + { + if (s->GetFD() > MaxFD) + MaxFD = s->GetFD(); + if (s->flags[SF_READABLE]) + FD_SET(s->GetFD(), &ReadFDs); + if (s->flags[SF_WRITABLE]) + FD_SET(s->GetFD(), &WriteFDs); + ++FDCount; + } + else if (before_registered && !now_registered) + { + if (s->GetFD() == MaxFD) + --MaxFD; + FD_CLR(s->GetFD(), &ReadFDs); + FD_CLR(s->GetFD(), &WriteFDs); + --FDCount; + } + else if (before_registered && now_registered) + { + if (s->flags[SF_READABLE]) + FD_SET(s->GetFD(), &ReadFDs); + else + FD_CLR(s->GetFD(), &ReadFDs); + + if (s->flags[SF_WRITABLE]) + FD_SET(s->GetFD(), &WriteFDs); + else + FD_CLR(s->GetFD(), &WriteFDs); + } +} + +void SocketEngine::Process() +{ + fd_set rfdset = ReadFDs, wfdset = WriteFDs, efdset = ReadFDs; + timeval tval; + tval.tv_sec = Config->ReadTimeout; + tval.tv_usec = 0; + +#ifdef _WIN32 + /* We can use the socket engine to "sleep" services for a period of + * time between connections to the uplink, which allows modules, + * timers, etc to function properly. Windows, being as useful as it is, + * does not allow to select() on 0 sockets and will immediately return error. + * Thus: + */ + if (FDCount == 0) + { + sleep(tval.tv_sec); + return; + } +#endif + + int sresult = select(MaxFD + 1, &rfdset, &wfdset, &efdset, &tval); + Anope::CurTime = time(NULL); + + if (sresult == -1) + { + Log() << "SockEngine::Process(): error: " << Anope::LastError(); + } + else if (sresult) + { + int processed = 0; + for (std::map::const_iterator it = Sockets.begin(), it_end = Sockets.end(); it != it_end && processed != sresult;) + { + Socket *s = it->second; + ++it; + + bool has_read = FD_ISSET(s->GetFD(), &rfdset), has_write = FD_ISSET(s->GetFD(), &wfdset), has_error = FD_ISSET(s->GetFD(), &efdset); + if (has_read || has_write || has_error) + ++processed; + + if (has_error) + { + s->ProcessError(); + delete s; + continue; + } + + if (!s->Process()) + { + if (s->flags[SF_DEAD]) + delete s; + continue; + } + + if (has_read && !s->ProcessRead()) + s->flags[SF_DEAD] = true; + + if (has_write && !s->ProcessWrite()) + s->flags[SF_DEAD] = true; + + if (s->flags[SF_DEAD]) + delete s; + } + } +} diff --git a/src/sockets.cpp b/src/sockets.cpp new file mode 100644 index 0000000..b5edc0e --- /dev/null +++ b/src/sockets.cpp @@ -0,0 +1,611 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "sockets.h" +#include "socketengine.h" +#include "logger.h" + +#ifndef _WIN32 +#include +#include +#include +#endif + +std::map SocketEngine::Sockets; + +uint32_t TotalRead = 0; +uint32_t TotalWritten = 0; + +SocketIO NormalSocketIO; + +sockaddrs::sockaddrs(const Anope::string &address) +{ + this->clear(); + if (!address.empty() && address.find_first_not_of_ci("0123456789abcdef.:") == Anope::string::npos) + this->pton(address.find(':') != Anope::string::npos ? AF_INET6 : AF_INET, address); +} + +void sockaddrs::clear() +{ + memset(this, 0, sizeof(*this)); +} + +int sockaddrs::family() const +{ + return sa.sa_family; +} + +size_t sockaddrs::size() const +{ + switch (sa.sa_family) + { + case AF_INET: + return sizeof(sa4); + case AF_INET6: + return sizeof(sa6); + default: + break; + } + + return 0; +} + +int sockaddrs::port() const +{ + switch (sa.sa_family) + { + case AF_INET: + return ntohs(sa4.sin_port); + case AF_INET6: + return ntohs(sa6.sin6_port); + default: + break; + } + + return -1; +} + +Anope::string sockaddrs::addr() const +{ + char address[INET6_ADDRSTRLEN]; + + switch (sa.sa_family) + { + case AF_INET: + if (inet_ntop(AF_INET, &sa4.sin_addr, address, sizeof(address))) + return address; + break; + case AF_INET6: + if (inet_ntop(AF_INET6, &sa6.sin6_addr, address, sizeof(address))) + return address; + break; + default: + break; + } + + return ""; +} + +Anope::string sockaddrs::reverse() const +{ + char address[128]; + + switch (sa.sa_family) + { + case AF_INET6: + { + static const char hex[] = "0123456789abcdef"; + unsigned reverse_ip_count = 0; + for (int j = 15; j >= 0; --j) + { + address[reverse_ip_count++] = hex[sa6.sin6_addr.s6_addr[j] & 0xF]; + address[reverse_ip_count++] = '.'; + address[reverse_ip_count++] = hex[sa6.sin6_addr.s6_addr[j] >> 4]; + address[reverse_ip_count++] = '.'; + } + /* Remove the last '.' */ + address[reverse_ip_count - 1] = 0; + return address; + } + case AF_INET: + { + unsigned long forward = sa4.sin_addr.s_addr; + in_addr rev; + rev.s_addr = forward << 24 | (forward & 0xFF00) << 8 | (forward & 0xFF0000) >> 8 | forward >> 24; + if (inet_ntop(AF_INET, &rev, address, sizeof(address))) + return address; + break; + } + } + + return ""; +} + +bool sockaddrs::ipv6() const +{ + return sa.sa_family == AF_INET6; +} + +bool sockaddrs::valid() const +{ + return size() != 0; +} + +bool sockaddrs::operator==(const sockaddrs &other) const +{ + if (sa.sa_family != other.sa.sa_family) + return false; + switch (sa.sa_family) + { + case AF_INET: + return (sa4.sin_port == other.sa4.sin_port) && (sa4.sin_addr.s_addr == other.sa4.sin_addr.s_addr); + case AF_INET6: + return (sa6.sin6_port == other.sa6.sin6_port) && !memcmp(sa6.sin6_addr.s6_addr, other.sa6.sin6_addr.s6_addr, 16); + default: + return !memcmp(this, &other, sizeof(*this)); + } + + return false; +} + +void sockaddrs::pton(int type, const Anope::string &address, int pport) +{ + this->clear(); + + switch (type) + { + case AF_INET: + { + int i = inet_pton(type, address.c_str(), &sa4.sin_addr); + if (i <= 0) + this->clear(); + else + { + sa4.sin_family = type; + sa4.sin_port = htons(pport); + } + break; + } + case AF_INET6: + { + int i = inet_pton(type, address.c_str(), &sa6.sin6_addr); + if (i <= 0) + this->clear(); + else + { + sa6.sin6_family = type; + sa6.sin6_port = htons(pport); + } + break; + } + default: + break; + } +} + +void sockaddrs::ntop(int type, const void *src) +{ + char buf[INET6_ADDRSTRLEN]; + + if (inet_ntop(type, src, buf, sizeof(buf)) != buf) + { + this->clear(); + return; + } + + switch (type) + { + case AF_INET: + sa4.sin_addr = *reinterpret_cast(src); + sa4.sin_family = type; + return; + case AF_INET6: + sa6.sin6_addr = *reinterpret_cast(src); + sa6.sin6_family = type; + return; + default: + break; + } + + this->clear(); +} + +cidr::cidr(const Anope::string &ip) +{ + bool ipv6 = ip.find(':') != Anope::string::npos; + size_t sl = ip.find_last_of('/'); + + if (sl == Anope::string::npos) + { + this->cidr_ip = ip; + this->cidr_len = ipv6 ? 128 : 32; + this->addr.pton(ipv6 ? AF_INET6 : AF_INET, ip); + } + else + { + Anope::string real_ip = ip.substr(0, sl); + Anope::string cidr_range = ip.substr(sl + 1); + + this->cidr_ip = real_ip; + this->cidr_len = ipv6 ? 128 : 32; + try + { + if (cidr_range.is_pos_number_only()) + this->cidr_len = convertTo(cidr_range); + } + catch (const ConvertException &) { } + this->addr.pton(ipv6 ? AF_INET6 : AF_INET, real_ip); + } +} + +cidr::cidr(const Anope::string &ip, unsigned char len) +{ + bool ipv6 = ip.find(':') != Anope::string::npos; + this->addr.pton(ipv6 ? AF_INET6 : AF_INET, ip); + this->cidr_ip = ip; + this->cidr_len = len; +} + +cidr::cidr(const sockaddrs &a, unsigned char len) : addr(a) +{ + this->cidr_ip = a.addr(); + this->cidr_len = len; +} + +Anope::string cidr::mask() const +{ + if ((this->addr.ipv6() && this->cidr_len == 128) || (!this->addr.ipv6() && this->cidr_len == 32)) + return this->cidr_ip; + else + return Anope::printf("%s/%d", this->cidr_ip.c_str(), this->cidr_len); +} + +bool cidr::match(const sockaddrs &other) +{ + if (!valid() || !other.valid() || this->addr.sa.sa_family != other.sa.sa_family) + return false; + + const uint8_t *ip, *their_ip; + uint8_t byte, len = this->cidr_len; + + switch (this->addr.sa.sa_family) + { + case AF_INET: + ip = reinterpret_cast(&this->addr.sa4.sin_addr); + if (len > 32) + len = 32; + byte = len / 8; + their_ip = reinterpret_cast(&other.sa4.sin_addr); + break; + case AF_INET6: + ip = reinterpret_cast(&this->addr.sa6.sin6_addr); + if (len > 128) + len = 128; + byte = len / 8; + their_ip = reinterpret_cast(&other.sa6.sin6_addr); + break; + default: + return false; + } + + if (memcmp(ip, their_ip, byte)) + return false; + + ip += byte; + their_ip += byte; + + byte = len % 8; + if (byte) + { + uint8_t m = ~0 << (8 - byte); + return (*ip & m) == (*their_ip & m); + } + + return true; +} + +bool cidr::operator<(const cidr &other) const +{ + if (this->addr.sa.sa_family != other.addr.sa.sa_family) + return this->addr.sa.sa_family < other.addr.sa.sa_family; + + switch (this->addr.sa.sa_family) + { + case AF_INET: + { + unsigned int m = 0xFFFFFFFFU >> (32 - this->cidr_len); + + return (this->addr.sa4.sin_addr.s_addr & m) < (other.addr.sa4.sin_addr.s_addr & m); + } + case AF_INET6: + { + int i = memcmp(&this->addr.sa6.sin6_addr.s6_addr, &other.addr.sa6.sin6_addr.s6_addr, this->cidr_len / 8); + if (i || this->cidr_len >= 128) + return i < 0; + + // Now all thats left is to compare 'remaining' bits at offset this->cidr_len / 8 + int remaining = this->cidr_len % 8; + unsigned char m = 0xFF << (8 - remaining); + + return (this->addr.sa6.sin6_addr.s6_addr[this->cidr_len / 8] & m) < (other.addr.sa6.sin6_addr.s6_addr[this->cidr_len / 8] & m); + } + default: + throw CoreException("Unknown AFTYPE for cidr"); + } +} + +bool cidr::operator==(const cidr &other) const +{ + return !(*this < other) && !(other < *this); +} + +bool cidr::operator!=(const cidr &other) const +{ + return !(*this == other); +} + +bool cidr::valid() const +{ + return this->addr.valid(); +} + +size_t cidr::hash::operator()(const cidr &s) const +{ + switch (s.addr.sa.sa_family) + { + case AF_INET: + { + unsigned int m = 0xFFFFFFFFU >> (32 - s.cidr_len); + return s.addr.sa4.sin_addr.s_addr & m; + } + case AF_INET6: + { + size_t h = 0; + + for (unsigned i = 0; i < s.cidr_len / 8; ++i) + h ^= (s.addr.sa6.sin6_addr.s6_addr[i] << ((i * 8) % sizeof(size_t))); + + int remaining = s.cidr_len % 8; + unsigned char m = 0xFF << (8 - remaining); + + h ^= s.addr.sa6.sin6_addr.s6_addr[s.cidr_len / 8] & m; + + return h; + } + default: + throw CoreException("Unknown AFTYPE for cidr"); + } +} + +int SocketIO::Recv(Socket *s, char *buf, size_t sz) +{ + int i = recv(s->GetFD(), buf, sz, 0); + if (i > 0) + TotalRead += i; + return i; +} + +int SocketIO::Send(Socket *s, const char *buf, size_t sz) +{ + int i = send(s->GetFD(), buf, sz, 0); + if (i > 0) + TotalWritten += i; + return i; +} + +int SocketIO::Send(Socket *s, const Anope::string &buf) +{ + return this->Send(s, buf.c_str(), buf.length()); +} + +ClientSocket *SocketIO::Accept(ListenSocket *s) +{ + sockaddrs conaddr; + + socklen_t size = sizeof(conaddr); + int newsock = accept(s->GetFD(), &conaddr.sa, &size); + + if (newsock >= 0) + { + ClientSocket *ns = s->OnAccept(newsock, conaddr); + ns->flags[SF_ACCEPTED] = true; + ns->OnAccept(); + return ns; + } + else + throw SocketException("Unable to accept connection: " + Anope::LastError()); +} + +SocketFlag SocketIO::FinishAccept(ClientSocket *cs) +{ + return SF_ACCEPTED; +} + +void SocketIO::Bind(Socket *s, const Anope::string &ip, int port) +{ + s->bindaddr.pton(s->IsIPv6() ? AF_INET6 : AF_INET, ip, port); + if (bind(s->GetFD(), &s->bindaddr.sa, s->bindaddr.size()) == -1) + throw SocketException("Unable to bind to address: " + Anope::LastError()); +} + +void SocketIO::Connect(ConnectionSocket *s, const Anope::string &target, int port) +{ + s->flags[SF_CONNECTING] = s->flags[SF_CONNECTED] = false; + s->conaddr.pton(s->IsIPv6() ? AF_INET6 : AF_INET, target, port); + int c = connect(s->GetFD(), &s->conaddr.sa, s->conaddr.size()); + if (c == -1) + { + if (!SocketEngine::IgnoreErrno()) + s->OnError(Anope::LastError()); + else + { + SocketEngine::Change(s, true, SF_WRITABLE); + s->flags[SF_CONNECTING] = true; + } + } + else + { + s->flags[SF_CONNECTED] = true; + s->OnConnect(); + } +} + +SocketFlag SocketIO::FinishConnect(ConnectionSocket *s) +{ + if (s->flags[SF_CONNECTED]) + return SF_CONNECTED; + else if (!s->flags[SF_CONNECTING]) + throw SocketException("SocketIO::FinishConnect called for a socket not connected nor connecting?"); + + int optval = 0; + socklen_t optlen = sizeof(optval); + if (!getsockopt(s->GetFD(), SOL_SOCKET, SO_ERROR, reinterpret_cast(&optval), &optlen) && !optval) + { + s->flags[SF_CONNECTED] = true; + s->flags[SF_CONNECTING] = false; + s->OnConnect(); + return SF_CONNECTED; + } + else + { + errno = optval; + s->OnError(optval ? Anope::LastError() : ""); + return SF_DEAD; + } +} + +Socket::Socket() +{ + throw CoreException("Socket::Socket() ?"); +} + +Socket::Socket(int s, bool i, int type) +{ + this->io = &NormalSocketIO; + this->ipv6 = i; + if (s == -1) + this->sock = socket(this->ipv6 ? AF_INET6 : AF_INET, type, 0); + else + this->sock = s; + this->SetBlocking(false); + SocketEngine::Sockets[this->sock] = this; + SocketEngine::Change(this, true, SF_READABLE); +} + +Socket::~Socket() +{ + SocketEngine::Change(this, false, SF_READABLE); + SocketEngine::Change(this, false, SF_WRITABLE); + anope_close(this->sock); + this->io->Destroy(); + SocketEngine::Sockets.erase(this->sock); +} + +int Socket::GetFD() const +{ + return sock; +} + +bool Socket::IsIPv6() const +{ + return ipv6; +} + +bool Socket::SetBlocking(bool state) +{ + int f = fcntl(this->GetFD(), F_GETFL, 0); + if (state) + return !fcntl(this->GetFD(), F_SETFL, f & ~O_NONBLOCK); + else + return !fcntl(this->GetFD(), F_SETFL, f | O_NONBLOCK); +} + +void Socket::Bind(const Anope::string &ip, int port) +{ + this->io->Bind(this, ip, port); +} + +bool Socket::Process() +{ + return true; +} + +bool Socket::ProcessRead() +{ + return true; +} + +bool Socket::ProcessWrite() +{ + return true; +} + +void Socket::ProcessError() +{ +} + +ListenSocket::ListenSocket(const Anope::string &bindip, int port, bool i) +{ + this->SetBlocking(false); + + const int op = 1; + setsockopt(this->GetFD(), SOL_SOCKET, SO_REUSEADDR, reinterpret_cast(&op), sizeof(op)); + + this->bindaddr.pton(i ? AF_INET6 : AF_INET, bindip, port); + this->io->Bind(this, bindip, port); + + if (listen(sock, SOMAXCONN) == -1) + throw SocketException("Unable to listen: " + Anope::LastError()); +} + +ListenSocket::~ListenSocket() +{ +} + +bool ListenSocket::ProcessRead() +{ + try + { + this->io->Accept(this); + } + catch (const SocketException &ex) + { + Log() << ex.GetReason(); + } + return true; +} + +int SocketEngine::GetLastError() +{ +#ifndef _WIN32 + return errno; +#else + return WSAGetLastError(); +#endif +} + +void SocketEngine::SetLastError(int err) +{ +#ifndef _WIN32 + errno = err; +#else + WSASetLastError(err); +#endif +} + +bool SocketEngine::IgnoreErrno() +{ + return GetLastError() == EAGAIN + || GetLastError() == EWOULDBLOCK + || GetLastError() == EINTR + || GetLastError() == EINPROGRESS; +} diff --git a/src/threadengine.cpp b/src/threadengine.cpp new file mode 100644 index 0000000..dba2f02 --- /dev/null +++ b/src/threadengine.cpp @@ -0,0 +1,136 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "threadengine.h" +#include "anope.h" + +#ifndef _WIN32 +#include +#endif + +static inline pthread_attr_t *get_engine_attr() +{ + /* Threadengine attributes used by this thread engine */ + static pthread_attr_t attr; + static bool inited = false; + + if (inited == false) + { + if (pthread_attr_init(&attr)) + throw CoreException("Error calling pthread_attr_init"); + if (pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_JOINABLE)) + throw CoreException("Unable to mark threads as joinable"); + inited = true; + } + + return &attr; +} + +static void *entry_point(void *parameter) +{ + Thread *thread = static_cast(parameter); + thread->Run(); + thread->SetExitState(); + pthread_exit(0); + return NULL; +} + +Thread::Thread() : exit(false) +{ +} + +Thread::~Thread() +{ +} + +void Thread::Join() +{ + this->SetExitState(); + pthread_join(handle, NULL); +} + +void Thread::SetExitState() +{ + this->Notify(); + exit = true; +} + +void Thread::Exit() +{ + this->SetExitState(); + pthread_exit(0); +} + +void Thread::Start() +{ + if (pthread_create(&this->handle, get_engine_attr(), entry_point, this)) + { + this->flags[SF_DEAD] = true; + throw CoreException("Unable to create thread: " + Anope::LastError()); + } +} + +bool Thread::GetExitState() const +{ + return exit; +} + +void Thread::OnNotify() +{ + this->Join(); + this->flags[SF_DEAD] = true; +} + +Mutex::Mutex() +{ + pthread_mutex_init(&mutex, NULL); +} + +Mutex::~Mutex() +{ + pthread_mutex_destroy(&mutex); +} + +void Mutex::Lock() +{ + pthread_mutex_lock(&mutex); +} + +void Mutex::Unlock() +{ + pthread_mutex_unlock(&mutex); +} + +bool Mutex::TryLock() +{ + return pthread_mutex_trylock(&mutex) == 0; +} + +Condition::Condition() : Mutex() +{ + pthread_cond_init(&cond, NULL); +} + +Condition::~Condition() +{ + pthread_cond_destroy(&cond); +} + +void Condition::Wakeup() +{ + pthread_cond_signal(&cond); +} + +void Condition::Wait() +{ + pthread_cond_wait(&cond, &mutex); +} diff --git a/src/timers.cpp b/src/timers.cpp new file mode 100644 index 0000000..abb8bfe --- /dev/null +++ b/src/timers.cpp @@ -0,0 +1,126 @@ +/* Timer stuff. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "services.h" +#include "timers.h" + +std::multimap TimerManager::Timers; + +Timer::Timer(long time_from_now, time_t now, bool repeating) +{ + owner = NULL; + trigger = now + time_from_now; + secs = time_from_now; + repeat = repeating; + settime = now; + + TimerManager::AddTimer(this); +} + +Timer::Timer(Module *creator, long time_from_now, time_t now, bool repeating) +{ + owner = creator; + trigger = now + time_from_now; + secs = time_from_now; + repeat = repeating; + settime = now; + + TimerManager::AddTimer(this); +} + +Timer::~Timer() +{ + TimerManager::DelTimer(this); +} + +void Timer::SetTimer(time_t t) +{ + TimerManager::DelTimer(this); + trigger = t; + TimerManager::AddTimer(this); +} + +time_t Timer::GetTimer() const +{ + return trigger; +} + +bool Timer::GetRepeat() const +{ + return repeat; +} + +time_t Timer::GetSetTime() const +{ + return settime; +} + +void Timer::SetSecs(time_t t) +{ + TimerManager::DelTimer(this); + secs = t; + trigger = Anope::CurTime + t; + TimerManager::AddTimer(this); +} + +long Timer::GetSecs() const +{ + return secs; +} + +Module *Timer::GetOwner() const +{ + return owner; +} + +void TimerManager::AddTimer(Timer *t) +{ + Timers.insert(std::make_pair(t->GetTimer(), t)); +} + +void TimerManager::DelTimer(Timer *t) +{ + std::pair::iterator, std::multimap::iterator> itpair = Timers.equal_range(t->GetTimer()); + for (std::multimap::iterator i = itpair.first; i != itpair.second; ++i) + { + if (i->second == t) + { + Timers.erase(i); + break; + } + } +} + +void TimerManager::TickTimers(time_t ctime) +{ + while (!Timers.empty()) + { + std::multimap::iterator it = Timers.begin(); + Timer *t = it->second; + + if (t->GetTimer() > ctime) + break; + + t->Tick(ctime); + + if (t->GetRepeat()) + t->SetTimer(ctime + t->GetSecs()); + else + delete t; + } +} + +void TimerManager::DeleteTimersFor(Module *m) +{ + for (std::multimap::iterator it = Timers.begin(), it_next = it; it != Timers.end(); it = it_next) + { + ++it_next; + if (it->second->GetOwner() == m) + delete it->second; + } +} diff --git a/src/tools/CMakeLists.txt b/src/tools/CMakeLists.txt new file mode 100644 index 0000000..3e00b98 --- /dev/null +++ b/src/tools/CMakeLists.txt @@ -0,0 +1,52 @@ +# Find all the *.cpp files within the current source directory, and sort the list +file(GLOB TOOLS_SRCS RELATIVE ${CMAKE_CURRENT_SOURCE_DIR} "*.cpp") +sort_list(TOOLS_SRCS) + +# Set all the files to use C++ as well as set their compile flags +set_source_files_properties(${TOOLS_SRCS} PROPERTIES LANGUAGE CXX COMPILE_FLAGS "${CXXFLAGS}") + +# Iterate through all the source files +foreach(SRC ${TOOLS_SRCS}) + # Convert the source file extension to have no extension + string(REGEX REPLACE "\\.cpp$" "" EXE ${SRC}) + # Calculate the header file dependencies for the given source file + calculate_depends(${SRC}) + # Only continue if this file isn't skipped + if(NOT SKIP) + # Generate the executable and set its linker flags, also set it to depend on the main Anope executable to be built beforehand + add_executable(${EXE} ${SRC}) + set_target_properties(${EXE} PROPERTIES LINKER_LANGUAGE CXX LINK_FLAGS "${LDFLAGS}") + add_dependencies(${EXE} ${PROGRAM_NAME}) + # Only for Windows, set anopesmtp to require the wsock32 library + if(WIN32 AND ${EXE} STREQUAL anopesmtp) + target_link_libraries(${EXE} wsock32) + endif(WIN32 AND ${EXE} STREQUAL anopesmtp) + if(${CMAKE_SYSTEM_NAME} STREQUAL "SunOS" AND ${EXE} STREQUAL anopesmtp) + target_link_libraries(${EXE} socket nsl) + endif(${CMAKE_SYSTEM_NAME} STREQUAL "SunOS" AND ${EXE} STREQUAL anopesmtp) + # Set the executable to be installed to the bin directory under the main directory + install(TARGETS ${EXE} + DESTINATION ${BIN_DIR} + ) + # Add the executable to the list of files for CPack to ignore + get_target_property(EXE_BINARY ${EXE} LOCATION) + get_filename_component(EXE_BINARY ${EXE_BINARY} NAME) + add_to_cpack_ignored_files("${EXE_BINARY}$" TRUE) + endif(NOT SKIP) +endforeach(SRC) + +# If not on Windows, generate anoperc and install it along with mydbgen +if(NOT WIN32) + configure_file(${Anope_SOURCE_DIR}/src/tools/anoperc.in ${Anope_BINARY_DIR}/src/tools/anoperc) + install (PROGRAMS ${CMAKE_CURRENT_BINARY_DIR}/anoperc + DESTINATION ${BIN_DIR} + ) + install (PROGRAMS geoipupdate.sh + DESTINATION ${BIN_DIR} + ) +endif(NOT WIN32) + +# On non-Windows platforms, if RUNGROUP is set, change the permissions of the tools directory +if(NOT WIN32 AND RUNGROUP) + install(CODE "execute_process(COMMAND ${CHMOD} 2770 \"\$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/bin\")") +endif(NOT WIN32 AND RUNGROUP) diff --git a/src/tools/anoperc.in b/src/tools/anoperc.in new file mode 100644 index 0000000..4b90819 --- /dev/null +++ b/src/tools/anoperc.in @@ -0,0 +1,137 @@ +#!/bin/sh +# +# Configuration script for Services +# +# (C) 2003-2022 Anope Team +# Contact us at team@anope.org +# +# Please read COPYING and README for further details. +# +# Based on the original code of Epona by Lara. +# Based on the original code of Services by Andy Church. +# +# + + + +ANOPEPID="@INSTDIR@/data/services.pid" +ANOPROG="@INSTDIR@/bin/services" +LOG="@INSTDIR@/logs/" +ARCVERSION="2" + +isAnopeRunning () { + if [ ! -f $ANOPEPID ] ; then + echo "Warning: Anope is not currently running" + exit 1 + fi + + PID=`cat $ANOPEPID` + kill -0 $PID 2>/dev/null + if [ $? -ne 0 ] ; then + echo "Warning: Anope is not currently running" + exit 1 + fi +} + +if [ ! -f $ANOPROG ] ; then + echo "Error: $ANOPROG cannot be accessed" + exit 1 +fi + +if [ "$UID" = "0" ] ; then + echo "######################################"; + echo "# Warning: Do NOT run Anope as root! #"; + echo "######################################"; + exit 1 +fi + +if [ "$1" = "start" ] ; then + if [ -f $ANOPEPID ] ; then + PID=`cat $ANOPEPID` + kill -0 $PID 2>/dev/null + if [ $? -eq 0 ] ; then + echo "Warning! Anope is already running" + exit 1 + fi + fi + + echo "Starting Anope" + shift + $ANOPROG $* + + if [ "$?" -ne "0" ] ; then + echo "" + echo "Unfortunately it seems Anope did not start successfully" + echo "This error has been logged in your Anope Log file" + echo "Located in "$LOG"" + echo "This may help you diagnose the problem" + echo "Further help may be available from https://www.anope.org/" + exit 1 + fi + +elif [ "$1" = "stop" ] ; then + isAnopeRunning + echo "Terminating Anope" + kill -15 `cat $ANOPEPID` + +elif [ "$1" = "status" ] ; then + if [ -f $ANOPEPID ] ; then + PID=`cat $ANOPEPID` + kill -0 $PID 2>/dev/null + if [ $? -eq 0 ] ; then + echo "Anope is currently running" + exit 0 + fi + fi + + echo "Anope is not currently running" + +elif [ "$1" = "restart" ] ; then + isAnopeRunning + echo "Restarting Anope" + kill -15 `cat $ANOPEPID` + sleep 1 + + shift + $ANOPROG $* + + if [ "$?" -ne "0" ] ; then + echo "" + echo "Unfortunately it seems Anope did not start successfully" + echo "This error has been logged in your Anope Log file" + echo "Located in "$LOG"" + echo "This may help you diagnose the problem" + echo "Further help may be available from https://www.anope.org/" + exit 1 + fi + +elif [ "$1" = "rehash" ] ; then + isAnopeRunning + echo "Saving Databases and Rehashing Configuration" + kill -1 `cat $ANOPEPID` + +elif [ "$1" = "version" ] ; then + $ANOPROG -version + +elif [ "$1" = "help" ] ; then + if [ "$2" = "paramlist" ] ; then + $ANOPROG -help + else + echo "AnopeRC is a remote control script for easy" + echo "controlling of Anope from the command console" + echo "$0 start Start Anope." + echo "$0 stop Shutdown Anope" + echo "$0 status Show Anope's Status" + echo "$0 restart Restart Anope (Databases will be saved)." + echo "$0 rehash Rehash Configuration and Save Databases" + echo "$0 version Return Anope Version and Build Information" + echo "$0 help Show this help menu" + echo "If you need further help please check the /docs/" + echo "folder or make use of our extensive online support at" + echo "https://www.anope.org/" + fi + +else + echo "Anope Remote Control ($ARCVERSION)" + echo "Usage: $0 [start|stop|status|restart|rehash|version|help]" +fi diff --git a/src/tools/anopesmtp.cpp b/src/tools/anopesmtp.cpp new file mode 100644 index 0000000..358d55a --- /dev/null +++ b/src/tools/anopesmtp.cpp @@ -0,0 +1,535 @@ +/* smtp stuff handler for win32. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + * + * Written by Dominick Meglio + * *nix port by Trystan Scott Lee + */ + +#include "sysconf.h" + +/* Some Linux boxes (or maybe glibc includes) require this for the + * prototype of strsignal(). */ +#ifndef _GNU_SOURCE +# define _GNU_SOURCE +#endif + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#ifndef _WIN32 +# include +# include +# include +# include +# include +# include +#else +# include +# define WIN32_LEAN_AND_MEAN +# include +#endif + +#include + +#ifdef _AIX +extern int strcasecmp(const char *, const char *); +extern int strncasecmp(const char *, const char *, size_t); +# if 0 /* These break on some AIX boxes (4.3.1 reported). */ +extern int socket(int, int, int); +extern int connect(int, struct sockaddr *, int); +# endif +#endif /* _AIX */ + +/* Some SUN fixs */ +#ifdef __sun +/* Solaris specific code, types that do not exist in Solaris' + * * sys/types.h + * **/ +# ifndef INADDR_NONE +# define INADDR_NONE (-1) +# endif +#endif + +#ifdef _WIN32 +typedef SOCKET ano_socket_t; +#define ano_sockclose(fd) closesocket(fd) +#define ano_sockread(fd, buf, len) recv(fd, buf, len, 0) +#define ano_sockwrite(fd, buf, len) send(fd, buf, len, 0) +#else +typedef int ano_socket_t; +#define ano_sockclose(fd) close(fd) +#define ano_sockread(fd, buf, len) read(fd, buf, len) +#define ano_sockwrite(fd, buf, len) write(fd, buf, len) +#define SOCKET_ERROR -1 +#endif + +/* Data structures */ +struct smtp_message +{ + std::vector smtp_headers; + std::vector smtp_body; + std::string from; + std::string to; + ano_socket_t sock; +}; + +int smtp_debug = 0; + +struct smtp_message smail; + +static std::string get_logname(struct tm *tm = NULL) +{ + char timestamp[32]; + + if (!tm) + { + time_t t = time(NULL); + tm = localtime(&t); + } + + strftime(timestamp, sizeof(timestamp), "%Y%m%d", tm); + std::string name = std::string("anopesmtp.") + timestamp; + return name; +} + +/* TimeStamp for Email Header */ +static std::string GetTimeStamp() +{ + char tbuf[256]; + time_t t = time(NULL); + struct tm *tm = gmtime(&t); + + strftime(tbuf, sizeof(tbuf) - 1, "%a, %d %b %Y %H:%M:%S +0000", tm); + + return tbuf; +} + +/* Log stuff to the log file with a datestamp. Note that errno is + * preserved by this routine and log_perror(). + */ + +void alog(const char *fmt, ...) +{ + if (!smtp_debug || !fmt) + return; + + std::fstream file; + file.open(get_logname().c_str(), std::ios_base::out | std::ios_base::app); + + if (!file.is_open()) + return; + + va_list args; + va_start(args, fmt); + + time_t t = time(NULL); + struct tm *tm = localtime(&t); + + char buf[256]; + strftime(buf, sizeof(buf) - 1, "[%b %d %H:%M:%S %Y] ", tm); + file << buf; + vsnprintf(buf, sizeof(buf), fmt, args); + file << buf << std::endl; + va_end(args); + va_end(args); + + file.close(); +} + +/* Remove a trailing \r\n */ +std::string strip(const std::string &buf) +{ + std::string newbuf = buf; + char c = newbuf[newbuf.size() - 1]; + while (c == '\n' || c == '\r') + { + newbuf.erase(newbuf.end() - 1); + c = newbuf[newbuf.size() - 1]; + } + return newbuf; +} + +/* Is the buffer a header? */ +bool smtp_is_header(const std::string &buf) +{ + size_t tmp = buf.find(' '); + + if (tmp == std::string::npos) + return false; + + if (tmp > 0 && buf[tmp - 1] == ':') + return true; + return false; +} + +/* Parse a header into a name and value */ +void smtp_parse_header(const std::string &buf, std::string &header, std::string &value) +{ + std::string newbuf = strip(buf); + + size_t space = newbuf.find(' '); + if (space != std::string::npos) + { + header = newbuf.substr(0, space); + value = newbuf.substr(space + 1); + } + else + { + header = newbuf; + value = ""; + } +} + +/* Have we reached the end of input? */ +bool smtp_is_end(const std::string &buf) +{ + if (buf[0] == '.') + if (buf[1] == '\r' || buf[1] == '\n') + return true; + + return false; +} + +/* Set who the email is to */ +void smtp_set_to(const std::string &to) +{ + smail.to = to; + size_t c = smail.to.rfind('<'); + if (c != std::string::npos && c + 1 < smail.to.size()) + { + smail.to = smail.to.substr(c + 1); + smail.to.erase(smail.to.end() - 1); + } +} + +/* Establish a connection to the SMTP server */ +int smtp_connect(const char *host, unsigned short port) +{ + struct sockaddr_in addr; + + if ((smail.sock = socket(AF_INET, SOCK_STREAM, 0)) == SOCKET_ERROR) + return 0; + + if ((addr.sin_addr.s_addr = inet_addr(host)) == INADDR_NONE) + { + struct hostent *hent; + if (!(hent = gethostbyname(host))) + return 0; + memcpy(&addr.sin_addr, hent->h_addr, hent->h_length); + } + addr.sin_family = AF_INET; + addr.sin_port = htons(port ? port : 25); + if (connect(smail.sock, reinterpret_cast(&addr), sizeof(struct sockaddr_in)) == SOCKET_ERROR) + { + ano_sockclose(smail.sock); + return 0; + } + + return 1; +} + +/* Send a line of text */ +int smtp_send(const char *text) +{ + int result = ano_sockwrite(smail.sock, text, strlen(text)); + + alog("SMTP: sent %s",text); + + if (result == SOCKET_ERROR) + ano_sockclose(smail.sock); + + return result; +} + +/* Read a line of text */ +int smtp_read(char *buf, int len) +{ + int result; + + memset(buf, 0, len); + result = ano_sockread(smail.sock, buf, len); + + if (result == SOCKET_ERROR) + ano_sockclose(smail.sock); + + return result; +} + +/* Retrieve a response code */ +int smtp_get_code(const std::string &text) +{ + size_t tmp = text.find(' '); + + if (tmp == std::string::npos) + return 0; + + return atol(text.substr(0, tmp).c_str()); +} + +/* Send the email */ +int smtp_send_email() +{ + char buf[1024]; + if (!smtp_read(buf, 1024)) + { + alog("SMTP: error reading buffer"); + return 0; + } + + int code = smtp_get_code(buf); + if (code != 220) + { + alog("SMTP: error expected code 220 got %d",code); + return 0; + } + + if (!smtp_send("HELO anope\r\n")) + { + alog("SMTP: error writing to socket"); + return 0; + } + + if (!smtp_read(buf, 1024)) + { + alog("SMTP: error reading buffer"); + return 0; + } + + code = smtp_get_code(buf); + if (code != 250) + { + alog("SMTP: error expected code 250 got %d",code); + return 0; + } + + strcpy(buf, "MAIL FROM: <"); + strcat(buf, smail.from.c_str()); + strcat(buf, ">\r\n"); + + if (!smtp_send(buf)) + { + alog("SMTP: error writing to socket"); + return 0; + } + + if (!smtp_read(buf, 1024)) + { + alog("SMTP: error reading buffer"); + return 0; + } + + code = smtp_get_code(buf); + if (code != 250) + return 0; + + strcpy(buf, "RCPT TO: <"); + strcat(buf, smail.to.c_str()); + strcat(buf, ">\r\n"); + + if (!smtp_send(buf)) + { + alog("SMTP: error writing to socket"); + return 0; + } + + if (!smtp_read(buf, 1024)) + { + alog("SMTP: error reading buffer"); + return 0; + } + + code = smtp_get_code(buf); + if (smtp_get_code(buf) != 250) + { + alog("SMTP: error expected code 250 got %d",code); + return 0; + } + + if (!smtp_send("DATA\r\n")) + { + alog("SMTP: error writing to socket"); + return 0; + } + + if (!smtp_read(buf, 1024)) + { + alog("SMTP: error reading buffer"); + return 0; + } + + code = smtp_get_code(buf); + if (code != 354) + { + alog("SMTP: error expected code 354 got %d",code); + return 0; + } + + for (std::vector::const_iterator it = smail.smtp_headers.begin(), it_end = smail.smtp_headers.end(); it != it_end; ++it) + if (!smtp_send(it->c_str())) + { + alog("SMTP: error writing to socket"); + return 0; + } + + if (!smtp_send("\r\n")) + { + alog("SMTP: error writing to socket"); + return 0; + } + + bool skip_done = false; + for (std::vector::const_iterator it = smail.smtp_body.begin(), it_end = smail.smtp_body.end(); it != it_end; ++it) + if (skip_done) + { + if (!smtp_send(it->c_str())) + { + alog("SMTP: error writing to socket"); + return 0; + } + } + else + skip_done = true; + + if (!smtp_send("\r\n.\r\n")) + { + alog("SMTP: error writing to socket"); + return 0; + } + + if (!smtp_read(buf, 1024)) + { + alog("SMTP: error reading buffer"); + return 0; + } + + code = smtp_get_code(buf); + if (code != 250) + { + alog("SMTP: error expected code 250 got %d",code); + return 0; + } + + return 1; +} + +void smtp_disconnect() +{ + char buf[1024]; + + if (!smtp_send("QUIT\r\n")) + { + alog("SMTP: error writing to socket"); + } + + if (!smtp_read(buf, 1024)) + { + alog("SMTP: error reading buffer"); + } + + int code = smtp_get_code(buf); + if (code != 221) + { + alog("SMTP: error expected code 221 got %d",code); + } + + ano_sockclose(smail.sock); +} + +int main(int argc, char *argv[]) +{ + /* Win32 stuff */ +#ifdef _WIN32 + WSADATA wsa; +#endif + + if (argc == 1) + return 0; + + if (argc == 3 && !strcmp(argv[2], "--debug")) + smtp_debug = 1; + + char *server = strtok(argv[1], ":"), *aport; + short port; + if ((aport = strtok(NULL, ""))) + port = atoi(aport); + else + port = 25; + + if (!server) + { + alog("No Server"); + /* Bad, bad, bad. This was a return from main with no value! -GD */ + return 0; + } + else + alog("SMTP: server %s port %d",server,port); + + /* The WSAStartup function initiates use of WS2_32.DLL by a process. */ + /* guessing we can skip it under *nix */ +#ifdef _WIN32 + if (WSAStartup(MAKEWORD(1, 1), &wsa)) + return 0; +#endif + + char buf[8192]; + bool headers_done = false; + /* Read the message and parse it */ + while (fgets(buf, 8192, stdin)) + { + if (smtp_is_header(buf) && !headers_done) + { + smail.smtp_headers.push_back(strip(buf) + "\r\n"); + std::string header, value; + smtp_parse_header(buf, header, value); + if (header == "From:") + { + alog("SMTP: from: %s", value.c_str()); + smail.from = value; + } + else if (header == "To:") + { + alog("SMTP: to: %s", value.c_str()); + smtp_set_to(value); + } + else if (smtp_is_end(buf)) + break; + else + { + smail.smtp_headers.push_back("Date: " + GetTimeStamp() + "\r\n"); + headers_done = true; + smail.smtp_body.push_back(strip(buf) + "\r\n"); + } + } + else + smail.smtp_body.push_back(strip(buf) + "\r\n"); + } + + if (!smtp_connect(server, port)) + { + alog("SMTP: failed to connect to %s:%d", server, port); + return 0; + } + if (!smtp_send_email()) + { + alog("SMTP: error during sending of mail"); + return 0; + } + smtp_disconnect(); + + return 1; +} diff --git a/src/tools/geoipupdate.sh b/src/tools/geoipupdate.sh new file mode 100755 index 0000000..5e6d987 --- /dev/null +++ b/src/tools/geoipupdate.sh @@ -0,0 +1,81 @@ +#!/bin/bash + +# This script is a helper script for the irc2sql module. +# It downloads the configured geoip databases and inserts +# them into existing mysql tables. The tables are created +# by the irc2sql module on the first load. + +# Don't forget to rename this file or your changes +# will be overwritten on the next 'make install' + +############################ +# Config +############################ + + +geoip_database="country" # available options: "country" and "city" +mysql_host="localhost" +mysql_user="anope" +mysql_password="anope" +mysql_database="anope" +prefix="anope_" +die="yes" + +########################### + +# The GeoIP data is created by MaxMind, available from www.maxmind.com. +geoip_country_source="https://geolite.maxmind.com/download/geoip/database/GeoIPCountryCSV.zip" +geoip_city_source="https://geolite.maxmind.com/download/geoip/database/GeoLiteCity_CSV/GeoLiteCity-latest.zip" +geoip_region_source="https://www.maxmind.com/download/geoip/misc/region_codes.csv" + +########################### +LOGIN="--host=$mysql_host --user=$mysql_user --password=$mysql_password $mysql_database" +PARAMS="--delete --local --fields-terminated-by=, --fields-enclosed-by=\" --lines-terminated-by=\n $LOGIN" + +download() { + local url=$1 + local desc=$2 + echo -n " $desc " + wget --progress=dot $url 2>&1 | grep --line-buffered "%" | sed -u -e "s,\.,,g" | awk '{printf("\b\b\b\b%4s", $2)}' + echo -ne " Done\n" +} + + +if test $die = "yes"; then + echo "You have to edit and configure this script first." + exit +fi + + +if test $geoip_database = "country"; then + echo "Downloading..." + download "$geoip_country_source" "Country Database:" + echo "Unpacking..." + unzip -jo GeoIPCountryCSV.zip + rm GeoIPCountryCSV.zip + echo "Converting to UTF-8..." + iconv -f ISO-8859-1 -t UTF-8 GeoIPCountryWhois.csv -o $prefix"geoip_country.csv" + rm GeoIPCountryWhois.csv + echo "Importing..." + mysqlimport --columns=@x,@x,start,end,countrycode,countryname $PARAMS $prefix"geoip_country.csv" + rm $prefix"geoip_country.csv" $prefix"geoip_country6.csv" + echo "Done..." +elif test $geoip_database = "city"; then + echo "Downloading..." + download "$geoip_city_source" "City Database:" + download "$geoip_region_source" "Region Database:" + echo "Unpacking..." + unzip -jo GeoLiteCity-latest.zip + rm GeoLiteCity-latest.zip + echo "Converting to utf-8..." + iconv -f ISO-8859-1 -t UTF-8 GeoLiteCity-Blocks.csv -o $prefix"geoip_city_blocks.csv" + iconv -f ISO-8859-1 -t UTF-8 GeoLiteCity-Location.csv -o $prefix"geoip_city_location.csv" + iconv -f ISO-8859-1 -t UTF-8 region.csv -o $prefix"geoip_city_region.csv" + rm GeoLiteCity-Blocks.csv GeoLiteCity-Location.csv region.csv + echo "Importing..." + mysqlimport --columns=start,end,locID --ignore-lines=2 $PARAMS $prefix"geoip_city_blocks.csv" + mysqlimport --columns=locID,country,region,city,@x,latitude,longitude,@x,areaCode --ignore-lines=2 $PARAMS $prefix"geoip_city_location.csv" + mysqlimport --columns=country,region,regionname $PARAMS $prefix"geoip_city_region.csv" + rm $prefix"geoip_city_blocks.csv" $prefix"geoip_city_location.csv" $prefix"geoip_city_region.csv" $prefix"geoip_country6.csv" + echo "Done..." +fi diff --git a/src/uplink.cpp b/src/uplink.cpp new file mode 100644 index 0000000..03d8d99 --- /dev/null +++ b/src/uplink.cpp @@ -0,0 +1,212 @@ +/* + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "uplink.h" +#include "logger.h" +#include "config.h" +#include "protocol.h" +#include "servers.h" + +UplinkSocket *UplinkSock = NULL; + +class ReconnectTimer : public Timer +{ + public: + ReconnectTimer(int wait) : Timer(wait) { } + + void Tick(time_t) + { + try + { + Uplink::Connect(); + } + catch (const SocketException &ex) + { + Log(LOG_TERMINAL) << "Unable to connect to uplink #" << (Anope::CurrentUplink + 1) << " (" << Config->Uplinks[Anope::CurrentUplink].host << ":" << Config->Uplinks[Anope::CurrentUplink].port << "): " << ex.GetReason(); + } + } +}; + +void Uplink::Connect() +{ + if (Config->Uplinks.empty()) + { + Log() << "Warning: There are no configured uplinks."; + return; + } + + if (static_cast(++Anope::CurrentUplink) >= Config->Uplinks.size()) + Anope::CurrentUplink = 0; + + Configuration::Uplink &u = Config->Uplinks[Anope::CurrentUplink]; + + new UplinkSocket(); + if (!Config->GetBlock("serverinfo")->Get("localhost").empty()) + UplinkSock->Bind(Config->GetBlock("serverinfo")->Get("localhost")); + FOREACH_MOD(OnPreServerConnect, ()); + Anope::string ip = Anope::Resolve(u.host, u.ipv6 ? AF_INET6 : AF_INET); + Log(LOG_TERMINAL) << "Attempting to connect to uplink #" << (Anope::CurrentUplink + 1) << " " << u.host << " (" << ip << '/' << u.port << ") with protocol " << IRCD->GetProtocolName(); + UplinkSock->Connect(ip, u.port); +} + +UplinkSocket::UplinkSocket() : Socket(-1, Config->Uplinks[Anope::CurrentUplink].ipv6), ConnectionSocket(), BufferedSocket() +{ + error = false; + UplinkSock = this; +} + +UplinkSocket::~UplinkSocket() +{ + if (!error && !Anope::Quitting) + { + this->OnError(""); + Module *protocol = ModuleManager::FindFirstOf(PROTOCOL); + if (protocol && !protocol->name.find("inspircd")) + Log(LOG_TERMINAL) << "Check that you have loaded m_spanningtree.so on InspIRCd, and are not connecting Anope to an SSL enabled port without configuring SSL in Anope (or vice versa)"; + else + Log(LOG_TERMINAL) << "Check that you are not connecting Anope to an SSL enabled port without configuring SSL in Anope (or vice versa)"; + } + + if (IRCD && Servers::GetUplink() && Servers::GetUplink()->IsSynced()) + { + FOREACH_MOD(OnServerDisconnect, ()); + + for (user_map::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) + { + User *u = it->second; + + if (u->server == Me) + { + /* Don't use quitmsg here, it may contain information you don't want people to see */ + IRCD->SendQuit(u, "Shutting down"); + BotInfo* bi = BotInfo::Find(u->GetUID()); + if (bi != NULL) + bi->introduced = false; + } + } + + IRCD->SendSquit(Me, Anope::QuitReason); + } + + for (unsigned i = Me->GetLinks().size(); i > 0; --i) + if (!Me->GetLinks()[i - 1]->IsJuped()) + Me->GetLinks()[i - 1]->Delete(Me->GetName() + " " + Me->GetLinks()[i - 1]->GetName()); + + this->ProcessWrite(); // Write out the last bit + UplinkSock = NULL; + + Me->Unsync(); + + if (Anope::AtTerm()) + { + if (static_cast(Anope::CurrentUplink + 1) == Config->Uplinks.size()) + { + Anope::QuitReason = "Unable to connect to any uplink"; + Anope::Quitting = true; + Anope::ReturnValue = -1; + } + else + { + new ReconnectTimer(1); + } + } + else if (!Anope::Quitting) + { + time_t retry = Config->GetBlock("options")->Get("retrywait"); + + Log() << "Disconnected, retrying in " << retry << " seconds"; + new ReconnectTimer(retry); + } +} + +bool UplinkSocket::ProcessRead() +{ + bool b = BufferedSocket::ProcessRead(); + for (Anope::string buf; (buf = this->GetLine()).empty() == false;) + { + Anope::Process(buf); + User::QuitUsers(); + Channel::DeleteChannels(); + } + return b; +} + +void UplinkSocket::OnConnect() +{ + Log(LOG_TERMINAL) << "Successfully connected to uplink #" << (Anope::CurrentUplink + 1) << " " << Config->Uplinks[Anope::CurrentUplink].host << ":" << Config->Uplinks[Anope::CurrentUplink].port; + IRCD->SendConnect(); + FOREACH_MOD(OnServerConnect, ()); +} + +void UplinkSocket::OnError(const Anope::string &err) +{ + Anope::string what = !this->flags[SF_CONNECTED] ? "Unable to connect to" : "Lost connection from"; + Log(LOG_TERMINAL) << what << " uplink #" << (Anope::CurrentUplink + 1) << " (" << Config->Uplinks[Anope::CurrentUplink].host << ":" << Config->Uplinks[Anope::CurrentUplink].port << ")" << (!err.empty() ? (": " + err) : ""); + error |= !err.empty(); +} + +UplinkSocket::Message::Message() : source(Me) +{ +} + +UplinkSocket::Message::Message(const MessageSource &src) : source(src) +{ +} + +UplinkSocket::Message::~Message() +{ + Anope::string message_source; + + if (this->source.GetServer() != NULL) + { + const Server *s = this->source.GetServer(); + + if (s != Me && !s->IsJuped()) + { + Log(LOG_DEBUG) << "Attempted to send \"" << this->buffer.str() << "\" from " << s->GetName() << " who is not from me?"; + return; + } + + message_source = s->GetSID(); + } + else if (this->source.GetUser() != NULL) + { + const User *u = this->source.GetUser(); + + if (u->server != Me && !u->server->IsJuped()) + { + Log(LOG_DEBUG) << "Attempted to send \"" << this->buffer.str() << "\" from " << u->nick << " who is not from me?"; + return; + } + + const BotInfo *bi = this->source.GetBot(); + if (bi != NULL && bi->introduced == false) + { + Log(LOG_DEBUG) << "Attempted to send \"" << this->buffer.str() << "\" from " << bi->nick << " when not introduced"; + return; + } + + message_source = u->GetUID(); + } + + if (!UplinkSock) + { + if (!message_source.empty()) + Log(LOG_DEBUG) << "Attempted to send \"" << message_source << " " << this->buffer.str() << "\" with UplinkSock NULL"; + else + Log(LOG_DEBUG) << "Attempted to send \"" << this->buffer.str() << "\" with UplinkSock NULL"; + return; + } + + Anope::string sent = IRCD->Format(message_source, this->buffer.str()); + UplinkSock->Write(sent); + Log(LOG_RAWIO) << "Sent: " << sent; +} diff --git a/src/users.cpp b/src/users.cpp new file mode 100644 index 0000000..67612a6 --- /dev/null +++ b/src/users.cpp @@ -0,0 +1,846 @@ +/* Routines to maintain a list of online users. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "modules.h" +#include "users.h" +#include "account.h" +#include "protocol.h" +#include "servers.h" +#include "channels.h" +#include "bots.h" +#include "config.h" +#include "opertype.h" +#include "language.h" +#include "sockets.h" +#include "uplink.h" + +user_map UserListByNick, UserListByUID; + +int OperCount = 0; +unsigned MaxUserCount = 0; +time_t MaxUserTime = 0; + +std::list User::quitting_users; + +User::User(const Anope::string &snick, const Anope::string &sident, const Anope::string &shost, const Anope::string &svhost, const Anope::string &uip, Server *sserver, const Anope::string &srealname, time_t ts, const Anope::string &smodes, const Anope::string &suid, NickCore *account) : ip(uip) +{ + if (snick.empty() || sident.empty() || shost.empty()) + throw CoreException("Bad args passed to User::User"); + + /* we used to do this by calloc, no more. */ + quit = false; + server = NULL; + invalid_pw_count = invalid_pw_time = lastmemosend = lastnickreg = lastmail = 0; + on_access = false; + + this->nick = snick; + this->ident = sident; + this->host = shost; + this->vhost = svhost; + this->chost = svhost; + this->server = sserver; + this->realname = srealname; + this->timestamp = this->signon = ts; + this->SetModesInternal(sserver, "%s", smodes.c_str()); + this->uid = suid; + this->super_admin = false; + this->nc = NULL; + + size_t old = UserListByNick.size(); + UserListByNick[snick] = this; + if (!suid.empty()) + UserListByUID[suid] = this; + if (old == UserListByNick.size()) + Log(LOG_DEBUG) << "Duplicate user " << snick << " in user table?"; + + this->Login(account); + this->UpdateHost(); + + if (sserver) // Our bots are introduced on startup with no server + { + ++sserver->users; + if (server->IsSynced()) + Log(this, "connect") << (!vhost.empty() && vhost != host ? "(" + vhost + ") " : "") << "(" << srealname << ") " << (!uip.empty() && uip != host ? "[" + uip + "] " : "") << "connected to the network (" << sserver->GetName() << ")"; + } + + if (UserListByNick.size() > MaxUserCount) + { + MaxUserCount = UserListByNick.size(); + MaxUserTime = Anope::CurTime; + if (sserver && sserver->IsSynced()) + Log(this, "maxusers") << "connected - new maximum user count: " << UserListByNick.size(); + } + + bool exempt = false; + if (server && server->IsULined()) + exempt = true; + FOREACH_MOD(OnUserConnect, (this, exempt)); +} + +static void CollideKill(User *target, const Anope::string &reason) +{ + if (target->server != Me) + target->Kill(Me, reason); + else + { + // Be sure my user is really dead + IRCD->SendQuit(target, "%s", reason.c_str()); + + // Reintroduce my client + if (BotInfo *bi = dynamic_cast(target)) + bi->OnKill(); + else + target->Quit(reason); + } +} + +static void Collide(User *u, const Anope::string &id, const Anope::string &type) +{ + // Kill incoming user + IRCD->SendKill(Me, id, type); + // Quit colliding user + CollideKill(u, type); +} + +User* User::OnIntroduce(const Anope::string &snick, const Anope::string &sident, const Anope::string &shost, const Anope::string &svhost, const Anope::string &sip, Server *sserver, const Anope::string &srealname, time_t ts, const Anope::string &smodes, const Anope::string &suid, NickCore *nc) +{ + // How IRCds handle collisions varies a lot, for safety well just always kill both sides + // With properly set qlines, this can almost never happen anyway + + User *u = User::Find(snick, true); + if (u) + { + Collide(u, !suid.empty() ? suid : snick, "Nick collision"); + return NULL; + } + + if (!suid.empty()) + { + u = User::Find(suid); + if (u) + { + Collide(u, suid, "ID collision"); + return NULL; + } + } + + return new User(snick, sident, shost, svhost, sip, sserver, srealname, ts, smodes, suid, nc); +} + +void User::ChangeNick(const Anope::string &newnick, time_t ts) +{ + /* Sanity check to make sure we don't segfault */ + if (newnick.empty()) + throw CoreException("User::ChangeNick() got a bad argument"); + + this->super_admin = false; + Log(this, "nick") << "(" << this->realname << ") changed nick to " << newnick; + + Anope::string old = this->nick; + this->timestamp = ts; + + if (this->nick.equals_ci(newnick)) + this->nick = newnick; + else + { + NickAlias *old_na = NickAlias::Find(this->nick); + if (old_na && (this->IsIdentified(true) || this->IsRecognized())) + old_na->last_seen = Anope::CurTime; + + UserListByNick.erase(this->nick); + + this->nick = newnick; + + User* &other = UserListByNick[this->nick]; + if (other) + { + CollideKill(this, "Nick collision"); + CollideKill(other, "Nick collision"); + return; + } + other = this; + + on_access = false; + NickAlias *na = NickAlias::Find(this->nick); + if (na) + on_access = na->nc->IsOnAccess(this); + + if (na && na->nc == this->Account()) + { + na->last_seen = Anope::CurTime; + this->UpdateHost(); + } + } + + FOREACH_MOD(OnUserNickChange, (this, old)); +} + +void User::SetDisplayedHost(const Anope::string &shost) +{ + if (shost.empty()) + throw CoreException("empty host? in MY services? it seems it's more likely than I thought."); + + this->vhost = shost; + + Log(this, "host") << "changed vhost to " << shost; + + FOREACH_MOD(OnSetDisplayedHost, (this)); + + this->UpdateHost(); +} + +const Anope::string &User::GetDisplayedHost() const +{ + if (!this->vhost.empty()) + return this->vhost; + else if (this->HasMode("CLOAK") && !this->GetCloakedHost().empty()) + return this->GetCloakedHost(); + else + return this->host; +} + +void User::SetCloakedHost(const Anope::string &newhost) +{ + if (newhost.empty()) + throw CoreException("empty host in User::SetCloakedHost"); + + chost = newhost; + + Log(this, "host") << "changed cloaked host to " << newhost; + + this->UpdateHost(); +} + +const Anope::string &User::GetCloakedHost() const +{ + return chost; +} + +const Anope::string &User::GetUID() const +{ + if (!this->uid.empty() && IRCD->RequiresID) + return this->uid; + else + return this->nick; +} + +void User::SetVIdent(const Anope::string &sident) +{ + this->vident = sident; + + Log(this, "ident") << "changed vident to " << sident; + + this->UpdateHost(); +} + +const Anope::string &User::GetVIdent() const +{ + if (!this->vident.empty()) + return this->vident; + else + return this->ident; +} + +void User::SetIdent(const Anope::string &sident) +{ + this->ident = sident; + + Log(this, "ident") << "changed real ident to " << sident; + + this->UpdateHost(); +} + +const Anope::string &User::GetIdent() const +{ + return this->ident; +} + +Anope::string User::GetMask() const +{ + return this->nick + "!" + this->ident + "@" + this->host; +} + +Anope::string User::GetDisplayedMask() const +{ + return this->nick + "!" + this->GetVIdent() + "@" + this->GetDisplayedHost(); +} + +void User::SetRealname(const Anope::string &srealname) +{ + if (srealname.empty()) + throw CoreException("realname empty in SetRealname"); + + this->realname = srealname; + NickAlias *na = NickAlias::Find(this->nick); + + if (na && (this->IsIdentified(true) || this->IsRecognized())) + na->last_realname = srealname; + + Log(this, "realname") << "changed realname to " << srealname; +} + +User::~User() +{ + UnsetExtensibles(); + + if (this->server != NULL) + { + if (this->server->IsSynced()) + Log(this, "disconnect") << "(" << this->realname << ") disconnected from the network (" << this->server->GetName() << ")"; + --this->server->users; + } + + FOREACH_MOD(OnPreUserLogoff, (this)); + + ModeManager::StackerDel(this); + this->Logout(); + + if (this->HasMode("OPER")) + --OperCount; + + while (!this->chans.empty()) + this->chans.begin()->second->chan->DeleteUser(this); + + UserListByNick.erase(this->nick); + if (!this->uid.empty()) + UserListByUID.erase(this->uid); + + FOREACH_MOD(OnPostUserLogoff, (this)); +} + +void User::SendMessage(BotInfo *source, const char *fmt, ...) +{ + va_list args; + char buf[BUFSIZE] = ""; + + const char *translated_message = Language::Translate(this, fmt); + + va_start(args, fmt); + vsnprintf(buf, BUFSIZE - 1, translated_message, args); + + this->SendMessage(source, Anope::string(buf)); + + va_end(args); +} + +void User::SendMessage(BotInfo *source, const Anope::string &msg) +{ + const char *translated_message = Language::Translate(this, msg.c_str()); + + /* Send privmsg instead of notice if: + * - UsePrivmsg is enabled + * - The user is not registered and NSDefMsg is enabled + * - The user is registered and has set /ns set msg on + */ + bool send_privmsg = Config->UsePrivmsg && ((!this->nc && Config->DefPrivmsg) || (this->nc && this->nc->HasExt("MSG"))); + sepstream sep(translated_message, '\n', true); + for (Anope::string tok; sep.GetToken(tok);) + { + if (send_privmsg) + IRCD->SendPrivmsg(source, this->GetUID(), "%s", tok.c_str()); + else + IRCD->SendNotice(source, this->GetUID(), "%s", tok.c_str()); + } +} + +void User::Identify(NickAlias *na) +{ + if (this->nick.equals_ci(na->nick)) + { + na->last_usermask = this->GetIdent() + "@" + this->GetDisplayedHost(); + na->last_realhost = this->GetIdent() + "@" + this->host; + na->last_realname = this->realname; + na->last_seen = Anope::CurTime; + } + + IRCD->SendLogin(this, na); + + this->Login(na->nc); + + FOREACH_MOD(OnNickIdentify, (this)); + + if (this->IsServicesOper()) + { + if (!this->nc->o->ot->modes.empty()) + { + this->SetModes(NULL, "%s", this->nc->o->ot->modes.c_str()); + this->SendMessage(NULL, "Changing your usermodes to \002%s\002", this->nc->o->ot->modes.c_str()); + UserMode *um = ModeManager::FindUserModeByName("OPER"); + if (um && !this->HasMode("OPER") && this->nc->o->ot->modes.find(um->mchar) != Anope::string::npos) + IRCD->SendOper(this); + } + if (IRCD->CanSetVHost && !this->nc->o->vhost.empty()) + { + this->SendMessage(NULL, "Changing your vhost to \002%s\002", this->nc->o->vhost.c_str()); + this->SetDisplayedHost(this->nc->o->vhost); + IRCD->SendVhost(this, "", this->nc->o->vhost); + } + } +} + + +void User::Login(NickCore *core) +{ + if (!core || core == this->nc) + return; + + this->Logout(); + this->nc = core; + core->users.push_back(this); + + this->UpdateHost(); + + if (this->server->IsSynced()) + Log(this, "account") << "is now identified as " << this->nc->display; + + FOREACH_MOD(OnUserLogin, (this)); +} + +void User::Logout() +{ + if (!this->nc) + return; + + Log(this, "account") << "is no longer identified as " << this->nc->display; + + std::list::iterator it = std::find(this->nc->users.begin(), this->nc->users.end(), this); + if (it != this->nc->users.end()) + this->nc->users.erase(it); + + this->nc = NULL; +} + +NickCore *User::Account() const +{ + return this->nc; +} + +bool User::IsIdentified(bool check_nick) const +{ + if (check_nick && this->nc) + { + NickAlias *na = NickAlias::Find(this->nick); + return na && *na->nc == *this->nc; + } + + return this->nc ? true : false; +} + +bool User::IsRecognized(bool check_secure) const +{ + if (check_secure && on_access) + { + const NickAlias *na = NickAlias::Find(this->nick); + + if (!na || na->nc->HasExt("NS_SECURE")) + return false; + } + + return on_access; +} + +bool User::IsServicesOper() +{ + if (!this->nc || !this->nc->IsServicesOper()) + // No opertype. + return false; + else if (this->nc->o->require_oper && !this->HasMode("OPER")) + return false; + else if (!this->nc->o->certfp.empty() && this->fingerprint != this->nc->o->certfp) + // Certfp mismatch + return false; + else if (!this->nc->o->hosts.empty()) + { + bool match = false; + Anope::string match_host = this->GetIdent() + "@" + this->host; + for (unsigned i = 0; i < this->nc->o->hosts.size(); ++i) + if (Anope::Match(match_host, this->nc->o->hosts[i])) + match = true; + if (match == false) + return false; + } + + EventReturn MOD_RESULT; + FOREACH_RESULT(IsServicesOper, MOD_RESULT, (this)); + if (MOD_RESULT == EVENT_STOP) + return false; + + return true; +} + +bool User::HasCommand(const Anope::string &command) +{ + if (this->IsServicesOper()) + return this->nc->o->ot->HasCommand(command); + return false; +} + +bool User::HasPriv(const Anope::string &priv) +{ + if (this->IsServicesOper()) + return this->nc->o->ot->HasPriv(priv); + return false; +} + +void User::UpdateHost() +{ + if (this->host.empty()) + return; + + NickAlias *na = NickAlias::Find(this->nick); + on_access = false; + if (na) + on_access = na->nc->IsOnAccess(this); + + if (na && (this->IsIdentified(true) || this->IsRecognized())) + { + Anope::string last_usermask = this->GetIdent() + "@" + this->GetDisplayedHost(); + Anope::string last_realhost = this->GetIdent() + "@" + this->host; + na->last_usermask = last_usermask; + na->last_realhost = last_realhost; + // This is called on signon, and if users are introduced with an account it won't update + na->last_realname = this->realname; + } +} + +bool User::HasMode(const Anope::string &mname) const +{ + return this->modes.count(mname); +} + +void User::SetModeInternal(const MessageSource &source, UserMode *um, const Anope::string ¶m) +{ + if (!um) + return; + + this->modes[um->name] = param; + + if (um->name == "OPER") + { + ++OperCount; + + if (this->IsServicesOper()) + { + if (!this->nc->o->ot->modes.empty()) + { + this->SetModes(NULL, "%s", this->nc->o->ot->modes.c_str()); + this->SendMessage(NULL, "Changing your usermodes to \002%s\002", this->nc->o->ot->modes.c_str()); + UserMode *oper = ModeManager::FindUserModeByName("OPER"); + if (oper && !this->HasMode("OPER") && this->nc->o->ot->modes.find(oper->mchar) != Anope::string::npos) + IRCD->SendOper(this); + } + if (IRCD->CanSetVHost && !this->nc->o->vhost.empty()) + { + this->SendMessage(NULL, "Changing your vhost to \002%s\002", this->nc->o->vhost.c_str()); + this->SetDisplayedHost(this->nc->o->vhost); + IRCD->SendVhost(this, "", this->nc->o->vhost); + } + } + } + + if (um->name == "CLOAK" || um->name == "VHOST") + this->UpdateHost(); + + FOREACH_MOD(OnUserModeSet, (source, this, um->name)); +} + +void User::RemoveModeInternal(const MessageSource &source, UserMode *um) +{ + if (!um) + return; + + this->modes.erase(um->name); + + if (um->name == "OPER") + { + --OperCount; + + // Don't let people de-oper and remain a SuperAdmin + this->super_admin = false; + } + + if (um->name == "CLOAK" || um->name == "VHOST") + { + this->vhost.clear(); + this->UpdateHost(); + } + + FOREACH_MOD(OnUserModeUnset, (source, this, um->name)); +} + +void User::SetMode(BotInfo *bi, UserMode *um, const Anope::string ¶m) +{ + if (!um || HasMode(um->name)) + return; + + ModeManager::StackerAdd(bi, this, um, true, param); + SetModeInternal(bi, um, param); +} + +void User::SetMode(BotInfo *bi, const Anope::string &uname, const Anope::string ¶m) +{ + SetMode(bi, ModeManager::FindUserModeByName(uname), param); +} + +void User::RemoveMode(BotInfo *bi, UserMode *um, const Anope::string ¶m) +{ + if (!um || !HasMode(um->name)) + return; + + ModeManager::StackerAdd(bi, this, um, false, param); + RemoveModeInternal(bi, um); +} + +void User::RemoveMode(BotInfo *bi, const Anope::string &name, const Anope::string ¶m) +{ + RemoveMode(bi, ModeManager::FindUserModeByName(name), param); +} + +void User::SetModes(BotInfo *bi, const char *umodes, ...) +{ + char buf[BUFSIZE] = ""; + va_list args; + Anope::string modebuf, sbuf; + int add = -1; + va_start(args, umodes); + vsnprintf(buf, BUFSIZE - 1, umodes, args); + va_end(args); + + spacesepstream sep(buf); + sep.GetToken(modebuf); + for (unsigned i = 0, end = modebuf.length(); i < end; ++i) + { + UserMode *um; + + switch (modebuf[i]) + { + case '+': + add = 1; + continue; + case '-': + add = 0; + continue; + default: + if (add == -1) + continue; + um = ModeManager::FindUserModeByChar(modebuf[i]); + if (!um) + continue; + } + + if (add) + { + if (um->type == MODE_PARAM && sep.GetToken(sbuf)) + this->SetMode(bi, um, sbuf); + else + this->SetMode(bi, um); + } + else + this->RemoveMode(bi, um); + } +} + +void User::SetModesInternal(const MessageSource &source, const char *umodes, ...) +{ + char buf[BUFSIZE] = ""; + va_list args; + Anope::string modebuf, sbuf; + int add = -1; + va_start(args, umodes); + vsnprintf(buf, BUFSIZE - 1, umodes, args); + va_end(args); + + if (this->server && this->server->IsSynced() && Anope::string(buf) != "+") + Log(this, "mode") << "changes modes to " << buf; + + spacesepstream sep(buf); + sep.GetToken(modebuf); + for (unsigned i = 0, end = modebuf.length(); i < end; ++i) + { + UserMode *um; + + switch (modebuf[i]) + { + case '+': + add = 1; + continue; + case '-': + add = 0; + continue; + default: + if (add == -1) + continue; + um = ModeManager::FindUserModeByChar(modebuf[i]); + if (!um) + continue; + } + + if (add) + { + if (um->type == MODE_PARAM && sep.GetToken(sbuf)) + this->SetModeInternal(source, um, sbuf); + else + this->SetModeInternal(source, um); + } + else + this->RemoveModeInternal(source, um); + } +} + +Anope::string User::GetModes() const +{ + Anope::string m, params; + + for (ModeList::const_iterator it = this->modes.begin(), it_end = this->modes.end(); it != it_end; ++it) + { + UserMode *um = ModeManager::FindUserModeByName(it->first); + if (um == NULL) + continue; + + m += um->mchar; + + if (!it->second.empty()) + params += " " + it->second; + } + + return m + params; +} + +const User::ModeList &User::GetModeList() const +{ + return modes; +} + +ChanUserContainer *User::FindChannel(Channel *c) const +{ + User::ChanUserList::const_iterator it = this->chans.find(c); + if (it != this->chans.end()) + return it->second; + return NULL; +} + +bool User::IsProtected() +{ + return this->HasMode("PROTECTED") || this->HasMode("GOD") || this->HasPriv("protected") || (this->server && this->server->IsULined()); +} + +void User::Kill(const MessageSource &source, const Anope::string &reason) +{ + Anope::string real_reason = source.GetName() + " (" + reason + ")"; + + IRCD->SendSVSKill(source, this, "%s", real_reason.c_str()); +} + +void User::KillInternal(const MessageSource &source, const Anope::string &reason) +{ + if (this->quit) + { + Log(LOG_DEBUG) << "Duplicate quit for " << this->nick; + return; + } + + Log(this, "killed") << "was killed by " << source.GetName() << " (Reason: " << reason << ")"; + + this->Quit(reason); +} + +void User::Quit(const Anope::string &reason) +{ + if (this->quit) + { + Log(LOG_DEBUG) << "Duplicate quit for " << this->nick; + return; + } + + FOREACH_MOD(OnUserQuit, (this, reason)); + + this->quit = true; + quitting_users.push_back(this); +} + +bool User::Quitting() const +{ + return this->quit; +} + +Anope::string User::Mask() const +{ + Anope::string mask; + const Anope::string &mident = this->GetIdent(); + const Anope::string &mhost = this->GetDisplayedHost(); + + if (mident[0] == '~') + mask = "*" + mident + "@"; + else + mask = mident + "@"; + + sockaddrs addr(mhost); + if (addr.valid() && addr.sa.sa_family == AF_INET) + { + size_t dot = mhost.rfind('.'); + mask += mhost.substr(0, dot) + (dot == Anope::string::npos ? "" : ".*"); + } + else + { + size_t dot = mhost.find('.'); + if (dot != Anope::string::npos && mhost.find('.', dot + 1) != Anope::string::npos) + mask += "*" + mhost.substr(dot); + else + mask += mhost; + } + + return mask; +} + +bool User::BadPassword() +{ + if (!Config->GetBlock("options")->Get("badpasslimit")) + return false; + + if (Config->GetBlock("options")->Get("badpasstimeout") > 0 && this->invalid_pw_time > 0 && this->invalid_pw_time < Anope::CurTime - Config->GetBlock("options")->Get("badpasstimeout")) + this->invalid_pw_count = 0; + ++this->invalid_pw_count; + this->invalid_pw_time = Anope::CurTime; + if (this->invalid_pw_count >= Config->GetBlock("options")->Get("badpasslimit")) + { + this->Kill(Me, "Too many invalid passwords"); + return true; + } + + return false; +} + +User* User::Find(const Anope::string &name, bool nick_only) +{ + if (!nick_only && IRCD && IRCD->RequiresID) + { + user_map::iterator it = UserListByUID.find(name); + if (it != UserListByUID.end()) + return it->second; + + if (IRCD->AmbiguousID) + return NULL; + } + + user_map::iterator it = UserListByNick.find(name); + if (it != UserListByNick.end()) + return it->second; + + return NULL; +} + +void User::QuitUsers() +{ + for (std::list::iterator it = quitting_users.begin(), it_end = quitting_users.end(); it != it_end; ++it) + delete *it; + quitting_users.clear(); +} diff --git a/src/version.sh b/src/version.sh new file mode 100644 index 0000000..08d819c --- /dev/null +++ b/src/version.sh @@ -0,0 +1,6 @@ +#!/bin/sh + +VERSION_MAJOR=2 +VERSION_MINOR=0 +VERSION_PATCH=12 +VERSION_EXTRA="" diff --git a/src/win32/Config.cs b/src/win32/Config.cs new file mode 100644 index 0000000..6c762c5 --- /dev/null +++ b/src/win32/Config.cs @@ -0,0 +1,363 @@ +/* + * Config.cs - Windows Configuration + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * This program is free but copyrighted software; see the file COPYING for + * details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + * + * Written by Scott + * Written by Adam + * Cleaned up by Naram Qashat + * + * Compile with: csc /out:../../Config.exe /win32icon:anope-icon.ico Config.cs + */ + +using System; +using System.Collections.Generic; +using System.Diagnostics; +using System.IO; +using System.Reflection; + +namespace Config +{ + class Config + { + static string ExecutablePath, InstallDirectory, ExtraIncludeDirs, ExtraLibDirs, ExtraArguments; + static bool UseNMake = true, BuildDebug = false; + + static bool CheckResponse(string InstallerResponse) + { + if (string.Compare(InstallerResponse, "yes", true) == 0 || string.Compare(InstallerResponse, "y", true) == 0) + return true; + return false; + } + + static bool LoadCache() + { + try + { + string[] cache = File.ReadAllLines(string.Format(@"{0}\config.cache", ExecutablePath)); + if (cache.Length > 0) + Console.WriteLine("Using defaults from config.cache"); + foreach (string line in cache) + { + int e = line.IndexOf('='); + string name = line.Substring(0, e); + string value = line.Substring(e + 1); + + if (name == "INSTDIR") + InstallDirectory = value; + else if (name == "DEBUG") + BuildDebug = CheckResponse(value); + else if (name == "USENMAKE") + UseNMake = CheckResponse(value); + else if (name == "EXTRAINCLUDE") + ExtraIncludeDirs = value; + else if (name == "EXTRALIBS") + ExtraLibDirs = value; + else if (name == "EXTRAARGS") + ExtraArguments = value; + } + + return true; + } + catch (Exception) + { + } + + return false; + } + + static void SaveCache() + { + using (TextWriter tw = new StreamWriter(string.Format(@"{0}\config.cache", ExecutablePath))) + { + tw.WriteLine("INSTDIR={0}", InstallDirectory); + tw.WriteLine("DEBUG={0}", BuildDebug ? "yes" : "no"); + tw.WriteLine("USENMAKE={0}", UseNMake ? "yes" : "no"); + tw.WriteLine("EXTRAINCLUDE={0}", ExtraIncludeDirs); + tw.WriteLine("EXTRALIBS={0}", ExtraLibDirs); + tw.WriteLine("EXTRAARGS={0}", ExtraArguments); + } + } + + static string HandleCache(int i) + { + switch (i) + { + case 0: + Console.Write("[{0}] ", InstallDirectory); + return InstallDirectory; + case 1: + Console.Write("[{0}] ", UseNMake ? "yes" : "no"); + return UseNMake ? "yes" : "no"; + case 2: + Console.Write("[{0}] ", BuildDebug ? "yes" : "no"); + return BuildDebug ? "yes" : "no"; + case 3: + Console.Write("[{0}] ", ExtraIncludeDirs); + return ExtraIncludeDirs; + case 4: + Console.Write("[{0}] ", ExtraLibDirs); + return ExtraLibDirs; + case 5: + Console.Write("[{0}] ", ExtraArguments); + return ExtraArguments; + default: + break; + } + + return null; + } + + static string FindAnopeVersion() + { + if (!File.Exists(string.Format(@"{0}\src\version.sh", ExecutablePath))) + return "Unknown"; + + Dictionary versions = new Dictionary(); + string[] versionfile = File.ReadAllLines(string.Format(@"{0}\src\version.sh", ExecutablePath)); + foreach (string line in versionfile) + if (line.StartsWith("VERSION_")) + { + string key = line.Split('_')[1].Split('=')[0]; + if (!versions.ContainsKey(key)) + versions.Add(key, line.Split('=')[1].Replace("\"", "").Replace("\'", "")); + } + + try + { + if (versions.ContainsKey("BUILD")) + return string.Format("{0}.{1}.{2}.{3}{4}", versions["MAJOR"], versions["MINOR"], versions["PATCH"], versions["BUILD"], versions["EXTRA"]); + else + return string.Format("{0}.{1}.{2}{3}", versions["MAJOR"], versions["MINOR"], versions["PATCH"], versions["EXTRA"]); + } + catch (Exception e) + { + Console.WriteLine(e.Message); + return "Unknown"; + } + } + + static void RunCMake(string cMake) + { + Console.WriteLine("cmake {0}", cMake); + try + { + ProcessStartInfo processStartInfo = new ProcessStartInfo("cmake") + { + RedirectStandardError = true, + RedirectStandardOutput = true, + UseShellExecute = false, + Arguments = cMake + }; + Process pCMake = Process.Start(processStartInfo); + StreamReader stdout = pCMake.StandardOutput, stderr = pCMake.StandardError; + string stdoutr, stderrr; + List errors = new List(); + while (!pCMake.HasExited) + { + if ((stdoutr = stdout.ReadLine()) != null) + Console.WriteLine(stdoutr); + if ((stderrr = stderr.ReadLine()) != null) + errors.Add(stderrr); + } + foreach (string error in errors) + Console.WriteLine(error); + Console.WriteLine(); + if (pCMake.ExitCode == 0) + { + if (UseNMake) + Console.WriteLine("To compile Anope, run 'nmake'. To install, run 'nmake install'"); + else + Console.WriteLine("To compile Anope, open Anope.sln and build the solution. To install, do a build on the INSTALL project"); + } + else + Console.WriteLine("There was an error attempting to run CMake! Check the above error message, and contact the Anope team if you are unsure how to proceed."); + } + catch (Exception e) + { + Console.WriteLine(); + Console.WriteLine(DateTime.UtcNow + " UTC: " + e.Message); + Console.WriteLine("There was an error attempting to run CMake! Check the above error message, and contact the Anope team if you are unsure how to proceed."); + } + } + + static int Main(string[] args) + { + bool IgnoreCache = false, NoIntro = false, DoQuick = false; + + if (args.Length > 0) + { + if (args[0] == "--help") + { + Console.WriteLine("Config utility for Anope"); + Console.WriteLine("------------------------"); + Console.WriteLine("Syntax: .\\Config.exe [options]"); + Console.WriteLine("-nocache Ignore settings saved in config.cache"); + Console.WriteLine("-nointro Skip intro (disclaimer, etc)"); + Console.WriteLine("-quick or -q Skip questions, go straight to cmake"); + return 0; + } + else if (args[0] == "-nocache") + IgnoreCache = true; + else if (args[0] == "-nointro") + NoIntro = true; + else if (args[0] == "-quick" || args[0] == "-q") + DoQuick = true; + } + + ExecutablePath = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location); + + string AnopeVersion = FindAnopeVersion(); + + if (!NoIntro && File.Exists(string.Format(@"{0}\.BANNER", ExecutablePath))) + Console.WriteLine(File.ReadAllText(string.Format(@"{0}\.BANNER", ExecutablePath)).Replace("CURVER", AnopeVersion).Replace("For more options type SOURCE_DIR/Config --help", "")); + + Console.WriteLine("Press Enter to begin"); + Console.WriteLine(); + Console.ReadKey(); + + bool UseCache = false; + + if (DoQuick || !IgnoreCache) + { + UseCache = LoadCache(); + if (DoQuick && !UseCache) + { + Console.WriteLine("Can't find cache file (config.cache), aborting..."); + return 1; + } + } + + if (!DoQuick) + { + List InstallerQuestions = new List() + { + "Where do you want Anope to be installed?", + "Would you like to build using NMake instead of using Visual Studio?\r\nNOTE: If you decide to use NMake, you must be in an environment where\r\nNMake can function, such as the Visual Studio command line. If you say\r\nyes to this while not in an environment that can run NMake, it can\r\ncause the CMake configuration to enter an endless loop. [y/n]", + "Would you like to build a debug version of Anope? [y/n]", + "Are there any extra include directories you wish to use?\nYou may only need to do this if CMake is unable to locate missing dependencies without hints.\nSeparate directories with semicolons and use slashes (aka /) instead of backslashes (aka \\).\nIf you need no extra include directories, enter NONE in all caps.", + "Are there any extra library directories you wish to use?\nYou may only need to do this if CMake is unable to locate missing dependencies without hints.\nSeparate directories with semicolons and use slashes (aka /) instead of backslashes (aka \\).\nIf you need no extra library directories, enter NONE in all caps.", + "Are there any extra arguments you wish to pass to CMake?\nIf you need no extra arguments to CMake, enter NONE in all caps." + }; + + for (int i = 0; i < InstallerQuestions.Count; ++i) + { + Console.WriteLine(InstallerQuestions[i]); + string CacheResponse = null; + if (UseCache) + CacheResponse = HandleCache(i); + string InstallerResponse = Console.ReadLine(); + Console.WriteLine(); + + if (!string.IsNullOrWhiteSpace(CacheResponse) && string.IsNullOrWhiteSpace(InstallerResponse)) + InstallerResponse = CacheResponse; + + // Question 4+ are optional + if (i < 3 && string.IsNullOrWhiteSpace(InstallerResponse)) + { + Console.WriteLine("Invalid option"); + --i; + continue; + } + + switch (i) + { + case 0: + if (!Directory.Exists(InstallerResponse)) + { + Console.WriteLine("Directory does not exist! Creating directory."); + Console.WriteLine(); + try + { + Directory.CreateDirectory(InstallerResponse); + InstallDirectory = InstallerResponse; + } + catch (Exception e) + { + Console.WriteLine("Unable to create directory: " + e.Message); + --i; + } + } + else if (File.Exists(InstallerResponse + @"\include\services.h")) + { + Console.WriteLine("You cannot use the Anope source directory as the target directory!"); + --i; + } + else + InstallDirectory = InstallerResponse; + break; + case 1: + UseNMake = CheckResponse(InstallerResponse); + if (UseNMake) + ++i; + break; + case 2: + BuildDebug = CheckResponse(InstallerResponse); + break; + case 3: + if (InstallerResponse == "NONE") + ExtraIncludeDirs = null; + else + ExtraIncludeDirs = InstallerResponse; + break; + case 4: + if (InstallerResponse == "NONE") + ExtraLibDirs = null; + else + ExtraLibDirs = InstallerResponse; + break; + case 5: + if (InstallerResponse == "NONE") + ExtraArguments = null; + else + ExtraArguments = InstallerResponse; + break; + default: + break; + } + } + } + + Console.WriteLine("Anope will be compiled with the following options:"); + Console.WriteLine("Install directory: {0}", InstallDirectory); + Console.WriteLine("Use NMake: {0}", UseNMake ? "Yes" : "No"); + Console.WriteLine("Build debug: {0}", BuildDebug ? "Yes" : "No"); + Console.WriteLine("Anope Version: {0}", AnopeVersion); + Console.WriteLine("Extra Include Directories: {0}", ExtraIncludeDirs); + Console.WriteLine("Extra Library Directories: {0}", ExtraLibDirs); + Console.WriteLine("Extra Arguments: {0}", ExtraArguments); + Console.WriteLine("Press Enter to continue..."); + Console.ReadKey(); + + SaveCache(); + + if (!string.IsNullOrWhiteSpace(ExtraIncludeDirs)) + ExtraIncludeDirs = string.Format("-DEXTRA_INCLUDE:STRING={0} ", ExtraIncludeDirs); + else + ExtraIncludeDirs = ""; + if (!string.IsNullOrWhiteSpace(ExtraLibDirs)) + ExtraLibDirs = string.Format("-DEXTRA_LIBS:STRING={0} ", ExtraLibDirs); + else + ExtraLibDirs = ""; + if (!string.IsNullOrWhiteSpace(ExtraArguments)) + ExtraArguments += " "; + else + ExtraArguments = ""; + + InstallDirectory = "-DINSTDIR:STRING=\"" + InstallDirectory.Replace('\\', '/') + "\" "; + string NMake = UseNMake ? "-G\"NMake Makefiles\" " : ""; + string Debug = BuildDebug ? "-DCMAKE_BUILD_TYPE:STRING=DEBUG " : "-DCMAKE_BUILD_TYPE:STRING=RELEASE "; + string cMake = InstallDirectory + NMake + Debug + ExtraIncludeDirs + ExtraLibDirs + ExtraArguments + "\"" + ExecutablePath.Replace('\\', '/') + "\""; + RunCMake(cMake); + + return 0; + } + } +} diff --git a/src/win32/anope-icon.ico b/src/win32/anope-icon.ico new file mode 100644 index 0000000000000000000000000000000000000000..be735614a22a08899139a3dff760729e214cb933 GIT binary patch literal 3774 zcmc&$eOQ*|75{nGgq(>_yxB^$?yWVYbc!rD%A(fhvSGHZPouSIfCLDNh(Pcvf{c(* z837_8;0u|Vp{W@nDpRNA<@^9;D1@I==eL52yq)tr&nxiC)dhd;_PU>QpL74txz8uQ zKrj9`Vg&f>iqd|-002XHvk33-7WwzBC843n2?)U2g$rSenuf2^=AbGk4gV@wfF1c6 z_~+tuR4kl_RdZsI8yJ9!{Cs?sm4*C}U^H%6hNBgw_%bB{xj{k52@FI7%L>9murxdr zb*l?dl{+7wTVqhWY6VjPaFFT&RBG_>8i zh3zX=u+2c!tjt5vw5eDY9gQtnsi@3M!KJfj(Q@SqR;8q%FftNtZEeU44#r~MH(FY- zZqXuaNS}+H97Fw=OVLzb!oCGyWl|EBTdg=$_Awgv>_Ow#HhlJeH0stAU|U`~%0EoP zp7rZd8XbvGW25ljBS&!M+&L6a4@YrS6pkM}2s^)3Sx|sR)^ELW11An0Li6Rz*tj4W z^*eW>n0-Cn*a%xp47PFZN|;_|8|zYMqiJI)$5_lUet@ku8cT~+ zUt5TqY;zOaKY!{J%I3!5llXX?J8=S~GpFMk=j(Hh`Rm+V5l+cXp zXRzCrg$?r)@ol*c|1Ql&>&=@e3=hMuvNCKbD#96lr*8Xp96fLV*RNf}t=3kQXC%Qk zYZeM3B5-)uE-Ynw?czo3DftLrq^9DNm`JRMn~DE$Y->}jSecxRva~dm#KyulBLc^2 zYq4)dF3Q=bHOcX)t*YW$Ou@#yJe0)6p}Hs&x7d%Ct5>lmJsq34e(N$barMFlY{<^W zsrq{El`!o4G#3X~<)a`x9Gkh$%M%i~c7@-2*AchBqC&5;w$mSW4K9c^F9+3P? zt!1ucR-}hz?z+9)yN%R=7U~h6ruGOw($l9WcyH3Qp5TYP)f4<5S`M_c|I5h3)_&L3sZ+gZRB>0Bj7&XgbUYqBpM41$&X%r&pN9PlzGyRar!Z(lb1CI7%_7$Z@vM@#c zU7IAasyL$5i6qDAA2?>F-5u?@IUy>M<|>u+*5hPJ=H$#~E9{!+5|5$Xj%kKlY~;_op_I+DM|(VsrT5SknxNPl@Yb@LH$j4sI&cd{yLst z=DSIgwR?$1@bTS%djgrfsXV&Cdo$Xd-tbc7q4~eP-u$SBFgOh}Z6YX@VPz2feKRs8{#}rT#pDb)Mn88bkaF%?#~wE?wPC~f1zy8{(bpmBO!aw$ z@!x^m{OnPI|9l7y?Tj-yPqxl$@NJKJKlCv7x=r+}i($I%75NzB_(x^dh?JhrL}~U0q!C zj~rb2b9bK~^(DH;NKNN2t8}@3&=JPJf$a88kl#Xf`!fb@Gij?yTbyX4$vbGJ$y-ed zgSP3^%C9lsCXX_0HED}U8-+duR0?%#r&i%zfKJrm`TvpX{_y(_zbe72gWrw9b37M> Wa=dz+31-}O&M%9532kIGrr!Z3+e7pK literal 0 HcmV?d00001 diff --git a/src/win32/anope.bat b/src/win32/anope.bat new file mode 100644 index 0000000..20cebfa --- /dev/null +++ b/src/win32/anope.bat @@ -0,0 +1,3 @@ +@ECHO OFF +anope.exe %1 %2 %3 %4 %5 +pause \ No newline at end of file diff --git a/src/win32/anope_windows.h b/src/win32/anope_windows.h new file mode 100644 index 0000000..accf40e --- /dev/null +++ b/src/win32/anope_windows.h @@ -0,0 +1,81 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2011 Robin Burchell + * (C) 2008-2022 Anope Team + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifndef WINDOWS_H +#define WINDOWS_H +#ifdef _WIN32 + +#define NOMINMAX + +#include +#include +#include +#include +#include + +#ifdef MODULE_COMPILE +# define CoreExport __declspec(dllimport) +# define DllExport __declspec(dllexport) +#else +# define CoreExport __declspec(dllexport) +# define DllExport __declspec(dllimport) +#endif + +#define MARK_DEPRECATED + +#if GETTEXT_FOUND +/* Undefine some functions libintl defines */ +# undef snprintf +# undef vsnprintf +# undef printf +#endif + +#define snprintf _snprintf +/* VS2008 hates having this define before its own */ +#define vsnprintf _vsnprintf + +#define anope_close windows_close + +#define stat _stat +#define S_ISREG(x) ((x) & _S_IFREG) + +#ifdef EINPROGRESS +# undef EINPROGRESS +#endif +#define EINPROGRESS WSAEWOULDBLOCK + +#include "socket.h" +#include "dir/dir.h" +#include "dl/dl.h" +#include "pipe/pipe.h" +#include "pthread/pthread.h" +#include "sigaction/sigaction.h" + +typedef int ssize_t; + +namespace Anope +{ + class string; +} + +extern CoreExport void OnStartup(); +extern CoreExport void OnShutdown(); +extern CoreExport USHORT WindowsGetLanguage(const Anope::string &lang); +extern CoreExport int gettimeofday(timeval *tv, void *); +extern CoreExport Anope::string GetWindowsVersion(); +extern CoreExport bool SupportedWindowsVersion(); +extern int setenv(const char *name, const char *value, int overwrite); +extern int unsetenv(const char *name); +extern int mkstemp(char *input); +extern void getcwd(char *buf, size_t sz); + +#endif // _WIN32 +#endif // WINDOWS_H diff --git a/src/win32/dir/dir.cpp b/src/win32/dir/dir.cpp new file mode 100644 index 0000000..8c8cdf9 --- /dev/null +++ b/src/win32/dir/dir.cpp @@ -0,0 +1,48 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "dir.h" +#include + +DIR *opendir(const char *path) +{ + char real_path[MAX_PATH]; + _snprintf(real_path, sizeof(real_path), "%s/*", path); + + DIR *d = new DIR(); + d->handle = FindFirstFile(real_path, &d->data); + d->read_first = false; + + if (d->handle == INVALID_HANDLE_VALUE) + { + delete d; + return NULL; + } + + return d; +} + +dirent *readdir(DIR *d) +{ + if (d->read_first == false) + d->read_first = true; + else if (!FindNextFile(d->handle, &d->data)) + return NULL; + + d->ent.d_ino = 1; + d->ent.d_name = d->data.cFileName; + + return &d->ent; +} + +int closedir(DIR *d) +{ + FindClose(d->handle); + delete d; + return 0; +} diff --git a/src/win32/dir/dir.h b/src/win32/dir/dir.h new file mode 100644 index 0000000..bfacdd4 --- /dev/null +++ b/src/win32/dir/dir.h @@ -0,0 +1,27 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include + +struct dirent +{ + int d_ino; + char *d_name; +}; + +struct DIR +{ + dirent ent; + HANDLE handle; + WIN32_FIND_DATA data; + bool read_first; +}; + +DIR *opendir(const char *); +dirent *readdir(DIR *); +int closedir(DIR *); diff --git a/src/win32/dl/dl.cpp b/src/win32/dl/dl.cpp new file mode 100644 index 0000000..5d29d25 --- /dev/null +++ b/src/win32/dl/dl.cpp @@ -0,0 +1,33 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "services.h" +#include "anope.h" + +void *dlopen(const char *filename, int) +{ + return LoadLibrary(filename); +} + +char *dlerror(void) +{ + static Anope::string err; + err = Anope::LastError(); + SetLastError(0); + return err.empty() ? NULL : const_cast(err.c_str()); +} + +void *dlsym(void *handle, const char *symbol) +{ + return GetProcAddress(reinterpret_cast(handle), symbol); +} + +int dlclose(void *handle) +{ + return !FreeLibrary(reinterpret_cast(handle)); +} diff --git a/src/win32/dl/dl.h b/src/win32/dl/dl.h new file mode 100644 index 0000000..112aa3a --- /dev/null +++ b/src/win32/dl/dl.h @@ -0,0 +1,14 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#define RTLD_NOW 0 + +extern void *dlopen(const char *filename, int); +extern char *dlerror(void); +extern void *dlsym(void *handle, const char *symbol); +extern int dlclose(void *handle); diff --git a/src/win32/pipe/pipe.cpp b/src/win32/pipe/pipe.cpp new file mode 100644 index 0000000..83a98a6 --- /dev/null +++ b/src/win32/pipe/pipe.cpp @@ -0,0 +1,61 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "services.h" +#include "sockets.h" + +int pipe(int fds[2]) +{ + sockaddrs localhost("127.0.0.1"); + + int cfd = socket(AF_INET, SOCK_STREAM, 0), lfd = socket(AF_INET, SOCK_STREAM, 0); + if (cfd == -1 || lfd == -1) + { + anope_close(cfd); + anope_close(lfd); + return -1; + } + + if (bind(lfd, &localhost.sa, localhost.size()) == -1) + { + anope_close(cfd); + anope_close(lfd); + return -1; + } + + if (listen(lfd, 1) == -1) + { + anope_close(cfd); + anope_close(lfd); + return -1; + } + + sockaddrs lfd_addr; + socklen_t sz = sizeof(lfd_addr); + getsockname(lfd, &lfd_addr.sa, &sz); + + if (connect(cfd, &lfd_addr.sa, lfd_addr.size())) + { + anope_close(cfd); + anope_close(lfd); + return -1; + } + + int afd = accept(lfd, NULL, NULL); + anope_close(lfd); + if (afd == -1) + { + anope_close(cfd); + return -1; + } + + fds[0] = cfd; + fds[1] = afd; + + return 0; +} diff --git a/src/win32/pipe/pipe.h b/src/win32/pipe/pipe.h new file mode 100644 index 0000000..53f37cb --- /dev/null +++ b/src/win32/pipe/pipe.h @@ -0,0 +1,9 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +extern int pipe(int fds[2]); diff --git a/src/win32/pthread/pthread.cpp b/src/win32/pthread/pthread.cpp new file mode 100644 index 0000000..9469a4e --- /dev/null +++ b/src/win32/pthread/pthread.cpp @@ -0,0 +1,119 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include "pthread.h" + +struct ThreadInfo +{ + void *(*entry)(void *); + void *param; +}; + +static DWORD WINAPI entry_point(void *parameter) +{ + ThreadInfo *ti = static_cast(parameter); + ti->entry(ti->param); + delete ti; + return 0; +} + +int pthread_attr_init(pthread_attr_t *) +{ + /* No need for this */ + return 0; +} + +int pthread_attr_setdetachstate(pthread_attr_t *, int) +{ + /* No need for this */ + return 0; +} + +int pthread_create(pthread_t *thread, const pthread_attr_t *, void *(*entry)(void *), void *param) +{ + ThreadInfo *ti = new ThreadInfo; + ti->entry = entry; + ti->param = param; + + *thread = CreateThread(NULL, 0, entry_point, ti, 0, NULL); + if (!*thread) + { + delete ti; + return -1; + } + + return 0; +} + +int pthread_join(pthread_t thread, void **) +{ + if (WaitForSingleObject(thread, INFINITE) == WAIT_FAILED) + return -1; + CloseHandle(thread); + return 0; +} + +void pthread_exit(int i) +{ + ExitThread(i); +} + +int pthread_mutex_init(pthread_mutex_t *mutex, const pthread_mutexattr_t *) +{ + InitializeCriticalSection(mutex); + return 0; +} + +int pthread_mutex_destroy(pthread_mutex_t *mutex) +{ + DeleteCriticalSection(mutex); + return 0; +} + +int pthread_mutex_lock(pthread_mutex_t *mutex) +{ + EnterCriticalSection(mutex); + return 0; +} + +int pthread_mutex_trylock(pthread_mutex_t *mutex) +{ + return !TryEnterCriticalSection(mutex); +} + +int pthread_mutex_unlock(pthread_mutex_t *mutex) +{ + LeaveCriticalSection(mutex); + return 0; +} + +int pthread_cond_init(pthread_cond_t *cond, const pthread_condattr_t *) +{ + *cond = CreateEvent(NULL, false, false, NULL); + if (*cond == NULL) + return -1; + return 0; +} + +int pthread_cond_destroy(pthread_cond_t *cond) +{ + return !CloseHandle(*cond); +} + +int pthread_cond_signal(pthread_cond_t *cond) +{ + return !PulseEvent(*cond); +} + +int pthread_cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex) +{ + LeaveCriticalSection(mutex); + WaitForSingleObject(*cond, INFINITE); + EnterCriticalSection(mutex); + return 0; +} diff --git a/src/win32/pthread/pthread.h b/src/win32/pthread/pthread.h new file mode 100644 index 0000000..872507a --- /dev/null +++ b/src/win32/pthread/pthread.h @@ -0,0 +1,35 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#include + +typedef HANDLE pthread_t; +typedef CRITICAL_SECTION pthread_mutex_t; +typedef HANDLE pthread_cond_t; +typedef int pthread_attr_t; +typedef void pthread_mutexattr_t; +typedef void pthread_condattr_t; + +#define PTHREAD_CREATE_JOINABLE 0 + +extern int pthread_attr_init(pthread_attr_t *); +extern int pthread_attr_setdetachstate(pthread_attr_t *, int); +extern int pthread_create(pthread_t *, const pthread_attr_t *, void *(*)(void *), void *); +extern int pthread_join(pthread_t, void **); +extern void pthread_exit(int); + +extern int pthread_mutex_init(pthread_mutex_t *, const pthread_mutexattr_t *); +extern int pthread_mutex_destroy(pthread_mutex_t *); +extern int pthread_mutex_lock(pthread_mutex_t *); +extern int pthread_mutex_trylock(pthread_mutex_t *); +extern int pthread_mutex_unlock(pthread_mutex_t *); + +extern int pthread_cond_init(pthread_cond_t *, const pthread_condattr_t *); +extern int pthread_cond_destroy(pthread_cond_t *); +extern int pthread_cond_signal(pthread_cond_t *); +extern int pthread_cond_wait(pthread_cond_t *, pthread_mutex_t *); diff --git a/src/win32/resource.h b/src/win32/resource.h new file mode 100644 index 0000000..7532528 --- /dev/null +++ b/src/win32/resource.h @@ -0,0 +1,28 @@ +/* + * + * (C) 2005-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +//{{NO_DEPENDENCIES}} +// Microsoft Developer Studio generated include file. +// Used by Win32GUI.rc +// +#define VER_ANOPE 1 +#define MANIFEST_RESOURCE_ID 2 +#define ICON_APP 129 + + +// Next default values for new objects +// +#ifdef APSTUDIO_INVOKED +#ifndef APSTUDIO_READONLY_SYMBOLS +#define _APS_NO_MFC 1 +#define _APS_NEXT_RESOURCE_VALUE 152 +#define _APS_NEXT_COMMAND_VALUE 40061 +#define _APS_NEXT_CONTROL_VALUE 1167 +#define _APS_NEXT_SYMED_VALUE 104 +#endif +#endif diff --git a/src/win32/sigaction/sigaction.cpp b/src/win32/sigaction/sigaction.cpp new file mode 100644 index 0000000..7973606 --- /dev/null +++ b/src/win32/sigaction/sigaction.cpp @@ -0,0 +1,31 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include +#include "sigaction.h" +#include + +int sigaction(int sig, struct sigaction *action, struct sigaction *old) +{ + if (sig == -1) + return 0; + if (old == NULL) + { + if (signal(sig, SIG_DFL) == SIG_ERR) + return -1; + } + else + { + if (signal(sig, action->sa_handler) == SIG_ERR) + return -1; + } + return 0; +} diff --git a/src/win32/sigaction/sigaction.h b/src/win32/sigaction/sigaction.h new file mode 100644 index 0000000..0e3dd1b --- /dev/null +++ b/src/win32/sigaction/sigaction.h @@ -0,0 +1,28 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#define sigemptyset(x) memset((x), 0, sizeof(*(x))) + +#ifndef SIGHUP +# define SIGHUP -1 +#endif +#ifndef SIGPIPE +# define SIGPIPE -1 +#endif + +struct sigaction +{ + void (*sa_handler)(int); + int sa_flags; + int sa_mask; +}; + +extern int sigaction(int, struct sigaction *, struct sigaction *); diff --git a/src/win32/socket.cpp b/src/win32/socket.cpp new file mode 100644 index 0000000..f1cbcc5 --- /dev/null +++ b/src/win32/socket.cpp @@ -0,0 +1,153 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#define WIN32_NO_OVERRIDE +#include "services.h" + +inline static bool is_socket(int fd) +{ + int optval; + socklen_t optlen = sizeof(optval); + return getsockopt(fd, SOL_SOCKET, SO_TYPE, reinterpret_cast(&optval), &optlen) == 0; +} + +int read(int fd, char *buf, size_t count) +{ + if (is_socket(fd)) + return recv(fd, buf, count, 0); + else + return _read(fd, buf, count); +} + +int write(int fd, const char *buf, size_t count) +{ + if (is_socket(fd)) + return send(fd, buf, count, 0); + else + return _write(fd, buf, count); +} + +int windows_close(int fd) +{ + if (is_socket(fd)) + return closesocket(fd); + else + return close(fd); +} + +int windows_accept(int fd, struct sockaddr *addr, int *addrlen) +{ + int i = accept(fd, addr, addrlen); + if (i == INVALID_SOCKET) + return -1; + return i; +} + +/** This is inet_pton, but it works on Windows + * @param af The protocol type, AF_INET or AF_INET6 + * @param src The address + * @param dst Struct to put results in + * @return 1 on success, -1 on error + */ +int windows_inet_pton(int af, const char *src, void *dst) +{ + int address_length; + sockaddr_storage sa; + sockaddr_in *sin = reinterpret_cast(&sa); + sockaddr_in6 *sin6 = reinterpret_cast(&sa); + + switch (af) + { + case AF_INET: + address_length = sizeof(sockaddr_in); + break; + case AF_INET6: + address_length = sizeof(sockaddr_in6); + break; + default: + return -1; + } + + if (!WSAStringToAddress(static_cast(const_cast(src)), af, NULL, reinterpret_cast(&sa), &address_length)) + { + switch (af) + { + case AF_INET: + memcpy(dst, &sin->sin_addr, sizeof(in_addr)); + break; + case AF_INET6: + memcpy(dst, &sin6->sin6_addr, sizeof(in6_addr)); + break; + } + return 1; + } + + return 0; +} + +/** This is inet_ntop, but it works on Windows + * @param af The protocol type, AF_INET or AF_INET6 + * @param src Network address structure + * @param dst After converting put it here + * @param size sizeof the dest + * @return dst + */ +const char *windows_inet_ntop(int af, const void *src, char *dst, size_t size) +{ + int address_length; + DWORD string_length = size; + sockaddr_storage sa; + sockaddr_in *sin = reinterpret_cast(&sa); + sockaddr_in6 *sin6 = reinterpret_cast(&sa); + + memset(&sa, 0, sizeof(sa)); + + switch (af) + { + case AF_INET: + address_length = sizeof(sockaddr_in); + sin->sin_family = af; + memcpy(&sin->sin_addr, src, sizeof(in_addr)); + break; + case AF_INET6: + address_length = sizeof(sockaddr_in6); + sin6->sin6_family = af; + memcpy(&sin6->sin6_addr, src, sizeof(in6_addr)); + break; + default: + return NULL; + } + + if (!WSAAddressToString(reinterpret_cast(&sa), address_length, NULL, dst, &string_length)) + return dst; + + return NULL; +} + +int fcntl(int fd, int cmd, int arg) +{ + if (cmd == F_GETFL) + { + return 0; + } + else if (cmd == F_SETFL) + { + if (arg & O_NONBLOCK) + { + unsigned long opt = 1; + return ioctlsocket(fd, FIONBIO, &opt); + } + else + { + unsigned long opt = 0; + return ioctlsocket(fd, FIONBIO, &opt); + } + } + + return -1; +} diff --git a/src/win32/socket.h b/src/win32/socket.h new file mode 100644 index 0000000..1472894 --- /dev/null +++ b/src/win32/socket.h @@ -0,0 +1,32 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + */ + +#define read read_not_used +#define write write_not_used +#include +#undef read +#undef write + +#define F_GETFL 0 +#define F_SETFL 1 + +#define O_NONBLOCK 1 + +extern CoreExport int read(int fd, char *buf, size_t count); +extern CoreExport int write(int fd, const char *buf, size_t count); +extern CoreExport int windows_close(int fd); +extern CoreExport int windows_accept(int fd, struct sockaddr *addr, int *addrlen); +extern CoreExport int windows_inet_pton(int af, const char *src, void *dst); +extern CoreExport const char *windows_inet_ntop(int af, const void *src, char *dst, size_t size); +extern CoreExport int fcntl(int fd, int cmd, int arg); + +#ifndef WIN32_NO_OVERRIDE +# define accept windows_accept +# define inet_pton windows_inet_pton +# define inet_ntop windows_inet_ntop +#endif diff --git a/src/win32/win32.rc.cmake b/src/win32/win32.rc.cmake new file mode 100644 index 0000000..703611e --- /dev/null +++ b/src/win32/win32.rc.cmake @@ -0,0 +1,92 @@ +///Microsoft Developer Studio generated resource script. +// +#include "resource.h" + +#define APSTUDIO_READONLY_SYMBOLS +///////////////////////////////////////////////////////////////////////////// +// +// Generated from the TEXTINCLUDE 2 resource. +// +#define APSTUDIO_HIDDEN_SYMBOLS +#include +#undef APSTUDIO_HIDDEN_SYMBOLS +#include "resource.h" + +///////////////////////////////////////////////////////////////////////////// +#undef APSTUDIO_READONLY_SYMBOLS + +///////////////////////////////////////////////////////////////////////////// +// English (U.S.) resources + +#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) +#ifdef _WIN32 +LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US +#pragma code_page(1252) +#endif //_WIN32 + +#ifndef _MAC + +///////////////////////////////////////////////////////////////////////////// +// +// Version +// + +VER_ANOPE VERSIONINFO + FILEVERSION @VERSION_COMMA@ + PRODUCTVERSION @VERSION_COMMA@ +#ifndef MINGW + FILEFLAGSMASK VS_FFI_FILEFLAGSMASK +#endif +#ifdef _DEBUG + FILEFLAGS VS_FF_DEBUG +#else + FILEFLAGS 0x0L +#endif + FILEOS VOS_NT + FILETYPE VFT_APP + FILESUBTYPE 0x0L +BEGIN + BLOCK "StringFileInfo" + BEGIN + BLOCK "040904b0" + BEGIN + VALUE "CompanyName", "Anope Team" + VALUE "FileDescription", "Anope IRC Services" + VALUE "FileVersion", "@VERSION_FULL@" + VALUE "InternalName", "Anope" + VALUE "LegalCopyright", "Copyright (C) 2003-2022 Anope Team" + VALUE "OriginalFilename", "anope.exe" + VALUE "ProductName", "Anope" + VALUE "ProductVersion", "@VERSION_DOTTED@" + END + END + BLOCK "VarFileInfo" + BEGIN + VALUE "Translation", 0x409, 1200 + END +END + +#endif // !_MAC + +///////////////////////////////////////////////////////////////////////////// +// +// Icon +// + +// Icon with lowest ID value placed first to ensure application icon +// remains consistent on all systems. +ICON_APP ICON "@Anope_SOURCE_DIR@/src/win32/anope-icon.ico" +#endif // English (U.S.) resources +///////////////////////////////////////////////////////////////////////////// + + + +#ifndef APSTUDIO_INVOKED +///////////////////////////////////////////////////////////////////////////// +// +// Generated from the TEXTINCLUDE 3 resource. +// + + +///////////////////////////////////////////////////////////////////////////// +#endif // not APSTUDIO_INVOKED diff --git a/src/win32/win32_memory.cpp b/src/win32/win32_memory.cpp new file mode 100644 index 0000000..db7a46e --- /dev/null +++ b/src/win32/win32_memory.cpp @@ -0,0 +1,64 @@ +/* +------------------------------------+ + * | Inspire Internet Relay Chat Daemon | + * +------------------------------------+ + * + * InspIRCd: (C) 2002-2011 InspIRCd Development Team + * See: https://wiki.inspircd.org/Credits + * + * This program is free but copyrighted software; see + * the file COPYING for details. + * + * --------------------------------------------------- + */ + +#ifdef _WIN32 + +#include +#include +#include +#include + +/** On windows, all dll files and executables have their own private heap, + * whereas on POSIX systems, shared objects loaded into an executable share + * the executable's heap. This means that if we pass an arbitrary pointer to + * a windows DLL which is not allocated in that dll, without some form of + * marshalling, we get a page fault. To fix this, these overrided operators + * new and delete use the windows HeapAlloc and HeapFree functions to claim + * memory from the windows global heap. This makes windows 'act like' POSIX + * when it comes to memory usage between dlls and exes. + */ + +void *::operator new(size_t iSize) +{ + void *ptr = HeapAlloc(GetProcessHeap(), 0, iSize); /* zero memory for unix compatibility */ + /* This is the correct behaviour according to C++ standards for out of memory, + * not returning null -- Brain + */ + if (!ptr) + throw std::bad_alloc(); + else + return ptr; +} + +void ::operator delete(void *ptr) +{ + if (ptr) + HeapFree(GetProcessHeap(), 0, ptr); +} + +void *operator new[](size_t iSize) +{ + void *ptr = HeapAlloc(GetProcessHeap(), 0, iSize); /* Why were we initializing the memory to zeros here? This is just a waste of cpu! */ + if (!ptr) + throw std::bad_alloc(); + else + return ptr; +} + +void operator delete[](void *ptr) +{ + if (ptr) + HeapFree(GetProcessHeap(), 0, ptr); +} + +#endif diff --git a/src/win32/windows.cpp b/src/win32/windows.cpp new file mode 100644 index 0000000..7ee7c8d --- /dev/null +++ b/src/win32/windows.cpp @@ -0,0 +1,261 @@ +/* POSIX emulation layer for Windows. + * + * (C) 2008-2011 Robin Burchell + * (C) 2008-2022 Anope Team + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#ifdef _WIN32 +#include "services.h" +#include "anope.h" + +#include +#include +#include +#include + +static struct WindowsLanguage +{ + Anope::string languageName; + USHORT windowsLanguageName; +} WindowsLanguages[] = { + {"ca_ES", LANG_CATALAN}, + {"de_DE", LANG_GERMAN}, + {"el_GR", LANG_GREEK}, + {"en_US", LANG_ENGLISH}, + {"es_ES", LANG_SPANISH}, + {"fr_FR", LANG_FRENCH}, + {"hu_HU", LANG_HUNGARIAN}, + {"it_IT", LANG_ITALIAN}, + {"nl_NL", LANG_DUTCH}, + {"pl_PL", LANG_POLISH}, + {"pt_PT", LANG_PORTUGUESE}, + {"ru_RU", LANG_RUSSIAN}, + {"tr_TR", LANG_TURKISH}, +}; + +static WSADATA wsa; + +void OnStartup() +{ + if (WSAStartup(MAKEWORD(2, 0), &wsa)) + throw CoreException("Failed to initialize WinSock library"); +} + +void OnShutdown() +{ + WSACleanup(); +} + +USHORT WindowsGetLanguage(const Anope::string &lang) +{ + for (int i = 0; i < sizeof(WindowsLanguages) / sizeof(WindowsLanguage); ++i) + { + WindowsLanguage &l = WindowsLanguages[i]; + + if (lang == l.languageName || !lang.find(l.languageName + ".")) + return l.windowsLanguageName; + } + + return LANG_NEUTRAL; +} + +/** Like gettimeofday(), but it works on Windows. + * @param tv A timeval struct + * @param tz Should be NULL, it is not used + * @return 0 on success + */ +int gettimeofday(timeval *tv, void *) +{ + SYSTEMTIME st; + GetSystemTime(&st); + + tv->tv_sec = Anope::CurTime; + tv->tv_usec = st.wMilliseconds; + + return 0; +} + +Anope::string GetWindowsVersion() +{ + OSVERSIONINFOEX osvi; + SYSTEM_INFO si; + + ZeroMemory(&osvi, sizeof(OSVERSIONINFOEX)); + ZeroMemory(&si, sizeof(SYSTEM_INFO)); + osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFOEX); + + BOOL bOsVersionInfoEx = GetVersionEx(reinterpret_cast(&osvi)); + if (!bOsVersionInfoEx) + { + osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFO); + if (!GetVersionEx(reinterpret_cast(&osvi))) + return ""; + } + GetSystemInfo(&si); + + Anope::string buf, extra, cputype; + /* Determine CPU type 32 or 64 */ + if (si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_AMD64) + cputype = " 64-bit"; + else if (si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_INTEL) + cputype = " 32-bit"; + else if (si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_IA64) + cputype = " Itanium 64-bit"; + + switch (osvi.dwPlatformId) + { + /* test for the Windows NT product family. */ + case VER_PLATFORM_WIN32_NT: + /* Windows Vista or Windows Server 2008 */ + if (osvi.dwMajorVersion == 6 && !osvi.dwMinorVersion) + { + if (osvi.wSuiteMask & VER_SUITE_ENTERPRISE) + extra = " Enterprise Edition"; + else if (osvi.wSuiteMask & VER_SUITE_DATACENTER) + extra = " Datacenter Edition"; + else if (osvi.wSuiteMask & VER_SUITE_PERSONAL) + extra = " Home Premium/Basic"; + if (osvi.dwMinorVersion == 0) + { + if (osvi.wProductType & VER_NT_WORKSTATION) + buf = "Microsoft Windows Vista" + cputype + extra; + else + buf = "Microsoft Windows Server 2008" + cputype + extra; + } + else if (osvi.dwMinorVersion == 1) + { + if (osvi.wProductType & VER_NT_WORKSTATION) + buf = "Microsoft Windows 7" + cputype + extra; + else + buf = "Microsoft Windows Server 2008 R2" + cputype + extra; + } + } + /* Windows 2003 or Windows XP Pro 64 */ + if (osvi.dwMajorVersion == 5 && osvi.dwMinorVersion == 2) + { + if (osvi.wSuiteMask & VER_SUITE_DATACENTER) + extra = " Datacenter Edition"; + else if (osvi.wSuiteMask & VER_SUITE_ENTERPRISE) + extra = " Enterprise Edition"; +#ifdef VER_SUITE_COMPUTE_SERVER + else if (osvi.wSuiteMask & VER_SUITE_COMPUTE_SERVER) + extra = " Compute Cluster Edition"; +#endif + else if (osvi.wSuiteMask == VER_SUITE_BLADE) + extra = " Web Edition"; + else + extra = " Standard Edition"; + if (osvi.wProductType & VER_NT_WORKSTATION && si.wProcessorArchitecture == PROCESSOR_ARCHITECTURE_AMD64) + buf = "Microsoft Windows XP Professional x64 Edition" + extra; + else + buf = "Microsoft Windows Server 2003 Family" + cputype + extra; + } + if (osvi.dwMajorVersion == 5 && osvi.dwMinorVersion == 1) + { + if (osvi.wSuiteMask & VER_SUITE_EMBEDDEDNT) + extra = " Embedded"; + else if (osvi.wSuiteMask & VER_SUITE_PERSONAL) + extra = " Home Edition"; + buf = "Microsoft Windows XP" + extra; + } + if (osvi.dwMajorVersion == 5 && !osvi.dwMinorVersion) + { + if (osvi.wSuiteMask & VER_SUITE_DATACENTER) + extra = " Datacenter Server"; + else if (osvi.wSuiteMask & VER_SUITE_ENTERPRISE) + extra = " Advanced Server"; + else + extra = " Server"; + buf = "Microsoft Windows 2000" + extra; + } + if (osvi.dwMajorVersion <= 4) + { + if (osvi.wSuiteMask & VER_SUITE_ENTERPRISE) + extra = " Enterprise Edition"; + buf = "Microsoft Windows NT Server 4.0" + extra; + } + break; + case VER_PLATFORM_WIN32_WINDOWS: + if (osvi.dwMajorVersion == 4 && !osvi.dwMinorVersion) + { + if (osvi.szCSDVersion[1] == 'C' || osvi.szCSDVersion[1] == 'B') + extra = " OSR2"; + buf = "Microsoft Windows 95" + extra; + } + if (osvi.dwMajorVersion == 4 && osvi.dwMinorVersion == 10) + { + if (osvi.szCSDVersion[1] == 'A') + extra = "SE"; + buf = "Microsoft Windows 98" + extra; + } + if (osvi.dwMajorVersion == 4 && osvi.dwMinorVersion == 90) + buf = "Microsoft Windows Millennium Edition"; + } + return buf; +} + +bool SupportedWindowsVersion() +{ + OSVERSIONINFOEX osvi; + + ZeroMemory(&osvi, sizeof(OSVERSIONINFOEX)); + osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFOEX); + + BOOL bOsVersionInfoEx = GetVersionEx(reinterpret_cast(&osvi)); + if (!bOsVersionInfoEx) + { + osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFO); + if (!GetVersionEx(reinterpret_cast(&osvi))) + return false; + } + + switch (osvi.dwPlatformId) + { + /* test for the Windows NT product family. */ + case VER_PLATFORM_WIN32_NT: + /* win nt4 */ + if (osvi.dwMajorVersion <= 4) + return false; + /* the rest */ + return true; + /* win95 win98 winME */ + case VER_PLATFORM_WIN32_WINDOWS: + return false; + } + return false; +} + +int setenv(const char *name, const char *value, int overwrite) +{ + return SetEnvironmentVariable(name, value); +} + +int unsetenv(const char *name) +{ + return SetEnvironmentVariable(name, NULL); +} + +int mkstemp(char *input) +{ + input = _mktemp(input); + if (input == NULL) + { + errno = EEXIST; + return -1; + } + + int fd = open(input, O_WRONLY | O_CREAT, S_IREAD | S_IWRITE); + return fd; +} + +void getcwd(char *buf, size_t sz) +{ + GetCurrentDirectory(sz, buf); +} + +#endif diff --git a/src/xline.cpp b/src/xline.cpp new file mode 100644 index 0000000..7c8034c --- /dev/null +++ b/src/xline.cpp @@ -0,0 +1,469 @@ +/* XLine functions. + * + * (C) 2003-2022 Anope Team + * Contact us at team@anope.org + * + * Please read COPYING and README for further details. + * + * Based on the original code of Epona by Lara. + * Based on the original code of Services by Andy Church. + */ + +#include "services.h" +#include "modules.h" +#include "xline.h" +#include "users.h" +#include "sockets.h" +#include "regexpr.h" +#include "config.h" +#include "commands.h" +#include "servers.h" + +/* List of XLine managers we check users against in XLineManager::CheckAll */ +std::list XLineManager::XLineManagers; +Serialize::Checker > XLineManager::XLinesByUID("XLine"); + +void XLine::Init() +{ + if (this->mask.length() >= 2 && this->mask[0] == '/' && this->mask[this->mask.length() - 1] == '/' && !Config->GetBlock("options")->Get("regexengine").empty()) + { + Anope::string stripped_mask = this->mask.substr(1, this->mask.length() - 2); + + ServiceReference provider("Regex", Config->GetBlock("options")->Get("regexengine")); + if (provider) + { + try + { + this->regex = provider->Compile(stripped_mask); + } + catch (const RegexException &ex) + { + Log(LOG_DEBUG) << ex.GetReason(); + } + } + } + + size_t nick_t = this->mask.find('!'); + if (nick_t != Anope::string::npos) + nick = this->mask.substr(0, nick_t); + + size_t user_t = this->mask.find('!'), host_t = this->mask.find('@'); + if (host_t != Anope::string::npos) + { + if (user_t != Anope::string::npos && host_t > user_t) + user = this->mask.substr(user_t + 1, host_t - user_t - 1); + else + user = this->mask.substr(0, host_t); + } + + size_t real_t = this->mask.find('#'); + if (host_t != Anope::string::npos) + { + if (real_t != Anope::string::npos && real_t > host_t) + host = this->mask.substr(host_t + 1, real_t - host_t - 1); + else + host = this->mask.substr(host_t + 1); + } + else + { + if (real_t != Anope::string::npos) + host = this->mask.substr(0, real_t); + else + host = this->mask; + } + + if (real_t != Anope::string::npos) + real = this->mask.substr(real_t + 1); + + if (host.find('/') != Anope::string::npos) + { + c = new cidr(host); + if (!c->valid()) + { + delete c; + c = NULL; + } + } +} + +XLine::XLine(const Anope::string &ma, const Anope::string &r, const Anope::string &uid) : Serializable("XLine"), mask(ma), by(Me->GetName()), created(0), expires(0), reason(r), id(uid) +{ + regex = NULL; + manager = NULL; + c = NULL; + + this->Init(); +} + +XLine::XLine(const Anope::string &ma, const Anope::string &b, const time_t ex, const Anope::string &r, const Anope::string &uid) : Serializable("XLine"), mask(ma), by(b), created(Anope::CurTime), expires(ex), reason(r), id(uid) +{ + regex = NULL; + manager = NULL; + c = NULL; + + this->Init(); +} + +XLine::~XLine() +{ + if (manager) + manager->RemoveXLine(this); + + delete regex; + delete c; +} + +const Anope::string &XLine::GetNick() const +{ + return nick; +} + +const Anope::string &XLine::GetUser() const +{ + return user; +} + +const Anope::string &XLine::GetHost() const +{ + return host; +} + +const Anope::string &XLine::GetReal() const +{ + return real; +} + +Anope::string XLine::GetReason() const +{ + Anope::string r = this->reason; + if (!this->id.empty()) + r += " (ID: " + this->id + ")"; + return r; +} + +bool XLine::HasNickOrReal() const +{ + return !this->GetNick().empty() || !this->GetReal().empty(); +} + +bool XLine::IsRegex() const +{ + return !this->mask.empty() && this->mask[0] == '/' && this->mask[this->mask.length() - 1] == '/'; +} + +void XLine::Serialize(Serialize::Data &data) const +{ + data["mask"] << this->mask; + data["by"] << this->by; + data["created"] << this->created; + data["expires"] << this->expires; + data["reason"] << this->reason; + data["uid"] << this->id; + if (this->manager) + data["manager"] << this->manager->name; +} + +Serializable* XLine::Unserialize(Serializable *obj, Serialize::Data &data) +{ + Anope::string smanager; + + data["manager"] >> smanager; + + ServiceReference xlm("XLineManager", smanager); + if (!xlm) + return NULL; + + XLine *xl; + if (obj) + { + xl = anope_dynamic_static_cast(obj); + data["mask"] >> xl->mask; + data["by"] >> xl->by; + data["reason"] >> xl->reason; + data["uid"] >> xl->id; + + if (xlm != xl->manager) + { + xl->manager->DelXLine(xl); + xlm->AddXLine(xl); + } + } + else + { + Anope::string smask, sby, sreason, suid; + time_t expires; + + data["mask"] >> smask; + data["by"] >> sby; + data["reason"] >> sreason; + data["uid"] >> suid; + data["expires"] >> expires; + + xl = new XLine(smask, sby, expires, sreason, suid); + xlm->AddXLine(xl); + } + + data["created"] >> xl->created; + xl->manager = xlm; + + return xl; +} + +void XLineManager::RegisterXLineManager(XLineManager *xlm) +{ + XLineManagers.push_back(xlm); +} + +void XLineManager::UnregisterXLineManager(XLineManager *xlm) +{ + std::list::iterator it = std::find(XLineManagers.begin(), XLineManagers.end(), xlm); + + if (it != XLineManagers.end()) + XLineManagers.erase(it); +} + +void XLineManager::CheckAll(User *u) +{ + for (std::list::iterator it = XLineManagers.begin(), it_end = XLineManagers.end(); it != it_end; ++it) + { + XLineManager *xlm = *it; + + if (xlm->CheckAllXLines(u)) + break; + } +} + +Anope::string XLineManager::GenerateUID() +{ + Anope::string id; + int count = 0; + do + { + id.clear(); + + if (++count > 10) + { + Log(LOG_DEBUG) << "Unable to generate XLine UID"; + break; + } + + for (int i = 0; i < 10; ++i) + { + char c; + do + c = (rand() % 75) + 48; + while (!isupper(c) && !isdigit(c)); + id += c; + } + } + while (XLinesByUID->count(id) > 0); + + return id; +} + +XLineManager::XLineManager(Module *creator, const Anope::string &xname, char t) : Service(creator, "XLineManager", xname), type(t), xlines("XLine") +{ +} + +XLineManager::~XLineManager() +{ + this->Clear(); +} + +const char &XLineManager::Type() +{ + return this->type; +} + +size_t XLineManager::GetCount() const +{ + return this->xlines->size(); +} + +const std::vector &XLineManager::GetList() const +{ + return this->xlines; +} + +void XLineManager::AddXLine(XLine *x) +{ + if (!x->id.empty()) + XLinesByUID->insert(std::make_pair(x->id, x)); + this->xlines->push_back(x); + x->manager = this; +} + +void XLineManager::RemoveXLine(XLine *x) +{ + /* called from the destructor */ + + std::vector::iterator it = std::find(this->xlines->begin(), this->xlines->end(), x); + + if (!x->id.empty()) + { + std::multimap::iterator it2 = XLinesByUID->find(x->id), it3 = XLinesByUID->upper_bound(x->id); + for (; it2 != XLinesByUID->end() && it2 != it3; ++it2) + if (it2->second == x) + { + XLinesByUID->erase(it2); + break; + } + } + + if (it != this->xlines->end()) + { + this->SendDel(x); + this->xlines->erase(it); + } +} + +bool XLineManager::DelXLine(XLine *x) +{ + std::vector::iterator it = std::find(this->xlines->begin(), this->xlines->end(), x); + + if (!x->id.empty()) + { + std::multimap::iterator it2 = XLinesByUID->find(x->id), it3 = XLinesByUID->upper_bound(x->id); + for (; it2 != XLinesByUID->end() && it2 != it3; ++it2) + if (it2->second == x) + { + XLinesByUID->erase(it2); + break; + } + } + + if (it != this->xlines->end()) + { + this->SendDel(x); + + x->manager = NULL; // Don't call remove + delete x; + this->xlines->erase(it); + + return true; + } + + return false; +} + +XLine* XLineManager::GetEntry(unsigned index) +{ + if (index >= this->xlines->size()) + return NULL; + + XLine *x = this->xlines->at(index); + x->QueueUpdate(); + return x; +} + +void XLineManager::Clear() +{ + std::vector xl; + this->xlines->swap(xl); + + for (unsigned i = 0; i < xl.size(); ++i) + { + XLine *x = xl[i]; + if (!x->id.empty()) + XLinesByUID->erase(x->id); + delete x; + } +} + +bool XLineManager::CanAdd(CommandSource &source, const Anope::string &mask, time_t expires, const Anope::string &reason) +{ + for (unsigned i = this->GetCount(); i > 0; --i) + { + XLine *x = this->GetEntry(i - 1); + + if (x->mask.equals_ci(mask)) + { + if (!x->expires || x->expires >= expires) + { + if (x->reason != reason) + { + x->reason = reason; + source.Reply(_("Reason for %s updated."), x->mask.c_str()); + } + else + source.Reply(_("%s already exists."), mask.c_str()); + } + else + { + x->expires = expires; + if (x->reason != reason) + { + x->reason = reason; + source.Reply(_("Expiry and reason updated for %s."), x->mask.c_str()); + } + else + source.Reply(_("Expiry for %s updated."), x->mask.c_str()); + } + + return false; + } + else if (Anope::Match(mask, x->mask) && (!x->expires || x->expires >= expires)) + { + source.Reply(_("%s is already covered by %s."), mask.c_str(), x->mask.c_str()); + return false; + } + else if (Anope::Match(x->mask, mask) && (!expires || x->expires <= expires)) + { + source.Reply(_("Removing %s because %s covers it."), x->mask.c_str(), mask.c_str()); + this->DelXLine(x); + } + } + + return true; +} + +XLine* XLineManager::HasEntry(const Anope::string &mask) +{ + std::multimap::iterator it = XLinesByUID->find(mask); + if (it != XLinesByUID->end()) + for (std::multimap::iterator it2 = XLinesByUID->upper_bound(mask); it != it2; ++it) + if (it->second->manager == NULL || it->second->manager == this) + { + it->second->QueueUpdate(); + return it->second; + } + for (unsigned i = 0, end = this->xlines->size(); i < end; ++i) + { + XLine *x = this->xlines->at(i); + + if (x->mask.equals_ci(mask)) + { + x->QueueUpdate(); + return x; + } + } + + return NULL; +} + +XLine *XLineManager::CheckAllXLines(User *u) +{ + for (unsigned i = this->xlines->size(); i > 0; --i) + { + XLine *x = this->xlines->at(i - 1); + + if (x->expires && x->expires < Anope::CurTime) + { + this->OnExpire(x); + this->DelXLine(x); + continue; + } + + if (this->Check(u, x)) + { + this->OnMatch(u, x); + return x; + } + } + + return NULL; +} + +void XLineManager::OnExpire(const XLine *x) +{ +}