Add-In Manager
(AddinManager.dll)
Software uses licensing method provided by SentinelLM Rainbow protection system (http://www.rainbow.com). The main license-check chain see on schema 1 below.

Init Add-Ins
Init
![]()
![]()
![]()
Check main license
Check Add-In license

Get license information

![]()
Schema 1 “License validation
process”
Main QT module get information about currently installed license from license manager, than call Add-In Manager to find and initialize all installed Add-Ins. For each founded Add-In module Add-In Manager send request to license manager about this module. License manager itself is COM object, which uses SentinelLM Rainbow API library to work with licenses.
No point to struggle with Rainbow with license decoding (they get big money in that field), so look close on license manager (lic_mng.dll). Use eXeScope.exe utility to get COM type-library to check license manager methods. Here is (the main functions):
Dispatch
IMercLMBasic; // IMercLMBasic Interface
GUID={340A025E-748D-11D2-823A-0080C838CEB0};
function Init(uLicType:UINT;
ProductName:BSTR);
function CheckLicense(feature:BSTR;
Version:BSTR; display_name:BSTR; retMsg:^BSTR);
function ReleaseLicense(feature:BSTR;
Version:BSTR);
function
RebuildServerList;
function GetLastError(retLastErr:^UI4;
retFeature:^BSTR; retMsg:^BSTR);
function GetLicInfo(iLicIdx:INT;
bsFeature:^BSTR; bsVersion:^BSTR; bsRetMsg:^BSTR; iLicOrigin:^INT;
iLicType:^INT; bsDisplayName:^BSTR; bsServerName:^BSTR;
iTimeToLive:^INT);
function
GetNumOfActiveLicenses(iNumOfLic:^INT);
function
GetLicInfoByName(bsFeature:BSTR; bsVersion:BSTR; bsRetMsg:^BSTR;
iLicOrigin:^INT; iLicType:^INT; bsDisplayName:^BSTR; bsServerName:^BSTR;
iTimeToLive:^INT);
function GetLicOrigin(iLicOrigin:^INT);
Not too much
for good protection and very clear function names. The main idea of how to make
QuickTest main module to forget about licenses is to make own license manager.
No point to make own COM control (possible CRC checks or other module validation
methods), but make own vtable entries – that’s right way.
Current
loader utility (ProStub32.exe) runs QuickTest module (in suspend mode – “load
and stop” execution) and injected QTLoader32.dll library into suspended process.
As license manager (lic_mng.dll) loaded by QTPro.exe after some time we need to
catch exact moment, when lic_mng.dll is loaded. To reach this goal –
QTLoader32.dll overrides LoadLibrary function (LoadLibraryA, LoadLibraryExA,
LoadLibraryW, LoadLibraryExW) and CreateProcess function (CreateProcessA,
CreateProcessW) and examine which .dll currently loaded. When lic_mng.dll
(license manager) is loaded – get pointer to vtable and replace original license
functions with new ones. Not all functions need to be overridden – Init,
CheckLicense, GetLicInfo, GetNumOfActiveLicenses, GetLicInfoByName
and GetLicOrigin (bolded functions are really called, others – just don’t
want to remove).
Short
description of functions:
Init – called to initialize SentinelLM Rainbow
API;
CheckLicense – called to “make sure license exists and
non-locked”;
GetLicInfoByName – called to get license information (type and
trial period left);
After playing with debugger and Soft-Ice I get next
solutions: program works if CheckLicense return 0 (STATUS_SUCCESS) and
GetLicInfoByName
return 0. Moreover, if
GetLicInfoByName can return license type = 3 (Permanent) and trial
left = “some value not important if license is permanent”. Init –
always return 0 (but it is overridden too, so even without valid license files –
its work).
The new vtable methods still calls original methods with ability to store return values to .log file and with ability to override these values with “correct” ones.