⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 httpd.c

📁 uclinux 下的vlc播放器源代码
💻 C
📖 第 1 页 / 共 5 页
字号:
    if( psz_mime && *psz_mime )    {        stream->psz_mime = strdup( psz_mime );    }    else    {        stream->psz_mime = strdup( httpd_MimeFromUrl( psz_url ) );    }    stream->i_header = 0;    stream->p_header = NULL;    stream->i_buffer_size = 5000000;    /* 5 Mo per stream */    stream->p_buffer = malloc( stream->i_buffer_size );    /* We set to 1 to make life simpler     * (this way i_body_offset can never be 0) */    stream->i_buffer_pos = 1;    stream->i_buffer_last_pos = 1;    httpd_UrlCatch( stream->url, HTTPD_MSG_HEAD, httpd_StreamCallBack,                    (httpd_callback_sys_t*)stream );    httpd_UrlCatch( stream->url, HTTPD_MSG_GET, httpd_StreamCallBack,                    (httpd_callback_sys_t*)stream );    httpd_UrlCatch( stream->url, HTTPD_MSG_POST, httpd_StreamCallBack,                    (httpd_callback_sys_t*)stream );    return stream;}int httpd_StreamHeader( httpd_stream_t *stream, uint8_t *p_data, int i_data ){    vlc_mutex_lock( &stream->lock );    if( stream->p_header )    {        free( stream->p_header );        stream->p_header = NULL;    }    stream->i_header = i_data;    if( i_data > 0 )    {        stream->p_header = malloc( i_data );        memcpy( stream->p_header, p_data, i_data );    }    vlc_mutex_unlock( &stream->lock );    return VLC_SUCCESS;}int httpd_StreamSend( httpd_stream_t *stream, uint8_t *p_data, int i_data ){    int i_count;    int i_pos;    if( i_data < 0 || p_data == NULL )    {        return VLC_SUCCESS;    }    vlc_mutex_lock( &stream->lock );    /* save this pointer (to be used by new connection) */    stream->i_buffer_last_pos = stream->i_buffer_pos;    i_pos = stream->i_buffer_pos % stream->i_buffer_size;    i_count = i_data;    while( i_count > 0)    {        int i_copy;        i_copy = __MIN( i_count, stream->i_buffer_size - i_pos );        /* Ok, we can't go past the end of our buffer */        memcpy( &stream->p_buffer[i_pos], p_data, i_copy );        i_pos = ( i_pos + i_copy ) % stream->i_buffer_size;        i_count -= i_copy;        p_data  += i_copy;    }    stream->i_buffer_pos += i_data;    vlc_mutex_unlock( &stream->lock );    return VLC_SUCCESS;}void httpd_StreamDelete( httpd_stream_t *stream ){    httpd_UrlDelete( stream->url );    vlc_mutex_destroy( &stream->lock );    if( stream->psz_mime ) free( stream->psz_mime );    if( stream->p_header ) free( stream->p_header );    if( stream->p_buffer ) free( stream->p_buffer );    free( stream );}/***************************************************************************** * Low level *****************************************************************************/static void httpd_HostThread( httpd_host_t * );/* create a new host */httpd_host_t *httpd_HostNew( vlc_object_t *p_this, const char *psz_host,                             int i_port ){    return httpd_TLSHostNew( p_this, psz_host, i_port, NULL, NULL, NULL, NULL                           );}httpd_host_t *httpd_TLSHostNew( vlc_object_t *p_this, const char *psz_hostname,                                int i_port,                                const char *psz_cert, const char *psz_key,                                const char *psz_ca, const char *psz_crl ){    httpd_t      *httpd;    httpd_host_t *host;    tls_server_t *p_tls;    char *psz_host;    vlc_value_t  lockval;    int i;    if( psz_hostname == NULL )        psz_hostname = "";    psz_host = strdup( psz_hostname );    if( psz_host == NULL )    {        msg_Err( p_this, "memory error" );        return NULL;    }    /* to be sure to avoid multiple creation */    var_Create( p_this->p_libvlc, "httpd_mutex", VLC_VAR_MUTEX );    var_Get( p_this->p_libvlc, "httpd_mutex", &lockval );    vlc_mutex_lock( lockval.p_address );    if( !(httpd = vlc_object_find( p_this, VLC_OBJECT_HTTPD, FIND_ANYWHERE )) )    {        msg_Info( p_this, "creating httpd" );        if( ( httpd = vlc_object_create( p_this, VLC_OBJECT_HTTPD ) ) == NULL )        {            vlc_mutex_unlock( lockval.p_address );            free( psz_host );            return NULL;        }        httpd->i_host = 0;        httpd->host   = NULL;        vlc_object_yield( httpd );        vlc_object_attach( httpd, p_this->p_vlc );    }    /* verify if it already exist */    for( i = httpd->i_host - 1; i >= 0; i-- )    {        host = httpd->host[i];        /* cannot mix TLS and non-TLS hosts */        if( ( ( httpd->host[i]->p_tls != NULL ) != ( psz_cert != NULL ) )         || ( host->i_port != i_port )         || strcmp( host->psz_hostname, psz_hostname ) )            continue;        /* yep found */        host->i_ref++;        vlc_mutex_unlock( lockval.p_address );        return host;    }    host = NULL;    /* determine TLS configuration */    if ( psz_cert != NULL )    {        p_tls = tls_ServerCreate( p_this, psz_cert, psz_key );        if ( p_tls == NULL )        {            msg_Err( p_this, "TLS initialization error" );            goto error;        }        if ( ( psz_ca != NULL) && tls_ServerAddCA( p_tls, psz_ca ) )        {            msg_Err( p_this, "TLS CA error" );            goto error;        }        if ( ( psz_crl != NULL) && tls_ServerAddCRL( p_tls, psz_crl ) )        {            msg_Err( p_this, "TLS CRL error" );            goto error;        }    }    else        p_tls = NULL;    /* create the new host */    host = vlc_object_create( p_this, VLC_OBJECT_HTTPD_HOST );    host->httpd = httpd;    vlc_mutex_init( httpd, &host->lock );    host->i_ref = 1;    host->fd = net_ListenTCP( p_this, psz_host, i_port );    if( host->fd == NULL )    {        msg_Err( p_this, "cannot create socket(s) for HTTP host" );        goto error;    }    host->i_port = i_port;    host->psz_hostname = psz_host;    host->i_url     = 0;    host->url       = NULL;    host->i_client  = 0;    host->client    = NULL;    host->p_tls = p_tls;    /* create the thread */    if( vlc_thread_create( host, "httpd host thread", httpd_HostThread,                           VLC_THREAD_PRIORITY_LOW, VLC_FALSE ) )    {        msg_Err( p_this, "cannot spawn http host thread" );        goto error;    }    /* now add it to httpd */    TAB_APPEND( httpd->i_host, httpd->host, host );    vlc_mutex_unlock( lockval.p_address );    return host;error:    free( psz_host );    if( httpd->i_host <= 0 )    {        vlc_object_release( httpd );        vlc_object_detach( httpd );        vlc_object_destroy( httpd );    }    vlc_mutex_unlock( lockval.p_address );    if( host != NULL )    {        net_ListenClose( host->fd );        vlc_mutex_destroy( &host->lock );        vlc_object_destroy( host );    }    if( p_tls != NULL )        tls_ServerDelete( p_tls );    return NULL;}/* delete a host */void httpd_HostDelete( httpd_host_t *host ){    httpd_t *httpd = host->httpd;    vlc_value_t lockval;    int i;    var_Get( httpd->p_libvlc, "httpd_mutex", &lockval );    vlc_mutex_lock( lockval.p_address );    host->i_ref--;    if( host->i_ref > 0 )    {        /* still used */        vlc_mutex_unlock( lockval.p_address );        msg_Dbg( host, "httpd_HostDelete: host still used" );        return;    }    TAB_REMOVE( httpd->i_host, httpd->host, host );    host->b_die = 1;    vlc_thread_join( host );    msg_Dbg( host, "HTTP host removed" );    for( i = 0; i < host->i_url; i++ )    {        msg_Err( host, "url still registered: %s", host->url[i]->psz_url );    }    for( i = 0; i < host->i_client; i++ )    {        httpd_client_t *cl = host->client[i];        msg_Warn( host, "client still connected" );        httpd_ClientClean( cl );        TAB_REMOVE( host->i_client, host->client, cl );        free( cl );        i--;        /* TODO */    }    if( host->p_tls != NULL)        tls_ServerDelete( host->p_tls );    net_ListenClose( host->fd );    free( host->psz_hostname );    vlc_mutex_destroy( &host->lock );    vlc_object_destroy( host );    vlc_object_release( httpd );    if( httpd->i_host <= 0 )    {        msg_Dbg( httpd, "no host left, stopping httpd" );        vlc_object_detach( httpd );        vlc_object_destroy( httpd );    }    vlc_mutex_unlock( lockval.p_address );}/* register a new url */static httpd_url_t *httpd_UrlNewPrivate( httpd_host_t *host, const char *psz_url,                                         const char *psz_user, const char *psz_password,                                         const vlc_acl_t *p_acl, vlc_bool_t b_check ){    httpd_url_t *url;    int         i;    vlc_mutex_lock( &host->lock );    if( b_check )    {        for( i = 0; i < host->i_url; i++ )        {            if( !strcmp( psz_url, host->url[i]->psz_url ) )            {                msg_Warn( host->httpd,                          "cannot add '%s' (url already defined)", psz_url );                vlc_mutex_unlock( &host->lock );                return NULL;            }        }    }    url = malloc( sizeof( httpd_url_t ) );    url->host = host;    vlc_mutex_init( host->httpd, &url->lock );    url->psz_url = strdup( psz_url );    url->psz_user = strdup( psz_user ? psz_user : "" );    url->psz_password = strdup( psz_password ? psz_password : "" );    url->p_acl = ACL_Duplicate( host, p_acl );    for( i = 0; i < HTTPD_MSG_MAX; i++ )    {        url->catch[i].cb = NULL;        url->catch[i].p_sys = NULL;    }    TAB_APPEND( host->i_url, host->url, url );    vlc_mutex_unlock( &host->lock );    return url;}httpd_url_t *httpd_UrlNew( httpd_host_t *host, const char *psz_url,                           const char *psz_user, const char *psz_password,                           const vlc_acl_t *p_acl ){    return httpd_UrlNewPrivate( host, psz_url, psz_user,                                psz_password, p_acl, VLC_FALSE );}httpd_url_t *httpd_UrlNewUnique( httpd_host_t *host, const char *psz_url,                                 const char *psz_user, const char *psz_password,                                 const vlc_acl_t *p_acl ){    return httpd_UrlNewPrivate( host, psz_url, psz_user,                                psz_password, p_acl, VLC_TRUE );}/* register callback on a url */int httpd_UrlCatch( httpd_url_t *url, int i_msg, httpd_callback_t cb,                    httpd_callback_sys_t *p_sys ){    vlc_mutex_lock( &url->lock );    url->catch[i_msg].cb   = cb;    url->catch[i_msg].p_sys= p_sys;    vlc_mutex_unlock( &url->lock );    return VLC_SUCCESS;}/* delete an url */void httpd_UrlDelete( httpd_url_t *url ){    httpd_host_t *host = url->host;    int          i;    vlc_mutex_lock( &host->lock );    TAB_REMOVE( host->i_url, host->url, url );    vlc_mutex_destroy( &url->lock );    free( url->psz_url );    free( url->psz_user );    free( url->psz_password );    ACL_Destroy( url->p_acl );    for( i = 0; i < host->i_client; i++ )    {        httpd_client_t *client = host->client[i];        if( client->url == url )        {            /* TODO complete it */            msg_Warn( host, "force closing connections" );            httpd_ClientClean( client );            TAB_REMOVE( host->i_client, host->client, client );            free( client );            i--;        }    }    free( url );    vlc_mutex_unlock( &host->lock );}void httpd_MsgInit( httpd_message_t *msg ){    msg->cl         = NULL;    msg->i_type     = HTTPD_MSG_NONE;    msg->i_proto    = HTTPD_PROTO_NONE;    msg->i_version  = -1;    msg->i_status   = 0;    msg->psz_status = NULL;    msg->psz_url    = NULL;    msg->psz_args   = NULL;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -