[vlc-devel] [PATCH V5] dcp: Creation of access-demux module for DCP

Nicolas Bertrand nicoinattendu at gmail.com
Tue Oct 8 17:11:58 CEST 2013


Thanks for the comment

First I address the main issue ( comment below)
in next mails the others

>> +int parserAssetmapXML ( demux_t * p_demux )
>> +{
>> +    dcp_t *p_dcp = p_demux->p_sys->p_dcp;
>> +    int type = 0;
>> +    const char* node = NULL;
>> +    int packinglist = 0;
>> +    int file_number = 0;
>> +    int asset_list = 0;
>> +    string filepath;
>> +    stream_t *p_stream = NULL;
>> +    xml_t *p_xml = NULL;
>> +    xml_reader_t *p_xmlReader = NULL;
>> +
>> +    /* init XML parser */
>> +    if( initXMLParser( p_demux, p_dcp->assetmapURI, &p_stream, &p_xml, &p_xmlReader ) )
>> +    {
>> +        msg_Err( p_demux, "Failed to initialize XML parser" );
>> +        goto error;
>> +    }
>> +
>> +    /* reading XML file ( node by node ) */
>> +    msg_Dbg( p_demux, "reading ASSETMAP file..." );
>> +    while( ( type = xml_ReaderNextNode( p_xmlReader, &node ) ) > 0 )
>> +    {
>> +        /* This condition determines if we are in AssetList part or not */
>> +        if( ( type == XML_READER_STARTELEM ) && ( strcasecmp( node, "AssetList" ) == 0 ) )
>> +        {
>> +            asset_list = 1;
>> +            continue;
>> +        }
>> +
>> +        /* When we are in AssetList part */
>> +        if( asset_list == 1 )
>> +        {
>> +            /* Set the UID of the file */
>> +            if( ( type == XML_READER_STARTELEM ) && ( strcasecmp( node, "Id" ) == 0 ) )
>> +            {
>> +                if( ( type = xml_ReaderNextNode( p_xmlReader, &node ) ) != XML_READER_TEXT )
>> +                {
>> +                    msg_Err( p_demux, "Id missing in ASSETMAP!" );
>> +                    goto error;
>> +                }
>> +                else
>> +                {
>> +                    p_dcp->files[ file_number ] = new ( nothrow ) file_t;
>> +                    if( !p_dcp->files[ file_number ] )
>> +                    {
>> +                        goto error;
>> +                    }
>> +                    if( node != NULL )
>> +                        p_dcp->files[file_number]->id = node;
>> +                    continue;
>> +                }
>> +            }
>> +
>> +            /* It determines if it is PKL File or not */
>> +            /* For PKL File, we have : <PackingList>true</PackingList> */
>> +            /* This tag seems to be used only for PKL file */
>> +            if( ( type == XML_READER_STARTELEM ) && ( strcasecmp ( node, "PackingList" ) == 0 ) )
>> +            {
>> +                packinglist = 1; /* next path info will be for PKL file */
>> +                continue;
>> +            }
>> +
>> +            /* Set the Path of the file */
>> +            /* If the file is an XML file, it is the PKL file or the CPL file */
>> +            if( ( type == XML_READER_STARTELEM ) && ( strcasecmp( node, "Path" ) == 0 ) )
>> +            {
>> +                if( ( type = xml_ReaderNextNode( p_xmlReader, &node ) ) != XML_READER_TEXT )
>> +                {
>> +                    msg_Err( p_demux, "Path missing in ASSETMAP" );
>> +                    goto error;
>> +                }
>> +                else
>> +                {
>> +                    filepath = p_dcp->path + node;
>> +                    if( endsWith( node, ".xml" ) )
>> +                    {
>> +                        if( packinglist == 1 )
>> +                        {
>> +                            /* it is PKL file name */
>> +                            p_dcp->pklfile = filepath;
>> +                            p_dcp->files[file_number]->path = filepath;
>> +                            packinglist = 0;
>> +                        }
>> +                        else
>> +                        {
>> +                            /* it is CPL file name */
>> +                            p_dcp->cplfileURI = vlc_path2uri( filepath.c_str(), "file" );
>> +                            p_dcp->files[file_number]->path = filepath;
>> +                        }
>> +                    }
>> +                    else
>> +                    {
>> +                        /* it is an other file (MXF in theory) */
>> +                        p_dcp->files[file_number]->path = filepath;
>> +                    }
>> +                    file_number++;
> I think this segfaults your file has Path before Id and leaks if the
> file is corrupted and don't have a Path

Yes, you are right, it would be much more cleaner to completely parse 
the XML assetmap file, create a structure according.
And then search for PKLs, CPLs and MXF files in the structuren intead of 
mixing it all.

>> +                }
>> +            }
>> +        }
>> +    }
>> +    if( asset_list == 0 )
>> +    {
>> +        msg_Err( p_demux, "Could not find AssetList tag in ASSETMAP" );
>> +        goto error;
>> +    }
>> +
>> +    if( !p_dcp->cplfileURI )
>> +    {
>> +        msg_Err( p_demux, "Could not find CPL file in ASSETMAP" );
>> +        goto error;
>> +    }
>> +    if( p_dcp->pklfile.empty() )
>> +    {
>> +        msg_Err( p_demux, "Could not find PKL file in ASSETMAP" );
>> +        goto error;
>> +    }
>> +
>> +    /* Set the number of files described in ASSETMAP file */
>> +    p_dcp->nb_files = file_number;
>> +
>> +    /* free memory */
>> +    freeMemXML( p_xmlReader, p_xml, p_stream );
>> +    return VLC_SUCCESS;
>> +
>> +error:
>> +    freeMemXML( p_xmlReader, p_xml, p_stream );
>> +    return VLC_EGENERIC;
>> +}
>> +
>> +/**
>> + * Function to found a MXF File in DCP directory.
>> + * Return True if file is found and update dcp strucure with
>> + * filepath accodring MXD media type
>> + * @param pp_dcp    dcp sturcture (in/out)
>> + * @param uuid      UUID of MXF file to found
>> + * @param MxfMedia  Type of Media to found ans store
>> + */
>> +
>> +static bool foundMxfFile(dcp_t **pp_dcp, const char *uuid, MxfMedia_t MxfMedia )
>> +{
>> +    bool found = false;
>> +    int i;
>> +    dcp_t *p_dcp = *pp_dcp;
>> +    for( i = 0; i < p_dcp->nb_files; i++ ) {
>> +        if( p_dcp->files[i]->id.compare( uuid ) == 0 ) {
>> +            switch (MxfMedia) {
>> +                case MXF_PICTURE:
>> +                    p_dcp->videofile = p_dcp->files[i]->path;
>> +                    found = true;
>> +                    break;
>> +                case MXF_AUDIO:
>> +                    p_dcp->audiofile = p_dcp->files[i]->path;
>> +                    found = true;
>> +                    break;
>> +                case MXF_UNKNOWN:
>> +                default:
>> +                    found = false;
> useless
>> +            }
>> +            if (found)
>> +                break;
>> +        }
>> +    }
>> +    return found;
>> +}
>> +/**
>> + * Function to parse the CPL file in order to retrieve UID of video and audio files.
>> + * When it is done, we can determine path to video and audio files using information
>> + * about files described in ASSETMAP file
>> + * @param p_demux DCP access_demux.
>> + */
>> +int parseCplXML ( demux_t * p_demux )
>> +{
>> +    dcp_t *p_dcp = p_demux->p_sys->p_dcp;
>> +    int type = 0;
>> +    const char *node = NULL;
>> +    stream_t *p_stream = NULL;
>> +    xml_t *p_xml = NULL;
>> +    xml_reader_t *p_xmlReader = NULL;
>> +
>> +    /* init XML reader */
>> +    if( initXMLParser( p_demux, p_dcp->cplfileURI, &p_stream, &p_xml, &p_xmlReader ) )
>> +    {
>> +        msg_Err( p_demux, "Failed to initialize XML parser" );
>> +        goto error;
>> +    }
>> +
>> +    /* Read XML file node by node */
>> +    msg_Dbg( p_demux, "reading CPL file..." );
>> +    while ( ( type = xml_ReaderNextNode( p_xmlReader, &node ) ) > 0 )
>> +    {
>> +        /* MainPicture data */
>> +        if ( ( type == XML_READER_STARTELEM) && ( strcasecmp( node, "MainPicture" ) == 0 || strcasecmp( node, "MainStereoscopicPicture" ) == 0 ) )
>> +        {
>> +            /* searching for the Id of the picture file */
>> +            while ( ( type = xml_ReaderNextNode( p_xmlReader, &node ) ) > 0 )
>> +            {
>> +                if ( ( type == XML_READER_STARTELEM ) && ( strcasecmp( node, "Id" ) == 0 ) )
>> +                {
>> +                    if (    ((type = xml_ReaderNextNode(p_xmlReader, &node ) == XML_READER_TEXT))
>> +                            &&
>> +                            (foundMxfFile(&p_dcp, node, MXF_PICTURE)))
>> +                        break;
>> +                     else {
>> +                        msg_Err( p_demux, "MainPicture Id missing in CPL!" );
>> +                        goto error;
>> +                    }
>> +                }
>> +            }
>> +        }
>> +
>> +        /* MainSound data */
>> +        if( ( type == XML_READER_STARTELEM) && ( strcasecmp( node, "MainSound" ) == 0 ) )
>> +        {
>> +            /* searching for the Id of the audio file */
>> +            while( ( type = xml_ReaderNextNode( p_xmlReader, &node ) ) > 0 )
>> +            {
>> +                if( ( type == XML_READER_STARTELEM ) && ( strcasecmp( node, "Id" ) == 0 ) )
>> +                {
>> +                    if (    (type = xml_ReaderNextNode( p_xmlReader, &node) == XML_READER_TEXT)
>> +                            &&
>> +                            (foundMxfFile(&p_dcp, node, MXF_AUDIO)))
>> +                        break;
>> +                    else {
>> +                        msg_Err( p_demux, "MainSound Id missing in CPL!" );
>> +                        goto error;
>> +                    }
>> +                }
>> +            }
>> +        }
>> +    }
>> +
>> +    if( p_dcp->videofile.empty() )
>> +    {
>> +        msg_Err( p_demux, "Could not find video file in ASSETMAP" );
>> +        goto error;
>> +    }
>> +
>> +    if( p_dcp->audiofile.empty() )
>> +    {
>> +        msg_Err( p_demux, "Could not find audio file in ASSETMAP" );
>> +        goto error;
>> +    }
>> +
>> +    /* free memory */
>> +    freeMemXML( p_xmlReader, p_xml, p_stream );
>> +    return VLC_SUCCESS;
>> +
>> +error:
>> +    freeMemXML( p_xmlReader, p_xml, p_stream );
>> +    return VLC_EGENERIC;
>> +}
>> +
>> +
>> +/**
>> + * Function which parses XML files in DCP directory in order to get video and audio files
>> + * @param p_demux Demux pointer.
>> + * @return Integer according to the success or not of the operation
>> + */
>> +int parseXML ( demux_t * p_demux )
>> +{
>> +    int retval;
>> +    /* We get the ASSETMAP file path */
>> +    if( assetmapPath( p_demux ) )
>> +        return VLC_EGENERIC;
>> +
>> +    /* We parse the ASSETMAP File in order to get CPL File path, PKL File path
>> +     and to store UID/Path of all files in DCP directory (except ASSETMAP file) */
>> +    if( ( retval = parserAssetmapXML( p_demux ) ) )
>> +        return retval;
>> +
>> +    /* We parse the CPL File : in order to retrieve video and audio files
>> +     according to UID of files described in CPL XML file */
>> +    if( ( retval = parseCplXML( p_demux ) ) )
>> +        return retval;
>> +
>> +    return VLC_SUCCESS; /* TODO : perform checking on XML parsing */
>> +}
>
> Regards,
>




More information about the vlc-devel mailing list