Author: tjansen Date: Mon Nov 9 12:25:13 2009 New Revision: 1588 Log: Added doxygen documentation for the libinet6 replacement code. Modified: trunk/community-operator/hipl.c Modified: trunk/community-operator/hipl.c ============================================================================== --- trunk/community-operator/hipl.c Sun Nov 8 15:18:36 2009 (r1587) +++ trunk/community-operator/hipl.c Mon Nov 9 12:25:13 2009 (r1588) @@ -14,8 +14,18 @@ #include <unistd.h> #include <netinet/in.h> +/* Most of the following code is a reimplementation of libinet6 functionality + * from HIPL. The code is very specialized and *not* intended to be a complete + * implementation for the general purpose of building arbitrary HIP packages. + * + * The two goals of this implementation are: + * 1) Building and signing a certificate + * 2) Finding out the default HIT of the local hipd + */ + #define HIP_MAX_PACKET 4096 +/* HIP header structure, network byte order */ typedef struct { uint8_t payload_proto; uint8_t payload_len; @@ -27,11 +37,17 @@ struct in6_addr hitr; } __attribute__ ((packed)) hip_common; +/* HIP attribute header structure, network byte order */ typedef struct { uint16_t type; uint16_t length; } __attribute__ ((packed)) hip_tlv_common; +/** + * Allocate a new HIP message. + * + * @return pointer to a new, zero-initialized chunk of memory + */ static hip_common *hip_msg_alloc(void) { hip_common *msg = malloc(HIP_MAX_PACKET); @@ -40,16 +56,36 @@ return msg; } +/** + * Free a HIP message. + * + * @param msg HIP message to be freed + */ static void hip_msg_free(hip_common *msg) { free(msg); } +/** + * Set the total length of a HIP packet. + * + * @param msg HIP message + */ static void hip_set_msg_total_len(hip_common *msg, uint16_t len) { msg->payload_len = (len < 8) ? 0 : ((len >> 3) - 1); } +/** + * Initialize a new packet. This has to be the first function called after + * hip_msg_alloc as we reset the packet size to indicate that no parameter has + * been added yet. + * + * @param msg HIP message + * @param base_type HIP message type + * @param err_val HIP message error, typically 0 + * return 0 on success, -1 otherwise + */ static int hip_build_user_hdr(hip_common *msg, uint8_t base_type, uint16_t err_val) { if (!msg) @@ -62,6 +98,12 @@ return 0; } +/** + * Get the total length of a HIP packet. + * + * @param msg HIP message + * @return length of the message in bytes + */ static int hip_get_msg_total_len(hip_common *msg) { return (msg->payload_len == 0) ? 0 : ((msg->payload_len + 1) << 3); @@ -70,11 +112,24 @@ #define HIP_LEN_PAD(len) \ ((((len) & 0x07) == 0) ? (len) : ((((len) >> 3) << 3) + 8)) +/** + * Get the padded length of a HIP message parameter. + * + * @param tlv HIP message parameter + * @return padded length in bytes + */ static uint16_t hip_get_param_total_len(const hip_tlv_common *tlv) { return HIP_LEN_PAD(sizeof(hip_tlv_common) + ntohs(tlv->length)); } +/** + * Sanity check if a new parameter fits into a message. + * + * @param msg HIP message + * @param param HIP message parameter + * @return 0 if the parameter does not fit, 1 if the parameter fits + */ static int hip_check_param_contents_len(hip_common *msg, hip_tlv_common *param) { int len = hip_get_param_total_len(param); @@ -90,11 +145,25 @@ return 1; } +/** + * Get the non-padded length of a HIP message parameter. + * + * @param param HIP message parameter + * @return length in bytes + */ static int hip_get_param_contents_len(hip_tlv_common *param) { return ntohs(param->length); } +/** + * Get the next HIP message parameter from a HIP message. If cur is NULL, the + * first parameter is returned. + * + * @param msg HIP message + * @param cur current HIP message parameter + * @return next HIP message parameter or NULL, if no next parameter exists + */ static hip_tlv_common *hip_get_next_param(hip_common *msg, hip_tlv_common *cur) { hip_tlv_common *next = NULL; @@ -116,6 +185,14 @@ return next; } +/** + * Get the first HIP message parameter of a given type. + * + * @param msg HIP message + * @param type desired parameter type + * @return first HIP message parameter of that type or NULL, if no such + * parameter exists + */ static hip_tlv_common *hip_get_param(hip_common *msg, uint16_t type) { hip_tlv_common *cur = NULL; @@ -128,11 +205,25 @@ return NULL; } +/** + * Get the contents of a HIP message parameter. We skip the common TLV header. + * + * @param param HIP message parameter + * @retrun parameter content + */ static void *hip_get_param_contents_direct(hip_tlv_common *param) { return (void*)(param + 1); } +/** + * Bind the socket to a port. We try to get a privileged port first as signing + * a certificate requires a privileged port. + * + * @param sock socket file descriptor + * @param addr IPv6 socket address, filled out except for the port + * @return 0 on success, -1 otherwise + */ static int hip_bind(int sock, struct sockaddr_in6 *addr) { int port = 1000; @@ -158,6 +249,15 @@ #define HIP_DAEMON_LOCAL_PORT 973 +/** + * Send a HIP message to the HIP daemon and wait for an answer. + * + * TODO: This function blocks indefinitely if we get no answer, implement a + * timeout mechanism, e.g. select(). + * + * @param msg HIP message + * @return 0 on success, -1 otherwise + */ static int hip_send_recv(hip_common *msg) { int sock = 0, on = 1, len, result = -1; @@ -191,6 +291,7 @@ if (send(sock, msg, len, 0) < len) goto err; + /* TODO: timeout mechanism */ if (recv(sock, msg, HIP_MAX_PACKET, 0) < 0) goto err; @@ -215,6 +316,16 @@ #define SO_HIP_CERT_SPKI_SIGN 141 #define HIP_PARAM_CERT_SPKI_INFO 32794 +/** + * Append a HIP message parameter to a HIP message. + * + * TODO: Check the bounds of the message to see if the new parameter is too + * long to fit. + * + * @param msg HIP message + * @param param HIP message parameter + * @return 0 on success, -1 otherwise + */ static int hip_param_append(hip_common *msg, hip_tlv_common *param) { hip_tlv_common *cur = NULL, *append = NULL; @@ -239,6 +350,13 @@ return 0; } +/** + * Build a cert SPKI parameter. + * + * @param msg HIP message + * @param cert_info certificate info that will be inserted + * @return 0 on success, -1 otherwise + */ static int hip_build_param_cert_spki_info(hip_common *msg, hip_cert_spki_info *cert_info) { @@ -251,6 +369,18 @@ return 0; } +/** + * Create a certificate info structure. + * + * @param content destination buffer for the certificate info + * @param issuer_type type of the issuer information, typically "hit" + * @param issuer HIT of the issuer + * @param subject_type type of the subject information, typically "hit" + * @param subject HIT of the subject + * @param not_before the certificate is only valid after this point in time + * @param not_after the certificate is only valid before this point in time + * @return 0 on success, -1 otherwise + */ static int hip_cert_spki_create_cert(hip_cert_spki_info *content, const char * issuer_type, struct in6_addr * issuer, @@ -308,6 +438,17 @@ return result; } +/** + * Create a certificate signed by the HIP daemon. + * + * @param not_before the certificate is only valid after this point in time + * @param not_after the certificate is only valid before this point in time + * @param hit HIT of the subject + * @param issuer_hit HIT of the issuer + * @param certificate destination buffer to hold the signed certificate + * @param size size of the destination buffer + * @return 0 on success, -1 otherwise + */ int create_certificate(time_t *not_before, time_t *not_after, struct in6_addr *hit, struct in6_addr *issuer_hit, char *certificate, size_t size) @@ -332,6 +473,12 @@ #define SO_HIP_DEFAULT_HIT 16 #define HIP_PARAM_HIT 32768 +/** + * Get the default HIT of the local HIP daemon. + * + * @param result destination buffer + * @return 0 on success, -1 otherwise + */ int get_default_hit(struct in6_addr *result) { hip_common *msg = NULL;