Buffer auslesen und in Variable schreiben



  • Hallo,

    ich möchte Daten aus einem Buffer auslesen und in eine Variable schreiben.
    Die Werte im Buffer sind immer 8 Bit lang und sollen aneinander gereiht einen UINT32 Wert ergeben.
    Der maximale Wert im Buffer ist 280 001 was Bedeutet ich muss nur die ersten 3 Buffer Werte auslesen. Soweit so gut. Jetzt habe ich versucht mal eine C Funktion zu schreiben, die leider nicht funktioniert. Kann mir jemand weiterhelfen?

    long int DatenAuslesen(Buffer){
    long int Daten;
    Daten = Buffer[0]:
    Daten = Daten + Buffer[1]<<8;
    Daten = Daten + Buffer[2]<<16;
    return Daten;
    } 
    


  • Bitte Fehlermeldung posten! Mit "... die leider nicht funktioniert" kann niemand was anfangen.

    Der Datentyp für den Parameter Buffer fehlt.



  • @Ollom sagte in Buffer auslesen und in Variable schreiben:

    Daten = Buffer[0]:

    Der Doppelpunkt sollte ein Semikolon sein.

    Ansonsten generelle Frage: sind die 4 Bytes in "aufsteigender" Reihenfolge? Musst du dich um Endianness kümmern?

    Was kommt raus, wenn 1 rauskommen soll? Was kommt raus, wenn 256 rauskommen soll? Das könnte Aufschluss auf deine Probleme geben, sollte der Doppelpunkt in Wirklichkeit ein Semikolon sein.



  • ... und dann spendieren wir Buffer noch einen Typ.

    @Ollom Zeig' echten Code. Copy&Paste. Und sag was Du versucht hast, was Du erwartet hast und was stattdessen dabei rauskommt.



  • Halo Ollom!

    Versuch es doch mal mit union:

    // Wenn ein Int-Wert aus 4 Bytes besteht, dann ist das hoechstwertigste Byte immer links
    // Danach das zweithöchste Byte, das  dritthochste, schliesslich Byte Nr. 0
    // Das liegt daran, das auch das binaere Zahlensystem ein dekadisches Ziffernsystem ist 
    #include <stdio.h>
    #include <stdlib.h>   // wegen EXIT_SUCCESS
    
    
    void intzuchar(int zuza, unsigned char twoword [])
    {
     union intpart{
     unsigned int erge;
     unsigned char ipart[4];
     } ipt;
    
     ipt.erge = zuza;
    
     twoword[0] = ipt.ipart[0];
     twoword[1] = ipt.ipart[1];
     twoword[2] = ipt.ipart[2];
     twoword[3] = ipt.ipart[3];
    
    }
    
    int main(int argc, char **argv)
    {
     int intval, i;
     unsigned char intchar[4];
     
     printf("int to char test\n");
     printf("Please enter a int-value: ");
     scanf("%d", &intval);
    
    
     printf("The value was: %d\n", intval); 
     
     intzuchar(intval, intchar);
     
     printf("The int value int Bytes:\n"); 
     for (i = 0; i < 4; i++)
      {
       printf("Byte Nr.: %d   intchar[%d] = %d\n", i, i, intchar[i]); 
      }   
     
     printf("End of Program\n"); 
     
     return EXIT_SUCCESS;
    }
    
    

    Dann ersparst du dir wenigstens die Bitschubserei.

    Man könnte auch Bitfelder nehmen. Bei uns in der Oberpfalz gibt es zu solch einer Vorgehensweise ein Sprichwort:

    "Mit der Kirche ums Dorf herum reiten"😍
    :

    /**strinit.cpp demonstriert das Prinzip von Bitfeldern */
    #include <stdio.h>
    #include <string.h>
    
    
    /* define a structure with bit fields */
    
    
    struct two_Bytes
    {
       unsigned short lbyte : 8;
       unsigned short hbyte : 8;
    } tb;
     
    /* define a union with bit fields */
    union mixed
    {
      unsigned short ganz;
      struct two_Bytes tb;
    } mx; 
    
     
    int main( ) 
    {
      unsigned short a, b, c;
       
      a = 25;
      b = 255;
      
      c = b + (a << 8); 
      
        
       printf( "Example for struct, Bitfield and uoion\n\n");
       printf( "Memory size occupied by two_Bytes: %lu Byte\n", sizeof(two_Bytes));
       printf( "Memory size occupied by mixed....: %lu Byte\n\n", sizeof(mixed));
    
       mx.tb.hbyte = 25;
       mx.tb.lbyte = 255;
       
       printf( "Sizeof( mxixed ) : %lu Byte\n", sizeof(mx) );
       printf( "eg.tl.hbyte..... : %d\n", mx.tb.hbyte);
       printf( "eg.tl.lbyte..... : %d\n", mx.tb.lbyte);
       printf( "eg.ganz.....     : %d\n", mx.ganz);
       
       printf( "a =  %d\nb = %d\n", a, b);
       
       printf( "result of c = b +(a << 8) : %d\n", c);
         
      return 0;
    }
    


  • @rustyoldguy sagte in Buffer auslesen und in Variable schreiben:

    #include <stdlib.h>   // wegen EXIT_SUCCESS
    // ...
    int main(/* */)
    {
    // ...
     return EXIT_SUCCESS;
    }
    

    Lass es doch einfach weg.


    Nur der Vollständigkeit halber will ich gesagt haben, daß solches type-pruning throu unions nur in C erlaubt ist, nicht in C++. (Accessing inactive union member and undefined behavior?)

    // edit: Weil wir ja hier im C-Forum sind sollte das eine Nebenbemerkung sein. Natürlich kann man es auch in C++ tun. Hey, no risk - no fun 🙄



  • Wieso mit fragwürdigen union Tricks rummachen wenn die Variante mit den Shifts die überall (C, C++) funktioniert sogar kürzer ist?

    Der einzige Grund der mit einfällt wäre wenn das was reinkommt immer "native endian" ist. Dann müsste man bei den Shifts eine Unterscheidung einbauen. Nur in dem Fall würde ich persönlich einfach memcpy verwenden. Es sei denn die Stelle wäre übelst performance-kritisch - dann würde ich mich nicht unbedingt darauf verlassen wollen dass mein Compiler das memcpy immer und in jedem Fall wegoptimiert.


Log in to reply