22
33#![ doc( hidden) ]
44
5- use std:: ffi:: { CStr , CString } ;
65use std:: { mem, slice} ;
76
8- use libc :: { self , size_t , c_char, c_void} ;
7+ use std :: os :: raw :: { c_char, c_void} ;
98
109use buffer:: AudioBuffer ;
1110use api:: consts:: * ;
@@ -60,6 +59,20 @@ pub fn get_parameter(effect: *mut AEffect, index: i32) -> f32 {
6059 unsafe { ( * effect) . get_plugin ( ) } . get_parameter ( index)
6160}
6261
62+ /// Copy a string into a destination buffer.
63+ ///
64+ /// String will be cut at `max` characters.
65+ fn copy_string ( dst : * mut c_void , src : & str , max : usize ) {
66+ unsafe {
67+ use std:: cmp:: min;
68+ use libc:: { c_void, memset, memcpy} ;
69+
70+ let dst = dst as * mut c_void ;
71+ memset ( dst, 0 , max) ;
72+ memcpy ( dst, src. as_ptr ( ) as * const c_void , min ( max, src. len ( ) ) ) ;
73+ }
74+ }
75+
6376/// VST2.4 dispatch function. This function handles dispatching all opcodes to the vst plugin.
6477pub fn dispatch ( effect : * mut AEffect , opcode : i32 , index : i32 , value : isize , ptr : * mut c_void , opt : f32 ) -> isize {
6578 use plugin:: { CanDo , OpCode } ;
@@ -69,15 +82,6 @@ pub fn dispatch(effect: *mut AEffect, opcode: i32, index: i32, value: isize, ptr
6982 // Plugin handle
7083 let mut plugin = unsafe { ( * effect) . get_plugin ( ) } ;
7184
72- // Copy a string into the `ptr` buffer
73- let copy_string = |string : & String , max : size_t | {
74- unsafe {
75- libc:: strncpy ( ptr as * mut c_char ,
76- CString :: new ( string. clone ( ) ) . unwrap ( ) . as_ptr ( ) ,
77- max) ;
78- }
79- } ;
80-
8185 match opcode {
8286 OpCode :: Initialize => plugin. init ( ) ,
8387 OpCode :: Shutdown => unsafe {
@@ -90,12 +94,12 @@ pub fn dispatch(effect: *mut AEffect, opcode: i32, index: i32, value: isize, ptr
9094 OpCode :: SetCurrentPresetName => plugin. set_preset_name ( read_string ( ptr) ) ,
9195 OpCode :: GetCurrentPresetName => {
9296 let num = plugin. get_preset_num ( ) ;
93- copy_string ( & plugin. get_preset_name ( num) , MAX_PRESET_NAME_LEN ) ;
97+ copy_string ( ptr , & plugin. get_preset_name ( num) , MAX_PRESET_NAME_LEN ) ;
9498 }
9599
96- OpCode :: GetParameterLabel => copy_string ( & plugin. get_parameter_label ( index) , MAX_PARAM_STR_LEN ) ,
97- OpCode :: GetParameterDisplay => copy_string ( & plugin. get_parameter_text ( index) , MAX_PARAM_STR_LEN ) ,
98- OpCode :: GetParameterName => copy_string ( & plugin. get_parameter_name ( index) , MAX_PARAM_STR_LEN ) ,
100+ OpCode :: GetParameterLabel => copy_string ( ptr , & plugin. get_parameter_label ( index) , MAX_PARAM_STR_LEN ) ,
101+ OpCode :: GetParameterDisplay => copy_string ( ptr , & plugin. get_parameter_text ( index) , MAX_PARAM_STR_LEN ) ,
102+ OpCode :: GetParameterName => copy_string ( ptr , & plugin. get_parameter_name ( index) , MAX_PARAM_STR_LEN ) ,
99103
100104 OpCode :: SetSampleRate => plugin. set_sample_rate ( opt) ,
101105 OpCode :: SetBlockSize => plugin. set_block_size ( value as i64 ) ,
@@ -184,7 +188,7 @@ pub fn dispatch(effect: *mut AEffect, opcode: i32, index: i32, value: isize, ptr
184188 OpCode :: CanBeAutomated => return plugin. can_be_automated ( index) as isize ,
185189 OpCode :: StringToParameter => return plugin. string_to_parameter ( index, read_string ( ptr) ) as isize ,
186190
187- OpCode :: GetPresetName => copy_string ( & plugin. get_preset_name ( index) , MAX_PRESET_NAME_LEN ) ,
191+ OpCode :: GetPresetName => copy_string ( ptr , & plugin. get_preset_name ( index) , MAX_PRESET_NAME_LEN ) ,
188192
189193 OpCode :: GetInputInfo => {
190194 if index >= 0 && index < plugin. get_info ( ) . inputs {
@@ -206,8 +210,8 @@ pub fn dispatch(effect: *mut AEffect, opcode: i32, index: i32, value: isize, ptr
206210 return plugin. get_info ( ) . category . into ( ) ;
207211 }
208212
209- OpCode :: GetVendorName => copy_string ( & plugin. get_info ( ) . vendor , MAX_VENDOR_STR_LEN ) ,
210- OpCode :: GetProductName => copy_string ( & plugin. get_info ( ) . name , MAX_PRODUCT_STR_LEN ) ,
213+ OpCode :: GetVendorName => copy_string ( ptr , & plugin. get_info ( ) . vendor , MAX_VENDOR_STR_LEN ) ,
214+ OpCode :: GetProductName => copy_string ( ptr , & plugin. get_info ( ) . name , MAX_PRODUCT_STR_LEN ) ,
211215 OpCode :: GetVendorVersion => return plugin. get_info ( ) . version as isize ,
212216 OpCode :: VendorSpecific => return plugin. vendor_specific ( index, value, ptr, opt) ,
213217 OpCode :: CanDo => {
@@ -265,15 +269,6 @@ pub fn host_dispatch(host: &mut Host,
265269 opt : f32 ) -> isize {
266270 use host:: OpCode ;
267271
268- // Copy a string into the `ptr` buffer
269- let copy_string = |string : & String , max : size_t | {
270- unsafe {
271- libc:: strncpy ( ptr as * mut c_char ,
272- CString :: new ( string. clone ( ) ) . unwrap ( ) . as_ptr ( ) ,
273- max) ;
274- }
275- } ;
276-
277272 match OpCode :: from ( opcode) {
278273 OpCode :: Version => return 2400 ,
279274 OpCode :: Automate => host. automate ( index, opt) ,
@@ -287,8 +282,8 @@ pub fn host_dispatch(host: &mut Host,
287282 }
288283
289284 OpCode :: GetVendorVersion => return host. get_info ( ) . 0 ,
290- OpCode :: GetVendorString => copy_string ( & host. get_info ( ) . 1 , MAX_VENDOR_STR_LEN ) ,
291- OpCode :: GetProductString => copy_string ( & host. get_info ( ) . 2 , MAX_PRODUCT_STR_LEN ) ,
285+ OpCode :: GetVendorString => copy_string ( ptr , & host. get_info ( ) . 1 , MAX_VENDOR_STR_LEN ) ,
286+ OpCode :: GetProductString => copy_string ( ptr , & host. get_info ( ) . 2 , MAX_PRODUCT_STR_LEN ) ,
292287 OpCode :: ProcessEvents => {
293288 let events: * const api:: Events = ptr as * const api:: Events ;
294289
@@ -313,6 +308,8 @@ pub fn host_dispatch(host: &mut Host,
313308
314309// Read a string from the `ptr` buffer
315310fn read_string ( ptr : * mut c_void ) -> String {
311+ use std:: ffi:: CStr ;
312+
316313 String :: from_utf8_lossy (
317314 unsafe { CStr :: from_ptr ( ptr as * mut c_char ) . to_bytes ( ) }
318315 ) . into_owned ( )
0 commit comments