Return to transform_attribute.c CVS log | Up to [ELWIX - Embedded LightWeight unIX -] / embedaddon / strongswan / src / libcharon / encoding / payloads |
1.1 misho 1: /* 2: * Copyright (C) 2005-2010 Martin Willi 3: * Copyright (C) 2010 revosec AG 4: * Copyright (C) 2005 Jan Hutter 5: * HSR Hochschule fuer Technik Rapperswil 6: * 7: * This program is free software; you can redistribute it and/or modify it 8: * under the terms of the GNU General Public License as published by the 9: * Free Software Foundation; either version 2 of the License, or (at your 10: * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>. 11: * 12: * This program is distributed in the hope that it will be useful, but 13: * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 14: * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 15: * for more details. 16: */ 17: 18: #include <string.h> 19: #include <stddef.h> 20: #include <stdint.h> 21: 22: #include "transform_attribute.h" 23: 24: #include <encoding/payloads/encodings.h> 25: #include <library.h> 26: 27: ENUM(tattr_ph1_names, TATTR_PH1_ENCRYPTION_ALGORITHM, TATTR_PH1_GROUP_ORDER, 28: "ENCRYPTION_ALGORITHM", 29: "HASH_ALGORITHM", 30: "AUTH_METHOD", 31: "GROUP", 32: "GROUP_TYPE", 33: "GROUP_PRIME", 34: "GROUP_GENONE", 35: "GROUP_GENTWO", 36: "GROUP_CURVE_A", 37: "GROUP_CURVE_B", 38: "LIFE_TYPE", 39: "LIFE_DURATION", 40: "PRF", 41: "KEY_LENGTH", 42: "FIELD_SIZE", 43: "GROUP_ORDER", 44: ); 45: 46: ENUM(tattr_ph2_names, TATTR_PH2_SA_LIFE_TYPE, TATTR_PH2_EXT_SEQ_NUMBER, 47: "SA_LIFE_TYPE", 48: "SA_LIFE_DURATION", 49: "GROUP", 50: "ENCAP_MODE", 51: "AUTH_ALGORITHM", 52: "KEY_LENGTH", 53: "KEY_ROUNDS", 54: "COMP_DICT_SIZE", 55: "COMP_PRIV_ALGORITHM", 56: "ECN_TUNNEL", 57: "EXT_SEQ_NUMBER", 58: ); 59: 60: ENUM(tattr_ikev2_names, TATTR_IKEV2_KEY_LENGTH, TATTR_IKEV2_KEY_LENGTH, 61: "KEY_LENGTH", 62: ); 63: 64: 65: typedef struct private_transform_attribute_t private_transform_attribute_t; 66: 67: /** 68: * Private data of an transform_attribute_t object. 69: */ 70: struct private_transform_attribute_t { 71: 72: /** 73: * Public transform_attribute_t interface. 74: */ 75: transform_attribute_t public; 76: 77: /** 78: * Attribute Format Flag. 79: * 80: * - TRUE means value is stored in attribute_length_or_value 81: * - FALSE means value is stored in attribute_value 82: */ 83: bool attribute_format; 84: 85: /** 86: * Type of the attribute. 87: */ 88: uint16_t attribute_type; 89: 90: /** 91: * Attribute Length if attribute_format is 0, attribute Value otherwise. 92: */ 93: uint16_t attribute_length_or_value; 94: 95: /** 96: * Attribute value as chunk if attribute_format is 0 (FALSE). 97: */ 98: chunk_t attribute_value; 99: 100: /** 101: * Payload type, PLV2_TRANSFORM_ATTRIBUTE or PLV1_TRANSFORM_ATTRIBUTE 102: */ 103: payload_type_t type; 104: }; 105: 106: /** 107: * Encoding rules for IKEv1/IKEv2 transform attributes 108: */ 109: static encoding_rule_t encodings[] = { 110: /* Flag defining the format of this payload */ 111: { ATTRIBUTE_FORMAT, offsetof(private_transform_attribute_t, attribute_format) }, 112: /* type of the attribute as 15 bit unsigned integer */ 113: { ATTRIBUTE_TYPE, offsetof(private_transform_attribute_t, attribute_type) }, 114: /* Length or value, depending on the attribute format flag */ 115: { ATTRIBUTE_LENGTH_OR_VALUE,offsetof(private_transform_attribute_t, attribute_length_or_value) }, 116: /* Value of attribute if attribute format flag is zero */ 117: { ATTRIBUTE_VALUE, offsetof(private_transform_attribute_t, attribute_value) } 118: }; 119: 120: /* 121: 1 2 3 122: 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 123: +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 124: !A! Attribute Type ! AF=0 Attribute Length ! 125: !F! ! AF=1 Attribute Value ! 126: +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 127: ! AF=0 Attribute Value ! 128: ! AF=1 Not Transmitted ! 129: +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 130: */ 131: 132: METHOD(payload_t, verify, status_t, 133: private_transform_attribute_t *this) 134: { 135: return SUCCESS; 136: } 137: 138: METHOD(payload_t, get_encoding_rules, int, 139: private_transform_attribute_t *this, encoding_rule_t **rules) 140: { 141: *rules = encodings; 142: return countof(encodings); 143: } 144: 145: METHOD(payload_t, get_header_length, int, 146: private_transform_attribute_t *this) 147: { 148: return 0; 149: } 150: 151: METHOD(payload_t, get_type, payload_type_t, 152: private_transform_attribute_t *this) 153: { 154: return this->type; 155: } 156: 157: METHOD(payload_t, get_next_type, payload_type_t, 158: private_transform_attribute_t *this) 159: { 160: return PL_NONE; 161: } 162: 163: METHOD(payload_t, set_next_type, void, 164: private_transform_attribute_t *this, payload_type_t type) 165: { 166: } 167: 168: METHOD(payload_t, get_length, size_t, 169: private_transform_attribute_t *this) 170: { 171: if (this->attribute_format) 172: { 173: return 4; 174: } 175: return this->attribute_length_or_value + 4; 176: } 177: 178: METHOD(transform_attribute_t, get_value_chunk, chunk_t, 179: private_transform_attribute_t *this) 180: { 181: if (this->attribute_format) 182: { 183: return chunk_from_thing(this->attribute_length_or_value); 184: } 185: return this->attribute_value; 186: } 187: 188: METHOD(transform_attribute_t, get_value, uint64_t, 189: private_transform_attribute_t *this) 190: { 191: uint64_t value = 0; 192: 193: if (this->attribute_format) 194: { 195: return this->attribute_length_or_value; 196: } 197: if (this->attribute_value.len > sizeof(value)) 198: { 199: return UINT64_MAX; 200: } 201: memcpy(((char*)&value) + sizeof(value) - this->attribute_value.len, 202: this->attribute_value.ptr, this->attribute_value.len); 203: return untoh64((char*)&value); 204: } 205: 206: METHOD(transform_attribute_t, get_attribute_type, uint16_t, 207: private_transform_attribute_t *this) 208: { 209: return this->attribute_type; 210: } 211: 212: METHOD2(payload_t, transform_attribute_t, destroy, void, 213: private_transform_attribute_t *this) 214: { 215: free(this->attribute_value.ptr); 216: free(this); 217: } 218: 219: /* 220: * Described in header. 221: */ 222: transform_attribute_t *transform_attribute_create(payload_type_t type) 223: { 224: private_transform_attribute_t *this; 225: 226: INIT(this, 227: .public = { 228: .payload_interface = { 229: .verify = _verify, 230: .get_encoding_rules = _get_encoding_rules, 231: .get_header_length = _get_header_length, 232: .get_length = _get_length, 233: .get_next_type = _get_next_type, 234: .set_next_type = _set_next_type, 235: .get_type = _get_type, 236: .destroy = _destroy, 237: }, 238: .get_value_chunk = _get_value_chunk, 239: .get_value = _get_value, 240: .get_attribute_type = _get_attribute_type, 241: .destroy = _destroy, 242: }, 243: .attribute_format = FALSE, 244: .type = type, 245: ); 246: return &this->public; 247: } 248: 249: /* 250: * Described in header. 251: */ 252: transform_attribute_t *transform_attribute_create_value(payload_type_t type, 253: transform_attribute_type_t kind, uint64_t value) 254: { 255: private_transform_attribute_t *this; 256: 257: this = (private_transform_attribute_t*)transform_attribute_create(type); 258: 259: this->attribute_type = kind & 0x7FFF; 260: 261: if (value <= UINT16_MAX) 262: { 263: this->attribute_length_or_value = value; 264: this->attribute_format = TRUE; 265: } 266: else if (value <= UINT32_MAX) 267: { 268: uint32_t val32; 269: 270: val32 = htonl(value); 271: this->attribute_value = chunk_clone(chunk_from_thing(val32)); 272: this->attribute_length_or_value = sizeof(val32); 273: } 274: else 275: { 276: htoun64(&value, value); 277: this->attribute_value = chunk_clone(chunk_from_thing(value)); 278: this->attribute_length_or_value = sizeof(value); 279: } 280: return &this->public; 281: }