Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Bump ffmpeg version to 7.0 #74

Merged
merged 1 commit into from
May 12, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
# Changelog

## bliss 0.7.0
* Bump ffmpeg-next version to 7.0
* Bump aubio-rs custom crate to disable compiling it with -std=c99
* Add the possibility to make playlists based on multiple songs using extended
isolation forest (Thanks @SimonTeixidor!)
Expand Down
34 changes: 27 additions & 7 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 2 additions & 2 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -40,8 +40,8 @@ serde = ["dep:serde", "extended-isolation-forest/serde"]
# Until https://github.com/aubio/aubio/issues/336 is somehow solved
# Hopefully we'll be able to use the official aubio-rs at some point.
bliss-audio-aubio-rs = "0.2.2"
ffmpeg-next = "6.1.1"
ffmpeg-sys-next = { version = "6.1.0", default-features = false }
ffmpeg-next = "7.0.1"
ffmpeg-sys-next = { version = "7.0.0", default-features = false }
log = "0.4.17"
# `rayon` is used only by `par_mapv_inplace` in chroma.rs.
# TODO: is the speed gain that substantial?
Expand Down
27 changes: 23 additions & 4 deletions src/song.rs
Original file line number Diff line number Diff line change
Expand Up @@ -193,6 +193,10 @@ impl Analysis {
}
}

// Safe because the other thread just reads the channel layout
struct SendChannelLayout(ChannelLayout);
unsafe impl Send for SendChannelLayout {}

impl Song {
/// Returns a decoded [Song] given a file path, or an error if the song
/// could not be analyzed for some reason.
Expand Down Expand Up @@ -445,23 +449,31 @@ impl Song {
t => Some(t.to_string()),
};
};

#[cfg(not(feature = "ffmpeg_7_0"))]
let is_channel_layout_empty = decoder.channel_layout() == ChannelLayout::empty();
#[cfg(feature = "ffmpeg_7_0")]
let is_channel_layout_empty = decoder.channel_layout().is_empty();

let (empty_in_channel_layout, in_channel_layout) = {
if decoder.channel_layout() == ChannelLayout::empty() {
if is_channel_layout_empty {
(true, ChannelLayout::default(decoder.channels().into()))
} else {
(false, decoder.channel_layout())
}
};
decoder.set_channel_layout(in_channel_layout);

let in_channel_layout_to_send = SendChannelLayout(in_channel_layout);

let (tx, rx) = mpsc::channel();
let in_codec_format = decoder.format();
let in_codec_rate = decoder.rate();
let child = thread::spawn(move || {
resample_frame(
rx,
in_codec_format,
in_channel_layout,
in_channel_layout_to_send,
in_codec_rate,
sample_array,
empty_in_channel_layout,
Expand Down Expand Up @@ -547,6 +559,7 @@ impl Song {
}

drop(tx);
// Waiting here ensures that ChannelLayout doesn't get dropped in the middle
song.sample_array = child.join().unwrap()?;
let duration_seconds = song.sample_array.len() as f32 / SAMPLE_RATE as f32;
song.duration = Duration::from_nanos((duration_seconds * 1e9_f32).round() as u64);
Expand All @@ -570,11 +583,12 @@ pub(crate) struct InternalSong {
fn resample_frame(
rx: Receiver<Audio>,
in_codec_format: Sample,
in_channel_layout: ChannelLayout,
sent_in_channel_layout: SendChannelLayout,
in_rate: u32,
mut sample_array: Vec<f32>,
empty_in_channel_layout: bool,
) -> BlissResult<Vec<f32>> {
let in_channel_layout = sent_in_channel_layout.0;
let mut resample_context = ffmpeg::software::resampling::context::Context::get(
in_codec_format,
in_channel_layout,
Expand All @@ -592,10 +606,15 @@ fn resample_frame(
let mut resampled = ffmpeg::frame::Audio::empty();
let mut something_happened = false;
for mut decoded in rx.iter() {
#[cfg(not(feature = "ffmpeg_7_0"))]
let is_channel_layout_empty = decoded.channel_layout() == ChannelLayout::empty();
#[cfg(feature = "ffmpeg_7_0")]
let is_channel_layout_empty = decoded.channel_layout().is_empty();

// If the decoded layout is empty, it means we forced the
// "in_channel_layout" to something default, not that
// the format is wrong.
if empty_in_channel_layout && decoded.channel_layout() == ChannelLayout::empty() {
if empty_in_channel_layout && is_channel_layout_empty {
decoded.set_channel_layout(in_channel_layout);
} else if in_codec_format != decoded.format()
|| (in_channel_layout != decoded.channel_layout())
Expand Down
Loading