Example #1
0
// This example creates a new spreadsheet, reads and modifies cell values and style.
func main() {
	ole.CoInitialize(0)
	unknown, errCreate := oleutil.CreateObject("com.sun.star.ServiceManager")
	checkError(errCreate, "Couldn't create a OLE connection to LibreOffice")
	ServiceManager, errSM := unknown.QueryInterface(ole.IID_IDispatch)
	checkError(errSM, "Couldn't start a LibreOffice instance")
	desktop := oleutil.MustCallMethod(ServiceManager,
		"createInstance", "com.sun.star.frame.Desktop").ToIDispatch()

	document := LONewSpreadsheet(desktop)
	sheet0 := LOGetWorksheet(document, 0)

	cell1_1 := LOGetCell(sheet0, 1, 1) // cell B2
	cell1_2 := LOGetCell(sheet0, 1, 2) // cell B3
	cell1_3 := LOGetCell(sheet0, 1, 3) // cell B4
	cell1_4 := LOGetCell(sheet0, 1, 4) // cell B5
	LOSetCellString(cell1_1, "Hello World")
	LOSetCellValue(cell1_2, 33.45)
	LOSetCellFormula(cell1_3, "=B3+5")
	b4Value := LOGetCellString(cell1_3)
	LOSetCellString(cell1_4, b4Value)
	// set background color yellow:
	oleutil.MustPutProperty(cell1_1, "cellbackcolor", 0xFFFF00)

	fmt.Printf("Press [ENTER] to exit")
	fmt.Scanf("%s")
	ServiceManager.Release()
	ole.CoUninitialize()
}
Example #2
0
func (c *AdodbConn) prepare(ctx context.Context, query string) (driver.Stmt, error) {
	unknown, err := oleutil.CreateObject("ADODB.Command")
	if err != nil {
		return nil, err
	}
	s, err := unknown.QueryInterface(ole.IID_IDispatch)
	if err != nil {
		return nil, err
	}
	_, err = oleutil.PutProperty(s, "ActiveConnection", c.db)
	if err != nil {
		return nil, err
	}
	_, err = oleutil.PutProperty(s, "CommandText", query)
	if err != nil {
		return nil, err
	}
	_, err = oleutil.PutProperty(s, "CommandType", 1)
	if err != nil {
		return nil, err
	}
	_, err = oleutil.PutProperty(s, "Prepared", true)
	if err != nil {
		return nil, err
	}
	val, err := oleutil.GetProperty(s, "Parameters")
	if err != nil {
		return nil, err
	}
	return &AdodbStmt{c, s, val.ToIDispatch(), nil}, nil
}
Example #3
0
func main() {
	ole.CoInitialize(0)

	unknown, err := oleutil.CreateObject("{248DD896-BB45-11CF-9ABC-0080C7E7B78D}")
	if err != nil {
		panic(err.Error())
	}
	winsock, _ := unknown.QueryInterface(ole.IID_IDispatch)
	iid, _ := ole.CLSIDFromString("{248DD893-BB45-11CF-9ABC-0080C7E7B78D}")

	dest := &EventReceiver{}
	dest.lpVtbl = &EventReceiverVtbl{}
	dest.lpVtbl.pQueryInterface = syscall.NewCallback(QueryInterface)
	dest.lpVtbl.pAddRef = syscall.NewCallback(AddRef)
	dest.lpVtbl.pRelease = syscall.NewCallback(Release)
	dest.lpVtbl.pGetTypeInfoCount = syscall.NewCallback(GetTypeInfoCount)
	dest.lpVtbl.pGetTypeInfo = syscall.NewCallback(GetTypeInfo)
	dest.lpVtbl.pGetIDsOfNames = syscall.NewCallback(GetIDsOfNames)
	dest.lpVtbl.pInvoke = syscall.NewCallback(Invoke)
	dest.host = winsock

	oleutil.ConnectObject(winsock, iid, (*ole.IUnknown)(unsafe.Pointer(dest)))
	_, err = oleutil.CallMethod(winsock, "Connect", "127.0.0.1", 80)
	if err != nil {
		log.Fatal(err)
	}

	var m ole.Msg
	for dest.ref != 0 {
		ole.GetMessage(&m, 0, 0, 0)
		ole.DispatchMessage(&m)
	}
}
Example #4
0
func main() {
	cwd, _ := os.Getwd()
	artworkjpg := filepath.Join(cwd, "artwork.jpg")

	gc := gntp.NewClient()
	gc.AppName = "nowplaying"
	gc.Register([]gntp.Notification{{"default", "", true}})

	ole.CoInitialize(0)
	unk, err := oleutil.CreateObject("iTunes.Application")
	if err != nil {
		log.Fatal(err)
	}
	unk.AddRef()
	dsp := unk.MustQueryInterface(ole.IID_IDispatch)

	prev := ""
	for {
		func() {
			defer func() {
				recover()
			}()
			track := oleutil.MustGetProperty(dsp, "CurrentTrack").ToIDispatch()
			if track != nil {
				name := oleutil.MustGetProperty(track, "Name").ToString()
				artist := oleutil.MustGetProperty(track, "artist").ToString()
				album := oleutil.MustGetProperty(track, "Album").ToString()
				curr := fmt.Sprintf("%s/%s\n%s", name, artist, album)
				if curr != prev {
					prev = curr
					artwork := oleutil.MustGetProperty(track, "Artwork").ToIDispatch()
					item := oleutil.MustGetProperty(artwork, "Item", 1).ToIDispatch()
					icon := ""
					if item != nil {
						_, err = oleutil.CallMethod(item, "SaveArtworkToFile", artworkjpg)
						if err != nil {
							log.Print(err)
						} else {
							icon = artworkjpg
						}
					}
					log.Print(curr)
					err = gc.Notify(&gntp.Message{
						Event: "default",
						Title: "iTunes",
						Text:  curr,
						Icon:  icon,
					})
					if err != nil {
						log.Print(err)
					}
				}
			}
		}()
		time.Sleep(3 * time.Second)
	}
}
Example #5
0
func iTunes() *ole.IDispatch {
	ole.CoInitialize(0)
	unknown, err := oleutil.CreateObject("iTunes.Application")
	if err != nil {
		log.Fatal(err)
	}
	itunes, err := unknown.QueryInterface(ole.IID_IDispatch)
	if err != nil {
		log.Fatal(err)
	}
	return itunes
}
func getFriendlyName(portname string) string {

	// this method panics a lot and i'm not sure why, just catch
	// the panic and return empty list
	defer func() {
		if e := recover(); e != nil {
			// e is the interface{} typed-value we passed to panic()
			log.Println("Got panic: ", e) // Prints "Whoops: boom!"
		}
	}()

	var friendlyName string

	// init COM, oh yeah
	ole.CoInitialize(0)
	defer ole.CoUninitialize()

	unknown, _ := oleutil.CreateObject("WbemScripting.SWbemLocator")
	defer unknown.Release()

	wmi, _ := unknown.QueryInterface(ole.IID_IDispatch)
	defer wmi.Release()

	// service is a SWbemServices
	serviceRaw, _ := oleutil.CallMethod(wmi, "ConnectServer")
	service := serviceRaw.ToIDispatch()
	defer service.Release()

	// result is a SWBemObjectSet
	//pname := syscall.StringToUTF16("SELECT * FROM Win32_PnPEntity where Name like '%" + "COM35" + "%'")
	pname := "SELECT * FROM Win32_PnPEntity where Name like '%" + portname + "%'"
	resultRaw, _ := oleutil.CallMethod(service, "ExecQuery", pname)
	result := resultRaw.ToIDispatch()
	defer result.Release()

	countVar, _ := oleutil.GetProperty(result, "Count")
	count := int(countVar.Val)

	for i := 0; i < count; i++ {
		// item is a SWbemObject, but really a Win32_Process
		itemRaw, _ := oleutil.CallMethod(result, "ItemIndex", i)
		item := itemRaw.ToIDispatch()
		defer item.Release()

		asString, _ := oleutil.GetProperty(item, "Name")

		println(asString.ToString())
		friendlyName = asString.ToString()
	}

	return friendlyName
}
Example #7
0
func main() {
	ole.CoInitialize(0)
	unknown, _ := oleutil.CreateObject("Agent.Control.1")
	agent, _ := unknown.QueryInterface(ole.IID_IDispatch)
	oleutil.PutProperty(agent, "Connected", true)
	characters := oleutil.MustGetProperty(agent, "Characters").ToIDispatch()
	oleutil.CallMethod(characters, "Load", "Merlin", "c:\\windows\\msagent\\chars\\Merlin.acs")
	character := oleutil.MustCallMethod(characters, "Character", "Merlin").ToIDispatch()
	oleutil.CallMethod(character, "Show")
	oleutil.CallMethod(character, "Speak", "こんにちわ世界")

	time.Sleep(4000000000)
}
Example #8
0
func createMdb(f string) error {
	unk, err := oleutil.CreateObject("ADOX.Catalog")
	if err != nil {
		return err
	}
	cat, err := unk.QueryInterface(ole.IID_IDispatch)
	if err != nil {
		return err
	}
	_, err = oleutil.CallMethod(cat, "Create", "Provider=Microsoft.Jet.OLEDB.4.0;Data Source="+f+";")
	if err != nil {
		return err
	}
	return nil
}
Example #9
0
func (d *AdodbDriver) Open(dsn string) (driver.Conn, error) {
	ole.CoInitialize(0)
	unknown, err := oleutil.CreateObject("ADODB.Connection")
	if err != nil {
		return nil, err
	}
	db, err := unknown.QueryInterface(ole.IID_IDispatch)
	if err != nil {
		return nil, err
	}
	_, err = oleutil.CallMethod(db, "Open", dsn)
	if err != nil {
		return nil, err
	}
	return &AdodbConn{db}, nil
}
Example #10
0
func Initialize(opt ...Option) (mso *MSO) {
	ole.CoInitialize(0)
	app, _ := oleutil.CreateObject("Excel.Application")
	excel, _ := app.QueryInterface(ole.IID_IDispatch)
	wbs := oleutil.MustGetProperty(excel, "WorkBooks").ToIDispatch()
	ver, _ := strconv.ParseFloat(oleutil.MustGetProperty(excel, "Version").ToString(), 64)

	if len(opt) == 0 {
		opt = []Option{{"Visible": true, "DisplayAlerts": true, "ScreenUpdating": true}}
	}
	mso = &MSO{Option: opt[0], IuApp: app, IdExcel: excel, IdWorkBooks: wbs, Version: ver}
	mso.SetOption(1)

	//XlFileFormat Enumeration: http://msdn.microsoft.com/en-us/library/office/ff198017%28v=office.15%29.aspx
	mso.FILEFORMAT = map[string]int{"txt": -4158, "csv": 6, "html": 44}
	return
}
Example #11
0
func main() {
	ole.CoInitialize(0)
	unknown, err := oleutil.CreateObject("WMPlayer.OCX")
	if err != nil {
		log.Fatal(err)
	}
	wmp := unknown.MustQueryInterface(ole.IID_IDispatch)
	collection := oleutil.MustGetProperty(wmp, "MediaCollection").ToIDispatch()
	list := oleutil.MustCallMethod(collection, "getAll").ToIDispatch()
	count := int(oleutil.MustGetProperty(list, "count").Val)
	for i := 0; i < count; i++ {
		item := oleutil.MustGetProperty(list, "item", i).ToIDispatch()
		name := oleutil.MustGetProperty(item, "name").ToString()
		sourceURL := oleutil.MustGetProperty(item, "sourceURL").ToString()
		fmt.Println(name, sourceURL)
	}
}
Example #12
0
func main() {
	log.SetFlags(log.Flags() | log.Lshortfile)
	ole.CoInitialize(0)
	unknown, _ := oleutil.CreateObject("Excel.Application")
	excel, _ := unknown.QueryInterface(ole.IID_IDispatch)
	oleutil.PutProperty(excel, "Visible", true)

	workbooks := oleutil.MustGetProperty(excel, "Workbooks").ToIDispatch()
	cwd, _ := os.Getwd()
	writeExample(excel, workbooks, cwd+"\\write.xls")
	readExample(cwd+"\\excel97-2003.xls", excel, workbooks)
	showMethodsAndProperties(workbooks)
	workbooks.Release()
	// oleutil.CallMethod(excel, "Quit")
	excel.Release()
	ole.CoUninitialize()
}
Example #13
0
func main() {
	ole.CoInitialize(0)
	unknown, _ := oleutil.CreateObject("Outlook.Application")
	outlook, _ := unknown.QueryInterface(ole.IID_IDispatch)
	ns := oleutil.MustCallMethod(outlook, "GetNamespace", "MAPI").ToIDispatch()
	folder := oleutil.MustCallMethod(ns, "GetDefaultFolder", 10).ToIDispatch()
	contacts := oleutil.MustCallMethod(folder, "Items").ToIDispatch()
	count := oleutil.MustGetProperty(contacts, "Count").Value().(int32)
	for i := 1; i <= int(count); i++ {
		item, err := oleutil.GetProperty(contacts, "Item", i)
		if err == nil && item.VT == ole.VT_DISPATCH {
			if value, err := oleutil.GetProperty(item.ToIDispatch(), "FullName"); err == nil {
				fmt.Println(value.Value())
			}
		}
	}
	oleutil.MustCallMethod(outlook, "Quit")
}
Example #14
0
func main() {
	ole.CoInitialize(0)
	unknown, _ := oleutil.CreateObject("Excel.Application")
	excel, _ := unknown.QueryInterface(ole.IID_IDispatch)
	oleutil.PutProperty(excel, "Visible", true)
	workbooks := oleutil.MustGetProperty(excel, "Workbooks").ToIDispatch()
	workbook := oleutil.MustCallMethod(workbooks, "Add", nil).ToIDispatch()
	worksheet := oleutil.MustGetProperty(workbook, "Worksheets", 1).ToIDispatch()
	cell := oleutil.MustGetProperty(worksheet, "Cells", 1, 1).ToIDispatch()
	oleutil.PutProperty(cell, "Value", 12345)

	time.Sleep(2000000000)

	oleutil.PutProperty(workbook, "Saved", true)
	oleutil.CallMethod(workbook, "Close", false)
	oleutil.CallMethod(excel, "Quit")
	excel.Release()

	ole.CoUninitialize()
}
Example #15
0
func main() {
	ole.CoInitialize(0)
	unknown, _ := oleutil.CreateObject("InternetExplorer.Application")
	ie, _ := unknown.QueryInterface(ole.IID_IDispatch)
	oleutil.CallMethod(ie, "Navigate", "http://www.google.com")
	oleutil.PutProperty(ie, "Visible", true)
	for {
		if oleutil.MustGetProperty(ie, "Busy").Val == 0 {
			break
		}
	}

	time.Sleep(1e9)

	document := oleutil.MustGetProperty(ie, "document").ToIDispatch()
	window := oleutil.MustGetProperty(document, "parentWindow").ToIDispatch()
	// set 'golang' to text box.
	oleutil.MustCallMethod(window, "eval", "document.getElementsByName('q')[0].value = 'golang'")
	// click btnG.
	btnG := oleutil.MustCallMethod(window, "eval", "document.getElementsByName('btnG')[0]").ToIDispatch()
	oleutil.MustCallMethod(btnG, "click")
}
Example #16
0
func main() {
	ole.CoInitialize(0)
	unknown, _ := oleutil.CreateObject("Microsoft.XMLHTTP")
	xmlhttp, _ := unknown.QueryInterface(ole.IID_IDispatch)
	_, err := oleutil.CallMethod(xmlhttp, "open", "GET", "http://rss.slashdot.org/Slashdot/slashdot", false)
	if err != nil {
		panic(err.Error())
	}
	_, err = oleutil.CallMethod(xmlhttp, "send", nil)
	if err != nil {
		panic(err.Error())
	}
	state := -1
	for state != 4 {
		state = int(oleutil.MustGetProperty(xmlhttp, "readyState").Val)
		time.Sleep(10000000)
	}
	responseXml := oleutil.MustGetProperty(xmlhttp, "responseXml").ToIDispatch()
	items := oleutil.MustCallMethod(responseXml, "selectNodes", "/rss/channel/item").ToIDispatch()
	length := int(oleutil.MustGetProperty(items, "length").Val)

	for n := 0; n < length; n++ {
		item := oleutil.MustGetProperty(items, "item", n).ToIDispatch()

		title := oleutil.MustCallMethod(item, "selectSingleNode", "title").ToIDispatch()
		fmt.Println(oleutil.MustGetProperty(title, "text").ToString())

		link := oleutil.MustCallMethod(item, "selectSingleNode", "link").ToIDispatch()
		fmt.Println("  " + oleutil.MustGetProperty(link, "text").ToString())

		title.Release()
		link.Release()
		item.Release()
	}
	items.Release()
	xmlhttp.Release()
}
Example #17
0
// NOTE:  This function will panic if called with high frequency (we should throttle the polling - probably caused by slow OLE calls that can't be parallel.. sigh ;))
func GetSerialPortList() ([]CommPort, error) {
	err := ole.CoInitializeEx(0, ole.COINIT_MULTITHREADED)
	if err != nil {
		log.Fatal("Init error: ", err)
	}
	defer ole.CoUninitialize()

	unknown, _ := oleutil.CreateObject("WbemScripting.SWbemLocator")
	defer unknown.Release()

	wmi, _ := unknown.QueryInterface(ole.IID_IDispatch)
	defer wmi.Release()

	serviceRaw, _ := oleutil.CallMethod(wmi, "ConnectServer")
	service := serviceRaw.ToIDispatch()
	defer service.Release()

	query := "SELECT * FROM Win32_PnPEntity WHERE ConfigManagerErrorCode = 0 and Name like '%(COM%'"
	queryResult, err2 := oleutil.CallMethod(service, "ExecQuery", query)

	commPorts := []CommPort{}

	if err2 != nil {
		log.Printf("Error from oleutil.CallMethod: ", err2)
		return nil, err2
	}

	result := queryResult.ToIDispatch()
	defer result.Release()

	countVar, _ := oleutil.GetProperty(result, "Count")
	count := int(countVar.Val)

	// Should we filter on VID/PID here or later?
	for i := 0; i < count; i++ {
		itemRaw, _ := oleutil.CallMethod(result, "ItemIndex", i)
		item := itemRaw.ToIDispatch()
		defer item.Release()

		displayName, _ := oleutil.GetProperty(item, "Name")

		fmt.Printf("Port found: %s\n", displayName.ToString())

		re := regexp.MustCompile("\\((COM[0-9]+)\\)").FindAllStringSubmatch(displayName.ToString(), 1)

		var path string = ""

		if re != nil && len(re[0]) > 1 {
			path = re[0][1]
		}

		fmt.Printf("Path: %v\n", path)

		deviceId, _ := oleutil.GetProperty(item, "DeviceID")

		re = regexp.MustCompile("ID_(....)").FindAllStringSubmatch(deviceId.ToString(), 2)

		var VID, PID uint16 = 0, 0

		if re != nil && len(re) == 2 {
			if len(re[0]) > 1 {
				val, _ := strconv.ParseUint(re[0][1], 16, 16)
				VID = uint16(val)
			}
			if len(re[1]) > 1 {
				val, _ := strconv.ParseUint(re[1][1], 16, 16)
				PID = uint16(val)
			}
			fmt.Printf("VID: %v, PID: %v\n", VID, PID)
		}

		commPorts = append(commPorts, CommPort{Path: path, VendorId: VID, ProductId: PID, DisplayName: displayName.ToString()})

	}

	return commPorts, err
}
Example #18
0
func listComPorts() {
	// init COM
	ole.CoInitialize(0)
	defer ole.CoUninitialize()

	locator, err := oleutil.CreateObject("WbemScripting.SWbemLocator")
	if err != nil {
		log.Fatal(err)
	}
	defer locator.Release()

	wmi, err := locator.QueryInterface(ole.IID_IDispatch)
	if err != nil {
		log.Fatal(err)
	}
	defer wmi.Release()

	// service is a SWbemServices
	serviceRaw, err := oleutil.CallMethod(wmi, "ConnectServer")
	if err != nil {
		log.Fatal(err)
	}
	service := serviceRaw.ToIDispatch()
	defer service.Release()

	// result is a SWBemObjectSet
	resultRaw, err := oleutil.CallMethod(service, "ExecQuery", "SELECT * FROM Win32_PnPEntity WHERE Name LIKE '%(COM%)'")
	if err != nil {
		log.Fatal(err)
	}
	result := resultRaw.ToIDispatch()
	defer result.Release()

	countVar, err := oleutil.GetProperty(result, "Count")
	if err != nil {
		log.Fatal(err)
	}
	count := int(countVar.Val)

	var ports Ports
	re := regexp.MustCompile(`(.*) \(COM(\d+)\)$`)
	for i := 0; i < count; i++ {
		// item is a SWbemObject, but really a Win32_Process
		itemRaw, err := oleutil.CallMethod(result, "ItemIndex", i)
		if err != nil {
			continue
		}
		item := itemRaw.ToIDispatch()
		defer item.Release()

		property, err := oleutil.GetProperty(item, "Name")
		if err != nil {
			continue
		}
		port := re.FindAllStringSubmatch(property.ToString(), -1)
		num, _ := strconv.Atoi(port[0][2])
		ports = append(ports, Port{num, port[0][1]})
	}

	sort.Sort(ports)

	digit := getDigit(ports[len(ports)-1].Number)
	for i := 0; i < len(ports); i++ {
		fmt.Println("COM" + strconv.Itoa(ports[i].Number) + strings.Repeat(" ", digit-getDigit(ports[i].Number)) + " : " + ports[i].Name)
	}
}
func getListViaWmiPnpEntity() ([]OsSerialPort, os.SyscallError) {

	//log.Println("Doing getListViaWmiPnpEntity()")

	// this method panics a lot and i'm not sure why, just catch
	// the panic and return empty list
	defer func() {
		if e := recover(); e != nil {
			// e is the interface{} typed-value we passed to panic()
			log.Println("Got panic: ", e) // Prints "Whoops: boom!"
		}
	}()

	var err os.SyscallError

	//var friendlyName string

	// init COM, oh yeah
	ole.CoInitialize(0)
	defer ole.CoUninitialize()

	unknown, _ := oleutil.CreateObject("WbemScripting.SWbemLocator")
	defer unknown.Release()

	wmi, _ := unknown.QueryInterface(ole.IID_IDispatch)
	defer wmi.Release()

	// service is a SWbemServices
	serviceRaw, _ := oleutil.CallMethod(wmi, "ConnectServer")
	service := serviceRaw.ToIDispatch()
	defer service.Release()

	// result is a SWBemObjectSet
	//pname := syscall.StringToUTF16("SELECT * FROM Win32_PnPEntity where Name like '%" + "COM35" + "%'")
	pname := "SELECT * FROM Win32_PnPEntity WHERE ConfigManagerErrorCode = 0 and Name like '%(COM%'"
	//pname := "SELECT * FROM Win32_PnPEntity WHERE ConfigManagerErrorCode = 0"
	resultRaw, err2 := oleutil.CallMethod(service, "ExecQuery", pname)
	//log.Println("Got result from oleutil.CallMethod")
	if err2 != nil {
		// we got back an error or empty list
		log.Printf("Got an error back from oleutil.CallMethod. err:%v", err2)
		return nil, err
	}

	result := resultRaw.ToIDispatch()
	defer result.Release()

	countVar, _ := oleutil.GetProperty(result, "Count")
	count := int(countVar.Val)

	list := make([]OsSerialPort, count)

	for i := 0; i < count; i++ {

		// items we're looping thru look like below and
		// thus we can query for any of these names
		/*
					__GENUS                     : 2
			__CLASS                     : Win32_PnPEntity
			__SUPERCLASS                : CIM_LogicalDevice
			__DYNASTY                   : CIM_ManagedSystemElement
			__RELPATH                   : Win32_PnPEntity.DeviceID="USB\\VID_1D50&PID_606D&MI_02\\6&2F09EA14&0&0002"
			__PROPERTY_COUNT            : 24
			__DERIVATION                : {CIM_LogicalDevice, CIM_LogicalElement, CIM_ManagedSystemElement}
			__SERVER                    : JOHN-ATIV
			__NAMESPACE                 : root\cimv2
			__PATH                      : \\JOHN-ATIV\root\cimv2:Win32_PnPEntity.DeviceID="USB\\VID_1D50&PID_606D&MI_02\\6&2F09EA14
			                              &0&0002"
			Availability                :
			Caption                     : TinyG v2 (Data Channel) (COM12)
			ClassGuid                   : {4d36e978-e325-11ce-bfc1-08002be10318}
			CompatibleID                : {USB\Class_02&SubClass_02&Prot_01, USB\Class_02&SubClass_02, USB\Class_02}
			ConfigManagerErrorCode      : 0
			ConfigManagerUserConfig     : False
			CreationClassName           : Win32_PnPEntity
			Description                 : TinyG v2 (Data Channel)
			DeviceID                    : USB\VID_1D50&PID_606D&MI_02\6&2F09EA14&0&0002
			ErrorCleared                :
			ErrorDescription            :
			HardwareID                  : {USB\VID_1D50&PID_606D&REV_0097&MI_02, USB\VID_1D50&PID_606D&MI_02}
			InstallDate                 :
			LastErrorCode               :
			Manufacturer                : Synthetos (www.synthetos.com)
			Name                        : TinyG v2 (Data Channel) (COM12)
			PNPDeviceID                 : USB\VID_1D50&PID_606D&MI_02\6&2F09EA14&0&0002
			PowerManagementCapabilities :
			PowerManagementSupported    :
			Service                     : usbser
			Status                      : OK
			StatusInfo                  :
			SystemCreationClassName     : Win32_ComputerSystem
			SystemName                  : JOHN-ATIV
			PSComputerName              : JOHN-ATIV
		*/

		// item is a SWbemObject, but really a Win32_Process
		itemRaw, _ := oleutil.CallMethod(result, "ItemIndex", i)
		item := itemRaw.ToIDispatch()
		defer item.Release()

		asString, _ := oleutil.GetProperty(item, "Name")

		//log.Println(asString.ToString())

		// get the com port
		//if false {
		s := strings.Split(asString.ToString(), "(COM")[1]
		s = "COM" + s
		s = strings.Split(s, ")")[0]
		list[i].Name = s
		list[i].FriendlyName = asString.ToString()
		//}

		// get the deviceid so we can figure out related ports
		// it will look similar to
		// USB\VID_1D50&PID_606D&MI_00\6&2F09EA14&0&0000
		deviceIdStr, _ := oleutil.GetProperty(item, "DeviceID")
		devIdItems := strings.Split(deviceIdStr.ToString(), "&")
		log.Printf("DeviceId elements:%v", devIdItems)
		if len(devIdItems) > 3 {
			list[i].SerialNumber = devIdItems[3]
			//list[i].IdProduct = strings.Replace(devIdItems[1], "PID_", "", 1)
			//list[i].IdVendor = strings.Replace(devIdItems[0], "USB\\VID_", "", 1)
		} else {
			list[i].SerialNumber = deviceIdStr.ToString()
		}

		pidMatch := regexp.MustCompile("PID_(....)").FindAllStringSubmatch(deviceIdStr.ToString(), -1)
		if len(pidMatch) > 0 {
			if len(pidMatch[0]) > 1 {
				list[i].IdProduct = pidMatch[0][1]
			}
		}
		vidMatch := regexp.MustCompile("VID_(....)").FindAllStringSubmatch(deviceIdStr.ToString(), -1)
		if len(vidMatch) > 0 {
			if len(vidMatch[0]) > 1 {
				list[i].IdVendor = vidMatch[0][1]
			}
		}

		manufStr, _ := oleutil.GetProperty(item, "Manufacturer")
		list[i].Manufacturer = manufStr.ToString()
		descStr, _ := oleutil.GetProperty(item, "Description")
		list[i].Product = descStr.ToString()
		//classStr, _ := oleutil.GetProperty(item, "CreationClassName")
		//list[i].DeviceClass = classStr.ToString()

	}

	for index, element := range list {

		log.Printf("index:%v, name:%v, friendly:%v ", index, element.Name, element.FriendlyName)
		log.Printf("pid:%v, vid:%v", element.IdProduct, element.IdVendor)

		for index2, element2 := range list {
			if index == index2 {
				continue
			}
			if element.SerialNumber == element2.SerialNumber {
				log.Printf("Found related element1:%v, element2:%v", element, element2)
				list[index].RelatedNames = append(list[index].RelatedNames, element2.Name)
			}
		}

	}

	return list, err
}
Example #20
0
// Query runs the WQL query and appends the values to dst.
//
// dst must have type *[]S or *[]*S, for some struct type S. Fields selected in
// the query must have the same name in dst. Supported types are all signed and
// unsigned integers, time.Time, string, bool, or a pointer to one of those.
// Array types are not supported.
//
// By default, the local machine and default namespace are used. These can be
// changed using connectServerArgs. See
// http://msdn.microsoft.com/en-us/library/aa393720.aspx for details.
func (c *Client) Query(query string, dst interface{}, connectServerArgs ...interface{}) error {
	dv := reflect.ValueOf(dst)
	if dv.Kind() != reflect.Ptr || dv.IsNil() {
		return ErrInvalidEntityType
	}
	dv = dv.Elem()
	mat, elemType := checkMultiArg(dv)
	if mat == multiArgTypeInvalid {
		return ErrInvalidEntityType
	}

	lock.Lock()
	defer lock.Unlock()
	runtime.LockOSThread()
	defer runtime.UnlockOSThread()

	err := ole.CoInitializeEx(0, ole.COINIT_MULTITHREADED)
	if err != nil {
		oleCode := err.(*ole.OleError).Code()
		if oleCode != ole.S_OK && oleCode != S_FALSE {
			return err
		}
	}
	defer ole.CoUninitialize()

	unknown, err := oleutil.CreateObject("WbemScripting.SWbemLocator")
	if err != nil {
		return err
	} else if unknown == nil {
		return ErrNilCreateObject
	}
	defer unknown.Release()

	wmi, err := unknown.QueryInterface(ole.IID_IDispatch)
	if err != nil {
		return err
	}
	defer wmi.Release()

	// service is a SWbemServices
	serviceRaw, err := oleutil.CallMethod(wmi, "ConnectServer", connectServerArgs...)
	if err != nil {
		return err
	}
	service := serviceRaw.ToIDispatch()
	defer serviceRaw.Clear()

	// result is a SWBemObjectSet
	resultRaw, err := oleutil.CallMethod(service, "ExecQuery", query)
	if err != nil {
		return err
	}
	result := resultRaw.ToIDispatch()
	defer resultRaw.Clear()

	count, err := oleInt64(result, "Count")
	if err != nil {
		return err
	}

	enumProperty, err := result.GetProperty("_NewEnum")
	if err != nil {
		return err
	}
	defer enumProperty.Clear()

	enum, err := enumProperty.ToIUnknown().IEnumVARIANT(ole.IID_IEnumVariant)
	if err != nil {
		return err
	}
	if enum == nil {
		return fmt.Errorf("can't get IEnumVARIANT, enum is nil")
	}
	defer enum.Release()

	// Initialize a slice with Count capacity
	dv.Set(reflect.MakeSlice(dv.Type(), 0, int(count)))

	var errFieldMismatch error
	for itemRaw, length, err := enum.Next(1); length > 0; itemRaw, length, err = enum.Next(1) {
		if err != nil {
			return err
		}

		err := func() error {
			// item is a SWbemObject, but really a Win32_Process
			item := itemRaw.ToIDispatch()
			defer item.Release()

			ev := reflect.New(elemType)
			if err = c.loadEntity(ev.Interface(), item); err != nil {
				if _, ok := err.(*ErrFieldMismatch); ok {
					// We continue loading entities even in the face of field mismatch errors.
					// If we encounter any other error, that other error is returned. Otherwise,
					// an ErrFieldMismatch is returned.
					errFieldMismatch = err
				} else {
					return err
				}
			}
			if mat != multiArgTypeStructPtr {
				ev = ev.Elem()
			}
			dv.Set(reflect.Append(dv, ev))
			return nil
		}()
		if err != nil {
			return err
		}
	}
	return errFieldMismatch
}
Example #21
0
// Query runs the WQL query and appends the values to dst.
//
// dst must have type *[]S or *[]*S, for some struct type S. Fields selected in
// the query must have the same name in dst. Supported types are all signed and
// unsigned integers, time.Time, string, bool, or a pointer to one of those.
// Array types are not supported.
//
// By default, the local machine and default namespace are used. These can be
// changed using connectServerArgs. See
// http://msdn.microsoft.com/en-us/library/aa393720.aspx for details.
func (c *Client) Query(query string, dst interface{}, connectServerArgs ...interface{}) error {
	dv := reflect.ValueOf(dst)
	if dv.Kind() != reflect.Ptr || dv.IsNil() {
		return ErrInvalidEntityType
	}
	dv = dv.Elem()
	mat, elemType := checkMultiArg(dv)
	if mat == multiArgTypeInvalid {
		return ErrInvalidEntityType
	}

	lock.Lock()
	defer lock.Unlock()
	runtime.LockOSThread()
	defer runtime.UnlockOSThread()

	err := ole.CoInitializeEx(0, ole.COINIT_MULTITHREADED)
	if err != nil {
		oleerr := err.(*ole.OleError)
		// S_FALSE           = 0x00000001 // CoInitializeEx was already called on this thread
		if oleerr.Code() != ole.S_OK && oleerr.Code() != 0x00000001 {
			return err
		}
	} else {
		// Only invoke CoUninitialize if the thread was not initizlied before.
		// This will allow other go packages based on go-ole play along
		// with this library.
		defer ole.CoUninitialize()
	}

	unknown, err := oleutil.CreateObject("WbemScripting.SWbemLocator")
	if err != nil {
		return err
	}
	defer unknown.Release()

	wmi, err := unknown.QueryInterface(ole.IID_IDispatch)
	if err != nil {
		return err
	}
	defer wmi.Release()

	// service is a SWbemServices
	serviceRaw, err := oleutil.CallMethod(wmi, "ConnectServer", connectServerArgs...)
	if err != nil {
		return err
	}
	service := serviceRaw.ToIDispatch()
	defer serviceRaw.Clear()

	// result is a SWBemObjectSet
	resultRaw, err := oleutil.CallMethod(service, "ExecQuery", query)
	if err != nil {
		return err
	}
	result := resultRaw.ToIDispatch()
	defer resultRaw.Clear()

	count, err := oleInt64(result, "Count")
	if err != nil {
		return err
	}

	// Initialize a slice with Count capacity
	dv.Set(reflect.MakeSlice(dv.Type(), 0, int(count)))

	var errFieldMismatch error
	for i := int64(0); i < count; i++ {
		err := func() error {
			// item is a SWbemObject, but really a Win32_Process
			itemRaw, err := oleutil.CallMethod(result, "ItemIndex", i)
			if err != nil {
				return err
			}
			item := itemRaw.ToIDispatch()
			defer itemRaw.Clear()

			ev := reflect.New(elemType)
			if err = c.loadEntity(ev.Interface(), item); err != nil {
				if _, ok := err.(*ErrFieldMismatch); ok {
					// We continue loading entities even in the face of field mismatch errors.
					// If we encounter any other error, that other error is returned. Otherwise,
					// an ErrFieldMismatch is returned.
					errFieldMismatch = err
				} else {
					return err
				}
			}
			if mat != multiArgTypeStructPtr {
				ev = ev.Elem()
			}
			dv.Set(reflect.Append(dv, ev))
			return nil
		}()
		if err != nil {
			return err
		}
	}
	return errFieldMismatch
}