GVOHub.cpp

Louge Thierry, 06/27/2014 04:11 PM

Download (9.91 KB)

 
1
/***************************************************************************
2
 *                     GVOHub.hpp - VO SAMP Hub class                     *
3
 * ----------------------------------------------------------------------- *
4
 *  copyright (C) 2014 by Juergen Knoedlseder & Thierry Louge                              *
5
 * ----------------------------------------------------------------------- *
6
 *                                                                         *
7
 *  This program is free software: you can redistribute it and/or modify   *
8
 *  it under the terms of the GNU General Public License as published by   *
9
 *  the Free Software Foundation, either version 3 of the License, or      *
10
 *  (at your option) any later version.                                    *
11
 *                                                                         *
12
 *  This program is distributed in the hope that it will be useful,        *
13
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of         *
14
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the          *
15
 *  GNU General Public License for more details.                           *
16
 *                                                                         *
17
 *  You should have received a copy of the GNU General Public License      *
18
 *  along with this program.  If not, see <http://www.gnu.org/licenses/>.  *
19
 *                                                                         *
20
 ***************************************************************************/
21
/**
22
 * @file GVOHub.cpp
23
 * @brief VO SAMP Hub class implementation
24
 * @author Juergen Knoedlseder, Thierry Louge
25
 */
26

    
27
/* __ Includes ___________________________________________________________ */
28
#ifdef HAVE_CONFIG_H
29
#include <config.h>
30
#endif
31
#include <cstdlib>         // std::getenv() function
32
#include <cstdio>          // std::fopen(), etc. functions
33
#include <cstring>         // std::memset() function
34
#include <unistd.h>        // close() function
35
#include <netdb.h>         // getaddrinfo() function
36
#include <sys/socket.h>    // socket(), connect() functions
37
#include "GVOHub.hpp"
38
#include "GException.hpp"
39
#include "GTools.hpp"
40
/*==========================================================================
41
 =                                                                         =
42
 =                         Constructors/destructors                        =
43
 =                                                                         =
44
 ==========================================================================*/
45

    
46
/***********************************************************************//**
47
 * @brief Void constructor
48
 ***************************************************************************/
49
GVOHub::GVOHub(void)
50
{
51
    // Initialise members
52
    init_members();
53

    
54
    // Creates Hub
55
    init_hub();
56
    
57
    // Starts the hub
58
    start_hub();
59
    // Return
60
    return;
61
}
62

    
63

    
64

    
65
/***********************************************************************//**
66
 * @brief Destructor
67
 ***************************************************************************/
68
GVOHub::~GVOHub(void)
69
{
70
    
71
    // Return
72
    return;
73
}
74

    
75

    
76
/*==========================================================================
77
 =                                                                         =
78
 =                             Public methods                              =
79
 =                                                                         =
80
 ==========================================================================*/
81

    
82
/***********************************************************************//**
83
 * @brief 
84
 *
85
 *
86
 ***************************************************************************/
87
void GVOHub::register_service(void)
88
{
89

    
90
    // Return
91
    return;
92
}
93

    
94
/***********************************************************************//**
95
 * @brief 
96
 *
97
 *
98
 ***************************************************************************/
99
void GVOHub::unregister(void)
100
{
101

    
102
    // Return
103
    return;
104
}
105

    
106
/*==========================================================================
107
 =                                                                         =
108
 =                             Private methods                             =
109
 =                                                                         =
110
 ==========================================================================*/
111
/***********************************************************************//**
112
 * @brief Initialise class members
113
 ***************************************************************************/
114
void GVOHub::init_members(void)
115
{
116
    // Initialise members
117
    m_name = "GammaLib";
118
    m_secret = "mysupersecret#0032557sentence";
119
    m_hub_url = "http://localhost:8001";
120
    m_hub_host = "127.0.0.1";
121
    m_hub_port = "8001";
122
    m_version = "1.3";
123
    //m_client_key.clear();
124
    m_hub_id = "b79884e0";
125
    //m_client_id.clear();
126
    //m_socket = -1;         // Signals no socket
127

    
128
    // Return
129
    return;
130
}
131
/***********************************************************************//**
132
 * @brief Creates the lockfile, fill it
133
 *
134
 *
135
 * Implements IVOA standard REC-SAMP-1.3-20120411.
136
 ***************************************************************************/
137
void GVOHub::init_hub(void)
138
{
139
   // Get lockfile URL
140
   std::string lockurl = get_hub_lockfile();
141

    
142
   // Open SAMP lockfile. Continue only if opening was successful
143
   FILE* fptr = fopen(lockurl.c_str(), "w");
144
   if (fptr != NULL) {
145
   //If successfull writes basic hub configuration to the lockfile
146
        fputs ("# SAMP lockfile \n # Required keys:\n",fptr);
147
        fputs (strcat(strcat("samp.secret= ",m_secret.c_str()),"\n"),fptr);
148
        fputs (strcat(strcat("samp.hub.xmlrpc.url=%s",m_hub_url.c_str()),"\n"),fptr);
149
        fputs (strcat(strcat("samp.profile.version=%s",m_version.c_str()),"\n"),fptr);
150
        fputs ("# Info stored by hub for some private reason:\n",fptr);
151
        fputs (strcat(strcat("com.yoyodyne.hubid=%s",m_hub_id.c_str()),"\n"),fptr);
152
   }
153
   // Close SAMP lockfile
154
   fclose(fptr);
155
}
156

    
157
/***********************************************************************//**
158
 * @brief Returns SAMP Hub lockfile URL
159
 *
160
 * @return SAMP Hub lockfile URL (empty if no lockfile was found).
161
 *
162
 * Implements IVOA standard REC-SAMP-1.3-20120411.
163
 ***************************************************************************/
164
std::string GVOHub::get_hub_lockfile(void) const
165
{
166
    // Initialise result
167
    std::string url = "";
168

    
169
    // Check for existence of the SAMP_HUB environment variable first
170
    char* hub_ptr = std::getenv("SAMP_HUB");
171
    if (hub_ptr != NULL) {
172

    
173
        // Check for mandatory std-lockurl: prefix (no other prefixe is
174
        // supported so far)
175
        std::string lockurl = std::string(hub_ptr);
176
        if (lockurl.compare(0, 12, "std-lockurl:") == 0) {
177

    
178
            // Extract URL
179
            url = lockurl.substr(12, std::string::npos);
180

    
181
        } // endif: std-lockurl: prefix found
182
  
183
    }
184

    
185
    // ... otherwise the lockfile should be $HOME/.samp
186
    else {
187

    
188
        // Get user's HOME directory path as the prefix of the full
189
        // path. If the HOME environment variable is not set we
190
        // expect that .samp is in the local directory. This is non
191
        // standard, but prevents for creating an exception here.
192
        std::string prefix = "";
193
        char* home_ptr = std::getenv("HOME");
194
        if (home_ptr != NULL) {
195
            prefix = std::string(home_ptr) + "/";
196
        }
197

    
198
        // Set filename
199
        url = prefix + ".samp";
200

    
201
    } // endelse: no SAMP_HUB environment variable found
202

    
203
    // Return URL
204
    return url;
205
}
206
/***********************************************************************//**
207
 * @brief Starts the SAMP hub socket and listens on it
208
 *
209
 * @return 1 if error comes out, nothing if everything is right (infinite listening loop)
210
 *
211
 ***************************************************************************/
212
int GVOHub::start_hub(void)
213
{
214
    struct sockaddr_in serv_addr,cli_addr;
215
    int clilen,portno,newsocket,pid,sockfd;
216

    
217
    // Prepare TCP/IP structure
218
    bzero((char *) &serv_addr, sizeof(serv_addr));
219
    portno = 8001;
220
    serv_addr.sin_family = AF_INET;
221
    serv_addr.sin_addr.s_addr = INADDR_ANY;
222
    serv_addr.sin_port = htons(portno);
223
    m_socket = socket(AF_INET, SOCK_STREAM, 0);
224
    if (m_socket < 0) 
225
    {
226
        return(1);
227
    }
228
    
229
    //Server socket is opened. Now, bind it to the port, with family etc.
230
    if (bind(m_socket, (struct sockaddr *) &serv_addr,sizeof(serv_addr)) < 0)
231
    {
232
         return(1);
233
    }
234

    
235
    //Now start listening for the clients: 5 requests simultaneously maximum
236
    listen(m_socket,5);
237
    clilen = sizeof(cli_addr);
238
    while (1) 
239
    {
240
            // Accept actual connection from the client 
241
            newsocket = accept(m_socket, (struct sockaddr *)&cli_addr, 
242
                                &clilen);
243
            if (newsocket < 0) 
244
            {
245
                return(1);
246
            }
247
            // Create child process to handle the request
248
        pid = fork();
249
        if (pid < 0)
250
        {
251
           return(1);
252
        }
253
        if (pid == 0)  
254
        {
255
            // Child process: client process
256
            close(sockfd);
257
            handle_request(newsocket);
258
            exit(0);
259
        }
260
        else
261
        {
262
            close(newsocket);
263
        }
264
    }
265
}
266

    
267
/***********************************************************************//**
268
 * @brief reads the 
269
 *
270
 * @return 0 if no problem, 1 if error comes out.
271
 *
272
 ***************************************************************************/
273
void GVOHub::handle_request (int sock)
274
{
275
    int n;
276
    char buffer[256];
277

    
278
    bzero(buffer,256);
279

    
280
    n = read(sock,buffer,255);
281
    if (n < 0)
282
    {
283
        return(1);
284
    }
285
    printf("Here is the message: %s\n",buffer);
286

    
287
    //Here, obviously not simple string matching but xml parsing to be done with 
288
    //help of GXml object. This is only for architectural purpose.
289
    if (strcmp(buffer,"register") == 0) {
290
        register_service();
291
    }
292
    //Same for writing, we'll use GXml
293
    n = write(sock,"I got your message",18);
294
    if (n < 0) 
295
    {
296
        return(1);
297
    }
298
    return(0);
299
}