[MPlayer-dev-eng] Re: [PATCH] edl now works when seeking, more

Attila Kinali attila at kinali.ch
Sat Aug 28 07:54:50 CEST 2004


On Thu, Aug 26, 2004 at 10:55:28PM -0400, Reynaldo H. Verdejo Pinochet wrote:
> On Thu, Aug 26, 2004 at 04:14:02PM +0900, Attila Kinali wrote:
> > On Wed, Aug 25, 2004 at 01:39:14AM -0400, Reynaldo H. Verdejo Pinochet wrote:
> > 
> > > Hope to get mencoder's edl working this weekend, please review and
> > > apply this patches ASAP
> > 
> > Patch needs to be reworked, detailed analysis given on irc.
> > 
> > 		Attila Kinali
> reworked
> 
> Regards
> 
>   Reynaldo
> 

> --- mplayer.c	2004-08-26 18:51:10.000000000 -0400
> +++ ../my_main/mplayer.c	2004-08-26 21:39:28.000000000 -0400
 - }
> +if (edl_check_mode() == EDL_ERROR && edl_filename)
> +{
> +    mp_msg(MSGT_CPLAYER, MSGL_WARN,
> +           "Cant use -edl and -edlout at the same time\n");
> +    mp_msg(MSGT_CPLAYER, MSGL_WARN, "Not using EDL at all!!!\n");

MSGL_WARN -> MSGL_ERR, fail end exit.

> +    edl_filename = NULL;
> +    edl_output_filename = NULL;
> +    edl_records = NULL;
> +    next_edl_record = edl_records;
> +} else if (edl_filename)
> +{
> +    edl_memory_slots = edl_count_entries();
> +    if (edl_memory_slots > 0)
> +    {
> +        edl_records = calloc(edl_memory_slots, sizeof(struct edl_record));

When is this memory freed again ?

> +        if (edl_records == NULL)
> +        {
> +            mp_msg(MSGT_CPLAYER, MSGL_FATAL,
> +                   "Cant allocate enough memory to hold EDL data, exiting!\n");
> +            exit_player(NULL);	    
> +        } else
> +        {
> +            if ((edl_operations = edl_parse_file(edl_records)) > 0)
> +            {
> +                mp_msg(MSGT_CPLAYER, MSGL_INFO, "Readed %d EDL actions\n",
> +                       edl_operations);
> +            } else
> +            {
> +
> +                mp_msg(MSGT_CPLAYER, MSGL_INFO,
> +                       "There are no EDL actions to take care of\n");
> +            }
> +        }
> +    }
> +
> +    next_edl_record = edl_records;
> +
> +} else if (edl_output_filename)
> +{
> +    if ((edl_fd = fopen(edl_output_filename, "w")) == NULL)
> +    {
> +        mp_msg(MSGT_CPLAYER, MSGL_WARN, 
> +	       "Error opening file [%s] for writing!\n",
> +               edl_output_filename);

MSGL_WARN -> MSGL_ERR, fail end exit.

> +        edl_output_filename = NULL;
> +        next_edl_record = edl_records;
> +    }
> +}
>  #endif
>  
>      if(!filename){
> @@ -2493,7 +2447,7 @@
>  //================= EDL =========================================
>  
>  #ifdef USE_EDL
> - if( next_edl_record->next ) { // Are we (still?) doing EDL?
> + if( next_edl_record ) { // Are we (still?) doing EDL?
>    if ( !sh_video ) {
>      mp_msg( MSGT_CPLAYER, MSGL_ERR, "Cannot use edit list without video. EDL disabled.\n" );
>      next_edl_record->next = NULL;
> @@ -2507,15 +2461,15 @@
>         printf( "\nEDL_SKIP: start [%f], stop [%f], length [%f]\n", next_edl_record->start_sec, next_edl_record->stop_sec, next_edl_record->length_sec );
>  #endif
>         edl_decision = 1;
> -       next_edl_record = next_edl_record->next;
>       } else if( next_edl_record->action == EDL_MUTE ) {
>         mixer_mute(&mixer);
> +       edl_mute_count++; // new edl seek behavior need this
>  #ifdef DEBUG_EDL
>         printf( "\nEDL_MUTE: [%f]\n", next_edl_record->start_sec );
>  #endif
>         edl_decision = 1;
> -       next_edl_record = next_edl_record->next;
>       }
> +     next_edl_record=next_edl_record->next;
>     }
>    }
>   }
> @@ -3548,20 +3502,52 @@
>        }
>    }
>  #ifdef USE_EDL
> -      {
> -	int x;
> -	if( !edl_decision ) {
> -	  for( x = 0; x < num_edl_records; x++ ) { // FIXME: do binary search
> -	    // Find first EDL entry where start follows current time
> -	    if( edl_records[ x ].start_sec >= sh_video->pts && edl_records[ x ].action != EDL_MUTE ) {
> -	      next_edl_record = &edl_records[ x ];
> -	      break;
> -	    }
> -	  }
> -	} else {
> -	  edl_decision = 0;
> -	}
> -      }
> +/*
> + * We Saw a seek, have to rewind the edl operations stak
> + * and find the next edl action to take care off
> + */

Saw -> saw :)

> +
> +next_edl_record = edl_records;
> +
> +while (next_edl_record)
> +{
> +    /* trying to remember if we need to mute/unmute first
> +     * prior edl implementation lacks this
> +     */
> +  
> +    if (next_edl_record->start_sec >= sh_video->pts)
> +    {
> +        if (edl_mute_count > 0)
> +        {
> +            if ((edl_mute_count % 2) == 0 &&
> +                next_edl_record->mute_state == EDL_MUTE_END)
> +            {
> +                mixer_mute(&mixer);
> +                edl_mute_count++;
> +            }
> +            if ((edl_mute_count % 2) != 0 &&
> +                next_edl_record->mute_state == EDL_MUTE_START)
> +            {
> +                mixer_mute(&mixer);
> +                edl_mute_count++;
> +            }
> +        } else if (next_edl_record->mute_state == EDL_MUTE_END)
> +        {
> +            mixer_mute(&mixer);
> +            edl_mute_count++;
> +        }
> +        break;
> +    }
> +
> +    next_edl_record = next_edl_record->next;
> +
> +    if (!next_edl_record && (edl_mute_count % 2) != 0
> +        && edl_mute_count > 0)
> +    {
> +        mixer_mute(&mixer);
> +        edl_mute_count++;
> +    }
> +}
>  #endif
>    rel_seek_secs=0;
>    abs_seek_pos=0;

> --- /dev/null	2004-08-08 23:33:15.000000000 -0400
> +++ edl.c	2004-08-26 22:04:34.000000000 -0400
> @@ -0,0 +1,161 @@
> +#include <stdio.h>
> +#include <stdlib.h>
> +#include "config.h"
> +#include "mp_msg.h"
> +#include "edl.h"
> +
> +#ifdef USE_EDL
> +
> +int edl_check_mode(void)
> +{
> +    if (edl_filename && edl_output_filename)
> +    {
> +        return (EDL_ERROR);
> +    }
> +
> +    return (1);
> +}
> +
> +int edl_count_entries(void)
> +{
> +    FILE *fd = NULL;
> +    int entries = 0;
> +    int action = 0;
> +    float start = 0;
> +    float stop = 0;
> +    char line[100];
> +
> +    if (edl_filename)
> +    {
> +        if ((fd = fopen(edl_filename, "r")) == NULL)
> +        {
> +            mp_msg(MSGT_CPLAYER, MSGL_WARN,
> +                   "Invalid EDL file, cant open '%s' for reading!\n",
> +                   edl_filename);
> +            return (EDL_ERROR);
> +        } else
> +        {
> +            while (fgets(line, 99, fd) != NULL)
> +            {
> +                if ((sscanf(line, "%f %f %d", &start, &stop, &action)) ==
> +                    3)
> +                {
> +                    if (action == EDL_SKIP)
> +                        entries += 1;
> +                    if (action == EDL_MUTE)
> +                        entries += 2;
> +                } else
> +                {
> +                    mp_msg(MSGT_CPLAYER, MSGL_WARN,
> +                           "Invalid EDL line: %s\n", line);
> +                    return (EDL_ERROR);
> +                }
> +
> +            }
> +        }
> +    } else
> +    {
> +        return (EDL_ERROR);
> +    }
> +
> +    return (entries);
> +}
> +
> +int edl_parse_file(edl_record_ptr edl_records)
> +{
> +    FILE *fd;
> +    char line[100];
> +    float start, stop;
> +    int action;
> +    int record_count = 0;
> +    int lineCount = 0;
> +    struct edl_record *next_edl_record = edl_records;
> +
> +    if (edl_filename)
> +    {
> +        if ((fd = fopen(edl_filename, "r")) == NULL)
> +        {
> +            return (EDL_ERROR);
> +        } else
> +        {
> +            while (fgets(line, 99, fd) != NULL)
> +            {
> +                lineCount++;
> +                if ((sscanf(line, "%f %f %d", &start, &stop, &action))
> +                    != 3)
> +                {
> +                    mp_msg(MSGT_CPLAYER, MSGL_WARN,
> +                           "Badly formated EDL line [%d]. Discarding!\n",
> +                           lineCount + 1, line);
> +                    continue;
> +                } else
> +                {
> +                    if (record_count > 0)
> +                    {
> +                        if (start <= (next_edl_record - 1)->stop_sec)
> +                        {
> +                            mp_msg(MSGT_CPLAYER, MSGL_WARN,
> +                                   "Invalid EDL line [%d]: %s",
> +                                   lineCount, line);
> +                            mp_msg(MSGT_CPLAYER, MSGL_WARN,
> +                                   "Last stop position was [%f]; next start is [%f]. Entries must be in chronological order and cannot overlap. Discarding!\n",
> +                                   (next_edl_record - 1)->stop_sec, start);
> +                            continue;
> +                        }
> +                    }
> +                    if (stop <= start)
> +                    {
> +                        mp_msg(MSGT_CPLAYER, MSGL_WARN,
> +                               "Invalid EDL line [%d]: %s", lineCount,
> +                               line);
> +                        mp_msg(MSGT_CPLAYER, MSGL_WARN,
> +                               "Stop time must follow start time. Discarding!\n");

"Stop time has to be after start time"
"follow" is not clear in this case.


Other than that, you should add doxygen (doxygen.sf.net) style
comments to all functions and global variables.
I'll try to write some docu about this as soon as possible.


			Attila Kinali




More information about the MPlayer-dev-eng mailing list