@@ -5,6 +5,7 @@ package cim
55
66import (
77 "fmt"
8+ "runtime"
89 "strings"
910
1011 "github.com/go-ole/go-ole"
@@ -366,3 +367,30 @@ var (
366367func FindInstancesByObjectIDMapping (instanceToFind []* cim.WmiInstance , associatedInstances []* cim.WmiInstance , instanceMappings map [string ]string ) ([]* cim.WmiInstance , error ) {
367368 return FindInstancesByMapping (instanceToFind , objectIDPropertyIndexer , associatedInstances , objectIDPropertyIndexer , instanceMappings )
368369}
370+
371+ // WithCOMThread runs the given function `fn` on a locked OS thread
372+ // with COM initialized using COINIT_MULTITHREADED.
373+ //
374+ // This is necessary for using COM/OLE APIs directly (e.g., via go-ole),
375+ // because COM requires that initialization and usage occur on the same thread.
376+ //
377+ // It performs the following steps:
378+ // - Locks the current goroutine to its OS thread
379+ // - Calls ole.CoInitializeEx with COINIT_MULTITHREADED
380+ // - Executes the user-provided function
381+ // - Uninitializes COM
382+ // - Unlocks the thread
383+ //
384+ // If COM initialization fails, or if the user's function returns an error,
385+ // that error is returned by WithCOMThread.
386+ func WithCOMThread (fn func () error ) error {
387+ runtime .LockOSThread ()
388+ defer runtime .UnlockOSThread ()
389+
390+ if err := ole .CoInitializeEx (0 , ole .COINIT_MULTITHREADED ); err != nil {
391+ return err
392+ }
393+ defer ole .CoUninitialize ()
394+
395+ return fn ()
396+ }
0 commit comments