Annotation of embedaddon/strongswan/src/libcharon/encoding/payloads/fragment_payload.c, revision 1.1.1.1

1.1       misho       1: /*
                      2:  * Copyright (C) 2012 Tobias Brunner
                      3:  * HSR Hochschule fuer Technik Rapperswil
                      4:  *
                      5:  * This program is free software; you can redistribute it and/or modify it
                      6:  * under the terms of the GNU General Public License as published by the
                      7:  * Free Software Foundation; either version 2 of the License, or (at your
                      8:  * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
                      9:  *
                     10:  * This program is distributed in the hope that it will be useful, but
                     11:  * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
                     12:  * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
                     13:  * for more details.
                     14:  */
                     15: 
                     16: #include "fragment_payload.h"
                     17: 
                     18: #include <encoding/payloads/encodings.h>
                     19: 
                     20: /** Flag that is set in case the given fragment is the last for the message */
                     21: #define LAST_FRAGMENT 0x01
                     22: 
                     23: typedef struct private_fragment_payload_t private_fragment_payload_t;
                     24: 
                     25: /**
                     26:  * Private data of an fragment_payload_t object.
                     27:  */
                     28: struct private_fragment_payload_t {
                     29: 
                     30:        /**
                     31:         * Public fragment_payload_t interface.
                     32:         */
                     33:        fragment_payload_t public;
                     34: 
                     35:        /**
                     36:         * Next payload type.
                     37:         */
                     38:        uint8_t next_payload;
                     39: 
                     40:        /**
                     41:         * Reserved byte
                     42:         */
                     43:        uint8_t reserved;
                     44: 
                     45:        /**
                     46:         * Length of this payload.
                     47:         */
                     48:        uint16_t payload_length;
                     49: 
                     50:        /**
                     51:         * Fragment ID.
                     52:         */
                     53:        uint16_t fragment_id;
                     54: 
                     55:        /**
                     56:         * Fragment number.
                     57:         */
                     58:        uint8_t fragment_number;
                     59: 
                     60:        /**
                     61:         * Flags
                     62:         */
                     63:        uint8_t flags;
                     64: 
                     65:        /**
                     66:         * The contained fragment data.
                     67:         */
                     68:        chunk_t data;
                     69: };
                     70: 
                     71: /**
                     72:  * Encoding rules for an IKEv1 fragment payload
                     73:  */
                     74: static encoding_rule_t encodings[] = {
                     75:        /* 1 Byte next payload type, stored in the field next_payload */
                     76:        { U_INT_8,                      offsetof(private_fragment_payload_t, next_payload)              },
                     77:        { RESERVED_BYTE,        offsetof(private_fragment_payload_t, reserved)                  },
                     78:        /* Length of the whole payload*/
                     79:        { PAYLOAD_LENGTH,       offsetof(private_fragment_payload_t, payload_length)    },
                     80:        { U_INT_16,                     offsetof(private_fragment_payload_t, fragment_id)               },
                     81:        { U_INT_8,                      offsetof(private_fragment_payload_t, fragment_number)   },
                     82:        { U_INT_8,                      offsetof(private_fragment_payload_t, flags)                             },
                     83:        /* Fragment data is of variable size */
                     84:        { CHUNK_DATA,           offsetof(private_fragment_payload_t, data)                              },
                     85: };
                     86: 
                     87: /*
                     88:                            1                   2                   3
                     89:        0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
                     90:       +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                     91:       ! Next Payload  !    RESERVED   !         Payload Length        !
                     92:       +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                     93:       !         Fragment ID           !  Fragment Num !     Flags     !
                     94:       +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                     95:       !                                                               !
                     96:       ~                       Fragment Data                           ~
                     97:       !                                                               !
                     98:       +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                     99: */
                    100: 
                    101: METHOD(payload_t, verify, status_t,
                    102:        private_fragment_payload_t *this)
                    103: {
                    104:        if (this->fragment_number == 0)
                    105:        {
                    106:                return FAILED;
                    107:        }
                    108:        return SUCCESS;
                    109: }
                    110: 
                    111: METHOD(payload_t, get_encoding_rules, int,
                    112:        private_fragment_payload_t *this, encoding_rule_t **rules)
                    113: {
                    114:        *rules = encodings;
                    115:        return countof(encodings);
                    116: }
                    117: 
                    118: METHOD(payload_t, get_header_length, int,
                    119:        private_fragment_payload_t *this)
                    120: {
                    121:        return 8;
                    122: }
                    123: 
                    124: METHOD(payload_t, get_type, payload_type_t,
                    125:        private_fragment_payload_t *this)
                    126: {
                    127:        return PLV1_FRAGMENT;
                    128: }
                    129: 
                    130: METHOD(payload_t, get_next_type, payload_type_t,
                    131:        private_fragment_payload_t *this)
                    132: {
                    133:        return this->next_payload;
                    134: }
                    135: 
                    136: METHOD(payload_t, set_next_type, void,
                    137:        private_fragment_payload_t *this, payload_type_t type)
                    138: {
                    139:        this->next_payload = type;
                    140: }
                    141: 
                    142: METHOD(payload_t, get_length, size_t,
                    143:        private_fragment_payload_t *this)
                    144: {
                    145:        return this->payload_length;
                    146: }
                    147: 
                    148: METHOD(fragment_payload_t, get_id, uint16_t,
                    149:        private_fragment_payload_t *this)
                    150: {
                    151:        return this->fragment_id;
                    152: }
                    153: 
                    154: METHOD(fragment_payload_t, get_number, uint8_t,
                    155:        private_fragment_payload_t *this)
                    156: {
                    157:        return this->fragment_number;
                    158: }
                    159: 
                    160: METHOD(fragment_payload_t, is_last, bool,
                    161:        private_fragment_payload_t *this)
                    162: {
                    163:        return (this->flags & LAST_FRAGMENT) == LAST_FRAGMENT;
                    164: }
                    165: 
                    166: METHOD(fragment_payload_t, get_data, chunk_t,
                    167:        private_fragment_payload_t *this)
                    168: {
                    169:        return this->data;
                    170: }
                    171: 
                    172: METHOD2(payload_t, fragment_payload_t, destroy, void,
                    173:        private_fragment_payload_t *this)
                    174: {
                    175:        free(this->data.ptr);
                    176:        free(this);
                    177: }
                    178: 
                    179: /*
                    180:  * Described in header
                    181:  */
                    182: fragment_payload_t *fragment_payload_create()
                    183: {
                    184:        private_fragment_payload_t *this;
                    185: 
                    186:        INIT(this,
                    187:                .public = {
                    188:                        .payload_interface = {
                    189:                                .verify = _verify,
                    190:                                .get_encoding_rules = _get_encoding_rules,
                    191:                                .get_header_length = _get_header_length,
                    192:                                .get_length = _get_length,
                    193:                                .get_next_type = _get_next_type,
                    194:                                .set_next_type = _set_next_type,
                    195:                                .get_type = _get_type,
                    196:                                .destroy = _destroy,
                    197:                        },
                    198:                        .get_id = _get_id,
                    199:                        .get_number = _get_number,
                    200:                        .is_last = _is_last,
                    201:                        .get_data = _get_data,
                    202:                        .destroy = _destroy,
                    203:                },
                    204:                .next_payload = PL_NONE,
                    205:        );
                    206:        this->payload_length = get_header_length(this);
                    207:        return &this->public;
                    208: }
                    209: 
                    210: /*
                    211:  * Described in header
                    212:  */
                    213: fragment_payload_t *fragment_payload_create_from_data(uint8_t num, bool last,
                    214:                                                                                                          chunk_t data)
                    215: {
                    216:        private_fragment_payload_t *this;
                    217: 
                    218:        this = (private_fragment_payload_t*)fragment_payload_create();
                    219:        this->fragment_id = 1;
                    220:        this->fragment_number = num;
                    221:        this->flags |= (last ? LAST_FRAGMENT : 0);
                    222:        this->data = chunk_clone(data);
                    223:        this->payload_length = get_header_length(this) + data.len;
                    224:        return &this->public;
                    225: }

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>