summaryrefslogtreecommitdiff
path: root/plugins/CryptoPP/crypto/blumshub.cpp
blob: 6ab2209925745e21464840f58e2cc415d863022d (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
// blumshub.cpp - written and placed in the public domain by Wei Dai

#include "pch.h"
#include "blumshub.h"

NAMESPACE_BEGIN(CryptoPP)

PublicBlumBlumShub::PublicBlumBlumShub(const Integer &n, const Integer &seed)
	: modn(n),
	  maxBits(BitPrecision(n.BitCount())-1)
{
	current = modn.Square(modn.Square(seed));
	bitsLeft = maxBits;
}

unsigned int PublicBlumBlumShub::GenerateBit()
{
	if (bitsLeft==0)
	{
		current = modn.Square(current);
		bitsLeft = maxBits;
	}

	return current.GetBit(--bitsLeft);
}

byte PublicBlumBlumShub::GenerateByte()
{
	byte b=0;
	for (int i=0; i<8; i++)
		b = (b << 1) | PublicBlumBlumShub::GenerateBit();
	return b;
}

void PublicBlumBlumShub::GenerateBlock(byte *output, size_t size)
{
	while (size--)
		*output++ = PublicBlumBlumShub::GenerateByte();
}

void PublicBlumBlumShub::ProcessData(byte *outString, const byte *inString, size_t length)
{
	while (length--)
		*outString++ = *inString++ ^ PublicBlumBlumShub::GenerateByte();
}

BlumBlumShub::BlumBlumShub(const Integer &p, const Integer &q, const Integer &seed)
	: PublicBlumBlumShub(p*q, seed),
	  p(p), q(q),
	  x0(modn.Square(seed))
{
}

void BlumBlumShub::Seek(lword index)
{
	Integer i(Integer::POSITIVE, index);
	i *= 8;
	Integer e = a_exp_b_mod_c (2, i / maxBits + 1, (p-1)*(q-1));
	current = modn.Exponentiate(x0, e);
	bitsLeft = maxBits - i % maxBits;
}

NAMESPACE_END