xref: /linux/net/netfilter/ipvs/ip_vs_est.c (revision 91ec2035134982b98fab0609a9fd8480e8217dc1)
1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3  * ip_vs_est.c: simple rate estimator for IPVS
4  *
5  * Authors:     Wensong Zhang <wensong@linuxvirtualserver.org>
6  *
7  * Changes:     Hans Schillstrom <hans.schillstrom@ericsson.com>
8  *              Network name space (netns) aware.
9  *              Global data moved to netns i.e struct netns_ipvs
10  *              Affected data: est_list and est_lock.
11  *              estimation_timer() runs with timer per netns.
12  *              get_stats()) do the per cpu summing.
13  */
14 
15 #define pr_fmt(fmt) "IPVS: " fmt
16 
17 #include <linux/kernel.h>
18 #include <linux/jiffies.h>
19 #include <linux/types.h>
20 #include <linux/interrupt.h>
21 #include <linux/sysctl.h>
22 #include <linux/list.h>
23 #include <linux/rcupdate_wait.h>
24 
25 #include <net/ip_vs.h>
26 
27 /*
28   This code is to estimate rate in a shorter interval (such as 8
29   seconds) for virtual services and real servers. For measure rate in a
30   long interval, it is easy to implement a user level daemon which
31   periodically reads those statistical counters and measure rate.
32 
33   We measure rate during the last 8 seconds every 2 seconds:
34 
35     avgrate = avgrate*(1-W) + rate*W
36 
37     where W = 2^(-2)
38 
39   NOTES.
40 
41   * Average bps is scaled by 2^5, while average pps and cps are scaled by 2^10.
42 
43   * Netlink users can see 64-bit values but sockopt users are restricted
44     to 32-bit values for conns, packets, bps, cps and pps.
45 
46   * A lot of code is taken from net/core/gen_estimator.c
47 
48   KEY POINTS:
49   - cpustats counters are updated per-cpu in SoftIRQ context with BH disabled
50   - kthreads read the cpustats to update the estimators (svcs, dests, total)
51   - the states of estimators can be read (get stats) or modified (zero stats)
52     from processes
53 
54   KTHREADS:
55   - estimators are added initially to est_temp_list and later kthread 0
56     distributes them to one or many kthreads for estimation
57   - kthread contexts are created and attached to array
58   - the kthread tasks are started when first service is added, before that
59     the total stats are not estimated
60   - when configuration (cpulist/nice) is changed, the tasks are restarted
61     by work (est_reload_work)
62   - kthread tasks are stopped while the cpulist is empty
63   - the kthread context holds lists with estimators (chains) which are
64     processed every 2 seconds
65   - as estimators can be added dynamically and in bursts, we try to spread
66     them to multiple chains which are estimated at different time
67   - on start, kthread 0 enters calculation phase to determine the chain limits
68     and the limit of estimators per kthread
69   - est_add_ktid: ktid where to add new ests, can point to empty slot where
70     we should add kt data
71   - data protected by service_mutex: est_temp_list, est_add_ktid,
72     est_kt_count(R/W), est_kt_arr(R/W), est_genid_done, kd->needed(R/W)
73   - data protected by est_mutex: est_genid, est_max_threads, sysctl_est_cpulist,
74     est_cpulist_valid, sysctl_est_nice, est_stopped, sysctl_run_estimation,
75     est_kt_count(R), est_kt_arr(R), kd->needed(R), kd->task (id > 0)
76  */
77 
78 static struct lock_class_key __ipvs_est_key;
79 
80 static void ip_vs_est_calc_phase(struct netns_ipvs *ipvs);
81 static void ip_vs_est_drain_temp_list(struct netns_ipvs *ipvs);
82 
ip_vs_chain_estimation(struct hlist_head * chain)83 static void ip_vs_chain_estimation(struct hlist_head *chain)
84 {
85 	struct ip_vs_estimator *e;
86 	struct ip_vs_cpu_stats *c;
87 	struct ip_vs_stats *s;
88 	u64 rate;
89 
90 	hlist_for_each_entry_rcu(e, chain, list) {
91 		u64 conns, inpkts, outpkts, inbytes, outbytes;
92 		u64 kconns = 0, kinpkts = 0, koutpkts = 0;
93 		u64 kinbytes = 0, koutbytes = 0;
94 		unsigned int start;
95 		int i;
96 
97 		if (kthread_should_stop())
98 			break;
99 
100 		s = container_of(e, struct ip_vs_stats, est);
101 		for_each_possible_cpu(i) {
102 			c = per_cpu_ptr(s->cpustats, i);
103 			do {
104 				start = u64_stats_fetch_begin(&c->syncp);
105 				conns = u64_stats_read(&c->cnt.conns);
106 				inpkts = u64_stats_read(&c->cnt.inpkts);
107 				outpkts = u64_stats_read(&c->cnt.outpkts);
108 				inbytes = u64_stats_read(&c->cnt.inbytes);
109 				outbytes = u64_stats_read(&c->cnt.outbytes);
110 			} while (u64_stats_fetch_retry(&c->syncp, start));
111 			kconns += conns;
112 			kinpkts += inpkts;
113 			koutpkts += outpkts;
114 			kinbytes += inbytes;
115 			koutbytes += outbytes;
116 		}
117 
118 		spin_lock(&s->lock);
119 
120 		s->kstats.conns = kconns;
121 		s->kstats.inpkts = kinpkts;
122 		s->kstats.outpkts = koutpkts;
123 		s->kstats.inbytes = kinbytes;
124 		s->kstats.outbytes = koutbytes;
125 
126 		/* scaled by 2^10, but divided 2 seconds */
127 		rate = (s->kstats.conns - e->last_conns) << 9;
128 		e->last_conns = s->kstats.conns;
129 		e->cps += ((s64)rate - (s64)e->cps) >> 2;
130 
131 		rate = (s->kstats.inpkts - e->last_inpkts) << 9;
132 		e->last_inpkts = s->kstats.inpkts;
133 		e->inpps += ((s64)rate - (s64)e->inpps) >> 2;
134 
135 		rate = (s->kstats.outpkts - e->last_outpkts) << 9;
136 		e->last_outpkts = s->kstats.outpkts;
137 		e->outpps += ((s64)rate - (s64)e->outpps) >> 2;
138 
139 		/* scaled by 2^5, but divided 2 seconds */
140 		rate = (s->kstats.inbytes - e->last_inbytes) << 4;
141 		e->last_inbytes = s->kstats.inbytes;
142 		e->inbps += ((s64)rate - (s64)e->inbps) >> 2;
143 
144 		rate = (s->kstats.outbytes - e->last_outbytes) << 4;
145 		e->last_outbytes = s->kstats.outbytes;
146 		e->outbps += ((s64)rate - (s64)e->outbps) >> 2;
147 		spin_unlock(&s->lock);
148 	}
149 }
150 
ip_vs_tick_estimation(struct ip_vs_est_kt_data * kd,int row)151 static void ip_vs_tick_estimation(struct ip_vs_est_kt_data *kd, int row)
152 {
153 	struct ip_vs_est_tick_data *td;
154 	int cid;
155 
156 	rcu_read_lock();
157 	td = rcu_dereference(kd->ticks[row]);
158 	if (!td)
159 		goto out;
160 	for_each_set_bit(cid, td->present, IPVS_EST_TICK_CHAINS) {
161 		if (kthread_should_stop())
162 			break;
163 		ip_vs_chain_estimation(&td->chains[cid]);
164 		cond_resched_rcu();
165 		td = rcu_dereference(kd->ticks[row]);
166 		if (!td)
167 			break;
168 	}
169 
170 out:
171 	rcu_read_unlock();
172 }
173 
ip_vs_estimation_kthread(void * data)174 static int ip_vs_estimation_kthread(void *data)
175 {
176 	struct ip_vs_est_kt_data *kd = data;
177 	struct netns_ipvs *ipvs = kd->ipvs;
178 	int row = kd->est_row;
179 	unsigned long now;
180 	int id = kd->id;
181 	long gap;
182 
183 	if (id > 0) {
184 		if (!ipvs->est_chain_max)
185 			return 0;
186 	} else {
187 		if (!ipvs->est_chain_max) {
188 			ipvs->est_calc_phase = 1;
189 			/* commit est_calc_phase before reading est_genid */
190 			smp_mb();
191 		}
192 
193 		/* kthread 0 will handle the calc phase */
194 		if (ipvs->est_calc_phase) {
195 			ip_vs_est_calc_phase(ipvs);
196 			if (kthread_should_stop() || !READ_ONCE(ipvs->enable))
197 				return 0;
198 		}
199 	}
200 
201 	while (1) {
202 		if (!id && !hlist_empty(&ipvs->est_temp_list))
203 			ip_vs_est_drain_temp_list(ipvs);
204 		set_current_state(TASK_IDLE);
205 		if (kthread_should_stop())
206 			break;
207 
208 		/* before estimation, check if we should sleep */
209 		now = jiffies;
210 		gap = kd->est_timer - now;
211 		if (gap > 0) {
212 			if (gap > IPVS_EST_TICK) {
213 				kd->est_timer = now - IPVS_EST_TICK;
214 				gap = IPVS_EST_TICK;
215 			}
216 			schedule_timeout(gap);
217 		} else {
218 			__set_current_state(TASK_RUNNING);
219 			if (gap < -8 * IPVS_EST_TICK)
220 				kd->est_timer = now;
221 		}
222 
223 		if (kd->tick_len[row])
224 			ip_vs_tick_estimation(kd, row);
225 
226 		row++;
227 		if (row >= IPVS_EST_NTICKS)
228 			row = 0;
229 		WRITE_ONCE(kd->est_row, row);
230 		kd->est_timer += IPVS_EST_TICK;
231 	}
232 	__set_current_state(TASK_RUNNING);
233 
234 	return 0;
235 }
236 
237 /* Schedule stop/start for kthread tasks */
ip_vs_est_reload_start(struct netns_ipvs * ipvs,bool restart)238 void ip_vs_est_reload_start(struct netns_ipvs *ipvs, bool restart)
239 {
240 	lockdep_assert_held(&ipvs->est_mutex);
241 
242 	/* Ignore reloads before first service is added */
243 	if (!READ_ONCE(ipvs->enable))
244 		return;
245 	ip_vs_est_stopped_recalc(ipvs);
246 	/* Bump the kthread configuration genid if stopping is requested */
247 	if (restart)
248 		atomic_inc(&ipvs->est_genid);
249 	queue_delayed_work(system_dfl_long_wq, &ipvs->est_reload_work, 0);
250 }
251 
252 /* Start kthread task with current configuration */
ip_vs_est_kthread_start(struct netns_ipvs * ipvs,struct ip_vs_est_kt_data * kd)253 int ip_vs_est_kthread_start(struct netns_ipvs *ipvs,
254 			    struct ip_vs_est_kt_data *kd)
255 {
256 	unsigned long now;
257 	int ret = 0;
258 	long gap;
259 
260 	lockdep_assert_held(&ipvs->est_mutex);
261 
262 	if (kd->task)
263 		goto out;
264 	now = jiffies;
265 	gap = kd->est_timer - now;
266 	/* Sync est_timer if task is starting later */
267 	if (abs(gap) > 4 * IPVS_EST_TICK)
268 		kd->est_timer = now;
269 	kd->task = kthread_create(ip_vs_estimation_kthread, kd, "ipvs-e:%d:%d",
270 				  ipvs->gen, kd->id);
271 	if (IS_ERR(kd->task)) {
272 		ret = PTR_ERR(kd->task);
273 		kd->task = NULL;
274 		goto out;
275 	}
276 	get_task_struct(kd->task);
277 
278 	set_user_nice(kd->task, sysctl_est_nice(ipvs));
279 	if (sysctl_est_preferred_cpulist(ipvs))
280 		kthread_affine_preferred(kd->task, sysctl_est_preferred_cpulist(ipvs));
281 
282 	pr_info("starting estimator thread %d...\n", kd->id);
283 	wake_up_process(kd->task);
284 
285 out:
286 	return ret;
287 }
288 
ip_vs_est_kthread_stop(struct ip_vs_est_kt_data * kd)289 void ip_vs_est_kthread_stop(struct ip_vs_est_kt_data *kd)
290 {
291 	if (kd->task) {
292 		pr_info("stopping estimator thread %d...\n", kd->id);
293 		kthread_stop_put(kd->task);
294 		kd->task = NULL;
295 	}
296 }
297 
298 /* Apply parameters to kthread */
ip_vs_est_set_params(struct netns_ipvs * ipvs,struct ip_vs_est_kt_data * kd)299 static void ip_vs_est_set_params(struct netns_ipvs *ipvs,
300 				 struct ip_vs_est_kt_data *kd)
301 {
302 	kd->chain_max = ipvs->est_chain_max;
303 	/* We are using single chain on RCU preemption */
304 	if (IPVS_EST_TICK_CHAINS == 1)
305 		kd->chain_max *= IPVS_EST_CHAIN_FACTOR;
306 	kd->tick_max = IPVS_EST_TICK_CHAINS * kd->chain_max;
307 	kd->est_max_count = IPVS_EST_NTICKS * kd->tick_max;
308 }
309 
310 /* Create and start estimation kthread in a free or new array slot */
ip_vs_est_add_kthread(struct netns_ipvs * ipvs)311 static int ip_vs_est_add_kthread(struct netns_ipvs *ipvs)
312 {
313 	struct ip_vs_est_kt_data *kd = NULL;
314 	int id = ipvs->est_kt_count;
315 	int ret = -ENOMEM;
316 	void *arr = NULL;
317 	int i;
318 
319 	mutex_lock(&ipvs->est_mutex);
320 
321 	/* Allow kt 0 data to be created before the services are added
322 	 * and limit the kthreads when services are present.
323 	 */
324 	if ((unsigned long)ipvs->est_kt_count >= ipvs->est_max_threads &&
325 	    READ_ONCE(ipvs->enable) && ipvs->est_max_threads) {
326 		ret = -EINVAL;
327 		goto out;
328 	}
329 
330 	for (i = 0; i < id; i++) {
331 		if (!ipvs->est_kt_arr[i])
332 			break;
333 	}
334 	if (i >= id) {
335 		arr = krealloc_array(ipvs->est_kt_arr, id + 1,
336 				     sizeof(struct ip_vs_est_kt_data *),
337 				     GFP_KERNEL);
338 		if (!arr)
339 			goto out;
340 		ipvs->est_kt_arr = arr;
341 	} else {
342 		id = i;
343 	}
344 
345 	kd = kzalloc_obj(*kd);
346 	if (!kd)
347 		goto out;
348 	kd->ipvs = ipvs;
349 	bitmap_fill(kd->avail, IPVS_EST_NTICKS);
350 	kd->est_timer = jiffies;
351 	kd->id = id;
352 	ip_vs_est_set_params(ipvs, kd);
353 	kd->needed = 1;
354 
355 	/* Pre-allocate stats used in calc phase */
356 	if (!id && !kd->calc_stats) {
357 		kd->calc_stats = ip_vs_stats_alloc();
358 		if (!kd->calc_stats)
359 			goto out;
360 	}
361 
362 	/* Request kthread to be started */
363 	ip_vs_est_reload_start(ipvs, false);
364 
365 	if (arr)
366 		ipvs->est_kt_count++;
367 	ipvs->est_kt_arr[id] = kd;
368 	kd = NULL;
369 	/* Use most recent kthread for new ests */
370 	ipvs->est_add_ktid = id;
371 	ret = 0;
372 
373 out:
374 	mutex_unlock(&ipvs->est_mutex);
375 	if (kd) {
376 		ip_vs_stats_free(kd->calc_stats);
377 		kfree(kd);
378 	}
379 
380 	return ret;
381 }
382 
383 /* Select ktid where to add new ests: available, unused or new slot */
ip_vs_est_update_ktid(struct netns_ipvs * ipvs)384 static void ip_vs_est_update_ktid(struct netns_ipvs *ipvs)
385 {
386 	int ktid, best = ipvs->est_kt_count;
387 	struct ip_vs_est_kt_data *kd;
388 
389 	for (ktid = 0; ktid < ipvs->est_kt_count; ktid++) {
390 		kd = ipvs->est_kt_arr[ktid];
391 		if (kd) {
392 			if (kd->est_count < kd->est_max_count) {
393 				best = ktid;
394 				break;
395 			}
396 		} else if (ktid < best) {
397 			best = ktid;
398 		}
399 	}
400 	ipvs->est_add_ktid = best;
401 }
402 
403 /* Add estimator to current kthread (est_add_ktid) */
ip_vs_enqueue_estimator(struct netns_ipvs * ipvs,struct ip_vs_estimator * est)404 static int ip_vs_enqueue_estimator(struct netns_ipvs *ipvs,
405 				   struct ip_vs_estimator *est)
406 {
407 	struct ip_vs_est_kt_data *kd = NULL;
408 	struct ip_vs_est_tick_data *td;
409 	int ktid, row, crow, cid, ret;
410 	int delay = est->ktrow;
411 
412 	BUILD_BUG_ON_MSG(IPVS_EST_TICK_CHAINS > 127,
413 			 "Too many chains for ktcid");
414 
415 	if (ipvs->est_add_ktid < ipvs->est_kt_count) {
416 		kd = ipvs->est_kt_arr[ipvs->est_add_ktid];
417 		if (kd)
418 			goto add_est;
419 	}
420 
421 	ret = ip_vs_est_add_kthread(ipvs);
422 	if (ret < 0)
423 		goto out;
424 	kd = ipvs->est_kt_arr[ipvs->est_add_ktid];
425 
426 add_est:
427 	ktid = kd->id;
428 	/* For small number of estimators prefer to use few ticks,
429 	 * otherwise try to add into the last estimated row.
430 	 * est_row and add_row point after the row we should use
431 	 */
432 	if (kd->est_count >= 2 * kd->tick_max || delay < IPVS_EST_NTICKS - 1)
433 		crow = READ_ONCE(kd->est_row);
434 	else
435 		crow = kd->add_row;
436 	crow += delay;
437 	if (crow >= IPVS_EST_NTICKS)
438 		crow -= IPVS_EST_NTICKS;
439 	/* Assume initial delay ? */
440 	if (delay >= IPVS_EST_NTICKS - 1) {
441 		/* Preserve initial delay or decrease it if no space in tick */
442 		row = crow;
443 		if (crow < IPVS_EST_NTICKS - 1) {
444 			crow++;
445 			row = find_last_bit(kd->avail, crow);
446 		}
447 		if (row >= crow)
448 			row = find_last_bit(kd->avail, IPVS_EST_NTICKS);
449 	} else {
450 		/* Preserve delay or increase it if no space in tick */
451 		row = IPVS_EST_NTICKS;
452 		if (crow > 0)
453 			row = find_next_bit(kd->avail, IPVS_EST_NTICKS, crow);
454 		if (row >= IPVS_EST_NTICKS)
455 			row = find_first_bit(kd->avail, IPVS_EST_NTICKS);
456 	}
457 
458 	td = rcu_dereference_protected(kd->ticks[row], 1);
459 	if (!td) {
460 		td = kzalloc_obj(*td);
461 		if (!td) {
462 			ret = -ENOMEM;
463 			goto out;
464 		}
465 		rcu_assign_pointer(kd->ticks[row], td);
466 	}
467 
468 	cid = find_first_zero_bit(td->full, IPVS_EST_TICK_CHAINS);
469 
470 	kd->est_count++;
471 	kd->tick_len[row]++;
472 	if (!td->chain_len[cid])
473 		__set_bit(cid, td->present);
474 	td->chain_len[cid]++;
475 	est->ktid = ktid;
476 	est->ktrow = row;
477 	est->ktcid = cid;
478 	hlist_add_head_rcu(&est->list, &td->chains[cid]);
479 
480 	if (td->chain_len[cid] >= kd->chain_max) {
481 		__set_bit(cid, td->full);
482 		if (kd->tick_len[row] >= kd->tick_max)
483 			__clear_bit(row, kd->avail);
484 	}
485 
486 	/* Update est_add_ktid to point to first available/empty kt slot */
487 	if (kd->est_count == kd->est_max_count)
488 		ip_vs_est_update_ktid(ipvs);
489 
490 	ret = 0;
491 
492 out:
493 	return ret;
494 }
495 
496 /* Start estimation for stats */
ip_vs_start_estimator(struct netns_ipvs * ipvs,struct ip_vs_stats * stats)497 int ip_vs_start_estimator(struct netns_ipvs *ipvs, struct ip_vs_stats *stats)
498 {
499 	struct ip_vs_est_kt_data *kd = ipvs->est_kt_count > 0 ?
500 				       ipvs->est_kt_arr[0] : NULL;
501 	struct ip_vs_estimator *est = &stats->est;
502 	int ret;
503 
504 	est->ktid = -1;
505 	est->ktrow = IPVS_EST_NTICKS - 1;	/* Initial delay */
506 
507 	/* We prefer this code to be short, kthread 0 will requeue the
508 	 * estimator to available chain. If tasks are disabled, we
509 	 * will not allocate much memory, just for kt 0.
510 	 */
511 	ret = 0;
512 	if (!kd) {
513 		ret = ip_vs_est_add_kthread(ipvs);
514 	} else if (!kd->needed) {
515 		mutex_lock(&ipvs->est_mutex);
516 		/* We have job for the kt 0 task */
517 		kd->needed = 1;
518 		ip_vs_est_reload_start(ipvs, true);
519 		mutex_unlock(&ipvs->est_mutex);
520 	}
521 	if (ret >= 0)
522 		hlist_add_head(&est->list, &ipvs->est_temp_list);
523 	else
524 		INIT_HLIST_NODE(&est->list);
525 	return ret;
526 }
527 
ip_vs_est_kthread_destroy(struct ip_vs_est_kt_data * kd)528 static void ip_vs_est_kthread_destroy(struct ip_vs_est_kt_data *kd)
529 {
530 	if (kd) {
531 		if (kd->task) {
532 			pr_info("stop unused estimator thread %d...\n", kd->id);
533 			kthread_stop_put(kd->task);
534 		}
535 		ip_vs_stats_free(kd->calc_stats);
536 		kfree(kd);
537 	}
538 }
539 
540 /* Unlink estimator from chain */
ip_vs_stop_estimator(struct netns_ipvs * ipvs,struct ip_vs_stats * stats)541 void ip_vs_stop_estimator(struct netns_ipvs *ipvs, struct ip_vs_stats *stats)
542 {
543 	struct ip_vs_estimator *est = &stats->est;
544 	struct ip_vs_est_tick_data *td;
545 	struct ip_vs_est_kt_data *kd;
546 	int ktid = est->ktid;
547 	int row = est->ktrow;
548 	int cid = est->ktcid;
549 
550 	/* Failed to add to chain ? */
551 	if (hlist_unhashed(&est->list))
552 		return;
553 
554 	/* On return, estimator can be freed, dequeue it now */
555 
556 	/* In est_temp_list ? */
557 	if (ktid < 0) {
558 		hlist_del(&est->list);
559 		goto end_kt0;
560 	}
561 
562 	hlist_del_rcu(&est->list);
563 	kd = ipvs->est_kt_arr[ktid];
564 	td = rcu_dereference_protected(kd->ticks[row], 1);
565 	__clear_bit(cid, td->full);
566 	td->chain_len[cid]--;
567 	if (!td->chain_len[cid])
568 		__clear_bit(cid, td->present);
569 	kd->tick_len[row]--;
570 	__set_bit(row, kd->avail);
571 	if (!kd->tick_len[row]) {
572 		RCU_INIT_POINTER(kd->ticks[row], NULL);
573 		kfree_rcu(td, rcu_head);
574 	}
575 	kd->est_count--;
576 	if (kd->est_count) {
577 		/* This kt slot can become available just now, prefer it */
578 		if (ktid < ipvs->est_add_ktid)
579 			ipvs->est_add_ktid = ktid;
580 		return;
581 	}
582 
583 	if (ktid > 0) {
584 		mutex_lock(&ipvs->est_mutex);
585 		ip_vs_est_kthread_destroy(kd);
586 		ipvs->est_kt_arr[ktid] = NULL;
587 		if (ktid == ipvs->est_kt_count - 1) {
588 			ipvs->est_kt_count--;
589 			while (ipvs->est_kt_count > 1 &&
590 			       !ipvs->est_kt_arr[ipvs->est_kt_count - 1])
591 				ipvs->est_kt_count--;
592 		}
593 		mutex_unlock(&ipvs->est_mutex);
594 
595 		/* This slot is now empty, prefer another available kt slot */
596 		if (ktid == ipvs->est_add_ktid)
597 			ip_vs_est_update_ktid(ipvs);
598 	}
599 
600 end_kt0:
601 	/* kt 0 task is stopped after all other kt slots and chains are empty */
602 	if (ipvs->est_kt_count == 1 && hlist_empty(&ipvs->est_temp_list)) {
603 		kd = ipvs->est_kt_arr[0];
604 		if (kd && !kd->est_count) {
605 			mutex_lock(&ipvs->est_mutex);
606 			/* Keep the kt0 data but request kthread_stop */
607 			kd->needed = 0;
608 			ip_vs_est_reload_start(ipvs, true);
609 			mutex_unlock(&ipvs->est_mutex);
610 			ipvs->est_add_ktid = 0;
611 		}
612 	}
613 }
614 
615 /* Register all ests from est_temp_list to kthreads */
ip_vs_est_drain_temp_list(struct netns_ipvs * ipvs)616 static void ip_vs_est_drain_temp_list(struct netns_ipvs *ipvs)
617 {
618 	struct ip_vs_estimator *est;
619 
620 	while (1) {
621 		int max = 16;
622 
623 		mutex_lock(&ipvs->service_mutex);
624 
625 		while (max-- > 0) {
626 			est = hlist_entry_safe(ipvs->est_temp_list.first,
627 					       struct ip_vs_estimator, list);
628 			if (est) {
629 				if (kthread_should_stop())
630 					goto unlock;
631 				hlist_del_init(&est->list);
632 				if (ip_vs_enqueue_estimator(ipvs, est) >= 0)
633 					continue;
634 				est->ktid = -1;
635 				hlist_add_head(&est->list,
636 					       &ipvs->est_temp_list);
637 				/* Abort, some entries will not be estimated
638 				 * until next attempt
639 				 */
640 			}
641 			goto unlock;
642 		}
643 		mutex_unlock(&ipvs->service_mutex);
644 		cond_resched();
645 	}
646 
647 unlock:
648 	mutex_unlock(&ipvs->service_mutex);
649 }
650 
651 /* Calculate limits for all kthreads */
ip_vs_est_calc_limits(struct netns_ipvs * ipvs,int * chain_max)652 static int ip_vs_est_calc_limits(struct netns_ipvs *ipvs, int *chain_max)
653 {
654 	DECLARE_WAIT_QUEUE_HEAD_ONSTACK(wq);
655 	struct ip_vs_est_kt_data *kd;
656 	struct hlist_head chain;
657 	struct ip_vs_stats *s;
658 	int cache_factor = 4;
659 	int i, loops, ntest;
660 	s32 min_est = 0;
661 	ktime_t t1, t2;
662 	int max = 8;
663 	int ret = 1;
664 	s64 diff;
665 	u64 val;
666 
667 	INIT_HLIST_HEAD(&chain);
668 	mutex_lock(&ipvs->est_mutex);
669 	kd = ipvs->est_kt_arr[0];
670 	mutex_unlock(&ipvs->est_mutex);
671 	s = kd ? kd->calc_stats : NULL;
672 	if (!s)
673 		goto out;
674 	hlist_add_head(&s->est.list, &chain);
675 
676 	loops = 1;
677 	/* Get best result from many tests */
678 	for (ntest = 0; ntest < 12; ntest++) {
679 		if (!(ntest & 3)) {
680 			/* Wait for cpufreq frequency transition */
681 			wait_event_idle_timeout(wq, kthread_should_stop(),
682 						HZ / 50);
683 			if (!READ_ONCE(ipvs->enable) || kthread_should_stop())
684 				goto stop;
685 		}
686 
687 		local_bh_disable();
688 		rcu_read_lock();
689 
690 		/* Put stats in cache */
691 		ip_vs_chain_estimation(&chain);
692 
693 		t1 = ktime_get();
694 		for (i = loops * cache_factor; i > 0; i--)
695 			ip_vs_chain_estimation(&chain);
696 		t2 = ktime_get();
697 
698 		rcu_read_unlock();
699 		local_bh_enable();
700 
701 		if (!READ_ONCE(ipvs->enable) || kthread_should_stop())
702 			goto stop;
703 		cond_resched();
704 
705 		diff = ktime_to_ns(ktime_sub(t2, t1));
706 		if (diff <= 1 * NSEC_PER_USEC) {
707 			/* Do more loops on low time resolution */
708 			loops *= 2;
709 			continue;
710 		}
711 		if (diff >= NSEC_PER_SEC)
712 			continue;
713 		val = diff;
714 		do_div(val, loops);
715 		if (!min_est || val < min_est) {
716 			min_est = val;
717 			/* goal: 95usec per chain */
718 			val = 95 * NSEC_PER_USEC;
719 			if (val >= min_est) {
720 				do_div(val, min_est);
721 				max = (int)val;
722 			} else {
723 				max = 1;
724 			}
725 		}
726 	}
727 
728 out:
729 	if (s)
730 		hlist_del_init(&s->est.list);
731 	*chain_max = max;
732 	return ret;
733 
734 stop:
735 	ret = 0;
736 	goto out;
737 }
738 
739 /* Calculate the parameters and apply them in context of kt #0
740  * ECP: est_calc_phase
741  * ECM: est_chain_max
742  * ECP	ECM	Insert Chain	enable	Description
743  * ---------------------------------------------------------------------------
744  * 0	0	est_temp_list	0	create kt #0 context
745  * 0	0	est_temp_list	0->1	service added, start kthread #0 task
746  * 0->1	0	est_temp_list	1	kt task #0 started, enters calc phase
747  * 1	0	est_temp_list	1	kt #0: determine est_chain_max,
748  *					stop tasks, move ests to est_temp_list
749  *					and free kd for kthreads 1..last
750  * 1->0	0->N	kt chains	1	ests can go to kthreads
751  * 0	N	kt chains	1	drain est_temp_list, create new kthread
752  *					contexts, start tasks, estimate
753  */
ip_vs_est_calc_phase(struct netns_ipvs * ipvs)754 static void ip_vs_est_calc_phase(struct netns_ipvs *ipvs)
755 {
756 	int genid = atomic_read(&ipvs->est_genid);
757 	struct ip_vs_est_tick_data *td;
758 	struct ip_vs_est_kt_data *kd;
759 	struct ip_vs_estimator *est;
760 	struct ip_vs_stats *stats;
761 	int id, row, cid, delay;
762 	bool last, last_td;
763 	int chain_max;
764 	int step;
765 
766 	if (!ip_vs_est_calc_limits(ipvs, &chain_max))
767 		return;
768 
769 	/* Stop all other tasks, so that we can immediately move the
770 	 * estimators to est_temp_list without RCU grace period
771 	 */
772 	mutex_lock(&ipvs->est_mutex);
773 	for (id = 1; id < ipvs->est_kt_count; id++) {
774 		/* netns clean up started, abort */
775 		if (kthread_should_stop() || !READ_ONCE(ipvs->enable)) {
776 			mutex_unlock(&ipvs->est_mutex);
777 			return;
778 		}
779 		kd = ipvs->est_kt_arr[id];
780 		if (!kd)
781 			continue;
782 		ip_vs_est_kthread_stop(kd);
783 	}
784 	mutex_unlock(&ipvs->est_mutex);
785 
786 	mutex_lock(&ipvs->service_mutex);
787 
788 	/* Move all estimators to est_temp_list but carefully,
789 	 * all estimators and kthread data can be released while
790 	 * we reschedule.
791 	 */
792 	step = 0;
793 
794 	/* Order entries in est_temp_list in ascending delay, so now
795 	 * walk delay(desc), id(desc), cid(asc)
796 	 */
797 	delay = IPVS_EST_NTICKS;
798 
799 next_delay:
800 	delay--;
801 	if (delay < 0)
802 		goto end_dequeue;
803 
804 last_kt:
805 	/* Destroy contexts backwards */
806 	id = ipvs->est_kt_count;
807 
808 next_kt:
809 	if (!READ_ONCE(ipvs->enable) || kthread_should_stop())
810 		goto unlock;
811 	id--;
812 	if (id < 0)
813 		goto next_delay;
814 	kd = ipvs->est_kt_arr[id];
815 	if (!kd)
816 		goto next_kt;
817 	/* kt 0 can exist with empty chains */
818 	if (!id && kd->est_count <= 1)
819 		goto next_delay;
820 
821 	row = kd->est_row + delay;
822 	if (row >= IPVS_EST_NTICKS)
823 		row -= IPVS_EST_NTICKS;
824 	td = rcu_dereference_protected(kd->ticks[row], 1);
825 	if (!td)
826 		goto next_kt;
827 
828 	cid = 0;
829 
830 walk_chain:
831 	if (kthread_should_stop())
832 		goto unlock;
833 	step++;
834 	if (!(step & 63)) {
835 		/* Give chance estimators to be added (to est_temp_list)
836 		 * and deleted (releasing kthread contexts)
837 		 */
838 		mutex_unlock(&ipvs->service_mutex);
839 		cond_resched();
840 		mutex_lock(&ipvs->service_mutex);
841 
842 		/* Current kt released ? */
843 		if (id >= ipvs->est_kt_count)
844 			goto last_kt;
845 		if (kd != ipvs->est_kt_arr[id])
846 			goto next_kt;
847 		/* Current td released ? */
848 		if (td != rcu_dereference_protected(kd->ticks[row], 1))
849 			goto next_kt;
850 		/* No fatal changes on the current kd and td */
851 	}
852 	est = hlist_entry_safe(td->chains[cid].first, struct ip_vs_estimator,
853 			       list);
854 	if (!est) {
855 		cid++;
856 		if (cid >= IPVS_EST_TICK_CHAINS)
857 			goto next_kt;
858 		goto walk_chain;
859 	}
860 	/* We can cheat and increase est_count to protect kt 0 context
861 	 * from release but we prefer to keep the last estimator
862 	 */
863 	last = kd->est_count <= 1;
864 	/* Do not free kt #0 data */
865 	if (!id && last)
866 		goto next_delay;
867 	last_td = kd->tick_len[row] <= 1;
868 	stats = container_of(est, struct ip_vs_stats, est);
869 	ip_vs_stop_estimator(ipvs, stats);
870 	/* Tasks are stopped, move without RCU grace period */
871 	est->ktid = -1;
872 	est->ktrow = delay;
873 	hlist_add_head(&est->list, &ipvs->est_temp_list);
874 	/* kd freed ? */
875 	if (last)
876 		goto next_kt;
877 	/* td freed ? */
878 	if (last_td)
879 		goto next_kt;
880 	goto walk_chain;
881 
882 end_dequeue:
883 	/* All estimators removed while calculating ? */
884 	if (!ipvs->est_kt_count)
885 		goto unlock;
886 	kd = ipvs->est_kt_arr[0];
887 	if (!kd)
888 		goto unlock;
889 	kd->add_row = kd->est_row;
890 	ipvs->est_chain_max = chain_max;
891 	ip_vs_est_set_params(ipvs, kd);
892 
893 	pr_info("using max %d ests per chain, %d per kthread\n",
894 		kd->chain_max, kd->est_max_count);
895 
896 	/* Try to keep tot_stats in kt0, enqueue it early */
897 	if (ipvs->tot_stats && !hlist_unhashed(&ipvs->tot_stats->s.est.list) &&
898 	    ipvs->tot_stats->s.est.ktid == -1) {
899 		hlist_del(&ipvs->tot_stats->s.est.list);
900 		hlist_add_head(&ipvs->tot_stats->s.est.list,
901 			       &ipvs->est_temp_list);
902 	}
903 
904 	mutex_lock(&ipvs->est_mutex);
905 
906 	/* We completed the calc phase, new calc phase not requested */
907 	if (genid == atomic_read(&ipvs->est_genid))
908 		ipvs->est_calc_phase = 0;
909 
910 	mutex_unlock(&ipvs->est_mutex);
911 
912 unlock:
913 	mutex_unlock(&ipvs->service_mutex);
914 }
915 
ip_vs_zero_estimator(struct ip_vs_stats * stats)916 void ip_vs_zero_estimator(struct ip_vs_stats *stats)
917 {
918 	struct ip_vs_estimator *est = &stats->est;
919 	struct ip_vs_kstats *k = &stats->kstats;
920 
921 	/* reset counters, caller must hold the stats->lock lock */
922 	est->last_inbytes = k->inbytes;
923 	est->last_outbytes = k->outbytes;
924 	est->last_conns = k->conns;
925 	est->last_inpkts = k->inpkts;
926 	est->last_outpkts = k->outpkts;
927 	est->cps = 0;
928 	est->inpps = 0;
929 	est->outpps = 0;
930 	est->inbps = 0;
931 	est->outbps = 0;
932 }
933 
934 /* Get decoded rates */
ip_vs_read_estimator(struct ip_vs_kstats * dst,struct ip_vs_stats * stats)935 void ip_vs_read_estimator(struct ip_vs_kstats *dst, struct ip_vs_stats *stats)
936 {
937 	struct ip_vs_estimator *e = &stats->est;
938 
939 	dst->cps = (e->cps + 0x1FF) >> 10;
940 	dst->inpps = (e->inpps + 0x1FF) >> 10;
941 	dst->outpps = (e->outpps + 0x1FF) >> 10;
942 	dst->inbps = (e->inbps + 0xF) >> 5;
943 	dst->outbps = (e->outbps + 0xF) >> 5;
944 }
945 
ip_vs_estimator_net_init(struct netns_ipvs * ipvs)946 int __net_init ip_vs_estimator_net_init(struct netns_ipvs *ipvs)
947 {
948 	INIT_HLIST_HEAD(&ipvs->est_temp_list);
949 	ipvs->est_kt_arr = NULL;
950 	ipvs->est_max_threads = 0;
951 	ipvs->est_calc_phase = 0;
952 	ipvs->est_chain_max = 0;
953 	ipvs->est_kt_count = 0;
954 	ipvs->est_add_ktid = 0;
955 	atomic_set(&ipvs->est_genid, 0);
956 	atomic_set(&ipvs->est_genid_done, 0);
957 	__mutex_init(&ipvs->est_mutex, "ipvs->est_mutex", &__ipvs_est_key);
958 	return 0;
959 }
960 
ip_vs_estimator_net_cleanup(struct netns_ipvs * ipvs)961 void __net_exit ip_vs_estimator_net_cleanup(struct netns_ipvs *ipvs)
962 {
963 	int i;
964 
965 	for (i = 0; i < ipvs->est_kt_count; i++)
966 		ip_vs_est_kthread_destroy(ipvs->est_kt_arr[i]);
967 	kfree(ipvs->est_kt_arr);
968 	mutex_destroy(&ipvs->est_mutex);
969 }
970