COM kann nicht als prozessexternen .Net-Server gestartet werden, der als AnyCPU kompiliert wurde

8

Ich versuche, COM dazu zu bringen, meinen ausgehenden COM-Server zu starten. Es funktioniert, wenn der Serverprozess mit x64 kompiliert wird, aber wenn ich AnyCPU verwende (was ich will), dann hängt es für eine Weile und scheitert schließlich mit 0x80080005 (CO_E_SERVER_EXEC_FAILURE). Wie kann ich das zum Laufen bringen?

  • Ich laufe auf einem 64-Bit-Rechner: Windows 7 mit Visual Studio 2008 SP1.
  • Ich kann im Task-Manager sehen, dass mein Server gestartet wird. Also ich vermute das Problem liegt in der Kommunikation zwischen COM und dem Server (Klassenregistrierung).
  • Meine Test-Client-Anwendung ist in C # geschrieben, aber es spielt keine Rolle, ob sie für x86 oder x64 kompiliert wird. Das Problem tritt auch bei etwas auf, das in 32-Bit C ++ geschrieben wurde.
  • Wenn ich den Server mithilfe von x64 neu erstellen und ausführen und dann als AnyCPU neu erstellen, kann COM ihn starten. Ein Neustart bringt mich zur ursprünglichen Situation zurück. Vielleicht weiß COM nicht im Voraus, welche Bissigkeit verwendet wird, und eine vorherige Ausführung hilft.
  • Ich habe den Blogeintrag von Andy McMullen gefunden und versucht, CLSCTX_ACTIVATE_64_BIT_SERVER an CoCreateInstance () zu übergeben, aber das löst früher einen Fehler aus: 0x80040154 (REGDB_E_CLASSNOTREG). Mache ich bei meiner COM-Registrierung etwas falsch? Sie können unten sehen, dass es sehr einfach ist. Die Registrierung erfolgt bei der Ausführung in 64 Bit, und das Problem tritt auf, wenn der Client 64 Bit ist, also sollte Wow6432Node nicht beteiligt sein.

Ein anderer Junge hatte ein ähnliches Problem : a>, aber die MSFT-Antwort ist verwirrend. Er scheint vorzuschlagen, dass es nur über DCOM (siehe Link) oder COM + funktionieren kann. Ich vermute, dass entweder sehr viel Arbeit und wesentlich schlechter als die Verteilung meiner .exe, die als x64 und x86 gebaut wird, sein wird.

Sie fragen sich vielleicht, warum ich IPersistFile implementiere. Das liegt daran, dass mein Problem darin besteht, BindMoniker () von einem 32-Bit-C ++ - Programm zu meinem AnyCPU .NET-Programm zu bringen. Ich habe mein Problem auf das einfachere Beispiel reduziert, das hier vorgestellt wird.

Hier ist der Client-Code:

%Vor%

und hier ist der Server:

%Vor%     
Oliver Bock 16.02.2012, 00:29
quelle

2 Antworten

1

Versuchen Sie, die Registrierungsdienste -Klasse zu verwenden, um Ihre com-Assembly zu registrieren . Es wird auch die richtigen Registry-Pfade auswählen und einige andere Dinge tun.

Beispiel:

%Vor%

Ich denke auch, dass .NET-Client-Assemblies einige Probleme mit .NET-Servern haben, aber ich finde keine Ressource dafür ...

Hoffe, es wird helfen ...

    
Aykut Çevik 22.02.2012 16:06
quelle
1

Ich schätze, das Problem liegt in der Laufzeit. Ich habe einen COM-Server erstellt, der sich mit einer C ++ - Bibliothek registriert (Registrierung wird fehlerfrei durchgeführt). Ich habe Probleme beim Wechseln zu AnyCPU von .NET (CS).

Die Architektur:

  • C ++ - Bibliothek Schnittstelle COM (auf beiden x64 und x86-Plattformen gebaut)
  • .NET-Bibliothekswrapper (CS) (richtet die erforderliche x64 / x86-C ++ - Bibliothek korrekt ein)
  • .NET-Anwendung (CS) - COM-Client oder COM-Server

Hässliche Dinge passieren beim Registrieren der .NET-Anwendung, die als "AnyCPU" erstellt wurde. Sobald der COM-Client den COM-Server über DCOM aufruft, wird die Serveranwendung gestartet, aber der Client erhält den Fehler, dass der COM-Server nicht gestartet werden konnte.

Ich ging ein paar Schritte weiter, analysierte Registrierungsdaten mit Procmon und anderen Tools und kam zu dem gleichen Ergebnis:

  • x86 registriert die Klassen in CLASSES \ Wow6432Node
  • x64 und AnyCPU registrieren die Klassen in CLASSES (auf einem x64-Windows-Rechner, genau die gleichen Schlüssel; ich wette, dass x86 und AnyCPU dasselbe auf einer x86-Maschine registrieren würden)

Nun habe ich noch ein paar Experimente gemacht: Der x86 / x64 / AnyCPU COM Client kann sich ohne Probleme mit irgendeinem x86 / x64 COM Server verbinden, aber er kann sich sowieso nicht mit einem AnyCPU COM Server verbinden ...

Ich habe dann die folgenden Testfälle durchgeführt:

  1. Lassen Sie den x86-COM-Server registrieren, ersetzen Sie die ausführbare Datei mit dem AnyCPU-COM-Server: COM Client hat den x86-COM-Server gestartet, aber keine Kommunikation ... er hat den Server immer wieder gestartet ..
  2. Lassen Sie den x64 COM Server registrieren, ersetzen Sie die ausführbare Datei mit dem AnyCPU COM Server: COM Client startete den x64 COM Server, aber keine Kommunikation ... er startete den Server immer und immer wieder ..
  3. Lassen Sie den AnyCPU-COM-Server registrieren, ersetzen Sie die ausführbare Datei durch den x86-COM-Server: COM-Client konnte erfolgreich starten und eine Verbindung zum x86-COM-Server herstellen.
  4. Lassen Sie den AnyCPU-COM-Server registrieren, ersetzen Sie die ausführbare Datei durch den x64-COM-Server: COM-Client konnte erfolgreich starten und eine Verbindung zum x64-COM-Server herstellen.
  5. Lassen Sie den x86-COM-Server registrieren, ersetzen Sie die ausführbare Datei durch den x64-COM-Server: COM-Client konnte erfolgreich starten und eine Verbindung zum x64-COM-Server herstellen.
  6. Lassen Sie den x64-COM-Server registrieren, ersetzen Sie die ausführbare Datei mit dem x86-COM-Server: COM-Client konnte erfolgreich starten und eine Verbindung zum x86-COM-Server herstellen.

Wo zur Hölle ist das Kommunikationsproblem? Das ist sehr merkwürdig ... Keine der vorgestellten Lösungen (CLSCTX_ACTIVATE_64_BIT_SERVER, PreferredServerBitness oder corflags) hat geholfen.

Hat jemand anderes in dieser Angelegenheit Fortschritte gemacht? Sollten wir uns mit Microsoft in Verbindung setzen?

    
ro0ter 04.06.2013 10:33
quelle

Tags und Links