int main(int argc,char *argv[]) { char *ptr[MAX_ALLOCS]; int freeStep,freeMin,freeMax,blockSize,numAllocs,j; printf("\n"); if (argc < 3 || strcmp(argv[1],"--help") == 0) { usageErr("%s num-allocs block-size [step [min [max]]]\n",argv[0]); } numAllocs = getInt(argv[1],GN_GT_0,"num-allocs"); if (numAllocs > MAX_ALLOCS) { cmdLineErr("num-allocs > %d\n",MAX_ALLOCS); } blockSize = getInt(argv[2],GN_GT_0 | GN_ANY_BASE,"block-size"); freeStep = (argc > 3) ? getInt(argv[3],GN_GT_0,"step") : 1; freeMin = (argc > 4) ? getInt(argv[4],GN_GT_0,"min") : 1; freeMax = (argc > 5) ? getInt(argv[5],GN_GT_0,"max") : numAllocs; if (freeMax > numAllocs) { cmdLineErr("free-max > num-allocs\n"); } printf("Initial program break: %10p\n",sbrk(0)); printf("Allocating %d*%d bytes\n",numAllocs,blockSize); for (j = 0; j < numAllocs; j++) { ptr[j] = malloc(blockSize); if (ptr[j] == NULL) { errExit("malloc"); } printf("Malloc[%d] program break: %10p\n ",j,sbrk(0)); } printf("Program break is now: %10p\n",sbrk(0)); printf("Freeing blocks from %d to %d in steps of %d\n",freeMin,freeMax,freeStep); for (j = freeMin - 1; j < freeMax; j += freeStep) { free(ptr[j]); } printf("After free(),program break is: %10p\n",sbrk(0)); exit(EXIT_SUCCESS); }
int main (int argc, char *argv[]) { if (argc != 2) { usageErr("%s login-name\n", argv[0]); } errno = 0; struct passwd *pw = my_getpwnam(argv[1]); if (pw == NULL) { if (errno != 0) { errExit("my_getpwnam\n"); } else { cmdLineErr("user %s doesn't exist\n", argv[1]); } } printf("Login name: %s\n", pw->pw_name); printf("Encrypted password: %s\n", pw->pw_passwd); printf("User ID: %ld\n", (long) pw->pw_uid); printf("Group ID: %ld\n", (long) pw->pw_gid); printf("Comment: %s\n", pw->pw_gecos); printf("Working directory: %s\n", pw->pw_dir); printf("Login shell: %s\n", pw->pw_shell); exit(EXIT_SUCCESS); }
int main(int argc, char *argv[]) { int fd; char *addr; fd = open(argv[1], O_RDWR); if (fd == -1) errExit("open"); addr = mmap(NULL, MEM_SIZE, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0); if (addr == MAP_FAILED) errExit("mmap"); if (close(fd) == -1) /* No longer need 'fd' */ errExit("close"); printf("Current string=%.*s\n", MEM_SIZE, addr); /* Secure practice: output at most MEM_SIZE bytes */ if (argc > 2) { if (strlen(argv[2]) > MEM_SIZE) cmdLineErr("'new-value' too large\n"); memset(addr, 0, MEM_SIZE); strncpy(addr, argv[2], MEM_SIZE - 1); if (msync(addr, MEM_SIZE, MS_SYNC) == -1) errExit("msync"); printf("Copied \"%s\" to shared memory\n", argv[2]); } exit(EXIT_SUCCESS); }
int main(int argc, char *argv[]) { int level, options, opt; options = 0; level = LOG_INFO; while ((opt = getopt(argc, argv, "l:pe")) != -1) { switch (opt) { case 'l': switch (optarg[0]) { case 'g': level = LOG_EMERG; break; case 'a': level = LOG_ALERT; break; case 'c': level = LOG_CRIT; break; case 'e': level = LOG_ERR; break; case 'w': level = LOG_WARNING; break; case 'n': level = LOG_NOTICE; break; case 'i': level = LOG_INFO; break; case 'd': level = LOG_DEBUG; break; default: cmdLineErr("Bad level: %c\n", optarg[0]); } break; case 'p': options |= LOG_PID; break; #if ! defined(__hpux) && ! defined(__sun) /* Not on HP-UX 11 or Solaris 8 */ case 'e': options |= LOG_PERROR; break; #endif default: fprintf(stderr, "Bad option\n"); usageError(argv[0]); } } if (argc != optind + 1) usageError(argv[0]); openlog(argv[0], options, LOG_USER); syslog(LOG_USER | level, "%s", argv[optind]); closelog(); exit(EXIT_SUCCESS); }
static int parseOps(char *arg, struct sembuf sops[]) { char *comma, *sign, *remaining, *flags; int numOps; /* Number of operations in 'arg' */ for (numOps = 0, remaining = arg; ; numOps++) { if (numOps >= MAX_SEMOPS) cmdLineErr("Too many operations (maximum=%d): \"%s\"\n", MAX_SEMOPS, arg); if (*remaining == '\0') fatal("Trailing comma or empty argument: \"%s\"", arg); if (!isdigit((unsigned char) *remaining)) cmdLineErr("Expected initial digit: \"%s\"\n", arg); sops[numOps].sem_num = strtol(remaining, &sign, 10); if (*sign == '\0' || strchr("+-=", *sign) == NULL) cmdLineErr("Expected '+', '-', or '=' in \"%s\"\n", arg); if (!isdigit((unsigned char) *(sign + 1))) cmdLineErr("Expected digit after '%c' in \"%s\"\n", *sign, arg); sops[numOps].sem_op = strtol(sign + 1, &flags, 10); if (*sign == '-') /* Reverse sign of operation */ sops[numOps].sem_op = - sops[numOps].sem_op; else if (*sign == '=') /* Should be '=0' */ if (sops[numOps].sem_op != 0) cmdLineErr("Expected \"=0\" in \"%s\"\n", arg); sops[numOps].sem_flg = 0; for (;; flags++) { if (*flags == 'n') sops[numOps].sem_flg |= IPC_NOWAIT; else if (*flags == 'u') sops[numOps].sem_flg |= SEM_UNDO; else break; } if (*flags != ',' && *flags != '\0') cmdLineErr("Bad trailing character (%c) in \"%s\"\n", *flags, arg); comma = strchr(remaining, ','); if (comma == NULL) break; /* No comma --> no more ops */ else remaining = comma + 1; } return numOps + 1; }
int main(int argc, char *argv[]) { int msqid, flags, msgLen; struct mbuf msg; /* Message buffer for msgsnd() */ int opt; /* Option character from getopt() */ /* Parse command-line options and arguments */ flags = 0; while ((opt = getopt(argc, argv, "n")) != -1) { if (opt == 'n') flags |= IPC_NOWAIT; else usageError(argv[0], NULL); } if (argc < optind + 2 || argc > optind + 3) usageError(argv[0], "Wrong number of arguments\n"); msqid = getInt(argv[optind], 0, "msqid"); msg.mtype = getInt(argv[optind + 1], 0, "msg-type"); if (argc > optind + 2) /* 'msg-text' was supplied */ { msgLen = strlen(argv[optind + 2]) + 1; if (msgLen > MAX_MTEXT) cmdLineErr("msg-text too long (max: %d characters)\n", MAX_MTEXT); memcpy(msg.mtext, argv[optind + 2], msgLen); } else /* No 'msg-text' ==> zero-length msg */ { msgLen = 0; } /* Send message */ if (msgsnd(msqid, &msg, msgLen, flags) == -1) errExit("msgsnd"); exit(EXIT_SUCCESS); }
int main(int argc, char *argv[]) { struct semid_ds ds; union semun arg; /* Fourth argument for semctl() */ int j, semid; if (argc < 3 || strcmp(argv[1], "--help") == 0) usageErr("%s semid val...\n", argv[0]); semid = getInt(argv[1], 0, "semid"); /* Obtain size of semaphore set */ arg.buf = &ds; if (semctl(semid, 0, IPC_STAT, arg) == -1) errExit("semctl"); /* The number of values supplied on the command line must match the number of semaphores in the set */ if (ds.sem_nsems != argc - 2) cmdLineErr("Set contains %ld semaphores, but %d values were supplied\n", (long) ds.sem_nsems, argc - 2); /* Set up array of values; perform semaphore initialization */ arg.array = calloc(ds.sem_nsems, sizeof(arg.array[0])); if (arg.array == NULL) errExit("calloc"); for (j = 2; j < argc; j++) arg.array[j - 2] = getInt(argv[j], 0, "val"); if (semctl(semid, 0, SETALL, arg) == -1) errExit("semctl-SETALL"); printf("Semaphore values changed (PID=%ld)\n", (long) getpid()); exit(EXIT_SUCCESS); }
int main(int argc, char *argv[]) { struct semid_ds ds; union semun arg; int semid; if(argc<3 || !strcmp(argv[1], "--help")) usageErr("%s semid val...\n", argv[0]); semid = getInt(argv[1], 0, "semid"); /* Obtain size of semaphore set */ arg.buf = &ds; if(semctl(semid, 0, IPC_STAT, arg) == -1) errExit("semctl()"); if(ds.sem_nsems != (unsigned long) (argc-2)) cmdLineErr("Set contains %jd semaphores, but %d values were supplied\n", (intmax_t) ds.sem_nsems, argc-2); /* Set up array of values; perform semaphore initialization */ arg.array = calloc(ds.sem_nsems, sizeof(arg.array[0])); if(arg.array == NULL) errExit("calloc()"); for(int j=2; j<argc; ++j) arg.array[j-2] = getInt(argv[j], 0, "val"); if(semctl(semid, 0, SETALL, arg) == -1) errExit("semctl() - SETALL"); printf("Semaphore values changed (PID = %jd)\n", (intmax_t) getpid()); exit(EXIT_SUCCESS); }
int main(int argc, char *argv[]) { size_t len; off_t offset; int fd, ap, j; char *buf; ssize_t numRead, numWritten; if (argc < 3 || strcmp(argv[1], "--help") == 0) usageErr("%s file {r<length>|R<length>|w<string>|s<offset>}...\n", argv[0]); fd = open(argv[1], O_RDWR | O_CREAT, S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH); /* rw-rw-rw- */ if (fd == -1) errExit("open"); for (ap = 2; ap < argc; ap++) { switch (argv[ap][0]) { case 'r': /* Display bytes at current offset, as text */ case 'R': /* Display bytes at current offset, in hex */ len = getLong(&argv[ap][1], GN_ANY_BASE, argv[ap]); buf = malloc(len); if (buf == NULL) errExit("malloc"); numRead = read(fd, buf, len); if (numRead == -1) errExit("read"); if (numRead == 0) { printf("%s: end-of-file\n", argv[ap]); } else { printf("%s: ", argv[ap]); for (j = 0; j < numRead; j++) { if (argv[ap][0] == 'r') printf("%c", isprint((unsigned char) buf[j]) ? buf[j] : '?'); else printf("%02x ", (unsigned int) buf[j]); } printf("\n"); } free(buf); break; case 'w': /* Write string at current offset */ numWritten = write(fd, &argv[ap][1], strlen(&argv[ap][1])); if (numWritten == -1) errExit("write"); printf("%s: wrote %ld bytes\n", argv[ap], (long) numWritten); break; case 's': /* Change file offset */ offset = getLong(&argv[ap][1], GN_ANY_BASE, argv[ap]); if (lseek(fd, offset, SEEK_SET) == -1) errExit("lseek"); printf("%s: seek succeeded\n", argv[ap]); break; default: cmdLineErr("Argument must start with [rRws]: %s\n", argv[ap]); } } if (close(fd) == -1) errExit("close"); exit(EXIT_SUCCESS); }
int main(int argc, char *argv[]) { fd_set readfds; int ready, nfds, flags; struct timeval timeout; struct timeval *pto; struct sigaction sa; char ch; int fd, j; if (argc < 2 || strcmp(argv[1], "--help") == 0) usageErr("%s {timeout|-} fd...\n" "\t\t('-' means infinite timeout)\n", argv[0]); /* Initialize 'timeout', 'readfds', and 'nfds' for select() */ if (strcmp(argv[1], "-") == 0) { pto = NULL; /* Infinite timeout */ } else { pto = &timeout; timeout.tv_sec = getLong(argv[1], 0, "timeout"); timeout.tv_usec = 0; /* No microseconds */ } nfds = 0; /* Build the 'readfds' from the fd numbers given in command line */ FD_ZERO(&readfds); for (j = 2; j < argc; j++) { fd = getInt(argv[j], 0, "fd"); if (fd >= FD_SETSIZE) cmdLineErr("file descriptor exceeds limit (%d)\n", FD_SETSIZE); if (fd >= nfds) nfds = fd + 1; /* Record maximum fd + 1 */ FD_SET(fd, &readfds); } /* Create pipe before establishing signal handler to prevent race */ if (pipe(pfd) == -1) errExit("pipe"); FD_SET(pfd[0], &readfds); /* Add read end of pipe to 'readfds' */ nfds = max(nfds, pfd[0] + 1); /* And adjust 'nfds' if required */ /* Make read and write ends of pipe nonblocking */ flags = fcntl(pfd[0], F_GETFL); if (flags == -1) errExit("fcntl-F_GETFL"); flags |= O_NONBLOCK; /* Make read end nonblocking */ if (fcntl(pfd[0], F_SETFL, flags) == -1) errExit("fcntl-F_SETFL"); flags = fcntl(pfd[1], F_GETFL); if (flags == -1) errExit("fcntl-F_GETFL"); flags |= O_NONBLOCK; /* Make write end nonblocking */ if (fcntl(pfd[1], F_SETFL, flags) == -1) errExit("fcntl-F_SETFL"); sigemptyset(&sa.sa_mask); sa.sa_flags = SA_RESTART; /* Restart interrupted reads()s */ sa.sa_handler = handler; if (sigaction(SIGINT, &sa, NULL) == -1) errExit("sigaction"); while ((ready = select(nfds, &readfds, NULL, NULL, pto)) == -1 && errno == EINTR) continue; /* Restart if interrupted by signal */ if (ready == -1) /* Unexpected error */ errExit("select"); if (FD_ISSET(pfd[0], &readfds)) { /* Handler was called */ printf("A signal was caught\n"); for (;;) { /* Consume bytes from pipe */ if (read(pfd[0], &ch, 1) == -1) { if (errno == EAGAIN) break; /* No more bytes */ else errExit("read"); /* Some other error */ } /* Perform any actions that should be taken in response to signal */ } } /* Examine file descriptor sets returned by select() to see which other file descriptors are ready */ printf("ready = %d\n", ready); for (j = 2; j < argc; j++) { fd = getInt(argv[j], 0, "fd"); printf("%d: %s\n", fd, FD_ISSET(fd, &readfds) ? "r" : ""); } /* And check if read end of pipe is ready */ printf("%d: %s (read end of pipe)\n", pfd[0], FD_ISSET(pfd[0], &readfds) ? "r" : ""); if (pto != NULL) printf("timeout after select(): %ld.%03ld\n", (long) timeout.tv_sec, (long) timeout.tv_usec / 1000); exit(EXIT_SUCCESS); }
int main(int argc, char *argv[]) { DIR *dirp; struct dirent *dp; char path[PATH_MAX]; char line[MAX_LINE], cmd[MAX_LINE]; FILE *fp; char *p; uid_t uid, checkedUid; Boolean gotName, gotUid; if (argc < 2 || strcmp(argv[1], "--help") == 0) usageErr("%s username\n", argv[0]); checkedUid = userIdFromName(argv[1]); if (checkedUid == -1) cmdLineErr("Bad username: %s\n", argv[1]); dirp = opendir("/proc"); if (dirp == NULL) errExit("opendir"); for (;;) { errno = 0; /* To distinguish error from end-of-directory */ dp = readdir(dirp); if (dp == NULL) { if (errno != 0) errExit("readdir"); else break; } if (dp->d_type != DT_DIR || !isdigit((unsigned char) dp->d_name[0])) continue; snprintf(path, PATH_MAX, "/proc/%s/status", dp->d_name); fp = fopen(path, "r"); if (fp == NULL) continue; /* Ignore errors: fopen() might fail if process has just terminated */ gotName = FALSE; gotUid = FALSE; while (!gotName || !gotUid) { if (fgets(line, MAX_LINE, fp) == NULL) break; /* The "Name:" line contains the name of the command that this process is running */ if (strncmp(line, "Name:", 5) == 0) { for (p = line + 5; *p != '\0' && isspace((unsigned char) *p); ) p++; strncpy(cmd, p, MAX_LINE - 1); cmd[MAX_LINE -1] = '\0'; /* Ensure null-terminated */ gotName = TRUE; } /* The "Uid:" line contains the real, effective, saved set-, and file-system user IDs */ if (strncmp(line, "Uid:", 4) == 0) { uid = strtol(line + 4, NULL, 10); gotUid = TRUE; } } fclose(fp); /* If we found a username and a UID, and the UID matches, then display the PID and command name */ if (gotName && gotUid && uid == checkedUid) printf("%5s %s", dp->d_name, cmd); } exit(EXIT_SUCCESS); }
int main(int argc, char *argv[]) { int numKeyFlags; /* Counts -f, -k, and -p options */ int flags, shmid, segSize; unsigned int perms; long lkey; key_t key; int opt; /* Option character from getopt() */ /* Parse command-line options and arguments */ numKeyFlags = 0; flags = 0; while ((opt = getopt(argc, argv, "cf:k:px")) != -1) { switch (opt) { case 'c': flags |= IPC_CREAT; break; case 'f': /* -f pathname */ key = ftok(optarg, 1); if (key == -1) errExit("ftok"); numKeyFlags++; break; case 'k': /* -k key (octal, decimal or hexadecimal) */ if (sscanf(optarg, "%li", &lkey) != 1) cmdLineErr("-k option requires a numeric argument\n"); key = lkey; numKeyFlags++; break; case 'p': key = IPC_PRIVATE; numKeyFlags++; break; case 'x': flags |= IPC_EXCL; break; default: usageError(argv[0], NULL); } } if (numKeyFlags != 1) usageError(argv[0], "Exactly one of the options -f, -k, " "or -p must be supplied\n"); if (optind >= argc) usageError(argv[0], "Size of segment must be specified\n"); segSize = getLong(argv[optind], GN_ANY_BASE, "seg-size"); perms = (argc <= optind + 1) ? (S_IRUSR | S_IWUSR) : getInt(argv[optind + 1], GN_BASE_8, "octal-perms"); shmid = shmget(key, segSize, flags | perms); if (shmid == -1) errExit("shmget"); printf("%d\n", shmid); /* On success, display shared mem. id */ exit(EXIT_SUCCESS); }
int main(int argc, char *argv[]) { struct requestMsg req; struct responseMsg resp; int serverId, numMsgs; ssize_t msgLen, totBytes; if (argc != 2 || strcmp(argv[1], "--help") == 0) usageErr("%s pathname\n", argv[0]); if (strlen(argv[1]) > sizeof(req.pathname) - 1) cmdLineErr("pathname too long (max: %ld bytes)\n", (long) sizeof(req.pathname) - 1); /* Get server's queue identifier; create queue for response */ serverId = msgget(SERVER_KEY, S_IWUSR); if (serverId == -1) errExit("msgget - server message queue"); clientId = msgget(IPC_PRIVATE, S_IRUSR | S_IWUSR | S_IWGRP); if (clientId == -1) errExit("msgget - client message queue"); if (atexit(removeQueue) != 0) errExit("atexit"); /* Send message asking for file named in argv[1] */ req.mtype = 1; /* Any type will do */ req.clientId = clientId; strncpy(req.pathname, argv[1], sizeof(req.pathname) - 1); req.pathname[sizeof(req.pathname) - 1] = '\0'; /* Ensure string is terminated */ if (msgsnd(serverId, &req, REQ_MSG_SIZE, 0) == -1) errExit("msgsnd"); /* Get first response, which may be failure notification */ msgLen = msgrcv(clientId, &resp, RESP_MSG_SIZE, 0, 0); if (msgLen == -1) errExit("msgrcv"); if (resp.mtype == RESP_MT_FAILURE) { printf("%s\n", resp.data); /* Display msg from server */ exit(EXIT_FAILURE); } /* File was opened successfully by server; process messages (including the one already received) containing file data */ totBytes = msgLen; /* Count first message */ for (numMsgs = 1; resp.mtype == RESP_MT_DATA; numMsgs++) { msgLen = msgrcv(clientId, &resp, RESP_MSG_SIZE, 0, 0); if (msgLen == -1) errExit("msgrcv"); totBytes += msgLen; } printf("Received %ld bytes (%d messages)\n", (long) totBytes, numMsgs); exit(EXIT_SUCCESS); }
int main(int argc, char *argv[]) { fd_set readfds, writefds; int ready, nfds, fd, numRead, j; struct timeval timeout; struct timeval *pto; char buf[10]; /* Large enough to hold "rw\0" */ if (argc < 2 || strcmp(argv[1], "--help") == 0) usageError(argv[0]); /* Timeout for select() is specified in argv[1] */ if (strcmp(argv[1], "-") == 0) { pto = NULL; /* Infinite timeout */ } else { pto = &timeout; timeout.tv_sec = getLong(argv[1], 0, "timeout"); timeout.tv_usec = 0; /* No microseconds */ } /* Process remaining arguments to build file descriptor sets */ nfds = 0; FD_ZERO(&readfds); FD_ZERO(&writefds); for (j = 2; j < argc; j++) { numRead = sscanf(argv[j], "%d%2[rw]", &fd, buf); if (numRead != 2) usageError(argv[0]); if (fd >= FD_SETSIZE) cmdLineErr("file descriptor exceeds limit (%d)\n", FD_SETSIZE); if (fd >= nfds) nfds = fd + 1; /* Record maximum fd + 1 */ if (strchr(buf, 'r') != NULL) FD_SET(fd, &readfds); if (strchr(buf, 'w') != NULL) FD_SET(fd, &writefds); } /* We've built all of the arguments; now call select() */ ready = select(nfds, &readfds, &writefds, NULL, pto); /* Ignore exceptional events */ if (ready == -1) errExit("select"); /* Display results of select() */ printf("ready = %d\n", ready); for (fd = 0; fd < nfds; fd++) printf("%d: %s%s\n", fd, FD_ISSET(fd, &readfds) ? "r" : "", FD_ISSET(fd, &writefds) ? "w" : ""); if (pto != NULL) printf("timeout after select(): %ld.%03ld\n", (long) timeout.tv_sec, (long) timeout.tv_usec / 10000); exit(EXIT_SUCCESS); }
int main(int argc, char *argv[]) { int numKeyFlags; /* Counts -f, -k, and -p options */ int flags, msqid, opt; unsigned int perms; long lkey; key_t key; /* Parse command-line options and arguments */ numKeyFlags = 0; flags = 0; while ((opt = getopt(argc, argv, "cf:k:px")) != -1) { switch (opt) { case 'c': flags |= IPC_CREAT; break; case 'f': /* -f pathname */ key = ftok(optarg, 1); if (key == -1) errExit("ftok"); numKeyFlags++; break; case 'k': /* -k key (octal, decimal or hexadecimal) */ if (sscanf(optarg, "%li", &lkey) != 1) cmdLineErr("-k option requires a numeric argument\n"); key = lkey; numKeyFlags++; break; case 'p': key = IPC_PRIVATE; numKeyFlags++; break; case 'x': flags |= IPC_EXCL; break; default: usageError(argv[0], "Bad option\n"); } } if (numKeyFlags != 1) usageError(argv[0], "Exactly one of the options -f, -k, " "or -p must be supplied\n"); perms = (optind == argc) ? (S_IRUSR | S_IWUSR) : getInt(argv[optind], GN_BASE_8, "octal-perms"); msqid = msgget(key, flags | perms); if (msqid == -1) errExit("msgget"); printf("%d\n", msqid); exit(EXIT_SUCCESS); }