Example #1
0
static void
cockpit_auth_remote_login_async (CockpitAuth *self,
                                 GHashTable *headers,
                                 const gchar *remote_peer,
                                 GAsyncReadyCallback callback,
                                 gpointer user_data)
{
  GSimpleAsyncResult *task;
  CockpitCreds *creds = NULL;
  RemoteLoginData *rl;
  const gchar *password;
  GBytes *input;
  gchar *type = NULL;
  gchar *user = NULL;

  task = g_simple_async_result_new (G_OBJECT (self), callback, user_data,
                                    cockpit_auth_remote_login_async);

  input = cockpit_auth_parse_authorization (headers, &type);

  if (type && input && g_str_equal (type, "basic"))
    {
      password = parse_basic_auth_password (input, &user);
      if (password && user)
        {
          creds = cockpit_creds_new (user,
                                     COCKPIT_CRED_PASSWORD, password,
                                     COCKPIT_CRED_RHOST, remote_peer,
                                     NULL);
        }
      g_free (user);
    }

  if (creds)
    {
      rl = g_new0 (RemoteLoginData, 1);
      rl->creds = creds;
      rl->transport = g_object_new (COCKPIT_TYPE_SSH_TRANSPORT,
                                    "host", "127.0.0.1",
                                    "port", cockpit_ws_specific_ssh_port,
                                    "command", cockpit_ws_bridge_program,
                                    "creds", creds,
                                    "ignore-key", TRUE,
                                    NULL);

      g_simple_async_result_set_op_res_gpointer (task, rl, remote_login_data_free);
      g_signal_connect (rl->transport, "result", G_CALLBACK (on_remote_login_done), g_object_ref (task));
    }
  else
    {
      g_simple_async_result_set_error (task, COCKPIT_ERROR, COCKPIT_ERROR_AUTHENTICATION_FAILED,
                                       "Basic authentication required");
      g_simple_async_result_complete_in_idle (task);
    }

  g_free (type);
  g_object_unref (task);
}
Example #2
0
static void
cockpit_auth_session_login_async (CockpitAuth *self,
                                  const gchar *path,
                                  GHashTable *headers,
                                  const gchar *remote_peer,
                                  GAsyncReadyCallback callback,
                                  gpointer user_data)
{
  GSimpleAsyncResult *result;
  SessionLoginData *sl;
  GBytes *input;
  gchar *application;
  gchar *type = NULL;

  result = g_simple_async_result_new (G_OBJECT (self), callback, user_data,
                                      cockpit_auth_session_login_async);

  application = cockpit_auth_parse_application (path);
  input = cockpit_auth_parse_authorization (headers, &type);

  if (input && application)
    {
      sl = g_new0 (SessionLoginData, 1);
      sl->remote_peer = g_strdup (remote_peer);
      sl->auth_type = type;
      sl->authorization = g_bytes_ref (input);
      sl->application = application;
      application = NULL;

      g_simple_async_result_set_op_res_gpointer (result, sl, session_login_data_free);

      sl->session_pipe = spawn_session_process (type, input, remote_peer, &sl->auth_pipe);

      if (sl->session_pipe)
        {
          g_signal_connect (sl->auth_pipe, "close",
                            G_CALLBACK (on_session_login_done), g_object_ref (result));
        }
      else
        {
          g_simple_async_result_set_error (result, COCKPIT_ERROR, COCKPIT_ERROR_FAILED,
                                           "Internal error starting session process");
          g_simple_async_result_complete_in_idle (result);
        }
    }
  else
    {
      g_free (type);
      g_simple_async_result_set_error (result, COCKPIT_ERROR, COCKPIT_ERROR_AUTHENTICATION_FAILED,
                                       "Authentication required");
      g_simple_async_result_complete_in_idle (result);
    }

  g_bytes_unref (input);
  g_free (application);
  g_object_unref (result);
}
Example #3
0
static void
cockpit_auth_spawn_login_async (CockpitAuth *self,
                                const gchar *application,
                                const gchar *type,
                                gboolean decode_header,
                                GHashTable *headers,
                                const gchar *remote_peer,
                                GAsyncReadyCallback callback,
                                gpointer user_data)
{
  GSimpleAsyncResult *result;
  GBytes *input = NULL;
  AuthData *ad = NULL;
  const gchar *command;

  const gchar *argv[] = {
      "command",
      type,
      remote_peer ? remote_peer : "",
      NULL,
  };

  result = g_simple_async_result_new (G_OBJECT (self), callback, user_data,
                                      cockpit_auth_spawn_login_async);

  command = type_option (type, "command", cockpit_ws_session_program);

  input = cockpit_auth_parse_authorization (headers, decode_header);
  if (!input && !gssapi_not_avail && g_strcmp0 (type, "negotiate") == 0)
    input = g_bytes_new_static ("", 0);

  if (input && application)
    {
      argv[0] = command;
      ad = create_auth_data (self, "localhost", application,
                             type, remote_peer, command, input);
      start_auth_process (self, ad, input, result,
                          cockpit_auth_spawn_login_async, argv);
    }
  else
    {
      g_simple_async_result_set_error (result, COCKPIT_ERROR, COCKPIT_ERROR_AUTHENTICATION_FAILED,
                                       "Authentication required");
      g_simple_async_result_complete_in_idle (result);
    }

  if (input)
    g_bytes_unref (input);

  if (ad)
    auth_data_unref (ad);

  g_object_unref (result);
}
Example #4
0
static void
cockpit_auth_remote_login_async (CockpitAuth *self,
                                 const gchar *application,
                                 const gchar *type,
                                 GHashTable *headers,
                                 const gchar *remote_peer,
                                 GAsyncReadyCallback callback,
                                 gpointer user_data)
{
  GSimpleAsyncResult *task;
  AuthData *ad = NULL;
  GBytes *input = NULL;
  GBytes *auth_bytes = NULL;
  gchar *user = NULL;
  gchar *password = NULL; /* owned by input */

  const gchar *data = NULL;
  const gchar *command;
  const gchar *host;
  const gchar *host_arg;
  gint next_arg = 1;

  const gchar *argv[] = {
      cockpit_ws_ssh_program,
      NULL,
      NULL,
      NULL,
      NULL,
      NULL,
      NULL,
  };

  task = g_simple_async_result_new (G_OBJECT (self), callback, user_data,
                                    cockpit_auth_remote_login_async);
  if (g_strcmp0 (type, "basic") == 0)
    {
      input = cockpit_auth_parse_authorization (headers, TRUE);
      data = g_bytes_get_data (input, NULL);

      password = strchr (data, ':');
      if (password != NULL)
        {
          user = g_strndup (data, password - data);
          password++;
          auth_bytes = g_bytes_new_static (password, strlen(password));
        }
    }
  else
    {
      input = cockpit_auth_parse_authorization (headers, FALSE);
      if (input)
        auth_bytes = g_bytes_ref (input);
    }

  if (application && auth_bytes && input)
    {
      command = type_option (SSH_SECTION, "command", cockpit_ws_ssh_program);
      argv[0] = command;

      host = application_parse_host (application);
      if (host)
        {
          host_arg = host;
          if (g_strcmp0 (remote_peer, "127.0.0.1") == 0 ||
              g_strcmp0 (remote_peer, "::1") == 0 ||
              cockpit_conf_bool (SSH_SECTION, "allowUnknown", FALSE))
            {
              argv[next_arg++] = "--prompt-unknown-hostkey";
            }
        }
      else
        {
          argv[next_arg++] = "--ignore-hostkey";
          if (cockpit_conf_string (SSH_SECTION, "host"))
            host_arg = cockpit_conf_string (SSH_SECTION, "host");
          else
            host_arg = "localhost";
        }

      argv[next_arg++] = host_arg;
      argv[next_arg++] = user;
      ad = create_auth_data (self, host_arg, application,
                             SSH_SECTION, remote_peer, command, input);
      start_auth_process (self, ad, auth_bytes, task,
                          cockpit_auth_remote_login_async, argv);
    }
  else
    {
      g_simple_async_result_set_error (task, COCKPIT_ERROR, COCKPIT_ERROR_AUTHENTICATION_FAILED,
                                       "Basic authentication required");
      g_simple_async_result_complete_in_idle (task);
    }

  if (auth_bytes)
    g_bytes_unref (auth_bytes);

  if (input)
    g_bytes_unref (input);

  if (ad)
    auth_data_unref (ad);

  if (user)
    g_free (user);

  g_object_unref (task);
}