Ah, j'en ai assez de lire la documentation du noyau Linux, alors les jouets sont sortis et j'ai joué.
«C'est bien que les choses bougent. --low level / raw level Important pour le débogage.
Nous avons examiné sur la base du contenu du site suivant. Cependant, je n'ai pas encore changé de voix, alors j'aimerais y réfléchir un peu plus ...
Utilisons RUST pour déplacer le "Pocket Miku" qui est sorti après le nettoyage.
Quand j'ai vérifié en utilisant la commande de compte, c'était NSX-39, donc "20: 0" semble être bien.
[kmtr@localhost rust-alsa]$ sudo LANG=C aconnect -l
client 0: 'System' [type=kernel]
0 'Timer '
1 'Announce '
client 14: 'Midi Through' [type=kernel]
0 'Midi Through Port-0'
client 16: 'Ensoniq AudioPCI' [type=kernel,card=0]
0 'ES1371 '
client 20: 'NSX-39' [type=kernel,card=1]
0 'NSX-39 MIDI 1 '
[kmtr@localhost rust-alsa]$
Ajouté alsa et clap à Cargo.toml.
Cargo.toml
[package]
name = "rust-alsa"
version = "0.1.0"
authors = ["kmtr"]
edition = "2018"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[dependencies]
alsa = "0.4.2"
clap = "2.20"
emballage alsa de rust Ce n'est ni dans une main ni dans celle-ci. Pour le moment, j'ai confirmé qu'il y avait un son.
src/main.rs
extern crate alsa;
use std::error;
use alsa::seq;
use std::ffi::CString;
use std::thread::sleep;
use std::time::Duration;
const DEFAULT_NAME: &str = "RUSTMIKU";
const MIKU_ID: i32 = 20;
const MIKU_PORT: i32 = 0;
fn note( s: &alsa::Seq, evt : alsa::seq::EventType, channel : u8, note: u8, velocity : u8, s_port:i32)
{
let o_note = alsa::seq::EvNote {
channel,
note,
velocity,
off_velocity: 0,
duration: 0
};
let mut o_event = alsa::seq::Event::new( evt , &o_note );
o_event.set_direct();
o_event.set_source( s_port );
o_event.set_dest( alsa::seq::Addr { client: MIKU_ID, port: MIKU_PORT } );
s.event_output( &mut o_event ) ;
s.drain_output();
}
fn sing() -> Result<alsa::Seq, Box<dyn error::Error> > {
// snd_seq_open()
let miku = alsa::Seq::open( None, Some(alsa::Direction::Playback), false ) ?;
// snd_seq_create_simple_port()
let cstr = CString::new(DEFAULT_NAME)?;
let client_port = miku.create_simple_port(&cstr,
alsa::seq::PortCap::READ,
alsa::seq::PortType::MIDI_GENERIC | alsa::seq::PortType::APPLICATION )?;
// subscribe_port()
let client_id = miku.client_id()?;
let subs = seq::PortSubscribe::empty()?;
subs.set_dest (seq::Addr { client: MIKU_ID, port: MIKU_PORT } );
subs.set_sender(seq::Addr { client: client_id, port: client_port });
miku.subscribe_port(&subs)?;
// Note on
note ( &miku, alsa::seq::EventType::Noteon, 0, 60, 64, client_port );
// Wait
sleep ( Duration::from_millis(1000) );
// Note off
note ( &miku, alsa::seq::EventType::Noteoff, 0, 60, 64, client_port );
Ok(miku)
}
fn main() {
sing();
}
Au début, je me demandais pourquoi il n'y avait pas de son. A cette époque, c'était strace qui était utile pour le débogage.
fcntl(3, F_SETFD, FD_CLOEXEC) = 0
ioctl(3, SNDRV_SEQ_IOCTL_PVERSION, 0x7ffe4a9ffeb8) = 0
ioctl(3, SNDRV_SEQ_IOCTL_CLIENT_ID, 0x7ffe4a9ffebc) = 0
ioctl(3, SNDRV_SEQ_IOCTL_RUNNING_MODE, 0x7ffe4a9ffec0) = 0
ioctl(3, SNDRV_SEQ_IOCTL_CREATE_PORT, 0x7ffe4aa00260) = 0
ioctl(3, SNDRV_SEQ_IOCTL_SUBSCRIBE_PORT, 0x560006f2b5b0) = 0
write(3, "\5\0\0\375\0\0\0\0\0\0\0\0\0\0\24\0\0<@\0\0\0\0\0\0\0\0\0", 28) = -1 EINVAL (Invalid argument)
nanosleep({tv_sec=1, tv_nsec=0}, 0x7ffe4aa00340) = 0
write(3, "\5\0\0\375\0\0\0\0\0\0\0\0\0\0\24\0\0<@\0\0\0\0\0\0\0\0\0\7\0\0\375"..., 56) = -1 EINVAL (Invalid argument)
close(3) = 0
sigaltstack({ss_sp=NULL, ss_flags=SS_DISABLE, ss_size=8192}, NULL) = 0
munmap(0x7f57fe537000, 8192) = 0
exit_group(0) = ?
+++ exited with 0 +++
Hmm? Je ne peux rien gérer. alors,
note (& miku, alsa :: seq :: EventType :: Note, 0, 60, 64, client_port); Vous avez remarqué que
note (& miku, alsa :: seq :: EventType :: Noteon, 0, 60, 64, client_port);`.
fcntl(3, F_SETFD, FD_CLOEXEC) = 0
ioctl(3, SNDRV_SEQ_IOCTL_PVERSION, 0x7ffc72b00148) = 0
ioctl(3, SNDRV_SEQ_IOCTL_CLIENT_ID, 0x7ffc72b0014c) = 0
ioctl(3, SNDRV_SEQ_IOCTL_RUNNING_MODE, 0x7ffc72b00150) = 0
ioctl(3, SNDRV_SEQ_IOCTL_CREATE_PORT, 0x7ffc72b004f0) = 0
ioctl(3, SNDRV_SEQ_IOCTL_SUBSCRIBE_PORT, 0x556f313ee5b0) = 0
write(3, "\6\0\0\375\0\0\0\0\0\0\0\0\0\0\24\0\0<@\0\0\0\0\0\0\0\0\0", 28) = 28
nanosleep({tv_sec=1, tv_nsec=0}, 0x7ffc72b005d0) = 0
write(3, "\7\0\0\375\0\0\0\0\0\0\0\0\0\0\24\0\0<@\0\0\0\0\0\0\0\0\0", 28) = 28
close(3) = 0
sigaltstack({ss_sp=NULL, ss_flags=SS_DISABLE, ss_size=8192}, NULL) = 0
munmap(0x7f59d2ff5000, 8192) = 0
exit_group(0)
Après tout, le débogage au niveau brut / bas niveau est important! !!
TODO
Je veux utiliser sysex pour changer ce que je dis ...
C'est tout.
Recommended Posts