diff options
Diffstat (limited to 'net/ipv4/ipvs/ip_vs_sync.c')
| -rw-r--r-- | net/ipv4/ipvs/ip_vs_sync.c | 24 |
1 files changed, 20 insertions, 4 deletions
diff --git a/net/ipv4/ipvs/ip_vs_sync.c b/net/ipv4/ipvs/ip_vs_sync.c index 0d4d9721cbd4..bd930efc18da 100644 --- a/net/ipv4/ipvs/ip_vs_sync.c +++ b/net/ipv4/ipvs/ip_vs_sync.c | |||
| @@ -284,6 +284,7 @@ static void ip_vs_process_message(const char *buffer, const size_t buflen) | |||
| 284 | struct ip_vs_sync_conn_options *opt; | 284 | struct ip_vs_sync_conn_options *opt; |
| 285 | struct ip_vs_conn *cp; | 285 | struct ip_vs_conn *cp; |
| 286 | struct ip_vs_protocol *pp; | 286 | struct ip_vs_protocol *pp; |
| 287 | struct ip_vs_dest *dest; | ||
| 287 | char *p; | 288 | char *p; |
| 288 | int i; | 289 | int i; |
| 289 | 290 | ||
| @@ -317,20 +318,34 @@ static void ip_vs_process_message(const char *buffer, const size_t buflen) | |||
| 317 | s->caddr, s->cport, | 318 | s->caddr, s->cport, |
| 318 | s->vaddr, s->vport); | 319 | s->vaddr, s->vport); |
| 319 | if (!cp) { | 320 | if (!cp) { |
| 321 | /* | ||
| 322 | * Find the appropriate destination for the connection. | ||
| 323 | * If it is not found the connection will remain unbound | ||
| 324 | * but still handled. | ||
| 325 | */ | ||
| 326 | dest = ip_vs_find_dest(s->daddr, s->dport, | ||
| 327 | s->vaddr, s->vport, | ||
| 328 | s->protocol); | ||
| 320 | cp = ip_vs_conn_new(s->protocol, | 329 | cp = ip_vs_conn_new(s->protocol, |
| 321 | s->caddr, s->cport, | 330 | s->caddr, s->cport, |
| 322 | s->vaddr, s->vport, | 331 | s->vaddr, s->vport, |
| 323 | s->daddr, s->dport, | 332 | s->daddr, s->dport, |
| 324 | flags, NULL); | 333 | flags, dest); |
| 334 | if (dest) | ||
| 335 | atomic_dec(&dest->refcnt); | ||
| 325 | if (!cp) { | 336 | if (!cp) { |
| 326 | IP_VS_ERR("ip_vs_conn_new failed\n"); | 337 | IP_VS_ERR("ip_vs_conn_new failed\n"); |
| 327 | return; | 338 | return; |
| 328 | } | 339 | } |
| 329 | cp->state = ntohs(s->state); | 340 | cp->state = ntohs(s->state); |
| 330 | } else if (!cp->dest) { | 341 | } else if (!cp->dest) { |
| 331 | /* it is an entry created by the synchronization */ | 342 | dest = ip_vs_try_bind_dest(cp); |
| 332 | cp->state = ntohs(s->state); | 343 | if (!dest) { |
| 333 | cp->flags = flags | IP_VS_CONN_F_HASHED; | 344 | /* it is an unbound entry created by |
| 345 | * synchronization */ | ||
| 346 | cp->flags = flags | IP_VS_CONN_F_HASHED; | ||
| 347 | } else | ||
| 348 | atomic_dec(&dest->refcnt); | ||
| 334 | } /* Note that we don't touch its state and flags | 349 | } /* Note that we don't touch its state and flags |
| 335 | if it is a normal entry. */ | 350 | if it is a normal entry. */ |
| 336 | 351 | ||
| @@ -342,6 +357,7 @@ static void ip_vs_process_message(const char *buffer, const size_t buflen) | |||
| 342 | p += SIMPLE_CONN_SIZE; | 357 | p += SIMPLE_CONN_SIZE; |
| 343 | 358 | ||
| 344 | atomic_set(&cp->in_pkts, sysctl_ip_vs_sync_threshold[0]); | 359 | atomic_set(&cp->in_pkts, sysctl_ip_vs_sync_threshold[0]); |
| 360 | cp->state = ntohs(s->state); | ||
| 345 | pp = ip_vs_proto_get(s->protocol); | 361 | pp = ip_vs_proto_get(s->protocol); |
| 346 | cp->timeout = pp->timeout_table[cp->state]; | 362 | cp->timeout = pp->timeout_table[cp->state]; |
| 347 | ip_vs_conn_put(cp); | 363 | ip_vs_conn_put(cp); |
