Compilerabhängiger Fehler bei :: CHttpConnection



  • Code:

    //(CHttpConnection.cpp)

    #define CBTR // Definieren, für Trace-Ausgaben
    #ifdef CBTR
    #include <iostream>
    #define CBTRACELN(s) std::cout << (s) << endl;
    #define CBTRACE(s) std::cout << (s);
    #else
    #define CBTRACELN(s)
    #define CBTRACE(s)
    #endif

    #include "CHttpConnection.h"
    #include "CFile.h"
    #include "CMemory.h"

    #include <vector>

    using namespace std;

    namespace Codebook {

    CHttpConnection::CHttpConnection()
    : m_iconn(0)
    { }

    bool CHttpConnection::connect(const std::string &host, unsigned int port) {
    CBTRACELN("CHttpConnection::connect: Verbindung wird aufgebaut");
    /*
    ** Eventuell bestehende Verbindung abbrechen
    /
    disconnect();
    /

    ** Internet-Verbindung mit entsprechender
    ** Adresse und Port herstellen
    /
    m_iconn=new CInternetConnection(host,port);
    if(m_iconn->isAvailable()) {
    CBTRACELN("Erfolg!");
    return(true);
    }
    /

    ** Verbindungsaufbau fehlgeschlagen?
    ** => CInternetConnection-Objekt löschen
    */
    else {
    m_lastError="Verbindungaufbau fehlgeschlagen!";
    CBTRACELN("Verbindungaufbau fehlgeschlagen!");
    delete(m_iconn);
    m_iconn=0;
    return(false);
    }
    }

    bool CHttpConnection::connect(const CUrl &url) {
    /*
    ** Host und Port aus CUrl holen
    */
    string host=url.getDomain();
    string sport=url.getPort();
    unsigned int port;

    if(sport=="")
    port=80;
    else
    port=atol(sport.c_str());
    /*
    ** connect für Host und Port aufrufen
    */
    return(connect(host,port));
    }

    void CHttpConnection::disconnect() {
    if(m_iconn) {
    delete(m_iconn);
    m_iconn=0;
    }
    }

    //***************************************************************
    // sendRequest
    //***************************************************************

    bool CHttpConnection::sendRequest(const CHttpRequest &request) {
    CBTRACELN("\nsendRequest\n-----------------------------------------------------");
    /*
    ** Request senden
    /
    string sreq=request.getRequest();
    CBTRACE(sreq);
    unsigned int sent=m_iconn->sendLine(sreq);
    /

    ** Sind weniger Zeichen gesendet worden als
    ** der Request lang ist?
    ** => Fehler!
    */
    if(sent<sreq.size()) {
    m_lastError="sendRequest fehlgeschlagen!";
    CBTRACELN("sendRequest fehlgeschlagen!");
    return(false);
    }
    else {
    CBTRACELN("Erfolg!");
    return(true);
    }
    }

    //***************************************************************
    // receiveResponse
    //***************************************************************

    bool CHttpConnection::receiveResponse(vector<string> &response) {
    CBTRACELN("\nreceiveResponse\n-----------------------------------------------------");
    string line;
    /*
    ** Server-Response zeilenweise einlesen
    */
    while((line=m_iconn->receiveLine())!="") {
    CBTRACELN("Empfangen: "+line);
    response.push_back(line);
    }
    if(response.size()==0)
    return(false);
    else
    return(true);
    }

    //***************************************************************
    // getHeadHeader
    //***************************************************************

    bool CHttpConnection::getHeadHeader(const CUrl &url, vector<string> &header) {
    CBTRACELN("\ngetHeadHeader\n-----------------------------------------------------");
    /*
    ** Head-Request formulieren
    /
    CHttpRequest request;
    request.setFromUrl(url);
    request.setRequestType(CHttpRequest::rtHEAD);
    request.setUserAgent(CHttpRequest::UAExplorer6);
    /

    ** Verbindung aufbauen
    /
    if(!connect(url)) {
    m_lastError="Fehler bei connect";
    CBTRACELN("Fehler bei connect");
    return(false);
    }
    /

    ** Request senden
    /
    if(!sendRequest(request)) {
    m_lastError="Fehler bei sendRequest";
    CBTRACELN("Fehler bei sendRequest");
    return(false);
    }
    /

    ** Antwort empfangen
    */
    if(!receiveResponse(header)) {
    m_lastError="Fehler bei receiveResponse";
    CBTRACELN("Fehler bei receiveResponse");
    return(false);
    }

    CBTRACELN("Erfolg!");
    return(true);
    }

    bool CHttpConnection::getHeadHeader(const CUrl &url, CHttpResponse &header) {
    vector<string> vr;
    if(!getHeadHeader(url, vr))
    return(false);
    header.extract(vr);
    return(true);
    }

    //***************************************************************
    // getTraceHeader
    //***************************************************************

    bool CHttpConnection::getTraceHeader(const CUrl &url, vector<string> &header, int maxforwards) {
    CBTRACELN("\ngetTraceHeader\n-----------------------------------------------------");
    /*
    ** Head-Request formulieren
    /
    CHttpRequest request;
    request.setFromUrl(url);
    request.setRequestType(CHttpRequest::rtTRACE);
    request.setUserAgent(CHttpRequest::UAExplorer6);
    request.setMaxForwards(maxforwards);
    /

    ** Verbindung aufbauen
    /
    if(!connect(url)) {
    m_lastError="Fehler bei connect";
    CBTRACELN("Fehler bei connect");
    return(false);
    }
    /

    ** Request senden
    /
    if(!sendRequest(request)) {
    m_lastError="Fehler bei sendRequest";
    CBTRACELN("Fehler bei sendRequest");
    return(false);
    }
    /

    ** Antwort empfangen
    */
    if(!receiveResponse(header)) {
    m_lastError="Fehler bei receiveResponse";
    CBTRACELN("Fehler bei receiveResponse");
    return(false);
    }

    CBTRACELN("Erfolg!");
    return(true);
    }

    bool CHttpConnection::getTraceHeader(const CUrl &url, CHttpResponse &header, int maxforwards) {
    vector<string> vr;
    if(!getTraceHeader(url, vr, maxforwards))
    return(false);
    header.extract(vr);
    return(true);
    }

    //***************************************************************
    // getFile
    //***************************************************************

    bool CHttpConnection::getFile(const CUrl &url, const string &filename) {
    CHttpRequest request;
    request.setFromUrl(url);
    request.setUserAgent(CHttpRequest::UAExplorer6);

    return(getFile(url,filename,request));
    }

    //***************************************************************
    // getFile
    //***************************************************************

    bool CHttpConnection::getFile(const CUrl &url, const string &filename, const CHttpRequest &request) {
    CBTRACELN("\ngetFile\n-----------------------------------------------------");

    /*
    ** Verbindung zum Server herstellen
    /
    if(!connect(url)) {
    m_lastError="Fehler bei connect";
    CBTRACELN("Fehler bei connect");
    return(false);
    }
    /

    ** Request senden
    /
    if(!sendRequest(request)) {
    m_lastError="Fehler bei sendRequest";
    CBTRACELN("Fehler bei sendRequest");
    return(false);
    }
    /

    ** Server-Response empfangen
    /
    vector<string> vresponse;
    if(!receiveResponse(vresponse)) {
    m_lastError="Fehler bei receiveResponse";
    CBTRACELN("Fehler bei receiveResponse");
    return(false);
    }
    /

    ** Response in ein CHttpResponse-Objekt umwandeln
    /
    bool success;
    CHttpResponse response;
    response.extract(vresponse);
    int code=response.getStatusCode();
    /

    ** Status zwischen 301 und 307?
    ** => Ressource wurde verschoben. Neue Location aus
    ** Response holen und getFile neu aufrufen
    /
    if((code>=301)&&(code<=307)&&(response.getLocation()!="")) {
    CBTRACELN("\nRessource verschoben. Neue Location bearbeiten...");
    disconnect();
    return(getFile(CUrl(response.getLocation()), filename));
    }
    /

    ** Alle Status-Codes außerhalb des 200er-Bereichs
    ** als Fehler betrachten
    /
    else if((response.getStatusCode()<200)||(response.getStatusCode()>=300)) {
    m_lastError=toString(response.getStatusCode())+" "+response.getStatusText();
    CBTRACELN("Server meldet Fehler");
    return(false);
    }
    else {
    /

    ** Je nachdem, ob Transfer an einem Stück oder
    ** in Chunks benötigt wird, die entsprechende
    ** Methode aufrufen
    /
    if(!response.isTransferChunked())
    success=normalFileTransfer(filename, response);
    else {
    success=chunkedFileTransfer(filename, response);
    /

    ** Hat ein Transfer in Chunks stattgefunden?
    ** => Hinter den Chunks nach eventuellen Entity-Headern
    ** Ausschau halten
    /
    if(success) {
    vresponse.clear();
    receiveResponse(vresponse);
    response.extract(vresponse,false);
    }
    }
    }
    /

    ** Komplette Server-Antwort im Objekt speichern
    */
    m_lastResponse=response;
    return(success);
    }

    //***************************************************************
    // normalFileTransfer
    //***************************************************************

    bool CHttpConnection::normalFileTransfer(const std::string &filename, const CHttpResponse &response) {
    /*
    ** Datei auf lokalem Datenträger zum Schreiben öffnen
    */
    CFile file;
    if(!file.open(filename,true,true)) {
    m_lastError="FEHLER! Lokale Datei konnte nicht zum Schreiben geoeffnet werden!";
    CBTRACELN("FEHLER! Lokale Datei konnte nicht zum Schreiben geoeffnet werden!");
    return(false);
    }
    CMemory<char> buf(10000);
    unsigned int amount;
    CHugeNumber totallyRead, bufsize("10000");

    /*
    ** Wenn Content-Length verfügbar, dann werden abgezählte
    ** Daten empfangen
    /
    if(response.isContenLengthAvailable()) {
    CHugeNumber length=response.getContentLength();
    CBTRACELN("Abgezaehlte Daten ("+length.getAsPointedNumber()+") werden gelesen!");
    do {
    /

    ** Darauf achten, dass nicht mehr Daten empfangen
    ** werden sollen als benötigt werden (weil read sonst
    ** blockiert.)
    */
    if(length>=bufsize)
    amount=m_iconn->receive(buf,10000);
    else
    amount=m_iconn->receive(buf,length.getAsUnsignedLong());

    file.writeBlock(buf,amount);
    totallyRead+=static_cast<unsigned long>(amount);
    length-=static_cast<unsigned long>(amount);
    CBTRACE("Bisher uebertragen: "+totallyRead.getAsPointedNumber()+" Bytes\r");
    /*
    ** Keine Daten mehr empfangen, obwohl noch nicht alle Daten
    ** angekommen sind?
    ** => Fehler!
    /
    if((totallyRead==0)&&(length!=0)) {
    m_lastError="chunkedTransfer: Übertragung abgebrochen";
    CBTRACE("chunkedTransfer: Übertragung abgebrochen");
    return(false);
    }
    } while(length!=0);
    }
    /

    ** Wenn keine Content-Length verfügbar, dann Daten
    ** empfangen, bis der Server die Verbindung trennt
    */
    else {
    CBTRACELN("Daten lesen bis zum Ende!");
    do {
    amount=m_iconn->receive(buf,10000);
    file.writeBlock(buf,amount);
    totallyRead+=static_cast<unsigned long>(amount);
    CBTRACE("Bisher uebertragen: "+totallyRead.getAsPointedNumber()+" Bytes\r");
    } while(amount);
    }

    CBTRACELN("\nErfolg!");
    return(true);
    }

    //***************************************************************
    // chunkedFileTransfer
    //***************************************************************

    bool CHttpConnection::chunkedFileTransfer(const std::string &filename, const CHttpResponse &response) {
    CBTRACELN("Uebertragung in Chunks beginnt...");
    /*
    ** Datei auf lokalem Datenträger zum Schreiben öffnen
    /
    CFile file;
    if(!file.open(filename,true,true)) {
    m_lastError="FEHLER! Lokale Datei konnte nicht zum Schreiben geoeffnet werden!";
    CBTRACELN("FEHLER! Lokale Datei konnte nicht zum Schreiben geoeffnet werden!");
    return(false);
    }
    CMemory<char> buf(10000);
    unsigned int amount;
    CHugeNumber totallyRead, bufsize("10000");
    /

    ** Größe des ersten Chunks einlesen
    /
    CHugeNumber length=hexToValue(m_iconn->receiveLine());
    /

    ** Solange eingelesene Chunk-Größe != 0
    /
    while(length!=0) {
    CBTRACELN("Chungroesse : "+length.getAsPointedNumber()+" Bytes");
    do {
    /

    ** Darauf achten, dass nicht mehr Daten empfangen
    ** werden als Chunk groß ist
    */
    if(length>=bufsize)
    amount=m_iconn->receive(buf,10000);
    else
    amount=m_iconn->receive(buf,length.getAsUnsignedLong());

    file.writeBlock(buf,amount);
    totallyRead+=static_cast<unsigned long>(amount);
    length-=static_cast<unsigned long>(amount);
    CBTRACE("Bisher uebertragen: "+totallyRead.getAsPointedNumber()+" Bytes\r");
    if((totallyRead==0)&&(length!=0)) {
    m_lastError="chunkedTransfer: Übertragung abgebrochen";
    CBTRACE("chunkedTransfer: Übertragung abgebrochen");
    return(false);
    }

    } while(length!=0);

    CBTRACELN("");
    /*
    ** CRLF hinter Chunk-Datn einlesen
    /
    m_iconn->receiveLine();
    /

    ** Größe des nächsten Chunks einlesen
    */
    length=hexToValue(m_iconn->receiveLine());
    }

    CBTRACELN("\nErfolg!");
    return(true);
    }

    }; // namespace Codebook

    😮

    Fehler:

    "IString.h": E2268 Aufruf der undefinierten Funktion 'tolower' in Funktion insensitive_char_traits::eq(const char &,const char &) in Zeile 19
    "IString.h": E2268 Aufruf der undefinierten Funktion 'tolower' in Funktion insensitive_char_traits::eq(const char &,const char &) in Zeile 19
    "IString.h": E2268 Aufruf der undefinierten Funktion 'tolower' in Funktion insensitive_char_traits::lt(const char &,const char &) in Zeile 23
    "IString.h": E2268 Aufruf der undefinierten Funktion 'tolower' in Funktion insensitive_char_traits::lt(const char &,const char &) in Zeile 23
    "CHttpRequest.h": E2361 'const' wurde bereits einbezogen in Zeile 16
    "CHttpRequest.h": E2361 'const' wurde bereits einbezogen in Zeile 17
    "CSpecificINetConn.h": E2209 include-Datei 'afxsock.h' kann nicht geöffnet werden in Zeile 6
    "CSpecificINetConn.h": E2312 'runtime_error' ist keine eindeutige Basisklasse von 'internet_error' in Funktion internet_error::internet_error(const _STL::string &) in Zeile 16
    "CSpecificINetConn.h": E2251 Standardkonstruktor zum Initialisieren der Basisklasse '_STL::runtime_error' nicht gefunden in Funktion internet_error::internet_error(const _STL::string &) in Zeile 17
    "CSpecificINetConn.h": E2139 In Deklaration fehlt ; in Zeile 22
    "CSpecificINetConn.h": E2303 Typname erwartet in Zeile 23
    "CSpecificINetConn.h": E2139 In Deklaration fehlt ; in Zeile 23
    "CSpecificINetConn.h": E2303 Typname erwartet in Zeile 24
    "CSpecificINetConn.h": E2139 In Deklaration fehlt ; in Zeile 24
    "CSpecificINetConn.h": E2303 Typname erwartet in Zeile 25
    "CSpecificINetConn.h": E2139 In Deklaration fehlt ; in Zeile 25
    "CHttpConnection.cpp": W8057 Parameter 'response' wird nie verwendet. in Funktion CHttpConnection::chunkedFileTransfer(const string &,const CHttpResponse &) in Zeile 469
    *** 16 Fehler bei der Compilierung ***
    BCC32 beendet mit Fehler-Code: 1
    Erzeugen wegen Fehler abgebrochen

    Problematischer Header:

    //(IString.h)

    #ifndef __ISTRING_H
    #define __ISTRING_H

    #include <iostream>
    #include <string>

    namespace Codebook {

    struct insensitive_char_traits {
    typedef char char_type;
    typedef int int_type;

    static void assign(char& c1, const char& c2) {
    c1 = c2;
    }

    static bool eq(const char& c1, const char& c2) {
    return (tolower(c1) == tolower(c2));
    }

    static bool lt(const char& c1, const char& c2) {
    return (tolower(c1) < tolower(c2));
    }

    static int compare(const char *s1, const char *s2, size_t len) {
    for (; 0 < len; --len, ++s1, ++s2)
    if (!eq(*s1, *s2))
    return (lt(*s1, *s2) ? -1 : +1);
    return (0);
    }

    static size_t length(const char *s) {
    size_t len;
    for (len = 0; !eq(*s, char()); ++s)
    ++len;
    return (len);
    }

    static char *copy(char *s1, const char *s2, size_t len) {
    char *ptr = s1;
    for (; 0 < len; --len, ++ptr, ++s2)
    assign(*ptr, *s2);
    return (s1);
    }

    static const char *find(const char *s, size_t len, const char& c) {
    for (; 0 < len; --len, ++s)
    if (eq(*s, c))
    return (s);
    return (0);
    }

    static char *move(char *s1, const char *s2, size_t len) {
    char ptr = s1;
    if (s2 < ptr && ptr < s2 + len)
    for (ptr += len, s2 += len; 0 < len; --len)
    assign(
    --ptr, *--s2);
    else
    for (; 0 < len; --len, ++ptr, ++s2)
    assign(*ptr, *s2);
    return (s1);
    }

    static char *assign(char *s, size_t len, char c) {
    char *ptr = s;
    for (; 0 < len; --len, ++ptr)
    assign(*ptr, c);
    return (s);
    }

    static char to_char_type(const int_type& i) {
    return (i);
    }

    static int_type to_int_type(const char& c) {
    return (c);
    }

    static bool eq_int_type(const int_type& c1, const int_type& c2) {
    return (c1 == c2);
    }

    static int_type eof() {
    return ((int_type)EOF);
    }

    static int_type not_eof(const int_type& i) {
    return (i != eof() ? i : !eof());
    }

    };

    typedef std::basic_string<char, insensitive_char_traits, std::allocator<char> >
    insensitive_string;

    }; // ende namespace Codebook
    #endif

    Post:

    Der Code sollte eigentlich funktionieren, allerdings macht er mir über Windows/C++BuilderXPersonal faxen! Ich hab kp, warum da soviele unsinnige Fehler kommen?!

    Wäre nett wenn sich jemand dem Problem annehmen könnte.

    Ich bin eigentlich nicht so gut in C++, die Datei ist aus dem Buch: "Das C++ Codebook"! Ich will versuchen das Programm nachzuvollziehen, doch es wäre gut, wenn es erstmal fehlerfrei wäre!

    Vielen Dank schonmal für die Hilfe,

    mfg
    HaNoCr.

    Ps:
    Kann mir mal einer sagen, wie man den Code, gleich übersichtlich übernehmen kann? So wie es jetzt ist, sieht es (ohne Tabs u. Farben) doch eher unübersichtlich aus.
    Wie macht ihr das ? 😕
    Ich mein, wenn ich den Artikel bearbeite, sind die Tabs ja wenigstens noch da, aber wenn man sich den Artikel dann fertig anguckt sind se weg ?!
    ...
    😡



  • Hallo

    Wenn du willst, das deine Post wirklich gelesen werden, dann
    - benutzt die CPP-Codetags fürs Posten von Code
    - rück deinen Code vernünftig ein
    - kürze deinen Code auf das wesentliche

    Nun zum Thema : Der Builder kennt CHttpConnection nicht. Das ist ein Teil der MFC, und die gibts nur beim Microsoft Visual Studio.
    Der Builder hat ähnliche Klassen, der Code aus dem Buch hilft dir dabei nicht viel.
    Also besorg dir entweder die MS-IDE (gibt eine kostenlose Version), oder arbeite mit dem Builder wie es der Builder erwartet. In jedemfall aber gewöhn dir an, sowas ins richtige Subforum zu schreiben.

    bis bald
    akari



  • Jop!
    Mach ich in Zukunft.

    Wie rücke ich den vernümftig ein bzw. Kopiere ihn komplett mit farben und tabs ?
    Entschuldige, aber was ist hier den mom das wesentliche ? Die problematik erstrekt sich über gesammten Code, oder nicht ?

    mfg
    HaNoCr



  • Hallo

    Den CPP-tags findest du beim Schreiben deines Posts genau unter den Smilies. Du schreibst deinen Code wie gewohnt, markierst den Bereich und klickst auf den C/C++ Button. Das einrücken der einzelnen Codeblöcke must du aber selber auch machen, wie du es auch im Codeeditor machen würdest/solltest.

    Das wesentliche wäre die Stelle gewesen, wo der Compiler mit der ersten Fehlermeldung (also die auf die sich auch dein Threadtitel bezieht) stehenbleibt.

    bis bald
    akari



  • Vielen Dank!

    mfg
    HaNoCr


Anmelden zum Antworten