rippled
PayChanClaim.cpp
1 //------------------------------------------------------------------------------
2 /*
3  This file is part of rippled: https://github.com/ripple/rippled
4  Copyright (c) 2012-2014 Ripple Labs Inc.
5 
6  Permission to use, copy, modify, and/or distribute this software for any
7  purpose with or without fee is hereby granted, provided that the above
8  copyright notice and this permission notice appear in all copies.
9 
10  THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11  WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12  MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13  ANY SPECIAL , DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14  WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15  ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16  OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17 */
18 //==============================================================================
19 
20 #include <ripple/app/main/Application.h>
21 #include <ripple/basics/StringUtilities.h>
22 #include <ripple/ledger/ReadView.h>
23 #include <ripple/net/RPCErr.h>
24 #include <ripple/protocol/ErrorCodes.h>
25 #include <ripple/protocol/PayChan.h>
26 #include <ripple/protocol/STAccount.h>
27 #include <ripple/protocol/jss.h>
28 #include <ripple/resource/Fees.h>
29 #include <ripple/rpc/Context.h>
30 #include <ripple/rpc/impl/RPCHelpers.h>
31 #include <ripple/rpc/impl/Tuning.h>
32 
33 #include <optional>
34 
35 namespace ripple {
36 
37 // {
38 // secret_key: <signing_secret_key>
39 // key_type: optional; either ed25519 or secp256k1 (default to secp256k1)
40 // channel_id: 256-bit channel id
41 // drops: 64-bit uint (as string)
42 // }
45 {
46  auto const& params(context.params);
47  for (auto const& p : {jss::channel_id, jss::amount})
48  if (!params.isMember(p))
49  return RPC::missing_field_error(p);
50 
51  // Compatibility if a key type isn't specified. If it is, the
52  // keypairForSignature code will validate parameters and return
53  // the appropriate error.
54  if (!params.isMember(jss::key_type) && !params.isMember(jss::secret))
55  return RPC::missing_field_error(jss::secret);
56 
57  Json::Value result;
59  RPC::keypairForSignature(params, result, context.apiVersion);
60 
61  assert(keyPair || RPC::contains_error(result));
62  if (!keyPair || RPC::contains_error(result))
63  return result;
64 
65  PublicKey const& pk = keyPair->first;
66  SecretKey const& sk = keyPair->second;
67 
68  uint256 channelId;
69  if (!channelId.parseHex(params[jss::channel_id].asString()))
71 
72  std::optional<std::uint64_t> const optDrops = params[jss::amount].isString()
73  ? to_uint64(params[jss::amount].asString())
74  : std::nullopt;
75 
76  if (!optDrops)
78 
79  std::uint64_t const drops = *optDrops;
80 
81  Serializer msg;
82  serializePayChanAuthorization(msg, channelId, XRPAmount(drops));
83 
84  try
85  {
86  auto const buf = sign(pk, sk, msg.slice());
87  result[jss::signature] = strHex(buf);
88  }
89  catch (std::exception const& ex)
90  {
91  result = RPC::make_error(
93  "Exception occurred during signing: " + std::string(ex.what()));
94  }
95  return result;
96 }
97 
98 // {
99 // public_key: <public_key>
100 // channel_id: 256-bit channel id
101 // drops: 64-bit uint (as string)
102 // signature: signature to verify
103 // }
106 {
107  auto const& params(context.params);
108  for (auto const& p :
109  {jss::public_key, jss::channel_id, jss::amount, jss::signature})
110  if (!params.isMember(p))
111  return RPC::missing_field_error(p);
112 
114  {
115  std::string const strPk = params[jss::public_key].asString();
116  pk = parseBase58<PublicKey>(TokenType::AccountPublic, strPk);
117 
118  if (!pk)
119  {
120  auto pkHex = strUnHex(strPk);
121  if (!pkHex)
123  auto const pkType = publicKeyType(makeSlice(*pkHex));
124  if (!pkType)
126  pk.emplace(makeSlice(*pkHex));
127  }
128  }
129 
130  uint256 channelId;
131  if (!channelId.parseHex(params[jss::channel_id].asString()))
133 
134  std::optional<std::uint64_t> const optDrops = params[jss::amount].isString()
135  ? to_uint64(params[jss::amount].asString())
136  : std::nullopt;
137 
138  if (!optDrops)
140 
141  std::uint64_t const drops = *optDrops;
142 
143  auto sig = strUnHex(params[jss::signature].asString());
144  if (!sig || !sig->size())
145  return rpcError(rpcINVALID_PARAMS);
146 
147  Serializer msg;
148  serializePayChanAuthorization(msg, channelId, XRPAmount(drops));
149 
150  Json::Value result;
151  result[jss::signature_verified] =
152  verify(*pk, msg.slice(), makeSlice(*sig), /*canonical*/ true);
153  return result;
154 }
155 
156 } // namespace ripple
ripple::RPC::JsonContext
Definition: Context.h:53
ripple::makeSlice
std::enable_if_t< std::is_same< T, char >::value||std::is_same< T, unsigned char >::value, Slice > makeSlice(std::array< T, N > const &a)
Definition: Slice.h:241
std::string
STL class.
ripple::rpcINVALID_PARAMS
@ rpcINVALID_PARAMS
Definition: ErrorCodes.h:84
ripple::rpcError
Json::Value rpcError(int iError)
Definition: RPCErr.cpp:29
std::exception
STL class.
ripple::RPC::keypairForSignature
std::optional< std::pair< PublicKey, SecretKey > > keypairForSignature(Json::Value const &params, Json::Value &error, unsigned int apiVersion)
Definition: RPCHelpers.cpp:796
ripple::verify
bool verify(PublicKey const &publicKey, Slice const &m, Slice const &sig, bool mustBeFullyCanonical) noexcept
Verify a signature on a message.
Definition: PublicKey.cpp:272
std::optional::emplace
T emplace(T... args)
ripple::doChannelVerify
Json::Value doChannelVerify(RPC::JsonContext &)
Definition: PayChanClaim.cpp:105
ripple::serializePayChanAuthorization
void serializePayChanAuthorization(Serializer &msg, uint256 const &key, XRPAmount const &amt)
Definition: protocol/PayChan.h:31
ripple::RPC::missing_field_error
Json::Value missing_field_error(std::string const &name)
Definition: ErrorCodes.h:268
ripple::publicKeyType
std::optional< KeyType > publicKeyType(Slice const &slice)
Returns the type of public key.
Definition: PublicKey.cpp:207
ripple::base_uint< 256 >
ripple::RPC::contains_error
bool contains_error(Json::Value const &json)
Returns true if the json contains an rpc error specification.
Definition: ErrorCodes.cpp:197
ripple::PublicKey
A public key.
Definition: PublicKey.h:61
ripple::doChannelAuthorize
Json::Value doChannelAuthorize(RPC::JsonContext &)
Definition: PayChanClaim.cpp:44
ripple::to_uint64
std::optional< std::uint64_t > to_uint64(std::string const &s)
ripple::rpcPUBLIC_MALFORMED
@ rpcPUBLIC_MALFORMED
Definition: ErrorCodes.h:117
ripple::Serializer::slice
Slice slice() const noexcept
Definition: Serializer.h:64
std::uint64_t
ripple::SecretKey
A secret key.
Definition: SecretKey.h:36
ripple::rpcINTERNAL
@ rpcINTERNAL
Definition: ErrorCodes.h:130
ripple::rpcCHANNEL_AMT_MALFORMED
@ rpcCHANNEL_AMT_MALFORMED
Definition: ErrorCodes.h:101
ripple::Serializer
Definition: Serializer.h:40
ripple
Use hash_* containers for keys that do not need a cryptographically secure hashing algorithm.
Definition: RCLCensorshipDetector.h:29
ripple::sign
Buffer sign(PublicKey const &pk, SecretKey const &sk, Slice const &m)
Generate a signature for a message.
Definition: SecretKey.cpp:238
ripple::RPC::Context::apiVersion
unsigned int apiVersion
Definition: Context.h:50
ripple::TokenType::AccountPublic
@ AccountPublic
ripple::rpcCHANNEL_MALFORMED
@ rpcCHANNEL_MALFORMED
Definition: ErrorCodes.h:100
optional
ripple::strHex
std::string strHex(FwdIt begin, FwdIt end)
Definition: strHex.h:30
ripple::base_uint::parseHex
constexpr bool parseHex(std::string_view sv)
Parse a hex string into a base_uint.
Definition: base_uint.h:496
ripple::strUnHex
std::optional< Blob > strUnHex(std::size_t strSize, Iterator begin, Iterator end)
Definition: StringUtilities.h:52
ripple::RPC::JsonContext::params
Json::Value params
Definition: Context.h:64
ripple::RPC::make_error
Json::Value make_error(error_code_i code)
Returns a new json object that reflects the error code.
Definition: ErrorCodes.cpp:181
std::exception::what
T what(T... args)
Json::Value
Represents a JSON value.
Definition: json_value.h:145
ripple::XRPAmount
Definition: XRPAmount.h:46