{"id":77,"date":"2007-06-02T20:30:45","date_gmt":"2007-06-02T18:30:45","guid":{"rendered":"http:\/\/blog.m-ri.de\/index.php\/2007\/06\/02\/wie-findet-die-mfc-80-eigentlich-die-mfc80llldll-dateien\/"},"modified":"2007-06-02T20:39:40","modified_gmt":"2007-06-02T18:39:40","slug":"wie-findet-die-mfc-80-eigentlich-die-mfc80llldll-dateien","status":"publish","type":"post","link":"http:\/\/blog.m-ri.de\/index.php\/2007\/06\/02\/wie-findet-die-mfc-80-eigentlich-die-mfc80llldll-dateien\/","title":{"rendered":"Wie findet die MFC 8.0 eigentlich die MFC80lll.DLL Dateien?"},"content":{"rendered":"<p>Es ist vielleicht schon machen aufgefallen, dass auch die sprachabh\u00e4ngigen Ressourcen-Dateien der MFC als Side by Side Assemblies installiert werden durch <em>VCREDIST_X86.EXE<\/em>.<br \/>\nSchaut man sich an wie ein Programm erzeugt wird, dass die MFC80.DLL\/MFC80U.DLL verwendet, dann wei\u00df man wie Manifeste aussehen die f\u00fcr das entsprechende Programm erzeugt werden. Wir finden im Allgemeinen drei Dependency-Eintr\u00e4ge f\u00fcr die MFC, die CRT und die ComCtl32 DLL.<\/p>\n<p>Erstaunlicherweise wird kein Eintrag f\u00fcr die Sprachdateien erzeugt und scheinbar auch nicht ben\u00f6tigt. Denn wenn man das Programm im Debugger auf einem Deutschen XP oder Vista\u00a0startet sieht man in der Debug-Ausgabe, dass die entsprechende Datei <em>MFC80DEU.DLL <\/em>aus dem Side by Side Storage geladen wird.<\/p>\n<p>Ein Blick in die <em>MFC80(U).DLL <\/em>zeigt auch ein Manifest. Dieses passt genau auf die Sprachdateien. Allerdings ist dieses Manifest nicht aktiv, denn es hat keine <em>&#8222;g\u00fcltige&#8220;<\/em> ID (1000), die\u00a0das Betriebsystem veranlassen w\u00fcrde es zu ber\u00fccksichtigen. Zudem h\u00e4tte dieses Manifest auch nur einen Effekt, wenn die Sprach-DLLs implitzit geladen w\u00fcrden.<br \/>\nDiese Dateien werden aber explizit geladen. Der Code der daf\u00fcr verantwortlich ist wird zuallererst in der <em>DllMain <\/em>und der Initialisierung der MFC80-DLL und ein zweites mal in <em>CWinApp::InitInstance<\/em> aufgerufen.<\/p>\n<p>Der entsprechende Code dort, l\u00e4dt das Manifest aus der DLL, erzeugt einen Aktivierungs-Kontext und f\u00fchrt dann den entsprechenden <em>AfxLoadLibrary<\/em> Aufruf durch. Anschlie\u00dfend wird der Kontext wieder zerst\u00f6rt. Wird die Sprach-DLL nicht gefunden wird ein zweites Mal versucht die Datei nun aus dem Programmverzeichnis bzw. \u00fcber die normalen Suchpfade zu laden.<\/p>\n<p>Diese Methode \u00fcber das eingebaute Manifest l\u00e4sst sich nicht aushebeln. Verwendet man selbst eine Technik, die die MFC-DLLs als private Assemblies l\u00e4dt, dann versucht die MFC dennoch die Sprach-DLLs Side by Side zu laden. Das Ganze ist etwas \u00e4rgerlich, wenn man private Assemblies <em>pur <\/em>verwenden m\u00f6chte. Einziger Trick w\u00e4re hier <em>CWinApp::LoadAppLangResourceDLL <\/em>zu \u00fcberschreiben, aber das verhindert nicht den ersten Aufruf aus der <em>DllMain <\/em>der MFC-DLL heraus.<\/p>\n<p>\u2757 Wer sich das Ganze genauer ansehen will, sollte sich die Datei <em>appcore.cpp<\/em> mal ansehen.<br \/>\nEntscheidend hier sind die Funktionen: <em>CWinApp::LoadAppLangResourceDLL <\/em>und <em>AfxLoadLangResourceDLLEx<\/em>.<\/p>\n<p>\u2757 Schaut man sich die MFC-DLLs \u00fcbrigends noch genauer an, dann stellt man fest, dass sie gar keine Manifeste enthalten. Und das ist auch gut so, sonst w\u00e4re es ja auch nicht m\u00f6glich die MFC und die zugeh\u00f6rige CRT als Private Assembly zu laden. Die MFC verwendet also immer die CRT, die im Kontext der EXE geladen wird.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Es ist vielleicht schon machen aufgefallen, dass auch die sprachabh\u00e4ngigen Ressourcen-Dateien der MFC als Side by Side Assemblies installiert werden durch VCREDIST_X86.EXE. Schaut man sich an wie ein Programm erzeugt wird, dass die MFC80.DLL\/MFC80U.DLL verwendet, dann wei\u00df man wie Manifeste aussehen die f\u00fcr das entsprechende Programm erzeugt werden. Wir finden im Allgemeinen drei Dependency-Eintr\u00e4ge f\u00fcr &hellip; <a href=\"http:\/\/blog.m-ri.de\/index.php\/2007\/06\/02\/wie-findet-die-mfc-80-eigentlich-die-mfc80llldll-dateien\/\" class=\"more-link\"><span class=\"screen-reader-text\">\u201eWie findet die MFC 8.0 eigentlich die MFC80lll.DLL Dateien?\u201c <\/span>weiterlesen<\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_jetpack_memberships_contains_paid_content":false,"footnotes":""},"categories":[4,3],"tags":[370,352,36],"class_list":["post-77","post","type-post","status-publish","format-standard","hentry","category-mfc","category-programmieren","tag-c","tag-mfc","tag-vs-2005"],"jetpack_featured_media_url":"","jetpack_sharing_enabled":true,"_links":{"self":[{"href":"http:\/\/blog.m-ri.de\/index.php\/wp-json\/wp\/v2\/posts\/77","targetHints":{"allow":["GET"]}}],"collection":[{"href":"http:\/\/blog.m-ri.de\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"http:\/\/blog.m-ri.de\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"http:\/\/blog.m-ri.de\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"http:\/\/blog.m-ri.de\/index.php\/wp-json\/wp\/v2\/comments?post=77"}],"version-history":[{"count":0,"href":"http:\/\/blog.m-ri.de\/index.php\/wp-json\/wp\/v2\/posts\/77\/revisions"}],"wp:attachment":[{"href":"http:\/\/blog.m-ri.de\/index.php\/wp-json\/wp\/v2\/media?parent=77"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"http:\/\/blog.m-ri.de\/index.php\/wp-json\/wp\/v2\/categories?post=77"},{"taxonomy":"post_tag","embeddable":true,"href":"http:\/\/blog.m-ri.de\/index.php\/wp-json\/wp\/v2\/tags?post=77"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}