1: /*
2: * Copyright (c) 1983 Regents of the University of California.
3: * All rights reserved. The Berkeley software License Agreement
4: * specifies the terms and conditions for redistribution.
5: */
6:
7: #ifndef lint
8: static char sccsid[] = "@(#)candidate.c 2.3 (Berkeley) 4/21/86";
9: #endif not lint
10:
11: #include "globals.h"
12: #include <protocols/timed.h>
13:
14: #define ELECTIONWAIT 3 /* seconds */
15:
16: /*
17: * `election' candidates a host as master: it is called by a slave
18: * which runs with the -M option set when its election timeout expires.
19: * Note the conservative approach: if a new timed comes up, or another
20: * candidate sends an election request, the candidature is withdrawn.
21: */
22:
23: election(net)
24: struct netinfo *net;
25: {
26: int ret;
27: struct tsp *resp, msg, *readmsg();
28: struct timeval wait;
29: struct tsp *answer, *acksend();
30: long casual();
31: struct sockaddr_in server;
32:
33: syslog(LOG_INFO, "THIS MACHINE IS A CANDIDATE");
34: if (trace) {
35: fprintf(fd, "THIS MACHINE IS A CANDIDATE\n");
36: }
37:
38: ret = MASTER;
39: slvcount = 1;
40:
41: msg.tsp_type = TSP_ELECTION;
42: msg.tsp_vers = TSPVERSION;
43: (void)strcpy(msg.tsp_name, hostname);
44: bytenetorder(&msg);
45: if (sendto(sock, (char *)&msg, sizeof(struct tsp), 0, &net->dest_addr,
46: sizeof(struct sockaddr_in)) < 0) {
47: syslog(LOG_ERR, "sendto: %m");
48: exit(1);
49: }
50:
51: do {
52: wait.tv_sec = ELECTIONWAIT;
53: wait.tv_usec = 0;
54: resp = readmsg(TSP_ANY, (char *)ANYADDR, &wait, net);
55: if (resp != NULL) {
56: switch (resp->tsp_type) {
57:
58: case TSP_ACCEPT:
59: (void) addmach(resp->tsp_name, &from);
60: break;
61:
62: case TSP_MASTERUP:
63: case TSP_MASTERREQ:
64: /*
65: * If a timedaemon is coming up at the same time,
66: * give up the candidature: it will be the master.
67: */
68: ret = SLAVE;
69: break;
70:
71: case TSP_QUIT:
72: case TSP_REFUSE:
73: /*
74: * Collision: change value of election timer
75: * using exponential backoff.
76: * The value of timer will be recomputed (in slave.c)
77: * using the original interval when election will
78: * be successfully completed.
79: */
80: backoff *= 2;
81: delay2 = casual((long)MINTOUT,
82: (long)(MAXTOUT * backoff));
83: ret = SLAVE;
84: break;
85:
86: case TSP_ELECTION:
87: /* no master for another round */
88: msg.tsp_type = TSP_REFUSE;
89: (void)strcpy(msg.tsp_name, hostname);
90: server = from;
91: answer = acksend(&msg, &server, resp->tsp_name,
92: TSP_ACK, (struct netinfo *)NULL);
93: if (answer == NULL) {
94: syslog(LOG_ERR, "error in election");
95: } else {
96: (void) addmach(resp->tsp_name, &from);
97: }
98: break;
99:
100: case TSP_SLAVEUP:
101: (void) addmach(resp->tsp_name, &from);
102: break;
103:
104: case TSP_SETDATE:
105: case TSP_SETDATEREQ:
106: break;
107:
108: default:
109: if (trace) {
110: fprintf(fd, "candidate: ");
111: print(resp, &from);
112: }
113: break;
114: }
115: } else {
116: break;
117: }
118: } while (ret == MASTER);
119: return(ret);
120: }
Defined functions
Defined variables
sccsid
defined in line
8;
never used
Defined macros