Coding a SYN Scanner guide ( source included )

Giorgos Keramidas keramida at ceid.upatras.gr
Thu Mar 29 15:12:00 EEST 2007


On 2007-03-29 05:13, - <advent.cloud.strife at gmail.com> wrote:
>V13 wrote:
>> Epeisis, to na xrisimopoieis etsi ta structs mallon problimata tha
>> soy dimioyrgisei logo alignment kai reordering. Des to
>> __attribute__((packed)) toy gcc. P.x. gia to IP:
>>
>> ----
>> struct pseudo_hdr {
>>         u_int32_t src;          /* 32bit source ip address*/
>>         u_int32_t dst;          /* 32bit destination ip address */
>>         u_char mbz;             /* 8 reserved bits (all 0)      */
>>         u_char proto;           /* protocol field of ip header */
>>         u_int16_t len;          /* tcp length (both header and data */
>> } __attribute__((packed));
>> ----
>>
>>   Des tin eksodo apo to parakato programma:
>> ----
>> #include <stdio.h>
>>
>> struct A { int a; char b; int c;};
>>
>> struct B { int a; char b; int c; } __attribute__((packed));
>>
>> int main()
>> {
>>         printf("%d\n%d\n", sizeof(struct A), sizeof(struct B));
>> }
>> ----
>>
>> v13 at hell:/tmp$ ./a
>> 12
>> 9
>>
>> Opos blepeis, logo alignment, to proto struct epiase 12 bytes giati
>> to c egine align sta 32bit (4 byte), opote kai to c ksekinoyse apo to
>> +2*4.  Ayto mporeis na to deis kanontas compile me to -Wpadded:
>
> thanx ! tetoiou eidous feedback perimenw.
> implicit reordering mias struct den nomizw na ginetai kai sumfwna me
> to C standard upo kanonikes sun8hkes den 8a prepei na ginetai

Σωστός.

> Twra gia to packing ston sugekrimeno kwdika mono gia ka8ara
> optimization skopus (  < size )  tha eixe isws nohma.

Αυτό όμως είναι λίγο λάθος.  Έχει δίκιο ο Στέφανος (V13).  Αν κάνεις
malloc() 12 bytes για ένα object τύπου "struct A", μπορεί ο memory
allocator να σου επιστρέψει τα παρακάτω bytes:

    A5 A5 A5 A5  A5 A5 A5 A5  A5 A5 A5 A5
    ___________  __           ___________
    a            b            c

Αν εσύ διαβάσεις από 'raw data' ένα πακέτο που έχει τιμές:

    a = 0x12345678 (4 bytes)
    b = 0xCC       (1 byte)
    c = 0x23456789 (4 bytes)

χρησιμοποιώντας απλά read() για όλο το struct κι όχι read() για κάθε
member ξεχωριστά, μπορεί να προσπαθήσεις να διαβάσεις περισσότερα bytes
από ότι είναι διαθέσιμα στο packet stream.

Αν από την άλλη, για κάποιο λόγο όντως προσπαθήσεις να διαβάσεις 9
bytes, τα δεδομένα θα γραφτούν σε ένα struct A με τη μορφή:

    12 34 56 78  CC 23 45 67  89 A5 A5 A5
    ___________  __           ___________
    a            b            c

και δεν θα είναι πολύ σωστές οι τιμές των struct members.

> To pseudo header allwste xrhsimopoieitai mono sto checksuming kai me ena
> sizeof upologizetai pada swsta to mege8os.

Δηλαδή, ακριβώς λόγω των "padding bytes" μπορεί να κάνεις checksum σε
λάθος δεδομένα (επειδή π.χ. δεν έκανες memset() σε μηδέν όλα τα bytes
πριν από *κάθε* read() call).

Δεν είναι πιο εύκολο να χρησιμοποιήσεις "packed structures"; :-)




More information about the unix-admin-gr mailing list