2016-01-20 00:00:00 +00:00
/*
* Copyright ( c ) 2013 - 2016 , The PurpleI2P Project
*
* This file is part of Purple i2pd project and licensed under BSD3
*
* See full license text in LICENSE file at top of project tree
*/
# include <cstdlib>
# include <iostream>
# include <fstream>
# include <map>
# include <string>
2016-01-27 00:00:00 +00:00
# include <boost/program_options/cmdline.hpp>
2016-01-20 00:00:00 +00:00
# include <boost/program_options/options_description.hpp>
# include <boost/program_options/parsers.hpp>
# include <boost/program_options/variables_map.hpp>
# include "Config.h"
# include "version.h"
using namespace boost : : program_options ;
namespace i2p {
namespace config {
options_description m_OptionsDesc ;
variables_map m_Options ;
void Init ( ) {
2016-07-13 15:12:51 +00:00
2016-01-20 00:00:00 +00:00
options_description general ( " General options " ) ;
general . add_options ( )
2016-02-01 00:00:00 +00:00
( " help " , " Show this message " )
2016-03-28 00:00:00 +00:00
( " conf " , value < std : : string > ( ) - > default_value ( " " ) , " Path to main i2pd config file (default: try ~/.i2pd/i2pd.conf or /var/lib/i2pd/i2pd.conf) " )
2016-03-28 00:00:00 +00:00
( " tunconf " , value < std : : string > ( ) - > default_value ( " " ) , " Path to config with tunnels list and options (default: try ~/.i2pd/tunnels.conf or /var/lib/i2pd/tunnels.conf) " )
2016-02-03 11:22:00 +00:00
( " pidfile " , value < std : : string > ( ) - > default_value ( " " ) , " Path to pidfile (default: ~/i2pd/i2pd.pid or /var/lib/i2pd/i2pd.pid) " )
2016-03-27 00:17:29 +00:00
( " log " , value < std : : string > ( ) - > default_value ( " " ) , " Logs destination: stdout, file, syslog (stdout if not set) " )
2016-02-01 00:00:00 +00:00
( " logfile " , value < std : : string > ( ) - > default_value ( " " ) , " Path to logfile (stdout if not set, autodetect if daemon) " )
2016-01-20 00:00:00 +00:00
( " loglevel " , value < std : : string > ( ) - > default_value ( " info " ) , " Set the minimal level of log messages (debug, info, warn, error) " )
2016-02-21 01:20:19 +00:00
( " family " , value < std : : string > ( ) - > default_value ( " " ) , " Specify a family, router belongs to " )
( " datadir " , value < std : : string > ( ) - > default_value ( " " ) , " Path to storage of i2pd data (RI, keys, peer profiles, ...) " )
2016-02-03 21:18:49 +00:00
( " host " , value < std : : string > ( ) - > default_value ( " 0.0.0.0 " ) , " External IP " )
2016-10-28 20:17:48 +00:00
( " ifname " , value < std : : string > ( ) - > default_value ( " " ) , " Network interface to bind to " )
( " nat " , value < bool > ( ) - > zero_tokens ( ) - > default_value ( true ) , " Should we assume we are behind NAT? " )
2016-02-03 11:22:00 +00:00
( " port " , value < uint16_t > ( ) - > default_value ( 0 ) , " Port to listen for incoming connections (default: auto) " )
2016-03-24 22:44:41 +00:00
( " ipv4 " , value < bool > ( ) - > zero_tokens ( ) - > default_value ( true ) , " Enable communication through ipv4 " )
2016-02-01 00:00:00 +00:00
( " ipv6 " , value < bool > ( ) - > zero_tokens ( ) - > default_value ( false ) , " Enable communication through ipv6 " )
2016-10-12 15:26:48 +00:00
( " netid " , value < int > ( ) - > default_value ( I2PD_NET_ID ) , " Specify NetID. Main I2P is 2 " )
2016-01-24 11:04:15 +00:00
( " daemon " , value < bool > ( ) - > zero_tokens ( ) - > default_value ( false ) , " Router will go to background after start " )
( " service " , value < bool > ( ) - > zero_tokens ( ) - > default_value ( false ) , " Router will use system folders like '/var/lib/i2pd' " )
2016-02-03 11:22:00 +00:00
( " notransit " , value < bool > ( ) - > zero_tokens ( ) - > default_value ( false ) , " Router will not accept transit tunnels at startup " )
( " floodfill " , value < bool > ( ) - > zero_tokens ( ) - > default_value ( false ) , " Router will be floodfill " )
2016-03-31 01:31:17 +00:00
( " bandwidth " , value < std : : string > ( ) - > default_value ( " " ) , " Bandwidth limit: integer in kbps or letters: L (32), O (256), P (2048), X (>9000) " )
2016-10-28 20:17:48 +00:00
( " ntcp " , value < bool > ( ) - > zero_tokens ( ) - > default_value ( true ) , " Enable NTCP transport " )
( " ssu " , value < bool > ( ) - > zero_tokens ( ) - > default_value ( true ) , " Enable SSU transport " )
2016-02-03 11:22:00 +00:00
# ifdef _WIN32
( " svcctl " , value < std : : string > ( ) - > default_value ( " " ) , " Windows service management ('install' or 'remove') " )
2016-03-10 02:20:27 +00:00
( " insomnia " , value < bool > ( ) - > zero_tokens ( ) - > default_value ( false ) , " Prevent system from sleeping " )
2016-03-31 00:00:00 +00:00
( " close " , value < std : : string > ( ) - > default_value ( " ask " ) , " Action on close: minimize, exit, ask " ) // TODO: add custom validator or something
2016-02-03 11:22:00 +00:00
# endif
2016-01-20 00:00:00 +00:00
;
2016-04-20 17:24:50 +00:00
2016-04-20 17:12:14 +00:00
options_description limits ( " Limits options " ) ;
limits . add_options ( )
2016-04-20 17:24:50 +00:00
( " limits.transittunnels " , value < uint16_t > ( ) - > default_value ( 2500 ) , " Maximum active transit sessions (default:2500) " )
2016-04-20 17:12:14 +00:00
;
2016-01-20 00:00:00 +00:00
options_description httpserver ( " HTTP Server options " ) ;
httpserver . add_options ( )
( " http.enabled " , value < bool > ( ) - > default_value ( true ) , " Enable or disable webconsole " )
( " http.address " , value < std : : string > ( ) - > default_value ( " 127.0.0.1 " ) , " Webconsole listen address " )
( " http.port " , value < uint16_t > ( ) - > default_value ( 7070 ) , " Webconsole listen port " )
2016-04-27 00:00:00 +00:00
( " http.auth " , value < bool > ( ) - > default_value ( false ) , " Enable Basic HTTP auth for webconsole " )
( " http.user " , value < std : : string > ( ) - > default_value ( " i2pd " ) , " Username for basic auth " )
( " http.pass " , value < std : : string > ( ) - > default_value ( " " ) , " Password for basic auth (default: random, see logs) " )
2016-01-20 00:00:00 +00:00
;
options_description httpproxy ( " HTTP Proxy options " ) ;
httpproxy . add_options ( )
( " httpproxy.enabled " , value < bool > ( ) - > default_value ( true ) , " Enable or disable HTTP Proxy " )
( " httpproxy.address " , value < std : : string > ( ) - > default_value ( " 127.0.0.1 " ) , " HTTP Proxy listen address " )
2016-02-01 00:00:00 +00:00
( " httpproxy.port " , value < uint16_t > ( ) - > default_value ( 4444 ) , " HTTP Proxy listen port " )
2016-02-03 20:29:15 +00:00
( " httpproxy.keys " , value < std : : string > ( ) - > default_value ( " " ) , " File to persist HTTP Proxy keys " )
2016-11-03 15:44:25 +00:00
( " httpproxy.inbound.length " , value < std : : string > ( ) - > default_value ( " 3 " ) , " HTTP proxy inbound tunnel length " )
( " httpproxy.outbound.length " , value < std : : string > ( ) - > default_value ( " 3 " ) , " HTTP proxy outbound tunnel length " )
( " httpproxy.inbound.quantity " , value < std : : string > ( ) - > default_value ( " 5 " ) , " HTTP proxy inbound tunnels quantity " )
( " httpproxy.outbound.quantity " , value < std : : string > ( ) - > default_value ( " 5 " ) , " HTTP proxy outbound tunnels quantity " )
2016-01-20 00:00:00 +00:00
;
options_description socksproxy ( " SOCKS Proxy options " ) ;
socksproxy . add_options ( )
( " socksproxy.enabled " , value < bool > ( ) - > default_value ( true ) , " Enable or disable SOCKS Proxy " )
( " socksproxy.address " , value < std : : string > ( ) - > default_value ( " 127.0.0.1 " ) , " SOCKS Proxy listen address " )
( " socksproxy.port " , value < uint16_t > ( ) - > default_value ( 4447 ) , " SOCKS Proxy listen port " )
2016-02-03 20:29:15 +00:00
( " socksproxy.keys " , value < std : : string > ( ) - > default_value ( " " ) , " File to persist SOCKS Proxy keys " )
2016-02-26 22:06:11 +00:00
( " socksproxy.outproxy " , value < std : : string > ( ) - > default_value ( " 127.0.0.1 " ) , " Upstream outproxy address for SOCKS Proxy " )
( " socksproxy.outproxyport " , value < uint16_t > ( ) - > default_value ( 9050 ) , " Upstream outproxy port for SOCKS Proxy " )
2016-01-20 00:00:00 +00:00
;
options_description sam ( " SAM bridge options " ) ;
sam . add_options ( )
( " sam.enabled " , value < bool > ( ) - > default_value ( false ) , " Enable or disable SAM Application bridge " )
( " sam.address " , value < std : : string > ( ) - > default_value ( " 127.0.0.1 " ) , " SAM listen address " )
( " sam.port " , value < uint16_t > ( ) - > default_value ( 7656 ) , " SAM listen port " )
;
options_description bob ( " BOB options " ) ;
bob . add_options ( )
( " bob.enabled " , value < bool > ( ) - > default_value ( false ) , " Enable or disable BOB command channel " )
( " bob.address " , value < std : : string > ( ) - > default_value ( " 127.0.0.1 " ) , " BOB listen address " )
( " bob.port " , value < uint16_t > ( ) - > default_value ( 2827 ) , " BOB listen port " )
;
2016-06-01 01:37:32 +00:00
options_description i2cp ( " I2CP options " ) ;
2016-06-01 00:00:00 +00:00
i2cp . add_options ( )
2016-05-31 15:54:45 +00:00
( " i2cp.enabled " , value < bool > ( ) - > default_value ( false ) , " Enable or disable I2CP " )
( " i2cp.address " , value < std : : string > ( ) - > default_value ( " 127.0.0.1 " ) , " I2CP listen address " )
2016-06-01 01:37:32 +00:00
( " i2cp.port " , value < uint16_t > ( ) - > default_value ( 7654 ) , " I2CP listen port " )
2016-05-31 15:54:45 +00:00
;
2016-01-20 00:00:00 +00:00
options_description i2pcontrol ( " I2PControl options " ) ;
i2pcontrol . add_options ( )
( " i2pcontrol.enabled " , value < bool > ( ) - > default_value ( false ) , " Enable or disable I2P Control Protocol " )
( " i2pcontrol.address " , value < std : : string > ( ) - > default_value ( " 127.0.0.1 " ) , " I2PCP listen address " )
( " i2pcontrol.port " , value < uint16_t > ( ) - > default_value ( 7650 ) , " I2PCP listen port " )
2016-01-21 07:35:26 +00:00
( " i2pcontrol.password " , value < std : : string > ( ) - > default_value ( " itoopie " ) , " I2PCP access password " )
2016-01-22 00:00:00 +00:00
( " i2pcontrol.cert " , value < std : : string > ( ) - > default_value ( " i2pcontrol.crt.pem " ) , " I2PCP connection cerificate " )
( " i2pcontrol.key " , value < std : : string > ( ) - > default_value ( " i2pcontrol.key.pem " ) , " I2PCP connection cerificate key " )
2016-01-20 00:00:00 +00:00
;
2016-07-13 15:12:51 +00:00
bool upnp_default = false ;
2016-07-20 13:33:50 +00:00
# if (defined(USE_UPNP) && (defined(WIN32_APP) || defined(ANDROID)))
2016-07-13 15:12:51 +00:00
upnp_default = true ; // enable UPNP for windows GUI and android by default
# endif
options_description upnp ( " UPnP options " ) ;
upnp . add_options ( )
( " upnp.enabled " , value < bool > ( ) - > default_value ( upnp_default ) , " Enable or disable UPnP: automatic port forwarding " )
2016-07-19 16:03:03 +00:00
( " upnp.name " , value < std : : string > ( ) - > default_value ( " I2Pd " ) , " Name i2pd appears in UPnP forwardings list " )
2016-07-12 00:00:00 +00:00
;
2016-04-17 20:57:58 +00:00
options_description precomputation ( " Precomputation options " ) ;
precomputation . add_options ( )
( " precomputation.elgamal " ,
# if defined(__x86_64__)
value < bool > ( ) - > default_value ( false ) ,
# else
value < bool > ( ) - > default_value ( true ) ,
# endif
" Enable or disable elgamal precomputation table " )
;
2016-08-12 14:33:53 +00:00
options_description reseed ( " Reseed options " ) ;
reseed . add_options ( )
2016-10-11 19:02:23 +00:00
( " reseed.verify " , value < bool > ( ) - > default_value ( false ) , " Verify .su3 signature " )
2016-08-12 14:33:53 +00:00
( " reseed.file " , value < std : : string > ( ) - > default_value ( " " ) , " Path to .su3 file " )
2016-09-16 22:56:51 +00:00
( " reseed.urls " , value < std : : string > ( ) - > default_value (
" https://reseed.i2p-projekt.de/, "
" https://i2p.mooo.com/netDb/, "
" https://netdb.i2p2.no/, "
" https://us.reseed.i2p2.no:444/, "
" https://uk.reseed.i2p2.no:444/, "
" https://i2p.manas.ca:8443/, "
" https://i2p-0.manas.ca:8443/, "
" https://reseed.i2p.vzaws.com:8443/, "
" https://download.xxlspeed.com/, "
2016-10-10 20:31:26 +00:00
" https://reseed-ru.lngserv.ru/, "
" https://reseed.atomike.ninja/ "
2016-09-16 22:56:51 +00:00
) , " Reseed URLs, separated by comma " )
2016-08-12 14:33:53 +00:00
;
2016-10-12 10:23:43 +00:00
options_description addressbook ( " AddressBook options " ) ;
addressbook . add_options ( )
( " addressbook.defaulturl " , value < std : : string > ( ) - > default_value (
" http://joajgazyztfssty4w2on5oaqksz6tqoxbduy553y34mf4byv6gpq.b32.i2p/export/alive-hosts.txt "
) , " AddressBook subscription URL for initial setup " )
( " addressbook.subscriptions " , value < std : : string > ( ) - > default_value ( " " ) ,
" AddressBook subscriptions URLs, separated by comma " ) ;
2016-08-12 14:33:53 +00:00
options_description trust ( " Trust options " ) ;
trust . add_options ( )
2016-10-28 20:17:48 +00:00
( " trust.enabled " , value < bool > ( ) - > default_value ( false ) , " Enable explicit trust options " )
2016-08-12 14:33:53 +00:00
( " trust.family " , value < std : : string > ( ) - > default_value ( " " ) , " Router Familiy to trust for first hops " )
2016-10-28 16:50:26 +00:00
( " trust.routers " , value < std : : string > ( ) - > default_value ( " " ) , " Only Connect to these routers " )
2016-10-28 20:17:48 +00:00
( " trust.hidden " , value < bool > ( ) - > default_value ( false ) , " Should we hide our router from other routers? " ) ;
2016-10-12 10:23:43 +00:00
2016-10-20 13:12:15 +00:00
options_description websocket ( " Websocket Options " ) ;
websocket . add_options ( )
( " websockets.enabled " , value < bool > ( ) - > default_value ( false ) , " enable websocket server " )
( " websockets.address " , value < std : : string > ( ) - > default_value ( " 127.0.0.1 " ) , " address to bind websocket server on " )
( " websockets.port " , value < uint16_t > ( ) - > default_value ( 7666 ) , " port to bind websocket server on " ) ;
2016-01-20 00:00:00 +00:00
m_OptionsDesc
. add ( general )
2016-06-01 01:37:32 +00:00
. add ( limits )
2016-01-20 00:00:00 +00:00
. add ( httpserver )
. add ( httpproxy )
. add ( socksproxy )
. add ( sam )
. add ( bob )
2016-06-01 01:37:32 +00:00
. add ( i2cp )
2016-01-20 00:00:00 +00:00
. add ( i2pcontrol )
2016-07-12 00:00:00 +00:00
. add ( upnp )
2016-06-17 15:03:33 +00:00
. add ( precomputation )
2016-08-12 14:33:53 +00:00
. add ( reseed )
2016-10-12 10:23:43 +00:00
. add ( addressbook )
2016-10-20 13:12:15 +00:00
. add ( trust )
. add ( websocket )
2016-01-20 00:00:00 +00:00
;
}
void ParseCmdline ( int argc , char * argv [ ] ) {
try {
2016-01-27 00:00:00 +00:00
auto style = boost : : program_options : : command_line_style : : unix_style
| boost : : program_options : : command_line_style : : allow_long_disguise ;
style & = ~ boost : : program_options : : command_line_style : : allow_guessing ;
2016-06-28 13:00:00 +00:00
store ( parse_command_line ( argc , argv , m_OptionsDesc , style ) , m_Options ) ;
2016-02-11 16:18:15 +00:00
} catch ( boost : : program_options : : error & e ) {
2016-01-20 00:00:00 +00:00
std : : cerr < < " args: " < < e . what ( ) < < std : : endl ;
exit ( EXIT_FAILURE ) ;
}
2016-01-27 00:00:00 +00:00
if ( m_Options . count ( " help " ) | | m_Options . count ( " h " ) ) {
2016-01-20 00:00:00 +00:00
std : : cout < < " i2pd version " < < I2PD_VERSION < < " ( " < < I2P_VERSION < < " ) " < < std : : endl ;
std : : cout < < m_OptionsDesc ;
exit ( EXIT_SUCCESS ) ;
}
}
void ParseConfig ( const std : : string & path ) {
2016-02-11 15:54:36 +00:00
if ( path = = " " ) return ;
2016-01-24 11:04:41 +00:00
2016-01-20 00:00:00 +00:00
std : : ifstream config ( path , std : : ios : : in ) ;
2016-02-11 15:54:36 +00:00
if ( ! config . is_open ( ) )
{
2016-01-20 00:00:00 +00:00
std : : cerr < < " missing/unreadable config file: " < < path < < std : : endl ;
exit ( EXIT_FAILURE ) ;
}
2016-02-11 15:54:36 +00:00
try
{
store ( boost : : program_options : : parse_config_file ( config , m_OptionsDesc ) , m_Options ) ;
}
catch ( boost : : program_options : : error & e )
{
2016-01-20 00:00:00 +00:00
std : : cerr < < e . what ( ) < < std : : endl ;
exit ( EXIT_FAILURE ) ;
} ;
}
void Finalize ( ) {
notify ( m_Options ) ;
2016-02-10 00:00:00 +00:00
}
bool IsDefault ( const char * name ) {
if ( ! m_Options . count ( name ) )
throw " try to check non-existent option " ;
if ( m_Options [ name ] . defaulted ( ) )
return true ;
return false ;
}
2016-01-20 00:00:00 +00:00
} // namespace config
} // namespace i2p