On Mon, Mar 12, 2012 at 09:29:29PM +0100, Diego Biurrun wrote: > On Thu, Mar 08, 2012 at 06:41:47PM +0100, Diego Biurrun wrote: > > On Fri, Mar 02, 2012 at 06:08:20PM +0000, Diego Biurrun wrote: > > > Diego Biurrun has proposed merging > > > lp:~hipl-core/hipl/certificate-exchange into lp:hipl. > > > > > > --- hipd/cert.c 2012-03-01 14:06:24 +0000 > > > +++ hipd/cert.c 2012-03-02 18:07:40 +0000 > > > > The functions in this file are HUUUUGE - IMO this needs some refactoring. > > Any volunteers? The original authors maybe? I still don't really > understand the "big picture" of this branch. Left for never^wlater. > > > --- lib/core/cert.c 1970-01-01 00:00:00 +0000 > > > +++ lib/core/cert.c 2012-03-02 18:07:40 +0000 > > > @@ -0,0 +1,292 @@ > > > +/** > > > + * Load a X509 certificate from @ file. If @ file contains more > > > + * than one certificate, the certificate at the top of the file is > > > + * returned. > > > + * > > > + * @param file the file to load the certficate from > > > + * @param fmt the input format of the certificate > > > + * > > > + * @return a X509 certificate on success, NULL on error > > > + */ > > > +X509 *cert_load_x509_certificate(const char *const file, > > > + enum encoding_format fmt) > > > +{ > > > + FILE *fp = NULL; > > > + X509 *cert = NULL; > > > + > > > + if (!file) { > > > + HIP_ERROR("Cannot read certificate from NULL-filename.\n"); > > > + return NULL; > > > + } > > > + > > > + fp = fopen(file, "rb"); > > > + if (!fp) { > > > + HIP_ERROR("Could not open file for reading: %s\n", file); > > > + return NULL; > > > + } > > > + > > > + if (fmt == ENCODING_FORMAT_PEM) { > > > + cert = PEM_read_X509(fp, NULL, NULL, NULL); > > > + } else if (fmt == ENCODING_FORMAT_DER) { > > > + cert = d2i_X509_fp(fp, NULL); > > > + } else { > > > + HIP_ERROR("Invalid encoding format %i \n", fmt); > > > + return NULL; > > > + } > > > > switch/case? Might more formats get added here? > > Anybody? Converted to switch/case, looks nicer at least. > > > + if (fclose(fp)) { > > > + HIP_ERROR("Error closing file: %s\n", file); > > > + X509_free(cert); > > > + return NULL; > > > + } else if (!cert) { > > > + HIP_ERROR("Could not decode certificate from file.\n"); > > > + return NULL; > > > + } > > > + > > > + return cert; > > > +} > > > > If I read this correctly, fp will not get closed on encountering an > > invalid encoding format. > > Is my assessment correct? It is correct, function logic fixed on branch. > > > +/** > > > + * Search for hip_cert parameter in @ msg and try to decode the data in > > > + * the first certificate parameter of a X509 certificate. > > > + * > > > + * @param msg the message to extract the certificate from > > > + * > > > + * @return the first X509 certificate found in the message on > > > success, > > > + * NULL on error and if no certificates were found > > > + */ > > > +X509 *cert_get_X509_from_msg(const struct hip_common *const msg) > > > +{ > > > + const struct hip_cert *param_cert = NULL; > > > + > > > + if (!(param_cert = hip_get_param(msg, HIP_PARAM_CERT))) { > > > + HIP_ERROR("Message contains no certificate.\n"); > > > + return NULL; > > > + } > > > + > > > + /* The contents of the certificate begin after the header of the > > > + * hip_cert parameter. */ > > > + return cert_DER_to_X509((const unsigned char *) (param_cert + 1), > > > + ntohs(param_cert->length) - > > > + sizeof(struct hip_cert) + > > > + sizeof(struct hip_tlv_common)); > > > +} > > > > What is "param_cert + 1" supposed to be? Are you trying to move the > > pointer past the struct? This is extremely brittle, see the cast > > and the length calculation that are necessary. > > I'm still mystified about this one. Christoph confirms the intention. Repairing this likely entails quite a bit of fiddling with structures. > > > --- lib/core/conf.c 2012-01-13 16:25:15 +0000 > > > +++ lib/core/conf.c 2012-03-02 18:07:40 +0000 > > > @@ -2424,6 +2435,122 @@ > > > > > > /** > > > + * Utility function which compactly checks whether a string represents > > > + * a positive natural number, since scanf() is too lenient. > > > + * > > > + * @param string NULL-terminated string to be checked > > > + * > > > + * @return 1 if the only characters in the string are digits, > > > + * optionally with one leading '+' sign; 0 otherwise > > > + */ > > > +static int is_pos_natural_number(const char *string) > > > +{ > > > + if (string) { > > > + size_t len; > > > + > > > + // allow one leading '+' > > > + if (string[0] == '+') { > > > + string++; > > > + } > > > + > > > + if ((len = strlen(string)) > 0) { > > > + for (size_t i = 0; i < len; i++) { > > > + if (string[i] < '0' || string[i] > '9') { > > > + return 0; > > > + } > > > + } > > > + return 1; > > > + } > > > + } > > > + return 0; > > > +} > > > + > > > +static int conf_handle_certificate(struct hip_common *msg, > > > + int action, > > > + const char *opt[], > > > + int optc, > > > + UNUSED int send_only) > > > +{ > > > + hip_hit_t subject_hit; > > > + uint32_t valid_until_h = 0, valid_until_n = > > > 0; > > > + int scanf_res = 0, err = 0; > > > + X509 *cert = NULL; > > > + const struct hip_cert_x509_resp *p = NULL; > > > + > > > + > > > + /* convert the parameter strings input by the user into the > > > + * appropriate binary formats for further processing */ > > > + const int pton_res = inet_pton(AF_INET6, opt[0], &subject_hit); > > > + > > > + if (optc == 2 && is_pos_natural_number(opt[1])) { > > > > OK, what exactly is the problem here? Why do you need the utility function? > > Can the original author shed some light on this? Christoph said scanf did not work for him. I guess we'll trust his word. Diego