blob: ec2780456f3142e64ab4f56a14c8e215848e4548 [file] [log] [blame]
Yingdi Yude222c72014-08-15 16:06:52 -07001/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2/**
3 * Copyright (c) 2013-2014 Regents of the University of California.
4 *
5 * This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions).
6 *
7 * ndn-cxx library is free software: you can redistribute it and/or modify it under the
8 * terms of the GNU Lesser General Public License as published by the Free Software
9 * Foundation, either version 3 of the License, or (at your option) any later version.
10 *
11 * ndn-cxx library is distributed in the hope that it will be useful, but WITHOUT ANY
12 * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
13 * PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
14 *
15 * You should have received copies of the GNU General Public License and GNU Lesser
16 * General Public License along with ndn-cxx, e.g., in COPYING.md file. If not, see
17 * <http://www.gnu.org/licenses/>.
18 *
19 * See AUTHORS.md for complete list of ndn-cxx authors and contributors.
20 */
21
22#include "digest.hpp"
23
24namespace ndn {
25namespace util {
26
27template<typename Hash>
28Digest<Hash>::Digest()
29{
30 reset();
31}
32
33template<typename Hash>
34void
35Digest<Hash>::reset()
36{
37 m_hash.Restart();
38 m_buffer = make_shared<Buffer>(m_hash.DigestSize());
39 m_isInProcess = false;
40 m_isFinalized = false;
41}
42
43template<typename Hash>
44void
45Digest<Hash>::finalize()
46{
47 // return immediately if Digest is finalized already.
48 if (m_isFinalized)
49 return;
50
51 m_hash.Final(m_buffer->get());
52
53 m_isFinalized = true;
54}
55
56template<typename Hash>
57ConstBufferPtr
58Digest<Hash>::computeDigest()
59{
60 finalize();
61 return m_buffer;
62}
63
64template<typename Hash>
65bool
66Digest<Hash>::operator==(Digest<Hash>& digest)
67{
68 return *computeDigest() == *digest.computeDigest();
69}
70
71template<typename Hash>
72Digest<Hash>&
73Digest<Hash>::operator<<(Digest<Hash>& src)
74{
75 ConstBufferPtr buffer = src.computeDigest();
76 update(buffer->get(), buffer->size());
77
78 return *this;
79}
80
81template<typename Hash>
82Digest<Hash>&
83Digest<Hash>::operator<<(const std::string& str)
84{
85 update(reinterpret_cast<const uint8_t*>(str.c_str()), str.size());
86
87 return *this;
88}
89
90template<typename Hash>
91Digest<Hash>&
92Digest<Hash>::operator<<(const Block& block)
93{
94 update(block.wire(), block.size());
95
96 return *this;
97}
98
99template<typename Hash>
100Digest<Hash>&
101Digest<Hash>::operator<<(uint64_t value)
102{
103 update(reinterpret_cast<const uint8_t*>(&value), sizeof(uint64_t));
104
105 return *this;
106}
107
108template<typename Hash>
109void
110Digest<Hash>::update(const uint8_t* buffer, size_t size)
111{
112 // cannot update Digest when it has been finalized
113 if (m_isFinalized)
114 throw Error("Digest has been already finalized");
115
116 m_hash.Update(buffer, size);
117
118 m_isInProcess = true;
119}
120
121template<typename Hash>
122ConstBufferPtr
123Digest<Hash>::computeDigest(const uint8_t* buffer, size_t size)
124{
125 Hash hash;
126 BufferPtr result = make_shared<Buffer>(hash.DigestSize());
127 hash.Update(buffer, size);
128 hash.Final(result->get());
129
130 return result;
131}
132
Yingdi Yu9ad2d722014-08-30 16:13:57 -0700133template<typename Hash>
134std::string
135Digest<Hash>::toString()
136{
137 std::ostringstream os;
138 os << *this;
139
140 return os.str();
141}
142
143template<typename Hash>
144std::ostream&
145operator<<(std::ostream& os, Digest<Hash>& digest)
146{
147 using namespace CryptoPP;
148
149 std::string output;
150 ConstBufferPtr buffer = digest.computeDigest();
151 StringSource(buffer->buf(), buffer->size(), true, new HexEncoder(new FileSink(os)));
152
153 return os;
154}
155
156template
157class Digest<CryptoPP::SHA256>;
158
159template
160std::ostream&
161operator<<(std::ostream& os, Digest<CryptoPP::SHA256>& digest);
162
Yingdi Yude222c72014-08-15 16:06:52 -0700163
164} // namespace util
165} // namespace ndn