ViewVC Help
View File | Revision Log | Show Annotations | Revision Graph | Root Listing
root/i-scream/projects/cms/source/ihost/ihost.c
Revision: 1.4
Committed: Sun May 12 12:00:33 2002 UTC (22 years ago) by pajs
Content type: text/plain
Branch: MAIN
Changes since 1.3: +94 -2 lines
Log Message:
Untested heartbeat code added. Changed last_modified to char* as we never
have to do any processing on it, so is easier to store it that way.

File Contents

# Content
1 #include <stdio.h>
2 #include <sys/socket.h>
3 #include <stdlib.h>
4 #include <unistd.h>
5 #include <syslog.h>
6 #include <netinet/in.h>
7 #include <ukcprog.h>
8 #include <netdb.h>
9 #include <strings.h>
10
11 #define RECONFIGURE_RETURN_CODE 2
12
13 typedef struct{
14 int fm_port;
15 char *fm_host;
16
17 char *my_fqdn;
18 char *server_fqdn;
19 int server_udp_port;
20 int server_tcp_port;
21 char *last_modified;
22 char *files_list;
23 char *key;
24 int udp_update_time;
25 int tcp_update_time;
26
27 }ihost_state_t;
28
29 char* sock_comm(FILE *f_r, FILE *f_w, char* sendString){
30 char *reply;
31 fprintf(f_w, "%s", sendString);
32 fflush(f_w);
33 reply=fpgetline(f_r);
34 /* Returns pointer to static buffer */
35 return reply;
36 }
37
38 int ihost_configure(ihost_state_t *ihost_state){
39 struct sockaddr_in addr;
40 struct in_addr haddr;
41 int sd;
42 FILE *fm_fd_r, *fm_fd_w;
43 char *reply;
44 char *reply_ptr;
45
46 if ((sd = socket(AF_INET, SOCK_STREAM, PF_UNSPEC)) < 0) {
47 errf("Can't create AF_INET socket (%m)");
48 return -1;
49 }
50
51 if (get_host_addr(ihost_state->fm_host, &haddr) != 0){
52 errf("Failed to resolve address %s (%m)", ihost_state->fm_host);
53 return -1;
54 }
55
56 memset((char *)&addr, 0, sizeof addr);
57 addr.sin_family = AF_INET;
58 memcpy((char *)&addr.sin_addr, &haddr, sizeof haddr);
59 addr.sin_port = htons(ihost_state->fm_port);
60
61 if (connect(sd, (struct sockaddr *)&addr, sizeof addr) != 0) {
62 errf("Failed to connect to %s on port %d (%m)", ihost_state->fm_host, ihost_state->fm_port);
63 return -1;
64 }
65
66 /* Need to open 2 files, one for reading one for writing, as it gets confused if we only use 1 :) */
67 if ((fm_fd_r=fdopen(sd,"r")) == NULL){
68 errf("Failed to open stream (%m)");
69 return -1;
70 }
71
72 if ((fm_fd_w=fdopen(dup(sd),"w")) == NULL){
73 errf("Failed to open stream (%m)");
74 return -1;
75 }
76
77 reply=sock_comm(fm_fd_r, fm_fd_w, "STARTCONFIG\n");
78 if ((reply==NULL) || (strncasecmp(reply, "OK", 2) != 0) ) {
79 errf("Server error");
80 return -1;
81 }
82
83 reply=sock_comm(fm_fd_r, fm_fd_w, "LASTMODIFIED\n");
84 if((reply== NULL) || (strncasecmp(reply, "ERROR", 5) ==0)){
85 errf("Server error (%m)");
86 return -1;
87 }
88 if((ihost_state->last_modified=strdup(reply)) == NULL){
89 errf("strdup failed (%m)");
90 return -1;
91 }
92
93 reply=sock_comm(fm_fd_r, fm_fd_w, "FILELIST\n");
94 if((reply== NULL) || (strncasecmp(reply, "ERROR", 5) ==0)){
95 errf("Server error (%m)");
96 return -1;
97 }
98 if((ihost_state->files_list=strdup(reply)) == NULL){
99 errf("strdup failed (%m)");
100 return -1;
101 }
102
103 reply=sock_comm(fm_fd_r, fm_fd_w, "FQDN\n");
104 if((reply== NULL) || (strncasecmp(reply, "ERROR", 5)==0)){
105 errf("Server error (%m)");
106 return -1;
107 }
108 if((ihost_state->my_fqdn=strdup(reply)) == NULL){
109 errf("strdup failed (%m)");
110 return -1;
111 }
112
113 reply=sock_comm(fm_fd_r, fm_fd_w, "UDPUpdateTime\n");
114 if(reply== NULL){
115 errf("Server error (%m)");
116 return -1;
117 }
118 if (strncasecmp(reply, "ERROR", 5) != 0){
119 ihost_state->udp_update_time=atoi(reply);
120 }
121
122 reply=sock_comm(fm_fd_r, fm_fd_w, "TCPUpdateTime\n");
123 if(reply== NULL){
124 errf("Server error (%m)");
125 return -1;
126 }
127 if (strncasecmp(reply, "ERROR", 5) != 0){
128 ihost_state->tcp_update_time=atoi(reply);
129 }
130
131 reply=sock_comm(fm_fd_r, fm_fd_w, "ENDCONFIG\n");
132 if(reply== NULL){
133 errf("Server error (%m)");
134 return -1;
135 }
136
137 reply=sock_comm(fm_fd_r, fm_fd_w, "FILTER\n");
138 if((reply== NULL) || (strncasecmp(reply, "ERROR", 5)==0)){
139 errf("Server error (%m)");
140 return -1;
141 }
142 reply_ptr=strchr(reply,';');
143 if (reply_ptr==NULL){
144 errf("Incorrect data returned");
145 return -1;
146 }
147 *reply_ptr='\0';
148 if((ihost_state->server_fqdn=strdup(reply)) == NULL){
149 errf("strdup failed (%m)");
150 return -1;
151 }
152 reply=++reply_ptr;
153 reply_ptr=strchr(reply,';');
154 if (reply_ptr==NULL){
155 errf("Incorrect data returned 2");
156 return -1;
157 }
158 *reply_ptr='\0';
159 ihost_state->server_udp_port=atoi(reply);
160 reply=++reply_ptr;
161 ihost_state->server_tcp_port=atoi(reply);
162 if ((ihost_state->server_tcp_port==0) || (ihost_state->server_udp_port==0)){
163 errf("Incorrect data returned 3 ");
164 return -1;
165 }
166
167 reply=sock_comm(fm_fd_r, fm_fd_w, "END\n");
168 if((reply== NULL) || (strncasecmp(reply, "ERROR", 5) ==0 )){
169 errf("Server error (%m)");
170 return -1;
171 }
172
173 if(fclose(fm_fd_r) !=0){
174 errf("Failed to close FD (%m)");
175 return -1;
176 }
177 if(fclose(fm_fd_w) !=0){
178 errf("Failed to close FD (%m)");
179 return -1;
180 }
181
182 return 0;
183 }
184
185 int heartbeat(ihost_state_t *ihost_state){
186 struct sockaddr_in addr;
187 struct in_addr haddr;
188 int sd;
189 FILE *fm_fd_r, *fm_fd_w;
190 char *reply;
191 int exitcode=0;
192
193 if ((sd = socket(AF_INET, SOCK_STREAM, PF_UNSPEC)) < 0) {
194 errf("Can't create AF_INET socket (%m)");
195 return -1;
196 }
197
198 if (get_host_addr(ihost_state->server_fqdn, &haddr) != 0){
199 errf("Failed to resolve address %s (%m)", ihost_state->fm_host);
200 return -1;
201 }
202
203 memset((char *)&addr, 0, sizeof addr);
204 addr.sin_family = AF_INET;
205 memcpy((char *)&addr.sin_addr, &haddr, sizeof haddr);
206 addr.sin_port = htons(ihost_state->server_tcp_port);
207
208 if (connect(sd, (struct sockaddr *)&addr, sizeof addr) != 0) {
209 errf("Failed to connect to %s on port %d (%m)", ihost_state->fm_host, ihost_state->fm_port);
210 return -1;
211 }
212
213 /* Need to open 2 files, one for reading one for writing, as it gets confused if we only use 1 :) */
214 if ((fm_fd_r=fdopen(sd,"r")) == NULL){
215 errf("Failed to open stream (%m)");
216 return -1;
217 }
218
219 if ((fm_fd_w=fdopen(dup(sd),"w")) == NULL){
220 errf("Failed to open stream (%m)");
221 return -1;
222 }
223
224 reply=sock_comm(fm_fd_r, fm_fd_w, "HEARTBEAT\n");
225 if ((reply==NULL) || (strncasecmp(reply, "ERROR", 2) == 0) ) {
226 errf("Server error");
227 return -1;
228 }
229
230 reply=sock_comm(fm_fd_r, fm_fd_w, "CONFIG\n");
231 if ((reply==NULL) || (strncasecmp(reply, "ERROR", 2) == 0) ) {
232 errf("Server error");
233 return -1;
234 }
235
236 reply=sock_comm(fm_fd_r, fm_fd_w, ihost_state->files_list);
237 if ((reply==NULL) || (strncasecmp(reply, "OK", 2) != 0) ) {
238 errf("Server error");
239 return -1;
240 }
241
242 reply=sock_comm(fm_fd_r, fm_fd_w, ihost_state->last_modified);
243 if (reply==NULL) {
244 errf("Server error");
245 return -1;
246 }
247 if (strncasecmp(reply, "ERROR", 2) == 0){
248 /* Means the config has changed */
249 exitcode=RECONFIGURE_RETURN_CODE;
250 }
251 reply=sock_comm(fm_fd_r, fm_fd_w, "KEY\n");
252 if ((reply==NULL) || (strncasecmp(reply, "ERROR", 2) == 0) ) {
253 errf("Server error");
254 return -1;
255 }
256
257 if((ihost_state->key=strdup(reply)) == NULL){
258 errf("strdup failed (%m)");
259 return -1;
260 }
261
262 reply=sock_comm(fm_fd_r, fm_fd_w, "END\n");
263 if((reply== NULL) || (strncasecmp(reply, "ERROR", 5) ==0 )){
264 errf("Server error (%m)");
265 return -1;
266 }
267
268 return exitcode;
269 }
270
271
272 int main(int argc, char **argv){
273 ihost_state_t ihost_state;
274 errf_set_progname(argv[0]);
275 if(argc!=3){
276 errf_usage("<host> <port>");
277 exit(1);
278 }
279
280 ihost_state.fm_host=argv[1];
281 ihost_state.fm_port=atoi(argv[2]);
282
283 if(ihost_configure(&ihost_state)!=0){
284 errf("configure failed");
285 }
286
287 return 0;
288 }
289