示例#1
0
/* This can be used for SHA1, SHA256 and SHA224 */
void ccdigest_final_64be(const struct ccdigest_info *di, ccdigest_ctx_t ctx,
                         unsigned char *digest) {
    ccdigest_nbits(di, ctx) += ccdigest_num(di, ctx) * 8;
    ccdigest_data(di, ctx)[ccdigest_num(di, ctx)++] = 0x80;

    /* If we don't have at least 8 bytes (for the length) left we need to add
     a second block. */
    if (ccdigest_num(di, ctx) > 64 - 8) {
        while (ccdigest_num(di, ctx) < 64) {
            ccdigest_data(di, ctx)[ccdigest_num(di, ctx)++] = 0;
        }
        di->compress(ccdigest_state(di, ctx), 1, ccdigest_data(di, ctx));
        ccdigest_num(di, ctx) = 0;
    }

    /* pad upto block_size minus 8 with 0s */
    while (ccdigest_num(di, ctx) < 64 - 8) {
        ccdigest_data(di, ctx)[ccdigest_num(di, ctx)++] = 0;
    }

    CC_STORE64_BE(ccdigest_nbits(di, ctx), ccdigest_data(di, ctx) + 64 - 8);
    di->compress(ccdigest_state(di, ctx), 1, ccdigest_data(di, ctx));

    /* copy output */
    for (unsigned int i = 0; i < di->output_size / 4; i++) {
        CC_STORE32_BE(ccdigest_state_u32(di, ctx)[i], digest+(4*i));
    }
}
void ccsha512_final(const struct ccdigest_info *di, ccdigest_ctx_t ctx,
                    unsigned char *digest) {
    ccdigest_nbits(di, ctx) += ccdigest_num(di, ctx) << 3;
    ccdigest_data(di, ctx)[ccdigest_num(di, ctx)++] = 0x80;

    /* If we don't have at least 16 bytes (for the length) left we need to add
       a second block. */
    if (ccdigest_num(di, ctx) > di->block_size - 16) {
        while (ccdigest_num(di, ctx) < di->block_size) {
            ccdigest_data(di, ctx)[ccdigest_num(di, ctx)++] = 0;
        }
        di->compress(ccdigest_state(di, ctx), 1, ccdigest_data(di, ctx));
        ccdigest_num(di, ctx) = 0;
    }

    /* Pad up to block_size minus 8 with 0s */
    while (ccdigest_num(di, ctx) < di->block_size - 8) {
        ccdigest_data(di, ctx)[ccdigest_num(di, ctx)++] = 0;
    }

    CC_STORE64_BE(ccdigest_nbits(di, ctx), ccdigest_data(di, ctx) + di->block_size - 8);
    di->compress(ccdigest_state(di, ctx), 1, ccdigest_data(di, ctx));

    /* Copy output */
    for (unsigned int i = 0; i < di->output_size / 8; i++) {
        CC_STORE64_BE(ccdigest_state_u64(di, ctx)[i], digest+(8*i));
    }
}
示例#3
0
void ccdigest_update(const struct ccdigest_info *di, ccdigest_ctx_t ctx,
                     unsigned long len, const void *data) {
    const char * data_ptr = data;
    while (len > 0) {
        if (ccdigest_num(di, ctx) == 0 && len > di->block_size) {
            unsigned long nblocks = len / di->block_size;
            di->compress(ccdigest_state(di, ctx), nblocks, data_ptr);
            unsigned long nbytes = nblocks * di->block_size;
            len -= nbytes;
            data_ptr += nbytes;
            ccdigest_nbits(di, ctx) += nbytes * 8;
        } else {
            unsigned long n = di->block_size - ccdigest_num(di, ctx);
            if (len < n)
                n = len;
            CC_MEMCPY(ccdigest_data(di, ctx) + ccdigest_num(di, ctx), data_ptr, n);
            /* typecast: less than block size, will always fit into an int */
            ccdigest_num(di, ctx) += (unsigned int)n;
            len -= n;
            data_ptr += n;
            if (ccdigest_num(di, ctx) == di->block_size) {
                di->compress(ccdigest_state(di, ctx), 1, ccdigest_data(di, ctx));
                ccdigest_nbits(di, ctx) += ccdigest_num(di, ctx) * 8;
                ccdigest_num(di, ctx) = 0;
            }
        }
    }
}
void ccdigest_init(const struct ccdigest_info *di, ccdigest_ctx_t ctx) {
    ccdigest_copy_state(di, ccdigest_state_ccn(di, ctx), di->initial_state);
    ccdigest_nbits(di, ctx) = 0;
    ccdigest_num(di, ctx) = 0;
}