Annotation of embedaddon/strongswan/src/libpttls/pt_tls.c, revision 1.1
1.1 ! misho 1: /*
! 2: * Copyright (C) 2012 Martin Willi
! 3: * Copyright (C) 2012 revosec AG
! 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 "pt_tls.h"
! 17:
! 18: #include <utils/debug.h>
! 19: #include <pen/pen.h>
! 20:
! 21: /**
! 22: * Described in header.
! 23: */
! 24: void libpttls_init(void)
! 25: {
! 26: /* empty */
! 27: }
! 28:
! 29: /*
! 30: * PT-TNC Message format:
! 31: * 1 2 3
! 32: * 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
! 33: * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
! 34: * | Reserved | Message Type Vendor ID |
! 35: * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
! 36: * | Message Type |
! 37: * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
! 38: * | Message Length |
! 39: * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
! 40: * | Message Identifier |
! 41: * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
! 42: * | Message Value (e.g. PB-TNC Batch) . . . |
! 43: * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
! 44: */
! 45:
! 46: ENUM(pt_tls_message_type_names, PT_TLS_EXPERIMENTAL, PT_TLS_ERROR,
! 47: "Experimental",
! 48: "Version Request",
! 49: "Version Response",
! 50: "SASL Mechanisms",
! 51: "SASL Mechanism Selection",
! 52: "SASL Authentication Data",
! 53: "SASL Result",
! 54: "PB-TNC Batch",
! 55: "PT-TLS Error"
! 56: );
! 57:
! 58: ENUM(pt_tls_sasl_result_names, PT_TLS_SASL_RESULT_SUCCESS,
! 59: PT_TLS_SASL_RESULT_MECH_FAILURE,
! 60: "Success",
! 61: "Failure",
! 62: "Abort",
! 63: "Mechanism Failure"
! 64: );
! 65:
! 66: /**
! 67: * Read a chunk of data from TLS, returning a reader for it
! 68: */
! 69: static bio_reader_t* read_tls(tls_socket_t *tls, size_t len)
! 70: {
! 71: ssize_t got, total = 0;
! 72: char *buf;
! 73:
! 74: buf = malloc(len);
! 75: while (total < len)
! 76: {
! 77: got = tls->read(tls, buf + total, len - total, TRUE);
! 78: if (got <= 0)
! 79: {
! 80: free(buf);
! 81: return NULL;
! 82: }
! 83: total += got;
! 84: }
! 85: return bio_reader_create_own(chunk_create(buf, len));
! 86: }
! 87:
! 88: /**
! 89: * Read a PT-TLS message, return header data
! 90: */
! 91: bio_reader_t* pt_tls_read(tls_socket_t *tls, uint32_t *vendor,
! 92: uint32_t *type, uint32_t *identifier)
! 93: {
! 94: bio_reader_t *reader;
! 95: uint32_t len;
! 96: uint8_t reserved;
! 97:
! 98: reader = read_tls(tls, PT_TLS_HEADER_LEN);
! 99: if (!reader)
! 100: {
! 101: return NULL;
! 102: }
! 103: if (!reader->read_uint8(reader, &reserved) ||
! 104: !reader->read_uint24(reader, vendor) ||
! 105: !reader->read_uint32(reader, type) ||
! 106: !reader->read_uint32(reader, &len) ||
! 107: !reader->read_uint32(reader, identifier))
! 108: {
! 109: reader->destroy(reader);
! 110: return NULL;
! 111: }
! 112: reader->destroy(reader);
! 113:
! 114: if (len < PT_TLS_HEADER_LEN)
! 115: {
! 116: DBG1(DBG_TNC, "received short PT-TLS header (%d bytes)", len);
! 117: return NULL;
! 118: }
! 119:
! 120: if (*vendor == PEN_IETF)
! 121: {
! 122: DBG2(DBG_TNC, "received PT-TLS message #%d of type '%N' (%d bytes)",
! 123: *identifier, pt_tls_message_type_names, *type, len);
! 124: }
! 125: else
! 126: {
! 127: DBG2(DBG_TNC, "received PT-TLS message #%d of unknown type "
! 128: "0x%06x/0x%08x (%d bytes)",
! 129: *identifier, *vendor, *type, len);
! 130: }
! 131:
! 132: return read_tls(tls, len - PT_TLS_HEADER_LEN);
! 133: }
! 134:
! 135: /**
! 136: * Prepend a PT-TLS header to a writer, send data, destroy writer
! 137: */
! 138: bool pt_tls_write(tls_socket_t *tls, pt_tls_message_type_t type,
! 139: uint32_t identifier, chunk_t data)
! 140: {
! 141: bio_writer_t *writer;
! 142: chunk_t out;
! 143: ssize_t len;
! 144:
! 145: len = PT_TLS_HEADER_LEN + data.len;
! 146: writer = bio_writer_create(len);
! 147:
! 148: /* write PT-TLS header */
! 149: writer->write_uint8 (writer, 0);
! 150: writer->write_uint24(writer, 0);
! 151: writer->write_uint32(writer, type);
! 152: writer->write_uint32(writer, len);
! 153: writer->write_uint32(writer, identifier);
! 154:
! 155: /* write PT-TLS body */
! 156: writer->write_data(writer, data);
! 157:
! 158: DBG2(DBG_TNC, "sending PT-TLS message #%d of type '%N' (%d bytes)",
! 159: identifier, pt_tls_message_type_names, type, len);
! 160:
! 161: out = writer->get_buf(writer);
! 162: len = tls->write(tls, out.ptr, out.len);
! 163: writer->destroy(writer);
! 164:
! 165: return len == out.len;
! 166: }
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>