blob: 42d4457eeab48d216d0dfa9fdb1931af43b3dc89 [file] [log] [blame]
#include <u.h>
#include <libc.h>
#include <bio.h>
#define ptsiz (sizeof(pt)/sizeof(pt[0]))
#define whsiz (sizeof(wheel)/sizeof(wheel[0]))
#define tabsiz (sizeof(table)/sizeof(table[0]))
#define tsiz8 (tabsiz*8)
double big = 9.007199254740992e15;
int pt[] =
{
2, 3, 5, 7, 11, 13, 17, 19, 23, 29,
31, 37, 41, 43, 47, 53, 59, 61, 67, 71,
73, 79, 83, 89, 97,101,103,107,109,113,
127,131,137,139,149,151,157,163,167,173,
179,181,191,193,197,199,211,223,227,229,
};
double wheel[] =
{
10, 2, 4, 2, 4, 6, 2, 6, 4, 2,
4, 6, 6, 2, 6, 4, 2, 6, 4, 6,
8, 4, 2, 4, 2, 4, 8, 6, 4, 6,
2, 4, 6, 2, 6, 6, 4, 2, 4, 6,
2, 6, 4, 2, 4, 2,10, 2,
};
uchar table[1000];
uchar bittab[] =
{
1, 2, 4, 8, 16, 32, 64, 128,
};
void mark(double nn, long k);
void ouch(void);
Biobuf bout;
void
main(int argc, char *argp[])
{
int i;
double k, temp, v, limit, nn;
Binit(&bout, 1, OWRITE);
if(argc <= 1) {
fprint(2, "usage: primes starting [ending]\n");
exits("usage");
}
nn = atof(argp[1]);
limit = big;
if(argc > 2) {
limit = atof(argp[2]);
if(limit < nn)
exits(0);
if(limit > big)
ouch();
}
if(nn < 0 || nn > big)
ouch();
if(nn == 0)
nn = 1;
if(nn < 230) {
for(i=0; i<ptsiz; i++) {
if(pt[i] < nn)
continue;
if(pt[i] > limit)
exits(0);
print("%d\n", pt[i]);
if(limit >= big)
exits(0);
}
nn = 230;
}
modf(nn/2, &temp);
nn = 2.*temp + 1;
/*
* clear the sieve table.
*/
for(;;) {
for(i=0; i<tabsiz; i++)
table[i] = 0;
/*
* run the sieve.
*/
v = sqrt(nn+tsiz8);
mark(nn, 3);
mark(nn, 5);
mark(nn, 7);
for(i=0,k=11; k<=v; k+=wheel[i]) {
mark(nn, k);
i++;
if(i >= whsiz)
i = 0;
}
/*
* now get the primes from the table
* and print them.
*/
for(i=0; i<tsiz8; i+=2) {
if(table[i>>3] & bittab[i&07])
continue;
temp = nn + i;
if(temp > limit)
exits(0);
Bprint(&bout, "%lld\n", (long long)temp);
if(limit >= big)
exits(0);
}
nn += tsiz8;
}
}
void
mark(double nn, long k)
{
double t1;
long j;
modf(nn/k, &t1);
j = k*t1 - nn;
if(j < 0)
j += k;
for(; j<tsiz8; j+=k)
table[j>>3] |= bittab[j&07];
}
void
ouch(void)
{
fprint(2, "limits exceeded\n");
exits("limits");
}