Example #1
0
void sim_init()
{
    /* Create memory and register files */
    initialized = 1;
    mem = init_mem(MEM_SIZE);
    reg = init_reg();
    
    /* create 5 pipe registers */
    pc_state     = new_pipe(sizeof(pc_ele), (void *) &bubble_pc);
    if_id_state  = new_pipe(sizeof(if_id_ele), (void *) &bubble_if_id);
    id_ex_state  = new_pipe(sizeof(id_ex_ele), (void *) &bubble_id_ex);
    ex_mem_state = new_pipe(sizeof(ex_mem_ele), (void *) &bubble_ex_mem);
    mem_wb_state = new_pipe(sizeof(mem_wb_ele), (void *) &bubble_mem_wb);
  
    /* connect them to the pipeline stages */
    pc_next   = pc_state->next;
    pc_curr   = pc_state->current;
  
    if_id_next = if_id_state->next;
    if_id_curr = if_id_state->current;

    id_ex_next = id_ex_state->next;
    id_ex_curr = id_ex_state->current;

    ex_mem_next = ex_mem_state->next;
    ex_mem_curr = ex_mem_state->current;

    mem_wb_next = mem_wb_state->next;
    mem_wb_curr = mem_wb_state->current;

    sim_reset();
    clear_mem(mem);
}
Example #2
0
void creat_pipe(QSP_ARG_DECL  const char *name, const char* command, const char* rw)
{
	Pipe *pp;
	int flg;

	if( *rw == 'r' ) flg=READ_PIPE;
	else if( *rw == 'w' ) flg=WRITE_PIPE;
	else {
		sprintf(ERROR_STRING,"create_pipe:  bad r/w string \"%s\"",rw);
		WARN(ERROR_STRING);
		return;
	}

	pp = new_pipe(QSP_ARG  name);
	if( pp == NO_PIPE ) return;

	pp->p_cmd = savestr(command);
	pp->p_flgs = flg;
	pp->p_fp = popen(command,rw);

	if( pp->p_fp == NULL ){
		sprintf(ERROR_STRING,
			"unable to execute command \"%s\"",command);
		WARN(ERROR_STRING);
		close_pipe(QSP_ARG  pp);
	}
}
Example #3
0
static void initialize_context(struct p_context *ctx) {
	ctx->pipe = NULL;
	ctx->child = NULL;
	ctx->list_head = new_pipe();
	ctx->pipe = ctx->list_head;
	ctx->w = RES_NONE;
	ctx->stack = NULL;
	ctx->old_flag = 0;
	done_command(ctx); /* creates the memory for working child */
}
Example #4
0
/*
 * syscall_pipe
 * 
 * Implements the pipe system call. This creates a pipe, as well as two file
 * handles. The first file handle can be used for reading from the pipe, and the
 * second for writing to it. Both handles are then associated with file descriptors
 * in the current process's file descriptor table.
 * 
 * The most common use of this function is when a process is about to fork. A pipe
 * is created to allow the parent and child process to communicate. When the fork
 * occurs, the child inherits references to the pipe, and both sides release either
 * the reading or writing file descriptor, depending on the direction in which the
 * data is to flow. The pipe can then be used to transfer data from the parent to
 * the child, or vice-versa.
 */
int syscall_pipe(int filedes[2])
{
	/*
	 * Ensure the supplied array is within the process's address space 
	 */
	if (!valid_pointer(filedes, 2 * sizeof(int)))
		return -EFAULT;

	/*
	 * Find two unused file descriptors 
	 */
	int readfd = -1;
	int writefd = -1;
	int i;
	for (i = 0; (i < MAX_FDS) && (-1 == writefd); i++) {
		if (NULL == current_process->filedesc[i]) {
			if (-1 == readfd)
				readfd = i;
			else if (-1 == writefd)
				writefd = i;
		}
	}

	/*
	 * If we were unable to allocate the file descriptors, the call cannot
	 * complete successfully. Return an error to the process indicating that there
	 * aren't enough file descriptors available. 
	 */
	if ((-1 == readfd) || (-1 == writefd))
		return -EMFILE;

	/*
	 * Create a new pipe 
	 */
	pipe_buffer *b = new_pipe();

	/*
	 * Create the file handles and place references to them in the process's
	 * file descriptor table 
	 */
	current_process->filedesc[readfd] = new_pipe_reader(b);
	current_process->filedesc[writefd] = new_pipe_writer(b);

	/*
	 * Store the file descriptors in the output array, so the process knows which
	 * ones to use for reading and writing to the pipe 
	 */
	filedes[0] = readfd;
	filedes[1] = writefd;

	return 0;
}
Example #5
0
void keyboard_init()
{
  INODE tmp[2];
  new_pipe(1024, tmp);
  keyboard_pipe = tmp[1];
  /* vfs_mount("/dev/kbd", tmp[0]); */
  vfs_open(keyboard_pipe, O_WRONLY);

  // Make keyboard stdin (first entry in file descriptor table)
  process_t *p = current->proc;
  p->fd[0] = calloc(1, sizeof(file_desc_t));
  fd_get(p->fd[0]);
  p->fd[0]->ino = tmp[0];
  p->fd[0]->flags = O_RDONLY;
  vfs_open(tmp[0], O_RDONLY);

  new_pipe(1024, tmp);
  keyboard_raw = tmp[1];
  vfs_mount("/dev/kbdraw", tmp[0]);
  vfs_open(keyboard_raw, O_WRONLY);

  register_int_handler(IRQ2INT(IRQ_KBD), keyboard_handler);
}
Example #6
0
	 || ctx->ctx_res_w == RES_FI
#endif
#if ENABLE_HUSH_LOOPS
	 || ctx->ctx_res_w == RES_DONE
	 || ctx->ctx_res_w == RES_FOR
	 || ctx->ctx_res_w == RES_IN
#endif
#if ENABLE_HUSH_CASE
	 || ctx->ctx_res_w == RES_ESAC
#endif
	) {
		struct pipe *new_p;
		debug_printf_parse("done_pipe: adding new pipe: "
				"not_null:%d ctx->ctx_res_w:%d\n",
				not_null, ctx->ctx_res_w);
		new_p = new_pipe();
		ctx->pipe->next = new_p;
		ctx->pipe = new_p;
		/* RES_THEN, RES_DO etc are "sticky" -
		 * they remain set for pipes inside if/while.
		 * This is used to control execution.
		 * RES_FOR and RES_IN are NOT sticky (needed to support
		 * cases where variable or value happens to match a keyword):
		 */
#if ENABLE_HUSH_LOOPS
		if (ctx->ctx_res_w == RES_FOR
		 || ctx->ctx_res_w == RES_IN)
			ctx->ctx_res_w = RES_NONE;
#endif
#if ENABLE_HUSH_CASE
		if (ctx->ctx_res_w == RES_MATCH)
void start_logger(const char *log_file, const char *original_command, uid_t uid) {

    struct fd_pair input;
    struct fd_pair output[2];
    int output_count;
    int i;
    int has_tty = isatty(STDIN_FILENO);

    if (has_tty) {
        /* use psedo terminal for communication */
        input = clone_pseudo_terminal(STDIN_FILENO);
        if (uid && fchown(input.read_side, uid, -1) < 0) perror("change owner of tty to user");
        output[0].write_side = dup(input.read_side);
        output[0].read_side =  dup(input.write_side);
        output_count = 1;
    }
    else {
        /* use pipes for communication */
        input = new_pipe();
        output[0] = new_pipe();
        output[1] = new_pipe();
        output_count = 2;
    }

    /* child will return and execute the command */
    pid_t child_pid = fork();
    if (child_pid == 0) {
        if (has_tty) {
            /* need to be session leader to be able to set the controlling terminal later on */
            if (setsid() < 0) perror("create new session");

            /* the controlling terminal is required by the shell for job control */
            if (ioctl(input.read_side, TIOCSCTTY, NULL) != 0) perror("set controlling terminal");
        }
        /* parent process runs session and redirects I/O to the pipes or pseudterminal */
        dup2(input.read_side, STDIN_FILENO);
        dup2(output[0].write_side, STDOUT_FILENO);
        dup2(output[output_count-1].write_side, STDERR_FILENO);

        close(input.read_side);
        close(input.write_side);
        for (i = 0; i < output_count; i++) {
            close(output[i].write_side);
            close(output[i].read_side);
        }

        return;
    }
    /* parent will collect and forward the session content */

    close(input.read_side);
    for (i = 0; i < output_count; i++) {
        close(output[i].write_side);
    }

    /* signal handling */
    signal(SIGINT, SIG_IGN);
    signal(SIGHUP, SIG_IGN);
    signal(SIGPIPE, SIG_IGN);

    /* child will do blocking writes on file */
    struct fd_pair internal = new_pipe();
    if (fork() == 0) {

        close(input.write_side);
        for (i = 0; i < output_count; i++) {
            close(output[i].read_side);
        }
        close(internal.write_side);

        char* dir = dirname(strdup(log_file));
        prepare_dir(dir);
        free(dir);

        int fd_log = open(log_file, O_WRONLY|O_APPEND|O_CREAT, S_IRUSR);
        if (fd_log < 0) {
            perror(log_file);
            free_options();
            exit(1);
        }
        free_options();

        close(STDIN_FILENO);
        close(STDOUT_FILENO);
        close(STDERR_FILENO);

        run_log_writer(internal.read_side, fd_log, original_command);

        exit(0);
    }
    free_options();
    close(internal.read_side);

    struct termios original_term;

    if (has_tty) {
        original_tty = dup(STDIN_FILENO); /* trick from bash */
        set_raw_input(original_tty, &original_term);
        child_tty = input.write_side;
        signal(SIGWINCH, resize_handler);
    }

    /* do the logging */
    run_log_forwarder(&internal, &input, output,
                      2 == output_count ? output + 1 : NULL,
                      original_command ? 0 : 1
                     );

    /* reset terminal */
    if (has_tty) {
        if (tcsetattr(original_tty, TCSAFLUSH, &original_term) != 0) {
            perror("reseting terminal");
        }
    }

    /* forward exit value of child */
    int status;
    waitpid(child_pid, &status, 0);
    exit(WEXITSTATUS(status));
}
Example #8
0
static int
add_stream(stream_player_t *sp, int s)
{
    tcvp_player_t *sh = sp->shared;
    tcvp_pipe_t *tp;
    int sid;
    int r = -1;

    pthread_mutex_lock(&sh->lock);
    sid = sh->sid++;
    sp->ms->used_streams[s] = 0;

    tc2_print("STREAM", TC2_PRINT_DEBUG, "new stream #%i\n", sid);

    if(s >= sp->nstreams){
        sp->streams = realloc(sp->streams, (s + 1) * sizeof(*sp->streams));
        memset(sp->streams + s, 0, (s+1-sp->nstreams) * sizeof(*sp->streams));
        sp->smap = realloc(sp->smap, (s + 1) * sizeof(*sp->smap));
        memset(sp->smap + s, 0xff, (s + 1 - sp->nstreams) * sizeof(*sp->smap));
        sp->nstreams = s + 1;
    }

    sp->smap[s] = sid;

    if(!use_stream(sh, sid, sp->ms->streams + s))
        goto out;
    r = -2;

    if(sp->ms->streams[s].stream_type == STREAM_TYPE_VIDEO){
        sh->vs = sid;
    } else if(sp->ms->streams[s].stream_type == STREAM_TYPE_AUDIO){
        sh->as = sid;
    } else if(sp->ms->streams[s].stream_type == STREAM_TYPE_SUBTITLE){
        sh->ss = sid;
    }

    tc2_print("STREAM", TC2_PRINT_DEBUG,
              "creating pipeline for stream #%i\n", sid);
    if(!(tp = new_pipe(sh, sp->ms, sp->ms->streams + s)))
        goto out;

    pthread_mutex_lock(&sp->lock);
    sp->pstreams++;
    pthread_mutex_unlock(&sp->lock);

    sp->streams[s].pipe = tp;
    sp->streams[s].end = pipe_end(tp);
    sp->streams[s].packets = tclist_new(TC_LOCK_NONE);
    sp->streams[s].probe = PROBE_AGAIN;
    sp->streams[s].sp = sp;
    sp->streams[s].starttime = -1LL;

    sp->ms->used_streams[s] = 1;
    if(!(sp->ms->streams[s].common.flags & TCVP_STREAM_FLAG_NOBUFFER))
        sp->nbuf |= 1ULL << s;

    r = 0;

out:
    pthread_mutex_unlock(&sh->lock);
    if(r < 0)
        sp->fail++;
    if(r < -1)
        tc2_print("STREAM", TC2_PRINT_WARNING,
                  "error opening stream #%i\n", sid);
    return r;
}