I’ve decided to write this entry to talk about twointertwined subjects:
- The published RDPESC parser needs a little tweakin order to function properly
- That tweak is a real life example of how tomodify an existing Netmon Parser
My goal is not to rewrite the [MS-RDPESC]document in this publication so I’ll be assuming that you are familiar with itand will touch the protocol details just tangentially.
I’ve recently worked on a case where a customer wasobserving that Netmon 3.4was not being able to decode some of the RDPESC packets correctly. The parserwas only going as far as the TLS layer and was taking the rest of the data as asimple Blob.
This is pretty much what it looked like:
The first thing that came to my mind was obviously that theparser version the customer was using was stale so, I provided the link to thelatest and greatest version of Netmon parsers: 03.04.2978.0001.
Hold your horses!
Although customer was happy with the way the newer versionof the parsers was handling the RDPESC structures… there was something notworking…
This is what the same frame looked like with the plainvanilla new parsers:
As we can see, this is day and night compared with nothaving anything parsed below TLS.
But… and there’s always a “but”, look at the RDPESC packetitself. There’s something wrong…
This is what other RDPESC packets look like (other controlcodes that is):
Don’t lose your headER!!!
Different calls and returns contain different data (duh!)… Evendifferent headers sometimes! (hmmm)
But, shouldn’t packets ALWAYS have a header?!?!
(What? What red pill? Oh…. Ok… lots of water? Ok, here itgoes…)
Sorry, my friend Morpheus was talking to me.
As I was saying, even though there might be protocols thatdo not have a properly design header structure, RDPESC is not one of those andits packets do indeed possess a header.
So, what could possibly go wrong with the parser that it istreating one return call differently from another return call?
Welcome to "The Parserix"…
If we right click on the RDPESC call return andselect “Go To Data Type Definition”, the RDPESC parser file opens up and thefirst thing we can see is this:
At first sight, having a “switch” clause is a good sign. Itwouldn’t be the first time someone misses a case in a switch clause… would it?
Although the above mentioned is a very common scenario, itwas not the EXACT case this time around.
Because of the way the RDPESC parser works, we need to lookat the initial call’s control code in order to figure out which of thescenarios it is that we are dealing with.
I present you with the control code for SCARD_IOCTL_ACCESSSTARTEDEVENT:
Once the control code has been identified, we can then seethat 0x900E0 is a special case on the RDPESC parser world:
All fine and dandy but, what’s wrong?
Well, basically the document specifies in section 3.1.4that:
“6. Otherwise,DR_DEVICE_IOCOMPLETION.IOStatus MUST be set to 0 (STATUS_SUCCESS) andDR_DEVICE_IOCOMPLETION.Parameters.DeviceIOControl.OutputBuffer MUST contain anencoding of the structure (as specified in the preceding Message ProcessingEvents and Sequencing Rules IOCTL Table) as specified in [MS-RPCE] section 2.2.6. DR_DEVICE_IOCOMPLETION.Parameters.DeviceIOControl.OutputBufferLengthis the length of the data.”
That means that the return call is to be parsed WITH anMSRPCHeader.
So, we need to modify the parser.
MUST… MODIFY… PARSER…
So in order to make this change to the parser, we can followeither of the two main ways we know we can use to modify parsers:
- We can either add a personalized copy of theparser to some “myparsers” folder and then set that folder as the first optionin the list of precedence in the current profile OR
- We can replace the existing RDPESC parser fromthe Windows profile in Network Monitor with an updated version of it.
In this case, we’ll use the second approach.
These are the steps:
1) Navigate to “C:\ProgramData\Microsoft\NetworkMonitor 3\NPL\NetworkMonitor Parsers\Windows”
2) Save a copy of rdpesc.npl to a safe location
3) Open the original file with a text editor
// SmartCardCall W/O MSRPCHeader
5) With: //
// SmartCardCall (Special case, see below)
//The "Call" does NOT have a RPCHeader
// Whereas, the "Return" does (so, handle the same way as all the otherIOCTLs)
6) Save the file back to its original place
Once the modification has been made, reopen thecapture in Network Monitor and look at the results. The return call should nowlook like this:
“It is done!”
PS: I was going to be more wordy for the conclusion of this entry but I figured out thatthe post was pretty much self-explanatory.BTW, if you want to learn some more details regarding parser modifications, youcan take a peek at my co-worker’s entry from some time ago: http://blogs.msdn.com/b/openspecification/archive/2011/08/08/customizing-in-box-netmon-parsers-how-to-edit-and-deploy-updated-netmon-parsers.aspx