Register OpenUSD plugin resources deployed beside the executable. On Windows: /usd/ — keeps relative LibraryPaths correct. On Linux: /../lib/usd/ — conventional layout. Must be called before any USD API usage (stage creation, schema lookup). The env-var approach (PXR_PLUGINPATH_NAME) does not work reliably on Windows because USD DLLs may initialise before main() runs.
| 139 | // The env-var approach (PXR_PLUGINPATH_NAME) does not work reliably on |
| 140 | // Windows because USD DLLs may initialise before main() runs. |
| 141 | void configure_usd_plugins() { |
| 142 | std::filesystem::path exe_dir; |
| 143 | try { |
| 144 | exe_dir = lfs::core::getExecutableDir(); |
| 145 | } catch (...) { |
| 146 | return; |
| 147 | } |
| 148 | |
| 149 | std::error_code ec; |
| 150 | |
| 151 | // On Windows, plugins sit next to the exe at <exe_dir>/usd/ so that |
| 152 | // relative LibraryPath entries (e.g. "../../usd_ar.dll") resolve to |
| 153 | // the DLL copies that are already loaded by Windows at startup. |
| 154 | // On Linux they follow the conventional <exe_dir>/../lib/usd/ layout. |
| 155 | #ifdef _WIN32 |
| 156 | auto usd_dir = exe_dir / "usd"; |
| 157 | #else |
| 158 | auto usd_dir = exe_dir / ".." / "lib" / "usd"; |
| 159 | #endif |
| 160 | usd_dir = std::filesystem::canonical(usd_dir, ec); |
| 161 | if (ec || !std::filesystem::is_directory(usd_dir, ec)) { |
| 162 | LOG_ERROR("[USD] plugin directory not found ({})", |
| 163 | ec ? ec.message() : "not a directory"); |
| 164 | return; |
| 165 | } |
| 166 | |
| 167 | const std::string path_utf8 = lfs::core::path_to_utf8(usd_dir); |
| 168 | |
| 169 | // Also set the env var for any code that reads it directly. |
| 170 | #ifdef _WIN32 |
| 171 | _putenv_s("PXR_PLUGINPATH_NAME", path_utf8.c_str()); |
| 172 | #else |
| 173 | setenv("PXR_PLUGINPATH_NAME", path_utf8.c_str(), /*overwrite=*/0); |
| 174 | #endif |
| 175 | |
| 176 | // Programmatically register plugins so the Plug system finds them |
| 177 | // regardless of compiled-in search paths or env var timing. |
| 178 | pxr::PlugRegistry::GetInstance().RegisterPlugins(path_utf8); |
| 179 | } |
| 180 | } // namespace |
| 181 | |
| 182 | int main(int argc, char* argv[]) { |
no test coverage detected