/*############################################################################ # Copyright 2016-2017 Intel Corporation # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # http://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # See the License for the specific language governing permissions and # limitations under the License. ############################################################################*/ /*! * \file * \brief Bignum C++ wrapper implementation. */ #include "epid/common-testhelper/bignum_wrapper-testhelper.h" #include "epid/common-testhelper/errors-testhelper.h" #include "epid/common/math/bignum.h" /// bignum deleter type struct BigNumDeleter { /// bignum deleter void operator()(BigNum* bn) { if (bn) { DeleteBigNum(&bn); } } }; /// bignum deleter singlton BigNumDeleter bignum_deleter; /// Internal state of the bignum wrapper struct BigNumObj::State { /// size of the stored BigNum size_t size; /// The stored BigNum std::shared_ptr bn_; /// Default initializing constructor State() : size(0), bn_() {} /// write a new value void write(unsigned char const* buf, size_t buflen, size_t len) { bool orig_has_data = (buf != nullptr) && (buflen > 0); std::shared_ptr bn; BigNum* bn_ptr = nullptr; THROW_ON_EPIDERR(NewBigNum(len, &bn_ptr)); bn.reset(bn_ptr, bignum_deleter); size = len; if (orig_has_data) { THROW_ON_EPIDERR(ReadBigNum(buf, buflen, bn.get())); } bn_ = bn; } }; BigNumObj::BigNumObj() : state_(new State) { state_->write(nullptr, 0, sizeof(BigNumStr)); } BigNumObj::BigNumObj(BigNumObj const& other) : state_(new State) { bool orig_has_data = other.state_->bn_.get() != nullptr; std::vector buf; if (orig_has_data) { buf.resize(other.state_->size); THROW_ON_EPIDERR(WriteBigNum(other.state_->bn_.get(), buf.size(), &buf[0])); } state_->write(&buf[0], other.state_->size, buf.size()); } BigNumObj& BigNumObj::operator=(BigNumObj const& other) { bool orig_has_data = other.state_->bn_.get() != nullptr; std::vector buf; if (orig_has_data) { buf.resize(other.state_->size); THROW_ON_EPIDERR(WriteBigNum(other.state_->bn_.get(), buf.size(), &buf[0])); } state_->write(&buf[0], other.state_->size, buf.size()); return *this; } BigNumObj::BigNumObj(size_t data_size_bytes) : state_(new State) { state_->write(nullptr, 0, data_size_bytes); } BigNumObj::BigNumObj(size_t data_size_bytes, std::vector const& bytes) : state_(new State) { state_->write(&bytes[0], bytes.size(), data_size_bytes); } BigNumObj::BigNumObj(size_t data_size_bytes, BigNumStr const& bytes) : state_(new State) { state_->write((unsigned char const*)&bytes, sizeof(BigNumStr), data_size_bytes); } BigNumObj::BigNumObj(std::vector const& bytes) : state_(new State) { state_->write(&bytes[0], bytes.size(), bytes.size()); } BigNumObj::BigNumObj(BigNumStr const& bytes) : state_(new State) { state_->write((unsigned char const*)&bytes, sizeof(BigNumStr), sizeof(BigNumStr)); } BigNumObj::~BigNumObj() {} BigNumObj::operator BigNum*() { return state_->bn_.get(); } BigNumObj::operator const BigNum*() const { return state_->bn_.get(); } BigNum* BigNumObj::get() { return state_->bn_.get(); } BigNum const* BigNumObj::getc() const { return state_->bn_.get(); }