Welcome to MSDN Blogs Sign in | Join | Help

Application Verifier Logs for a Service

If you have a service and have told AppVerifier to monitor it, you might wonder where the logs are and how you can see them. (Two separate questions). You can find the logs here "c:\windows\system32\config\systemprofile\appverifierlogs" (or the corresponding directory given the system drive and bitness of your application).

Now if you want to see them in AppVerifier, the easiest way is to just copy them over to the current user profile and then do a view logs from AppVerifier.

Posted by maartenb | 1 Comments

OEM Ready Links

While I'm trying to find out how to fix the portals, here are some links to documents we frequently use.

  

Posted by maartenb | 1 Comments

Shared Components

If you need to install components that are shared between multiple applications, you want them to go to Common Files. I found a decent description in this doc: "Windows Vista Application Development Requirements for User Account Control Compatibility".You should stay out of system32.

Posted by maartenb | 1 Comments

How Do I know if Windbg I actually took effect?

So you're ready to test your application with Application Verifier. The OEM Ready and Certified for Windows Vista (CFWV) test documents specify you type Windbg –I from an elevated command prompt. So you add your application to Application Verifier, add the specific tests under basic and miscellaneous and start your app. You run through your "normal operations" and exit the application. Nothing happened.

Now you have a lingering doubt: did my app not trigger any AppVerif breakpoints? Or did I not set it up right? Hmm.

Here is a little test app. Copy this in a C command line app and build; add the application.exe to AppVerif as in the test steps and it should break in with a NULL handle stop code 303.

#include "stdafx.h"

#include "windows.h"

 

int _tmain(int argc, _TCHAR* argv[])

{

    HANDLE h = NULL;

 

    WaitForSingleObject( h, 0 );

 

    wprintf(L"Okiedokie\n\r");

 

    return 0;

}

Posted by maartenb | 1 Comments

How to Roll Back WinDbg –I

For OEM Ready tests (and for Certified for Windows Vista) one of the requirements is to set up an interactive debugger. The documentation specifies Windbg since it allows you to do use extensions such as "!analyze –v" which will give you a ton of information. One question that then comes up is "How do get back my machine back to its original state before I ran WinDbg –I?"

Those are the registry keys in question that "WinDbg –I" changes:

  • \\HKEY_LOCAL_MACHINE\Software\Microsoft\Windows NT\CurrentVersion\AeDebug
  • \\HKEY_LOCAL_MACHINE\Software\Wow6432Node\Microsoft\Windows NT\CurrentVersion\AeDebug

When you set WinDbg –I, Windbg will add a new string value "Debugger" with a path to windbg.exe.     There is also an Auto string value added.

The recommendation is to back up the registry key before running WinDbg –I. On one of my clean systems the key was existent but the Debugger and Auto values were missing. Removing those effectively rolled back my system to the state it was in before. But don't take my observation as official guidance.

On a final note, if you absolutely don't like WinDbg, you can use Visual Studio as your interactive debugger. Under Tools/Options/Debugging you will find a Just-In-Time section. If you click the "Native" checkbox, your application will break in to Visual Studio when a breakpoint is encountered.

Posted by maartenb | 1 Comments

Where is my Session 0 notification?

Today I was working on an OEM Ready application. It is basically a subset of the Certified for Windows Vista program. Application Verifier is used to test reliability (heap overruns, handle usage, etc.). The test steps outline that you need to set up an interactive debugger. You will pass the test if you never see your app break in the debugger.

I had Application Verifier monitor services as well. One of the services seemed to be hanging. When something is not functioning with services in Vista or Windows Server 2008, first thing you need to think about is session 0 isolation. So I opened taskmgr, clicked "Show Processes for All Users" in the process tab and looked for Windbg. Yes it was there. (If you select Session and PID from the options column, you can even see that WinDbg is running in Session 0). But why did I not get my Session 0 notification?

There is a service called UI0Detect (for Interactive Service Detection) and it is set to start manually. As soon as I started the service, the Interactive Service notification popped up and now I could debug the AppVerifier break in.

Posted by maartenb | 0 Comments

HighestAvailable and requiresAdministrator when you’re neither Standard User nor Administrator

There is something between standard users and administrators. In UAC discussions we limit ourselves often times to members of the administrators group who get the filtered token and the full token when they log on. But what if you're a member of – say – Network Configuration operators. In that case you're not a standard user (you can do a little more) and you're certainly not an administrator.

Let's test. I have two applications: one manifested with highestAvailable and another with requiresAdministrator. Now I log in as a member of the Network Configuration Operators and I try to run both applications. Here is what happens when I run the first application:

 

Ah. The credentials dialog. So I need to retype my credentials (remember that if I were a member of administrators group, I would get the UAC prompt). This will allow me to give admin credentials as well. So I can see why this was chosen instead of the UAC prompt. At least it defaults to the logged in account.

When I launch the requireAdministrator application I get this one.

No surprise, just the regular over-the-shoulder credential dialog. Here is what happens if I type the Network Configuration Operators password:

As expected it won't elevate: the requested operation requires elevation. Elevation to a full administrator that is since it is manifested with requiresElevation.

 

Posted by maartenb | 0 Comments

Memory mapped files from XP to Vista

So you have an NT service and a user application that share date through memory mapped files. It has worked for years. It even survived XP SP2. Now Vista comes along and boom. No more. Let's see what's up.

You create your memory mapped file from your service. Something like this:

    HANDLE mmfile = CreateFileMapping(

INVALID_HANDLE_VALUE,

NULL,

PAGE_READWRITE,

upperSize,

lowerSize,

L"MaartensMap" );

And then from your user application you connect to it like so:

HANDLE mmfile = OpenFileMapping (

FILE_MAP_ALL_ACCESS,

FALSE,

L"MaartensMap" );

In Vista GetLastError() will return 2 (ERROR_FILE_NOT_FOUND). Hmm. Where did it go?

Let's look at where the file gets created on XP. Process Explorer shows this for XP:

And this for Vista:

That gives us no clue whatsoever. Identical as far as I can tell. Let's run the server code on both XP and Vista in the user session and see what Process Explorer makes of that. This might give us a clue how the client side user application will look for the memory mapped file. Here is the XP version:

And here is the one on Vista:

Oopsie. That looks different. Suppose that the client application is actually looking under this same name. No wonder that you would get an File not Found error. The names are different. Online search for "sessions\1\basenamedobject" gives hits that point to Terminal Services. There appear to be Local Global and Session namespaces. So prior to Vista and Server 2008 all services shared the same namespace as the first user logging in to the machine. This was session 0. With Vista this is no longer the case. Just like all compatibility issues it is explained in the cookbook.

Apparently if I want to keep this working I wil need to prefix my name with Global. Let's give that a try.

You will see in Process Explorer that the named object created from the service still looks the same. When you try opening it from the user mode application, you will get a different error: 5 this time. That means Access Denied, but at least we were able to find the file. Progress. The reason we get Access Denied is because we set a standard ACL on the memory mapped file and then from the user application we try to open it with All Access. So there is still some work to be done. But that is outside the scope of this blog. J A quick fix could be to open the file on the client size with only read only. But that will imply one-way traffic.

So we have sessions you say. And somewhere you read that Fast User Switching makes use of those sessions. But wait, FUS existed in the XP days as well! Why didn't that break things then, hmm? Hmm, dunno. Maybe it did. So back to the XP machine and make sure to log in as a different user while keeping the initial session alive. Running the server and trying to hook up the client gives us the initial Error 2: file not found. And when running the server side code from within a user app shows the familiar: "Sessions\1\BaseNamedObjects\MaartensMap". Conclusion: this is not a new issue but a lot more visible due to Session 0 isolation.

Posted by maartenb | 0 Comments

Enabling DCOM in Windows Server 2008

In order to make DCOM applications work in Windows Server 2008 you need to do two things. Installing the Application role is not needed (but it does add the COM+ network access as in 1) below).

  1. Allow "COM+ network access" in firewall rules (type firewall.cpl from a command prompt and on the left you'll see the setting). COM+ is somewhat of a misnomer since it is also for DCOM. COM+ Network Access is a preconfigured program in the exception list that you can just check off.
  2. Add your DCOM server to the list of program exceptions in the firewall.

A quick test of DCOM access is the DCOM test client/server app.

Posted by maartenb | 0 Comments

Vista’s Task Scheduler

Last week I was working with an OEM who had two applications: a main application and a scheduler. The sole purpose of the latter was to start the main application. Now the good thing obviously was that the customer did not want to overburden the CPU with the main application during the logon process. A polite gesture for both end-users and other applications that want to be first. However, one could ask why not use the built-in Task Scheduler?

The answer is that on XP the scheduler did not have enough flexibility for a delay. On Vista it does. You can specify all kinds of events (logon, startup, even your events that are logged in the event log). And from there you can specify the delay.

You can schedule tasks programmatically with a COM object model or you can use schtasks.exe to batch script it. No more need for custom schedulers.

Posted by maartenb | 0 Comments

Welcome Yves

My good friend Yves joined our team last week. He will be helping out with all the Windows Application Compatibility efforts we are undertaking. Yves and I always have heated discussions; maybe some of it will spill over J.

I am really delighted to have him with us.

Posted by maartenb | 1 Comments

b20 Labs and Ice cream

One of the daily challenges is passing this thing in b20 every day

.

It's refilled every week.

If you want one while pondering how to make your application compatible with WS08 or Vista, check out the MTC labs section here http://devreadiness.org. It is not explicitly mentioned but ISVs are encouraged to drop us a line if they want to come in.

Posted by maartenb | 0 Comments

Calling OOP COM Broker from PMIE finally

I kept getting -2146827859 (800A01AD Automation server can't create object) when I was trying to create my OOP COM component from PMIE. I could create the component all day long from a Low MIC console app, but not from IE. This shows my inexperience with IE development. It needs a setting that it is safe for scripting. As soon as I added http://localhost to trusted sites and lowered the security level, I got a nice warning but the component was created and returned my data.

Posted by maartenb | 1 Comments

COM Server and PMIE again.

I'm still trying to create a COM out-of-process broker that I can call from Protected Mode IE. Amazing how rusty you get, it you don't do this daily. Here are some of my encounters.

I'm using Visual Studio 2008 with ATL 9.0 to create an ATL server. I add a Simple ATL component and register it (/regserver is the flag. Hope to remember it now.) I hunt for the COM server in DCOMCNFG and change the Identity of the server to run under an administrative user. If I don't specify a different user account, the COM server will be launched under the same credentials as the client. Since the goal is to create a broker that can do things that PMIE can't do, I need to change the account. (Whether I want to use a custom local account in a deployed scenario is different matter. I'd rather use the built-in service accounts so that I don't have to mess with passwords.)

Problem 1. ATL 9.0

Now I create a little vbs script to create the component and call a method on it. Works fine. Let me check the account that the COM server runs under. Aye. Nothing has changed. It is still launched with the client Identity that my little VB script runs under. What gives? It appears that ATL9.0 does not hook up my APPID to the CLSID of the component. So I can configure the identity of the COM server all day long, the CLSID for my component has no idea it has changed (found this with ProcMon of course). So I added the APPID entry under the CLSID of my component. Now it works. Or better, it doesn't. But that is expected. I get an Access Denied (800a0046) when I try to create the component from a standard user client. Reason is that COM gives the server a high MIC level and does not allow access by lower than high MIC clients (by default). That is all outlined here (or look for "CoCreateInstance and Integrity Levels" which will give you a document with a misnomer as title).

In that same doc, it is outlined how you can change the integrity level programmatically. So I set the MIC level to Medium with this SDDL: "O:BAG:BAD:(A;;0xb;;;IU)S:(ML;;NX;;;ME". And now I can create the component again from a standard user application (that runs with medium MIC). I still can't create it from a low MIC process such as PMIE. For that I need to change the ME in the SDDL to LW.

There was another observation.

Problem 2. DCOMCNFG and registry

This is actually a problem with how I called the program snippet from the MSDN documentation. When you change the Launch and Access permissions on the COM server, the security property page for my server in DCOMCNFG will change from "use default" to "customize" for Launch/Act and Access. Since I'm doing this on an x64 machine and my application is 32 bit, I am changing the values in wow6432 (HKEY_CLASSES_ROOT\Wow6432Node\AppID\{MyAppID}). DCOMCNFG gets its information from the HKCR\AppID\{MyAppid} so it doesn't pick up the customized values. If you change values back from "customize" to "use default", DCOMCNFG updates both HKCR\AppID as well as the WOW6432 (again as observed with ProcMon).

Still not there yet. The goal is to create an Out of Process COM component from PMIE. Maybe later. I hit another CreateObject error when I tried calling it from IE. Weird since a low MIC command line app worked fine.

Posted by maartenb | 1 Comments

Where is my COM Component?

I'm desperately trying to get a managed BHO to interop with my IE Broker. The Broker should be a Remoting server that runs and medium MIC level so that it can make changes that the managed BHO can't make because it is running in Protected Mode IE at low MIC level. At first I spent a good deal of time, trying to do this all in C#. This document describes how to lower MIC level on resources such as named pipes (remoting IPC protocol). Some of the Security APIs mentioned are not available in the managed world yet. And since my PInvoke skills are lacking, I was going for COM/Interop. I wrote a little ATL component, copied the code over and wanted to call it from my remoting server. Not so fast.

However hard I tried, the remoting server could not instantiate the COM component. I kept getting this:

Retrieving the COM class factory for component with CLSID {15D665F5-DFDE-4F73-B4EA-56C7C7318A36} failed due to the following error: 80040154.
Press any key to continue . . .

Could it be that the class was not registered? Looking up the ProgID, it was there. Might it be that quirky COM UAC thing? Uh-uh. Elevated, non-elevated, same thing. ProcMon to the rescue. Hmm! CLSID not found. Whaatt? Raw registry search for the CLSID. Ah! Wow6432.

When compiling my remoting server, it was compiled in mixed mode. This meant it was going for x64 on my x64 bit Vista. My COM component was still x86. So SCM was not looking for x86. After some fiddling around with the build settings, I was able to fix it.

Posted by maartenb | 0 Comments
More Posts Next page »
 
Page view tracker