Datengröße für std::exception ändern



  • Hallo,

    gibt's irgendwo einen Schalter, mit dem man einstellen kann, wie viel
    Text man einer Exception mitgeben kann?

    irgendwie ist da nach 255 Zeichen Feierabend 😞

    Bsp:

    char myMessage[] = "ein schöner langer Text länger als 255 Zeichen... ";
    throw (std::runtime_error(myMessage));
    
    ...
    
    catch(std::exception & Ex)
    {
    // hier kommen von nur ca. 255 Zeichen an
    // (habs ned genau gezählt aber ich vermute mal wegen \0 nicht 256)
    std::cout<<Ex.what()<<std::endl;
    }
    

    Wäre schön, wenns da eine Möglichkeit gäbe,
    weil ich erst vor kurzem von eigenen Exception-Objekten
    auf std::exception umgestellt hab.
    (Wär dann ziemlich für die Katz gewesen ...)

    Danke
    Martin

    PS:
    Warum so ein langer Text?
    Ist für eine Datenbankanbindung,
    soll Anfrage + Datenbankfehlermeldung ausspucken.

    Da kommen schon mal mehr als 255 Zeichen dabei raus.



  • Welchen Compiler benutzt du denn? Bei Visual C++ 2003 geht mehr. (ich denke unbegrenzt) Habs mit 385 ausprobiert.
    Guck doch mal in die Header-Datei exception, da müsste das doch implementiert sein.



  • Da std::exception::what() virtual ist, kannst du doch diese ganz einfach überschreiben.

    Machste sowas hier:

    class sql_exception : public std::exception {
    public:
      	sql_exception(){
            }
    	sql_exception(const char *msg) {
                my_what = msg;
            }
            sql_exception(const std::string &msg) {
               my_what = msg;
            }
    
            virtual const char *what() const {
                return my_what.c_str();
            }
    private:
       std::string my_what;
    };
    

    Jetzt kannste unendlich lange Texte raushauen. Am besten du machst aber eine allgemeinere exception, die du für alle deine Exceptions benutzen kannst, die hier ist jetzt natürlich speziell für dein eines Problem.



  • Achja, da zeigt sich mal wieder das Problem, wenn man auf std::string verzichtet, weil es _angeblich_ mit Kanonen auf Spatzen geschossen ist. Es rächt sich irgendwann!!! Genauso wie wenn einige hier anstatt vector noch auf normale Arrays schwören.



  • also ich seh gerade unter visual c++ arbeitet std::runtime_error mit std::string:

    http://www.rafb.net/paste/results/xviWBQ22.html



  • Artchi schrieb:

    Achja, da zeigt sich mal wieder das Problem, wenn man auf std::string verzichtet, weil es _angeblich_ mit Kanonen auf Spatzen geschossen ist. Es rächt sich irgendwann!!! Genauso wie wenn einige hier anstatt vector noch auf normale Arrays schwören.

    das problem ist einfach, dass std::string selber durch new eine exception schmeissen kann, und wenn das passiert während grad eine exception geworfen wird, macht dein gesamtes programm einen abgang.

    von daher würd ich bei kritischen ausnahmen einen char buffer[256] favorisieren.



  • @denker: sehr klug: "Posts expire after 24 hours. " 🙄

    packs doch hier ins forum:

    class runtime_error
    	: public _XSTD exception
    	{	// base of all runtime-error exceptions
    public:
    	explicit runtime_error(const string& _Message)
    		: _Str(_Message)
    		{	// construct from message string
    		}
    
    	virtual ~runtime_error()
    		{}	// destroy the object
    
    	virtual const char *what() const _THROW0()
    		{	// return pointer to message string
    		return (_Str.c_str());
    		}
    
     #if !_HAS_EXCEPTIONS
    protected:
    	virtual void _Doraise() const
    		{	// perform class-specific exception handling
    		_RAISE(*this);
    		}
     #endif /* _HAS_EXCEPTIONS */
    
    private:
    	string _Str;	// the stored message string
    	};
    


  • denker schrieb:

    Welchen Compiler benutzt du denn?

    Hab hier den Borland Compiler 5.6.4 (der beim C++Builder X Personal dabei ist).

    @Artchi:
    Ableiten funktioniert wunderbestens unter obigem Compiler.

    Allerdings spuckt mir der gcc einen haufen Fehler aus,
    mit denen ich ned wirklich viel anfangen kann...

    "mqlException.hpp": files/include/mql/mqlException.hpp looser throw specifier for `virtual in Zeile 10
    MQL::EXCEPTION::~EXCEPTION()'
    "exception": C:/Programme/compInt/cbx/mingw/include/c++/3.2/exception overriding ` in Zeile 54
    virtual std::exception::~exception() throw ()'
    "mqlException.hpp": files/include/mql/mqlException.hpp looser throw specifier for `virtual in Zeile 12
    const char* MQL::EXCEPTION::what() const'
    "exception": C:/Programme/compInt/cbx/mingw/include/c++/3.2/exception overriding ` in Zeile 57
    virtual const char* std::exception::what() const throw ()'
     MinGW GNU C++ Compiler beendet mit Fehler-Code: 1
    Erzeugen wegen Fehler abgebrochen
    

    Der Code dazu:
    mql.hpp

    class MQL
    {
    public:
    #include "mqlException.hpp"
    ...
    };
    

    mqlException.hpp

    #ifndef GUARD_MQL_EXCEPTION
    #define GUARD_MQL_EXCEPTION
    
    #include <stdexcept>
    
    class EXCEPTION : public std::exception
    {
    public:
    	EXCEPTION(const STRING & What = "");
    	[virtual] ~EXCEPTION();   // egal, ob mit oder ohne virtual
    
    	[virtual] const char * what()const; //siehe Destruktor
    
    private:
    	STRING m_what;
    };
    #endif
    


  • Der Compiler sagt es dir doch bereits, dir fehlt throw() hinter der Funktion:

    virtual const char* what() const throw() {
       //irgendwas
    }
    

    entsprechend auch beim CTor und DTor.

    mfg
    v R



  • So sieht std::exception vom Borland C++ Compiler aus:

    class _STLP_CLASS_DECLSPEC __Named_exception : public _STLP_EXCEPTION_BASE {
    public:
      __Named_exception(const string& __str) 
    # ifdef _STLP_OWN_IOSTREAMS
        ;
      const char* what() const _STLP_NOTHROW_INHERENTLY;
      ~__Named_exception() _STLP_NOTHROW_INHERENTLY;
    # else
      {
        strncpy(_M_name, __get_c_string(__str), _S_bufsize);
        _M_name[_S_bufsize - 1] = '\0';
      }
      const char* what() const _STLP_NOTHROW_INHERENTLY { return _M_name; }
    # endif
    
    private:
      enum { _S_bufsize = 256 };
      char _M_name[_S_bufsize];
    };
    


  • Ja, GCC und mein VC++ haben verschiedene STD-Lib-Implementierungen. Bei mir war kein throw. Mußt du dann natürlich bei dir anpassen.

    Ich find übrigens deinen Code mit den Eckigen Klammern um virtual herum und wie du includierst seeeeeeehr merkwürdig. 😕



  • virtuell Realisticer schrieb:

    Der Compiler sagt es dir doch bereits, dir fehlt throw() hinter der Funktion:

    virtual const char* what() const throw() {
       //irgendwas
    }
    

    entsprechend auch beim CTor und DTor.

    mfg
    v R

    hm,
    sowas seh ich grade zum allerersten mal.
    Hab zwar keinen Plan, für was das "throw()" gut ist/sein soll, aber funktionieren tuts.

    Artchi schrieb:

    Ich find übrigens deinen Code mit den Eckigen Klammern um virtual herum und wie du includierst seeeeeeehr merkwürdig. 😕

    eckiges virtual
    Das sollte andeuten, dass der Fehler sowohl mit "virtual" auftaucht,
    also auch ohne.

    Includes:
    Hab hier mehrere Klassen ineinander geschachtelt.
    Wird dann relativ unübersichtlich, drum hab ich's in mehrere
    Dateien zerlegt

    Dann noch ein herzlichen Dankeschön an alle für die Hilfe.



  • anonymus schrieb:

    Hab zwar keinen Plan, für was das "throw()" gut ist/sein soll, aber funktionieren tuts.

    throw () bedeutet, dass diese Funktion keine Exceptions wirft/werfen darf und gehört AFAIK zur Signatur.


Anmelden zum Antworten