Yes, I understand the problem (and have come across it myself a few times).
Itâs definitely possible, but itâs not simple, at all, due to a combination of relevance limitations & unresolved bugs.
We can definitely use your query to retrieve the files that we want to inspect, the problem then is that once we know we want to look in \windows\inf\oem1.inf and \windows\inf\oem3.inf, we need to retrieve the right values from those files.
The first inclination I had was to use the âsection of fileâ and âkey of sectionâ inspectors to treat these as INI files; the problem there is that we have no iterator for sections or keys, you have to know the exact names of the sections and the exact names of the keys to retrieve the values. In this case we might know the names of the sections (itâs not always exactly Microsoft.NTamd64, sometimes it would be Microsoft.NTamd64.10.0 for example) ⌠but in no case would we know the names of the values we want to retrieve.
The next solution Iâd try would be to use the âvariables of fileâ inspector, which would give a list of every variable name and value in a format like
q: variables of (native files "c:\temp\test.inf")
A: [Version].Signature="$Windows NT$"
A: [Version].Class=Net
A: [Version].ClassGUID={4d36e972-e325-11ce-bfc1-08002be10318}
A: [Version].Provider=%25Microsoft%25
A: [Version].CatalogFile=msux64w10.cat ;; for WHQL certified
A: [Version].DriverVer=01/24/2017,10.4.0124.2017
A: [Manufacturer].%25Microsoft%25=Microsoft, NTamd64.10.0
A: [ControlFlags].ExcludeFromSelect=*
âŚbut this inspector is broken in that it cannot process files encoded in anything other than ASCII / UTF-8, and most of these INF files are encoded in UTF-16; they give no results for the âvariables of fileâ inspector.
With the easy paths out of the way, I think weâll have to build our own parsing logic. That makes this similar to a relevance challenge I posted previously at Relevance Challenge December 2019 BONUS: Parsing Paragraphs (answer provided) that has several different solutions.
Of the solutions there, I think the easiest to understand and probably the best to use in this case is where we concatenate all the lines together into one string so we can use âpreceding textâ and âfollowing textâ to isolate the one section that we want, then split that back out into its individual lines. I concatenate (and then split) on the "%0a"
character, which is a newline character so we know itâs not actually a literal value in the file. Leaving aside âhow to find the right INF fileâ for the moment, this illustrates what I mean:
q: lines of files "c:\temp\test.inf"
A: ; ** COPYRIGHT (C) 2007-2017 Microsoft CORPORATION
A: ;
...
A:
A: [Version]
A: Signature = "$Windows NT$"
...
A:
A: [Microsoft.NTamd64.10.0]
A: %25RTL8153.DeviceDesc%25 = RTL8153.ndi,USB\VID_045E&PID_07C6&REV_3000
A: %25RTL8153.DeviceDesc%25 = RTL8153B.ndi,USB\VID_045E&PID_0927&REV_3100
A: %25RTL8153.DeviceDesc%25 = RTL8153B_S5WOL.ndi,USB\VID_045E&PID_0927&REV_3101
A:
A: ;;****************************************************************************
A: ;; Windows 10
A: ;;****************************************************************************
A: [RTL8152B.ndi.NT]
A: AddReg = MSUX64W10.NT.Reg
...
q: concatenation "%0a" of lines of files "c:\temp\test.inf"
A: ; ** COPYRIGHT (C) 2007-2017 Microsoft CORPORATION%0a;%0a%0a;;%0a;; This product is covered by one or more of the following patents:%0a;; US6,570,884, US6,115,776, and US6,327,625.%0a;;%0a%0a[Version]%0aSignature = "$Windows NT$"%0aClass = Net%0aClassGUID = {4d36e972-e325-11ce-bfc1-08002be10318}%0aProvider = %25Microsoft%25%0aCatalogFile = msux64w10.cat ;; for WHQL certified%0aDriverVer = 01/24/2017,10.4.0124.2017%0a%0a[Manufacturer]%0a%25Microsoft%25 = Microsoft, NTamd64.10.0%0a%0a[ControlFlags]%0aExcludeFromSelect = *%0a%0a[Microsoft]%0a;Empty section, so this INf does not support win2000%0a%0a[Microsoft.NTamd64.10.0]%0a%25RTL8153.DeviceDesc%25 = RTL8153.ndi,USB\VID_045E&PID_07C6&REV_3000%0a%25RTL8153.DeviceDesc%25 = RTL8153B.ndi,USB\VID_045E&PID_0927&REV_3100%0a%25RTL8153.DeviceDesc%25 = RTL8153B_S5WOL.ndi,USB\VID_045E&PID_0927&REV_3101%0a%0a;;****************************************************************************%0a;; Windows 10%0a;;****************************************************************************%0a[RTL8152B.ndi.NT]%0aAddReg = MSUX64W10.NT.Reg%0a
// isolate the section that we want - beginning from the first ']' after '[Microsoft.NTamd64' and ending at the next combination of newline & '[' (or, the end of the file, if there is no new section after this one). ALso keep track of the filename, since we may want to reference the specific oemxx.inf file later:
q: (names of it, ((preceding text of first "%0a[" of it | it) of following texts of firsts "]" of following texts of firsts "[Microsoft.NTamd64" of it) of concatenations "%0a" of lines of it) of files ("oem1.inf";"oem3.inf") of folders "c:\windows\inf"
A: oem3.inf, ( %0a%25RTL8153.DeviceDesc%25 = RTL8153.ndi,USB\VID_045E&PID_07C6&REV_3000%0a%25RTL8153.DeviceDesc%25 = RTL8153B.ndi,USB\VID_045E&PID_0927&REV_3100%0a%25RTL8153.DeviceDesc%25 = RTL8153B_S5WOL.ndi,USB\VID_045E&PID_0927&REV_3101%0a%0a;;****************************************************************************%0a;; Windows 10%0a;;**************************************************************************** )
T: 33.677 ms
I: plural ( string, substring )
// with the right section isolated, split it back up into separate results again
q: (names of it, (substrings separated by "%0a" of it) of ((preceding text of first "%0a[" of it | it) of following texts of firsts "]" of following texts of firsts "[Microsoft.NTamd64" of it) of concatenations "%0a" of lines of it) of files ("oem1.inf";"oem3.inf") of folders "c:\windows\inf"
A: oem3.inf,
A: oem3.inf, ( %25RTL8153.DeviceDesc%25 = RTL8153.ndi,USB\VID_045E&PID_07C6&REV_3000 )
A: oem3.inf, ( %25RTL8153.DeviceDesc%25 = RTL8153B.ndi,USB\VID_045E&PID_0927&REV_3100 )
A: oem3.inf, ( %25RTL8153.DeviceDesc%25 = RTL8153B_S5WOL.ndi,USB\VID_045E&PID_0927&REV_3101 )
A: oem3.inf,
A: oem3.inf, ;;****************************************************************************
A: oem3.inf, ;; Windows 10
A: oem3.inf, ;;****************************************************************************
T: 33.293 ms
I: plural ( string, substring )
// since we only want the names of the values, take the preceding texts of the equals signs. And since the name may be repeated, take the 'unique values of it'.
q: (names of it, unique values of (preceding texts of firsts " = " of it as trimmed string) of (substrings separated by "%0a" of it) of ((preceding text of first "%0a[" of it | it) of following texts of firsts "]" of following texts of firsts "[Microsoft.NTamd64" of it) of concatenations "%0a" of lines of it) of files ("oem1.inf";"oem3.inf") of folders "c:\windows\inf"
A: oem3.inf, %25RTL8153.DeviceDesc%25
T: 33.641 ms
I: plural ( string, string with multiplicity )
Next we need to deal with retrieving the right .inf files to inspect. Hereâs an example of testing more than one file; weâll just need to substitute in your query in place of the list of filenames
q: (names of it, unique values of (preceding texts of firsts " = " of it as trimmed string) of (substrings separated by "%0a" of it) of ((preceding text of first "%0a[" of it | it) of following texts of firsts "]" of following texts of firsts "[Microsoft.NTamd64" of it) of concatenations "%0a" of lines of it) of files ( /* YOUR QUERY HERE */ "oem1.inf";"oem3.inf" ) of folders "c:\windows\inf"
A: oem3.inf, %25RTL8153.DeviceDesc%25
T: 15.200 ms
I: plural ( string, string with multiplicity )
So, what I think should work is
q: (names of it, unique values of (preceding texts of firsts "=" of it as trimmed string) of (substrings separated by "%0a" of it) of ((preceding text of first "%0a[" of it | it) of following texts of firsts "]" of following texts of firsts "[Microsoft.NTamd64" of it) of concatenations "%0a" of lines of it) of files ( (preceding texts of lasts "%22 BlockMigration=" of following texts of firsts "<DriverPackage Inf=%22" of lines containing "BlockMigration=%22True%22" of (file "ScanResult.xml" of folder "$WINDOWS.~BT\Sources\Panther" of drive of system folder) as string) ) of folders "c:\windows\inf"