2011-12-09 21:50:25 +01:00
|
|
|
|
2012-05-03 21:27:05 +02:00
|
|
|
// #include <lib/lib.h>
|
|
|
|
#include <algebra/algebra.h>
|
2011-12-09 21:50:25 +01:00
|
|
|
|
2012-07-28 19:48:17 +02:00
|
|
|
writer::writer (bool raw_)
|
|
|
|
: raw(raw_),
|
|
|
|
aw(new algebra_writer)
|
|
|
|
{
|
|
|
|
}
|
|
|
|
|
|
|
|
writer::~writer ()
|
|
|
|
{
|
|
|
|
delete aw;
|
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
void
|
|
|
|
writer::write_int (int x)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-28 18:55:46 +02:00
|
|
|
if (raw)
|
|
|
|
write_raw (&x, sizeof x, 1);
|
|
|
|
else
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-28 18:55:46 +02:00
|
|
|
uint8 buf[5];
|
|
|
|
unsigned n = 0;
|
|
|
|
|
|
|
|
bool more = 1;
|
|
|
|
while (more)
|
|
|
|
{
|
|
|
|
uint8 b = (uint8)(x & 0x7f);
|
|
|
|
x >>= 7;
|
2012-07-27 21:37:47 +02:00
|
|
|
|
2012-07-28 18:55:46 +02:00
|
|
|
if ((x == 0
|
|
|
|
&& ! (b & 0x40))
|
|
|
|
|| (x == -1
|
|
|
|
&& (b & 0x40) == 0x40))
|
|
|
|
more = 0;
|
|
|
|
else
|
|
|
|
b |= 0x80;
|
|
|
|
|
|
|
|
assert (n < 5);
|
|
|
|
buf[n] = b;
|
|
|
|
n ++;
|
|
|
|
}
|
2012-07-27 21:37:47 +02:00
|
|
|
|
2012-07-28 18:55:46 +02:00
|
|
|
write_raw (buf, sizeof buf[0], n);
|
2011-12-09 21:50:25 +01:00
|
|
|
}
|
2011-12-22 21:35:49 +01:00
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
void
|
|
|
|
writer::write_unsigned (unsigned x)
|
2011-12-22 21:35:49 +01:00
|
|
|
{
|
2012-07-28 18:55:46 +02:00
|
|
|
if (raw)
|
|
|
|
write_raw (&x, sizeof x, 1);
|
|
|
|
else
|
2012-07-27 21:37:47 +02:00
|
|
|
{
|
2012-07-28 18:55:46 +02:00
|
|
|
uint8 buf[5];
|
|
|
|
unsigned n = 0;
|
|
|
|
|
|
|
|
bool more = 1;
|
|
|
|
while (more)
|
|
|
|
{
|
|
|
|
uint8 b = (uint8)(x & 0x7f);
|
|
|
|
x >>= 7;
|
2012-07-27 21:37:47 +02:00
|
|
|
|
2012-07-28 18:55:46 +02:00
|
|
|
if ((x == 0
|
|
|
|
&& ! (b & 0x40)))
|
|
|
|
more = 0;
|
|
|
|
else
|
|
|
|
b |= 0x80;
|
2012-07-27 21:37:47 +02:00
|
|
|
|
2012-07-28 18:55:46 +02:00
|
|
|
assert (n < 5);
|
|
|
|
buf[n] = b;
|
|
|
|
n ++;
|
|
|
|
}
|
2012-07-27 21:37:47 +02:00
|
|
|
|
2012-07-28 18:55:46 +02:00
|
|
|
write_raw (buf, sizeof buf[0], n);
|
|
|
|
}
|
2011-12-09 21:50:25 +01:00
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
void
|
|
|
|
writer::write_uint64 (uint64 x)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-28 18:55:46 +02:00
|
|
|
if (raw)
|
|
|
|
write_raw (&x, sizeof x, 1);
|
|
|
|
else
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-28 18:55:46 +02:00
|
|
|
uint8 buf[10];
|
|
|
|
unsigned n = 0;
|
|
|
|
|
|
|
|
bool more = 1;
|
|
|
|
while (more)
|
|
|
|
{
|
|
|
|
uint8 b = (uint8)(x & 0x7f);
|
|
|
|
x >>= 7;
|
2012-07-27 21:37:47 +02:00
|
|
|
|
2012-07-28 18:55:46 +02:00
|
|
|
if ((x == 0
|
|
|
|
&& ! (b & 0x40)))
|
|
|
|
more = 0;
|
|
|
|
else
|
|
|
|
b |= 0x80;
|
2012-07-27 21:37:47 +02:00
|
|
|
|
2012-07-28 18:55:46 +02:00
|
|
|
assert (n < 10);
|
|
|
|
buf[n] = b;
|
|
|
|
n ++;
|
|
|
|
}
|
2012-07-27 21:37:47 +02:00
|
|
|
|
2012-07-28 18:55:46 +02:00
|
|
|
write_raw (buf, sizeof buf[0], n);
|
|
|
|
}
|
2011-12-09 21:50:25 +01:00
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
void
|
|
|
|
writer::write_mpz (const mpz_t x)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-28 18:55:46 +02:00
|
|
|
assert (!raw);
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
size_t count;
|
|
|
|
void *buf = mpz_export (nullptr, &count, -1, 1, -1, 0, x);
|
|
|
|
|
|
|
|
write_unsigned ((unsigned)count);
|
|
|
|
write_raw (buf, 1, count);
|
|
|
|
|
|
|
|
free (buf);
|
2011-12-09 21:50:25 +01:00
|
|
|
}
|
|
|
|
|
2012-07-28 19:48:17 +02:00
|
|
|
reader::reader (bool raw_)
|
|
|
|
: raw(raw_),
|
|
|
|
ar(new algebra_reader)
|
|
|
|
{
|
|
|
|
}
|
|
|
|
|
|
|
|
reader::~reader ()
|
|
|
|
{
|
|
|
|
delete ar;
|
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
int
|
|
|
|
reader::read_int ()
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
int x = 0;
|
2012-07-28 18:55:46 +02:00
|
|
|
|
|
|
|
if (raw)
|
|
|
|
read_raw (&x, sizeof x, 1);
|
|
|
|
else
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-28 18:55:46 +02:00
|
|
|
int shift = 0;
|
|
|
|
for (;;)
|
2012-07-27 21:37:47 +02:00
|
|
|
{
|
2012-07-28 18:55:46 +02:00
|
|
|
uint8 b = read_uint8 ();
|
|
|
|
x |= ((int)(b & 0x7f) << shift);
|
|
|
|
shift += 7;
|
|
|
|
if (! (b & 0x80))
|
|
|
|
{
|
|
|
|
if (shift < int_bits
|
|
|
|
&& (b & 0x40))
|
|
|
|
x = (x << (int_bits - shift)) >> (int_bits - shift);
|
|
|
|
break;
|
|
|
|
}
|
2012-07-27 21:37:47 +02:00
|
|
|
}
|
2011-12-09 21:50:25 +01:00
|
|
|
}
|
2012-07-28 18:55:46 +02:00
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
return x;
|
2011-12-09 21:50:25 +01:00
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
unsigned
|
|
|
|
reader::read_unsigned ()
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
unsigned x = 0;
|
2012-07-28 18:55:46 +02:00
|
|
|
|
|
|
|
if (raw)
|
|
|
|
read_raw (&x, sizeof x, 1);
|
|
|
|
else
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-28 18:55:46 +02:00
|
|
|
unsigned shift = 0;
|
|
|
|
for (;;)
|
|
|
|
{
|
|
|
|
uint8 b = read_uint8 ();
|
|
|
|
x |= ((unsigned)(b & 0x7f) << shift);
|
|
|
|
shift += 7;
|
|
|
|
if (! (b & 0x80))
|
|
|
|
break;
|
|
|
|
}
|
2011-12-09 21:50:25 +01:00
|
|
|
}
|
2012-07-28 18:55:46 +02:00
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
return x;
|
2011-12-09 21:50:25 +01:00
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
uint64
|
|
|
|
reader::read_uint64 ()
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
uint64 x = 0;
|
2012-07-28 18:55:46 +02:00
|
|
|
|
|
|
|
if (raw)
|
|
|
|
read_raw (&x, sizeof x, 1);
|
|
|
|
else
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-28 18:55:46 +02:00
|
|
|
uint64 shift = 0;
|
|
|
|
for (;;)
|
|
|
|
{
|
|
|
|
uint8 b = read_uint8 ();
|
|
|
|
x |= ((uint64)(b & 0x7f) << shift);
|
|
|
|
shift += 7;
|
|
|
|
if (! (b & 0x80))
|
|
|
|
break;
|
|
|
|
}
|
2011-12-09 21:50:25 +01:00
|
|
|
}
|
2012-07-28 18:55:46 +02:00
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
return x;
|
2011-12-09 21:50:25 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
2012-07-27 21:37:47 +02:00
|
|
|
reader::read_mpz (mpz_t x)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-28 18:55:46 +02:00
|
|
|
assert (!raw);
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
unsigned count = read_unsigned ();
|
|
|
|
void *p = malloc (count);
|
|
|
|
if (!p)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
stderror ("malloc");
|
2011-12-09 21:50:25 +01:00
|
|
|
exit (EXIT_FAILURE);
|
|
|
|
}
|
2012-07-27 21:37:47 +02:00
|
|
|
|
|
|
|
read_raw (p, 1, count);
|
|
|
|
|
|
|
|
mpz_import (x, count, -1, 1, -1, 0, p);
|
|
|
|
|
|
|
|
free (p);
|
2011-12-09 21:50:25 +01:00
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
FILE *open_file (const std::string &file, const char *mode)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
FILE *fp = fopen (file.c_str (), mode);
|
|
|
|
if (!fp)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
stderror ("fopen: %s", file.c_str ());
|
2011-12-09 21:50:25 +01:00
|
|
|
exit (EXIT_FAILURE);
|
|
|
|
}
|
2012-07-27 21:37:47 +02:00
|
|
|
return fp;
|
2011-12-09 21:50:25 +01:00
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
void close_file (FILE *fp)
|
|
|
|
{
|
|
|
|
fclose (fp);
|
|
|
|
}
|
|
|
|
|
|
|
|
gzFile
|
|
|
|
open_gzfile (const std::string &file, const char *mode)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
gzFile gzfp = gzopen (file.c_str (), mode);
|
|
|
|
if (!gzfp)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
stderror ("gzopen: %s", file.c_str ());
|
2011-12-09 21:50:25 +01:00
|
|
|
exit (EXIT_FAILURE);
|
|
|
|
}
|
2012-07-27 21:37:47 +02:00
|
|
|
return gzfp;
|
2011-12-09 21:50:25 +01:00
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
extern void close_gzfile (gzFile gzfp)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
int r = gzclose (gzfp);
|
|
|
|
if (r != Z_OK)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
stderror ("gzclose");
|
2011-12-09 21:50:25 +01:00
|
|
|
exit (EXIT_FAILURE);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
void
|
|
|
|
file_writer::write_raw (const void *p, size_t itemsize, size_t nitems)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
if (fwrite (p, itemsize, nitems, fp) != nitems)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
stderror ("fwrite");
|
2011-12-09 21:50:25 +01:00
|
|
|
exit (EXIT_FAILURE);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2012-07-28 18:55:46 +02:00
|
|
|
void
|
|
|
|
file_writer::write_mpz (const mpz_t x)
|
|
|
|
{
|
|
|
|
mpz_out_raw (fp, x);
|
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
void
|
|
|
|
file_reader::read_raw (void *p, size_t itemsize, size_t nitems)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
if (fread (p, itemsize, nitems, fp) != nitems)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
|
|
|
stderror ("fread");
|
|
|
|
exit (EXIT_FAILURE);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2012-07-28 18:55:46 +02:00
|
|
|
void
|
|
|
|
file_reader::read_mpz (mpz_t x)
|
|
|
|
{
|
|
|
|
mpz_inp_raw (x, fp);
|
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
void
|
|
|
|
gzfile_writer::write_raw (const void *p, size_t itemsize, size_t nitems)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
unsigned nbytes = itemsize*nitems;
|
|
|
|
if (gzwrite (gzfp, p, nbytes) != nbytes)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
stderror ("gzwrite");
|
2011-12-09 21:50:25 +01:00
|
|
|
exit (EXIT_FAILURE);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
void
|
|
|
|
gzfile_reader::read_raw (void *p, size_t itemsize, size_t nitems)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
2012-07-27 21:37:47 +02:00
|
|
|
unsigned nbytes = itemsize*nitems;
|
|
|
|
if (gzread (gzfp, p, nbytes) != nitems)
|
2011-12-09 21:50:25 +01:00
|
|
|
{
|
|
|
|
stderror ("fread");
|
|
|
|
exit (EXIT_FAILURE);
|
|
|
|
}
|
|
|
|
}
|
2011-12-30 01:38:02 +01:00
|
|
|
|
|
|
|
void
|
|
|
|
read (reader &r, std::string &s)
|
|
|
|
{
|
|
|
|
unsigned n = r.read_unsigned ();
|
|
|
|
|
|
|
|
char buf[n + 1];
|
2012-07-27 21:37:47 +02:00
|
|
|
r.read_raw (buf, sizeof (char), n + 1);
|
2011-12-30 01:38:02 +01:00
|
|
|
assert (buf[n] == 0);
|
|
|
|
|
|
|
|
s = std::string (buf);
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
write (writer &w, const std::string &s)
|
|
|
|
{
|
|
|
|
unsigned n = s.length ();
|
|
|
|
w.write_unsigned (n);
|
|
|
|
|
2012-07-27 21:37:47 +02:00
|
|
|
w.write_raw (s.c_str (), sizeof (char), n + 1);
|
2011-12-30 01:38:02 +01:00
|
|
|
}
|