4 Copyright (C) Andrew Tridgell 2006
6 This library is free software; you can redistribute it and/or
7 modify it under the terms of the GNU Lesser General Public
8 License as published by the Free Software Foundation; either
9 version 2 of the License, or (at your option) any later version.
11 This library is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 Lesser General Public License for more details.
16 You should have received a copy of the GNU Lesser General Public
17 License along with this library; if not, write to the Free Software
18 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
22 #include "system/network.h"
23 #include "../include/ctdb.h"
24 #include "../include/ctdb_private.h"
26 #define CTDB_SOCKET "/tmp/ctdb.socket.127.0.0.1"
30 connect to the unix domain socket
32 static int ux_socket_connect(const char *name)
34 struct sockaddr_un addr;
37 memset(&addr, 0, sizeof(addr));
38 addr.sun_family = AF_UNIX;
39 strncpy(addr.sun_path, name, sizeof(addr.sun_path));
41 fd = socket(AF_UNIX, SOCK_STREAM, 0);
46 if (connect(fd, (struct sockaddr *)&addr, sizeof(addr)) == -1) {
54 void register_pid_with_daemon(int fd, int pid)
56 struct ctdb_req_register r;
59 r.hdr.length = sizeof(r);
60 r.hdr.ctdb_magic = CTDB_MAGIC;
61 r.hdr.ctdb_version = CTDB_VERSION;
62 r.hdr.operation = CTDB_REQ_REGISTER;
65 /* XXX must deal with partial writes here */
66 write(fd, &r, sizeof(r));
69 /* send a command to the cluster to wait until all nodes are connected
70 and the cluster is fully operational
72 int wait_for_cluster(int fd)
74 struct ctdb_req_connect_wait req;
75 struct ctdb_reply_connect_wait rep;
78 /* send a connect wait command to the local node */
79 bzero(&req, sizeof(req));
80 req.hdr.length = sizeof(req);
81 req.hdr.ctdb_magic = CTDB_MAGIC;
82 req.hdr.ctdb_version = CTDB_VERSION;
83 req.hdr.operation = CTDB_REQ_CONNECT_WAIT;
85 /* XXX must deal with partial writes here */
86 write(fd, &req, sizeof(req));
89 /* read the 4 bytes of length for the pdu */
94 numread=read(fd, ((char *)&rep)+cnt, tot-cnt);
99 /* read the rest of the pdu */
103 numread=read(fd, ((char *)&rep)+cnt, tot-cnt);
113 int send_a_message(int fd, int ourvnn, int vnn, int pid, TDB_DATA data)
115 struct ctdb_req_message r;
118 len = offsetof(struct ctdb_req_message, data) + data.dsize;
120 r.hdr.ctdb_magic = CTDB_MAGIC;
121 r.hdr.ctdb_version = CTDB_VERSION;
122 r.hdr.operation = CTDB_REQ_MESSAGE;
123 r.hdr.destnode = vnn;
124 r.hdr.srcnode = ourvnn;
127 r.datalen = data.dsize;
130 cnt=write(fd, &r, offsetof(struct ctdb_req_message, data));
133 cnt+=write(fd, data.dptr, data.dsize);
137 void wait_for_a_message(int fd)
141 struct ctdb_req_message *msg;
143 /* read the 4 bytes of length for the pdu */
148 numread=read(fd, ((char *)&len)+cnt, tot-cnt);
155 /* read the rest of the pdu */
159 numread=read(fd, (char *)msg+cnt, tot-cnt);
164 printf("got a message : %s\n",&msg->data[0]);
167 int main(int argc, const char *argv[])
169 int fd, pid, vnn, dstvnn, dstpid;
172 /* open the socket to talk to the local ctdb daemon */
173 fd=ux_socket_connect(CTDB_SOCKET);
175 printf("failed to open domain socket\n");
180 /* register our local server id with the daemon so that it knows
181 where to send messages addressed to our local pid.
184 register_pid_with_daemon(fd, pid);
187 /* do a connect wait to ensure that all nodes in the cluster are up
189 this also tells us the vnn of the local cluster.
190 If someone wants to send us a emssage they should send it to
193 vnn=wait_for_cluster(fd);
194 printf("our address is vnn:%d pid:%d if someone wants to send us a message!\n",vnn,pid);
197 /* send a message to ourself */
200 message.dptr="Test message";
201 message.dsize=strlen(message.dptr)+1;
202 send_a_message(fd, vnn, dstvnn, dstpid, message);
205 /* wait for the message to come back.
206 i.e. the one we just sent to ourself
208 wait_for_a_message(fd);