📄 modules.c
字号:
free( psz_fullpath ); } /* Free plugin-path */ if( path[ sizeof(path)/sizeof(char*) - 2 ] ) free( path[ sizeof(path)/sizeof(char*) - 2 ] ); path[ sizeof(path)/sizeof(char*) - 2 ] = NULL;}/***************************************************************************** * AllocatePluginDir: recursively parse a directory to look for plugins *****************************************************************************/static void AllocatePluginDir( vlc_object_t *p_this, const char *psz_dir, int i_maxdepth ){#if defined( UNDER_CE ) || defined( _MSC_VER )#ifdef UNDER_CE wchar_t psz_wpath[MAX_PATH + 256]; wchar_t psz_wdir[MAX_PATH];#endif char psz_path[MAX_PATH + 256]; WIN32_FIND_DATA finddata; HANDLE handle; int rc;#else int i_dirlen; DIR * dir; struct dirent * file;#endif char * psz_file; if( p_this->p_vlc->b_die || i_maxdepth < 0 ) { return; }#if defined( UNDER_CE ) || defined( _MSC_VER )#ifdef UNDER_CE MultiByteToWideChar( CP_ACP, 0, psz_dir, -1, psz_wdir, MAX_PATH ); rc = GetFileAttributes( psz_wdir ); if( rc<0 || !(rc&FILE_ATTRIBUTE_DIRECTORY) ) return; /* Not a directory */ /* Parse all files in the directory */ swprintf( psz_wpath, L"%ls\\*", psz_wdir );#else rc = GetFileAttributes( psz_dir ); if( rc<0 || !(rc&FILE_ATTRIBUTE_DIRECTORY) ) return; /* Not a directory */#endif /* Parse all files in the directory */ sprintf( psz_path, "%s\\*", psz_dir );#ifdef UNDER_CE handle = FindFirstFile( psz_wpath, &finddata );#else handle = FindFirstFile( psz_path, &finddata );#endif if( handle == INVALID_HANDLE_VALUE ) { /* Empty directory */ return; } /* Parse the directory and try to load all files it contains. */ do {#ifdef UNDER_CE unsigned int i_len = wcslen( finddata.cFileName ); swprintf( psz_wpath, L"%ls\\%ls", psz_wdir, finddata.cFileName ); sprintf( psz_path, "%s\\%ls", psz_dir, finddata.cFileName );#else unsigned int i_len = strlen( finddata.cFileName ); sprintf( psz_path, "%s\\%s", psz_dir, finddata.cFileName );#endif /* Skip ".", ".." and anything starting with "." */ if( !*finddata.cFileName || *finddata.cFileName == '.' ) { if( !FindNextFile( handle, &finddata ) ) break; continue; }#ifdef UNDER_CE if( GetFileAttributes( psz_wpath ) & FILE_ATTRIBUTE_DIRECTORY )#else if( GetFileAttributes( psz_path ) & FILE_ATTRIBUTE_DIRECTORY )#endif { AllocatePluginDir( p_this, psz_path, i_maxdepth - 1 ); } else if( i_len > strlen( LIBEXT ) /* We only load files ending with LIBEXT */ && !strncasecmp( psz_path + strlen( psz_path) - strlen( LIBEXT ), LIBEXT, strlen( LIBEXT ) ) ) { WIN32_FILE_ATTRIBUTE_DATA attrbuf; int64_t i_time = 0, i_size = 0;#ifdef UNDER_CE if( GetFileAttributesEx( psz_wpath, GetFileExInfoStandard, &attrbuf ) )#else if( GetFileAttributesEx( psz_path, GetFileExInfoStandard, &attrbuf ) )#endif { i_time = attrbuf.ftLastWriteTime.dwHighDateTime; i_time <<= 32; i_time |= attrbuf.ftLastWriteTime.dwLowDateTime; i_size = attrbuf.nFileSizeHigh; i_size <<= 32; i_size |= attrbuf.nFileSizeLow; } psz_file = psz_path; AllocatePluginFile( p_this, psz_file, i_time, i_size ); } } while( !p_this->p_vlc->b_die && FindNextFile( handle, &finddata ) ); /* Close the directory */ FindClose( handle );#else dir = opendir( psz_dir ); if( !dir ) { return; } i_dirlen = strlen( psz_dir ); /* Parse the directory and try to load all files it contains. */ while( !p_this->p_vlc->b_die && (file = readdir( dir )) ) { struct stat statbuf; unsigned int i_len; int i_stat; /* Skip ".", ".." and anything starting with "." */ if( !*file->d_name || *file->d_name == '.' ) { continue; } i_len = strlen( file->d_name ); psz_file = malloc( i_dirlen + 1 + i_len + 1 );#ifdef WIN32 sprintf( psz_file, "%s\\%s", psz_dir, file->d_name );#else sprintf( psz_file, "%s/%s", psz_dir, file->d_name );#endif i_stat = stat( psz_file, &statbuf ); if( !i_stat && statbuf.st_mode & S_IFDIR ) { AllocatePluginDir( p_this, psz_file, i_maxdepth - 1 ); } else if( i_len > strlen( LIBEXT ) /* We only load files ending with LIBEXT */ && !strncasecmp( file->d_name + i_len - strlen( LIBEXT ), LIBEXT, strlen( LIBEXT ) ) ) { int64_t i_time = 0, i_size = 0; if( !i_stat ) { i_time = statbuf.st_mtime; i_size = statbuf.st_size; } AllocatePluginFile( p_this, psz_file, i_time, i_size ); } free( psz_file ); } /* Close the directory */ closedir( dir );#endif}/***************************************************************************** * AllocatePluginFile: load a module into memory and initialize it. ***************************************************************************** * This function loads a dynamically loadable module and allocates a structure * for its information data. The module can then be handled by module_Need * and module_Unneed. It can be removed by DeleteModule. *****************************************************************************/static int AllocatePluginFile( vlc_object_t * p_this, char * psz_file, int64_t i_file_time, int64_t i_file_size ){ module_t * p_module; module_cache_t *p_cache_entry = NULL; /* * Check our plugins cache first then load plugin if needed */ p_cache_entry = CacheFind( p_this, psz_file, i_file_time, i_file_size ); if( !p_cache_entry ) { p_module = AllocatePlugin( p_this, psz_file ); } else { /* If junk dll, don't try to load it */ if( p_cache_entry->b_junk ) { p_module = NULL; } else { module_config_t *p_item; p_module = p_cache_entry->p_module; p_module->b_loaded = VLC_FALSE; /* For now we force loading if the module's config contains * callbacks or actions. * Could be optimized by adding an API call.*/ for( p_item = p_module->p_config; p_item->i_type != CONFIG_HINT_END; p_item++ ) { if( p_item->pf_callback || p_item->i_action ) p_module = AllocatePlugin( p_this, psz_file ); } } } if( p_module ) { /* Everything worked fine ! * The module is ready to be added to the list. */ p_module->b_builtin = VLC_FALSE; /* msg_Dbg( p_this, "plugin \"%s\", %s", p_module->psz_object_name, p_module->psz_longname ); */ vlc_object_attach( p_module, p_this->p_libvlc->p_module_bank ); } if( !p_this->p_libvlc->p_module_bank->b_cache ) return 0; /* Add entry to cache */#define p_bank p_this->p_libvlc->p_module_bank p_bank->pp_cache = realloc( p_bank->pp_cache, (p_bank->i_cache + 1) * sizeof(void *) ); p_bank->pp_cache[p_bank->i_cache] = malloc( sizeof(module_cache_t) ); p_bank->pp_cache[p_bank->i_cache]->psz_file = strdup( psz_file ); p_bank->pp_cache[p_bank->i_cache]->i_time = i_file_time; p_bank->pp_cache[p_bank->i_cache]->i_size = i_file_size; p_bank->pp_cache[p_bank->i_cache]->b_junk = p_module ? 0 : 1; p_bank->pp_cache[p_bank->i_cache]->p_module = p_module; p_bank->i_cache++; return p_module ? 0 : -1;}/***************************************************************************** * AllocatePlugin: load a module into memory and initialize it. ***************************************************************************** * This function loads a dynamically loadable module and allocates a structure * for its information data. The module can then be handled by module_Need * and module_Unneed. It can be removed by DeleteModule. *****************************************************************************/static module_t * AllocatePlugin( vlc_object_t * p_this, char * psz_file ){ module_t * p_module; module_handle_t handle; if( LoadModule( p_this, psz_file, &handle ) ) return NULL; /* Now that we have successfully loaded the module, we can * allocate a structure for it */ p_module = vlc_object_create( p_this, VLC_OBJECT_MODULE ); if( p_module == NULL ) { msg_Err( p_this, "out of memory" ); CloseModule( handle ); return NULL; } /* We need to fill these since they may be needed by CallEntry() */ p_module->psz_filename = psz_file; p_module->handle = handle; p_module->p_symbols = &p_this->p_libvlc->p_module_bank->symbols; p_module->b_loaded = VLC_TRUE; /* Initialize the module: fill p_module, default config */ if( CallEntry( p_module ) != 0 ) { /* We couldn't call module_init() */ vlc_object_destroy( p_module ); CloseModule( handle ); return NULL; } DupModule( p_module ); p_module->psz_filename = strdup( p_module->psz_filename ); /* Everything worked fine ! The module is ready to be added to the list. */ p_module->b_builtin = VLC_FALSE; return p_module;}/***************************************************************************** * DupModule: make a plugin module standalone. ***************************************************************************** * This function duplicates all strings in the module, so that the dynamic * object can be unloaded. It acts recursively on submodules. *****************************************************************************/static void DupModule( module_t *p_module ){ char **pp_shortcut; int i_submodule; for( pp_shortcut = p_module->pp_shortcuts ; *pp_shortcut ; pp_shortcut++ ) { *pp_shortcut = strdup( *pp_shortcut ); } /* We strdup() these entries so that they are still valid when the * module is unloaded. */ p_module->psz_object_name = strdup( p_module->psz_object_name ); p_module->psz_capability = strdup( p_module->psz_capability ); p_module->psz_shortname = p_module->psz_shortname ? strdup( p_module->psz_shortname ) : NULL; p_module->psz_longname = strdup( p_module->psz_longname ); if( p_module->psz_program != NULL ) { p_module->psz_program = strdup( p_module->psz_program ); } for( i_submodule = 0; i_submodule < p_module->i_children; i_submodule++ ) { DupModule( (module_t*)p_module->pp_children[ i_submodule ] ); }}/***************************************************************************** * UndupModule: free a duplicated module. ***************************************************************************** * This function frees the allocations done in DupModule(). *****************************************************************************/static void UndupModule( module_t *p_module ){ char **pp_shortcut; int i_submodule; for( i_submodule = 0; i_submodule < p_module->i_children; i_submodule++ ) { UndupModule( (module_t*)p_module->pp_children[ i_submodule ] ); } for( pp_shortcut = p_module->pp_shortcuts ; *pp_shortcut ; pp_shortcut++ ) { free( *pp_shortcut ); } free( p_module->psz_object_name ); free( p_module->psz_capability ); if( p_module->psz_shortname ) free( p_module->psz_shortname ); free( p_module->psz_longname ); if( p_module->psz_program != NULL ) { free( p_module->psz_program ); }}#endif /* HAVE_DYNAMIC_PLUGINS *//***************************************************************************** * AllocateBuiltinModule: initialize a builtin module. ***************************************************************************** * This function registers a builtin module and allocates a structure * for its information data. The module can then be handled by module_Need * and module_Unneed. It can be removed by DeleteModule. *****************************************************************************/static int AllocateBuiltinModule( vlc_object_t * p_this, int ( *pf_entry ) ( module_t * ) ){ module_t * p_module; /* Now that we have successfully loaded the module, we can * allocate a structure for it */ p_module = vlc_object_create( p_this, VLC_OBJECT_MODULE ); if( p_module == NULL ) { msg_Err( p_this, "out of memory" ); return -1; }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -