Пример #1
0
void pic_remap(uint8_t irq0_offset, uint8_t irq8_offset)
{
	unsigned char mask1, mask2;

	mask1 = port_read_8(PIC_MASTER_DATA_PORT);
	mask2 = port_read_8(PIC_SLAVE_DATA_PORT);

	port_write_8(PIC_MASTER_COMMAND_PORT, 0x11);
	port_wait();
	port_write_8(PIC_SLAVE_COMMAND_PORT, 0x11);
	port_wait();
	port_write_8(PIC_MASTER_DATA_PORT, irq0_offset);
	port_wait();
	port_write_8(PIC_SLAVE_DATA_PORT, irq8_offset);
	port_wait();
	port_write_8(PIC_MASTER_DATA_PORT, 4);
	port_wait();
	port_write_8(PIC_SLAVE_DATA_PORT, 2);
	port_wait();
	port_write_8(PIC_MASTER_DATA_PORT, 1);
	port_wait();
	port_write_8(PIC_SLAVE_DATA_PORT, 1);
	port_wait();

	port_write_8(PIC_MASTER_DATA_PORT, mask1);
	port_write_8(PIC_SLAVE_DATA_PORT, mask2);
}
Пример #2
0
void set_log_listener_active(bool active) {
    if (active) {
        port_wait(&port, &log_ph);
    } else {
        port_cancel(&port, &log_ph);
    }
}
Пример #3
0
static void setup_dir_watcher(const char* dir,
                              zx_status_t (*cb)(port_handler_t*, zx_signals_t, uint32_t),
                              port_handler_t* ph,
                              int* fd_out) {
    *fd_out = -1;
    fbl::unique_fd fd(open(dir, O_DIRECTORY | O_RDONLY));
    if (!fd) {
        return;
    }
    zx::channel client, server;
    if (zx::channel::create(0, &client, &server) != ZX_OK) {
        return;
    }

    fzl::FdioCaller caller(std::move(fd));
    zx_status_t status;
    zx_status_t io_status = fuchsia_io_DirectoryWatch(caller.borrow_channel(),
                                                      fuchsia_io_WATCH_MASK_ALL, 0,
                                                      server.release(),
                                                      &status);
    if (io_status != ZX_OK || status != ZX_OK) {
        return;
    }

    *fd_out = caller.release().release();
    ph->handle = client.release();
    ph->waitfor = ZX_CHANNEL_READABLE | ZX_CHANNEL_PEER_CLOSED;
    ph->func = cb;
    port_wait(&port, ph);
}
Пример #4
0
static zx_status_t new_vc_cb(port_handler_t* ph, zx_signals_t signals, uint32_t evt) {
    zx_handle_t h;
    uint32_t dcount, hcount;
    if (zx_channel_read(ph->handle, 0, NULL, &h, 0, 1, &dcount, &hcount) < 0) {
        return ZX_OK;
    }
    if (hcount != 1) {
        return ZX_OK;
    }

    vc_t* vc;
    int fd;
    if (session_create(&vc, &fd, true, false) < 0) {
        zx_handle_close(h);
        return ZX_OK;
    }

    zx_handle_t handles[FDIO_MAX_HANDLES];
    uint32_t types[FDIO_MAX_HANDLES];
    zx_status_t r = fdio_transfer_fd(fd, FDIO_FLAG_USE_FOR_STDIO | 0, handles, types);
    if (zx_channel_write(h, 0, types,
                         static_cast<uint32_t>(r * sizeof(uint32_t)), handles, r) != ZX_OK) {
        session_destroy(vc);
    } else {
        port_wait(&port, &vc->fh.ph);
    }

    zx_handle_close(h);
    return ZX_OK;
}
Пример #5
0
int main(int argc, char** argv) {
    // NOTE: devmgr has getenv_bool. when more options are added, consider
    // sharing that.
    bool keep_log = false;
    const char* value = getenv("virtcon.keep-log-visible");
    if (value == NULL ||
        ((strcmp(value, "0") == 0) ||
         (strcmp(value, "false") == 0) ||
         (strcmp(value, "off") == 0))) {
        keep_log = false;
    } else {
        keep_log = true;
    }

    const char* cmd = NULL;
    int shells = 0;
    while (argc > 1) {
        if (!strcmp(argv[1], "--run")) {
            if (argc > 2) {
                argc--;
                argv++;
                cmd = argv[1];
                if (shells < 1)
                    shells = 1;
                printf("CMD: %s\n", cmd);
            }
        } else if (!strcmp(argv[1], "--shells")) {
            if (argc > 2) {
                argc--;
                argv++;
                shells = atoi(argv[1]);
            }
        }
        argc--;
        argv++;
    }

    if (port_init(&port) < 0) {
        return -1;
    }

    // create initial console for debug log
    if (vc_create(&log_vc, false) != ZX_OK) {
        return -1;
    }
    snprintf(log_vc->title, sizeof(log_vc->title), "debuglog");

    // Get our process koid so the log reader can
    // filter out our own debug messages from the log
    zx_info_handle_basic_t info;
    if (zx_object_get_info(zx_process_self(), ZX_INFO_HANDLE_BASIC, &info,
                           sizeof(info), NULL, NULL) == ZX_OK) {
        proc_koid = info.koid;
    }

    log_ph.handle = zx_take_startup_handle(PA_HND(PA_USER0, 1));
    if (log_ph.handle == ZX_HANDLE_INVALID) {
        printf("vc log listener: did not receive log startup handle\n");
        return -1;
    }

    log_ph.func = log_reader_cb;
    log_ph.waitfor = ZX_LOG_READABLE;

    if ((new_vc_ph.handle = zx_take_startup_handle(PA_HND(PA_USER0, 0))) != ZX_HANDLE_INVALID) {
        new_vc_ph.func = new_vc_cb;
        new_vc_ph.waitfor = ZX_CHANNEL_READABLE;
        port_wait(&port, &new_vc_ph);
    }

    setup_dir_watcher("/dev/class/input", input_cb, &input_ph, &input_dir_fd);

    if (!vc_display_init()) {
        return -1;
    }

    setenv("TERM", "xterm", 1);

    for (int i = 0; i < shells; ++i) {
        if (i == 0)
            start_shell(!keep_log, cmd);
        else
            start_shell(false, NULL);
    }

    zx_status_t r = port_dispatch(&port, ZX_TIME_INFINITE, false);
    printf("vc: port failure: %d\n", r);
    return -1;
}
Пример #6
0
static zx_status_t session_create(vc_t** out, int* out_fd, bool make_active, bool special) {
    int fd;

    // The ptmx device can start later than these threads
    int retry = 30;
    while ((fd = open("/dev/misc/ptmx", O_RDWR | O_NONBLOCK)) < 0) {
        if (--retry == 0) {
            return ZX_ERR_IO;
        }
        usleep(100000);
    }

    int client_fd = openat(fd, "0", O_RDWR);
    if (client_fd < 0) {
        close(fd);
        return ZX_ERR_IO;
    }

    vc_t* vc;
    if (vc_create(&vc, special)) {
        close(fd);
        close(client_fd);
        return ZX_ERR_INTERNAL;
    }
    zx_status_t r;
    if ((r = port_fd_handler_init(&vc->fh, fd, POLLIN | POLLRDHUP | POLLHUP)) < 0) {
        vc_destroy(vc);
        close(fd);
        close(client_fd);
        return r;
    }
    vc->fd = fd;

    if (make_active) {
        vc_set_active(-1, vc);
    }

    pty_window_size_t wsz = {
        .width = vc->columns,
        .height = vc->rows,
    };
    ioctl_pty_set_window_size(fd, &wsz);

    vc->fh.func = session_io_cb;

    *out = vc;
    *out_fd = client_fd;
    return ZX_OK;
}

static void start_shell(bool make_active, const char* cmd) {
    vc_t* vc;
    int fd;

    if (session_create(&vc, &fd, make_active, cmd != NULL) < 0) {
        return;
    }

    vc->is_shell = true;

    if (launch_shell(vc, fd, cmd) < 0) {
        session_destroy(vc);
    } else {
        port_wait(&port, &vc->fh.ph);
    }
}