1 /*
2 * Copyright 1995-2002 Sun Microsystems, Inc. All rights reserved.
3 * Use is subject to license terms.
4 *
5 * Copyright 2013 Nexenta Systems. All rights reserved.
6 */
7
8 /*
9 * Test client for kwarnd. This program is not shipped on the binary
10 * release. This code was taken and modified from gssdtest.c
11 */
12
13 #include <stdio.h>
14 #include <strings.h>
15 #include <ctype.h>
16 #include <stdlib.h>
17 #include "kwarnd.h"
18 #include <rpc/rpc.h>
19
20 #define LOOP_COUNTER 100
21
22 #define OCTAL_MACRO "%03.3o."
23 #define MALLOC(n) malloc(n)
24 #define CALLOC(n, s) calloc((n), (s))
25 #define FREE(x, n) free(x)
26
27 static void instructs(void);
28 static void usage(void);
29 static int parse_input_line(char *, int *, char ***);
30 extern uid_t getuid(void);
31
32 static void _kwarnd_add_warning(int, char **);
33 static void _kwarnd_del_warning(int, char **);
34
35 static int do_kwarndtest(char *buf);
36
37 extern OM_UINT32 kwarn_add_warning();
38 extern OM_UINT32 kwarn_del_warning();
39
read_line(char * buf,int size)40 static int read_line(char *buf, int size)
41 {
42 int len;
43
44 /* read the next line. If cntl-d, return with zero char count */
45 printf(gettext("\n> "));
46
47 if (fgets(buf, size, stdin) == NULL)
48 return (0);
49
50 len = strlen(buf);
51 buf[--len] = '\0';
52 return (len);
53 }
54
55 int
main()56 main()
57 {
58 char buf[512];
59 int len, ret;
60
61 /* Print out usage and instructions to start off the session */
62
63 instructs();
64 usage();
65
66 /*
67 * Loop, repeatedly calling parse_input_line() to get the
68 * next line and parse it into argc and argv. Act on the
69 * arguements found on the line.
70 */
71
72 do {
73 len = read_line(buf, 512);
74 if (len)
75 ret = do_kwarndtest(buf);
76 } while (len && !ret);
77
78 return (0);
79 }
80
81 static int
do_kwarndtest(char * buf)82 do_kwarndtest(char *buf)
83 {
84 int argc;
85 char **argv, **argv_array;
86
87 char *cmd;
88
89 argv = 0;
90
91 if (parse_input_line(buf, &argc, &argv) == 0) {
92 printf(gettext("\n"));
93 return (1);
94 }
95
96 if (argc == 0) {
97 usage();
98 FREE(argv, (argc+1)*sizeof (char *));
99 return (0);
100 }
101
102 /*
103 * remember argv_array address, which is memory calloc'd by
104 * parse_input_line, so it can be free'd at the end of the loop.
105 */
106
107 argv_array = argv;
108
109 cmd = argv[0];
110
111 argc--;
112 argv++;
113
114 if (strcmp(cmd, "kwarn_add_warning") == 0 ||
115 strcmp(cmd, "add") == 0) {
116 _kwarnd_add_warning(argc, argv);
117 } else if (strcmp(cmd, "kwarn_del_warning") == 0 ||
118 strcmp(cmd, "delete") == 0) {
119 _kwarnd_del_warning(argc, argv);
120 } else if (strcmp(cmd, "exit") == 0) {
121 printf(gettext("\n"));
122 FREE(argv_array, (argc+2) * sizeof (char *));
123 return (1);
124 } else
125 usage();
126
127 /* free argv array */
128
129 FREE(argv_array, (argc+2) * sizeof (char *));
130 return (0);
131 }
132
133 static void
_kwarnd_add_warning(int argc,char ** argv)134 _kwarnd_add_warning(int argc, char **argv)
135 {
136 OM_UINT32 status;
137 time_t exptime;
138 time_t now;
139
140 /* set up the arguments specified in the input parameters */
141
142 if (argc == 0) {
143 usage();
144 return;
145 }
146
147 if (argc != 2) {
148 usage();
149 return;
150 }
151
152 time(&now);
153 exptime = atol(argv[1]);
154 exptime = now + exptime;
155
156 status = kwarn_add_warning(argv[0], exptime);
157
158 if (status == 0) {
159 printf(gettext("\nadd of credential\n\n"));
160 printf(gettext("warning message successful for \"%s\"\n\n"),
161 argv[0]);
162 } else {
163 printf(gettext("server ret err (octal) %o (%s)\n"),
164 status, gettext("add warning error"));
165 }
166
167 return;
168
169 }
170
171 static void
_kwarnd_del_warning(int argc,char ** argv)172 _kwarnd_del_warning(int argc, char **argv)
173 {
174 OM_UINT32 status;
175
176 if (argc != 1) {
177 usage();
178 return;
179 }
180
181 status = kwarn_del_warning(argv[0]);
182
183 if (status == 0) {
184 printf(gettext("delete of principal warning message"
185 "for %s successful"),
186 argv[0]);
187 } else {
188 printf(gettext("delete of principal %s unsuccessful\n\n"),
189 argv[0]);
190 }
191 }
192
193 static void
instructs(void)194 instructs(void)
195 {
196 fprintf(stderr,
197 gettext(
198 "\nThis program will test kwarnd. kwarnd must be running as root. Enter\n"
199 "the desired command and the principal to be added/deleted. If adding a\n"
200 "principal, also include the expiration time in seconds.\n"));
201 }
202
203 static void
usage(void)204 usage(void)
205 {
206 fprintf(stderr,
207 gettext(
208 "\nusage:\t[kwarn_add_warning | add] (principal) (exptime)\n"
209 "\t[kwarn_del_warning | delete] (principal)\n"
210 "\texit\n\n"));
211 }
212
213 /* Copied from parse_argv(), then modified */
214
215 static int
parse_input_line(char * input_line,int * argc,char *** argv)216 parse_input_line(char *input_line, int *argc, char ***argv)
217 {
218 const char nil = '\0';
219 char *chptr;
220 int chr_cnt;
221 int arg_cnt = 0;
222 int ch_was_space = 1;
223 int ch_is_space;
224
225 chr_cnt = strlen(input_line);
226
227 /* Count the arguments in the input_line string */
228
229 *argc = 1;
230
231 for (chptr = &input_line[0]; *chptr != nil; chptr++) {
232 ch_is_space = isspace(*chptr);
233 if (ch_is_space && !ch_was_space) {
234 (*argc)++;
235 }
236 ch_was_space = ch_is_space;
237 }
238
239 if (ch_was_space) {
240 (*argc)--;
241 } /* minus trailing spaces */
242
243 /* Now that we know how many args calloc the argv array */
244
245 *argv = (char **)CALLOC((*argc)+1, sizeof (char *));
246 chptr = (char *)(&input_line[0]);
247
248 for (ch_was_space = 1; *chptr != nil; chptr++) {
249 ch_is_space = isspace(*chptr);
250 if (ch_is_space) {
251 *chptr = nil; /* replace each space with nil */
252 } else if (ch_was_space) { /* begining of word? */
253 (*argv)[arg_cnt++] = chptr; /* new argument ? */
254 }
255
256 ch_was_space = ch_is_space;
257 }
258
259 return (chr_cnt);
260 }
261