| Autor |
Nachricht |
BlackCubeX
Mitglied
Benutzerprofil
Anmeldungsdatum: 19.12.2011
Beiträge: 17
|
BlackCubeX Mitglied
16:43:18 23.02.2012 Titel: |
Binärdaten über Sockets empfangen? |
Zitieren |
Hey,
wie der Titel schon sagt arbeite ich an einem einfachen HTTP 1.0 Client, habe aber Probleme mit Binärdaten. Textdateien lassen sich einfach über
| C++: | do {
count = recv( sock, buffer, sizeof(buffer), 0);
strcat(content, buffer);
}
while (count > 0); | |
empfangen.
Wenn ich aber nun z.B. ein PNG anfordere und in eine Datei schreibe, ist diese nicht lesbar.
Kann mir pls jmd helfen? |
|
|
|
 |
rüdiger
Moderator
Benutzerprofil
Anmeldungsdatum: 11.07.2001
Beiträge: 23067
|
rüdiger Moderator
17:02:23 23.02.2012 Titel: |
|
Zitieren |
Autsch. Dein Code zeigt einfach, dass du Stringhandling in C nicht verstanden hast. In C sind Strings mit 0-terminiert. strcat etc. arbeitet mit Strings. Aber recv liefert keine 0-terminierten Strings! Du bekommst einfach die Daten wie sie empfangen wurden und über den Rückgabewert die Anzahl der Bytes.
Du kannst hier kein strcat nehmen! Aber es ist noch schlimmer. strcat führt keinerlei Überprüfung von Buffergrößen durch. Es wäre also ein leichtes den content Buffer überlaufen zu lassen.
Und strcat ist auch der Grund, warum es mit Binärdaten nicht klappt. Binärdaten können nämlich 0en enthalten.
Ich hoffe, dass das kein Produktivcode werden soll. Nimm dann lieber etwas fertiges (zB libcurl). |
|
|
|
 |
BlackCubeX
Mitglied
Benutzerprofil
Anmeldungsdatum: 19.12.2011
Beiträge: 17
|
BlackCubeX Mitglied
17:30:58 23.02.2012 Titel: |
|
Zitieren |
Danke für die Erklärung, das hat mich schon deutlich weiter gebracht.
Nein, das sollte keine Produktivsoftware werden, da würd ich mich ja zum Obst der Woche machn
libcurl hatt ich mich schonmal mit beschäftigt, gefällt mir aber iwie nich so. Was hältst du von libwww? |
|
|
|
 |
cooky451
Mitglied
Benutzerprofil
Anmeldungsdatum: 16.10.2010
Beiträge: 6866
|
cooky451 Mitglied
18:52:13 23.02.2012 Titel: |
|
Zitieren |
Solange du C nicht verstanden hast hilft dir auch keine lib. Versuche einfach mal das vernünftig zu machen, wenn du C dann kannst, kannst du immer noch libcurl nutzen auf C++ umsteigen. |
_________________ Sie sind nicht berechtigt unrechtmäßige Kopien dieses Datenträgers zu erstellen.™
Keksverteilungsbeauftragter
|
|
 |
EOP
Mitglied
Benutzerprofil
Anmeldungsdatum: 15.09.2007
Beiträge: 798
|
EOP Mitglied
22:18:36 23.02.2012 Titel: |
|
Zitieren |
Statt strcat memcpy benutzen.
Ist aber nix für 'nen Anfänger. Sonst kracht's recht schnell. |
|
|
|
 |
BlackCubeX
Mitglied
Benutzerprofil
Anmeldungsdatum: 19.12.2011
Beiträge: 17
|
BlackCubeX Mitglied
00:44:48 24.02.2012 Titel: |
|
Zitieren |
Kannst du bitte erläutern, wie du das mit memcpy machen würdest? |
|
|
|
 |
EOP
Mitglied
Benutzerprofil
Anmeldungsdatum: 15.09.2007
Beiträge: 798
|
EOP Mitglied
01:07:34 24.02.2012 Titel: |
|
Zitieren |
| C++: | char *m_data;
int m_data_size, m_buf_size; | |
| C++: | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 | bool CCharBuffer::AppendData( char *p, int amount )
{
if( !p || amount < 0 )
return( false );
size_t uamount = static_cast<size_t> ( amount );
if( m_data_size+amount < m_buf_size )
{
memcpy(m_data+m_data_size, p, uamount);
m_data[m_data_size+amount] = 0;
}
else
{
char *tmp = new char[m_data_size+amount+1];
if( !tmp )
{
return( false );
}
memcpy(tmp, m_data, m_data_size);
delete [] m_data;
memcpy(tmp+m_data_size, p, uamount);
tmp[m_data_size+amount] = 0;
m_data = tmp;
m_buf_size = m_data_size+amount+1;
}
m_data_size += amount;
return( true );
} // bool CCharBuffer::AppendData( char *p, int amount ) | | |
|
|
|
 |
TyRoXx
Mitglied
Benutzerprofil
Anmeldungsdatum: 30.06.2009
Beiträge: 1033
|
TyRoXx Mitglied
18:08:49 24.02.2012 Titel: |
|
Zitieren |
| EOP schrieb: | | C++: | char *m_data;
int m_data_size, m_buf_size; | |
| C++: | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 | bool CCharBuffer::AppendData( char *p, int amount )
{
if( !p || amount < 0 )
return( false );
size_t uamount = static_cast<size_t> ( amount );
if( m_data_size+amount < m_buf_size )
{
memcpy(m_data+m_data_size, p, uamount);
m_data[m_data_size+amount] = 0;
}
else
{
char *tmp = new char[m_data_size+amount+1];
if( !tmp )
{
return( false );
}
memcpy(tmp, m_data, m_data_size);
delete [] m_data;
memcpy(tmp+m_data_size, p, uamount);
tmp[m_data_size+amount] = 0;
m_data = tmp;
m_buf_size = m_data_size+amount+1;
}
m_data_size += amount;
return( true );
} // bool CCharBuffer::AppendData( char *p, int amount ) | |
|
Wo hast du diese Scheiße denn ausgegraben? |
_________________ .. aber dann wäre C++ uneinheitlich und nicht mehr so anfängergerecht.
|
|
 |
EOP
Mitglied
Benutzerprofil
Anmeldungsdatum: 15.09.2007
Beiträge: 798
|
EOP Mitglied
21:35:56 24.02.2012 Titel: |
|
Zitieren |
| TyRoXx schrieb: |
Wo hast du diese Scheiße denn ausgegraben? | Was hast du da dran auszusetzen?
Komm mir jetzt bloß nicht mit vector<char>. Das ist was für Mädchen.
Es ging darum wie man memcpy benutzt und um dem OP zu zeigen, daß man sich Größen und Positionen merken muss. |
Zuletzt bearbeitet von EOP am 21:53:11 24.02.2012, insgesamt 2-mal bearbeitet |
|
 |
TyRoXx
Mitglied
Benutzerprofil
Anmeldungsdatum: 30.06.2009
Beiträge: 1033
|
TyRoXx Mitglied
22:38:46 24.02.2012 Titel: |
|
Zitieren |
| EOP schrieb: | | TyRoXx schrieb: |
Wo hast du diese Scheiße denn ausgegraben? | Was hast du da dran auszusetzen?
Komm mir jetzt bloß nicht mit vector<char>. Das ist was für Mädchen.
Es ging darum wie man memcpy benutzt und um dem OP zu zeigen, daß man sich Größen und Positionen merken muss. |
Ich glaube hier geht es um C, also kommt vector nicht direkt in Frage. Das heißt aber nicht, dass man unterirdisches C mit Klassen propagieren muss.
| C++: | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 | bool //schon mal was von Ausnahmen gehört?
CCharBuffer //eine hässliche Unart
::AppendData( char *p, //const fehlt, p ist kein vernünftiger Name
int amount ) //warum denn int?
{
if( !p || amount < 0 ) //assert(..), und warum nicht einfach size_t?
return( false ); //überflüssige und falsch gesetzte Klammern
size_t uamount = static_cast<size_t> ( amount ); //jetzt auf einmal doch size_t
if( m_data_size+amount < m_buf_size ) //das könnte man einfacher haben mit vector<char>
{
memcpy(m_data+m_data_size, p, uamount);
m_data[m_data_size+amount] = 0; //wieso das denn? Müsste die Klasse dann nicht CString heißen?
}
else
{
char *tmp = new char[m_data_size+amount+1]; //aua
if( !tmp ) //new gibt nicht 0 zurück
{
return( false );
}
memcpy(tmp, m_data, m_data_size);
delete [] m_data;
memcpy(tmp+m_data_size, p, uamount);
tmp[m_data_size+amount] = 0;
m_data = tmp;
m_buf_size = m_data_size+amount+1; //die drei Summanden hatten wir eben schon bei new[]
}
m_data_size += amount;
return( true );
} // bool CCharBuffer::AppendData( char *p, int amount ) | | |
_________________ .. aber dann wäre C++ uneinheitlich und nicht mehr so anfängergerecht.
Zuletzt bearbeitet von TyRoXx am 22:40:09 24.02.2012, insgesamt 1-mal bearbeitet |
|
 |
|
Nächstes Thema anzeigen
Vorheriges Thema anzeigen
Sie können Beiträge in dieses Forum schreiben. Sie können auf Beiträge in diesem Forum antworten. Sie können Ihre Beiträge in diesem Forum nicht bearbeiten. Sie können Ihre Beiträge in diesem Forum nicht löschen. Sie können an Umfragen in diesem Forum nicht mitmachen.
|
|
|
|
|