pb-event: Add help message
[petitboot] / utils / pb-event.c
1 /*
2  *  Copyright (C) 2009 Sony Computer Entertainment Inc.
3  *  Copyright 2009 Sony Corp.
4  *
5  *  This program is free software; you can redistribute it and/or modify
6  *  it under the terms of the GNU General Public License as published by
7  *  the Free Software Foundation; version 2 of the License.
8  *
9  *  This program is distributed in the hope that it will be useful,
10  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
11  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  *  GNU General Public License for more details.
13  *
14  *  You should have received a copy of the GNU General Public License
15  *  along with this program; if not, write to the Free Software
16  *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
17  */
18
19 #if defined(HAVE_CONFIG_H)
20 #include "config.h"
21 #endif
22
23 #define _GNU_SOURCE
24 #include <assert.h>
25 #include <errno.h>
26 #include <stdio.h>
27 #include <stdlib.h>
28 #include <string.h>
29 #include <unistd.h>
30 #include <sys/socket.h>
31 #include <sys/types.h>
32 #include <sys/un.h>
33
34 #include "discover/user-event.h"
35
36 #if defined(DEBUG)
37 #define DBG(_args...) do {fprintf(stderr, _args); fflush(stderr); } while (0)
38 #else
39 static inline int __attribute__ ((format (printf, 1, 2))) DBG(
40         __attribute__((unused)) const char *fmt, ...) {return 0; }
41 #endif
42
43 static void print_version(void)
44 {
45         printf("pb-event (" PACKAGE_NAME ") " PACKAGE_VERSION "\n");
46 }
47
48 static void print_usage(void)
49 {
50         print_version();
51         printf(
52 "Usage: pb-event [-h, --help] [-V, --version]\n"
53 "\n"
54 "       Reads a single petitboot user event on stdin and forwards it to the\n"
55 "       petitboot discover server pb-discover.  User events must have the\n"
56 "       following format:\n"
57 "\n"
58 "         (add|remove)@device-id\\0[name=value\\0][image=value\\0][args=value\\0]\n"
59 "\n"
60 "Examples:\n"
61 "\n"
62 "       echo -ne 'add@/net/eth0\\0name=netboot\\0image=tftp://192.168.1.10/vmlinux\\0args=root=/dev/nfs nfsroot=192.168.1.10:/target\\0' | pb-event\n"
63 "       echo -ne 'remove@/net/eth0\\0' | pb-event\n"
64 "\n");
65 }
66
67 int main(int argc, __attribute__((unused)) char *argv[])
68 {
69         int result;
70         struct sockaddr_un addr;
71         char buf[PBOOT_USER_EVENT_SIZE];
72         ssize_t len;
73         int s;
74         int i;
75         
76         if (argc > 1) {
77                 print_usage();
78                 return EXIT_FAILURE;
79         }
80         
81         s = socket(PF_UNIX, SOCK_DGRAM, 0);
82
83         if (s < 0) {
84                 fprintf(stderr, "pb-event: socket: %s\n", strerror(errno));
85                 return EXIT_FAILURE;
86         }
87
88         result = EXIT_SUCCESS;
89
90         len = fread(buf, 1, sizeof(buf), stdin);
91
92         if (!feof(stdin)) {
93                 fprintf(stderr, "pb-event: msg too big (%u byte max)\n",
94                         (unsigned int)sizeof(buf));
95                 result = EXIT_FAILURE;
96                 /* continue on and try to write msg */
97         }
98
99         if (!len)
100                 return result;
101
102         memset(&addr, 0, sizeof(addr));
103         addr.sun_family = AF_UNIX;
104         strcpy(addr.sun_path, PBOOT_USER_EVENT_SOCKET);
105
106         for (i = 10; i; i--) {
107                 ssize_t sent = sendto(s, buf, len, 0, (struct sockaddr *)&addr,
108                         SUN_LEN(&addr));
109
110                 if (sent == len)
111                         break;
112
113                 DBG("pb-event: waiting for server %d\n", i);
114                 sleep(1);
115         }
116
117         if (!i) {
118                 fprintf(stderr, "pb-event: send: %s\n", strerror(errno));
119                 return EXIT_FAILURE;
120         }
121
122         DBG("pb-event: wrote %u bytes\n", (unsigned int)len);
123         return result;
124 }