From ed517d7ebf8769bb48b200e65ec8e723838f6ca9 Mon Sep 17 00:00:00 2001 From: ammorais Date: Fri, 10 Jul 2009 16:40:42 +0000 Subject: [PATCH] More of the same git-svn-id: http://svn.code.sf.net/p/retroshare/code/branches/ammorais_branch@1350 b45a01b8-16f6-495d-af2f-9b41ad6348cc --- libretroshare/src/Makefile | 21 +- .../src/_commonfuncs/commonfuncs.pri | 6 + .../src/_commonfuncs/getcurrentts.cc | 52 + libretroshare/src/_commonfuncs/getcurrentts.h | 6 + libretroshare/src/_dht/b64.cc | 478 ++++ libretroshare/src/_dht/b64.h | 42 + libretroshare/src/_dht/dht.pri | 16 + libretroshare/src/_dht/dht_bootstrap.cc | 414 +++ libretroshare/src/_dht/dht_bootstrap.h | 94 + libretroshare/src/_dht/dht_check_peers.cc | 432 +++ libretroshare/src/_dht/dht_check_peers.h | 143 + libretroshare/src/_dht/dhtclient.h | 74 + libretroshare/src/_dht/dhthandler.cc | 698 +++++ libretroshare/src/_dht/dhthandler.h | 107 + libretroshare/src/_dht/odhtmgr_test.cc | 157 ++ libretroshare/src/_dht/odhtpost_test.cc | 65 + libretroshare/src/_dht/odhtstr_test.cc | 88 + libretroshare/src/_dht/opendht.cc | 821 ++++++ libretroshare/src/_dht/opendht.h | 84 + libretroshare/src/_dht/opendhtmgr.cc | 192 ++ libretroshare/src/_dht/opendhtmgr.h | 82 + libretroshare/src/_dht/servers.txt | 163 ++ libretroshare/src/_dht/tst.ini | 272 ++ libretroshare/src/_pqi/authgpg.cc | 2335 +++++++++++++++++ libretroshare/src/_pqi/authgpg.h | 385 +++ libretroshare/src/_pqi/pqi.pri | 7 + libretroshare/src/_rsiface/rsiface.pri | 1 + libretroshare/src/_rsserver/p3blog.cc | 2 +- libretroshare/src/_rsserver/p3blog.h | 23 +- libretroshare/src/_rsserver/p3face-config.cc | 7 + libretroshare/src/_rsserver/p3face-msgs.cc | 9 + libretroshare/src/_rsserver/p3face-server.cc | 6 + libretroshare/src/_rsserver/p3face-startup.cc | 4 + libretroshare/src/_rsserver/p3face.cc | 239 -- libretroshare/src/_rsserver/p3face.h | 178 +- libretroshare/src/_rsserver/p3files.h | 123 + libretroshare/src/_rsserver/p3msgs.cc | 191 ++ libretroshare/src/_rsserver/p3msgs.h | 80 + libretroshare/src/_rsserver/p3peers.cc | 1016 +++++++ libretroshare/src/_rsserver/p3peers.h | 98 + libretroshare/src/_rsserver/p3photo.cc | 143 + libretroshare/src/_rsserver/p3photo.h | 70 + libretroshare/src/_rsserver/p3rank.cc | 104 + libretroshare/src/_rsserver/p3rank.h | 64 + libretroshare/src/_rsserver/rsserver.cc | 429 +++ libretroshare/src/_rsserver/rsserver.h | 181 ++ libretroshare/src/_rsserver/rsserver.pri | 28 +- libretroshare/src/_rsserver/testrschanid.cc | 59 + libretroshare/src/libretroshare.pro | 4 + libretroshare/src/pqi/pqipersongrp.h | 2 +- 50 files changed, 9855 insertions(+), 440 deletions(-) create mode 100644 libretroshare/src/_commonfuncs/commonfuncs.pri create mode 100644 libretroshare/src/_commonfuncs/getcurrentts.cc create mode 100644 libretroshare/src/_commonfuncs/getcurrentts.h create mode 100644 libretroshare/src/_dht/b64.cc create mode 100644 libretroshare/src/_dht/b64.h create mode 100644 libretroshare/src/_dht/dht.pri create mode 100644 libretroshare/src/_dht/dht_bootstrap.cc create mode 100644 libretroshare/src/_dht/dht_bootstrap.h create mode 100644 libretroshare/src/_dht/dht_check_peers.cc create mode 100644 libretroshare/src/_dht/dht_check_peers.h create mode 100644 libretroshare/src/_dht/dhtclient.h create mode 100644 libretroshare/src/_dht/dhthandler.cc create mode 100644 libretroshare/src/_dht/dhthandler.h create mode 100644 libretroshare/src/_dht/odhtmgr_test.cc create mode 100644 libretroshare/src/_dht/odhtpost_test.cc create mode 100644 libretroshare/src/_dht/odhtstr_test.cc create mode 100644 libretroshare/src/_dht/opendht.cc create mode 100644 libretroshare/src/_dht/opendht.h create mode 100644 libretroshare/src/_dht/opendhtmgr.cc create mode 100644 libretroshare/src/_dht/opendhtmgr.h create mode 100644 libretroshare/src/_dht/servers.txt create mode 100644 libretroshare/src/_dht/tst.ini create mode 100644 libretroshare/src/_pqi/authgpg.cc create mode 100644 libretroshare/src/_pqi/authgpg.h create mode 100644 libretroshare/src/_pqi/pqi.pri create mode 100644 libretroshare/src/_rsserver/p3face-config.cc create mode 100644 libretroshare/src/_rsserver/p3face-msgs.cc create mode 100644 libretroshare/src/_rsserver/p3face-server.cc create mode 100644 libretroshare/src/_rsserver/p3face-startup.cc delete mode 100644 libretroshare/src/_rsserver/p3face.cc create mode 100644 libretroshare/src/_rsserver/p3files.h create mode 100644 libretroshare/src/_rsserver/p3msgs.cc create mode 100644 libretroshare/src/_rsserver/p3msgs.h create mode 100644 libretroshare/src/_rsserver/p3peers.cc create mode 100644 libretroshare/src/_rsserver/p3peers.h create mode 100644 libretroshare/src/_rsserver/p3photo.cc create mode 100644 libretroshare/src/_rsserver/p3photo.h create mode 100644 libretroshare/src/_rsserver/p3rank.cc create mode 100644 libretroshare/src/_rsserver/p3rank.h create mode 100644 libretroshare/src/_rsserver/rsserver.cc create mode 100644 libretroshare/src/_rsserver/rsserver.h create mode 100644 libretroshare/src/_rsserver/testrschanid.cc diff --git a/libretroshare/src/Makefile b/libretroshare/src/Makefile index b86c89e2c..9b6de90a0 100644 --- a/libretroshare/src/Makefile +++ b/libretroshare/src/Makefile @@ -1,6 +1,6 @@ ############################################################################# # Makefile for building: libretroshare.a -# Generated by qmake (2.01a) (Qt 4.5.2) on: Thu Jul 9 23:31:15 2009 +# Generated by qmake (2.01a) (Qt 4.5.2) on: Fri Jul 10 06:58:42 2009 # Project: libretroshare.pro # Template: lib # Command: /usr/bin/qmake -spec /usr/share/qt4/mkspecs/linux-g++ -unix CONFIG+=debug -o Makefile libretroshare.pro @@ -13,7 +13,7 @@ CXX = g++ DEFINES = -DDEBUG -DP3TURTLE_DEBUG -DCONTROL_DEBUG -DFT_DEBUG -DPQI_USE_XPGP -DMINIUPNPC_VERSION=10 -DQT_NO_DEBUG -DQT_GUI_LIB -DQT_CORE_LIB -DQT_SHARED CFLAGS = -pipe -march=native -mtune=native -O2 -pipe -fPIC -Wall -W -D_REENTRANT $(DEFINES) CXXFLAGS = -pipe -g -Wall -march=native -mtune=native -O2 -pipe -fPIC -Wall -W -D_REENTRANT $(DEFINES) -INCPATH = -I/usr/share/qt4/mkspecs/linux-g++ -I. -I/usr/include/qt4/QtCore -I/usr/include/qt4/QtGui -I/usr/include/qt4 -I_rsiface -I.. -I. -I../../../../openssl-0.9.7g-xpgp-0.1c/include -I../../../../miniupnpc-1.0 -I. +INCPATH = -I/usr/share/qt4/mkspecs/linux-g++ -I. -I/usr/include/qt4/QtCore -I/usr/include/qt4/QtGui -I/usr/include/qt4 -I_rsiface -I.. -I_rsserver -I.. -I_commonfuncs -I.. -I_dht -I.. -I_pqi -I.. -I. -I../../../../openssl-0.9.7g-xpgp-0.1c/include -I../../../../miniupnpc-1.0 -I. AR = ar cqs RANLIB = QMAKE = /usr/bin/qmake @@ -266,6 +266,10 @@ DIST = /usr/share/qt4/mkspecs/common/g++.conf \ /usr/share/qt4/mkspecs/features/exclusive_builds.prf \ /usr/share/qt4/mkspecs/features/default_pre.prf \ _rsiface/rsiface.pri \ + _rsserver/rsserver.pri \ + _commonfuncs/commonfuncs.pri \ + _dht/dht.pri \ + _pqi/pqi.pri \ /usr/share/qt4/mkspecs/features/release.prf \ /usr/share/qt4/mkspecs/features/default_post.prf \ /usr/share/qt4/mkspecs/features/static.prf \ @@ -327,6 +331,10 @@ Makefile: libretroshare.pro /usr/share/qt4/mkspecs/linux-g++/qmake.conf /usr/sh /usr/share/qt4/mkspecs/features/exclusive_builds.prf \ /usr/share/qt4/mkspecs/features/default_pre.prf \ _rsiface/rsiface.pri \ + _rsserver/rsserver.pri \ + _commonfuncs/commonfuncs.pri \ + _dht/dht.pri \ + _pqi/pqi.pri \ /usr/share/qt4/mkspecs/features/release.prf \ /usr/share/qt4/mkspecs/features/default_post.prf \ /usr/share/qt4/mkspecs/features/static.prf \ @@ -352,6 +360,10 @@ Makefile: libretroshare.pro /usr/share/qt4/mkspecs/linux-g++/qmake.conf /usr/sh /usr/share/qt4/mkspecs/features/exclusive_builds.prf: /usr/share/qt4/mkspecs/features/default_pre.prf: _rsiface/rsiface.pri: +_rsserver/rsserver.pri: +_commonfuncs/commonfuncs.pri: +_dht/dht.pri: +_pqi/pqi.pri: /usr/share/qt4/mkspecs/features/release.prf: /usr/share/qt4/mkspecs/features/default_post.prf: /usr/share/qt4/mkspecs/features/static.prf: @@ -372,7 +384,7 @@ qmake: FORCE dist: @$(CHK_DIR_EXISTS) temp/linux-g++/obj/retroshare1.0.0 || $(MKDIR) temp/linux-g++/obj/retroshare1.0.0 - $(COPY_FILE) --parents $(SOURCES) $(DIST) temp/linux-g++/obj/retroshare1.0.0/ && $(COPY_FILE) --parents /rsinit.h /rsiface.h /rscontrol.h /notifybase.h /rsifacereal.h /rstypes.h /rsfiles.h /rsexpr.h /rsgame.h /rsforums.h /rsqblog.h /rschannels.h /rsdisc.h /rsdistrib.h /rsmsgs.h /rsnotify.h dbase/cachestrapper.h dbase/fimonitor.h dbase/findex.h dbase/fistore.h dht/b64.h dht/dhtclient.h dht/opendht.h dht/opendhtmgr.h dht/opendhtstr.h ft/ftcontroller.h ft/ftdata.h ft/ftdatamultiplex.h ft/ftdbase.h ft/ftextralist.h ft/ftfilecreator.h ft/ftfileprovider.h ft/ftfilesearch.h ft/ftsearch.h ft/ftserver.h ft/fttransfermodule.h pqi/authssl.h pqi/authxpgp.h pqi/cleanupxpgp.h pqi/p3authmgr.h pqi/p3cfgmgr.h pqi/p3connmgr.h pqi/p3dhtmgr.h pqi/p3notify.h pqi/p3upnpmgr.h pqi/pqi.h pqi/pqi_base.h pqi/pqiarchive.h pqi/pqiassist.h pqi/pqibin.h pqi/pqihandler.h pqi/pqihash.h pqi/pqiindic.h pqi/pqilistener.h pqi/pqiloopback.h pqi/pqimonitor.h pqi/pqinetwork.h pqi/pqinotify.h pqi/pqiperson.h pqi/pqipersongrp.h pqi/pqisecurity.h pqi/pqiservice.h pqi/pqistore.h pqi/pqissl.h pqi/pqissllistener.h pqi/pqisslpersongrp.h pqi/pqissludp.h pqi/pqistreamer.h pqi/sslcert.h pqi/xpgpcert.h rsiface/rschannels.h rsiface/rsdisc.h rsiface/rsdistrib.h rsiface/rsexpr.h rsiface/rsfiles.h rsiface/rsforums.h rsiface/rsgame.h rsiface/rsiface.h rsiface/rsmsgs.h rsiface/rsnotify.h rsiface/rspeers.h rsiface/rsphoto.h rsiface/rsQblog.h rsiface/rsrank.h rsiface/rsstatus.h rsiface/rstypes.h rsserver/p3Blog.h rsserver/p3discovery.h rsserver/p3face.h rsserver/p3files.h rsserver/p3msgs.h rsserver/p3peers.h rsserver/p3photo.h rsserver/p3rank.h serialiser/rsbaseitems.h serialiser/rsbaseserial.h serialiser/rschannelitems.h serialiser/rsconfigitems.h serialiser/rsdiscitems.h serialiser/rsdistribitems.h serialiser/rsforumitems.h serialiser/rsgameitems.h serialiser/rsmsgitems.h serialiser/rsphotoitems.h serialiser/rsqblogitems.h serialiser/rsrankitems.h serialiser/rsserial.h serialiser/rsserviceids.h serialiser/rsserviceitems.h serialiser/rsstatusitems.h serialiser/rstlvbase.h serialiser/rstlvkeys.h serialiser/rstlvkvwide.h serialiser/rstlvtypes.h serialiser/rstlvutil.h services/p3channels.h services/p3chatservice.h services/p3disc.h services/p3distrib.h services/p3forums.h services/p3gamelauncher.h services/p3gameservice.h services/p3msgservice.h services/p3photoservice.h services/p3portservice.h services/p3Qblog.h services/p3ranking.h services/p3service.h services/p3status.h turtle/p3turtle.h turtle/turtletypes.h turtle/rsturtleitem.h tcponudp/extaddrfinder.h tcponudp/bio_tou.h tcponudp/tcppacket.h tcponudp/tcpstream.h tcponudp/tou.h tcponudp/tou_errno.h tcponudp/tou_net.h tcponudp/udplayer.h tcponudp/udpsorter.h upnp/upnphandler.h upnp/upnputil.h util/rsdebug.h util/rsdir.h util/rsnet.h util/rsprint.h util/rsthreads.h util/rswin.h util/rsversion.h temp/linux-g++/obj/retroshare1.0.0/ && $(COPY_FILE) --parents dht/dht_check_peers.cc dht/dht_bootstrap.cc pqi/xpgp_id.cc rsserver/p3face-msgs.cc rsserver/rsiface.cc rsserver/rstypes.cc rsserver/p3face-startup.cc rsserver/p3face-config.cc rsserver/p3face-server.cc rsserver/p3Blog.cc rsserver/p3discovery.cc rsserver/p3msgs.cc rsserver/p3photo.cc rsserver/p3rank.cc rsserver/p3peers.cc ft/ftcontroller.cc ft/ftserver.cc ft/ftdbase.cc ft/fttransfermodule.cc ft/ftdatamultiplex.cc ft/ftfilesearch.cc ft/ftextralist.cc ft/ftfilecreator.cc ft/ftdata.cc ft/ftfileprovider.cc upnp/upnputil.c dht/opendhtmgr.cc upnp/upnphandler.cc dht/opendht.cc dht/opendhtstr.cc dht/b64.c services/p3portservice.cc services/p3channels.cc services/p3forums.cc services/p3Qblog.cc services/p3status.cc services/p3distrib.cc services/p3photoservice.cc services/p3disc.cc services/p3ranking.cc services/p3gamelauncher.cc services/p3msgservice.cc services/p3chatservice.cc services/p3service.cc turtle/p3turtle.cc turtle/rsturtleitem.cc dbase/rsexpr.cc dbase/cachestrapper.cc dbase/fistore.cc dbase/fimonitor.cc dbase/findex.cc pqi/p3notify.cc pqi/pqipersongrp.cc pqi/pqihandler.cc pqi/pqiservice.cc pqi/pqiperson.cc pqi/pqissludp.cc pqi/authxpgp.cc pqi/cleanupxpgp.cc pqi/pqisslpersongrp.cc pqi/pqissllistener.cc pqi/pqissl.cc pqi/pqistore.cc pqi/p3authmgr.cc pqi/p3cfgmgr.cc pqi/p3connmgr.cc pqi/p3dhtmgr.cc pqi/pqiarchive.cc pqi/pqibin.cc pqi/pqimonitor.cc pqi/pqistreamer.cc pqi/pqiloopback.cc pqi/pqinetwork.cc pqi/pqisecurity.cc serialiser/rsqblogitems.cc serialiser/rsstatusitems.cc serialiser/rschannelitems.cc serialiser/rsforumitems.cc serialiser/rsdistribitems.cc serialiser/rsgameitems.cc serialiser/rsphotoitems.cc serialiser/rsrankitems.cc serialiser/rsconfigitems.cc serialiser/rsdiscitems.cc serialiser/rsmsgitems.cc serialiser/rsbaseitems.cc serialiser/rstlvkvwide.cc serialiser/rstlvimage.cc serialiser/rstlvutil.cc serialiser/rstlvfileitem.cc serialiser/rstlvkeys.cc serialiser/rsbaseserial.cc serialiser/rstlvbase.cc serialiser/rstlvtypes.cc serialiser/rsserial.cc tcponudp/extaddrfinder.cc tcponudp/bss_tou.c tcponudp/tcpstream.cc tcponudp/tou.cc tcponudp/tcppacket.cc tcponudp/udpsorter.cc tcponudp/tou_net.cc tcponudp/udplayer.cc util/rsdebug.cc util/rsdir.cc util/rsnet.cc util/rsprint.cc util/rsthreads.cc util/rsversion.cc temp/linux-g++/obj/retroshare1.0.0/ && (cd `dirname temp/linux-g++/obj/retroshare1.0.0` && $(TAR) retroshare1.0.0.tar retroshare1.0.0 && $(COMPRESS) retroshare1.0.0.tar) && $(MOVE) `dirname temp/linux-g++/obj/retroshare1.0.0`/retroshare1.0.0.tar.gz . && $(DEL_FILE) -r temp/linux-g++/obj/retroshare1.0.0 + $(COPY_FILE) --parents $(SOURCES) $(DIST) temp/linux-g++/obj/retroshare1.0.0/ && $(COPY_FILE) --parents _pqi/authgpg.h dbase/cachestrapper.h dbase/fimonitor.h dbase/findex.h dbase/fistore.h dht/b64.h dht/dhtclient.h dht/opendht.h dht/opendhtmgr.h dht/opendhtstr.h ft/ftcontroller.h ft/ftdata.h ft/ftdatamultiplex.h ft/ftdbase.h ft/ftextralist.h ft/ftfilecreator.h ft/ftfileprovider.h ft/ftfilesearch.h ft/ftsearch.h ft/ftserver.h ft/fttransfermodule.h pqi/authssl.h pqi/authxpgp.h pqi/cleanupxpgp.h pqi/p3authmgr.h pqi/p3cfgmgr.h pqi/p3connmgr.h pqi/p3dhtmgr.h pqi/p3notify.h pqi/p3upnpmgr.h pqi/pqi.h pqi/pqi_base.h pqi/pqiarchive.h pqi/pqiassist.h pqi/pqibin.h pqi/pqihandler.h pqi/pqihash.h pqi/pqiindic.h pqi/pqilistener.h pqi/pqiloopback.h pqi/pqimonitor.h pqi/pqinetwork.h pqi/pqinotify.h pqi/pqiperson.h pqi/pqipersongrp.h pqi/pqisecurity.h pqi/pqiservice.h pqi/pqistore.h pqi/pqissl.h pqi/pqissllistener.h pqi/pqisslpersongrp.h pqi/pqissludp.h pqi/pqistreamer.h pqi/sslcert.h pqi/xpgpcert.h rsiface/rschannels.h rsiface/rsdisc.h rsiface/rsdistrib.h rsiface/rsexpr.h rsiface/rsfiles.h rsiface/rsforums.h rsiface/rsgame.h rsiface/rsiface.h rsiface/rsmsgs.h rsiface/rsnotify.h rsiface/rspeers.h rsiface/rsphoto.h rsiface/rsQblog.h rsiface/rsrank.h rsiface/rsstatus.h rsiface/rstypes.h rsserver/p3Blog.h rsserver/p3discovery.h rsserver/p3face.h rsserver/p3files.h rsserver/p3msgs.h rsserver/p3peers.h rsserver/p3photo.h rsserver/p3rank.h serialiser/rsbaseitems.h serialiser/rsbaseserial.h serialiser/rschannelitems.h serialiser/rsconfigitems.h serialiser/rsdiscitems.h serialiser/rsdistribitems.h serialiser/rsforumitems.h serialiser/rsgameitems.h serialiser/rsmsgitems.h serialiser/rsphotoitems.h serialiser/rsqblogitems.h serialiser/rsrankitems.h serialiser/rsserial.h serialiser/rsserviceids.h serialiser/rsserviceitems.h serialiser/rsstatusitems.h serialiser/rstlvbase.h serialiser/rstlvkeys.h serialiser/rstlvkvwide.h serialiser/rstlvtypes.h serialiser/rstlvutil.h services/p3channels.h services/p3chatservice.h services/p3disc.h services/p3distrib.h services/p3forums.h services/p3gamelauncher.h services/p3gameservice.h services/p3msgservice.h services/p3photoservice.h services/p3portservice.h services/p3Qblog.h services/p3ranking.h services/p3service.h services/p3status.h turtle/p3turtle.h turtle/turtletypes.h turtle/rsturtleitem.h tcponudp/extaddrfinder.h tcponudp/bio_tou.h tcponudp/tcppacket.h tcponudp/tcpstream.h tcponudp/tou.h tcponudp/tou_errno.h tcponudp/tou_net.h tcponudp/udplayer.h tcponudp/udpsorter.h upnp/upnphandler.h upnp/upnputil.h util/rsdebug.h util/rsdir.h util/rsnet.h util/rsprint.h util/rsthreads.h util/rswin.h util/rsversion.h temp/linux-g++/obj/retroshare1.0.0/ && $(COPY_FILE) --parents dht/dht_check_peers.cc dht/dht_bootstrap.cc pqi/xpgp_id.cc rsserver/p3face-msgs.cc rsserver/rsiface.cc rsserver/rstypes.cc rsserver/p3face-startup.cc rsserver/p3face-config.cc rsserver/p3face-server.cc rsserver/p3Blog.cc rsserver/p3discovery.cc rsserver/p3msgs.cc rsserver/p3photo.cc rsserver/p3rank.cc rsserver/p3peers.cc ft/ftcontroller.cc ft/ftserver.cc ft/ftdbase.cc ft/fttransfermodule.cc ft/ftdatamultiplex.cc ft/ftfilesearch.cc ft/ftextralist.cc ft/ftfilecreator.cc ft/ftdata.cc ft/ftfileprovider.cc upnp/upnputil.c dht/opendhtmgr.cc upnp/upnphandler.cc dht/opendht.cc dht/opendhtstr.cc dht/b64.c services/p3portservice.cc services/p3channels.cc services/p3forums.cc services/p3Qblog.cc services/p3status.cc services/p3distrib.cc services/p3photoservice.cc services/p3disc.cc services/p3ranking.cc services/p3gamelauncher.cc services/p3msgservice.cc services/p3chatservice.cc services/p3service.cc turtle/p3turtle.cc turtle/rsturtleitem.cc dbase/rsexpr.cc dbase/cachestrapper.cc dbase/fistore.cc dbase/fimonitor.cc dbase/findex.cc pqi/p3notify.cc pqi/pqipersongrp.cc pqi/pqihandler.cc pqi/pqiservice.cc pqi/pqiperson.cc pqi/pqissludp.cc pqi/authxpgp.cc pqi/cleanupxpgp.cc pqi/pqisslpersongrp.cc pqi/pqissllistener.cc pqi/pqissl.cc pqi/pqistore.cc pqi/p3authmgr.cc pqi/p3cfgmgr.cc pqi/p3connmgr.cc pqi/p3dhtmgr.cc pqi/pqiarchive.cc pqi/pqibin.cc pqi/pqimonitor.cc pqi/pqistreamer.cc pqi/pqiloopback.cc pqi/pqinetwork.cc pqi/pqisecurity.cc serialiser/rsqblogitems.cc serialiser/rsstatusitems.cc serialiser/rschannelitems.cc serialiser/rsforumitems.cc serialiser/rsdistribitems.cc serialiser/rsgameitems.cc serialiser/rsphotoitems.cc serialiser/rsrankitems.cc serialiser/rsconfigitems.cc serialiser/rsdiscitems.cc serialiser/rsmsgitems.cc serialiser/rsbaseitems.cc serialiser/rstlvkvwide.cc serialiser/rstlvimage.cc serialiser/rstlvutil.cc serialiser/rstlvfileitem.cc serialiser/rstlvkeys.cc serialiser/rsbaseserial.cc serialiser/rstlvbase.cc serialiser/rstlvtypes.cc serialiser/rsserial.cc tcponudp/extaddrfinder.cc tcponudp/bss_tou.c tcponudp/tcpstream.cc tcponudp/tou.cc tcponudp/tcppacket.cc tcponudp/udpsorter.cc tcponudp/tou_net.cc tcponudp/udplayer.cc util/rsdebug.cc util/rsdir.cc util/rsnet.cc util/rsprint.cc util/rsthreads.cc util/rsversion.cc temp/linux-g++/obj/retroshare1.0.0/ && (cd `dirname temp/linux-g++/obj/retroshare1.0.0` && $(TAR) retroshare1.0.0.tar retroshare1.0.0 && $(COMPRESS) retroshare1.0.0.tar) && $(MOVE) `dirname temp/linux-g++/obj/retroshare1.0.0`/retroshare1.0.0.tar.gz . && $(DEL_FILE) -r temp/linux-g++/obj/retroshare1.0.0 clean:compiler_clean @@ -1197,7 +1209,8 @@ temp/linux-g++/obj/p3Qblog.o: services/p3Qblog.cc serialiser/rsqblogitems.h \ $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp/linux-g++/obj/p3Qblog.o services/p3Qblog.cc temp/linux-g++/obj/p3status.o: services/p3status.cc services/p3status.h \ - rsiface/rsstatus.h + rsiface/rsstatus.h \ + _rsiface/rsstatus.h $(CXX) -c $(CXXFLAGS) $(INCPATH) -o temp/linux-g++/obj/p3status.o services/p3status.cc temp/linux-g++/obj/p3distrib.o: services/p3distrib.cc rsiface/rsdistrib.h \ diff --git a/libretroshare/src/_commonfuncs/commonfuncs.pri b/libretroshare/src/_commonfuncs/commonfuncs.pri new file mode 100644 index 000000000..b9ed87bd8 --- /dev/null +++ b/libretroshare/src/_commonfuncs/commonfuncs.pri @@ -0,0 +1,6 @@ +INCLUDEPATH += $$PWD \ + ../$$PWP +DEPENDPATH += $$PWD + +HEADERS += getcurrentts.h +SOURCES += getcurrentts.cc diff --git a/libretroshare/src/_commonfuncs/getcurrentts.cc b/libretroshare/src/_commonfuncs/getcurrentts.cc new file mode 100644 index 000000000..3593e5001 --- /dev/null +++ b/libretroshare/src/_commonfuncs/getcurrentts.cc @@ -0,0 +1,52 @@ +#include "getcurrentts.h" + +/* + * "$Id: getcurrentts.cc,v 1.5 2007-04-15 18:45:23 rmf24 Exp $" + * + * RetroShare C++ Interface. + * + * Copyright 2004-2006 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#ifdef WINDOWS_SYS +#include +#include +#endif +#else +#include +#include +#endif + +static double getCurrentTS() +{ + +#ifndef WINDOWS_SYS + struct timeval cts_tmp; + gettimeofday(&cts_tmp, NULL); + double cts = (cts_tmp.tv_sec) + ((double) cts_tmp.tv_usec) / 1000000.0; +#else + struct _timeb timebuf; + _ftime( &timebuf); + double cts = (timebuf.time) + ((double) timebuf.millitm) / 1000.0; +#endif + return cts; +} + + diff --git a/libretroshare/src/_commonfuncs/getcurrentts.h b/libretroshare/src/_commonfuncs/getcurrentts.h new file mode 100644 index 000000000..bb7d0b39b --- /dev/null +++ b/libretroshare/src/_commonfuncs/getcurrentts.h @@ -0,0 +1,6 @@ +#ifndef GETCURRENTTS_H +#define GETCURRENTTS_H + +static double getCurrentTS(); + +#endif // GETCURRENTTS_H diff --git a/libretroshare/src/_dht/b64.cc b/libretroshare/src/_dht/b64.cc new file mode 100644 index 000000000..ae77a1877 --- /dev/null +++ b/libretroshare/src/_dht/b64.cc @@ -0,0 +1,478 @@ +/*********************************************************************\ + +MODULE NAME: b64.c + +AUTHOR: Bob Trower 08/04/01 + +PROJECT: Crypt Data Packaging + +COPYRIGHT: Copyright (c) Trantor Standard Systems Inc., 2001 + +NOTE: This source code may be used as you wish, subject to + the MIT license. See the LICENCE section below. + +DESCRIPTION: + This little utility implements the Base64 + Content-Transfer-Encoding standard described in + RFC1113 (http://www.faqs.org/rfcs/rfc1113.html). + + This is the coding scheme used by MIME to allow + binary data to be transferred by SMTP mail. + + Groups of 3 bytes from a binary stream are coded as + groups of 4 bytes in a text stream. + + The input stream is 'padded' with zeros to create + an input that is an even multiple of 3. + + A special character ('=') is used to denote padding so + that the stream can be decoded back to its exact size. + + Encoded output is formatted in lines which should + be a maximum of 72 characters to conform to the + specification. This program defaults to 72 characters, + but will allow more or less through the use of a + switch. The program enforces a minimum line size + of 4 characters. + + Example encoding: + + The stream 'ABCD' is 32 bits long. It is mapped as + follows: + + ABCD + + A (65) B (66) C (67) D (68) (None) (None) + 01000001 01000010 01000011 01000100 + + 16 (Q) 20 (U) 9 (J) 3 (D) 17 (R) 0 (A) NA (=) NA (=) + 010000 010100 001001 000011 010001 000000 000000 000000 + + + QUJDRA== + + Decoding is the process in reverse. A 'decode' lookup + table has been created to avoid string scans. + +DESIGN GOALS: Specifically: + Code is a stand-alone utility to perform base64 + encoding/decoding. It should be genuinely useful + when the need arises and it meets a need that is + likely to occur for some users. + Code acts as sample code to show the author's + design and coding style. + + Generally: + This program is designed to survive: + Everything you need is in a single source file. + It compiles cleanly using a vanilla ANSI C compiler. + It does its job correctly with a minimum of fuss. + The code is not overly clever, not overly simplistic + and not overly verbose. + Access is 'cut and paste' from a web page. + Terms of use are reasonable. + +VALIDATION: Non-trivial code is never without errors. This + file likely has some problems, since it has only + been tested by the author. It is expected with most + source code that there is a period of 'burn-in' when + problems are identified and corrected. That being + said, it is possible to have 'reasonably correct' + code by following a regime of unit test that covers + the most likely cases and regression testing prior + to release. This has been done with this code and + it has a good probability of performing as expected. + + Unit Test Cases: + + case 0:empty file: + CASE0.DAT -> -> + (Zero length target file created + on both encode and decode.) + + case 1:One input character: + CASE1.DAT A -> QQ== -> A + + case 2:Two input characters: + CASE2.DAT AB -> QUJD -> AB + + case 3:Three input characters: + CASE3.DAT ABC -> QUJD -> ABC + + case 4:Four input characters: + case4.dat ABCD -> QUJDRA== -> ABCD + + case 5:All chars from 0 to ff, linesize set to 50: + + AAECAwQFBgcICQoLDA0ODxAREhMUFRYXGBkaGxwdHh8gISIj + JCUmJygpKissLS4vMDEyMzQ1Njc4OTo7PD0+P0BBQkNERUZH + SElKS0xNTk9QUVJTVFVWV1hZWltcXV5fYGFiY2RlZmdoaWpr + bG1ub3BxcnN0dXZ3eHl6e3x9fn+AgYKDhIWGh4iJiouMjY6P + kJGSk5SVlpeYmZqbnJ2en6ChoqOkpaanqKmqq6ytrq+wsbKz + tLW2t7i5uru8vb6/wMHCw8TFxsfIycrLzM3Oz9DR0tPU1dbX + 2Nna29zd3t/g4eLj5OXm5+jp6uvs7e7v8PHy8/T19vf4+fr7 + /P3+/w== + + case 6:Mime Block from e-mail: + (Data same as test case 5) + + case 7: Large files: + Tested 28 MB file in/out. + + case 8: Random Binary Integrity: + This binary program (b64.exe) was encoded to base64, + back to binary and then executed. + + case 9 Stress: + All files in a working directory encoded/decoded + and compared with file comparison utility to + ensure that multiple runs do not cause problems + such as exhausting file handles, tmp storage, etc. + + ------------- + + Syntax, operation and failure: + All options/switches tested. Performs as + expected. + + case 10: + No Args -- Shows Usage Screen + Return Code 1 (Invalid Syntax) + case 11: + One Arg (invalid) -- Shows Usage Screen + Return Code 1 (Invalid Syntax) + case 12: + One Arg Help (-?) -- Shows detailed Usage Screen. + Return Code 0 (Success -- help request is valid). + case 13: + One Arg Help (-h) -- Shows detailed Usage Screen. + Return Code 0 (Success -- help request is valid). + case 14: + One Arg (valid) -- Uses stdin/stdout (filter) + Return Code 0 (Sucess) + case 15: + Two Args (invalid file) -- shows system error. + Return Code 2 (File Error) + case 16: + Encode non-existent file -- shows system error. + Return Code 2 (File Error) + case 17: + Out of disk space -- shows system error. + Return Code 3 (File I/O Error) + + ------------- + + Compile/Regression test: + gcc compiled binary under Cygwin + Microsoft Visual Studio under Windows 2000 + Microsoft Version 6.0 C under Windows 2000 + +DEPENDENCIES: None + +LICENCE: Copyright (c) 2001 Bob Trower, Trantor Standard Systems Inc. + + 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. + +VERSION HISTORY: + Bob Trower 08/04/01 -- Create Version 0.00.00B + +\******************************************************************* */ + +#include +#include + +/* +** Translation Table as described in RFC1113 +*/ +static const char cb64[]="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"; + +/* +** Translation Table to decode (created by author) +*/ +static const char cd64[]="|$$$}rstuvwxyz{$$$$$$$>?@ABCDEFGHIJKLMNOPQRSTUVW$$$$$$XYZ[\\]^_`abcdefghijklmnopq"; + +/* +** encodeblock +** +** encode 3 8-bit binary bytes as 4 '6-bit' characters +*/ +void encodeblock( unsigned char in[3], unsigned char out[4], int len ) +{ + out[0] = cb64[ in[0] >> 2 ]; + out[1] = cb64[ ((in[0] & 0x03) << 4) | ((in[1] & 0xf0) >> 4) ]; + out[2] = (unsigned char) (len > 1 ? cb64[ ((in[1] & 0x0f) << 2) | ((in[2] & 0xc0) >> 6) ] : '='); + out[3] = (unsigned char) (len > 2 ? cb64[ in[2] & 0x3f ] : '='); +} + +/* +** decodeblock +** +** decode 4 '6-bit' characters into 3 8-bit binary bytes +*/ +void decodeblock( unsigned char in[4], unsigned char out[3] ) +{ + out[ 0 ] = (unsigned char ) (((in[0] << 2) & 0xff) | ((in[1] >> 4) & 0xff)); + out[ 1 ] = (unsigned char ) (((in[1] << 4) & 0xff) | ((in[2] >> 2) & 0xff)); + out[ 2 ] = (unsigned char ) (((in[2] << 6) & 0xc0) | (in[3] & 0xff)); +} + + +/* mods ... Hacked it up badly ...Robert Fernie (c) */ + +#include +#include +#include +#include +#include +#include "b64.h" + +std::string displayBlock(unsigned char *arr, unsigned int len); + +std::string convertToBase64(std::string input) +{ + unsigned char in[3]; + unsigned char out[4]; + unsigned int len; + + std::string result; + + for(unsigned int i = 0; i < input.length(); i+= 3) + { + len = input.length() - i; + in[0] = input[i]; + if (len > 1) + in[1] = input[i+1]; + else + in[1] = 0; + + if (len > 2) + in[2] = input[i+2]; + else + in[2] = 0; + + + encodeblock(in, out, len); + //std::cerr << "eNcode Block in :" << displayBlock(in, 3); + //std::cerr << "eNcode Block out:" << displayBlock(out, 4); + + for(unsigned int j = 0; j < 4; j++) + { + result += out[j]; + } + } + + return result; +} + +std::string convertFromBase64(std::string input) +{ + unsigned char in[4]; + unsigned char out[3]; + unsigned int len, outlen; + + std::string result; + + for(unsigned int i = 0; i < input.length(); i+= 4) + { + len = input.length() - i; + if (len < 4) + { + /* error */ + std::cerr << "ERROR LENGTH in convertFromBase64"; + std::cerr << std::endl; + return result; + } + outlen = 3; + in[0] = input[i]; + in[1] = input[i+1]; + in[2] = input[i+2]; + in[3] = input[i+3]; + + if (in[3] == '=') + { + outlen--; + } + if (in[2] == '=') + { + outlen--; + } + //std::cerr << "Decode Block in :" << displayBlock(in, 4); + + for(unsigned int j = 0; j < 4; j++) + { + unsigned char v = input[i+j]; + v = (unsigned char) ((v < 43 || v > 122) ? 0 : cd64[ v - 43 ]); + if( v ) { + v = (unsigned char) ((v == '$') ? 0 : v - 61); + } + in[j] = v-1; + } + + decodeblock(in, out); + //std::cerr << "Decode Block out:" << displayBlock(out, 3); + + for(unsigned int j = 0; j < outlen; j++) + { + result += out[j]; + } + } + + return result; +} + + +std::string convertDataToBase64(unsigned char *data, uint32_t dlen) +{ + unsigned char in[3]; + unsigned char out[4]; + unsigned int len; + + std::string result; + + for(unsigned int i = 0; i < dlen; i+= 3) + { + len = dlen - i; + in[0] = data[i]; + if (len > 1) + in[1] = data[i+1]; + else + in[1] = 0; + + if (len > 2) + in[2] = data[i+2]; + else + in[2] = 0; + + + encodeblock(in, out, len); + //std::cerr << "eNcode Block in :" << displayBlock(in, 3); + //std::cerr << "eNcode Block out:" << displayBlock(out, 4); + + for(unsigned int j = 0; j < 4; j++) + { + result += out[j]; + } + } + return result; +} + + +uint32_t DataLenFromBase64(std::string input) +{ + uint32_t len = input.length(); + len = (len / 4) * 3; + /* remove extra char - if '=' */ + if (input[input.length()-1] == '=') + len--; + if (input[input.length()-2] == '=') + len--; + return len; +} + + +bool convertDataFromBase64(std::string input, unsigned char *data, uint32_t *dlen) +{ + unsigned char in[4]; + unsigned char out[3]; + unsigned int len, outlen; + unsigned int offset = 0; + + std::string result; + + len = DataLenFromBase64(input); + if (len > *dlen) + { + std::cerr << "ERROR LENGTH(1) in convertDataFromBase64"; + std::cerr << std::endl; + return false; + } + + for(unsigned int i = 0; i < input.length(); i+= 4) + { + len = input.length() - i; + if (len < 4) + { + /* error */ + std::cerr << "ERROR LENGTH in convertDataFromBase64"; + std::cerr << std::endl; + return false; + } + outlen = 3; + in[0] = input[i]; + in[1] = input[i+1]; + in[2] = input[i+2]; + in[3] = input[i+3]; + + if (in[3] == '=') + { + outlen--; + } + if (in[2] == '=') + { + outlen--; + } + //std::cerr << "Decode Block in :" << displayBlock(in, 4); + + for(unsigned int j = 0; j < 4; j++) + { + unsigned char v = input[i+j]; + v = (unsigned char) ((v < 43 || v > 122) ? 0 : cd64[ v - 43 ]); + if( v ) { + v = (unsigned char) ((v == '$') ? 0 : v - 61); + } + in[j] = v-1; + } + + decodeblock(in, out); + //std::cerr << "Decode Block out:" << displayBlock(out, 3); + + for(unsigned int j = 0; j < outlen; j++) + { + data[offset++] = out[j]; + } + } + + *dlen = offset; + return true; +} + + + + +std::string displayBlock(unsigned char *arr, unsigned int len) +{ + std::ostringstream out; + + for(unsigned int j = 0; j < len; j++) + { + out << std::hex << (int) arr[j] << "[" << arr[j] << "] "; + } + out << std::endl; + return out.str(); +} + + + + + + diff --git a/libretroshare/src/_dht/b64.h b/libretroshare/src/_dht/b64.h new file mode 100644 index 000000000..ec2344d62 --- /dev/null +++ b/libretroshare/src/_dht/b64.h @@ -0,0 +1,42 @@ +/* + * libretroshare/src/dht: b64.h + * + * Interface with OpenDHT for RetroShare. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + + +#ifndef B64_H +#define B64_H + +#include + +std::string convertToBase64(std::string input); +std::string convertFromBase64(std::string input); + + +uint32_t DataLenFromBase64(std::string input); +std::string convertDataToBase64(unsigned char *data, uint32_t dlen); +bool convertDataFromBase64(std::string input, unsigned char *data, uint32_t *dlen); + + +#endif + diff --git a/libretroshare/src/_dht/dht.pri b/libretroshare/src/_dht/dht.pri new file mode 100644 index 000000000..21bb5e138 --- /dev/null +++ b/libretroshare/src/_dht/dht.pri @@ -0,0 +1,16 @@ +INCLUDEPATH += $$PWD \ + ../$$PWP +DEPENDPATH += $$PWD +SOURCES = b64.cc \ + dht_bootstrap.cc \ + dht_check_peers.cc \ + dhthandler.cc \ + opendht.cc \ + opendhtmgr.cc +HEADERS = b64.h \ + dht_bootstrap.h \ + dhtclient.h \ + dht_check_peers.h \ + dhthandler.h \ + opendht.h \ + opendhtmgr.h diff --git a/libretroshare/src/_dht/dht_bootstrap.cc b/libretroshare/src/_dht/dht_bootstrap.cc new file mode 100644 index 000000000..ab89e5c93 --- /dev/null +++ b/libretroshare/src/_dht/dht_bootstrap.cc @@ -0,0 +1,414 @@ +/* + * libretroshare/src/dht: odhtmgr_test.cc + * + * Interface with OpenDHT for RetroShare. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + + + +/***** Test for the new DHT system *****/ + +#include "_dht/dht_bootstrap.h" + +#define BOOTSTRAP_DEBUG 1 + +namespace DHT_Bootstrap { + +void usage(char *name) +{ + std::cerr << "USAGE: " << name << " -o OwnId [ -p PeerId1 [ -p PeerId2 [ ... ] ] ] "; + std::cerr << std::endl; + exit(1); +} + + + +pqiConnectCbStun::pqiConnectCbStun() +{ +} + +pqiConnectCbStun::~pqiConnectCbStun() +{ +} + +void pqiConnectCbStun::addPeer(std::string id) +{ + RsStackMutex stack(peerMtx); /**** LOCK MUTEX ***/ + std::map::iterator it; + it = peerMap.find(id); + if (it == peerMap.end()) + { + StunDetails sd; + sd.id = id; + peerMap[id] = sd; + } +} + +void pqiConnectCbStun::peerStatus(std::string id, + struct sockaddr_in laddr, struct sockaddr_in raddr, + uint32_t type, uint32_t mode, uint32_t source) +{ +} + +void pqiConnectCbStun::printPeerStatus() +{ + RsStackMutex stack(peerMtx); /**** LOCK MUTEX ***/ + + time_t t = time(NULL); + std::string timestr = ctime(&t); + std::cerr << "BootstrapStatus: " << timestr; + std::cerr << "BootstrapStatus: " << peerMap.size() << " Peers"; + std::cerr << std::endl; + std::cerr << "BootstrapStatus: ID --------------------- DHT ENTRY ---"; + std::cerr << " EXT PORT -- STUN OK -- %AVAIL -- LAST DHT TS"; + std::cerr << std::endl; + + std::map::iterator it; + + for(it = peerMap.begin(); it != peerMap.end(); it++) + { + std::cerr << RsUtil::BinToHex(it->first); + + bool dhtActive = (time(NULL) - it->second.lastStatus < 1900); + bool stunActive = (time(NULL) - it->second.lastStunResult < 1900); + bool extPort = it->second.type & RS_NET_CONN_TCP_EXTERNAL; + float percentAvailable = it->second.stunResults * 100.0 / (it->second.stunAttempts + 0.0001); + + if (dhtActive) + { + std::cerr << " Yes --->"; + } + else + { + std::cerr << " No "; + } + + if (extPort) + { + std::cerr << " Yes --->"; + } + else + { + std::cerr << " No "; + } + + if (stunActive) + { + std::cerr << " Yes --->"; + } + else + { + std::cerr << " No "; + } + + std::cerr << " " << std::setw(4) << percentAvailable; + std::cerr << " "; + + if (it->second.lastStatus == 0) + { + std::cerr << " NEVER "; + } + else + { + std::cerr << " " << time(NULL) - it->second.lastStatus; + std::cerr << " secs ago "; + } + std::cerr << std::endl; + } +} + +void pqiConnectCbStun::stunPeer(std::string id, struct sockaddr_in peeraddr) +{ + std::cerr << "stunPeer: 0x" << RsUtil::BinToHex(id); + + std::cerr << std::endl; + + /* launch a publishThread */ + pthread_t tid; + + dhtStunData *pub = new dhtStunData; + pub->stunCb = this; + pub->id = id; + pub->toaddr = peeraddr; + + void *data = (void *) pub; + pthread_create(&tid, 0, &doStunPeer, data); + pthread_detach(tid); +} + + +void pqiConnectCbStun::peerConnectRequest(std::string id, + struct sockaddr_in raddr, uint32_t source) +{ +} + + +void pqiConnectCbStun::stunStatus(std::string id, struct sockaddr_in raddr, uint32_t type, uint32_t flags) +{ + addPeer(id); + { + RsStackMutex stack(peerMtx); /**** LOCK MUTEX ***/ + + std::map::iterator it; + it = peerMap.find(id); + if (it == peerMap.end()) + { + std::cerr << "peerStatus() for unknown Peer id: 0x" << RsUtil::BinToHex(id); + std::cerr << std::endl; + return; + } + it->second.raddr = raddr; + it->second.type = type; + it->second.lastStatus = time(NULL); + + it->second.stunAttempts++; /* as we are about to try! */ + } + + printPeerStatus(); + stunPeer(id, raddr); +} + +void pqiConnectCbStun::stunSuccess(std::string id, struct sockaddr_in toaddr, struct sockaddr_in ansaddr) +{ + + RsStackMutex stack(peerMtx); /**** LOCK MUTEX ***/ + + std::map::iterator it; + it = peerMap.find(id); + if (it == peerMap.end()) + { + std::cerr << "stunSuccess() for unknown Peer id: 0x" << RsUtil::BinToHex(id); + std::cerr << std::endl; + return; + } + std::cerr << "stunSuccess() for id: 0x" << RsUtil::BinToHex(id); + std::cerr << std::endl; + + it->second.lastStunResult = time(NULL); + it->second.stunResults++; + + printPeerStatus(); +} + +} + +extern "C" void* doStunPeer(void* p) +{ + dhtStunData *data = (dhtStunData *) p; + if ((!data) || (!data->stunCb)) + { + pthread_exit(NULL); + } + + /* stun it! */ + if (stunPeer(data->toaddr, data->ansaddr)) + { + data->stunCb->stunSuccess(data->id, data->toaddr, data->ansaddr); + } + + delete data; + + pthread_exit(NULL); + + return NULL; +} + + +#ifndef JUST_LIBRARY + + +int main(int argc, char **argv) +{ + int c; + bool setOwnId = false; + std::string ownId; + std::list peerIds; + + while(-1 != (c = getopt(argc, argv, "o:p:"))) + { + switch (c) + { + case 'o': + ownId = optarg; + setOwnId = true; + break; + case 'p': + peerIds.push_back(std::string(optarg)); + break; + default: + usage(argv[0]); + break; + } + } +/******************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#else +/* for static PThreads under windows... we need to init the library... + */ + #ifdef PTW32_STATIC_LIB + pthread_win32_process_attach_np(); + #endif + + // Windows Networking Init. + WORD wVerReq = MAKEWORD(2,2); + WSADATA wsaData; + + if (0 != WSAStartup(wVerReq, &wsaData)) + { + std::cerr << "Failed to Startup Windows Networking"; + std::cerr << std::endl; + } + else + { + std::cerr << "Started Windows Networking"; + std::cerr << std::endl; + } + +#endif + + srand(time(NULL)); /* randomise! */ + + if (!setOwnId) + { + std::cerr << "Missing OwnId: Setting dummy Id"; + std::cerr << std::endl; + + setOwnId = true; + ownId = "dummyOwnId"; + } + + pqiConnectCbStun cbStun; + OpenDHTMgr dhtTester(ownId, &cbStun, "."); + + /* startup dht */ + std::cerr << "Starting up DhtTester()" << std::endl; + dhtTester.start(); + + /* wait for a little before switching on */ +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS + sleep(1); +#else + Sleep(1000); +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ + + + std::cerr << "Switching on DhtTester()" << std::endl; + dhtTester.enable(true); + + /* wait loop */ + while(1) + { + cbStun.printPeerStatus(); + std::cerr << "Main waiting..." << std::endl; +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS + sleep(30); +#else + Sleep(30000); +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ + } +}; + + + + +bool stunPeer(struct sockaddr_in toaddr, struct sockaddr_in &ansaddr) +{ +#ifdef BOOTSTRAP_DEBUG + std::cerr << "stunPeer: " << toaddr << std::endl; +#endif + /* open a socket */ + int sockfd = tounet_socket(PF_INET, SOCK_DGRAM, 0); + if (-1 == tounet_fcntl(sockfd, F_SETFL, O_NONBLOCK)) + { +#ifdef BOOTSTRAP_DEBUG + std::cerr << "Failed to Make Non-Blocking" << std::endl; +#endif + } + + /* create a stun packet */ + char stunpkt[100]; + int maxlen = 100; + int len = maxlen; + + UdpStun_generate_stun_pkt((void *) stunpkt, &len); + +#ifdef BOOTSTRAP_DEBUG + std::cerr << "stunPeer() Send packet length: " << len << std::endl; +#endif + + /* send stun packet */ + tounet_sendto(sockfd, stunpkt, len, 0, + (struct sockaddr *) &(toaddr), + sizeof(toaddr)); + + /* wait */ +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS + sleep(2); +#else + Sleep(2000); +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ + + /* check for response */ + struct sockaddr_in fromaddr; + socklen_t fromsize = sizeof(fromaddr); + int insize = maxlen; + + insize = tounet_recvfrom(sockfd,stunpkt,insize,0, + (struct sockaddr*)&fromaddr,&fromsize); + + tounet_close(sockfd); + + if (0 >= insize) + { +#ifdef BOOTSTRAP_DEBUG + std::cerr << "No Stun response from: " << toaddr; + std::cerr << std::endl; +#endif + return false; + } + + if (UdpStun_response(stunpkt, insize, ansaddr)) + { +#ifdef BOOTSTRAP_DEBUG + std::cerr << "received Stun Reply from : " << fromaddr; + std::cerr << std::endl; + std::cerr << "External Address is: " << ansaddr; + std::cerr << std::endl; +#endif + return true; + } + +#ifdef BOOTSTRAP_DEBUG + std::cerr << "received Data (not Stun Reply) from : " << fromaddr; + std::cerr << std::endl; +#endif + return false; +} + +#endif // JUST_LIBRARY diff --git a/libretroshare/src/_dht/dht_bootstrap.h b/libretroshare/src/_dht/dht_bootstrap.h new file mode 100644 index 000000000..386b39573 --- /dev/null +++ b/libretroshare/src/_dht/dht_bootstrap.h @@ -0,0 +1,94 @@ +#ifndef DHT_BOOTSTRAP_H +#define DHT_BOOTSTRAP_H + +#include "pqi/p3dhtmgr.h" +#include "pqi/p3connmgr.h" +#include "pqi/pqimonitor.h" +#include "dht/opendhtmgr.h" + +#include "util/rsnet.h" +#include "util/rsthreads.h" +#include "util/rsprint.h" + +#include "tcponudp/tou_net.h" +#include "tcponudp/udpsorter.h" + +#include +#include +#include +#include + +namespace DHT_Bootstrap { + +// Function Prototypes +void usage(char *name); +void addPeer(std::string id); +extern "C" void* doStunPeer(void* p); + +class pqiConnectCbStun; + +// CHANGED: REMOVED : Reason -> not implemented +//void loadBootStrapIds(std::list &peerIds); +//bool stunPeer(struct sockaddr_in toaddr, struct sockaddr_in &ansaddr); + +// CHANGED: CLASS_TO_STRUCT +struct dhtStunData +{ + pqiConnectCbStun *stunCb; + std::string id; + struct sockaddr_in toaddr; + struct sockaddr_in ansaddr; +}; + + +class StunDetails +{ + StunDetails(); + + std::string id; + + /* peerStatus details */ + struct sockaddr_in laddr, raddr; + uint32_t type, mode, source; + + /* stun response */ + uint32_t stunAttempts; + uint32_t stunResults; + struct sockaddr_in stunaddr; + + /* timestamps */ + time_t lastStatus; + time_t lastStunResult; +}; + +class pqiConnectCbStun: public pqiConnectCb +{ +public: + pqiConnectCbStun(); + + virtual ~pqiConnectCbStun(); + + void addPeer(std::string id); + virtual void peerStatus(std::string id, + struct sockaddr_in laddr, struct sockaddr_in raddr, + uint32_t type, uint32_t mode, uint32_t source); + void printPeerStatus(); + void stunPeer(std::string id, struct sockaddr_in peeraddr); + + virtual void peerConnectRequest(std::string id, + struct sockaddr_in raddr, uint32_t source); + + virtual void stunStatus(std::string id, struct sockaddr_in raddr, + uint32_t type, uint32_t flags); + + virtual void stunSuccess(std::string id, struct sockaddr_in toaddr, + struct sockaddr_in ansaddr); +private: + + RsMutex peerMtx; + std::map peerMap; +}; + + +}; +#endif // DHT_BOOTSTRAP_H diff --git a/libretroshare/src/_dht/dht_check_peers.cc b/libretroshare/src/_dht/dht_check_peers.cc new file mode 100644 index 000000000..d59e82f11 --- /dev/null +++ b/libretroshare/src/_dht/dht_check_peers.cc @@ -0,0 +1,432 @@ +/* + * libretroshare/src/dht: odhtmgr_test.cc + * + * Interface with OpenDHT for RetroShare. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#include "_dht/dht_check_peers.cc" + + +namespace DHT_CheckPears { + +void usage(char *name) +{ + std::cerr << "USAGE: " << name << " -o OwnId [ -p PeerId1 [ -p PeerId2 [ ... ] ] ] "; + std::cerr << std::endl; + exit(1); +} + +class pqiConnectCbStun; + + +pqiConnectCbStun::pqiConnectCbStun() +{ + return; +} + +pqiConnectCbStun::~pqiConnectCbStun() +{ + return; +} + +void pqiConnectCbStun::addPeer(std::string id) +{ + RsStackMutex stack(peerMtx); /**** LOCK MUTEX ***/ + std::map::iterator it; + it = peerMap.find(id); + if (it == peerMap.end()) + { + StunDetails sd; + sd.id = id; + peerMap[id] = sd; + } +} + +void pqiConnectCbStun::peerStatus(std::string id, + struct sockaddr_in laddr, struct sockaddr_in raddr, + uint32_t type, uint32_t mode, uint32_t source) +{ + + { + RsStackMutex stack(peerMtx); /**** LOCK MUTEX ***/ + + std::map::iterator it; + it = peerMap.find(id); + if (it == peerMap.end()) + { + std::cerr << "peerStatus() for unknown Peer id: " << id; + std::cerr << std::endl; + return; + } + it->second.laddr = laddr; + it->second.raddr = raddr; + it->second.type = type; + it->second.mode = mode; + it->second.source= source; + + it->second.lastStatus = time(NULL); + + it->second.stunAttempts++; /* as we are about to try! */ + } + + printPeerStatus(); + stunPeer(id, raddr); +} + +void pqiConnectCbStun::printPeerStatus() +{ + RsStackMutex stack(peerMtx); /**** LOCK MUTEX ***/ + + time_t t = time(NULL); + std::string timestr = ctime(&t); + std::cerr << "BootstrapStatus: " << timestr; + std::cerr << "BootstrapStatus: " << peerMap.size() << " Peers"; + std::cerr << std::endl; + std::cerr << "BootstrapStatus: ID ---------- DHT ENTRY ---"; + std::cerr << " EXT PORT -- STUN OK -- %AVAIL -- LAST DHT TS"; + std::cerr << std::endl; + + std::map::iterator it; + + for(it = peerMap.begin(); it != peerMap.end(); it++) + { + std::cerr << it->first; + + bool dhtActive = (time(NULL) - it->second.lastStatus < 1900); + bool stunActive = (time(NULL) - it->second.lastStunResult < 1900); + bool extPort = it->second.type & RS_NET_CONN_TCP_EXTERNAL; + float percentAvailable = it->second.stunResults * 100.0 / (it->second.stunAttempts + 0.0001); + + if (dhtActive) + { + std::cerr << " Yes --->"; + } + else + { + std::cerr << " No "; + } + + if (extPort) + { + std::cerr << " Yes --->"; + } + else + { + std::cerr << " No "; + } + + if (stunActive) + { + std::cerr << " Yes --->"; + } + else + { + std::cerr << " No "; + } + + std::cerr << " " << std::setw(4) << percentAvailable; + std::cerr << " "; + + if (it->second.lastStatus == 0) + { + std::cerr << " NEVER "; + } + else + { + std::cerr << " " << time(NULL) - it->second.lastStatus; + std::cerr << " secs ago "; + } + std::cerr << std::endl; + } +} + +void pqiConnectCbStun::stunPeer(std::string id, struct sockaddr_in peeraddr) +{ + std::cerr << "Should Stun Peer: " << id; + std::cerr << std::endl; + + /* launch a publishThread */ + pthread_t tid; + + dhtStunData *pub = new dhtStunData; + pub->stunCb = this; + pub->id = id; + pub->toaddr = peeraddr; + + void *data = (void *) pub; + pthread_create(&tid, 0, &doStunPeer, data); + + return; + +} + + +void pqiConnectCbStun::peerConnectRequest(std::string id, + struct sockaddr_in raddr, + uint32_t source) +{ +} + + +void pqiConnectCbStun::stunStatus(std::string id, struct sockaddr_in raddr, + uint32_t type, uint32_t flags) +{ + +} + +void pqiConnectCbStun::stunSuccess(std::string id, struct sockaddr_in toaddr, struct sockaddr_in ansaddr) +{ + { + RsStackMutex stack(peerMtx); /**** LOCK MUTEX ***/ + + std::map::iterator it; + it = peerMap.find(id); + if (it == peerMap.end()) + { + std::cerr << "stunSuccess() for unknown Peer id: " << id; + std::cerr << std::endl; + return; + } + std::cerr << "stunSuccess() for id: " << id; + std::cerr << std::endl; + + it->second.lastStunResult = time(NULL); + it->second.stunResults++; + } + + printPeerStatus(); +} + +} // Namespace End + + +extern "C" void* doStunPeer(void* p) +{ + dhtStunData *data = (dhtStunData *) p; + if ((!data) || (!data->stunCb)) + { + pthread_exit(NULL); + } + + /* stun it! */ + if (stunPeer(data->toaddr, data->ansaddr)) + { + data->stunCb->stunSuccess(data->id, data->toaddr, data->ansaddr); + } + + delete data; + + pthread_exit(NULL); + + return NULL; +} + + +#ifndef JUST_LIBRARY + + +int main(int argc, char **argv) +{ + int c; + bool setOwnId = false; + std::string ownId; + std::list peerIds; + + while(-1 != (c = getopt(argc, argv, "o:p:"))) + { + switch (c) + { + case 'o': + ownId = optarg; + setOwnId = true; + break; + case 'p': + peerIds.push_back(std::string(optarg)); + break; + default: + usage(argv[0]); + break; + } + } +/******************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#else +/* for static PThreads under windows... we need to init the library... + */ + #ifdef PTW32_STATIC_LIB + pthread_win32_process_attach_np(); + #endif + + // Windows Networking Init. + WORD wVerReq = MAKEWORD(2,2); + WSADATA wsaData; + + if (0 != WSAStartup(wVerReq, &wsaData)) + { + std::cerr << "Failed to Startup Windows Networking"; + std::cerr << std::endl; + } + else + { + std::cerr << "Started Windows Networking"; + std::cerr << std::endl; + } + +#endif + + + if (!setOwnId) + { + std::cerr << "Missing OwnId: Setting dummy Id"; + std::cerr << std::endl; + + setOwnId = true; + ownId = "dummyOwnId"; + } + + pqiConnectCbStun cbStun; + OpenDHTMgr dhtTester(ownId, &cbStun, "."); + + /* startup dht */ + std::cerr << "Starting up DhtTester()" << std::endl; + dhtTester.start(); + + /* wait for a little before switching on */ +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS + sleep(1); +#else + Sleep(1000); +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ + + + std::cerr << "Switching on DhtTester()" << std::endl; + dhtTester.enable(true); + + std::cerr << "Adding a List of Peers" << std::endl; + std::list::iterator it; + for(it = peerIds.begin(); it != peerIds.end(); it++) + { + cbStun.addPeer(*it); + dhtTester.findPeer(*it); + } + + /* switch off Stun/Bootstrap stuff */ + dhtTester.enableStun(false); + dhtTester.setBootstrapAllowed(false); + + + /* wait loop */ + while(1) + { + cbStun.printPeerStatus(); + std::cerr << "Main waiting..." << std::endl; +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS + sleep(30); +#else + Sleep(30000); +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ + } +}; + + +bool stunPeer(struct sockaddr_in toaddr, struct sockaddr_in &ansaddr) +{ +#ifdef BOOTSTRAP_DEBUG + std::cerr << "stunPeer: " << toaddr << std::endl; +#endif + /* open a socket */ + int sockfd = tounet_socket(PF_INET, SOCK_DGRAM, 0); + if (-1 == tounet_fcntl(sockfd, F_SETFL, O_NONBLOCK)) + { +#ifdef BOOTSTRAP_DEBUG + std::cerr << "Failed to Make Non-Blocking" << std::endl; +#endif + } + + /* create a stun packet */ + char stunpkt[100]; + int maxlen = 100; + int len = maxlen; + + UdpStun_generate_stun_pkt((void *) stunpkt, &len); + +#ifdef BOOTSTRAP_DEBUG + std::cerr << "stunPeer() Send packet length: " << len << std::endl; +#endif + + /* send stun packet */ + tounet_sendto(sockfd, stunpkt, len, 0, + (struct sockaddr *) &(toaddr), + sizeof(toaddr)); + + /* wait */ +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS + sleep(2); +#else + Sleep(2000); +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ + + /* check for response */ + struct sockaddr_in fromaddr; + socklen_t fromsize = sizeof(fromaddr); + int insize = maxlen; + + insize = tounet_recvfrom(sockfd,stunpkt,insize,0, + (struct sockaddr*)&fromaddr,&fromsize); + + tounet_close(sockfd); + + if (0 >= insize) + { +#ifdef BOOTSTRAP_DEBUG + std::cerr << "No Stun response from: " << toaddr; + std::cerr << std::endl; +#endif + return false; + } + + if (UdpStun_response(stunpkt, insize, ansaddr)) + { +#ifdef BOOTSTRAP_DEBUG + std::cerr << "received Stun Reply from : " << fromaddr; + std::cerr << std::endl; + std::cerr << "External Address is: " << ansaddr; + std::cerr << std::endl; +#endif + return true; + } + +#ifdef BOOTSTRAP_DEBUG + std::cerr << "received Data (not Stun Reply) from : " << fromaddr; + std::cerr << std::endl; +#endif + return false; +} + +#endif // JUST_LIBRARY diff --git a/libretroshare/src/_dht/dht_check_peers.h b/libretroshare/src/_dht/dht_check_peers.h new file mode 100644 index 000000000..7fd5ebea6 --- /dev/null +++ b/libretroshare/src/_dht/dht_check_peers.h @@ -0,0 +1,143 @@ +/* + * libretroshare/src/dht: odhtmgr_test.cc + * + * Interface with OpenDHT for RetroShare. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#ifndef DHT_CHECK_PEERS_H +#define DHT_CHECK_PEERS_H + + +/***** Test for the new DHT system *****/ + +#include "pqi/p3dhtmgr.h" +#include "pqi/p3connmgr.h" +#include "pqi/pqimonitor.h" +#include "dht/opendhtmgr.h" + +#include "util/rsnet.h" +#include "util/rsthreads.h" +#include "util/rsprint.h" + +#include "tcponudp/tou_net.h" +#include "tcponudp/udpsorter.h" + +#include +#include +#include +#include + +#define BOOTSTRAP_DEBUG 1 + +extern "C" void* doStunPeer(void* p); + +namespace DHT_CheckPears { + + +// Function Prototypes +void usage(char *name); +bool stunPeer(struct sockaddr_in toaddr, struct sockaddr_in &ansaddr); + + +class StunDetails +{ + StunDetails() : + lastStatus(0), + lastStunResult(0), + stunAttemps(0), + stunResults(0) {} + + std::string id; + + /* peerStatus details */ + struct sockaddr_in laddr, raddr; + uint32_t type, mode, source; + + /* stun response */ + uint32_t stunAttempts; + uint32_t stunResults; + struct sockaddr_in stunaddr; + + /* timestamps */ + time_t lastStatus; + time_t lastStunResult; +}; + +// CHANGED: CLASS_TO_STRUCT +struct dhtStunData +{ + pqiConnectCbStun *stunCb; + std::string id; + struct sockaddr_in toaddr; + struct sockaddr_in ansaddr; +}; + + +class StunDetails +{ +public: + StunDetails(); + std::string id; + /* peerStatus details */ + struct sockaddr_in laddr, raddr; + uint32_t type, mode, source; + + /* stun response */ + uint32_t stunAttempts; + uint32_t stunResults; + struct sockaddr_in stunaddr; + + /* timestamps */ + time_t lastStatus; + time_t lastStunResult; +}; + +class pqiConnectCbStun: public pqiConnectCb +{ +public: + pqiConnectCbStun(); + + virtual ~pqiConnectCbStun(); + + void addPeer(std::string id); + virtual void peerStatus(std::string id, + struct sockaddr_in laddr, struct sockaddr_in raddr, + uint32_t type, uint32_t mode, uint32_t source); + void printPeerStatus(); + void stunPeer(std::string id, struct sockaddr_in peeraddr); + + virtual void peerConnectRequest(std::string id, + struct sockaddr_in raddr, uint32_t source); + + virtual void stunStatus(std::string id, struct sockaddr_in raddr, + uint32_t type, uint32_t flags); + + virtual void stunSuccess(std::string id, struct sockaddr_in toaddr, + struct sockaddr_in ansaddr); +private: + + RsMutex peerMtx; + std::map peerMap; +}; + +} +#endif // DHT_CHECK_PEERS_H diff --git a/libretroshare/src/_dht/dhtclient.h b/libretroshare/src/_dht/dhtclient.h new file mode 100644 index 000000000..bc7a3e446 --- /dev/null +++ b/libretroshare/src/_dht/dhtclient.h @@ -0,0 +1,74 @@ +/* + * libretroshare/src/dht: dhtclient.h + * + * Interface with DHT Client for RetroShare. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#ifndef DHCLIENT_H +#define DHCLIENT_H + +#include +#include +#include + +class DHTClient +{ +public: + + /* initialise from file */ + virtual bool checkServerFile(std::string filename) = 0; + virtual bool loadServers(std::string filename) = 0; + virtual bool loadServersFromWeb(std::string storename) = 0; + virtual bool loadServers(std::istream&) = 0; + + /* check that its working */ + virtual bool dhtActive() = 0; + + /* publish / search */ + virtual bool publishKey(std::string key, std::string value, uint32_t ttl) = 0; + virtual bool searchKey(std::string key, std::list &values) = 0; + +}; + + +class DHTClientDummy: public DHTClient +{ +public: + + /* initialise from file */ + virtual bool checkServerFile(std::string filename) { return false; } + virtual bool loadServers(std::string filename) { return true; } + virtual bool loadServersFromWeb(std::string storename) { return true; } + virtual bool loadServers(std::istream&) { return true; } + + /* check that its working */ + virtual bool dhtActive() { return true; } + + /* publish / search */ + virtual bool publishKey(std::string key, std::string value, uint32_t ttl) { return true; } + virtual bool searchKey(std::string key, std::list &values) { return true; } + +}; + + +#endif + diff --git a/libretroshare/src/_dht/dhthandler.cc b/libretroshare/src/_dht/dhthandler.cc new file mode 100644 index 000000000..06bf7939a --- /dev/null +++ b/libretroshare/src/_dht/dhthandler.cc @@ -0,0 +1,698 @@ + +#include "dht/dhthandler.h" + + +/* This stuff is actually C */ + +#ifdef __cplusplus +extern "C" { +#endif + +#include +#include +#include +#include + +#ifdef __cplusplus +} /* extern C */ +#endif +/* This stuff is actually C */ + +std::ostream &operator<<(std::ostream &out, dhtentry &ent) +{ + out << "DHTENTRY(" << ent.id << "): Status: " << ent.status; + out << std::endl; + out << "\taddr: " << inet_ntoa(ent.addr.sin_addr) << ":" << ntohs(ent.addr.sin_port); + out << std::endl; + out << "\tlastTS: " << time(NULL) - ent.lastTs << " secs ago"; + out << "\tFlags: " << ent.flags; + out << std::endl; + return out; +} + +#define DHT_UNKNOWN 0 +#define DHT_SEARCHING 1 /* for peers */ +#define DHT_PUBLISHING 1 /* for self */ +#define DHT_FOUND 2 + +/* time periods */ +#define DHT_MIN_PERIOD 10 +#define DHT_SEARCH_PERIOD 300 +#define DHT_REPUBLISH_PERIOD 1200 + +void cleardhtentry(dhtentry *ent, std::string id) +{ + ent -> name = ""; + ent -> id = id; + ent -> addr.sin_addr.s_addr = 0; + ent -> addr.sin_port = 0; + ent -> flags = 0; + ent -> status = DHT_UNKNOWN; + ent -> lastTs = 0; +} + + +void initdhtentry(dhtentry *ent) +{ + ent -> name = ""; + // leave these ... + //ent -> addr.sin_addr.in_addr = 0; + //ent -> addr.sin_port = 0; + //ent -> flags = 0; + ent -> status = DHT_SEARCHING; + ent -> lastTs = time(NULL); + return; +} + +void founddhtentry(dhtentry *ent, struct sockaddr_in inaddr, unsigned int flags) +{ + ent -> addr = inaddr; + ent -> flags = flags; + ent -> status = DHT_FOUND; + ent -> lastTs = time(NULL); +} + + +dhthandler::dhthandler(std::string inifile) + :mShutdown(false), dhtOk(false) +{ + /* init own to null */ + dataMtx.lock(); /* LOCK MUTEX */ + cleardhtentry(&ownId, ""); + kadcFile = inifile; + dataMtx.unlock(); /* UNLOCK MUTEX */ + + /* start up the threads... */ + init(); +} + +dhthandler::~dhthandler() +{ + +} + /* This is internal - only called when active */ +bool dhthandler::networkUp() +{ + /* no need for mutex? */ + return (20 < KadC_getnknodes(pkcc)); +} + + /* this is external */ +int dhthandler::dhtPeers() +{ + int count = 0; + dataMtx.lock(); /* LOCK MUTEX */ + if (dhtOk) + { + count = KadC_getnknodes(pkcc); + } + dataMtx.unlock(); /* UNLOCK MUTEX */ + return count; + +} + + + /* set own tag */ +void dhthandler::setOwnHash(std::string id) +{ + dataMtx.lock(); /* LOCK MUTEX */ + ownId.id = id; + dataMtx.unlock(); /* UNLOCK MUTEX */ +} + +void dhthandler::setOwnPort(short port) +{ + dataMtx.lock(); /* LOCK MUTEX */ + ownId.addr.sin_port = htons(port); + /* reset own status -> so we republish */ + ownId.status = DHT_UNKNOWN; + + dataMtx.unlock(); /* UNLOCK MUTEX */ +} + +bool dhthandler::getExtAddr(struct sockaddr_in &addr, unsigned int &flags) +{ + dataMtx.lock(); /* LOCK MUTEX */ + + if (ownId.status == DHT_UNKNOWN) + { + dataMtx.unlock(); /* UNLOCK MUTEX */ + return false; + } + + addr = ownId.addr; + flags = ownId.flags; + + dataMtx.unlock(); /* UNLOCK MUTEX */ + return true; +} + + /* at startup */ +void dhthandler::addFriend(std::string id) +{ + dataMtx.lock(); /* LOCK MUTEX */ + std::map::iterator it; + it = addrs.find(id); + if (it == addrs.end()) + { + /* not found - add */ + dhtentry ent; + cleardhtentry(&ent, id); + addrs[id] = ent; + } + else + { + /* already there */ + std::cerr << "dhthandler::addFriend() Already there!" << std::endl; + } + dataMtx.unlock(); /* UNLOCK MUTEX */ +} + +void dhthandler::removeFriend(std::string id) +{ + dataMtx.lock(); /* LOCK MUTEX */ + std::map::iterator it; + it = addrs.find(id); + if (it == addrs.end()) + { + /* not found - complain*/ + std::cerr << "dhthandler::addFriend() Already there!" << std::endl; + } + else + { + /* found */ + addrs.erase(it); + } + dataMtx.unlock(); /* UNLOCK MUTEX */ +} + + /* called prior to connect */ +bool dhthandler::addrFriend(std::string id, struct sockaddr_in &addr, unsigned int &flags) +{ + + dataMtx.lock(); /* LOCK MUTEX */ + + /* look it up */ + bool ret = false; + std::map::iterator it; + it = addrs.find(id); + if (it == addrs.end()) + { + /* not found - complain*/ + std::cerr << "dhthandler::addrFriend() Non-existant!" << std::endl; + ret = false; + } + else + { + if (it->second.status == DHT_FOUND) + { + addr = it->second.addr; + ret = true; + } + } + dataMtx.unlock(); /* UNLOCK MUTEX */ + return ret; +} + +int dhthandler::init() +{ + dataMtx.lock(); /* LOCK MUTEX */ + + /* HACK TO SWITCH THIS OFF during testing */ +#ifdef NO_DHT_RUNNING + dataMtx.unlock(); /* UNLOCK MUTEX */ + dhtOk = false; + return 1; +#endif + + char *filename = (char *) malloc(1024); + sprintf(filename, "%.1023s", kadcFile.c_str()); + + /* start up the dht server. */ + KadC_log("KadC - library version: %d.%d.%d\n", + KadC_version.major, KadC_version.minor, KadC_version.patchlevel); + + /* file, Leaf, StartNetworking (->false in full version) */ + kcc = KadC_start(filename, true, 1); + if(kcc.s != KADC_OK) { + KadC_log("KadC_start(%s, %d) returned error %d:\n", + kadcFile.c_str(), 1, kcc.s); + KadC_log("%s %s", kcc.errmsg1, kcc.errmsg2); + + dhtOk = false; + } + else + { + dhtOk = true; + } + + pkcc = &kcc; + + dataMtx.unlock(); /* UNLOCK MUTEX */ + return 1; +} + +int dhthandler::shutdown() +{ + dataMtx.lock(); /* LOCK MUTEX */ + /* end the dht server. */ + kcs = KadC_stop(&kcc); + if(kcs != KADC_OK) { + KadC_log("KadC_stop(&kcc) returned error %d:\n", kcc.s); + KadC_log("%s %s", kcc.errmsg1, kcc.errmsg2); + } + + KadC_list_outstanding_mallocs(10); + + dataMtx.unlock(); /* UNLOCK MUTEX */ + return 0; +} + + +int dhthandler::write_inifile() +{ + /* if we're up and we have enough valid ones */ + +#define MIN_KONTACTS 50 + + if (KadC_getncontacts(pkcc) > MIN_KONTACTS) + { + std::cerr << "DhtHandler::Write_IniFile() Writing File" << std::endl; + if (KADC_OK != KadC_write_inifile(pkcc, NULL)) + { + KadC_log("KadC_write_inifile(%s, %d) returned error %d:\n", + kadcFile.c_str(), 1, kcc.s); + KadC_log("%s %s", kcc.errmsg1, kcc.errmsg2); + } + } + else + { + std::cerr << "DhtHandler::Write_IniFile() Not enough contacts" << std::endl; + } + return 1; +} + + +void dhthandler::run() +{ + + /* infinite loop */ + int totalsleep = 0; + while(1) + { + // std::cerr << "DhtHandler::Run()" << std::endl; + + if (!dhtOk) + { + std::cerr << "DhtHandler::Run() Failed to Start" << std::endl; + +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS + sleep(1); +#else + + Sleep(1000); +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ + + continue; + } + + /* lock it up */ + dataMtx.lock(); /* LOCK MUTEX */ + + bool toShutdown = mShutdown; + + /* shutdown */ + dataMtx.unlock(); /* UNLOCK MUTEX */ + + + print(); + + if (toShutdown) + { + shutdown(); + dhtOk = false; + } + + + /* check ids */ + + int allowedSleep = checkOwnStatus(); + int nextPeerCheck = checkPeerIds(); + if (nextPeerCheck < allowedSleep) + { + allowedSleep = nextPeerCheck; + } + if (allowedSleep > 10) + { + allowedSleep = 10; + } + else if (allowedSleep < 10) + { + allowedSleep = 10; + } + // std::cerr << "DhtHandler::Run() sleeping for:" << allowedSleep << std::endl; +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS + sleep(allowedSleep); +#else + Sleep(1000 * allowedSleep); +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ + +#define DHT_INIT_STORE_PERIOD 300 + + totalsleep += allowedSleep; + if (totalsleep > DHT_INIT_STORE_PERIOD) + { + write_inifile(); + totalsleep = 0; + } + + + } + return; +} + +int dhthandler::print() +{ + dataMtx.lock(); /* LOCK MUTEX */ + + std::cerr << "DHT Status:" << std::endl; + std::cerr << "KNodes: " << KadC_getnknodes(pkcc); + std::cerr << std::endl; + std::cerr << "Kontacts: " << KadC_getncontacts(pkcc); + std::cerr << std::endl; + std::cerr << "KBuckets: "; + std::cerr << std::endl; + KadC_listkbuckets(pkcc); + std::cerr << std::endl; + std::cerr << "Own DHT:" << std::endl; + std::cerr << ownId << std::endl; + + std::cerr << addrs.size() << " Peers:" << std::endl; + + std::map::iterator it; + for(it = addrs.begin(); it != addrs.end(); it++) + { + std::cerr << "Peer DHT" << std::endl; + std::cerr << it -> second << std::endl; + } + + dataMtx.unlock(); /* UNLOCK MUTEX */ + return 1; +} + + +int dhthandler::checkOwnStatus() +{ + dataMtx.lock(); /* LOCK MUTEX */ + + int nextcall = DHT_REPUBLISH_PERIOD; + bool toPublish = false; + + /* if we are publishing, and time up ... republish */ + if (ownId.status == DHT_UNKNOWN) + { + /* if valid Hash and Port */ + if ((ownId.id != "") && (ownId.addr.sin_port != 0) && + (networkUp())) /* network is up */ + { + unsigned long int extip = KadC_getextIP(pkcc); + ownId.flags = KadC_getfwstatus(pkcc); + if (extip != 0) + { + ownId.addr.sin_addr.s_addr = htonl(extip); + toPublish = true; + } + } + nextcall = DHT_MIN_PERIOD; + } + else /* ownId.status == DHT_PUBLISHING */ + { + /* check time. + */ + if (ownId.lastTs + DHT_REPUBLISH_PERIOD < time(NULL)) + { + toPublish = true; + } + } + + dataMtx.unlock(); /* UNLOCK MUTEX */ + + if (toPublish) + { + publishOwnId(); + } + + return nextcall; +} + +int dhthandler::checkPeerIds() +{ + dataMtx.lock(); /* LOCK MUTEX */ + /* if we are unknown .... wait */ + int nextcall = DHT_REPUBLISH_PERIOD; + std::map::iterator it; + + /* local list */ + std::list idsToUpdate; + std::list::iterator it2; + + for(it = addrs.begin(); it != addrs.end(); it++) + { + /* if we are publishing, and time up ... republish */ + if (it -> second.status == DHT_UNKNOWN) + { + /* startup */ + idsToUpdate.push_back(it->first); + } + else if (it -> second.status == DHT_SEARCHING) + { + /* check if time */ + if (it -> second.lastTs + DHT_SEARCH_PERIOD < time(NULL)) + { + idsToUpdate.push_back(it->first); + } + nextcall = DHT_SEARCH_PERIOD; + } + else if (it -> second.status == DHT_FOUND) + { + /* check if time */ + if (it -> second.lastTs + DHT_REPUBLISH_PERIOD < time(NULL)) + { + idsToUpdate.push_back(it->first); + } + } + } + + dataMtx.unlock(); /* UNLOCK MUTEX */ + + for(it2 = idsToUpdate.begin(); it2 != idsToUpdate.end(); it2++) + { + searchId(*it2); + } + + return nextcall; +} + +/* already locked */ +int dhthandler::publishOwnId() +{ + dataMtx.lock(); /* LOCK MUTEX */ + /* publish command */ + /* publish {#[khash]|key} {#[vhash]|value} [meta-list [nthreads [nsecs]]] */ + char index[1024]; + sprintf(index, "#%.1023s", ownId.id.c_str()); + char value[1024]; + sprintf(value, "#%.1023s", ownId.id.c_str()); + + /* to store the ip address and flags */ + char metalist[1024]; + sprintf(metalist, "rsid=%s:%d;flags=%04X;", + inet_ntoa(ownId.addr.sin_addr), + ntohs(ownId.addr.sin_port), + ownId.flags); + + dataMtx.unlock(); /* UNLOCK MUTEX */ + + + int nthreads = 10; + int duration = 15; + int status; + + /* might as well hash back to us? */ + status = KadC_republish(pkcc, index, value, metalist, nthreads, duration); + if(status == 1) + { + KadC_log("Syntax error preparing search. Try: p key #hash [tagname=tagvalue[;...]]\n"); + } + + dataMtx.lock(); /* LOCK MUTEX */ + + /* update entry */ + initdhtentry(&ownId); + + dataMtx.unlock(); /* UNLOCK MUTEX */ + + return 1; +} + + +/* must be protected by mutex externally */ +dhtentry *dhthandler::finddht(std::string id) +{ + std::map::iterator it; + it = addrs.find(id); + if (it == addrs.end()) + { + return NULL; + } + return &(it->second); +} + +int dhthandler::searchId(std::string id) +{ + if (!networkUp()) + return 0; + + /* ack search */ + bool updated = false; + + /* search */ + void *iter; + KadCdictionary *pkd; + char *filter = ""; + int nthreads = 10; + int duration = 15; + int maxhits = 100; + time_t starttime = time(NULL); + void *resdictrbt; + int nhits; + + char index[1024]; + sprintf(index, "#%.1023s", id.c_str()); + + /* cannot be holding mutex here... (up to 15 secs) */ + resdictrbt = KadC_find(pkcc, index, filter, nthreads, maxhits, duration); + + nhits = rbt_size(resdictrbt); + + /* list each KadCdictionary returned in the rbt */ + for(iter = rbt_begin(resdictrbt); iter != NULL; iter = rbt_next(resdictrbt, iter)) { + pkd = rbt_value(iter); + + KadC_log("Found: "); + KadC_int128flog(stdout, KadCdictionary_gethash(pkd)); + KadC_log("\n"); + KadCdictionary_dump(pkd); + KadC_log("\n"); + + KadCtag_iter iter; + unsigned int i; + + bool found = false; + std::string addrline; + std::string flagsline; + for(i = 0, KadCtag_begin(pkd, &iter); (i < iter.tagsleft); i++, KadCtag_next(&iter)) { + if(i > 0) + KadC_log(";"); + if ((strncmp("rsid", iter.tagname, 4) == 0) + && (iter.tagtype == KADCTAG_STRING)) + { + KadC_log("DECODING:%s", (char *)iter.tagvalue); + addrline = (char *) iter.tagvalue; + found = true; + } + if ((strncmp("flags", iter.tagname, 5) == 0) + && (iter.tagtype == KADCTAG_STRING)) + { + KadC_log("DECODING:%s", (char *)iter.tagvalue); + flagsline = (char *) iter.tagvalue; + } + } + + /* must parse:rsid=ddd.ddd.ddd.ddd:dddd;flags=xxxx */ + struct sockaddr_in addr; + unsigned int flags = 0; + unsigned int a, b, c, d, e; + if ((found) && + (5 == sscanf(addrline.c_str(), "%d.%d.%d.%d:%d", &a, &b, &c, &d, &e))) + { + std::ostringstream out; + out << a << "." << b << "." << c << "." << d; + inet_aton(out.str().c_str(), &(addr.sin_addr)); + addr.sin_port = htons(e); + + if (flagsline != "") + sscanf(flagsline.c_str(), "%x", &flags); + + std::cerr << "Decoded entry: " << out.str() << " : " << e << std::endl; + + + dataMtx.lock(); /* LOCK MUTEX */ + + dhtentry *ent = finddht(id); + if (ent) + { + founddhtentry(ent, addr, flags); + updated = true; + } + + dataMtx.unlock(); /* UNLOCK MUTEX */ + + } + else + { + std::cerr << "Failed to Scan:" << addrline << " <-----" << std::endl; + } + + } + KadC_log("Search completed in %d seconds - %d hit%s returned\n", + time(NULL)-starttime, nhits, (nhits == 1 ? "" : "s")); + + for(iter = rbt_begin(resdictrbt); iter != NULL; iter = rbt_begin(resdictrbt)) { + pkd = rbt_value(iter); + rbt_erase(resdictrbt, iter); + KadCdictionary_destroy(pkd); + } + rbt_destroy(resdictrbt); + + dataMtx.lock(); /* LOCK MUTEX */ + if (!updated) + { + dhtentry *ent = finddht(id); + if (ent) + { + initdhtentry(ent); + } + } + dataMtx.unlock(); /* UNLOCK MUTEX */ + + return 1; +} + +#if (0) + +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include /* required by net.h, sigh... */ +#include /* only for domain2hip() */ + +#include + +#endif + diff --git a/libretroshare/src/_dht/dhthandler.h b/libretroshare/src/_dht/dhthandler.h new file mode 100644 index 000000000..b46cf41b1 --- /dev/null +++ b/libretroshare/src/_dht/dhthandler.h @@ -0,0 +1,107 @@ +#ifndef _RS_DHT_IFACE_H +#define _RS_DHT_IFACE_H + + +/* This stuff is actually C */ + +#ifdef __cplusplus +extern "C" { +#endif + +#include +#include + +#ifdef __cplusplus +} /* extern C */ +#endif +/* This stuff is actually C */ + +#include +#include +#include +#include +#include + +/* platform independent networking... */ +#include "pqi/pqinetwork.h" +#include "pqi/pqiaddrstore.h" +#include "util/rsthreads.h" + +/* HACK TO SWITCH THIS OFF during testing */ +/*define NO_DHT_RUNNING 1*/ + + +std::ostream &operator<<(std::ostream &out, dhtentry &ent); +void cleardhtentry(dhtentry *ent, std::string id); +void initdhtentry(dhtentry *ent); +void founddhtentry(dhtentry *ent, struct sockaddr_in inaddr, unsigned int flags); + +// CHANGED: CLASS_TO_STRUCT +struct dhtentry +{ + std::string name; + std::string id; + struct sockaddr_in addr; + unsigned int flags; + int status; + int lastTs; +}; + +class dhthandler: public RsThread, public pqiAddrStore +{ +public: + + dhthandler(std::string inifile); + ~dhthandler(); + + /* RsIface */ + /* set own tag */ + void setOwnHash(std::string id); + void setOwnPort(short port); + bool getExtAddr(sockaddr_in &addr, unsigned int &flags); + + /* at startup */ + void addFriend(std::string id); + void removeFriend(std::string id); + int dhtPeers(); + + /* pqiAddrStore ... called prior to connect */ + virtual bool addrFriend(std::string id, struct sockaddr_in &addr, unsigned int &flags); + + int init(); + int shutdown(); + int print(); + + /* must run thread */ + virtual void run(); + +private: + + int write_inifile(); + + bool networkUp(); /* get status */ + + int checkOwnStatus(); + int checkPeerIds(); + int publishOwnId(); + int searchId(std::string id); + + dhtentry *finddht(std::string id); + + /* Mutex for data below */ + RsMutex dataMtx; + + dhtentry ownId; + std::map addrs; + + KadCcontext kcc, *pkcc; + KadC_status kcs; + std::string kadcFile; + bool mShutdown; + + bool dhtOk; +}; + + + +#endif /* _RS_DHT_IFACE_H */ diff --git a/libretroshare/src/_dht/odhtmgr_test.cc b/libretroshare/src/_dht/odhtmgr_test.cc new file mode 100644 index 000000000..088cd409e --- /dev/null +++ b/libretroshare/src/_dht/odhtmgr_test.cc @@ -0,0 +1,157 @@ +/* + * libretroshare/src/dht: odhtmgr_test.cc + * + * Interface with OpenDHT for RetroShare. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + + + +/***** Test for the new DHT system *****/ + +#include "pqi/p3dhtmgr.h" +#include "pqi/pqimonitor.h" +#include "dht/opendhtmgr.h" + +#include "util/rsnet.h" +#include "util/rsthreads.h" +#include "util/rsprint.h" + + +#include +#include +#include + +void usage(char *name) +{ + std::cerr << "USAGE: " << name << " -o OwnId [ -p PeerId1 [ -p PeerId2 [ ... ] ] ] "; + std::cerr << std::endl; + exit(1); +} + +int main(int argc, char **argv) +{ + int c; + bool setOwnId = false; + std::string ownId; + std::list peerIds; + + while(-1 != (c = getopt(argc, argv, "o:p:"))) + { + switch (c) + { + case 'o': + ownId = optarg; + setOwnId = true; + break; + case 'p': + peerIds.push_back(std::string(optarg)); + break; + default: + usage(argv[0]); + break; + } + } + + if (!setOwnId) + { + std::cerr << "Missing OwnId!"; + usage(argv[0]); + } + + bool haveOwnAddress = false; + time_t startTime = time(NULL); + + pqiConnectCbDummy cbTester; + OpenDHTMgr dhtTester(ownId, &cbTester, "."); + + /* startup dht */ + std::cerr << "Starting up DhtTester()" << std::endl; + dhtTester.start(); + + /* wait for a little before switching on */ +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS + sleep(1); +#else + Sleep(1000); +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ + + + std::cerr << "Switching on DhtTester()" << std::endl; + dhtTester.enable(true); + + std::cerr << "Adding a List of Peers" << std::endl; + std::list::iterator it; + for(it = peerIds.begin(); it != peerIds.end(); it++) + { + dhtTester.findPeer(*it); + } + + + /* wait loop */ + while(1) + { + std::cerr << "Main waiting..." << std::endl; +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS + sleep(3); +#else + Sleep(3000); +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ + + if (!haveOwnAddress) + { + if (time(NULL) - startTime > 20) + { + std::cerr << "Setting Own Address!" << std::endl; + haveOwnAddress = true; + + uint32_t type = DHT_ADDR_UDP; + + struct sockaddr_in laddr; + inet_aton("10.0.0.111", &(laddr.sin_addr)); + laddr.sin_port = htons(7812); + laddr.sin_family = AF_INET; + + struct sockaddr_in raddr; + inet_aton("10.0.0.11", &(raddr.sin_addr)); + raddr.sin_port = htons(7812); + raddr.sin_family = AF_INET; + + dhtTester.setExternalInterface(laddr, raddr, type); + } + } + + } +}; + + + + + + + + + + diff --git a/libretroshare/src/_dht/odhtpost_test.cc b/libretroshare/src/_dht/odhtpost_test.cc new file mode 100644 index 000000000..fba186668 --- /dev/null +++ b/libretroshare/src/_dht/odhtpost_test.cc @@ -0,0 +1,65 @@ +/* + * libretroshare/src/dht: odhtport_test.cc + * + * Interface with OpenDHT for RetroShare. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + + +#include "opendht.h" +#include "util/rsprint.h" + +#include + +int main() +{ + std::string agent = "Hand-Crafted Thread"; + std::string keyIn = "color"; + //std::string value = "aaaaBBBBccccDDDDe"; + std::string value = "1234567890aaaaBBBBccccDDDDe"; + //std::string value = "12345678901234567890aaaaBBBBccccDDDDe"; + //std::string value = "aaa12345678901234567890aaaaBBBBccccDDDDe"; + uint32_t ttl = 600; + std::string client= "Retroshare v0.4"; + uint32_t maxresp= 1024; + + std::string key = RsUtil::HashId(keyIn, false); + + OpenDHTClient dht; + dht.loadServers("./servers.txt"); + + dht.publishKey(key, value, ttl); + +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS + sleep(10); +#else + Sleep(10000); +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ + + std::list values; + dht.searchKey(key, values); + + + return 1; +} + diff --git a/libretroshare/src/_dht/odhtstr_test.cc b/libretroshare/src/_dht/odhtstr_test.cc new file mode 100644 index 000000000..bffa6d309 --- /dev/null +++ b/libretroshare/src/_dht/odhtstr_test.cc @@ -0,0 +1,88 @@ +/* + * libretroshare/src/dht: odhtstr_test.cc + * + * Interface with OpenDHT for RetroShare. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#include "opendhtstr.h" +#include "b64.h" +#include + +int main() +{ + + std::string host = "abc.bgg.trer.dgg"; + uint16_t port = 9242; + + std::string agent = "Hand-Crafted Thread"; + std::string key = "BigKey"; + std::string value = "96324623924"; + uint32_t ttl = 600; + std::string client= "Retroshare v0.4"; + uint32_t maxresp= 1024; + + /* some encodings */ + std::string i1 = "color"; + std::string i2 = "green"; + std::string i3 = "blue"; + std::string i4 = "abdflhdffjadlgfal12=345=="; + + std::string o1 = convertToBase64(i1); + std::string o2 = convertToBase64(i2); + std::string o3 = convertToBase64(i3); + std::string o4 = convertToBase64(i4); + std::string o5 = "bdD+gAEUW+xKEtDiLacRxJcNAAs="; + + std::cerr << "In:" << i1 << " encoded:" << o1 << " decoded:" << convertFromBase64(o1); + std::cerr << std::endl; + std::cerr << "In:" << i2 << " encoded:" << o2 << " decoded:" << convertFromBase64(o2); + std::cerr << std::endl; + std::cerr << "In:" << i3 << " encoded:" << o3 << " decoded:" << convertFromBase64(o3); + std::cerr << std::endl; + std::cerr << "In:" << i4 << " encoded:" << o4 << " decoded:" << convertFromBase64(o4); + std::cerr << std::endl; + std::cerr << "Encoded:" << o5 << " decoded:" << convertFromBase64(o5); + std::cerr << std::endl; + + + /* create some strings */ + + std::string req1 = createOpenDHT_put(key, value, ttl, client); + std::string req2 = createOpenDHT_get(key, maxresp, client); + + std::string putheader = createHttpHeader(host, port, agent, req1.length()); + std::string getheader = createHttpHeader(host, port, agent, req2.length()); + + std::string putreq = putheader + req1; + std::string getreq = getheader + req2; + + + std::cerr << "Example Put Request is:" << std::endl; + std::cerr << putreq << std::endl; + + std::cerr << "Example Get Request is:" << std::endl; + std::cerr << getreq << std::endl; + + return 1; +} + + diff --git a/libretroshare/src/_dht/opendht.cc b/libretroshare/src/_dht/opendht.cc new file mode 100644 index 000000000..0da7f5ccd --- /dev/null +++ b/libretroshare/src/_dht/opendht.cc @@ -0,0 +1,821 @@ +/* + * libretroshare/src/dht: opendht.cc + * + * Interface with OpenDHT for RetroShare. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#include "_dht/opendht.h" +#include "_dht/opendhtstr.h" +#include "_dht/b64.h" +#include +#include + +#include +#include +#include "util/rsnet.h" +#include "util/rsprint.h" + +const std::string openDHT_Client = "Retroshare V0.4"; +const std::string openDHT_Agent = "RS-HTTP-V0.4"; + +#define MAX_DHT_PEER_FAILS 2 /* then discard */ +#define MAX_DHT_TOTAL_FAILS 10 /* in a row -> think we're not connected! */ +#define MAX_DHT_ATTEMPTS 10 /* attempts per search/publish */ +#define MIN_DHT_SERVERS 5 + +/**** + * #define OPENDHT_DEBUG 1 + ****/ + +bool OpenDHTClient::checkServerFile(std::string filename) +{ +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::checkServerFile(" << filename << ")" << std::endl; +#endif + + /* open the file */ + std::ifstream file(filename.c_str()); + + if (file.fail()) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::checkServerFile() Open Failed" << std::endl; +#endif + return false; + } + + /* get the first line */ + std::string line; + getline(file, line); + char day[16], month[16]; + int date; + char day2[16], month2[16]; + int date2; + + if (3 != sscanf(line.c_str(), "%15s %15s %d", day, month, &date)) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::checkServerFile() failed file TS parse"; + std::cerr << std::endl; +#endif + return false; + } + +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::checkServerFile() file TS month: "; + std::cerr << month << " date: " << date << std::endl; +#endif + + /* store current timestamp */ + struct tm result; + time_t now = time(NULL); + char nowstr[1023]; + + asctime_r(gmtime_r(&now, &result), nowstr); + + if (3 != sscanf(nowstr, "%15s %15s %d", day2, month2, &date2)) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::checkServerFile() failed now TS parse"; + std::cerr << std::endl; +#endif + return false; + } + +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::checkServerFile() current TS month: "; + std::cerr << month2 << " date: " << date2 << std::endl; +#endif + + /* if month is different */ + if (0 != strcmp(month, month2)) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::checkServerFile() different MONTHS fail"; + std::cerr << std::endl; +#endif + return false; + } + + /* if month is different */ + int delta = abs(date-date2); + if (delta > 2) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::checkServerFile() fail - large DATE diff: " << delta; + std::cerr << std::endl; +#endif + return false; + } + +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::checkServerFile() file is up-to-date!"; + std::cerr << std::endl; +#endif + + return true; +} + + + +bool OpenDHTClient::loadServers(std::string filename) +{ + /* open the file */ + std::ifstream file(filename.c_str()); + + + return loadServers(file); +} + +bool OpenDHTClient::loadServers(std::istream &instr) +{ + + std::string line; + char number[1024]; + char ipaddr[1024]; + char dnsname[1024]; + + dhtMutex.lock(); /**** LOCK ****/ + mServers.clear(); + dhtMutex.unlock(); /**** UNLOCK ****/ + + /* chew first line */ + instr.ignore(1024, '\n'); + + while((!instr.eof()) && (!instr.fail())) + { + line = ""; + getline(instr, line); + + if (3 == sscanf(line.c_str(), "%1023s %1023s %1023s", number, ipaddr, dnsname)) + { + dhtServer srv; + srv.host = dnsname; + srv.port = 5851; + srv.failed = 0; + srv.ts = 0; + srv.addr.sin_addr.s_addr = 0; + srv.addr.sin_port = 0; + +#ifdef OPENDHT_DEBUG + std::cerr << "Read Server: " << dnsname << std::endl; +#endif + + dhtMutex.lock(); /**** LOCK ****/ + mServers[dnsname] = srv; + dhtMutex.unlock(); /**** UNLOCK ****/ + + } + else + { + +#ifdef OPENDHT_DEBUG + std::cerr << "Failed to Read Server" << std::endl; +#endif + } + + dhtMutex.lock(); /**** LOCK ****/ + mDHTFailCount = 0; + dhtMutex.unlock(); /**** UNLOCK ****/ + } + + dhtMutex.lock(); /**** LOCK ****/ + uint32_t count = mServers.size(); + dhtMutex.unlock(); /**** UNLOCK ****/ + + return (count >= MIN_DHT_SERVERS); +} + +/******* refresh Servers from WebPage ******/ + +bool OpenDHTClient::loadServersFromWeb(std::string storename) +{ + +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::loadServersFromWeb()" << std::endl; +#endif + + std::string response; + if (!openDHT_getDHTList(response)) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::loadServersFromWeb() Web GET failed" << std::endl; +#endif + return false; + } + + std::string::size_type i; + if (std::string::npos == (i = response.find("\r\n\r\n"))) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::loadServersFromWeb() Failed to Find Content" << std::endl; +#endif + return false; + } + + /* now step past 4 chars */ + i += 4; + + std::string content(response, i, response.length() - i); + +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::loadServersFromWeb() Content:" << std::endl; + std::cerr << content << std::endl; + std::cerr << "<== OpenDHTClient::loadServersFromWeb() Content" << std::endl; +#endif + + std::istringstream iss(content); + + if (loadServers(iss)) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::loadServersFromWeb() Saving WebData to: "; + std::cerr << storename << std::endl; +#endif + /* save the data to file - replacing old data */ + std::ofstream ofstr(storename.c_str()); + ofstr << content; + ofstr.close(); + + return true; + } + + return false; + +} + + +bool OpenDHTClient::getServer(std::string &host, uint16_t &port, struct sockaddr_in &addr) +{ + /* randomly choose one */ + dhtMutex.lock(); /**** LOCK ****/ + +#ifndef WINDOWS_SYS +#else + + /* WINDOWS don't randomise properly so we'll do it ourselves... + */ + + uint32_t randomize = timeGetTime(); + srand(randomize); +#endif + + uint32_t len = mServers.size(); + uint32_t rnd = len * (rand() / (RAND_MAX + 1.0)); + + if (len < 1) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::getServer() No Servers available!" << std::endl; +#endif + dhtMutex.unlock(); /**** UNLOCK ****/ + return false; + } + + std::map::const_iterator it; + uint32_t i = 0; + for(it = mServers.begin(); (it != mServers.end()) && (i < rnd); it++, i++); + + if (it == mServers.end()) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::getServer() Error getting Server!" << std::endl; +#endif + dhtMutex.unlock(); /**** UNLOCK ****/ + return false; + } + + host = (it->second).host; + port = (it->second).port; + + time_t now = time(NULL); + + if (now - (it->second).ts < 3600) + { + addr = (it->second).addr; + } + else + { + addr.sin_addr.s_addr = 0; + } + + dhtMutex.unlock(); /**** UNLOCK ****/ + + return true; +} + + +bool OpenDHTClient::setServerIp(std::string host, struct sockaddr_in addr) +{ + dhtMutex.lock(); /**** LOCK ****/ + + std::map::iterator it; + it = mServers.find(host); + if (it == mServers.end()) + { + dhtMutex.unlock(); /**** UNLOCK ****/ +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::setServerIp() Error finding Server!" << std::endl; +#endif + return false; + } + + (it -> second).addr = addr; + (it -> second).ts = time(NULL); + (it -> second).failed = 0; + + mDHTFailCount = 0; + + dhtMutex.unlock(); /**** UNLOCK ****/ + + return true; +} + + +void OpenDHTClient::setServerFailed(std::string host) +{ + dhtMutex.lock(); /**** LOCK ****/ + + std::map::iterator it; + it = mServers.find(host); + if (it == mServers.end()) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::setServerFailed() Error finding Server!" << std::endl; +#endif + dhtMutex.unlock(); /**** UNLOCK ****/ + return; + } + + mDHTFailCount++; + if (mDHTFailCount > MAX_DHT_TOTAL_FAILS) /* might be not connected to Internet */ + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::setServerFailed() Probably not connected!" << std::endl; +#endif + dhtMutex.unlock(); /**** UNLOCK ****/ + return; + } + + /* up the fail count on this one */ + (it -> second).failed++; + + if ((it -> second).failed > MAX_DHT_PEER_FAILS) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::setServerFailed() fail count high -> removing: "; + std::cerr << host << " from list" << std::endl; +#endif + /* remove from list */ + mServers.erase(it); + } + + dhtMutex.unlock(); /**** UNLOCK ****/ + return; +} + +bool OpenDHTClient::dhtActive() +{ + dhtMutex.lock(); /**** LOCK ****/ + + bool ok = (mDHTFailCount <= MAX_DHT_TOTAL_FAILS) && + (mServers.size() > MIN_DHT_SERVERS); + + dhtMutex.unlock(); /**** UNLOCK ****/ + + return ok; +} + +bool OpenDHTClient::publishKey(std::string key, std::string value, uint32_t ttl) +{ + /* create request */ +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_publishKey() key: 0x" << RsUtil::BinToHex(key) << " value: 0x" << RsUtil::BinToHex(value); + std::cerr << std::endl; +#endif + std::string putmsg = createOpenDHT_put(key, value, ttl, openDHT_Client); + std::string response; + + for(uint16_t i = 0; (!openDHT_sendMessage(putmsg, response)); i++) + { + if (i > MAX_DHT_ATTEMPTS) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_publishKey() Failed -> Giving Up"; + std::cerr << std::endl; +#endif + return false; + } + +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_publishKey() Failed -> reattempting"; + std::cerr << std::endl; +#endif + } + + /* check response */ + return true; +} + + +bool OpenDHTClient::searchKey(std::string key, std::list &values) +{ +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_searchKey() key: 0x" << RsUtil::BinToHex(key); + std::cerr << std::endl; +#endif + + /* create request */ + std::string getmsg = createOpenDHT_get(key, 1024, openDHT_Client); + std::string response; + + for(uint16_t i = 0; (!openDHT_sendMessage(getmsg, response)); i++) + { + if (i > MAX_DHT_ATTEMPTS) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_searchKey() Failed -> Giving Up"; + std::cerr << std::endl; +#endif + return false; + } +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_searchKey() Failed -> reattempting"; + std::cerr << std::endl; +#endif + } + +#ifdef OPENDHT_DEBUG + std::cerr << "Parsing expression :$$$$$$$$$-" << response << "-$$$$$$$$" << std::endl ; +#endif + + /* search through the response for ... */ + + std::string::size_type start = 0; + std::string::size_type loc = 0; + std::string::size_type end = 0; + + while(1) + { + loc = response.find("", start); + if (loc == std::string::npos) + return true; /* finished */ +#ifdef OPENDHT_DEBUG + std::cerr << "found loc=" << loc << std::endl ; +#endif + loc += 8; /* shift to end of */ + + end = response.find("", loc); + if (end == std::string::npos) + return true; /* finished */ +#ifdef OPENDHT_DEBUG + std::cerr << "found end=" << end << std::endl ; +#endif + + std::string value = response.substr(loc, end-loc); +#ifdef OPENDHT_DEBUG + std::cerr << "found value=" << value << std::endl ; +#endif + + /* clear out whitespace */ + for(std::string::size_type i = 0; i < value.length();) + { + if (isspace(value[i])) + { + value.erase(i,1); +#ifdef OPENDHT_DEBUG + std::cerr << "Cleanup Result:" << value << ":END:" << std::endl; +#endif + } + else + { + i++; + } + } + + if (value.length() > 0) + { + std::string result = convertFromBase64(value); + values.push_back(result); +#ifdef OPENDHT_DEBUG + std::cerr << "openDHT_searchKey() Value:" << value << ":END:" << std::endl; + std::cerr << "openDHT_searchKey() Result: 0x" << RsUtil::BinToHex(result) << ":END:" << std::endl; +#endif + } + + /* the answer should be between loc and end */ + start = end + 9; + } + + /* parse response */ + return true; +} + + +bool OpenDHTClient::openDHT_sendMessage(std::string msg, std::string &response) +{ + struct sockaddr_in addr; + std::string host; + uint16_t port; + + if (!getServer(host, port, addr)) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_sendMessage() Failed to get Server"; + std::cerr << std::endl; +#endif + return false; + } + + if (addr.sin_addr.s_addr == 0) + { + /* lookup the address */ + addr.sin_port = htons(port); + if (LookupDNSAddr(host, addr) && + (addr.sin_addr.s_addr != 0)) + { + /* update the IP addr if necessary */ + setServerIp(host, addr); + } + else + { + /* no address */ +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_sendMessage()"; + std::cerr << " ERROR: No Address"; + std::cerr << std::endl; +#endif + setServerFailed(host); + + return false; + } + } + +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_sendMessage()"; + std::cerr << " Connecting to:" << host << ":" << port; + std::cerr << " (" << inet_ntoa(addr.sin_addr) << ":" << ntohs(addr.sin_port) << ")"; + std::cerr << std::endl; +#endif + + /* create request */ + std::string putheader = createHttpHeader(host, port, openDHT_Agent, msg.length()); + + /* open a socket */ + int sockfd = unix_socket(PF_INET, SOCK_STREAM, 0); + + /* connect */ + int err = unix_connect(sockfd, (struct sockaddr *) &addr, sizeof(addr)); + if (err) + { + unix_close(sockfd); +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_sendMessage()"; + std::cerr << " ERROR: Failed to Connect"; + std::cerr << std::endl; +#endif + + setServerFailed(host); + + return false; + } + +#ifdef OPENDHT_DEBUG + std::cerr << "HTTP message *******************" << std::endl; + std::cerr << putheader; + std::cerr << msg; + std::cerr << std::endl; + std::cerr << "HTTP message *******************" << std::endl; +#endif + + /* send data */ + int sendsize = strlen(putheader.c_str()); + int size = send(sockfd, putheader.c_str(), sendsize, 0); + if (sendsize != size) + { + unix_close(sockfd); +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_sendMessage()"; + std::cerr << " ERROR: Failed to Send(1)"; + std::cerr << std::endl; +#endif + + setServerFailed(host); + + return false; + } +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_sendMessage()"; + std::cerr << " Send(1):" << size; + std::cerr << std::endl; +#endif + + sendsize = strlen(msg.c_str()); + size = send(sockfd, msg.c_str(), sendsize, 0); + if (sendsize != size) + { + unix_close(sockfd); +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_sendMessage()"; + std::cerr << " ERROR: Failed to Send(2)"; + std::cerr << std::endl; +#endif + + setServerFailed(host); + + return false; + } + +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_sendMessage()"; + std::cerr << " Send(2):" << size; + std::cerr << std::endl; +#endif + + /* now wait for the response */ +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS + sleep(1); +#else + Sleep(1000); +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ + + int recvsize = 51200; /* 50kb */ + char *inbuf = (char *) malloc(recvsize); + uint32_t idx = 0; + while(0 < (size = recv(sockfd, &(inbuf[idx]), recvsize - idx, 0))) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_sendMessage()"; + std::cerr << " Recvd Chunk:" << size; + std::cerr << std::endl; +#endif + idx += size; + } + +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_sendMessage()"; + std::cerr << " Recvd Msg:" << idx; +#endif + + response = std::string(inbuf, idx); + free(inbuf); + + /* print it out */ +#ifdef OPENDHT_DEBUG + std::cerr << "HTTP What We Sent ***************" << std::endl; + std::cerr << putheader; + std::cerr << msg; + std::cerr << std::endl; + std::cerr << "HTTP response *******************" << std::endl; + std::cerr << response; + std::cerr << std::endl; + std::cerr << "HTTP response *******************" << std::endl; +#endif + + unix_close(sockfd); + + return true; +} + +bool OpenDHTClient::openDHT_getDHTList(std::string &response) +{ + struct sockaddr_in addr; + std::string host = "www.opendht.org"; + uint16_t port = 80; + + sockaddr_clear(&addr); + + /* lookup the address */ + addr.sin_family = AF_INET; + addr.sin_port = htons(port); + if (!LookupDNSAddr(host, addr)) + { + /* no address */ +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_getDHTList()"; + std::cerr << " ERROR: No Address"; + std::cerr << std::endl; +#endif + + return false; + } + +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_getDHTList()"; + std::cerr << " Connecting to:" << host << ":" << port; + std::cerr << " (" << inet_ntoa(addr.sin_addr) << ":" << ntohs(addr.sin_port) << ")"; + std::cerr << std::endl; +#endif + + /* create request */ + std::string putheader = createHttpHeaderGET(host, port, "servers.txt", openDHT_Agent, 0); + + /* open a socket */ + int sockfd = unix_socket(PF_INET, SOCK_STREAM, 0); + + /* connect */ + int err = unix_connect(sockfd, (struct sockaddr *) &addr, sizeof(addr)); + if (err) + { + unix_close(sockfd); +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_getDHTList()"; + std::cerr << " ERROR: Failed to Connect"; + std::cerr << std::endl; +#endif + + return false; + } + +#ifdef OPENDHT_DEBUG + std::cerr << "HTTP message *******************" << std::endl; + std::cerr << putheader; + std::cerr << std::endl; + std::cerr << "HTTP message *******************" << std::endl; +#endif + + /* send data */ + int sendsize = strlen(putheader.c_str()); + int size = send(sockfd, putheader.c_str(), sendsize, 0); + if (sendsize != size) + { + unix_close(sockfd); +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_getDHTList()"; + std::cerr << " ERROR: Failed to Send(1)"; + std::cerr << std::endl; +#endif + + return false; + } +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_getDHTList()"; + std::cerr << " Send(1):" << size; + std::cerr << std::endl; +#endif + + /* now wait for the response */ +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ +#ifndef WINDOWS_SYS + sleep(1); +#else + Sleep(1000); +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART ******************/ + + int recvsize = 51200; /* 50kb */ + char *inbuf = (char *) malloc(recvsize); + uint32_t idx = 0; + while(0 < (size = recv(sockfd, &(inbuf[idx]), recvsize - idx, 0))) + { +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_getDHTList()"; + std::cerr << " Recvd Chunk:" << size; + std::cerr << std::endl; +#endif + idx += size; + } + +#ifdef OPENDHT_DEBUG + std::cerr << "OpenDHTClient::openDHT_getDHTList()"; + std::cerr << " Recvd Msg:" << idx; +#endif + + response = std::string(inbuf, idx); + free(inbuf); + + /* print it out */ +#ifdef OPENDHT_DEBUG + std::cerr << "HTTP response *******************" << std::endl; + std::cerr << response; + std::cerr << std::endl; + std::cerr << "HTTP response *******************" << std::endl; +#endif + + unix_close(sockfd); + + return true; +} + + diff --git a/libretroshare/src/_dht/opendht.h b/libretroshare/src/_dht/opendht.h new file mode 100644 index 000000000..02f2391cd --- /dev/null +++ b/libretroshare/src/_dht/opendht.h @@ -0,0 +1,84 @@ +/* + * libretroshare/src/dht: opendht.h + * + * Interface with OpenDHT for RetroShare. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#ifndef OPENDHT_H +#define OPENDHT_H + +#include "pqi/pqinetwork.h" +#include "util/rsthreads.h" + +#include +#include +#include +#include + +#include "dht/dhtclient.h" + +// CHANGED: CLASS_TO_STRUCT +struct dhtServer +{ + std::string host; + uint16_t port; + uint16_t failed; + time_t ts; + struct sockaddr_in addr; +}; + +class OpenDHTClient: public DHTClient +{ +public: + + virtual bool publishKey(std::string key, std::string value, uint32_t ttl); + virtual bool searchKey(std::string key, std::list &values); + + /* Fns accessing data */ + virtual bool checkServerFile(std::string filename); + virtual bool loadServers(std::string filename); + virtual bool loadServersFromWeb(std::string storefname); + virtual bool loadServers(std::istream&); + + virtual bool dhtActive(); + +private: + bool getServer(std::string &host, uint16_t &port, struct sockaddr_in &addr); + bool setServerIp(std::string host, struct sockaddr_in addr); + void setServerFailed(std::string host); + +private: + + /* generic send msg */ + bool openDHT_sendMessage(std::string msg, std::string &response); + bool openDHT_getDHTList(std::string &response); + + RsMutex dhtMutex; + std::map mServers; + uint32_t mDHTFailCount; + +}; + + +#endif + + diff --git a/libretroshare/src/_dht/opendhtmgr.cc b/libretroshare/src/_dht/opendhtmgr.cc new file mode 100644 index 000000000..fe591edc4 --- /dev/null +++ b/libretroshare/src/_dht/opendhtmgr.cc @@ -0,0 +1,192 @@ +/* + * libretroshare/src/dht: opendhtmgr.cc + * + * Interface with OpenDHT for RetroShare. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#include "dht/opendhtmgr.h" +#include "dht/opendht.h" +#include "util/rsthreads.h" /* for pthreads headers */ + + +/* Thread routines */ + +extern "C" void* doDhtPublish(void* p) +{ +#ifdef OPENDHT_DEBUG + std::cerr << "in doDhtPublish(void* p)" << std::endl ; +#endif + dhtPublishData *data = (dhtPublishData *) p; + if(data == NULL) + { + pthread_exit(NULL); + return NULL; + } + + /* publish it! */ + if(data->mgr != NULL && data->client != NULL) + data->client->publishKey(data->key, data->value, data->ttl); + + delete data; + pthread_exit(NULL); + + return NULL; +} + + +extern "C" void* doDhtSearch(void* p) +{ + dhtSearchData *data = (dhtSearchData *) p; + if ((!data) || (!data->mgr) || (!data->client)) + { + pthread_exit(NULL); + return NULL; + } + + /* search it! */ + std::list values; + + if (data->client->searchKey(data->key, values)) + { + /* callback */ + std::list::iterator it; + for(it = values.begin(); it != values.end(); it++) + { + data->mgr->resultDHT(data->key, *it); + } + } + + delete data; + pthread_exit(NULL); + + return NULL; +} + + + + +OpenDHTMgr::OpenDHTMgr(std::string ownId, pqiConnectCb* cb, std::string configdir) : + p3DhtMgr(ownId, cb), + mConfigDir(configdir) +{ + return; +} + + + /********** OVERLOADED FROM p3DhtMgr ***************/ +bool OpenDHTMgr::dhtInit() +{ + std::string configpath = mConfigDir; + + /* load up DHT gateways */ + mClient = new OpenDHTClient(); + //mClient = new DHTClientDummy(); + + std::string filename = configpath; + if (configpath.size() > 0) + { + filename += "/"; + } + filename += "ODHTservers.txt"; + + /* check file date first */ + if (mClient -> checkServerFile(filename)) + { + return mClient -> loadServers(filename); + } + else if (!mClient -> loadServersFromWeb(filename)) + { + return mClient -> loadServers(filename); + } + return true; +} + +bool OpenDHTMgr::dhtShutdown() +{ + /* do nothing */ + if (mClient) + { + delete mClient; + mClient = NULL; + return true; + } + + return false; +} + +bool OpenDHTMgr::dhtActive() +{ + /* do nothing */ + if ((mClient) && (mClient -> dhtActive())) + { + return true; + } + return false; +} + +int OpenDHTMgr::status(std::ostream &out) +{ + /* do nothing */ + return 1; +} + + +/* Blocking calls (only from thread) */ +bool OpenDHTMgr::publishDHT(std::string key, std::string value, uint32_t ttl) +{ + /* launch a publishThread */ + pthread_t tid; + +#ifdef OPENDHT_DEBUG + std::cerr << "in publishDHT(.......)" << std::endl ; +#endif + + dhtPublishData *pub = new dhtPublishData; + pub->mgr = this; + pub->client = mClient; + pub->key = key; + pub->value = value; + pub->ttl = ttl; + + void *data = (void *) pub; + pthread_create(&tid, 0, &doDhtPublish, data); + pthread_detach(tid); /* so memory is reclaimed in linux */ + + return true; +} + +bool OpenDHTMgr::searchDHT(std::string key) +{ + /* launch a publishThread */ + pthread_t tid; + + dhtSearchData *dht = new dhtSearchData; + dht->mgr = this; + dht->client = mClient; + dht->key = key; + + void *data = (void *) dht; + pthread_create(&tid, 0, &doDhtSearch, data); + pthread_detach(tid); /* so memory is reclaimed in linux */ + + return true; +} diff --git a/libretroshare/src/_dht/opendhtmgr.h b/libretroshare/src/_dht/opendhtmgr.h new file mode 100644 index 000000000..c6c5e9e84 --- /dev/null +++ b/libretroshare/src/_dht/opendhtmgr.h @@ -0,0 +1,82 @@ +/* + * libretroshare/src/dht: opendhtmgr.cc + * + * Interface with OpenDHT for RetroShare. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#ifndef OPENDHTMGR_H +#define OPENDHTMGR_H + +#include "dht/opendhtmgr.h" +#include "dht/opendht.h" +#include "util/rsthreads.h" /* for pthreads headers */ + +extern "C" void* doDhtPublish(void* p); +extern "C" void* doDhtSearch(void* p); + + +// CHANGED: CLASS_TO_STRUCT +struct dhtSearchData +{ + OpenDHTMgr *mgr; + DHTClient *client; + std::string key; +}; + + +// CHANGED: CLASS_TO_STRUCT +struct dhtPublishData +{ + OpenDHTMgr *mgr; + DHTClient *client; + std::string key; + std::string value; + uint32_t ttl; +}; + +class OpenDHTMgr: public p3DhtMgr +{ +public: + + OpenDHTMgr(std::string ownId, pqiConnectCb* cb, std::string configdir); + +protected: + + /********** OVERLOADED FROM p3DhtMgr ***************/ + virtual bool dhtInit(); + virtual bool dhtShutdown(); + virtual bool dhtActive(); + virtual int status(std::ostream &out); + + /* Blocking calls (only from thread) */ + virtual bool publishDHT(std::string key, std::string value, uint32_t ttl); + virtual bool searchDHT(std::string key); + + /********** OVERLOADED FROM p3DhtMgr ***************/ + +private: + DHTClient *mClient; + std::string mConfigDir; +}; + + +#endif // OPENDHTMGR_H diff --git a/libretroshare/src/_dht/servers.txt b/libretroshare/src/_dht/servers.txt new file mode 100644 index 000000000..588cb8e95 --- /dev/null +++ b/libretroshare/src/_dht/servers.txt @@ -0,0 +1,163 @@ +Wed Jan 16 04:13:01 UTC 2008 +1: 128.84.154.45:5850 planetlab6.cs.cornell.edu +2: 129.107.35.132:5850 planetlab2.uta.edu +3: 128.8.126.112:5850 pepper.planetlab.cs.umd.edu +4: 128.220.247.29:5850 planetlab2.isi.jhu.edu +5: 141.117.68.62:5850 planetlab-2.rml.ryerson.ca +6: 128.119.247.211:5850 planetlab2.cs.umass.edu +7: 129.10.120.194:5850 planetlabtwo.ccs.neu.edu +8: 152.3.138.4:5850 planetlab4.cs.duke.edu +9: 138.23.204.232:5850 planet-lab2.cs.ucr.edu +10: 192.197.121.3:5850 node-2.mcgillplanetlab.org +11: 169.229.50.8:5850 planetlab6.Millennium.Berkeley.EDU +12: 75.130.96.12:5850 75-130-96-12.static.oxfr.ma.charter.com +13: 12.46.129.21:5850 planet1.berkeley.intel-research.net +14: 128.112.139.82:5850 planetlab-8.CS.Princeton.EDU +15: 128.31.1.13:5850 planetlab3.csail.mit.edu +16: 134.121.64.4:5850 planetlab1.eecs.wsu.edu +17: 205.189.33.178:5850 planet1.ottawa.canet4.nodes.planet-lab.org +18: 143.205.172.12:5850 plab2-itec.uni-klu.ac.at +19: 192.16.125.12:5850 planetlab-2.ssvl.kth.se +20: 128.238.88.65:5850 planetlab2.poly.edu +21: 193.10.133.129:5850 planetlab-2.it.uu.se +22: 128.227.56.81:5850 planetlab1.acis.ufl.edu +23: 130.75.87.83:5850 planet1.l3s.uni-hannover.de +24: 152.3.138.3:5850 planetlab3.cs.duke.edu +25: 213.19.160.196:5850 planetlab-3.amst.nodes.planet-lab.org +26: 195.116.60.1:5850 planetlab1.warsaw.rd.tp.pl +27: 128.83.122.180:5850 planetlab2.csres.utexas.edu +28: 128.114.63.14:5850 planetslug1.cse.ucsc.edu +29: 129.174.79.248:5850 plgmu2.gmu.edu +30: 169.229.50.18:5850 planetlab16.Millennium.Berkeley.EDU +31: 138.15.10.55:5850 plab1.nec-labs.com +32: 128.208.4.197:5850 planetlab01.cs.washington.edu +33: 129.108.202.11:5850 planetlab2.utep.edu +34: 128.220.247.28:5850 planetlab1.isi.jhu.edu +35: 131.179.112.70:5850 Planetlab1.CS.UCLA.EDU +36: 169.229.50.15:5850 planetlab13.Millennium.Berkeley.EDU +37: 129.137.253.252:5850 planetlab2.uc.edu +38: 128.112.139.96:5850 planetlab-4.CS.Princeton.EDU +39: 128.232.103.201:5850 planetlab1.xeno.cl.cam.ac.uk +40: 128.208.4.199:5850 planetlab03.cs.washington.edu +41: 194.80.38.243:5850 planetlab2.cs-ipv6.lancs.ac.uk +42: 193.1.201.26:5850 planetlab-1.tssg.org +43: 193.136.191.26:5850 planetlab-2.iscte.pt +44: 150.65.32.68:5850 planet1.jaist.ac.jp +45: 136.145.115.196:5850 planetlab-02.ece.uprm.edu +46: 192.6.26.33:5850 pli2-pa-3.hpl.hp.com +47: 203.178.133.11:5850 203.178.133.11 +48: 128.31.1.12:5850 planetlab2.csail.mit.edu +49: 128.112.139.73:5850 planetlab-3.CS.Princeton.EDU +50: 129.137.253.253:5850 planetlab1.uc.edu +51: 131.246.191.41:5850 planetlab1.itwm.fhg.de +52: 129.170.214.192:5850 planetlab2.cs.dartmouth.edu +53: 128.31.1.17:5850 planetlab7.csail.mit.edu +54: 139.19.142.1:5850 planetlab01.mpi-sws.mpg.de +55: 129.105.44.253:5850 planetlab2.cs.northwestern.edu +56: 128.252.19.21:5850 vn2.cse.wustl.edu +57: 129.22.150.105:5850 planetlab-2.EECS.CWRU.Edu +58: 139.19.142.4:5850 planetlab04.mpi-sws.mpg.de +59: 142.150.238.13:5850 pl2.csl.utoronto.ca +60: 128.10.19.53:5850 planetlab2.cs.purdue.edu +61: 129.240.67.18:5850 planetlab4.ifi.uio.no +62: 128.163.142.20:5850 planetlab1.netlab.uky.edu +63: 163.221.11.74:5850 planetlab-04.naist.jp +64: 192.33.90.66:5850 planetlab1.inf.ethz.ch +65: 219.243.200.53:5850 dlut1.6planetlab.edu.cn +66: 128.112.139.78:5850 planetlab-10.CS.Princeton.EDU +67: 128.232.103.203:5850 planetlab3.xeno.cl.cam.ac.uk +68: 219.243.200.93:5850 ustc1.6planetlab.edu.cn +69: 128.42.6.143:5850 ricepl-1.cs.rice.edu +70: 152.15.98.227:5850 planetlab02.uncc.edu +71: 169.229.50.14:5850 planetlab12.Millennium.Berkeley.EDU +72: 129.22.150.90:5850 planetlab-1.EECS.CWRU.Edu +73: 128.10.19.52:5850 planetlab1.cs.purdue.edu +74: 128.252.19.20:5850 vn1.cse.wustl.edu +75: 64.161.10.2:5850 64.161.10.2 +76: 206.207.248.34:5850 planetlab1.arizona-gigapop.net +77: 128.208.4.198:5850 planetlab02.cs.washington.edu +78: 169.229.50.11:5850 planetlab9.Millennium.Berkeley.EDU +79: 128.232.103.202:5850 planetlab2.xeno.cl.cam.ac.uk +80: 141.213.4.201:5850 planetlab1.eecs.umich.edu +81: 63.64.153.84:5850 63.64.153.84 +82: 163.221.11.71:5850 planetlab-01.naist.jp +83: 128.208.4.99:5850 planetlab04.cs.washington.edu +84: 128.151.65.102:5850 planet2.cs.rochester.edu +85: 12.46.129.15:5850 planet5.berkeley.intel-research.net +86: 130.161.40.153:5850 planetlab1.ewi.tudelft.nl +87: 139.19.142.5:5850 planetlab05.mpi-sws.mpg.de +88: 141.76.45.17:5850 planet1.inf.tu-dresden.de +89: 150.65.32.66:5850 planet0.jaist.ac.jp +90: 128.119.247.210:5850 planetlab1.cs.umass.edu +91: 128.223.8.112:5850 planetlab2.cs.uoregon.edu +92: 132.68.237.34:5850 ds-pl1.technion.ac.il +93: 152.3.138.5:5850 planetlab5.cs.duke.edu +94: 132.252.152.194:5850 planetlab2.exp-math.uni-essen.de +95: 128.31.1.14:5850 planetlab4.csail.mit.edu +96: 64.161.10.3:5850 64.161.10.3 +97: 63.64.153.82:5850 63.64.153.82 +98: 192.42.83.252:5850 192.42.83.252 +99: 130.136.254.21:5850 planetlab1.CS.UniBO.IT +100: 128.59.20.226:5850 planetlab1.cs.columbia.edu +101: 128.192.101.217:5850 itchy.cs.uga.edu +102: 128.2.223.65:5850 PLANETLAB-3.CMCL.CS.CMU.EDU +103: 128.59.20.227:5850 planetlab2.cs.columbia.edu +104: 128.31.1.11:5850 planetlab1.csail.mit.edu +105: 128.220.231.3:5850 128.220.231.3 +106: 63.64.153.83:5850 63.64.153.83 +107: 128.8.126.111:5850 salt.planetlab.cs.umd.edu +108: 128.31.1.16:5850 planetlab6.csail.mit.edu +109: 128.220.231.2:5850 128.220.231.2 +110: 129.10.120.193:5850 planetlabone.ccs.neu.edu +111: 75.130.96.13:5850 75-130-96-13.static.oxfr.ma.charter.com +112: 202.244.160.251:5850 202.244.160.251 +113: 128.42.6.145:5850 ricepl-3.cs.rice.edu +114: 194.29.178.13:5850 planetlab3.mini.pw.edu.pl +115: 192.33.210.16:5850 lsirextpc01.epfl.ch +116: 169.229.50.16:5850 planetlab14.Millennium.Berkeley.EDU +117: 128.252.19.22:5850 vn3.cse.wustl.edu +118: 194.70.143.50:5850 system18.ncl-ext.net +119: 143.215.129.115:5850 planet2.cc.gt.atl.ga.us +120: 141.24.249.130:5850 planetlab2.fem.tu-ilmenau.de +121: 132.68.237.36:5850 ds-pl3.technion.ac.il +122: 35.9.27.26:5850 planetlab1.cse.msu.edu +123: 195.130.121.204:5850 planetlab1.cs.uoi.gr +124: 203.178.133.3:5850 planetlab1.otemachi.wide.ad.jp +125: 128.135.11.149:5850 planetlab1.cs.uchicago.edu +126: 200.132.0.70:5850 planetlab2.pop-rs.rnp.br +127: 150.165.15.19:5850 planetlab2.lsd.ufcg.edu.br +128: 128.84.154.49:5850 planetlab1.cs.cornell.edu +129: 192.6.19.120:5850 grouse.hpl.external.hp.com +130: 193.136.227.163:5850 planetlab1.fct.ualg.pt +131: 158.130.6.254:5850 planetlab1.cis.UPENN.EDU +132: 194.36.10.154:5850 194.36.10.154 +133: 69.110.237.115:5850 69.110.237.115 +134: 194.80.38.242:5850 planetlab1.cs-ipv6.lancs.ac.uk +135: 128.138.207.181:5850 planetlab1.cs.colorado.edu +136: 129.69.210.97:5850 planetvs2.informatik.uni-stuttgart.de +137: 141.76.45.18:5850 planet2.inf.tu-dresden.de +138: 216.165.109.82:5850 planet2.scs.cs.nyu.edu +139: 128.223.8.113:5850 planetlab3.cs.uoregon.edu +140: 128.238.88.64:5850 planetlab1.poly.edu +141: 12.46.129.22:5850 planet2.berkeley.intel-research.net +142: 131.246.191.42:5850 planetlab2.itwm.fhg.de +143: 129.130.252.138:5850 plab1.eece.ksu.edu +144: 219.243.200.81:5850 uestc1.6planetlab.edu.cn +145: 129.82.12.187:5850 planetlab-1.cs.colostate.edu +146: 140.247.60.126:5850 righthand.eecs.harvard.edu +147: 132.252.152.193:5850 planetlab1.iem.uni-due.de +148: 12.46.129.14:5850 planet4.berkeley.intel-research.net +149: 128.59.20.228:5850 planetlab3.cs.columbia.edu +150: 192.42.83.251:5850 192.42.83.251 +151: 128.84.154.71:5850 planetlab2.cs.cornell.edu +152: 203.30.39.241:5850 planetlab2.singaren.net.sg +153: 129.170.214.191:5850 planetlab1.cs.dartmouth.edu +154: 220.245.140.197:5850 220-245-140-197.static.tpgi.com.au +155: 133.11.240.56:5850 planetlab1.iii.u-tokyo.ac.jp +156: 129.69.210.96:5850 planetvs1.informatik.uni-stuttgart.de +157: 129.108.202.10:5850 planetlab1.utep.edu +158: 193.174.67.186:5850 planet01.HHI.FRAUNHOFER.DE +159: 128.135.11.152:5850 planetlab3.cs.uchicago.edu +160: 206.117.37.4:5850 206.117.37.4 +161: 219.243.201.17:5850 thu2.6planetlab.edu.cn +162: 155.98.35.2:5850 planetlab1.flux.utah.edu diff --git a/libretroshare/src/_dht/tst.ini b/libretroshare/src/_dht/tst.ini new file mode 100644 index 000000000..5e0904576 --- /dev/null +++ b/libretroshare/src/_dht/tst.ini @@ -0,0 +1,272 @@ +[local] +# if the hash (first arg) is 0, a random value will be used. +0 0.0.0.0 1234 4662 0 +[some_ignored_stuff] +these lines... +...under unrecognized sections... +...are ignored and left alone... +[overnet_peers] +# 259 contacts follow +01e32c7d216d1479ff1738b88f81bf3b 82.224.47.90 11297 0 +01ee86531f5070a344e9d0484744d14d 85.157.111.164 6267 0 +028b0545ae661b53d1538d90a7728fac 87.238.10.193 8150 0 +032a16ddd72ad9873e036db246930163 83.78.25.111 10089 0 +035a2148d7da45022bc36088cbeaa2d5 84.188.185.143 6780 0 +035d1f176411bd53b4578e383a66bcdd 82.82.140.226 4298 0 +03b47000764e0b3be3efaff6f81e1a0b 24.0.148.14 4665 0 +057b9a66771826db0bbd51483a10ff93 85.97.196.22 5678 0 +084fe60f368e1117c52e88e8f209113e 85.16.152.185 9363 0 +0857c84b6c77bf9e0d0cdeea6e56f11a 172.159.137.252 11316 1 +08ca7126b6ead7e6ea3870d13f32d004 83.11.233.250 3911 0 +090b57278c13cc673230893305538d1f 82.252.210.95 15030 1 +09166e1c64456cc7b3a989d1acb6bd65 84.98.135.162 11933 0 +092a05ae3c651f430c806bc49aeb2cb9 210.213.140.62 10521 0 +0941d60b7b2d83ef565047610570998c 83.181.168.72 3450 0 +09729bc4c1639fe3f4d914cbb8ddc213 82.247.37.205 7663 0 +098b7599f442273d1ec2f04710ff436f 80.142.123.8 6133 0 +09ebe97100d307d2e5419fa2f7cdfec3 87.10.147.210 10301 0 +0a157ca24a7445da325322144ee01993 24.74.148.251 9464 0 +0a23207ed240aa7f35202bd4e63b8bdd 84.170.225.102 22222 0 +0a2e67bee755ff15c5518b3072867034 87.14.169.88 4445 0 +0a39d5f89b4910945087ef9886f58c77 82.235.178.185 9818 0 +0becaf5dbbe2eb30694c86408cffb25b 82.234.43.27 19632 0 +1284fc9d5064cf0c89630fcc06f86f96 122.254.164.2 11839 0 +12b0ebaa0b3e17e16e38f7149f899e96 82.52.190.151 5405 0 +12cefeb85edc41e33686ec23f707621c 90.27.87.164 5637 0 +12dd8d3931c05d9dc7f9fe0fafc54e46 213.103.153.186 11880 0 +12e075a67748bd9888a537b1ddfc68bb 75.162.143.84 12100 0 +12f298eb89c926b23eef71724794f386 80.97.199.30 7007 0 +12f9fb4045af33cb47f5b87ac618b39d 85.140.95.208 6484 0 +12fced7a66d90c3c029e2fbb0d27d44e 70.48.189.93 6093 1 +13005d05429d43624683fd2c3ce83c65 83.214.38.125 7448 0 +13c90dbc29a45b6d8297ce758772c056 58.77.54.12 12291 0 +140470e218c7f8184af176e54cecc294 62.94.193.218 5600 0 +148a88de9e03129f7e3e15bdeae59fe1 70.48.175.156 10301 0 +14d04c790464ad46121934041d6254ec 62.57.36.125 4041 0 +14d589f5f766e40c0838fd9a74218f7a 71.56.125.35 7543 0 +158889e94d84e71c135935061743d456 200.16.221.180 3432 0 +1667353bcc5e4953c9dcb2b025a8e87b 212.76.242.34 9574 1 +168d639d6f6b4f87e1bd9b1df8344729 218.162.61.52 12901 0 +16c3bcc5ffc4ce92cdfc7db9f8d52184 80.188.8.104 4662 0 +182015e86828a195e22ccb2455378e91 220.134.22.185 3315 0 +18f43620c84d373a5935eb1cffa4bb96 89.169.146.14 8323 0 +1998abaf1be11abe19a2ea5961befa38 75.36.191.184 5002 0 +19f0b20dce022dca4ca915b7ce859b17 59.124.237.86 11590 0 +19ffaeafef17d524126ed45ff7326c2b 83.2.140.63 3128 0 +1a0b0df71afbac06620431e1ddb5f939 212.106.171.142 6711 0 +1b6b5245e54d2f68972bfb178b887724 203.49.242.90 6324 0 +1c20dc407cfa9b57778e929a7867af8a 87.175.196.166 5713 1 +21b3df22b8c563ac18ee4dfe35a155bc 58.232.60.235 4197 0 +21d59ad8e70e8e60659638e29eef5c25 80.203.138.183 6350 0 +220c4cc811b0511f13ccd0672fe2954a 83.28.247.107 3884 0 +287f16f02efd285381d7657ca5cd99d9 87.221.0.217 6672 0 +2981223354677a4ddf777902e9225bef 81.179.202.34 4222 0 +29a7a5751d92da3ade58ad92a1ed942d 124.8.65.42 4422 0 +29be351bbe4318605d535c76b9a76a6d 83.23.38.244 11386 0 +29cf29ab2b870b288a292cefed0d94bf 151.44.119.139 7688 0 +29d063f9aba16668462ab3edf2f43ab7 61.224.52.103 5687 0 +2a0c14e8d6383d9e5bf2730f0d0ec857 82.130.210.82 50020 0 +2a11275793d740d102a1348fd3f45909 80.53.196.58 9936 0 +2a519604b6a0119c126194063edf4b8c 68.148.121.42 6472 0 +2a83ac042d1278798b00d3352aefe98d 24.243.188.178 10301 0 +2acf26c3b18173eb4eb6f73622540c6a 86.56.213.115 3558 0 +2bf18d609eb338c9697c9e99379fd16a 85.137.81.79 11717 0 +3279ca195c2f4ddf598b8a7dbfd670b6 84.125.74.120 23232 0 +32ac6a1eeabdcf65f1505d2a95cee6c9 83.24.146.73 11964 1 +3304d216ec77e0fa5c18712d53c008f6 85.57.160.211 7721 0 +33a550bed46568b18eb91fae70ca0dbe 24.225.232.219 12164 0 +33e97bddd82e4d09131b7342acfeb79c 24.132.162.32 3016 0 +33e9ca51aa7f521589a2e6a3438b2821 80.180.76.149 12777 0 +34085309549df35140c8e27068083a63 212.59.192.220 4029 0 +36196c2ea442dd5ae56cd35a7d1f8619 90.10.169.218 12214 0 +361cea6dd0d377f200474a2d72ca7ba6 149.135.104.131 8190 0 +3625c3d644b80f221568d688f0f135c5 90.7.181.106 12615 0 +36317d125a1aff13035bcd3c0dec4978 80.36.124.22 46675 0 +3640f164a682b2c5d249bdcd8bf38274 80.35.196.42 4665 0 +36a55737e170cc90ef3ebee1c3b0dc72 217.228.164.18 5325 0 +36d7979c3328056ab80a53e94588ae9c 87.122.0.101 9902 0 +37075f69ca1fe6aabe53567c2ab48a1a 87.227.73.35 7776 0 +375615ba9163d8ecc6a5aed410fe4182 81.1.118.25 5667 1 +3796255e359f42a5c4fe41976307b5cc 85.141.108.236 4505 0 +38b0e0fb572b282ed6a610adf7a90de8 82.232.90.43 12223 0 +38b39efee6bf73cdcc5aff57e816d6ea 71.17.52.65 11438 0 +38f6091d65b3483cb6f90d670cb3e8fa 151.97.69.209 9997 0 +39037677e44d021350494e6f7c055a8b 82.225.33.80 11541 0 +39145af608906d68f059d04b64e8a291 84.129.0.36 8940 0 +397460b987ff9e9e360f52136618b2c3 83.38.86.240 3378 0 +3ab05f4b0cebd8a2ff689ce8bfb55232 82.238.254.166 3868 0 +3acac309140ec0f5e906b6c4ad64d4f4 212.241.66.225 10986 0 +3b27d9526ef86fbbf0723ae413723c1d 85.16.150.41 9948 0 +3ebecd58d1f7263b087d9159664997c3 80.192.21.44 3751 0 +3f614043083f37e5c8487d36b237ea78 124.57.75.101 9934 0 +3f755464997b43d4d0826fcbbc8b266f 219.84.26.38 7583 0 +3fac223d6c8f833c42d2ae248e206f21 220.72.28.213 4105 0 +40bbdfb51868764a24fb96ddf1035f33 70.113.90.243 11327 0 +40ce92ad1ac65e7290541e2fa1915bdc 148.160.184.5 4669 0 +416297dd4a79f9fe526182de7dbb1e4d 88.73.212.252 11139 1 +418b6b00550617e913a3f85cb6043aa4 80.33.124.231 7000 0 +41d492e47d76f13e4cb76579123a99e7 84.151.121.46 5687 0 +48ae47cc410aa2ae05c1b707744301f4 82.55.119.14 5875 0 +48d9789199fc1008b36acb095f9fc787 62.43.160.213 12573 0 +48e228897865a53b264f4c57db5312d1 71.107.201.77 4864 0 +49ad250210a9842cfce8fb6d8b848cc9 70.244.241.16 8155 0 +49c0c086162a51a485c8fc579176ba03 84.148.228.169 12762 0 +4a6a309f7d179856cffb9e6e47921c6a 88.22.50.75 6955 0 +4abd70a4ceeee66563edf074f152d4ce 89.180.5.149 12492 0 +4e2006734147d86a4f7f47199014be4c 70.53.44.52 80 0 +4e2540fad59bfabd00ff5b28519b1e61 82.7.244.135 4614 0 +4f8e9b83504d589c5591d58e81406e18 123.99.82.220 9992 0 +4fd92008c42283607a0ce22e90897696 86.139.46.140 8308 0 +4fedf465f25cdf48a66e5dec9d1bdd17 83.6.241.127 6882 0 +50bb895dd390303527424e828e5b54be 24.202.246.85 8230 0 +51ac71921161bcb6d8b7f8880f46eefc 24.232.81.207 7851 0 +51b83c36ac4adb9707fbc719f422cbe8 70.80.1.95 10677 0 +51f280b2fb3151daee581811edb3460d 172.183.248.32 10456 0 +523fcbe15ed90076457197d9e6750f1e 84.60.0.22 12831 0 +531d8c87b014bcf993094c420ed08cfe 74.103.42.209 4111 0 +53a75112814d14ecca2d80bf4a05304c 195.4.200.62 8750 0 +541e2bb43da70411b0ec9e4a2e3aa0bc 84.125.22.187 3867 0 +5abf0e1bb97d86db40d4002d4709bf1a 220.70.254.220 5244 0 +5dc4f61ca975687da17ad01d7a06285d 211.201.124.116 6059 0 +5efb862926700079413f76ab2c3e79e2 84.126.46.156 5444 0 +5f27354bfa0ba9ca2bae6106899cc1a3 83.10.113.23 5410 0 +5f5774d921ce06f3f12dfcb40dd73a49 213.185.6.53 4665 0 +5f5e5d1d9726f0e0149ffaa75751b05d 82.5.42.25 10301 0 +6060d6810bc1d07ba691bbe90b95585c 82.56.93.76 4792 0 +654bf80221c0dec4c74b0342c045abc6 83.53.130.173 4267 0 +68f38041f26ff4625247ccfa6c9645a2 83.27.138.127 3241 0 +6928f1993de7d20516fd1dd489213dbc 216.28.31.253 3620 0 +6b14fa18fc8b5ed357133b1a2502a094 82.159.13.169 12286 0 +6e21525341966500c9900aa17df49bf3 85.53.89.43 4582 0 +6e2614fe5389f95f36093d8723536929 58.234.36.88 5225 1 +6e4fc1983cc5fe4a310712bd063b9de4 83.192.115.177 6265 0 +6e93bca819d46c7c31164938482e276c 82.49.27.239 8463 0 +6eb7eb16713cf56f3d8e1ce368bebdab 87.10.218.82 10301 0 +6f0083083a91360160326195a59ea476 85.49.253.102 11583 1 +6f414f0a142b802b05932ee4fb810b12 62.80.230.79 6000 0 +6f548dd7068651c0ee22bfef37080862 172.141.131.116 3003 0 +6f66be33cebe99344cfcf328aa702cfc 82.234.247.90 5596 0 +70875fedb3fd7b5e49bcf7fb8323caad 211.213.130.221 4152 0 +70bbf8199ffef9edd68041ec954dfca0 218.101.206.9 3322 0 +70d009412251fd40d46d5475c33b5b4d 213.213.249.47 4662 0 +70dff47cbddf76aa58e13b4124076526 83.42.124.195 9256 0 +70ecffa5c424f8169d50922cf0de9267 81.60.195.33 47047 0 +7102b6d37c71f4bb249b4b6e20ac4c0d 146.115.56.136 3682 1 +712d6dc23289c4c269823f5cb6899e25 84.55.206.118 9228 0 +7156fd747d07a6865f5b02a8971bc78a 62.235.24.23 17008 0 +7186f68b51e03cfb745b65f8612f5619 83.198.187.23 5864 1 +71cc7aa04be67418f10bfbe4adb1bacf 87.5.76.116 5569 0 +71dbfe600812a1dd9a841951f68edca0 74.78.2.177 4548 0 +723b96cefcde27f6394bb312ddb3bc73 62.42.1.125 5783 0 +72f43b744b3170537794cde315148361 84.121.109.184 4175 0 +7341869dd42cdd9054e2578b68d53029 81.220.168.54 4985 1 +7a1956c5b41f66669c4b74c71742a058 88.23.168.112 9433 0 +7a1a6c659c387c936fef2666a1912a32 80.132.101.112 3633 0 +7a316a90de24721a9733d86d5321e8f0 84.189.143.14 4394 0 +7a50edadd981b09ba88b6f06acef3718 62.15.235.127 7095 0 +7a552fce17bb88689f601e531a7e572b 61.64.69.133 6719 0 +7a753356842ad958e7057a1fcfd2c083 211.201.93.71 10674 0 +7aa5334de0f210a741c5f1354104b3b1 70.252.73.94 10504 0 +7b0fc9ae76a8a2727ae54e843bfc3977 80.48.142.10 6162 0 +7b31f2b3500d8aa49537625afaac52db 24.67.81.50 9469 0 +7b441d23d521023f5a42cc9b594dd92a 83.92.40.199 6164 0 +7b4ecae988a881b978f7748088d8e051 67.168.85.39 9273 0 +7b65226b440f58717ec06ef5d935bc45 86.208.174.157 7253 0 +7b870dabafbd3419fe46740a5cd7fdfc 82.121.160.160 5040 0 +7b8879cd08a41d3bf18cb6b00b12e61c 88.24.51.189 11127 0 +7b8feeeecb097e817fe35416be73fc56 83.6.232.250 5181 0 +7bd571d08d784662e96f7bae7f7f17b3 84.57.158.33 7222 0 +7bf2513793a5994b5cad8546f6231e89 84.75.199.138 6082 0 +7c4e2c83d7417f42afb85c25d903629f 83.26.117.189 4736 0 +7db9b910b7a85739740f86b81321c5e1 83.21.71.92 6174 0 +7f51b9d5b5e986f212f34274aff7e4c3 90.154.213.232 59800 0 +7f9b3a74b692c7bb5b75e450122d6608 84.77.5.138 55000 0 +7fd158be4a5f243789e123ef83d3edf0 82.54.224.155 23830 0 +84396c8cf1a26258cba101ea007a49d9 89.228.227.215 8654 0 +84c97bd4a9fa479440ee7ef35947ce38 70.82.82.220 5290 0 +8ae1f2710e59c77f8266a12d028a8aaf 212.241.64.215 4854 0 +900ffda15c6702a93b220738f6f6bccb 84.25.7.56 7746 0 +90a87e1fe896621f14416995bd3166af 134.109.132.156 16563 0 +90a8d8cb9c9af9c2e76dac650c189d00 83.23.155.182 8914 0 +90b399ec0fbe1dab3471e208598d2e7e 84.44.231.141 28583 0 +90bcf4c6d0620aa9faa928b6da3b1d17 213.47.112.74 3404 0 +9200db48b63d6331b747621d73cfd3ef 125.135.73.172 5510 0 +923a3ca51d2c173795ea7980fec03fa4 82.61.70.247 8014 0 +92de6303460273a43508296b6237c078 124.61.19.247 3348 0 +92f2c65e8d8c984ecae982c8f9cad81e 85.16.150.41 9948 0 +945f69d2b0fed4d40c501d18ac1ee335 84.255.205.251 6818 0 +95f23a606a61d0eedccfc88c671c9504 210.159.160.154 4188 0 +960ed75cdf0e8e55d8bdf2122779006b 80.102.115.141 3915 0 +96e1ba371333a60439608576f729617e 84.121.87.1 47047 0 +98d02d1b5b7ad14dd13535ed11b51c48 85.53.69.99 10003 0 +9d9a51252908efca21b7f5940d5c16ae 82.225.38.240 7821 0 +9e31d3105d1be1be100c2dbca9c1cedb 84.183.164.47 7204 0 +9e53862ce85a043876da4a5784ad1661 85.140.63.22 7516 0 +9edc2fc255ebae8396d622cb15957176 83.112.107.20 8180 1 +9ee556648ad3baf1f792aad85e470a7c 219.74.80.197 6601 0 +9fa9acb2252a2b65b5bfe032cb434281 81.240.140.43 9703 0 +a167a1c1a719856704541c0a1c3e03a9 69.241.238.138 11593 0 +a82320cb11db5a34d2e692c5b7ad19d8 88.24.214.34 9534 0 +a8967880514d80246b2d940d89907976 220.244.126.14 4668 1 +a914e917b7c972d0ddb0f5d654e9aadc 84.122.49.158 12769 0 +a91b9efdde30841d46de0b12040b948c 85.155.209.92 5707 0 +a9b06362d0342d42b24902cb3d71683d 75.46.112.130 9576 0 +acaca1572ac1f9cb9953e55b2729249d 83.35.237.97 4665 0 +b2ae365b21df68b48988045b63d4d6fc 189.172.29.169 9874 0 +b4bddaca531a4f012d4fa46900f69813 71.9.169.115 5775 0 +b5c9a247777ddae8fcfa83cee4ac676e 219.68.29.74 6230 1 +b74595669f238061c5b30a518ae33fa5 83.25.82.238 5326 0 +c12d62c54b9b343874dc7c8366c2cfb6 189.157.29.196 8705 0 +c14322f92dc74c67dc0f864d272fcbf7 69.31.93.178 3471 0 +c1604c1d202792be1dca16283d8e9d5a 220.124.224.75 9581 0 +c1bef91ee0fac09f1a54d827546e6a0a 87.11.206.239 3959 0 +c21d96781cc4c3d2b16407d76f02e944 218.163.184.113 8597 0 +c23d212ae659766e8e46438fcfd7dc22 172.180.110.81 3086 0 +c285e7b2ab22453496522299b15b3801 59.12.208.195 11267 0 +c2bd693941ef041db66d2fe5c1692e59 88.9.121.245 9384 1 +c30bdae50cb39cba80ba9ac1a5e1a65a 82.58.189.230 10301 0 +c3b0f868f4a9abae3eb7007ab9e2e7c8 87.123.217.188 9030 0 +c54a4feeb6618bfe854146f560ad4c47 81.214.39.120 10000 0 +c57a5e547d138d1f581221f17e0e272e 86.215.168.93 11447 0 +c5be09328b367f7702397cae1711f586 83.53.177.127 11315 0 +c5bf7360aa07f31c07830a7370431c8a 61.224.78.247 12595 0 +c8618647749d12e3e0995e3f0c556a5b 70.111.26.144 6133 0 +c8ac99b1bfc68b615e165129f9b182d5 211.233.2.100 12542 0 +db19cb61c98529a91384cf06493be556 210.180.124.29 3246 0 +db45d9513bbaf7c3c5bf3e2fffd3012c 83.31.233.170 4471 0 +db4b83b43f36bc58ac2685743533a389 65.189.237.244 8044 0 +db5dc765e684ba9a610a865800de3416 81.198.131.36 12718 0 +db8be48ab25ea2ebff67f3f4312dd204 84.48.235.130 5999 1 +db9ffaa55e3712f9cee25b805732ee7b 84.9.76.208 10209 0 +dbb5697be82496bb0c46c3c0a2df3110 61.247.84.226 12426 0 +dbd681193c024ffce547fdb999ae8339 84.177.92.139 7017 0 +dbdd57d92f889e6c84a344d862e23826 84.61.146.49 5751 0 +dbe7aec6a2535f0ff4172ca2917c853c 89.78.201.185 6787 0 +e119f64361e2022eb2f8e16ab704ac79 70.177.168.143 3893 0 +e26c5ade9519477fbfb754e142758641 87.123.168.236 5002 0 +e32ad67eef113f2788c5e438932968d8 85.216.39.254 8579 0 +e36b23d3b0e5c4e653008aa0fe683941 213.216.232.88 11108 0 +e38016ff75ecb0de179162256b5afdb1 83.61.12.146 8020 0 +e380e102024f2e299e7ed2ed847c0edc 87.103.45.238 10901 0 +e39b3800ff70830b5e158f334197cb7b 222.106.229.231 4474 0 +e7025c81e4f11bd9595eb5b12635ad88 68.185.86.95 6842 0 +e702aab5bf92f3356d3a26590e736def 74.56.202.29 8029 0 +e71f3f7252bc12414cd3fa425f9ae8f3 88.17.127.248 10863 0 +e75578be101ba7e8a36ae1072682f5f7 122.34.133.174 9592 0 +e75f71fd8126965e32e23f1056056141 81.203.63.82 1756 0 +edd8190b83b7ed219536320d4ecb7691 67.83.25.1 4662 0 +efaff405e405967bae5ea9264229f386 211.187.188.231 3915 0 +efbdc05dc73789a0656b091186ee1089 71.100.59.158 7519 0 +f0831665903a6b37e4205ace3621a925 74.114.66.20 3420 0 +f0a877163f230e7fc690022d564ad4f5 213.46.9.204 9676 0 +f0c1976867bfa84bbd0929ebb1ec8028 74.103.127.57 8805 0 +f296f17abd4ccb3ad63a99468eb96060 82.232.173.22 8754 0 +f5932b7cee522a08ecb627d47f5b60f5 121.124.152.54 4104 0 +f66f25c51aa05ea462694b9055b70193 84.143.27.99 7665 0 +f7508519f31549d0018f363e58e4646c 125.224.193.111 10729 0 +f8aa2bd3d4b288fbc520ad0f121416d7 213.239.205.232 10755 0 +f8ca9f346d4ac702695dbddbf5b7f0bb 90.13.150.216 11403 0 +[other_stuff] +blah blah +blah +[blacklisted_nodes] diff --git a/libretroshare/src/_pqi/authgpg.cc b/libretroshare/src/_pqi/authgpg.cc new file mode 100644 index 000000000..1b3865d54 --- /dev/null +++ b/libretroshare/src/_pqi/authgpg.cc @@ -0,0 +1,2335 @@ +/* + * libretroshare/src gpgauthmgr.cc + * + * GnuPG/GPGme interface for RetroShare. + * + * Copyright 2008-2009 by Robert Fernie, Retroshare Team. + * + * This library is free software; you can redistribute it and/or + * modify it under the termsf the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + * + */ + +/**** + * At an SSL Certificate level: + * Processx509() calls (virtual) ValidateCertificate() to check if it correctly + * signed by an known PGP certificate. + * + * this will return true - even if the pgp cert is not authed. + * + * a connection will cause VerifyX509Callback to be called. This is a virtual fn. + * + * AuthCertificate() is called to make a certificate authenticated. + * this does nothing but set a flag at the SSL level + * no real auth at SSL only level. + * + * GPG Functions: + * ValidateCertificate() calls, + * bool GPGAuthMgr::AuthX509(X509 *x509) + * VerifySignature() + * + * VerifyX509Callback() + * calls AuthX509(). + * calls isPGPAuthenticated(std::string id) + * + * AuthCertificate(). + * check isPGPAuthenticated(). + * if not - sign PGP certificate. + * + * access to local data is protected via pgpMtx. + */ + +#include "authgpg.h" +#include +#include + +/* Turn a set of parameters into a string */ +static std::string setKeyPairParams(bool useRsa, unsigned int blen, + std::string name, std::string comment, std::string email, + std::string passphrase); + +static gpgme_key_t getKey(gpgme_ctx_t, std::string, std::string, std::string); + +static gpg_error_t keySignCallback(void *, gpgme_status_code_t, \ + const char *, int); + +static gpg_error_t trustCallback(void *, gpgme_status_code_t, \ + const char *, int); + +static void ProcessPGPmeError(gpgme_error_t ERR); + +/* Function to sign X509_REQ via GPGme. + */ + +// the single instance of this, but only when SSL Only +static GPGAuthMgr instance_gpgroot; + +p3AuthMgr *getAuthMgr() +{ + return &instance_gpgroot; +} + +gpgcert::gpgcert() + :key(NULL) +{ + return; +} + +gpgcert::~gpgcert() +{ + if (key) + { + gpgme_key_unref(key); + } +} + +gpg_error_t pgp_pwd_callback(void *hook, const char *uid_hint, const char *passphrase_info, int prev_was_bad, int fd) +{ + const char *passwd = (const char *) hook; + + if (prev_was_bad) + fprintf(stderr, "pgp_pwd_callback() Prev was bad!\n"); + //fprintf(stderr, "pgp_pwd_callback() Set Password to:\"%s\"\n", passwd); + fprintf(stderr, "pgp_pwd_callback() Set Password\n"); + + write(fd, passwd, strlen(passwd)); + write(fd, "\n", 1); /* needs a new line? */ + + return 0; +} + +static char *PgpPassword = NULL; + +bool GPGAuthMgr::setPGPPassword_locked(std::string pwd) +{ + /* reset it while we change it */ + gpgme_set_passphrase_cb(CTX, NULL, NULL); + + if (PgpPassword) + free(PgpPassword); + PgpPassword = (char *) malloc(pwd.length() + 1); + memcpy(PgpPassword, pwd.c_str(), pwd.length()); + PgpPassword[pwd.length()] = '\0'; + + gpgme_set_passphrase_cb(CTX, pgp_pwd_callback, (void *) PgpPassword); + + return true; +} + + +GPGAuthMgr::GPGAuthMgr() + :gpgmeInit(false) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + setlocale(LC_ALL, ""); + gpgme_check_version(NULL); + gpgme_set_locale(NULL, LC_CTYPE, setlocale (LC_CTYPE, NULL)); + + #ifndef HAVE_W32_SYSTEM + gpgme_set_locale(NULL, LC_MESSAGES, setlocale (LC_MESSAGES, NULL)); + #endif + + if (GPG_ERR_NO_ERROR != gpgme_engine_check_version(GPGME_PROTOCOL_OpenPGP)) + { + std::cerr << "Error check engine version"; + std::cerr << std::endl; + return; + } + + if (GPG_ERR_NO_ERROR != gpgme_get_engine_info(&INFO)) + { + std::cerr << "Error getting engine info"; + std::cerr << std::endl; + return; + } + + /* Create New Contexts */ + if (GPG_ERR_NO_ERROR != gpgme_new(&CTX)) + { + std::cerr << "Error creating GPGME Context"; + std::cerr << std::endl; + return; + } + + /* setup the protocol */ + if (GPG_ERR_NO_ERROR != gpgme_set_protocol(CTX, GPGME_PROTOCOL_OpenPGP)) + { + std::cerr << "Error creating Setting Protocol"; + std::cerr << std::endl; + return; + } + + /* if we get to here -> we have inited okay */ + gpgmeInit = true; + + storeAllKeys_locked(); + printAllKeys_locked(); + updateTrustAllKeys_locked(); +} + +/* This function is called when retroshare is first started + * to get the list of available GPG certificates. + * This function should only return certs for which + * the private(secret) keys are available. + * + * returns false if GnuPG is not available. + */ + +bool GPGAuthMgr::availablePGPCertificates(std::list &ids) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + int i = 0; + gpgme_key_t KEY = NULL; + gpg_error_t ERR; + + /* XXX should check that CTX is valid */ + if (!gpgmeInit) + { + return false; + } + + + /* Initiates a key listing */ + if (GPG_ERR_NO_ERROR != gpgme_op_keylist_start (CTX, "", 1)) + { + std::cerr << "Error iterating through KeyList"; + std::cerr << std::endl; + return false; + + } + + /* Loop until end of key */ + for(i = 0;(GPG_ERR_NO_ERROR == (ERR = gpgme_op_keylist_next (CTX, &KEY))); i++) + { + if (KEY->subkeys) + { + ids.push_back(KEY->subkeys->keyid); + std::cerr << "GPGAuthMgr::availablePGPCertificates() Added: " + << KEY->subkeys->keyid << std::endl; + } + else + { + std::cerr << "GPGAuthMgr::availablePGPCertificates() Missing subkey" + << std::endl; + } + } + + if (GPG_ERR_NO_ERROR != gpgme_op_keylist_end(CTX)) + { + std::cerr << "Error ending KeyList"; + std::cerr << std::endl; + return false; + } + + std::cerr << "GPGAuthMgr::availablePGPCertificates() Secret Key Count: " << i << std::endl; + + /* return false if there are no private keys */ + return (i > 0); +} + +/* You can initialise Retroshare with + * (a) load existing certificate. + * (b) a new certificate. + * + * This function must be called successfully (return == 1) + * before anything else can be done. (except above fn). + */ +int GPGAuthMgr::GPGInit(std::string ownId, std::string name, std::string passphrase) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + gpgme_key_t newKey; + gpg_error_t ERR; + + if (!gpgmeInit) { + return 0; + } + +/***** + if (!isOwnCert(ownId)) + { + return 0; + } +*****/ + + if(GPG_ERR_NO_ERROR != (ERR = gpgme_get_key(CTX, ownId.c_str(), &newKey, 1))) { + std::cerr << "Error reading the key from keyring" << std::endl; + return 0; + } + + mOwnGpgCert.user.name = name; + mOwnGpgCert.user.email = newKey->uids->email; + mOwnGpgCert.user.fpr = newKey->subkeys->fpr; + mOwnGpgCert.user.id = ownId; + mOwnGpgCert.key = newKey; + this->passphrase = passphrase; + + mOwnId = ownId; + gpgmeKeySelected = true; + + setPGPPassword_locked(passphrase); + + return true; +} + +int GPGAuthMgr::GPGInit(std::string name, std::string comment, + std::string email, std::string passphrase) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + gpgme_key_t newKey; + gpgme_genkey_result_t result; + gpg_error_t ERR; + + if (!gpgmeInit) { + return 0; + } + + if(GPG_ERR_NO_ERROR != (ERR = gpgme_op_genkey(CTX, setKeyPairParams(true, 2048, name, comment, email, \ + passphrase).c_str(), NULL, NULL))) { + std::cerr << "Error generating the key" << std::endl; + return 0; + } + + if((result = gpgme_op_genkey_result(CTX)) == NULL) + return 0; + + + if(GPG_ERR_NO_ERROR != (ERR = gpgme_get_key(CTX, result->fpr, &newKey, 1))) { + std::cerr << "Error reading own key" << std::endl; + return 0; + } + + mOwnGpgCert.user.name = name; + mOwnGpgCert.user.email = email; + mOwnGpgCert.user.fpr = newKey->subkeys->fpr; + mOwnGpgCert.user.id = newKey->subkeys->keyid; + mOwnGpgCert.key = newKey; + + this->passphrase = passphrase; + setPGPPassword_locked(passphrase); + + mOwnId = mOwnGpgCert.user.id; + gpgmeKeySelected = true; + + return 1; +} + + GPGAuthMgr::~GPGAuthMgr() +{ +} + + +// store all keys in map mKeyList to avoid callin gpgme exe repeatedly +bool GPGAuthMgr::storeAllKeys_locked() +{ + std::cerr << "GPGAuthMgr::storeAllKeys_locked()"; + std::cerr << std::endl; + + gpg_error_t ERR; + if (!gpgmeInit) + { + std::cerr << "Error since GPG is not initialised"; + std::cerr << std::endl; + return false; + } + + std::cerr << "GPGAuthMgr::storeAllKeys_locked() clearing existing ones"; + std::cerr << std::endl; + mKeyList.clear(); + + /* enable SIG mode */ + gpgme_keylist_mode_t origmode = gpgme_get_keylist_mode(CTX); + gpgme_keylist_mode_t mode = origmode | GPGME_KEYLIST_MODE_SIGS; + + gpgme_set_keylist_mode(CTX, mode); + + /* store keys */ + gpgme_key_t KEY = NULL; + + /* Initiates a key listing 0 = All Keys */ + if (GPG_ERR_NO_ERROR != gpgme_op_keylist_start (CTX, "", 0)) + { + std::cerr << "Error iterating through KeyList"; + std::cerr << std::endl; + gpgme_set_keylist_mode(CTX, origmode); + return false; + } + + /* Loop until end of key */ + for(int i = 0;(GPG_ERR_NO_ERROR == (ERR = gpgme_op_keylist_next (CTX, &KEY))); i++) + { + /* store in pqiAuthDetails */ + gpgcert nu; + + /* NB subkeys is a linked list and can contain multiple keys. + * first key is primary. + */ + + if ((!KEY->subkeys) || (!KEY->uids)) + { + std::cerr << "Invalid Key in List... skipping"; + std::cerr << std::endl; + continue; + } + + /* In general MainSubKey is used to sign all others! + * Don't really need to worry about other ids either. + */ + gpgme_subkey_t mainsubkey = KEY->subkeys; + nu.user.id = mainsubkey->keyid; + nu.user.fpr = mainsubkey->fpr; + + std::cerr << "MAIN KEYID: " << nu.user.id; + std::cerr << " FPR: " << nu.user.fpr; + std::cerr << std::endl; + + + gpgme_subkey_t subkeylist = KEY->subkeys; + while(subkeylist != NULL) + { + std::cerr << "\tKEYID: " << subkeylist->keyid; + std::cerr << " FPR: " << subkeylist->fpr; + std::cerr << std::endl; + + subkeylist = subkeylist->next; + } + + + /* NB uids is a linked list and can contain multiple ids. + * first id is primary. + */ + + gpgme_user_id_t mainuid = KEY->uids; + nu.user.name = mainuid->name; + nu.user.email = mainuid->email; + gpgme_key_sig_t mainsiglist = mainuid->signatures; + while(mainsiglist != NULL) + { + if (mainsiglist->status == GPG_ERR_NO_ERROR) + { + /* add as a signature ... even if the + * we haven't go the peer yet. + * (might be yet to come). + */ + + std::string keyid = mainsiglist->keyid; + if (nu.user.signers.end() == std::find( + nu.user.signers.begin(), + nu.user.signers.end(),keyid)) + { + nu.user.signers.push_back(keyid); + } + } + mainsiglist = mainsiglist->next; + } + + gpgme_user_id_t uidlist = KEY->uids; + while(uidlist != NULL) + { + std::cerr << "\tUID: " << uidlist->uid; + std::cerr << " NAME: " << uidlist->name; + std::cerr << " EMAIL: " << uidlist->email; + std::cerr << " VALIDITY: " << uidlist->validity; + std::cerr << std::endl; + gpgme_key_sig_t usiglist = uidlist->signatures; + while(usiglist != NULL) + { + std::cerr << "\t\tSIG KEYID: " << usiglist->keyid; + std::cerr << " UID: " << usiglist->uid; + std::cerr << " NAME: " << usiglist->name; + std::cerr << " EMAIL: " << usiglist->email; + std::cerr << " VALIDITY: " << (usiglist->status == GPG_ERR_NO_ERROR); + std::cerr << std::endl; + + usiglist = usiglist->next; + } + + uidlist = uidlist->next; + } + + /* signatures are attached to uids... but only supplied + * if GPGME_KEYLIST_MODE_SIGS is on. + * signature notation supplied is GPGME_KEYLIST_MODE_SIG_NOTATION is on + */ + + nu.user.trustLvl = KEY->owner_trust; + nu.user.ownsign = KEY->can_sign; + nu.user.validLvl = mainuid->validity; + nu.user.trusted = (mainuid->validity > GPGME_VALIDITY_MARGINAL); + + /* grab a reference, so the key remains */ + gpgme_key_ref(KEY); + nu.key = KEY; + + /* store in map */ + mKeyList[nu.user.id] = nu; + } + + if (GPG_ERR_NO_ERROR != gpgme_op_keylist_end(CTX)) + { + std::cerr << "Error ending KeyList"; + std::cerr << std::endl; + gpgme_set_keylist_mode(CTX, origmode); + return false; + } + + gpgme_set_keylist_mode(CTX, origmode); + return true; + +} + +// update trust on all available keys. +bool GPGAuthMgr::updateTrustAllKeys_locked() +{ + gpg_error_t ERR; + if (!gpgmeInit) + { + std::cerr << "Error since GPG is not initialised"; + std::cerr << std::endl; + return false; + } + + + /* have to do this the hard way! */ + gpgme_trust_item_t ti = NULL; + std::map::iterator it; + + for(it = mKeyList.begin(); it != mKeyList.end(); it++) + { + /* check for trust items associated with key */ + std::string peerid = it->second.user.email; + std::cerr << "Searching GPGme for TrustInfo on: " << peerid; + std::cerr << std::endl; + + /* Initiates a key listing. NB: maxlevel is ignored!*/ + if (GPG_ERR_NO_ERROR != (ERR = gpgme_op_trustlist_start (CTX, peerid.c_str(), 0))) + { + std::cerr << "Error Starting Trust List"; + std::cerr << std::endl; + ProcessPGPmeError(ERR); + continue; + } + + + /* Loop until end of key */ + for(int i = 0;(GPG_ERR_NO_ERROR == (ERR = + gpgme_op_trustlist_next (CTX, &ti))); i++) + { + std::string keyid = ti->keyid; + int type = ti->type; + int level = ti->level; + + /* identify the peers, and add trust level */ + std::cerr << "GPGme Trust Item for: " << keyid; + std::cerr << std::endl; + + std::cerr << "\t Type: " << type; + std::cerr << " Level: " << level; + std::cerr << std::endl; + + std::cerr << "\t Owner Trust: " << ti->owner_trust; + std::cerr << " Validity: " << ti->validity; + std::cerr << " Name: " << ti->name; + std::cerr << std::endl; + + } + + std::cerr << "End of TrustList Iteration."; + std::cerr << std::endl; + ProcessPGPmeError(ERR); + + if (GPG_ERR_NO_ERROR != gpgme_op_trustlist_end(CTX)) + { + std::cerr << "Error ending TrustList"; + std::cerr << std::endl; + + ProcessPGPmeError(ERR); + } + } + + return true; + +} +bool GPGAuthMgr::printAllKeys_locked() +{ + + certmap::const_iterator it; + for(it = mKeyList.begin(); it != mKeyList.end(); it++) + { + std::cerr << "PGP Key: " << it->second.user.id; + std::cerr << std::endl; + + std::cerr << "\tName: " << it->second.user.name; + std::cerr << std::endl; + std::cerr << "\tEmail: " << it->second.user.email; + std::cerr << std::endl; + + std::cerr << "\ttrustLvl: " << it->second.user.trustLvl; + std::cerr << std::endl; + std::cerr << "\townsign?: " << it->second.user.ownsign; + std::cerr << std::endl; + std::cerr << "\ttrusted/valid: " << it->second.user.trusted; + std::cerr << std::endl; + std::cerr << "\tEmail: " << it->second.user.email; + std::cerr << std::endl; + + std::list::const_iterator sit; + for(sit = it->second.user.signers.begin(); + sit != it->second.user.signers.end(); sit++) + { + std::cerr << "\t\tSigner ID:" << *sit; + + /* do a naughty second search.. should be ok + * as we aren't modifying list. + */ + certmap::const_iterator kit = mKeyList.find(*sit); + if (kit != mKeyList.end()) + { + std::cerr << " Name:" << kit->second.user.name; + std::cerr << std::endl; + } + } + } + return true; +} + +bool GPGAuthMgr::printOwnKeys_locked() +{ + + certmap::iterator it; + for(it = mKeyList.begin(); it != mKeyList.end(); it++) + { + if (it->second.user.ownsign) + { + std::cerr << "Own PGP Key: " << it->second.user.id; + std::cerr << std::endl; + + std::cerr << "\tName: " << it->second.user.name; + std::cerr << std::endl; + std::cerr << "\tEmail: " << it->second.user.email; + std::cerr << std::endl; + } + } + return true; +} + + +X509 *GPGAuthMgr::SignX509Req(X509_REQ *req, long days, std::string gpg_passwd) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + /* Transform the X509_REQ into a suitable format to + * generate DIGEST hash. (for SSL to do grunt work) + */ + + +#define SERIAL_RAND_BITS 64 + + const EVP_MD *digest = EVP_sha1(); + ASN1_INTEGER *serial = ASN1_INTEGER_new(); + EVP_PKEY *tmppkey; + X509 *x509 = X509_new(); + if (x509 == NULL) + { + std::cerr << "GPGAuthMgr::SignX509Req() FAIL" << std::endl; + return NULL; + } + + long version = 0x00; + unsigned long chtype = MBSTRING_ASC; + X509_NAME *issuer_name = X509_NAME_new(); + X509_NAME_add_entry_by_txt(issuer_name, "CN", chtype, + (unsigned char *) mOwnId.c_str(), -1, -1, 0); +/**** + X509_NAME_add_entry_by_NID(issuer_name, 48, 0, + (unsigned char *) "email@email.com", -1, -1, 0); + X509_NAME_add_entry_by_txt(issuer_name, "O", chtype, + (unsigned char *) "org", -1, -1, 0); + X509_NAME_add_entry_by_txt(x509_name, "L", chtype, + (unsigned char *) "loc", -1, -1, 0); +****/ + + std::cerr << "GPGAuthMgr::SignX509Req() Issuer name: " << mOwnId << std::endl; + + BIGNUM *btmp = BN_new(); + if (!BN_pseudo_rand(btmp, SERIAL_RAND_BITS, 0, 0)) + { + std::cerr << "GPGAuthMgr::SignX509Req() rand FAIL" << std::endl; + return NULL; + } + if (!BN_to_ASN1_INTEGER(btmp, serial)) + { + std::cerr << "GPGAuthMgr::SignX509Req() asn1 FAIL" << std::endl; + return NULL; + } + BN_free(btmp); + + if (!X509_set_serialNumber(x509, serial)) + { + std::cerr << "GPGAuthMgr::SignX509Req() serial FAIL" << std::endl; + return NULL; + } + ASN1_INTEGER_free(serial); + + /* Generate SUITABLE issuer name. + * Must reference OpenPGP key, that is used to verify it + */ + + if (!X509_set_issuer_name(x509, issuer_name)) + { + std::cerr << "GPGAuthMgr::SignX509Req() issue FAIL" << std::endl; + return NULL; + } + X509_NAME_free(issuer_name); + + + if (!X509_gmtime_adj(X509_get_notBefore(x509),0)) + { + std::cerr << "GPGAuthMgr::SignX509Req() notbefore FAIL" << std::endl; + return NULL; + } + + if (!X509_gmtime_adj(X509_get_notAfter(x509), (long)60*60*24*days)) + { + std::cerr << "GPGAuthMgr::SignX509Req() notafter FAIL" << std::endl; + return NULL; + } + + if (!X509_set_subject_name(x509, X509_REQ_get_subject_name(req))) + { + std::cerr << "GPGAuthMgr::SignX509Req() sub FAIL" << std::endl; + return NULL; + } + + tmppkey = X509_REQ_get_pubkey(req); + if (!tmppkey || !X509_set_pubkey(x509,tmppkey)) + { + std::cerr << "GPGAuthMgr::SignX509Req() pub FAIL" << std::endl; + return NULL; + } + + std::cerr << "X509 Cert, prepared for signing" << std::endl; + + /*** NOW The Manual signing bit (HACKED FROM asn1/a_sign.c) ***/ + int (*i2d)(X509_CINF*, unsigned char**) = i2d_X509_CINF; + X509_ALGOR *algor1 = x509->cert_info->signature; + X509_ALGOR *algor2 = x509->sig_alg; + ASN1_BIT_STRING *signature = x509->signature; + X509_CINF *data = x509->cert_info; + EVP_PKEY *pkey = NULL; + const EVP_MD *type = EVP_sha1(); + + EVP_MD_CTX ctx; + unsigned char *p,*buf_in=NULL; + unsigned char *buf_hashout=NULL,*buf_sigout=NULL; + int i,inl=0,hashoutl=0,hashoutll=0; + int sigoutl=0,sigoutll=0; + X509_ALGOR *a; + + EVP_MD_CTX_init(&ctx); + + /* FIX ALGORITHMS */ + + a = algor1; + ASN1_TYPE_free(a->parameter); + a->parameter=ASN1_TYPE_new(); + a->parameter->type=V_ASN1_NULL; + + ASN1_OBJECT_free(a->algorithm); + a->algorithm=OBJ_nid2obj(type->pkey_type); + + a = algor2; + ASN1_TYPE_free(a->parameter); + a->parameter=ASN1_TYPE_new(); + a->parameter->type=V_ASN1_NULL; + + ASN1_OBJECT_free(a->algorithm); + a->algorithm=OBJ_nid2obj(type->pkey_type); + + + std::cerr << "Algorithms Fixed" << std::endl; + + /* input buffer */ + inl=i2d(data,NULL); + buf_in=(unsigned char *)OPENSSL_malloc((unsigned int)inl); + + hashoutll=hashoutl=EVP_MD_size(type); + buf_hashout=(unsigned char *)OPENSSL_malloc((unsigned int)hashoutl); + + sigoutll=sigoutl=2048; // hashoutl; //EVP_PKEY_size(pkey); + buf_sigout=(unsigned char *)OPENSSL_malloc((unsigned int)sigoutl); + + std::cerr << "Buffer Sizes: in: " << inl; + std::cerr << " HashOut: " << hashoutl; + std::cerr << " SigOut: " << sigoutl; + std::cerr << std::endl; + + if ((buf_in == NULL) || (buf_hashout == NULL) || (buf_sigout == NULL)) + { + hashoutl=0; + sigoutl=0; + fprintf(stderr, "GPGAuthMgr::SignX509Req: ASN1err(ASN1_F_ASN1_SIGN,ERR_R_MALLOC_FAILURE)\n"); + goto err; + } + p=buf_in; + + std::cerr << "Buffers Allocated" << std::endl; + + i2d(data,&p); + /* data in buf_in, ready to be hashed */ + EVP_DigestInit_ex(&ctx,type, NULL); + EVP_DigestUpdate(&ctx,(unsigned char *)buf_in,inl); + if (!EVP_DigestFinal(&ctx,(unsigned char *)buf_hashout, + (unsigned int *)&hashoutl)) + { + hashoutl=0; + fprintf(stderr, "GPGAuthMgr::SignX509Req: ASN1err(ASN1_F_ASN1_SIGN,ERR_R_EVP_LIB)\n"); + goto err; + } + + std::cerr << "Digest Applied: len: " << hashoutl << std::endl; + + /* NOW Sign via GPG Functions */ + if (!DoOwnSignature_locked(buf_hashout, hashoutl, buf_sigout, (unsigned int *) &sigoutl)) + { + sigoutl = 0; + goto err; + } + + passphrase = "NULL"; + + std::cerr << "Signature done: len:" << sigoutl << std::endl; + + /* ADD Signature back into Cert... Signed!. */ + + if (signature->data != NULL) OPENSSL_free(signature->data); + signature->data=buf_sigout; + buf_sigout=NULL; + signature->length=sigoutl; + /* In the interests of compatibility, I'll make sure that + * the bit string has a 'not-used bits' value of 0 + */ + signature->flags&= ~(ASN1_STRING_FLAG_BITS_LEFT|0x07); + signature->flags|=ASN1_STRING_FLAG_BITS_LEFT; + + std::cerr << "Certificate Complete" << std::endl; + + return x509; + + + err: + /* cleanup */ + std::cerr << "GPGAuthMgr::SignX509Req() err: FAIL" << std::endl; + + return NULL; +} + + + +#if 0 + int ASN1_sign(int (*i2d)(), X509_ALGOR *algor1, X509_ALGOR *algor2, + ASN1_BIT_STRING *signature, char *data, EVP_PKEY *pkey, + const EVP_MD *type) + +#define X509_sign(x,pkey,md) \ + ASN1_sign((int (*)())i2d_X509_CINF, x->cert_info->signature, \ + x->sig_alg, x->signature, (char *)x->cert_info,pkey,md) + + + return NULL; +} +#endif + + +bool GPGAuthMgr::AuthX509(X509 *x509) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + /* extract CN for peer Id */ + X509_NAME *issuer = X509_get_issuer_name(x509); + std::string id = ""; + + /* verify signature */ + + /*** NOW The Manual signing bit (HACKED FROM asn1/a_sign.c) ***/ + int (*i2d)(X509_CINF*, unsigned char**) = i2d_X509_CINF; + ASN1_BIT_STRING *signature = x509->signature; + X509_CINF *data = x509->cert_info; + EVP_PKEY *pkey = NULL; + const EVP_MD *type = EVP_sha1(); + + EVP_MD_CTX ctx; + unsigned char *p,*buf_in=NULL; + unsigned char *buf_hashout=NULL,*buf_sigout=NULL; + int i,inl=0,hashoutl=0,hashoutll=0; + int sigoutl=0,sigoutll=0; + X509_ALGOR *a; + + fprintf(stderr, "GPGAuthMgr::AuthX509()\n"); + + EVP_MD_CTX_init(&ctx); + + /* input buffer */ + inl=i2d(data,NULL); + buf_in=(unsigned char *)OPENSSL_malloc((unsigned int)inl); + + hashoutll=hashoutl=EVP_MD_size(type); + buf_hashout=(unsigned char *)OPENSSL_malloc((unsigned int)hashoutl); + + sigoutll=sigoutl=2048; //hashoutl; //EVP_PKEY_size(pkey); + buf_sigout=(unsigned char *)OPENSSL_malloc((unsigned int)sigoutl); + + std::cerr << "Buffer Sizes: in: " << inl; + std::cerr << " HashOut: " << hashoutl; + std::cerr << " SigOut: " << sigoutl; + std::cerr << std::endl; + + if ((buf_in == NULL) || (buf_hashout == NULL) || (buf_sigout == NULL)) + { + hashoutl=0; + sigoutl=0; + fprintf(stderr, "GPGAuthMgr::AuthX509: ASN1err(ASN1_F_ASN1_SIGN,ERR_R_MALLOC_FAILURE)\n"); + goto err; + } + p=buf_in; + + std::cerr << "Buffers Allocated" << std::endl; + + i2d(data,&p); + /* data in buf_in, ready to be hashed */ + EVP_DigestInit_ex(&ctx,type, NULL); + EVP_DigestUpdate(&ctx,(unsigned char *)buf_in,inl); + if (!EVP_DigestFinal(&ctx,(unsigned char *)buf_hashout, + (unsigned int *)&hashoutl)) + { + hashoutl=0; + fprintf(stderr, "GPGAuthMgr::AuthX509: ASN1err(ASN1_F_ASN1_SIGN,ERR_R_EVP_LIB)\n"); + goto err; + } + + std::cerr << "Digest Applied: len: " << hashoutl << std::endl; + + /* copy data into signature */ + sigoutl = signature->length; + memmove(buf_sigout, signature->data, sigoutl); + + /* NOW Sign via GPG Functions */ + if (!VerifySignature_locked(id, buf_hashout, hashoutl, buf_sigout, (unsigned int) sigoutl)) + { + sigoutl = 0; + goto err; + } + + return true; + + err: + return false; +} + + +void ProcessPGPmeError(gpgme_error_t ERR) +{ + gpgme_err_code_t code = gpgme_err_code(ERR); + gpgme_err_source_t src = gpgme_err_source(ERR); + + std::cerr << "GPGme ERROR: Code: " << code << " Source: " << src << std::endl; + std::cerr << "GPGme ERROR: " << gpgme_strerror(ERR) << std::endl; + +} + +void print_pgpme_verify_summary(unsigned int summary) +{ + std::cerr << "\tFLAGS:"; + if (summary & GPGME_SIGSUM_VALID) + std::cerr << " VALID "; + if (summary & GPGME_SIGSUM_GREEN) + std::cerr << " GREEN "; + if (summary & GPGME_SIGSUM_RED) + std::cerr << " RED "; + if (summary & GPGME_SIGSUM_KEY_REVOKED) + std::cerr << " KEY_REVOKED "; + if (summary & GPGME_SIGSUM_KEY_EXPIRED) + std::cerr << " KEY_EXPIRED "; + if (summary & GPGME_SIGSUM_KEY_MISSING) + std::cerr << " KEY_MISSING "; + if (summary & GPGME_SIGSUM_CRL_MISSING) + std::cerr << " CRL_MISSING "; + if (summary & GPGME_SIGSUM_CRL_TOO_OLD) + std::cerr << " CRL_TOO_OLD "; + if (summary & GPGME_SIGSUM_BAD_POLICY) + std::cerr << " BAD_POLICY "; + if (summary & GPGME_SIGSUM_SYS_ERROR) + std::cerr << " SYS_ERROR "; + std::cerr << std::endl; +} + + +bool GPGAuthMgr::DoOwnSignature_locked(void *data, unsigned int datalen, void *buf_sigout, unsigned int *outl) +{ + /* setup signers */ + gpgme_signers_clear(CTX); + if (GPG_ERR_NO_ERROR != gpgme_signers_add(CTX, mOwnGpgCert.key)) + { + std::cerr << "GPGAuthMgr::DoOwnSignature() Error Adding Signer"; + std::cerr << std::endl; + } + + gpgme_data_t gpgmeData; + gpgme_data_t gpgmeSig; + if (GPG_ERR_NO_ERROR != gpgme_data_new_from_mem(&gpgmeData, (const char *) data, datalen, 1)) + { + std::cerr << "Error create Data"; + std::cerr << std::endl; + } + + if (GPG_ERR_NO_ERROR != gpgme_data_new(&gpgmeSig)) + { + std::cerr << "Error create Sig"; + std::cerr << std::endl; + } + + /* move string data to gpgmeData */ + gpgme_set_armor (CTX, 0); + + gpgme_sig_mode_t mode = GPGME_SIG_MODE_DETACH; + gpg_error_t ERR; + if (GPG_ERR_NO_ERROR != (ERR = gpgme_op_sign(CTX,gpgmeData, gpgmeSig, mode))) + { + ProcessPGPmeError(ERR); + std::cerr << "GPGAuthMgr::Sign FAILED ERR: " << ERR; + std::cerr << std::endl; + } + + gpgme_sign_result_t res = gpgme_op_sign_result(CTX); + + if (res) + { + fprintf(stderr, "Sign Got Result\n"); + } + else + { + fprintf(stderr, "Sign Failed to get Result\n"); + } + + gpgme_invalid_key_t ik = res->invalid_signers; + gpgme_new_signature_t sg = res->signatures; + while(ik != NULL) + { + fprintf(stderr, "GPGAuthMgr::Sign, Invalid by: %s\n", ik->fpr); + ik = ik->next; + } + + while(sg != NULL) + { + fprintf(stderr, "GPGAuthMgr::Signed by: %s\n", sg->fpr); + sg = sg->next; + } + + /* now extract the data from gpgmeSig */ + size_t len = 0; + int len2 = len; + char *export_sig = gpgme_data_release_and_get_mem(gpgmeSig, &len); + fprintf(stderr, "GPGAuthMgr::Signature len: %d \n", len2); + if (len < *outl) + { + *outl = len; + } + memmove(buf_sigout, export_sig, *outl); + gpgme_free(export_sig); + gpgme_data_release (gpgmeData); + + /* extract id(s)! */ + return true; +} + + +/* import to GnuPG and other Certificates */ +bool GPGAuthMgr::VerifySignature_locked(std::string id, void *data, int datalen, + void *sig, unsigned int siglen) +{ + gpgme_data_t gpgmeSig; + gpgme_data_t gpgmeData; + + std::cerr << "VerifySignature: datalen: " << datalen << " siglen: " << siglen; + std::cerr << std::endl; + + if (GPG_ERR_NO_ERROR != gpgme_data_new_from_mem(&gpgmeData, (const char *) data, datalen, 1)) + { + std::cerr << "Error create Data"; + std::cerr << std::endl; + } + + if (GPG_ERR_NO_ERROR != gpgme_data_new_from_mem(&gpgmeSig, (const char *) sig, siglen, 1)) + { + std::cerr << "Error create Sig"; + std::cerr << std::endl; + } + + /* move string data to gpgmeData */ + + gpgme_set_armor (CTX, 0); + + gpgme_error_t ERR; + if (GPG_ERR_NO_ERROR != (ERR = gpgme_op_verify(CTX,gpgmeSig, gpgmeData, NULL))) + { + ProcessPGPmeError(ERR); + std::cerr << "GPGAuthMgr::Verify FAILED"; + std::cerr << std::endl; + } + + gpgme_verify_result_t res = gpgme_op_verify_result(CTX); + + if (res) + { + fprintf(stderr, "VerifySignature Got Result\n"); + } + else + { + fprintf(stderr, "VerifySignature Failed to get Result\n"); + } + + gpgme_signature_t sg = res->signatures; + bool valid = false; + + while(sg != NULL) + { + fprintf(stderr, "GPGAuthMgr::Verify Sig by: %s, Result: %d\n", sg->fpr, sg->summary); + print_pgpme_verify_summary(sg->summary); + + if (sg->summary & GPGME_SIGSUM_VALID) + { + fprintf(stderr, "GPGAuthMgr::VerifySignature() OK\n"); + valid = true; + } + + sg = sg->next; + } + + gpgme_data_release (gpgmeData); + gpgme_data_release (gpgmeSig); + + /* extract id(s)! */ + if (!valid) + { + fprintf(stderr, "GPGAuthMgr::VerifySignature() FAILED\n"); + } + + + return valid; +} + + + + +bool GPGAuthMgr::active() +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + return ((gpgmeInit) && (gpgmeKeySelected) && (gpgmeX509Selected)); +} + +int GPGAuthMgr::InitAuth(const char *srvr_cert, const char *priv_key, + const char *passwd) +{ + /* Initialise the SSL part */ + if (AuthSSL::InitAuth(srvr_cert, priv_key, passwd)) + { + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + gpgmeX509Selected = true; + return 1; + } + + return 0; +} + +bool GPGAuthMgr::CloseAuth() +{ + return true; +} + +#if 0 /**** no saving here! let AuthSSL store directories! ****/ + +int GPGAuthMgr::setConfigDirectories(std::string confFile, std::string neighDir) +{ + return 1; +} + +#endif + +/**** The standard versions of the OwnId/get*List ... return SSL ids + * There are alternative functions for gpg ids. + ****/ + +std::string GPGAuthMgr::OwnId() +{ + /* to the external libretroshare world, we are our SSL id */ + return AuthSSL::OwnId(); +} + +bool GPGAuthMgr::getAllList(std::list &ids) +{ + /* get all of the certificates */ + return AuthSSL::getAllList(ids); +} + +bool GPGAuthMgr::getAuthenticatedList(std::list &ids) +{ + return AuthSSL::getAuthenticatedList(ids); +} + +bool GPGAuthMgr::getUnknownList(std::list &ids) +{ + return AuthSSL::getUnknownList(ids); +} + +/*******************************/ + +bool GPGAuthMgr::isValid(std::string id) +{ + return AuthSSL::isValid(id); +} + +bool GPGAuthMgr::isAuthenticated(std::string id) +{ + /* This must be handled at PGP level */ + + /* get pgpid */ + std::string pgpid = getIssuerName(id); + + return isPGPAuthenticated(pgpid); + //return AuthSSL::isAuthenticated(id); +} + +bool GPGAuthMgr::isTrustingMe(std::string) +{ + return false; +} + +void GPGAuthMgr::addTrustingPeer(std::string) +{ + + +} + +/**** These Two are common */ +std::string GPGAuthMgr::getName(std::string id) +{ + std::string name = AuthSSL::getName(id); + if (name != "") + { + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + certmap::iterator it; + if (mKeyList.end() != (it = mKeyList.find(id))) + { + return it->second.user.name; + } + } + return name; +} + +bool GPGAuthMgr::getDetails(std::string id, pqiAuthDetails &details) +{ + /**** GPG Details. + * Ids are the SSL id cert ids, so we have to get issuer id (pgpid) + * before we can add any gpg details + ****/ + + if (AuthSSL::getDetails(id, details)) + { + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + certmap::iterator it; + if (mKeyList.end() != (it = mKeyList.find(details.issuer))) + { + /* what do we want from the gpg mgr */ + details.location = details.name; + details.name = it->second.user.name; + details.email = it->second.user.email; + + //details = it->second.user; + return true; + } + return true; + } + else + { + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + /* if we cannot find a ssl cert - might be a pgp cert */ + certmap::iterator it; + if (mKeyList.end() != (it = mKeyList.find(id))) + { + /* what do we want from the gpg mgr */ + details = it->second.user; + return true; + } + } + return false; +} + + +/**** GPG versions ***/ + +std::string GPGAuthMgr::PGPOwnId() +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + return mOwnId; +} + +bool GPGAuthMgr::getPGPAllList(std::list &ids) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + /* add an id for each pgp certificate */ + certmap::iterator it; + for(it = mKeyList.begin(); it != mKeyList.end(); it++) + { + ids.push_back(it->first); + } + return true; +} + +bool GPGAuthMgr::getPGPAuthenticatedList(std::list &ids) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + certmap::iterator it; + for(it = mKeyList.begin(); it != mKeyList.end(); it++) + { + if (it->second.user.trusted) + { + ids.push_back(it->first); + } + } + return true; +} + +bool GPGAuthMgr::getPGPUnknownList(std::list &ids) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + certmap::iterator it; + for(it = mKeyList.begin(); it != mKeyList.end(); it++) + { + if (!(it->second.user.trusted)) + { + ids.push_back(it->first); + } + } + return true; +} + + +bool GPGAuthMgr::isPGPValid(std::string id) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + certmap::iterator it; + return (mKeyList.end() != mKeyList.find(id)); +} + + +bool GPGAuthMgr::isPGPAuthenticated(std::string id) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + certmap::iterator it; + if (mKeyList.end() != (it = mKeyList.find(id))) + { + /* trustLvl... is just that ... we are interested in validity. + * which is the 'trusted' flag. + */ + + return (it->second.user.trusted); + } + return false; +} + +/****** Large Parts of the p3AuthMgr is provided by AuthSSL ****** + * As the majority of functions require SSL Certs + * + * We don't need to save/load openpgp certificates, as the gpgme + * handles this. + * + */ + +#if 0 + +bool GPGAuthMgr::FinalSaveCertificates() +{ + return false; +} + +bool GPGAuthMgr::CheckSaveCertificates() +{ + return false; +} + +bool GPGAuthMgr::saveCertificates() +{ + return false; +} + +bool GPGAuthMgr::loadCertificates() +{ + return false; +} + +#endif + +/***************************************************************** + * Loading and Saving Certificates - this has to + * be able to handle both openpgp and X509 certificates. + * + * X509 are passed onto AuthSSL, OpenPGP are passed to gpgme. + * + */ + + +/* SKTAN : do not know how to use std::string id */ +std::string GPGAuthMgr::SaveCertificateToString(std::string id) +{ + + if (!isPGPValid(id)) + { + /* check if it is a SSL Certificate */ + if (isValid(id)) + { + std::string sslcert = AuthSSL::SaveCertificateToString(id); + return sslcert; + } + std::string emptystr; + return emptystr; + } + + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + std::string tmp; + const char *pattern[] = { NULL, NULL }; + pattern[0] = id.c_str(); + gpgme_data_t gpgmeData; + + if (GPG_ERR_NO_ERROR != gpgme_data_new (&gpgmeData)) + { + std::cerr << "Error create Data"; + std::cerr << std::endl; + } + gpgme_set_armor (CTX, 1); + + if (GPG_ERR_NO_ERROR != gpgme_op_export_ext (CTX, pattern, 0, gpgmeData)) + { + std::cerr << "Error export Data"; + std::cerr << std::endl; + } + + fflush (NULL); + fputs ("Begin Result:\n", stdout); + showData (gpgmeData); + fputs ("End Result.\n", stdout); + + size_t len = 0; + char *export_txt = gpgme_data_release_and_get_mem(gpgmeData, &len); + tmp = std::string(export_txt); + + gpgme_free(export_txt); + + return tmp; +} + +/* import to GnuPG and other Certificates */ +bool GPGAuthMgr::LoadCertificateFromString(std::string str, std::string &id) +{ + + /* catch SSL Certs and pass to AuthSSL. */ + std::string sslmarker("-----BEGIN CERTIFICATE-----"); + size_t pos = str.find(sslmarker); + if (pos != std::string::npos) + { + return AuthSSL::LoadCertificateFromString(str, id); + } + + /* otherwise assume it is a PGP cert */ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + gpgme_data_t gpgmeData; + if (GPG_ERR_NO_ERROR != gpgme_data_new_from_mem(&gpgmeData, str.c_str(), str.length(), 1)) + { + std::cerr << "Error create Data"; + std::cerr << std::endl; + } + + /* move string data to gpgmeData */ + + gpgme_set_armor (CTX, 1); + + if (GPG_ERR_NO_ERROR != gpgme_op_import (CTX,gpgmeData)) + { + std::cerr << "GPGAuthMgr::Error Importing Certificate"; + std::cerr << std::endl; + } + + + gpgme_import_result_t res = gpgme_op_import_result(CTX); + + int imported = res->imported; + + fprintf(stderr, "ImportCertificate(Considered: %d Imported: %d)\n", + res->considered, res->imported); + + /* do we need to delete res??? */ + + gpgme_data_release (gpgmeData); + + /* extract id(s)! (only if we actually imported one) */ + if (imported) + { + storeAllKeys_locked(); + } + + return true; +} + +/*** These are passed to SSL ****/ +bool GPGAuthMgr::LoadCertificateFromFile(std::string filename, std::string &id) +{ + return false; +} + +bool GPGAuthMgr::SaveCertificateToFile(std::string id, std::string filename) +{ + return false; +} + +bool GPGAuthMgr::LoadCertificateFromBinary(const uint8_t *ptr, uint32_t len, std::string &id) +{ + return AuthSSL::LoadCertificateFromBinary(ptr, len, id); +} + +bool GPGAuthMgr::SaveCertificateToBinary(std::string id, uint8_t **ptr, uint32_t *len) +{ + return AuthSSL::SaveCertificateToBinary(id, ptr, len); +} + +/***************************************************************** + * Auth...? Signing, Revoke, Trust are all done at + * the PGP level.... + * + * Only Signing of SSL is done at setup. + * Auth should be done... ?? not sure + * maybe + * + */ + + +/*************************************/ + +/* Auth takes SSL Certificate */ +bool GPGAuthMgr::AuthCertificate(std::string id) +{ + /** + * we are passed an SSL cert, check if the cert is signed + * by an already authed peer. + **/ + std::cerr << "GPGAuthMgr::AuthCertificate(" << id << ")"; + std::cerr << std::endl; + + std::string pgpid = AuthSSL::getIssuerName(id); + + if (isPGPAuthenticated(pgpid)) + { + return true; + } + + if (!isPGPValid(pgpid)) + { + return false; + } + + return SignCertificate(pgpid); +} + +/* These take PGP Ids */ +bool GPGAuthMgr::SignCertificate(std::string id) +{ + + std::cerr << "GPGAuthMgr::SignCertificate(" << id << ")"; + std::cerr << std::endl; + + + if (1 != signCertificate(id)) + { + return false; + } + + /* reload stuff now ... */ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + storeAllKeys_locked(); + + return true; +} + +bool GPGAuthMgr::RevokeCertificate(std::string id) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + std::cerr << "GPGAuthMgr::RevokeCertificate(" << id << ")"; + std::cerr << std::endl; + + return false; +} + +bool GPGAuthMgr::TrustCertificate(std::string id, bool trust) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + std::cerr << "GPGAuthMgr::TrustCertificate(" << id << "," << trust << ")"; + std::cerr << std::endl; + + return false; +} + +/***************************************************************** + * Signing data is done by the SSL certificate. + * + */ + +#if 0 + +bool GPGAuthMgr::SignData(std::string input, std::string &sign) +{ + return false; +} + +bool GPGAuthMgr::SignData(const void *data, const uint32_t len, std::string &sign) +{ + return false; +} + + +bool GPGAuthMgr::SignDataBin(std::string input, unsigned char *sign, unsigned int *signlen) +{ + return false; +} + +bool GPGAuthMgr::SignDataBin(const void *data, const uint32_t len, + unsigned char *sign, unsigned int *signlen) +{ + return false; +} + +#endif + + + /************* Virtual Functions from AuthSSL *************/ + +bool GPGAuthMgr::ValidateCertificate(X509 *x509, std::string &peerId) +{ + std::cerr << "GPGAuthMgr::ValidateCertificate()"; + std::cerr << std::endl; + + bool val = AuthX509(x509); + if (val) + { + return getX509id(x509, peerId); + } + /* be sure to get the id anyway */ + getX509id(x509, peerId); + + return false; +} + + +int GPGAuthMgr::VerifyX509Callback(int preverify_ok, X509_STORE_CTX *ctx) +{ + char buf[256]; + X509 *err_cert; + int err, depth; + + err_cert = X509_STORE_CTX_get_current_cert(ctx); + err = X509_STORE_CTX_get_error(ctx); + depth = X509_STORE_CTX_get_error_depth(ctx); + + std::cerr << "GPGAuthMgr::VerifyX509Callback(preverify_ok: " << preverify_ok + << " Err: " << err << " Depth: " << depth; + std::cerr << std::endl; + + /* + * Retrieve the pointer to the SSL of the connection currently treated + * and the application specific data stored into the SSL object. + */ + + X509_NAME_oneline(X509_get_subject_name(err_cert), buf, 256); + + std::cerr << "GPGAuthMgr::VerifyX509Callback: depth: " << depth << ":" << buf; + std::cerr << std::endl; + + + if (!preverify_ok) { + fprintf(stderr, "Verify error:num=%d:%s:depth=%d:%s\n", err, + X509_verify_cert_error_string(err), depth, buf); + } + + /* + * At this point, err contains the last verification error. We can use + * it for something special + */ + + if (!preverify_ok) + { + if ((err == X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT) || + (err == X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT_LOCALLY)) + { + X509_NAME_oneline(X509_get_issuer_name(ctx->current_cert), buf, 256); + printf("issuer= %s\n", buf); + + fprintf(stderr, "Doing REAL PGP Certificates\n"); + /* do the REAL Authentication */ + if (!AuthX509(ctx->current_cert)) + { + return false; + } + std::string pgpid = getX509CNString(ctx->current_cert->cert_info->issuer); + if (!isPGPAuthenticated(pgpid)) + { + return false; + } + preverify_ok = true; + } + else if ((err == X509_V_ERR_CERT_UNTRUSTED) || + (err == X509_V_ERR_UNABLE_TO_VERIFY_LEAF_SIGNATURE)) + { + std::string pgpid = getX509CNString(ctx->current_cert->cert_info->issuer); + if (!isPGPAuthenticated(pgpid)) + { + return false; + } + preverify_ok = true; + } + } + else + { + fprintf(stderr, "Failing Normal Certificate!!!\n"); + preverify_ok = false; + } + + return preverify_ok; +} + + + /************* Virtual Functions from AuthSSL *************/ + + + + /* Sign/Trust stuff */ + +int GPGAuthMgr::signCertificate(std::string id) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + /* The key should be in Others list and not in Peers list ?? + * Once the key is signed, it moves from Others to Peers list ??? + */ + + certmap::iterator it; + if (mKeyList.end() == (it = mKeyList.find(id))) + { + return false; + } + + gpgme_key_t signKey = it->second.key; + gpgme_key_t ownKey = mOwnGpgCert.key; + + class SignParams sparams("0", passphrase); + class EditParams params(SIGN_START, &sparams); + gpgme_data_t out; + gpg_error_t ERR; + + if(GPG_ERR_NO_ERROR != (ERR = gpgme_data_new(&out))) { + return 0; + } + + gpgme_signers_clear(CTX); + if(GPG_ERR_NO_ERROR != (ERR = gpgme_signers_add(CTX, ownKey))) { + return 0; + } + + + if(GPG_ERR_NO_ERROR != (ERR = gpgme_op_edit(CTX, signKey, keySignCallback, \ + ¶ms, out))) { + return 0; + } + + /* Should I move the certificate from Others to Peers ??? */ + + return 1; +} + +/* revoke the signature on Certificate */ +int GPGAuthMgr::revokeCertificate(std::string id) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + return 0; +} + +int GPGAuthMgr::trustCertificate(std::string id, int trustlvl) +{ + RsStackMutex stack(pgpMtx); /******* LOCKED ******/ + + /* The certificate should be in Peers list ??? */ + + if(!isAuthenticated(id)) { + std::cerr << "Invalid Certificate" << std::endl; + return 0; + } + + gpgcert trustCert = mKeyList.find(id)->second; + gpgme_key_t trustKey = trustCert.key; + const char *lvls[] = {"1", "2", "3", "4", "5"}; + class EditParams params(TRUST_START, (void *) *(lvls + trustlvl -1)); + gpgme_data_t out; + gpg_error_t ERR; + + + if(GPG_ERR_NO_ERROR != (ERR = gpgme_data_new(&out))) { + return 0; + } + + if(GPG_ERR_NO_ERROR != (ERR = gpgme_op_edit(CTX, trustKey, trustCallback, ¶ms, out))) + return 0; + + return 1; +} + + +/* This function to print Data */ +void GPGAuthMgr::showData(gpgme_data_t dh) +{ + #define BUF_SIZE 512 + char buf[BUF_SIZE + 1]; + int ret; + + ret = gpgme_data_seek (dh, 0, SEEK_SET); + if (ret) + { + std::cerr << "Fail data seek"; + std::cerr << std::endl; + // fail_if_err (gpgme_err_code_from_errno (errno)); + } + + while ((ret = gpgme_data_read (dh, buf, BUF_SIZE)) > 0) + fwrite (buf, ret, 1, stdout); + + if (ret < 0) + { + std::cerr << "Fail data seek"; + std::cerr << std::endl; + //fail_if_err (gpgme_err_code_from_errno (errno)); + } +} + +/******************************************************************************/ +/* TEST/DEBUG */ +/******************************************************************************/ +/* + * Create a number of friends and add them to the Map of peers. + * Create a number of friends and add them to the Map of "others" -- people who + * are known but are not allowed to access retroshare + */ +void GPGAuthMgr::createDummyFriends() +{ + const unsigned int DUMMY_KEY_LEN = 2048; + + // create key params for a few dummies + std::string friend1 = setKeyPairParams(true, DUMMY_KEY_LEN, "friend89", + "I am your first friend", "friend1@friend.com", "1234"); + std::string friend2 = setKeyPairParams(true, DUMMY_KEY_LEN, "friend2", + "I am your second friend", "friend2@friend.com", "2345"); + std::string friend3 = setKeyPairParams(true, DUMMY_KEY_LEN, "friend3", + "I am your third friend", "friend3@friend.com", "3456"); + + // params for others + std::string other1 = setKeyPairParams(true, DUMMY_KEY_LEN, "other89", + "I am your first other", "other@other.com", "1234"); + std::string other2 = setKeyPairParams(true, DUMMY_KEY_LEN, "other2", + "I am your second other", "other2@other.com", "2345"); + std::string other3 = setKeyPairParams(true, DUMMY_KEY_LEN, "other3", + "I am your third other", "other3@other.com", "3456"); + + gpgme_error_t rc = GPG_ERR_NO_ERROR; // assume OK + rc = gpgme_op_genkey(CTX, friend1.c_str(), NULL, NULL); + rc = gpgme_op_genkey(CTX, friend2.c_str(), NULL, NULL); + rc = gpgme_op_genkey(CTX, friend3.c_str(), NULL, NULL); + + rc = gpgme_op_genkey(CTX, other1.c_str(), NULL, NULL); + rc = gpgme_op_genkey(CTX, other2.c_str(), NULL, NULL); + rc = gpgme_op_genkey(CTX, other3.c_str(), NULL, NULL); + + std::cout << "createDummyFriends(): exit" << std::endl; + return; +} + +static std::string setKeyPairParams(bool useRsa, unsigned int blen, + std::string name, std::string comment, std::string email, + std::string passphrase) +{ + std::ostringstream params; + params << ""<< std::endl; + if (useRsa) + { + params << "Key-Type: RSA"<< std::endl; + if (blen < 1024) + { + std::cerr << "Weak Key... strengthing..."<< std::endl; + blen = 1024; + } + blen = ((blen / 512) * 512); /* make multiple of 512 */ + params << "Key-Length: "<< blen << std::endl; + } + else + { + params << "Key-Type: DSA"<< std::endl; + params << "Key-Length: 1024"<< std::endl; + params << "Subkey-Type: ELG-E"<< std::endl; + params << "Subkey-Length: 1024"<< std::endl; + } + params << "Name-Real: "<< name << std::endl; + params << "Name-Comment: "<< comment << std::endl; + params << "Name-Email: "<< email << std::endl; + params << "Expire-Date: 0"<< std::endl; + params << "Passphrase: "<< passphrase << std::endl; + params << ""<< std::endl; + + return params.str(); +} + + + +/* Author: Shiva + * This function returns the key macthing the user parameters + * from the keyring + */ + +static gpgme_key_t getKey(gpgme_ctx_t CTX, std::string name, std::string comment, std::string email) { + + gpgme_key_t key; + gpgme_user_id_t user; + + /* Initiates a key listing */ + if (GPG_ERR_NO_ERROR != gpgme_op_keylist_start (CTX, "", 0)) + { + std::cerr << "Error iterating through KeyList"; + std::cerr << std::endl; + return false; + + } + + /* Loop until end of key */ + for(int i = 0;(GPG_ERR_NO_ERROR == gpgme_op_keylist_next (CTX, &key)); i++) + { + user = key->uids; + + while(user != NULL) { + if((name.size() && name == user->name) && (comment.size() && comment == user->comment) && \ + (email.size() && email == user->email)) + { + /* grab a reference to the key */ + gpgme_op_keylist_end(CTX); + if (GPG_ERR_NO_ERROR != gpgme_op_keylist_end(CTX)) + { + std::cerr << "Error ending KeyList"; + std::cerr << std::endl; + } + gpgme_key_ref(key); + return key; + } + user = user->next; + } + } + + if (GPG_ERR_NO_ERROR != gpgme_op_keylist_end(CTX)) + { + std::cerr << "Error ending KeyList"; + std::cerr << std::endl; + } + return NULL; +} + + +/* Callback function for key signing */ + +static gpg_error_t keySignCallback(void *opaque, gpgme_status_code_t status, \ + const char *args, int fd) { + + class EditParams *params = (class EditParams *)opaque; + class SignParams *sparams = (class SignParams *)params->oParams; + const char *result = NULL; + + fprintf(stderr,"keySignCallback status: %d args: %s, params->state: %d\n", status, args, params->state); + + /* printf stuff out */ + if (status == GPGME_STATUS_EOF) + fprintf(stderr,"keySignCallback GPGME_STATUS_EOF\n"); + if (status == GPGME_STATUS_GOT_IT) + fprintf(stderr,"keySignCallback GPGME_STATUS_GOT_IT\n"); + if (status == GPGME_STATUS_USERID_HINT) + fprintf(stderr,"keySignCallback GPGME_STATUS_USERID_HINT\n"); + if (status == GPGME_STATUS_NEED_PASSPHRASE) + fprintf(stderr,"keySignCallback GPGME_STATUS_NEED_PASSPHRASE\n"); + if (status == GPGME_STATUS_GOOD_PASSPHRASE) + fprintf(stderr,"keySignCallback GPGME_STATUS_GOOD_PASSPHRASE\n"); + if (status == GPGME_STATUS_BAD_PASSPHRASE) + fprintf(stderr,"keySignCallback GPGME_STATUS_BAD_PASSPHRASE\n"); + + if (status == GPGME_STATUS_GET_LINE) + fprintf(stderr,"keySignCallback GPGME_STATUS_GET_LINE\n"); + if (status == GPGME_STATUS_GET_BOOL) + fprintf(stderr,"keySignCallback GPGME_STATUS_GET_BOOL\n"); + if (status == GPGME_STATUS_ALREADY_SIGNED) + fprintf(stderr,"keySignCallback GPGME_STATUS_ALREADY_SIGNED\n"); + + + if(status == GPGME_STATUS_EOF || + status == GPGME_STATUS_GOT_IT || + status == GPGME_STATUS_USERID_HINT || + status == GPGME_STATUS_NEED_PASSPHRASE || + // status == GPGME_STATUS_GOOD_PASSPHRASE || + status == GPGME_STATUS_BAD_PASSPHRASE) { + + + fprintf(stderr,"keySignCallback Error status\n"); + ProcessPGPmeError(params->err); + + return params->err; + } + + switch (params->state) + { + case SIGN_START: + fprintf(stderr,"keySignCallback SIGN_START\n"); + + if (status == GPGME_STATUS_GET_LINE && + (!std::string("keyedit.prompt").compare(args))) + { + params->state = SIGN_COMMAND; + result = "sign"; + } + else + { + params->state = SIGN_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + case SIGN_COMMAND: + fprintf(stderr,"keySignCallback SIGN_COMMAND\n"); + + if (status == GPGME_STATUS_GET_BOOL && + (!std::string("keyedit.sign_all.okay").compare(args))) + { + params->state = SIGN_UIDS; + result = "Y"; + } + else if (status == GPGME_STATUS_GET_BOOL && + (!std::string("sign_uid.okay").compare(args))) + { + params->state = SIGN_ENTER_PASSPHRASE; + result = "Y"; + } + else if (status == GPGME_STATUS_GET_LINE && + (!std::string("sign_uid.expire").compare(args))) + { + params->state = SIGN_SET_EXPIRE; + result = "Y"; + } + else if (status == GPGME_STATUS_GET_LINE && + (!std::string("sign_uid.class").compare(args))) + { + params->state = SIGN_SET_CHECK_LEVEL; + result = sparams->checkLvl.c_str(); + } + else if (status == GPGME_STATUS_ALREADY_SIGNED) + { + /* The key has already been signed with this key */ + params->state = SIGN_ERROR; + params->err = gpg_error (GPG_ERR_CONFLICT); + } + else if (status == GPGME_STATUS_GET_LINE && + (!std::string("keyedit.prompt").compare(args))) + { + /* Failed sign: expired key */ + params->state = SIGN_ERROR; + params->err = gpg_error (GPG_ERR_UNUSABLE_PUBKEY); + } + else + { + params->state = SIGN_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + case SIGN_UIDS: + fprintf(stderr,"keySignCallback SIGN_UIDS\n"); + + if (status == GPGME_STATUS_GET_LINE && + (!std::string("sign_uid.expire").compare(args))) + { + params->state = SIGN_SET_EXPIRE; + result = "Y"; + } + else if (status == GPGME_STATUS_GET_LINE && + (!std::string("sign_uid.class").compare(args))) + { + params->state = SIGN_SET_CHECK_LEVEL; + result = sparams->checkLvl.c_str(); + } + else if (status == GPGME_STATUS_GET_BOOL && + (!std::string("sign_uid.okay").compare(args))) + { + params->state = SIGN_ENTER_PASSPHRASE; + result = "Y"; + } + else if (status == GPGME_STATUS_GET_LINE && + (!std::string("keyedit.prompt").compare(args))) + { + /* Failed sign: expired key */ + params->state = SIGN_ERROR; + params->err = gpg_error (GPG_ERR_UNUSABLE_PUBKEY); + } + else + { + params->state = SIGN_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + case SIGN_SET_EXPIRE: + fprintf(stderr,"keySignCallback SIGN_SET_EXPIRE\n"); + + if (status == GPGME_STATUS_GET_LINE && + (!std::string("sign_uid.class").compare(args))) + { + params->state = SIGN_SET_CHECK_LEVEL; + result = sparams->checkLvl.c_str(); + } + else + { + params->state = SIGN_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + case SIGN_SET_CHECK_LEVEL: + fprintf(stderr,"keySignCallback SIGN_SET_CHECK_LEVEL\n"); + + if (status == GPGME_STATUS_GET_BOOL && + (!std::string("sign_uid.okay").compare(args))) + { + params->state = SIGN_ENTER_PASSPHRASE; + result = "Y"; + } + else + { + params->state = SIGN_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + case SIGN_ENTER_PASSPHRASE: + fprintf(stderr,"keySignCallback SIGN_ENTER_PASSPHRASE\n"); + + if(status == GPGME_STATUS_GET_HIDDEN && + (!std::string("passphrase.enter").compare(args))) + { + params->state = SIGN_CONFIRM; + result = sparams->passphrase.c_str(); + } + // If using pgp_pwd_callback, then never have to enter passphrase this way. + // must catch GOOD_PASSPHRASE to move on. + else if (status == GPGME_STATUS_GOOD_PASSPHRASE) + { + params->state = SIGN_CONFIRM; + } + else + { + params->state = SIGN_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + case SIGN_CONFIRM: + fprintf(stderr,"keySignCallback SIGN_CONFIRM\n"); + + if (status == GPGME_STATUS_GET_LINE && + (!std::string("keyedit.prompt").compare(args))) + { + params->state = SIGN_QUIT; + result = "quit"; + } + else + { + params->state = SIGN_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + case SIGN_QUIT: + fprintf(stderr,"keySignCallback SIGN_QUIT\n"); + + if (status == GPGME_STATUS_GET_BOOL && + (!std::string("keyedit.save.okay").compare(args))) + { + params->state = SIGN_SAVE; + result = "Y"; + } + else + { + params->state = SIGN_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + case SIGN_ERROR: + fprintf(stderr,"keySignCallback SIGN_ERROR\n"); + + if (status == GPGME_STATUS_GET_LINE && + (!std::string("keyedit.prompt").compare(args))) + { + /* Go to quit operation state */ + params->state = SIGN_QUIT; + result = "quit"; + } + else + { + params->state = SIGN_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + default: + fprintf(stderr,"keySignCallback UNKNOWN state\n"); + break; + } + + if (result) + { + fprintf(stderr,"keySignCallback result:%s\n", result); + if (*result) + write (fd, result, strlen (result)); + write (fd, "\n", 1); + } + + fprintf(stderr,"keySignCallback Error status\n"); + ProcessPGPmeError(params->err); + + return params->err; +} + + + +/* Callback function for assigning trust level */ + +static gpgme_error_t trustCallback(void *opaque, gpgme_status_code_t status, \ + const char *args, int fd) { + + class EditParams *params = (class EditParams *)opaque; + const char *result = NULL; + char *trustLvl = (char *)params->oParams; + + if(status == GPGME_STATUS_EOF || + status == GPGME_STATUS_GOT_IT) { + return params->err; + } + + + switch (params->state) + { + case TRUST_START: + if (status == GPGME_STATUS_GET_LINE && + (!std::string("keyedit.prompt").compare(args))) { + params->state = TRUST_COMMAND; + result = "trust"; + } else { + params->state = TRUST_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + + case TRUST_COMMAND: + if (status == GPGME_STATUS_GET_LINE && + (!std::string("edit_ownertrust.value").compare(args))) { + params->state = TRUST_VALUE; + result = trustLvl; + } else { + params->state = TRUST_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + case TRUST_VALUE: + if (status == GPGME_STATUS_GET_LINE && + (!std::string("keyedit.prompt").compare(args))) { + params->state = TRUST_QUIT; + result = "quit"; + } + else if (status == GPGME_STATUS_GET_BOOL && + (!std::string("edit_ownertrust.set_ultimate.okay").compare(args))) { + params->state = TRUST_REALLY_ULTIMATE; + result = "Y"; + } + else { + params->state = TRUST_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + case TRUST_REALLY_ULTIMATE: + if (status == GPGME_STATUS_GET_LINE && + (!std::string("keyedit.prompt").compare(args))) { + params->state = TRUST_QUIT; + result = "quit"; + } else { + params->state = TRUST_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + case TRUST_QUIT: + if (status == GPGME_STATUS_GET_BOOL && + (!std::string("keyedit.save.okay").compare(args))) { + params->state = TRUST_SAVE; + result = "Y"; + } else { + params->state = TRUST_ERROR; + params->err = gpg_error (GPG_ERR_GENERAL); + } + break; + case TRUST_ERROR: + if (status == GPGME_STATUS_GET_LINE && + (!std::string("keyedit.prompt").compare(args))) { + /* Go to quit operation state */ + params->state = TRUST_QUIT; + result = "quit"; + } else { + params->state = TRUST_ERROR; + } + break; + } + + if (result) + { + if (*result) + write (fd, result, strlen (result)); + write (fd, "\n", 1); + } + + return params->err; +} diff --git a/libretroshare/src/_pqi/authgpg.h b/libretroshare/src/_pqi/authgpg.h new file mode 100644 index 000000000..c7d24ece4 --- /dev/null +++ b/libretroshare/src/_pqi/authgpg.h @@ -0,0 +1,385 @@ +/* + * libretroshare/src/ : gpgauthmgr.h + * + * GPG interface for RetroShare. + * + * Copyright 2008-2009 by Raghu Dev R. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + * This is *THE* auth manager. It provides the web-of-trust via + * gpgme, and authenticates the certificates that are managed + * by the sublayer AuthSSL. + * + */ + +#ifndef RS_GPG_AUTH_HEADER +#define RS_GPG_AUTH_HEADER + +//#include "p3authmgr.h" +#include "authssl.h" +#include + +/* gpgcert is the identifier for a person. + * It is a wrapper class for a GPGme OpenPGP certificate. + */ + +class gpgcert +{ +public: + gpgcert(); + ~gpgcert(); + + pqiAuthDetails user; + gpgme_key_t key; +}; + +/* + * The certificate map type + */ +typedef std::map certmap; + +class GPGAuthMgr: public AuthSSL +{ +private: + + /* Internal functions */ + bool setPGPPassword_locked(std::string pwd); + bool DoOwnSignature_locked(void *, unsigned int, void *, unsigned int *); + bool VerifySignature_locked(std::string id, void *data, int datalen, + void *sig, unsigned int siglen); + + // store all keys in map mKeyList to avoid calling gpgme exe repeatedly + bool storeAllKeys_locked(); + bool updateTrustAllKeys_locked(); + + bool printAllKeys_locked(); + bool printOwnKeys_locked(); + +public: + + GPGAuthMgr(); + ~GPGAuthMgr(); + + + X509* SignX509Req(X509_REQ *req, long days, std::string); + bool AuthX509(X509 *x509); + + + bool availablePGPCertificates(std::list &ids); + + int GPGInit(std::string ownId, std::string name, std::string passwd); + int GPGInit(std::string name, std::string comment, + std::string email, std::string passwd); + /* Sign/Trust stuff */ + int signCertificate(std::string id); + int revokeCertificate(std::string id); /* revoke the signature on Certificate */ + int trustCertificate(std::string id, int trustlvl); + + /* SKTAN */ + void showData(gpgme_data_t dh); + void createDummyFriends(void); //NYI + +/*********************************************************************************/ +/************************* STAGE 1 ***********************************************/ +/*********************************************************************************/ +/***** + * STAGE 1: Initialisation.... As we are switching to OpenPGP the init functions + * will be different. Just move the initialisation functions over.... + * + * As GPGMe requires external calls to the GPG executable, which could potentially + * be expensive, We'll want to cache the GPG keys in this class. + * This should be done at initialisation, and saved in a map. + * (see storage at the end of the class) + * + ****/ + + /* initialisation -> done by derived classes */ + bool active(); + + /* Init by generating new Own PGP Cert, or selecting existing PGP Cert + */ + + /* Arguments passed on to AuthSSL */ + int InitAuth(const char *srvr_cert, const char *priv_key, + const char *passwd); + bool CloseAuth(); + // int setConfigDirectories(std::string confFile, std::string neighDir); + + +/*********************************************************************************/ +/************************* STAGE 2 ***********************************************/ +/*********************************************************************************/ +/***** + * STAGE 2: These are some of the most commonly used functions in Retroshare. + * + * provide access to the cache list that was created in stage 1. + * + ****/ + + /* get Certificate Ids */ + + std::string OwnId(); + bool getAllList(std::list &ids); + bool getAuthenticatedList(std::list &ids); + bool getUnknownList(std::list &ids); + +/*********************************************************************************/ +/************************* STAGE 3 ***********************************************/ +/*********************************************************************************/ +/***** + * STAGE 3: These are some of the most commonly used functions in Retroshare. + * + * More commonly used functions. + * + * provide access to details in cache list. + * + ****/ + + /* get Details from the Certificates */ + + bool isValid(std::string id); + bool isAuthenticated(std::string id); + std::string getName(std::string id); + bool getDetails(std::string id, pqiAuthDetails &details); + + virtual bool isTrustingMe(std::string); + virtual void addTrustingPeer(std::string); + + + /* PGP versions of Certificate Fns */ + + std::string PGPOwnId(); + bool getPGPAllList(std::list &ids); + bool getPGPAuthenticatedList(std::list &ids); + bool getPGPUnknownList(std::list &ids); + bool isPGPValid(std::string id); + bool isPGPAuthenticated(std::string id); + bool getPGPDetails(std::string id, pqiAuthDetails &details); + +/*********************************************************************************/ +/************************* STAGE 4 ***********************************************/ +/*********************************************************************************/ +/***** + * STAGE 4: Loading and Saving Certificates. (Strings and Files) + * + ****/ + + + /* Load/Save certificates */ + bool LoadCertificateFromString(std::string pem, std::string &id); + std::string SaveCertificateToString(std::string id); + bool LoadCertificateFromFile(std::string filename, std::string &id); + bool SaveCertificateToFile(std::string id, std::string filename); + +/*********************************************************************************/ +/************************* STAGE 5 ***********************************************/ +/*********************************************************************************/ +/***** + * STAGE 5: Loading and Saving Certificates (Binary) + * + * The existing function arguments are based on OpenSSL functions. + * Feel free to change this format if required. + * + ****/ + + bool LoadCertificateFromBinary(const uint8_t *ptr, uint32_t len, std::string &id); + bool SaveCertificateToBinary(std::string id, uint8_t **ptr, uint32_t *len); + +/*********************************************************************************/ +/************************* STAGE 6 ***********************************************/ +/*********************************************************************************/ +/***** + * STAGE 6: Authentication, Trust and Signing. + * + * This is some of the harder functions, but they should have been + * done in gpgroot already. + * + ****/ + + /* Signatures */ + bool AuthCertificate(std::string uid); + bool SignCertificate(std::string id); + bool RevokeCertificate(std::string id); /* Particularly hard - leave for later */ + bool TrustCertificate(std::string id, bool trust); + +/*********************************************************************************/ +/************************* STAGE 7 ***********************************************/ +/*********************************************************************************/ +/***** + * STAGE 7: Signing Data. + * + * There should also be Encryption Functions... (do later). + * + ****/ + +#if 0 + virtual bool SignData(std::string input, std::string &sign); + virtual bool SignData(const void *data, const uint32_t len, std::string &sign); + virtual bool SignDataBin(std::string input, unsigned char *sign, unsigned int *signlen); + virtual bool SignDataBin(const void *data, const uint32_t len, + unsigned char *sign, unsigned int *signlen); + virtual bool VerifySignBin(std::string, const void*, uint32_t, unsigned char*, unsigned int); + +#endif + +/*********************************************************************************/ +/************************* PGP Specific functions ********************************/ +/*********************************************************************************/ + +/* + * These support the authentication process. + * + */ + + /************* Virtual Functions from AuthSSL *************/ + virtual bool ValidateCertificate(X509 *x509, std::string &peerId); + virtual int VerifyX509Callback(int preverify_ok, X509_STORE_CTX *ctx); + /************* Virtual Functions from AuthSSL *************/ + +/* + * + */ + + bool checkSignature(std::string id, std::string hash, std::string signature); + + + + +/*********************************************************************************/ +/************************* OTHER FUNCTIONS ***************************************/ +/*********************************************************************************/ + + /* High Level Load/Save Configuration */ +/***** + * These functions call straight through to AuthSSL. + * We don't need these functions here - as GPG stores the keys for us. + bool FinalSaveCertificates(); + bool CheckSaveCertificates(); + bool saveCertificates(); + bool loadCertificates(); + ****/ + +private: + + RsMutex pgpMtx; + /* Below is protected via the mutex */ + + certmap mKeyList; + + bool gpgmeInit; + bool gpgmeKeySelected; + bool gpgmeX509Selected; + + gpgme_engine_info_t INFO; + gpgme_ctx_t CTX; + + std::string mOwnId; + std::string mX509id; + + gpgcert mOwnGpgCert; + + std::string passphrase; +}; + +/***** + * + * Support Functions for OpenSSL verification. + * + */ + +//int verify_pgp_callback(int preverify_ok, X509_STORE_CTX *ctx); + + +/* Sign a key */ + +typedef enum +{ + SIGN_START, + SIGN_COMMAND, + SIGN_UIDS, + SIGN_SET_EXPIRE, + SIGN_SET_CHECK_LEVEL, + SIGN_ENTER_PASSPHRASE, + SIGN_CONFIRM, + SIGN_QUIT, + SIGN_SAVE, + SIGN_ERROR +} SignState; + + +/* Change the key ownertrust */ + +typedef enum +{ + TRUST_START, + TRUST_COMMAND, + TRUST_VALUE, + TRUST_REALLY_ULTIMATE, + TRUST_QUIT, + TRUST_SAVE, + TRUST_ERROR +} TrustState; + + + +/* This is the generic data object passed to the + * callback function in a gpgme_op_edit operation. + * The contents of this object are modified during + * each callback, to keep track of states, errors + * and other data. + */ + +class EditParams +{ + public: + int state; + /* The return code of gpgme_op_edit() is the return value of + * the last invocation of the callback. But returning an error + * from the callback does not abort the edit operation, so we + * must remember any error. + */ + gpg_error_t err; + + /* Parameters specific to the key operation */ + void *oParams; + + EditParams(int state, void *oParams) { + this->state = state; + this->err = gpgme_error(GPG_ERR_NO_ERROR); + this->oParams = oParams; + } + +}; + +/* Data specific to key signing */ + +class SignParams +{ +public: + + std::string checkLvl; + std::string passphrase; + + SignParams(std::string checkLvl, std::string passphrase) + { + this->checkLvl = checkLvl; + this->passphrase = passphrase; + } +}; + +#endif diff --git a/libretroshare/src/_pqi/pqi.pri b/libretroshare/src/_pqi/pqi.pri new file mode 100644 index 000000000..f9a0516ae --- /dev/null +++ b/libretroshare/src/_pqi/pqi.pri @@ -0,0 +1,7 @@ +INCLUDEPATH += $$PWD \ + ../$$PWP +DEPENDPATH += $$PWD + +SOURCES = authgpg.cc + +HEADERS = authgpg.h diff --git a/libretroshare/src/_rsiface/rsiface.pri b/libretroshare/src/_rsiface/rsiface.pri index 0d40ff511..9e96f0191 100644 --- a/libretroshare/src/_rsiface/rsiface.pri +++ b/libretroshare/src/_rsiface/rsiface.pri @@ -1,6 +1,7 @@ INCLUDEPATH += $$PWD \ ../$$PWP DEPENDPATH += $$PWD + SOURCES = $$PWP/rsinit.cc \ $$PWP/rsiface.cc \ $$PWP/rscontrol.cc \ diff --git a/libretroshare/src/_rsserver/p3blog.cc b/libretroshare/src/_rsserver/p3blog.cc index f071fafb5..f7251f8ae 100644 --- a/libretroshare/src/_rsserver/p3blog.cc +++ b/libretroshare/src/_rsserver/p3blog.cc @@ -23,7 +23,7 @@ * */ -#include "_rsserver/p3Blog.h" +#include "_rsserver/p3blog.h" RsQblog* rsQblog = NULL; diff --git a/libretroshare/src/_rsserver/p3blog.h b/libretroshare/src/_rsserver/p3blog.h index fb6b36a1e..52e5fe005 100644 --- a/libretroshare/src/_rsserver/p3blog.h +++ b/libretroshare/src/_rsserver/p3blog.h @@ -1,6 +1,3 @@ - - - #ifndef P3BLOG_H_ #define P3BLOG_H_ @@ -29,7 +26,7 @@ * */ -#include "_rsiface/rsQblog.h" +#include "_rsiface/rsqblog.h" #include "services/p3Qblog.h" /*! @@ -38,19 +35,19 @@ */ class p3Blog : public RsQblog { - public: +public: - p3Blog(p3Qblog* qblog); - virtual ~p3Blog(); + p3Blog(p3Qblog* qblog); + virtual ~p3Blog(); - virtual bool sendBlog(const std::wstring &msg); - virtual bool getBlogs(std::map< std::string, std::multimap > &blogs); - virtual bool getPeerLatestBlog(std::string id, uint32_t &ts, std::wstring &post); + virtual bool sendBlog(const std::wstring &msg); + virtual bool getBlogs(std::map< std::string, std::multimap > &blogs); + virtual bool getPeerLatestBlog(std::string id, uint32_t &ts, std::wstring &post); - private: +private: - /// to make rsCore blog-service calls - p3Qblog* mQblog; + /// to make rsCore blog-service calls + p3Qblog* mQblog; }; diff --git a/libretroshare/src/_rsserver/p3face-config.cc b/libretroshare/src/_rsserver/p3face-config.cc new file mode 100644 index 000000000..904c5a3da --- /dev/null +++ b/libretroshare/src/_rsserver/p3face-config.cc @@ -0,0 +1,7 @@ +/* + This File is dying +*/ + +#include "_rsserver/p3face.h" + + diff --git a/libretroshare/src/_rsserver/p3face-msgs.cc b/libretroshare/src/_rsserver/p3face-msgs.cc new file mode 100644 index 000000000..6fca96880 --- /dev/null +++ b/libretroshare/src/_rsserver/p3face-msgs.cc @@ -0,0 +1,9 @@ +// This File is dieying + +#include "_rsserver/rsserver.h" + + + + + + diff --git a/libretroshare/src/_rsserver/p3face-server.cc b/libretroshare/src/_rsserver/p3face-server.cc new file mode 100644 index 000000000..0235eefae --- /dev/null +++ b/libretroshare/src/_rsserver/p3face-server.cc @@ -0,0 +1,6 @@ +// This file is dying + +#include "_rsserver/rsserver.h" + + + diff --git a/libretroshare/src/_rsserver/p3face-startup.cc b/libretroshare/src/_rsserver/p3face-startup.cc new file mode 100644 index 000000000..803cb9b8c --- /dev/null +++ b/libretroshare/src/_rsserver/p3face-startup.cc @@ -0,0 +1,4 @@ +// This File is dieying + +#include "_rsiface/rsinit.h" + diff --git a/libretroshare/src/_rsserver/p3face.cc b/libretroshare/src/_rsserver/p3face.cc deleted file mode 100644 index 90e342ae4..000000000 --- a/libretroshare/src/_rsserver/p3face.cc +++ /dev/null @@ -1,239 +0,0 @@ -/* - * "$Id: p3face-msgs.cc,v 1.7 2007-05-05 16:10:06 rmf24 Exp $" - * - * RetroShare C++ Interface. - * - * Copyright 2004-2006 by Robert Fernie. - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Library General Public - * License Version 2 as published by the Free Software Foundation. - * - * This library 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 - * Library General Public License for more details. - * - * You should have received a copy of the GNU Library General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - * USA. - * - * Please report all bugs and problems to "retroshare@lunamutt.com". - * - */ - - -#include "p3face.h" -#include "util/rsdir.h" - -#include -#include - -#include "util/rsdebug.h" - - -#include -#include - -const int p3facemsgzone = 11453; - -void RsServer::lockRsCore() -{ - // std::cerr << "RsServer::lockRsCore()" << std::endl; - coreMutex.lock(); -} - -void RsServer::unlockRsCore() -{ - // std::cerr << "RsServer::unlockRsCore()" << std::endl; - coreMutex.unlock(); -} - - /* Flagging Persons / Channels / Files in or out of a set (CheckLists) */ -int RsServer::ClearInChat() -{ - lockRsCore(); /* LOCK */ - - mInChatList.clear(); - - unlockRsCore(); /* UNLOCK */ - - return 1; -} - - -/* Flagging Persons / Channels / Files in or out of a set (CheckLists) */ -int RsServer::SetInChat(std::string id, bool in) /* friend : chat msgs */ -{ - /* so we send this.... */ - lockRsCore(); /* LOCK */ - - //std::cerr << "Set InChat(" << id << ") to " << (in ? "True" : "False") << std::endl; - std::list::iterator it; - it = std::find(mInChatList.begin(), mInChatList.end(), id); - if (it == mInChatList.end()) - { - if (in) - { - mInChatList.push_back(id); - } - } - else - { - if (!in) - { - mInChatList.erase(it); - } - } - - unlockRsCore(); /* UNLOCK */ - - return 1; -} - - -int RsServer::ClearInMsg() -{ - lockRsCore(); /* LOCK */ - - mInMsgList.clear(); - - unlockRsCore(); /* UNLOCK */ - - return 1; -} - - -int RsServer::SetInMsg(std::string id, bool in) /* friend : msgs */ -{ - /* so we send this.... */ - lockRsCore(); /* LOCK */ - - //std::cerr << "Set InMsg(" << id << ") to " << (in ? "True" : "False") << std::endl; - std::list::iterator it; - it = std::find(mInMsgList.begin(), mInMsgList.end(), id); - if (it == mInMsgList.end()) - { - if (in) - { - mInMsgList.push_back(id); - } - } - else - { - if (!in) - { - mInMsgList.erase(it); - } - } - - unlockRsCore(); /* UNLOCK */ - return 1; -} - -bool RsServer::IsInChat(std::string id) /* friend : chat msgs */ -{ - /* so we send this.... */ - lockRsCore(); /* LOCK */ - - std::list::iterator it; - it = std::find(mInChatList.begin(), mInChatList.end(), id); - bool inChat = (it != mInChatList.end()); - - unlockRsCore(); /* UNLOCK */ - - return inChat; -} - - -bool RsServer::IsInMsg(std::string id) /* friend : msg recpts*/ -{ - /* so we send this.... */ - lockRsCore(); /* LOCK */ - - std::list::iterator it; - it = std::find(mInMsgList.begin(), mInMsgList.end(), id); - bool inMsg = (it != mInMsgList.end()); - - unlockRsCore(); /* UNLOCK */ - - return inMsg; -} - - - - -int RsServer::ClearInBroadcast() -{ - return 1; -} - -int RsServer::ClearInSubscribe() -{ - return 1; -} - -int RsServer::SetInBroadcast(std::string id, bool in) /* channel : channel broadcast */ -{ - return 1; -} - -int RsServer::SetInSubscribe(std::string id, bool in) /* channel : subscribed channels */ -{ - return 1; -} - -int RsServer::ClearInRecommend() -{ - /* find in people ... set chat flag */ - RsIface &iface = getIface(); - iface.lockData(); /* LOCK IFACE */ - - std::list &recs = iface.mRecommendList; - std::list::iterator it; - - for(it = recs.begin(); it != recs.end(); it++) - { - it -> inRecommend = false; - } - - iface.unlockData(); /* UNLOCK IFACE */ - - return 1; -} - - -int RsServer::SetInRecommend(std::string id, bool in) /* file : recommended file */ -{ - /* find in people ... set chat flag */ - RsIface &iface = getIface(); - iface.lockData(); /* LOCK IFACE */ - - std::list &recs = iface.mRecommendList; - std::list::iterator it; - - for(it = recs.begin(); it != recs.end(); it++) - { - if (it -> fname == id) - { - /* set flag */ - it -> inRecommend = in; - //std::cerr << "Set InRecommend (" << id << ") to " << (in ? "True" : "False") << std::endl; - } - } - - iface.unlockData(); /* UNLOCK IFACE */ - - return 1; -} - -std::string make_path_unix(std::string path) -{ - for(unsigned int i = 0; i < path.length(); i++) - { - if (path[i] == '\\') - path[i] = '/'; - } - return path; -} diff --git a/libretroshare/src/_rsserver/p3face.h b/libretroshare/src/_rsserver/p3face.h index 052cf30e7..32c89e893 100644 --- a/libretroshare/src/_rsserver/p3face.h +++ b/libretroshare/src/_rsserver/p3face.h @@ -1,181 +1,7 @@ #ifndef P3FACE_H #define P3FACE_H -/* - * "$Id: p3face.h,v 1.9 2007-05-05 16:10:06 rmf24 Exp $" - * - * RetroShare C++ Interface. - * - * Copyright 2004-2006 by Robert Fernie. - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Library General Public - * License Version 2 as published by the Free Software Foundation. - * - * This library 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 - * Library General Public License for more details. - * - * You should have received a copy of the GNU Library General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - * USA. - * - * Please report all bugs and problems to "retroshare@lunamutt.com". - * - */ - -//#include "server/filedexserver.h" -#include "ft/ftserver.h" -//#include "pqi/pqissl.h" - -#include "pqi/p3cfgmgr.h" -#include "pqi/p3connmgr.h" -#include "pqi/pqipersongrp.h" - -#include "_rsiface/rsiface.h" -#include "_rsiface/rstypes.h" -#include "util/rsthreads.h" - -#include "services/p3disc.h" -#include "services/p3msgservice.h" -#include "services/p3chatservice.h" -#include "services/p3ranking.h" -#include "services/p3Qblog.h" - -/* The Main Interface Class - for controlling the server */ - -/* The init functions are actually Defined in p3face-startup.cc - */ -//RsInit *InitRsConfig(); -//void CleanupRsConfig(RsInit *); -//int InitRetroShare(int argc, char **argv, RsInit *config); -//int LoadCertificates(RsInit *config); - -RsControl *createRsControl(RsIface &iface, NotifyBase ¬ify); +#include "_rsserver/rsserver.h" -class RsServer: public RsControl, public RsThread -{ -public: - /****************************************/ - /* p3face-startup.cc: init... */ - virtual int StartupRetroShare(); - - public: - /****************************************/ - /* p3face.cc: main loop / util fns / locking. */ - - RsServer(RsIface &i, NotifyBase &callback); - virtual ~RsServer(); - - /* Thread Fn: Run the Core */ - virtual void run(); - -public: // no longer private:!!! - /* locking stuff */ - void lockRsCore(); - - void unlockRsCore(); - -private: - - /* mutex */ - RsMutex coreMutex; - - /* General Internal Helper Functions - (Must be Locked) - */ -#if 0 - cert *intFindCert(RsCertId id); - RsCertId intGetCertId(cert *c); -#endif - - /****************************************/ - /****************************************/ - /* p3face-msg Operations */ - -public: - virtual const std::string& certificateFileName() ; - - /* Flagging Persons / Channels / Files in or out of a set (CheckLists) */ - virtual int SetInChat(std::string id, bool in); /* friend : chat msgs */ - virtual int SetInMsg(std::string id, bool in); /* friend : msg receipients */ - virtual int SetInBroadcast(std::string id, bool in); /* channel : channel broadcast */ - virtual int SetInSubscribe(std::string id, bool in); /* channel : subscribed channels */ - virtual int SetInRecommend(std::string id, bool in); /* file : recommended file */ - virtual int ClearInChat(); - virtual int ClearInMsg(); - virtual int ClearInBroadcast(); - virtual int ClearInSubscribe(); - virtual int ClearInRecommend(); - - virtual bool IsInChat(std::string id); /* friend : chat msgs */ - virtual bool IsInMsg(std::string id); /* friend : msg recpts*/ - - -private: - - std::list mInChatList, mInMsgList; - - void initRsMI(RsMsgItem *msg, MessageInfo &mi); - - /****************************************/ - /****************************************/ - /****************************************/ -public: - /* Config */ - - virtual int ConfigGetDataRates(float &inKb, float &outKb); - virtual int ConfigSetDataRates( int totalDownload, int totalUpload ); - virtual int ConfigSetBootPrompt( bool on ); - - virtual void ConfigFinalSave( ); - /************* Rs shut down function: in upnp 'port lease time' bug *****************/ - - /** - * This function is responsible for ensuring Retroshare exits in a legal state: - * i.e. releases all held resources and saves current configuration - */ - virtual void rsGlobalShutDown( ); -private: - int UpdateAllConfig(); - - /****************************************/ -private: - - // The real Server Parts. - //filedexserver *server; - ftServer *ftserver; - - p3ConnectMgr *mConnMgr; - p3AuthMgr *mAuthMgr; - - pqipersongrp *pqih; - - //sslroot *sslr; - - /* services */ - p3disc *ad; - p3MsgService *msgSrv; - p3ChatService *chatSrv; - - /* caches (that need ticking) */ - p3Ranking *mRanking; - p3Qblog *mQblog; - - /* Config */ - p3ConfigMgr *mConfigMgr; - p3GeneralConfig *mGeneralConfig; - - // Worker Data..... -}; - -/* Helper function to convert windows paths - * into unix (ie switch \ to /) for FLTK's file chooser - */ - -std::string make_path_unix(std::string winpath); - -#endif +#endif //P3FACE_H diff --git a/libretroshare/src/_rsserver/p3files.h b/libretroshare/src/_rsserver/p3files.h new file mode 100644 index 000000000..595009c8e --- /dev/null +++ b/libretroshare/src/_rsserver/p3files.h @@ -0,0 +1,123 @@ +#ifndef P3FILES_H +#define P3FILES_H + +/* + * libretroshare/src/rsserver: p3files.h + * + * RetroShare C++ Interface. + * + * Copyright 2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + + +#include +#include +#include +#include + +#include "_rsiface/rsfiles.h" + +#include "util/rsthreads.h" + +class filedexserver; +class RsServer; +class p3AuthMgr; + + +// CHANGED: CODE CHANGED : The p3Files is not implemented in any way so it's pure virtual +// Added " = 0 " to the functions + +class p3Files: public RsFiles +{ +public: + + p3Files(filedexserver *s, RsServer *c, p3AuthMgr *a) + :mServer(s), mCore(c), mAuthMgr(a) {} + + virtual ~p3Files() { return; } + + /****************************************/ + /* 1) Access to downloading / uploading files. */ + + virtual bool FileDownloads(std::list &hashs) = 0; + virtual bool FileUploads(std::list &hashs) = 0; + virtual bool FileDetails(std::string hash, uint32_t hintflags, FileInfo &info) = 0; + + /* 2) Control of Downloads. */ + virtual bool FileRequest(std::string fname, std::string hash, uint64_t size, + std::string dest, uint32_t flags, + std::list srcIds) = 0; + virtual bool FileCancel(std::string hash) = 0; + virtual bool FileControl(std::string hash, uint32_t flags) = 0; + virtual bool FileClearCompleted() = 0; + + /* 3) Addition of Extra Files... From File System */ + + virtual bool ExtraFileAdd(std::string fname, std::string hash, uint64_t size, + uint32_t period, uint32_t flags) = 0; + virtual bool ExtraFileRemove(std::string hash, uint32_t flags) = 0; + virtual bool ExtraFileHash(std::string localpath, + uint32_t period, uint32_t flags); + virtual bool ExtraFileStatus(std::string localpath, FileInfo &info) = 0; + + /* 4) Search and Listing Interface */ + + virtual int RequestDirDetails(std::string uid, std::string path, DirDetails &details) = 0; + virtual int RequestDirDetails(void *ref, DirDetails &details, uint32_t flags) = 0; + + virtual int SearchKeywords(std::list keywords, std::list &results) = 0; + virtual int SearchBoolExp(Expression * exp, std::list &results) = 0; + + /* 5) Utility Functions. */ + + virtual bool ConvertSharedFilePath(std::string path, std::string &fullpath) = 0; + virtual void ForceDirectoryCheck() = 0; + virtual bool InDirectoryCheck() = 0; + + + virtual void setDownloadDirectory(std::string path) = 0; + virtual void setPartialsDirectory(std::string path) = 0; + virtual std::string getDownloadDirectory() = 0; + virtual std::string getPartialsDirectory() = 0; + + virtual bool getSharedDirectories(std::list &dirs) = 0; + virtual bool addSharedDirectory(std::string dir) = 0; + virtual bool removeSharedDirectory(std::string dir) = 0; + + + /* Update functions! */ + int UpdateAllTransfers() = 0; + +private: + + void lockRsCore() = 0; + void unlockRsCore() = 0; + + filedexserver *mServer = 0; + RsServer *mCore; + p3AuthMgr *mAuthMgr; + + RsMutex fMutex; + std::map mTransfers; + +}; + + +#endif //P3FILES_H diff --git a/libretroshare/src/_rsserver/p3msgs.cc b/libretroshare/src/_rsserver/p3msgs.cc new file mode 100644 index 000000000..a3bead43b --- /dev/null +++ b/libretroshare/src/_rsserver/p3msgs.cc @@ -0,0 +1,191 @@ + +/* + * "$Id: p3face-msgs.cc,v 1.7 2007-05-05 16:10:06 rmf24 Exp $" + * + * RetroShare C++ Interface. + * + * Copyright 2004-2006 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + + + +#include +#include + +#include "util/rsdir.h" +#include "util/rsdebug.h" +const int p3facemsgzone = 11453; + +#include +#include + +#include "rsiface/rstypes.h" +#include "rsserver/p3msgs.h" + +#include "services/p3msgservice.h" +#include "services/p3chatservice.h" + +/* external reference point */ +RsMsgs *rsMsgs = NULL; + +/****************************************/ +/****************************************/ + +bool p3Msgs::getMessageSummaries(std::list &msgList) +{ + return mMsgSrv->getMessageSummaries(msgList); +} + + + +bool p3Msgs::getMessage(std::string mid, MessageInfo &msg) +{ + return mMsgSrv->getMessage(mid, msg); +} + + + +/****************************************/ +/****************************************/ + /* Message Items */ +bool p3Msgs::MessageSend(MessageInfo &info) +{ + return mMsgSrv->MessageSend(info); +} + +/****************************************/ +/****************************************/ +bool p3Msgs::MessageDelete(std::string mid) +{ + //std::cerr << "p3Msgs::MessageDelete() "; + //std::cerr << "mid: " << mid << std::endl; + + mMsgSrv -> removeMsgId(mid); + + return 1; +} + +bool p3Msgs::MessageRead(std::string mid) +{ + //std::cerr << "p3Msgs::MessageRead() "; + //std::cerr << "mid: " << mid << std::endl; + + mMsgSrv -> markMsgIdRead(mid); + + return 1; +} + +/****************************************/ +/****************************************/ +bool p3Msgs::ChatSend(ChatInfo &ci) +{ + /* send a message to all for now */ + if (ci.chatflags & RS_CHAT_PRIVATE) + { + mChatSrv -> sendPrivateChat(ci.msg, ci.rsid); + } + else + { + /* global */ + mChatSrv -> sendChat(ci.msg); + } + return true; +} + +void p3Msgs::sendStatusString(const std::string& peer_id,const std::string& status_string) +{ + mChatSrv->sendStatusString(peer_id,status_string); +} + +bool p3Msgs::chatAvailable() +{ + return mChatSrv->receivedItems(); +} + +bool p3Msgs::getNewChat(std::list &chats) +{ + /* get any messages and push them to iface */ + + // get the items from the list. + std::list clist = mChatSrv -> getChatQueue(); + if (clist.size() < 1) + { + return false; + } + + std::list::iterator it; + for(it = clist.begin(); it != clist.end(); it++) + { + ChatInfo ci; + initRsChatInfo((*it), ci); + chats.push_back(ci); + delete (*it); + } + return true; +} + +/**** HELPER FNS For Chat/Msg/Channel Lists ************ + * + * The iface->Mutex is required to be locked + * for intAddChannel / intAddChannelMsg. + */ + +void p3Msgs::initRsChatInfo(RsChatMsgItem *c, ChatInfo &i) +{ + i.rsid = c -> PeerId(); + i.name = mAuthMgr->getName(i.rsid); + i.chatflags = 0 ; + i.msg = c -> message; + + if (c -> chatFlags & RS_CHAT_FLAG_PRIVATE) + { + i.chatflags |= RS_CHAT_PRIVATE; + //std::cerr << "RsServer::initRsChatInfo() Chat Private!!!"; + } + else + { + i.chatflags |= RS_CHAT_PUBLIC; + //std::cerr << "RsServer::initRsChatInfo() Chat Public!!!"; + } + //std::cerr << std::endl; + + if(c->chatFlags & RS_CHAT_FLAG_AVATAR_AVAILABLE) + { + std::cerr << "p3msgs::initRsChatInfo(): new avatar available for peer " << i.rsid << ". Sending above." << std::endl ; + i.chatflags |= RS_CHAT_AVATAR_AVAILABLE; + } +} + +void p3Msgs::getOwnAvatarData(unsigned char *& data,int& size) +{ + mChatSrv->getOwnAvatarJpegData(data,size) ; +} + +void p3Msgs::setOwnAvatarData(const unsigned char *data,int size) +{ + mChatSrv->setOwnAvatarJpegData(data,size) ; +} + +void p3Msgs::getAvatarData(std::string pid,unsigned char *& data,int& size) +{ + mChatSrv->getAvatarJpegData(pid,data,size) ; +} + + diff --git a/libretroshare/src/_rsserver/p3msgs.h b/libretroshare/src/_rsserver/p3msgs.h new file mode 100644 index 000000000..01e9d4931 --- /dev/null +++ b/libretroshare/src/_rsserver/p3msgs.h @@ -0,0 +1,80 @@ +#ifndef P3MSGS_H +#define P3MSGS_H + +/* + * libretroshare/src/rsserver: p3msgs.h + * + * RetroShare C++ Interface. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#include "_rsiface/rsmsgs.h" + +class p3AuthMgr; +class p3MsgService; +class p3ChatService; + +class RsChatMsgItem; + +class p3Msgs: public RsMsgs +{ + public: + + p3Msgs(p3AuthMgr *p3a, p3MsgService *p3m, p3ChatService *p3c) + :mAuthMgr(p3a), mMsgSrv(p3m), mChatSrv(p3c) { return; } + virtual ~p3Msgs() { return; } + + /****************************************/ + /* Message Items */ + + virtual bool getMessageSummaries(std::list &msgList); + virtual bool getMessage(std::string mId, MessageInfo &msg); + + virtual bool MessageSend(MessageInfo &info); + virtual bool MessageDelete(std::string mid); + virtual bool MessageRead(std::string mid); + + // gets avatar from peer id in jpeg format. + virtual void getAvatarData(std::string pid,unsigned char *& data,int& size); + virtual void setOwnAvatarData(const unsigned char *data,int size); + virtual void getOwnAvatarData(unsigned char *& data,int& size); + + /****************************************/ + /* Chat */ + virtual bool chatAvailable(); + virtual bool ChatSend(ChatInfo &ci); + virtual bool getNewChat(std::list &chats); + virtual void sendStatusString(const std::string& peer_id,const std::string& status_string) ; + + /****************************************/ + + + private: + + void initRsChatInfo(RsChatMsgItem *c, ChatInfo &i); + + p3AuthMgr *mAuthMgr; + p3MsgService *mMsgSrv; + p3ChatService *mChatSrv; +}; + + +#endif // P3MSGS_H diff --git a/libretroshare/src/_rsserver/p3peers.cc b/libretroshare/src/_rsserver/p3peers.cc new file mode 100644 index 000000000..5e7123897 --- /dev/null +++ b/libretroshare/src/_rsserver/p3peers.cc @@ -0,0 +1,1016 @@ +/* + * libretroshare/src/rsserver: p3peers.cc + * + * RetroShare C++ Interface. + * + * Copyright 2004-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#include "_rsserver/p3peers.h" +#include "_rsserver/p3face.h" +#include "pqi/p3connmgr.h" +#include "pqi/p3authmgr.h" +#include "_rsiface/rsinit.h" + +#include +#include +#include + +#ifdef RS_USE_PGPSSL + #include +#endif + +/**************** PQI_USE_XPGP ******************/ +#if defined(PQI_USE_XPGP) + #include "pqi/authxpgp.h" +#else /* X509 Certificates */ +/**************** PQI_USE_XPGP ******************/ + #include "pqi/authssl.h" +#endif /* X509 Certificates */ +/**************** PQI_USE_XPGP ******************/ + + +RsPeers *rsPeers = NULL; + +/******* + * #define P3PEERS_DEBUG 1 + *******/ +#define P3PEERS_DEBUG 1 + +static uint32_t RsPeerTranslateTrust(uint32_t trustLvl); +int ensureExtension(std::string &name, std::string def_ext); + +std::string RsPeerTrustString(uint32_t trustLvl) +{ + + std::string str; + +#ifdef RS_USE_PGPSSL + switch(trustLvl) + { + default: + case GPGME_VALIDITY_UNKNOWN: + str = "GPGME_VALIDITY_UNKNOWN"; + break; + case GPGME_VALIDITY_UNDEFINED: + str = "GPGME_VALIDITY_UNDEFINED"; + break; + case GPGME_VALIDITY_NEVER: + str = "GPGME_VALIDITY_NEVER"; + break; + case GPGME_VALIDITY_MARGINAL: + str = "GPGME_VALIDITY_MARGINAL"; + break; + case GPGME_VALIDITY_FULL: + str = "GPGME_VALIDITY_FULL"; + break; + case GPGME_VALIDITY_ULTIMATE: + str = "GPGME_VALIDITY_ULTIMATE"; + break; + } + return str; +#endif + + if (trustLvl == RS_TRUST_LVL_GOOD) + { + str = "Good"; + } + else if (trustLvl == RS_TRUST_LVL_MARGINAL) + { + str = "Marginal"; + } + else + { + str = "No Trust"; + } + return str; +} + + + +std::string RsPeerStateString(uint32_t state) +{ + std::string str; + if (state & RS_PEER_STATE_CONNECTED) + { + str = "Connected"; + } + else if (state & RS_PEER_STATE_UNREACHABLE) + { + str = "Unreachable"; + } + else if (state & RS_PEER_STATE_ONLINE) + { + str = "Available"; + } + else if (state & RS_PEER_STATE_FRIEND) + { + str = "Offline"; + } + else + { + str = "Neighbour"; + } + return str; +} + +std::string RsPeerNetModeString(uint32_t netModel) +{ + std::string str; + if (netModel == RS_NETMODE_EXT) + { + str = "External Port"; + } + else if (netModel == RS_NETMODE_UPNP) + { + str = "Ext (UPnP)"; + } + else if (netModel == RS_NETMODE_UDP) + { + str = "UDP Mode"; + } + else if (netModel == RS_NETMODE_UNREACHABLE) + { + str = "UDP Mode (Unreachable)"; + } + else + { + str = "Unknown NetMode"; + } + return str; +} + + +std::string RsPeerLastConnectString(uint32_t lastConnect) +{ + std::ostringstream out; + out << lastConnect << " secs ago"; + return out.str(); +} + + +p3Peers::p3Peers(p3ConnectMgr *cm, p3AuthMgr *am) + :mConnMgr(cm), mAuthMgr(am) +{ + return; +} + + /* Updates ... */ +bool p3Peers::FriendsChanged() +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::FriendsChanged()"; + std::cerr << std::endl; +#endif + + /* TODO */ + return false; +} + +bool p3Peers::OthersChanged() +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::OthersChanged()"; + std::cerr << std::endl; +#endif + + /* TODO */ + return false; +} + + /* Peer Details (Net & Auth) */ +std::string p3Peers::getOwnId() +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::getOwnId()"; + std::cerr << std::endl; +#endif + + return mAuthMgr->OwnId(); +} + +bool p3Peers::getOnlineList(std::list &ids) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::getOnlineList()"; + std::cerr << std::endl; +#endif + + /* get from mConnectMgr */ + mConnMgr->getOnlineList(ids); + return true; +} + +bool p3Peers::getFriendList(std::list &ids) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::getFriendList()"; + std::cerr << std::endl; +#endif + + /* get from mConnectMgr */ + mConnMgr->getFriendList(ids); + return true; +} + +bool p3Peers::getOthersList(std::list &ids) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::getOthersList()"; + std::cerr << std::endl; +#endif + + /* get from mAuthMgr */ + mAuthMgr->getAllList(ids); + return true; +} + +bool p3Peers::isOnline(std::string id) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::isOnline() " << id; + std::cerr << std::endl; +#endif + + /* get from mConnectMgr */ + peerConnectState state; + if (mConnMgr->getFriendNetStatus(id, state) && + (state.state & RS_PEER_S_CONNECTED)) + { + return true; + } + return false; +} + +bool p3Peers::isTrustingMe(std::string id) const +{ + return mAuthMgr->isTrustingMe(id) ; +} + +bool p3Peers::isFriend(std::string id) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::isFriend() " << id; + std::cerr << std::endl; +#endif + + /* get from mConnectMgr */ + peerConnectState state; + if (mConnMgr->getFriendNetStatus(id, state) && + (state.state & RS_PEER_S_FRIEND)) + { + return true; + } + return false; +} + +bool p3Peers::getPeerDetails(std::string id, RsPeerDetails &d) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::getPeerDetails() " << id; + std::cerr << std::endl; +#endif + + /* get from mAuthMgr (first) */ + pqiAuthDetails authDetail; + if (!mAuthMgr->getDetails(id, authDetail)) + { + return false; + } + + d.fpr = authDetail.fpr; + d.id = authDetail.id; + d.name = authDetail.name; + d.email = authDetail.email; + d.location = authDetail.location; + d.org = authDetail.org; + d.signers = authDetail.signers; + + d.ownsign = authDetail.ownsign; + d.trusted = authDetail.trusted; + +#ifdef RS_USE_PGPSSL + d.trustLvl = authDetail.trustLvl; + d.validLvl = authDetail.validLvl; +#else + d.trustLvl = RsPeerTranslateTrust(authDetail.trustLvl); + d.validLvl = RsPeerTranslateTrust(authDetail.trustLvl); +#endif + + /* generate */ + d.authcode = "AUTHCODE"; + + /* get from mConnectMgr */ + peerConnectState pcs; + + if (id == mAuthMgr->OwnId()) + { + mConnMgr->getOwnNetStatus(pcs); + } + else if (!mConnMgr->getFriendNetStatus(id, pcs)) + { + if (!mConnMgr->getOthersNetStatus(id, pcs)) + { + /* fill in blank data */ + d.localPort = 0; + d.extPort = 0; + d.lastConnect = 0; + d.connectPeriod = 0; + d.state = 0; + d.netMode = 0; + + return true; + } + } + + /* fill from pcs */ + + d.localAddr = inet_ntoa(pcs.localaddr.sin_addr); + d.localPort = ntohs(pcs.localaddr.sin_port); + d.extAddr = inet_ntoa(pcs.serveraddr.sin_addr); + d.extPort = ntohs(pcs.serveraddr.sin_port); + d.lastConnect = pcs.lastcontact; + d.connectPeriod = 0; + + /* Translate */ + + d.state = 0; + if (pcs.state & RS_PEER_S_FRIEND) + d.state |= RS_PEER_STATE_FRIEND; + if (pcs.state & RS_PEER_S_ONLINE) + d.state |= RS_PEER_STATE_ONLINE; + if (pcs.state & RS_PEER_S_CONNECTED) + d.state |= RS_PEER_STATE_CONNECTED; + if (pcs.state & RS_PEER_S_UNREACHABLE) + d.state |= RS_PEER_STATE_UNREACHABLE; + + switch(pcs.netMode & RS_NET_MODE_ACTUAL) + { + case RS_NET_MODE_EXT: + d.netMode = RS_NETMODE_EXT; + break; + case RS_NET_MODE_UPNP: + d.netMode = RS_NETMODE_UPNP; + break; + case RS_NET_MODE_UDP: + d.netMode = RS_NETMODE_UDP; + break; + case RS_NET_MODE_UNREACHABLE: + case RS_NET_MODE_UNKNOWN: + default: + d.netMode = RS_NETMODE_UNREACHABLE; + break; + } + + if (pcs.netMode & RS_NET_MODE_TRY_EXT) + { + d.tryNetMode = RS_NETMODE_EXT; + } + else if (pcs.netMode & RS_NET_MODE_TRY_UPNP) + { + d.tryNetMode = RS_NETMODE_UPNP; + } + else + { + d.tryNetMode = RS_NETMODE_UDP; + } + + d.visState = 0; + if (!(pcs.visState & RS_VIS_STATE_NODISC)) + { + d.visState |= RS_VS_DISC_ON; + } + + if (!(pcs.visState & RS_VIS_STATE_NODHT)) + { + d.visState |= RS_VS_DHT_ON; + } + + + /* Finally determine AutoConnect Status */ + std::ostringstream autostr; + if (pcs.inConnAttempt) + { + /* + */ + autostr << "Trying "; + switch(pcs.currentConnAddr.type) + { + case RS_NET_CONN_TCP_LOCAL: + autostr << "TCP (Local)"; + break; + case RS_NET_CONN_TCP_EXTERNAL: + autostr << "TCP (External)"; + break; + case RS_NET_CONN_UDP_DHT_SYNC: + autostr << "UDP (ETA: "; + autostr << 420 - (time(NULL) - pcs.currentConnAddr.ts); + autostr << ")"; + break; + default: + autostr << "Unknown"; + break; + } + + } + else if (pcs.state & RS_PEER_S_CONNECTED) + { + if (pcs.connecttype == RS_NET_CONN_TCP_ALL) + { + autostr << "Connected: TCP"; + } + else if (pcs.connecttype == RS_NET_CONN_UDP_ALL) + { + autostr << "Connected: UDP"; + } + else + { + autostr << "Connected: Unknown"; + } + } + else + { + autostr << RsPeerStateString(pcs.state); + } + + d.autoconnect = autostr.str(); + + return true; +} + + +std::string p3Peers::getPeerName(std::string id) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::getPeerName() " << id; + std::cerr << std::endl; +#endif + + /* get from mAuthMgr as it should have more peers? */ + return mAuthMgr->getName(id); +} + + +bool p3Peers::getPGPFriendList(std::list &ids) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::getPGPFriendList()"; + std::cerr << std::endl; +#endif + + std::list certids; + std::list::iterator it; + + mConnMgr->getFriendList(certids); + + /* get from mAuthMgr (first) */ + for(it = certids.begin(); it != certids.end(); it++) + { + pqiAuthDetails detail; + if (!mAuthMgr->getDetails(*it, detail)) + { + continue; + } + +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::getPGPFriendList() Cert Id: " << *it; + std::cerr << " Issuer: " << detail.issuer; + std::cerr << std::endl; +#endif + +#if 0 + if (!mAuthMgr->isPGPvalid(detail.issuer)) + { + continue; + } +#endif + + if (ids.end() == std::find(ids.begin(),ids.end(),detail.issuer)) + { + +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::getPGPFriendList() Adding Friend: "; + std::cerr << detail.issuer; + std::cerr << std::endl; +#endif + + ids.push_back(detail.issuer); + } + } + return true; +} + + + +bool p3Peers::getPGPAllList(std::list &ids) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::getPGPOthersList()"; + std::cerr << std::endl; +#endif + + /* get from mAuthMgr */ + mAuthMgr->getPGPAllList(ids); + return true; +} + +std::string p3Peers::getPGPOwnId() +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::getPGPOwnId()"; + std::cerr << std::endl; +#endif + + /* get from mAuthMgr */ + return mAuthMgr->PGPOwnId(); +} + + + + + /* Add/Remove Friends */ +bool p3Peers::addFriend(std::string id) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::addFriend() " << id; + std::cerr << std::endl; +#endif + + return mConnMgr->addFriend(id); +} + +bool p3Peers::removeFriend(std::string id) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::removeFriend() " << id; + std::cerr << std::endl; +#endif + + return mConnMgr->removeFriend(id); +} + + /* Network Stuff */ +bool p3Peers::connectAttempt(std::string id) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::connectAttempt() " << id; + std::cerr << std::endl; +#endif + + return mConnMgr->retryConnect(id); +} + +void p3Peers::getIPServersList(std::list& ip_servers) +{ + mConnMgr->getIPServersList(ip_servers) ; +} +void p3Peers::allowServerIPDetermination(bool b) +{ + mConnMgr->setIPServersEnabled(b) ; +} +bool p3Peers::getAllowServerIPDetermination() +{ + return mConnMgr->getIPServersEnabled() ; +} + +bool p3Peers::setLocalAddress(std::string id, std::string addr_str, uint16_t port) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::setLocalAddress() " << id; + std::cerr << std::endl; +#endif + + struct sockaddr_in addr; + addr.sin_family = AF_INET; + addr.sin_port = htons(port); + + int ret = 1; +/********************************** WINDOWS/UNIX SPECIFIC PART *******************/ +#ifndef WINDOWS_SYS + if (ret && (0 != inet_aton(addr_str.c_str(), &(addr.sin_addr)))) +#else + addr.sin_addr.s_addr = inet_addr(addr_str.c_str()); + if (ret) +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART *******************/ + { + return mConnMgr->setLocalAddress(id, addr); + } + return false; +} + +bool p3Peers::setExtAddress(std::string id, std::string addr_str, uint16_t port) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::setExtAddress() " << id; + std::cerr << std::endl; +#endif + + struct sockaddr_in addr; + addr.sin_family = AF_INET; + addr.sin_port = htons(port); + + int ret = 1; +/********************************** WINDOWS/UNIX SPECIFIC PART *******************/ +#ifndef WINDOWS_SYS + if (ret && (0 != inet_aton(addr_str.c_str(), &(addr.sin_addr)))) +#else + addr.sin_addr.s_addr = inet_addr(addr_str.c_str()); + if (ret) +#endif +/********************************** WINDOWS/UNIX SPECIFIC PART *******************/ + { + return mConnMgr->setExtAddress(id, addr); + } + return false; +} + + +bool p3Peers::setNetworkMode(std::string id, uint32_t extNetMode) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::setNetworkMode() " << id; + std::cerr << std::endl; +#endif + + /* translate */ + uint32_t netMode = 0; + switch(extNetMode) + { + case RS_NETMODE_EXT: + netMode = RS_NET_MODE_EXT; + break; + case RS_NETMODE_UPNP: + netMode = RS_NET_MODE_UPNP; + break; + case RS_NETMODE_UDP: + netMode = RS_NET_MODE_UDP; + break; + case RS_NETMODE_UNREACHABLE: + netMode = RS_NET_MODE_UNREACHABLE; + break; + default: + break; + } + + return mConnMgr->setNetworkMode(id, netMode); +} + + +bool +p3Peers::setVisState(std::string id, uint32_t extVisState) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::setVisState() " << id; + std::cerr << std::endl; +#endif + + uint32_t visState = 0; + if (!(extVisState & RS_VS_DHT_ON)) + visState |= RS_VIS_STATE_NODHT; + if (!(extVisState & RS_VS_DISC_ON)) + visState |= RS_VIS_STATE_NODISC; + + return mConnMgr->setVisState(id, visState); +} + +//=========================================================================== + /* Auth Stuff */ +std::string +p3Peers::GetRetroshareInvite() +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::GetRetroshareInvite()"; + std::cerr << std::endl; +#endif + + std::cerr << "p3Peers::GetRetroshareInvite()"; + std::cerr << std::endl; + + std::string ownId = mAuthMgr->OwnId(); + std::string certstr = mAuthMgr->SaveCertificateToString(ownId); + std::string name = mAuthMgr->getName(ownId); + + std::string pgpownId = mAuthMgr->PGPOwnId(); + std::string pgpcertstr = mAuthMgr->SaveCertificateToString(pgpownId); + + std::cerr << "p3Peers::GetRetroshareInvite() SSL Cert:"; + std::cerr << std::endl; + std::cerr << certstr; + std::cerr << std::endl; + + std::cerr << "p3Peers::GetRetroshareInvite() PGP Cert:"; + std::cerr << std::endl; + std::cerr << pgpcertstr; + std::cerr << std::endl; + + std::string combinedcerts = certstr; + combinedcerts += '\n'; + combinedcerts += pgpcertstr; + combinedcerts += '\n'; + + return combinedcerts; +} + +//=========================================================================== + +bool p3Peers::LoadCertificateFromFile(std::string fname, std::string &id) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::LoadCertificateFromFile() "; + std::cerr << std::endl; +#endif + + return mAuthMgr->LoadCertificateFromFile(fname, id); +} + + +bool splitCerts(std::string in, std::string &sslcert, std::string &pgpcert) +{ + std::cerr << "splitCerts():" << in; + std::cerr << std::endl; + + /* search for -----END CERTIFICATE----- */ + std::string sslend("-----END CERTIFICATE-----"); + std::string pgpend("-----END PGP PUBLIC KEY BLOCK-----"); + size_t pos = in.find(sslend); + size_t pos2 = in.find(pgpend); + size_t ssllen, pgplen; + + if (pos != std::string::npos) + { + std::cerr << "splitCerts(): Found SSL Cert"; + std::cerr << std::endl; + + ssllen = pos + sslend.length(); + sslcert = in.substr(0, ssllen); + + if (pos2 != std::string::npos) + { + std::cerr << "splitCerts(): Found SSL + PGP Cert"; + std::cerr << std::endl; + + pgplen = pos2 + pgpend.length() - ssllen; + pgpcert = in.substr(ssllen, pgplen); + } + return true; + } + else if (pos2 != std::string::npos) + { + std::cerr << "splitCerts(): Found PGP Cert Only"; + std::cerr << std::endl; + + pgplen = pos2 + pgpend.length(); + pgpcert = in.substr(0, pgplen); + return true; + } + return false; +} + + + +bool p3Peers::LoadCertificateFromString(std::string cert, std::string &id) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::LoadCertificateFromString() "; + std::cerr << std::endl; +#endif + + std::string sslcert; + std::string pgpcert; + bool ret = false; + if (splitCerts(cert, sslcert, pgpcert)) + { + if (pgpcert != "") + { + std::cerr << "pgpcert .... " << std::endl; + std::cerr << pgpcert << std::endl; + + ret = mAuthMgr->LoadCertificateFromString(pgpcert, id); + } + if (sslcert != "") + { + std::cerr << "sslcert .... " << std::endl; + std::cerr << sslcert << std::endl; + + ret = mAuthMgr->LoadCertificateFromString(sslcert, id); + } + } + + return ret; +} + + + + + +bool p3Peers::SaveCertificateToFile(std::string id, std::string fname) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::SaveCertificateToFile() " << id; + std::cerr << std::endl; +#endif + + ensureExtension(fname, "pqi"); + + return mAuthMgr->SaveCertificateToFile(id, fname); +} + +std::string p3Peers::SaveCertificateToString(std::string id) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::SaveCertificateToString() " << id; + std::cerr << std::endl; +#endif + + return mAuthMgr->SaveCertificateToString(id); +} + +bool p3Peers::AuthCertificate(std::string id, std::string code) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::AuthCertificate() " << id; + std::cerr << std::endl; +#endif + + if (mAuthMgr->AuthCertificate(id)) + { +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::AuthCertificate() OK ... Adding as Friend"; + std::cerr << std::endl; +#endif + + /* add in as a friend */ + return mConnMgr->addFriend(id); + } + return false; +} + +bool p3Peers::SignCertificate(std::string id) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::SignCertificate() " << id; + std::cerr << std::endl; +#endif + + return mAuthMgr->SignCertificate(id); +} + +bool p3Peers::TrustCertificate(std::string id, bool trust) +{ +#ifdef P3PEERS_DEBUG + std::cerr << "p3Peers::TrustCertificate() " << id; + std::cerr << std::endl; +#endif + + return mAuthMgr->TrustCertificate(id, trust); +} + + + +int ensureExtension(std::string &name, std::string def_ext) +{ + /* if it has an extension, don't change */ + int len = name.length(); + int extpos = name.find_last_of('.'); + + std::ostringstream out; + out << "ensureExtension() name: " << name << std::endl; + out << "\t\t extpos: " << extpos; + out << " len: " << len << std::endl; + + /* check that the '.' has between 1 and 4 char after it (an extension) */ + if ((extpos > 0) && (extpos < len - 1) && (extpos + 6 > len)) + { + /* extension there */ + std::string curext = name.substr(extpos, len); + out << "ensureExtension() curext: " << curext << std::endl; + std::cerr << out.str(); + return 0; + } + + if (extpos != len - 1) + { + name += "."; + } + name += def_ext; + + out << "ensureExtension() added ext: " << name << std::endl; + + std::cerr << out.str(); + return 1; +} + + + + + +RsPeerDetails::RsPeerDetails() + :trustLvl(0), ownsign(false), trusted(false), state(0), netMode(0), + lastConnect(0), connectPeriod(0) +{ + return; +} + +std::ostream &operator<<(std::ostream &out, const RsPeerDetails &detail) +{ + out << "RsPeerDetail: " << detail.name << " <" << detail.id << ">"; + out << std::endl; + + out << " email: " << detail.email; + out << " location:" << detail.location; + out << " org: " << detail.org; + out << std::endl; + + out << " fpr: " << detail.fpr; + out << " authcode:" << detail.authcode; + out << std::endl; + + out << " signers:"; + out << std::endl; + + std::list::const_iterator it; + for(it = detail.signers.begin(); + it != detail.signers.end(); it++) + { + out << "\t" << *it; + out << std::endl; + } + out << std::endl; + + out << " trustLvl: " << detail.trustLvl; + out << " ownSign: " << detail.ownsign; + out << " trusted: " << detail.trusted; + out << std::endl; + + out << " state: " << detail.state; + out << " netMode: " << detail.netMode; + out << std::endl; + + out << " localAddr: " << detail.localAddr; + out << ":" << detail.localPort; + out << std::endl; + out << " extAddr: " << detail.extAddr; + out << ":" << detail.extPort; + out << std::endl; + + + out << " lastConnect: " << detail.lastConnect; + out << " connectPeriod: " << detail.connectPeriod; + out << std::endl; + + return out; +} + + +/********** TRANSLATION ****/ + + +uint32_t RsPeerTranslateTrust(uint32_t trustLvl) +{ +/**************** PQI_USE_XPGP ******************/ +#if defined(PQI_USE_XPGP) + switch(trustLvl) + { + case TRUST_SIGN_OWN: + case TRUST_SIGN_TRSTED: + case TRUST_SIGN_AUTHEN: + return RS_TRUST_LVL_GOOD; + break; + + case TRUST_SIGN_BASIC: + return RS_TRUST_LVL_MARGINAL; + break; + + case TRUST_SIGN_UNTRUSTED: + case TRUST_SIGN_UNKNOWN: + case TRUST_SIGN_NONE: + default: + return RS_TRUST_LVL_UNKNOWN; + break; + } +#else /* X509 Certificates */ +/**************** PQI_USE_XPGP ******************/ +#endif /* X509 Certificates */ +/**************** PQI_USE_XPGP ******************/ + + return RS_TRUST_LVL_UNKNOWN; +} + diff --git a/libretroshare/src/_rsserver/p3peers.h b/libretroshare/src/_rsserver/p3peers.h new file mode 100644 index 000000000..3ddf0ec94 --- /dev/null +++ b/libretroshare/src/_rsserver/p3peers.h @@ -0,0 +1,98 @@ +#ifndef RETROSHARE_P3_PEER_INTERFACE_H +#define RETROSHARE_P3_PEER_INTERFACE_H + +/* + * libretroshare/src/rsserver: p3peers.h + * + * RetroShare C++ Interface. + * + * Copyright 2004-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#include "_rsiface/rspeers.h" +#include "pqi/p3connmgr.h" +#include "pqi/p3authmgr.h" + +class p3Peers: public RsPeers +{ +public: + + p3Peers(p3ConnectMgr *cm, p3AuthMgr *am); + virtual ~p3Peers() { return; } + + /* Updates ... */ + virtual bool FriendsChanged(); + virtual bool OthersChanged(); + + /* Peer Details (Net & Auth) */ + virtual std::string getOwnId(); + + virtual bool getOnlineList(std::list &ids); + virtual bool getFriendList(std::list &ids); + virtual bool getOthersList(std::list &ids); + + virtual bool isOnline(std::string id); + virtual bool isFriend(std::string id); + virtual std::string getPeerName(std::string id); + virtual bool getPeerDetails(std::string id, RsPeerDetails &d); + + /* Using PGP Ids */ + virtual std::string getPGPOwnId(); + virtual bool getPGPFriendList(std::list &ids); + virtual bool getPGPAllList(std::list &ids); + + + /* Add/Remove Friends */ + virtual bool addFriend(std::string id); + virtual bool removeFriend(std::string id); + + /* get/set third party info about who trusts me */ + virtual bool isTrustingMe(std::string id) const ; + + /* Network Stuff */ + virtual bool connectAttempt(std::string id); + virtual bool setLocalAddress(std::string id, std::string addr, uint16_t port); + virtual bool setExtAddress(std::string id, std::string addr, uint16_t port); + virtual bool setNetworkMode(std::string id, uint32_t netMode); + virtual bool setVisState(std::string id, uint32_t mode); + + virtual void getIPServersList(std::list& ip_servers) ; + virtual void allowServerIPDetermination(bool) ; + virtual bool getAllowServerIPDetermination() ; + + /* Auth Stuff */ + virtual std::string GetRetroshareInvite(); + + virtual bool LoadCertificateFromFile(std::string fname, std::string &id); + virtual bool LoadCertificateFromString(std::string cert, std::string &id); + virtual bool SaveCertificateToFile(std::string id, std::string fname); + virtual std::string SaveCertificateToString(std::string id); + + virtual bool AuthCertificate(std::string id, std::string code); + virtual bool SignCertificate(std::string id); + virtual bool TrustCertificate(std::string id, bool trust); + +private: + + p3ConnectMgr *mConnMgr; + p3AuthMgr *mAuthMgr; +}; + +#endif diff --git a/libretroshare/src/_rsserver/p3photo.cc b/libretroshare/src/_rsserver/p3photo.cc new file mode 100644 index 000000000..6189c80b9 --- /dev/null +++ b/libretroshare/src/_rsserver/p3photo.cc @@ -0,0 +1,143 @@ +/* + * libretroshare/src/rsserver: p3photo.cc + * + * RetroShare C++ Interface. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#include "_rsserver/p3photo.h" +#include "services/p3photoservice.h" + +RsPhoto *rsPhoto = NULL; + + +RsPhotoDetails::RsPhotoDetails() +{ + return; +} + +RsPhotoShowDetails::RsPhotoShowDetails() +{ + return; +} + +p3Photo::p3Photo(p3PhotoService *p3ps) + :mPhoto(p3ps) +{ + return; +} + +p3Photo::~p3Photo() +{ + return; +} + + /* needs update? */ +bool p3Photo::updated() +{ + return mPhoto->updated(); +} + + /* access data */ +bool p3Photo::getPhotoList(std::string id, std::list &hashs) +{ + return mPhoto->getPhotoList(id, hashs); +} + +bool p3Photo::getShowList(std::string id, std::list &showIds) +{ + return mPhoto -> getShowList(id, showIds); +} + + +bool p3Photo::getShowDetails(std::string id, std::string showId, RsPhotoShowDetails &detail) +{ + return mPhoto -> getShowDetails(id, showId, detail); +} + + +bool p3Photo::getPhotoDetails(std::string id, std::string photoId, RsPhotoDetails &detail) +{ + return mPhoto -> getPhotoDetails(id, photoId, detail); +} + + + /* add / delete */ +std::string p3Photo::createShow(std::string name) +{ + return mPhoto -> createShow(name); +} + +bool p3Photo::deleteShow(std::string showId) +{ + return mPhoto -> deleteShow(showId); +} + +bool p3Photo::addPhotoToShow(std::string showId, std::string photoId, int16_t index) +{ + return mPhoto -> addPhotoToShow(showId, photoId, index); +} + +bool p3Photo::movePhotoInShow(std::string showId, std::string photoId, int16_t index) +{ + return mPhoto -> movePhotoInShow(showId, photoId, index); +} + +bool p3Photo::removePhotoFromShow(std::string showId, std::string photoId) +{ + return mPhoto -> removePhotoFromShow(showId, photoId); +} + + +std::string p3Photo::addPhoto(std::string path) /* add from file */ +{ + return mPhoto -> addPhoto(path); /* add from file */ +} + +bool p3Photo::addPhoto(std::string srcId, std::string photoId) /* add from peers photos */ +{ + return mPhoto -> addPhoto(srcId, photoId); /* add from peers photos */ + +} + +bool p3Photo::deletePhoto(std::string photoId) +{ + return mPhoto -> deletePhoto(photoId); +} + + + /* modify properties (TODO) */ +bool p3Photo::modifyShow(std::string showId, std::wstring name, std::wstring comment) +{ + return mPhoto -> modifyShow(showId, name, comment); +} + +bool p3Photo::modifyPhoto(std::string photoId, std::wstring name, std::wstring comment) +{ + return mPhoto -> modifyPhoto(photoId, name, comment); +} + +bool p3Photo::modifyShowComment(std::string showId, std::string photoId, std::wstring comment) +{ + return mPhoto -> modifyShowComment(showId, photoId, comment); +} + + diff --git a/libretroshare/src/_rsserver/p3photo.h b/libretroshare/src/_rsserver/p3photo.h new file mode 100644 index 000000000..df29f0129 --- /dev/null +++ b/libretroshare/src/_rsserver/p3photo.h @@ -0,0 +1,70 @@ +#ifndef P3PHOTO_H +#define P3PHOTO_H + +/* + * libretroshare/src/rsserver: p3photo.h + * + * RetroShare C++ Interface. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#include "_rsiface/rsphoto.h" +#include "services/p3photoservice.h" + +class p3Photo: public RsPhoto +{ +public: + + p3Photo(p3PhotoService *p3ps); + virtual ~p3Photo(); + + /* changed? */ + virtual bool updated(); + + /* access data */ + virtual bool getPhotoList(std::string id, std::list &hashs); + virtual bool getShowList(std::string id, std::list &showIds); + virtual bool getShowDetails(std::string id, std::string showId, RsPhotoShowDetails &detail); + virtual bool getPhotoDetails(std::string id, std::string photoId, RsPhotoDetails &detail); + + /* add / delete */ + virtual std::string createShow(std::string name); + virtual bool deleteShow(std::string showId); + virtual bool addPhotoToShow(std::string showId, std::string photoId, int16_t index); + virtual bool movePhotoInShow(std::string showId, std::string photoId, int16_t index); + virtual bool removePhotoFromShow(std::string showId, std::string photoId); + + virtual std::string addPhoto(std::string path); /* add from file */ + virtual bool addPhoto(std::string srcId, std::string photoId); /* add from peers photos */ + virtual bool deletePhoto(std::string photoId); + + /* modify properties (TODO) */ + virtual bool modifyShow(std::string showId, std::wstring name, std::wstring comment); + virtual bool modifyPhoto(std::string photoId, std::wstring name, std::wstring comment); + virtual bool modifyShowComment(std::string showId, std::string photoId, std::wstring comment); + +private: + + p3PhotoService *mPhoto; +}; + +#endif // P3PHOTO_H + diff --git a/libretroshare/src/_rsserver/p3rank.cc b/libretroshare/src/_rsserver/p3rank.cc new file mode 100644 index 000000000..09b034bfa --- /dev/null +++ b/libretroshare/src/_rsserver/p3rank.cc @@ -0,0 +1,104 @@ +/* + * libretroshare/src/rsserver: p3rank.cc + * + * RetroShare C++ Interface. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#include ":_rsserver/p3rank.h" + +RsRanks *rsRanks = NULL; + +p3Rank::p3Rank(p3Ranking *ranking) + :mRank(ranking) +{ + return; +} + +p3Rank::~p3Rank() +{ + return; +} + /* needs update? */ +bool p3Rank::updated() +{ + return mRank->updated(); +} + + /* Set Sort Methods */ +bool p3Rank::setSortPeriod(uint32_t period) +{ + return mRank->setSortPeriod(period); +} + +bool p3Rank::setSortMethod(uint32_t type) +{ + return mRank->setSortMethod(type); +} + +bool p3Rank::clearPeerFilter() +{ + return mRank->clearPeerFilter(); +} + +bool p3Rank::setPeerFilter(std::list peers) +{ + return mRank->setPeerFilter(peers); +} + + /* get Ids */ +uint32_t p3Rank::getRankingsCount() +{ + return mRank->getRankingsCount(); +} + +float p3Rank::getMaxRank() +{ + return mRank->getMaxRank(); +} + +bool p3Rank::getRankings(uint32_t first, uint32_t count, std::list &rids) +{ + return mRank->getRankings(first, count, rids); +} + +bool p3Rank::getRankDetails(std::string rid, RsRankDetails &details) +{ + return mRank->getRankDetails(rid, details); +} + + + /* Add New Comment / Msg */ +std::string p3Rank::newRankMsg(std::wstring link, std::wstring title, std::wstring comment, int32_t score) +{ + return mRank->newRankMsg(link, title, comment, score); +} + +bool p3Rank::updateComment(std::string rid, std::wstring comment, int32_t score) +{ + return mRank->updateComment(rid, comment, score); +} + +std::string p3Rank::anonRankMsg(std::string rid, std::wstring link, std::wstring title) +{ + return mRank->anonRankMsg(rid, link, title); +} + diff --git a/libretroshare/src/_rsserver/p3rank.h b/libretroshare/src/_rsserver/p3rank.h new file mode 100644 index 000000000..03b7751c5 --- /dev/null +++ b/libretroshare/src/_rsserver/p3rank.h @@ -0,0 +1,64 @@ +#ifndef RETROSHARE_P3_RANKING_INTERFACE_H +#define RETROSHARE_P3_RANKING_INTERFACE_H + +/* + * libretroshare/src/rsserver: p3rank.h + * + * RetroShare C++ Interface. + * + * Copyright 2007-2008 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#include "_rsiface/rsrank.h" +#include "services/p3ranking.h" + +class p3Rank: public RsRanks +{ +public: + + p3Rank(p3Ranking *ranking); + virtual ~p3Rank(); + + /* needs update? */ + virtual bool updated(); + + /* Set Sort Methods */ + virtual bool setSortPeriod(uint32_t period); + virtual bool setSortMethod(uint32_t type); + virtual bool clearPeerFilter(); + virtual bool setPeerFilter(std::list peers); + + /* get Ids */ + virtual uint32_t getRankingsCount(); + virtual float getMaxRank(); + virtual bool getRankings(uint32_t first, uint32_t count, std::list &rids); + virtual bool getRankDetails(std::string rid, RsRankDetails &details); + + /* Add New Comment / Msg */ + virtual std::string newRankMsg(std::wstring link, std::wstring title, std::wstring comment, int32_t score); + virtual bool updateComment(std::string rid, std::wstring comment, int32_t score); + virtual std::string anonRankMsg(std::string rid, std::wstring link, std::wstring title); + +private: + + p3Ranking *mRank; +}; + +#endif diff --git a/libretroshare/src/_rsserver/rsserver.cc b/libretroshare/src/_rsserver/rsserver.cc new file mode 100644 index 000000000..344d18cbc --- /dev/null +++ b/libretroshare/src/_rsserver/rsserver.cc @@ -0,0 +1,429 @@ +/* + * "$Id: p3face-msgs.cc,v 1.7 2007-05-05 16:10:06 rmf24 Exp $" + * + * RetroShare C++ Interface. + * + * Copyright 2004-2006 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +#include "_rsserver/rsserver.h" +#include "_commonfuncs/getcurrentts.h" +#include "util/rsdir.h" + +#include +#include + +#include "util/rsdebug.h" + + +#include +#include + +// CHANGED: DELETED : reason-> never used in any project; +//const int p3facemsgzone = 11453; + +void RsServer::lockRsCore() +{ + // std::cerr << "RsServer::lockRsCore()" << std::endl; + coreMutex.lock(); +} + +void RsServer::unlockRsCore() +{ + // std::cerr << "RsServer::unlockRsCore()" << std::endl; + coreMutex.unlock(); +} + + /* Flagging Persons / Channels / Files in or out of a set (CheckLists) */ +int RsServer::ClearInChat() +{ + lockRsCore(); /* LOCK */ + + mInChatList.clear(); + + unlockRsCore(); /* UNLOCK */ + + return 1; +} + + +/* Flagging Persons / Channels / Files in or out of a set (CheckLists) */ +int RsServer::SetInChat(std::string id, bool in) /* friend : chat msgs */ +{ + /* so we send this.... */ + lockRsCore(); /* LOCK */ + + //std::cerr << "Set InChat(" << id << ") to " << (in ? "True" : "False") << std::endl; + std::list::iterator it; + it = std::find(mInChatList.begin(), mInChatList.end(), id); + if (it == mInChatList.end()) + { + if (in) + { + mInChatList.push_back(id); + } + } + else + { + if (!in) + { + mInChatList.erase(it); + } + } + + unlockRsCore(); /* UNLOCK */ + + return 1; +} + + +int RsServer::ClearInMsg() +{ + lockRsCore(); /* LOCK */ + + mInMsgList.clear(); + + unlockRsCore(); /* UNLOCK */ + + return 1; +} + + +int RsServer::SetInMsg(std::string id, bool in) /* friend : msgs */ +{ + /* so we send this.... */ + lockRsCore(); /* LOCK */ + + //std::cerr << "Set InMsg(" << id << ") to " << (in ? "True" : "False") << std::endl; + std::list::iterator it; + it = std::find(mInMsgList.begin(), mInMsgList.end(), id); + if (it == mInMsgList.end()) + { + if (in) + { + mInMsgList.push_back(id); + } + } + else + { + if (!in) + { + mInMsgList.erase(it); + } + } + + unlockRsCore(); /* UNLOCK */ + return 1; +} + +bool RsServer::IsInChat(std::string id) /* friend : chat msgs */ +{ + /* so we send this.... */ + lockRsCore(); /* LOCK */ + + std::list::iterator it; + it = std::find(mInChatList.begin(), mInChatList.end(), id); + bool inChat = (it != mInChatList.end()); + + unlockRsCore(); /* UNLOCK */ + + return inChat; +} + + +bool RsServer::IsInMsg(std::string id) /* friend : msg recpts*/ +{ + /* so we send this.... */ + lockRsCore(); /* LOCK */ + + std::list::iterator it; + it = std::find(mInMsgList.begin(), mInMsgList.end(), id); + bool inMsg = (it != mInMsgList.end()); + + unlockRsCore(); /* UNLOCK */ + + return inMsg; +} + + + + +int RsServer::ClearInBroadcast() +{ + return 1; +} + +int RsServer::ClearInSubscribe() +{ + return 1; +} + +int RsServer::SetInBroadcast(std::string id, bool in) /* channel : channel broadcast */ +{ + return 1; +} + +int RsServer::SetInSubscribe(std::string id, bool in) /* channel : subscribed channels */ +{ + return 1; +} + +int RsServer::ClearInRecommend() +{ + /* find in people ... set chat flag */ + RsIface &iface = getIface(); + iface.lockData(); /* LOCK IFACE */ + + std::list &recs = iface.mRecommendList; + std::list::iterator it; + + for(it = recs.begin(); it != recs.end(); it++) + { + it -> inRecommend = false; + } + + iface.unlockData(); /* UNLOCK IFACE */ + + return 1; +} + + +int RsServer::SetInRecommend(std::string id, bool in) /* file : recommended file */ +{ + /* find in people ... set chat flag */ + RsIface &iface = getIface(); + iface.lockData(); /* LOCK IFACE */ + + std::list &recs = iface.mRecommendList; + std::list::iterator it; + + for(it = recs.begin(); it != recs.end(); it++) + { + if (it -> fname == id) + { + /* set flag */ + it -> inRecommend = in; + //std::cerr << "Set InRecommend (" << id << ") to " << (in ? "True" : "False") << std::endl; + } + } + + iface.unlockData(); /* UNLOCK IFACE */ + + return 1; +} + +std::string make_path_unix(std::string path) +{ + for(unsigned int i = 0; i < path.length(); i++) + { + if (path[i] == '\\') + path[i] = '/'; + } + return path; +} + + /* Thread Fn: Run the Core */ +void RsServer::run() +{ + + double timeDelta = 0.25; + double minTimeDelta = 0.1; // 25; + double maxTimeDelta = 0.5; + double kickLimit = 0.15; + + double avgTickRate = timeDelta; + + double lastts, ts; + lastts = ts = getCurrentTS(); + + long lastSec = 0; /* for the slower ticked stuff */ + + int min = 0; + int loop = 0; + + while(1) + { +#ifndef WINDOWS_SYS + usleep((int) (timeDelta * 1000000)); +#else + Sleep((int) (timeDelta * 1000)); +#endif + + ts = getCurrentTS(); + double delta = ts - lastts; + + /* for the fast ticked stuff */ + if (delta > timeDelta) + { +#ifdef DEBUG_TICK + std::cerr << "Delta: " << delta << std::endl; + std::cerr << "Time Delta: " << timeDelta << std::endl; + std::cerr << "Avg Tick Rate: " << avgTickRate << std::endl; +#endif + + lastts = ts; + +/******************************** RUN SERVER *****************/ + lockRsCore(); + + int moreToTick = ftserver -> tick(); + +#ifdef DEBUG_TICK + std::cerr << "RsServer::run() ftserver->tick(): moreToTick: " << moreToTick << std::endl; +#endif + + unlockRsCore(); + + /* tick the connection Manager */ + mConnMgr->tick(); +/******************************** RUN SERVER *****************/ + + /* adjust tick rate depending on whether there is more. + */ + + avgTickRate = 0.2 * timeDelta + 0.8 * avgTickRate; + + if (1 == moreToTick) + { + timeDelta = 0.9 * avgTickRate; + if (timeDelta > kickLimit) + { + /* force next tick in one sec + * if we are reading data. + */ + timeDelta = kickLimit; + avgTickRate = kickLimit; + } + } + else + { + timeDelta = 1.1 * avgTickRate; + } + + /* limiter */ + if (timeDelta < minTimeDelta) + { + timeDelta = minTimeDelta; + } + else if (timeDelta > maxTimeDelta) + { + timeDelta = maxTimeDelta; + } + + /* Fast Updates */ + + + /* now we have the slow ticking stuff */ + /* stuff ticked once a second (but can be slowed down) */ + if ((int) ts > lastSec) + { + lastSec = (int) ts; + + // Every second! (UDP keepalive). + tou_tick_stunkeepalive(); + + // every five loops (> 5 secs) + if (loop % 5 == 0) + { + // update_quick_stats(); + + // Update All Every 5 Seconds. + // These Update Functions do the locking themselves. +#ifdef DEBUG_TICK + std::cerr << "RsServer::run() Updates()" << std::endl; +#endif + + // These two have been completed! + //std::cerr << "RsServer::run() UpdateAllCerts()" << std::endl; + //UpdateAllCerts(); + //std::cerr << "RsServer::run() UpdateAllNetwork()" << std::endl; + //UpdateAllNetwork(); + + // currently Dummy Functions. + //std::cerr << "RsServer::run() UpdateAllTransfers()" << std::endl; + + //std::cerr << "RsServer::run() "; + //std::cerr << "UpdateRemotePeople()"<tick(); + + + if(mQblog) + mQblog->tick(); + + + +#if 0 + std::string opt; + std::string val = "VALUE"; + { + std::ostringstream out; + out << "SEC:" << lastSec; + opt = out.str(); + } + + mGeneralConfig->setSetting(opt, val); +#endif + + mConfigMgr->tick(); /* saves stuff */ + + } + + // every 60 loops (> 1 min) + if (++loop >= 60) + { + loop = 0; + + /* force saving FileTransferStatus TODO */ + //ftserver->saveFileTransferStatus(); + + /* see if we need to resave certs */ + mAuthMgr->CheckSaveCertificates(); + + /* hour loop */ + if (++min >= 60) + { + min = 0; + } + } + + // slow update tick as well. + // update(); + } // end of slow tick. + + } // end of only once a second. + } + return; +} diff --git a/libretroshare/src/_rsserver/rsserver.h b/libretroshare/src/_rsserver/rsserver.h new file mode 100644 index 000000000..6b64cef96 --- /dev/null +++ b/libretroshare/src/_rsserver/rsserver.h @@ -0,0 +1,181 @@ +#ifndef RSSERVER_H +#define RSSERVER_H + +/* + * "$Id: p3face.h,v 1.9 2007-05-05 16:10:06 rmf24 Exp $" + * + * RetroShare C++ Interface. + * + * Copyright 2004-2006 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + +//#include "server/filedexserver.h" +#include "ft/ftserver.h" +//#include "pqi/pqissl.h" + +#include "pqi/p3cfgmgr.h" +#include "pqi/p3connmgr.h" +#include "pqi/pqipersongrp.h" + +#include "_rsiface/rsiface.h" +#include "_rsiface/rstypes.h" +#include "util/rsthreads.h" + +#include "services/p3disc.h" +#include "services/p3msgservice.h" +#include "services/p3chatservice.h" +#include "services/p3ranking.h" +#include "services/p3Qblog.h" + +/* The Main Interface Class - for controlling the server */ + +/* The init functions are actually Defined in p3face-startup.cc + */ +//RsInit *InitRsConfig(); +//void CleanupRsConfig(RsInit *); +//int InitRetroShare(int argc, char **argv, RsInit *config); +//int LoadCertificates(RsInit *config); + +RsControl *createRsControl(RsIface &iface, NotifyBase ¬ify); + + +class RsServer: public RsControl, public RsThread +{ +public: + /****************************************/ + /* p3face-startup.cc: init... */ + virtual int StartupRetroShare(); + + public: + /****************************************/ + /* p3face.cc: main loop / util fns / locking. */ + + RsServer(RsIface &i, NotifyBase &callback); + virtual ~RsServer(); + + /* Thread Fn: Run the Core */ + virtual void run(); + +public: // no longer private:!!! + /* locking stuff */ + void lockRsCore(); + + void unlockRsCore(); + +private: + + /* mutex */ + RsMutex coreMutex; + + /* General Internal Helper Functions + (Must be Locked) + */ +#if 0 + cert *intFindCert(RsCertId id); + RsCertId intGetCertId(cert *c); +#endif + + /****************************************/ + /****************************************/ + /* p3face-msg Operations */ + +public: + virtual const std::string& certificateFileName() ; + + /* Flagging Persons / Channels / Files in or out of a set (CheckLists) */ + virtual int SetInChat(std::string id, bool in); /* friend : chat msgs */ + virtual int SetInMsg(std::string id, bool in); /* friend : msg receipients */ + virtual int SetInBroadcast(std::string id, bool in); /* channel : channel broadcast */ + virtual int SetInSubscribe(std::string id, bool in); /* channel : subscribed channels */ + virtual int SetInRecommend(std::string id, bool in); /* file : recommended file */ + virtual int ClearInChat(); + virtual int ClearInMsg(); + virtual int ClearInBroadcast(); + virtual int ClearInSubscribe(); + virtual int ClearInRecommend(); + + virtual bool IsInChat(std::string id); /* friend : chat msgs */ + virtual bool IsInMsg(std::string id); /* friend : msg recpts*/ + + +private: + + std::list mInChatList, mInMsgList; + + void initRsMI(RsMsgItem *msg, MessageInfo &mi); + + /****************************************/ + /****************************************/ + /****************************************/ +public: + /* Config */ + + virtual int ConfigGetDataRates(float &inKb, float &outKb); + virtual int ConfigSetDataRates( int totalDownload, int totalUpload ); + virtual int ConfigSetBootPrompt( bool on ); + + virtual void ConfigFinalSave( ); + /************* Rs shut down function: in upnp 'port lease time' bug *****************/ + + /** + * This function is responsible for ensuring Retroshare exits in a legal state: + * i.e. releases all held resources and saves current configuration + */ + virtual void rsGlobalShutDown( ); +private: + int UpdateAllConfig(); + + /****************************************/ +private: + + // The real Server Parts. + //filedexserver *server; + ftServer *ftserver; + + p3ConnectMgr *mConnMgr; + p3AuthMgr *mAuthMgr; + + pqipersongrp *pqih; + + //sslroot *sslr; + + /* services */ + p3disc *ad; + p3MsgService *msgSrv; + p3ChatService *chatSrv; + + /* caches (that need ticking) */ + p3Ranking *mRanking; + p3Qblog *mQblog; + + /* Config */ + p3ConfigMgr *mConfigMgr; + p3GeneralConfig *mGeneralConfig; + + // Worker Data..... +}; + +/* Helper function to convert windows paths + * into unix (ie switch \ to /) for FLTK's file chooser + */ + +std::string make_path_unix(std::string winpath); + +#endif // RSSERVER_H diff --git a/libretroshare/src/_rsserver/rsserver.pri b/libretroshare/src/_rsserver/rsserver.pri index d18a1a735..86cd0428b 100644 --- a/libretroshare/src/_rsserver/rsserver.pri +++ b/libretroshare/src/_rsserver/rsserver.pri @@ -1,10 +1,26 @@ INCLUDEPATH += $$PWD \ ../$$PWP DEPENDPATH += $$PWD -HEADERS = $$PWP/p3face.h \ - $$PWP/p3blog.h \ - $$PWP/p3discovery.h -SOURCES += p3face.cc \ - $$PWP/p3blog.cc \ - $$PWP/p3discovery.cc +HEADERS = $$PWP/p3face.h \ + $$PWP/p3blog.h \ + $$PWP/p3discovery.h \ + rsserver.h \ + p3files.h \ + p3msgs.h \ + p3peers.h \ + p3photo.h \ + p3rank.h +SOURCES += $$PWP/p3blog.cc \ + $$PWP/p3discovery.cc \ + $$PWP/p3face-config.cc \ + rsserver.cc \ + p3face-msgs.cc \ + p3face-server.cc \ + p3face-startup.cc \ + p3msgs.cc \ + p3peers.cc \ + p3photo.cc \ + p3rank.cc \ + testrschanid.cc + diff --git a/libretroshare/src/_rsserver/testrschanid.cc b/libretroshare/src/_rsserver/testrschanid.cc new file mode 100644 index 000000000..220abe8aa --- /dev/null +++ b/libretroshare/src/_rsserver/testrschanid.cc @@ -0,0 +1,59 @@ + +/* + * "$Id: testRsChanId.cc,v 1.1 2007-02-19 20:08:30 rmf24 Exp $" + * + * RetroShare C++ Interface. + * + * Copyright 2004-2007 by Robert Fernie. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License Version 2 as published by the Free Software Foundation. + * + * This library 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 + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 + * USA. + * + * Please report all bugs and problems to "retroshare@lunamutt.com". + * + */ + + + +#include "_rsiface/rstypes.h" +#include +#include +#include + +int main() +{ + RsCertId id; + + int i; + for(i = 0; i < 16; i++) + { + id.data[i] = i+121; + } + + std::cerr << "Cert Id: " << id << std::endl; + + std::ostringstream out; + out << id; + std::string idstr = out.str(); + + std::cerr << "Cert Id (str): " << idstr << std::endl; + + RsCertId id2(idstr); + + std::cerr << "Cert Id2 (from str): " << id2 << std::endl; + return 1; +} + + + diff --git a/libretroshare/src/libretroshare.pro b/libretroshare/src/libretroshare.pro index d8605fb07..fecbfa7a8 100644 --- a/libretroshare/src/libretroshare.pro +++ b/libretroshare/src/libretroshare.pro @@ -1,5 +1,9 @@ include(_rsiface/rsiface.pri) include(_rsserver/rsserver.pri) +include(_commonfuncs/commonfuncs.pri) +include(_dht/dht.pri) +include(_pqi/pqi.pri) + TEMPLATE = lib CONFIG += static TARGET = retroshare diff --git a/libretroshare/src/pqi/pqipersongrp.h b/libretroshare/src/pqi/pqipersongrp.h index ddfca87f7..b261c7571 100644 --- a/libretroshare/src/pqi/pqipersongrp.h +++ b/libretroshare/src/pqi/pqipersongrp.h @@ -85,7 +85,7 @@ virtual pqiperson *createPerson(std::string id, pqilistener *listener) = 0; /* Overloaded RsItem Check * checks item->cid vs Person */ -virtual int checkOutgoingRsItem(RsItem *item, int global) { return 1; } +virtual int checkOutgoingRsItem(RsItem *item, int global) { (void)item; (void)global; return 1; } private: