Пример #1
0
static VALUE
ttymode(VALUE io, VALUE (*func)(VALUE), void (*setter)(conmode *, void *), void *arg)
{
    rb_io_t *fptr;
    int status = -1;
    int error = 0;
    int fd[FD_PER_IO];
    conmode t[FD_PER_IO];
    VALUE result = Qnil;

    GetOpenFile(io, fptr);
    fd[0] = GetReadFD(fptr);
    if (fd[0] != -1) {
	if (set_ttymode(fd[0], t+0, setter, arg)) {
	    status = 0;
	}
	else {
	    error = errno;
	    fd[0] = -1;
	}
    }
    fd[1] = GetWriteFD(fptr);
    if (fd[1] != -1 && fd[1] != fd[0]) {
	if (set_ttymode(fd[1], t+1, setter, arg)) {
	    status = 0;
	}
	else {
	    error = errno;
	    fd[1] = -1;
	}
    }
    if (status == 0) {
	result = rb_protect(func, io, &status);
    }
    GetOpenFile(io, fptr);
    if (fd[0] != -1 && fd[0] == GetReadFD(fptr)) {
	if (!setattr(fd[0], t+0)) {
	    error = errno;
	    status = -1;
	}
    }
    if (fd[1] != -1 && fd[1] != fd[0] && fd[1] == GetWriteFD(fptr)) {
	if (!setattr(fd[1], t+1)) {
	    error = errno;
	    status = -1;
	}
    }
    if (status) {
	if (status == -1) {
	    errno = error;
	    rb_sys_fail(0);
	}
	rb_jump_tag(status);
    }
    return result;
}
Пример #2
0
/*
 * call-seq:
 *   io.winsize = [rows, columns]
 *
 * Tries to set console size.  The effect depends on the platform and
 * the running environment.
 *
 * You must require 'io/console' to use this method.
 */
static VALUE
console_set_winsize(VALUE io, VALUE size)
{
    rb_io_t *fptr;
    rb_console_size_t ws;
#if defined _WIN32
    HANDLE wh;
    int newrow, newcol;
#endif
    VALUE row, col, xpixel, ypixel;
    const VALUE *sz;
    int fd;

    GetOpenFile(io, fptr);
    size = rb_Array(size);
    rb_check_arity(RARRAY_LENINT(size), 2, 4);
    sz = RARRAY_CONST_PTR(size);
    row = sz[0], col = sz[1], xpixel = sz[2], ypixel = sz[3];
    fd = GetWriteFD(fptr);
#if defined TIOCSWINSZ
    ws.ws_row = ws.ws_col = ws.ws_xpixel = ws.ws_ypixel = 0;
#define SET(m) ws.ws_##m = NIL_P(m) ? 0 : (unsigned short)NUM2UINT(m)
    SET(row);
    SET(col);
    SET(xpixel);
    SET(ypixel);
#undef SET
    if (!setwinsize(fd, &ws)) rb_sys_fail(0);
#elif defined _WIN32
    wh = (HANDLE)rb_w32_get_osfhandle(fd);
#define SET(m) new##m = NIL_P(m) ? 0 : (unsigned short)NUM2UINT(m)
    SET(row);
    SET(col);
#undef SET
    if (!NIL_P(xpixel)) (void)NUM2UINT(xpixel);
    if (!NIL_P(ypixel)) (void)NUM2UINT(ypixel);
    if (!GetConsoleScreenBufferInfo(wh, &ws)) {
	rb_syserr_fail(LAST_ERROR, "GetConsoleScreenBufferInfo");
    }
    if ((ws.dwSize.X < newcol && (ws.dwSize.X = newcol, 1)) ||
	(ws.dwSize.Y < newrow && (ws.dwSize.Y = newrow, 1))) {
	if (!SetConsoleScreenBufferSize(wh, ws.dwSize)) {
	    rb_syserr_fail(LAST_ERROR, "SetConsoleScreenBufferInfo");
	}
    }
    ws.srWindow.Left = 0;
    ws.srWindow.Top = 0;
    ws.srWindow.Right = newcol;
    ws.srWindow.Bottom = newrow;
    if (!SetConsoleWindowInfo(wh, FALSE, &ws.srWindow)) {
	rb_syserr_fail(LAST_ERROR, "SetConsoleWindowInfo");
    }
#endif
    return io;
}
Пример #3
0
/*
 * call-seq:
 *   io.winsize     -> [rows, columns]
 *
 * Returns console size.
 *
 * You must require 'io/console' to use this method.
 */
static VALUE
console_winsize(VALUE io)
{
    rb_io_t *fptr;
    int fd;
    rb_console_size_t ws;

    GetOpenFile(io, fptr);
    fd = GetWriteFD(fptr);
    if (!getwinsize(fd, &ws)) rb_sys_fail(0);
    return rb_assoc_new(INT2NUM(winsize_row(&ws)), INT2NUM(winsize_col(&ws)));
}
Пример #4
0
/*
 * call-seq:
 *   io.oflush
 *
 * Flushes output buffer in kernel.
 */
static VALUE
console_oflush(VALUE io)
{
    rb_io_t *fptr;
    int fd;

    GetOpenFile(io, fptr);
    fd = GetWriteFD(fptr);
#if defined HAVE_TERMIOS_H || defined HAVE_TERMIO_H
    if (tcflush(fd, TCOFLUSH)) rb_sys_fail(0);
#endif
    return io;
}
Пример #5
0
/*
 * call-seq:
 *   io.winsize = [rows, columns]
 *
 * Tries to set console size.  The effect depends on the platform and
 * the running environment.
 *
 * You must require 'io/console' to use this method.
 */
static VALUE
console_set_winsize(VALUE io, VALUE size)
{
    rb_io_t *fptr;
    rb_console_size_t ws;
#if defined _WIN32
    HANDLE wh;
    int newrow, newcol;
#endif
    VALUE row, col, xpixel, ypixel;
#if defined TIOCSWINSZ
    int fd;
#endif

    GetOpenFile(io, fptr);
    size = rb_Array(size);
    rb_scan_args((int)RARRAY_LEN(size), RARRAY_PTR(size), "22",
                &row, &col, &xpixel, &ypixel);
#if defined TIOCSWINSZ
    fd = GetWriteFD(fptr);
    ws.ws_row = ws.ws_col = ws.ws_xpixel = ws.ws_ypixel = 0;
#define SET(m) ws.ws_##m = NIL_P(m) ? 0 : (unsigned short)NUM2UINT(m)
    SET(row);
    SET(col);
    SET(xpixel);
    SET(ypixel);
#undef SET
    if (!setwinsize(fd, &ws)) rb_sys_fail(0);
#elif defined _WIN32
    wh = (HANDLE)rb_w32_get_osfhandle(GetReadFD(fptr));
    newrow = (SHORT)NUM2UINT(row);
    newcol = (SHORT)NUM2UINT(col);
    if (!getwinsize(GetReadFD(fptr), &ws)) {
	rb_sys_fail("GetConsoleScreenBufferInfo");
    }
    if ((ws.dwSize.X < newcol && (ws.dwSize.X = newcol, 1)) ||
	(ws.dwSize.Y < newrow && (ws.dwSize.Y = newrow, 1))) {
	if (!(SetConsoleScreenBufferSize(wh, ws.dwSize) || SET_LAST_ERROR)) {
	    rb_sys_fail("SetConsoleScreenBufferInfo");
	}
    }
    ws.srWindow.Left = 0;
    ws.srWindow.Top = 0;
    ws.srWindow.Right = newcol;
    ws.srWindow.Bottom = newrow;
    if (!(SetConsoleWindowInfo(wh, FALSE, &ws.srWindow) || SET_LAST_ERROR)) {
	rb_sys_fail("SetConsoleWindowInfo");
    }
#endif
    return io;
}
Пример #6
0
static VALUE
console_cursor_pos(VALUE io)
{
    rb_io_t *fptr;
    int fd;
    rb_console_size_t ws;

    GetOpenFile(io, fptr);
    fd = GetWriteFD(fptr);
    if (!GetConsoleScreenBufferInfo((HANDLE)rb_w32_get_osfhandle(fd), &ws)) {
	rb_syserr_fail(LAST_ERROR, 0);
    }
    return rb_assoc_new(UINT2NUM(ws.dwCursorPosition.X), UINT2NUM(ws.dwCursorPosition.Y));
}
Пример #7
0
static VALUE
console_goto(VALUE io, VALUE x, VALUE y)
{
    rb_io_t *fptr;
    int fd;
    COORD pos;

    GetOpenFile(io, fptr);
    fd = GetWriteFD(fptr);
    pos.X = NUM2UINT(x);
    pos.Y = NUM2UINT(y);
    if (!SetConsoleCursorPosition((HANDLE)rb_w32_get_osfhandle(fd), pos)) {
	rb_syserr_fail(LAST_ERROR, 0);
    }
    return io;
}
Пример #8
0
static VALUE
console_beep(VALUE io)
{
    rb_io_t *fptr;
    int fd;

    GetOpenFile(io, fptr);
    fd = GetWriteFD(fptr);
#ifdef _WIN32
    (void)fd;
    MessageBeep(0);
#else
    if (write(fd, "\a", 1) < 0)
	rb_sys_fail(0);
#endif
    return io;
}
Пример #9
0
/*
 * call-seq:
 *   io.ioflush
 *
 * Flushes input and output buffers in kernel.
 *
 * You must require 'io/console' to use this method.
 */
static VALUE
console_ioflush(VALUE io)
{
    rb_io_t *fptr;
#if defined HAVE_TERMIOS_H || defined HAVE_TERMIO_H
    int fd1, fd2;
#endif

    GetOpenFile(io, fptr);
#if defined HAVE_TERMIOS_H || defined HAVE_TERMIO_H
    fd1 = GetReadFD(fptr);
    fd2 = GetWriteFD(fptr);
    if (fd2 != -1 && fd1 != fd2) {
	if (tcflush(fd1, TCIFLUSH)) rb_sys_fail(0);
	if (tcflush(fd2, TCOFLUSH)) rb_sys_fail(0);
    }
    else {
	if (tcflush(fd1, TCIOFLUSH)) rb_sys_fail(0);
    }
#endif
    return io;
}
Пример #10
0
			inline bool IsWriteReady()
			{
				return GetWriteFD() > 0;
			}