This project has moved. For the latest updates, please go here.

Starting a new PowerPoint.Application when PowerPoint is already running causes a CO_E_SERVER_EXEC_FAILURE exception

Oct 29, 2011 at 4:55 PM

Firstly let me thank you for building and publishing this library.  I needed to automate PowerPoint in a version independent way and was part way through crafting my own wrapper for late binding to PowerPoint when I found this project.

ok to this error.  Consider the following trivial app

LateBindingApi.Core.Factory.Initialize();
PowerPoint.Application application = new PowerPoint.Application();
application.Dispose()

if powerpoint (2007) is already running, the app will time out on the new PowerPoint.Application statement eventually raising a CO_E_SERVER_EXEC_FAILURE exception.

I tried a simple console app that uses the RunningObjectTable class from Examples/Misc as follows;

 

static void Main(string[] args)
{
    LateBindingApi.Core.Factory.Initialize();
    PowerPoint.Application application = null;
    object testProxy = RunningObjectTable.GetRunningPowerPointInstanceFromROT();
    if (null != testProxy)
    {
        application = new PowerPoint.Application(null, testProxy);

    }
    else
        application = new PowerPoint.Application();
    //...//
    if (null == testProxy)
        application.Quit();
    application.Dispose();
}

 

testProxy is always null, whether PowerPoint (2007) is loaded or not, and the next line of code that creates a new PowerPoint.Application raises the exception.

Coordinator
Oct 29, 2011 at 5:25 PM

hey khiron,

I do 2 tests on 2 virtual machines with xp and 2007

- open a powerpoint application
- runs powerpoint example01

this works fine on 2 systems, but the new Application statement don't create a new app, it allocates the already running app.
i'm not sure this is a powerpoint 'feature' or i do a mistake but its the same behavoir with the interop assemblies.
the second thing what i do is to GetRunningPowerPointInstanceFromROT and it works also fine on the virtual machines.

can i have some additional informations, windows version 32/64 Office 32/64 Student Edition or something like that, multiple versions of office installed and any what is helpful
to reproduce the error.

*Sebastian

( i see the misc examples contains faulty reference paths *damn* )

 

Oct 30, 2011 at 2:50 AM
Edited Oct 30, 2011 at 3:04 AM

I think I found my problem, or at least I reckon I can get my problem to show on your system.

Try running Visual Studio elevated (run as Administrator), with Powerpoint run normally.  Running VS non-elevated immediately fixed my symptoms.

I'm running Office 2007 Ultimate (only version installed), VS2010, on Windows 7 Ultimate (x64)

Nov 15, 2011 at 6:07 PM

I've run into a very similar issue both with Office 2010 and Office 2000 on Windows 7 professional and home. It seems to be related to the elevated permissions as khiron suggests. When I run as administrator new PowerPoint.Application(); just freezes, both when PowerPoint is already running and when it is not. If I run normally then I don't experience these issues, but my app needs elevated permissions. Any suggestions?

Coordinator
Nov 15, 2011 at 6:14 PM

i do a new test on a windows7 x64 VM immediately.
do you have 2000 and 2010 installed on one single machine?

 

Nov 15, 2011 at 6:18 PM

No, they are on different machines.

Coordinator
Nov 15, 2011 at 6:52 PM

test is in progress. i give you a response in 1 hour.

Coordinator
Nov 15, 2011 at 8:00 PM

i start all power point examples in a vm as administrator and it works wonderfull for me.
what i want to do is create a special diagnostic version of LateBindingApi.Core.dll to see what exactly is the problem.
which .net version do you use?

 

Nov 15, 2011 at 8:03 PM
Thanks for your help and quick investigation. We are using 2.0
On Tue, Nov 15, 2011 at 2:00 PM, SebastianDotNet <notifications@codeplex.com> wrote:

From: SebastianDotNet

i start all power point examples in a vm as administrator and it works wonderfull for me.
what i want to do is create a special diagnostic version of LateBindingApi.Core.dll to see what exactly is the problem.
which .net version do you use?

Read the full discussion online.

To add a post to this discussion, reply to this email (netoffice@discussions.codeplex.com)

To start a new discussion for this project, email netoffice@discussions.codeplex.com

You are receiving this email because you subscribed to this discussion on CodePlex. You can unsubscribe on CodePlex.com.

Please note: Images and attachments will be removed from emails. Any posts to this discussion will also be available online at CodePlex.com


Coordinator
Nov 16, 2011 at 12:55 AM

it's done. i have created a diagnostic version of the LateBinding core.
the dll is temporary available in the download section of NetOffice.
please download, replace and use the NetOffice Debug Console (available since NetOffice 1.3)
use the Debug Console as follows:

DebugConsole.LogFile = "C:\\myFile.log";
DebugConsole.Mode = ConsoleMode.LogFile;



an example for using the debug console is online available: http://netoffice.codeplex.com/wikipage?title=Misc01
copy the content of the file below your next post.
it's possible you create a normal interop assembly project to see the problem occurs here?
what NetOffice is do in the ctor is very simpel.

_instanceType = System.Type.GetTypeFromProgID(progId);
_underlyingObject = Activator.CreateInstance(_instanceType);

 

No dirty hacks, no tricky stuff, but one these method calls freeze your application.
i have the source code from .NET 2 installed on my pc and see tomorrow what does these methods.
maybe i can replace the problematic method. we find a solution for your problem, i'm sure!

 

 

Nov 16, 2011 at 10:37 AM

I don't think it's in your code Sebastien, I could be wrong but I suspect it's a flaw in the design of PowerPoint.  The PowerPoint instance is designed to be a singleton, only one of them on a PC handling all requests, but it can only be run with the rights of the logged in user and doesn't handle requests from other users.

I can replicate the problem with 

 

        static void Main(string[] args)
        {
            try
            {
                Activator.CreateInstance(Type.GetTypeFromProgID("Powerpoint.Application"));
            }
            catch(Exception ex)
            {
                Console.WriteLine(ex.Message);
                Console.ReadKey();
            }
        }

 

If my app is running elevated and PowerPoint is already loaded non-elevated then the call to CreateInstance will time out raising the following exception

Retrieving the COM class factory for component with CLSID {91493441-5A91-11CF-8700-00AA0060263B} failed due to the following error: 80080005.

Coordinator
Nov 16, 2011 at 2:44 PM

hey khiron,

nice to read you again. yes i think also, netoffice does no mistake here but anyway, lets find us a solution!
maybe i can create a alternate failback class,
1. take a look in the registry to see which file path has ppoint.exe, 1. create powerpoint process at hand, fetch the ROT with the proxy and returns.
but i wait for the response from cvchristensen currently.

*regards
Sebastian

Nov 16, 2011 at 4:13 PM
Thanks for all your quick work on this Sebastian. We'll load that new diagnostic Latebinding dll in today and see what happens.

On Wed, Nov 16, 2011 at 8:44 AM, SebastianDotNet <notifications@codeplex.com> wrote:

From: SebastianDotNet

hey khiron,

nice to read you again. yes i think also, netoffice does no mistake here but anyway, lets find us a solution!
maybe i can create a alternate failback class,
1. take a look in the registry to see which file path has ppoint.exe, 1. create powerpoint process at hand, fetch the ROT with the proxy and returns.
but i wait for the response from cvchristensen currently.

*regards
Sebastian

Read the full discussion online.

To add a post to this discussion, reply to this email (netoffice@discussions.codeplex.com)

To start a new discussion for this project, email netoffice@discussions.codeplex.com

You are receiving this email because you subscribed to this discussion on CodePlex. You can unsubscribe on CodePlex.com.

Please note: Images and attachments will be removed from emails. Any posts to this discussion will also be available online at CodePlex.com


Nov 16, 2011 at 10:21 PM

Sebastien, your approach would be much better than mine. 

What I ended up doing is during the call to create the COM class, if my process is running elevated, and PowerPoint is already loaded, I raise an exception immediately rather than making the user wait out the timeout period.  The message I uses is "Can not connect to an existing PowerPoint instance from an elevated state (eg: as Administrator).   Close down PowerPoint and try again, or run from a non-elevated state".

Coordinator
Nov 17, 2011 at 3:38 AM

i create a small sample application to start powerpoint in a different way.
please check the download section!

regards
*Sebastian

Nov 17, 2011 at 8:35 AM

I had to make a few changes to your application to get it to work, on my PC (Win7x64) the path in the registry to PowerPoint is different 

string keyPath = string.Format("Software\\Wow6432Node\\Microsoft\\Office\\{0}\\Common\\InstallRoot", item);

Also in ROTHelper I had to change from Milliseconds to TotalMilliseconds to get the timeout to work as expected 

        public static PowerPoint.Application GetRunningPowerPointInstancesFromROT(int delayMilliSeconds)
        {
            DateTime startTime = DateTime.Now;
            PowerPoint.Application application = GetApplicationInstancesFromROT(new string[] { "PowerPoint", "Microsoft PowerPoint" }, "Application");
            while((application == null) && (DateTime.Now.Subtract(startTime).TotalMilliseconds <= delayMilliSeconds))
                application = GetApplicationInstancesFromROT(new string[] { "PowerPoint", "Microsoft PowerPoint" }, "Application");
            return application;
        }

The result for me was if I ran this app elevated ( running it inside VS which is running "As Administrator") and if PowerPoint was already loaded then GetRunningPowerPointInstancesFromROT returns null (it times out).

The Problem seems to be that the Running Object Table is different depending on what user your are running as, Powerpoint is running on the ROT established by the non-elevated user, and this app is querying the ROT for Administrator waiting to see a running instance that never shows.

Interestingly the call to StartVersion does push the window of the running instance of PowerPoint to the front of the z-order - but unfortunately there seems no way to get a hold of the process from the elevated version of the ROT.

 

Coordinator
Nov 17, 2011 at 1:23 PM

i'm still a happy xp user but i test the next sample version in a window7 x64 VM.
uuups, sorry i create the sample, very quickly at night. i try to improve the sample today.

Coordinator
Nov 17, 2011 at 8:45 PM

an updated example version is available.
its a little bit more COM low level stuff inside but it works on my x64 W7 with office x64.
*regards
Sebastian

Nov 17, 2011 at 8:58 PM
Edited Nov 17, 2011 at 8:59 PM

Sebastian,

We tried to use the diagnostic latebinding dll that we downloaded but had some sort of version mismatch issue (1.3 vs 1.0?). We have, however, found that our app on client machines doesn't need the elevated permissions it does on our domain so it has become a non-issue. Thank you for all your work on this. We appreciate your responsiveness.

Coordinator
Nov 17, 2011 at 9:05 PM
Edited Nov 18, 2011 at 5:09 AM

version 1.3 is top of 1.0 i make sure existing code for previous NetOffice releases are compatible with newer versions.
Set specific version in 'references' to False. (right click on the reference) but nice to hear your problem is resolved!

update: now i realize, the other netoffice assemblies needs LateBindingApi.Core.dl in same version. my bad!

Nov 18, 2011 at 4:25 AM
Edited Nov 18, 2011 at 4:28 AM

I tried the updated project.  

PowerPoint.Application GetApplicationInstancesFromROT fails when called from an elevated application if PowerPoint has already been loaded from the desktop (loaded using my non-elevated credentials).  

It succeeds if run from a non-elevated state, and PowerPoint is already loaded from the desktop.

It succeeds when run from an elevated or non-elevated state if PowerPoint is not already loaded.

Interestingly, It succeeds if I previously load PowerPoint in an elevated state (by going to the install location and right clicking the PowerPoint.exe file and selecting to "Run as Administrator").

When it fails the GetApplicationInstancesFromROT method is able to get the ROT and iterate through it fine, but a process serving the PowerPoint interface just does not appear on the ROT.  It is as if an app invoked from one set of credentials does not appear in the ROT for any request invoked from a different set, it seems the two ROTs are quarantined from each other.

Hope this is useful for tracking this down.  I should note that I have worked around this by just not allowing someone to try to start PowerPoint if it's already started, which solves my problem.

Coordinator
Nov 19, 2011 at 8:32 AM

i can't reproduce these scarry effect in any virtual machine. the only problem here is the 2 seconds delay is not enough( vm's are slow of course)
can you do me a pleasure and add a log output to the GetApplicationInstancesFromROT method.
please log the enumerated interface guid's when powerpoint is running and the method can't find them.

Nov 20, 2011 at 2:29 AM

I logged every GUID that GetApplicationInstancesFromROT found as follows

Guid typeGuid = GetDispatchID(dispatch);
if (Guid.Empty != typeGuid)
{
    sw.Write(String.Format("GUID:{0} ", typeGuid));
    if ((typeGuid == _powerPointDispatchID32) || (typeGuid == _powerPointDispatchID64))
        isPowerPoint = true;
}
The complete logs are too big to post as the time out enabled routine cycles through many times failing to find the PowerPoint GUIDs

The result when VS is run as Admin (app is elevated) and Powerpoint is already loaded from the desktop (non elevated) is 

GUID:04a72314-32e9-48e2-9b87-a63603454f3e 
GUID:cda7305c-78b6-4d9d-90ad-93ebe71f9341 
GUID:04a72314-32e9-48e2-9b87-a63603454f3e 
GUID:cda7305c-78b6-4d9d-90ad-93ebe71f9341 
the above repeated over and over until the 2sec time out is reached

The result when VS is loaded elevated and PowerPoint is not already loaded (so the app can load it elevated) is 
GUID:04a72314-32e9-48e2-9b87-a63603454f3e 
GUID:cda7305c-78b6-4d9d-90ad-93ebe71f9341 
GUID:04a72314-32e9-48e2-9b87-a63603454f3e 
GUID:cda7305c-78b6-4d9d-90ad-93ebe71f9341 
x 29 times and then the powerpoint interface shows up 
GUID:04a72314-32e9-48e2-9b87-a63603454f3e 
GUID:91493442-5a91-11cf-8700-00aa0060263b

When I run VS non-elevated and Powerpoint is already loaded non-elevated the entire log file is 
 ---Start Logging 20/11/2011 2:26:51 PM
 --GetRunningPowerPointInstancesFromROT
GUID:91493442-5a91-11cf-8700-00aa0060263b 
 ---Stop Logging 20/11/2011 2:26:51 PM
So it's pretty much the first interface found in the non time out version of GetRunningPowerPointInstancesFromROT


Nov 19, 2012 at 8:33 AM

Hi,

Did any of you find a solution to this? How to attach to a running PowerPoint instance if your process in running elevated and the PowerPoint process is not?

Regards,
Erik