IP-Adress-Blöcke aus String-Parameter auslesen



  • Th69 schrieb:

    @mekick: der Code von Swordfish ist absolut reines ANSI-C ohne irgendwelche externen Libs!
    Kannst du überhaupt C - du scheinst einiges völlig falsch zu verstehen?!?

    Führe doch einfach mal den Code aus...

    Ja ich bin gerade fertig mit der Schule und habe nur n "ITA", arbeite im Moment als Praktikant in SW-Entwicklung. ANSI-C hatten wir schulisch ein Jahr, aber nicht besonders umfangreich und eher auf Mikroprozessor-Programmierung ausgelegt.

    Ich möchte probieren die Werte, die ich benötige mit int-Arrays zu bekommen. Gibt es keine Möglichkeit einen "String", also in C: ein "char-Array" nach Zahlen zu durchsuchen oder soetwas, und daraus einzelne int-Werte zu basteln?

    Das wäre nämlich eine Lösung, die ich auf anhieb verstehen würde.
    Falls das so gehen würde, wäre ich für eine Code-Idee sehr dankbar & in der Zeit teste ich den Code von @Swordfish.

    Danke & lieben Gruß!



  • mekick schrieb:

    1. Mitgegebenen Parameter in char[] abspeichern
    

    Sind sie schon. Dafür ist argv da. (Es ist kein richtiges Array, da du die Werte nicht verändern darfst. Aber lesend gibt es keinen Unterschied für dich)

    mekick schrieb:

    2. Array nach aneinanderhängenden Zahlen 0-9 durchsuchen
    

    Das macht sscanf für dich ( http://www.cplusplus.com/reference/cstdio/sscanf/ )

    mekick schrieb:

    3. jeweils in ein int[] abspeichern
    

    Das macht der Code von Swordfish in der Zeile mit dem sscanf.

    mekick schrieb:

    Gibt es keine Möglichkeit einen "String", also in C: ein "char-Array" nach Zahlen zu durchsuchen oder soetwas, und daraus einzelne int-Werte zu basteln?

    Einige.
    sscanf wurde schon genannt und ist hier das richtige, da du ja gleich vier Werte durch . getrennt haben willst.
    strtol oder strtoul
    atoi
    und für Fließkommazahlen strtod und atof



  • Ah. Danke!

    Das hab ich gebraucht!
    Jemanden, der mir mal die Augen aufmacht für das, was ich habe und was nicht.
    Danke!

    Auch euch beiden @Swordfish und @Th69.

    Verwirrend war für mich nur, dass in dem Code von dir, Swordfish, so oft einfach der Datentyp ausgelassen wurde, das ist neu für mich, da wir in der Schule immer alles ausgeschrieben haben & uns nciht mirt irgendwelchen ANSI-Definitionen oder Normen beschäftigt haben.

    #close
    (oder wie auch immer ihr das hier handhabt^^)



  • unsigned ist eine ganz korrekte Kurzschreibweise für unsigned int

    Seit Anbeginn von C



  • DirkB schrieb:

    unsigned ist eine ganz korrekte Kurzschreibweise für unsigned int

    Seit Anbeginn von C

    Ja ich find das ja auch nciht irgendwie doof oder unübersichtlich. Mir fehlte einzig und allein das Wissen 😕
    Tut mir leid .. Aber um so mehr: Danke für das ausführliche erklären (mit Geduld).
    Ich habe mich Heute hier im forum angemeldet und hoffe,
    dass ich weiter so gute Erfahrungen hier machen kann
    und anderen auch eine Hilfe sein kann
    (wobei das wahrscheinlich erst später der Fall sein dürfte).

    LG,
    Felix



  • ...



  • mekick schrieb:

    Was ich sagen will ist:
    Ich kann aufgrund von Speicherplatzminimierung nicht so viele spezielle LIBs und Heads einbinden und möchte möglichst mit int und char arbeiten, anstatt diese speziellen Datentypen zu verwenden, wie "IP" oder "size_t".

    Du schaust erstmal, was es auf Deiner Zielplattform gibt und benutzt genau das.
    Nicht ganz überraschend ist das meiste, was Du mit IP-Adressen machen willst schon mal gemacht worden und im Regelfall besser.

    Z.B. gibt es eine Struktur die IPV4 Adressen als das speichert, was sie sind: 32Bit Zahlen und nicht als int[4], dessen Größe wohl wahlweise 64, 128 oder 256 Bit betragen wird.

    Z.B.:

    #include <stdio.h>
    
    #include <arpa/inet.h>
    #include <libgen.h>
    
    void print_address(const struct in_addr* addr, const char* str){
      static char buf[]="000.000.000.000";
      static const size_t size=sizeof(buf);
      inet_ntop(AF_INET, addr, buf, size);
      printf("%s: %s\n", str, buf);
    }
    
    int main(int argc, char* argv[]){
      struct in_addr host, netmask, network;
      if(argc<3){
        fprintf(stderr, "usage: %s host netmask\n", basename(argv[0]) );
        return -1;
      }
      inet_pton(AF_INET, argv[1], &host);
      inet_pton(AF_INET, argv[2], &netmask);
      print_address(&host, "host");
      print_address(&netmask, "netmask");
      network.s_addr = host.s_addr & netmask.s_addr;
      print_address(&network, "network");
    }
    

  • Mod

    Es ist übrigens ein Irrtum anzunehmen, dass Bibliotheken und Header irgendwie Speicherplatz belegen würden* (abgesehen davon dass hier - wie schon gesagt wurde - ohnehin nur Standard-C benutzt wurde, wenn auch Teile, die dir anscheinend noch nicht bekannt waren). Bibliotheken können nicht zaubern, dein eigener Code aber auch nicht. Wenn du Code schreibst, einmal direkt im Programm und einmal als Bibliothek, die von einem anderen Programm genutzt wird, dann kommt am Ende das gleiche raus, bloß der Weg ist ein anderer (meistens ist der Weg über die Bibliothek der bessere, da man sich Arbeit spart. Dazu sind Bibliotheken schließlich da).

    *: Außer natürlich auf dem System, auf dem die Übersetzung stattfindet. Da müssen die Header und Bibliotheken sowohl gespeichert als auch Verarbeitet werden.



  • Furble Wurble schrieb:

    mekick schrieb:

    Was ich sagen will ist:
    Ich kann aufgrund von Speicherplatzminimierung nicht so viele spezielle LIBs und Heads einbinden und möchte möglichst mit int und char arbeiten, anstatt diese speziellen Datentypen zu verwenden, wie "IP" oder "size_t".

    Du schaust erstmal, was es auf Deiner Zielplattform gibt und benutzt genau das.
    Nicht ganz überraschend ist das meiste, was Du mit IP-Adressen machen willst schon mal gemacht worden und im Regelfall besser.

    Z.B. gibt es eine Struktur die IPV4 Adressen als das speichert, was sie sind: 32Bit Zahlen und nicht als int[4], dessen Größe wohl wahlweise 64, 128 oder 256 Bit betragen wird.

    Z.B.:

    #include <stdio.h>
    
    #include <arpa/inet.h>
    #include <libgen.h>
    
    void print_address(const struct in_addr* addr, const char* str){
      static char buf[]="000.000.000.000";
      static const size_t size=sizeof(buf);
      inet_ntop(AF_INET, addr, buf, size);
      printf("%s: %s\n", str, buf);
    }
    
    int main(int argc, char* argv[]){
      struct in_addr host, netmask, network;
      if(argc<3){
        fprintf(stderr, "usage: %s host netmask\n", basename(argv[0]) );
        return -1;
      }
      inet_pton(AF_INET, argv[1], &host);
      inet_pton(AF_INET, argv[2], &netmask);
      print_address(&host, "host");
      print_address(&netmask, "netmask");
      network.s_addr = host.s_addr & netmask.s_addr;
      print_address(&network, "network");
    }
    

    Ich habe char[4] genommen, da ein char ein Byte ist, genau wie ein IP-Address Block. So haben wir auch in Mikrocontrollertechnik gelernt. D.h. Speicherorientiert ..?

    Aber danke und ich schätze ich werde die Lösung dann doch mal etwas verändern ...

    LG Felix



  • char ist für Zeichen.
    Nimm unsigned char oder uint8_t aus der stdint.h



  • Also, habe jetzt folgende Lösung implementiert:

    //für die spätere Dezimaldarstellung, die ich zum weiterverarbeitenden ausgeben brauche:
      unsigned char IP_adr[15], IP_mask[15], IP_net[15];
    
      // IP-Adress-Structs für IP_Adresse, Subnetzmaske und Netzwerkadresse
      struct in_addr host, netmask, network;
    
      inet_pton(AF_INET, argv[2], &host);
      inet_pton(AF_INET, argv[3], &netmask);
      network.s_addr = host.s_addr & netmask.s_addr; 
    
      // IP-Adressen Als Strings Abspeichern
      static char buf[]="000.000.000.000"; 
      static const size_t size=sizeof(buf); 
      inet_ntop(AF_INET, &host, buf, size);
      sprintf(IP_adr, "%s", buf); 
      inet_ntop(AF_INET, &netmask, buf, size);
      sprintf(IP_mask, "%s", buf); 
      inet_ntop(AF_INET, &network, buf, size);
      sprintf(IP_net, "%s", buf);
    

    Danke an alle, die ihren Senf dazugegeben haben 🙂

    Liebe Grüße,
    Felix



  • ⚠

    //für die spätere Dezimaldarstellung, die ich zum weiterverarbeitenden ausgeben brauche:
      unsigned char IP_adr[15], IP_mask[15], IP_net[15]; // Wenn das für Text ist, dann nur char (unsigned char ist zum rechnen)
    
      sprintf(IP_adr, "%s", buf);  // Dafür gibt es strcpy
    

Anmelden zum Antworten