/* BEGIN DEFUNCT */ obreak() { struct a { char *nsiz; }; register size_t n, d, ds; /* * set n to new data size */ n = btoc(((struct a *)u.u_ap)->nsiz) - ctos(u.u_tsize) * stoc(1); if (n < 0) n = 0; /* * since we can't pass a -ve argument for the difference to chksize, * if d is negative, make ds equal to the final value and clear d. * keep the real difference in n for later use in expand. */ ds = u.u_dsize; if ((n = d = clrnd(n - u.u_dsize)) < 0) { ds += d; d = 0; } if (ctob(ds + d) > u.u_rlimit[RLIMIT_DATA].rlim_cur) { u.u_error = ENOMEM; return; } if (chksize((u_int)u.u_tsize, (u_int)ds, (u_int)d, (u_int)u.u_ssize)) return; if (swpexpand(ds + d, u.u_ssize, &u.u_dmap, &u.u_smap) == 0) return; expand((int)n, 0); }
/* * Read printer jobs sent by lpd and copy them to the spooling directory. * Return the number of jobs successfully transfered. */ static int readjob() { register int size, nfiles; register char *cp; ack(); nfiles = 0; for (;;) { /* * Read a command to tell us what to do */ cp = line; do { if ((size = read(1, cp, 1)) != 1) { if (size < 0) frecverr("%s: Lost connection",printer); return(nfiles); } } while (*cp++ != '\n'); *--cp = '\0'; cp = line; switch (*cp++) { case '\1': /* cleanup because data sent was bad */ rcleanup(0); continue; case '\2': /* read cf file */ size = 0; while (*cp >= '0' && *cp <= '9') size = size * 10 + (*cp++ - '0'); if (*cp++ != ' ') break; /* * host name has been authenticated, we use our * view of the host name since we may be passed * something different than what gethostbyaddr() * returns */ strcpy(cp + 6, from); strcpy(tfname, cp); tfname[0] = 't'; if (!chksize(size)) { (void) write(1, "\2", 1); continue; } if (!readfile(tfname, size)) { rcleanup(0); continue; } if (link(tfname, cp) < 0) frecverr("%s: %m", tfname); (void) unlink(tfname); tfname[0] = '\0'; nfiles++; continue; case '\3': /* read df file */ size = 0; while (*cp >= '0' && *cp <= '9') size = size * 10 + (*cp++ - '0'); if (*cp++ != ' ') break; if (!chksize(size)) { (void) write(1, "\2", 1); continue; } (void) strcpy(dfname, cp); if (index(dfname, '/')) frecverr("readjob: %s: illegal path name", dfname); (void) readfile(dfname, size); continue; } frecverr("protocol screwup: %s", line); } }
void loadregs(void) /* * initialize allocated registers */ { CSE *csp; ENODE *exptr; unsigned mask, rmask, i, fmask, frmask, size; AMODE *ap, *ap2; csp = olist; while (csp != 0) { int sz; if (csp->reg != - 1) { /* see if preload needed */ exptr = csp->exp; if (!lvalue(exptr) || ((SYM*)exptr->v.p[0]->v.p[0])->funcparm) { exptr = csp->exp; InitRegs(); sz = csp->size; ap = gen_expr_external(exptr, FALSE, F_MEM | F_DREG | F_IMMED, sz); if (csp->reg < 16) { if (ap->mode == am_dreg) peep_tail->oper1->preg = csp->reg; else { if (csp->reg > 3 && chksize(BESZ_WORD, sz)) DIAG("byte sized non-register in analyze"); ap2 = makedreg(csp->reg); ap2->length = BESZ_DWORD; if (ap->mode == am_immed || ap->length == BESZ_DWORD || ap ->length == - BESZ_DWORD) gen_codes(op_mov, BESZ_DWORD, ap2, ap); else if (sz < 0) gen_code(op_movsx, ap2, ap); else gen_code(op_movzx, ap2, ap); } } else if (csp->reg < 32) { if (ap->mode == am_dreg) peep_tail->oper1->preg = csp->reg - 12; else { if (csp->reg - 12 > 3 && chksize(BESZ_WORD, sz)) DIAG("byte sized non-register in analyze"); ap2 = makedreg(csp->reg - 12); ap2->length = BESZ_DWORD; if (ap->mode == am_immed || ap->length == BESZ_DWORD || ap ->length == - BESZ_DWORD) gen_codes(op_mov, BESZ_DWORD, ap2, ap); else if (sz < 0) gen_code(op_movsx, ap2, ap); else gen_code(op_movzx, ap2, ap); } } else { /* Should never get here */ DIAG("float reg assigned in analyze"); } if (lvalue(exptr) && ((SYM*)exptr->v.p[0]->v.p[0])->funcparm) { ((SYM*)exptr->v.p[0]->v.p[0])->mainsym->inreg = TRUE; ((SYM*)exptr->v.p[0]->v.p[0])->mainsym->value.i = - csp ->reg - (csp->size < 0 ? - csp->size: csp->size) *256; } } } csp = csp->next; } gen_label(startlab); }
/* * Read printer jobs sent by lpd and copy them to the spooling directory. * Return the number of jobs successfully transferred. */ static int readjob(void) { int size, nfiles; char *cp; ack(); nfiles = 0; for (;;) { /* * Read a command to tell us what to do */ cp = line; do { if ((size = read(STDOUT_FILENO, cp, 1)) != 1) { if (size < 0) frecverr("%s: Lost connection", printer); return(nfiles); } } while (*cp++ != '\n' && (cp - line + 1) < sizeof(line)); if (cp - line + 1 >= sizeof(line)) frecverr("readjob overflow"); *--cp = '\0'; cp = line; switch (*cp++) { case '\1': /* cleanup because data sent was bad */ rcleanup(0); continue; case '\2': /* read cf file */ size = 0; while (*cp >= '0' && *cp <= '9') size = size * 10 + (*cp++ - '0'); if (*cp++ != ' ') break; /* * host name has been authenticated, we use our * view of the host name since we may be passed * something different than what gethostbyaddr() * returns */ strlcpy(cp + 6, from, sizeof(line) + line - cp - 6); if (strchr(cp, '/')) frecverr("readjob: %s: illegal path name", cp); strlcpy(tfname, cp, sizeof(tfname)); tfname[0] = 't'; if (!chksize(size)) { (void)write(STDOUT_FILENO, "\2", 1); continue; } /* * XXX * We blindly believe what the remote host puts * for the path to the df file. In general this * is OK since we don't allow paths with '/' in * them. Still, it would be better to sanity * check the cf file sent to us and make the * df name match the cf name we used. That way * we avoid any possible collisions. */ if (!readfile(tfname, size)) { rcleanup(0); continue; } if (link(tfname, cp) < 0) frecverr("link %s %s: %m", tfname, cp); (void)unlink(tfname); tfname[0] = '\0'; nfiles++; continue; case '\3': /* read df file */ size = 0; while (*cp >= '0' && *cp <= '9') size = size * 10 + (*cp++ - '0'); if (*cp++ != ' ') break; if (strchr(cp, '/')) frecverr("readjob: %s: illegal path name", cp); if (!chksize(size)) { (void)write(STDOUT_FILENO, "\2", 1); continue; } (void)strlcpy(dfname, cp, sizeof(dfname)); (void)readfile(dfname, size); continue; } frecverr("protocol screwup: %s", line); } }
int main(int argc, char** argv) { char* bucket; int bucket_read = 0; int bucket_size = 256; int arg_c = 0; int args_size = 256; node *head = NULL; node *cur = NULL; //initialize with prompt char *prompt; if(argc >= 2) prompt = argv[1]; else prompt = "myshell:"; //parsing section bucket = (char *) safe_malloc(bucket_size*sizeof(char), "fatal error in main: bucket could not be malloced"); while(1) { printf("\n%s", prompt); char c; cur = create_node(); while((c = getchar())) { if(c == EOF) { cleanup_nodes(head); free(cur); free(bucket); exit(0); } if(isalnum(c) || c >= 33 && c <=37 || c >=39 && c <= 47 || c >= 91 && c <= 96 || c == 123 || c == 125 || c == 126) { bucket = (char *) chksize(bucket, bucket_read, &bucket_size, bucket_size*2+1); bucket[bucket_read] = c; bucket_read += 1; } else if (c == SPACE || c == '\n'){ if(bucket_read >= 1) { if(cur->args == NULL) cur->args = safe_malloc(args_size*sizeof(char *), "fatal error: could not malloc args array"); cur->args[arg_c] = (char *) safe_malloc(bucket_read*sizeof(char)+2, "could not malloc datum in node"); strncpy(cur->args[arg_c], bucket, bucket_read); cur->args[arg_c+1] = '\0'; cur->args[arg_c][bucket_read] = '\0'; bucket_read = 0; arg_c += 1; } if(c == '\n') { arg_c = 0; if(head == NULL) head = cur; break; } } else if(memchr(cmds, c, 5)) { if(bucket_read >= 1) { if(cur->args == NULL) cur->args = safe_malloc(args_size*sizeof(char *), "fatal error: could not malloc args array"); cur->args[arg_c] = (char *) safe_malloc(bucket_read*sizeof(char)+1, "could not malloc datum in node"); strncpy(cur->args[arg_c], bucket, bucket_read); cur->args[arg_c+1] = '\0'; cur->args[arg_c][bucket_read] = '\0'; bucket_read = 0; arg_c += 1; } node *next = create_node(); cur->next = next; next->prev = cur; next->datum = (char *) safe_malloc(2*sizeof(char), "could not malloc datum in node"); next->datum[0] = c; next->datum[1] = '\0'; if(head == NULL) head = cur; cur = cur->next; node *tmp = create_node(); cur->next = tmp; tmp->prev = cur; cur = tmp; arg_c = 0; } } cur=head; if(head != NULL && head->args != NULL && strstr(head->args[0], "exit")) { cleanup_nodes(head); free(cur); free(bucket); exit(0); } cur = head; //arguments section int pid, status; while(cur != NULL) { int AMPERSAND = 0; //start command states: if(cur->datum != NULL && cur->datum[0] == '&'){ AMPERSAND = WNOHANG; node *tmp = cur->prev; if(cur->next != NULL && cur->next->datum != NULL || cur->next->args != NULL){ tmp->next = cur->next; cur->next->prev = tmp; } else { tmp->next = NULL; free(cur->next); } free(cur->datum); free(cur->args); free(cur); cur = tmp; } if(cur->args != NULL && cur->args[0] != NULL && strstr(cur->args[0], "cd")) { //cd as a builtin command if(chdir(cur->args[1]) != 0) { perror("changing directory failed: invalid path"); } } else if(cur != NULL && cur->datum != NULL && cur->datum[0] == '|') { //pipe cur = pipline(cur->prev); } else if (cur != NULL && cur->datum != NULL && cur->datum[0] == '>') { //redirect output if((pid = fork()) == -1) perror("could not fork in output redirecton"); if(pid == 0) { //child char **args = cur->prev->args; if(cur->next->datum == NULL && cur->next->args == NULL) { //handle >> command cur = cur->next->next->next; //advance the args list past the second > cur->fd[1] = -1; cur->fd[0] = -1; if((cur->fd[1] = open(cur->args[0], O_RDWR | O_CREAT | O_APPEND, 0666)) < 0) perror("could not open fd in input redirection"); } else { cur = cur->next; cur->fd[1] = -1; cur->fd[0] = -1; if((cur->fd[1] = open(cur->args[0], O_RDWR | O_CREAT, 0666)) < 0) perror("could not open fd in input redirection"); } if(dup2(cur->fd[1], STDOUT_FILENO) < 0) { perror("fatal error: dup2 failed in file redirection"); } if(close(cur->fd[1]) < 0) { perror("close operation in redirection failed"); } execvp(args[0], args); perror(""); } else { if(cur != NULL && cur->next->datum != NULL && cur->next->datum[0] == '>') cur = cur->next; //advance the args list past the second > cur = cur->next; waitpid(-1, &status, AMPERSAND); } //redirect file } else if (cur != NULL && cur->datum != NULL && cur->datum[0] == '<') { if((pid = fork()) == -1) perror("could not fork in file redirecton"); if(pid == 0) { //child cur->next->fd[1] = -1; cur->next->fd[0] = -1; char* arg = cur->prev->datum; if((cur->next->fd[0] = open(cur->next->args[0], O_RDONLY)) < 0){ perror("could not open fd in input redirection"); } else { if(dup2(cur->next->fd[0], STDIN_FILENO) == -1) { perror("fatal error: dup2 failed in file redirection"); } if(close(cur->next->fd[0]) < 0) { perror("close operation in redirection failed"); } execvp(cur->prev->args[0], cur->prev->args); perror(""); } } else { //parent cur = cur->next; waitpid(-1, &status, AMPERSAND); } } else if (AMPERSAND || cur->next == NULL || cur->datum != NULL && cur->datum[0] ==';') { if((pid = fork()) == -1) perror("could not fork in run command"); if(pid == 0) { //child if(cur->datum != NULL && cur->datum[0] == ';') cur = cur->prev; execvp(cur->args[0], cur->args); perror(""); } else { if(AMPERSAND) { if(cur->next != NULL && cur->next->datum != NULL && cur->next->datum[0] == ';') cur = cur->next; } waitpid(-1, &status, AMPERSAND); } } if(cur != NULL) cur = cur->next; } //while cur !NULL cleanup_nodes(head); head = NULL; cur = NULL; for(int i = 0; i < bucket_size; i++) { bucket[i] = '\0';} arg_c = 0; } //while 1 free(bucket); return 0; }