Пример #1
0
/*
 * The execNode() function takes in a pointer to the node we are trying to execute. First we redirect the input and output files as given to us in the assignment. Then we use the makeargv() function to separate the command line arguments into tokens, and call execvp() to execute the arguments. Lastly, freemakeargv is called to free the allocated memory.
 */
int execNode(node_t *node) {
  char **myArgv;
  char *delim = " ";
  int numTokens;
  int i;
  // code from line 75-93 comes from redirect.c which was given with the assignment
    // Redirects the input file
    printf("Executing Node: %d\n", node -> id);
    int input_file = open(node -> input, O_RDONLY, 0666);
    if (input_file < 0){
      perror("Error opening input file in child after fork! Exiting.");
      exit(0);
    } else {
      dup2(input_file, STDIN_FILENO);
      close(input_file);
    }

    // Redirects the output file
    int output_file = open(node -> output, O_WRONLY|O_CREAT|O_TRUNC, 0644);
    if (output_file < 0) {
      perror("Error opening output file in child after fork! Exiting.");
      exit(0);
    } else {
      dup2(output_file, STDOUT_FILENO);
      close(output_file);
    }
  numTokens = makeargv(node -> prog, delim, &myArgv); // Let's create a makeargv with the program name
  execvp(myArgv[0], myArgv); //Now, execute it.
  freemakeargv(myArgv); // Prevent a memory leak.
  return 1;
}
Пример #2
0
// == Construct Node ==
// This function takes a colen-delimited line from the input file and, if valid
// data, allocates space for a node struct, popluates it with the data from the line,
// and returns a pointer to the new node. The line number is also used to fill
// the id parameter.
node_t * construct_node(const char * line, int line_number) {	
	node_t * result = NULL;
	int substring_count = 0;
	char ** temp_parameter_strings;
	int i;
	char* new_line_location;
	
	substring_count = makeargv(line, ":", &temp_parameter_strings);
	
	for (i = 0; i < substring_count; i++) {
		if((new_line_location = strpbrk(temp_parameter_strings[i], "\n\r"))) // If the line ends in newline,
			*(new_line_location) = '\0'; // Cut it off!
	}
	
	if (substring_count == 4) { // The appropriate number of parameters were read
		result = (node_t*)malloc(sizeof(node_t));
		if (result) { // Verify that space was successfully allocated
			result->id = line_number;
			strcpy(result->prog, temp_parameter_strings[0]);
			strcpy(result->input, temp_parameter_strings[2]);
			strcpy(result->output, temp_parameter_strings[3]);
			result->num_children = extract_children(temp_parameter_strings[1], result->children, MAX_CHILDREN_COUNT);
			result->status = INELIGIBLE; // Assume ineligibility until verified
		}
	}
	
	freemakeargv(temp_parameter_strings);
	return result;

		
}
Пример #3
0
int APIENTRY WinMain (HINSTANCE hInst, HINSTANCE hPrev, LPSTR lpCmd, int nShow)
{
	char **argv= NULL;
	int argc;

	win_command_line = GetCommandLine();
	argc = makeargv(win_command_line, " \t\n", &argv);

	Main(argc, (char **) argv);
	freemakeargv(argv);

	// attempt to restart if requested
	if(restart_required > 0){
		STARTUPINFO si;
		PROCESS_INFORMATION pi;

		LOG_INFO("Restarting %s", win_command_line);
		ZeroMemory( &si, sizeof(si) );
		si.cb = sizeof(si);
		ZeroMemory( &pi, sizeof(pi) );

		CreateProcess(NULL, win_command_line,
			NULL,			// Process handle not inheritable.
			NULL,			// Thread handle not inheritable.
			FALSE,			// Set handle inheritance to FALSE.
			DETACHED_PROCESS,	// Keep this separate
			NULL,			// Use parent's environment block.
			NULL,			// Use parent's starting directory.
			&si,			// Pointer to STARTUPINFO structure.
			&pi);          // Pointer to PROCESS_INFORMATION structure
	}

	return 0;
}
Пример #4
0
int main(int argc, char **argv) {

	char input[MAX_INPUT];
	int numtokens;
	char **tokens;

	prompt[0] = '>';
	prompt[1] = '>';
	prompt[2] = ' ';
	prompt[3] = '\0';

	// Init the flags
	zombie = -1;
	bg = 0;

	// Print opening text
	printf("Welcome to the G(raham) Shell!\n");
	printf("To exit, type exit\n");

	// Loop indefinitely.
	while (1) {
		// Print the prompt!
		printf("%s", prompt);
		
		// Get the input line!
		// Move on if input is null or empty newline
		if (fgets(input, MAX_INPUT, stdin) == NULL) {
			// Fixes a bug where the signal handler interrupts the read system
			// call and forces an infinite prompt loop.
			// Thanks to Daniel Bittman and Justin Lardinois on Piazza :)
			clearerr(stdin);
			continue;
		}
		if (input[0] == '\n') continue;
		
		// Cut trailing newline
		int inputlen = strlen(input);
		if (input[inputlen - 1] == '\n') input[inputlen - 1] = 0;
		
		// Get the tokens
		numtokens = makeargv(input, DELIMITERS, &tokens);
		// Parse the command line!
		parseargv(numtokens, tokens);
		
		// Clean up
		freemakeargv(tokens);
	}
}
Пример #5
0
/**********************************************
 * get_request
   - parameters:
      - fd is the file descriptor obtained by accept_connection()
        from where you wish to get a request
      - filename is the location of a character buf in which
        this function should store the requested filename. (buf
        should be of size 1024 bytes.)
   - returns 0 on success, nonzero on failure. You must account
     for failures because some connections might send faulty
     requests. This is a recoverable error - you must not exit
     inside the thread that called get_request. After an error, you
     must NOT use a return_request or return_error function for that
     specific 'connection'.
************************************************/
int get_request(int fd, char *filename) 
{
        char buf[1024];
        char ** request; 
         
        if (read(fd, buf, 1024) < 0) {
               
                return -1;
        }
       
        int num_of_lines = 0;
        if ((num_of_lines = makeargv(buf, "\n", &request)) < 0) {
                
                return -1;
        }
       
        int i;
	      keep_alive_flag=0;
        for (i = 0; i < num_of_lines; i++) {
               
                char ** row;
             
                if (makeargv(request[i], " ", &row) < 0) {
                       
                        return -1;
                }
              
                if (strcmp(row[0], "GET") == 0) {
                        strncpy(filename, row[1], 1023);
                }
  
                if (strcmp(row[0], "Connection:") == 0) {
                       if (strcmp(row[1], "Keep-Alive") == 0) { 
			  pthread_mutex_lock(&accept_con_mutex);
			  keep_alive_flag = 1; 
			  
			  pthread_mutex_unlock(&accept_con_mutex);}
                      
                }
             
        }
        freemakeargv(request);
        return 0;

}
Пример #6
0
/**
 * Parse the input line at s, and populate the node at n, which will
 * have id set to id.
 * Return 0 on success or -1 and set errno on failure.
 */
static int parse_input_line(char *s, int id, node_t *n) {

  char **strings;
  char **child_list;
  int c = 0;

  /* Split the line on ":" delimiters */
  if (makeargv(s, ":", &strings) == -1) {
    return -1;
  }

  /* Parse the space-delimited child list */
  if (makeargv(strings[1], " ", &child_list) == -1) {
    freemakeargv(strings);
    return -1;
  }

  strcpy(n->prog, strings[0]);
	// fprintf(stderr,"n=%d n->prog=%s\n",id,n->prog);
  strcpy(n->input, strings[2]);
	// fprintf(stderr,"n=%d n->input=%s\n",id,n->input);
  strcpy(n->output, strings[3]);
	// fprintf(stderr,"n=%d n->output=%s\n",id,n->output);
  n->id = id;
	// fprintf(stderr,"n=%d n->id=%d\n",id,id);
  n->num_children = 0;

  //if strcmp is not equal none
  if (strcmp(child_list[c], "none") != 0) {
    for (c = 0; child_list[c] != NULL; c++) {
      n->children[c] = atoi(child_list[c]);
      // fprintf(stderr,"n=%d n->child[%d]=%d\n",id,c,n->children[c]);
      n->num_children++;
    }
  } 
	// fprintf(stderr,"n=%d n->numchildren=%d\n",id,n->num_children);

  //start all nodes as ineligible
  n->status = INELIGIBLE;
  // fprintf(stderr,"n=%d n->status=%d\n",id,n->status);

  return 0;
}
Пример #7
0
// == Extract Children ==
// This function takes a string that contains space-delimited child-id's and fills
// an allocated array of children up to a max number.
int extract_children(const char * child_string, int * children, int max_children_count) {
	int child_index = 0;
	char** temp_child_strings;
	int child_count;
	int child;
	int i;

	if (strcmp(child_string, "none") != 0) {
		child_count = makeargv(child_string, " ", &temp_child_strings);
		for (i = 0; i < child_count; i++) {
			// If substring_start contains non-numeric garbage, atoi will return 0 (false).
			// But if substring_start actually contains the value 0, we want to use the value 0.
			if((child = atoi(temp_child_strings[i])) || (temp_child_strings[i][0] == '0')) 				
				children[child_index++] = child;
		}
		freemakeargv(temp_child_strings);

	}
	return child_index;
}
Пример #8
0
Файл: main.c Проект: DarylX/4061
int parse_input_line(char *s, int id, node_t *node) {
    
	char **strings;
	char **child_list;
    char* line_location;
	int count = 0;
    int i;
    
    //parse lines at every : and check errors
    int tok_count = makeargv(s, ":", &strings);
	if (tok_count == -1) return 0;
    
	//parse child list (strings[1]) at every space for processes, check errors
	if(makeargv(strings[1], " ", &child_list) == -1) return 0;
    
    //read text line into line_location
    for (i = 0; i < tok_count; i++) {
		if((line_location = strpbrk(strings[i], "\n\r"))){
			*line_location = '\0';
        }
	}
    
	//set prog, input, output and id fields
	strcpy(node->prog,strings[0]);
	strcpy(node->input,strings[2]);
	strcpy(node->output,strings[3]);
	node->id = id;
    
	node->num_children = 0;
    
	//create child list and set number of children
	while (child_list[count] != NULL && strcmp(child_list[count],"none")!=0) {
		node->children[count] = atoi(child_list[count]);
		node->num_children++;
		count++;
	}
    
    freemakeargv(strings);
	return 1;
}
Пример #9
0
// == Run Node ==
// This function takes a node, assuming it is eligible to run, and opens the
// necessary files and makes the apppropriate dup/dup2 calls to direct input,
// forks and execs the node process. Returns 
int run_node(node_t * node) {
	char ** child_argv;
	int child_argc;
	int oldstdin, oldstdout;
	int input_fd, output_fd;
	
	int status;
	pid_t child_pid;

	// ----- Store old input and output FD's -----
	fflush(stdout);
	if ((oldstdin = dup(0)) == -1) { // Save current stdin
		perror("Failed to back-up stdin:\n");
		exit(EXIT_STATUS_COULD_NOT_REDIRECT_FILES);
	}
	if ((oldstdout = dup(1)) == -1) { // Save current stdout
		perror("Failed to back-up stdout:\n");
		exit(EXIT_STATUS_COULD_NOT_REDIRECT_FILES);
	}
	// -------------------------------------------
	
	
	// ----- Open input and output FD's ----------
	if ((input_fd  = open(node->input, O_RDONLY | O_CREAT, 0644)) == -1) {
		fprintf(stderr, "Failed to open node %d's input file %s:\n",
				node->id, node->input);
		perror(NULL);
		exit(EXIT_STATUS_COULD_NOT_OPEN_FILES);
	}
	if ((output_fd = open(node->output, O_WRONLY | O_CREAT, 0644)) == -1) {
		fprintf(stderr, "Failed to open node %d's output file %s:\n",
				node->id, node->output);
		perror(NULL);
		exit(EXIT_STATUS_COULD_NOT_OPEN_FILES);
	}
	// --------------------------------------------

	// ----- Redirect input and output FD's -------
	fflush(stdout);
	if (dup2(input_fd, STDIN_FILENO) == -1) {
		perror("Failed to redirect stdin.\n");
		exit(EXIT_STATUS_COULD_NOT_REDIRECT_FILES);
	}
	if (dup2(output_fd, STDOUT_FILENO) == -1) {
		perror("Failed to redirect stdout.\n");
		exit(EXIT_STATUS_COULD_NOT_REDIRECT_FILES);
	}
	// --------------------------------------------

	
	child_argc = makeargv(node->prog, " ", &child_argv);

	node->status = RUNNING;
	
	//----- Fork, exec, and wait ------------------
	node->pid = child_pid = fork();
	if (child_pid) {
		wait(&status);
	} else {
		execvp(child_argv[0], &child_argv[0]);
	}
	// --------------------------------------------

	freemakeargv(child_argv);
	
	node->return_value = status;
	node->status = FINISHED;

	
	// ----- Replace old input and output FD's ----
	fflush(stdout);
	if (dup2(oldstdout, STDOUT_FILENO) == -1) {
		perror("Failed to redirect stdout to original stdout.\n");
		exit(EXIT_STATUS_COULD_NOT_REDIRECT_FILES);
	}
	if (dup2(oldstdin, STDIN_FILENO) == -1) {
		perror("Failed to redirect stdin to original stdin.\n");
		exit(EXIT_STATUS_COULD_NOT_REDIRECT_FILES);
	}
	// --------------------------------------------
	
	if (close(input_fd))
		perror("input_fd failed to close:");	
	if (close(output_fd))
		perror("output_fd failed to close:");
	if (close(oldstdin))
		perror("oldstdin failed to close:");
	if (close(oldstdout))
		perror("oldstdin failed to close:");
	
	return node->return_value;
}
Пример #10
0
Файл: main.c Проект: DarylX/4061
int run_node(node_t * node) {
	char ** child_argv;
	int child_argc;
	int oldstdin, oldstdout;
	int input_fd, output_fd;
    
	int status;
	pid_t child_pid;
    
	//store old input and output file descriptors
	fflush(stdout);
	if ((oldstdin = dup(0)) == -1) {
		perror("Failed to back-up stdin");
        return -1;
    }
	if ((oldstdout = dup(1)) == -1) {
		perror("Failed to back-up stdout");
		return -1;
	}
    
	//open input and output file descriptors
	if ((input_fd = open(node->input, O_RDONLY | O_CREAT, 0644)) == -1) {
		perror("Failed to open input file");
        return -1;
    }
	if ((output_fd = open(node->output, O_WRONLY | O_CREAT, 0644)) == -1) {
		perror("Failed to open output file");
        return -1;
    }
    
	//redirect input and output file descriptors
	fflush(stdout);
	if (dup2(input_fd, STDIN_FILENO) == -1) {
		perror("Failed to redirect stdin");
        return -1;
    }
	if (dup2(output_fd, STDOUT_FILENO) == -1) {
		perror("Failed to redirect stdout");
        return -1;
    }
    
    //parse arg at every space
	child_argc = makeargv(node->prog, " ", &child_argv);
    
    node->status = RUNNING;
    
	//fork, exec, and wait
	node->pid = child_pid = fork();
	if (child_pid) wait(&status);
	else execvp(child_argv[0], &child_argv[0]);

	freemakeargv(child_argv);
    
	//node->return_value = status;
	node->status = FINISHED;
    
    
	//replace old input and output file descriptors
	fflush(stdout);
	if (dup2(oldstdout, STDOUT_FILENO) == -1) {
		perror("Failed to redirect stdout to original stdout");
        return -1;
    }
	if (dup2(oldstdin, STDIN_FILENO) == -1) {
		perror("Failed to redirect stdin to original stdin");
        return -1;
    }
    
	if (close(input_fd)) perror("Failed to close input_fd");
	if (close(output_fd)) perror("Failed to close output_fd");
	if (close(oldstdin)) perror("Failed to close oldstdin");
	if (close(oldstdout)) perror("Failed to close oldstdout");
    
	return node->status;
}
Пример #11
0
//Handles all forking and exec'ing of commands. Execs the commands (if there are
//any) for the processes with zero dependencies that have not been built.
//Decriments the number of dependencies for parents.  Also handles timestamps.  
int forkExec(Node **toBeExeced, int numElements){
	int i;
	int k = 0;
	int comp;
	
	if(strcmp(targ, "clean")==0)
		commands[1] = 1;
	
	for(i=0;i<numElements;i++){
		char **execargv;
		pid_t childpid;
		int execargc;
		int status;
		int recompile = 1;
		//if recompile is 1, then build
		
		//-n flag set
		if(commands[1] == 0){

			recompile = 1;
			for(k = 0;k<toBeExeced[i]->sizeDepends;k++){
				comp = compare_modification_time(toBeExeced[i]->dependencies[k],toBeExeced[i]->target);
				int child_timestamp = get_file_modification_time(toBeExeced[i]->dependencies[k]);
				int parent_timestamp = get_file_modification_time(toBeExeced[i]->target);

				//if the timestamp for one doesn't exist, or the timestamp of the child is greater (newer) than the parent
				if(comp < 2 || (parent_timestamp == -1)){
					recompile = 1;
				}
			}
		}
		//if child is older than the parent, don't rebuild
		if(recompile == 0 && commands[0] != 1){
			continue;
		}
		
		if (strcmp (toBeExeced[i]->command, " ") != 0){	
			if(commands[0] == 1){
				printf("%s\n", toBeExeced[i]->command);
				if (toBeExeced[i]->toParent != NULL){
					toBeExeced[i]->toParent->numTargetDep--;
				}
				continue;
			}
			execargc = makeargv (toBeExeced[i]->command," ",&execargv);
			toBeExeced[i]->pid = childpid = fork();
		}else
		{
			continue;
		}
		if (childpid == -1){
			perror("Failed to Fork\n");
			return -1;
		}
		if(childpid ==0){
			execvp(execargv[0],&execargv[0]);
			perror("Child failed to Exec \n");
			return -1;
		}
		if(childpid > 0){
			wait(&status);
			if(toBeExeced[i]->toParent != NULL){
				toBeExeced[i]->toParent->numTargetDep--;
			}
		}
		freemakeargv(execargv);
	}
	return 1;
}