mirror of
https://gitlab.freedesktop.org/gstreamer/gst-plugins-rs.git
synced 2024-12-20 09:06:32 +00:00
Refactor plugin registration
This commit is contained in:
parent
19c8caee1e
commit
e25f644f30
5 changed files with 288 additions and 223 deletions
283
src/lib.rs
283
src/lib.rs
|
@ -33,6 +33,8 @@ pub mod utils;
|
|||
pub mod error;
|
||||
pub mod buffer;
|
||||
pub mod adapter;
|
||||
#[macro_use]
|
||||
pub mod plugin;
|
||||
pub mod rssource;
|
||||
pub mod rssink;
|
||||
pub mod rsfilesrc;
|
||||
|
@ -41,241 +43,76 @@ pub mod rsfilesink;
|
|||
pub mod rsdemuxer;
|
||||
pub mod flvdemux;
|
||||
|
||||
use utils::*;
|
||||
use plugin::*;
|
||||
use rssource::*;
|
||||
use rsfilesrc::FileSrc;
|
||||
use rshttpsrc::HttpSrc;
|
||||
use rssink::*;
|
||||
use rsfilesink::FileSink;
|
||||
use rsdemuxer::*;
|
||||
use flvdemux::FlvDemux;
|
||||
|
||||
use std::os::raw::c_void;
|
||||
use libc::c_char;
|
||||
use std::ffi::CString;
|
||||
|
||||
unsafe fn source_register(plugin: *const c_void,
|
||||
name: &str,
|
||||
long_name: &str,
|
||||
description: &str,
|
||||
classification: &str,
|
||||
author: &str,
|
||||
rank: i32,
|
||||
create_instance: *const c_void,
|
||||
protocols: &str,
|
||||
push_only: bool) {
|
||||
|
||||
extern "C" {
|
||||
fn gst_rs_source_register(plugin: *const c_void,
|
||||
name: *const c_char,
|
||||
long_name: *const c_char,
|
||||
description: *const c_char,
|
||||
classification: *const c_char,
|
||||
author: *const c_char,
|
||||
rank: i32,
|
||||
create_instance: *const c_void,
|
||||
protocols: *const c_char,
|
||||
push_only: GBoolean)
|
||||
-> GBoolean;
|
||||
}
|
||||
|
||||
let cname = CString::new(name).unwrap();
|
||||
let clong_name = CString::new(long_name).unwrap();
|
||||
let cdescription = CString::new(description).unwrap();
|
||||
let cclassification = CString::new(classification).unwrap();
|
||||
let cauthor = CString::new(author).unwrap();
|
||||
let cprotocols = CString::new(protocols).unwrap();
|
||||
|
||||
gst_rs_source_register(plugin,
|
||||
cname.as_ptr(),
|
||||
clong_name.as_ptr(),
|
||||
cdescription.as_ptr(),
|
||||
cclassification.as_ptr(),
|
||||
cauthor.as_ptr(),
|
||||
rank,
|
||||
create_instance,
|
||||
cprotocols.as_ptr(),
|
||||
GBoolean::from_bool(push_only));
|
||||
|
||||
}
|
||||
|
||||
unsafe fn sources_register(plugin: *const c_void) -> GBoolean {
|
||||
fn plugin_init(plugin: &Plugin) -> bool {
|
||||
source_register(plugin,
|
||||
"rsfilesrc",
|
||||
"File Source",
|
||||
"Reads local files",
|
||||
"Source/File",
|
||||
"Sebastian Dröge <sebastian@centricular.com>",
|
||||
256 + 100,
|
||||
FileSrc::new_boxed as *const c_void,
|
||||
"file",
|
||||
false);
|
||||
&SourceInfo {
|
||||
name: "rsfilesrc",
|
||||
long_name: "File Source",
|
||||
description: "Reads local files",
|
||||
classification: "Source/File",
|
||||
author: "Sebastian Dröge <sebastian@centricular.com>",
|
||||
rank: 256 + 100,
|
||||
create_instance: FileSrc::new_boxed,
|
||||
protocols: "file",
|
||||
push_only: false,
|
||||
});
|
||||
|
||||
source_register(plugin,
|
||||
"rshttpsrc",
|
||||
"HTTP Source",
|
||||
"Read HTTP/HTTPS files",
|
||||
"Source/Network/HTTP",
|
||||
"Sebastian Dröge <sebastian@centricular.com>",
|
||||
256 + 100,
|
||||
HttpSrc::new_boxed as *const c_void,
|
||||
"http:https",
|
||||
true);
|
||||
&SourceInfo {
|
||||
name: "rshttpsrc",
|
||||
long_name: "HTTP Source",
|
||||
description: "Reads HTTP/HTTPS streams",
|
||||
classification: "Source/Network/HTTP",
|
||||
author: "Sebastian Dröge <sebastian@centricular.com>",
|
||||
rank: 256 + 100,
|
||||
create_instance: HttpSrc::new_boxed,
|
||||
protocols: "http:https",
|
||||
push_only: true,
|
||||
});
|
||||
|
||||
GBoolean::True
|
||||
}
|
||||
|
||||
unsafe fn sink_register(plugin: *const c_void,
|
||||
name: &str,
|
||||
long_name: &str,
|
||||
description: &str,
|
||||
classification: &str,
|
||||
author: &str,
|
||||
rank: i32,
|
||||
create_instance: *const c_void,
|
||||
protocols: &str) {
|
||||
extern "C" {
|
||||
fn gst_rs_sink_register(plugin: *const c_void,
|
||||
name: *const c_char,
|
||||
long_name: *const c_char,
|
||||
description: *const c_char,
|
||||
classification: *const c_char,
|
||||
author: *const c_char,
|
||||
rank: i32,
|
||||
create_instance: *const c_void,
|
||||
protocols: *const c_char)
|
||||
-> GBoolean;
|
||||
}
|
||||
|
||||
let cname = CString::new(name).unwrap();
|
||||
let clong_name = CString::new(long_name).unwrap();
|
||||
let cdescription = CString::new(description).unwrap();
|
||||
let cclassification = CString::new(classification).unwrap();
|
||||
let cauthor = CString::new(author).unwrap();
|
||||
let cprotocols = CString::new(protocols).unwrap();
|
||||
|
||||
gst_rs_sink_register(plugin,
|
||||
cname.as_ptr(),
|
||||
clong_name.as_ptr(),
|
||||
cdescription.as_ptr(),
|
||||
cclassification.as_ptr(),
|
||||
cauthor.as_ptr(),
|
||||
rank,
|
||||
create_instance,
|
||||
cprotocols.as_ptr());
|
||||
}
|
||||
|
||||
unsafe fn sinks_register(plugin: *const c_void) -> GBoolean {
|
||||
sink_register(plugin,
|
||||
"rsfilesink",
|
||||
"File Sink",
|
||||
"Writes to local files",
|
||||
"Sink/File",
|
||||
"Luis de Bethencourt <luisbg@osg.samsung.com>",
|
||||
256 + 100,
|
||||
FileSink::new_boxed as *const c_void,
|
||||
"file");
|
||||
&SinkInfo {
|
||||
name: "rsfilesink",
|
||||
long_name: "File Sink",
|
||||
description: "Writes to local files",
|
||||
classification: "Sink/File",
|
||||
author: "Luis de Bethencourt <luisbg@osg.samsung.com>",
|
||||
rank: 256 + 100,
|
||||
create_instance: FileSink::new_boxed,
|
||||
protocols: "file",
|
||||
});
|
||||
|
||||
GBoolean::True
|
||||
}
|
||||
|
||||
unsafe fn demuxer_register(plugin: *const c_void,
|
||||
name: &str,
|
||||
long_name: &str,
|
||||
description: &str,
|
||||
classification: &str,
|
||||
author: &str,
|
||||
rank: i32,
|
||||
create_instance: *const c_void,
|
||||
input_format: &str,
|
||||
output_formats: &str) {
|
||||
extern "C" {
|
||||
fn gst_rs_demuxer_register(plugin: *const c_void,
|
||||
name: *const c_char,
|
||||
long_name: *const c_char,
|
||||
description: *const c_char,
|
||||
classification: *const c_char,
|
||||
author: *const c_char,
|
||||
rank: i32,
|
||||
create_instance: *const c_void,
|
||||
input_format: *const c_char,
|
||||
output_formats: *const c_char)
|
||||
-> GBoolean;
|
||||
}
|
||||
|
||||
let cname = CString::new(name).unwrap();
|
||||
let clong_name = CString::new(long_name).unwrap();
|
||||
let cdescription = CString::new(description).unwrap();
|
||||
let cclassification = CString::new(classification).unwrap();
|
||||
let cauthor = CString::new(author).unwrap();
|
||||
let cinput_format = CString::new(input_format).unwrap();
|
||||
let coutput_formats = CString::new(output_formats).unwrap();
|
||||
|
||||
gst_rs_demuxer_register(plugin,
|
||||
cname.as_ptr(),
|
||||
clong_name.as_ptr(),
|
||||
cdescription.as_ptr(),
|
||||
cclassification.as_ptr(),
|
||||
cauthor.as_ptr(),
|
||||
rank,
|
||||
create_instance,
|
||||
cinput_format.as_ptr(),
|
||||
coutput_formats.as_ptr());
|
||||
}
|
||||
|
||||
unsafe fn demuxers_register(plugin: *const c_void) -> GBoolean {
|
||||
demuxer_register(plugin,
|
||||
"rsflvdemux",
|
||||
"FLV Demuxer",
|
||||
"Demuxes FLV Streams",
|
||||
"Codec/Demuxer",
|
||||
"Sebastian Dröge <sebastian@centricular.com>",
|
||||
256 + 100,
|
||||
FlvDemux::new_boxed as *const c_void,
|
||||
"video/x-flv",
|
||||
"ANY");
|
||||
&DemuxerInfo {
|
||||
name: "rsflvdemux",
|
||||
long_name: "FLV Demuxer",
|
||||
description: "Demuxes FLV Streams",
|
||||
classification: "Codec/Demuxer",
|
||||
author: "Sebastian Dröge <sebastian@centricular.com>",
|
||||
rank: 256 + 100,
|
||||
create_instance: FlvDemux::new_boxed,
|
||||
input_formats: "video/x-flv",
|
||||
output_formats: "ANY",
|
||||
});
|
||||
|
||||
GBoolean::True
|
||||
true
|
||||
}
|
||||
|
||||
#[repr(C)]
|
||||
pub struct GstPluginDesc {
|
||||
major_version: i32,
|
||||
minor_version: i32,
|
||||
name: *const u8,
|
||||
description: *const u8,
|
||||
plugin_init: extern "C" fn(plugin: *const c_void) -> GBoolean,
|
||||
version: *const u8,
|
||||
license: *const u8,
|
||||
source: *const u8,
|
||||
package: *const u8,
|
||||
origin: *const u8,
|
||||
release_datetime: *const u8,
|
||||
_gst_reserved: [usize; 4],
|
||||
}
|
||||
|
||||
unsafe impl Sync for GstPluginDesc {}
|
||||
|
||||
extern "C" fn plugin_init(plugin: *const c_void) -> GBoolean {
|
||||
unsafe {
|
||||
sources_register(plugin);
|
||||
sinks_register(plugin);
|
||||
demuxers_register(plugin);
|
||||
}
|
||||
|
||||
GBoolean::True
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
#[allow(non_upper_case_globals)]
|
||||
pub static gst_plugin_desc: GstPluginDesc = GstPluginDesc {
|
||||
major_version: 1,
|
||||
minor_version: 10,
|
||||
name: b"rsplugin\0" as *const u8,
|
||||
description: b"Rust Plugin\0" as *const u8,
|
||||
plugin_init: plugin_init,
|
||||
version: b"1.0\0" as *const u8,
|
||||
license: b"LGPL\0" as *const u8,
|
||||
source: b"rsplugin\0" as *const u8,
|
||||
package: b"rsplugin\0" as *const u8,
|
||||
origin: b"https://github.com/sdroege/rsplugin\0" as *const u8,
|
||||
release_datetime: b"2016-12-08\0" as *const u8,
|
||||
_gst_reserved: [0, 0, 0, 0],
|
||||
};
|
||||
plugin_define!(b"rsplugin\0",
|
||||
b"Rust Plugin\0",
|
||||
plugin_init,
|
||||
b"1.0\0",
|
||||
b"LGPL\0",
|
||||
b"rsplugin\0",
|
||||
b"rsplugin\0",
|
||||
b"https://github.com/sdroege/rsplugin\0",
|
||||
b"2016-12-08\0");
|
||||
|
|
82
src/plugin.rs
Normal file
82
src/plugin.rs
Normal file
|
@ -0,0 +1,82 @@
|
|||
// Copyright (C) 2016 Sebastian Dröge <sebastian@centricular.com>
|
||||
// 2016 Luis de Bethencourt <luisbg@osg.samsung.com>
|
||||
//
|
||||
// This library is free software; you can redistribute it and/or
|
||||
// modify it under the terms of the GNU Library General Public
|
||||
// License as published by the Free Software Foundation; either
|
||||
// version 2 of the License, or (at your option) any later version.
|
||||
//
|
||||
// This library is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
// Library General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU Library General Public
|
||||
// License along with this library; if not, write to the
|
||||
// Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
|
||||
// Boston, MA 02110-1301, USA.
|
||||
|
||||
use std::os::raw::c_void;
|
||||
|
||||
pub struct Plugin(*const c_void);
|
||||
|
||||
impl Plugin {
|
||||
pub unsafe fn new(plugin: *const c_void) -> Plugin {
|
||||
Plugin(plugin)
|
||||
}
|
||||
|
||||
pub unsafe fn to_raw(&self) -> *const c_void {
|
||||
self.0
|
||||
}
|
||||
}
|
||||
|
||||
macro_rules! plugin_define(
|
||||
($name:expr, $description:expr, $plugin_init:ident,
|
||||
$version:expr, $license:expr, $source:expr,
|
||||
$package:expr, $origin:expr, $release_datetime:expr) => {
|
||||
pub mod plugin_desc {
|
||||
use std::os::raw::c_void;
|
||||
use utils::GBoolean;
|
||||
use plugin::Plugin;
|
||||
|
||||
#[repr(C)]
|
||||
pub struct GstPluginDesc {
|
||||
major_version: i32,
|
||||
minor_version: i32,
|
||||
name: *const u8,
|
||||
description: *const u8,
|
||||
plugin_init: unsafe extern "C" fn(plugin: *const c_void) -> GBoolean,
|
||||
version: *const u8,
|
||||
license: *const u8,
|
||||
source: *const u8,
|
||||
package: *const u8,
|
||||
origin: *const u8,
|
||||
release_datetime: *const u8,
|
||||
_gst_reserved: [usize; 4],
|
||||
}
|
||||
|
||||
unsafe impl Sync for GstPluginDesc {}
|
||||
|
||||
#[no_mangle]
|
||||
#[allow(non_upper_case_globals)]
|
||||
pub static gst_plugin_desc: GstPluginDesc = GstPluginDesc {
|
||||
major_version: 1,
|
||||
minor_version: 10,
|
||||
name: $name as *const u8,
|
||||
description: $description as *const u8,
|
||||
plugin_init: plugin_init_trampoline,
|
||||
version: $version as *const u8,
|
||||
license: $license as *const u8,
|
||||
source: $source as *const u8,
|
||||
package: $package as *const u8,
|
||||
origin: $origin as *const u8,
|
||||
release_datetime: $release_datetime as *const u8,
|
||||
_gst_reserved: [0, 0, 0, 0],
|
||||
};
|
||||
|
||||
unsafe extern "C" fn plugin_init_trampoline(plugin: *const c_void) -> GBoolean {
|
||||
GBoolean::from_bool(super::$plugin_init(&Plugin::new(plugin)))
|
||||
}
|
||||
}
|
||||
};
|
||||
);
|
|
@ -30,6 +30,7 @@ use std::u64;
|
|||
use utils::*;
|
||||
use error::*;
|
||||
use buffer::*;
|
||||
use plugin::Plugin;
|
||||
|
||||
pub type StreamIndex = u32;
|
||||
|
||||
|
@ -442,3 +443,52 @@ pub unsafe extern "C" fn demuxer_end_of_stream(ptr: *mut DemuxerWrapper) {
|
|||
wrap.end_of_stream();
|
||||
})
|
||||
}
|
||||
|
||||
pub struct DemuxerInfo<'a> {
|
||||
pub name: &'a str,
|
||||
pub long_name: &'a str,
|
||||
pub description: &'a str,
|
||||
pub classification: &'a str,
|
||||
pub author: &'a str,
|
||||
pub rank: i32,
|
||||
pub create_instance: fn() -> Box<Demuxer>,
|
||||
pub input_formats: &'a str,
|
||||
pub output_formats: &'a str,
|
||||
}
|
||||
|
||||
pub fn demuxer_register(plugin: &Plugin, demuxer_info: &DemuxerInfo) {
|
||||
extern "C" {
|
||||
fn gst_rs_demuxer_register(plugin: *const c_void,
|
||||
name: *const c_char,
|
||||
long_name: *const c_char,
|
||||
description: *const c_char,
|
||||
classification: *const c_char,
|
||||
author: *const c_char,
|
||||
rank: i32,
|
||||
create_instance: *const c_void,
|
||||
input_format: *const c_char,
|
||||
output_formats: *const c_char)
|
||||
-> GBoolean;
|
||||
}
|
||||
|
||||
let cname = CString::new(demuxer_info.name).unwrap();
|
||||
let clong_name = CString::new(demuxer_info.long_name).unwrap();
|
||||
let cdescription = CString::new(demuxer_info.description).unwrap();
|
||||
let cclassification = CString::new(demuxer_info.classification).unwrap();
|
||||
let cauthor = CString::new(demuxer_info.author).unwrap();
|
||||
let cinput_format = CString::new(demuxer_info.input_formats).unwrap();
|
||||
let coutput_formats = CString::new(demuxer_info.output_formats).unwrap();
|
||||
|
||||
unsafe {
|
||||
gst_rs_demuxer_register(plugin.to_raw(),
|
||||
cname.as_ptr(),
|
||||
clong_name.as_ptr(),
|
||||
cdescription.as_ptr(),
|
||||
cclassification.as_ptr(),
|
||||
cauthor.as_ptr(),
|
||||
demuxer_info.rank,
|
||||
demuxer_info.create_instance as *const c_void,
|
||||
cinput_format.as_ptr(),
|
||||
coutput_formats.as_ptr());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -31,6 +31,7 @@ use url::Url;
|
|||
use utils::*;
|
||||
use error::*;
|
||||
use buffer::*;
|
||||
use plugin::Plugin;
|
||||
|
||||
#[derive(Debug)]
|
||||
pub enum SinkError {
|
||||
|
@ -249,3 +250,48 @@ pub unsafe extern "C" fn sink_render(ptr: *const SinkWrapper,
|
|||
wrap.render(&*buffer)
|
||||
})
|
||||
}
|
||||
|
||||
pub struct SinkInfo<'a> {
|
||||
pub name: &'a str,
|
||||
pub long_name: &'a str,
|
||||
pub description: &'a str,
|
||||
pub classification: &'a str,
|
||||
pub author: &'a str,
|
||||
pub rank: i32,
|
||||
pub create_instance: fn() -> Box<Sink>,
|
||||
pub protocols: &'a str,
|
||||
}
|
||||
|
||||
pub fn sink_register(plugin: &Plugin, sink_info: &SinkInfo) {
|
||||
extern "C" {
|
||||
fn gst_rs_sink_register(plugin: *const c_void,
|
||||
name: *const c_char,
|
||||
long_name: *const c_char,
|
||||
description: *const c_char,
|
||||
classification: *const c_char,
|
||||
author: *const c_char,
|
||||
rank: i32,
|
||||
create_instance: *const c_void,
|
||||
protocols: *const c_char)
|
||||
-> GBoolean;
|
||||
}
|
||||
|
||||
let cname = CString::new(sink_info.name).unwrap();
|
||||
let clong_name = CString::new(sink_info.long_name).unwrap();
|
||||
let cdescription = CString::new(sink_info.description).unwrap();
|
||||
let cclassification = CString::new(sink_info.classification).unwrap();
|
||||
let cauthor = CString::new(sink_info.author).unwrap();
|
||||
let cprotocols = CString::new(sink_info.protocols).unwrap();
|
||||
|
||||
unsafe {
|
||||
gst_rs_sink_register(plugin.to_raw(),
|
||||
cname.as_ptr(),
|
||||
clong_name.as_ptr(),
|
||||
cdescription.as_ptr(),
|
||||
cclassification.as_ptr(),
|
||||
cauthor.as_ptr(),
|
||||
sink_info.rank,
|
||||
sink_info.create_instance as *const c_void,
|
||||
cprotocols.as_ptr());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -28,6 +28,7 @@ use std::sync::atomic::{AtomicBool, Ordering};
|
|||
|
||||
use url::Url;
|
||||
|
||||
use plugin::Plugin;
|
||||
use utils::*;
|
||||
use error::*;
|
||||
use buffer::*;
|
||||
|
@ -302,3 +303,52 @@ pub unsafe extern "C" fn source_seek(ptr: *const SourceWrapper, start: u64, stop
|
|||
GBoolean::from_bool(wrap.seek(start, if stop == u64::MAX { None } else { Some(stop) }))
|
||||
})
|
||||
}
|
||||
|
||||
pub struct SourceInfo<'a> {
|
||||
pub name: &'a str,
|
||||
pub long_name: &'a str,
|
||||
pub description: &'a str,
|
||||
pub classification: &'a str,
|
||||
pub author: &'a str,
|
||||
pub rank: i32,
|
||||
pub create_instance: fn() -> Box<Source>,
|
||||
pub protocols: &'a str,
|
||||
pub push_only: bool,
|
||||
}
|
||||
|
||||
pub fn source_register(plugin: &Plugin, source_info: &SourceInfo) {
|
||||
|
||||
extern "C" {
|
||||
fn gst_rs_source_register(plugin: *const c_void,
|
||||
name: *const c_char,
|
||||
long_name: *const c_char,
|
||||
description: *const c_char,
|
||||
classification: *const c_char,
|
||||
author: *const c_char,
|
||||
rank: i32,
|
||||
create_instance: *const c_void,
|
||||
protocols: *const c_char,
|
||||
push_only: GBoolean)
|
||||
-> GBoolean;
|
||||
}
|
||||
|
||||
let cname = CString::new(source_info.name).unwrap();
|
||||
let clong_name = CString::new(source_info.long_name).unwrap();
|
||||
let cdescription = CString::new(source_info.description).unwrap();
|
||||
let cclassification = CString::new(source_info.classification).unwrap();
|
||||
let cauthor = CString::new(source_info.author).unwrap();
|
||||
let cprotocols = CString::new(source_info.protocols).unwrap();
|
||||
|
||||
unsafe {
|
||||
gst_rs_source_register(plugin.to_raw(),
|
||||
cname.as_ptr(),
|
||||
clong_name.as_ptr(),
|
||||
cdescription.as_ptr(),
|
||||
cclassification.as_ptr(),
|
||||
cauthor.as_ptr(),
|
||||
source_info.rank,
|
||||
source_info.create_instance as *const c_void,
|
||||
cprotocols.as_ptr(),
|
||||
GBoolean::from_bool(source_info.push_only));
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue