Annotation of fam/test/test.c++, Revision 1.1
1.1 ! trev 1: #include <sys/types.h>
! 2: #include <sys/time.h>
! 3: #include <stdio.h>
! 4: #include <string.h>
! 5: #include <unistd.h>
! 6: #include <stdlib.h>
! 7: #include <signal.h>
! 8: #include <errno.h>
! 9: #include <stdarg.h>
! 10: //#include <fcntl.h>
! 11: #include "fam.h"
! 12: //#include "Boolean.h"
! 13: /*
! 14:
! 15: FILE test.c - simple fam test program
! 16:
! 17: Usage: test [-r] [-f <file>] [-d <directory>]
! 18: ex. test -f /etc/hosts -d /tmp
! 19:
! 20: -r includes request IDs in output (if you use this, put it first)
! 21: -f [file] monitors the given file
! 22: -d [dir] monitors the given directory
! 23:
! 24: */
! 25:
! 26:
! 27: void processDirEvents(FAMEvent* fe);
! 28:
! 29: bool suspend = false;
! 30: bool cont = false;
! 31: bool intr = false;
! 32: bool usr1 = false;
! 33: bool usr2 = false;
! 34: bool showReqIDs = false;
! 35: //int lockfd = -1;
! 36: //FILE *fout;
! 37:
! 38: void handle_stop(int) {
! 39: printf("Suspended!\n");
! 40: suspend = true;
! 41: }
! 42:
! 43: void handle_cont(int) {
! 44: printf("Resumed!\n");
! 45: signal(SIGCONT, handle_cont);
! 46: cont = true;
! 47: }
! 48:
! 49: void handle_int(int)
! 50: {
! 51: printf("Interupted!\n");
! 52: signal(SIGINT, handle_int);
! 53: intr = true;
! 54: }
! 55:
! 56: void handle_usr1(int)
! 57: {
! 58: printf("Got USR1!\n");
! 59: signal(SIGUSR1, handle_usr1);
! 60: usr1 = true;
! 61: }
! 62:
! 63: void handle_usr2(int)
! 64: {
! 65: printf("Got USR2!\n");
! 66: signal(SIGUSR2, handle_usr2);
! 67: usr2 = true;
! 68: }
! 69:
! 70: struct TestRequest
! 71: {
! 72: FAMRequest fr;
! 73: char path[PATH_MAX];
! 74: char userData[PATH_MAX];
! 75: bool isDir;
! 76: };
! 77:
! 78: void sendRequests(FAMConnection &fc, TestRequest tr[], int trlen)
! 79: {
! 80: for (int ii = 0; ii < trlen; ++ii) {
! 81: if (tr[ii].isDir) {
! 82: printf("FAMMonitorDirectory(\"%s\")\n", tr[ii].path);
! 83: if (FAMMonitorDirectory(&fc, tr[ii].path, &(tr[ii].fr), tr[ii].userData) < 0) {
! 84: fprintf(stderr, "FAMMonitorDirectory error\n");
! 85: exit(1);
! 86: }
! 87: if (showReqIDs) printf("req %d: ", tr[ii].fr.reqnum);
! 88: printf("FAMMonitorDirectory(\"%s\")\n", tr[ii].path);
! 89: } else {
! 90: printf("FAMMonitorFile(\"%s\")\n", tr[ii].path);
! 91: if (FAMMonitorFile(&fc, tr[ii].path, &(tr[ii].fr), tr[ii].userData) < 0) {
! 92: fprintf(stderr, "FAMMonitorFile error\n");
! 93: exit(1);
! 94: }
! 95: if (showReqIDs) printf("req %d: ", tr[ii].fr.reqnum);
! 96: printf("FAMMonitorFile(\"%s\")\n", tr[ii].path);
! 97: }
! 98: }
! 99: }
! 100:
! 101: //int lprintf(const char *fmt, ...) {
! 102: // int rv;
! 103: // va_list args;
! 104: // int lockfd = fileno(fout);
! 105: //
! 106: // if (lockfd > 2) {
! 107: //fprintf(stderr, "locking fd %d...\n", lockfd);
! 108: //fflush(stderr);
! 109: // lockf(lockfd, F_LOCK, 0);
! 110: // lseek(lockfd, 0, SEEK_END);
! 111: //fprintf(stderr, " locked!\n");
! 112: //fflush(stderr);
! 113: // }
! 114: // va_start(args, fmt);
! 115: // rv = vfprintf(fout, fmt, args);
! 116: // va_end(args);
! 117: // fflush(fout);
! 118: // if (lockfd > 2) {
! 119: // lockf(lockfd, F_ULOCK, 0);
! 120: // }
! 121: // return rv;
! 122: //}
! 123:
! 124: int
! 125: main(int argc, char **argv)
! 126: {
! 127: /* Create fam test */
! 128: // fout = stdout;
! 129: FAMConnection fc;
! 130: TestRequest tr[100];
! 131: int requests = 0;
! 132: FAMEvent fe;
! 133: fd_set readfds;
! 134: fd_set readfdscpy;
! 135: setbuf(stdout, NULL);
! 136:
! 137: if (argc < 2 /*|| (argc %2 != 1)*/ ) {
! 138: printf("usage: %s [-r] [-f <filename>] [-d <dirname>]\n", argv[0]);
! 139: exit(1);
! 140: }
! 141: int arg;
! 142: extern char *optarg;
! 143: extern int optind;
! 144:
! 145: if(FAMOpen(&fc) < 0)
! 146: {
! 147: fprintf(stderr, "FAMOpen failed!\n");
! 148: exit(1);
! 149: }
! 150: FD_ZERO(&readfds);
! 151: FD_SET(fc.fd, &readfds);
! 152: //fcntl(STDIN_FILENO, F_SETFL, FNONBLK);
! 153: //FD_SET(STDIN_FILENO, &readfds);
! 154: while ((arg = getopt(argc, argv, "f:d:r")) != -1)
! 155: {
! 156: switch (arg)
! 157: {
! 158: case 'd':
! 159: case 'f':
! 160: snprintf(tr[requests].userData, PATH_MAX, "%s %s: ",
! 161: (arg == 'd') ? "DIR " : "FILE", optarg);
! 162: snprintf(tr[requests].path, PATH_MAX, "%s", optarg);
! 163: tr[requests].isDir = (arg == 'd');
! 164: ++requests; // just don't use more than 100, OK?
! 165: break;
! 166: case 'r':
! 167: showReqIDs = true;
! 168: break;
! 169: }
! 170: }
! 171:
! 172: signal(SIGTSTP, handle_stop);
! 173: signal(SIGCONT, handle_cont);
! 174: signal(SIGINT, handle_int);
! 175: signal(SIGUSR1, handle_usr1);
! 176: signal(SIGUSR2, handle_usr2);
! 177:
! 178: sendRequests(fc, tr, requests);
! 179:
! 180: while (1) {
! 181: if (suspend) {
! 182: for (int ii = 0; ii < requests; ii++)
! 183: {
! 184: FAMSuspendMonitor(&fc, &(tr[ii].fr));
! 185: printf("Suspended monitoring of request %i\n", ii);
! 186: }
! 187: fflush(stdout);
! 188: suspend = false;
! 189: kill(getpid(),SIGTSTP);
! 190: signal(SIGTSTP, handle_stop);
! 191: }
! 192: if (cont) {
! 193: for (int ii = 0; ii < requests; ii++)
! 194: {
! 195: FAMResumeMonitor(&fc, &(tr[ii].fr));
! 196: printf("Resumed monitoring of request %i\n", ii);
! 197: }
! 198: fflush(stdout);
! 199: cont = false;
! 200: }
! 201: if (intr) {
! 202: // Cancel monitoring of every other request. This makes
! 203: // sure fam can handle the case where the connection goes
! 204: // down with requests outstanding.
! 205: for (int ii = 0; ii < requests ; ii++)
! 206: {
! 207: if (ii % 2 == 0) continue;
! 208: FAMCancelMonitor(&fc, &(tr[ii].fr));
! 209: printf("Canceled monitoring of request %i\n", ii);
! 210: }
! 211: FAMClose(&fc);
! 212: exit(0);
! 213: }
! 214: if (usr1) {
! 215: // Cancel all requests, close the connection, and reopen it.
! 216: // This makes sure long-lived clients can connect, monitor, and
! 217: // disconnect repeatedly without leaking.
! 218: usr1 = false;
! 219: int sleeptime = 1;
! 220: for (int ii = 0; ii < requests ; ii++)
! 221: {
! 222: FAMCancelMonitor(&fc, &(tr[ii].fr));
! 223: printf("Canceled monitoring of request %i\n", ii);
! 224: }
! 225: FAMClose(&fc);
! 226: printf("Closed connection, sleeping %d...\n", sleeptime);
! 227: sleep(sleeptime);
! 228:
! 229: // Now reconnect and resend the requests.
! 230: if(FAMOpen(&fc) < 0)
! 231: {
! 232: fprintf(stderr, "FAMOpen failed!\n");
! 233: exit(1);
! 234: }
! 235: FD_ZERO(&readfds);
! 236: FD_SET(fc.fd, &readfds);
! 237: sendRequests(fc, tr, requests);
! 238: }
! 239: if (usr2) {
! 240: // Clean things up like a well-behaved client and exit.
! 241: for (int ii = 0; ii < requests ; ii++)
! 242: {
! 243: FAMCancelMonitor(&fc, &(tr[ii].fr));
! 244: printf("Canceled monitoring of request %i\n", ii);
! 245: }
! 246: FAMClose(&fc);
! 247: printf("Closed connection\n");
! 248: exit(0);
! 249: }
! 250:
! 251: readfdscpy = readfds;
! 252: if (select(FD_SETSIZE, &readfdscpy, NULL, NULL, NULL) < 0) {
! 253: if (errno == EINTR)
! 254: {
! 255: continue;
! 256: }
! 257: break;
! 258: }
! 259: // while (FAMPending(&fc) > 0) {
! 260: for (; FAMPending(&fc); ) {
! 261: if (FAMNextEvent(&fc, &fe) < 0) {
! 262: printf("Gahh, FAMNextEvent() returned < 0!\n");
! 263: exit(1);
! 264: }
! 265: processDirEvents(&fe);
! 266: fflush(stdout);
! 267: }
! 268: // if (FD_ISSET(STDIN_FILENO, &readfdscpy)) {
! 269: //fprintf(stderr, "reading on stdin...\n");
! 270: //fflush(stderr);
! 271: // int readlen;
! 272: // char buf[PATH_MAX];
! 273: // while ((readlen = read(STDIN_FILENO, buf, PATH_MAX - 1)) > 0) {
! 274: //fprintf(stderr, " readlen == %d\n", readlen);
! 275: //fflush(stderr);
! 276: // buf[readlen] = '\0';
! 277: // printf("%s", buf);
! 278: // }
! 279: //fprintf(stderr, " readlen == %d, errno == %d%s\n", readlen, errno, errno == EAGAIN ? " (EAGAIN)" : "");
! 280: //fflush(stderr);
! 281: // }
! 282: }
! 283: return(EXIT_SUCCESS);
! 284: }
! 285:
! 286:
! 287:
! 288: void
! 289: processDirEvents(FAMEvent* fe)
! 290: {
! 291: if (fe->userdata) printf("%s ", (char *)fe->userdata);
! 292: if (showReqIDs) printf("req %d: ", fe->fr.reqnum);
! 293: switch (fe->code) {
! 294: case FAMExists:
! 295: printf("%s Exists\n", fe->filename);
! 296: break;
! 297: case FAMEndExist:
! 298: printf("%s EndExist\n", fe->filename);
! 299: break;
! 300: case FAMChanged:
! 301: printf("%s Changed\n", fe->filename);
! 302: break;
! 303: case FAMDeleted:
! 304: printf("%s was deleted\n", fe->filename);
! 305: break;
! 306: case FAMStartExecuting:
! 307: printf("%s started executing\n", fe->filename);
! 308: break;
! 309: case FAMStopExecuting:
! 310: printf("%s stopped executing\n", fe->filename);
! 311: break;
! 312: case FAMCreated:
! 313: printf("%s was created\n", fe->filename);
! 314: break;
! 315: case FAMMoved:
! 316: printf("%s was moved\n", fe->filename);
! 317: break;
! 318: default:
! 319: printf("(unknown event %d on %s)\n", fe->code, fe->filename);
! 320: }
! 321: }
! 322:
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>