Commit 965f5075 authored by Thomas Guillem's avatar Thomas Guillem

keystore: add a unique memory keystore

This keystore is used to store credentials on memory if no others keystore is
found or if the user doesn't want to store them permanently. This keystore is
owned by libvlc and is shared with all vlc objects. It's released when the
libvlc instance is released.
parent 394b4bf7
......@@ -27,6 +27,14 @@ typedef struct vlc_keystore vlc_keystore;
typedef struct vlc_keystore_entry vlc_keystore_entry;
typedef struct vlc_credential vlc_credential;
/* Called from src/libvlc.c */
int
libvlc_InternalKeystoreInit(libvlc_int_t *p_libvlc);
/* Called from src/libvlc.c */
void
libvlc_InternalKeystoreClean(libvlc_int_t *p_libvlc);
/**
* @defgroup keystore Keystore and credential API
* @{
......@@ -168,6 +176,7 @@ struct vlc_credential
enum {
GET_FROM_URL,
GET_FROM_OPTION,
GET_FROM_MEMORY_KEYSTORE,
GET_FROM_KEYSTORE,
GET_FROM_DIALOG,
} i_get_order;
......@@ -242,7 +251,9 @@ vlc_credential_get(vlc_credential *p_credential, vlc_object_t *p_parent,
* otherwise
*/
VLC_API bool
vlc_credential_store(vlc_credential *p_credential);
vlc_credential_store(vlc_credential *p_credential, vlc_object_t *p_parent);
#define vlc_credential_store(a, b) \
vlc_credential_store(a, VLC_OBJECT(b))
/**
* @}
......
......@@ -384,7 +384,7 @@ success:
credential.psz_realm ) == -1 )
p_sys->psz_domain_opt = NULL;
if( !vlc_credential_store( &credential )
if( !vlc_credential_store( &credential, p_access )
&& asprintf( &p_sys->psz_pwd_opt, "smb-pwd=%s", psz_password ) == -1 )
p_sys->psz_pwd_opt = NULL;
}
......
......@@ -427,7 +427,7 @@ static int Login( vlc_object_t *p_access, access_sys_t *p_sys )
&& !b_logged );
if( b_logged )
{
vlc_credential_store( &credential );
vlc_credential_store( &credential, p_access );
vlc_credential_clean( &credential );
vlc_UrlClean( &url );
return 0;
......
......@@ -407,7 +407,7 @@ connect:
goto error;
}
else
vlc_credential_store( &credential );
vlc_credential_store( &credential, p_access );
if( ( p_sys->i_code == 301 || p_sys->i_code == 302 ||
p_sys->i_code == 303 || p_sys->i_code == 307 ) &&
......
......@@ -680,7 +680,7 @@ describe:
i_ret = VLC_EGENERIC;
}
else
vlc_credential_store( &credential );
vlc_credential_store( &credential, p_demux );
bailout:
/* malloc-ated copy */
......
......@@ -223,7 +223,7 @@ static int Open( vlc_object_t* p_this )
credential.psz_username,
credential.psz_password ) == 0 )
{
b_stored = vlc_credential_store( &credential );
b_stored = vlc_credential_store( &credential, p_access );
break;
}
else
......
......@@ -211,7 +211,7 @@ static int Open( vlc_object_t *p_this )
break;
}
vlc_credential_store( &credential );
vlc_credential_store( &credential, p_access );
vlc_credential_clean( &credential );
free(psz_var_domain);
vlc_UrlClean( &url );
......
......@@ -62,6 +62,7 @@
#include <vlc_charset.h>
#include <vlc_dialog.h>
#include <vlc_keystore.h>
#include <vlc_fs.h>
#include <vlc_cpu.h>
#include <vlc_url.h>
......@@ -241,6 +242,8 @@ int libvlc_InternalInit( libvlc_int_t *p_libvlc, int i_argc,
module_EndBank (true);
return VLC_ENOMEM;
}
if( libvlc_InternalKeystoreInit( p_libvlc ) != VLC_SUCCESS )
msg_Warn( p_libvlc, "memory keystore init failed" );
/* FIXME: could be replaced by using Unix sockets */
#ifdef HAVE_DBUS
......@@ -511,6 +514,7 @@ void libvlc_InternalCleanup( libvlc_int_t *p_libvlc )
intf_DestroyAll( p_libvlc );
libvlc_InternalDialogClean( p_libvlc );
libvlc_InternalKeystoreClean( p_libvlc );
#ifdef ENABLE_VLM
/* Destroy VLM if created in libvlc_InternalInit */
......
......@@ -134,6 +134,7 @@ void vlc_object_set_destructor (vlc_object_t *, vlc_destructor_t);
* Private LibVLC instance data.
*/
typedef struct vlc_dialog_provider vlc_dialog_provider;
typedef struct vlc_keystore vlc_keystore;
typedef struct libvlc_priv_t
{
......@@ -146,6 +147,7 @@ typedef struct libvlc_priv_t
vlc_logger_t *logger;
vlm_t *p_vlm; ///< the VLM singleton (or NULL)
vlc_dialog_provider *p_dialog_provider; ///< dialog provider
vlc_keystore *p_memory_keystore; ///< memory keystore
struct playlist_t *playlist; ///< Playlist for interfaces
struct playlist_preparser_t *parser; ///< Input item meta data handler
struct vlc_actions *actions; ///< Hotkeys handler
......
......@@ -224,6 +224,8 @@ intf_Create
libvlc_InternalAddIntf
libvlc_InternalDialogInit
libvlc_InternalDialogClean
libvlc_InternalKeystoreInit
libvlc_InternalKeystoreClean
libvlc_InternalPlay
libvlc_InternalCleanup
libvlc_InternalCreate
......
......@@ -32,18 +32,15 @@
#include <assert.h>
#include <limits.h>
#undef vlc_keystore_create
vlc_keystore *
vlc_keystore_create(vlc_object_t *p_parent)
static vlc_keystore *
keystore_create(vlc_object_t *p_parent, const char *psz_name)
{
assert(p_parent);
vlc_keystore *p_keystore = vlc_custom_create(p_parent, sizeof (*p_keystore),
"keystore");
if (unlikely(p_keystore == NULL))
return NULL;
p_keystore->p_module = module_need(p_keystore, "keystore", "$keystore",
true);
p_keystore->p_module = module_need(p_keystore, "keystore", psz_name, true);
if (p_keystore->p_module == NULL)
{
vlc_object_release(p_keystore);
......@@ -56,6 +53,14 @@ vlc_keystore_create(vlc_object_t *p_parent)
return p_keystore;
}
#undef vlc_keystore_create
vlc_keystore *
vlc_keystore_create(vlc_object_t *p_parent)
{
assert(p_parent);
return keystore_create(p_parent, "$keystore");
}
void
vlc_keystore_release(vlc_keystore *p_keystore)
{
......@@ -120,6 +125,35 @@ vlc_keystore_release_entries(vlc_keystore_entry *p_entries, unsigned int i_count
free(p_entries);
}
int
libvlc_InternalKeystoreInit(libvlc_int_t *p_libvlc)
{
assert(p_libvlc != NULL);
libvlc_priv_t *p_priv = libvlc_priv(p_libvlc);
p_priv->p_memory_keystore = keystore_create(VLC_OBJECT(p_libvlc), "memory");
return p_priv->p_memory_keystore != NULL ? VLC_SUCCESS : VLC_EGENERIC;
}
void
libvlc_InternalKeystoreClean(libvlc_int_t *p_libvlc)
{
assert(p_libvlc != NULL);
libvlc_priv_t *p_priv = libvlc_priv(p_libvlc);
if (p_priv->p_memory_keystore != NULL)
{
vlc_keystore_release(p_priv->p_memory_keystore);
p_priv->p_memory_keystore = NULL;
}
}
static vlc_keystore *
get_memory_keystore(vlc_object_t *p_obj)
{
return libvlc_priv(p_obj->p_libvlc)->p_memory_keystore;
}
static vlc_keystore_entry *
find_closest_path(vlc_keystore_entry *p_entries, unsigned i_count,
const char *psz_path)
......@@ -231,7 +265,7 @@ smb_split_domain(vlc_credential *p_credential)
}
static void
credential_find_keystore(vlc_credential *p_credential)
credential_find_keystore(vlc_credential *p_credential, vlc_keystore *p_keystore)
{
const vlc_url_t *p_url = p_credential->p_url;
......@@ -249,16 +283,18 @@ credential_find_keystore(vlc_credential *p_credential)
ppsz_values[KEY_PORT] = psz_port;
}
vlc_keystore_entry *p_entries;
unsigned int i_entries_count;
i_entries_count = vlc_keystore_find(p_keystore, ppsz_values, &p_entries);
/* Remove last entries after vlc_keystore_find call since
* p_credential->psz_username (default username) can be a pointer to an
* entry */
if (p_credential->i_entries_count > 0)
{
vlc_keystore_release_entries(p_credential->p_entries,
p_credential->i_entries_count);
p_credential->i_entries_count = 0;
}
p_credential->i_entries_count = vlc_keystore_find(p_credential->p_keystore,
ppsz_values,
&p_credential->p_entries);
p_credential->p_entries = p_entries;
p_credential->i_entries_count = i_entries_count;
if (p_credential->i_entries_count > 0)
{
......@@ -298,13 +334,11 @@ vlc_credential_init(vlc_credential *p_credential, const vlc_url_t *p_url)
void
vlc_credential_clean(vlc_credential *p_credential)
{
if (p_credential->i_entries_count > 0)
vlc_keystore_release_entries(p_credential->p_entries,
p_credential->i_entries_count);
if (p_credential->p_keystore)
{
if (p_credential->i_entries_count > 0)
vlc_keystore_release_entries(p_credential->p_entries,
p_credential->i_entries_count);
vlc_keystore_release(p_credential->p_keystore);
}
free(p_credential->psz_split_realm);
free(p_credential->psz_var_username);
......@@ -378,6 +412,18 @@ vlc_credential_get(vlc_credential *p_credential, vlc_object_t *p_parent,
p_credential->i_get_order++;
break;
case GET_FROM_MEMORY_KEYSTORE:
{
if (!psz_dialog_title || !psz_dialog_fmt)
return false;
vlc_keystore *p_keystore = get_memory_keystore(p_parent);
if (p_keystore != NULL)
credential_find_keystore(p_credential, p_keystore);
p_credential->i_get_order++;
break;
}
case GET_FROM_KEYSTORE:
if (!psz_dialog_title || !psz_dialog_fmt)
return false;
......@@ -385,7 +431,7 @@ vlc_credential_get(vlc_credential *p_credential, vlc_object_t *p_parent,
if (p_credential->p_keystore == NULL)
p_credential->p_keystore = vlc_keystore_create(p_parent);
if (p_credential->p_keystore != NULL)
credential_find_keystore(p_credential);
credential_find_keystore(p_credential, p_credential->p_keystore);
p_credential->i_get_order++;
break;
......@@ -434,13 +480,29 @@ vlc_credential_get(vlc_credential *p_credential, vlc_object_t *p_parent,
return is_credential_valid(p_credential);
}
#undef vlc_credential_store
bool
vlc_credential_store(vlc_credential *p_credential)
vlc_credential_store(vlc_credential *p_credential, vlc_object_t *p_parent)
{
if (!p_credential->p_keystore || !p_credential->b_store
|| p_credential->b_from_keystore)
/* Don't need to store again */
if (p_credential->b_from_keystore)
return p_credential->b_from_keystore;
vlc_keystore *p_keystore;
if (p_credential->b_store)
{
/* Store in permanent keystore */
assert(p_credential->p_keystore != NULL);
p_keystore = p_credential->p_keystore;
}
else
{
/* Store in memory keystore */
p_keystore = get_memory_keystore(p_parent);
}
if (p_keystore == NULL)
return false;
const vlc_url_t *p_url = p_credential->p_url;
char *psz_path = NULL;
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment