Exemplo n.º 1
0
static inline u_int64_t
getblock64(const u_int64_t *p, int i)
{
	const u_int8_t *bytes = (const u_int8_t *)(void *)(uintptr_t)(p + i);
	u_int64_t value;

	if (ALIGNED64(p)) {
		value = p[i];
	} else {
#if BYTE_ORDER == BIG_ENDIAN
		value =
		    (((u_int64_t)bytes[0]) << 56) |
		    (((u_int64_t)bytes[1]) << 48) |
		    (((u_int64_t)bytes[2]) << 40) |
		    (((u_int64_t)bytes[3]) << 32) |
		    (((u_int64_t)bytes[4]) << 24) |
		    (((u_int64_t)bytes[5]) << 16) |
		    (((u_int64_t)bytes[6]) << 8) |
		    ((u_int64_t)bytes[7]);
#else /* LITTLE_ENDIAN */
		value =
		    (((u_int64_t)bytes[7]) << 56) |
		    (((u_int64_t)bytes[6]) << 48) |
		    (((u_int64_t)bytes[5]) << 40) |
		    (((u_int64_t)bytes[4]) << 32) |
		    (((u_int64_t)bytes[3]) << 24) |
		    (((u_int64_t)bytes[2]) << 16) |
		    (((u_int64_t)bytes[1]) << 8) |
		    ((u_int64_t)bytes[0]);
#endif /* LITTLE_ENDIAN */
	}
	return (value);
}
Exemplo n.º 2
0
void cryptonite_chacha_generate(uint8_t *dst, cryptonite_chacha_context *ctx, uint32_t bytes)
{
    cryptonite_chacha_state *st;
    block out;
    int i;

    if (!bytes)
        return;

    /* xor the previous buffer first (if any) */
    if (ctx->prev_len > 0) {
        int to_copy = (ctx->prev_len < bytes) ? ctx->prev_len : bytes;
        for (i = 0; i < to_copy; i++)
            dst[i] = ctx->prev[ctx->prev_ofs+i];
        memset(ctx->prev + ctx->prev_ofs, 0, to_copy);
        ctx->prev_len -= to_copy;
        ctx->prev_ofs += to_copy;
        dst += to_copy;
        bytes -= to_copy;
    }

    if (bytes == 0)
        return;

    st = &ctx->st;

    if (ALIGNED64(dst)) {
        /* xor new 64-bytes chunks and store the left over if any */
        for (; bytes >= 64; bytes -= 64, dst += 64) {
            /* generate new chunk and update state */
            chacha_core(ctx->nb_rounds, (block *) dst, st);
            st->d[12] += 1;
            if (st->d[12] == 0)
                st->d[13] += 1;
        }
    } else {
        /* xor new 64-bytes chunks and store the left over if any */
        for (; bytes >= 64; bytes -= 64, dst += 64) {
            /* generate new chunk and update state */
            chacha_core(ctx->nb_rounds, &out, st);
            st->d[12] += 1;
            if (st->d[12] == 0)
                st->d[13] += 1;

            for (i = 0; i < 64; ++i)
                dst[i] = out.b[i];
        }
    }

    if (bytes > 0) {
        /* generate new chunk and update state */
        chacha_core(ctx->nb_rounds, &out, st);
        st->d[12] += 1;
        if (st->d[12] == 0)
            st->d[13] += 1;

        /* xor as much as needed */
        for (i = 0; i < bytes; i++)
            dst[i] = out.b[i];

        /* copy the left over in the buffer */
        ctx->prev_len = 64 - bytes;
        ctx->prev_ofs = i;
        for (; i < 64; i++)
            ctx->prev[i] = out.b[i];
    }
}