core.c 7.05 KB
Newer Older
zorglub's avatar
zorglub committed
1
/*****************************************************************************
2
 * core.c: Core libvlc new API functions : initialization
zorglub's avatar
zorglub committed
3
 *****************************************************************************
4
 * Copyright (C) 2005 the VideoLAN team
5
 * $Id$
zorglub's avatar
zorglub committed
6
 *
7
 * Authors: Clément Stenac <zorglub@videolan.org>
zorglub's avatar
zorglub committed
8
9
10
11
12
13
14
15
16
17
18
19
20
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 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 General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
dionoea's avatar
dionoea committed
21
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
zorglub's avatar
zorglub committed
22
 *****************************************************************************/
23

24
25
26
27
#ifdef HAVE_CONFIG_H
# include "config.h"
#endif

zorglub's avatar
zorglub committed
28
#include "libvlc_internal.h"
fawek's avatar
fawek committed
29
#include <vlc_modules.h>
zorglub's avatar
zorglub committed
30
#include <vlc/libvlc.h>
zorglub's avatar
zorglub committed
31

zorglub's avatar
zorglub committed
32
#include <vlc_interface.h>
33
#include <vlc_vlm.h>
zorglub's avatar
zorglub committed
34

35
36
37
38
#include <stdarg.h>
#include <limits.h>
#include <assert.h>

Rémi Denis-Courmont's avatar
Rémi Denis-Courmont committed
39
40
static const char nomemstr[] = "Insufficient memory";

41
libvlc_instance_t * libvlc_new( int argc, const char *const *argv )
42
{
43
44
45
    libvlc_instance_t *p_new = malloc (sizeof (*p_new));
    if (unlikely(p_new == NULL))
        return NULL;
46
47
48

    libvlc_init_threads ();

49
50
51
52
53
54
    const char *my_argv[argc + 2];
    my_argv[0] = "libvlc"; /* dummy arg0, skipped by getopt() et al */
    for( int i = 0; i < argc; i++ )
         my_argv[i + 1] = argv[i];
    my_argv[argc + 1] = NULL; /* C calling conventions require a NULL */

55
56
57
    libvlc_int_t *p_libvlc_int = libvlc_InternalCreate();
    if (unlikely (p_libvlc_int == NULL))
        goto error;
58

59
    if (libvlc_InternalInit( p_libvlc_int, argc + 1, my_argv ))
ivoire's avatar
ivoire committed
60
    {
Rémi Denis-Courmont's avatar
Rémi Denis-Courmont committed
61
        libvlc_InternalDestroy( p_libvlc_int );
62
        goto error;
ivoire's avatar
ivoire committed
63
    }
zorglub's avatar
zorglub committed
64

65
    p_new->p_libvlc_int = p_libvlc_int;
66
67
68
    p_new->libvlc_vlm.p_vlm = NULL;
    p_new->libvlc_vlm.p_event_manager = NULL;
    p_new->libvlc_vlm.pf_release = NULL;
69
    p_new->ref_count = 1;
70
    p_new->verbosity = 1;
71
    p_new->p_callback_list = NULL;
72
    vlc_mutex_init(&p_new->instance_lock);
73
74
    var_Create( p_libvlc_int, "http-user-agent",
                VLC_VAR_STRING|VLC_VAR_DOINHERIT );
zorglub's avatar
zorglub committed
75
    return p_new;
76
77
78
79
80

error:
    libvlc_deinit_threads ();
    free (p_new);
    return NULL;
zorglub's avatar
zorglub committed
81
82
}

83
84
85
86
87
88
89
90
91
92
void libvlc_retain( libvlc_instance_t *p_instance )
{
    assert( p_instance != NULL );
    assert( p_instance->ref_count < UINT_MAX );

    vlc_mutex_lock( &p_instance->instance_lock );
    p_instance->ref_count++;
    vlc_mutex_unlock( &p_instance->instance_lock );
}

93
void libvlc_release( libvlc_instance_t *p_instance )
zorglub's avatar
zorglub committed
94
{
95
96
97
    vlc_mutex_t *lock = &p_instance->instance_lock;
    int refs;

98
    vlc_mutex_lock( lock );
99
    assert( p_instance->ref_count > 0 );
100
    refs = --p_instance->ref_count;
101
    vlc_mutex_unlock( lock );
102
103
104

    if( refs == 0 )
    {
105
        vlc_mutex_destroy( lock );
106
107
        if( p_instance->libvlc_vlm.pf_release )
            p_instance->libvlc_vlm.pf_release( p_instance );
108
        libvlc_InternalCleanup( p_instance->p_libvlc_int );
109
        libvlc_InternalDestroy( p_instance->p_libvlc_int );
110
        free( p_instance );
111
        libvlc_deinit_threads ();
112
    }
zorglub's avatar
zorglub committed
113
}
damienf's avatar
damienf committed
114

115
int libvlc_add_intf( libvlc_instance_t *p_i, const char *name )
116
{
117
    return libvlc_InternalAddIntf( p_i->p_libvlc_int, name ) ? -1 : 0;
118
119
}

120
121
122
123
124
125
126
void libvlc_set_exit_handler( libvlc_instance_t *p_i, void (*cb) (void *),
                              void *data )
{
    libvlc_int_t *p_libvlc = p_i->p_libvlc_int;
    libvlc_SetExitHandler( p_libvlc, cb, data );
}

127
128
129
void libvlc_wait( libvlc_instance_t *p_i )
{
    libvlc_int_t *p_libvlc = p_i->p_libvlc_int;
Rémi Denis-Courmont's avatar
Rémi Denis-Courmont committed
130
    libvlc_InternalWait( p_libvlc );
131
132
}

133
134
135
136
void libvlc_set_user_agent (libvlc_instance_t *p_i,
                            const char *name, const char *http)
{
    libvlc_int_t *p_libvlc = p_i->p_libvlc_int;
137
    char *str;
138
139

    var_SetString (p_libvlc, "user-agent", name);
140
141
142
143
144
145
    if ((http != NULL)
     && (asprintf (&str, "%s LibVLC/"PACKAGE_VERSION, http) != -1))
    {
        var_SetString (p_libvlc, "http-user-agent", str);
        free (str);
    }
146
147
}

Rémi Denis-Courmont's avatar
Rémi Denis-Courmont committed
148
const char * libvlc_get_version(void)
149
{
150
    return VERSION_MESSAGE;
151
152
}

Rémi Denis-Courmont's avatar
Rémi Denis-Courmont committed
153
const char * libvlc_get_compiler(void)
154
155
156
157
{
    return VLC_Compiler();
}

Rémi Denis-Courmont's avatar
Rémi Denis-Courmont committed
158
const char * libvlc_get_changeset(void)
159
{
160
161
    extern const char psz_vlc_changeset[];
    return psz_vlc_changeset;
162
}
163
164
165
166
167

void libvlc_free( void *ptr )
{
    free( ptr );
}
fawek's avatar
fawek committed
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240

libvlc_module_description_t *libvlc_module_description_list_get( libvlc_instance_t *p_instance, const char *capability )
{
    VLC_UNUSED( p_instance );
    libvlc_module_description_t *p_list = NULL,
                          *p_actual = NULL,
                          *p_previous = NULL;
    module_t **module_list = module_list_get( NULL );

    for (size_t i = 0; module_list[i]; i++)
    {
        module_t *p_module = module_list[i];

        if ( !module_provides( p_module, capability ) )
            continue;

        p_actual = ( libvlc_module_description_t * ) malloc( sizeof( libvlc_module_description_t ) );
        if ( p_actual == NULL )
        {
            libvlc_printerr( "Not enough memory" );
            libvlc_module_description_list_release( p_list );
            module_list_free( module_list );
            return NULL;
        }

        if ( p_list == NULL )
            p_list = p_actual;

        const char* name = module_get_object( p_module );
        const char* shortname = module_get_name( p_module, false );
        const char* longname = module_get_name( p_module, true );
        const char* help = module_get_help( p_module );
        p_actual->psz_name = name ? strdup( name ) : NULL;
        p_actual->psz_shortname = shortname ? strdup( shortname ) : NULL;
        p_actual->psz_longname = longname ? strdup( longname ) : NULL;
        p_actual->psz_help = help ? strdup( help ) : NULL;

        p_actual->p_next = NULL;
        if ( p_previous )
            p_previous->p_next = p_actual;
        p_previous = p_actual;
    }

    module_list_free( module_list );
    return p_list;
}

void libvlc_module_description_list_release( libvlc_module_description_t *p_list )
{
    libvlc_module_description_t *p_actual, *p_before;
    p_actual = p_list;

    while ( p_actual )
    {
        free( p_actual->psz_name );
        free( p_actual->psz_shortname );
        free( p_actual->psz_longname );
        free( p_actual->psz_help );
        p_before = p_actual;
        p_actual = p_before->p_next;
        free( p_before );
    }
}

libvlc_module_description_t *libvlc_audio_filter_list_get( libvlc_instance_t *p_instance )
{
    return libvlc_module_description_list_get( p_instance, "audio filter" );
}

libvlc_module_description_t *libvlc_video_filter_list_get( libvlc_instance_t *p_instance )
{
    return libvlc_module_description_list_get( p_instance, "video filter2" );
}
241
242
243
244
245

int64_t libvlc_clock(void)
{
    return mdate();
}