LCOV - code coverage report
Current view: top level - sd/source/ui/remotecontrol - DiscoveryService.cxx (source / functions) Hit Total Coverage
Test: commit e02a6cb2c3e2b23b203b422e4e0680877f232636 Lines: 0 50 0.0 %
Date: 2014-04-14 Functions: 0 8 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  */
       9             : 
      10             : #include <errno.h>
      11             : #include <stdlib.h>
      12             : #include <string.h>
      13             : #include <algorithm>
      14             : #include <vector>
      15             : #include <iostream>
      16             : 
      17             : #include <comphelper/processfactory.hxx>
      18             : #include <rtl/strbuf.hxx>
      19             : #include <config_features.h>
      20             : 
      21             : #include "DiscoveryService.hxx"
      22             : 
      23             : #ifdef WIN32
      24             :   // LO vs WinAPI conflict
      25             :   #undef WB_LEFT
      26             :   #undef WB_RIGHT
      27             : 
      28             :   #include <winsock2.h>
      29             :   #include <ws2tcpip.h>
      30             : 
      31             :   #include "WINNetworkService.hxx"
      32             :   typedef int socklen_t;
      33             : #else
      34             :   #include <unistd.h>
      35             :   #include <sys/types.h>
      36             :   #include <sys/socket.h>
      37             :   #include <netinet/in.h>
      38             :   #include <arpa/inet.h>
      39             : #endif
      40             : 
      41             : #ifdef MACOSX
      42             :   #include <osl/conditn.hxx>
      43             :   #include <premac.h>
      44             :   #import <CoreFoundation/CoreFoundation.h>
      45             :   #include <postmac.h>
      46             :   #import "OSXNetworkService.hxx"
      47             : #endif
      48             : 
      49             : #if HAVE_FEATURE_AVAHI
      50             :   #include "AvahiNetworkService.hxx"
      51             : #endif
      52             : 
      53             : using namespace osl;
      54             : using namespace rtl;
      55             : using namespace sd;
      56             : 
      57           0 : DiscoveryService::DiscoveryService()
      58             :     : mSocket(-1)
      59           0 :     , zService(0)
      60             : {
      61           0 : }
      62             : 
      63           0 : DiscoveryService::~DiscoveryService()
      64             : {
      65           0 :     if (mSocket != -1)
      66             :     {
      67             : #ifdef WNT
      68             :         closesocket( mSocket );
      69             : #else
      70           0 :         close( mSocket );
      71             : #endif
      72             :     }
      73             : 
      74           0 :      if (zService)
      75           0 :          zService->clear();
      76           0 : }
      77             : 
      78           0 : void DiscoveryService::setupSockets()
      79             : {
      80             : 
      81             : #ifdef MACOSX
      82             :     // Bonjour for OSX
      83             :     zService = new OSXNetworkService();
      84             : #endif
      85             : 
      86             : #if HAVE_FEATURE_AVAHI
      87             :     // Avahi for Linux
      88             :     char hostname[1024];
      89             :     hostname[1023] = '\0';
      90             :     gethostname(hostname, 1023);
      91             : 
      92             :     zService = new AvahiNetworkService(hostname);
      93             : #endif
      94             : 
      95             : #ifdef WIN32
      96             :     zService = new WINNetworkService();
      97             : #endif
      98             : 
      99           0 :     if (zService)
     100           0 :         zService->setup();
     101             : 
     102             :     // Old implementation for backward compatibility matter
     103           0 :     mSocket = socket( AF_INET, SOCK_DGRAM, IPPROTO_UDP );
     104           0 :     if (mSocket == -1)
     105             :     {
     106             :         SAL_WARN("sd", "DiscoveryService: socket failed: " << errno);
     107           0 :         return; // would be better to throw, but unsure if caller handles that
     108             :     }
     109             : 
     110             :     sockaddr_in aAddr;
     111           0 :     memset(&aAddr, 0, sizeof(aAddr));
     112           0 :     aAddr.sin_family = AF_INET;
     113           0 :     aAddr.sin_addr.s_addr = htonl(INADDR_ANY);
     114           0 :     aAddr.sin_port = htons( PORT_DISCOVERY );
     115             : 
     116           0 :     int rc = bind( mSocket, (sockaddr*) &aAddr, sizeof(sockaddr_in) );
     117             : 
     118           0 :     if (rc)
     119             :     {
     120             :         SAL_WARN("sd", "DiscoveryService: bind failed: " << errno);
     121           0 :         return; // would be better to throw, but unsure if caller handles that
     122             :     }
     123             : 
     124             :     struct ip_mreq multicastRequest;
     125             : 
     126           0 :     multicastRequest.imr_multiaddr.s_addr = inet_addr( "239.0.0.1" );
     127           0 :     multicastRequest.imr_interface.s_addr = htonl(INADDR_ANY);
     128             : 
     129             :     rc = setsockopt( mSocket, IPPROTO_IP, IP_ADD_MEMBERSHIP,
     130             :     #ifdef WNT
     131             :         (const char*)
     132             :     #endif
     133           0 :         &multicastRequest, sizeof(multicastRequest));
     134             : 
     135           0 :     if (rc)
     136             :     {
     137             :         SAL_WARN("sd", "DiscoveryService: setsockopt failed: " << errno);
     138           0 :         return; // would be better to throw, but unsure if caller handles that
     139             :     }
     140             : }
     141             : 
     142           0 : void SAL_CALL DiscoveryService::run()
     143             : {
     144           0 :     osl::Thread::setName("DiscoveryService");
     145             : 
     146           0 :     setupSockets();
     147             : 
     148             :     // Kept for backwrad compatibility
     149             :     char aBuffer[BUFFER_SIZE];
     150             :     while ( true )
     151             :     {
     152           0 :         memset( aBuffer, 0, sizeof(char) * BUFFER_SIZE );
     153             :         sockaddr_in aAddr;
     154           0 :         socklen_t aLen = sizeof( aAddr );
     155           0 :         recvfrom( mSocket, aBuffer, BUFFER_SIZE, 0, (sockaddr*) &aAddr, &aLen );
     156           0 :         OString aString( aBuffer, strlen( "LOREMOTE_SEARCH" ) );
     157           0 :         if ( aString == "LOREMOTE_SEARCH" )
     158             :         {
     159           0 :             OStringBuffer aStringBuffer("LOREMOTE_ADVERTISE\n");
     160             :             aStringBuffer.append( OUStringToOString(
     161           0 :                 osl::SocketAddr::getLocalHostname(), RTL_TEXTENCODING_UTF8 ) )
     162           0 :                 .append( "\n\n" );
     163           0 :             if ( sendto( mSocket, aStringBuffer.getStr(),
     164           0 :                 aStringBuffer.getLength(), 0, (sockaddr*) &aAddr,
     165           0 :                          sizeof(aAddr) ) <= 0 )
     166             :             {
     167             :                 // Read error or closed socket -- we are done.
     168           0 :                 return;
     169           0 :             }
     170             :         }
     171           0 :     }
     172             : }
     173             : 
     174             : DiscoveryService *sd::DiscoveryService::spService = NULL;
     175             : 
     176           0 : void DiscoveryService::setup()
     177             : {
     178           0 :   if (spService)
     179           0 :     return;
     180             : 
     181           0 :   spService = new DiscoveryService();
     182           0 :   spService->create();
     183           0 : }
     184             : 
     185             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10