1

I want to make a function in c, that will capture video under Linux. I embedded ffmpeg command via system() in my c program, which captures video. ffmpeg terminates by pressing [q]. How can I include termination into my c program.

This function is part of a server.c program. When client requests for termination, I want video cature function to terminate. Is this possible?

#include<stdio.h>
#include <string.h>


main()
{

char command[180];

sprintf(command, "ffmpeg -f v4l2 -r 25 -s 640x480 -i /dev/video0 out.avi");
system(command);

}
dempap
  • 352
  • 1
  • 9
  • 21
  • 1
    system is synchronous, it wan't exit until your child process not done. Maybe somehow from another thread,actually i'm not even sure it is possible.Maybe just don't use system, and use fork(), execv(), and then kill whenever you decide to stop the child process – Dabo Feb 17 '14 at 15:00
  • Maybe this will help: http://www.thegeekstuff.com/2012/03/catch-signals-sample-c-code/ – Fiddling Bits Feb 17 '14 at 15:19
  • 1
    @FiddlingBits: It won't, as the OP is using the ready-made `ffmpeg` and therefore has no possibilty to make it catch any signals to behave specially. The OP should go the `fork()`-, `exec*()`-, `kill()`-child path as proposed by *Dabo* in his comment or implement the necessary functionality directly by using `ffmpegs` C-interface. If going this latter way, implementing signal handling on the other hand might be necessary and helpful. – alk Feb 17 '14 at 16:50
  • @alk Is a sample code possible? – dempap Feb 17 '14 at 17:08
  • This won't be a a three liner. So for `fork()`and `exec*()` this might be an intro: http://stackoverflow.com/q/1653340/694576 For signal handling there are various answers on this site and also you have the link provided by *Fiddling Bits* in his comment. For how to use `ffmpeg`'s C-interface you might like to dig around here: http://ffmpeg.org/ A starting point would be to look at the sources of `ffmpeg` itself. – alk Feb 17 '14 at 17:12

1 Answers1

1

As you asked sample for fork, exec, kill here is possible solution. avconv is replacement for ffmpeg on my pc.

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <signal.h>
#include <errno.h>
#include <assert.h>
#include <unistd.h>
#include <sched.h>
#include <sys/wait.h>

pid_t parent_pid;

void sigquit_handler (int sig)
{
    assert(sig == SIGKILL);
    pid_t self = getpid();
    if (parent_pid != self)
    {
        printf("recording done");
        _exit(0);
    }
}

int main()
{
    int pid = 0;
    int status;
    pid_t child;

    signal(SIGKILL, sigquit_handler);
    parent_pid = getpid();

    pid = fork();

    if ( pid == 0)
    {
        execl("/usr/bin/avconv","avconv","-f","video4linux2","-r","25","-s","640x480","-i","/dev/video0","out.avi",(char*)0);
    }
    else if( pid > 0)
    {
        sleep(5);
        kill(pid, SIGKILL);

        child = wait(&status);
        printf("child %d succesully quit\n", (int)child);
    }
    return 0;
}
Dabo
  • 2,371
  • 2
  • 18
  • 26
  • I tried with:`execl("/home/root/ffmpeg","ffmpeg","-f","v4l2","-r","25","-s","640x480","-i","/dev/video0","out.avi",(char*)0);` but code skips this command. Do you know what I am missing? Thank's in advance. – dempap Feb 18 '14 at 15:32
  • /home/root does not look like location of ffmpeg command. It should be something like in my example. – Dabo Feb 18 '14 at 15:43
  • /home/root is where ffmpeg folder was located after installation. There is no ffmpeg anywhere else except /home/root. However, I can run the command `ffmpeg` itself from any directory. – dempap Feb 18 '14 at 16:03
  • 1
    Problem solved after copying ffmpeg folder to `/usr/bin` directory. Thank's for your help. – dempap Feb 18 '14 at 16:54