none
Error C2338 bei Übersetzung mit Compileroption /J RRS feed

  • Frage

  • Hallo zusammen!

    Habe eine MFC-Anwendung die aus historischen Gründen bisher mit der Compileroption /J (_CHAR_UNSIGNED) übersetzt wurde. Beim Versuch auf Visual Studio 2010 zu migrieren kommt es jetzt leider zu der Fehlermeldung:

    • error C2338: CVarTypeInfo< char > cannot be compiled with /J or _CHAR_UNSIGNED flag enabled c:\program files (x86)\microsoft visual studio 10.0\vc\atlmfc\include\atlcomcli.h 

    Anscheinend verträgt sich die Option /J nicht mit dem Header atlcomcli.h. Eigentlich ist in den Projektoptionen eingestellt, dass kein ATL benutzt wird. Deshalb frage ich mich wieso der Header atlcomcli.h überhaupt eingebunden wird.

    Gibt es eine Möglichkeit das Einbinden des Headers atlcomcli.h zu vermeiden wenn ATL sowieso nicht benutzt wird?

    Gruss Speedy.

    Dienstag, 15. Juni 2010 09:00

Antworten

Alle Antworten

  • Hallo Speedy!

    Anscheinend verträgt sich die Option /J nicht mit dem Header atlcomcli.h. Eigentlich ist in den Projektoptionen eingestellt, dass kein ATL benutzt wird. Deshalb frage ich mich wieso der Header atlcomcli.h überhaupt eingebunden wird.

    Irgendjemand wird sie ja verwenden, sonst würde sie nicht geleaden werden...

    Suche entweder mal nach dem String (vermutlich wird sie aber nur indirekt eingebunde).

    Das einfachst ist: Du aktivierst die Compiler-Option "/P" für Dein
    Projekt (musst Du unter "C/C++ | Command Line | Advanced options" eintragen!).

    Dann wird für jede C/C++ Datei eine entsprechende "*.i" Datei erzeugt, die alle include dateien in der entstsprechende Reihenfolge enthält... dort findest Du dann auf jeden Fall den "atlcomcli.h" und dann musst Du dich halt nach oben arbeiten, wo es eingebunden wird...

    PS: Wenn Du "/P" aktiviert hast, tritt ein Linker Fehler auf, da in diesem Fall keine obj-Dateien erzeugt werden... Du musst dann das "/P" wieder entfernen, wenn Du das Problem gefunden hast!


    Jochen Kalmbach (MVP VC++)
    Dienstag, 15. Juni 2010 09:15
  • @Jochen:
    Wenn das eine MFC Anwednung ist kann er nicht verhindern, dass dieser
    Header benutzt wird.
     
    @Speedy G.:
    Du wirst wohl den Code umbauen müssen, sofern Du nicht auf die ATL
    Header verzichten kannst.
     
    Oder isoliere den alten Code in eine einzige CPP/C Datei, die Du so
    übersetzt ohne MFC und alles andere...
     
     

    Martin Richter -- MVP for VC++ [Germany] -- http://blog.m-ri.de
    • Als Antwort markiert Speedy G. _ Donnerstag, 17. Juni 2010 14:34
    Dienstag, 15. Juni 2010 09:42
    Moderator
  • @Jochen:

    Unter "Konfigurationseigenschaften-->C/C++-->Erweitert-->Includes anzeigen" kann man sich übrigens eine übersichtliche Liste der eingebundenen Header erzeugen, was bei mir zu folgendem Resultat (maßgebliche Zeilen extrahiert) führt:

    1> Hinweis: Einlesen der Datei: c:\ipc\nt\source\exe\stdafx.h
    1> Hinweis: Einlesen der Datei:  C:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\atlmfc\include\afxwin.h
    1> Hinweis: Einlesen der Datei:  C:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\atlmfc\include\afx.h
    1> Hinweis: Einlesen der Datei:   C:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\atlmfc\include\afxstr.h
    1> Hinweis: Einlesen der Datei:   C:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\atlmfc\include\cstringt.h
    1> Hinweis: Einlesen der Datei:    C:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\atlmfc\include\atlsimpstr.h
    1> Hinweis: Einlesen der Datei:    C:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\atlmfc\include\atlmem.h
    1> Hinweis: Einlesen der Datei:     C:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\atlmfc\include\atlcommem.h
    1> Hinweis: Einlesen der Datei:     C:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\atlmfc\include\atlcomcli.h
    
    @Martin:
    Du wirst wohl den Code umbauen müssen, sofern Du nicht auf die ATL
    Header verzichten kannst.
    Auf die ATL kann mein Code wegen mir problemlos verzichten. Unter "Konfigurationseigenschaften-->Allgemein-->Verwendung von ATL" habe ich deshalb schon eingetragen "ATL wird nicht verwendet". Allein dieser Eintrag nützt nichts. Gibt es eine andere/zusätzliche Möglichkeit das Einbinden des ATL-Headers  "atlcomcli.h" zu verhindern, trotz MFC-Anwendung?
     
    Oder isoliere den alten Code in eine einzige CPP/C Datei, die Du so
    übersetzt ohne MFC und alles andere...

    Das mit dem zusammenfassen sagt sich so leicht. Das ganze ist ein Projekt mit ca. 20 Teilprojekten und insgesamt über 2000 Dateien. Das wäre ein Riesenaufwand. Genau wie das übersetzen ohne die Option /J und entsprechendes Anpassen der ganzen Stellen im Code (ca. 3500). Also wäre ich äußerst dankbar wenn es eine andere Möglichkeit gäbe?

    Gruß Speedy

    Dienstag, 15. Juni 2010 12:16
  • Auf die ATL kann mein Code wegen mir problemlos verzichten. Unter "Konfigurationseigenschaften-->Allgemein-->Verwendung von ATL" habe ich deshalb schon eingetragen "ATL wird nicht verwendet". Allein dieser Eintrag nützt nichts. Gibt es eine andere/zusätzliche Möglichkeit das Einbinden des ATL-Headers  "atlcomcli.h" zu verhindern, trotz MFC-Anwendung?

    Nein! Denn die MFC kann seit VC-2003 nicht mehr auf die ATL verzichten!
    Seit VC-2003 (oder war es 2002?) sind MFC und ATL eine enge Hochzeit eingegangen...

    Du hast einen Konflikt, der sich so nicht beheben lässt!

    Das mit dem zusammenfassen sagt sich so leicht. Das ganze ist ein Projekt mit ca. 20 Teilprojekten und insgesamt über 2000 Dateien. Das wäre ein Riesenaufwand. Genau wie das übersetzen ohne die Option /J und entsprechendes Anpassen der ganzen Stellen im Code (ca. 3500). Also wäre ich äußerst dankbar wenn es eine andere Möglichkeit gäbe?

    Ich kenne keine andere Lösung! Sorry!
    Wende Dich an den MS-Support aber der wird Dir auch sagen: Löse Dein Code-Problem...

    /J zu verwenden ist schon extrem. Das wurde mit Sicherheit gemacht um Probleme auf die Schnelle zu fixen, das rächt sich nun. Es verursacht eben andere Probleme. Der richtige Weg wäre es gewesen typensicher zu arbeiten.

    Erkläre mir noch mal wo jetzt das Problem liegt?
    Was ist passiert wenn man ohne /J übersetzt. Warnungen kann man zur Not ignorieren ;)



    Martin Richter -- MVP for VC++ [Germany] -- http://blog.m-ri.de
    Dienstag, 15. Juni 2010 13:11
    Moderator
  • Seit VC-2003 (oder war es 2002?) sind MFC und ATL eine enge Hochzeit eingegangen... Du hast einen Konflikt, der sich so nicht beheben lässt!
    Aber wieso funktioniert das ganze dann unter Visual Studio 2008? Dort wird der Header atlcomcli.h auch eingebunden, verursacht aber keine Probleme? Hat Microsoft da jetzt was umgestellt?
    /J zu verwenden ist schon extrem. Das wurde mit Sicherheit gemacht um Probleme auf die Schnelle zu fixen, das rächt sich nun. Es verursacht eben andere Probleme. Der richtige Weg wäre es gewesen typensicher zu arbeiten.
    Na ja ganz so ist das nicht. Das ganze rührt noch her aus der Zeit des guten alten C6-Compilers. Und das ist alles schon sauber sprich typsicher programmiert, aber eben für unsigned Standardtypen (was bis jetzt ja auch problemlos umstellbar war).
    Was ist passiert wenn man ohne /J übersetzt. Warnungen kann man zur Not ignorieren ;)
    Das mit dem ignorieren der Warnung hab ich auch schon überlegt. Aber wohl ist mir dabei nicht.
    Gruss Speedy
    Dienstag, 15. Juni 2010 13:43
    • Als Antwort markiert Speedy G. _ Donnerstag, 17. Juni 2010 14:35
    Dienstag, 15. Juni 2010 14:44
    Moderator

  • Na ja ganz so ist das nicht. Das ganze rührt noch her aus der Zeit des guten alten C6-Compilers. Und das ist alles schon sauber sprich typsicher programmiert, aber eben für unsigned Standardtypen (was bis jetzt ja auch problemlos umstellbar war)..

    Typsicher wäre es gewesen selbst unsigned char (also BYTE) zu benutzen oder signed char, wenn Du das brauchst.

    Was ist passiert wenn man ohne /J übersetzt. Warnungen kann man zur Not ignorieren ;)
    Das mit dem ignorieren der Warnung hab ich auch schon überlegt. Aber wohl ist mir dabei nicht.

    Problematisch wird es nur, wenn Du Artithmetik betreibst oder fliegend char nach int umlädst, bzw. die Typen wechselst....



    Martin Richter -- MVP for VC++ [Germany] -- http://blog.m-ri.de
    Dienstag, 15. Juni 2010 18:41
    Moderator
  • Hallo Martin,

    Gott sei Dank hat sich das Problem bei genauerer Untersuchung entschärft. Die Projekte (C++/MFC/ATL) die bei der Option /J Probleme machten konnte ich tatsächlich auch ohne /J übersetzen und das ohne die Warnungen (C4057) zu erhalten. Übrig blieben einige C-Projekte die ich weiterhin mit /J übersetzen muss was aber kein Problem ist weil die ja keine MFC/ATL benutzen.

    Es bleibt noch die Frage ob es ein Problem ist diese mit /J übersetzten statischen C-Bibliotheken (.lib) in die MFC-Applikation (.exe) einzubinden die ansonsten jetzt komplett einschließlich aller sonstigen statischen C++-Bibliotheken (.lib) ohne die Option /J übersetzt wurde? Ich denke nicht oder?

    Gruss Wolfgang

    Donnerstag, 17. Juni 2010 13:27
  • Es bleibt noch die Frage ob es ein Problem ist diese mit /J übersetzten statischen C-Bibliotheken (.lib) in die MFC-Applikation (.exe) einzubinden die ansonsten jetzt komplett einschließlich aller sonstigen statischen C++-Bibliotheken (.lib) ohne die Option /J übersetzt wurde? Ich denke nicht oder?

    Nein! Mit Sicherheit nicht. Der Code ist ja bereits erzeugt. D.h. wie ein char intern interpretiert wird steckt in der .LIB.

    Die muss nur klar sein, dass wenn Du ein char übergibst dieses eine Signextension erfährt, wenn es an eine Funktion dieser LIB übergeben wird. Denn die Behandlung eines char wird ja immer in der entsprechenden Compilation Unit geregelt.


    Martin Richter -- MVP for VC++ [Germany] -- http://blog.m-ri.de
    Donnerstag, 17. Juni 2010 13:42
    Moderator
  • Hallo Martin,

    Die Schnittstelle benutzt gar keine char-Parameter, dort wird immer explizit unsigned char benutzt.

    Vielen Dank für die Hilfe.

    Gruß Wolfgang

    Donnerstag, 17. Juni 2010 14:34
  • Hallo,

    wenn kein COM in der Anwendung verwendet wird, kann man die Zeilen im MFC header auskommentieren:

    //#ifdef _CHAR_UNSIGNED
    // ATLSTATIC_ASSERT(false, "CVarTypeInfo< char > cannot be compiled with /J or _CHAR_UNSIGNED flag enabled");
    //#endif

    oder man definiert für das entsprechende Modul eine Präprozessor Konstante, auf die in atlcomcli.h Bezug genommen wird.

    Martin

    Dienstag, 5. März 2013 12:22