Use latest Cygwin setup on AppVeyor
[cygwin-setup.git] / csu_util / MD5Sum.cc
blob596089dfc45cb2b1c34a948fc8a651908d01fe0b
1 /*
2 * Copyright (c) 2004 Max Bowsher
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
9 * A copy of the GNU General Public License can be found at
10 * http://www.gnu.org/
12 * Written by Max Bowsher
15 #include "MD5Sum.h"
16 #include <string>
17 #include <sstream>
18 #include <iostream>
19 #include <iomanip>
20 #include <stdexcept>
22 MD5Sum::MD5Sum(const MD5Sum& source)
24 *this = source;
27 MD5Sum&
28 MD5Sum::operator= (const MD5Sum& source)
30 state = source.state;
31 memcpy(digest, source.digest, sizeof(digest));
32 internalData = 0;
33 if (source.internalData)
35 internalData = new gcry_md_hd_t;
36 *internalData = *(source.internalData);
38 return *this;
41 MD5Sum::~MD5Sum()
43 if (internalData) delete internalData;
46 void
47 MD5Sum::set(const unsigned char digest[16])
49 memcpy(this->digest, digest, sizeof(this->digest));
50 state = Set;
51 if (internalData) delete internalData;
54 void
55 MD5Sum::begin()
57 if (internalData) delete internalData;
58 internalData = new gcry_md_hd_t;
59 state = Accumulating;
60 gcry_md_open(internalData, GCRY_MD_MD5, 0);
63 void
64 MD5Sum::append(const unsigned char* data, int nbytes)
66 if (!internalData)
67 throw new std::logic_error("MD5Sum::append() called on an object not "
68 "in the 'Accumulating' state");
69 gcry_md_write(*internalData, data, nbytes);
72 void
73 MD5Sum::finish()
75 if (!internalData)
76 throw new std::logic_error("MD5Sum::finish() called on an object not "
77 "in the 'Accumulating' state");
78 memcpy(digest, gcry_md_read(*internalData, GCRY_MD_MD5), 16);
79 state = Set;
80 delete internalData; internalData = 0;
83 std::string
84 MD5Sum::str() const
86 std::ostringstream hexdigest;
88 for (int i=0; i<16; ++i )
89 hexdigest << std::hex << std::setfill('0') << std::setw(2)
90 << static_cast<unsigned int>(digest[i]);
91 return hexdigest.str();
94 bool
95 MD5Sum::operator == (const MD5Sum& other) const
97 if (state != Set || other.state != Set)
98 throw new std::logic_error("MD5Sum comparison attempted on operands not "
99 "in the 'Set' state");
100 return (memcmp(digest, other.digest, sizeof(digest)) == 0);