import * as ffi from 'ffi-napi' ; import { Config , FModel } from 'win32-def' ; const dllInst = new Map < string , any > ( ) ; export function load < T > ( dllName , dllFuncs , fns ? , settings ? ) { const st = parse_settings ( settings ) ; if ( st . singleton ) { let inst = get_inst_by_name < T > ( dllName ) ; if ( ! inst ) { inst = ffi . Library ( dllName , gen_api_opts ( dllFuncs , fns ) ) as T ; set_inst_by_name ( dllName , inst ) ; } return inst ; } else { return ffi . Library ( dllName , gen_api_opts ( dllFuncs , fns ) ) ; } } /**
 * Generate function definitions via converting macro windows data type (like PVOID) to the expected value.
 * Skip assignment if property undefined
 */ export function gen_api_opts ( dllFuncs , fns ? ) { const ret = { } ; if ( fns && Array . isArray ( fns ) && fns . length ) { for ( const fn of fns ) { const ps = dllFuncs [ fn ] ; if ( typeof ps !== 'undefined' ) { Object . defineProperty ( ret , fn , { value : ps , writable : false , enumerable : true , configurable : false , } ) ; } } } else { for ( const fn of Object . keys ( dllFuncs ) ) { const ps = dllFuncs [ fn ] as any ; if ( typeof ps !== 'undefined' ) { Object . defineProperty ( ret , fn , { value : ps as FModel . FnParams , writable : false , enumerable : true , configurable : false , } ) ; } } } return ret ; } function get_inst_by_name < T > ( dllName ) { return dllInst . get ( dllName ) as T | undefined ; } function set_inst_by_name < T > ( dllName , inst ) { dllInst . set ( dllName , inst ) ; } function parse_settings ( settings ? ) { const st = { ... Config . settingsDefault } ; if ( typeof settings !== 'undefined' && Object . keys ( settings ) . length ) { Object . assign ( st , settings ) ; } return st ; }