Move exit_now variable to main() function
[bpdyndnsd] / src / service_ods.cpp
1 /** @file
2  * @brief ODS Service class implementation. This class represents the ODS service.
3  *
4  *
5  *
6  * @copyright Intra2net AG
7  * @license GPLv2
8 */
9
10 #include "service_ods.hpp"
11 #include "net_helper.hpp"
12 #include "util.hpp"
13
14 using namespace std;
15
16
17 /**
18  * Default Constructor, needed for object serialization.
19  */
20 ServiceOds::ServiceOds()
21 {
22 }
23
24
25 /**
26  * Constructor.
27  * @param _hostname The hostname to update
28  * @param _login The login name.
29  * @param _password The corresponding password.
30  */
31 ServiceOds::ServiceOds(const string& _protocol, const string& _hostname, const string& _login, const string& _password, const Logger::Ptr& _logger, const int _update_interval, const int _max_updates_within_interval, const int _dns_cache_ttl)
32     : UpdateServer("update.ods.org")
33     , Port("7071")
34 {
35     if ( _update_interval == -1 )        // If _update_interval is default po::option_desc (not specified via config)
36         set_update_interval(15);              // use default protocol value
37     else
38         set_update_interval(_update_interval);
39
40     if ( _max_updates_within_interval == -1 )
41         set_max_updates_within_interval(3);
42     else
43         set_max_updates_within_interval(_max_updates_within_interval);
44
45     if ( _dns_cache_ttl == -1 )
46         set_dns_cache_ttl(180);
47     else
48         set_dns_cache_ttl(_dns_cache_ttl);
49
50     set_protocol(_protocol);
51     set_hostname(_hostname);
52     set_login(_login);
53     set_password(_password);
54     set_logger(_logger);
55 }
56
57
58 /**
59  * Default destructor.
60  */
61 ServiceOds::~ServiceOds()
62 {
63 }
64
65
66 /**
67  * Performs the Service update.
68  * @param ip IP Address to set.
69  * @return 0 if all is fine, -1 otherwise.
70  */
71 int ServiceOds::perform_update(const std::string& ip)
72 {
73     // First of all create a boost shared pointer to the NetHelper.
74     NetHelper::Ptr connection(new NetHelper(get_logger()));
75
76     // Then open the connection to the ODS update server.
77     if (connection->open_connection(UpdateServer,Port) != 0)
78         return -1;
79
80     // Receive the server greeting.
81     string server_greeting = connection->receive_data();
82     if ( server_greeting.empty() )
83     {
84         connection->close_connection(); /*lint !e534 */
85         return -1;
86     }
87
88     // Send login command
89     ostringstream login;
90     login << "LOGIN " << get_login() << " " << get_password() << endl;
91     if (connection->send_data(login.str()) != 0)
92     {
93         connection->close_connection(); /*lint !e534 */
94         return -1;
95     }
96
97     // Receive login reply
98     string login_reply = connection->receive_data();
99     if ( login_reply.empty() )
100     {
101         connection->close_connection(); /*lint !e534 */
102         return -1;
103     }
104     else
105     {
106         // Get the return code out of the received data
107         string status_code = Util::parse_status_code(login_reply);
108         if ( status_code == "520" )
109         {
110             // Login failed
111             get_logger()->print_service_not_authorized(UpdateServer,get_login(),get_password());
112             connection->close_connection(); /*lint !e534 */
113             return -1;
114         }
115         else if ( status_code != "225" )
116         {
117             // Undefined protocol error, Log login_reply
118             get_logger()->print_undefined_protocol_error("ODS",login_reply);
119             connection->close_connection(); /*lint !e534 */
120             return -1;
121         }
122     }
123
124     // Successfully loged in, status_code should be 225
125
126     // Perform delete operation until there is no RR or we have performed it 10 times.
127     int del_count = 0;
128     string delete_reply, reply_code;
129     ostringstream delete_request;
130     delete_request << "DELRR " << get_hostname() << " A " << endl;
131     do
132     {
133         // Send delete request
134         if (connection->send_data(delete_request.str()) != 0)
135         {
136             connection->close_connection(); /*lint !e534 */
137             return -1;
138         }
139         // Get delete reply
140         delete_reply = connection->receive_data();
141         if ( delete_reply.empty() )
142         {
143             connection->close_connection(); /*lint !e534 */
144             return -1;
145         }
146         del_count++;
147         reply_code = Util::parse_status_code(delete_reply);
148     }while ( (del_count < 10) && (reply_code != "300") );
149
150
151     // Send update request
152     ostringstream update_request;
153     update_request << "ADDRR " << get_hostname() << " A " << ip << endl;
154     if (connection->send_data(update_request.str()) != 0)
155     {
156         connection->close_connection(); /*lint !e534 */
157         return -1;
158     }
159
160     // Receive update request server reply
161     string update_reply = connection->receive_data();
162     if ( update_reply.empty() )
163     {
164         connection->close_connection(); /*lint !e534 */
165         return -1;
166     }
167     else
168     {
169         // Get the return code out of the received data
170         string status_code = Util::parse_status_code(update_reply);
171         if ( status_code != "795" )
172         {
173             get_logger()->print_undefined_protocol_error("ODS",update_reply);
174             connection->close_connection(); /*lint !e534 */
175             return -1;
176         }
177     }
178
179     // Successfully updated host
180     connection->close_connection(); /*lint !e534 */
181     return 0;
182 }