Annotation of src/usr.bin/cvs/watch.c, Revision 1.10
1.10 ! xsa 1: /* $OpenBSD: watch.c,v 1.9 2005/12/30 02:03:28 joris Exp $ */
1.1 xsa 2: /*
3: * Copyright (c) 2005 Xavier Santolaria <xsa@openbsd.org>
1.7 moritz 4: * Copyright (c) 2005 Moritz Jodeit <moritz@openbsd.org>
1.1 xsa 5: * All rights reserved.
6: *
7: * Redistribution and use in source and binary forms, with or without
8: * modification, are permitted provided that the following conditions
9: * are met:
10: *
11: * 1. Redistributions of source code must retain the above copyright
12: * notice, this list of conditions and the following disclaimer.
13: * 2. The name of the author may not be used to endorse or promote products
14: * derived from this software without specific prior written permission.
15: *
16: * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
17: * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
18: * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
19: * THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
20: * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
21: * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
22: * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
23: * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
24: * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
25: * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26: */
27:
28: #include <sys/types.h>
29:
30: #include <errno.h>
31: #include <fcntl.h>
32: #include <stdio.h>
33: #include <stdlib.h>
34: #include <string.h>
35: #include <unistd.h>
36:
37: #include "cvs.h"
38: #include "log.h"
39: #include "proto.h"
40:
1.5 xsa 41: static int cvs_watch_init(struct cvs_cmd *, int, char **, int *);
1.7 moritz 42: static int cvs_watch_pre_exec(struct cvsroot *);
1.5 xsa 43: static int cvs_watch_remote(CVSFILE *, void*);
44: static int cvs_watch_local(CVSFILE *, void*);
1.1 xsa 45:
1.7 moritz 46: static int cvs_watchers_init(struct cvs_cmd *, int, char **, int *);
1.5 xsa 47: static int cvs_watchers_local(CVSFILE *, void*);
1.1 xsa 48:
49:
50: struct cvs_cmd cvs_cmd_watch = {
51: CVS_OP_WATCH, CVS_REQ_NOOP, "watch",
52: {},
1.3 xsa 53: "Set watches",
1.1 xsa 54: "on | off | add | remove [-lR] [-a action] [file ...]",
55: "a:lR",
56: NULL,
1.7 moritz 57: CF_SORT | CF_IGNORE | CF_RECURSE,
1.1 xsa 58: cvs_watch_init,
1.7 moritz 59: cvs_watch_pre_exec,
1.1 xsa 60: cvs_watch_remote,
61: cvs_watch_local,
62: NULL,
63: NULL,
1.7 moritz 64: CVS_CMD_SENDDIR | CVS_CMD_ALLOWSPEC | CVS_CMD_SENDARGS2
1.1 xsa 65: };
66:
67: struct cvs_cmd cvs_cmd_watchers = {
1.4 joris 68: CVS_OP_WATCHERS, CVS_REQ_WATCHERS, "watchers",
69: {},
70: "See who is watching a file",
71: "[-lR] [file ...]",
72: "lR",
73: NULL,
1.7 moritz 74: CF_SORT | CF_IGNORE | CF_RECURSE,
75: cvs_watchers_init,
1.4 joris 76: NULL,
1.7 moritz 77: cvs_watch_remote,
1.4 joris 78: cvs_watchers_local,
79: NULL,
80: NULL,
1.6 xsa 81: CVS_CMD_SENDDIR | CVS_CMD_ALLOWSPEC | CVS_CMD_SENDARGS2
1.1 xsa 82: };
83:
84:
1.7 moritz 85: static char *aoptstr = NULL;
86: static int watchreq = 0;
1.1 xsa 87:
88: static int
89: cvs_watch_init(struct cvs_cmd *cmd, int argc, char **argv, int *arg)
90: {
91: int ch;
1.4 joris 92:
1.7 moritz 93: if (argc < 2)
94: return (CVS_EX_USAGE);
95:
96: if (strcmp(argv[1], "on") == 0)
97: watchreq = CVS_REQ_WATCH_ON;
98: else if (strcmp(argv[1], "off") == 0)
99: watchreq = CVS_REQ_WATCH_OFF;
100: else if (strcmp(argv[1], "add") == 0)
101: watchreq = CVS_REQ_WATCH_ADD;
102: else if (strcmp(argv[1], "remove") == 0)
103: watchreq = CVS_REQ_WATCH_REMOVE;
104: else
105: return (CVS_EX_USAGE);
106:
107: cmd->cmd_req = watchreq;
108: optind = 2;
109:
1.1 xsa 110: while ((ch = getopt(argc, argv, cmd->cmd_opts)) != -1) {
111: switch (ch) {
112: case 'a':
1.2 xsa 113: /*
1.7 moritz 114: * Only `watch add | remove' support the -a option.
115: * Check which command has been issued.
1.2 xsa 116: */
1.10 ! xsa 117: if ((watchreq != CVS_REQ_WATCH_ADD) &&
! 118: (watchreq != CVS_REQ_WATCH_REMOVE))
1.7 moritz 119: return (CVS_EX_USAGE);
1.10 ! xsa 120: if ((strcmp(optarg, "commit") != 0) &&
! 121: (strcmp(optarg, "edit") != 0) &&
! 122: (strcmp(optarg, "unedit") != 0) &&
! 123: (strcmp(optarg, "all") != 0) &&
! 124: (strcmp(optarg, "none") != 0))
1.1 xsa 125: return (CVS_EX_USAGE);
1.8 joris 126: aoptstr = xstrdup(optarg);
1.1 xsa 127: break;
128: case 'l':
129: cmd->file_flags &= ~CF_RECURSE;
130: break;
131: case 'R':
132: cmd->file_flags |= CF_RECURSE;
133: break;
134: default:
135: return (CVS_EX_USAGE);
136: }
137: }
138:
139: *arg = optind;
140: return (CVS_EX_OK);
141: }
142:
143:
144: /*
1.7 moritz 145: * cvs_watch_pre_exec()
1.1 xsa 146: *
147: */
148: static int
1.7 moritz 149: cvs_watch_pre_exec(struct cvsroot *root)
1.1 xsa 150: {
1.7 moritz 151: if (root->cr_method != CVS_METHOD_LOCAL) {
1.10 ! xsa 152: if ((watchreq != CVS_REQ_WATCH_ADD) &&
! 153: (watchreq != CVS_REQ_WATCH_REMOVE))
1.7 moritz 154: return (CVS_EX_OK);
155:
156: if (aoptstr == NULL || strcmp(aoptstr, "all") == 0) {
157: /* Defaults to: edit, unedit, commit */
1.9 joris 158: cvs_sendarg(root, "-a", 0);
159: cvs_sendarg(root, "edit", 0);
160: cvs_sendarg(root, "-a", 0);
161: cvs_sendarg(root, "unedit", 0);
162: cvs_sendarg(root, "-a", 0);
163: cvs_sendarg(root, "commit", 0);
1.7 moritz 164: } else {
1.9 joris 165: cvs_sendarg(root, "-a", 0);
166: cvs_sendarg(root, aoptstr, 0);
1.7 moritz 167: }
168: }
1.9 joris 169:
1.8 joris 170: xfree(aoptstr);
1.7 moritz 171:
1.1 xsa 172: return (CVS_EX_OK);
173: }
174:
175:
176: /*
177: * cvs_watch_local()
178: *
179: */
180: static int
1.6 xsa 181: cvs_watch_local(CVSFILE *cf, void *arg)
1.1 xsa 182: {
183: return (CVS_EX_OK);
184: }
185:
186:
187: /*
1.7 moritz 188: * cvs_watch_remote()
1.1 xsa 189: *
190: */
191: static int
1.7 moritz 192: cvs_watch_remote(CVSFILE *cf, void *arg)
1.1 xsa 193: {
1.6 xsa 194: struct cvsroot *root;
195:
196: root = CVS_DIR_ROOT(cf);
197:
198: if (cf->cf_type == DT_DIR) {
199: if (cf->cf_cvstat == CVS_FST_UNKNOWN)
1.9 joris 200: cvs_sendreq(root, CVS_REQ_QUESTIONABLE, cf->cf_name);
1.6 xsa 201: else
1.9 joris 202: cvs_senddir(root, cf);
203: return (0);
1.6 xsa 204: }
205:
1.9 joris 206: cvs_sendentry(root, cf);
1.6 xsa 207:
208: switch (cf->cf_cvstat) {
209: case CVS_FST_UNKNOWN:
1.9 joris 210: cvs_sendreq(root, CVS_REQ_QUESTIONABLE, cf->cf_name);
1.6 xsa 211: break;
212: case CVS_FST_UPTODATE:
1.9 joris 213: cvs_sendreq(root, CVS_REQ_UNCHANGED, cf->cf_name);
1.6 xsa 214: break;
215: case CVS_FST_ADDED:
216: case CVS_FST_MODIFIED:
1.9 joris 217: cvs_sendreq(root, CVS_REQ_ISMODIFIED, cf->cf_name);
1.6 xsa 218: break;
219: default:
220: break;
221: }
222:
1.9 joris 223: return (0);
1.1 xsa 224: }
1.7 moritz 225:
226:
227: /*
228: * cvs_watchers_init()
229: *
230: */
231: static int
232: cvs_watchers_init(struct cvs_cmd *cmd, int argc, char **argv, int *arg)
233: {
234: int ch;
235:
236: while ((ch = getopt(argc, argv, cmd->cmd_opts)) != -1) {
237: switch (ch) {
238: case 'l':
239: cmd->file_flags &= ~CF_RECURSE;
240: break;
241: case 'R':
242: cmd->file_flags |= CF_RECURSE;
243: break;
244: default:
245: return (CVS_EX_USAGE);
246: }
247: }
248:
249: *arg = optind;
250: return (CVS_EX_OK);
251: }
252:
1.4 joris 253:
1.1 xsa 254: /*
255: * cvs_watchers_local()
256: *
257: */
258: static int
1.6 xsa 259: cvs_watchers_local(CVSFILE *cf, void *arg)
1.1 xsa 260: {
261: return (CVS_EX_OK);
262: }