Combining GStreamer, AnyEvent and EV (perl) - perl

I'm trying to use GStreamer within an existing perl application that uses AnyEvent with the EV event loop. It is not a Glib application. I have loaded EV::Glib to get the Glib main loop to use EV. I freely admit that, with respect to Glib, I am pretty ignorant. I think that I have all the bits that I need but I am struggling (failing) to get them to work together.
If I use a standalone perl program to build a GStreamer pipeline and then put it into PLAYING state then it all simply works. I do not need to do anything with a Glib mainloop or otherwise tickle the GStreamer bus.
Building the same pipeline in my existing application, within the context of an AnyEvent event-handler, then it fails to run the pipeline. I have played around with various ways of trying to exercise it, including calling $pipeline->get_bus->poll(). If I call ...->poll() repeatedly in the original event handler (that is, the handler does not return) then it works but this is clearly not a valid solution. Calling ...->poll() in an AnyEvent timer callback does not run the pipeline.
My best guess at the moment is that EV::Glib enables some level of integration but does not actually run the necessary bits of the main loop. What am I missing?

I came here with a similar question regarding EV::Glib usage, but ended up having no issues using it.. So maybe I'm missing what you're trying to do here.
Here is the simple script I knocked up to test how EV::Glib works:
use EV::Glib;
use Gtk2 '-init';
my $t = EV::timer 1, 1, sub { print "I am here!\n" };
Glib::Timeout->add(1000, sub { print "I am also here!\n" });
my $window = Gtk2::Window->new('toplevel');
$window->signal_connect(delete_event => sub { EV::unloop });
my $button = Gtk2::Button->new('Action');
$button->signal_connect(clicked => sub {
print("Hello Gtk2-EV-Perl\n");
});
$window->add($button);
$window->show_all;
EV::loop;
With this the signal handler on the button will work, and so too will both the timer events. So the EV loop will correctly drive the entire thing.
The main issue I can see is in the documentation: "This [module] makes Glib compatible to EV. Calls into the Glib main loop are more or less equivalent to calls to EV::loop (but not vice versa, you have to use the Glib mainloop functions)."
What this means is if you're hookling up an EV::loop event, it won't equate to a Glib::mainloop and so might not 'tickle' (or 'be tickled by') your GStreamer event. Maybe that could be the issue you're experiencing, especially if you're using AnyEvent and its generic callbacks which are likely translating to EV::loop calls instead of Glib::MainLoop calls.
This is all just a guess though -- I've never used GStreamer myself, and I certainly don't know what you're trying to achieve without seeing more code. But I think my halfassed conclusion is pretty sound advice regardless: If you're using something specific to Glib, you should probably be hooking up events to it using Glib.

EV::Glib embeds Glib into EV - you (and everybody else) has to use EV to make it work. Chances are that gstreamer doesn't know about this and disrespectfully calls glib mainloop functions internally, which doesn't work.
Fortunately there is another module that does just the opposite: Glib::EV. That module makes Glib use EV internally. When using it, you can/should use the glib mainloop functions (you can use EV watchers, but you cannot call glib functions from the EV callbacks, as glib doesn't support that).
It might be better suited to your application, as applications using glib will "just work", as the EV usage is completely internal.
Another possible issue is that perl modules are dynamically linked, and only "accidentally" get the same library. For all of this to work, you need to ensure that all perl modules link against the same shared glib library.

Related

How to force AnyEvent to use EV

I have been using AnyEvent for a while and EV is installed in my computer.
I have the understanding that if EV is installed AnyEvent will try to use it as first resort, but I keep seeing people doing this:
use EV;
use AnyEvent;
From the documentation:
During the first call of any watcher-creation method, the module tries to detect the currently loaded event loop by probing whether one of the following modules is already loaded: EV, AnyEvent::Loop, Event, Glib, Tk, Event::Lib, Qt, POE. The first one found is used.
This means it will first check if any of these modules are already loaded and then use it. For example if Tk is loaded but EV not it will use Tk like in the following example:
use Some_Module_Which_Implicitly_loads_Tk;
use AnyEvent;
By explicitly loading EV one makes sure that it is available when doing the probing described above and that it is thus used even if other event loop modules are loaded too.

Catching runtime errors in Perl and converting to exceptions

Perl currently implements $SIG{__DIE__} in such a way that it will catch any error that occurs, even inside eval blocks. This has a really useful property that you can halt the code at the exact point where the error occurs, collect a stack trace of the actual error, wrap this up in an object, and then call die manually with this object as the parameter.
This abuse of $SIG{__DIE__} is deprecated. Officially, you are supposed to replace $SIG{__DIE__} with *CORE::GLOBAL::die. However, these two are NOT remotely equivalent. *CORE::GLOBAL::die is NOT called when a runtime error occurs! All it does is replace explicit calls to die().
I am not interested in replacing die.
I am specifically interested in catching runtime errors.
I need to ensure that any runtime error, in any function, at any depth, in any module, causes Perl to pass control to me so that I can collect the stack trace and rethrow. This needs to work inside an eval block -- one or more enclosing eval blocks may want to catch the exception, but the runtime error could be in a function without an enclosing eval, inside any module, from anywhere.
$SIG{__DIE__} supports this perfectly—and has served me faithfully for a couple of years or more—but the Powers that Be™ warn that this fantastic facility may be snatched away at any time, and I don't want a nasty surprise one day down the line.
Ideally, for Perl itself, they could create a new signal $SIG{__RTMERR__} for this purpose (switching signal is easy enough, for me anyway, as it's only hooked in one place). Unfortunately, my persuasive powers wouldn't lead an alcoholic to crack open a bottle, so assuming this will not happen, how exactly is one supposed to achieve this aim of catching runtime errors cleanly?
(For example, another answer here recommends Carp::Always, which … also hooks DIE!)
Just do it. I've done it. Probably everyone who's aware of this hook has done it.
It's Perl; it's still compatible going back decades. I interpret "deprecated" here to mean "please don't use this if you don't need it, ew, gross". But you do need it, and seem to understand the implications, so imo go for it. I seriously doubt an irreplaceable language feature is going away any time soon.
And release your work on CPAN so the next dev doesn't need to reinvent this yet again. :)

threads in Dancer

I'm using Dancer 1.31, in a standard configuration (plackup/Starman).
In a request I wished to call a perl function asynchronously, so that the request returns inmmediately. Think of the typical "long running operation" scenario, in which one wants to return a "processing page" with a refresh+redirect.
I (naively?) tried with a thread:
sub myfunc {
sleep 9; # just for testing a slow operation
}
any '/test1' => sub {
my $thr = threads->create('myfunc');
$thr->detach();
return "done" ;
};
I does not work, the server seems to freeze, and the error log does not show anything. I guess manual creation of threads are forbidden inside Dancer? It's an issue with PSGI? Which is the recommended way?
I would stay away from perl threads especially in a web server environment. It will most likely crash your server when you join or detach them.
I usually create a few threads (thread pool) BEFORE initializing other modules and keep them around for the entire life time of the application. Thread::Queue nicely provides communication between the workers and the main thread.
The best asynchronous solution I find in Perl is POE. In Linux I prefer using POE::Wheel::Run to run executables and subroutines asynchronously. It uses fork and has a beautiful interface allowing communication with the child process. (In Windows it's not usable due to thread dependency)
Setting up Dancer and POE inside the same application/script may cause problems and POE's event loop may be blocked. A single worker thread dedicated to POE may come handy, or I would write another server based on POE and just communicate with the Dancer application via sockets.
Threads are definitively iffy with Perl. It might be possible to write some threaded Dancer code, but to be honest I don't think we ever tried it. And considering that Dancer 1's core use simpleton classes, it might also be very tricky.
As Ogla says, there are other ways to implement asynchronous behavior in Dancer. You say that you are using Starman, which is a forking engine. But there is also Twiggy, which is AnyEvent-based. To see how to leverage it to write asynchronous code, have a gander at Dancer::Plugin::Async.

How can I replace all 'die's with 'confess' in a Perl application?

I'm working in a large Perl application and would like to get stack traces every time 'die' is called. I'm aware of the Carp module, but I would prefer not to search/replace every instance of 'die' with 'confess'. In addition, I would like full stack traces for errors in Perl modules or the Perl interpreter itself, and obviously I can't change those to use Carp.
So, is there a way for me to modify the 'die' function at runtime so that it behaves like 'confess'? Or, is there a Perl interpreter setting that will throw full stack traces from 'die'?
Use Devel::SimpleTrace or Carp::Always and they'll do what you're asking for without any hard work on your part. They have global effect, which means they can easily be added for just one run on the commandline using e.g. -MDevel::SimpleTrace.
What about setting a __DIE__ signal handler? Something like
$SIG{__DIE__} = sub { Carp::confess #_ };
at the top of your script? See perlvar %SIG for more information.
I usually only want to replace the dies in a bit of code, so I localize the __DIE__ handler:
{
use Carp;
local $SIG{__DIE__} = \&Carp::confess;
....
}
As a development tool this can work, but some modules play tricks with this to get their features to work. Those features may break in odd ways when you override the handler they were expecting. It's not a good practice, but it happens sometimes.
The Error module will convert all dies to Error::Simple objects, which contain a full stacktrace (the constructor parses the "at file... line.." text and creates a stack trace). You can use an arbitrary object (generally subclassed from Error::Simple) to handle errors with the $Error::ObjectifyCallback preference.
This is especially handy if you commonly throw around exceptions of other types to signal other events, as then you just add a handler for Error::Simple (or whatever other class you are using for errors) and have it dump its stacktrace or perform specialized logging depending on the type of error.

Is there a way to have managed processes in Perl (i.e. a threads replacement that actually works)?

I have a multithreded application in perl for which I have to rely on several non-thread safe modules, so I have been using fork()ed processes with kill() signals as a message passing interface.
The problem is that the signal handlers are a bit erratic (to say the least) and often end up with processes that get killed in inapropriate states.
Is there a better way to do this?
Depending on exactly what your program needs to do, you might consider using POE, which is a Perl framework for multi-threaded applications with user-space threads. It's complex, but elegant and powerful and can help you avoid non-thread-safe modules by confining activity to a single Perl interpreter thread.
Helpful resources to get started:
Programming POE presentation by Matt Sergeant (start here to understand what it is and does)
POE project page (lots of cookbook examples)
Plus there are hundreds of pre-built POE components you can use to assemble into an application.
You can always have a pipe between parent and child to pass messages back and forth.
pipe my $reader, my $writer;
my $pid = fork();
if ( $pid == 0 ) {
close $reader;
...
}
else {
close $writer;
my $msg_from_child = <$reader>;
....
}
Not a very comfortable way of programming, but it shouldn't be 'erratic'.
Have a look at forks.pm, a "drop-in replacement for Perl threads using fork()" which makes for much more sensible memory usage (but don't use it on Win32). It will allow you to declare "shared" variables and then it automatically passes changes made to such variables between the processes (similar to how threads.pm does things).
From perl 5.8 onwards you should be looking at the core threads module. Have a look at http://metacpan.org/pod/threads
If you want to use modules which aren't thread safe you can usually load them with a require and import inside the thread entry point.