Пример #1
0
Файл: shell.c Проект: kjk/qemacs
EditBuffer *new_shell_buffer(const char *name, const char *path,
                             const char **argv, int is_shell)
{
    ShellState *s;
    EditBuffer *b, *b_color;

    b = eb_new("", BF_SAVELOG);
    if (!b)
        return NULL;
    set_buffer_name(b, name); /* ensure that the name is unique */
    eb_set_charset(b, &charset_vt100);

    s = malloc(sizeof(ShellState));
    if (!s) {
        eb_free(b);
        return NULL;
    }
    memset(s, 0, sizeof(ShellState));
    b->priv_data = s;
    b->close = shell_close;
    eb_add_callback(b, eb_offset_callback, &s->cur_offset);
    s->b = b;
    s->pty_fd = -1;
    s->pid = -1;
    s->is_shell = is_shell;
    s->qe_state = &qe_state;
    tty_init(s);

    /* add color buffer */
    if (is_shell) {
        b_color = eb_new("*color*", BF_SYSTEM);
        if (!b_color) {
            eb_free(b);
            free(s);
            return NULL;
        }
        /* no undo info in this color buffer */
        b_color->save_log = 0;
        eb_add_callback(b, shell_color_callback, s);
        s->b_color = b_color;
    }

    /* launch shell */
    if (run_process(path, argv, &s->pty_fd, &s->pid) < 0) {
        eb_free(b);
        return NULL;
    }

    set_read_handler(s->pty_fd, shell_read_cb, s);
    set_pid_handler(s->pid, shell_pid_cb, s);
    return b;
}
Пример #2
0
Файл: shell.c Проект: kjk/qemacs
void shell_pid_cb(void *opaque, int status)
{
    ShellState *s = opaque;
    EditBuffer *b = s->b;
    QEmacsState *qs = s->qe_state;
    EditState *e;
    char buf[1024];

    if (s->is_shell) {
        snprintf(buf, sizeof(buf), "\nProcess shell finished\n");
    } else {
        time_t ti;
        char *time_str;
        
        ti = time(NULL);
        time_str = ctime(&ti);
        if (WIFEXITED(status))
            status = WEXITSTATUS(status);
        else
            status = -1;
        if (status == 0) {
            snprintf(buf, sizeof(buf), "\nCompilation finished at %s", 
                     time_str);
        } else {
            snprintf(buf, sizeof(buf), "\nCompilation exited abnormally with code %d at %s", 
                     status, time_str);
        }
    }
    eb_write(b, b->total_size, buf, strlen(buf));
    set_pid_handler(s->pid, NULL, NULL);
    s->pid = -1;
    /* no need to leave the pty opened */
    if (s->pty_fd >= 0) {
        set_read_handler(s->pty_fd, NULL, NULL);
        close(s->pty_fd);
        s->pty_fd = -1;
    }

    /* remove shell input mode */
    s->grab_keys = 0;
    qe_ungrab_keys();
    for (e = qs->first_window; e != NULL; e = e->next_window) {
        if (e->b == b)
            e->interactive = 0;
    }
    edit_display(qs);
    dpy_flush(qs->screen);
}
Пример #3
0
Файл: shell.c Проект: kjk/qemacs
static void shell_close(EditBuffer *b)
{
    ShellState *s = b->priv_data;
    int status;

    eb_free_callback(b, eb_offset_callback, &s->cur_offset);

    if (s->pid != -1) {
        kill(s->pid, SIGINT);
        /* wait first 100 ms */
        usleep(100 * 1000);
        if (waitpid(s->pid, &status, WNOHANG) != s->pid) {
            /* if still not killed, then try harder (useful for
               shells) */
            kill(s->pid, SIGKILL);
            while (waitpid(s->pid, &status, 0) != s->pid);
        }
        s->pid = -1;
    }
    if (s->pty_fd >= 0) {
        set_read_handler(s->pty_fd, NULL, NULL);
    }
    free(s);
}
Пример #4
0
static int qt_init(QEditScreen *s, int w, int h)
{
    QEStyleDef default_style;
    int xsize, ysize, font_ysize;

    QEQtContext *ctx;
    ctx = new QEQtContext();
    if (ctx == NULL) {
        return -1;
    }
    s->priv_data = ctx;

    s->media = CSS_MEDIA_SCREEN;
    s->bitmap_format = QEBITMAP_FORMAT_RGBA32;

    int event_pipe[2];
    if (pipe(event_pipe) < 0)
        return -1;

    fcntl(event_pipe[0], F_SETFD, FD_CLOEXEC);
    fcntl(event_pipe[1], F_SETFD, FD_CLOEXEC);

    ctx->events_rd = event_pipe[0];
    ctx->events_wr  = event_pipe[1];
    set_read_handler(event_pipe[0], qt_handle_event, s);

    /* At this point, we should be able to ask for metrics */
    if (font_ptsize)
        qe_styles[0].font_size = font_ptsize;
    get_style(NULL, &default_style, 0);

    QEFont *font = qt_open_font(s, default_style.font_style,
                                default_style.font_size);
    if (!font) {
        fprintf(stderr, "Could not open default font\n");
        exit(1);
    }
    QFont *qt_font = (QFont *)font->priv_data;
    QFontMetrics fm(*qt_font);
    font_xsize = fm.width("n");
    font_ysize = fm.height();
    qt_close_font(s, &font);

    if (w == 0)
        w = 80;
    if (h == 0)
        h = 25;
    xsize = w * font_xsize;
    ysize = h * font_ysize;

    s->width = xsize;
    s->height = ysize;
    s->charset = &charset_utf8;

    s->clip_x1 = 0;
    s->clip_y1 = 0;
    s->clip_x2 = s->width;
    s->clip_y2 = s->height;

    ctx->view->resize(xsize, ysize);

    return 2;
}