From 628b01be310a80d34a699c9509f9491da252d50d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?R=C3=A9mi=20Denis-Courmont?= Date: Sun, 24 Mar 2013 19:11:07 +0200 Subject: [PATCH] core: remove media library support --- configure.ac | 11 - include/vlc_media_library.h | 1130 ----------------------------------- src/Makefile.am | 1 - src/libvlc-module.c | 4 - src/libvlc.c | 33 - src/libvlc.h | 2 - src/libvlccore.sym | 6 - src/misc/media_library.c | 417 ------------- src/missing.c | 71 --- 9 files changed, 1675 deletions(-) delete mode 100644 src/misc/media_library.c diff --git a/configure.ac b/configure.ac index 429c95b7a236..a19039c50d98 100644 --- a/configure.ac +++ b/configure.ac @@ -3959,17 +3959,6 @@ dnl Libnotify notification plugin dnl PKG_ENABLE_MODULES_VLC([NOTIFY], [], [libnotify gtk+-2.0], [libnotify notification], [auto]) -dnl -dnl media library -dnl -AC_ARG_ENABLE(media-library, - [ --enable-media-library media library (default disabled)]) -AS_IF([test "${enable_media_library}" = "yes"], [ - AC_DEFINE([MEDIA_LIBRARY], 1, [Define if you want to use the VLC media library]) - VLC_ADD_CPPFLAGS([qt4],"-DMEDIA_LIBRARY") -]) - - dnl dnl Endianness check dnl diff --git a/include/vlc_media_library.h b/include/vlc_media_library.h index d86f5fae8bea..a35d9729ca37 100644 --- a/include/vlc_media_library.h +++ b/include/vlc_media_library.h @@ -32,9 +32,6 @@ extern "C" { # endif -#include -#include - /***************************************************************************** * ML Enums *****************************************************************************/ @@ -45,8 +42,6 @@ extern "C" { #define ML_PERSON_PUBLISHER "Publisher" -#define ml_priv( gc, t ) ((t *)(((char *)(gc)) - offsetof(t, ml_gc_data))) - /** List of Query select types. * In a query array or variable argument list, each select type is followed * by an argument (X) of variable type (char* or int, @see ml_element_t). @@ -125,1131 +120,6 @@ typedef enum { ML_TYPE_MEDIA, /**< A pointer to a media ml_media_t* */ } ml_result_type_e; -/** Arguments for VLC Control for the media library */ -typedef enum -{ - ML_SET_DATABASE, /**< arg1 = char *psz_host - arg2 = int i_port - arg3 = char *psz_user - arg4 = char *psz_pass */ - ML_INIT_DATABASE, /**< No arg */ - ML_ADD_INPUT_ITEM, /**< arg1 = input_item_t* */ - ML_ADD_PLAYLIST_ITEM, /**< arg1 = playlist_item_t * */ - ML_ADD_MONITORED, /**< arg1 = char* */ - ML_DEL_MONITORED, /**< arg1 = char* */ - ML_GET_MONITORED, /**< arg1 = vlc_array_t* */ -} ml_control_e; - -/* Operations that can be specified between find conditions */ -typedef enum -{ - ML_OP_NONE = 0, /**< This is to specify an actual condition */ - ML_OP_AND, /**< AND condition */ - ML_OP_OR, /**< OR condition */ - ML_OP_NOT, /**< NOT condition */ - ML_OP_SPECIAL /**< This is for inclusion of - * special stuffs like LIMIT */ -} ml_op_e; - -/* Comparison operators used in a single find condition */ -typedef enum -{ - ML_COMP_NONE = 0, - ML_COMP_LESSER, ///< < - ML_COMP_LESSER_OR_EQUAL, ///< <= - ML_COMP_EQUAL, ///< == - ML_COMP_GREATER_OR_EQUAL, ///< >= - ML_COMP_GREATER, ///< > - ML_COMP_HAS, ///< "Contains", equivalent to SQL "LIKE %x%" - ML_COMP_STARTS_WITH, ///< Equivalent to SQL "LIKE %x" - ML_COMP_ENDS_WITH, ///< Equivalent to SQL "LIKE x%" -} ml_comp_e; - -/***************************************************************************** - * ML Structures and types - *****************************************************************************/ - -typedef struct media_library_t media_library_t; -typedef struct media_library_sys_t media_library_sys_t; - -typedef struct ml_media_t ml_media_t; -typedef struct ml_result_t ml_result_t; -typedef struct ml_element_t ml_element_t; -typedef struct ml_person_t ml_person_t; -typedef struct ml_ftree_t ml_ftree_t; - - -typedef struct ml_gc_object_t -{ - bool pool; - uintptr_t refs; - void (*pf_destructor) (struct ml_gc_object_t *); -} ml_gc_object_t; - -#define ML_GC_MEMBERS ml_gc_object_t ml_gc_data; - -/** Main structure of the media library. VLC object. */ -struct media_library_t -{ - VLC_COMMON_MEMBERS - - module_t *p_module; /**< the media library module */ - media_library_sys_t *p_sys; /**< internal struture */ - - /** Member functions */ - struct - { - /**< Search in the database */ - int ( * pf_Find ) ( media_library_t *p_media_library, - vlc_array_t *p_result_array, - va_list args ); - - /**< Search in the database using an array of arguments */ - int ( * pf_FindAdv ) ( media_library_t *p_media_library, - vlc_array_t *p_result_array, - ml_select_e selected_type, - const char *psz_lvalue, - ml_ftree_t *tree ); - - /**< Update the database using an array of arguments */ - int ( * pf_Update ) ( media_library_t *p_media_library, - ml_select_e selected_type, - const char *psz_lvalue, - ml_ftree_t *where, - vlc_array_t *changes ); - - /**< Delete many medias in the database */ - int ( * pf_Delete ) ( media_library_t *p_media_library, - vlc_array_t *p_array ); - - /**< Control the media library */ - int ( * pf_Control ) ( media_library_t *p_media_library, - int i_query, va_list args ); - - /**< Create associated input item */ - input_item_t* ( * pf_InputItemFromMedia ) ( - media_library_t *p_media_library, int i_media ); - - /**< Get a media */ - ml_media_t* ( * pf_GetMedia ) ( - media_library_t *p_media_library, int i_media, - ml_select_e select, bool reload ); - } functions; -}; - - -/** - * @brief Structure to describe a media - * - * This is the main structure holding the meta data in ML. - * @see b_sparse indicates whether the media struct has valid values - * in its Extra fields. Otherwise, it must be loaded with the API - * function. - * @see i_id indicates whether this struct is saved in the ML if i_id > 0 - * Otherwise, it can be added to the database - */ -struct ml_media_t -{ - ML_GC_MEMBERS - vlc_mutex_t lock; /**< Mutex for multithreaded access */ - bool b_sparse; /**< Specifies if media is loaded fully */ - ml_type_e i_type; /**< Type of the media (ml_type_e) */ - int8_t i_vote; /**< User vote */ - int16_t i_disc_number; /**< Disc number of media */ - int16_t i_track_number; /**< Track number */ - int16_t i_year; /**< Year of release */ - int32_t i_id; /**< Media ID in the database */ - int32_t i_score; /**< Score computed about the media */ - int32_t i_album_id; /**< Album id */ - int32_t i_played_count; /**< How many time the media was played */ - int32_t i_skipped_count; /**< No. of times file was skipped */ - int32_t i_bitrate; /**< Extra: Bitrate of the media */ - int32_t i_samplerate; /**< Extra: Samplerate of the media */ - int32_t i_bpm; /**< Extra: Beats per minute */ - char *psz_uri; /**< URI to find the media */ - char *psz_title; /**< Title of the media */ - char *psz_orig_title; /**< Original title (mainly for movies) */ - char *psz_album; /**< Name of the album */ - char *psz_cover; /**< URI of the cover */ - char *psz_genre; /**< Genre of the media */ - char *psz_preview; /**< Preview thumbnail for video, if any */ - char *psz_comment; /**< Comment or description about media */ - char *psz_language; /**< Extra: Language */ - char *psz_extra; /**< Extra: Some extra datas like lyrics */ - ml_person_t *p_people; /**< Extra: People associated with this - media This meta holds only one - artist if b_sparse = true */ - int64_t i_filesize; /**< Size of the file */ - mtime_t i_duration; /**< Duration in microseconds */ - mtime_t i_last_played; /**< Time when the media was last played */ - mtime_t i_last_skipped; /**< Time when the media was last skipped */ - mtime_t i_first_played; /**< First played */ - mtime_t i_import_time; /**< Time when media was added */ - -}; - - -/** - * @brief Main communication struct between GUI and sql_media_library. - * Generic representation of an ML/SQL query result. - */ -struct ml_result_t -{ - int32_t id; /**< Media/Album/Artist... ID (if any) */ - ml_result_type_e type; /**< Type of value */ - union - { - /* Classical results */ - int i; - char *psz; - mtime_t time; - - /* Complex result: media descriptor */ - ml_media_t *p_media; - } value; /**< Value of the result obtained */ -}; - - -/** - * @brief Element of a query: criteria type/value pair - * Used for update and delete queries - */ -struct ml_element_t -{ - ml_select_e criteria; /**< SELECT criteria type. @see ml_select_e */ - union - { - int i; - char* str; - } value; /**< SELECT criteria value (string or int) */ - union - { - int i; - char* str; - } lvalue; /**< Refer to @see ml_ftree_t lvalue docs */ -}; - -/** - * Binary tree used to parse the WHERE condition for a search - * - * Let [expr] indicate a valid expression - * [expr] = [expr] AND [expr], where the left and right are respective - * [expr] = [expr] OR [expr] - * [expr] = [expr] NOT [NULL] - * [expr] = [expr] SPEC [spec_expr] - * [expr] = [criteria=val] - * [spec_expr] = [DISTINCT/LIMIT/ASC/DESC = val ] - */ -struct ml_ftree_t -{ - ml_op_e op; /**< Operator. ML_OP_NONE means this is a leaf - * node. Criteria and value gives its data. - * ML_OP_SPECIAL specifies a special node - * that does not form a part of the WHERE. - * The right node consists of the data - * with its criteria set to the special val - * and the left node is the corresponding - * subtree of the parent node. - * ML_OP_NOT only left sub tree is considered - * ML_OP_AND and ML_OP_OR consider both - * left and right subtrees */ - ml_ftree_t *left; /**< Left child of Bin tree */ - ml_ftree_t *right; /**< Right child of Bin tree */ - ml_select_e criteria; /**< SELECT criteria type @see ml_select_e - * The criteria value is considered only when - * op = ML_OP_NONE i.e. in leaf nodes */ - ml_comp_e comp; /**< Condition between type and value */ - union - { - int i; - char *str; - } value; /**< SELECT criteria value ( string or int ) */ - union - { - int i; - char *str; - } lvalue; /**< Used as key value for people types/roles. - An empty string "" denotes ANY person role. - NULL is used for all other criterias */ -}; - - -/** - * Person class. Implemented as a linked list - */ -struct ml_person_t -{ - char *psz_role; /**< Type of person */ - char *psz_name; /**< Name of the person */ - int i_id; /**< ID in the database */ - ml_person_t *p_next; /**< Next person in list */ -}; - - -/***************************************************************************** - * ML Function headers - *****************************************************************************/ - -/** - * @brief Acquire a reference to the media library singleton - * @param p_this The object holding the media library - * @return The media library object. NULL if the media library - * object could not be loaded - */ -VLC_API media_library_t* ml_Get( vlc_object_t* p_this ); -#define ml_Get( a ) ml_Get( VLC_OBJECT(a) ) - -/** - * @brief Create a Media Library VLC object. - * @param p_this Parent to attach the ML object to. - * @param psz_name Name for the module - * @return The ML object. - */ -media_library_t* ml_Create( vlc_object_t *p_this, char* psz_name ); - -/** - * @brief Destructor for the Media library singleton - * @param p_this Parent the ML object is attached to - */ -void ml_Destroy( vlc_object_t* p_this ); - -/** - * @brief Control the Media Library - * @param p_media_library the media library object - * @param i_type one of ml_control_e values @see ml_control_e. - * @param ... optional arguments. - * @return VLC_SUCCESS or an error - */ -static inline int ml_ControlVa( media_library_t *p_media_library, - ml_control_e i_type, va_list args ) -{ - return p_media_library->functions.pf_Control( p_media_library, - i_type, - args ); -} - -/** - * @brief Control the Media Library - * @param i_type one of ml_control_e values @see ml_control_e. - * Variable arguments list equivalent - */ -#define ml_Control( a, b, args... ) __ml_Control( a, b, ## args ) -static inline int __ml_Control( media_library_t *p_media_library, - ml_control_e i_type, ... ) -{ - va_list args; - int returned; - - va_start( args, i_type ); - returned = ml_ControlVa( p_media_library, i_type, args ); - va_end( args ); - - return returned; -} - -/** - * @brief Determine an attribute's type (int or string) - * @param meta Attribute to test @see ml_select_e - * @return -1 if invalid, 0 if this is an integer, 1 if this is a string - */ -static inline int ml_AttributeIsString( ml_select_e meta ) -{ - switch( meta ) - { - /* Strings */ - case ML_ALBUM: - case ML_ARTIST: - case ML_COMMENT: - case ML_COVER: - case ML_EXTRA: - case ML_GENRE: - case ML_LANGUAGE: - case ML_PREVIEW: - case ML_PEOPLE: - case ML_PEOPLE_ROLE: - case ML_ORIGINAL_TITLE: - case ML_TITLE: - case ML_URI: - return 1; - - /* Integers */ - case ML_ALBUM_ID: - case ML_ARTIST_ID: - case ML_DURATION: - case ML_DISC_NUMBER: - case ML_COUNT_MEDIA: - case ML_COUNT_ALBUM: - case ML_COUNT_PEOPLE: - case ML_FILESIZE: - case ML_FIRST_PLAYED: - case ML_ID: - case ML_IMPORT_TIME: - case ML_LAST_PLAYED: - case ML_LIMIT: - case ML_PLAYED_COUNT: - case ML_PEOPLE_ID: - case ML_SCORE: - case ML_SKIPPED_COUNT: - case ML_TRACK_NUMBER: - case ML_TYPE: - case ML_VOTE: - case ML_YEAR: - return 0; - - /* Invalid or no following value (in a SELECT statement) */ - default: - return -1; - } -} - -/* Reference Counting Functions */ -/** - * @brief Increment reference count of media - * @param p_media The media object - */ -static inline void ml_gc_incref( ml_media_t* p_media ) -{ - ml_gc_object_t* p_gc = &p_media->ml_gc_data; - if( p_gc == NULL ) - return; - - ++p_gc->refs; -} - -/** - * @brief Decrease reference count of media - * @param p_media The media object - */ -static inline void ml_gc_decref( ml_media_t* p_media ) -{ - /* The below code is from vlc_release(). */ - unsigned refs; - bool pool; - ml_gc_object_t* p_gc = &p_media->ml_gc_data; - if( p_gc == NULL ) - return; - - refs = --p_gc->refs; - pool = p_gc->pool; - - if( refs == 0 && !pool ) - { - p_gc->pf_destructor (p_gc); - } -} - -/***************************************************************************** - * ML Free Functions - *****************************************************************************/ - -/** - * @brief Free a person object - * @param p_media Person object to free - * @note This function is NOT threadsafe - */ -static inline void ml_FreePeople( ml_person_t *p_person ) -{ - if( p_person == NULL ) - return; - ml_FreePeople( p_person->p_next ); - free( p_person->psz_name ); - free( p_person->psz_role ); - free( p_person ); -} - -/** - * @brief Free only the content of a media. @see ml_media_t - * @param p_media Media object - * @note This function is NOT threadsafe. - */ -static inline void ml_FreeMediaContent( ml_media_t *p_media ) -{ - FREENULL( p_media->psz_uri ); - FREENULL( p_media->psz_title ); - FREENULL( p_media->psz_orig_title ); - FREENULL( p_media->psz_cover ); - FREENULL( p_media->psz_comment ); - FREENULL( p_media->psz_extra ); - FREENULL( p_media->psz_genre ); - FREENULL( p_media->psz_album ); - FREENULL( p_media->psz_preview ); - FREENULL( p_media->psz_language ); - ml_FreePeople( p_media->p_people ); - p_media->b_sparse = true; - p_media->i_id = 0; - p_media->i_type = ML_UNKNOWN; - p_media->i_album_id = 0; - p_media->i_disc_number = 0; - p_media->i_track_number = 0; - p_media->i_year = 0; - p_media->i_vote = 0; - p_media->i_score = 0; - p_media->i_filesize = 0; - p_media->i_duration = 0; - p_media->i_played_count = 0; - p_media->i_last_played = 0; - p_media->i_skipped_count = 0; - p_media->i_last_skipped = 0; - p_media->i_first_played = 0; - p_media->i_import_time = 0; - p_media->i_bitrate = 0; - p_media->i_samplerate = 0; - p_media->i_bpm = 0; -} - -/** - * @brief Free a result item. @see ml_result_t - * @param p_result Result item to free - * @note This will free any strings and decref medias. - */ -static inline void ml_FreeResult( ml_result_t *p_result ) -{ - if( p_result ) - { - switch( p_result->type ) - { - case ML_TYPE_PSZ: - free( p_result->value.psz ); - break; - case ML_TYPE_MEDIA: - ml_gc_decref( p_result->value.p_media ); - break; - default: - break; - } - free( p_result ); - } -} - - -/** - * @brief Free a ml_element_t item. - * @param p_find Find object to free - * @see ml_element_t */ -static inline void ml_FreeElement( ml_element_t *p_elt ) -{ - if( p_elt ) - { - if( ml_AttributeIsString( p_elt->criteria ) ) - { - free( p_elt->value.str ); - } - if( p_elt->criteria == ML_PEOPLE ) - { - free( p_elt->lvalue.str ); - } - free( p_elt ); - } -} - - -/** - * @brief Destroy a vlc_array_t of ml_result_t - * @param ml_result_array The result array to free - * @note Frees all results and contents of the results - */ -static inline void ml_DestroyResultArray( vlc_array_t *p_result_array ) -{ - for( int i = 0; i < vlc_array_count( p_result_array ); i++ ) - { - ml_FreeResult( ( ml_result_t* ) vlc_array_item_at_index( - p_result_array, i ) ); - } -} - - - -/***************************************************************************** - * ML Object Management Functions - *****************************************************************************/ - -/** Helpers for locking and unlocking */ -#define ml_LockMedia( a ) vlc_mutex_lock( &a->lock ) -#define ml_UnlockMedia( a ) vlc_mutex_unlock( &a->lock ) - -/** - * @brief Object constructor for ml_media_t - * @param p_ml The media library object - * @param id If 0, this item isn't in database. If non zero, it is and - * it will be a singleton - * @param select Type of object - * @param reload Whether to reload from database - */ -VLC_API ml_media_t *media_New( media_library_t* p_ml, int id, - ml_select_e select, bool reload ); - - -/* Forward declaration */ -static inline int ml_CopyPersons( ml_person_t** a, ml_person_t* b ); - -/** - * @brief Copy all members of a ml_media_t to another. - * @param b Destination media, already allocated - * @param a Source media, cannot be NULL, const - * @note This does not check memory allocation (for strdup). It is threadsafe - * @todo Free b content, before inserting a? - */ -static inline int ml_CopyMedia( ml_media_t *b, ml_media_t *a ) -{ - if( !a || !b ) return VLC_EGENERIC; - if( a == b ) return VLC_SUCCESS; - ml_LockMedia( a ); - ml_LockMedia( b ); - b->b_sparse = a->b_sparse; - b->i_id = a->i_id; - b->i_type = a->i_type; - b->i_album_id = a->i_album_id; - b->i_disc_number = a->i_disc_number; - b->i_track_number = a->i_track_number; - b->i_year = a->i_year; - b->i_vote = a->i_vote; - b->i_score = a->i_score; - b->i_filesize = a->i_filesize; - b->i_duration = a->i_duration; - b->i_played_count = a->i_played_count; - b->i_last_played = a->i_last_played; - b->i_skipped_count = a->i_skipped_count; - b->i_last_skipped = a->i_last_skipped; - b->i_first_played = a->i_first_played; - b->i_import_time = a->i_import_time; - b->i_bitrate = a->i_bitrate; - b->i_samplerate = a->i_samplerate; - b->i_bpm = a->i_bpm; - FREENULL( b->psz_uri ); - if( a->psz_uri ) - b->psz_uri = strdup( a->psz_uri ); - FREENULL( b->psz_title ); - if( a->psz_title ) - b->psz_title = strdup( a->psz_title ); - FREENULL( b->psz_orig_title ); - if( a->psz_orig_title ) - b->psz_orig_title = strdup( a->psz_orig_title ); - FREENULL( b->psz_album ); - if( a->psz_album ) - b->psz_album = strdup( a->psz_album ); - FREENULL( b->psz_cover ); - if( a->psz_cover ) - b->psz_cover = strdup( a->psz_cover ); - FREENULL( b->psz_genre ); - if( a->psz_genre ) - b->psz_genre = strdup( a->psz_genre ); - FREENULL( b->psz_comment ); - if( a->psz_comment ) - b->psz_comment = strdup( a->psz_comment ); - FREENULL( b->psz_extra ); - if( a->psz_extra ) - b->psz_extra = strdup( a->psz_extra ); - FREENULL( b->psz_preview ); - if( a->psz_preview ) - b->psz_preview = strdup( a->psz_preview ); - FREENULL( b->psz_language ); - if( a->psz_language ) - b->psz_language = strdup( a->psz_language ); - ml_FreePeople( b->p_people ); - b->p_people = NULL; - if( a->p_people ) ml_CopyPersons( &( b->p_people ), a->p_people ); - ml_UnlockMedia( b ); - ml_UnlockMedia( a ); - return VLC_SUCCESS; -} - -/***************************************************************************** - * ML Find Tree Related Functions - *****************************************************************************/ -#define ml_FreeFindTree( tree ) ml_GenericFreeFindTree( tree, true ) -#define ml_ShallowFreeFindTree( tree ) ml_GenericFreeFindTree( tree, false ) -/** - * @brief Free a find tree - * @param Find tree to free - * @param true to free any associated strings, false to not free them - */ -static inline void ml_GenericFreeFindTree( ml_ftree_t* tree, bool freestrings ) -{ - if( tree == NULL ) - return; - if( tree->left ) - { - ml_GenericFreeFindTree( tree->left, freestrings ); - free( tree->left ); - } - if( tree->right ) - { - ml_GenericFreeFindTree( tree->right, freestrings ); - free( tree->right ); - } - if( tree->op == ML_OP_NONE && ml_AttributeIsString( tree->criteria ) - && freestrings) - { - free( tree->value.str ); - if( tree->criteria == ML_PEOPLE ) - free( tree->lvalue.str ); - } -} - -/** - * @brief Checks if a given find tree has leaf nodes - * @param Find tree - * @return Number of leaf nodes - */ -static inline int ml_FtreeHasOp( ml_ftree_t* tree ) -{ - if( tree == NULL ) - return 0; - if( tree->criteria > 0 && tree->op == ML_OP_NONE ) - return 1; - else - return ml_FtreeHasOp( tree->left ) + ml_FtreeHasOp( tree->right ); -} - - -/** - * @brief Connect up a find tree - * @param op operator to connect with - * If op = ML_OP_NONE, then you are connecting to a tree consisting of - * only SPECIAL nodes. - * If op = ML_OP_NOT, then right MUST be NULL - * op must not be ML_OP_SPECIAL, @see ml_FtreeSpec - * @param left part of the tree - * @param right part of the tree - * @return Pointer to new tree - * @note Use the helpers! - */ -VLC_API ml_ftree_t *ml_OpConnectChilds( ml_op_e op, ml_ftree_t* left, - ml_ftree_t* right ); - -/** - * @brief Attaches a special node to a tree - * @param tree Tree to attach special node to - * @param crit Criteria may be SORT_ASC, SORT_DESC, LIMIT or DISTINCT - * @param limit Limit used if LIMIT criteria used - * @param Sort string used if SORT criteria is used - * @return Pointer to new tree - * @note Use the helpers - */ -VLC_API ml_ftree_t *ml_FtreeSpec( ml_ftree_t* tree, - ml_select_e crit, - int limit, - char* sort ); - -/** - * @brief This function gives quick sequential adding capability - * @param left Tree to add to. This may be NULL - * @param right Tree to append. May not be NULL - * @return Pointer to new tree.*/ -static inline ml_ftree_t* ml_FtreeFastAnd( ml_ftree_t* left, - ml_ftree_t* right ) -{ - if( ml_FtreeHasOp( left ) == 0 ) - { - return ml_OpConnectChilds( ML_OP_NONE, left, right ); - } - else - { - return ml_OpConnectChilds( ML_OP_AND, left, right ); - } -} -#define ml_FtreeAnd( left, right ) ml_OpConnectChilds( ML_OP_AND, left, right ) -#define ml_FtreeOr( left, right ) ml_OpConnectChilds( ML_OP_OR, left, right ) -#define ml_FtreeNot( left ) ml_OpConnectChilds( ML_OP_NOT, left, NULL ) - -#define ml_FtreeSpecAsc( tree, str ) ml_FtreeSpec( tree, ML_SORT_ASC, 0, str ) -#define ml_FtreeSpecDesc( tree, str ) ml_FtreeSpec( tree, ML_SORT_DESC, 0, str ) -#define ml_FtreeSpecLimit( tree, limit ) ml_FtreeSpec( tree, ML_LIMIT, limit, NULL ) -#define ml_FtreeSpecDistinct( tree ) ml_FtreeSpec( tree, ML_DISTINCT, 0, NULL ) - - -/***************************************************************************** - * ML Core Functions - *****************************************************************************/ - -/** - * @brief Create input item from media - * @param p_media_library This ML instance. - * @param i_media_id ID of the media to use to create an input_item. - * @return The media item. - */ -static inline input_item_t* ml_CreateInputItem( - media_library_t *p_media_library, int i_media_id ) -{ - return p_media_library->functions.pf_InputItemFromMedia( p_media_library, - i_media_id ); -} - -/** - * @brief Search in the database according some criterias - * - * @param p_media_library the media library object - * @param result a pointer to a result array - * @param ... parameters to select the data - * @return VLC_SUCCESS or an error - */ -static inline int __ml_Find( media_library_t *p_media_library, - vlc_array_t *p_result_array, ... ) -{ - va_list args; - int returned; - - va_start( args, p_result_array ); - returned = p_media_library->functions.pf_Find( p_media_library, - p_result_array, args ); - va_end( args ); - - return returned; -} - - -/** - * @brief Search in the database according some criterias (threaded) - * @param p_media_library the media library object - * @param result_array a pointer to a result array - * @param result_type type of data to retrieve - * @param psz_lvalue This should contain any necessary lvalue/key - * for the given result_type. Used for ML_PEOPLE. Otherwise NULL - * @param args parameters to select the data - * @return VLC_SUCCESS or an error - */ -static inline int ml_FindAdv( media_library_t *p_media_library, - vlc_array_t *p_result_array, - ml_select_e result_type, - char* psz_lvalue, - ml_ftree_t *tree ) -{ - return p_media_library->functions.pf_FindAdv( p_media_library, - p_result_array, - result_type, - psz_lvalue, - tree ); -} - - -/** - * @brief Find a value in the ML database, fill p_result with it. - * @param p_media_library Media library object - * @param p_result Object to put result into - * @param Args [ SelectType [ PersonType ] Value ] ... ML_END - * @note Do not use this function directly. - */ -static inline int __ml_GetValue( media_library_t *p_media_library, - ml_result_t *p_result, - va_list args ) -{ - vlc_array_t *p_result_array = vlc_array_new(); - int i_ret = p_media_library->functions.pf_Find( p_media_library, - p_result_array, - args ); - if( i_ret != VLC_SUCCESS ) - goto exit; - if( vlc_array_count( p_result_array ) > 0 ) - memcpy( p_result, - ( ml_result_t* ) vlc_array_item_at_index( p_result_array, 0 ), - sizeof( ml_result_t) ); - else - i_ret = VLC_EGENERIC; - -exit: - /* Note: Do not free the results, because of memcpy */ - vlc_array_destroy( p_result_array ); - return i_ret; -} - -/** - * @brief Search an INTEGER in the database - * This uses a Query but returns only one integer (>0), or an error code. - * - * @param p_media_library the media library object - * @param va_args parameters to select the data - * @return Found INTEGER >= 0 or an error - */ -#define ml_GetInt( ml, ... ) __ml_GetInt( ml, __VA_ARGS__, ML_LIMIT, 1, ML_END ) -static inline int __ml_GetInt( media_library_t *p_media_library, ... ) -{ - va_list args; - va_start( args, p_media_library ); - ml_result_t result; - int i_ret = __ml_GetValue( p_media_library, &result, args ); - va_end( args ); - if( i_ret != VLC_SUCCESS ) - return i_ret; - else - return result.value.i; -} - - -/** - * @brief Search a string (VARCHAR) in the database - * This uses a Query but returns only one integer (>0), or an error code. - * - * @param p_media_library the media library object - * @param va_args parameters to select the data - * @return Found string, or NULL if not found or in case of error - */ -#define ml_FindPsz( ml, ... ) __ml_GetPsz( ml, __VA_ARGS__, ML_LIMIT, 1, ML_END ) -static inline char* __ml_GetPsz( media_library_t *p_media_library, ... ) -{ - va_list args; - va_start( args, p_media_library ); - ml_result_t result; - int i_ret = __ml_GetValue( p_media_library, &result, args ); - va_end( args ); - if( i_ret != VLC_SUCCESS ) - return NULL; - else - return result.value.psz; // no need to duplicate -} - -/** - * @brief Generic update in Media Library database - * - * @param p_media_library the media library object - * @param selected_type the type of the element we're selecting - * @param where list of ids/uris to be changed - * @param changes list of changes to make in the entries - * @return VLC_SUCCESS or VLC_EGENERIC - */ -static inline int ml_Update( media_library_t *p_media_library, - ml_select_e selected_type, - const char* psz_lvalue, - ml_ftree_t *where, - vlc_array_t *changes ) -{ - return p_media_library->functions.pf_Update( p_media_library, - selected_type, psz_lvalue, - where, changes ); -} - -/** - * @brief Update a given table - * @param p_media_library The media library object - * @param selected_type The table to update - * @param psz_lvalue The role of the person if selected_type = ML_PEOPLE - * @param id The id of the row to update - * @param ... The update data. [SelectType [RoleType] Value] - */ -VLC_API int ml_UpdateSimple( media_library_t *p_media_library, - ml_select_e selected_type, - const char* psz_lvalue, - int id, ... ); -#define ml_UpdateSimple( ml, sel, lval, id, ... ) \ - ml_UpdateSimple( ml, sel, lval, id, __VA_ARGS__, ML_END ) - -/** - * @brief Generic DELETE function - * Delete a media and all its references which don't point - * to anything else. - * - * @param p_media_library This media_library_t object - * @param id the id of the media to delete - * @return VLC_SUCCESS or VLC_EGENERIC - */ -static inline int -ml_DeleteSimple( media_library_t *p_media_library, int id ) -{ - vlc_array_t* p_where = vlc_array_new(); - ml_element_t* p_find = (ml_element_t *) calloc( 1, sizeof( ml_element_t ) ); - p_find->criteria = ML_ID; - p_find->value.i = id; - vlc_array_append( p_where, p_find ); - int i_return = p_media_library->functions.pf_Delete( p_media_library, - p_where ); - free( p_find ); - vlc_array_destroy( p_where ); - return i_return; -} - -/** - * @brief Delete many medias in the media library - * @param p_media_library Media library object - * @param p_array Array of ids to delete - * @return VLC_SUCCESS or VLC_EGENERIC - */ -static inline int -ml_Delete( media_library_t *p_media_library, vlc_array_t* p_array ) -{ - return p_media_library->functions.pf_Delete( p_media_library, - p_array ); -} - - -/***************************************************************************** - * ML Person Related Functions - *****************************************************************************/ - -/** - * @brief Create and append a person object to the given list - * @param pp_person pointer to person list. Set the address to null to create new list - * @param i_role The role of the person - * @param psz_name The name string. Will be strdup'd - * @param i_id The id in the database - * @note This function is NOT thread safe. Please lock any associated media - */ -static inline int ml_CreateAppendPersonAdv( ml_person_t **pp_person, - const char* psz_role, const char* psz_name, int i_id ) -{ - if( i_id == 0 || !( psz_name && *psz_name && psz_role && *psz_role ) ) - return VLC_SUCCESS; - if( !pp_person ) - return VLC_EGENERIC; - if( *pp_person != NULL ) - return ml_CreateAppendPersonAdv( &((**pp_person).p_next), - psz_role, psz_name, i_id); - *pp_person = ( ml_person_t * ) calloc( 1, sizeof( ml_person_t ) ); - (*pp_person)->psz_name = (psz_name && *psz_name) ? strdup( psz_name ): NULL; - (*pp_person)->psz_role = (psz_role && *psz_role) ? strdup( psz_role ): NULL; - (*pp_person)->i_id = i_id; - (*pp_person)->p_next = NULL; - return VLC_SUCCESS; -} - -/** - * @brief Create and append a person object to the given list - * @param pp_person pointer to person list. - * Set the address to NULL to create a new list - * @param personfrom Person object to copy from - * @note Ignores the next variable and copies only the variables. - * Uses ml_CreateAppendPersonAdv - * @note This function is NOT threadsafe - */ -static inline int ml_CreateAppendPerson( ml_person_t **pp_person, - ml_person_t *p_personfrom ) -{ - return ml_CreateAppendPersonAdv( pp_person, - p_personfrom->psz_role, - p_personfrom->psz_name, - p_personfrom->i_id ); -} - -/** - * @brief Copy one person list into another - * @param a To list - * @param b From list - * @note On errors, you have to free any allocated persons yourself - * @note This function is NOT threadsafe. Please ensure your medias are locked - */ -static inline int ml_CopyPersons( ml_person_t** a, ml_person_t* b ) -{ - int i_ret; - while( b ) - { - i_ret = ml_CreateAppendPerson( a, b ); - if( i_ret != VLC_SUCCESS ) - return i_ret; - b = b->p_next; - } - return VLC_SUCCESS; -} - - -/** - * @brief Returns a person list of given type - * @param p_ml The ML object - * @param p_media The Media object - * @param i_type The person type - * @note This function is thread safe - */ -VLC_API ml_person_t *ml_GetPersonsFromMedia( media_library_t* p_ml, - ml_media_t* p_media, - const char *psz_role ); - - -#define ml_GetAlbumArtistsFromMedia( a, b ) ml_GetPersonsFromMedia( a, b, ML_PERSON_ALBUM_ARTIST ); -#define ml_GetArtistsFromMedia( a, b ) ml_GetPersonsFromMedia( a, b, ML_PERSON_ARTIST ); -#define ml_GetEncodersFromMedia( a, b ) ml_GetPersonsFromMedia( a, b, ML_PERSON_ENCODER ); -#define ml_GetPublishersFromMedia( a, b ) ml_GetPersonsFromMedia( a, b, ML_PERSON_PUBLISHER ); - -/** - * @brief Delete a certain type of people from a media - * @param p_media Media to delete from - * @param i_type Type of person to delete - * @note This function is threadsafe - */ -VLC_API void ml_DeletePersonTypeFromMedia( ml_media_t* p_media, - const char *psz_role ); - - -/** - * Convenience Macros - */ - -/** - * Get information using the *media* ID. This returns only 1 information. - * @note You have to free the string returned (if that's a string!). - */ -#define ml_GetAlbumById( a, id ) ml_GetPsz( a, ML_ALBUM, ML_ID, id ) -#define ml_GetArtistById( a, id ) ml_GetPsz( a, ML_PEOPLE, ML_PERSON_ARTIST, ML_ID, id ) -#define ml_GetCoverUriById( a, id ) ml_GetPsz( a, ML_COVER, ML_ID, id ) -#define ml_GetEncoderById( a, id ) ml_GetPsz( a, ML_PEOPLE, ML_PERSON_ENCODER, ML_ID, id ) -#define ml_GetExtraById( a, id ) ml_GetPsz( a, ML_EXTRA, ML_ID, id ) -#define ml_GetGenreById( a, id ) ml_GetPsz( a, ML_GENRE, ML_ID, id ) -#define ml_GetOriginalTitleById( a, id ) ml_GetPsz( a, ML_ORIGINAL_TITLE, ML_ID, id ) -#define ml_GetPublisherById( a, id ) ml_GetPsz( a, ML_PEOPLE, ML_PERSON_PUBLISHER, ML_ID, id ) -#define ml_GetTitleById( a, id ) ml_GetPsz( a, ML_TITLE, ML_ID, id ) -#define ml_GetUriById( a, id ) ml_GetPsz( a, ML_URI, ML_ID, id ) - -#define ml_GetAlbumIdById( a, id ) ml_GetInt( a, ML_ALBUM_ID, ML_ID, id ) -#define ml_GetArtistIdById( a, id ) ml_GetInt( a, ML_PEOPLE_ID, ML_PERSON_ARTIST, ML_ID, id ) -#define ml_GetDurationById( a, id ) ml_GetInt( a, ML_DURATION, ML_ID, id ) -#define ml_GetEncoderIdById( a, id ) ml_GetInt( a, ML_PEOPLE_ID, ML_PERSON_ENCODER, ML_ID, id ) -#define ml_GetLastPlayedById( a, id ) ml_GetInt( a, ML_LAST_PLAYED, ML_ID, id ) -#define ml_GetPlayedCountById( a, id ) ml_GetInt( a, ML_PLAYED_COUNT, ML_ID, id ) -#define ml_GetPublisherIdById( a, id ) ml_GetInt( a, ML_PEOPLE_ID, ML_PERSON_PUBLISHER, ML_ID, id ) -#define ml_GetScoreById( a, id ) ml_GetInt( a, ML_SCORE, ML_ID, id ) -#define ml_GetTrackNumberById( a, id ) ml_GetInt( a, ML_TRACK_NUMBER, ML_ID, id ) -#define ml_GetTypeById( a, id ) ml_GetInt( a, ML_TYPE, ML_ID, id ) -#define ml_GetYearById( a, id ) ml_GetInt( a, ML_YEAR, ML_ID, id ) -#define ml_GetVoteById( a, id ) ml_GetInt( a, ML_VOTE, ML_ID, id ) - -/** Albums handling */ -#define ml_GetAlbumId( a, b ) ml_GetInt( a, ML_ALBUM_ID, ML_ALBUM, b ) - -/** People handling */ -#define ml_GetArtistId( a, b ) ml_GetInt( a, ML_PERSON_ID, ML_PERSON_ARTIST, ML_PERSON, ML_PERSON_ARTIST, b ) -#define ml_GetEncoderId( a, b ) ml_GetInt( a, ML_PERSON_ID, ML_PERSON_ENCODER, ML_PERSON, ML_PERSON_ENCODER, b ) -#define ml_GetPublisherId( a, b ) ml_GetInt( a, ML_PERSON_ID, ML_PERSON_PUBLISHER, ML_PERSON, ML_PERSON_PUBLISHER, b ) - -/** Counts handling */ -#define ml_GetMediaCount( a, ... ) __ml_GetInt( a, ML_COUNT_MEDIA, __VA_ARGS__, ML_END ) -#define ml_GetAlbumCount( a, ... ) __ml_GetInt( a, ML_COUNT_ALBUM, __VA_ARGS__, ML_END ) -#define ml_GetPeopleCount( a, ... ) __ml_GetInt( a, ML_COUNT_PEOPLE, __VA_ARGS__, ML_END ) - -#define ml_Find( a, b, ... ) __ml_Find( a, b, __VA_ARGS__, ML_END ) - -#define ml_FindAlbum( a, b, ... ) __ml_Find( a, b, ML_ALBUM, __VA_ARGS__, ML_END ) -#define ml_FindArtist( a, b, ... ) __ml_Find( a, b, ML_PERSON, ML_PERSON_ARTIST, __VA_ARGS__, ML_END ) -#define ml_FindEncoder( a, b, ... ) __ml_Find( a, b, ML_PERSON, ML_PERSON_ENCODER, __VA_ARGS__, ML_END ) -#define ml_FindGenre( a, b, ... ) __ml_Find( a, b, ML_GENRE, __VA_ARGS__, ML_END ) -#define ml_FindMedia( a, b, ... ) __ml_Find( a, b, ML_MEDIA, __VA_ARGS__, ML_END ) -#define ml_FindOriginalTitle( a, b, ... ) __ml_Find( a, b, ML_ORIGINAL_TITLE, __VA_ARGS__, ML_END ) -#define ml_FindPublisher( a, b, ... ) __ml_Find( a, b, ML_PERSON, ML_PERSON_PUBLISHER, __VA_ARGS__, ML_END ) -#define ml_FindTitle( a, b, ... ) __ml_Find( a, b, ML_TITLE, __VA_ARGS__, ML_END ) -#define ml_FindType( a, b, ... ) __ml_Find( a, b, ML_TYPE, __VA_ARGS__, ML_END ) -#define ml_FindUri( a, b, ... ) __ml_Find( a, b, ML_URI, __VA_ARGS__, ML_END ) -#define ml_FindYear( a, b, ... ) __ml_Find( a, b, ML_YEAR, __VA_ARGS__, ML_END ) - -#define ml_FindAllAlbums( a, b ) ml_FindAlbum( a, b, ML_DISTINCT ) -#define ml_FindAllArtists( a, b ) ml_FindArtist( a, b, ML_DISTINCT ) -#define ml_FindAllGenres( a, b ) ml_FindGenre( a, b, ML_DISTINCT ) -#define ml_FindAllMedias( a, b ) ml_FindMedia( a, b, ML_DISTINCT ) -#define ml_FindAllOriginalTitles( a, b ) ml_FindOriginalTitle( a, b, ML_DISTINCT ) -#define ml_FindAllPublishers( a, b, ... ) ml_FindPublisher( a, b, ML_DISTINCT ) -#define ml_FindAllTitles( a, b ) ml_FindTitle( a, b, ML_DISTINCT ) -#define ml_FindAllTypes( a, b ) ml_FindType( a, b, ML_DISTINCT ) -#define ml_FindAllUris( a, b ) ml_FindUri( a, b, ML_DISTINCT ) -#define ml_FindAllYears( a, b ) ml_FindYear( a, b, ML_DISTINCT ) - -#define ml_FindAlbumAdv( a, b, c ) ml_FindAdv( a, b, ML_ALBUM, NULL, c ) -#define ml_FindArtistAdv( a, b, c ) ml_FindAdv( a, b, ML_PERSON, ML_PERSON_ARTIST, c ) -#define ml_FindEncoderAdv( a, b, c ) ml_FindAdv( a, b, ML_PERSON, ML_PERSON_ENCODER, c ) -#define ml_FindGenreAdv( a, b, c ) ml_FindAdv( a, b, ML_GENRE, NULL, c ) -#define ml_FindMediaAdv( a, b, c ) ml_FindAdv( a, b, ML_MEDIA, NULL, c ) -#define ml_FindOriginalTitleAdv( a, b, c ) ml_FindAdv( a, b, ML_ORIGINAL_TITLE,NULL, c ) -#define ml_FindPublisherAdv( a, b, c ) ml_FindAdv( a, b, ML_PUBLISHER, ML_PERSON_PUBLISHER, c ) -#define ml_FindTitleAdv( a, b, c ) ml_FindAdv( a, b, ML_TITLE, NULL, c ) -#define ml_FindTypeAdv( a, b, c ) ml_FindAdv( a, b, ML_TYPE, NULL, c ) -#define ml_FindUriAdv( a, b, c ) ml_FindAdv( a, b, ML_URI, NULL, c ) -#define ml_FindYearAdv( a, b, c ) ml_FindAdv( a, b, ML_YEAR, NULL, c ) - - - #ifdef __cplusplus } #endif /* C++ */ diff --git a/src/Makefile.am b/src/Makefile.am index f21b447643d6..73fed5b3aec3 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -461,7 +461,6 @@ SOURCES_libvlc_common = \ misc/update.c \ misc/update_crypto.c \ misc/xml.c \ - misc/media_library.c \ extras/libc.c \ extras/tdestroy.c \ misc/filter.c \ diff --git a/src/libvlc-module.c b/src/libvlc-module.c index a173aedbcf2f..688281978ffa 100644 --- a/src/libvlc-module.c +++ b/src/libvlc-module.c @@ -2033,10 +2033,6 @@ vlc_module_begin () PLAYLISTENQUEUE_LONGTEXT, true ) #endif add_bool( "media-library", 0, ML_TEXT, ML_LONGTEXT, false ) -#if defined( MEDIA_LIBRARY ) - add_bool( "load-media-library-on-startup", 1, LOAD_ML_TEXT, - LOAD_ML_LONGTEXT, false ) -#endif add_bool( "playlist-tree", 0, PLTREE_TEXT, PLTREE_LONGTEXT, false ) add_string( "open", "", OPEN_TEXT, OPEN_LONGTEXT, false ) diff --git a/src/libvlc.c b/src/libvlc.c index 54933cf76c38..ced65b011582 100644 --- a/src/libvlc.c +++ b/src/libvlc.c @@ -55,7 +55,6 @@ #endif -#include #include #include @@ -109,12 +108,9 @@ libvlc_int_t * libvlc_InternalCreate( void ) priv = libvlc_priv (p_libvlc); priv->p_playlist = NULL; - priv->p_ml = NULL; priv->p_dialog_provider = NULL; priv->p_vlm = NULL; - /* Initialize mutexes */ - vlc_mutex_init( &priv->ml_lock ); vlc_ExitInit( &priv->exit ); return p_libvlc; @@ -395,23 +391,6 @@ int libvlc_InternalInit( libvlc_int_t *p_libvlc, int i_argc, /* System specific configuration */ system_Configure( p_libvlc, i_argc - vlc_optind, ppsz_argv + vlc_optind ); -#if defined(MEDIA_LIBRARY) - /* Get the ML */ - if( var_GetBool( p_libvlc, "load-media-library-on-startup" ) ) - { - priv->p_ml = ml_Create( VLC_OBJECT( p_libvlc ), NULL ); - if( !priv->p_ml ) - { - msg_Err( p_libvlc, "ML initialization failed" ); - return VLC_EGENERIC; - } - } - else - { - priv->p_ml = NULL; - } -#endif - #ifdef ENABLE_VLM /* Initialize VLM if vlm-conf is specified */ psz_parser = var_CreateGetNonEmptyString( p_libvlc, "vlm-conf" ); @@ -551,16 +530,6 @@ void libvlc_InternalCleanup( libvlc_int_t *p_libvlc ) } #endif -#if defined(MEDIA_LIBRARY) - media_library_t* p_ml = priv->p_ml; - if( p_ml ) - { - ml_Destroy( VLC_OBJECT( p_ml ) ); - vlc_object_release( p_ml ); - libvlc_priv(p_playlist->p_libvlc)->p_ml = NULL; - } -#endif - /* Free playlist now, all threads are gone */ playlist_t *p_playlist = libvlc_priv (p_libvlc)->p_playlist; if( p_playlist != NULL ) @@ -612,9 +581,7 @@ void libvlc_InternalDestroy( libvlc_int_t *p_libvlc ) { libvlc_priv_t *priv = libvlc_priv( p_libvlc ); - /* Destroy mutexes */ vlc_ExitDestroy( &priv->exit ); - vlc_mutex_destroy( &priv->ml_lock ); assert( atomic_load(&(vlc_internals(p_libvlc)->refs)) == 1 ); vlc_object_release( p_libvlc ); diff --git a/src/libvlc.h b/src/libvlc.h index 2a869bb7cb28..c116d035b4ef 100644 --- a/src/libvlc.h +++ b/src/libvlc.h @@ -159,8 +159,6 @@ typedef struct libvlc_priv_t /* Singleton objects */ playlist_t *p_playlist; ///< the playlist singleton - struct media_library_t *p_ml; ///< the ML singleton - vlc_mutex_t ml_lock; ///< Mutex for ML creation vlm_t *p_vlm; ///< the VLM singleton (or NULL) vlc_object_t *p_dialog_provider; ///< dialog provider #ifdef ENABLE_SOUT diff --git a/src/libvlccore.sym b/src/libvlccore.sym index 5c67642bc86f..3159dfca8f9c 100644 --- a/src/libvlccore.sym +++ b/src/libvlccore.sym @@ -230,13 +230,7 @@ vlc_UrlClean vlc_path2uri make_path mdate -ml_Get media_New -ml_OpConnectChilds -ml_FtreeSpec -ml_UpdateSimple -ml_GetPersonsFromMedia -ml_DeletePersonTypeFromMedia module_config_free module_config_get module_exists diff --git a/src/misc/media_library.c b/src/misc/media_library.c deleted file mode 100644 index 05e900890405..000000000000 --- a/src/misc/media_library.c +++ /dev/null @@ -1,417 +0,0 @@ -/***************************************************************************** - * media_library.c: SQL-based media library: ML creators and destructors - ***************************************************************************** - * Copyright (C) 2009-2010 VLC authors and VideoLAN and AUTHORS - * $Id$ - * - * Authors: Srikanth Raju - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU Lesser General Public License as published by - * the Free Software Foundation; either version 2.1 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with this program; if not, write to the Free Software Foundation, - * Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA. - *****************************************************************************/ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#if defined(MEDIA_LIBRARY) - -#include -#include -#include -#include "../libvlc.h" - -/** - * @brief Destroy the medialibrary object - * @param Parent object that holds the media library object - */ -void ml_Destroy( vlc_object_t * p_this ) -{ - media_library_t* p_ml = ( media_library_t* )p_this; - module_unneed( p_ml, p_ml->p_module ); -} - - -/** - * Atomically set the reference count to 1. - * @param p_gc reference counted object - * @param pf_destruct destruction calback - * @return p_gc. - */ -static void *ml_gc_init (ml_gc_object_t *p_gc, void (*pf_destruct) (ml_gc_object_t *)) -{ - /* There is no point in using the GC if there is no destructor... */ - assert (pf_destruct); - p_gc->pf_destructor = pf_destruct; - - p_gc->pool = false; - p_gc->refs = 1; - return p_gc; -} - - - -/** - * @brief Create an instance of the media library - * @param p_this Parent object - * @param psz_name Name which is passed to module_need (not needed) - * @return p_ml created and attached, module loaded. NULL if - * not able to load - */ -media_library_t *ml_Create( vlc_object_t *p_this, char *psz_name ) -{ - media_library_t *p_ml; - - p_ml = ( media_library_t * ) vlc_custom_create( - p_this, sizeof( media_library_t ), - "media-library" ); - if( !p_ml ) - { - msg_Err( p_this, "unable to create media library object" ); - return NULL; - } - - p_ml->p_module = module_need( p_ml, "media-library", psz_name, false ); - if( !p_ml->p_module ) - { - vlc_object_release( p_ml ); - msg_Err( p_this, "Media Library provider not found" ); - return NULL; - } - - return p_ml; -} - -#undef ml_Get -/** - * @brief Acquire a reference to the media library singleton - * @param p_this Object that holds the reference - * @return media_library_t The ml object. NULL if not compiled with - * media library or if unable to load - */ -media_library_t* ml_Get( vlc_object_t* p_this ) -{ - media_library_t* p_ml; - vlc_mutex_lock( &( libvlc_priv( p_this->p_libvlc )->ml_lock ) ); - p_ml = libvlc_priv (p_this->p_libvlc)->p_ml; - assert( VLC_OBJECT( p_ml ) != p_this ); - if( p_ml == NULL && - !var_GetBool( p_this->p_libvlc, "load-media-library-on-startup" ) ) - { - libvlc_priv (p_this->p_libvlc)->p_ml - = ml_Create( VLC_OBJECT( p_this->p_libvlc ), NULL ); - p_ml = libvlc_priv (p_this->p_libvlc)->p_ml; - } - vlc_mutex_unlock( &( libvlc_priv( p_this->p_libvlc )->ml_lock ) ); - return p_ml; -} - -/** - * @brief Destructor for ml_media_t - */ -static void media_Destroy( ml_gc_object_t *p_gc ) -{ - ml_media_t* p_media = ml_priv( p_gc, ml_media_t ); - vlc_mutex_destroy( &p_media->lock ); - ml_FreeMediaContent( p_media ); - free( p_media ); -} - -/** - * @brief Object constructor for ml_media_t - * @param p_ml The media library object - * @param id If 0, this item isn't in database. If non zero, it is and - * it will be a singleton - * @param select Type of object - * @param reload Whether to reload from database - */ -ml_media_t* media_New( media_library_t* p_ml, int id, - ml_select_e select, bool reload ) -{ - if( id == 0 ) - { - ml_media_t* p_media = NULL; - p_media = ( ml_media_t* )calloc( 1, sizeof( ml_media_t ) ); - ml_gc_init( &p_media->ml_gc_data, media_Destroy ); - vlc_mutex_init( &p_media->lock ); - return p_media; - } - else - return p_ml->functions.pf_GetMedia( p_ml, id, select, reload ); -} - -#undef ml_UpdateSimple -/** - * @brief Update a given table - * @param p_media_library The media library object - * @param selected_type The table to update - * @param psz_lvalue The role of the person if selected_type = ML_PEOPLE - * @param id The id of the row to update - * @param ... The update data. [SelectType [RoleType] Value] ... ML_END - */ -int ml_UpdateSimple( media_library_t *p_media_library, - ml_select_e selected_type, - const char* psz_lvalue, - int id, ... ) -{ - ml_element_t *update; - vlc_array_t *array = vlc_array_new(); - int i_ret = VLC_SUCCESS; - - va_list args; - va_start( args, id ); - - ml_select_e sel; - do { - update = ( ml_element_t* ) calloc( 1, sizeof( ml_element_t ) ); - sel = ( ml_select_e ) va_arg( args, int ); - update->criteria = sel; - if( sel == ML_PEOPLE ) - { - update->lvalue.str = va_arg( args, char* ); - update->value.str = va_arg( args, char* ); - vlc_array_append( array, update ); - } - else if( sel == ML_PEOPLE_ID ) - { - update->lvalue.str = va_arg( args, char* ); - update->value.i = va_arg( args, int ); - vlc_array_append( array, update ); - } - else if( sel == ML_PEOPLE_ROLE ) - { -#ifndef NDEBUG - msg_Dbg( p_media_library, - "this argument is invalid for Update: %d", - (int)sel ); -#endif - } - else - { - switch( ml_AttributeIsString( sel ) ) - { - case -1: - if( sel != ML_END ) - { -#ifndef NDEBUG - msg_Dbg( p_media_library, - "this argument is invalid for Update: %d", - (int)sel ); -#endif - i_ret = VLC_EBADVAR; - } - else if( sel == ML_END ) - vlc_array_append( array, update ); - break; - case 1: - update->value.str = va_arg( args, char* ); - vlc_array_append( array, update ); - break; - case 0: - update->value.i = va_arg( args, int ); - vlc_array_append( array, update ); - break; - } - } - } while( sel != ML_END ); - - va_end( args ); - - ml_ftree_t* p_where = NULL; - ml_ftree_t* find = ( ml_ftree_t* ) calloc( 1, sizeof( ml_ftree_t ) ); - find->criteria = ML_ID; - find->value.i = id ; - find->comp = ML_COMP_EQUAL; - p_where = ml_FtreeFastAnd( p_where, find ); - - /* Let's update the database ! */ - if( i_ret == VLC_SUCCESS ) - i_ret = ml_Update( p_media_library, selected_type, psz_lvalue, - p_where, array ); - - /* Destroying array */ - for( int i = 0; i < vlc_array_count( array ); i++ ) - { - free( vlc_array_item_at_index( array, i ) ); - } - vlc_array_destroy( array ); - ml_FreeFindTree( p_where ); - - return i_ret; -} - -/** - * @brief Connect up a find tree - * @param op operator to connect with - * If op = ML_OP_NONE, then you are connecting to a tree consisting of - * only SPECIAL nodes. - * If op = ML_OP_NOT, then right MUST be NULL - * op must not be ML_OP_SPECIAL, @see ml_FtreeSpec - * @param left part of the tree - * @param right part of the tree - * @return Pointer to new tree - * @note Use the helpers! - */ -ml_ftree_t* ml_OpConnectChilds( ml_op_e op, ml_ftree_t* left, - ml_ftree_t* right ) -{ - /* Use this Op for fresh trees (with only special nodes/none at all!) */ - if( op == ML_OP_NONE ) - { - assert( ml_FtreeHasOp( left ) == 0 ); - if( left == NULL ) - return right; - /* Percolate down tree only for special nodes */ - assert( left->op == ML_OP_SPECIAL ); - if( left->left == NULL ) - { - left->left = right; - return left; - } - else - { - return ml_OpConnectChilds( ML_OP_NONE, left->left, right ); - } - } - else if( op == ML_OP_NOT ) - { - assert( right == NULL && left != NULL ); - assert( ml_FtreeHasOp( left ) > 0 ); - } - else if( op == ML_OP_SPECIAL ) - { - assert( 0 ); - } - else - { - assert( right != NULL && left != NULL ); - assert( ml_FtreeHasOp( left ) > 0 ); - assert( ml_FtreeHasOp( right ) > 0 ); - } - ml_ftree_t* p_parent = (ml_ftree_t *) calloc( 1, sizeof( ml_ftree_t ) ); - p_parent->op = op; - p_parent->left = left; - p_parent->right = right; - return p_parent; -} - -#undef ml_FtreeSpec -/** - * @brief Attaches a special node to a tree - * @param tree Tree to attach special node to - * @param crit Criteria may be SORT_ASC, SORT_DESC, LIMIT or DISTINCT - * @param limit Limit used if LIMIT criteria used - * @param Sort string used if SORT criteria is used - * @return Pointer to new tree - * @note Use the helpers - */ -ml_ftree_t* ml_FtreeSpec( ml_ftree_t* tree, - ml_select_e crit, - int limit, - char* sort ) -{ - assert( crit == ML_SORT_ASC || crit == ML_LIMIT || crit == ML_SORT_DESC || - crit == ML_DISTINCT ); - ml_ftree_t* right = ( ml_ftree_t* ) calloc( 1, sizeof( ml_ftree_t ) ); - right->criteria = crit; - if( crit == ML_LIMIT ) - right->value.i = limit; - else if( crit == ML_SORT_ASC || crit == ML_SORT_DESC ) - right->value.str = strdup( sort ); - right->op = ML_OP_NONE; - ml_ftree_t* p_parent = ( ml_ftree_t* ) calloc( 1, sizeof( ml_ftree_t ) ); - p_parent->right = right; - p_parent->op = ML_OP_SPECIAL; - p_parent->left = tree; - return p_parent; -} - - -/** - * @brief Returns a person list of given type - * @param p_ml The ML object - * @param p_media The Media object - * @param i_type The person type - * @note This function is thread safe - */ -ml_person_t* ml_GetPersonsFromMedia( media_library_t* p_ml, - ml_media_t* p_media, - const char *psz_role ) -{ - VLC_UNUSED( p_ml ); - assert( p_media != NULL ); - ml_person_t* p_return = NULL; - ml_LockMedia( p_media ); - ml_person_t* p_person = p_media->p_people; - while( p_person ) - { - if( strcmp( p_person->psz_role, psz_role ) == 0 ) - { - int i_ret = ml_CreateAppendPerson( &p_return, p_person ); - if( i_ret != VLC_SUCCESS ) - { - ml_UnlockMedia( p_media ); - ml_FreePeople( p_return ); - return NULL; - } - } - p_person = p_person->p_next; - } - ml_UnlockMedia( p_media ); - //TODO: Fill up empty names + clean up list - return p_return; -} - -/** - * @brief Delete a certain type of people from a media - * @param p_media Media to delete from - * @param i_type Type of person to delete - * @note This function is threadsafe - */ -void ml_DeletePersonTypeFromMedia( ml_media_t* p_media, const char *psz_role ) -{ - assert( p_media ); - ml_LockMedia( p_media ); - ml_person_t* p_prev = NULL; - ml_person_t* p_person = p_media->p_people; - - while( p_person ) - { - if( strcmp( p_person->psz_role, psz_role ) == 0 ) - { - if( p_prev == NULL ) - { - p_media->p_people = p_person->p_next; - p_person->p_next = NULL; - ml_FreePeople( p_person ); - p_person = p_media->p_people; - } - else - { - p_prev->p_next = p_person->p_next; - p_person->p_next = NULL; - ml_FreePeople( p_person ); - p_person = p_prev->p_next; - } - } - else - { - p_prev = p_person; - p_person = p_person->p_next; - } - } - ml_UnlockMedia( p_media ); -} - -#endif /* MEDIA_LIBRARY */ diff --git a/src/missing.c b/src/missing.c index 2bd3dd172ef9..73a401a1ee43 100644 --- a/src/missing.c +++ b/src/missing.c @@ -368,74 +368,3 @@ vlm_t *vlm_New (vlc_object_t *obj) return NULL; } #endif /* !ENABLE_VLM */ - -#ifndef MEDIA_LIBRARY -#include - -#undef ml_Get -media_library_t* ml_Get ( vlc_object_t* p_this ) -{ - VLC_UNUSED( p_this ); - return NULL; -} - -ml_media_t* media_New( media_library_t* p_ml, int id, ml_select_e select, bool reload ) -{ - VLC_UNUSED( p_ml ); - VLC_UNUSED( id ); - VLC_UNUSED( select ); - VLC_UNUSED( reload ); - assert( 0 ); - return NULL; -} - -#undef ml_UpdateSimple -int ml_UpdateSimple( media_library_t *p_media_library, ml_select_e selected_type, - const char* psz_lvalue, int id, ... ) -{ - VLC_UNUSED( p_media_library ); - VLC_UNUSED( selected_type ); - VLC_UNUSED( psz_lvalue ); - VLC_UNUSED( id ); - assert( 0 ); - return 0; -} - -ml_ftree_t* ml_OpConnectChilds( ml_op_e op, ml_ftree_t* left, ml_ftree_t* right ) -{ - VLC_UNUSED( op ); - VLC_UNUSED( left ); - VLC_UNUSED( right ); - assert( 0 ); - return NULL; -} - -ml_ftree_t* ml_FtreeSpec( ml_ftree_t* tree, ml_select_e crit, int limit, - char* sort ) -{ - VLC_UNUSED( tree ); - VLC_UNUSED( crit ); - VLC_UNUSED( limit ); - VLC_UNUSED( sort ); - assert( 0 ); - return NULL; -} - -void ml_DeletePersonTypeFromMedia( ml_media_t* p_media, const char *psz_role ) -{ - VLC_UNUSED( p_media ); - VLC_UNUSED( psz_role ); - assert( 0 ); -} - -ml_person_t* ml_GetPersonsFromMedia( media_library_t* p_ml, - ml_media_t* p_media, - const char *psz_role ) -{ - VLC_UNUSED( p_ml ); - VLC_UNUSED( p_media ); - VLC_UNUSED( psz_role ); - assert( 0 ); - return NULL; -} -#endif /* !MEDIA_LIBRARY */