How do i get SerialNumber of BaseBoard with WMI? - wmi

A nice example is there to use WMI in Powerbuilder that terminates a running process.
The same technique can be used to get SerialNumber of BaseBoard. I need to extend the same code to handle return values of the WQL query.
The WQL query i want to execute is:
SELECT Product, SerialNumber FROM Win32_BaseBoard
I can execute the query above but dont know how to save the SerialNumber in a variable after the ExecuteStatement() function is called.
Please take a look at the link for complete PowerBuilder code.
How to terminate a process if it has specific folder name in its path?
Following is a portion of a sample code taken from the link above to show the function.
wsh = CREATE OleObject
wsh.ConnectToNewObject("MSScriptControl.ScriptControl")
wsh.Language = "VBScript"
wsh.AddCode(TheCode)
TRY
wsh.ExecuteStatement(FunctionName)
CATCH (RunTimeError Re01)
MessageBox("Query Error", "Following code has some problems.~r~n~r~n" + TheCode, StopSign!)
END TRY
wsh.DisconnectObject()
DESTROY wsh
The important function call
wsh.ExecuteStatement(FunctionName)
What to do after that function call to set my PowerBuilder local variables with the returned SerialNumber of BaseBoard?

OLEObject ole_wsh
Any la_baseboard[]
string ls_message
ole_wsh = CREATE OLEObject
ole_wsh.ConnectToNewObject("MSScriptControl.ScriptControl")
ole_wsh.Language = "vbscript"
ole_wsh.AddCode('Function rtnBaseBoard()~r~n' &
+ 'DIM objBaseBoard(2)~r~n' &
+ 'strComputer = "."~r~n' &
+ 'Set objWMIService =' &
+ ' GetObject("winmgmts:\\" & strComputer & "\root\cimv2")~r~n' &
+ 'Set colItems =' &
+ ' objWMIService.ExecQuery("SELECT Product, SerialNumber FROM Win32_BaseBoard")~r~n' &
+ 'For Each objItem in colItems~r~n' &
+ 'objBaseBoard(0) = objItem.Product~r~n' &
+ 'objBaseBoard(1) = objItem.SerialNumber~r~n' &
+ 'Next~r~n' &
+ 'rtnBaseBoard = objBaseBoard~r~n' &
+ 'End Function')
la_baseboard[] = ole_wsh.Eval("rtnBaseBoard")
ole_wsh.DisconnectObject()
DESTROY ole_wsh
ls_message = "Product: " + string(la_baseboard[1]) + "~r~n" + &
+ "SerialNumber: " + string(la_baseboard[2]) + "~r~n"
MessageBox("Win32 BaseBoard",ls_message)
See more examples using WMI from Powerbuilder

Related

WMI : MSVM_Imagemanagmentservice mount method does not assign drive letter

I m trying to mount a vhd on windows 2012 hyperV core datacenter edition. For mounting the vhd I m using the MSVM_Imagemanagementservice class and mount method inside that. The disk is mounted but the problem is no drive letter is getting assigned. I have tried it on other 2012 datacenter edition and 2012 core as well it works fine. i.e after mount the drive letter gets assigned.
Any thoughts on this will help.
You can query for the drive letters list and then assign the drive letter as per your requirement. Given below is the function to get the drive letters list.
Function GetDriveLetterList(path)
'Where path is path of VHD
Dim mountedImage, diskDevice, diskPartition, diskPartitions, logicalPartition, timeout, query
Dim logicalPartitionList
timeout = 0
driveLetterList = ""
path = Replace(path,"\","\\")
Set wmiServiceCIM = GetObject("winmgmts:\\.\root\cimv2")
Do
WScript.Sleep(3000)
timeout = timeout + 3
Set mountedImage = (wmiService.ExecQuery("SELECT * FROM Msvm_MountedStorageImage WHERE Name='" & path & "'")).ItemIndex(0)
query = "SELECT * From Win32_DiskDrive WHERE Model='Msft Virtual Disk SCSI Disk Device' and SCSITargetId='" & mountedImage.TargetId & "' and SCSILogicalUnit='" & mountedImage.Lun & "' and SCSIPort='" & mountedImage.PortNumber & "'"
Set diskDevice = wmiServiceCIM.ExecQuery(query).ItemIndex(0)
query = "ASSOCIATORS OF {" & diskDevice.Path_.Path & "} where AssocClass=Win32_DiskDriveToDiskPartition"
Set diskPartitions = wmiServiceCIM.ExecQuery(query)
For Each diskPartition In diskPartitions
query = "ASSOCIATORS OF {" & diskPartition.Path_.Path & "} WHERE AssocClass=Win32_LogicalDiskToPartition"
Set logicalPartitionList = wmiServiceCIM.ExecQuery(query)
If logicalPartitionList.count > 0 Then
Set logicalPartition = logicalPartitionList.ItemIndex(0)
'WScript.Echo logicalPartition.DeviceID
driveLetterList = driveLetterList + logicalPartition.DeviceID
End If
Next
End Function
If you want to check for systems drive . Then you can do this ...
folderPath = driveLetter + ":\Windows\System32"
Set fileSys = CreateObject("Scripting.FileSystemObject")
If filesys.FolderExists(folderPath) Then
//doStuff
End If

c# NetworkInterface.GetAllNetworkInterfaces vs WMI Win32_NetworkAdapter

I get a InterfaceIndex with GetBestInterface (iphlpapi.dll).
The goal : read other interface properties.
This WMI query is slow :
SELECT MACAddress,Name,GUID,NetConnectionID FROM Win32_NetworkAdapter WHERE InterfaceIndex=
In C# there is, faster,
NetworkInterface.GetAllNetworkInterfaces()
but each NetworkInterface hasn't the property InterfaceIndex ( sic ! ).
I don't know how to optimize this :
EnumerationOptions wmi_options = new EnumerationOptions();
wmi_options.Rewindable = false;
wmi_options.ReturnImmediately = true;
string wql = "SELECT MACAddress,Name,GUID,NetConnectionID FROM Win32_NetworkAdapter WHERE InterfaceIndex=" + iface;
ManagementObjectCollection recordset = new ManagementObjectSearcher(#"root\cimv2", wql, wmi_options).Get();
foreach (ManagementObject mo in recordset)
The options don't seem to help.
Can I split the operations and cache any step ?
Or another path : avoid WMI and lookup the interface ( with InterfaceIndex ) from the registry ?
HKLM\SYSTEM\CurrentControlSet\Services\tcpip\Parameters\Interfaces
HKLM\SYSTEM\CurrentControlSet\Control\Network{4D36E972-E325-11CE-BFC1-08002BE10318}
i dont know if this is actually faster but have you tried powershell?
string IfIndex = "15";
string psscript = "get-netadapter | Where-Object interfaceindex -eq " + IfIndex;
PowerShell powershell = PowerShell.Create();
powershell.Runspace = RunspaceFactory.CreateRunspace();
powershell.Runspace.Open();
powershell.AddScript(psscript);
foreach (PSObject result in powershell.Invoke())
{
Console.WriteLine("Name: {0} " + "Status: {1}",result.Members["Name"].Value, result.Members["status"].Value);
}
Console.Read();
run this from your application, using System.Management.Automation &
System.Management.Automation.Runspaces;
i haven't tested the code yet, this is the top of my head.

How to get maxpwdAge attribute value in ActiveDirectory using C++?

i am working with AD Server,i want to get the maxpwdAge attribute value...
i already try ADSi for that,but it gives an issue.
VARIANT var;
bsNamingContext=L"maxpwdAge";
hr = ADsGetObject(pszADsPath, IID_IADsUser, (void**) &pUser);
if(SUCCEEDED(hr))
{
VariantInit(&var);
hr = pUser->Get(bsNamingContext, &var);
}
but,it gives -2147463155 (8000500d) error...
but i am using bsNamingContext=L"cn";
it gives the CN values correctly...
anyone can resolve it?
maxpwdAge is not included in user/contact/person LDAP class, so you can not retrieve it that way.
You need to query it from domain object, not user object
Try this:
Const ONE_HUNDRED_NANOSECOND = .000000100 ' .000000100 is equal to 10^-7
Const SECONDS_IN_DAY = 86400
Set objDomain = GetObject("LDAP://DC=fabrikam,DC=com") ' LINE 4
Set objMaxPwdAge = objDomain.Get("maxPwdAge") ' LINE 5
If objMaxPwdAge.LowPart = 0 Then
WScript.Echo "The Maximum Password Age is set to 0 in the " & _
"domain. Therefore, the password does not expire."
WScript.Quit
Else
dblMaxPwdNano = Abs(objMaxPwdAge.HighPart * 2^32 + objMaxPwdAge.LowPart)
dblMaxPwdSecs = dblMaxPwdNano * ONE_HUNDRED_NANOSECOND ' LINE 13
dblMaxPwdDays = Int(dblMaxPwdSecs / SECONDS_IN_DAY) ' LINE 14
WScript.Echo "Maximum password age: " & dblMaxPwdDays & " days"
End If
UPDATE:
To convert large integer to human readable value use IADsLargeInteger dispatch interface
Note 1 : Example is in VB, but you can easily rewrite it, because of COM.
Note 2 : maxpwdAge is not configured per user, but per domain (until fine-grained password policies are enabled)
Further readings:
http://msdn.microsoft.com/en-us/library/ms974598.aspx [Recommended]
http://msdn.microsoft.com/en-us/library/cc220201%28prot.20%29.aspx
http://ldapwiki.willeke.com/wiki/AD%20Determining%20Password%20Expiration
http://ldapwiki.willeke.com/wiki/Domain%20Wide%20Account%20Policies
I struggled with this one too. Eventually, I was able to get it with the following criteria.
baseDN: 'DC=myofficedomain,DC=local',
filter: '(objectClass=domain)',
attributes: ['maxPwdAge']
I hope this helps anyone else using ldapsearch or NodeJS with ActiveDirectory.

WMI USB Enable and Disable

Hi I am using WMI to change the remote registry value for USBSTOR. I want to change the value of start attribute to 4 or 3 for enabling and disabling.
But the datatype for Start attribute in registry is DWORD, if i can the datatype to size it does not work .
I need to keep the Datatype to DWORD. Can someone please tell me how to setDWORDValue using WMI, following is the piece of code that i tried, it worked succesfully but still the value of start field is unchanged in registry.
const uint HKEY_LOCAL_MACHINE = 0x80000002;
ManagementBaseObject methodParams = registryTask.GetMethodParameters(typeOfValue);
methodParams["hDefKey"] = HKEY_LOCAL_MACHINE;// BaseKey;
methodParams["sSubKeyName"] = #"SYSTEM\\CurrentControlSet\\Servic\\USBSTOR";
methodParams["sValueName"] = "Start";
try
{
methodParams["sValue"] = "3";
}
catch
{
methodParams["uValue"] = (UInt32)Convert.ToInt32("3");
}
ManagementBaseObject exitValue = registryTask.InvokeMethod(typeOfValue, methodParams, null);
Simple solution using python.
import wmi
import win32api,_winreg
c = wmi.WMI()
# To get the binary value of particular subkey
# Please note that 0x80000002 represents HKEY_LOCAL_MACHINE
ReturnValue, uValue = c.StdRegProv.GetBinaryValue(0x80000002,"AFD","SYSTEM\CurrentControlSet\Services")
# To get the list of all the subkeys available in particular key
ret, subKeys = c.StdRegProv.EnumKey (0x80000002, "SYSTEM\CurrentControlSet\Services")
print ret
for key in subKeys:
print key
ReturnValue=c.StdRegProv.SetDWORDValue(0x80000002,"Type","SYSTEM\CurrentControlSet\Services\USBSTOR",0x4)
#HKEY_CLASSES_ROOT (2147483648 (0x80000000))
#HKEY_CURRENT_USER (2147483649 (0x80000001))
#HKEY_LOCAL_MACHINE (2147483650 (0x80000002))
#HKEY_USERS (2147483651 (0x80000003))
#HKEY_CURRENT_CONFIG (2147483653 (0x80000005))
#HKEY_DYN_DATA (2147483654 (0x80000006))
Yes it can be done. Here's the code, referencing this Microsoft link and this one. Replace 3389 with the new value you want to use, and change the key as needed:
const HKEY_LOCAL_MACHINE = &H80000002
strComputer = "."
'Set StdOut = WScript.StdOut
Set oReg=GetObject( _
"winmgmts:{impersonationLevel=impersonate}!\\" &_
strComputer & "\root\default:StdRegProv")
strKeyPath = "SYSTEM\CurrentControlSet\Control\Terminal Server\WinStations\RDP-Tcp"
strValueName = "PortNumber"
' Display old value
oReg.GetDWORDValue HKEY_LOCAL_MACHINE,strKeyPath,strValueName,dwValue
WScript.Echo "Old RDP value=" & dwValue
' Set new value
dwValue= 3389
oReg.SetDWORDValue HKEY_LOCAL_MACHINE,strKeyPath,strValueName,dwValue
If Err = 0 Then
oReg.GetDWORDValue _
HKEY_LOCAL_MACHINE,strKeyPath,strValueName,dwValue
WScript.Echo "New RDP Value =" & dwValue
Else
WScript.Echo "Error in creating key" & _
" and DWORD value = " & Err.Number
End If

use wmi to get newest Windows log events

I want to use WMI to monitor the Windows event log and get newest log events every 15 minute. Although I can use WQL to do the query, it does not have the keywords such as order by. Any ideas how to work around this problem?
you can use a dataset. Below is done using vbscript, and only on the fields ComputerName,EventCode and Message. Add the other fields as desired
Const adVarChar = 200
Const MaxCharacters = 1024
Const adFldIsNullable = 32
Set DataList = CreateObject("ADOR.Recordset")
DataList.Fields.Append "ComputerName", adVarChar, MaxCharacters,adFldIsNullable
DataList.Fields.Append "EventCode", adVarChar, MaxCharacters,adFldIsNullable
DataList.Fields.Append "Message",adVarChar,MaxCharacters,adFldIsNullable
DataList.Open
strComputer = "."
strComputer = "."
Set objWMIService = GetObject("winmgmts:{impersonationLevel=impersonate}!\\" & strComputer & "\root\cimv2")
Set colLoggedEvents = objWMIService.ExecQuery("Select * from Win32_NTLogEvent Where Logfile = 'Application'")
For Each evt in colLoggedEvents
DataList.AddNew
DataList("ComputerName") = evt.ComputerName
DataList("EventCode") = evt.EventCode
DataList("Message") = evt.Message
DataList.Update
Next
'sort by eventcode
DataList..Sort = "EventCode DESC"
DataList.MoveFirst
Do Until DataList.EOF
Wscript.Echo DataList.Fields.Item("ComputerName") & vbTab & DataList.Fields.Item("EventCode") & vbTab & DataList.Fields.Item("Message")
DataList.MoveNext
Loop