mIRC Scripting

mIRC: Component Object Model (COM)

COM objects are best described as pieces of compiled code that execute tasks. This is not the same as object oriented programming. Applications interact with each other through functions called interfaces (As a side note: All OLE services are COM interfaces). These interfaces usually start with an "I". (IDispatch and IUnknown for example)

Each object has its own methods, or "actions" for lack of a better term. The methods exposed by such objects work with multiple applications with scripting capabilities. Lucky for us, mIRC is one of those applications.

COM is the solution to the four basic problems that occur within component software. As stated by MSDN, these are Basic Component Interoperability, Versioning, Language Independence, and Transparent Cross-Process Interoperability. In other words, this is why mIRC is even capable of using COM. Since we can use COM, we can provide mIRC with greater functionality and create scripts that do things mIRC isn't able to do itself.

By: Champagne

mIRC Commands

Open COM Connection:
Opens a COM connection to specified programmatic identifier with assigned name.

/comopen <name> <progid>

Close COM Connection:
Closes the COM connection to which the specified name was assigned.

/comclose <name>

Register & Unregister COM Connection:
The following command can be used to register or unregister a COM dll with windows.
Regsvr32 command will not register .NET assemblies. (Regasm Might Help)

/comreg -u <filename>
;-u swiftch unregister a COM DLL with windows

COM Errors

Error Checking
Often used to check for an error after calling a COM command or identifer.Its is a good practice to check for an error after every call to any COM command or identifier

$comerr
;Returns 1 if there was an error, 0 otherwise.

Example:

//comopen x wscript.shell | if ($comerr) { halt } | else { comclose x }

$com properties

This identifier is used to performs the actions you want to utilize using the opened COM connection.

$com(name,member,method,type1,value1,...,typeN,valueN)
;Returns 0 if there was an error, 1 if its ok

progid - Programmatic Identifier the COM is associated with.

//comopen Name wscript.shell | echo -a $com(Name).progid

result - Returns the result after calling a COM member.

Alias com_result {
  .comopen x WbemScripting.SWbemLocator
  .comclose x $com(x,connectserver,3,dispatch* y)
  .comclose y $com(y,instancesof,3,bstr,win32_process,dispatch* x)
  noop $com(x,count,3)
  echo -a $com(x).result
  .comclose x
}

errortext - If there was an error, returns a description.
argerr - mIRC Help File: "Nth argument that caused the error, if the error was due to an invalid variable type."
dispatch - Boolean returned if dispatch pointer.
unknown - Boolean returned if unknown pointer

$comcall(name,alias,...)

Executes given alias when the COM call is finished. (Same syntax as $com except for the alias)

alias test {
  .comopen x wscript.shell
  noop $comcall(x,test2,sendkeys,3,bstr,hello world)
  echo -a hi
}
alias test2 {
  echo -a $com(1) y z
  .comclose x
}

$Com

$com(name/N)

Returns (name of Nth connection/name if connection is open) * N = 0 returns number of open COMs.

alias test_com {
  .comopen x wscript.shell
  echo -a $com(0)
  echo -a $com(1)
  echo -a $com(x)
  .comclose x
}

Returns value of specified variable name

$com(name/N,varname)

$comval

$comval(name,N,member)

Returns member value for the Nth instantiation of the enumerated collection in name." In laymans terms, Returns the value of the Nth item in a collection of items.
Used to give a general idea of the concept.

alias process_list {
  .comopen x WbemScripting.SWbemLocator
  if (!$comerr) {
    .comclose x $com(x,connectserver,3,dispatch* y)
    .comclose y $com(y,instancesof,3,bstr,win32_process,dispatch* x)
    if ($com(x)) {
      var %z = 1
      while ($comval(x,%z,name)) {
        echo -a $v1
        inc %z
      }
      .comclose x
    }
  }
}

Methods

Methods are a combination of the following values

DISPATCH_METHOD = 1- Call a member of an object
DISPATCH_PROPERTYGET = 2 - Return a value
DISPATCH_PROPERTYPUT = 4 - Set a property
DISPATCH_PROPERTYPUTREF = 8 - Set a property by reference

So, to set a property with a member: 1 + 4 = 5
$com(x,member,5,...)
Likewise, to call a member of an object and return a value: 1 + 2 = 3
$com(x,member,3,...)

Variable Type

Type Desc. Values
i1 single byte signed integer 0 to 225
ui1 single byte unsigned integer 0 to 255
i2 two byte signed integer -32768 to 32767
ui2 two byte unsigned integer 0 to 65535
i4 four byte signed integer +/- 2147483647
ui4 Holds unsigned 32-bit (4-byte) integers 0 through 4,294,967,295
int integer -2147483648 to 2147483647
uint unsigned integer 0 to 4294967295
r4 real, 4-byte floating point number 1.17549435E-38 to 3.40282347E+38
r8 double real, 8-byte floating point number 2.2250738585072014E-308 - 1.7976931348623157E+308
cy eight byte curreny number -922337203685477.5625 to 922337203685477.5625
date contains date and time, stored as an 8-byte floating-point number +/-79,228,162,514,264,337,593,543,950,335
decimal Holds signed 128-bit (16-byte) values representing 96-bit (12-byte) integer numbers. +/-79,228,162,514,264,337,593,543,950,335
bool contain any string or numeric representation.  
bstr null-terminated unicode character string value. A string can contain from 0 to approximately 2 billion (2^31) Unicode characters.
variant can contain string, date, time, boolean, or numeric values.  
dispatch This data type indicates a pointer to an IDispatch interface on an OLE object (DBTYPE_IDISPATCH).  
unknown This data type indicates a pointer to an IUnknown interface on an OLE object (DBTYPE_IUNKNOWN).  
error This data type indicates a 32-bit error code (DBTYPE_ERROR)  

- Source MSDN

Programmatic Identifiers

also known as: progid(s) for short
Now, naturally, progids are the object with which you'd like to open a COM connection. Therefore, one would find it a good idea to know the follwing:

  • a) What they're made up of
  • -- A progid consists of a Project and a ClassName in the format of: Project.ClassName
    -- Examples of such include: WScript.shell - Shell.application - Excel.application - WMPlayer.ocx
  • b) Be able to find them
  • -- here are ways to find progids in multiple scripting languages.

 

mIRC Scripting Language:

alias progid_list {
  .comopen a WbemScripting.SWbemLocator
  .comclose a $com(a,connectserver,3,dispatch* b)
  .comclose b $com(b,execquery,3,bstr,select progid from win32_progidspecification where progid like $qt($(%.%,)),dispatch* c)
  if ($com(c)) {
    var %c = 1
    while ($comval(c,%c,progid)) {
      echo -a $v1
      inc %c
    }
    .comclose c
  }
}

VBScript:

On Error Resume Next
z = "."
Set a = GetObject("winmgmts:{impersonationLevel=impersonate}!\\" & z & "
\root\cimv2")
Set b = a.ExecQuery("Select * FROM Win32_ProgIDSpecification")
For Each c in b
  WScript.Echo c.ProgID & vbCRLF & c.Description
Next

Windows Powershell:

dir REGISTRY::HKEY_CLASSES_ROOT\CLSID -include PROGID -recurse | foreach {$_.GetValue("")}

Aside from this, you can check out progids by searching for "progid" in you registry editor, and repeatedly pressing F3 to search for the next match.

Example Scripts

Please Choose An Example

OLE-COM Object Viewer

Microsoft has a tool called “OLE-COM Object Viewer” that can be quite handy when you want to get more info on a particular object.

You can get it here.