예제 #1
0
파일: chansrv.c 프로젝트: skdong/nfs-ovd
	int DEFAULT_CC
main(int argc, char** argv)
{
	int pid;
	char text[256];
	if (argc != 2)
	{
		g_printf("Usage : xrdp-chansrv 'username'\n");
		g_exit(1);
	}
	username = argv[1];
	g_init(); /* os_calls */
	read_ini();
	read_logging_conf();
	chan_init();
	log_start(&log_conf);
	pid = g_getpid();
	log_message(&log_conf, LOG_LEVEL_DEBUG, "chansrv[main]: "
			"app started pid %d(0x%8.8x)", pid, pid);
	g_signal_kill(term_signal_handler); /* SIGKILL */
	g_signal_terminate(term_signal_handler); /* SIGTERM */
	g_signal_user_interrupt(term_signal_handler); /* SIGINT */
	g_signal_pipe(nil_signal_handler); /* SIGPIPE */
	g_signal_child_stop(stop_signal_handler);
	g_snprintf(text, 255, "xrdp_chansrv_%8.8x_main_term", pid);
	g_term_event = g_create_wait_obj(text);
	g_snprintf(text, 255, "xrdp_chansrv_%8.8x_thread_done", pid);
	g_thread_done_event = g_create_wait_obj(text);
	tc_thread_create(channel_thread_loop, 0);
	while (!g_is_wait_obj_set(g_term_event))
	{
		if (g_obj_wait(&g_term_event, 1, 0, 0, 0) != 0)
		{
			log_message(&log_conf, LOG_LEVEL_WARNING, "chansrv[main]: "
					"main: error, g_obj_wait failed");
			break;
		}
	}
	while (!g_is_wait_obj_set(g_thread_done_event))
	{
		/* wait for thread to exit */
		if (g_obj_wait(&g_thread_done_event, 1, 0, 0, 0) != 0)
		{
			log_message(&log_conf, LOG_LEVEL_WARNING, "chansrv[main]: "
					"main: error, g_obj_wait failed");
			break;
		}
	}
	/* cleanup */
	main_cleanup();
	log_message(&log_conf, LOG_LEVEL_INFO, "chansrv[main]: "
			"main: app exiting pid %d(0x%8.8x)", pid, pid);
	return 0;
}
예제 #2
0
/* wait for incoming connections */
int APP_CC
xrdp_listen_main_loop(struct xrdp_listen* self)
{
  int error;
  int robjs_count;
  int cont;
  char port[8];
  tbus robjs[8];
  tbus term_obj;
  tbus sync_obj;
  tbus sck_obj;
  tbus done_obj;
  struct xrdp_process* process;

  self->status = 1;
  xrdp_listen_get_port(port, sizeof(port));
  self->sck = g_tcp_socket();
  g_tcp_set_non_blocking(self->sck);
  error = g_tcp_bind(self->sck, port);
  if (error != 0)
  {
    g_writeln("bind error in xrdp_listen_main_loop");
    g_tcp_close(self->sck);
    self->status = -1;
    return 1;
  }
  error = g_tcp_listen(self->sck);
  if (error == 0)
  {
    term_obj = g_get_term_event();
    sync_obj = g_get_sync_event();
    sck_obj = g_create_wait_obj_from_socket(self->sck, 0);
    done_obj = self->pro_done_event;
    cont = 1;
    while (cont)
    {
      /* build the wait obj list */
      robjs_count = 0;
      robjs[robjs_count++] = term_obj;
      robjs[robjs_count++] = sync_obj;
      robjs[robjs_count++] = sck_obj;
      robjs[robjs_count++] = done_obj;
      /* wait */
      if (g_obj_wait(robjs, robjs_count, 0, 0, -1) != 0)
      {
        /* error, should not get here */
        g_sleep(100);
      }
      if (g_is_wait_obj_set(term_obj)) /* term */
      {
        break;
      }
      if (g_is_wait_obj_set(sync_obj)) /* sync */
      {
        g_reset_wait_obj(sync_obj);
        g_loop();
      }
      if (g_is_wait_obj_set(sck_obj)) /* incomming connection */
      {
        error = g_tcp_accept(self->sck);
        if ((error == -1) && g_tcp_last_error_would_block(self->sck))
        {
          /* should not get here */
          g_sleep(100);
        }
        else if (error == -1)
        {
          /* error, should not get here */
          break;
        }
        else
        {
          process = xrdp_process_create(self, self->pro_done_event);
          if (xrdp_listen_add_pro(self, process) == 0)
          {
            /* start thread */
            process->sck = error;
            g_process = process;
            tc_thread_create(xrdp_process_run, 0);
            tc_sem_dec(g_process_sem); /* this will wait */
          }
          else
          {
            xrdp_process_delete(process);
          }
        }
      }
      if (g_is_wait_obj_set(done_obj)) /* pro_done_event */
      {
        g_reset_wait_obj(done_obj);
        xrdp_listen_delete_done_pro(self);
      }
    }
    /* stop listening */
    g_delete_wait_obj_from_socket(sck_obj);
    g_tcp_close(self->sck);
    /* second loop to wait for all process threads to close */
    cont = 1;
    while (cont)
    {
      if (self->process_list->count == 0)
      {
        break;
      }
      /* build the wait obj list */
      robjs_count = 0;
      robjs[robjs_count++] = sync_obj;
      robjs[robjs_count++] = done_obj;
      /* wait */
      if (g_obj_wait(robjs, robjs_count, 0, 0, -1) != 0)
      {
        /* error, should not get here */
        g_sleep(100);
      }
      if (g_is_wait_obj_set(sync_obj)) /* sync */
      {
        g_reset_wait_obj(sync_obj);
        g_loop();
      }
      if (g_is_wait_obj_set(done_obj)) /* pro_done_event */
      {
        g_reset_wait_obj(done_obj);
        xrdp_listen_delete_done_pro(self);
      }
    }
  }
  else
  {
    DEBUG(("listen error in xrdp_listen_main_loop"));
  }
  self->status = -1;
  return 0;
}
예제 #3
0
파일: chansrv.c 프로젝트: skdong/nfs-ovd
	THREAD_RV THREAD_CC
channel_thread_loop(void* in_val)
{
	tbus objs[32];
	int num_objs;
	int timeout;
	int error;
	THREAD_RV rv;
	log_message(&log_conf, LOG_LEVEL_DEBUG, "chansrv[channel_thread_loop]: "
			"channel_thread_loop: thread start");
	rv = 0;
	error = setup_listen();
	if (error == 0)
	{
		timeout = 0;
		num_objs = 0;
		objs[num_objs] = g_term_event;
		num_objs++;
		trans_get_wait_objs(g_lis_trans, objs, &num_objs, &timeout);
		while (g_obj_wait(objs, num_objs, 0, 0, timeout) == 0)
		{
			if (g_is_wait_obj_set(g_term_event))
			{
				log_message(&log_conf, LOG_LEVEL_DEBUG, "chansrv[channel_thread_loop]: "
						"channel_thread_loop: g_term_event set");
				//clipboard_deinit();
				//sound_deinit();
				//dev_redir_deinit();
				//seamrdp_deinit();
				user_channel_deinit();
				break;
			}
			if (g_lis_trans != 0)
			{
				if (trans_check_wait_objs(g_lis_trans) != 0)
				{
					log_message(&log_conf, LOG_LEVEL_WARNING, "chansrv[channel_thread_loop]: "
							"trans_check_wait_objs error");
				}
			}
			if (g_con_trans != 0)
			{
				if (trans_check_wait_objs(g_con_trans) != 0)
				{
					log_message(&log_conf, LOG_LEVEL_WARNING, "chansrv[channel_thread_loop]: "
							"trans_check_wait_objs error resetting");
					//clipboard_deinit();
					//sound_deinit();
					//dev_redir_deinit();
					//seamrdp_deinit();
					user_channel_deinit();

					trans_delete(g_con_trans);
					g_con_trans = 0;
					error = setup_listen();
					if (error != 0)
					{
						break;
					}
				}
			}
			//clipboard_check_wait_objs();
			//sound_check_wait_objs();
			//dev_redir_check_wait_objs();
			//seamrdp_check_wait_objs();
			user_channel_check_wait_objs();
			timeout = 0;
			num_objs = 0;
			objs[num_objs] = g_term_event;
			num_objs++;
			trans_get_wait_objs(g_lis_trans, objs, &num_objs, &timeout);
			trans_get_wait_objs(g_con_trans, objs, &num_objs, &timeout);
			//clipboard_get_wait_objs(objs, &num_objs, &timeout);
			//sound_get_wait_objs(objs, &num_objs, &timeout);
			//dev_redir_get_wait_objs(objs, &num_objs, &timeout);
			//seamrdp_get_wait_objs(objs, &num_objs, &timeout);
			user_channel_get_wait_objs(objs, &num_objs, &timeout);

		}
	}
	trans_delete(g_lis_trans);
	g_lis_trans = 0;
	trans_delete(g_con_trans);
	g_con_trans = 0;
	log_message(&log_conf, LOG_LEVEL_DEBUG, "chansrv[channel_thread_loop]: "
			"channel_thread_loop: thread stop");
	g_set_wait_obj(g_thread_done_event);
	return rv;
}
예제 #4
0
/**
 *
 * @brief Starts sesman main loop
 *
 */
static void DEFAULT_CC
sesman_main_loop(void)
{
	int in_sck;
	int error;
	int robjs_count;
	int cont;
	tbus sck_obj;
	tbus robjs[8];

	/*main program loop*/
	log_message(&(g_cfg->log), LOG_LEVEL_INFO, "sesman[sesman_main_loop]: "
				"listening...");
	g_sck = g_tcp_socket();
	g_tcp_set_non_blocking(g_sck);
	error = scp_tcp_bind(g_sck, g_cfg->listen_address, g_cfg->listen_port);
	if (error == 0)
	{
		error = g_tcp_listen(g_sck);
		if (error == 0)
		{
			sck_obj = g_create_wait_obj_from_socket(g_sck, 0);
			cont = 1;
			while (cont)
			{
				/* build the wait obj list */
				robjs_count = 0;
				robjs[robjs_count++] = sck_obj;
				robjs[robjs_count++] = g_term_event;
				robjs[robjs_count++] = g_sync_event;
				/* wait */
				if (g_obj_wait(robjs, robjs_count, 0, 0, -1) != 0)
				{
					/* error, should not get here */
					g_sleep(100);
				}
				if (g_is_wait_obj_set(g_term_event)) /* term */
				{
					break;
				}
				if (g_is_wait_obj_set(g_sync_event)) /* sync */
				{
					g_reset_wait_obj(g_sync_event);
					session_sync_start();
				}
				if (g_is_wait_obj_set(sck_obj)) /* incomming connection */
				{
					in_sck = g_tcp_accept(g_sck);
					if ((in_sck == -1) && g_tcp_last_error_would_block(g_sck))
					{
						/* should not get here */
						g_sleep(100);
					}
					else if (in_sck == -1)
					{
						/* error, should not get here */
						break;
					}
					else
					{
						/* we've got a connection, so we pass it to scp code */
						log_message(&(g_cfg->log), LOG_LEVEL_INFO, "sesman[sesman_main_loop]: "
								"new connection");
						thread_scp_start(in_sck);
						/* todo, do we have to wait here ? */
					}
				}
			}
			g_delete_wait_obj_from_socket(sck_obj);
		}
		else
		{
			log_message(&(g_cfg->log), LOG_LEVEL_ERROR, "sesman[sesman_main_loop]: "
					"listen error %d (%s)", g_get_errno(), g_get_strerror());
		}
	}
	else
	{
		log_message(&(g_cfg->log), LOG_LEVEL_ERROR, "bind error on "
				"port '%s': %d (%s)", g_cfg->listen_port, g_get_errno(), g_get_strerror());
	}
	g_tcp_close(g_sck);
}
예제 #5
0
/* wait for incoming connections */
int APP_CC
xrdp_listen_main_loop(struct xrdp_listen *self)
{
    int error;
    int robjs_count;
    int cont;
    int timeout = 0;
    char port[128];
    char address[256];
    tbus robjs[8];
    tbus term_obj;
    tbus sync_obj;
    tbus done_obj;
    int tcp_nodelay;
    int tcp_keepalive;
    int bytes;

    self->status = 1;

    if (xrdp_listen_get_port_address(port, sizeof(port),
                                     address, sizeof(address),
                                     &tcp_nodelay, &tcp_keepalive,
                                     self->startup_params) != 0)
    {
        log_message(LOG_LEVEL_ERROR,"xrdp_listen_main_loop: xrdp_listen_get_port failed");
        self->status = -1;
        return 1;
    }

    if (port[0] == '/')
    {
        /* set UDS mode */
        self->listen_trans->mode = TRANS_MODE_UNIX;
        /* not valid with UDS */
        tcp_nodelay = 0;
    }

    /* Create socket */
    error = trans_listen_address(self->listen_trans, port, address);

    if (error == 0)
    {
        if (tcp_nodelay)
        {
            if (g_tcp_set_no_delay(self->listen_trans->sck))
            {
                log_message(LOG_LEVEL_ERROR,"Error setting tcp_nodelay");
            }
        }

        if (tcp_keepalive)
        {
            if (g_tcp_set_keepalive(self->listen_trans->sck))
            {
                log_message(LOG_LEVEL_ERROR,"Error setting tcp_keepalive");
            }
        }

        if (self->startup_params->send_buffer_bytes > 0)
        {
            bytes = self->startup_params->send_buffer_bytes;
            log_message(LOG_LEVEL_INFO, "setting send buffer to %d bytes",
                        bytes);
            if (g_sck_set_send_buffer_bytes(self->listen_trans->sck,
                                            bytes) != 0)
            {
                log_message(LOG_LEVEL_ERROR, "error setting send buffer");
            }
            else
            {
                if (g_sck_get_send_buffer_bytes(self->listen_trans->sck,
                                                &bytes) != 0)
                {
                    log_message(LOG_LEVEL_ERROR, "error getting send buffer");
                }
                else
                {
                    log_message(LOG_LEVEL_INFO, "send buffer set to %d bytes", bytes);
                }
            }
        }

        if (self->startup_params->recv_buffer_bytes > 0)
        {
            bytes = self->startup_params->recv_buffer_bytes;
            log_message(LOG_LEVEL_INFO, "setting recv buffer to %d bytes",
                        bytes);
            if (g_sck_set_recv_buffer_bytes(self->listen_trans->sck,
                                            bytes) != 0)
            {
                log_message(LOG_LEVEL_ERROR, "error setting recv buffer");
            }
            else
            {
                if (g_sck_get_recv_buffer_bytes(self->listen_trans->sck,
                                                &bytes) != 0)
                {
                    log_message(LOG_LEVEL_ERROR, "error getting recv buffer");
                }
                else
                {
                    log_message(LOG_LEVEL_INFO, "recv buffer set to %d bytes", bytes);
                }
            }
        }

        self->listen_trans->trans_conn_in = xrdp_listen_conn_in;
        self->listen_trans->callback_data = self;
        term_obj = g_get_term_event(); /*Global termination event */
        sync_obj = g_get_sync_event();
        done_obj = self->pro_done_event;
        cont = 1;

        while (cont)
        {
            /* build the wait obj list */
            robjs_count = 0;
            robjs[robjs_count++] = term_obj;
            robjs[robjs_count++] = sync_obj;
            robjs[robjs_count++] = done_obj;
            timeout = -1;

            /* if (self->listen_trans != 0) */
            {
                if (trans_get_wait_objs(self->listen_trans, robjs,
                                        &robjs_count) != 0)
                {
                    log_message(LOG_LEVEL_ERROR,"Listening socket is in wrong state we "
                              "terminate listener");
                    break;
                }
            }

            /* wait - timeout -1 means wait indefinitely*/
            if (g_obj_wait(robjs, robjs_count, 0, 0, timeout) != 0)
            {
                /* error, should not get here */
                g_sleep(100);
            }

            if (g_is_wait_obj_set(term_obj)) /* termination called */
            {
                break;
            }

            /* some function must be processed by this thread */
            if (g_is_wait_obj_set(sync_obj))
            {
                g_reset_wait_obj(sync_obj);
                g_process_waiting_function(); /* run the function */
            }

            if (g_is_wait_obj_set(done_obj)) /* pro_done_event */
            {
                g_reset_wait_obj(done_obj);
                /* a process has died remove it from lists*/
                xrdp_listen_delete_done_pro(self);
            }

            /* Run the callback when accept() returns a new socket*/
            if (trans_check_wait_objs(self->listen_trans) != 0)
            {
                break;
            }
        }

        /* stop listening */
        trans_delete(self->listen_trans);
        self->listen_trans = 0;
        /* second loop to wait for all process threads to close */
        cont = 1;

        while (cont)
        {
            if (self->process_list->count == 0)
            {
                break;
            }

            timeout = -1;
            /* build the wait obj list */
            robjs_count = 0;
            robjs[robjs_count++] = sync_obj;
            robjs[robjs_count++] = done_obj;

            /* wait - timeout -1 means wait indefinitely*/
            if (g_obj_wait(robjs, robjs_count, 0, 0, timeout) != 0)
            {
                /* error, should not get here */
                g_sleep(100);
            }

            /* some function must be processed by this thread */
            if (g_is_wait_obj_set(sync_obj))
            {
                g_reset_wait_obj(sync_obj);
                g_process_waiting_function(); /* run the function that is waiting*/
            }

            if (g_is_wait_obj_set(done_obj)) /* pro_done_event */
            {
                g_reset_wait_obj(done_obj);
                xrdp_listen_delete_done_pro(self);
            }
        }
    }
    else
    {
        log_message(LOG_LEVEL_ERROR,"xrdp_listen_main_loop: listen error, possible port "
                  "already in use");
    }

    self->status = -1;
    return 0;
}
예제 #6
0
int APP_CC
xrdp_process_main_loop(struct xrdp_process* self)
{
  int robjs_count;
  int wobjs_count;
  int cont;
  int timeout;
  tbus robjs[32];
  tbus wobjs[32];
  tbus term_obj;
  tbus sck_obj;

  self->status = 1;
  self->session = libxrdp_init((long)self, self->sck);
  /* this callback function is in xrdp_wm.c */
  self->session->callback = callback;
  /* this function is just above */
  self->session->is_term = xrdp_is_term;
  g_tcp_set_non_blocking(self->sck);
  g_tcp_set_no_delay(self->sck);
  if (libxrdp_process_incomming(self->session) == 0)
  {
    term_obj = g_get_term_event();
    sck_obj = g_create_wait_obj_from_socket(self->sck, 0);
    cont = 1;
    while (cont)
    {
      /* build the wait obj list */
      timeout = -1;
      robjs_count = 0;
      wobjs_count = 0;
      robjs[robjs_count++] = term_obj;
      robjs[robjs_count++] = sck_obj;
      robjs[robjs_count++] = self->self_term_event;
      xrdp_wm_get_wait_objs(self->wm, robjs, &robjs_count,
                            wobjs, &wobjs_count, &timeout);
      /* wait */
      if (g_obj_wait(robjs, robjs_count, wobjs, wobjs_count, timeout) != 0)
      {
        /* error, should not get here */
        g_sleep(100);
      }
      if (g_is_wait_obj_set(term_obj)) /* term */
      {
        break;
      }
      if (g_is_wait_obj_set(self->self_term_event))
      {
        break;
      }
      if (g_is_wait_obj_set(sck_obj)) /* incomming client data */
      {
        if (xrdp_process_loop(self) != 0)
        {
          break;
        }
      }
      if (xrdp_wm_check_wait_objs(self->wm) != 0)
      {
        break;
      }
    }
    g_delete_wait_obj_from_socket(sck_obj);
    libxrdp_disconnect(self->session);
  }
  xrdp_process_mod_end(self);
  libxrdp_exit(self->session);
  self->session = 0;
  g_tcp_close(self->sck);
  self->status = -1;
  g_set_wait_obj(self->done_event);
  return 0;
}
예제 #7
0
int APP_CC
xrdp_process_main_loop(struct xrdp_process* self)
{
  int robjs_count;
  int wobjs_count;
  int cont;
  int timeout = 0;
  tbus robjs[32];
  tbus wobjs[32];
  tbus term_obj;

  DEBUG(("xrdp_process_main_loop"));
  self->status = 1;
  self->server_trans->trans_data_in = xrdp_process_data_in;
  self->server_trans->callback_data = self;
  self->session = libxrdp_init((tbus)self, self->server_trans);
  /* this callback function is in xrdp_wm.c */
  self->session->callback = callback;
  /* this function is just above */
  self->session->is_term = xrdp_is_term;
  if (libxrdp_process_incomming(self->session) == 0)
  {
    term_obj = g_get_term_event();
    cont = 1;
    while (cont)
    {
      /* build the wait obj list */
      timeout = -1;
      robjs_count = 0;
      wobjs_count = 0;
      robjs[robjs_count++] = term_obj;
      robjs[robjs_count++] = self->self_term_event;
      xrdp_wm_get_wait_objs(self->wm, robjs, &robjs_count,
                            wobjs, &wobjs_count, &timeout);
      trans_get_wait_objs(self->server_trans, robjs, &robjs_count, &timeout);
      /* wait */
      if (g_obj_wait(robjs, robjs_count, wobjs, wobjs_count, timeout) != 0)
      {
        /* error, should not get here */
        g_sleep(100);
      }
      if (g_is_wait_obj_set(term_obj)) /* term */
      {
        break;
      }
      if (g_is_wait_obj_set(self->self_term_event))
      {
        break;
      }
      if (xrdp_wm_check_wait_objs(self->wm) != 0)
      {
        break;
      }
      if (trans_check_wait_objs(self->server_trans) != 0)
      {
        break;
      }
    }
    libxrdp_disconnect(self->session);
  }
  xrdp_process_mod_end(self);
  libxrdp_exit(self->session);
  self->session = 0;
  self->status = -1;
  g_set_wait_obj(self->done_event);
  return 0;
}
예제 #8
0
파일: sesman.c 프로젝트: speidy/xrdp
/**
 *
 * @brief Starts sesman main loop
 *
 */
static void DEFAULT_CC
sesman_main_loop(void)
{
    int in_sck;
    int error;
    int robjs_count;
    int cont;
    tbus sck_obj;
    tbus robjs[8];

    g_sck = g_tcp_socket();
    if (g_sck < 0)
    {
        log_message(LOG_LEVEL_ERROR, "error opening socket, g_tcp_socket() failed...");
        return;
    }

    g_tcp_set_non_blocking(g_sck);
    error = scp_tcp_bind(g_sck, g_cfg->listen_address, g_cfg->listen_port);

    if (error == 0)
    {
        error = g_tcp_listen(g_sck);

        if (error == 0)
        {
            log_message(LOG_LEVEL_INFO, "listening to port %s on %s",
                        g_cfg->listen_port, g_cfg->listen_address);
            sck_obj = g_create_wait_obj_from_socket(g_sck, 0);
            cont = 1;

            while (cont)
            {
                /* build the wait obj list */
                robjs_count = 0;
                robjs[robjs_count++] = sck_obj;
                robjs[robjs_count++] = g_term_event;

                /* wait */
                if (g_obj_wait(robjs, robjs_count, 0, 0, -1) != 0)
                {
                    /* error, should not get here */
                    g_sleep(100);
                }

                if (g_is_wait_obj_set(g_term_event)) /* term */
                {
                    break;
                }

                if (g_is_wait_obj_set(sck_obj)) /* incoming connection */
                {
                    in_sck = g_tcp_accept(g_sck);

                    if ((in_sck == -1) && g_tcp_last_error_would_block(g_sck))
                    {
                        /* should not get here */
                        g_sleep(100);
                    }
                    else if (in_sck == -1)
                    {
                        /* error, should not get here */
                        break;
                    }
                    else
                    {
                        /* we've got a connection, so we pass it to scp code */
                        LOG_DBG("new connection");
                        scp_process_start((void*)(tintptr)in_sck);
                        g_sck_close(in_sck);
                    }
                }
            }

            g_delete_wait_obj_from_socket(sck_obj);
        }
        else
        {
            log_message(LOG_LEVEL_ERROR, "listen error %d (%s)",
                        g_get_errno(), g_get_strerror());
        }
    }
    else
    {
        log_message(LOG_LEVEL_ERROR, "bind error on "
                    "port '%s': %d (%s)", g_cfg->listen_port,
                    g_get_errno(), g_get_strerror());
    }
    g_tcp_close(g_sck);
}
예제 #9
0
파일: xrdp_process.c 프로젝트: speidy/xrdp
int APP_CC
xrdp_process_main_loop(struct xrdp_process *self)
{
    int robjs_count;
    int wobjs_count;
    int cont;
    int timeout = 0;
    tbus robjs[32];
    tbus wobjs[32];
    tbus term_obj;

    DEBUG(("xrdp_process_main_loop"));
    self->status = 1;
    self->server_trans->extra_flags = 0;
    self->server_trans->header_size = 0;
    self->server_trans->no_stream_init_on_data_in = 1;
    self->server_trans->trans_data_in = xrdp_process_data_in;
    self->server_trans->callback_data = self;
    init_stream(self->server_trans->in_s, 8192 * 4);
    self->session = libxrdp_init((tbus)self, self->server_trans);
    self->server_trans->si = &(self->session->si);
    self->server_trans->my_source = XRDP_SOURCE_CLIENT;
    /* this callback function is in xrdp_wm.c */
    self->session->callback = callback;
    /* this function is just above */
    self->session->is_term = xrdp_is_term;

    if (libxrdp_process_incoming(self->session) == 0)
    {
        init_stream(self->server_trans->in_s, 32 * 1024);

        term_obj = g_get_term_event();
        cont = 1;

        while (cont)
        {
            /* build the wait obj list */
            timeout = -1;
            robjs_count = 0;
            wobjs_count = 0;
            robjs[robjs_count++] = term_obj;
            robjs[robjs_count++] = self->self_term_event;
            xrdp_wm_get_wait_objs(self->wm, robjs, &robjs_count,
                                  wobjs, &wobjs_count, &timeout);
            trans_get_wait_objs_rw(self->server_trans, robjs, &robjs_count,
                                   wobjs, &wobjs_count, &timeout);
            /* wait */
            if (g_obj_wait(robjs, robjs_count, wobjs, wobjs_count, timeout) != 0)
            {
                /* error, should not get here */
                g_sleep(100);
            }

            if (g_is_wait_obj_set(term_obj)) /* term */
            {
                break;
            }

            if (g_is_wait_obj_set(self->self_term_event))
            {
                break;
            }

            if (xrdp_wm_check_wait_objs(self->wm) != 0)
            {
                break;
            }

            if (trans_check_wait_objs(self->server_trans) != 0)
            {
                break;
            }
        }
        /* send disconnect message if possible */
        libxrdp_disconnect(self->session);
    }
    else
    {
        g_writeln("xrdp_process_main_loop: libxrdp_process_incoming failed");
        /* this will try to send a disconnect,
           maybe should check that connection got far enough */
        libxrdp_disconnect(self->session);
    }
    /* Run end in module */
    xrdp_process_mod_end(self);
    libxrdp_exit(self->session);
    self->session = 0;
    self->status = -1;
    g_set_wait_obj(self->done_event);
    return 0;
}
예제 #10
0
/* wait for incoming connections */
int APP_CC
xrdp_listen_main_loop(struct xrdp_listen* self)
{
  int error;
  int robjs_count;
  int cont;
  int timeout = 0;
  char port[8];
  char address[256];
  tbus robjs[8];
  tbus term_obj;
  tbus sync_obj;
  tbus sck_obj;
  tbus done_obj;

  self->status = 1;
  if (xrdp_listen_get_port_address(port, sizeof(port),
                                   address, sizeof(address)) != 0)
  {
    g_writeln("xrdp_listen_main_loop: xrdp_listen_get_port failed");
    self->status = -1;
    return 1;
  }
  error = trans_listen_address(self->listen_trans, port, address);
  if (error == 0)
  {
    self->listen_trans->trans_conn_in = xrdp_listen_conn_in;
    self->listen_trans->callback_data = self;
    term_obj = g_get_term_event();
    sync_obj = g_get_sync_event();
    done_obj = self->pro_done_event;
    cont = 1;
    while (cont)
    {
      /* build the wait obj list */
      robjs_count = 0;
      robjs[robjs_count++] = term_obj;
      robjs[robjs_count++] = sync_obj;
      robjs[robjs_count++] = done_obj;
      timeout = -1;
      if (trans_get_wait_objs(self->listen_trans, robjs, &robjs_count,
                              &timeout) != 0)
      {
        break;
      }
      /* wait */
      if (g_obj_wait(robjs, robjs_count, 0, 0, timeout) != 0)
      {
        /* error, should not get here */
        g_sleep(100);
      }
      if (g_is_wait_obj_set(term_obj)) /* term */
      {
        break;
      }
      if (g_is_wait_obj_set(sync_obj)) /* sync */
      {
        g_reset_wait_obj(sync_obj);
        g_loop();
      }
      if (g_is_wait_obj_set(done_obj)) /* pro_done_event */
      {
        g_reset_wait_obj(done_obj);
        xrdp_listen_delete_done_pro(self);
      }
      if (trans_check_wait_objs(self->listen_trans) != 0)
      {
        break;  
      }
    }
    /* stop listening */
    trans_delete(self->listen_trans);
    self->listen_trans = 0;
    /* second loop to wait for all process threads to close */
    cont = 1;
    while (cont)
    {
      if (self->process_list->count == 0)
      {
        break;
      }
      /* build the wait obj list */
      robjs_count = 0;
      robjs[robjs_count++] = sync_obj;
      robjs[robjs_count++] = done_obj;
      /* wait */
      if (g_obj_wait(robjs, robjs_count, 0, 0, -1) != 0)
      {
        /* error, should not get here */
        g_sleep(100);
      }
      if (g_is_wait_obj_set(sync_obj)) /* sync */
      {
        g_reset_wait_obj(sync_obj);
        g_loop();
      }
      if (g_is_wait_obj_set(done_obj)) /* pro_done_event */
      {
        g_reset_wait_obj(done_obj);
        xrdp_listen_delete_done_pro(self);
      }
    }
  }
  else
  {
    DEBUG(("listen error in xrdp_listen_main_loop"));
  }
  self->status = -1;
  return 0;
}
예제 #11
0
파일: chansrv.c 프로젝트: eric011/xrdp
THREAD_RV THREAD_CC
channel_thread_loop(void *in_val)
{
    tbus objs[32];
    int num_objs;
    int timeout;
    int error;
    THREAD_RV rv;

    LOGM((LOG_LEVEL_INFO, "channel_thread_loop: thread start"));
    rv = 0;
    setup_api_listen();
    error = setup_listen();

    if (error == 0)
    {
        timeout = -1;
        num_objs = 0;
        objs[num_objs] = g_term_event;
        num_objs++;
        trans_get_wait_objs(g_lis_trans, objs, &num_objs);
        trans_get_wait_objs(g_api_lis_trans, objs, &num_objs);

        while (g_obj_wait(objs, num_objs, 0, 0, timeout) == 0)
        {
            if (g_is_wait_obj_set(g_term_event))
            {
                LOGM((LOG_LEVEL_INFO, "channel_thread_loop: g_term_event set"));
                clipboard_deinit();
                sound_deinit();
                dev_redir_deinit();
                rail_deinit();
                break;
            }

            if (g_lis_trans != 0)
            {
                if (trans_check_wait_objs(g_lis_trans) != 0)
                {
                    LOGM((LOG_LEVEL_INFO, "channel_thread_loop: "
                          "trans_check_wait_objs error"));
                }
            }

            if (g_con_trans != 0)
            {
                if (trans_check_wait_objs(g_con_trans) != 0)
                {
                    LOGM((LOG_LEVEL_INFO, "channel_thread_loop: "
                          "trans_check_wait_objs error resetting"));
                    clipboard_deinit();
                    sound_deinit();
                    dev_redir_deinit();
                    rail_deinit();
                    /* delete g_con_trans */
                    trans_delete(g_con_trans);
                    g_con_trans = 0;
                    /* create new listener */
                    error = setup_listen();

                    if (error != 0)
                    {
                        break;
                    }
                }
            }

            if (g_api_lis_trans != 0)
            {
                if (trans_check_wait_objs(g_api_lis_trans) != 0)
                {
                    LOG(0, ("channel_thread_loop: trans_check_wait_objs failed"));
                }
            }

            LOG(10, ("0 %p", g_api_con_trans));

            if (g_api_con_trans != 0)
            {
                LOG(10, ("1 %p %d", g_api_con_trans, g_tcp_can_recv(g_api_con_trans->sck, 0)));

                if (trans_check_wait_objs(g_api_con_trans) != 0)
                {
                    LOG(10, ("channel_thread_loop: trans_check_wait_objs failed, "
                             "or disconnected"));
                    g_free(g_api_con_trans->callback_data);
                    trans_delete(g_api_con_trans);
                    g_api_con_trans = 0;
                }
            }

            xcommon_check_wait_objs();
            sound_check_wait_objs();
            dev_redir_check_wait_objs();
            fuse_check_wait_objs();
            timeout = -1;
            num_objs = 0;
            objs[num_objs] = g_term_event;
            num_objs++;
            trans_get_wait_objs(g_lis_trans, objs, &num_objs);
            trans_get_wait_objs(g_con_trans, objs, &num_objs);
            trans_get_wait_objs(g_api_lis_trans, objs, &num_objs);
            trans_get_wait_objs(g_api_con_trans, objs, &num_objs);
            xcommon_get_wait_objs(objs, &num_objs, &timeout);
            sound_get_wait_objs(objs, &num_objs, &timeout);
            dev_redir_get_wait_objs(objs, &num_objs, &timeout);
            fuse_get_wait_objs(objs, &num_objs, &timeout);
        }
    }

    trans_delete(g_lis_trans);
    g_lis_trans = 0;
    trans_delete(g_con_trans);
    g_con_trans = 0;
    trans_delete(g_api_lis_trans);
    g_api_lis_trans = 0;
    trans_delete(g_api_con_trans);
    g_api_con_trans = 0;
    LOGM((LOG_LEVEL_INFO, "channel_thread_loop: thread stop"));
    g_set_wait_obj(g_thread_done_event);
    return rv;
}
예제 #12
0
파일: chansrv.c 프로젝트: eric011/xrdp
int DEFAULT_CC
main(int argc, char **argv)
{
    tbus waiters[4];
    int pid = 0;
    char text[256];
    char *home_text;
    char *display_text;
    char log_file[256];
    enum logReturns error;
    struct log_config logconfig;

    g_init("xrdp-chansrv"); /* os_calls */

    home_text = g_getenv("HOME");

    if (home_text == 0)
    {
        g_writeln("error reading HOME environment variable");
        g_deinit();
        return 1;
    }

    read_ini();
    pid = g_getpid();

    /* starting logging subsystem */
    g_memset(&logconfig, 0, sizeof(struct log_config));
    logconfig.program_name = "XRDP-Chansrv";
    g_snprintf(log_file, 255, "%s/xrdp-chansrv.log", home_text);
    g_writeln("chansrv::main: using log file [%s]", log_file);

    if (g_file_exist(log_file))
    {
        g_file_delete(log_file);
    }

    logconfig.log_file = log_file;
    logconfig.fd = -1;
    logconfig.log_level = LOG_LEVEL_ERROR;
    logconfig.enable_syslog = 0;
    logconfig.syslog_level = 0;
    error = log_start_from_param(&logconfig);

    if (error != LOG_STARTUP_OK)
    {
        switch (error)
        {
            case LOG_ERROR_MALLOC:
                g_writeln("error on malloc. cannot start logging. quitting.");
                break;
            case LOG_ERROR_FILE_OPEN:
                g_writeln("error opening log file [%s]. quitting.",
                          getLogFile(text, 255));
                break;
            default:
                g_writeln("log_start error");
                break;
        }

        g_deinit();
        return 1;
    }

    LOGM((LOG_LEVEL_ALWAYS, "main: app started pid %d(0x%8.8x)", pid, pid));
    /*  set up signal handler  */
    g_signal_kill(term_signal_handler); /* SIGKILL */
    g_signal_terminate(term_signal_handler); /* SIGTERM */
    g_signal_user_interrupt(term_signal_handler); /* SIGINT */
    g_signal_pipe(nil_signal_handler); /* SIGPIPE */
    g_signal_child_stop(child_signal_handler); /* SIGCHLD */
    display_text = g_getenv("DISPLAY");
    LOGM((LOG_LEVEL_INFO, "main: DISPLAY env var set to %s", display_text));
    get_display_num_from_display(display_text);

    if (g_display_num == 0)
    {
        LOGM((LOG_LEVEL_ERROR, "main: error, display is zero"));
        g_deinit();
        return 1;
    }

    LOGM((LOG_LEVEL_INFO, "main: using DISPLAY %d", g_display_num));
    g_snprintf(text, 255, "xrdp_chansrv_%8.8x_main_term", pid);
    g_term_event = g_create_wait_obj(text);
    g_snprintf(text, 255, "xrdp_chansrv_%8.8x_thread_done", pid);
    g_thread_done_event = g_create_wait_obj(text);
    g_snprintf(text, 255, "xrdp_chansrv_%8.8x_exec", pid);
    g_exec_event = g_create_wait_obj(text);
    g_exec_mutex = tc_mutex_create();
    g_exec_sem = tc_sem_create(0);
    tc_thread_create(channel_thread_loop, 0);

    while (g_term_event > 0 && !g_is_wait_obj_set(g_term_event))
    {
        waiters[0] = g_term_event;
        waiters[1] = g_exec_event;

        if (g_obj_wait(waiters, 2, 0, 0, 0) != 0)
        {
            LOGM((LOG_LEVEL_ERROR, "main: error, g_obj_wait failed"));
            break;
        }

        if (g_is_wait_obj_set(g_term_event))
        {
            break;
        }

        if (g_is_wait_obj_set(g_exec_event))
        {
            g_reset_wait_obj(g_exec_event);
            run_exec();
        }
    }

    while (g_thread_done_event > 0 && !g_is_wait_obj_set(g_thread_done_event))
    {
        /* wait for thread to exit */
        if (g_obj_wait(&g_thread_done_event, 1, 0, 0, 0) != 0)
        {
            LOGM((LOG_LEVEL_ERROR, "main: error, g_obj_wait failed"));
            break;
        }
    }

    /* cleanup */
    main_cleanup();
    LOGM((LOG_LEVEL_INFO, "main: app exiting pid %d(0x%8.8x)", pid, pid));
    g_deinit();
    return 0;
}