merged with upstream

This commit is contained in:
csoler 2016-02-10 00:00:21 -05:00
commit 3db3ccf636
185 changed files with 61045 additions and 37839 deletions

View File

@ -55,6 +55,9 @@ GXS
VOIP
H [ ] use proper video encoding. What we have now is decent for video, but sound should be prioritized. Experiments
with QtAV seem to work nicely. Finish and integrate!
M [ ] Deactivate Voip Buttons, when Friend has no Voip plugin enabled.
M [ ] Implement Voice for Video Chat
M [ ] Improve Voice and Video Quality
M [ ] Video Quality/Resolution Settings (High, Medium, Low) HD, HQ, SD )
M [ ] Video Device: WebCam(s) or Desktop Selection
M [ ] Audio Input Device Selection (Microphone)
@ -68,6 +71,7 @@ VOIP
Messages
H [X] make the mail system re-send failed emails notified by the global router. This is hard because it needs a proper management of duplicate messages
E [X] add flags to allow distant messaging from contact list only / everyone / noone / only signed ids.
M [ ] add Signature feature to rs messages
Chat
E [X] add flags to allow distant chat from contact list only / everyone / noone / only signed ids.

View File

@ -1,5 +1,137 @@
retroshare06 (0.6.0-1.XXXXXX~YYYYYY) YYYYYY; urgency=low
a41d9df csoler Mon, 1 Feb 2016 09:59:13 -0500 fixed small bug in probability computation in grouter
6d1a393 csoler Mon, 1 Feb 2016 00:33:11 -0500 fixed but in re-sending of failed grouter items
aa194ca csoler Sun, 31 Jan 2016 20:27:53 -0500 fixed bug preventing save of routage info in distant messaging
a85b5d2 csoler Sat, 30 Jan 2016 20:35:08 -0500 re-enabled GRouter tunnels (disabled for testing). Removed debug output.
f0a49a4 csoler Sat, 30 Jan 2016 20:27:56 -0500 changed global router routing strategy. Should be more effective now.
59d4c2c csoler Sat, 30 Jan 2016 20:27:27 -0500 removed some compilation warnings
3cfd976 thunder2 Fri, 29 Jan 2016 16:23:28 +0100 Added Windows installer script for Qt5.
58e59d1 csoler Thu, 28 Jan 2016 20:19:44 -0500 added sounds to chat lobbies (patch fromManuel Davis)
8dde723 thunder2 Thu, 28 Jan 2016 16:20:11 +0100 Added security hardening flags for ASLR and DEP protection for Windows compile.
85cdfcc csoler Thu, 28 Jan 2016 10:44:37 -0500 fixed bug causing multi-tunneling not to be used (found by jo)
b1f165f csoler Thu, 28 Jan 2016 10:22:32 -0500 added sound event to lobbies (patch from Manuel Davis)
3bc444b csoler Tue, 26 Jan 2016 23:00:10 -0500 removed some debug info
af770fd csoler Tue, 26 Jan 2016 22:46:07 -0500 fixed messagebox to remember which from ID was used last time
749ca08 csoler Tue, 26 Jan 2016 22:30:04 -0500 slightly improved message shown over lobby names
f063e5b csoler Tue, 26 Jan 2016 22:16:45 -0500 Allow main window to resize to much smaller size when needed. Should help people with
2072ca4 csoler Tue, 26 Jan 2016 22:08:17 -0500 fixed bug in getPeerDetails causing callstacks to be displayed for non initialised IP
b70057a csoler Tue, 26 Jan 2016 18:50:33 -0500 removed sending probability in GXS since it is not justified anymore. This should fix
39b3df9 csoler Mon, 25 Jan 2016 22:39:10 -0500 fixed bug causing net reset when closing config
49e2ee1 csoler Mon, 25 Jan 2016 21:45:58 -0500 Merge pull request #247 from heini/stretch_qt5
2f3350f electron128 Sun, 24 Jan 2016 19:56:53 +0100 Merge pull request #248 from heini/sqlcipher_needs_fpic
f13c81b csoler Sat, 23 Jan 2016 13:17:12 -0500 Merge pull request #258 from PhenomRetroShare/Fix_QuoteLinesWithImage
9b64b96 csoler Sat, 23 Jan 2016 13:03:29 -0500 fixed potential crash in pqisslstore
1d2be23 Phenom Sat, 23 Jan 2016 18:17:49 +0100 Fix Quote Lines With Image
70bf938 defnax Sat, 23 Jan 2016 13:37:08 +0100 reduced the default width & height reorder in MessagePage, move Distant Message box to the top.
fc0067f csoler Fri, 22 Jan 2016 22:06:31 -0500 fixed bug in network graph search sizes
c428739 csoler Fri, 22 Jan 2016 21:32:35 -0500 cleaned the network graph a little bit. Removed text, updated bounding boxes, removed background
b362544 csoler Fri, 22 Jan 2016 09:31:40 -0500 fixed compilation
b3df4c1 csoler Thu, 21 Jan 2016 23:55:22 -0500 made the Global router stats widget more efficient/compact/explicit
449aba9 csoler Thu, 21 Jan 2016 22:44:48 -0500 fixed compilation of SearchDialog.cpp
94b5868 csoler Thu, 21 Jan 2016 21:49:52 -0500 moved SearchDialog into FileTransfer/
6a32da2 csoler Thu, 21 Jan 2016 21:40:48 -0500 removed explicit size constraint on listview for config page (screws up the view in HDPI screens
55d0a21 csoler Thu, 21 Jan 2016 21:19:40 -0500 added cache of latest GXS tunnel data items for the last 10 minutes in order to avoid replays of
9347b86 csoler Thu, 21 Jan 2016 11:48:41 -0500 new simple solution for sound on linux based on using system sound player. To be tested.
9999742 csoler Thu, 21 Jan 2016 11:32:17 -0500 reverted commit for phonon since phonon is deprecated. Will be replaced by qtmultimedia in
7488ba1 csoler Wed, 20 Jan 2016 23:56:22 -0500 removed feedback from messages to mGrpServerUpdateTS, which is now only updated when the subscri
c473200 csoler Wed, 20 Jan 2016 23:34:25 -0500 moved getCurrentTS() inside RTT packet sending loop (suggestion from Jo)
e25787b csoler Wed, 20 Jan 2016 23:25:08 -0500 fixed sound on linux using phonon. This should be extensible to all unix systems
fc3606c csoler Wed, 20 Jan 2016 14:02:13 -0500 fixed DHT icon size problem
9063612 csoler Wed, 20 Jan 2016 11:19:36 -0500 fixed utf8 issue in ChatWidget. To be tested.
c597c8c csoler Tue, 19 Jan 2016 23:19:46 -0500 removed explicit spacing sizes in plugins page
3203249 csoler Tue, 19 Jan 2016 22:59:11 -0500 fixed size of help icons in MainPage class
597f541 csoler Tue, 19 Jan 2016 22:44:27 -0500 added 2 icons
3d58f9b csoler Tue, 19 Jan 2016 22:35:58 -0500 added correct icons in ToasterStatus
b382c3e csoler Tue, 19 Jan 2016 22:16:25 -0500 fixed icon sizes in peerstatus/statusbar
a2d8cc8 csoler Tue, 19 Jan 2016 22:01:26 -0500 fixed DHT status icon sizes and added tooltip
37204d7 csoler Tue, 19 Jan 2016 21:46:22 -0500 fixed icon in NewsFeed, added missing spacer in IdDialog
49c1d56 csoler Tue, 19 Jan 2016 21:45:55 -0500 increased GXS post size limit to just below 200K
1471979 csoler Tue, 19 Jan 2016 18:08:47 -0500 added a few tooltips in Tor configuration panel
43ee506 csoler Tue, 19 Jan 2016 10:13:24 -0500 added automatic GXS message rejection when item size exceeds 200K. Should fix the forums that go
dedd6d4 csoler Mon, 18 Jan 2016 23:53:54 -0500 disabled debug info
68a0395 csoler Mon, 18 Jan 2016 23:53:06 -0500 fixed a few bugs in existing msg fragmentation code. Signature checking still not working, not N
2b52456 defnax Mon, 18 Jan 2016 13:36:38 +0100 Added new iconset for Voip, by Beluga
39e6a9b csoler Sat, 16 Jan 2016 20:44:52 -0500 fixed up People context menu so as to handle actions for multiple persons at once
1edfcf9 csoler Sat, 16 Jan 2016 13:41:24 -0500 do not time stamp banned GXS ids
8296fa9 csoler Sat, 16 Jan 2016 11:30:15 -0500 added checkbox to toggle logscale in statistics
63b88ec defnax Sat, 16 Jan 2016 14:50:12 +0100 correct sorting for "Reputation" in People, patch by Eugene Tooms
-- Cyril Soler <csoler@users.sourceforge.net> Mon, 01 Feb 2016 20:00:00 +0100
retroshare06 (0.6.0-1.20160115.a34f66aa~trusty) trusty; urgency=low
0ff6349 thunder2 Fri, 15 Jan 2016 12:01:37 +0100 Fixed possibility of XXE injection in FeedReader plugin.
748147f thunder2 Fri, 15 Jan 2016 12:00:02 +0100 Fixed Windows compile.
b5f6059 Cyril Soler Fri, 15 Jan 2016 10:07:21 -0500 deprecated updateClientSyncTS() which is not needed anymore
c24447f csoler Thu, 14 Jan 2016 20:11:26 -0500 fixed update of mGrpClientUpdateMap when no new group is available, avoiding unnecessary GXS grp list traffic (patch from jolavillette)
3b18c43 csoler Wed, 13 Jan 2016 20:25:18 -0500 removed [dos] LF from rsgxsnetservice (causes merging rampage)
086b076 csoler Wed, 13 Jan 2016 12:22:55 -0500 fixed a few serialisation issues
96f3446 csoler Wed, 13 Jan 2016 11:13:23 -0500 added size limit to packet grouping
b56881e csoler Wed, 13 Jan 2016 10:23:21 -0500 fixed windows compilation
4916496 csoler Wed, 13 Jan 2016 10:20:51 -0500 Merge pull request #253 from csoler/v0.6-SecurityReview
2c019d9 csoler Wed, 13 Jan 2016 00:39:22 -0500 added load image option in forum posts when images are to be displayed
60408b3 csoler Wed, 13 Jan 2016 00:13:16 -0500 fixed a bug in GRouterGenericDataItem::duplicate()
2a8fc7f csoler Wed, 13 Jan 2016 00:08:27 -0500 hardened the restriction to image loading to avoid external resources in RSTextBrowser
d55993d csoler Tue, 12 Jan 2016 21:43:04 -0500 removed two instances of malloc(0) captured by new rs_malloc funtion
d13526f csoler Tue, 12 Jan 2016 21:10:11 -0500 added a new method rs_malloc that checks its arguments and prints a stacktrace on error/weird call.
Changed the code everywhere to use this instead of malloc. Removed some mallocs and replaced with RsTemporaryMemory
9c6e7df csoler Mon, 11 Jan 2016 23:49:00 -0500 added checks after mallocs in several files
46520b0 csoler Mon, 11 Jan 2016 20:49:26 -0500 fixed potential integer overflow / Out of bounds read in gxstunnelitems.cc
8e666fc csoler Mon, 11 Jan 2016 20:40:57 -0500 fixed potential integer overflow / Out of bounds read in rsturtleitems.cc
6e9d96e csoler Mon, 11 Jan 2016 20:26:19 -0500 fixed potential integer overflow / Out of bounds read in RsVOIPDataItem.cc
98f0c10 csoler Mon, 11 Jan 2016 19:26:54 -0500 fixed potential integer overflow / Out of bounds read in GRouterItems.cc
3094b52 csoler Mon, 11 Jan 2016 19:08:52 -0500 fixed potential integer overflow / Out of bounds read in rsbaseserial.cc. Also added a few more error output.
8e6998b electron128 Sun, 10 Jan 2016 14:34:08 +0100 removed redundant map _lobby_ids from DistributedChatService. The same information and more is stored in the _chat_lobbys map.
_lobby_ids is unused since commit 67e1495d9a78ac259649014355cd127a2febeaaf
09ed1ea electron128 Sun, 10 Jan 2016 14:22:06 +0100 removed getVirtualPeerId method from rsmsgs lobby interface. It is not neccesary anymore to have the virtual peer id exposed to the GUI layer.
67e1495 electron128 Sun, 10 Jan 2016 13:29:40 +0100 use ChatId instead of virtual peer id for chat lobby popup. Removed a now unused method from rsmsgs interface and DistributedChatService.
c3d422a csoler Sat, 9 Jan 2016 14:31:20 -0500 added some tooltips on keys and certificate details
994bfaf csoler Sat, 9 Jan 2016 13:54:24 -0500 updated TODO
e01b1a4 csoler Sat, 9 Jan 2016 11:00:57 -0500 Merge pull request #245 from csoler/v0.6-Messaging
ee84ab7 csoler Sat, 9 Jan 2016 10:58:49 -0500 fixed serialisation error (missing call) for received Distant msg hash map
b125cb1 electron128 Sat, 9 Jan 2016 12:09:43 +0100 fix the bug where a filter is applied in friends file list even if view mode is tree and search box is hidden. Problem was:
SharedFilesDialog::FilterItems() is called from multiple places. The check if we should filter or not is now in the filter function itself.
a118870 electron128 Sat, 9 Jan 2016 12:01:32 +0100 if file in friends file list is available locally or is being downloaded, then show it in red like in search. The color is hardcoded, because
it is not possible to style arbitrary QObjects with stylesheets. closes #195
9f4256c csoler Fri, 8 Jan 2016 23:19:45 -0500 Merge pull request #244 from csoler/v0.6-Messaging
fe02167 csoler Fri, 8 Jan 2016 23:18:45 -0500 disabled part of msg re-sending code in order to improve it later
56a844b csoler Fri, 8 Jan 2016 23:08:14 -0500 Merge pull request #243 from csoler/v0.6-Messaging
a540ffd csoler Fri, 8 Jan 2016 22:52:01 -0500 removed two debug outputs from MessageDialog
3f6964b csoler Fri, 8 Jan 2016 22:50:03 -0500 added back messages to sent box
75edb46 csoler Fri, 8 Jan 2016 20:48:47 -0500 added auto-resend of unsent messages. Fixed display of From field in outbox
0c591f0 csoler Thu, 7 Jan 2016 22:22:05 -0500 added auto re-send of distant messages after global router notified the message cannot be sent. Added a map n p3msgService to avoid
receiving multiple times the same message.
9651f43 csoler Thu, 7 Jan 2016 21:01:50 -0500 fixed wrong usage of local client ids in global router causing distant messages to stay in outbox forever.
81e2a59 defnax Thu, 7 Jan 2016 19:25:52 +0100 Fixing People Margins Update emotes file
4484b08 csoler Thu, 7 Jan 2016 00:04:52 -0500 cleaned up the problem of outgoing messages being shown with the from from field.
3d6fa0c csoler Wed, 6 Jan 2016 18:38:27 -0500 fixed bug causing turtle to keep asking for a tunnel after a distant chat is closed if not connected
61f8e73 csoler Wed, 6 Jan 2016 18:12:15 -0500 improved text of warning against pasting pgp keys in connect wizard
984ce2d csoler Wed, 6 Jan 2016 18:07:20 -0500 removed circles tab from IdDialog. Came from a difficult manual merging between dos and unix encoded files
7da2ad1 csoler Wed, 6 Jan 2016 10:31:59 -0500 re-enabled previously disabled code in rsgxsnetservice, that proved useful
6398b7b csoler Tue, 5 Jan 2016 23:00:26 -0500 added comment in rsgxsnetservice.cc
3fa8d86 csoler Tue, 5 Jan 2016 22:53:56 -0500 removed time-stamp-ing of messages on client side in locked_genReqMsgTransaction() as it is already handled when receiving messages,
and the need to stamp non subscribed groups is not justified anymore
678afe7 csoler Tue, 5 Jan 2016 22:27:00 -0500 fixed stupid mistake in previous commit (GXS transaction timestamp)
7b3fd53 csoler Tue, 5 Jan 2016 19:23:59 -0500 added correct timestamp in msg list response items for GXS. To be tested.
141f092 csoler Tue, 5 Jan 2016 14:22:27 -0500 added tooltip and fixed text in connect friend dialog
496546e defnax Tue, 5 Jan 2016 18:25:44 +0100 Merge branch 'master' of https://github.com/RetroShare/RetroShare
19011ba defnax Tue, 5 Jan 2016 18:23:43 +0100 clean up emotes, removed some unused. changed icons for emotes button. reduze the size of the emoticons
9fd0fc5 csoler Tue, 5 Jan 2016 11:43:50 -0500 fixed bandwidth measurement in pqistreamer
e6cd4a4 defnax Tue, 5 Jan 2016 16:09:14 +0100 Merge pull request #240 from sehraf/pr-smiley-whitespace
54f9912 sehraf Tue, 5 Jan 2016 14:58:41 +0100 Add whitespaces around smileys. Only replace smileys with an image when they are surrounded by whitespaces.
This fixes smileys in links and other text that happen to include the sequence for a smiley.
f1f111f csoler Mon, 4 Jan 2016 20:05:44 -0500 merged
e04b933 B.Cristea Mon, 4 Jan 2016 15:25:22 +0200 corrected compilation inst on openSUSE
fddc008 csoler Sun, 3 Jan 2016 17:31:22 -0500 merged with origin
3d5042b csoler Sun, 3 Jan 2016 14:29:33 -0500 Merge pull request #237 from G10h4ck/master
05fd33b Gio Sun, 3 Jan 2016 17:21:11 +0100 p3ServiceControl: Optimize checkFilter(...), solve memory leak removing mSerialiser, code cleanup
1082a8d csoler Sat, 2 Jan 2016 18:59:05 -0500 updated ubuntu changelog
-- Cyril Soler <csoler@users.sourceforge.net> Thu, 14 Jan 2016 20:00:00 +0100
retroshare06 (0.6.0-1.20160102.1082a8d1~trusty) trusty; urgency=low
4953324 electron128 Sat, 2 Jan 2016 14:53:24 +0100 Merge pull request #235 from PhenomRetroShare/Fix_MakeMACOS_PluginWorking
c5e6f62 Phenom Sat, 2 Jan 2016 14:19:53 +0100 Make Plugin working in Mac OSX.
b6b5f9c csoler Fri, 1 Jan 2016 22:36:07 -0500 fixed some of the issues reported by coverity scan (mainly uninitialised class members)

View File

@ -0,0 +1,44 @@
Source: retroshare06
Section: devel
Priority: standard
Maintainer: Cyril Soler <csoler@users.sourceforge.net>
Build-Depends: debhelper (>= 7), libglib2.0-dev, libupnp-dev, libssl-dev, libxss-dev, libgnome-keyring-dev, libbz2-dev, libspeex-dev, libspeexdsp-dev, libxslt1-dev, cmake, libcurl4-openssl-dev, libopencv-dev, tcl8.6, libsqlcipher-dev, libmicrohttpd-dev, libavcodec-dev, qtmultimedia5-dev, qttools5-dev, libqt5x11extras5-dev, qt5-default
Standards-Version: 3.9.6
Homepage: http://retroshare.sourceforge.net
Package: retroshare06-voip-plugin
Architecture: any
Depends: ${shlibs:Depends}, ${misc:Depends}, retroshare06, libspeex1, libspeexdsp1, libqt5multimedia5
Description: RetroShare VOIP plugin
This package provides a plugin for RetroShare, a secured Friend-to-Friend communication
plateform. The plugin adds voice-over-IP functionality to the private chat window. Both
friends chatting together need the plugin installed to be able to talk together.
Package: retroshare06-feedreader-plugin
Architecture: any
Depends: ${shlibs:Depends}, ${misc:Depends}, retroshare06
Description: RetroShare FeedReader plugin
This package provides a plugin for RetroShare, a secured Friend-to-Friend communication
plateform. The plugin adds a RSS feed reader tab to retroshare.
Package: retroshare06-nogui
Architecture: any
Depends: ${shlibs:Depends}, ${misc:Depends}, gnome-keyring
Conflicts: retroshare06
Description: Secure communication with friends
This is the command-line client for RetroShare network. This client
can be contacted and talked-to using SSL. Clients exist for portable
devices running e.g. Android.
Package: retroshare06
Architecture: any
Depends: ${shlibs:Depends}, ${misc:Depends}, gnome-keyring
Conflicts: retroshare06-nogui
Description: Secure communication with friends
RetroShare is a Open Source cross-platform, private and secure decentralised
commmunication platform. It lets you to securely chat and share files with your
friends and family, using a web-of-trust to authenticate peers and OpenSSL to
encrypt all communication. RetroShare provides filesharing, chat, messages,
forums and channels.

View File

@ -133,6 +133,9 @@ for i in ${dist}; do
cp ../control.squeeze_bubba3 debian/control
elif test "${i}" = "precise" ; then
cp ../control.precise debian/control
elif test "${i}" = "stretch" ; then
cp ../control.${i} debian/control
cp ../rules.${i} debian/rules
else
cp ../debian/control debian/control
fi

View File

@ -0,0 +1,61 @@
#!/usr/bin/make -f
configure: configure-stamp
configure-stamp:
dh_testdir
cd src && qmake "CONFIG-=debug" "CONFIG+=release" PREFIX=/usr LIB_DIR=/usr/lib RetroShare.pro
touch $@
build: build-stamp
build-stamp: configure-stamp
dh_testdir
# Add here commands to compile the package.
# cd libssh-0.6.4 && mkdir -p build && cd build && cmake -DWITH_STATIC_LIB=ON .. && make
# cd sqlcipher && ./configure --disable-shared --enable-static --enable-tempstore=yes CFLAGS="-DSQLITE_HAS_CODEC" LDFLAGS="-lcrypto" && make
# mkdir lib
# cp -r libssh-0.6.4 lib/
#cp -r sqlcipher lib/
#cd src/rsctrl/src && make
cd src && $(MAKE)
touch $@
clean:
dh_testdir
dh_testroot
rm -f configure-stamp build-stamp
# Add here commands to clean up after the build process.
[ ! -f src/Makefile ] || (cd src && $(MAKE) distclean)
dh_clean
install: build
dh_testdir
dh_testroot
dh_clean -k
#dh_installdirs
cd src && $(MAKE) INSTALL_ROOT=$(CURDIR)/debian/tmp install
# Build architecture-independent files here.
binary-indep: build install
# We have nothing to do by default.
# Build architecture-dependent files here.
binary-arch: build install
dh_testdir
dh_testroot
dh_install --list-missing
#dh_installdocs
#dh_installexamples
#dh_installman
dh_link
dh_strip
dh_compress
dh_fixperms
dh_installdeb
dh_shlibdeps
dh_gencontrol
dh_md5sums
dh_builddeb
binary: binary-indep binary-arch
.PHONY: build clean binary-indep binary-arch binary install configure

View File

@ -52,7 +52,7 @@ This package provides a plugin for RetroShare, a secured Friend-to-Friend commun
%build
cd lib/sqlcipher
./configure --disable-shared --enable-static --enable-tempstore=yes CFLAGS="-DSQLITE_HAS_CODEC" LDFLAGS="-lcrypto"
./configure --disable-shared --enable-static --enable-tempstore=yes CFLAGS="-fPIC -DSQLITE_HAS_CODEC" LDFLAGS="-lcrypto"
make
cd -
cd src

View File

@ -33,14 +33,7 @@ if errorlevel 1 goto exit
if "%Revision%"=="" (
echo.
echo Version not found in
echo %VersionFile%
goto exit
)
if "%BuildAdd%"=="" (
echo.
echo Version not found in
echo %VersionFile%
echo Version not found
goto exit
)

View File

@ -102,7 +102,7 @@ Var StyleSheetDir
!define MUI_COMPONENTSPAGE_SMALLDESC
!define MUI_FINISHPAGE_LINK "Visit the RetroShare forum for the latest news and support"
!define MUI_FINISHPAGE_LINK_LOCATION "http://retroshare.sourceforge.net/forum/"
!define MUI_FINISHPAGE_RUN "$INSTDIR\RetroShare.exe"
!define MUI_FINISHPAGE_RUN "$INSTDIR\RetroShare06.exe"
!define MUI_FINISHPAGE_SHOWREADME $INSTDIR\changelog.txt
!define MUI_FINISHPAGE_SHOWREADME_TEXT changelog.txt
!define MUI_FINISHPAGE_SHOWREADME_NOTCHECKED
@ -175,8 +175,8 @@ Section $(Section_Main) Section_Main
; Main binaries
SetOutPath "$INSTDIR"
File /oname=RetroShare.exe "${RELEASEDIR}\retroshare-gui\src\release\RetroShare06.exe"
File /oname=retroshare-nogui.exe "${RELEASEDIR}\retroshare-nogui\src\release\RetroShare06-nogui.exe"
File /oname=RetroShare06.exe "${RELEASEDIR}\retroshare-gui\src\release\RetroShare06.exe"
File /oname=retroshare06-nogui.exe "${RELEASEDIR}\retroshare-nogui\src\release\RetroShare06-nogui.exe"
; Qt binaries
File "${QTDIR}\bin\QtCore4.dll"
@ -265,7 +265,7 @@ SectionEnd
; WriteRegStr HKCR retroshare "" "PQI File"
; WriteRegBin HKCR retroshare EditFlags 00000100
; WriteRegStr HKCR "retroshare\shell" "" open
; WriteRegStr HKCR "retroshare\shell\open\command" "" `"$INSTDIR\RetroShare.exe" "%1"`
; WriteRegStr HKCR "retroshare\shell\open\command" "" `"$INSTDIR\RetroShare06.exe" "%1"`
;SectionEnd
# Shortcuts
@ -274,24 +274,24 @@ Section $(Section_StartMenu) Section_StartMenu
SetOutPath "$INSTDIR"
CreateDirectory "$SMPROGRAMS\${APPNAME}"
CreateShortCut "$SMPROGRAMS\${APPNAME}\$(Link_Uninstall).lnk" "$INSTDIR\uninstall.exe" "" "$INSTDIR\uninstall.exe" 0
CreateShortCut "$SMPROGRAMS\${APPNAME}\${APPNAME}.lnk" "$INSTDIR\RetroShare.exe" "" "$INSTDIR\RetroShare.exe" 0
CreateShortCut "$SMPROGRAMS\${APPNAME}\${APPNAME}.lnk" "$INSTDIR\RetroShare06.exe" "" "$INSTDIR\RetroShare06.exe" 0
SectionEnd
Section $(Section_Desktop) Section_Desktop
CreateShortCut "$DESKTOP\${APPNAME}.lnk" "$INSTDIR\RetroShare.exe" "" "$INSTDIR\RetroShare.exe" 0
CreateShortCut "$DESKTOP\${APPNAME}.lnk" "$INSTDIR\RetroShare06.exe" "" "$INSTDIR\RetroShare06.exe" 0
SectionEnd
Section $(Section_QuickLaunch) Section_QuickLaunch
CreateShortCut "$QUICKLAUNCH\${APPNAME}.lnk" "$INSTDIR\RetroShare.exe" "" "$INSTDIR\RetroShare.exe" 0
CreateShortCut "$QUICKLAUNCH\${APPNAME}.lnk" "$INSTDIR\RetroShare06.exe" "" "$INSTDIR\RetroShare06.exe" 0
SectionEnd
SectionGroupEnd
Section $(Section_AutoStart) Section_AutoStart
WriteRegStr HKCU "Software\Microsoft\Windows\CurrentVersion\Run" "RetroShare" "$INSTDIR\${APPNAME}.exe -m"
WriteRegStr HKCU "Software\Microsoft\Windows\CurrentVersion\Run" "RetroShare" "$INSTDIR\${APPNAME}06.exe -m"
SectionEnd
;Section $(Section_AutoStart) Section_AutoStart
; CreateShortCut "$SMSTARTUP\${APPNAME}.lnk" "$INSTDIR\RetroShare.exe" "" "$INSTDIR\RetroShare.exe -m" 0
; CreateShortCut "$SMSTARTUP\${APPNAME}.lnk" "$INSTDIR\RetroShare06.exe" "" "$INSTDIR\RetroShare06.exe -m" 0
;SectionEnd
Section -FinishSection
@ -300,7 +300,7 @@ Section -FinishSection
WriteRegStr HKLM "Software\${APPNAME}" "Version" "${VERSION}"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "DisplayName" "${APPNAME}"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "DisplayVersion" "${VERSION}"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "DisplayIcon" "$INSTDIR\RetroShare.exe"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "DisplayIcon" "$INSTDIR\RetroShare06.exe"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "Publisher" "${PUBLISHER}"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "NoModify" "1"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "NoRepair" "1"

View File

@ -0,0 +1,486 @@
; Script generated with the Venis Install Wizard & modified by defnax
; Reworked by Thunder
# Needed defines
;!define BUILDADD ""
;!define SOURCEDIR ""
;!define RELEASEDIR ""
;!define QTDIR ""
;!define MINGWDIR ""
# Optional defines
;!define OUTDIR ""
# Check needed defines
!ifndef BUILDADD
!error "BUILDADD is not defined"
!endif
!ifndef SOURCEDIR
!error "SOURCEDIR is not defined"
!endif
!ifndef RELEASEDIR
!error "RELEASEDIR is not defined"
!endif
!ifndef QTDIR
!error "QTDIR is not defined"
!endif
!ifndef MINGWDIR
!error "MINGWDIR is not defined"
!endif
# Check optional defines
!ifdef OUTDIR
!define OUTDIR_ "${OUTDIR}\"
!else
!define OUTDIR ""
!define OUTDIR_ ""
!endif
# Get version from executable
!GetDllVersion "${RELEASEDIR}\retroshare-gui\src\release\RetroShare06.exe" VERSION_
!define VERSION ${VERSION_1}.${VERSION_2}.${VERSION_3}${BUILDADD}
;!define REVISION ${VERSION_4}
# Check version
!ifndef REVISION
!error "REVISION is not defined"
!endif
!ifndef REVISION
!error "REVISION is not defined"
!endif
# Date
!define /date Date "%Y%m%d"
# Application name and version
!define APPNAME "RetroShare"
!define APPNAMEANDVERSION "${APPNAME} ${VERSION}"
!define PUBLISHER "RetroShare Team"
# Install path
!define INSTDIR_NORMAL "$ProgramFiles\${APPNAME}"
!define INSTDIR_PORTABLE "$Desktop\${APPNAME}"
!define DATADIR_NORMAL "$APPDATA\${APPNAME}"
!define DATADIR_PORTABLE "$INSTDIR\Data"
# Main Install settings
Name "${APPNAMEANDVERSION}"
InstallDirRegKey HKLM "Software\${APPNAME}" ""
OutFile "${OUTDIR_}RetroShare-${VERSION}-${Date}-${REVISION}-setup.exe"
BrandingText "${APPNAMEANDVERSION}"
RequestExecutionlevel highest
# Use compression
SetCompressor /SOLID LZMA
# Global variables
Var PortableMode
Var InstDirNormal
Var InstDirPortable
Var DataDir
Var StyleSheetDir
# Modern interface settings
!include Sections.nsh
!include nsDialogs.nsh
!include "MUI.nsh"
# Interface Settings
!define MUI_ABORTWARNING
!define MUI_HEADERIMAGE
!define MUI_HEADERIMAGE_BITMAP "${SOURCEDIR}\build_scripts\Windows\HeaderImage.bmp"
;!define MUI_WELCOMEFINISHPAGE_BITMAP "...bmp"
# MUI defines
!define MUI_ICON "${NSISDIR}\Contrib\Graphics\Icons\orange-install.ico"
!define MUI_FINISHPAGE_NOAUTOCLOSE
!define MUI_LICENSEPAGE_RADIOBUTTONS
!define MUI_COMPONENTSPAGE_SMALLDESC
!define MUI_FINISHPAGE_LINK "Visit the RetroShare forum for the latest news and support"
!define MUI_FINISHPAGE_LINK_LOCATION "http://retroshare.sourceforge.net/forum/"
!define MUI_FINISHPAGE_RUN "$INSTDIR\RetroShare06.exe"
!define MUI_FINISHPAGE_SHOWREADME $INSTDIR\changelog.txt
!define MUI_FINISHPAGE_SHOWREADME_TEXT changelog.txt
!define MUI_FINISHPAGE_SHOWREADME_NOTCHECKED
!define MUI_UNICON "${NSISDIR}\Contrib\Graphics\Icons\orange-uninstall.ico"
!define MUI_UNFINISHPAGE_NOAUTOCLOSE
;!define MUI_LANGDLL_REGISTRY_ROOT HKLM
;!define MUI_LANGDLL_REGISTRY_KEY ${REGKEY}
;!define MUI_LANGDLL_REGISTRY_VALUENAME InstallerLanguage
# Defines the un-/installer logo of RetroShare
!insertmacro MUI_DEFAULT MUI_WELCOMEFINISHPAGE_BITMAP "${NSISDIR}\Contrib\Graphics\Wizard\orange.bmp"
!insertmacro MUI_DEFAULT MUI_UNWELCOMEFINISHPAGE_BITMAP "${NSISDIR}\Contrib\Graphics\Wizard\orange-uninstall.bmp"
# Installer pages
!insertmacro MUI_PAGE_WELCOME
!insertmacro MUI_PAGE_LICENSE "$(myLicenseData)"
Page Custom PortableModePageCreate PortableModePageLeave
!define MUI_PAGE_CUSTOMFUNCTION_LEAVE dir_leave
!insertmacro MUI_PAGE_DIRECTORY
!insertmacro MUI_PAGE_COMPONENTS
!insertmacro MUI_PAGE_INSTFILES
!insertmacro MUI_PAGE_FINISH
!insertmacro MUI_UNPAGE_CONFIRM
!insertmacro MUI_UNPAGE_INSTFILES
# Set languages (first is default language)
!insertmacro MUI_RESERVEFILE_LANGDLL
# Installer languages
!define MUI_LANGDLL_ALLLANGUAGES
# Translations
!macro LANG_LOAD LANGUAGE LANGCODE LANGID LICENCEFILE
!insertmacro MUI_LANGUAGE "${LANGUAGE}"
; !verbose off
!define LANG "${LANGUAGE}"
!include "lang\${LANGCODE}.nsh"
LangString LANGUAGEID "${LANG_${LANG}}" "1031"
LicenseLangString myLicenseData ${LANGCODE} ${LICENCEFILE}
; !verbose on
!undef LANG
!macroend
!macro LANG_STRING NAME VALUE
LangString "${NAME}" "${LANG_${LANG}}" "${VALUE}"
!macroend
!insertmacro LANG_LOAD "English" "en" "1033" "${SOURCEDIR}\retroshare-gui\src\license\license.txt"
!insertmacro LANG_LOAD "French" "fr" "1036" "${SOURCEDIR}\retroshare-gui\src\license\license-FR.txt"
!insertmacro LANG_LOAD "German" "de" "1031" "${SOURCEDIR}\retroshare-gui\src\license\license-GER.txt"
!insertmacro LANG_LOAD "Turkish" "tr" "1055" "${SOURCEDIR}\retroshare-gui\src\license\license-TR.txt"
!insertmacro LANG_LOAD "SimpChinese" "zh_CN" "2052" "${SOURCEDIR}\retroshare-gui\src\license\license.txt"
!insertmacro LANG_LOAD "Polish" "pl" "1045" "${SOURCEDIR}\retroshare-gui\src\license\license.txt"
!insertmacro LANG_LOAD "Spanish" "es" "1034" "${SOURCEDIR}\retroshare-gui\src\license\license.txt"
!insertmacro LANG_LOAD "Russian" "ru" "1049" "${SOURCEDIR}\retroshare-gui\src\license\license.txt"
!insertmacro LANG_LOAD "Catalan" "ca_ES" "1027" "${SOURCEDIR}\retroshare-gui\src\license\license.txt"
LicenseData $(myLicenseData)
# Main binaries
Section $(Section_Main) Section_Main
;Set Section required
SectionIn RO
; Set Section properties
SetOverwrite on
; Clears previous error logs
; Delete "$INSTDIR\*.log"
; Main binaries
SetOutPath "$INSTDIR"
File /oname=RetroShare06.exe "${RELEASEDIR}\retroshare-gui\src\release\RetroShare06.exe"
File /oname=retroshare06-nogui.exe "${RELEASEDIR}\retroshare-nogui\src\release\RetroShare06-nogui.exe"
; Qt binaries
File "${QTDIR}\bin\Qt5Core.dll"
File "${QTDIR}\bin\Qt5Gui.dll"
File "${QTDIR}\bin\Qt5Multimedia.dll"
File "${QTDIR}\bin\Qt5Network.dll"
File "${QTDIR}\bin\Qt5PrintSupport.dll"
File "${QTDIR}\bin\Qt5Svg.dll"
File "${QTDIR}\bin\Qt5Widgets.dll"
File "${QTDIR}\bin\Qt5Xml.dll"
; Qt audio
SetOutPath "$INSTDIR\audio"
File /r "${QTDIR}\plugins\audio\qtaudio_windows.dll"
; Qt platforms
SetOutPath "$INSTDIR\platforms"
File /r "${QTDIR}\plugins\platforms\qwindows.dll"
; MinGW binaries
SetOutPath "$INSTDIR"
File "${MINGWDIR}\bin\libstdc++-6.dll"
File "${MINGWDIR}\bin\libgcc_s_dw2-1.dll"
File "${MINGWDIR}\bin\libwinpthread-1.dll"
; External binaries
File "${SOURCEDIR}\..\libs\bin\miniupnpc.dll"
File "${SOURCEDIR}\..\libs\bin\libeay32.dll"
File "${SOURCEDIR}\..\libs\bin\ssleay32.dll"
; Other files
File "${SOURCEDIR}\retroshare-gui\src\changelog.txt"
File "${SOURCEDIR}\libbitdht\src\bitdht\bdboot.txt"
; Image formats
SetOutPath "$INSTDIR\imageformats"
File /r "${QTDIR}\plugins\imageformats\qgif.dll"
File /r "${QTDIR}\plugins\imageformats\qicns.dll"
File /r "${QTDIR}\plugins\imageformats\qico.dll"
File /r "${QTDIR}\plugins\imageformats\qjp2.dll"
File /r "${QTDIR}\plugins\imageformats\qjpeg.dll"
File /r "${QTDIR}\plugins\imageformats\qmng.dll"
File /r "${QTDIR}\plugins\imageformats\qsvg.dll"
File /r "${QTDIR}\plugins\imageformats\qtga.dll"
File /r "${QTDIR}\plugins\imageformats\qtiff.dll"
File /r "${QTDIR}\plugins\imageformats\qwbmp.dll"
File /r "${QTDIR}\plugins\imageformats\qwebp.dll"
; Sounds
SetOutPath "$INSTDIR\sounds"
File /r "${SOURCEDIR}\retroshare-gui\src\sounds\*.*"
; Translations
SetOutPath "$INSTDIR\translations"
File /r "${SOURCEDIR}\retroshare-gui\src\translations\*.qm"
File /r "${QTDIR}\translations\qt_*.qm"
File /r "${QTDIR}\translations\qtbase_*.qm"
File /r "${QTDIR}\translations\qtscript_*.qm"
File /r "${QTDIR}\translations\qtquick1_*.qm"
File /r "${QTDIR}\translations\qtmultimedia_*.qm"
File /r "${QTDIR}\translations\qtxmlpatterns_*.qm"
; WebUI
SetOutPath "$INSTDIR\webui"
File /r "${SOURCEDIR}\libresapi\src\webfiles\*.*"
; License
SetOutPath "$INSTDIR\license"
File /r "${SOURCEDIR}\retroshare-gui\src\license\*.*"
SectionEnd
# Plugins
SectionGroup $(Section_Plugins) Section_Plugins
Section $(Section_Plugin_FeedReader) Section_Plugin_FeedReader
SetOutPath "$DataDir\extensions6"
File "${RELEASEDIR}\plugins\FeedReader\release\FeedReader.dll"
SectionEnd
Section $(Section_Plugin_VOIP) Section_Plugin_VOIP
SetOutPath "$DataDir\extensions6"
File "${RELEASEDIR}\plugins\VOIP\release\VOIP.dll"
SectionEnd
SectionGroupEnd
# Data (Styles)
Section $(Section_Data) Section_Data
; Set Section properties
SetOverwrite on
; Chat style
SetOutPath "$StyleSheetDir\stylesheets\Bubble"
File /r "${SOURCEDIR}\retroshare-gui\src\gui\qss\chat\Bubble\*.*"
SetOutPath "$StyleSheetDir\stylesheets\Bubble_Compact"
File /r "${SOURCEDIR}\retroshare-gui\src\gui\qss\chat\Bubble_Compact\*.*"
; Stylesheets
SetOutPath "$INSTDIR\qss"
File /r "${SOURCEDIR}\retroshare-gui\src\qss\*.*"
SectionEnd
;Section $(Section_Link) Section_Link
; Delete any existing keys
; Write the file association
; WriteRegStr HKCR .pqi "" retroshare
; WriteRegStr HKCR retroshare "" "PQI File"
; WriteRegBin HKCR retroshare EditFlags 00000100
; WriteRegStr HKCR "retroshare\shell" "" open
; WriteRegStr HKCR "retroshare\shell\open\command" "" `"$INSTDIR\RetroShare06.exe" "%1"`
;SectionEnd
# Shortcuts
SectionGroup $(Section_Shortcuts) Section_Shortcuts
Section $(Section_StartMenu) Section_StartMenu
SetOutPath "$INSTDIR"
CreateDirectory "$SMPROGRAMS\${APPNAME}"
CreateShortCut "$SMPROGRAMS\${APPNAME}\$(Link_Uninstall).lnk" "$INSTDIR\uninstall.exe" "" "$INSTDIR\uninstall.exe" 0
CreateShortCut "$SMPROGRAMS\${APPNAME}\${APPNAME}.lnk" "$INSTDIR\RetroShare06.exe" "" "$INSTDIR\RetroShare06.exe" 0
SectionEnd
Section $(Section_Desktop) Section_Desktop
CreateShortCut "$DESKTOP\${APPNAME}.lnk" "$INSTDIR\RetroShare06.exe" "" "$INSTDIR\RetroShare06.exe" 0
SectionEnd
Section $(Section_QuickLaunch) Section_QuickLaunch
CreateShortCut "$QUICKLAUNCH\${APPNAME}.lnk" "$INSTDIR\RetroShare06.exe" "" "$INSTDIR\RetroShare06.exe" 0
SectionEnd
SectionGroupEnd
Section $(Section_AutoStart) Section_AutoStart
WriteRegStr HKCU "Software\Microsoft\Windows\CurrentVersion\Run" "RetroShare" "$INSTDIR\${APPNAME}06.exe -m"
SectionEnd
;Section $(Section_AutoStart) Section_AutoStart
; CreateShortCut "$SMSTARTUP\${APPNAME}.lnk" "$INSTDIR\RetroShare06.exe" "" "$INSTDIR\RetroShare06.exe -m" 0
;SectionEnd
Section -FinishSection
${If} $PortableMode = 0
WriteRegStr HKLM "Software\${APPNAME}" "" "$INSTDIR"
WriteRegStr HKLM "Software\${APPNAME}" "Version" "${VERSION}"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "DisplayName" "${APPNAME}"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "DisplayVersion" "${VERSION}"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "DisplayIcon" "$INSTDIR\RetroShare06.exe"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "Publisher" "${PUBLISHER}"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "NoModify" "1"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "NoRepair" "1"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "UninstallString" "$INSTDIR\uninstall.exe"
WriteUninstaller "$INSTDIR\uninstall.exe"
${Else}
; Create the file the application uses to detect portable mode
FileOpen $0 "$INSTDIR\portable" w
FileClose $0
${EndIf}
SectionEnd
# Descriptions
!insertmacro MUI_FUNCTION_DESCRIPTION_BEGIN
!insertmacro MUI_DESCRIPTION_TEXT ${Section_Main} $(Section_Main_Desc)
!insertmacro MUI_DESCRIPTION_TEXT ${Section_Data} $(Section_Data_Desc)
!insertmacro MUI_DESCRIPTION_TEXT ${Section_Shortcuts} $(Section_Shortcuts_Desc)
!insertmacro MUI_DESCRIPTION_TEXT ${Section_StartMenu} $(Section_StartMenu_Desc)
!insertmacro MUI_DESCRIPTION_TEXT ${Section_Desktop} $(Section_Desktop_Desc)
!insertmacro MUI_DESCRIPTION_TEXT ${Section_QuickLaunch} $(Section_QuickLaunch_Desc)
!insertmacro MUI_DESCRIPTION_TEXT ${Section_Plugins} $(Section_Plugins_Desc)
!insertmacro MUI_DESCRIPTION_TEXT ${Section_Plugin_FeedReader} $(Section_Plugin_FeedReader_Desc)
!insertmacro MUI_DESCRIPTION_TEXT ${Section_Plugin_VOIP} $(Section_Plugin_VOIP_Desc)
; !insertmacro MUI_DESCRIPTION_TEXT ${Section_Link} $(Section_Link_Desc)
!insertmacro MUI_DESCRIPTION_TEXT ${Section_AutoStart} $(Section_AutoStart_Desc)
!insertmacro MUI_FUNCTION_DESCRIPTION_END
# Uninstall
Section "Uninstall"
; Remove file association registry keys
; DeleteRegKey HKCR .pqi
DeleteRegKey HKCR RetroShare
; Remove program/uninstall regsitry keys
DeleteRegKey HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}"
DeleteRegKey HKLM SOFTWARE\${APPNAME}
DeleteRegValue HKCU "Software\Microsoft\Windows\CurrentVersion\Run" "RetroShare"
; Remove shortcuts, if any
Delete "$SMPROGRAMS\${APPNAME}\*.*"
; Remove desktop shortcut
Delete "$DESKTOP\${APPNAME}.lnk"
; Remove Quicklaunch shortcut
Delete "$QUICKLAUNCH\${APPNAME}.lnk"
; Remove Autstart
Delete "$SMSTARTUP\${APPNAME}.lnk"
; Remove directories used
RMDir "$SMPROGRAMS\${APPNAME}"
RMDir /r "$INSTDIR"
; Don't remove the directory, otherwise
; we lose the XPGP keys.
; Should make this an option though...
RMDir /r "${DATADIR_NORMAL}\extensions6"
RMDir /r "${DATADIR_NORMAL}\stylesheets"
SectionEnd
Function .onInit
StrCpy $InstDirNormal "${INSTDIR_NORMAL}"
StrCpy $InstDirPortable "${INSTDIR_PORTABLE}"
StrCpy $PortableMode 0
StrCpy $INSTDIR "$InstDirNormal"
StrCpy $DataDir "${DATADIR_NORMAL}"
InitPluginsDir
Push $R1
File /oname=$PLUGINSDIR\spltmp.bmp "${SOURCEDIR}\retroshare-gui\src\gui\images\logo\logo_splash.png"
advsplash::show 1200 1000 1000 -1 $PLUGINSDIR\spltmp
Pop $R1
Pop $R1
!insertmacro MUI_LANGDLL_DISPLAY
FunctionEnd
# Installation mode
Function RequireAdmin
UserInfo::GetAccountType
Pop $8
${If} $8 != "admin"
MessageBox MB_ICONSTOP "You need administrator rights to install ${APPNAME}"
SetErrorLevel 740 ;ERROR_ELEVATION_REQUIRED
Abort
${EndIf}
FunctionEnd
Function SetModeDestinationFromInstdir
${If} $PortableMode = 0
StrCpy $InstDirNormal $INSTDIR
${Else}
StrCpy $InstDirPortable $INSTDIR
${EndIf}
FunctionEnd
Function PortableModePageCreate
Call SetModeDestinationFromInstdir ; If the user clicks BACK on the directory page we will remember their mode specific directory
!insertmacro MUI_HEADER_TEXT $(Page_InstallMode) $(Page_InstallMode_Desc)
nsDialogs::Create 1018
Pop $0
${NSD_CreateRadioButton} 5u 25u -10u 8u $(Page_InstallMode_Standard)
Pop $1
${NSD_CreateLabel} 18u 40u -10u 24u $(Page_InstallMode_Standard_Desc)
Pop $0
${NSD_CreateRadioButton} 5u 75u -10u 8u $(Page_InstallMode_Portable)
Pop $2
${NSD_CreateLabel} 18u 90u -10u 24u $(Page_InstallMode_Portable_Desc)
Pop $0
${If} $PortableMode = 0
SendMessage $1 ${BM_SETCHECK} ${BST_CHECKED} 0
${Else}
SendMessage $2 ${BM_SETCHECK} ${BST_CHECKED} 0
${EndIf}
nsDialogs::Show
FunctionEnd
Function PortableModePageLeave
${NSD_GetState} $1 $0
${If} $0 <> ${BST_UNCHECKED}
StrCpy $PortableMode 0
StrCpy $INSTDIR $InstDirNormal
Call RequireAdmin
; Enable sections
SectionSetText ${Section_Shortcuts} $(Section_Shortcuts)
SectionSetText ${Section_StartMenu} $(Section_StartMenu)
SectionSetText ${Section_Desktop} $(Section_Desktop)
SectionSetText ${Section_QuickLaunch} $(Section_QuickLaunch)
SectionSetText ${Section_AutoStart} $(Section_AutoStart)
!insertmacro SelectSection ${Section_Shortcuts}
!insertmacro SelectSection ${Section_AutoStart}
!insertmacro SelectSection ${Section_StartMenu}
!insertmacro SelectSection ${Section_Desktop}
!insertmacro SelectSection ${Section_QuickLaunch}
${Else}
StrCpy $PortableMode 1
StrCpy $INSTDIR $InstDirPortable
; Disable sections
!insertmacro UnselectSection ${Section_Shortcuts}
!insertmacro UnselectSection ${Section_AutoStart}
!insertmacro UnselectSection ${Section_StartMenu}
!insertmacro UnselectSection ${Section_Desktop}
!insertmacro UnselectSection ${Section_QuickLaunch}
SectionSetText ${Section_Shortcuts} ""
SectionSetText ${Section_StartMenu} ""
SectionSetText ${Section_Desktop} ""
SectionSetText ${Section_QuickLaunch} ""
SectionSetText ${Section_AutoStart} ""
${EndIf}
FunctionEnd
Function dir_leave
${If} $PortableMode = 0
StrCpy $DataDir "${DATADIR_NORMAL}"
StrCpy $StyleSheetDir $DataDir
${Else}
StrCpy $DataDir "${DATADIR_PORTABLE}"
StrCpy $StyleSheetDir $INSTDIR
${EndIf}
FunctionEnd

View File

@ -299,10 +299,10 @@ bool p3BitDht::loadList(std::list<RsItem *>& load)
return false;
}
std::cerr << "BITDHT Load Item:";
std::cerr << std::endl;
//std::cerr << "BITDHT Load Item:";
//std::cerr << std::endl;
config->print(std::cerr, 0);
//config->print(std::cerr, 0);
std::list<std::string> servers;
int peers[RSDHT_RELAY_NUM_CLASS] = {0};
@ -320,16 +320,16 @@ bool p3BitDht::loadList(std::list<RsItem *>& load)
{
/* add to RELAY_SERVER List */
servers.push_back(value);
std::cerr << "p3BitDht::loadList() Found Server: " << value;
std::cerr << std::endl;
//std::cerr << "p3BitDht::loadList() Found Server: " << value;
//std::cerr << std::endl;
}
else if (0 == strncmp(key.c_str(), "RELAY_MODE", 10))
{
mode = atoi(value.c_str());
haveMode = true;
std::cerr << "p3BitDht::loadList() Found Mode: " << mode;
std::cerr << std::endl;
//std::cerr << "p3BitDht::loadList() Found Mode: " << mode;
//std::cerr << std::endl;
}
else if (0 == strncmp(key.c_str(), "RELAY_CLASS", 11))
{
@ -358,24 +358,24 @@ bool p3BitDht::loadList(std::list<RsItem *>& load)
if (key[13] == 'C')
{
std::cerr << "p3BitDht::loadList() Found Count(" << idx << "): ";
std::cerr << val;
std::cerr << std::endl;
//std::cerr << "p3BitDht::loadList() Found Count(" << idx << "): ";
//std::cerr << val;
//std::cerr << std::endl;
peers[idx] = val;
}
else
{
std::cerr << "p3BitDht::loadList() Found Bandwidth(" << idx << "): ";
std::cerr << val;
std::cerr << std::endl;
//std::cerr << "p3BitDht::loadList() Found Bandwidth(" << idx << "): ";
//std::cerr << val;
//std::cerr << std::endl;
bandwidth[idx] = val;
}
}
else
{
std::cerr << "p3BitDht::loadList() Unknown Key:value: " << key;
std::cerr << ":" << value;
std::cerr << std::endl;
//std::cerr << "p3BitDht::loadList() Unknown Key:value: " << key;
//std::cerr << ":" << value;
//std::cerr << std::endl;
}
}

View File

@ -61,7 +61,7 @@ public:
// This method is called by the global router when a message has been received, or cannot be sent, etc.
//
virtual void notifyDataStatus(const GRouterMsgPropagationId& received_id,uint32_t data_status)
virtual void notifyDataStatus(const GRouterMsgPropagationId& received_id,const RsGxsId& signer_id,uint32_t data_status)
{
std::cerr << "!!!!!! Received Data status from global router, but the client service is not handling it !!!!!!!!!!" << std::endl ;
std::cerr << " message ID = " << received_id << std::endl;

View File

@ -142,25 +142,44 @@ RsGRouterGenericDataItem *RsGRouterSerialiser::deserialise_RsGRouterGenericDataI
ok &= getRawUInt32(data, pktsize, &offset, &item->service_id);
ok &= getRawUInt32(data, pktsize, &offset, &item->data_size);
if(item->data_size > rssize || offset > rssize - item->data_size) // better than if(item->data_size + offset > rssize)
if(item->data_size > 0) // This happens when the item data has been deleted from the cache
{
std::cerr << __PRETTY_FUNCTION__ << ": Cannot read beyond item size. Serialisation error!" << std::endl;
delete item;
return NULL ;
}
if(item->data_size > rssize || offset > rssize - item->data_size) // better than if(item->data_size + offset > rssize)
{
std::cerr << __PRETTY_FUNCTION__ << ": Cannot read beyond item size. Serialisation error!" << std::endl;
delete item;
return NULL ;
}
if( NULL == (item->data_bytes = (uint8_t*)rs_malloc(item->data_size)))
{
delete item;
return NULL ;
}
if( NULL == (item->data_bytes = (uint8_t*)rs_malloc(item->data_size)))
{
delete item;
return NULL ;
}
memcpy(item->data_bytes,&((uint8_t*)data)[offset],item->data_size) ;
offset += item->data_size ;
memcpy(item->data_bytes,&((uint8_t*)data)[offset],item->data_size) ;
offset += item->data_size ;
}
else
item->data_bytes = NULL ;
ok &= item->signature.GetTlv(data, pktsize, &offset) ;
ok &= getRawUInt32(data, pktsize, &offset, &item->randomized_distance);
ok &= getRawUInt32(data, pktsize, &offset, &item->duplication_factor);
// make sure the duplication factor is not altered by friends. In the worst case, the item will duplicate a bit more.
if(item->duplication_factor < 1)
{
item->duplication_factor = 1 ;
std::cerr << "(II) correcting GRouter item duplication factor from 0 to 1, to ensure backward compat." << std::endl;
}
if(item->duplication_factor > GROUTER_MAX_DUPLICATION_FACTOR)
{
std::cerr << "(WW) correcting GRouter item duplication factor of " << item->duplication_factor << ". This is very unexpected." << std::endl;
item->duplication_factor = GROUTER_MAX_DUPLICATION_FACTOR ;
}
ok &= getRawUInt32(data, pktsize, &offset, &item->flags);
if (offset != rssize || !ok)
@ -382,7 +401,7 @@ uint32_t RsGRouterGenericDataItem::serial_size() const
s += 4 ; // service id
s += data_size ; // data
s += signature.TlvSize() ; // signature
s += 4 ; // randomized distance
s += 4 ; // duplication_factor
s += 4 ; // flags
return s ;
@ -483,7 +502,7 @@ bool RsGRouterGenericDataItem::serialise(void *data,uint32_t& size) const
ok &= signature.SetTlv(data, tlvsize, &offset) ;
ok &= setRawUInt32(data, tlvsize, &offset, randomized_distance) ;
ok &= setRawUInt32(data, tlvsize, &offset, duplication_factor) ;
ok &= setRawUInt32(data, tlvsize, &offset, flags) ;
if (offset != tlvsize)
@ -796,7 +815,7 @@ std::ostream& RsGRouterGenericDataItem::print(std::ostream& o, uint16_t)
o << " Data size: " << data_size << std::endl ;
o << " Data hash: " << RsDirUtil::sha1sum(data_bytes,data_size) << std::endl ;
o << " signature key: " << signature.keyId << std::endl;
o << " randomized dist:" << randomized_distance << std::endl;
o << " duplication fac:" << duplication_factor << std::endl;
o << " flags: " << flags << std::endl;
return o ;

View File

@ -133,7 +133,7 @@ class RsGRouterGenericDataItem: public RsGRouterAbstractMsgItem, public RsGRoute
uint32_t data_size ;
uint8_t *data_bytes;
uint32_t randomized_distance ; // number of hops (tunnel wise. Does not preclude of the real distance)
uint32_t duplication_factor ; // number of duplicates allowed. Should be capped at each de-serialise operation!
// utility methods for signing data
virtual uint32_t signed_data_size() const ;

View File

@ -203,7 +203,7 @@ void GRouterMatrix::debugDump() const
std::cerr << " " << it->first << ": from " << it->second.friend_id << " " << now - it->second.time_stamp << " secs ago." << std::endl;
}
bool GRouterMatrix::computeRoutingProbabilities(const GRouterKeyId& key_id, const std::vector<RsPeerId>& friends, std::vector<float>& probas) const
bool GRouterMatrix::computeRoutingProbabilities(const GRouterKeyId& key_id, const std::vector<RsPeerId>& friends, std::vector<float>& probas, float& maximum) const
{
// Routing probabilities are computed according to routing clues
//
@ -239,6 +239,7 @@ bool GRouterMatrix::computeRoutingProbabilities(const GRouterKeyId& key_id, cons
return false ;
}
const std::vector<float>& w(it2->second) ;
maximum = 0.0f ;
for(uint32_t i=0;i<friends.size();++i)
{
@ -250,6 +251,9 @@ bool GRouterMatrix::computeRoutingProbabilities(const GRouterKeyId& key_id, cons
{
probas[i] = w[findex] ;
total += w[findex] ;
if(maximum < w[findex])
maximum = w[findex] ;
}
}

View File

@ -57,7 +57,7 @@ class GRouterMatrix
// the computation accounts for the time at which the info was received and the
// weight of each routing hit record.
//
bool computeRoutingProbabilities(const GRouterKeyId& id, const std::vector<RsPeerId>& friends, std::vector<float>& probas) const ;
bool computeRoutingProbabilities(const GRouterKeyId& id, const std::vector<RsPeerId>& friends, std::vector<float>& probas, float &maximum) const ;
// Update routing probabilities for each key, accounting for all received events, but without
// activity information

View File

@ -44,16 +44,21 @@ static const uint32_t RS_GROUTER_MAX_KEEP_TRACKING_CLUES = 86400*10 ; // m
static const float RS_GROUTER_BASE_WEIGHT_ROUTED_MSG = 1.0f ; // base contribution of routed message clue to routing matrix
static const float RS_GROUTER_BASE_WEIGHT_GXS_PACKET = 0.1f ; // base contribution of GXS message to routing matrix
static const float RS_GROUTER_PROBABILITY_THRESHOLD_FOR_RANDOM_ROUTING = 0.01f ; // routing probability under which the routage is performed randomly
static const float RS_GROUTER_PROBABILITY_THRESHOLD_BEST_PEERS_SELECT = 0.5f ; // min ratio of forward proba with respect to best peer.
static const uint32_t MAX_TUNNEL_WAIT_TIME = 60 ; // wait for 60 seconds at most for a tunnel response.
static const uint32_t MAX_TUNNEL_UNMANAGED_TIME = 600 ; // min time before retry tunnels for that msg.
static const uint32_t MAX_DELAY_FOR_RESEND = 2*86400+300 ; // re-send if held for more than 2 days (cache store period) plus security delay.
static const uint32_t MAX_DESTINATION_KEEP_TIME = 20*86400 ; // keep for 20 days in destination cache to avoid re-
static const uint32_t MAX_RECEIPT_KEEP_TIME = 20*86400 ; // keep for 20 days in destination cache to avoid re-
static const uint32_t TUNNEL_OK_WAIT_TIME = 2 ; // wait for 2 seconds after last tunnel ok, so that we have a complete set of tunnels.
static const uint32_t MAX_GROUTER_DATA_SIZE = 2*1024*1024 ; // 2MB size limit. This is of course arbitrary.
static const uint32_t MAX_TRANSACTION_ACK_WAITING_TIME = 60 ; // wait for at most 60 secs for a ACK. If not restart the transaction.
static const uint32_t DIRECT_FRIEND_TRY_DELAY = 20 ; // wait for 20 secs if no friends available, then try tunnels.
static const uint32_t MAX_INACTIVE_DATA_PIPE_DELAY = 300 ; // clean inactive data pipes for more than 5 mins
static const uint32_t GROUTER_MAX_DUPLICATION_FACTOR = 10 ; // max number of duplicates for a given message to keep in the network
static const uint32_t GROUTER_MAX_BRANCHING_FACTOR = 3 ; // max number of branches, for locally forwarding items
static const time_t RS_GROUTER_DEBUG_OUTPUT_PERIOD = 10 ; // Output everything
static const time_t RS_GROUTER_AUTOWASH_PERIOD = 10 ; // Autowash every minute. Not a costly operation.

View File

@ -190,6 +190,8 @@
#include "services/p3idservice.h"
#include "turtle/p3turtle.h"
#include "gxs/rsgixs.h"
#include "retroshare/rspeers.h"
#include "retroshare/rsreputations.h"
#include "p3grouter.h"
#include "grouteritems.h"
@ -855,6 +857,34 @@ void p3GRouter::handleTunnels()
}
}
void p3GRouter::locked_sendToPeers(RsGRouterGenericDataItem *data_item,const std::map<RsPeerId,uint32_t>& peers_and_duplication_factors)
{
// slice the data appropriately and send.
uint32_t saved_duplication_factor = data_item->duplication_factor ; // this little trick avoids copying the item for each peer before slicing it up
for(std::map<RsPeerId,uint32_t>::const_iterator itpid(peers_and_duplication_factors.begin());itpid!=peers_and_duplication_factors.end();++itpid)
{
std::list<RsGRouterTransactionChunkItem*> chunks ;
data_item->duplication_factor = itpid->second;
sliceDataItem(data_item,chunks) ;
for(std::list<RsGRouterTransactionChunkItem*>::const_iterator it2(chunks.begin());it2!=chunks.end();++it2)
locked_sendTransactionData(itpid->first,*(*it2) ) ;
#ifdef GROUTER_DEBUG
std::cerr << " sending " << chunks.size() << " slices to peer " << itpid->first << " with duplication factor = " << itpid->second << std::endl;
#endif
// delete temporary items
for(std::list<RsGRouterTransactionChunkItem*>::const_iterator cit=chunks.begin();cit!=chunks.end();++cit)
delete *cit;
}
data_item->duplication_factor = saved_duplication_factor ;
}
void p3GRouter::routePendingObjects()
{
// Go throught he list of pending messages. For those with a peer ready, send the message to that peer.
@ -885,17 +915,45 @@ void p3GRouter::routePendingObjects()
{
// Look for tunnels and friends where to send the data. Send to both.
std::list<RsPeerId> peers ;
std::map<RsPeerId,uint32_t> peers_and_duplication_factors ;
if(it->second.routing_flags & GRouterRoutingInfo::ROUTING_FLAGS_ALLOW_TUNNELS)
locked_collectAvailableTunnels(it->second.tunnel_hash,peers);
locked_collectAvailableTunnels(it->second.tunnel_hash,it->second.data_item->duplication_factor,peers_and_duplication_factors);
// For now, disable friends. We'll first check that the good old tunnel system works as before.
if(!peers_and_duplication_factors.empty())
{
#ifdef GROUTER_DEBUG
std::cerr << " tunnels available! sending!" << std::endl;
#endif
locked_sendToPeers(it->second.data_item,peers_and_duplication_factors) ;
// change item state in waiting list
it->second.data_status = RS_GROUTER_DATA_STATUS_ONGOING ;
it->second.data_transaction_TS = now ;
pending_messages_changed = true ;
continue ; // no need to seek for friend asynced routes since tunnels directly go to the final destination!
}
if(it->second.routing_flags & GRouterRoutingInfo::ROUTING_FLAGS_ALLOW_FRIENDS)
locked_collectAvailableFriends(it->second.data_item->destination_key,peers, it->second.incoming_routes.ids, it->second.routing_flags & GRouterRoutingInfo::ROUTING_FLAGS_IS_ORIGIN);
locked_collectAvailableFriends(it->second.data_item->destination_key,it->second.incoming_routes.ids,it->second.data_item->duplication_factor,peers_and_duplication_factors);
if(peers.empty())
if(!peers_and_duplication_factors.empty())
{
#ifdef GROUTER_DEBUG
std::cerr << " friends available! sending!" << std::endl;
#endif
locked_sendToPeers(it->second.data_item,peers_and_duplication_factors) ;
// change item state in waiting list
it->second.data_status = RS_GROUTER_DATA_STATUS_ONGOING ;
it->second.data_transaction_TS = now ;
pending_messages_changed = true ;
}
else
{
#ifdef GROUTER_DEBUG
std::cerr << " no direct friends available" << std::endl;
@ -908,33 +966,8 @@ void p3GRouter::routePendingObjects()
#endif
it->second.routing_flags |= GRouterRoutingInfo::ROUTING_FLAGS_ALLOW_TUNNELS ;
}
continue ;
}
// slice the data appropriately and send.
std::list<RsGRouterTransactionChunkItem*> chunks ;
sliceDataItem(it->second.data_item,chunks) ;
#ifdef GROUTER_DEBUG
if(!peers.empty())
std::cerr << " sending to peers:" << std::endl;
#endif
for(std::list<RsPeerId>::const_iterator itpid(peers.begin());itpid!=peers.end();++itpid)
for(std::list<RsGRouterTransactionChunkItem*>::const_iterator it2(chunks.begin());it2!=chunks.end();++it2)
locked_sendTransactionData(*itpid,*(*it2) ) ;
// delete temporary items
for(std::list<RsGRouterTransactionChunkItem*>::const_iterator cit=chunks.begin();cit!=chunks.end();++cit)
delete *cit;
// change item state in waiting list
it->second.data_status = RS_GROUTER_DATA_STATUS_ONGOING ;
it->second.data_transaction_TS = now ;
pending_messages_changed = true ;
}
else if(it->second.data_status == RS_GROUTER_DATA_STATUS_ONGOING && now > MAX_TRANSACTION_ACK_WAITING_TIME + it->second.data_transaction_TS)
{
@ -1014,44 +1047,127 @@ void p3GRouter::routePendingObjects()
IndicateConfigChanged() ;
}
void p3GRouter::locked_collectAvailableFriends(const GRouterKeyId& gxs_id,std::list<RsPeerId>& friend_peers,const std::set<RsPeerId>& incoming_routes,bool is_origin)
void p3GRouter::locked_collectAvailableFriends(const GRouterKeyId& gxs_id,const std::set<RsPeerId>& incoming_routes,uint32_t duplication_factor, std::map<RsPeerId,uint32_t>& friend_peers_and_duplication_factors)
{
// The strategy is the following:
// Old strategy was the following:
// if origin
// send to multiple neighbors : best and random
// else
// send to a single "best" neighbor (determined by threshold over routing probability),
std::set<RsPeerId> ids ;
mServiceControl->getPeersConnected(getServiceInfo().mServiceType,ids) ;
std::vector<float> probas;
std::vector<RsPeerId> tmp_peers;
// remove previous peers
for(std::set<RsPeerId>::const_iterator it(ids.begin());it!=ids.end();++it)
if(incoming_routes.find(*it) == incoming_routes.end())
tmp_peers.push_back(*it) ;
if(tmp_peers.empty())
return ;
_routing_matrix.computeRoutingProbabilities(gxs_id, tmp_peers, probas) ;
// New strategy is:
//
// Characteristics of the distribution to look at:
// * who's online, who's not
// * all values quite equal
// * single value well above others
// * largest value is small
// Algorithm:
//
// 0 - encode duplicate factor in routed item and allow at most N duplicates
// - when forwarding to N peers, split the duplication factor into N bins, each being proportional to the forwarding probability.
// Example for N=3 and D=10:
//
// p Calculation Final bin
//
// +-0.21--> 0.21*10=2.1 --> 2 0.1 below
// |
// 10 ----+-0.45--> 0.45*10=4.5 --> 4.6-> 5 0.4 above
// |
// +-0.34--> 0.34*10=3.4 --> 3.0-> 3 0
//
//
// 1 - get routing probabilities p_i for all peers as well as the maximum proba p before normalization.
//
// Set N = min(3,item->duplication_factor) // max number of friends to route to
//
// if p < threshold // That means the routage info is too old => Fallback to random routing.
// Select N random online friends and forward to them.
// else
// Let p_i be the probabilities of all peers
// Select all online peers for which p_i >= 0.5*p.
// if !empty
// Update duplication factors according to probabilities and number of peers
// Route to these peers
// else
// Keep the item
//
#ifdef GROUTER_DEBUG
std::cerr << "locked_getAvailableFriends()" << std::endl;
std::cerr << " getting connected friends, computing routing probabilities" << std::endl;
std::cerr << " looking for friends for item to ID " << gxs_id << " duplication factor = " << duplication_factor << std::endl;
std::cerr << " retrieving online friends and all friends lists." << std::endl;
#endif
std::set<RsPeerId> online_ids ;
std::list<RsPeerId> all_ids ;
rsPeers->getFriendList(all_ids) ;
mServiceControl->getPeersConnected(getServiceInfo().mServiceType,online_ids) ;
std::vector<RsPeerId> tmp_peers;
for(std::list<RsPeerId>::const_iterator it(all_ids.begin());it!=all_ids.end();++it)
tmp_peers.push_back(*it) ;
std::vector<float> probas;
float maximum = 1.0;
float max_probability = 0.0;
_routing_matrix.computeRoutingProbabilities(gxs_id, tmp_peers, probas, maximum) ;
#ifdef GROUTER_DEBUG
std::cerr << " initial routing probabilities (maximum=" << maximum << ")" << std::endl;
for(uint32_t i=0;i<tmp_peers.size();++i)
std::cerr << " " << tmp_peers[i] << " " << probas[i] << std::endl;
#endif
if(maximum < RS_GROUTER_PROBABILITY_THRESHOLD_FOR_RANDOM_ROUTING)
{
max_probability = 0.0f ;
#ifdef GROUTER_DEBUG
std::cerr << " max proba: " << maximum << " is below random threshold => using uniform random routing." << std::endl;
#endif
}
else
{
for(uint32_t i=0;i<tmp_peers.size();++i)
max_probability = std::max(max_probability,probas[i]) ;
}
#ifdef GROUTER_DEBUG
std::cerr << " maxi probability=" << max_probability << std::endl;
#endif
// remove incoming peers and peers for which the proba is less than half the maximum proba
uint32_t count=0;
for(uint32_t i=0;i<tmp_peers.size();++i)
if(incoming_routes.find(tmp_peers[i]) != incoming_routes.end())
std::cerr << " removing " << tmp_peers[i] << " which is an incoming route" << std::endl;
else if(probas[i] < RS_GROUTER_PROBABILITY_THRESHOLD_BEST_PEERS_SELECT*max_probability)
std::cerr << " removing " << tmp_peers[i] << " because probability is below best peers threshold" << std::endl;
else
{
tmp_peers[count] = tmp_peers[i] ;
probas[count] = (max_probability==0.0)? (0.5+0.001*RSRandom::random_f32()) : probas[i] ;
++count ;
}
tmp_peers.resize(count) ;
probas.resize(count) ;
if(tmp_peers.empty())
{
#ifdef GROUTER_DEBUG
std::cerr << " online - available peers empty => giving up." << std::endl;
#endif
return ;
}
// now select the N best peers
#ifdef GROUTER_DEBUG
std::cerr << " Remaining peers and routing probabilities:" << std::endl;
for(uint32_t i=0;i<tmp_peers.size();++i)
std::cerr << " " << tmp_peers[i] << ", probability: " << probas[i] << std::endl;
#endif
uint32_t max_count = is_origin?3:1 ;
float probability_threshold = is_origin?0.0:0.5 ;
#ifdef GROUTER_DEBUG
std::cerr << " position at origin: " << is_origin << " => mac_count=" << max_count << ", proba threshold=" << probability_threshold << std::endl;
#endif
std::vector<std::pair<float,RsPeerId> > mypairs ;
for(uint32_t i=0;i<tmp_peers.size();++i)
@ -1060,24 +1176,37 @@ void p3GRouter::locked_collectAvailableFriends(const GRouterKeyId& gxs_id,std::l
// now sort them up
std::sort(mypairs.begin(),mypairs.end(),item_comparator_001()) ;
// take the max_count peers that are still above min_probability
uint32_t n=0 ;
for(std::vector<std::pair<float,RsPeerId> >::const_reverse_iterator it = mypairs.rbegin();it!=mypairs.rend() && n<max_count;++it)
if( (*it).first >= probability_threshold )
{
friend_peers.push_back( (*it).second ), ++n ;
int max_count = std::min(std::min((uint32_t)mypairs.size(),(uint32_t)GROUTER_MAX_BRANCHING_FACTOR),duplication_factor);
// normalise the probabilities
#ifdef GROUTER_DEBUG
std::cerr << " keeping " << (*it).second << std::endl;
std::cerr << " Normalising probabilities..." << std::endl;
#endif
if(!is_origin) // only collect one peer if we're not at origin.
break ;
float total_probas = 0.0f ;
if(mypairs.size() > 0 && max_count > 0)
{
for(int i=mypairs.size()-1,n=0;i>=0 && n<max_count;--i,++n) total_probas += mypairs[i].first ;
for(int i=mypairs.size()-1,n=0;i>=0 && n<max_count;--i,++n) mypairs[i].first /= total_probas ;
}
float duplication_factor_delta =0.0;
for(int i=mypairs.size()-1,n=0;i>=0 && n<max_count;--i,++n)
{
float ideal_dupl = duplication_factor*mypairs[i].first - duplication_factor_delta ; // correct what was taken in advance
uint32_t real_dupl = std::min( duplication_factor - max_count+1,std::max(1u,uint32_t(rint(ideal_dupl)))) ;
duplication_factor_delta = real_dupl - ideal_dupl ;
std::cerr << " Peer " << mypairs[i].second << " prob=" << mypairs[i].first << ", ideal_dupl=" << ideal_dupl << ", real=" << real_dupl << ". Delta = " << duplication_factor_delta << std::endl;
friend_peers_and_duplication_factors[ mypairs[i].second ] = real_dupl ; // should be updated correctly
}
}
void p3GRouter::locked_collectAvailableTunnels(const TurtleFileHash& hash,std::list<RsPeerId>& tunnel_peers)
void p3GRouter::locked_collectAvailableTunnels(const TurtleFileHash& hash,uint32_t total_duplication,std::map<RsPeerId,uint32_t>& tunnel_peers_and_duplication_factors)
{
time_t now = time(NULL) ;
@ -1110,7 +1239,7 @@ void p3GRouter::locked_collectAvailableTunnels(const TurtleFileHash& hash,std::l
#endif
TurtleVirtualPeerId vpid = *(vpit->second.virtual_peers.begin()) ;
tunnel_peers.push_back(vpid) ;
tunnel_peers_and_duplication_factors[vpid] = total_duplication ;
}
bool p3GRouter::locked_sendTransactionData(const RsPeerId& pid,const RsGRouterTransactionItem& trans_item)
@ -1165,19 +1294,30 @@ void p3GRouter::autoWash()
bool items_deleted = false ;
time_t now = time(NULL) ;
std::map<GRouterMsgPropagationId,GRouterClientService *> failed_msgs ;
std::map<GRouterMsgPropagationId,std::pair<GRouterClientService *,RsGxsId> > failed_msgs ;
{
RS_STACK_MUTEX(grMtx) ;
for(std::map<GRouterMsgPropagationId, GRouterRoutingInfo>::iterator it=_pending_messages.begin();it!=_pending_messages.end();)
if( (it->second.data_status == RS_GROUTER_DATA_STATUS_DONE &&
(!(it->second.routing_flags & GRouterRoutingInfo::ROUTING_FLAGS_IS_DESTINATION)
|| it->second.received_time_TS + MAX_DESTINATION_KEEP_TIME < now))
|| ((it->second.received_time_TS + GROUTER_ITEM_MAX_CACHE_KEEP_TIME < now)
&& !(it->second.routing_flags & GRouterRoutingInfo::ROUTING_FLAGS_IS_ORIGIN)
&& !(it->second.routing_flags & GRouterRoutingInfo::ROUTING_FLAGS_IS_DESTINATION)
)) // is the item too old for cache
{
bool delete_entry = false ;
if(it->second.data_status == RS_GROUTER_DATA_STATUS_DONE )
{
if(!(it->second.routing_flags & GRouterRoutingInfo::ROUTING_FLAGS_IS_DESTINATION) || it->second.received_time_TS + MAX_DESTINATION_KEEP_TIME < now) // is the item too old for cache
delete_entry = true ;
}
else if(it->second.data_status == RS_GROUTER_DATA_STATUS_RECEIPT_OK )
{
if(it->second.received_time_TS + MAX_RECEIPT_KEEP_TIME < now) // is the item too old for cache
delete_entry = true ;
}
else
if(it->second.received_time_TS + GROUTER_ITEM_MAX_CACHE_KEEP_TIME < now)
delete_entry = true ;
if(delete_entry)
{
#ifdef GROUTER_DEBUG
grouter_debug() << " Removing cached item " << std::hex << it->first << std::dec << std::endl;
@ -1190,7 +1330,7 @@ void p3GRouter::autoWash()
GRouterClientService *client = NULL;
if(locked_getLocallyRegisteredClientFromServiceId(it->second.client_id,client))
failed_msgs[it->first] = client ;
failed_msgs[it->first] = std::make_pair(client,it->second.data_item->signature.keyId) ;
else
std::cerr << " ERROR: client id " << it->second.client_id << " not registered. Consistency error." << std::endl;
}
@ -1209,6 +1349,7 @@ void p3GRouter::autoWash()
}
else
++it ;
}
// also check all existing tunnels
@ -1248,12 +1389,12 @@ void p3GRouter::autoWash()
}
// Look into pending items.
for(std::map<GRouterMsgPropagationId,GRouterClientService*>::const_iterator it(failed_msgs.begin());it!=failed_msgs.end();++it)
for(std::map<GRouterMsgPropagationId,std::pair<GRouterClientService*,RsGxsId> >::const_iterator it(failed_msgs.begin());it!=failed_msgs.end();++it)
{
#ifdef GROUTER_DEBUG
std::cerr << " notifying client for message id " << std::hex << it->first << " state = FAILED" << std::endl;
#endif
it->second->notifyDataStatus(it->first ,GROUTER_CLIENT_SERVICE_DATA_STATUS_FAILED) ;
it->second.first->notifyDataStatus(it->first,it->second.second ,GROUTER_CLIENT_SERVICE_DATA_STATUS_FAILED) ;
}
if(items_deleted)
@ -1361,13 +1502,13 @@ void p3GRouter::handleIncomingReceiptItem(RsGRouterSignedReceiptItem *receipt_it
std::cerr << "Item content:" << std::endl;
receipt_item->print(std::cerr,2) ;
#endif
RsGxsId signer_id ;
// Because we don't do proxy-transmission yet, the client needs to be notified. Otherwise, we will need to
// first check if we're a proxy or not. We also remove the message from the global router sending list.
// in the proxy case, we should only store the receipt.
GRouterClientService *client_service = NULL;
GRouterServiceId service_id ;
GRouterMsgPropagationId mid = 0 ;
{
@ -1379,6 +1520,7 @@ void p3GRouter::handleIncomingReceiptItem(RsGRouterSignedReceiptItem *receipt_it
std::cerr << " ERROR: no routing ID corresponds to this message. Inconsistency!" << std::endl;
return ;
}
signer_id = it->second.data_item->signature.keyId ;
// check hash.
@ -1435,7 +1577,7 @@ void p3GRouter::handleIncomingReceiptItem(RsGRouterSignedReceiptItem *receipt_it
#ifdef GROUTER_DEBUG
std::cerr << " notifying client " << (void*)client_service << " that msg " << std::hex << mid << std::dec << " was received." << std::endl;
#endif
client_service->notifyDataStatus(mid, GROUTER_CLIENT_SERVICE_DATA_STATUS_RECEIVED) ;
client_service->notifyDataStatus(mid, signer_id, GROUTER_CLIENT_SERVICE_DATA_STATUS_RECEIVED) ;
}
// also note the incoming route in the routing matrix
@ -1830,7 +1972,11 @@ bool p3GRouter::verifySignedDataItem(RsGRouterAbstractMsgItem *item)
{
try
{
RsTlvSecurityKey signature_key ;
if(rsReputations->isIdentityBanned(item->signature.keyId))
{
std::cerr << "(WW) received global router message from banned identity " << item->signature.keyId << ". Rejecting the message." << std::endl;
return false ;
}
uint32_t data_size = item->signed_data_size() ;
RsTemporaryMemory data(data_size) ;
@ -1843,12 +1989,20 @@ bool p3GRouter::verifySignedDataItem(RsGRouterAbstractMsgItem *item)
uint32_t error_status ;
if(!mGixs->validateData(data,data_size,item->signature,true,error_status))
{
switch(error_status)
{
case RsGixs::RS_GIXS_ERROR_KEY_NOT_AVAILABLE: std::cerr << "(EE) Key for GXS Id " << item->signature.keyId << " is not available. Cannot verify." << std::endl;
case RsGixs::RS_GIXS_ERROR_KEY_NOT_AVAILABLE:
{
std::list<RsPeerId> peer_ids ;
peer_ids.push_back(item->PeerId()) ;
std::cerr << "(EE) Key for GXS Id " << item->signature.keyId << " is not available. Cannot verify. Asking key to peer " << item->PeerId() << std::endl;
mGixs->requestKey(item->signature.keyId,peer_ids) ; // request the key around
}
break ;
case RsGixs::RS_GIXS_ERROR_SIGNATURE_MISMATCH: std::cerr << "(EE) Signature mismatch. Spoofing/Corrupted/MITM?." << std::endl;
break ;
@ -1927,7 +2081,7 @@ bool p3GRouter::sendData(const RsGxsId& destination,const GRouterServiceId& clie
data_item->data_size = data_size ;
data_item->routing_id = propagation_id ;
data_item->randomized_distance = 0 ;
data_item->duplication_factor = GROUTER_MAX_DUPLICATION_FACTOR ;
data_item->service_id = client_id ;
data_item->destination_key = destination ;
data_item->flags = 0 ; // this is unused for now.
@ -1987,7 +2141,7 @@ bool p3GRouter::sendData(const RsGxsId& destination,const GRouterServiceId& clie
grouter_debug() << " data status = " << info.data_status << std::endl;
grouter_debug() << " tunnel status = " << info.tunnel_status << std::endl;
grouter_debug() << " sending attempt= " << info.sending_attempts << std::endl;
grouter_debug() << " distance = " << info.data_item->randomized_distance << std::endl;
grouter_debug() << " duplicate fact = " << info.data_item->duplication_factor << std::endl;
grouter_debug() << " recv time = " << info.received_time_TS << std::endl;
grouter_debug() << " client id = " << std::hex << data_item->service_id << std::dec << std::endl;
grouter_debug() << " tunnel hash = " << info.tunnel_hash << std::endl;
@ -2134,21 +2288,23 @@ bool p3GRouter::getRoutingMatrixInfo(RsGRouter::GRouterRoutingMatrixInfo& info)
info.friend_ids.clear() ;
info.published_keys.clear() ;
std::set<RsPeerId> ids ;
mServiceControl->getPeersConnected(getServiceInfo().mServiceType,ids) ;
std::list<RsPeerId> ids ;
//mServiceControl->getPeersConnected(getServiceInfo().mServiceType,ids) ;
rsPeers->getFriendList(ids) ;
info.published_keys = _owned_key_ids ;
for(std::set<RsPeerId>::const_iterator it(ids.begin());it!=ids.end();++it)
for(std::list<RsPeerId>::const_iterator it(ids.begin());it!=ids.end();++it)
info.friend_ids.push_back(*it) ;
std::vector<GRouterKeyId> known_keys ;
std::vector<float> probas ;
float maximum= 0.0f;
_routing_matrix.getListOfKnownKeys(known_keys) ;
for(uint32_t i=0;i<known_keys.size();++i)
{
_routing_matrix.computeRoutingProbabilities(known_keys[i],info.friend_ids,probas) ;
_routing_matrix.computeRoutingProbabilities(known_keys[i],info.friend_ids,probas,maximum) ;
info.per_friend_probabilities[known_keys[i]] = probas ;
}
@ -2167,6 +2323,7 @@ bool p3GRouter::getRoutingCacheInfo(std::vector<GRouterRoutingCacheInfo>& infos)
cinfo.mid = it->first ;
cinfo.local_origin = it->second.incoming_routes.ids ;
cinfo.destination = it->second.data_item->destination_key ;
cinfo.duplication_factor = it->second.data_item->duplication_factor ;
cinfo.routing_time = it->second.received_time_TS ;
cinfo.last_tunnel_attempt_time = it->second.last_tunnel_request_TS ;
cinfo.last_sent_time = it->second.last_sent_TS ;
@ -2220,15 +2377,16 @@ void p3GRouter::debugDump()
{
grouter_debug() << " Msg id: " << std::hex << it->first << std::dec ;
grouter_debug() << " data hash: " << it->second.item_hash ;
grouter_debug() << " client id: " << std::hex << it->second.client_id << std::dec;
grouter_debug() << " client: " << std::hex << it->second.client_id << std::dec;
grouter_debug() << " Flags: " << std::hex << it->second.routing_flags << std::dec;
grouter_debug() << " Destination: " << it->second.data_item->destination_key ;
grouter_debug() << " Received: " << now - it->second.received_time_TS << " secs ago.";
grouter_debug() << " Last sent: " << now - it->second.last_sent_TS << " secs ago.";
grouter_debug() << " Transaction TS: " << now - it->second.data_transaction_TS << " secs ago.";
grouter_debug() << " Data Status: " << statusString[it->second.data_status] << std::endl;
grouter_debug() << " Tunl Status: " << statusString[it->second.tunnel_status] << std::endl;
grouter_debug() << " Receipt ok: " << (it->second.receipt_item != NULL) << std::endl;
grouter_debug() << " Dest: " << it->second.data_item->destination_key ;
grouter_debug() << " Recd: " << now - it->second.received_time_TS << " secs ago.";
grouter_debug() << " Sent: " << now - it->second.last_sent_TS << " secs ago.";
grouter_debug() << " Trans. TS: " << now - it->second.data_transaction_TS << " secs ago." ;
grouter_debug() << " Data Status: " << statusString[it->second.data_status] ;
grouter_debug() << " Tunl Status: " << statusString[it->second.tunnel_status] ;
grouter_debug() << " Receipt ok: " << (it->second.receipt_item != NULL) ;
grouter_debug() << " Dup: " << it->second.data_item->duplication_factor << std::endl;
}
grouter_debug() << " Tunnels: " << std::endl;
@ -2251,8 +2409,8 @@ void p3GRouter::debugDump()
grouter_debug() << " Routing matrix: " << std::endl;
if(_debug_enabled)
_routing_matrix.debugDump() ;
// if(_debug_enabled)
// _routing_matrix.debugDump() ;
}

View File

@ -272,8 +272,9 @@ private:
//bool locked_getGxsIdAndClientId(const TurtleFileHash &sum,RsGxsId& gxs_id,GRouterServiceId& client_id);
bool locked_sendTransactionData(const RsPeerId& pid,const RsGRouterTransactionItem& item);
void locked_collectAvailableFriends(const GRouterKeyId &gxs_id,std::list<RsPeerId>& friend_peers, const std::set<RsPeerId>& incoming_routes,bool is_origin);
void locked_collectAvailableTunnels(const TurtleFileHash& hash,std::list<RsPeerId>& tunnel_peers);
void locked_collectAvailableFriends(const GRouterKeyId &gxs_id, const std::set<RsPeerId>& incoming_routes,uint32_t duplication_factor, std::map<RsPeerId, uint32_t> &friend_peers_and_duplication_factors);
void locked_collectAvailableTunnels(const TurtleFileHash& hash, uint32_t total_duplication, std::map<RsPeerId, uint32_t> &tunnel_peers_and_duplication_factors);
void locked_sendToPeers(RsGRouterGenericDataItem *data_item, const std::map<RsPeerId, uint32_t> &peers_and_duplication_factors);
//===================================================//
// p3Config methods //

View File

@ -2365,7 +2365,10 @@ void RsGenExchange::publishGrps()
if(ggps.mIsUpdate)
mDataAccess->updateGroupData(grp);
else
mDataAccess->addGroupData(grp);
mDataAccess->addGroupData(grp);
if(mNetService!=NULL)
mNetService->subscribeStatusChanged(grpId,true) ;
}
else
{

View File

@ -221,6 +221,7 @@
#define NXS_NET_DEBUG_7 1
#define GIXS_CUT_OFF 0
//#define NXS_FRAG
// The constant below have a direct influence on how fast forums/channels/posted/identity groups propagate and on the overloading of queues:
//
@ -235,8 +236,9 @@
#define TRANSAC_TIMEOUT 2000 // In seconds. Has been increased to avoid epidemic transaction cancelling due to overloaded outqueues.
#define SECURITY_DELAY_TO_FORCE_CLIENT_REUPDATE 3600 // force re-update if there happens to be a large delay between our server side TS and the client side TS of friends
#define REJECTED_MESSAGE_RETRY_DELAY 24*3600 // re-try rejected messages every 24hrs. Most of the time this is because the peer's reputation has changed.
#define GROUP_STATS_UPDATE_DELAY 1800 // update unsubscribed group statistics every 30 mins
#define GROUP_STATS_UPDATE_NB_PEERS 2 // update unsubscribed group statistics every 30 mins
#define GROUP_STATS_UPDATE_DELAY 240 // update unsubscribed group statistics every 3 mins
#define GROUP_STATS_UPDATE_NB_PEERS 2 // number of peers to which the group stats are asked
#define MAX_ALLOWED_GXS_MESSAGE_SIZE 199000 // 200,000 bytes including signature and headers
// Debug system to allow to print only for some IDs (group, Peer, etc)
@ -245,7 +247,7 @@
static const RsPeerId peer_to_print = RsPeerId(std::string("")) ;
static const RsGxsGroupId group_id_to_print = RsGxsGroupId(std::string("" )) ; // use this to allow to this group id only, or "" for all IDs
static const uint32_t service_to_print = 0 ; // use this to allow to this service id only, or 0 for all services
static const uint32_t service_to_print = 0x215 ; // use this to allow to this service id only, or 0 for all services
// warning. Numbers should be SERVICE IDS (see serialiser/rsserviceids.h. E.g. 0x0215 for forums)
class nullstream: public std::ostream {};
@ -597,7 +599,7 @@ void RsGxsNetService::syncWithPeers()
grp->PeerId(*sit);
grp->updateTS = updateTS;
NxsBandwidthRecorder::recordEvent(mServType,grp) ;
//NxsBandwidthRecorder::recordEvent(mServType,grp) ;
#ifdef NXS_NET_DEBUG_5
GXSNETDEBUG_P_(*sit) << "Service "<< std::hex << ((mServiceInfo.mServiceType >> 8)& 0xffff) << std::dec << " sending global group TS of peer id: " << *sit << " ts=" << nice_time_stamp(time(NULL),updateTS) << " (secs ago) to himself" << std::endl;
@ -632,7 +634,11 @@ void RsGxsNetService::syncWithPeers()
sit = peers.begin();
float sending_probability = NxsBandwidthRecorder::computeCurrentSendingProbability() ;
// Jan. 26, 2016. This has been disabled, since GXS has been fixed, groups will not re-ask for data. So even if outqueues are filled up by multiple
// attempts of the same request, the transfer will eventually end up. The code for NxsBandwidthRecorder should be kept for a while,
// just in case.
// float sending_probability = NxsBandwidthRecorder::computeCurrentSendingProbability() ;
#ifdef NXS_NET_DEBUG_2
std::cerr << " syncWithPeers(): Sending probability = " << sending_probability << std::endl;
#endif
@ -688,22 +694,24 @@ void RsGxsNetService::syncWithPeers()
msg->grpId = grpId;
msg->updateTS = updateTS;
NxsBandwidthRecorder::recordEvent(mServType,msg) ;
//NxsBandwidthRecorder::recordEvent(mServType,msg) ;
if(RSRandom::random_f32() < sending_probability)
{
sendItem(msg);
//if(RSRandom::random_f32() < sending_probability)
//{
sendItem(msg);
#ifdef NXS_NET_DEBUG_5
GXSNETDEBUG_PG(*sit,grpId) << "Service "<< std::hex << ((mServiceInfo.mServiceType >> 8)& 0xffff) << std::dec << " sending global message TS of peer id: " << *sit << " ts=" << nice_time_stamp(time(NULL),updateTS) << " (secs ago) for group " << grpId << " to himself" << std::endl;
#endif
}
else
{
delete msg ;
#ifdef NXS_NET_DEBUG_0
GXSNETDEBUG_PG(*sit,grpId) << " cancel RsNxsSyncMsg req (last local update TS for group+peer) for grpId=" << grpId << " to peer " << *sit << ": not enough bandwidth." << std::endl;
#endif
}
//}
//else
//{
// delete msg ;
//#ifdef NXS_NET_DEBUG_0
// GXSNETDEBUG_PG(*sit,grpId) << " cancel RsNxsSyncMsg req (last local update TS for group+peer) for grpId=" << grpId << " to peer " << *sit << ": not enough bandwidth." << std::endl;
//#endif
//}
}
}
@ -897,7 +905,13 @@ void RsGxsNetService::subscribeStatusChanged(const RsGxsGroupId& grpId,bool subs
else
it->second->msgUpdateTS = 0 ; // reset!
// no need to update mGrpServerUpdateItem since the ::updateServerSyncTS() call will do it.
// We also update mGrpServerUpdateItem so as to trigger a new grp list exchange with friends (friends will send their known ClientTS which
// will be lower than our own grpUpdateTS, triggering our sending of the new subscribed grp list.
if(mGrpServerUpdateItem == NULL)
mGrpServerUpdateItem = new RsGxsServerGrpUpdateItem(mServType);
mGrpServerUpdateItem->grpUpdateTS = time(NULL) ;
}
bool RsGxsNetService::fragmentMsg(RsNxsMsg& msg, MsgFragments& msgFragments) const
@ -906,7 +920,8 @@ bool RsGxsNetService::fragmentMsg(RsNxsMsg& msg, MsgFragments& msgFragments) con
uint32_t msgSize = msg.msg.TlvSize();
uint32_t dataLeft = msgSize;
uint8_t nFragments = ceil(float(msgSize)/FRAGMENT_SIZE);
char buffer[FRAGMENT_SIZE];
RsTemporaryMemory buffer(FRAGMENT_SIZE);
int currPos = 0;
@ -972,10 +987,25 @@ RsNxsMsg* RsGxsNetService::deFragmentMsg(MsgFragments& msgFragments) const
if(msgFragments.size() == 1)
{
RsNxsMsg* m = msgFragments.front();
if(m->count > 1)
if(m->count > 1) // normally mcount should be exactly 1, but if not initialised (old versions) it's going to be 0
{
// delete everything
std::cerr << "(WW) Cannot deFragment message set. m->count=" << m->count << ", but msgFragments.size()=" << msgFragments.size() << ". Incomplete? Dropping all." << std::endl;
for(uint32_t i=0;i<msgFragments.size();++i)
delete msgFragments[i] ;
msgFragments.clear();
return NULL;
}
else
{
// single piece. No need to say anything. Just return it.
msgFragments.clear();
return m;
}
}
// first determine total size for binary data
@ -985,9 +1015,21 @@ RsNxsMsg* RsGxsNetService::deFragmentMsg(MsgFragments& msgFragments) const
for(; mit != msgFragments.end(); ++mit)
datSize += (*mit)->msg.bin_len;
char* data = new char[datSize];
RsTemporaryMemory data(datSize) ;
if(!data)
{
for(uint32_t i=0;i<msgFragments.size();++i)
delete msgFragments[i] ;
msgFragments.clear();
return NULL ;
}
uint32_t currPos = 0;
std::cerr << "(II) deFragmenting long message of size " << datSize << ", from " << msgFragments.size() << " pieces." << std::endl;
for(mit = msgFragments.begin(); mit != msgFragments.end(); ++mit)
{
RsNxsMsg* msg = *mit;
@ -1003,10 +1045,17 @@ RsNxsMsg* RsGxsNetService::deFragmentMsg(MsgFragments& msgFragments) const
msg->transactionNumber = m.transactionNumber;
msg->meta = m.meta;
delete[] data;
// now clean!
for(uint32_t i=0;i<msgFragments.size();++i)
delete msgFragments[i] ;
msgFragments.clear();
return msg;
}
// This is unused apparently, since groups are never large. Anyway, we keep it in case we need it.
RsNxsGrp* RsGxsNetService::deFragmentGrp(GrpFragments& grpFragments) const
{
if(grpFragments.empty()) return NULL;
@ -1265,7 +1314,7 @@ struct MsgFragCollate
bool operator()(RsNxsMsg* msg) { return msg->msgId == mMsgId;}
};
void RsGxsNetService::collateMsgFragments(MsgFragments fragments, std::map<RsGxsMessageId, MsgFragments>& partFragments) const
void RsGxsNetService::collateMsgFragments(MsgFragments& fragments, std::map<RsGxsMessageId, MsgFragments>& partFragments) const
{
// get all unique message Ids;
MsgFragments::iterator vit = fragments.begin();
@ -1359,31 +1408,33 @@ private:
bool RsGxsNetService::loadList(std::list<RsItem *> &load)
{
RS_STACK_MUTEX(mNxsMutex) ;
RS_STACK_MUTEX(mNxsMutex) ;
// The delete is done in StoreHere, if necessary
// The delete is done in StoreHere, if necessary
std::for_each(load.begin(), load.end(), StoreHere(mClientGrpUpdateMap, mClientMsgUpdateMap, mServerMsgUpdateMap, mGrpServerUpdateItem));
// We reset group statistics here. This is the best place since we know at this point which are all unsubscribed groups.
std::for_each(load.begin(), load.end(), StoreHere(mClientGrpUpdateMap, mClientMsgUpdateMap, mServerMsgUpdateMap, mGrpServerUpdateItem));
time_t now = time(NULL);
for(ClientMsgMap::iterator it = mClientMsgUpdateMap.begin();it!=mClientMsgUpdateMap.end();++it)
for(std::map<RsGxsGroupId,RsGxsMsgUpdateItem::MsgUpdateInfo>::const_iterator it2(it->second->msgUpdateInfos.begin());it2!=it->second->msgUpdateInfos.end();++it2)
{
RsGroupNetworkStatsRecord& gnsr = mGroupNetworkStats[it2->first] ;
time_t now = time(NULL);
for(std::map<RsGxsGroupId,RsGroupNetworkStatsRecord>::iterator it(mGroupNetworkStats.begin());it!=mGroupNetworkStats.end();++it)
{
// At each reload, we reset the count of visible messages. It will be rapidely restored to its real value from friends.
// At each reload, divide the last count by 2. This gradually flushes old information away.
it->second.max_visible_count = 0; // std::max(it2->second.message_count,gnsr.max_visible_count) ;
// the update time stamp is randomised so as not to ask all friends at once about group statistics.
it->second.update_TS = now - GROUP_STATS_UPDATE_DELAY + (RSRandom::random_u32()%(GROUP_STATS_UPDATE_DELAY/10)) ;
gnsr.max_visible_count = std::max(it2->second.message_count,gnsr.max_visible_count/2) ;
gnsr.update_TS = now - GROUP_STATS_UPDATE_DELAY + (RSRandom::random_u32()%(GROUP_STATS_UPDATE_DELAY/10)) ;
// Similarly, we remove all suppliers.
// Actual suppliers will come back automatically.
// Similarly, we remove some of the suppliers randomly. If they are
// actual suppliers, they will come back automatically. If they are
// not, they will be forgotten.
it->second.suppliers.clear() ;
}
if(RSRandom::random_f32() > 0.2)
gnsr.suppliers.insert(it->first) ;
}
return true;
return true;
}
#include <algorithm>
@ -1675,7 +1726,9 @@ void RsGxsNetService::data_tick()
if(mUpdateCounter >= 120) // 60 seconds
{
updateServerSyncTS();
#ifdef TO_REMOVE
updateClientSyncTS();
#endif
mUpdateCounter = 1;
}
else
@ -1733,6 +1786,7 @@ void RsGxsNetService::debugDump()
#endif
}
#ifdef TO_REMOVE
// This method is normally not needed, but we use it to correct possible inconsistencies in the updte time stamps
// on the client side.
@ -1770,6 +1824,7 @@ void RsGxsNetService::updateClientSyncTS()
}
}
}
#endif
void RsGxsNetService::updateServerSyncTS()
{
@ -1784,6 +1839,10 @@ void RsGxsNetService::updateServerSyncTS()
// retrieve all grps and update TS
mDataStore->retrieveGxsGrpMetaData(gxsMap);
#ifdef TO_REMOVE
// (cyril) This code is removed because it is inconsistent: the list of grps does not need to be updated when
// new posts arrive. The two (grp list and msg list) are handled independently.
// as a grp list server also note this is the latest item you have
if(mGrpServerUpdateItem == NULL)
mGrpServerUpdateItem = new RsGxsServerGrpUpdateItem(mServType);
@ -1792,6 +1851,7 @@ void RsGxsNetService::updateServerSyncTS()
// we have unsubscribed a group.
mGrpServerUpdateItem->grpUpdateTS = 0 ;
#endif
bool change = false;
// then remove from mServerMsgUpdateMap, all items that are not in the group list!
@ -1829,6 +1889,7 @@ void RsGxsNetService::updateServerSyncTS()
ServerMsgMap::iterator mapIT = mServerMsgUpdateMap.find(grpId);
RsGxsServerMsgUpdateItem* msui = NULL;
#ifdef TO_REMOVE
// That accounts for modification of the meta data.
if(mGrpServerUpdateItem->grpUpdateTS < grpMeta->mPublishTs)
@ -1838,6 +1899,7 @@ void RsGxsNetService::updateServerSyncTS()
#endif
mGrpServerUpdateItem->grpUpdateTS = grpMeta->mPublishTs;
}
#endif
if(mapIT == mServerMsgUpdateMap.end())
{
@ -1861,6 +1923,7 @@ void RsGxsNetService::updateServerSyncTS()
#endif
}
#ifdef TO_REMOVE
// This might be very inefficient with time. This is needed because an old message might have been received, so the last modification time
// needs to account for this so that a friend who hasn't
@ -1872,6 +1935,7 @@ void RsGxsNetService::updateServerSyncTS()
mGrpServerUpdateItem->grpUpdateTS = grpMeta->mRecvTS;
change = true;
}
#endif
}
// actual change in config settings, then save configuration
@ -2261,7 +2325,6 @@ void RsGxsNetService::locked_processCompletedIncomingTrans(NxsTransaction* tr)
GXSNETDEBUG_P_(tr->mTransaction->PeerId()) << " and updating mClientGrpUpdateMap for peer " << peerFrom << " of new time stamp " << nice_time_stamp(time(NULL),updateTS) << std::endl;
#endif
#warning should not we conservatively use the most recent one, in case the peer has reset its mServerGrpUpdate time?? What happens if the peer unsubscribed a recent group?
item->grpUpdateTS = updateTS;
item->peerId = peerFrom;
@ -2295,13 +2358,15 @@ void RsGxsNetService::locked_processCompletedIncomingTrans(NxsTransaction* tr)
std::cerr << "RsGxsNetService::processCompletedTransactions(): item did not caste to msg" << std::endl;
}
#ifdef NSXS_FRAG
std::map<RsGxsGroupId, MsgFragments > collatedMsgs;
collateMsgFragments(msgs, collatedMsgs);
#ifdef NXS_FRAG
// (cyril) This code does not work. Since we do not really need message fragmenting, I won't fix it.
std::map<RsGxsMessageId, MsgFragments > collatedMsgs;
collateMsgFragments(msgs, collatedMsgs); // this destroys msgs whatsoever and recovers memory when needed
msgs.clear();
std::map<RsGxsGroupId, MsgFragments >::iterator mit = collatedMsgs.begin();
std::map<RsGxsMessageId, MsgFragments >::iterator mit = collatedMsgs.begin();
for(; mit != collatedMsgs.end(); ++mit)
{
MsgFragments& f = mit->second;
@ -2310,6 +2375,7 @@ void RsGxsNetService::locked_processCompletedIncomingTrans(NxsTransaction* tr)
if(msg)
msgs.push_back(msg);
}
collatedMsgs.clear();
#endif
#ifdef NXS_NET_DEBUG_0
GXSNETDEBUG_PG(tr->mTransaction->PeerId(),grpId) << " ...and notifying observer of " << msgs.size() << " new messages." << std::endl;
@ -2542,7 +2608,12 @@ void RsGxsNetService::locked_genReqMsgTransaction(NxsTransaction* tr)
mDataStore->retrieveGxsGrpMetaData(grpMetaMap);
RsGxsGrpMetaData* grpMeta = grpMetaMap[grpId];
#warning TODO: what if grpMeta is NULL?
if(grpMeta == NULL) // this should not happen, but just in case...
{
std::cerr << "(EE) grpMeta is NULL in " << __PRETTY_FUNCTION__ << " line " << __LINE__ << ". This is very unexpected." << std::endl;
return ;
}
if(! (grpMeta->mSubscribeFlags & GXS_SERV::GROUP_SUBSCRIBE_SUBSCRIBED ))
{
// For unsubscribed groups, we update the timestamp something more recent, so that the group content will not be asked to the same
@ -2945,6 +3016,24 @@ void RsGxsNetService::locked_genReqGrpTransaction(NxsTransaction* tr)
if(!reqList.empty())
locked_pushGrpTransactionFromList(reqList, tr->mTransaction->PeerId(), transN);
else
{
ClientGrpMap::iterator it = mClientGrpUpdateMap.find(tr->mTransaction->PeerId());
RsGxsGrpUpdateItem* item = NULL;
if(it != mClientGrpUpdateMap.end())
item = it->second;
else
{
item = new RsGxsGrpUpdateItem(mServType);
mClientGrpUpdateMap.insert(std::make_pair(tr->mTransaction->PeerId(), item));
}
#ifdef NXS_NET_DEBUG_0
GXSNETDEBUG_P_(tr->mTransaction->PeerId()) << " reqList is empty, updating anyway ClientGrpUpdate TS for peer " << tr->mTransaction->PeerId() << " to: " << tr->mTransaction->updateTS << std::endl;
#endif
item->grpUpdateTS = tr->mTransaction->updateTS;
item->peerId = tr->mTransaction->PeerId();
IndicateConfigChanged();
}
}
void RsGxsNetService::locked_genSendGrpsTransaction(NxsTransaction* tr)
@ -3162,37 +3251,52 @@ void RsGxsNetService::locked_genSendMsgsTransaction(NxsTransaction* tr)
uint32_t msgSize = 0;
for(;mit != msgs.end(); ++mit)
{
std::vector<RsNxsMsg*>& msgV = mit->second;
std::vector<RsNxsMsg*>::iterator vit = msgV.begin();
{
std::vector<RsNxsMsg*>& msgV = mit->second;
std::vector<RsNxsMsg*>::iterator vit = msgV.begin();
for(; vit != msgV.end(); ++vit)
{
RsNxsMsg* msg = *vit;
msg->PeerId(peerId);
msg->transactionNumber = transN;
for(; vit != msgV.end(); ++vit)
{
RsNxsMsg* msg = *vit;
msg->PeerId(peerId);
msg->transactionNumber = transN;
#ifndef NXS_FRAG
newTr->mItems.push_back(msg);
msgSize++;
// Quick trick to clamp messages with an exceptionnally large size. Signature will fail on client side, and the message
// will be rejected.
if(msg->msg.bin_len > MAX_ALLOWED_GXS_MESSAGE_SIZE)
{
std::cerr << "(WW) message with ID " << msg->msgId << " in group " << msg->grpId << " exceeds size limit of " << MAX_ALLOWED_GXS_MESSAGE_SIZE << " bytes. Actual size is " << msg->msg.bin_len << " bytes. Message will be truncated and rejected at client." << std::endl;
msg->msg.bin_len = 1 ; // arbitrary small size, but not 0. No need to send the data since it's going to be rejected.
}
#ifdef NXS_FRAG
MsgFragments fragments;
fragmentMsg(*msg, fragments);
delete msg ;
MsgFragments::iterator mit = fragments.begin();
for(; mit != fragments.end(); ++mit)
{
newTr->mItems.push_back(*mit);
msgSize++;
}
#else
MsgFragments fragments;
fragmentMsg(*msg, fragments);
msg->count = 1; // only one piece. This is to keep compatibility if we ever implement fragmenting in the future.
msg->pos = 0;
MsgFragments::iterator mit = fragments.begin();
for(; mit != fragments.end(); ++mit)
{
newTr->mItems.push_back(*mit);
msgSize++;
}
newTr->mItems.push_back(msg);
msgSize++;
#endif
}
}
if(newTr->mItems.empty()){
delete newTr;
return;
}
}
}
if(newTr->mItems.empty()){
delete newTr;
return;
}
// now if transaction is limited to an external group, encrypt it for members of the group.
@ -3553,6 +3657,10 @@ void RsGxsNetService::locked_pushGrpRespFromList(std::list<RsNxsItem*>& respList
trItem->timestamp = 0;
trItem->PeerId(peer);
trItem->transactionNumber = transN;
#ifdef NXS_NET_DEBUG_0
GXSNETDEBUG_P_ (peer) << "Setting tr->mTransaction->updateTS to " << mGrpServerUpdateItem->grpUpdateTS << std::endl;
#endif
trItem->updateTS = mGrpServerUpdateItem->grpUpdateTS;
// also make a copy for the resident transaction
tr->mTransaction = new RsNxsTransacItem(*trItem);
tr->mTransaction->PeerId(mOwnId);
@ -3921,13 +4029,20 @@ bool RsGxsNetService::locked_CanReceiveUpdate(const RsNxsSyncMsgReqItem *item)
}
void RsGxsNetService::handleRecvSyncMessage(RsNxsSyncMsgReqItem *item)
{
if (!item)
return;
if (!item)
return;
RS_STACK_MUTEX(mNxsMutex) ;
RS_STACK_MUTEX(mNxsMutex) ;
const RsPeerId& peer = item->PeerId();
// Insert the PeerId in suppliers list for this grpId
#ifdef NXS_NET_DEBUG_6
GXSNETDEBUG_PG(item->PeerId(),item->grpId) << "RsGxsNetService::handleRecvSyncMessage(): Inserting PeerId " << item->PeerId() << " in suppliers list for group " << item->grpId << std::endl;
#endif
RsGroupNetworkStatsRecord& rec(mGroupNetworkStats[item->grpId]) ; // this creates it if needed
rec.suppliers.insert(peer) ;
#ifdef NXS_NET_DEBUG_0
GXSNETDEBUG_PG(item->PeerId(),item->grpId) << "handleRecvSyncMsg(): Received last update TS of group " << item->grpId << ", for peer " << peer << ", TS = " << time(NULL) - item->updateTS << " secs ago." ;
#endif

View File

@ -378,7 +378,9 @@ private:
void locked_doMsgUpdateWork(const RsNxsTransacItem* nxsTrans, const RsGxsGroupId& grpId);
void updateServerSyncTS();
#ifdef TO_REMOVE
void updateClientSyncTS();
#endif
bool locked_CanReceiveUpdate(const RsNxsSyncGrpReqItem *item);
bool locked_CanReceiveUpdate(const RsNxsSyncMsgReqItem* item);
@ -433,7 +435,7 @@ private:
* @param fragments message fragments which are not necessarily from the same message
* @param partFragments the partitioned fragments (into message ids)
*/
void collateMsgFragments(MsgFragments fragments, std::map<RsGxsMessageId, MsgFragments>& partFragments) const;
void collateMsgFragments(MsgFragments &fragments, std::map<RsGxsMessageId, MsgFragments>& partFragments) const;
/*!
* Note that if all fragments for a group are not found then its fragments are dropped

View File

@ -28,6 +28,7 @@
#include "rsgxsutil.h"
#include "retroshare/rsgxsflags.h"
#include "retroshare/rspeers.h"
#include "retroshare/rsreputations.h"
#include "pqi/pqihash.h"
#include "gxs/rsgixs.h"
@ -161,7 +162,8 @@ bool RsGxsIntegrityCheck::check()
std::cerr << "TimeStamping group authors' key ID " << grp->metaData->mAuthorId << " in group ID " << grp->grpId << std::endl;
#endif
used_gxs_ids.insert(grp->metaData->mAuthorId) ;
if(rsReputations!=NULL && !rsReputations->isIdentityBanned(grp->metaData->mAuthorId))
used_gxs_ids.insert(grp->metaData->mAuthorId) ;
}
}
}
@ -242,7 +244,8 @@ bool RsGxsIntegrityCheck::check()
#ifdef GXSUTIL_DEBUG
std::cerr << "TimeStamping message authors' key ID " << msg->metaData->mAuthorId << " in message " << msg->msgId << ", group ID " << msg->grpId<< std::endl;
#endif
used_gxs_ids.insert(msg->metaData->mAuthorId) ;
if(rsReputations!=NULL && !rsReputations->isIdentityBanned(msg->metaData->mAuthorId))
used_gxs_ids.insert(msg->metaData->mAuthorId) ;
}
delete msg;

View File

@ -53,7 +53,8 @@ static const uint32_t RS_GXS_TUNNEL_DH_STATUS_UNINITIALIZED = 0x0000 ;
static const uint32_t RS_GXS_TUNNEL_DH_STATUS_HALF_KEY_DONE = 0x0001 ;
static const uint32_t RS_GXS_TUNNEL_DH_STATUS_KEY_AVAILABLE = 0x0002 ;
static const uint32_t RS_GXS_TUNNEL_DELAY_BETWEEN_RESEND = 10 ; // re-send every 10 secs.
static const uint32_t RS_GXS_TUNNEL_DELAY_BETWEEN_RESEND = 10 ; // re-send every 10 secs.
static const uint32_t RS_GXS_TUNNEL_DATA_PRINT_STORAGE_DELAY = 600 ; // store old message ids for 10 minutes.
static const uint32_t GXS_TUNNEL_ENCRYPTION_HMAC_SIZE = SHA_DIGEST_LENGTH ;
static const uint32_t GXS_TUNNEL_ENCRYPTION_IV_SIZE = 8 ;
@ -73,9 +74,6 @@ p3GxsTunnelService::p3GxsTunnelService(RsGixs *pids)
: mGixs(pids), mGxsTunnelMtx("GXS tunnel")
{
mTurtle = NULL ;
// any value is fine here, even 0, since items in different RS sessions will use different AES keys.
global_item_counter = 0;//RSRandom::random_u64() ;
}
void p3GxsTunnelService::connectToTurtleRouter(p3turtle *tr)
@ -103,7 +101,6 @@ bool p3GxsTunnelService::registerClientService(uint32_t service_id,RsGxsTunnelSe
int p3GxsTunnelService::tick()
{
static time_t last_dump = 0 ;
#ifdef DEBUG_GXS_TUNNEL
time_t now = time(NULL);
@ -196,7 +193,9 @@ void p3GxsTunnelService::flush()
for(std::map<RsGxsTunnelId,GxsTunnelPeerInfo>::iterator it(_gxs_tunnel_contacts.begin());it!=_gxs_tunnel_contacts.end();)
{
// Remove any tunnel that was remotely closed, since we cannot use it anymore.
// All sorts of cleaning. We start with the ones that may remove stuff, for efficiency reasons.
// 1 - Remove any tunnel that was remotely closed, since we cannot use it anymore.
if(it->second.status == RS_GXS_TUNNEL_STATUS_REMOTELY_CLOSED && it->second.last_contact + 20 < now)
{
@ -207,6 +206,8 @@ void p3GxsTunnelService::flush()
continue ;
}
// 2 - re-digg tunnels that have died out of inaction
if(it->second.last_contact+20+GXS_TUNNEL_KEEP_ALIVE_TIMEOUT < now && it->second.status == RS_GXS_TUNNEL_STATUS_CAN_TALK)
{
#ifdef DEBUG_GXS_TUNNEL
@ -228,6 +229,9 @@ void p3GxsTunnelService::flush()
mTurtle->forceReDiggTunnels( randomHashFromDestinationGxsId(it->second.to_gxs_id) );
}
}
// send keep alive packets to active tunnels.
if(it->second.last_keep_alive_sent + GXS_TUNNEL_KEEP_ALIVE_TIMEOUT < now && it->second.status == RS_GXS_TUNNEL_STATUS_CAN_TALK)
{
RsGxsTunnelStatusItem *cs = new RsGxsTunnelStatusItem ;
@ -244,6 +248,23 @@ void p3GxsTunnelService::flush()
std::cerr << "(II) GxsTunnelService:: Sending keep alive packet to gxs id " << it->first << std::endl;
#endif
}
// clean old received data prints.
for(std::map<uint64_t,time_t>::iterator it2=it->second.received_data_prints.begin();it2!=it->second.received_data_prints.end();)
if(now > it2->second + RS_GXS_TUNNEL_DATA_PRINT_STORAGE_DELAY)
{
#ifdef DEBUG_GXS_TUNNEL
std::cerr << "(II) erasing old data print for message #" << it2->first << " in tunnel " << it->first << std::endl;
#endif
std::map<uint64_t,time_t>::iterator tmp(it2) ;
++tmp ;
it->second.received_data_prints.erase(it2) ;
it2 = tmp ;
}
else
++it2 ;
++it ;
}
}
@ -347,6 +368,16 @@ void p3GxsTunnelService::handleRecvTunnelDataItem(const RsGxsTunnelId& tunnel_id
it2->second.client_services.insert(item->service_id) ;
peer_from = it2->second.to_gxs_id ;
}
// Check if the item has already been received. This is necessary because we actually re-send items until an ACK is received. If the ACK gets lost (connection interrupted) the
// item may be received twice. This is conservative and ensure that no item is lost nor received twice.
if(it2->second.received_data_prints.find(item->unique_item_counter) != it2->second.received_data_prints.end())
{
std::cerr << "(WW) received the same data item #" << std::hex << item->unique_item_counter << std::dec << " twice in last 20 mins. Tunnel id=" << tunnel_id << ". Probably a replay. Item will be dropped." << std::endl;
return ;
}
it2->second.received_data_prints[item->unique_item_counter] = time(NULL) ;
}
if(service->acceptDataFromPeer(peer_from,tunnel_id))
@ -1325,7 +1356,7 @@ bool p3GxsTunnelService::sendData(const RsGxsTunnelId &tunnel_id, uint32_t servi
RsGxsTunnelDataItem *item = new RsGxsTunnelDataItem ;
item->unique_item_counter = global_item_counter++; // this allows to make the item unique
item->unique_item_counter = RSRandom::random_u64(); // this allows to make the item unique, except very rarely, we we don't care.
item->flags = 0; // not used yet.
item->service_id = service_id;
item->data_size = size; // encrypted data size

View File

@ -171,6 +171,7 @@ private:
RsTurtleGenericTunnelItem::Direction direction ; // specifiec wether we are client(managing the tunnel) or server.
TurtleFileHash hash ; // hash that is last used. This is necessary for handling tunnel establishment
std::set<uint32_t> client_services ;// services that used this tunnel
std::map<uint64_t,time_t> received_data_prints ; // list of recently received messages, to avoid duplicates. Kept for 20 mins at most.
uint32_t total_sent ;
uint32_t total_received ;
};
@ -252,8 +253,6 @@ private:
RsGixs *mGixs ;
RsMutex mGxsTunnelMtx ;
uint64_t global_item_counter ;
std::map<uint32_t,RsGxsTunnelClientService*> mRegisteredServices ;
void debug_dump();

View File

@ -1212,7 +1212,7 @@ bool p3NetMgrIMPL::setExtAddress(const struct sockaddr_storage &addr)
bool changed = false;
{
RsStackMutex stack(mNetMtx); /****** STACK LOCK MUTEX *******/
if (sockaddr_storage_same(mExtAddr, addr))
if (!sockaddr_storage_same(mExtAddr, addr))
{
changed = true;
}

View File

@ -25,6 +25,7 @@
#ifdef WINDOWS_SYS
#include "util/rswin.h"
#include "util/rsmemory.h"
#include <ws2tcpip.h>
#endif // WINDOWS_SYS

View File

@ -434,9 +434,9 @@ int pqipersongrp::removePeer(const RsPeerId& id)
std::map<RsPeerId, SearchModule *>::iterator it;
#ifdef PGRP_DEBUG
#endif
std::cerr << "pqipersongrp::removePeer() id: " << id;
std::cerr << std::endl;
#endif
RsStackMutex stack(coreMtx); /**************** LOCKED MUTEX ****************/

View File

@ -391,25 +391,26 @@ bool pqiSSLstore::encryptedSendItems(const std::list<RsItem*>& rsItemList)
std::list<RsItem*>::const_iterator it;
uint32_t sizeItems = 0, sizeItem = 0;
uint32_t offset = 0;
char* data = NULL;
for(it = rsItemList.begin(); it != rsItemList.end(); ++it)
sizeItems += rsSerialiser->size(*it);
if(*it != NULL)
sizeItems += rsSerialiser->size(*it);
data = new char[sizeItems];
RsTemporaryMemory data(sizeItems) ;
for(it = rsItemList.begin(); it != rsItemList.end(); ++it)
{
sizeItem = rsSerialiser->size(*it);
if(*it != NULL)
{
sizeItem = rsSerialiser->size(*it);
if(rsSerialiser->serialise(*it, (data+offset),&sizeItem))
offset += sizeItem;
else
std::cerr << "(EE) pqiSSLstore::encryptedSendItems(): One item did not serialize. The item is probably unknown from the serializer. Dropping the item. " << std::endl;
if(rsSerialiser->serialise(*it, &data[offset],&sizeItem))
offset += sizeItem;
else
std::cerr << "(EE) pqiSSLstore::encryptedSendItems(): One item did not serialize. The item is probably unknown from the serializer. Dropping the item. " << std::endl;
if (!(bio_flags & BIN_FLAGS_NO_DELETE))
delete *it;
}
if (!(bio_flags & BIN_FLAGS_NO_DELETE))
delete *it;
}
bool result = true;
@ -418,9 +419,6 @@ bool pqiSSLstore::encryptedSendItems(const std::list<RsItem*>& rsItemList)
else
result = false;
if(data != NULL)
delete[] data;
return result;
}

View File

@ -50,6 +50,7 @@ public:
time_t last_tunnel_attempt_time;
time_t last_sent_time;
bool receipt_available ;
uint32_t duplication_factor ;
uint32_t data_status ;
uint32_t tunnel_status ;
uint32_t data_size ;

View File

@ -1,7 +1,7 @@
#define RS_MAJOR_VERSION 0
#define RS_MINOR_VERSION 6
#define RS_BUILD_NUMBER 0
#define RS_BUILD_NUMBER_ADD "x" // <-- do we need this?
#define RS_BUILD_NUMBER_ADD ""
// The revision number should be the 4 first bytes of the git revision hash, which is obtained using:
// git log --pretty="%H" | head -1 | cut -c1-8

View File

@ -296,8 +296,17 @@ bool p3Peers::getPeerDetails(const RsPeerId& id, RsPeerDetails &d)
d.hiddenNodeAddress = ps.hiddenDomain;
d.hiddenNodePort = ps.hiddenPort;
d.hiddenType = ps.hiddenType;
d.localAddr = sockaddr_storage_iptostring(ps.localaddr);
d.localPort = sockaddr_storage_port(ps.localaddr);
if(sockaddr_storage_isnull(ps.localaddr)) // that happens if the address is not initialised.
{
d.localAddr = "INVALID_IP";
d.localPort = 0 ;
}
else
{
d.localAddr = sockaddr_storage_iptostring(ps.localaddr);
d.localPort = sockaddr_storage_port(ps.localaddr);
}
d.extAddr = "hidden";
d.extPort = 0;
d.dyndns = "";

View File

@ -1336,7 +1336,14 @@ int RsServer::StartupRetroShare()
false,false); // don't synchronise group automatic (need explicit group request)
// don't sync messages at all.
// Normally we wouldn't need this (we do in other service):
// mGxsIdService->setNetworkExchangeService(gxsid_ns) ;
// ...since GxsIds are propagated manually. But that requires the gen exchange of GXSids to
// constantly test that mNetService is not null. The call below is to make the service aware of the
// netService so that it can request the missing ids. We'll need to fix this.
mGxsIdService->setNes(gxsid_ns);
/**** GxsCircle service ****/
// create GXS Circle service

View File

@ -275,7 +275,7 @@ bool RsLoginHandler::tryAutoLogin(const RsPeerId& ssl_id,std::string& ssl_passwd
fseek(fp, 0, SEEK_SET);
dataptr = (char *) rs_malloc(datalen);
if(data_ptr == NULL)
if(dataptr == NULL)
{
fclose(fp);
return false;

View File

@ -354,7 +354,6 @@ int p3MsgService::checkOutgoingMessages()
* if online, send
*/
time_t now = time(NULL);
bool changed = false ;
std::list<RsMsgItem*> output_queue ;
@ -1853,7 +1852,7 @@ void p3MsgService::manageDistantPeers()
}
}
void p3MsgService::notifyDataStatus(const GRouterMsgPropagationId& id,uint32_t data_status)
void p3MsgService::notifyDataStatus(const GRouterMsgPropagationId& id, const RsGxsId &signer_id, uint32_t data_status)
{
if(data_status == GROUTER_CLIENT_SERVICE_DATA_STATUS_FAILED)
{
@ -1861,7 +1860,7 @@ void p3MsgService::notifyDataStatus(const GRouterMsgPropagationId& id,uint32_t d
std::cerr << "(WW) p3MsgService::notifyDataStatus: Global router tells us that item ID " << id << " could not be delivered on time." ;
std::map<GRouterMsgPropagationId,uint32_t>::iterator it = _ongoing_messages.find(id) ;
if(it == _ongoing_messages.end())
{
std::cerr << " (EE) cannot find pending message to acknowledge. Weird. grouter id = " << id << std::endl;
@ -1869,6 +1868,7 @@ void p3MsgService::notifyDataStatus(const GRouterMsgPropagationId& id,uint32_t d
}
uint32_t msg_id = it->second ;
std::cerr << " message id = " << msg_id << std::endl;
mDistantOutgoingMsgSigners[msg_id] = signer_id ; // this is needed because it's not saved in config, but we should probably include it in _ongoing_messages
std::map<uint32_t,RsMsgItem*>::iterator mit = msgOutgoing.find(msg_id) ;
@ -1992,7 +1992,15 @@ void p3MsgService::sendDistantMsgItem(RsMsgItem *msgitem)
{
RS_STACK_MUTEX(mMsgMtx) ;
signing_key_id = mDistantOutgoingMsgSigners[msgitem->msgId] ;
std::map<uint32_t,RsGxsId>::const_iterator it = mDistantOutgoingMsgSigners.find(msgitem->msgId) ;
if(it == mDistantOutgoingMsgSigners.end())
{
std::cerr << "(EE) no signer registered for distant message " << msgitem->msgId << ". Cannot send!" << std::endl;
return ;
}
signing_key_id = it->second ;
if(signing_key_id.isNull())
{
@ -2033,6 +2041,7 @@ void p3MsgService::sendDistantMsgItem(RsMsgItem *msgitem)
RS_STACK_MUTEX(mMsgMtx) ;
_ongoing_messages[grouter_message_id] = msgitem->msgId ;
}
IndicateConfigChanged(); // save _ongoing_messages
}

View File

@ -142,7 +142,7 @@ private:
virtual bool acceptDataFromPeer(const RsGxsId& gxs_id) ;
virtual void receiveGRouterData(const RsGxsId& destination_key,const RsGxsId& signing_key, GRouterServiceId &client_id, uint8_t *data, uint32_t data_size) ;
virtual void notifyDataStatus(const GRouterMsgPropagationId& msg_id,uint32_t data_status) ;
virtual void notifyDataStatus(const GRouterMsgPropagationId& msg_id,const RsGxsId& signer_id,uint32_t data_status) ;
// Utility functions

View File

@ -190,8 +190,6 @@ void p3rtt::sendPingMeasurements()
mServiceCtrl->getPeersConnected(getServiceInfo().mServiceType, idList);
double ts = getCurrentTS();
#ifdef DEBUG_RTT
std::cerr << "p3rtt::sendPingMeasurements() @ts: " << ts;
std::cerr << std::endl;
@ -205,7 +203,8 @@ void p3rtt::sendPingMeasurements()
std::cerr << "p3rtt::sendPingMeasurements() Pinging: " << *it;
std::cerr << std::endl;
#endif
double ts = getCurrentTS();
/* create the packet */
RsRttPingItem *pingPkt = new RsRttPingItem();
pingPkt->PeerId(*it);

View File

@ -1872,6 +1872,7 @@ void p3turtle::monitorTunnels(const RsFileHash& hash,RsTurtleClientService *clie
// No tunnels at start, but this triggers digging new tunnels.
//
_incoming_file_hashes[hash].tunnels.clear();
_incoming_file_hashes[hash].use_aggressive_mode = allow_multi_tunnels ;
// also should send associated request to the file transfer module.
_incoming_file_hashes[hash].last_digg_time = RSRandom::random_u32()%10 ;

View File

@ -28,6 +28,14 @@ win32 {
QMAKE_CFLAGS += -Wextra
QMAKE_CXXFLAGS += -Wextra
CONFIG(debug, debug|release) {
} else {
# Tell linker to use ASLR protection
QMAKE_LFLAGS += -Wl,-dynamicbase
# Tell linker to use DEP protection
QMAKE_LFLAGS += -Wl,-nxcompat
}
# solve linker warnings because of the order of the libraries
QMAKE_LFLAGS += -Wl,--start-group

View File

@ -182,7 +182,7 @@ bool XMLWrapper::readXML(const char *xml)
cleanup();
handleError(true, mLastErrorString);
mDocument = xmlReadDoc(BAD_CAST xml, "", NULL, /*XML_PARSE_NOERROR | XML_PARSE_NOWARNING | */XML_PARSE_COMPACT | XML_PARSE_NOENT | XML_PARSE_NOCDATA);
mDocument = xmlReadDoc(BAD_CAST xml, "", NULL, /*XML_PARSE_NOERROR | XML_PARSE_NOWARNING | */XML_PARSE_COMPACT | XML_PARSE_NOCDATA);
handleError(false, mLastErrorString);
if (mDocument) {

View File

@ -53,11 +53,11 @@ VOIPChatWidgetHolder::VOIPChatWidgetHolder(ChatWidget *chatWidget, VOIPNotify *n
QSize buttonSize = QSize(iconSize + QSize(3,3));
QIcon iconaudioListenToggleButton ;
iconaudioListenToggleButton.addPixmap(QPixmap(":/images/audio-volume-muted.png")) ;
iconaudioListenToggleButton.addPixmap(QPixmap(":/images/audio-volume-high.png"),QIcon::Normal,QIcon::On) ;
iconaudioListenToggleButton.addPixmap(QPixmap(":/images/audio-volume-high.png"),QIcon::Disabled,QIcon::On) ;
iconaudioListenToggleButton.addPixmap(QPixmap(":/images/audio-volume-high.png"),QIcon::Active,QIcon::On) ;
iconaudioListenToggleButton.addPixmap(QPixmap(":/images/audio-volume-high.png"),QIcon::Selected,QIcon::On) ;
iconaudioListenToggleButton.addPixmap(QPixmap(":/images/speaker_mute.png")) ;
iconaudioListenToggleButton.addPixmap(QPixmap(":/images/speaker.png"),QIcon::Normal,QIcon::On) ;
iconaudioListenToggleButton.addPixmap(QPixmap(":/images/speaker.png"),QIcon::Disabled,QIcon::On) ;
iconaudioListenToggleButton.addPixmap(QPixmap(":/images/speaker.png"),QIcon::Active,QIcon::On) ;
iconaudioListenToggleButton.addPixmap(QPixmap(":/images/speaker.png"),QIcon::Selected,QIcon::On) ;
audioListenToggleButton = new QToolButton ;
audioListenToggleButton->setIcon(iconaudioListenToggleButton) ;
@ -71,11 +71,11 @@ VOIPChatWidgetHolder::VOIPChatWidgetHolder(ChatWidget *chatWidget, VOIPNotify *n
audioListenToggleButton->setEnabled(false);
QIcon iconaudioCaptureToggleButton ;
iconaudioCaptureToggleButton.addPixmap(QPixmap(":/images/call-start.png")) ;
iconaudioCaptureToggleButton.addPixmap(QPixmap(":/images/call-hold.png"),QIcon::Normal,QIcon::On) ;
iconaudioCaptureToggleButton.addPixmap(QPixmap(":/images/call-hold.png"),QIcon::Disabled,QIcon::On) ;
iconaudioCaptureToggleButton.addPixmap(QPixmap(":/images/call-hold.png"),QIcon::Active,QIcon::On) ;
iconaudioCaptureToggleButton.addPixmap(QPixmap(":/images/call-hold.png"),QIcon::Selected,QIcon::On) ;
iconaudioCaptureToggleButton.addPixmap(QPixmap(":/images/phone.png")) ;
iconaudioCaptureToggleButton.addPixmap(QPixmap(":/images/microphone_mute.png"),QIcon::Normal,QIcon::On) ;
iconaudioCaptureToggleButton.addPixmap(QPixmap(":/images/microphone_mute.png"),QIcon::Disabled,QIcon::On) ;
iconaudioCaptureToggleButton.addPixmap(QPixmap(":/images/microphone_mute.png"),QIcon::Active,QIcon::On) ;
iconaudioCaptureToggleButton.addPixmap(QPixmap(":/images/microphone_mute.png"),QIcon::Selected,QIcon::On) ;
audioCaptureToggleButton = new QToolButton ;
audioCaptureToggleButton->setIcon(iconaudioCaptureToggleButton) ;
@ -88,11 +88,11 @@ VOIPChatWidgetHolder::VOIPChatWidgetHolder(ChatWidget *chatWidget, VOIPNotify *n
audioCaptureToggleButton->setToolTip(tr("Start Call"));
QIcon iconvideoCaptureToggleButton ;
iconvideoCaptureToggleButton.addPixmap(QPixmap(":/images/video-icon-on.png")) ;
iconvideoCaptureToggleButton.addPixmap(QPixmap(":/images/video-icon-off.png"),QIcon::Normal,QIcon::On) ;
iconvideoCaptureToggleButton.addPixmap(QPixmap(":/images/video-icon-off.png"),QIcon::Disabled,QIcon::On) ;
iconvideoCaptureToggleButton.addPixmap(QPixmap(":/images/video-icon-off.png"),QIcon::Active,QIcon::On) ;
iconvideoCaptureToggleButton.addPixmap(QPixmap(":/images/video-icon-off.png"),QIcon::Selected,QIcon::On) ;
iconvideoCaptureToggleButton.addPixmap(QPixmap(":/images/filmcam.png")) ;
iconvideoCaptureToggleButton.addPixmap(QPixmap(":/images/filmcam-off.png"),QIcon::Normal,QIcon::On) ;
iconvideoCaptureToggleButton.addPixmap(QPixmap(":/images/filmcam-off.png"),QIcon::Disabled,QIcon::On) ;
iconvideoCaptureToggleButton.addPixmap(QPixmap(":/images/filmcam-off.png"),QIcon::Active,QIcon::On) ;
iconvideoCaptureToggleButton.addPixmap(QPixmap(":/images/filmcam-off.png"),QIcon::Selected,QIcon::On) ;
videoCaptureToggleButton = new QToolButton ;
videoCaptureToggleButton->setIcon(iconvideoCaptureToggleButton) ;
@ -105,7 +105,7 @@ VOIPChatWidgetHolder::VOIPChatWidgetHolder(ChatWidget *chatWidget, VOIPNotify *n
videoCaptureToggleButton->setToolTip(tr("Start Video Call"));
hangupButton = new QToolButton ;
hangupButton->setIcon(QIcon(":/images/call-stop.png")) ;
hangupButton->setIcon(QIcon(":/images/phone_hangup.png")) ;
hangupButton->setIconSize(iconSize) ;
hangupButton->setMinimumSize(buttonSize) ;
hangupButton->setMaximumSize(buttonSize) ;
@ -116,11 +116,11 @@ VOIPChatWidgetHolder::VOIPChatWidgetHolder(ChatWidget *chatWidget, VOIPNotify *n
hangupButton->hide();
QIcon iconhideChatTextToggleButton ;
iconhideChatTextToggleButton.addPixmap(QPixmap(":/images/orange-bubble-64.png")) ;
iconhideChatTextToggleButton.addPixmap(QPixmap(":/images/white-bubble-64.png"),QIcon::Normal,QIcon::On) ;
iconhideChatTextToggleButton.addPixmap(QPixmap(":/images/white-bubble-64.png"),QIcon::Disabled,QIcon::On) ;
iconhideChatTextToggleButton.addPixmap(QPixmap(":/images/white-bubble-64.png"),QIcon::Active,QIcon::On) ;
iconhideChatTextToggleButton.addPixmap(QPixmap(":/images/white-bubble-64.png"),QIcon::Selected,QIcon::On) ;
iconhideChatTextToggleButton.addPixmap(QPixmap(":/images/chat-bubble.png")) ;
iconhideChatTextToggleButton.addPixmap(QPixmap(":/images/chat-bubble.png"),QIcon::Normal,QIcon::On) ;
iconhideChatTextToggleButton.addPixmap(QPixmap(":/images/chat-bubble.png"),QIcon::Disabled,QIcon::On) ;
iconhideChatTextToggleButton.addPixmap(QPixmap(":/images/chat-bubble.png"),QIcon::Active,QIcon::On) ;
iconhideChatTextToggleButton.addPixmap(QPixmap(":/images/chat-bubble.png"),QIcon::Selected,QIcon::On) ;
hideChatTextToggleButton = new QToolButton ;
hideChatTextToggleButton->setIcon(iconhideChatTextToggleButton) ;
@ -134,11 +134,11 @@ VOIPChatWidgetHolder::VOIPChatWidgetHolder(ChatWidget *chatWidget, VOIPNotify *n
hideChatTextToggleButton->setEnabled(false) ;
QIcon iconfullscreenToggleButton ;
iconfullscreenToggleButton.addPixmap(QPixmap(":/images/channels32.png")) ;
iconfullscreenToggleButton.addPixmap(QPixmap(":/images/folder-draft24.png"),QIcon::Normal,QIcon::On) ;
iconfullscreenToggleButton.addPixmap(QPixmap(":/images/folder-draft24.png"),QIcon::Disabled,QIcon::On) ;
iconfullscreenToggleButton.addPixmap(QPixmap(":/images/folder-draft24.png"),QIcon::Active,QIcon::On) ;
iconfullscreenToggleButton.addPixmap(QPixmap(":/images/folder-draft24.png"),QIcon::Selected,QIcon::On) ;
iconfullscreenToggleButton.addPixmap(QPixmap(":/images/fullscreen_arrows.png")) ;
iconfullscreenToggleButton.addPixmap(QPixmap(":/images/fullscreen.png"),QIcon::Normal,QIcon::On) ;
iconfullscreenToggleButton.addPixmap(QPixmap(":/images/fullscreen.png"),QIcon::Disabled,QIcon::On) ;
iconfullscreenToggleButton.addPixmap(QPixmap(":/images/fullscreen.png"),QIcon::Active,QIcon::On) ;
iconfullscreenToggleButton.addPixmap(QPixmap(":/images/fullscreen.png"),QIcon::Selected,QIcon::On) ;
fullscreenToggleButton = new QToolButton ;
fullscreenToggleButton->setIcon(iconfullscreenToggleButton) ;
@ -236,7 +236,7 @@ VOIPChatWidgetHolder::VOIPChatWidgetHolder(ChatWidget *chatWidget, VOIPNotify *n
videoCaptureToggleButtonFS->setToolTip(tr("Start Video Call"));
hangupButtonFS = new QToolButton(fullScreenFrame) ;
hangupButtonFS->setIcon(QIcon(":/images/call-stop.png")) ;
hangupButtonFS->setIcon(QIcon(":/images/phone_hangup.png")) ;
hangupButtonFS->setIconSize(iconSize) ;
hangupButtonFS->setMinimumSize(buttonSize) ;
hangupButtonFS->setMaximumSize(buttonSize) ;

View File

@ -1,18 +1,19 @@
<RCC>
<qresource prefix="/">
<file>images/audio-volume-high.png</file>
<file>images/muted_self.svg</file>
<file>images/audio-volume-muted.png</file>
<file>images/talking_on.svg</file>
<file>images/talking_off.svg</file>
<file>images/call-start.png</file>
<file>images/call-stop.png</file>
<file>images/call-hold.png</file>
<file>images/camera-on.png</file>
<file>images/camera-off.png</file>
<file>images/video-icon-big.png</file>
<file>images/video-icon-on.png</file>
<file>images/video-icon-off.png</file>
</qresource>
<qresource prefix="/">
<file>images/muted_self.svg</file>
<file>images/talking_on.svg</file>
<file>images/talking_off.svg</file>
<file>images/chat-bubble.png</file>
<file>images/filmcam.png</file>
<file>images/fullscreen.png</file>
<file>images/fullscreen_arrows.png</file>
<file>images/microphone.png</file>
<file>images/microphone_mute.png</file>
<file>images/phone.png</file>
<file>images/phone_hangup.png</file>
<file>images/speaker.png</file>
<file>images/speaker_mute.png</file>
<file>images/webcam.png</file>
<file>images/video-icon-big.png</file>
</qresource>
</RCC>

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 814 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 699 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 721 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.8 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 995 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.4 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 9.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 9.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 11 KiB

View File

@ -134,11 +134,36 @@
<source>Video Processing</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+43"/>
<source>Available bandwidth:</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+7"/>
<source>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Use this field to simulate the maximum bandwidth available so as to preview what the encoded video will look like with the corresponding compression rate.&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+3"/>
<source>KB/s</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+21"/>
<source>&lt;html&gt;&lt;head/&gt;&lt;body&gt;&lt;p&gt;Display encoded (and then decoded) frame, to check the codec&apos;s quality. If not selected, the image above only shows the frame that is grabbed from your camera.&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+3"/>
<source>preview</source>
<translation type="unfinished"></translation>
</message>
</context>
<context>
<name>AudioInputConfig</name>
<message>
<location filename="../gui/AudioInputConfig.cpp" line="+180"/>
<location filename="../gui/AudioInputConfig.cpp" line="+202"/>
<source>Continuous</source>
<translation type="unfinished"></translation>
</message>
@ -168,7 +193,7 @@
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../gui/AudioInputConfig.h" line="+93"/>
<location filename="../gui/AudioInputConfig.h" line="+94"/>
<source>VOIP</source>
<translation type="unfinished"></translation>
</message>
@ -460,7 +485,7 @@
<context>
<name>QObject</name>
<message>
<location filename="../VOIPPlugin.cpp" line="+125"/>
<location filename="../VOIPPlugin.cpp" line="+128"/>
<source>&lt;h3&gt;RetroShare VOIP plugin&lt;/h3&gt;&lt;br/&gt; * Contributors: Cyril Soler, Josselin Jacquard&lt;br/&gt;</source>
<translation type="unfinished"></translation>
</message>
@ -502,31 +527,111 @@
<source>This plugin provides voice communication between friends in RetroShare.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+40"/>
<location line="+4"/>
<location line="+4"/>
<location line="+4"/>
<source>VOIP</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="-11"/>
<source>Incoming audio call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+4"/>
<source>Incoming video call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+4"/>
<source>Outgoing audio call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+4"/>
<source>Outgoing video call</source>
<translation type="unfinished"></translation>
</message>
</context>
<context>
<name>VOIPChatWidgetHolder</name>
<message>
<location filename="../gui/VOIPChatWidgetHolder.cpp" line="+63"/>
<location filename="../gui/VOIPChatWidgetHolder.cpp" line="+70"/>
<location line="+146"/>
<source>Mute</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+13"/>
<location line="-128"/>
<location line="+138"/>
<source>Start Call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+28"/>
<location line="-121"/>
<location line="+131"/>
<source>Start Video Call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="-14"/>
<location line="-121"/>
<location line="+131"/>
<source>Hangup Call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+79"/>
<location line="-113"/>
<location line="+626"/>
<source>Hide Chat Text</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="-608"/>
<location line="+106"/>
<location line="+523"/>
<source>Fullscreen mode</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="-412"/>
<source>%1 inviting you to start an audio conversation. Do you want Accept or Decline the invitation?</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+2"/>
<source>Accept Audio Call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+17"/>
<source>Decline Audio Call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+1"/>
<source>Refuse audio call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+33"/>
<source>%1 inviting you to start a video conversation. Do you want Accept or Decline the invitation?</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+19"/>
<source>Decline Video Call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+1"/>
<source>Refuse video call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+102"/>
<source>Mute yourself</source>
<translation type="unfinished"></translation>
</message>
@ -536,83 +641,129 @@
<translation type="unfinished"></translation>
</message>
<message>
<location line="+19"/>
<location line="+37"/>
<location line="+38"/>
<location line="+18"/>
<location line="+13"/>
<location line="+92"/>
<location line="+589"/>
<source>Waiting your friend respond your video call.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+14"/>
<source>Your friend is calling you for video. Respond.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="-781"/>
<location line="+53"/>
<location line="+188"/>
<location line="+24"/>
<location line="+57"/>
<location line="+28"/>
<location line="+284"/>
<location line="+11"/>
<location line="+11"/>
<location line="+21"/>
<location line="+11"/>
<source>VoIP Status</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="-198"/>
<source>Outgoing Call stopped.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+19"/>
<location line="-467"/>
<source>Hold Call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+18"/>
<location line="+20"/>
<source>Outgoing Call is started...</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+15"/>
<location line="+9"/>
<source>Resume Call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+20"/>
<location line="+16"/>
<source>Outgoing Audio Call stopped.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+46"/>
<source>Shut camera off</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+4"/>
<location line="+11"/>
<source>You&apos;re now sending video...</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+12"/>
<location line="+21"/>
<location line="-266"/>
<location line="+279"/>
<source>Activate camera</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="-15"/>
<location line="+15"/>
<source>Video call stopped</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+13"/>
<source>%1 inviting you to start a video conversation. do you want Accept or Decline the invitation?</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+1"/>
<location line="-295"/>
<source>Accept Video Call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+91"/>
<source>%1 inviting you to start a audio conversation. do you want Accept or Decline the invitation?</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+1"/>
<source>Accept Call</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+1"/>
<location line="-52"/>
<source>Activate audio</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+384"/>
<source>Show Chat Text</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+19"/>
<source>Return to normal view.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+228"/>
<source>%1 hang up. Your call is closed.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+11"/>
<source>%1 hang up. Your audio call is closed.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+11"/>
<source>%1 hang up. Your video call is closed.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+21"/>
<source>%1 accepted your audio call.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+11"/>
<source>%1 accepted your video call.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+20"/>
<source>Waiting your friend respond your audio call.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+14"/>
<source>Your friend is calling you for audio. Respond.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location line="+17"/>
<location line="+58"/>
<source>Answer</source>
<translation type="unfinished"></translation>
</message>
@ -620,7 +771,7 @@
<context>
<name>VOIPPlugin</name>
<message>
<location filename="../VOIPPlugin.cpp" line="+5"/>
<location filename="../VOIPPlugin.cpp" line="-48"/>
<source>VOIP</source>
<translation type="unfinished"></translation>
</message>
@ -637,6 +788,11 @@
<source>Answer with video</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../gui/VOIPToasterItem.ui" line="+232"/>
<source>Decline</source>
<translation type="unfinished"></translation>
</message>
</context>
<context>
<name>VOIPToasterNotify</name>
@ -750,7 +906,7 @@
<context>
<name>voipGraphSource</name>
<message>
<location filename="../gui/AudioInputConfig.cpp" line="-236"/>
<location filename="../gui/AudioInputConfig.cpp" line="-260"/>
<source>Required bandwidth</source>
<translation type="unfinished"></translation>
</message>

Binary file not shown.

View File

@ -588,7 +588,7 @@
<message>
<location line="+13"/>
<source>%1 inviting you to start a video conversation. do you want Accept or Decline the invitation?</source>
<translation>%1 le está invitando a iniciar una conversación de vídeo. ¿Quiere aceptar o declinar la invitación?</translation>
<translation>%1 le está invitando a iniciar una conversación de vídeo. ¿Quiere aceptar o rechazar la invitación?</translation>
</message>
<message>
<location line="+1"/>

Binary file not shown.

View File

@ -508,7 +508,7 @@
<message>
<location filename="../gui/VOIPChatWidgetHolder.cpp" line="+63"/>
<source>Mute</source>
<translation type="unfinished"/>
<translation>Muto</translation>
</message>
<message>
<location line="+13"/>
@ -518,7 +518,7 @@
<message>
<location line="+28"/>
<source>Start Video Call</source>
<translation type="unfinished"/>
<translation>Inizia una Video Chiamata</translation>
</message>
<message>
<location line="-14"/>
@ -548,7 +548,7 @@
<message>
<location line="-198"/>
<source>Outgoing Call stopped.</source>
<translation type="unfinished"/>
<translation>Chiamata in uscita terminata.</translation>
</message>
<message>
<location line="+19"/>
@ -568,48 +568,48 @@
<message>
<location line="+20"/>
<source>Shut camera off</source>
<translation type="unfinished"/>
<translation>Spegni webcam/videocamera</translation>
</message>
<message>
<location line="+4"/>
<source>You&apos;re now sending video...</source>
<translation type="unfinished"/>
<translation>Invio video in corso...</translation>
</message>
<message>
<location line="+12"/>
<location line="+21"/>
<source>Activate camera</source>
<translation type="unfinished"/>
<translation>Attiva webcam/videocamera</translation>
</message>
<message>
<location line="-15"/>
<source>Video call stopped</source>
<translation type="unfinished"/>
<translation>Video chiamata terminata</translation>
</message>
<message>
<location line="+13"/>
<source>%1 inviting you to start a video conversation. do you want Accept or Decline the invitation?</source>
<translation type="unfinished"/>
<translation>%1 vuole iniziare una conversazione video con te. Accetti o Rifiuti l&apos;invito?</translation>
</message>
<message>
<location line="+1"/>
<source>Accept Video Call</source>
<translation type="unfinished"/>
<translation>Accetta Video Chiamata</translation>
</message>
<message>
<location line="+91"/>
<source>%1 inviting you to start a audio conversation. do you want Accept or Decline the invitation?</source>
<translation type="unfinished"/>
<translation>%1 vuole iniziare una conversazione audio con te. Accetti o Rifiuti l&apos;invito?</translation>
</message>
<message>
<location line="+1"/>
<source>Accept Call</source>
<translation type="unfinished"/>
<translation>Accetta Chiamata</translation>
</message>
<message>
<location line="+1"/>
<source>Activate audio</source>
<translation type="unfinished"/>
<translation>Attiva audio</translation>
</message>
<message>
<location line="+21"/>
@ -635,7 +635,7 @@
<message>
<location line="+4"/>
<source>Answer with video</source>
<translation type="unfinished"/>
<translation>Rispondi con video</translation>
</message>
</context>
<context>
@ -653,12 +653,12 @@
<message>
<location line="+1"/>
<source>Bandwidth Information</source>
<translation type="unfinished"/>
<translation>Informazioni Larghezza Banda</translation>
</message>
<message>
<location line="+1"/>
<source>Audio or Video Data</source>
<translation type="unfinished"/>
<translation>Informazioni Audio o Video</translation>
</message>
<message>
<location line="+1"/>
@ -668,17 +668,17 @@
<message>
<location line="+1"/>
<source>Invitation</source>
<translation type="unfinished"/>
<translation>Invito</translation>
</message>
<message>
<location line="+2"/>
<source>Audio Call</source>
<translation type="unfinished"/>
<translation>Audio Chiamata</translation>
</message>
<message>
<location line="+1"/>
<source>Video Call</source>
<translation type="unfinished"/>
<translation>Video Chiamata</translation>
</message>
<message>
<location line="+110"/>
@ -744,7 +744,7 @@
<location line="+25"/>
<location line="+24"/>
<source>calling</source>
<translation type="unfinished"/>
<translation>in chiamata</translation>
</message>
</context>
</TS>

View File

@ -26,16 +26,16 @@
#include "rshare.h"
#include "SearchDialog.h"
#include "RetroShareLink.h"
#include "msgs/MessageComposer.h"
#include "gui/RSHumanReadableDelegate.h"
#include "gui/RetroShareLink.h"
#include "retroshare-gui/RsAutoUpdatePage.h"
#include "gui/msgs/MessageComposer.h"
#include "gui/common/RsCollectionFile.h"
#include "gui/common/FilesDefs.h"
#include <gui/common/RsUrlHandler.h>
#include "settings/rsharesettings.h"
#include "advsearch/advancedsearchdialog.h"
#include "common/RSTreeWidgetItem.h"
#include "gui/common/RsUrlHandler.h"
#include "gui/settings/rsharesettings.h"
#include "gui/advsearch/advancedsearchdialog.h"
#include "gui/common/RSTreeWidgetItem.h"
#include "util/QtVersion.h"
#include <retroshare/rsfiles.h>
@ -857,7 +857,7 @@ void SearchDialog::searchKeywords(const QString& keywords)
req_id = rsTurtle->turtleSearch(lin_exp) ;
}
else
req_id = ((((uint32_t)rand()) << 16)^0x1e2fd5e4) + (((uint32_t)rand())^0x1b19acfe) ; // generate a random 32 bits request id
req_id = RSRandom::random_u32() ; // generate a random 32 bits request id
initSearchResult(keywords,req_id, ui.FileTypeComboBox->currentIndex(), false) ; // this will act before turtle results come to the interface, thanks to the signals scheduling policy.

View File

@ -43,7 +43,7 @@
#include "DLListDelegate.h"
#include "ULListDelegate.h"
#include "FileTransferInfoWidget.h"
#include <gui/SearchDialog.h>
#include <gui/FileTransfer/SearchDialog.h>
#include <gui/SharedFilesDialog.h>
#include "xprogressbar.h"
#include <gui/settings/rsharesettings.h>

View File

@ -87,7 +87,26 @@
#define RSID_FILTER_ALL 0xffff
#define IMAGE_EDIT ":/images/edit_16.png"
// quick solution for RSID_COL_VOTES sorting
class TreeWidgetItem : public QTreeWidgetItem {
public:
TreeWidgetItem(int type=Type): QTreeWidgetItem(type) {}
TreeWidgetItem(QTreeWidget *tree): QTreeWidgetItem(tree) {}
TreeWidgetItem(const QStringList& strings): QTreeWidgetItem (strings) {}
bool operator< (const QTreeWidgetItem& other ) const {
int column = treeWidget()->sortColumn();
const QVariant v1 = data(column, Qt::DisplayRole);
const QVariant v2 = other.data(column, Qt::DisplayRole);
double value1 = v1.toDouble();
double value2 = v2.toDouble();
if (value1 != value2) {
return value1 < value2;
}
else {
return (v1.toString().compare (v2.toString(), Qt::CaseInsensitive) < 0);
}
}
};
/** Constructor */
IdDialog::IdDialog(QWidget *parent) :
RsGxsUpdateBroadcastPage(rsIdentity, parent),
@ -637,7 +656,7 @@ bool IdDialog::fillIdListItem(const RsGxsIdGroup& data, QTreeWidgetItem *&item,
return false;
if (!item)
item = new QTreeWidgetItem();
item = new TreeWidgetItem();
RsReputations::ReputationInfo info ;
rsReputations->getReputationInfo(RsGxsId(data.mMeta.mGroupId),info) ;
@ -1225,105 +1244,133 @@ void IdDialog::loadRequest(const TokenQueue * queue, const TokenRequest &req)
void IdDialog::IdListCustomPopupMenu( QPoint )
{
QMenu contextMnu( this );
QMenu contextMnu( this );
std::list<RsGxsId> own_identities ;
rsIdentity->getOwnIds(own_identities) ;
std::list<RsGxsId> own_identities ;
rsIdentity->getOwnIds(own_identities) ;
QTreeWidgetItem *item = ui->idTreeWidget->currentItem();
if(item != allItem && item != contactsItem) {
uint32_t item_flags = item->data(RSID_COL_KEYID,Qt::UserRole).toUInt() ;
// make some stats about what's selected. If the same value is used for all selected items, it can be switched.
if(!(item_flags & RSID_FILTER_OWNED_BY_YOU))
{
if(own_identities.size() <= 1)
{
QAction *action = contextMnu.addAction(QIcon(":/images/chat_24.png"), tr("Chat with this person"), this, SLOT(chatIdentity()));
QList<QTreeWidgetItem *> selected_items = ui->idTreeWidget->selectedItems();
if(own_identities.empty())
action->setEnabled(false) ;
else
action->setData(QString::fromStdString((own_identities.front()).toStdString())) ;
}
else
{
QMenu *mnu = contextMnu.addMenu(QIcon(":/images/chat_24.png"),tr("Chat with this person as...")) ;
bool root_node_present = false ;
bool one_item_owned_by_you = false ;
uint32_t n_positive_reputations = 0 ;
uint32_t n_negative_reputations = 0 ;
uint32_t n_neutral_reputations = 0 ;
uint32_t n_is_a_contact = 0 ;
uint32_t n_is_not_a_contact = 0 ;
uint32_t n_selected_items =0 ;
for(std::list<RsGxsId>::const_iterator it=own_identities.begin();it!=own_identities.end();++it)
{
RsIdentityDetails idd ;
rsIdentity->getIdDetails(*it,idd) ;
for(QList<QTreeWidgetItem*>::const_iterator it(selected_items.begin());it!=selected_items.end();++it)
{
if(*it == allItem || *it == contactsItem)
{
root_node_present = true ;
continue ;
}
QPixmap pixmap ;
uint32_t item_flags = (*it)->data(RSID_COL_KEYID,Qt::UserRole).toUInt() ;
if(idd.mAvatar.mSize == 0 || !pixmap.loadFromData(idd.mAvatar.mData, idd.mAvatar.mSize, "PNG"))
pixmap = QPixmap::fromImage(GxsIdDetails::makeDefaultIcon(*it)) ;
if(item_flags & RSID_FILTER_OWNED_BY_YOU)
one_item_owned_by_you = true ;
std::cerr << " item flags = " << item_flags << std::endl;
RsGxsId keyId((*it)->text(RSID_COL_KEYID).toStdString());
QAction *action = mnu->addAction(QIcon(pixmap), QString("%1 (%2)").arg(QString::fromUtf8(idd.mNickname.c_str()), QString::fromStdString((*it).toStdString())), this, SLOT(chatIdentity()));
action->setData(QString::fromStdString((*it).toStdString())) ;
}
}
RsReputations::ReputationInfo info ;
rsReputations->getReputationInfo(keyId,info) ;
contextMnu.addAction(QIcon(":/images/mail_new.png"), tr("Send message to this person"), this, SLOT(sendMsg()));
contextMnu.addSeparator();
switch(info.mOwnOpinion)
{
case RsReputations::OPINION_NEGATIVE: ++n_negative_reputations ;
break ;
case RsReputations::OPINION_POSITIVE: ++n_positive_reputations ;
break ;
case RsReputations::OPINION_NEUTRAL: ++n_neutral_reputations ;
break ;
}
RsIdentityDetails details;
std::string keyId = item->text(RSID_COL_KEYID).toStdString();
++n_selected_items ;
rsIdentity->getIdDetails(RsGxsId(keyId), details);
QAction *addContact = contextMnu.addAction(QIcon(), tr("Add to Contacts"), this, SLOT(addtoContacts()));
QAction *removeContact = contextMnu.addAction(QIcon(":/images/cancel.png"), tr("Remove from Contacts"), this, SLOT(removefromContacts()));
if(rsIdentity->isARegularContact(keyId))
++n_is_a_contact ;
else
++n_is_not_a_contact ;
}
if(details.mFlags & RS_IDENTITY_FLAGS_IS_A_CONTACT)
{
addContact->setVisible(false);
removeContact->setVisible(true);
}
else
{
addContact->setVisible(true);
removeContact->setVisible(false);
}
contextMnu.addSeparator();
if(root_node_present) // don't show menu if some of the root nodes are present
return ;
RsReputations::ReputationInfo info ;
std::string Id = item->text(RSID_COL_KEYID).toStdString();
rsReputations->getReputationInfo(RsGxsId(Id),info) ;
if(!one_item_owned_by_you)
{
if(n_selected_items == 1) // if only one item is selected, allow to chat with this item
if(own_identities.size() <= 1)
{
QAction *action = contextMnu.addAction(QIcon(":/images/chat_24.png"), tr("Chat with this person"), this, SLOT(chatIdentity()));
QAction *banaction = contextMnu.addAction(QIcon(":/images/denied16.png"), tr("Ban this person"), this, SLOT(banPerson()));
QAction *unbanaction = contextMnu.addAction(QIcon(), tr("Unban this person"), this, SLOT(unbanPerson()));
if(own_identities.empty())
action->setEnabled(false) ;
else
action->setData(QString::fromStdString((own_identities.front()).toStdString())) ;
}
else
{
QMenu *mnu = contextMnu.addMenu(QIcon(":/images/chat_24.png"),tr("Chat with this person as...")) ;
for(std::list<RsGxsId>::const_iterator it=own_identities.begin();it!=own_identities.end();++it)
{
RsIdentityDetails idd ;
rsIdentity->getIdDetails(*it,idd) ;
QPixmap pixmap ;
if(idd.mAvatar.mSize == 0 || !pixmap.loadFromData(idd.mAvatar.mData, idd.mAvatar.mSize, "PNG"))
pixmap = QPixmap::fromImage(GxsIdDetails::makeDefaultIcon(*it)) ;
QAction *action = mnu->addAction(QIcon(pixmap), QString("%1 (%2)").arg(QString::fromUtf8(idd.mNickname.c_str()), QString::fromStdString((*it).toStdString())), this, SLOT(chatIdentity()));
action->setData(QString::fromStdString((*it).toStdString())) ;
}
}
// always allow to send messages
contextMnu.addAction(QIcon(":/images/mail_new.png"), tr("Send message"), this, SLOT(sendMsg()));
contextMnu.addSeparator();
if(n_is_a_contact == 0)
contextMnu.addAction(QIcon(), tr("Add to Contacts"), this, SLOT(addtoContacts()));
if(n_is_not_a_contact == 0)
contextMnu.addAction(QIcon(":/images/cancel.png"), tr("Remove from Contacts"), this, SLOT(removefromContacts()));
contextMnu.addSeparator();
if(n_positive_reputations == 0) // only unban when all items are banned
contextMnu.addAction(QIcon(), tr("Set positive opinion"), this, SLOT(positivePerson()));
if(n_neutral_reputations == 0) // only unban when all items are banned
contextMnu.addAction(QIcon(), tr("Set neutral opinion"), this, SLOT(neutralPerson()));
if(n_negative_reputations == 0)
contextMnu.addAction(QIcon(":/images/denied16.png"), tr("Set negative opinion"), this, SLOT(negativePerson()));
}
if(one_item_owned_by_you && n_selected_items==1)
{
contextMnu.addSeparator();
contextMnu.addAction(ui->editIdentity);
contextMnu.addAction(ui->removeIdentity);
}
if(info.mAssessment == RsReputations::ASSESSMENT_BAD)
{
banaction->setVisible(false);
unbanaction->setVisible(true);
}
else
{
banaction->setVisible(true);
unbanaction->setVisible(false);
}
}
contextMnu.addSeparator();
contextMnu.addAction(ui->editIdentity);
contextMnu.addAction(ui->removeIdentity);
}
contextMnu.addSeparator();
contextMnu.exec(QCursor::pos());
contextMnu.exec(QCursor::pos());
}
void IdDialog::chatIdentity()
@ -1352,25 +1399,27 @@ void IdDialog::chatIdentity()
void IdDialog::sendMsg()
{
QTreeWidgetItem *item = ui->idTreeWidget->currentItem();
if (!item)
{
return;
}
QList<QTreeWidgetItem *> selected_items = ui->idTreeWidget->selectedItems();
MessageComposer *nMsgDialog = MessageComposer::newMsg();
if (nMsgDialog == NULL) {
return;
}
if(selected_items.empty())
return ;
std::string keyId = item->text(RSID_COL_KEYID).toStdString();
MessageComposer *nMsgDialog = MessageComposer::newMsg();
if (nMsgDialog == NULL)
return;
nMsgDialog->addRecipient(MessageComposer::TO, RsGxsId(keyId));
nMsgDialog->show();
nMsgDialog->activateWindow();
for(QList<QTreeWidgetItem*>::const_iterator it(selected_items.begin());it!=selected_items.end();++it)
{
QTreeWidgetItem *item = *it ;
std::string keyId = item->text(RSID_COL_KEYID).toStdString();
nMsgDialog->addRecipient(MessageComposer::TO, RsGxsId(keyId));
}
nMsgDialog->show();
nMsgDialog->activateWindow();
/* window will destroy itself! */
}
QString IdDialog::inviteMessage()
@ -1409,33 +1458,48 @@ void IdDialog::sendInvite()
}
void IdDialog::banPerson()
void IdDialog::negativePerson()
{
QTreeWidgetItem *item = ui->idTreeWidget->currentItem();
if (!item)
{
return;
}
QList<QTreeWidgetItem *> selected_items = ui->idTreeWidget->selectedItems();
for(QList<QTreeWidgetItem*>::const_iterator it(selected_items.begin());it!=selected_items.end();++it)
{
QTreeWidgetItem *item = *it ;
std::string Id = item->text(RSID_COL_KEYID).toStdString();
rsReputations->setOwnOpinion(RsGxsId(Id),RsReputations::OPINION_NEGATIVE) ;
}
requestIdDetails();
requestIdList();
}
void IdDialog::unbanPerson()
void IdDialog::neutralPerson()
{
QTreeWidgetItem *item = ui->idTreeWidget->currentItem();
if (!item)
{
return;
}
QList<QTreeWidgetItem *> selected_items = ui->idTreeWidget->selectedItems();
for(QList<QTreeWidgetItem*>::const_iterator it(selected_items.begin());it!=selected_items.end();++it)
{
QTreeWidgetItem *item = *it ;
std::string Id = item->text(RSID_COL_KEYID).toStdString();
rsReputations->setOwnOpinion(RsGxsId(Id),RsReputations::OPINION_NEUTRAL) ;
}
requestIdDetails();
requestIdList();
}
void IdDialog::positivePerson()
{
QList<QTreeWidgetItem *> selected_items = ui->idTreeWidget->selectedItems();
for(QList<QTreeWidgetItem*>::const_iterator it(selected_items.begin());it!=selected_items.end();++it)
{
QTreeWidgetItem *item = *it ;
std::string Id = item->text(RSID_COL_KEYID).toStdString();
rsReputations->setOwnOpinion(RsGxsId(Id),RsReputations::OPINION_POSITIVE) ;
}
requestIdDetails();
requestIdList();
@ -1443,30 +1507,28 @@ void IdDialog::unbanPerson()
void IdDialog::addtoContacts()
{
QTreeWidgetItem *item = ui->idTreeWidget->currentItem();
if (!item)
{
return;
}
QList<QTreeWidgetItem *> selected_items = ui->idTreeWidget->selectedItems();
for(QList<QTreeWidgetItem*>::const_iterator it(selected_items.begin());it!=selected_items.end();++it)
{
QTreeWidgetItem *item = *it ;
std::string Id = item->text(RSID_COL_KEYID).toStdString();
rsIdentity->setAsRegularContact(RsGxsId(Id),true);
}
requestIdList();
}
void IdDialog::removefromContacts()
{
QTreeWidgetItem *item = ui->idTreeWidget->currentItem();
if (!item)
{
return;
}
QList<QTreeWidgetItem *> selected_items = ui->idTreeWidget->selectedItems();
for(QList<QTreeWidgetItem*>::const_iterator it(selected_items.begin());it!=selected_items.end();++it)
{
QTreeWidgetItem *item = *it ;
std::string Id = item->text(RSID_COL_KEYID).toStdString();
rsIdentity->setAsRegularContact(RsGxsId(Id),false);
}
requestIdList();
}

View File

@ -85,8 +85,9 @@ private slots:
void addtoContacts();
void removefromContacts();
void banPerson();
void unbanPerson();
void negativePerson();
void positivePerson();
void neutralPerson();
static QString inviteMessage();
void sendInvite();

View File

@ -6,8 +6,8 @@
<rect>
<x>0</x>
<y>0</y>
<width>1484</width>
<height>791</height>
<width>747</width>
<height>657</height>
</rect>
</property>
<property name="sizePolicy">
@ -19,8 +19,14 @@
<property name="windowTitle">
<string/>
</property>
<layout class="QVBoxLayout" name="verticalLayout_6">
<item>
<layout class="QGridLayout" name="gridLayout_5">
<property name="horizontalSpacing">
<number>0</number>
</property>
<property name="margin">
<number>0</number>
</property>
<item row="0" column="0">
<widget class="QFrame" name="titleBarFrame">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Maximum">
@ -35,6 +41,9 @@
<enum>QFrame::Sunken</enum>
</property>
<layout class="QHBoxLayout" name="horizontalLayout">
<property name="margin">
<number>2</number>
</property>
<item>
<widget class="QLabel" name="titleBarPixmap">
<property name="minimumSize">
@ -107,7 +116,7 @@
</layout>
</widget>
</item>
<item>
<item row="0" column="0">
<widget class="QSplitter" name="splitter">
<property name="orientation">
<enum>Qt::Horizontal</enum>
@ -500,22 +509,9 @@
&lt;html&gt;&lt;head&gt;&lt;meta name=&quot;qrichtext&quot; content=&quot;1&quot; /&gt;&lt;style type=&quot;text/css&quot;&gt;
p, li { white-space: pre-wrap; }
&lt;/style&gt;&lt;/head&gt;&lt;body style=&quot; font-family:'Sans'; font-size:9pt; font-weight:400; font-style:normal;&quot;&gt;
&lt;p style=&quot; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;Your own opinion about an identity rules the visibility of that identity for yourself,&lt;/p&gt;
&lt;p style=&quot; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;and is shared among friends. A final score is calculated according to a formula that accounts your own opinion and your friends' opinions about someone:&lt;/p&gt;
&lt;p style=&quot; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;Your own opinion about an identity rules the visibility of that identity for yourself and your friend nodes. Your own opinion is shared among friends and used to compute a reputation score: If your opinion about an identity is neutral, the reputation score is the average of your friend's opinions. If not, your own opinion gives the score.&lt;/p&gt;
&lt;p style=&quot; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;The overall score is used in chat lobbies, forums and channels to decide on the actions to take for each specific identity. When the overall score is lower than -0.6, the identity is banned, which prevents all messages and forums/channels authored by this identity to be forwarded, both ways. Some forums also have special anti-spam flags that require a higher reputation level, making them more sensitive to bad opinions. Banned identities gradually lose their activity and eventually disappear (after 30 days). &lt;/p&gt;
&lt;p style=&quot;-qt-paragraph-type:empty; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;&lt;br /&gt;&lt;/p&gt;
&lt;p style=&quot; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt; S = own_opinion * a + friends_opinion * (1-a)&lt;/p&gt;
&lt;p style=&quot;-qt-paragraph-type:empty; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;&lt;br /&gt;&lt;/p&gt;
&lt;p style=&quot; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;The factor 'a' depends on the type of ID. &lt;/p&gt;
&lt;p style=&quot; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;- anonymous IDs: &lt;/p&gt;
&lt;p style=&quot; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;- PGP-signed IDs by unknown PGP keys: a=&lt;/p&gt;
&lt;p style=&quot;-qt-paragraph-type:empty; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;&lt;br /&gt;&lt;/p&gt;
&lt;p style=&quot; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;The overall score is used in chat lobbies, forums and channels to decide on the actions to take for each specific identity:&lt;/p&gt;
&lt;p style=&quot;-qt-paragraph-type:empty; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;&lt;br /&gt;&lt;/p&gt;
&lt;p style=&quot; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;S &amp;lt; -0.5: Posts are not stored, nor forwarded &lt;/p&gt;
&lt;p style=&quot; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;S &amp;lt; 0.2: Posts are hidden, but still transmitted&lt;/p&gt;
&lt;p style=&quot; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;S &amp;lt; 0.0: &lt;/p&gt;
&lt;p style=&quot;-qt-paragraph-type:empty; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;&lt;br /&gt;&lt;/p&gt;
&lt;p style=&quot; margin-top:12px; margin-bottom:12px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;The overall rating is computed in such a way that it is not possible for a single person to deterministically change someone's status at neighbor nodes.&lt;/p&gt;
&lt;p style=&quot;-qt-paragraph-type:empty; margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;&lt;br /&gt;&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="currentIndex">

View File

@ -1,3 +1,5 @@
#include <QToolButton>
#include <retroshare-gui/mainpage.h>
#include "common/FloatingHelpBrowser.h"
@ -9,12 +11,13 @@ MainPage::MainPage(QWidget *parent , Qt::WindowFlags flags ) : QWidget(parent, f
mHelp = "";
}
void MainPage::registerHelpButton(QAbstractButton *button,const QString& help_html_txt)
void MainPage::registerHelpButton(QToolButton *button,const QString& help_html_txt)
{
if (mHelpBrowser == NULL)
{
mHelpBrowser = new FloatingHelpBrowser(this, button) ;
}
float S = QFontMetricsF(button->font()).height() ;
button->setIconSize(QSize(S,S)) ;
mHelpBrowser->setHelpText(help_html_txt) ;
}

View File

@ -40,7 +40,7 @@
#include "ui_MainWindow.h"
#include "MessengerWindow.h"
#include "NetworkDialog.h"
#include "SearchDialog.h"
#include "gui/FileTransfer/SearchDialog.h"
#include "gui/FileTransfer/TransfersDialog.h"
#include "MessagesDialog.h"
#include "SharedFilesDialog.h"

View File

@ -43,7 +43,7 @@ NetworkView::NetworkView(QWidget *parent)
mScene = new QGraphicsScene();
mScene->setItemIndexMethod(QGraphicsScene::NoIndex);
mScene->setSceneRect(-200, -200, 1200, 1200);
mScene->setSceneRect(0, 0, ui.graphicsView->width(), ui.graphicsView->height());
ui.graphicsView->setScene(mScene);
ui.graphicsView->setEdgeLength(ui.edgeLengthSB->value()) ;

View File

@ -91,8 +91,8 @@
<enum>Qt::NoFocus</enum>
</property>
<property name="icon">
<iconset resource="icons.qrc">
<normaloff>:/icons/information_128.png</normaloff>:/icons/information_128.png</iconset>
<iconset resource="images.qrc">
<normaloff>:/icons/help_64.png</normaloff>:/icons/help_64.png</iconset>
</property>
<property name="iconSize">
<size>

View File

@ -38,7 +38,7 @@
#include "MainWindow.h"
#include "gui/gxsforums/GxsForumsDialog.h"
#include "gui/gxschannels/GxsChannelDialog.h"
#include "SearchDialog.h"
#include "gui/FileTransfer/SearchDialog.h"
#include "msgs/MessageComposer.h"
#include "util/misc.h"
#include "common/PeerDefs.h"

View File

@ -20,6 +20,8 @@
****************************************************************/
#include <QApplication>
#include <QFile>
#include <QProcess>
#include <QSound>
#include <QDir>
@ -28,6 +30,10 @@
#include <QAudioDeviceInfo>
#endif
// #ifdef QMEDIAPLAYER
// #nclude <QMediaPlayer>
// #endif
#include "SoundManager.h"
#include "settings/rsharesettings.h"
#include "retroshare/rsinit.h"
@ -79,6 +85,7 @@ void SoundManager::soundEvents(SoundEvents &events)
events.addEvent(tr("Chatmessage"), tr("New Msg"), SOUND_NEW_CHAT_MESSAGE, QFileInfo(baseDir, "incomingchat.wav").absoluteFilePath());
events.addEvent(tr("Message"), tr("Message arrived"), SOUND_MESSAGE_ARRIVED, QFileInfo(baseDir, "receive.wav").absoluteFilePath());
events.addEvent(tr("Download"), tr("Download complete"), SOUND_DOWNLOAD_COMPLETE, QFileInfo(baseDir, "ft_complete.wav").absoluteFilePath());
events.addEvent(tr("Lobby"), tr("Message arrived"), SOUND_NEW_LOBBY_MESSAGE, QFileInfo(baseDir, "incomingchat.wav").absoluteFilePath());
/* add plugin events */
int pluginCount = rsPlugins->nbPlugins();
@ -234,12 +241,60 @@ void SoundManager::playFile(const QString &filename)
}
QString playFilename = realFilename(filename);
bool played = false ;
#if QT_VERSION >= QT_VERSION_CHECK (5, 0, 0)
if (!QAudioDeviceInfo::availableDevices(QAudio::AudioOutput).isEmpty()) {
if (!QAudioDeviceInfo::availableDevices(QAudio::AudioOutput).isEmpty())
#else
if (QSound::isAvailable()) {
if (QSound::isAvailable())
#endif
QSound::play(playFilename);
}
{
QSound::play(playFilename);
played = true ;
}
if(!played) // let's go for the hard core stuff
{
// #ifdef QMEDIAPLAYER
// static QMediaPlayer *qmplayer;
// if (qmplayer == NULL) {
// qmplayer = new QMediaPlayer();
// qmplayer->setMedia(QMediaContent(QUrl::fromLocalFile(playFilename)));
// }
// std::cerr << "Play QMediaPlayer" << std::endl;
// qmplayer->play();
// return;
// #endif
#ifdef Q_OS_LINUX
QString player_cmd = soundDetectPlayer();
QStringList args = player_cmd.split(' ');
args += filename;
QString prog = args.takeFirst();
//std::cerr << "Play " << prog.toStdString() << std::endl;
QProcess::startDetached(prog, args);
#endif
}
}
#ifdef Q_OS_LINUX
/** Detect default player helper on unix like systems
* Inspired by Psi IM (0.15) in common.cpp
*/
QString SoundManager::soundDetectPlayer()
{
// prefer ALSA on linux
if (QFile("/proc/asound").exists()) {
return "aplay -q";
}
// fallback to "play"
return "play";
}
#endif

View File

@ -29,6 +29,7 @@
#define SOUND_USER_ONLINE "User_go_Online"
#define SOUND_MESSAGE_ARRIVED "MessageArrived"
#define SOUND_DOWNLOAD_COMPLETE "DownloadComplete"
#define SOUND_NEW_LOBBY_MESSAGE "NewLobbyMessage"
class SoundEvents
{
@ -67,6 +68,10 @@ signals:
public:
static void create();
#ifdef Q_OS_LINUX
static QString soundDetectPlayer();
#endif
static void initDefault();
static QString defaultFilename(const QString &event, bool check);
static QString convertFilename(const QString &filename);
@ -84,7 +89,7 @@ public:
static QString eventFilename(const QString &event);
static void setEventFilename(const QString &event, const QString &filename);
private:
SoundManager();
};

View File

@ -18,6 +18,11 @@
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor,
* Boston, MA 02110-1301, USA.
*
* ccr . 2016 Jan 26
*
* Play sound on incoming messages.
*
****************************************************************/
#include <unistd.h>
@ -42,6 +47,7 @@
#include "gui/gxs/GxsIdChooser.h"
#include "gui/gxs/GxsIdDetails.h"
#include "util/HandleRichText.h"
#include "gui/SoundManager.h"
#include <retroshare/rsnotify.h>
@ -400,7 +406,8 @@ void ChatLobbyDialog::addChatMsg(const ChatMessage& msg)
name = QString::fromUtf8(msg.peer_alternate_nickname.c_str()) + " (" + QString::fromStdString(gxs_id.toStdString()) + ")" ;
ui.chatWidget->addChatMsg(msg.incoming, name, gxs_id, sendTime, recvTime, message, ChatWidget::MSGTYPE_NORMAL);
emit messageReceived(msg.incoming, id(), sendTime, name, message) ;
emit messageReceived(msg.incoming, id(), sendTime, name, message) ;
SoundManager::play(SOUND_NEW_LOBBY_MESSAGE);
// This is a trick to translate HTML into text.
QTextEdit editor;

View File

@ -127,6 +127,7 @@ ChatWidget::ChatWidget(QWidget *parent) :
connect(ui->actionChooseColor, SIGNAL(triggered()), this, SLOT(chooseColor()));
connect(ui->actionResetFont, SIGNAL(triggered()), this, SLOT(resetFont()));
connect(ui->actionQuote, SIGNAL(triggered()), this, SLOT(quote()));
connect(ui->actionDropPlacemark, SIGNAL(triggered()), this, SLOT(dropPlacemark()));
connect(ui->actionSave_image, SIGNAL(triggered()), this, SLOT(saveImage()));
connect(ui->hashBox, SIGNAL(fileHashingFinished(QList<HashedFile>)), this, SLOT(fileHashingFinished(QList<HashedFile>)));
@ -923,7 +924,7 @@ void ChatWidget::addChatMsg(bool incoming, const QString &name, const RsGxsId gx
QString strGxsId = "";
if (!gxsId.isNull())
strGxsId = QString::fromStdString(gxsId.toStdString());
formatMsg.replace(QString("<a name=\"name\">"),QString("<a name=\"%1\">").arg(strGxsId));
formatMsg.replace(QString("<a name=\"name\">"),QString("<a name=\"Person Id: %1\">").arg(strGxsId));
QTextCursor textCursor = QTextCursor(ui->textBrowser->textCursor());
textCursor.movePosition(QTextCursor::End);
@ -979,6 +980,7 @@ void ChatWidget::contextMenuTextBrowser(QPoint point)
contextMnu->addSeparator();
contextMnu->addAction(ui->actionClearChatHistory);
contextMnu->addAction(ui->actionQuote);
contextMnu->addAction(ui->actionDropPlacemark);
QTextCursor cursor = ui->textBrowser->cursorForPosition(point);
if(ImageUtil::checkImage(cursor))
@ -1657,7 +1659,7 @@ void ChatWidget::updatePeersCustomStateString(const QString& /*peer_id*/, const
void ChatWidget::updateStatusString(const QString &statusMask, const QString &statusString, bool permanent)
{
ui->typingLabel->setText(QString(statusMask).arg(tr(statusString.toLatin1()))); // displays info for 5 secs.
ui->typingLabel->setText(QString(statusMask).arg(tr(statusString.toUtf8()))); // displays info for 5 secs.
ui->typingpixmapLabel->setPixmap(QPixmap(":images/typing.png") );
if (statusString == "is typing...") {
@ -1693,10 +1695,16 @@ void ChatWidget::quote()
{
QStringList sl = text.split(QRegExp("[\r\n]"),QString::SkipEmptyParts);
text = sl.join("\n>");
text.replace(QChar(-4),"");//Char used when image on text.
emit ui->chatTextEdit->append(QString(">") + text);
}
}
void ChatWidget::dropPlacemark()
{
ui->textBrowser->append("----------");
}
void ChatWidget::saveImage()
{
QPoint point = ui->actionSave_image->data().toPoint();

View File

@ -186,6 +186,7 @@ private slots:
bool fileSaveAs();
void quote();
void dropPlacemark();
void saveImage();
private:

View File

@ -1052,6 +1052,14 @@ border-image: url(:/images/closepressed.png)
<string>Quotes the selected text</string>
</property>
</action>
<action name="actionDropPlacemark">
<property name="text">
<string>Drop Placemark</string>
</property>
<property name="toolTip">
<string>Insert horizontal rule</string>
</property>
</action>
<action name="actionSave_image">
<property name="icon">
<iconset resource="../images.qrc">

View File

@ -254,10 +254,10 @@ void FriendSelectionWidget::loadRequest(const TokenQueue */*queue*/, const Token
for(uint32_t i=0;i<datavector.size();++i)
{
gxsIds.push_back(datavector[i].mMeta.mGroupId) ;
std::cerr << " got ID = " << datavector[i].mMeta.mGroupId << std::endl;
//std::cerr << " got ID = " << datavector[i].mMeta.mGroupId << std::endl;
}
std::cerr << "Got all " << datavector.size() << " ids from rsIdentity. Calling update of list." << std::endl;
//std::cerr << "Got all " << datavector.size() << " ids from rsIdentity. Calling update of list." << std::endl;
fillList() ;
}

View File

@ -269,7 +269,7 @@ void MimeTextEdit::pasteOwnCertificateLink()
void MimeTextEdit::pastePlainText()
{
insertPlainText(QApplication::clipboard()->text());
insertPlainText(QApplication::clipboard()->text().remove(QChar(-4)));//Char used when image on text.
}
void MimeTextEdit::spoiler()

View File

@ -127,7 +127,8 @@ GraphWidget::GraphWidget(QWidget *)
// scene->setItemIndexMethod(QGraphicsScene::NoIndex);
// scene->clear() ;
// setScene(scene);
// scene->setSceneRect(0, 0, 500, 500);
// scene()->setSceneRect(0, 0, width(), height());
setCacheMode(CacheBackground);
setViewportUpdateMode(BoundingRectViewportUpdate);
@ -154,7 +155,8 @@ void GraphWidget::clearGraph()
// }
scene()->clear();
scene()->setSceneRect(-200, -200, 1000, 1000);
scene()->setSceneRect(0, 0, width(), height());
_edges.clear();
_nodes.clear();
_friction_factor = 1.0f ;
@ -391,9 +393,11 @@ void GraphWidget::setEdgeLength(uint32_t l)
void GraphWidget::setNameSearch(QString s)
{
float f = QFontMetrics(font()).height()/16.0 ;
if (s.length() == 0){
for(uint32_t i=0;i<_nodes.size();++i)
_nodes[i]->setNodeDrawSize(20);
_nodes[i]->setNodeDrawSize(12 * f);
forceRedraw();
return;
}
@ -405,10 +409,10 @@ void GraphWidget::setNameSearch(QString s)
if (ns.find(qs) != std::string::npos) {
//std::cout << "found!" << '\n';
ni->setNodeDrawSize(22);
ni->setNodeDrawSize(22 * f);
//std::cout << ni->getNodeDrawSize() << '\n';
} else {
ni->setNodeDrawSize(12);
ni->setNodeDrawSize(12 * f);
}
}
@ -420,47 +424,53 @@ void GraphWidget::forceRedraw()
for(uint32_t i=0;i<_nodes.size();++i)
_nodes[i]->update(_nodes[i]->boundingRect()) ;
}
void GraphWidget::resizeEvent(QResizeEvent *event)
{
scene()->setSceneRect(QRectF(QPointF(0,0),event->size()));
}
void GraphWidget::wheelEvent(QWheelEvent *event)
{
scaleView(pow((double)2, -event->delta() / 240.0));
}
void GraphWidget::drawBackground(QPainter *painter, const QRectF &rect)
{
Q_UNUSED(rect);
// Shadow
QRectF sceneRect = this->sceneRect();
QRectF rightShadow(sceneRect.right(), sceneRect.top() + 5, 5, sceneRect.height());
QRectF bottomShadow(sceneRect.left() + 5, sceneRect.bottom(), sceneRect.width(), 5);
if (rightShadow.intersects(rect) || rightShadow.contains(rect))
painter->fillRect(rightShadow, Qt::darkGray);
if (bottomShadow.intersects(rect) || bottomShadow.contains(rect))
painter->fillRect(bottomShadow, Qt::darkGray);
// Fill
QLinearGradient gradient(sceneRect.topLeft(), sceneRect.bottomRight());
gradient.setColorAt(0, Qt::white);
gradient.setColorAt(1, Qt::lightGray);
painter->fillRect(rect.intersected(sceneRect), gradient);
painter->setBrush(Qt::NoBrush);
painter->drawRect(sceneRect);
// Text
QRectF textRect(sceneRect.left() + 4, sceneRect.top() + 4,
sceneRect.width() - 4, sceneRect.height() - 4);
QString message(tr("Click and drag the nodes around, and zoom with the mouse "
"wheel or the '+' and '-' keys"));
QFont font = painter->font();
font.setBold(true);
font.setPointSize(14);
painter->setFont(font);
painter->setPen(Qt::lightGray);
painter->drawText(textRect.translated(2, 2), message);
painter->setPen(Qt::black);
painter->drawText(textRect, message);
}
//void GraphWidget::drawBackground(QPainter *painter, const QRectF &rect)
//{
// Q_UNUSED(rect);
//
// // Shadow
// QRectF sceneRect = this->sceneRect();
// QRectF rightShadow(sceneRect.right(), sceneRect.top() + 5, 5, sceneRect.height());
// QRectF bottomShadow(sceneRect.left() + 5, sceneRect.bottom(), sceneRect.width(), 5);
// if (rightShadow.intersects(rect) || rightShadow.contains(rect))
// painter->fillRect(rightShadow, Qt::darkGray);
// if (bottomShadow.intersects(rect) || bottomShadow.contains(rect))
// painter->fillRect(bottomShadow, Qt::darkGray);
//
// // Fill
// QLinearGradient gradient(sceneRect.topLeft(), sceneRect.bottomRight());
// gradient.setColorAt(0, Qt::white);
// gradient.setColorAt(1, Qt::lightGray);
// painter->fillRect(rect.intersected(sceneRect), gradient);
// painter->setBrush(Qt::NoBrush);
// painter->drawRect(sceneRect);
//
// // Text
// QRectF textRect(sceneRect.left() + 4, sceneRect.top() + 4,
// sceneRect.width() - 4, sceneRect.height() - 4);
// QString message(tr("Click and drag the nodes around, and zoom with the mouse "
// "wheel or the '+' and '-' keys"));
//
// QFont font = painter->font();
// font.setBold(true);
// font.setPointSize(14);
// painter->setFont(font);
// painter->setPen(Qt::lightGray);
// painter->drawText(textRect.translated(2, 2), message);
// painter->setPen(Qt::black);
// painter->drawText(textRect, message);
//}
void GraphWidget::scaleView(qreal scaleFactor)
{

View File

@ -91,10 +91,11 @@ public:
void forceRedraw() ;
protected:
void keyPressEvent(QKeyEvent *event);
void timerEvent(QTimerEvent *event);
void wheelEvent(QWheelEvent *event);
void drawBackground(QPainter *painter, const QRectF &rect);
virtual void keyPressEvent(QKeyEvent *event);
virtual void timerEvent(QTimerEvent *event);
virtual void wheelEvent(QWheelEvent *event);
virtual void resizeEvent(QResizeEvent *event);
//void drawBackground(QPainter *painter, const QRectF &rect);
void scaleView(qreal scaleFactor);

View File

@ -205,8 +205,8 @@ void Node::calculateForces(const double *map,int width,int height,int W,int H,fl
QRectF sceneRect = scene()->sceneRect();
newPos = pos() + QPointF(_speedx, _speedy) / friction_factor;
newPos.setX(qMin(qMax(newPos.x(), sceneRect.left() + 10), sceneRect.right() - 10));
newPos.setY(qMin(qMax(newPos.y(), sceneRect.top() + 10), sceneRect.bottom() - 10));
newPos.setX(qMin(qMax(newPos.x(), sceneRect.left()), sceneRect.right()));
newPos.setY(qMin(qMax(newPos.y(), sceneRect.top()) , sceneRect.bottom()));
}
bool Node::advance()
@ -222,20 +222,22 @@ bool Node::advance()
QRectF Node::boundingRect() const
{
qreal adjust = 2;
float m = QFontMetricsF(graph->font()).height();
float f = m/16.0;
qreal adjust = 2*f;
/* add in the size of the text */
qreal realwidth = 40;
qreal realwidth = 40*f;
if (mDeterminedBB)
{
realwidth = mBBWidth + adjust;
}
if (realwidth < 23 + adjust)
if (realwidth < 23*f + adjust)
{
realwidth = 23 + adjust;
realwidth = 23*f + adjust;
}
return QRectF(-10 - adjust, -10 - adjust,
realwidth, 23 + adjust);
return QRectF(-10*f - adjust, -10*f - adjust, realwidth, 23*f + adjust);
}
QPainterPath Node::shape() const
@ -314,12 +316,17 @@ void Node::paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWid
painter->setBrush(gradient);
painter->setPen(QPen(Qt::black, 0));
painter->drawEllipse(-mNodeDrawSize2, -mNodeDrawSize2, mNodeDrawSize, mNodeDrawSize);
painter->drawText(-10, 0, QString::fromUtf8(_desc_string.c_str()));
QString txt = QString::fromUtf8(_desc_string.c_str());
float m = QFontMetricsF(graph->font()).height();
float f = m/16.0;
painter->drawText(-10, 5*f, txt) ;
if (!mDeterminedBB)
{
QRect textBox = painter->boundingRect(-10, 0, 400, 20, 0, QString::fromUtf8(_desc_string.c_str()));
mBBWidth = textBox.width();
QRect textBox = painter->boundingRect(-10, 5*f, QFontMetricsF(graph->font()).width(txt), 1.5*m, Qt::AlignVCenter, QString::fromUtf8(_desc_string.c_str()));
mBBWidth = textBox.width()+40*f;
mDeterminedBB = true;
}
}

View File

@ -160,11 +160,11 @@ static void loadPrivateIdsCallback(GxsIdDetailsType type, const RsIdentityDetail
chooser->setItemData(index, (type == GXS_ID_DETAILS_TYPE_DONE) ? TYPE_FOUND_ID : TYPE_UNKNOWN_ID, ROLE_TYPE);
chooser->setItemIcon(index, icons.empty() ? QIcon() : icons[0]);
std::cerr << "ID=" << details.mId << ", chooser->flags()=" << chooser->flags() << ", flags=" << details.mFlags ;
//std::cerr << "ID=" << details.mId << ", chooser->flags()=" << chooser->flags() << ", flags=" << details.mFlags ;
if((chooser->flags() & IDCHOOSER_NON_ANONYMOUS) && !(details.mFlags & RS_IDENTITY_FLAGS_PGP_LINKED))
{
std::cerr << " - disabling ID - entry = " << index << std::endl;
//std::cerr << " - disabling ID - entry = " << index << std::endl;
chooser->setEntryEnabled(index,false) ;
}
std::cerr << std::endl;

View File

@ -3,6 +3,9 @@
<file>icons/add_user_256.png</file>
<file>icons/anonymous_blue_128.png</file>
<file>icons/anonymous_green_128.png</file>
<file>icons/aol.png</file>
<file>icons/avatar_128.png</file>
<file>icons/avatar_grey_128.png</file>
<file>icons/blank_blue_128.png</file>
<file>icons/blank_green_128.png</file>
<file>icons/browsable_blue_128.png</file>
@ -19,6 +22,7 @@
<file>icons/friends_128.png</file>
<file>icons/global_switch_off_128.png</file>
<file>icons/global_switch_on_128.png</file>
<file>icons/gmail.png</file>
<file>icons/help_128.png</file>
<file>icons/help_64.png</file>
<file>icons/information_128.png</file>
@ -38,6 +42,7 @@
<file>icons/mail_old_128.png</file>
<file>icons/mail_red_128.png</file>
<file>icons/newsfeed128.png</file>
<file>icons/outlook.png</file>
<file>icons/plugins_128.png</file>
<file>icons/posted_128.png</file>
<file>icons/posted_red_128.png</file>
@ -55,19 +60,18 @@
<file>icons/tile_downloaded_48.png</file>
<file>icons/tile_downloading_48.png</file>
<file>icons/tile_inactive_48.png</file>
<file>icons/tor-logo.png</file>
<file>icons/tor-off.png</file>
<file>icons/tor-on.png</file>
<file>icons/tor-starting.png</file>
<file>icons/tor-stopping.png</file>
<file>icons/user-away_64.png</file>
<file>icons/user-away-extended_64.png</file>
<file>icons/user-busy_64.png</file>
<file>icons/user-offline_64.png</file>
<file>icons/user-online_64.png</file>
<file>icons/yellow_biohazard64.png</file>
<file>icons/gmail.png</file>
<file>icons/yahoo.png</file>
<file>icons/outlook.png</file>
<file>icons/aol.png</file>
<file>icons/yandex.png</file>
<file>icons/tor-on.png</file>
<file>icons/tor-logo.png</file>
<file>icons/tor-off.png</file>
<file>icons/yellow_biohazard64.png</file>
</qresource>
</RCC>

Binary file not shown.

After

Width:  |  Height:  |  Size: 13 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.1 KiB

View File

@ -20,6 +20,26 @@
* Boston, MA 02110-1301, USA.
****************************************************************/
/* ccr . 2015 Aug 01 . Resize Main page and Main window.
*
* On very small legacy CRTs of about 15" (38 cm) RetroShare pages are
* initially too deep (too tall) to fit the screen at 1024x768
* resolution. Some can be shrunk down manually from their initial
* size. Others cannot. This patch tries to allow each page to be
* shrunk somewhat. Then code that runs elsewhere to fit the logical
* Main window into the physical screen will have a better chance of
* success. Notably, on Linux -- Gnome3 -- X11 systems, only when the
* Main window first fits entirely into the physical screen, can it
* then be maximized.
*
* This code is borrowed from a Stack Overflow post:
*
* o Darkgaze. "Resize QStackedWidget to the Page Which Is Opened." 23
* Jan. 2013. Online posting. Stack Overflow. 1 Aug. 2015
* <https://stackoverflow.com/questions/14480696/resize-qstackedwidget-to-the-page-which-is-opened>.
*
*/
#include <QAction>
#include "mainpagestack.h"
@ -34,6 +54,7 @@ void
MainPageStack::add(MainPage *page, QAction *action)
{
_pages.insert(action, page);
page->setSizePolicy(QSizePolicy::Ignored, QSizePolicy::Ignored); /* 2015 Aug 01 */
insertWidget(count(), page);
}
@ -61,3 +82,14 @@ MainPageStack::showPage(QAction *pageAction)
setCurrentWidget(_pages.value(pageAction));
}
/** Adjusts the size of the Main page and the Main window. */
void
MainPageStack::onCurrentChanged(int index) /* 2015 Aug 01 */
{
QWidget* pWidget = widget(index);
Q_ASSERT(pWidget);
pWidget->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
pWidget->adjustSize();
adjustSize();
}

Some files were not shown because too many files have changed in this diff Show More