Ejemplo n.º 1
0
int ssl3_digest_cached_records(
    SSL *s, enum should_free_handshake_buffer_t should_free_handshake_buffer) {
  int i;
  long mask;
  const EVP_MD *md;
  const uint8_t *hdata;
  size_t hdatalen;

  /* Allocate handshake_dgst array */
  ssl3_free_digest_list(s);
  s->s3->handshake_dgst = OPENSSL_malloc(SSL_MAX_DIGEST * sizeof(EVP_MD_CTX *));
  if (s->s3->handshake_dgst == NULL) {
    OPENSSL_PUT_ERROR(SSL, ssl3_digest_cached_records, ERR_R_MALLOC_FAILURE);
    return 0;
  }

  memset(s->s3->handshake_dgst, 0, SSL_MAX_DIGEST * sizeof(EVP_MD_CTX *));
  if (!BIO_mem_contents(s->s3->handshake_buffer, &hdata, &hdatalen)) {
    OPENSSL_PUT_ERROR(SSL, ssl3_digest_cached_records,
                      SSL_R_BAD_HANDSHAKE_LENGTH);
    return 0;
  }

  /* Loop through bits of algorithm2 field and create MD_CTX-es */
  for (i = 0; ssl_get_handshake_digest(i, &mask, &md); i++) {
    if ((mask & ssl_get_algorithm2(s)) && md) {
      s->s3->handshake_dgst[i] = EVP_MD_CTX_create();
      if (s->s3->handshake_dgst[i] == NULL) {
        OPENSSL_PUT_ERROR(SSL, ssl3_digest_cached_records, ERR_LIB_EVP);
        return 0;
      }
      if (!EVP_DigestInit_ex(s->s3->handshake_dgst[i], md, NULL)) {
        EVP_MD_CTX_destroy(s->s3->handshake_dgst[i]);
        s->s3->handshake_dgst[i] = NULL;
        OPENSSL_PUT_ERROR(SSL, ssl3_digest_cached_records, ERR_LIB_EVP);
        return 0;
      }
      EVP_DigestUpdate(s->s3->handshake_dgst[i], hdata, hdatalen);
    } else {
      s->s3->handshake_dgst[i] = NULL;
    }
  }

  if (should_free_handshake_buffer == free_handshake_buffer) {
    /* Free handshake_buffer BIO */
    BIO_free(s->s3->handshake_buffer);
    s->s3->handshake_buffer = NULL;
  }

  return 1;
}
Ejemplo n.º 2
0
static int test_printf(void) {
  /* Test a short output, a very long one, and various sizes around
   * 256 (the size of the buffer) to ensure edge cases are correct. */
  static const size_t kLengths[] = { 5, 250, 251, 252, 253, 254, 1023 };
  BIO *bio;
  char string[1024];
  int ret;
  const uint8_t *contents;
  size_t i, len;

  bio = BIO_new(BIO_s_mem());
  if (!bio) {
    fprintf(stderr, "BIO_new failed\n");
    return 0;
  }

  for (i = 0; i < sizeof(kLengths) / sizeof(kLengths[0]); i++) {
    if (kLengths[i] >= sizeof(string)) {
      fprintf(stderr, "Bad test string length\n");
      return 0;
    }
    memset(string, 'a', sizeof(string));
    string[kLengths[i]] = '\0';

    ret = BIO_printf(bio, "test %s", string);
    if (ret != 5 + kLengths[i]) {
      fprintf(stderr, "BIO_printf failed: %d\n", ret);
      return 0;
    }
    if (!BIO_mem_contents(bio, &contents, &len)) {
      fprintf(stderr, "BIO_mem_contents failed\n");
      return 0;
    }
    if (len != 5 + kLengths[i] ||
        strncmp((const char *)contents, "test ", 5) != 0 ||
        strncmp((const char *)contents + 5, string, kLengths[i]) != 0) {
      fprintf(stderr, "Contents did not match: %.*s\n", (int)len, contents);
      return 0;
    }

    if (!BIO_reset(bio)) {
      fprintf(stderr, "BIO_reset failed\n");
      return 0;
    }
  }

  BIO_free(bio);
  return 1;
}
Ejemplo n.º 3
0
int ssl3_cert_verify_hash(SSL *s, uint8_t *out, size_t *out_len,
                          const EVP_MD **out_md, EVP_PKEY *pkey) {
  /* For TLS v1.2 send signature algorithm and signature using
   * agreed digest and cached handshake records. Otherwise, use
   * SHA1 or MD5 + SHA1 depending on key type.  */
  if (SSL_USE_SIGALGS(s)) {
    const uint8_t *hdata;
    size_t hdatalen;
    EVP_MD_CTX mctx;
    unsigned len;

    if (!BIO_mem_contents(s->s3->handshake_buffer, &hdata, &hdatalen)) {
      OPENSSL_PUT_ERROR(SSL, ssl3_cert_verify_hash, ERR_R_INTERNAL_ERROR);
      return 0;
    }
    EVP_MD_CTX_init(&mctx);
    if (!EVP_DigestInit_ex(&mctx, *out_md, NULL) ||
        !EVP_DigestUpdate(&mctx, hdata, hdatalen) ||
        !EVP_DigestFinal(&mctx, out, &len)) {
      OPENSSL_PUT_ERROR(SSL, ssl3_cert_verify_hash, ERR_R_EVP_LIB);
      EVP_MD_CTX_cleanup(&mctx);
      return 0;
    }
    *out_len = len;
  } else if (pkey->type == EVP_PKEY_RSA) {
    if (s->enc_method->cert_verify_mac(s, NID_md5, out) == 0 ||
        s->enc_method->cert_verify_mac(s, NID_sha1, out + MD5_DIGEST_LENGTH) ==
            0) {
      return 0;
    }
    *out_len = MD5_DIGEST_LENGTH + SHA_DIGEST_LENGTH;
    *out_md = EVP_md5_sha1();
  } else if (pkey->type == EVP_PKEY_EC) {
    if (s->enc_method->cert_verify_mac(s, NID_sha1, out) == 0) {
      return 0;
    }
    *out_len = SHA_DIGEST_LENGTH;
    *out_md = EVP_sha1();
  } else {
    OPENSSL_PUT_ERROR(SSL, ssl3_cert_verify_hash, ERR_R_INTERNAL_ERROR);
    return 0;
  }

  return 1;
}