Skip to content

Instantly share code, notes, and snippets.

@Ciantic
Created July 4, 2020 20:06
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Ciantic/de5f3189f31673b3f997011f9431d118 to your computer and use it in GitHub Desktop.
Save Ciantic/de5f3189f31673b3f997011f9431d118 to your computer and use it in GitHub Desktop.
use com::{
runtime::{init_apartment, ApartmentType},
sys::CoCreateInstance,
ComInterface, ComPtr, ComRc, CLSID, IID,
};
fn errorhandler<T, F>(f: F, error: HRESULT, retry: u32) -> Result<T, HRESULT>
where
F: Fn() -> Result<T, HRESULT>,
{
if retry == 0 {
Err(error)
} else {
match error {
// Com class is not registered
HRESULT(0x80040154) => comrun(f, retry),
// Com not initialized
HRESULT(0x800401F0) => {
init_apartment(ApartmentType::Multithreaded).map_err(HRESULT::from_i32)?;
comrun(f, retry)
}
// RPC went away
HRESULT(0x800706BA) => comrun(f, retry),
// Others as is
HRESULT(v) => Err(HRESULT(v)),
}
}
}
fn comrun<T, F>(f: F, retry: u32) -> Result<T, HRESULT>
where
F: Fn() -> Result<T, HRESULT>,
{
match f() {
Ok(v) => Ok(v),
Err(err) => errorhandler(f, err, retry - 1),
}
}
pub fn run<F, T>(f: F) -> Result<T, HRESULT>
where
F: Fn() -> Result<T, HRESULT>,
{
comrun(f, 6)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment