Kleitkommawerte übertragen
-
CStoll schrieb:
..als einen Block aus 4 beliebigen char-Werten.
8

-
CStoll schrieb:
Wieso sollte er? Natürlich mußt du es richtig casten:
double d; sendto(socket,(char*)&d,sizeof(double),...); //oder für C++ Puristen: sendto(socket,reinterpret_cast<char*>(&d),sizeof(double),...);Das schneidet überhaupt nichts ab, sondern interpretiert den Speicherbereich, auf dem 'd' liegt als einen Block aus 4 beliebigen char-Werten.
(wie gesagt mußt du nur darauf hoffen, daß der Empfänger die selbe Repräsentation für double's verwendet, sonst wird es (hmm) unangenehm)den Empfänger schreibe ich mir ja selber, das sollte dann nicht das problem sein.
Wobei ich mich damit dann ersteinmal auseinandersetzen muss.Wenn ich jetzt mitlogge was er über das Netzwerk schickt bekomm ich
30 4E 2A 12 02 00 00 00 als Hex für 5.2Die Frage ist für mich wie man daraus dann wieder 5.2 erhält?
-
neugier schrieb:
den Empfänger schreibe ich mir ja selber, das sollte dann nicht das problem sein.
Wobei ich mich damit dann ersteinmal auseinandersetzen muss.Der Knackpunkt ist weniger das, was du schreibst, sondern das drunterliegende System. Da gibt es durchaus Interpretationsspielräume, wie man aus einem 8 Byte großen Datenblock eine Gleitkommazahl rekonstruieren kann - und deshalb sollten beide beteiligten Systeme eine identische Darstellung verwenden, damit sie kommunizieren können.
Wenn ich jetzt mitlogge was er über das Netzwerk schickt bekomm ich
30 4E 2A 12 02 00 00 00 als Hex für 5.2Die Frage ist für mich wie man daraus dann wieder 5.2 erhält?
Im optimalsten Fall genauso durch einen reinterpret_cast<>, im schlechtesten Fall gar nicht (das meinte ich mit der Repräsentation).
Wenn die Systeme nicht kompatibel sind, mußt du vermutlich bis auf Systemebene heruntersteigen und die Daten manuell zerlegen und wieder rekonstruieren.@pale dog: OK, sagen wir 8, wenn es dich glücklich macht - ich kenne die konkreten Größenanforderungen nicht auswendig (und wenn ich es in der Praxis benötige, verwende ich einfach 'sizeof()').
-
CStoll schrieb:
@pale dog: OK, sagen wir 8, wenn es dich glücklich macht - ich kenne die konkreten Größenanforderungen nicht auswendig (und wenn ich es in der Praxis benötige, verwende ich einfach 'sizeof()').
no problem

btw: bei mir ist 5.2 übrigens: 0xCD, 0xCC, 0xCC, 0xCC, 0xCC, 0xCC, 0x14, 0x40
(sagt zumindest der winhex data interpreter)
ich schätze da läuft beim senden noch irgendwas schief...

-
pale dog schrieb:
no problem

btw: bei mir ist 5.2 übrigens: 0xCD, 0xCC, 0xCC, 0xCC, 0xCC, 0xCC, 0x14, 0x40
(sagt zumindest der winhex data interpreter)
ich schätze da läuft beim senden noch irgendwas schief...

Die Frage ist nur was da noch schief läuft.
wenn ich es "normal" übertrage, ohne den cast, kommt 05 heraus.
Ok es wird mal wieder die Nachkommastelle abgeschnitten.
Aber sonst macht er nichts ungewolltes...
-
neugier schrieb:
pale dog schrieb:
no problem

btw: bei mir ist 5.2 übrigens: 0xCD, 0xCC, 0xCC, 0xCC, 0xCC, 0xCC, 0x14, 0x40
(sagt zumindest der winhex data interpreter)
ich schätze da läuft beim senden noch irgendwas schief...

Die Frage ist nur was da noch schief läuft.
weiss nicht...
hier hast du ein kleines progrämmchen, mit dem man die bytes einen doubles anzeigen kann, vielleicht hilft's:#include <stdio.h> int main() { double x = 5.2; unsigned char *px = (unsigned char*)&x; int s; for (s=0; s<sizeof(double); s++) printf ("%02x ", px[s]); }
-
neugier schrieb:
Die Frage ist nur was da noch schief läuft.
wenn ich es "normal" übertrage, ohne den cast, kommt 05 heraus.
Ok es wird mal wieder die Nachkommastelle abgeschnitten.Zeig mal Code.
-
static void mdlOutputs(SimStruct *S, int_T tid) { /* input ports */ double **u = (double**) ssGetInputPortRealSignalPtrs(S,0); uint32_T **dataLen = (uint32_T**) ssGetInputPortSignalPtrs(S,1); int iBufSize = (int)floor((*mxGetPr(ssGetSFcnParam(S,2)))+0.5); int i, retval; SInfo *info = GetStructure(S); int length = (int)floor(*dataLen[0]+0.5); int sock_error; /* retrieve pointer to pointers work vector */ void **PWork = ssGetPWork(S); /* assign buffer pointer */ unsigned char *buffer; buffer = (unsigned char *)PWork[1]; length = (iBufSize<length) ? iBufSize : length; for(i=0;i<length;i++) { buffer[i]=*u[i]; } switch(info->connState) { case csConnected: if(length>0) { retval = sendto(info->clisock, reinterpret_cast<char*>(&buffer), length*4, 0, (sockaddr *)&(info->cli_sin), info->iAddrLen); if(retval>=0) { /* printf("Sent %d bytes from %d bytes.\n", retval, length); */ } else if (retval == SOCKET_ERROR) { sock_error = WSAGetLastError(); if(sock_error == WSAESHUTDOWN || sock_error == WSAENOTCONN || sock_error == WSAEHOSTUNREACH || sock_error == WSAECONNABORTED || sock_error == WSAECONNRESET || sock_error == WSAETIMEDOUT) { closesocket(info->clisock); info->connState = csError; } printf("Error code: %d\n", WSAGetLastError()); } } break; case csError: StartUDPClient(S, info); break; } }
-
neugier schrieb:
unsigned char *buffer; retval = sendto(info->clisock, reinterpret_cast<char*>(&buffer), length*4, 0, (sockaddr *)&(info->cli_sin), info->iAddrLen);Wieso überträgst du die Adresse von buffer? Ist der Inhalt nicht viel interessanter? Mal davon abgesehen hättest du den Code etwas zusammenstreichen können, 99% sind doch für die Frage irrelevant.
-
neugier schrieb:
retval = sendto(info->clisock, reinterpret_cast<char*>(&buffer), length*4, 0, (sockaddr *)&(info->cli_sin), info->iAddrLen);versuch stattdessen mal:
[cpp]retval = sendto(info->clisock, (char)buffer*, ....
[/cpp]
ich schätze das & stört etwas...
-
pale dog schrieb:
neugier schrieb:
retval = sendto(info->clisock, reinterpret_cast<char*>(&buffer), length*4, 0, (sockaddr *)&(info->cli_sin), info->iAddrLen);versuch stattdessen mal:
[cpp]retval = sendto(info->clisock, (char)buffer*, ....
[/cpp]
ich schätze das & stört etwas...Sobald ich das so mache, schneidet er mir die Nachkommastellen ab.

-
neugier schrieb:
Sobald ich das so mache, schneidet er mir die Nachkommastellen ab.

dann ist noch was anderes faul.
die adresse von 'buffer' zu nehmen ist in dem fall jedenfalls verkehrt und das solltest du besser lassen...
