aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristian Grothoff <christian@grothoff.org>2019-04-10 21:53:53 +0200
committerChristian Grothoff <christian@grothoff.org>2019-04-10 21:53:53 +0200
commitc457ee81954163e0b7295fbd4a713474b3059abf (patch)
tree32e36fbcb51f2578d1a39828879364d32532aed3
parentce23f02091d48dae13fe23f3c87a1c0b7ab741f3 (diff)
downloadgnunet-c457ee81954163e0b7295fbd4a713474b3059abf.tar.gz
gnunet-c457ee81954163e0b7295fbd4a713474b3059abf.zip
send validation challenges
-rw-r--r--src/include/gnunet_protocols.h12
-rw-r--r--src/transport/gnunet-service-tng.c276
-rw-r--r--src/transport/transport.h2
3 files changed, 191 insertions, 99 deletions
diff --git a/src/include/gnunet_protocols.h b/src/include/gnunet_protocols.h
index 4f97d3078..f461249eb 100644
--- a/src/include/gnunet_protocols.h
+++ b/src/include/gnunet_protocols.h
@@ -3196,6 +3196,18 @@ extern "C"
3196#define GNUNET_MESSAGE_TYPE_TRANSPORT_REQUEST_HELLO_VALIDATION 1302 3196#define GNUNET_MESSAGE_TYPE_TRANSPORT_REQUEST_HELLO_VALIDATION 1302
3197 3197
3198 3198
3199/**
3200 * P2P message: transport requests confirmation that an address works.
3201 */
3202#define GNUNET_MESSAGE_TYPE_TRANSPORT_ADDRESS_VALIDATION_CHALLENGE 1303
3203
3204/**
3205 * P2P message: transport proves that an address worked.
3206 */
3207#define GNUNET_MESSAGE_TYPE_TRANSPORT_ADDRESS_VALIDATION_RESPONSE 1304
3208
3209
3210
3199/* ************** NEW (NG) ATS Messages ************* */ 3211/* ************** NEW (NG) ATS Messages ************* */
3200/* NOTE: it is not clear ATS will survive in TNG */ 3212/* NOTE: it is not clear ATS will survive in TNG */
3201 3213
diff --git a/src/transport/gnunet-service-tng.c b/src/transport/gnunet-service-tng.c
index 937ae249e..e685e28a6 100644
--- a/src/transport/gnunet-service-tng.c
+++ b/src/transport/gnunet-service-tng.c
@@ -553,7 +553,7 @@ struct TransportValidationChallenge
553{ 553{
554 554
555 /** 555 /**
556 * Type is #GNUNET_MESSAGE_TYPE_ADDRESS_VALIDATION_CHALLENGE 556 * Type is #GNUNET_MESSAGE_TYPE_TRANSPORT_ADDRESS_VALIDATION_CHALLENGE
557 */ 557 */
558 struct GNUNET_MessageHeader header; 558 struct GNUNET_MessageHeader header;
559 559
@@ -609,7 +609,7 @@ struct TransportValidationResponse
609{ 609{
610 610
611 /** 611 /**
612 * Type is #GNUNET_MESSAGE_TYPE_ADDRESS_VALIDATION_RESPONSE 612 * Type is #GNUNET_MESSAGE_TYPE_TRANSPORT_ADDRESS_VALIDATION_RESPONSE
613 */ 613 */
614 struct GNUNET_MessageHeader header; 614 struct GNUNET_MessageHeader header;
615 615
@@ -3802,7 +3802,7 @@ handle_dv_box (void *cls,
3802 cmc->im.sender = dvb->origin; 3802 cmc->im.sender = dvb->origin;
3803 cmc->total_hops = ntohs (dvb->total_hops); 3803 cmc->total_hops = ntohs (dvb->total_hops);
3804 demultiplex_with_cmc (cmc, 3804 demultiplex_with_cmc (cmc,
3805 inbox); 3805 inbox);
3806} 3806}
3807 3807
3808 3808
@@ -3830,6 +3830,41 @@ check_incoming_msg (void *cls,
3830 3830
3831 3831
3832/** 3832/**
3833 * Communicator gave us a transport address validation challenge. Process the request.
3834 *
3835 * @param cls a `struct CommunicatorMessageContext` (must call #finish_cmc_handling() when done)
3836 * @param tvc the message that was received
3837 */
3838static void
3839handle_validation_challenge (void *cls,
3840 const struct TransportValidationChallenge *tvc)
3841{
3842 struct CommunicatorMessageContext *cmc = cls;
3843
3844 // FIXME: sign challenge and try to get it back to the origin!
3845 finish_cmc_handling (cmc);
3846}
3847
3848
3849/**
3850 * Communicator gave us a transport address validation response. Process the request.
3851 *
3852 * @param cls a `struct CommunicatorMessageContext` (must call #finish_cmc_handling() when done)
3853 * @param tvr the message that was received
3854 */
3855static void
3856handle_validation_response (void *cls,
3857 const struct TransportValidationResponse *tvr)
3858{
3859 struct CommunicatorMessageContext *cmc = cls;
3860
3861 // FIXME: check for matching pending challenge and mark address
3862 // as valid if applicable (passing to PEERSTORE as well!)
3863 finish_cmc_handling (cmc);
3864}
3865
3866
3867/**
3833 * Incoming meessage. Process the request. 3868 * Incoming meessage. Process the request.
3834 * 3869 *
3835 * @param im the send message that was received 3870 * @param im the send message that was received
@@ -3844,7 +3879,7 @@ handle_incoming_msg (void *cls,
3844 cmc->tc = tc; 3879 cmc->tc = tc;
3845 cmc->im = *im; 3880 cmc->im = *im;
3846 demultiplex_with_cmc (cmc, 3881 demultiplex_with_cmc (cmc,
3847 (const struct GNUNET_MessageHeader *) &im[1]); 3882 (const struct GNUNET_MessageHeader *) &im[1]);
3848} 3883}
3849 3884
3850 3885
@@ -3857,43 +3892,51 @@ handle_incoming_msg (void *cls,
3857 */ 3892 */
3858static void 3893static void
3859demultiplex_with_cmc (struct CommunicatorMessageContext *cmc, 3894demultiplex_with_cmc (struct CommunicatorMessageContext *cmc,
3860 const struct GNUNET_MessageHeader *msg) 3895 const struct GNUNET_MessageHeader *msg)
3861{ 3896{
3862 struct GNUNET_MQ_MessageHandler handlers[] = { 3897 struct GNUNET_MQ_MessageHandler handlers[] = {
3863 GNUNET_MQ_hd_var_size (fragment_box, 3898 GNUNET_MQ_hd_var_size (fragment_box,
3864 GNUNET_MESSAGE_TYPE_TRANSPORT_FRAGMENT, 3899 GNUNET_MESSAGE_TYPE_TRANSPORT_FRAGMENT,
3865 struct TransportFragmentBox, 3900 struct TransportFragmentBox,
3866 &cmc), 3901 &cmc),
3867 GNUNET_MQ_hd_fixed_size (fragment_ack, 3902 GNUNET_MQ_hd_fixed_size (fragment_ack,
3868 GNUNET_MESSAGE_TYPE_TRANSPORT_FRAGMENT_ACK, 3903 GNUNET_MESSAGE_TYPE_TRANSPORT_FRAGMENT_ACK,
3869 struct TransportFragmentAckMessage, 3904 struct TransportFragmentAckMessage,
3870 &cmc), 3905 &cmc),
3871 GNUNET_MQ_hd_var_size (reliability_box, 3906 GNUNET_MQ_hd_var_size (reliability_box,
3872 GNUNET_MESSAGE_TYPE_TRANSPORT_RELIABILITY_BOX, 3907 GNUNET_MESSAGE_TYPE_TRANSPORT_RELIABILITY_BOX,
3873 struct TransportReliabilityBox, 3908 struct TransportReliabilityBox,
3874 &cmc), 3909 &cmc),
3875 GNUNET_MQ_hd_fixed_size (reliability_ack, 3910 GNUNET_MQ_hd_fixed_size (reliability_ack,
3876 GNUNET_MESSAGE_TYPE_TRANSPORT_RELIABILITY_ACK, 3911 GNUNET_MESSAGE_TYPE_TRANSPORT_RELIABILITY_ACK,
3877 struct TransportReliabilityAckMessage, 3912 struct TransportReliabilityAckMessage,
3878 &cmc), 3913 &cmc),
3879 GNUNET_MQ_hd_var_size (backchannel_encapsulation, 3914 GNUNET_MQ_hd_var_size (backchannel_encapsulation,
3880 GNUNET_MESSAGE_TYPE_TRANSPORT_BACKCHANNEL_ENCAPSULATION, 3915 GNUNET_MESSAGE_TYPE_TRANSPORT_BACKCHANNEL_ENCAPSULATION,
3881 struct TransportBackchannelEncapsulationMessage, 3916 struct TransportBackchannelEncapsulationMessage,
3882 &cmc), 3917 &cmc),
3883 GNUNET_MQ_hd_var_size (dv_learn, 3918 GNUNET_MQ_hd_var_size (dv_learn,
3884 GNUNET_MESSAGE_TYPE_TRANSPORT_DV_LEARN, 3919 GNUNET_MESSAGE_TYPE_TRANSPORT_DV_LEARN,
3885 struct TransportDVLearn, 3920 struct TransportDVLearn,
3886 &cmc), 3921 &cmc),
3887 GNUNET_MQ_hd_var_size (dv_box, 3922 GNUNET_MQ_hd_var_size (dv_box,
3888 GNUNET_MESSAGE_TYPE_TRANSPORT_DV_BOX, 3923 GNUNET_MESSAGE_TYPE_TRANSPORT_DV_BOX,
3889 struct TransportDVBox, 3924 struct TransportDVBox,
3890 &cmc), 3925 &cmc),
3926 GNUNET_MQ_hd_fixed_size (validation_challenge,
3927 GNUNET_MESSAGE_TYPE_TRANSPORT_ADDRESS_VALIDATION_CHALLENGE,
3928 struct TransportValidationChallenge,
3929 &cmc),
3930 GNUNET_MQ_hd_fixed_size (validation_response,
3931 GNUNET_MESSAGE_TYPE_TRANSPORT_ADDRESS_VALIDATION_RESPONSE,
3932 struct TransportValidationResponse,
3933 &cmc),
3891 GNUNET_MQ_handler_end() 3934 GNUNET_MQ_handler_end()
3892 }; 3935 };
3893 int ret; 3936 int ret;
3894 3937
3895 ret = GNUNET_MQ_handle_message (handlers, 3938 ret = GNUNET_MQ_handle_message (handlers,
3896 msg); 3939 msg);
3897 if (GNUNET_SYSERR == ret) 3940 if (GNUNET_SYSERR == ret)
3898 { 3941 {
3899 GNUNET_break (0); 3942 GNUNET_break (0);
@@ -3905,7 +3948,7 @@ demultiplex_with_cmc (struct CommunicatorMessageContext *cmc,
3905 { 3948 {
3906 /* unencapsulated 'raw' message */ 3949 /* unencapsulated 'raw' message */
3907 handle_raw_message (&cmc, 3950 handle_raw_message (&cmc,
3908 msg); 3951 msg);
3909 } 3952 }
3910} 3953}
3911 3954
@@ -4145,7 +4188,6 @@ transmit_on_queue (void *cls)
4145{ 4188{
4146 struct Queue *queue = cls; 4189 struct Queue *queue = cls;
4147 struct Neighbour *n = queue->neighbour; 4190 struct Neighbour *n = queue->neighbour;
4148 struct QueueEntry *qe;
4149 struct PendingMessage *pm; 4191 struct PendingMessage *pm;
4150 struct PendingMessage *s; 4192 struct PendingMessage *s;
4151 uint32_t overhead; 4193 uint32_t overhead;
@@ -4191,27 +4233,32 @@ transmit_on_queue (void *cls)
4191 } 4233 }
4192 4234
4193 /* Pass 's' for transission to the communicator */ 4235 /* Pass 's' for transission to the communicator */
4194 qe = GNUNET_new (struct QueueEntry);
4195 qe->mid = queue->mid_gen++;
4196 qe->queue = queue;
4197 // qe->pm = s; // FIXME: not so easy, reference management on 'free(s)'!
4198 GNUNET_CONTAINER_DLL_insert (queue->queue_head,
4199 queue->queue_tail,
4200 qe);
4201 env = GNUNET_MQ_msg_extra (smt, 4236 env = GNUNET_MQ_msg_extra (smt,
4202 s->bytes_msg, 4237 s->bytes_msg,
4203 GNUNET_MESSAGE_TYPE_TRANSPORT_SEND_MSG); 4238 GNUNET_MESSAGE_TYPE_TRANSPORT_SEND_MSG);
4204 smt->qid = queue->qid; 4239 smt->qid = queue->qid;
4205 smt->mid = qe->mid; 4240 smt->mid = queue->mid_gen;
4206 smt->receiver = n->pid; 4241 smt->receiver = n->pid;
4207 memcpy (&smt[1], 4242 memcpy (&smt[1],
4208 &s[1], 4243 &s[1],
4209 s->bytes_msg); 4244 s->bytes_msg);
4210 GNUNET_assert (CT_COMMUNICATOR == queue->tc->type); 4245 {
4211 queue->queue_length++; 4246 /* Pass the env to the communicator of queue for transmission. */
4212 queue->tc->details.communicator.total_queue_length++; 4247 struct QueueEntry *qe;
4213 GNUNET_MQ_send (queue->tc->mq, 4248
4214 env); 4249 qe = GNUNET_new (struct QueueEntry);
4250 qe->mid = queue->mid_gen++;
4251 qe->queue = queue;
4252 // qe->pm = s; // FIXME: not so easy, reference management on 'free(s)'!
4253 GNUNET_CONTAINER_DLL_insert (queue->queue_head,
4254 queue->queue_tail,
4255 qe);
4256 GNUNET_assert (CT_COMMUNICATOR == queue->tc->type);
4257 queue->queue_length++;
4258 queue->tc->details.communicator.total_queue_length++;
4259 GNUNET_MQ_send (queue->tc->mq,
4260 env);
4261 }
4215 4262
4216 // FIXME: do something similar to the logic below 4263 // FIXME: do something similar to the logic below
4217 // in defragmentation / reliability ACK handling! 4264 // in defragmentation / reliability ACK handling!
@@ -4719,13 +4766,17 @@ static void
4719validation_transmit_on_queue (struct Queue *q, 4766validation_transmit_on_queue (struct Queue *q,
4720 struct ValidationState *vs) 4767 struct ValidationState *vs)
4721{ 4768{
4722 struct TransportValidationChallenge tvc; 4769 struct GNUNET_MQ_Envelope *env;
4770 struct TransportValidationChallenge *tvc;
4723 4771
4724 vs->last_challenge_use = GNUNET_TIME_absolute_get (); 4772 vs->last_challenge_use = GNUNET_TIME_absolute_get ();
4725 tvc.reserved = htonl (0); 4773 env = GNUNET_MQ_msg (tvc,
4726 tvc.challenge = vs->challenge; 4774 GNUNET_MESSAGE_TYPE_TRANSPORT_ADDRESS_VALIDATION_CHALLENGE);
4727 tvc.sender_time = GNUNET_TIME_absolute_hton (vs->last_challenge_use); 4775 tvc->reserved = htonl (0);
4728 // FIXME: actually send on queue! 4776 tvc->challenge = vs->challenge;
4777 tvc->sender_time = GNUNET_TIME_absolute_hton (vs->last_challenge_use);
4778 GNUNET_MQ_send (q->tc->mq,
4779 env);
4729} 4780}
4730 4781
4731 4782
@@ -5163,75 +5214,58 @@ check_known_address (void *cls,
5163 5214
5164 5215
5165/** 5216/**
5166 * Given another peers address, consider checking it for validity 5217 * Start address validation.
5167 * and then adding it to the Peerstore.
5168 * 5218 *
5169 * @param cls a `struct TransportClient` 5219 * @param pid peer the @a address is for
5170 * @param hdr message containing the raw address data and 5220 * @param address an address to reach @a pid (presumably)
5171 * signature in the body, see #GNUNET_HELLO_extract_address() 5221 * @param expiration when did @a pid claim @a address will become invalid
5222 * @param nt network type of @a address
5172 */ 5223 */
5173static void 5224static void
5174handle_address_consider_verify (void *cls, 5225start_address_validation (const struct GNUNET_PeerIdentity *pid,
5175 const struct GNUNET_TRANSPORT_AddressToVerify *hdr) 5226 const char *address,
5227 struct GNUNET_TIME_Absolute expiration,
5228 enum GNUNET_NetworkType nt)
5176{ 5229{
5177 char *address;
5178 enum GNUNET_NetworkType nt;
5179 struct GNUNET_TIME_Absolute expiration;
5180 struct GNUNET_TIME_Absolute now; 5230 struct GNUNET_TIME_Absolute now;
5181 struct ValidationState *vs; 5231 struct ValidationState *vs;
5232 struct CheckKnownAddressContext ckac = {
5233 .address = address,
5234 .vs = NULL
5235 };
5236
5182 5237
5183 (void) cls;
5184 // FIXME: checking that we know this address already should
5185 // be done BEFORE checking the signature => HELLO API change!
5186 // FIXME: pre-check: rate-limit signature verification / validation?!
5187 address = GNUNET_HELLO_extract_address (&hdr[1],
5188 ntohs (hdr->header.size) - sizeof (*hdr),
5189 &hdr->peer,
5190 &nt,
5191 &expiration);
5192 if (NULL == address)
5193 {
5194 GNUNET_break_op (0);
5195 return;
5196 }
5197 if (0 == GNUNET_TIME_absolute_get_remaining (expiration).rel_value_us) 5238 if (0 == GNUNET_TIME_absolute_get_remaining (expiration).rel_value_us)
5198 return; /* expired */ 5239 return; /* expired */
5199 {
5200 struct CheckKnownAddressContext ckac = {
5201 .address = address,
5202 .vs = NULL
5203 };
5204 5240
5205 (void) GNUNET_CONTAINER_multipeermap_get_multiple (validation_map, 5241 (void) GNUNET_CONTAINER_multipeermap_get_multiple (validation_map,
5206 &hdr->peer, 5242 pid,
5207 &check_known_address, 5243 &check_known_address,
5208 &ckac); 5244 &ckac);
5209 if (NULL != (vs = ckac.vs)) 5245 if (NULL != (vs = ckac.vs))
5246 {
5247 /* if 'vs' is not currently valid, we need to speed up retrying the validation */
5248 if (vs->validated_until.abs_value_us < vs->next_challenge.abs_value_us)
5210 { 5249 {
5211 /* if 'vs' is not currently valid, we need to speed up retrying the validation */ 5250 /* reduce backoff as we got a fresh advertisement */
5212 if (vs->validated_until.abs_value_us < vs->next_challenge.abs_value_us) 5251 vs->challenge_backoff = GNUNET_TIME_relative_min (FAST_VALIDATION_CHALLENGE_FREQ,
5213 { 5252 GNUNET_TIME_relative_divide (vs->challenge_backoff,
5214 /* reduce backoff as we got a fresh advertisement */ 5253 2));
5215 vs->challenge_backoff = GNUNET_TIME_relative_min (FAST_VALIDATION_CHALLENGE_FREQ, 5254 update_next_challenge_time (vs,
5216 GNUNET_TIME_relative_divide (vs->challenge_backoff, 5255 GNUNET_TIME_relative_to_absolute (vs->challenge_backoff));
5217 2));
5218 update_next_challenge_time (vs,
5219 GNUNET_TIME_relative_to_absolute (vs->challenge_backoff));
5220 }
5221 GNUNET_free (address);
5222 return;
5223 } 5256 }
5257 return;
5224 } 5258 }
5225 now = GNUNET_TIME_absolute_get(); 5259 now = GNUNET_TIME_absolute_get();
5226 vs = GNUNET_new (struct ValidationState); 5260 vs = GNUNET_new (struct ValidationState);
5227 vs->pid = hdr->peer; 5261 vs->pid = *pid;
5228 vs->valid_until = expiration; 5262 vs->valid_until = expiration;
5229 vs->first_challenge_use = now; 5263 vs->first_challenge_use = now;
5230 vs->validation_rtt = GNUNET_TIME_UNIT_FOREVER_REL; 5264 vs->validation_rtt = GNUNET_TIME_UNIT_FOREVER_REL;
5231 GNUNET_CRYPTO_random_block (GNUNET_CRYPTO_QUALITY_NONCE, 5265 GNUNET_CRYPTO_random_block (GNUNET_CRYPTO_QUALITY_NONCE,
5232 &vs->challenge, 5266 &vs->challenge,
5233 sizeof (vs->challenge)); 5267 sizeof (vs->challenge));
5234 vs->address = address; 5268 vs->address = GNUNET_strdup (address);
5235 vs->nt = nt; 5269 vs->nt = nt;
5236 GNUNET_assert (GNUNET_YES == 5270 GNUNET_assert (GNUNET_YES ==
5237 GNUNET_CONTAINER_multipeermap_put (validation_map, 5271 GNUNET_CONTAINER_multipeermap_put (validation_map,
@@ -5244,6 +5278,46 @@ handle_address_consider_verify (void *cls,
5244 5278
5245 5279
5246/** 5280/**
5281 * Given another peers address, consider checking it for validity
5282 * and then adding it to the Peerstore.
5283 *
5284 * @param cls a `struct TransportClient`
5285 * @param hdr message containing the raw address data and
5286 * signature in the body, see #GNUNET_HELLO_extract_address()
5287 */
5288static void
5289handle_address_consider_verify (void *cls,
5290 const struct GNUNET_TRANSPORT_AddressToVerify *hdr)
5291{
5292 struct TransportClient *tc = cls;
5293 char *address;
5294 enum GNUNET_NetworkType nt;
5295 struct GNUNET_TIME_Absolute expiration;
5296
5297 (void) cls;
5298 // FIXME: checking that we know this address already should
5299 // be done BEFORE checking the signature => HELLO API change!
5300 // FIXME: pre-check: rate-limit signature verification / validation?!
5301 address = GNUNET_HELLO_extract_address (&hdr[1],
5302 ntohs (hdr->header.size) - sizeof (*hdr),
5303 &hdr->peer,
5304 &nt,
5305 &expiration);
5306 if (NULL == address)
5307 {
5308 GNUNET_break_op (0);
5309 return;
5310 }
5311 start_address_validation (&hdr->peer,
5312 address,
5313 expiration,
5314 nt);
5315 GNUNET_free (address);
5316 GNUNET_SERVICE_client_continue (tc->client);
5317}
5318
5319
5320/**
5247 * Check #GNUNET_MESSAGE_TYPE_TRANSPORT_REQUEST_HELLO_VALIDATION 5321 * Check #GNUNET_MESSAGE_TYPE_TRANSPORT_REQUEST_HELLO_VALIDATION
5248 * messages. 5322 * messages.
5249 * 5323 *
@@ -5271,7 +5345,13 @@ static void
5271handle_request_hello_validation (void *cls, 5345handle_request_hello_validation (void *cls,
5272 const struct RequestHelloValidationMessage *m) 5346 const struct RequestHelloValidationMessage *m)
5273{ 5347{
5274 // FIXME: implement validation! 5348 struct TransportClient *tc = cls;
5349
5350 start_address_validation (&m->peer,
5351 (const char *) &m[1],
5352 GNUNET_TIME_absolute_ntoh (m->expiration),
5353 (enum GNUNET_NetworkType) ntohl (m->nt));
5354 GNUNET_SERVICE_client_continue (tc->client);
5275} 5355}
5276 5356
5277 5357
diff --git a/src/transport/transport.h b/src/transport/transport.h
index fe1044383..7e0d9c2d4 100644
--- a/src/transport/transport.h
+++ b/src/transport/transport.h
@@ -1146,7 +1146,7 @@ struct ExpressPreferenceMessage
1146struct RequestHelloValidationMessage 1146struct RequestHelloValidationMessage
1147{ 1147{
1148 1148
1149 /** 1149 /**
1150 * Type is #GNUNET_MESSAGE_TYPE_TRANSPORT_REQUEST_HELLO_VALIDATION. 1150 * Type is #GNUNET_MESSAGE_TYPE_TRANSPORT_REQUEST_HELLO_VALIDATION.
1151 */ 1151 */
1152 struct GNUNET_MessageHeader header; 1152 struct GNUNET_MessageHeader header;