| 3101 | } |
| 3102 | |
| 3103 | size_t SSU2Session::CreateRelayResponseBlock (uint8_t * buf, size_t len, |
| 3104 | SSU2RelayResponseCode code, uint32_t nonce, uint64_t token, bool v4) |
| 3105 | { |
| 3106 | buf[0] = eSSU2BlkRelayResponse; |
| 3107 | buf[3] = 0; // flag |
| 3108 | buf[4] = code; // code |
| 3109 | htobe32buf (buf + 5, nonce); // nonce |
| 3110 | htobe32buf (buf + 9, i2p::util::GetSecondsSinceEpoch ()); // timestamp |
| 3111 | buf[13] = 2; // ver |
| 3112 | size_t csz = 0; |
| 3113 | if (code == eSSU2RelayResponseCodeAccept) |
| 3114 | { |
| 3115 | auto addr = i2p::context.GetRouterInfo ().GetSSU2Address (v4); |
| 3116 | if (!addr) |
| 3117 | { |
| 3118 | LogPrint (eLogError, "SSU2: Can't find local address for RelayResponse"); |
| 3119 | return 0; |
| 3120 | } |
| 3121 | csz = CreateEndpoint (buf + 15, len - 15, boost::asio::ip::udp::endpoint (addr->host, addr->port)); |
| 3122 | if (!csz) |
| 3123 | { |
| 3124 | LogPrint (eLogError, "SSU2: Can't create local endpoint for RelayResponse"); |
| 3125 | return 0; |
| 3126 | } |
| 3127 | } |
| 3128 | buf[14] = csz; // csz |
| 3129 | // signature |
| 3130 | size_t signatureLen = i2p::context.GetIdentity ()->GetSignatureLen (); |
| 3131 | if (15 + csz + signatureLen > len) |
| 3132 | { |
| 3133 | LogPrint (eLogError, "SSU2: Buffer for RelayResponse signature is too small ", len); |
| 3134 | return 0; |
| 3135 | } |
| 3136 | SignedData<128> s; |
| 3137 | s.Insert ((const uint8_t *)"RelayAgreementOK", 16); // prologue |
| 3138 | if (code == eSSU2RelayResponseCodeAccept || code >= 64) // Charlie |
| 3139 | s.Insert (GetRemoteIdentity ()->GetIdentHash (), 32); // bhash |
| 3140 | else // Bob's reject |
| 3141 | s.Insert (i2p::context.GetIdentity ()->GetIdentHash (), 32); // bhash |
| 3142 | s.Insert (buf + 5, 10 + csz); // nonce, timestamp, ver, csz and Charlie's endpoint |
| 3143 | s.Sign (i2p::context.GetPrivateKeys (), buf + 15 + csz); |
| 3144 | size_t payloadSize = 12 + csz + signatureLen; |
| 3145 | if (!code) |
| 3146 | { |
| 3147 | if (payloadSize + 11 > len) |
| 3148 | { |
| 3149 | LogPrint (eLogError, "SSU2: Buffer for RelayResponse token is too small ", len); |
| 3150 | return 0; |
| 3151 | } |
| 3152 | memcpy (buf + 3 + payloadSize, &token, 8); |
| 3153 | payloadSize += 8; |
| 3154 | } |
| 3155 | htobe16buf (buf + 1, payloadSize); // size |
| 3156 | return payloadSize + 3; |
| 3157 | } |
| 3158 | |
| 3159 | size_t SSU2Session::CreatePeerTestBlock (uint8_t * buf, size_t len, uint8_t msg, SSU2PeerTestCode code, |
| 3160 | const uint8_t * routerHash, const uint8_t * signedData, size_t signedDataLen) |
nothing calls this directly
no test coverage detected