[MPlayer-dev-eng] mplayer slave mode question

Reimar Döffinger Reimar.Doeffinger at stud.uni-karlsruhe.de
Tue Aug 28 08:33:16 CEST 2007


Hello,
On Mon, Aug 27, 2007 at 05:45:17PM -0500, Kevron Rees wrote:
>  >>From pygme's homepage(http://pygme.sourceforge.net):
> >>
> >> "There's no way one can get information from audio and video files
> >> without duplicating the work already being done in mplayer."
> >>
> >>Is this true? I've run into the same issue in my c++ program using
> >> fork() and pipe().
> >>
> >> and suggestions on how we can fix this issue?
> >
> >-identify?
> 
> From my experience, I can successfully pipe commands to mplayer through
> mplayer's stdin.  I can also create a pipe from mplayer's stdout but
> whenever I retrieve info from mplayer via that fd, I get blocking and my
> program locks up.

At which point it changes from an MPlayer question to "how to use my
favorite programming language".
But anyway, as soon as you don't close the other side of the pipe on
your end you don't magically get a broken pipe when your forked process
dies but instead your application waits for input from itself.
The solution is to simply use two pipe. Though using select or
non-blocking reads wouldn't hurt either then at least your application
won't hang just because MPlayer does.

> To work around this problem, I want to be able to pipe mplayer's stdout
> to a file in which I can just purge anytime I want new data.  However, I
> don't know how I can do this.  Mplayer doesn't have a -stdout=foo.txt
> does it?

What for? I recommend reading the man page for fork, exec and dup2 and
just set stdout to that textfile if you really want, just like the shell
would do.
Btw. these 26 lines of code are enough for two-way communication (and
yes I know that -frames 0 would have made much more sense than sending
"quit").
You might want to consider using fdopen and fgets instead of read to get
the output pre-split by lines.

#include <unistd.h>
#include <stdio.h>
int main(void) {
  int pipefds1[2];
  int pipefds2[2];
  int child;
  pipe(pipefds1);
  pipe(pipefds2);
  child = fork();
  close(pipefds1[!!child]);
  close(pipefds2[!child]);
  if (!child) {
    dup2(pipefds1[1], 1);
    dup2(pipefds2[0], 0);
    execlp("mplayer", "mplayer", "-slave", "-identify", "test.avi",
NULL);
  } else {
    char buf[100];
    int r;
    write(pipefds2[1], "quit\n", 5);
    while ((r = read(pipefds1[0], buf, 100)) > 0) {
      buf[r] = 0;
      printf("MPlayer out: %s\n", buf);
    }
  }
  return 0;
}

Greetings,
Reimar Döffinger



More information about the MPlayer-dev-eng mailing list