parameter_description_list api_generator::load_parameters(const fc::variants& json_parameter_descriptions)
{
  parameter_description_list parameters;
  for (const fc::variant& parameter_description_variant : json_parameter_descriptions)
  {
    fc::variant_object json_parameter_description = parameter_description_variant.get_object();
    parameter_description parameter;
    FC_ASSERT(json_parameter_description.contains("name"), "parameter is missing \"name\"");
    parameter.name = json_parameter_description["name"].as_string();
    try
    {
      FC_ASSERT(json_parameter_description.contains("description"), "parameter is missing \"description\"");
      parameter.description = json_parameter_description["description"].as_string();
      FC_ASSERT(json_parameter_description.contains("type"), "parameter is missing \"type\"");
      parameter.type = lookup_type_mapping(json_parameter_description["type"].as_string());
      if( json_parameter_description.contains( "prompt" ) )
         parameter.prompt = json_parameter_description["prompt"].as_bool();
      if (json_parameter_description.contains("default_value"))
        parameter.default_value = json_parameter_description["default_value"];
      if (json_parameter_description.contains("example"))
        parameter.example = json_parameter_description["example"];
    }
    FC_RETHROW_EXCEPTIONS(error, "error processing parameter ${name}", ("name", parameter.name));
    parameters.push_back(parameter);
  }
  return parameters;
}
Exemplo n.º 2
0
   char parseEscape( T& in )
   {
      if( in.peek() == '\\' )
      {
         try {
            in.get();
            switch( in.peek() )
            {
               case 't':
                  in.get();
                  return '\t';
               case 'n':
                  in.get();
                  return '\n';
               case 'r':
                  in.get();
                  return '\r';
               case '\\':
                  in.get();
                  return '\\';
               default:
                  return in.get();
            }
         } FC_RETHROW_EXCEPTIONS( info, "Stream ended with '\\'" );
      }
	    FC_THROW_EXCEPTION( parse_error_exception, "Expected '\\'"  );
   }
Exemplo n.º 3
0
void    signed_transaction::sign( const fc::ecc::private_key& k )
{
    try {
        sigs.insert( k.sign_compact( digest() ) );
    }
    FC_RETHROW_EXCEPTIONS( warn, "error signing transaction", ("trx", *this ) );
}
Exemplo n.º 4
0
void stcp_socket::close()
{
  try 
  {
    _sock.close();
  }FC_RETHROW_EXCEPTIONS( warn, "error closing stcp socket" );
}
Exemplo n.º 5
0
  /**
   *  A price will reorder the asset types such that the
   *  asset type with the lower enum value is always the
   *  denominator.  Therefore  bts/usd and  usd/bts will
   *  always result in a price measured in usd/bts because
   *  asset::bts <  asset::usd.
   */
  price operator / ( const asset& a, const asset& b )
  {
    try 
    {
        if( a.asset_id == b.asset_id )
           FC_CAPTURE_AND_THROW( asset_divide_by_self );

        price p;
        auto l = a; auto r = b;
        if( l.asset_id < r.asset_id ) { std::swap(l,r); }
        ilog( "${a} / ${b}", ("a",l)("b",r) );

        if( r.amount == 0 )
           FC_CAPTURE_AND_THROW( asset_divide_by_zero, (r) );

        p.base_asset_id = r.asset_id;
        p.quote_asset_id = l.asset_id;

        fc::bigint bl = l.amount;
        fc::bigint br = r.amount;
        fc::bigint result = (bl * fc::bigint(BTS_PRICE_PRECISION)) / br;

        p.ratio = result;
        return p;
    } FC_RETHROW_EXCEPTIONS( warn, "${a} / ${b}", ("a",a)("b",b) );
  }
Exemplo n.º 6
0
   variants arrayFromStream( T& in )
   {
      variants ar;
      try
      {
        if( in.peek() != '[' )
           FC_THROW_EXCEPTION( parse_error_exception, "Expected '['" );
        in.get();
        skip_white_space(in);

        while( in.peek() != ']' )
        {
           if( in.peek() == ',' )
           {
              in.get();
              continue;
           }
           if( skip_white_space(in) ) continue;
           ar.push_back( variant_from_stream<T, parser_type>(in) );
           skip_white_space(in);
        }
        if( in.peek() != ']' )
           FC_THROW_EXCEPTION( parse_error_exception, "Expected ']' after parsing ${variant}",
                                    ("variant", ar) );

        in.get();
      } FC_RETHROW_EXCEPTIONS( warn, "Attempting to parse array ${array}",
                                         ("array", ar ) );
      return ar;
   }
Exemplo n.º 7
0
   variants arrayFromStreamBase( T& in, std::function<variant(T&)>& get_value  )
   {
      variants ar;
      try
      {
        if( in.peek() != '[' )
           FC_THROW_EXCEPTION( parse_error_exception, "Expected '['" );
        in.get();

        while( in.peek() != ']' )
        {
           if( in.peek() == ',' )
           {
              in.get();
              continue;
           }
           if( skip_white_space(in) ) continue;
           ar.push_back( get_value(in) );
        }
        if( in.peek() != ']' )
           FC_THROW_EXCEPTION( parse_error_exception, "Expected ']' after parsing ${variant}",
                                    ("variant", ar) );

        in.get();
      } FC_RETHROW_EXCEPTIONS( warn, "Attempting to parse array ${array}",
                                         ("array", ar ) );
      return ar;
   }
Exemplo n.º 8
0
  /**
   *  A price will reorder the asset types such that the
   *  asset type with the lower enum value is always the
   *  denominator.  Therefore  bts/usd and  usd/bts will
   *  always result in a price measured in usd/bts because
   *  asset::bts <  asset::usd.
   */
  price operator / ( const asset& a, const asset& b )
  {
    try 
    {
        ilog( "${a} / ${b}", ("a",a)("b",b) );
        price p;
        auto l = a; auto r = b;
        if( l.asset_id < r.asset_id ) { std::swap(l,r); }
        ilog( "${a} / ${b}", ("a",l)("b",r) );

        p.base_asset_id = r.asset_id;
        p.quote_asset_id = l.asset_id;

        //fc::uint128 bl(l.amount);
        //fc::uint128 bl(r.amount);

       // p.ratio = (bl* BTS_PRICE_PRECISION) / br;
        fc::bigint bl = l.amount;
        fc::bigint br = r.amount;
        fc::bigint result = (bl * fc::bigint(BTS_PRICE_PRECISION)) / br;

        p.ratio = result;
        return p;
    } FC_RETHROW_EXCEPTIONS( warn, "${a} / ${b}", ("a",a)("b",b) );
  }
Exemplo n.º 9
0
 void tcp_socket::close() {
   try {
       if( is_open() )
       { 
         my->_sock.close();
       }
   } FC_RETHROW_EXCEPTIONS( warn, "error closing tcp socket" );
 }
Exemplo n.º 10
0
 void tcp_server::accept( tcp_socket& s ) 
 {
   try
   {
     FC_ASSERT( my != nullptr );
     fc::asio::tcp::accept( my->_accept, s.my->_sock  ); 
   } FC_RETHROW_EXCEPTIONS( warn, "Unable to accept connection on socket." );
 }
Exemplo n.º 11
0
 fc::ip::endpoint tcp_socket::remote_endpoint()const
 {
   try
   {
     auto rep = my->_sock.remote_endpoint();
     return  fc::ip::endpoint(rep.address().to_v4().to_ulong(), rep.port() );
   } 
   FC_RETHROW_EXCEPTIONS( warn, "error getting socket's remote endpoint" );
 }
Exemplo n.º 12
0
 fc::ip::endpoint tcp_socket::local_endpoint() const
 {
   try
   {
     auto boost_local_endpoint = my->_sock.local_endpoint();
     return fc::ip::endpoint(boost_local_endpoint.address().to_v4().to_ulong(), boost_local_endpoint.port() );
   } 
   FC_RETHROW_EXCEPTIONS( warn, "error getting socket's local endpoint" );
 }
Exemplo n.º 13
0
   std::string tokenFromStream( T& in )
   {
      fc::stringstream token;
      try
      {
         char c = in.peek();

         while( true )
         {
            switch( c = in.peek() )
            {
               case '\\':
                  token << parseEscape( in );
                  break;
               case '\t':
               case ' ':
               case ',':
               case ':':
               case '\0':
               case '\n':
               case '\x04':
                  in.get();
                  return token.str();
               case 'a': case 'b': case 'c': case 'd': case 'e': case 'f': case 'g': case 'h':
               case 'i': case 'j': case 'k': case 'l': case 'm': case 'n': case 'o': case 'p':
               case 'q': case 'r': case 's': case 't': case 'u': case 'v': case 'w': case 'x':
               case 'y': case 'z':
               case 'A': case 'B': case 'C': case 'D': case 'E': case 'F': case 'G': case 'H':
               case 'I': case 'J': case 'K': case 'L': case 'M': case 'N': case 'O': case 'P':
               case 'Q': case 'R': case 'S': case 'T': case 'U': case 'V': case 'W': case 'X':
               case 'Y': case 'Z':
               case '0': case '1': case '2': case '3': case '4': case '5': case '6': case '7':
               case '8': case '9':
               case '_': case '-': case '.': case '+': case '/':
                  token << c;
                  in.get();
                  break;
               default:
                  return token.str();
            }
         }
         return token.str();
      }
      catch( const fc::eof_exception& eof )
      {
         return token.str();
      }
      catch (const std::ios_base::failure&)
      {
         return token.str();
      }

      FC_RETHROW_EXCEPTIONS( warn, "while parsing token '${token}'",
                                          ("token", token.str() ) );
   }
Exemplo n.º 14
0
  /**
   *  Assuming a.type is either the numerator.type or denominator.type in
   *  the price equation, return the number of the other asset type that
   *  could be exchanged at price p.
   *
   *  ie:  p = 3 usd/bts & a = 4 bts then result = 12 usd
   *  ie:  p = 3 usd/bts & a = 4 usd then result = 1.333 bts 
   */
  asset operator * ( const asset& a, const price& p )
  {
    try {
        if( a.asset_id == p.base_asset_id )
        {
            fc::bigint ba( a.amount ); // 64.64
            fc::bigint r( p.ratio ); // 64.64

            auto amnt = ba * r; //  128.128
            amnt /= BTS_PRICE_PRECISION; // 128.64 
            auto lg2 = amnt.log2();
            if( lg2 >= 128 )
            {
               FC_THROW_EXCEPTION( addition_overflow, "overflow ${a} * ${p}", ("a",a)("p",p) );
            }

            asset rtn;
            rtn.amount = amnt.to_int64();
            rtn.asset_id = p.quote_asset_id;

            ilog( "${a} * ${p} => ${rtn}", ("a", a)("p",p )("rtn",rtn) );
            return rtn;
        }
        else if( a.asset_id == p.quote_asset_id )
        {
            fc::bigint amt( a.amount ); // 64.64
            amt *= BTS_PRICE_PRECISION; //<<= 64;  // 64.128
            fc::bigint pri( p.ratio ); // 64.64

            auto result = amt / pri;  // 64.64
//            ilog( "amt: ${amt} / ${pri}", ("amt",string(amt))("pri",string(pri) ) );
 //           ilog( "${r}", ("r",string(result) ) );

            auto lg2 = result.log2();
            if( lg2 >= 128 )
            {
             //  wlog( "." );
               FC_THROW_EXCEPTION( addition_overflow, 
                                    "overflow ${a} / ${p} = ${r} lg2 = ${l}", 
                                    ("a",a)("p",p)("r", std::string(result)  )("l",lg2) );
            }
          //  result += 5000000000; // TODO: evaluate this rounding factor..
            asset r;
            r.amount    = result.to_int64();
            r.asset_id  = p.base_asset_id;
            ilog( "r.amount = ${r}", ("r",r.amount) );
            ilog( "${a} * ${p} => ${rtn}", ("a", a)("p",p )("rtn",r) );
            return r;
        }
        FC_THROW_EXCEPTION( asset_type_mismatch, "type mismatch multiplying asset ${a} by price ${p}", 
                                            ("a",a)("p",p) );
    } FC_RETHROW_EXCEPTIONS( warn, "type mismatch multiplying asset ${a} by price ${p}", 
                                        ("a",a)("p",p) );

  }
Exemplo n.º 15
0
   std::string stringFromStream( T& in )
   {
      try
      {
         char c = in.peek(), c2;

         switch( c )
         {
             case '\'':
                 if( strict )
                     FC_THROW_EXCEPTION( parse_error_exception, "expected: '\"' at beginning of string, got '\''" );
                 // falls through
             case '"':
                 return quoteStringFromStream<T, strict, true>( in );
             case 'r':
                 if( strict )
                     FC_THROW_EXCEPTION( parse_error_exception, "raw strings not supported in strict mode" );
             case 'R':
                 in.get();
                 c2 = in.peek();
                 switch( c2 )
                 {
                     case '"':
                     case '\'':
                         if( strict )
                             FC_THROW_EXCEPTION( parse_error_exception, "raw strings not supported in strict mode" );
                         return quoteStringFromStream<T, strict, false>( in );
                     default:
                         if( strict )
                             FC_THROW_EXCEPTION( parse_error_exception, "unquoted strings not supported in strict mode" );
                         return c+tokenFromStream( in );
                 }
                 break;
             case 'a': case 'b': case 'c': case 'd': case 'e': case 'f': case 'g': case 'h':
             case 'i': case 'j': case 'k': case 'l': case 'm': case 'n': case 'o': case 'p':
             case 'q':           case 's': case 't': case 'u': case 'v': case 'w': case 'x':
             case 'y': case 'z':
             case 'A': case 'B': case 'C': case 'D': case 'E': case 'F': case 'G': case 'H':
             case 'I': case 'J': case 'K': case 'L': case 'M': case 'N': case 'O': case 'P':
             case 'Q':           case 'S': case 'T': case 'U': case 'V': case 'W': case 'X':
             case 'Y': case 'Z':
             case '0': case '1': case '2': case '3': case '4': case '5': case '6': case '7':
             case '8': case '9':
             case '_': case '-': case '.': case '+': case '/':
                 if( strict )
                     FC_THROW_EXCEPTION( parse_error_exception, "unquoted strings not supported in strict mode" );
                 return tokenFromStream( in );
             default:
                 FC_THROW_EXCEPTION( parse_error_exception, "expected: string" );
         }

       } FC_RETHROW_EXCEPTIONS( warn, "while parsing string" );

       return {};
   }
Exemplo n.º 16
0
 void connection::connect( const fc::ip::endpoint& ep )
 {
    try {
      // TODO: do we have to worry about multiple calls to connect?
      my->sock = std::make_shared<stcp_socket>();
      my->sock->connect_to(ep); 
      my->remote_ep = remote_endpoint();
      ilog( "    connected to ${ep}", ("ep", ep) );
      my->_read_loop_complete = fc::async( [=](){ my->read_loop(); } );
    } FC_RETHROW_EXCEPTIONS( warn, "error connecting to ${ep}", ("ep",ep) );
 }
Exemplo n.º 17
0
 void tcp_server::listen( uint16_t port ) 
 {
   if( !my ) 
     my = new impl;
   try
   {
     my->_accept.bind(boost::asio::ip::tcp::endpoint(boost::asio::ip::address_v4(), port));
     my->_accept.listen(256);
   } 
   FC_RETHROW_EXCEPTIONS(warn, "error listening on socket");
 }
Exemplo n.º 18
0
 void tcp_server::listen( const fc::ip::endpoint& ep ) 
 {
   if( !my ) 
     my = new impl;
   try
   {
     my->_accept.bind(boost::asio::ip::tcp::endpoint(boost::asio::ip::address_v4::from_string((string)ep.get_address()), ep.port()));
     my->_accept.listen();
   } 
   FC_RETHROW_EXCEPTIONS(warn, "error listening on socket");
 }
/**
 *  Adds the owner to the required signature list
 *  Adds the balance to the trx balance sheet
 *
 *  TODO: this input is also valid if it is 1 year old and an output exists
 *        paying 95% of the balance back to the owner.
 *
 *  TODO: what if the source is an unvested market order... it means the
 *        proceeds of this trx are also 'unvested'.  Perhaps we will have to
 *        propagate the vested state along with the trx, if any inputs are
 *        sourced from an unvested trx, the new trx is also 'unvested' until
 *        the most receint input is fully vested.
 */
void trx_validation_state::validate_signature( const meta_trx_input& in )
{
   try {
       auto cbs = in.output.as<claim_by_signature_output>();
       ilog( "${cbs}", ("cbs",cbs));
       required_sigs.insert( cbs.owner );

       asset output_bal( in.output.amount, in.output.unit );
       balance_sheet[(asset::type)in.output.unit].in += output_bal;
   
   } FC_RETHROW_EXCEPTIONS( warn, "validating signature input ${i}", ("i",in) );
}
Exemplo n.º 20
0
 void connection::send( const message& m )
 {
   try {
     fc::scoped_lock<fc::mutex> lock(my->write_lock);
     size_t len = MAIL_PACKED_MESSAGE_HEADER + m.size;
     len = 16*((len+15)/16); //pad the message we send to a multiple of 16 bytes
     std::vector<char> tmp(len);
     memcpy( tmp.data(), (char*)&m, MAIL_PACKED_MESSAGE_HEADER );
     memcpy( tmp.data() + MAIL_PACKED_MESSAGE_HEADER, m.data.data(), m.size );
     my->sock->write( tmp.data(), tmp.size() );
     my->sock->flush();
   } FC_RETHROW_EXCEPTIONS( warn, "unable to send message" );
 }
Exemplo n.º 21
0
   variant_object objectFromStream( T& in, uint32_t depth )
   {
      depth++;
      FC_ASSERT( depth <= JSON_MAX_RECURSION_DEPTH );
      mutable_variant_object obj;
      try
      {
         char c = in.peek();
         if( c != '{' )
            FC_THROW_EXCEPTION( parse_error_exception,
                                     "Expected '{', but read '${char}'",
                                     ("char",string(&c, &c + 1)) );
         in.get();
         skip_white_space( in, depth );
         while( in.peek() != '}' )
         {
            if( in.peek() == ',' )
            {
               in.get();
               continue;
            }
            if( skip_white_space( in, depth ) ) continue;
            string key = stringFromStream( in, depth );
            skip_white_space( in, depth );
            if( in.peek() != ':' )
            {
               FC_THROW_EXCEPTION( parse_error_exception, "Expected ':' after key \"${key}\"",
                                        ("key", key) );
            }
            in.get();
            auto val = variant_from_stream<T, parser_type>( in, depth );

            obj(std::move(key),std::move(val));
            skip_white_space( in, depth );
         }
         if( in.peek() == '}' )
         {
            in.get();
            return obj;
         }
         FC_THROW_EXCEPTION( parse_error_exception, "Expected '}' after ${variant}", ("variant", obj ) );
      }
      catch( const fc::eof_exception& e )
      {
         FC_THROW_EXCEPTION( parse_error_exception, "Unexpected EOF: ${e}", ("e", e.to_detail_string() ) );
      }
      catch( const std::ios_base::failure& e )
      {
         FC_THROW_EXCEPTION( parse_error_exception, "Unexpected EOF: ${e}", ("e", e.what() ) );
      } FC_RETHROW_EXCEPTIONS( warn, "Error parsing object" );
   }
Exemplo n.º 22
0
        void store( const Key& k, const Value& v, bool sync = false )
        { try {
           FC_ASSERT( is_open(), "Database is not open!" );

           ldb::Slice ks( (char*)&k, sizeof(k) );
           auto vec = fc::raw::pack(v);
           ldb::Slice vs( vec.data(), vec.size() );

           auto status = _db->Put( sync ? _sync_options : _write_options, ks, vs );
           if( !status.ok() )
           {
               FC_THROW_EXCEPTION( level_pod_map_failure, "database error: ${msg}", ("msg", status.ToString() ) );
           }
        } FC_RETHROW_EXCEPTIONS( warn, "error storing ${key} = ${value}", ("key",k)("value",v) ); }
void api_generator::load_method_descriptions(const fc::variants& method_descriptions)
{
  for (const fc::variant& method_description_variant : method_descriptions)
  {
    fc::variant_object json_method_description = method_description_variant.get_object();
    FC_ASSERT(json_method_description.contains("method_name"), "method entry missing \"method_name\"");
    std::string method_name = json_method_description["method_name"].as_string();
    FC_ASSERT(_registered_method_names.find(method_name) == _registered_method_names.end(),
              "Error: multiple methods registered with the name ${name}", ("name", method_name));
    _registered_method_names.insert(method_name);
    try
    {
      method_description method;
      method.name = method_name;
      FC_ASSERT(json_method_description.contains("return_type"), "method entry missing \"return_type\"");
      std::string return_type_name = json_method_description["return_type"].as_string();
      method.return_type = lookup_type_mapping(return_type_name);
      
      FC_ASSERT(json_method_description.contains("parameters"), "method entry missing \"parameters\"");
      method.parameters = load_parameters(json_method_description["parameters"].get_array());

      method.is_const = json_method_description.contains("is_const") && 
                               json_method_description["is_const"].as_bool();

      FC_ASSERT(json_method_description.contains("prerequisites"), "method entry missing \"prerequisites\"");
      method.prerequisites = load_prerequisites(json_method_description["prerequisites"]);

      if (json_method_description.contains("aliases"))
      {
        method.aliases = json_method_description["aliases"].as<std::vector<std::string> >();
        for (const std::string& alias : method.aliases)
        {
          FC_ASSERT(_registered_method_names.find(alias) == _registered_method_names.end(),
                    "Error: alias \"${alias}\" conflicts with an existing method or alias", ("alias", alias));
          _registered_method_names.insert(alias);
        }
      }
      
      if (json_method_description.contains("description"))
        method.brief_description = json_method_description["description"].as_string();

      if (json_method_description.contains("detailed_description"))
        method.detailed_description = json_method_description["detailed_description"].as_string();

      _methods.push_back(method);
    }
    FC_RETHROW_EXCEPTIONS(warn, "error encountered parsing method description for method \"${method_name}\"", ("method_name", method_name));
  }
}
Exemplo n.º 24
0
        bool last( Key& k )
        { try {
           FC_ASSERT( is_open(), "Database is not open!" );

           std::unique_ptr<ldb::Iterator> it( _db->NewIterator( _iter_options ) );
           FC_ASSERT( it != nullptr );
           it->SeekToLast();
           if( !it->Valid() )
           {
             return false;
           }
           FC_ASSERT( sizeof( Key) == it->key().size() );
           k = *((Key*)it->key().data());
           return true;
        } FC_RETHROW_EXCEPTIONS( warn, "error reading last item from database" ); }
Exemplo n.º 25
0
 void store( const Key& k, const Value& v )
 {
   try
   {
      ldb::Slice ks( (char*)&k, sizeof(k) );
      auto vec = fc::raw::pack(v);
      ldb::Slice vs( vec.data(), vec.size() );
      
      auto status = _db->Put( ldb::WriteOptions(), ks, vs );
      if( !status.ok() )
      {
          FC_THROW_EXCEPTION( exception, "database error: ${msg}", ("msg", status.ToString() ) );
      }
   } FC_RETHROW_EXCEPTIONS( warn, "error storing ${key} = ${value}", ("key",k)("value",v) );
 }
Exemplo n.º 26
0
        bool last( Key& k )
        { try {
           FC_ASSERT( is_open(), "Database is not open!" );

           std::unique_ptr<ldb::Iterator> it( _db->NewIterator( ldb::ReadOptions() ) );
           FC_ASSERT( it != nullptr );
           it->SeekToLast();
           if( !it->Valid() )
           {
             return false;
           }
           fc::datastream<const char*> ds2( it->key().data(), it->key().size() );
           fc::raw::unpack( ds2, k );
           return true;
        } FC_RETHROW_EXCEPTIONS( warn, "error reading last item from database" ); }
Exemplo n.º 27
0
        void remove( const Key& k, bool sync = false )
        { try {
           FC_ASSERT( is_open(), "Database is not open!" );

           ldb::Slice ks( (char*)&k, sizeof(k) );
           auto status = _db->Delete( sync ? _sync_options : _write_options, ks );
           if( status.IsNotFound() )
           {
             FC_THROW_EXCEPTION( fc::key_not_found_exception, "unable to find key ${key}", ("key",k) );
           }
           if( !status.ok() )
           {
               FC_THROW_EXCEPTION( level_pod_map_failure, "database error: ${msg}", ("msg", status.ToString() ) );
           }
        } FC_RETHROW_EXCEPTIONS( warn, "error removing ${key}", ("key",k) ); }
    void message_oriented_connection_impl::send_message(const message& message_to_send)
    {
      VERIFY_CORRECT_THREAD();
#if 0 // this gets too verbose
#ifndef NDEBUG
      fc::optional<fc::ip::endpoint> remote_endpoint;
      if (_sock.get_socket().is_open())
        remote_endpoint = _sock.get_socket().remote_endpoint();
      struct scope_logger {
        const fc::optional<fc::ip::endpoint>& endpoint;
        scope_logger(const fc::optional<fc::ip::endpoint>& endpoint) : endpoint(endpoint) { dlog("entering message_oriented_connection::send_message() for peer ${endpoint}", ("endpoint", endpoint)); }
        ~scope_logger() { dlog("leaving message_oriented_connection::send_message() for peer ${endpoint}", ("endpoint", endpoint)); }
      } send_message_scope_logger(remote_endpoint);
#endif
#endif
      struct verify_no_send_in_progress {
        bool& var;
        verify_no_send_in_progress(bool& var) : var(var)
        {
          if (var)
            elog("Error: two tasks are calling message_oriented_connection::send_message() at the same time");
          assert(!var);
          var = true;
        }
        ~verify_no_send_in_progress() { var = false; }
      } _verify_no_send_in_progress(_send_message_in_progress);

      try
      {
        size_t size_of_message_and_header = sizeof(message_header) + message_to_send.size;
        if( message_to_send.size > MAX_MESSAGE_SIZE )
           elog("Trying to send a message larger than MAX_MESSAGE_SIZE. This probably won't work...");
        //pad the message we send to a multiple of 16 bytes
        size_t size_with_padding = 16 * ((size_of_message_and_header + 15) / 16);
        std::unique_ptr<char[]> padded_message(new char[size_with_padding]);

        memcpy(padded_message.get(), (char*)&message_to_send, sizeof(message_header));
        memcpy(padded_message.get() + sizeof(message_header), message_to_send.data.data(), message_to_send.size );
        char* paddingSpace = padded_message.get() + sizeof(message_header) + message_to_send.size;
        size_t toClean = size_with_padding - size_of_message_and_header;
        memset(paddingSpace, 0, toClean);

        _sock.write(padded_message.get(), size_with_padding);
        _sock.flush();
        _bytes_sent += size_with_padding;
        _last_message_sent_time = fc::time_point::now();
      } FC_RETHROW_EXCEPTIONS( warn, "unable to send message" );
    }
Exemplo n.º 29
0
        void remove( const Key& k, bool sync = false )
        { try {
           FC_ASSERT( is_open(), "Database is not open!" );

           std::vector<char> kslice = fc::raw::pack( k );
           ldb::Slice ks( kslice.data(), kslice.size() );
           auto status = _db->Delete( ldb::WriteOptions(), ks );
           if( status.IsNotFound() )
           {
             FC_THROW_EXCEPTION( fc::key_not_found_exception, "unable to find key ${key}", ("key",k) );
           }
           if( !status.ok() )
           {
               FC_THROW_EXCEPTION( db_exception, "database error: ${msg}", ("msg", status.ToString() ) );
           }
        } FC_RETHROW_EXCEPTIONS( warn, "error removing ${key}", ("key",k) ); }
Exemplo n.º 30
0
        void store( const Key& k, const Value& v, bool sync = false )
        { try {
           FC_ASSERT( is_open(), "Database is not open!" );

           std::vector<char> kslice = fc::raw::pack( k );
           ldb::Slice ks( kslice.data(), kslice.size() );

           auto vec = fc::raw::pack(v);
           ldb::Slice vs( vec.data(), vec.size() );

           auto status = _db->Put( ldb::WriteOptions(), ks, vs );
           if( !status.ok() )
           {
               FC_THROW_EXCEPTION( db_exception, "database error: ${msg}", ("msg", status.ToString() ) );
           }
        } FC_RETHROW_EXCEPTIONS( warn, "error storing ${key} = ${value}", ("key",k)("value",v) ); }