diff options
-rw-r--r-- | src/mesh/gnunet-service-mesh-enc.c | 240 |
1 files changed, 62 insertions, 178 deletions
diff --git a/src/mesh/gnunet-service-mesh-enc.c b/src/mesh/gnunet-service-mesh-enc.c index e1bcc686d..6fdd5d601 100644 --- a/src/mesh/gnunet-service-mesh-enc.c +++ b/src/mesh/gnunet-service-mesh-enc.c | |||
@@ -3847,140 +3847,57 @@ queue_destroy (struct MeshPeerQueue *queue, int clear_cls) | |||
3847 | { | 3847 | { |
3848 | struct MeshFlowControl *fc; | 3848 | struct MeshFlowControl *fc; |
3849 | 3849 | ||
3850 | fc = queue->peer->fc; | ||
3850 | if (GNUNET_YES == clear_cls) | 3851 | if (GNUNET_YES == clear_cls) |
3851 | { | 3852 | { |
3852 | switch (queue->type) | 3853 | switch (queue->type) |
3853 | { | 3854 | { |
3854 | case GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY: | 3855 | case GNUNET_MESSAGE_TYPE_MESH_CONNECTION_DESTROY: |
3855 | GNUNET_log (GNUNET_ERROR_TYPE_INFO, " cancelling TUNNEL_DESTROY\n"); | 3856 | GNUNET_log (GNUNET_ERROR_TYPE_INFO, "destroying CONNECTION_DESTROY\n"); |
3856 | GNUNET_break (GNUNET_YES == queue->tunnel->destroy); | 3857 | GNUNET_break (GNUNET_YES == queue->c->destroy); |
3857 | /* fall through */ | 3858 | /* fall through */ |
3858 | case GNUNET_MESSAGE_TYPE_MESH_UNICAST: | 3859 | case GNUNET_MESSAGE_TYPE_MESH_FWD: |
3859 | case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: | 3860 | case GNUNET_MESSAGE_TYPE_MESH_BCK: |
3860 | case GNUNET_MESSAGE_TYPE_MESH_ACK: | 3861 | case GNUNET_MESSAGE_TYPE_MESH_ACK: |
3861 | case GNUNET_MESSAGE_TYPE_MESH_UNICAST_ACK: | ||
3862 | case GNUNET_MESSAGE_TYPE_MESH_TO_ORIG_ACK: | ||
3863 | case GNUNET_MESSAGE_TYPE_MESH_POLL: | 3862 | case GNUNET_MESSAGE_TYPE_MESH_POLL: |
3864 | case GNUNET_MESSAGE_TYPE_MESH_FWD_KEEPALIVE: | 3863 | case GNUNET_MESSAGE_TYPE_MESH_CONNECTION_ACK: |
3865 | case GNUNET_MESSAGE_TYPE_MESH_BCK_KEEPALIVE: | 3864 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " prebuilt message\n"); |
3866 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 3865 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type %s\n", |
3867 | " prebuilt message\n"); | ||
3868 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
3869 | " type %s\n", | ||
3870 | GNUNET_MESH_DEBUG_M2S (queue->type)); | 3866 | GNUNET_MESH_DEBUG_M2S (queue->type)); |
3871 | break; | 3867 | break; |
3868 | |||
3872 | case GNUNET_MESSAGE_TYPE_MESH_CONNECTION_CREATE: | 3869 | case GNUNET_MESSAGE_TYPE_MESH_CONNECTION_CREATE: |
3873 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type create path\n"); | 3870 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, " type create path\n"); |
3874 | break; | 3871 | break; |
3872 | |||
3875 | default: | 3873 | default: |
3876 | GNUNET_break (0); | 3874 | GNUNET_break (0); |
3877 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | 3875 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, " type %s unknown!\n", |
3878 | " type %s unknown!\n", | ||
3879 | GNUNET_MESH_DEBUG_M2S (queue->type)); | 3876 | GNUNET_MESH_DEBUG_M2S (queue->type)); |
3880 | } | 3877 | } |
3881 | GNUNET_free_non_null (queue->cls); | 3878 | GNUNET_free_non_null (queue->cls); |
3882 | } | 3879 | } |
3883 | GNUNET_CONTAINER_DLL_remove (queue->peer->queue_head, | 3880 | GNUNET_CONTAINER_DLL_remove (fc->queue_head, fc->queue_tail, queue); |
3884 | queue->peer->queue_tail, | ||
3885 | queue); | ||
3886 | |||
3887 | /* Delete from appropriate fc in the tunnel */ | ||
3888 | if (GNUNET_MESSAGE_TYPE_MESH_UNICAST == queue->type || | ||
3889 | GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN == queue->type ) | ||
3890 | { | ||
3891 | if (queue->peer->id == queue->tunnel->prev_hop) | ||
3892 | fc = &queue->tunnel->prev_fc; | ||
3893 | else if (queue->peer->id == queue->tunnel->next_hop) | ||
3894 | fc = &queue->tunnel->next_fc; | ||
3895 | else | ||
3896 | { | ||
3897 | GNUNET_break (0); | ||
3898 | GNUNET_free (queue); | ||
3899 | return; | ||
3900 | } | ||
3901 | fc->queue_n--; | ||
3902 | } | ||
3903 | GNUNET_free (queue); | ||
3904 | } | ||
3905 | |||
3906 | |||
3907 | /** | ||
3908 | * @brief Get the next transmittable message from the queue. | ||
3909 | * | ||
3910 | * This will be the head, except in the case of being a data packet | ||
3911 | * not allowed by the destination peer. | ||
3912 | * | ||
3913 | * @param peer Destination peer. | ||
3914 | * | ||
3915 | * @return The next viable MeshPeerQueue element to send to that peer. | ||
3916 | * NULL when there are no transmittable messages. | ||
3917 | */ | ||
3918 | struct MeshPeerQueue * | ||
3919 | queue_get_next (const struct MeshPeer *peer) | ||
3920 | { | ||
3921 | struct MeshPeerQueue *q; | ||
3922 | 3881 | ||
3923 | struct GNUNET_MESH_Data *dmsg; | 3882 | fc->queue_n--; |
3924 | struct MeshTunnel2 *t; | ||
3925 | uint32_t pid; | ||
3926 | uint32_t ack; | ||
3927 | 3883 | ||
3928 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "* selecting message\n"); | 3884 | GNUNET_free (queue); |
3929 | for (q = peer->fc->queue_head; NULL != q; q = q->next) | ||
3930 | { | ||
3931 | t = q->tunnel; | ||
3932 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
3933 | "* %s\n", | ||
3934 | GNUNET_MESH_DEBUG_M2S (q->type)); | ||
3935 | dmsg = (struct GNUNET_MESH_Data *) q->cls; | ||
3936 | pid = ntohl (dmsg->pid); | ||
3937 | switch (q->type) | ||
3938 | { | ||
3939 | case GNUNET_MESSAGE_TYPE_MESH_UNICAST: | ||
3940 | ack = t->next_fc.last_ack_recv; | ||
3941 | break; | ||
3942 | case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: | ||
3943 | ack = t->prev_fc.last_ack_recv; | ||
3944 | break; | ||
3945 | default: | ||
3946 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
3947 | "* OK!\n"); | ||
3948 | return q; | ||
3949 | } | ||
3950 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
3951 | "* ACK: %u, PID: %u, MID: %u\n", | ||
3952 | ack, pid, ntohl (dmsg->mid)); | ||
3953 | if (GNUNET_NO == GMC_is_pid_bigger (pid, ack)) | ||
3954 | { | ||
3955 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
3956 | "* OK!\n"); | ||
3957 | return q; | ||
3958 | } | ||
3959 | else | ||
3960 | { | ||
3961 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
3962 | "* NEXT!\n"); | ||
3963 | } | ||
3964 | } | ||
3965 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
3966 | "* nothing found\n"); | ||
3967 | return NULL; | ||
3968 | } | 3885 | } |
3969 | 3886 | ||
3970 | |||
3971 | static size_t | 3887 | static size_t |
3972 | queue_send (void *cls, size_t size, void *buf) | 3888 | queue_send (void *cls, size_t size, void *buf) |
3973 | { | 3889 | { |
3974 | struct MeshPeer *peer = cls; | 3890 | struct MeshPeer *peer = cls; |
3891 | const struct GNUNET_PeerIdentity *dst_id; | ||
3975 | struct GNUNET_MessageHeader *msg; | 3892 | struct GNUNET_MessageHeader *msg; |
3976 | struct MeshPeerQueue *queue; | 3893 | struct MeshPeerQueue *queue; |
3977 | struct MeshTunnel2 *t; | 3894 | struct MeshTunnel2 *t; |
3978 | struct GNUNET_PeerIdentity *dst_id; | ||
3979 | struct MeshFlowControl *fc; | 3895 | struct MeshFlowControl *fc; |
3980 | struct MeshConnection *c; | 3896 | struct MeshConnection *c; |
3981 | size_t data_size; | 3897 | size_t data_size; |
3982 | uint32_t pid; | 3898 | uint32_t pid; |
3983 | uint16_t type; | 3899 | uint16_t type; |
3900 | int fwd; | ||
3984 | 3901 | ||
3985 | fc = peer->fc; | 3902 | fc = peer->fc; |
3986 | if (NULL == fc) | 3903 | if (NULL == fc) |
@@ -3997,28 +3914,21 @@ queue_send (void *cls, size_t size, void *buf) | |||
3997 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "* Buffer size 0.\n"); | 3914 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "* Buffer size 0.\n"); |
3998 | return 0; | 3915 | return 0; |
3999 | } | 3916 | } |
4000 | queue = queue_get_next (peer); | 3917 | queue = fc->queue_head; |
4001 | 3918 | ||
4002 | /* Queue has no internal mesh traffic nor sendable payload */ | 3919 | /* Queue has no traffic */ |
4003 | if (NULL == queue) | 3920 | if (NULL == queue) |
4004 | { | 3921 | { |
4005 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "* not ready, return\n"); | 3922 | GNUNET_break (0); /* Core tmt_rdy should've been canceled */ |
4006 | if (NULL == fc->queue_head) | ||
4007 | GNUNET_break (0); /* Core tmt_rdy should've been canceled */ | ||
4008 | return 0; | 3923 | return 0; |
4009 | } | 3924 | } |
4010 | 3925 | ||
4011 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "* not empty\n"); | 3926 | dst_id = GNUNET_PEER_resolve2 (peer->id); |
4012 | 3927 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "* towards %s\n", GNUNET_i2s (dst_id)); | |
4013 | dst_id = GNUNET_PEER_resolve (peer->id); | ||
4014 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
4015 | "* towards %s\n", | ||
4016 | GNUNET_i2s (dst_id)); | ||
4017 | /* Check if buffer size is enough for the message */ | 3928 | /* Check if buffer size is enough for the message */ |
4018 | if (queue->size > size) | 3929 | if (queue->size > size) |
4019 | { | 3930 | { |
4020 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 3931 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "* not enough room, reissue\n"); |
4021 | "* not enough room, reissue\n"); | ||
4022 | fc->core_transmit = | 3932 | fc->core_transmit = |
4023 | GNUNET_CORE_notify_transmit_ready (core_handle, | 3933 | GNUNET_CORE_notify_transmit_ready (core_handle, |
4024 | GNUNET_NO, | 3934 | GNUNET_NO, |
@@ -4039,16 +3949,12 @@ queue_send (void *cls, size_t size, void *buf) | |||
4039 | /* Fill buf */ | 3949 | /* Fill buf */ |
4040 | switch (queue->type) | 3950 | switch (queue->type) |
4041 | { | 3951 | { |
4042 | case 0: | 3952 | case GNUNET_MESSAGE_TYPE_MESH_CONNECTION_DESTROY: |
3953 | case GNUNET_MESSAGE_TYPE_MESH_CONNECTION_BROKEN: | ||
3954 | case GNUNET_MESSAGE_TYPE_MESH_FWD: | ||
3955 | case GNUNET_MESSAGE_TYPE_MESH_BCK: | ||
4043 | case GNUNET_MESSAGE_TYPE_MESH_ACK: | 3956 | case GNUNET_MESSAGE_TYPE_MESH_ACK: |
4044 | case GNUNET_MESSAGE_TYPE_MESH_UNICAST_ACK: | ||
4045 | case GNUNET_MESSAGE_TYPE_MESH_TO_ORIG_ACK: | ||
4046 | case GNUNET_MESSAGE_TYPE_MESH_POLL: | 3957 | case GNUNET_MESSAGE_TYPE_MESH_POLL: |
4047 | case GNUNET_MESSAGE_TYPE_MESH_PATH_BROKEN: | ||
4048 | case GNUNET_MESSAGE_TYPE_MESH_PATH_DESTROY: | ||
4049 | case GNUNET_MESSAGE_TYPE_MESH_TUNNEL_DESTROY: | ||
4050 | case GNUNET_MESSAGE_TYPE_MESH_FWD_KEEPALIVE: | ||
4051 | case GNUNET_MESSAGE_TYPE_MESH_BCK_KEEPALIVE: | ||
4052 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 3958 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
4053 | "* raw: %s\n", | 3959 | "* raw: %s\n", |
4054 | GNUNET_MESH_DEBUG_M2S (queue->type)); | 3960 | GNUNET_MESH_DEBUG_M2S (queue->type)); |
@@ -4065,95 +3971,73 @@ queue_send (void *cls, size_t size, void *buf) | |||
4065 | break; | 3971 | break; |
4066 | case GNUNET_MESSAGE_TYPE_MESH_CONNECTION_ACK: | 3972 | case GNUNET_MESSAGE_TYPE_MESH_CONNECTION_ACK: |
4067 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "* path ack\n"); | 3973 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "* path ack\n"); |
4068 | if (NULL != t->client) | 3974 | if (NULL != c->t->channel_head) |
4069 | data_size = send_core_connection_ack (queue->cls, size, buf); | 3975 | data_size = send_core_connection_ack (queue->cls, size, buf); |
4070 | else | 3976 | else |
4071 | data_size = send_core_data_raw (queue->cls, size, buf); | 3977 | data_size = send_core_data_raw (queue->cls, size, buf); |
4072 | break; | 3978 | break; |
4073 | default: | 3979 | default: |
4074 | GNUNET_break (0); | 3980 | GNUNET_break (0); |
4075 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | 3981 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "* type unknown: %u\n", |
4076 | "* type unknown: %u\n", | ||
4077 | queue->type); | 3982 | queue->type); |
4078 | data_size = 0; | 3983 | data_size = 0; |
4079 | } | 3984 | } |
4080 | 3985 | ||
3986 | fc->queue_n--; | ||
3987 | |||
4081 | if (0 < drop_percent && | 3988 | if (0 < drop_percent && |
4082 | GNUNET_CRYPTO_random_u32(GNUNET_CRYPTO_QUALITY_WEAK, 101) < drop_percent) | 3989 | GNUNET_CRYPTO_random_u32(GNUNET_CRYPTO_QUALITY_WEAK, 101) < drop_percent) |
4083 | { | 3990 | { |
4084 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | 3991 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, |
4085 | "Dropping message of type %s\n", | 3992 | "Dropping message of type %s\n", |
4086 | GNUNET_MESH_DEBUG_M2S(queue->type)); | 3993 | GNUNET_MESH_DEBUG_M2S (queue->type)); |
4087 | data_size = 0; | 3994 | data_size = 0; |
4088 | } | 3995 | } |
4089 | /* Free queue, but cls was freed by send_core_* */ | 3996 | /* Free queue, but cls was freed by send_core_* */ |
4090 | queue_destroy (queue, GNUNET_NO); | 3997 | queue_destroy (queue, GNUNET_NO); |
4091 | 3998 | ||
4092 | /* Send ACK if needed, after accounting for sent ID in fc->queue_n */ | 3999 | /* Send ACK if needed, after accounting for sent ID in fc->queue_n */ |
4093 | pid = ((struct GNUNET_MESH_Data *) buf)->pid; | 4000 | fwd = GNUNET_NO; |
4094 | pid = ntohl (pid); | ||
4095 | switch (type) | 4001 | switch (type) |
4096 | { | 4002 | { |
4097 | case GNUNET_MESSAGE_TYPE_MESH_UNICAST: | 4003 | case GNUNET_MESSAGE_TYPE_MESH_FWD: |
4098 | t->next_fc.last_pid_sent = pid; | 4004 | fwd = GNUNET_YES; |
4099 | tunnel_send_ack (t, GNUNET_MESSAGE_TYPE_MESH_UNICAST, GNUNET_YES); | 4005 | /* fall through */ |
4100 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 4006 | case GNUNET_MESSAGE_TYPE_MESH_BCK: |
4101 | "!!! FWD %u\n", | 4007 | pid = ntohl ( ((struct GNUNET_MESH_Encrypted *) buf)->pid ); |
4102 | ntohl ( ((struct GNUNET_MESH_Data *) buf)->mid ) ); | 4008 | fc->last_pid_sent = pid; |
4103 | break; | 4009 | connection_send_ack (c, fwd); |
4104 | case GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN: | ||
4105 | t->prev_fc.last_pid_sent = pid; | ||
4106 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
4107 | "!!! BCK %u\n", | ||
4108 | ntohl ( ((struct GNUNET_MESH_Data *) buf)->mid ) ); | ||
4109 | tunnel_send_ack (t, GNUNET_MESSAGE_TYPE_MESH_TO_ORIGIN, GNUNET_NO); | ||
4110 | break; | 4010 | break; |
4111 | default: | 4011 | default: |
4112 | break; | 4012 | break; |
4113 | } | 4013 | } |
4114 | 4014 | ||
4115 | /* If more data in queue, send next */ | 4015 | /* If more data in queue, send next */ |
4116 | queue = queue_get_next (peer); | 4016 | queue = fc->queue_head; |
4117 | if (NULL != queue) | 4017 | if (NULL != queue) |
4118 | { | 4018 | { |
4119 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "* more data!\n"); | 4019 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "* more data!\n"); |
4120 | if (NULL == peer->core_transmit) { | 4020 | if (NULL == fc->core_transmit) { |
4121 | peer->core_transmit = | 4021 | peer->fc->core_transmit = |
4122 | GNUNET_CORE_notify_transmit_ready(core_handle, | 4022 | GNUNET_CORE_notify_transmit_ready(core_handle, |
4123 | 0, | 4023 | 0, |
4124 | 0, | 4024 | 0, |
4125 | GNUNET_TIME_UNIT_FOREVER_REL, | 4025 | GNUNET_TIME_UNIT_FOREVER_REL, |
4126 | &dst_id, | 4026 | dst_id, |
4127 | queue->size, | 4027 | queue->size, |
4128 | &queue_send, | 4028 | &queue_send, |
4129 | peer); | 4029 | peer); |
4130 | } | 4030 | } |
4131 | else | 4031 | else |
4132 | { | ||
4133 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
4134 | "* tmt rdy called somewhere else\n"); | ||
4135 | } | ||
4136 | } | ||
4137 | if (peer->id == t->next_hop) | ||
4138 | fc = &t->next_fc; | ||
4139 | else if (peer->id == t->prev_hop) | ||
4140 | fc = &t->prev_fc; | ||
4141 | else | ||
4142 | { | ||
4143 | GNUNET_break (0); | ||
4144 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "id: %u, next: %u, prev: %u\n", | ||
4145 | peer->id, t->next_hop, t->prev_hop); | ||
4146 | return data_size; | ||
4147 | } | ||
4148 | if (NULL != peer->queue_head) | ||
4149 | { | ||
4150 | if (GNUNET_SCHEDULER_NO_TASK == fc->poll_task && fc->queue_n > 0) | ||
4151 | { | 4032 | { |
4152 | GNUNET_log (GNUNET_ERROR_TYPE_INFO, | 4033 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
4153 | "* %s starting poll timeout\n", | 4034 | "* tmt rdy called somewhere else\n"); |
4154 | GNUNET_i2s (&my_full_id)); | 4035 | } |
4155 | fc->poll_task = GNUNET_SCHEDULER_add_delayed (fc->poll_time, | 4036 | if (GNUNET_SCHEDULER_NO_TASK == fc->poll_task) |
4156 | &tunnel_poll, fc); | 4037 | { |
4038 | GNUNET_log (GNUNET_ERROR_TYPE_INFO, "* %s starting poll timeout\n"); | ||
4039 | fc->poll_task = | ||
4040 | GNUNET_SCHEDULER_add_delayed (fc->poll_time, &peer_poll, fc); | ||
4157 | } | 4041 | } |
4158 | } | 4042 | } |
4159 | else | 4043 | else |