Пример #1
0
/*
 * refresh_screen: Whenever the REFRESH_SCREEN function is activated, this
 * swoops into effect 
 */
void refresh_screen (unsigned char dumb, char *dumber)
{
extern int need_redraw;

#if !defined(WINNT) && !defined(__EMX__)
	term_clear_screen();
	unflash();
#else
	xterm_settitle();
	term_clear_screen();
#endif

#if 0
	for (tmp = screen_list; tmp; tmp = tmp->next)
		tmp->co = TI_cols, tmp->li = TI_lines;
#endif
	if (term_resize())
		recalculate_windows(current_window->screen);
	else
		redraw_all_windows();
	if (need_redraw)
		need_redraw = 0;
	update_all_windows();
	update_input(UPDATE_ALL);
}
Пример #2
0
void	redraw_all_screens (void)
{
	Screen *s, *old_os;

	old_os = output_screen;
	for (s = screen_list; s; s = s->next)
	{
		if (!s->alive)
			continue;

		output_screen = s;
		unflash();
		term_clear_screen();
		if (s == main_screen && term_resize())
			recalculate_windows(current_window->screen);
	}

	/* Logically mark all windows as needing a redraw */
	redraw_all_windows();

	/* Physically redraw all windows and status bars */
	update_all_windows();

	/* Physically redraw all input lines */
	update_input(NULL, UPDATE_ALL);

	output_screen = old_os;
	need_redraw = 0;
}
Пример #3
0
void
x_resize(size_t width, size_t height)
{
    if (X.win_width == width && X.win_height == height) {
        return;
    }

    debug("%lux%lu", (long unsigned)width, (long unsigned)height);

    /* Update pixmap */
    if (X.pixmap)
        XFreePixmap(X.dpy, X.pixmap);
    X.pixmap = XCreatePixmap(X.dpy,
                             X.window,
                             width, height,
                             XDefaultDepth(X.dpy, X.screen));
    XSetForeground(X.dpy,
                   X.gc,
                   config.background);
    XFillRectangle(X.dpy,
                   X.pixmap,
                   X.gc,
                   0, 0,
                   width, height);

    X.win_width  = width;
    X.win_height = height;

    size_t glyphs_w = X.win_width  / X.glyph_width;
    size_t glyphs_h = X.win_height / X.glyph_height;

    term_resize(glyphs_w, glyphs_h);
}
Пример #4
0
static void
sig_term_resize(int sig GCC_UNUSED)
{
    struct winsize  newsize;
    Signal(SIGWINCH, SIG_IGN);	/* Don't bother me! */
    ioctl(0, TIOCGWINSZ, &newsize);
    term_resize(newsize.ws_col, newsize.ws_row);
}
Пример #5
0
/*
 * refresh_screen: Whenever the REFRESH_SCREEN function is activated, this
 * swoops into effect 
 */
void
refresh_screen(u_int key, u_char *ptr)
{
	term_clear_screen();
	if (term_resize())
#if 1
		balance_windows();
#else
		recalculate_windows();
#endif
	else
Пример #6
0
/* init_windows:  */
int init_screen (void)
{
extern int term_initialized;
	term_initialized = 1;
	term_clear_screen();
	term_resize();
	create_new_screen();
	new_window(main_screen);
	update_all_windows();
	term_move_cursor(0, 0);
	return 0;
}
Пример #7
0
/* Resize the terminal if needed */
void term_resize_dirty(void)
{
        int width, height;

	if (!resize_dirty)
		return;

        resize_dirty = FALSE;

	if (!term_get_size(&width, &height))
		width = height = -1;

	term_resize(width, height);
	mainwindows_resize(term_width, term_height);
	term_resize_final(width, height);
}
Пример #8
0
void	refresh_a_screen (Screen *screen)
{
	unflash();
	term_clear_screen();

	if (screen != main_screen || term_resize())
		recalculate_windows(screen);
	else
		redraw_all_windows();

	if (need_redraw)
		need_redraw = 0;

	update_all_windows();
	update_input(UPDATE_ALL);
}
Пример #9
0
/*
 * init_screen() sets up a full screen display for normal display mode.
 * It will fail if your TERM setting doesn't have all of the necessary
 * capabilities to run in full screen mode.  The client is expected to 
 * fail-over to dumb mode in this case.
 * This may only be called once, at initial startup (by main()).
 */
int	init_screen (void)
{
	/* Investigate TERM and put the console in full-screen mode */
	if (term_init())
		return -1;

	term_clear_screen();
	term_resize();

	/*
	 * System independant stuff
	 */
	create_new_screen();
	new_window(main_screen);
	update_all_windows();

	term_move_cursor(0, 0);
	return 0;
}
Пример #10
0
/* init_windows:  */
int	init_screen (void)
{
	/*
	 * System dependant stuff
	 */
	if (term_init())
		return -1;

	term_clear_screen();
	term_resize();

	/*
	 * System independant stuff
	 */
	create_new_screen();
	new_window(main_screen);
	update_all_windows();

	term_move_cursor(0, 0);
	return 0;
}
Пример #11
0
int main(int argc, char* argv[])
{
    printf("START! pid = %d\n", getpid());

    if (!system("./restart.rb"))
        exit(1);

    if (signal(SIGUSR1, RestartHandler) == SIG_ERR) {
        fprintf(stderr, "An error occurred while setting a signal handler.\n");
        exit(1);
    }

    bool fullscreen = true;
    s_config = new AppConfig(fullscreen, false, 1280, 800);
    SDL_Init(SDL_INIT_VIDEO | SDL_INIT_JOYSTICK);
    SDL_Window* displayWindow;
    SDL_Renderer* displayRenderer;

    uint32_t flags = SDL_WINDOW_OPENGL | (s_config->fullscreen ? SDL_WINDOW_FULLSCREEN_DESKTOP : 0);
	int err = SDL_CreateWindowAndRenderer(s_config->width, s_config->height, flags, &displayWindow, &displayRenderer);
	if (err == -1 || !displayWindow || !displayRenderer) {
		fprintf(stderr, "SDL_CreateWindowAndRenderer failed!\n");
	}

	SDL_RendererInfo displayRendererInfo;
    SDL_GetRendererInfo(displayRenderer, &displayRendererInfo);
    /* TODO: Check that we have OpenGL */
    if ((displayRendererInfo.flags & SDL_RENDERER_ACCELERATED) == 0 ||
        (displayRendererInfo.flags & SDL_RENDERER_TARGETTEXTURE) == 0) {
        /* TODO: Handle this. We have no render surface and not accelerated. */
        fprintf(stderr, "NO RENDERER wtf!\n");
    }

    atexit(SDL_Quit);

    JOYSTICK_Init();

    AppConfig& config = *s_config;
    config.title = "riftty";

    //SDL_WM_SetCaption(config.title.c_str(), config.title.c_str());
    //SDL_EnableKeyRepeat(SDL_DEFAULT_REPEAT_DELAY, SDL_DEFAULT_REPEAT_INTERVAL);

    /*
    // clear
    glClearColor(s_clearColor.x, s_clearColor.y, s_clearColor.z, s_clearColor.w);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    SDL_GL_SwapWindow(displayWindow);
    */

    RiftSetup();

    RenderInit();

    win_init();

    init_config();

    struct passwd *pw = getpwuid(getuid());
    const char *homedir = pw->pw_dir;
    char config_filename[512];
    strncpy(config_filename, homedir, 512);
    strncat(config_filename, "/.riftty", 512);
    load_config(config_filename);

    cs_init();  // TODO: code pages do not want

    // TODO: determine this based on window-size & font-size or vice versa.
    cfg.rows = 25;
    cfg.cols = 80;

    // TODO: load config from /etc/riffty or ~/.rifttyrc
    finish_config();
    win_reconfig();

    // TODO: get SHELL from env

    cs_reconfig(); // TODO: do not want

    term_init();
    term_reset();
    term_resize(cfg.rows, cfg.cols);

    // TODO:
    int font_width = 10;
    int font_height = 10;
    unsigned short term_width = font_width * cfg.cols;
    unsigned short term_height = font_height * cfg.rows;

    char login[128];
    strncpy(login, getlogin(), 128);
    const char* login_argv[] = {"login", "-pfl", login, NULL};
    unsigned short rows = cfg.rows;
    unsigned short cols = cfg.cols;
    winsize ws = {rows, cols, term_width, term_height};
    child_create(login_argv, &ws);

    bool done = false;
    while (!done)
    {
        JOYSTICK_ClearFlags();

        SDL_Event event;
        while (SDL_PollEvent(&event))
        {
            switch (event.type)
            {
            case SDL_QUIT:
                done = true;
                break;

            case SDL_MOUSEMOTION:
                if (event.motion.state & SDL_BUTTON(1)) {
                    // move touch
                }
                break;

            case SDL_MOUSEBUTTONDOWN:
                if (event.button.button == SDL_BUTTON_LEFT) {
                    // start touch
                }
                break;

            case SDL_MOUSEBUTTONUP:
                if (event.button.button == SDL_BUTTON_LEFT) {
                    // end touch
                }
                break;

            case SDL_JOYAXISMOTION:
                JOYSTICK_UpdateMotion(&event.jaxis);
                break;

            case SDL_JOYBUTTONDOWN:
            case SDL_JOYBUTTONUP:
                JOYSTICK_UpdateButton(&event.jbutton);
                break;

            case SDL_KEYDOWN:
            case SDL_KEYUP:
                if (ProcessKeyEvent(&event.key)) {
                    done = true;
                }
                break;
            }
        }

        if (!done)
        {
            if (s_needsRestart)
                Restart();

            unsigned int now = SDL_GetTicks();  // milliseconds
            float dt = (now - s_ticks) / 1000.0f;	// convert to seconds.
            s_ticks = now;

            //printf("fps = %.0f\n", 1.0f/dt);

            Process(dt);
            Render(dt);
        }
    }

    child_kill(true);
    win_shutdown();

    RiftShutdown();
    JOYSTICK_Shutdown();

    return 0;
}
Пример #12
0
void
reattach_tty(char *tty, char *password)
{
	int s = -1;
	char *name;
	struct sockaddr_in addr;
	struct hostent *hp;
	int len = 0;
	fd_set rd_fd;
	struct timeval tm = {0};
	char chr_c[] = "\003";

/*
 * this buffer has to be big enough to handle a full screen of
 * information from the detached process.
 */
	unsigned char buffer[6 * BIG_BUFFER_SIZE + 1];
	char *p;
	int port = 0;

#if defined (TIOCGWINSZ)
	struct winsize window;

#endif
	memset(&parm, 0, sizeof(struct param));

	if (!(name = find_detach_socket(socket_path, tty))) {
		fprintf(stderr, "No detached process to attach to.\r\n");
		_exit(1);
	}
	strcpy(parm.cookie, get_cookie(name));
	if (!*parm.cookie)
		_exit(1);
	if ((p = strrchr(name, '/')))
		p++;
	sscanf(p, "%d.%*s.%*s", &port);
	displays = 1;
	if ((s = socket(AF_INET, SOCK_STREAM, 0)) < 0) {
		displays = 0;
		_exit(1);
	}
	chmod(name, SOCKMODE);
	set_socket_options(s);
	memset(&addr, 0, sizeof(struct sockaddr_in));
	addr.sin_port = htons(port);
	addr.sin_family = AF_INET;
	if ((hp = gethostbyname("localhost")))
		memcpy(&addr.sin_addr, hp->h_addr, hp->h_length);
	else
		inet_aton("127.0.0.1", (struct in_addr *)&addr.sin_addr);
	if (connect(s, (struct sockaddr *)&addr, sizeof(addr)) < 0) {
		fprintf(stderr, "connection refused for %s\r\n", name);
		_exit(1);
	}
	parm.pid = getpid();
	parm.pgrp = getpgrp();
	parm.uid = getuid();
	strcpy(parm.tty, ttyname(0));
	strncpy(parm.termid, getenv("TERM"), 80);
	if (password)
		strncpy(parm.password, password, 60);
	fprintf(stderr, "attempting to wakeup %s\r\n", find_tty_name(name));
#if defined (TIOCGWINSZ)
	if (ioctl(0, TIOCGWINSZ, &window) > -1) {
		parm.cols = window.ws_col;
		parm.rows = window.ws_row;
	} else
#endif
	{
		parm.cols = 79;
		parm.rows = 25;
	}
	write(s, &parm, sizeof(struct param));
	sleep(2);
	alarm(15);
	len = read(s, &parm, sizeof(struct param));
	alarm(0);
	if (len <= 0) {
		fprintf(stderr, "error reconnecting to %s\r\n", find_tty_name(name));
		displays = 0;
		chmod(name, SOCKMODE);
		exit(1);
	}
	unlink(name);

	term_init(parm.termid);
	set_term_eight_bit(1);
	charset_ibmpc();
	term_clear_screen();
	term_resize();
	term_move_cursor(0, 0);

	my_signal(SIGPIPE, handle_pipe, 0);
	my_signal(SIGINT, handle_ctrlc, 0);
	my_signal(SIGHUP, handle_hup, 0);

	/*
	 * according to MHacker we need to set errno to 0 under BSD.
	 * for some reason we get a address in use from a socket
	 *
	 */
	errno = 0;
	while (1) {
		FD_ZERO(&rd_fd);
		FD_SET(0, &rd_fd);
		FD_SET(s, &rd_fd);
		tm.tv_sec = 2;

		switch (select(s + 1, &rd_fd, NULL, NULL, &tm)) {
		case -1:
			if (ctrl_c) {
				write(s, chr_c, 1);
				ctrl_c = 0;
			} else if (errno != EINTR) {
				close(s);
				_exit(1);
			}
			break;
		case 0:
			break;
		default:
		{
			if (FD_ISSET(0, &rd_fd)) {
				len = read(0, buffer, sizeof(buffer) - 1);
				write(s, buffer, len);
			}
			if (FD_ISSET(s, &rd_fd)) {
				len = read(s, buffer, sizeof(buffer) - 1);
				write(1, buffer, len);
			}
		}
		}
	}
	close(s);
	fprintf(stderr, "Never should have got here");
	_exit(1);

	return;                         /* error return */
}
Пример #13
0
/* input:  raw character
 * output: telnet command if c was handled, otherwise zero.
 */
unsigned int
telnet_handler(unsigned char c)
{
    static unsigned char iac_quote = 0; /* as byte to reduce memory */
    static unsigned char iac_opt_req = 0;

    static unsigned char iac_buf[TELNET_IAC_MAXLEN];
    static unsigned int  iac_buflen = 0;

    /* we have to quote all IACs. */
    if(c == IAC && !iac_quote) {
	iac_quote = 1;
	return NOP;
    }

#ifdef DETECT_CLIENT
    /* hash client telnet sequences */
    if(cuser.userid[0]==0) {
	if(iac_state == IAC_WAIT_SE) {
	    // skip suboption
	} else {
	    if(iac_quote)
		UpdateClientCode(IAC);
	    UpdateClientCode(c);
	}
    }
#endif

    /* a special case is the top level iac. otherwise, iac is just a quote. */
    if (iac_quote) {
	if(iac_state == IAC_NONE)
	    iac_state = IAC_COMMAND;
	if(iac_state == IAC_WAIT_SE && c == SE)
	    iac_state = IAC_PROCESS_OPT;
	iac_quote = 0;
    }

    /* now, let's process commands by state */
    switch(iac_state) {

	case IAC_NONE:
	    return 0;

	case IAC_COMMAND:
#if 0 // def DEBUG
	    {
		int cx = c; /* to make compiler happy */
		write(0, "-", 1);
		if(TELCMD_OK(cx))
		    write(0, TELCMD(c), strlen(TELCMD(c)));
		write(0, " ", 1);
	    }
#endif
	    iac_state = IAC_NONE; /* by default we restore state. */
	    switch(c) {
		case IAC:
		    // return 0;
		    // we don't want to allow IACs as input.
		    return 1;

		/* we don't want to process these. or maybe in future. */
		case BREAK:           /* break */
#ifdef DBG_OUTRPT
		    fakeEscape = !fakeEscape;
		    return NOP;
#endif

		case ABORT:           /* Abort process */
		case SUSP:            /* Suspend process */
		case AO:              /* abort output--but let prog finish */
		case IP:              /* interrupt process--permanently */
		case EOR:             /* end of record (transparent mode) */
		case DM:              /* data mark--for connect. cleaning */
		case xEOF:            /* End of file: EOF is already used... */
		    return NOP;

		case NOP:             /* nop */
		    return NOP;

		/* we should process these, but maybe in future. */
		case GA:              /* you may reverse the line */
		case EL:              /* erase the current line */
		case EC:              /* erase the current character */
		    return NOP;

		/* good */
		case AYT:             /* are you there */
		    {
			    const char *alive = "I'm still alive, loading: ";
			    char buf[STRLEN];

			    /* respond as fast as we can */
			    write(0, alive, strlen(alive));
//			    cpuload(buf);
			    buf[0] = '0';	// TODO: cpuload
			    write(0, buf, strlen(buf));
			    write(0, "\r\n", 2);
		    }
		    return NOP;

		case DONT:            /* you are not to use option */
		case DO:              /* please, you use option */
		case WONT:            /* I won't use option */
		case WILL:            /* I will use option */
		    iac_opt_req = c;
		    iac_state = IAC_WAIT_OPT;
		    return NOP;

		case SB:              /* interpret as subnegotiation */
		    iac_state = IAC_WAIT_SE;
		    iac_buflen = 0;
		    return NOP;

		case SE:              /* end sub negotiation */
		default:
		    return NOP;
	    }
	    return 1;

	case IAC_WAIT_OPT:
#if 0 // def DEBUG
	    write(0, "-", 1);
	    if(TELOPT_OK(c))
		write(0, TELOPT(c), strlen(TELOPT(c)));
	    write(0, " ", 1);
#endif
	    iac_state = IAC_NONE;
	    /*
	     * According to RFC, there're some tricky steps to prevent loop.
	     * However because we have a poor term which does not allow
	     * most abilities, let's be a strong boss here.
	     *
	     * Although my old imeplementation worked, it's even better to follow this:
	     * http://www.tcpipguide.com/free/t_TelnetOptionsandOptionNegotiation-3.htm
	     */
	    switch(c) {
		/* i-dont-care: i don't care about what client is.
		 * these should be clamed in init and
		 * client must follow me. */
		case TELOPT_TTYPE:	/* termtype or line. */
		case TELOPT_NAWS:       /* resize terminal */
		case TELOPT_SGA:	/* supress GA */
		case TELOPT_ECHO:       /* echo */
		case TELOPT_BINARY:	/* we are CJK. */
		    break;

		/* i-dont-agree: i don't understand/agree these.
		 * according to RFC, saying NO stopped further
		 * requests so there'll not be endless loop. */
		case TELOPT_RCP:         /* prepare to reconnect */
		default:
		    if (iac_opt_req == WILL || iac_opt_req == DO)
		    {
			/* unknown option, reply with won't */
			unsigned char cmd[3] = { IAC, DONT, 0 };
			if(iac_opt_req == DO) cmd[1] = WONT;
			cmd[2] = c;
			write(0, cmd, sizeof(cmd));
		    }
		    break;
	    }
	    return 1;

	case IAC_WAIT_SE:
	    iac_buf[iac_buflen++] = c;
	    /* no need to convert state because previous quoting will do. */

	    if(iac_buflen == TELNET_IAC_MAXLEN) {
		/* may be broken protocol?
		 * whether finished or not, break for safety
		 * or user may be frozen.
		 */
		iac_state = IAC_NONE;
		return 0;
	    }
	    return 1;

	case IAC_PROCESS_OPT:
	    iac_state = IAC_NONE;
#if 0 // def DEBUG
	    write(0, "-", 1);
	    if(TELOPT_OK(iac_buf[0]))
		write(0, TELOPT(iac_buf[0]), strlen(TELOPT(iac_buf[0])));
	    write(0, " ", 1);
#endif
	    switch(iac_buf[0]) {

		/* resize terminal */
		case TELOPT_NAWS:
		    {
			int w = (iac_buf[1] << 8) + (iac_buf[2]);
			int h = (iac_buf[3] << 8) + (iac_buf[4]);
			term_resize(w, h);
#ifdef DETECT_CLIENT
			if(cuser.userid[0]==0) {
			    UpdateClientCode(iac_buf[0]);
			    if(w==80 && h==24)
				UpdateClientCode(1);
			    else if(w==80)
				UpdateClientCode(2);
			    else if(h==24)
				UpdateClientCode(3);
			    else
				UpdateClientCode(4);
			    UpdateClientCode(IAC);
			    UpdateClientCode(SE);
			}
#endif
		    }
		    break;

		default:
#ifdef DETECT_CLIENT
		    if(cuser.userid[0]==0) {
			int i;
			for(i=0;i<iac_buflen;i++)
			    UpdateClientCode(iac_buf[i]);
			UpdateClientCode(IAC);
			UpdateClientCode(SE);
		    }
#endif
		    break;
	    }
	    return 1;
    }
    return 1; /* never reached */
}
Пример #14
0
int	main (int argc, char **argv)
{
	fd_set	reads;
	int	nread;
	char * 	port;
	char *	host;
	char *	tmp;
	char	stuff[100];

	my_signal(SIGHUP, SIG_IGN);
	my_signal(SIGQUIT, SIG_IGN);
	my_signal(SIGINT, ignore);
	my_signal(SIGWINCH, sigwinch_func);

	if (argc != 3)    		/* no socket is passed */
		my_exit(1);

	host = argv[1];
	port = argv[2];

	if ((data = connectory(host, port)) < 0)
		my_exit(23);

	if ((cmd = connectory(host, port)) < 0)
		my_exit(25);

	/*
	 * First thing we do is tell the parent what protocol we plan on
	 * talking.  We will start the protocol at version 4, for this is
	 * the fourth generation of wservs.
	 *
	 * We cannot use 'snprintf' here because we do not have the compat
	 * functions and some systems do not have snprintf!  This use of
	 * sprintf is demonstrably safe.
	 */
	sprintf(stuff, "version=%d\n", CURRENT_WSERV_VERSION);
	write(cmd, stuff, strlen(stuff));

	/*
	 * Next thing we take care of is to tell the parent client
	 * what tty we are using and tell them what geometry our screen
	 * is.  This provides some amount of sanity against whatever
	 * brain damage might occur.  The parent client takes our word
	 * for what size this screen should be, and handles it accordingly.
	 *
	 * Warning:  I am using sprintf() and write() because previous
	 * attempts to use writev() have shown that linux does not have
	 * an atomic writev() function (boo, hiss).  The parent client
	 * does not take kindly to this data coming in multiple packets.
	 */
	tmp = ttyname(0);
	sprintf(stuff, "tty=%s\n", tmp);
	write(cmd, stuff, strlen(stuff));

	term_init();		/* Set up the xterm */
	term_resize();		/* Figure out how big xterm is and tell epic */

	/*
	 * The select call..  reads from the socket, and from the window..
	 * and pipes the output from out to the other..  nice and simple.
	 * The command pipe is write-only.  The parent client does not
	 * send anything to us over the command pipe.
	 */
	for (;;)
	{
		FD_ZERO(&reads);
		FD_SET(0, &reads);
		FD_SET(data, &reads);
		if (select(data + 1, &reads, NULL, NULL, NULL) <= 0)
		{
			if (errno == EINTR && got_sigwinch)
			{
				got_sigwinch = 0;
				term_resize();
			}
			continue;
		}

		if (FD_ISSET(0, &reads))
		{
			if ((nread = read(0, buffer, sizeof(buffer))) > 0)
				write(data, buffer, nread);
			else
				my_exit(3);
		}
		if (FD_ISSET(data, &reads))
		{
			if ((nread = read(data, buffer, sizeof(buffer))) > 0)
				write(0, buffer, nread);
			else
				my_exit(4);
		}
	}

	my_exit(8);
}