Resolving Network Printing Error – Again

In the previous article about “Text Mode Printing Through USB”, I had a brief encounter with “System error 1231” when trying to perform net use command.

In that occurence, the problem is resolved by installing the “Microsoft Loopback Adapter”.

So, I think the case is closed, until about 2 months later, when I am starting to explore printing method in my own notebook computer.

The “System error 1231” is happening again. OK, nevermind, I think I’ve not yet installed the Microsoft Loopback Adapter in my notebook. So, after installing it and activate the Adapter, and firing again the net use command :

I can not believe that I am encountering the same problem again, even with the presence of Microsoft Loopback Adapter.

This time, using error 1231 as the only information for researching through the net proved to be futile. There are many references to the problem statement, but no conclusive solution.

It’s time to examine more closely what’s going on inside the net use command.

The NET command is executed by the NET.EXE file that is resided in windows system folder, usually c:\windows\system32.

Using the WinDBG as the debugger, I’ve quickly found that for the NET USE command above, the NET.EXE is using WNetUseConnection function via WNetAddConnection2 function, which is part of MPR.DLL file. It is the error result of this function that the NET.EXE is reported to me. This is proved by returned value of WNetUseConnection as follows :

After the call to this function, the eax register is filled with 0x4CF which is 1231. In Windows SDK file, this error code is defined as :

#define ERROR_NETWORK_UNREACHABLE 1231L

By tracing the call tree through this function, I arrived at the last function that calls to the server via RPC framework which is NdrClientCall2. It is because of failed call to this function that gives the 0x4cf error code.

The first parameter for NdrClientCall2 is MIDL_STUB_DESC, and the record of interest of this structure here is void* RpcInterfaceInformation.

By performing examination of the record detail of RPC Interface Information record, it is found that the interface ID that is passed to NdrClientCall2 to be :

6BFFD098-A112-3610-9833-46C3F87E345A

From Microsoft’s documentation, this ID is actually an implementation of Workstation Service Remote Protocol Specification [MS-WKST]. You can obtain further information about this protocol here :

http://msdn.microsoft.com/en-us/library/cc250262(v=PROT.10).aspx

Now, I can move to perform WinDBG debug on the server side. But the question is, which application ?

By using the tasklist /svc command, I can list all of the candidates of application that is related to workstation service :

Hmm, seems that the svchost.exe process number 432 is a good candidate for a more detailed examination. This is because there is a service name (lanmanworkstation) that might be related to workstation function we sought for.

Let’s first examine the loaded DLLs for this service application :

From the module list, there’s a DLL named WKSSVC.DLL that could be the location of the workstation function.

To verify this, I am performing the look up of the failed call in client side just before NdrClientCall2 to be :

5b86e6b4 e830000000 call NETAPI32!NetrUseAdd (5b86e6e9)

So, maybe there’s equivalent server side function for that function :

By marking the breakpoint for this candidate functions, I can now arrive at the correct server side workstation function that is related to net use command :

Tracing inside wkssvc!NetrUseAdd, it is found that the error code is originated from wkssvc!WsOpenCreateConnection. Inside this function, the error code 0x4cf is the result of mapping function of error code 0xc000023c by way of wkssvc!WsMapStatus.

So, the search for error code is now at 0xc000023c, which originated from the result of ntdll!NtCreateFile.

Inside NtCreateFile, there is an assignment of system service number to 0x25 before the call to kernel address space using ntdll!KiFastSystemCall. It is the return of this system call that causes 0xc000023c error code.

So, it’s time to utilize my Virtual Machine (I am using Microsoft Virtual Machine 2007) in order to do the debugging of kernel address space.

After successfully emulating the desired error code in my Virtual Machine, I am now connected to the virtual machine with my WinDBG, and perform the breakpoint of nt!NtCreateFile function.

But, here, because I am now inside kernel address space, there should be many calls of nt!NtCreateFile function called from active threads that resides to my virtual machine.

To prevent losing many of my hairs and time spent trying to sieve to many of the NtCreateFile function calls, I am performing conditional break-point only when certain parameters of interest happen to be exist within NtCreateFile function call.

In my case, the net use command :

Is transformed to \Device\Lanmanredirector\;LPT1:0000000000008ee6\127.0.0.1\lx300 as one of parameters to NtCreateFile function.

When the break-point is occured at the desired NtCreateFile function, my next step is to perform the bottom-up and statistical approach by probing each candidate function and their stacks for the occurrence of 0xc000023c. This rather tedious approach is inevitable due to the impossibility to perform usual top-down approach by performing step-trace inside NtCreateFile function.

It’s impossible because at the time that I am doing the step trace, the WinDBG will pick up any running thread inside return address of the function being debugged. In other words, I will came in at first at the correct thread, but with high probability of getting out inside wrong thread. Welcome to the wonder worlds of windows kernel debugging 🙂

Using the method I’ve described, eventually I arrived at :

It is the call of certain driver in nt!IopfCallDriver that returns the 0xc000023c. The first parameter of this function contains information about the driver being called.

To perform break-point just before the call to nt!IopfCallDriver so that the driver information can be retrieved, I have to first perform break-point to the desired NtCreateFile call, record the thread id, then perform conditional break-point to the address just before the nt!IopfCallDriver for that thread id.

When I arrive at this break-point location for the desired thread, using !devobj command now I know that the driver in question happen to be MRxSmb.sys.

At this time, the tracing task become more easier, because now, I can revert back to usual top-down approach. In this fashion, I am quickly arrived at the source of the error code, that happens to be the result of hard-coded error inside mrxsmb!VctInstantiateServerTransport.

This function checks for offset 0x4 of mrxsmb!MRxSmbTransports structure, which is of 0x0 (null value). The null value causes VctInstantiateServerTransport returned hard-coded 0xc000023c to the caller.

The conclusion is that net use command requires that offset 0x4 of mrxsmb!MRxSmbTransports should be already initialized by some value. It would be very difficult, if not impossible to determine the cause of why this offset is not initialized.

Fortunately, my virtual machine happens to carry out the net use command successfully when I activate the network function, where as my notebook the net use command failed. The offset 0x4 is initialized when the network is activated, and it is null when the network is disabled in the virtual machine.

To determine when the address is initialized, I am performing break-point on write to the offset 0x4, and activate the network function.

When this is carried out, I arrive at curious callstack below :

Seems that netbt.sys is somehow related to the initialization of the address at offset 0x4 of mrxsmb!MRxSmbTransports structure.

By researching the net (googling) about this driver (netbt.sys), from :

http://support.microsoft.com/kb/946937

It turns out that netbt.sys is activated by adding the TransportBindName with \Device\ as the value in the HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\NetBT\Parameters :

This time, after re-starting the notebook, and re-activate Microsoft Loopback Adapter, the net use command is now executed successfully.

After researching further, I’ve found that netbt is related to port 445 that is vulnerable to network attack. So, the reader is advised to activate netbt.sys when it is absolutely necessary, i.e. when performing the print redirection using net use command line function.

Advertisements

One Response to “Resolving Network Printing Error – Again”

  1. webseite Says:

    Thank you for sharing your thoughts. I truly
    appreciate your efforts and I am waiting for your next write ups thank
    you once again.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s


%d bloggers like this: