1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * Intel dynamic_speed_select -- Enumerate and control features
4  * Copyright (c) 2019 Intel Corporation.
5  */
6 
7 #include "isst.h"
8 
9 static void printcpulist(int str_len, char *str, int mask_size,
10 			 cpu_set_t *cpu_mask)
11 {
12 	int i, first, curr_index, index;
13 
14 	if (!CPU_COUNT_S(mask_size, cpu_mask)) {
15 		snprintf(str, str_len, "none");
16 		return;
17 	}
18 
19 	curr_index = 0;
20 	first = 1;
21 	for (i = 0; i < get_topo_max_cpus(); ++i) {
22 		if (!CPU_ISSET_S(i, mask_size, cpu_mask))
23 			continue;
24 		if (!first) {
25 			index = snprintf(&str[curr_index],
26 					 str_len - curr_index, ",");
27 			curr_index += index;
28 			if (curr_index >= str_len)
29 				break;
30 		}
31 		index = snprintf(&str[curr_index], str_len - curr_index, "%d",
32 				 i);
33 		curr_index += index;
34 		if (curr_index >= str_len)
35 			break;
36 		first = 0;
37 	}
38 }
39 
40 static void printcpumask(int str_len, char *str, int mask_size,
41 			 cpu_set_t *cpu_mask)
42 {
43 	int i, max_cpus = get_topo_max_cpus();
44 	unsigned int *mask;
45 	int size, index, curr_index;
46 
47 	size = max_cpus / (sizeof(unsigned int) * 8);
48 	if (max_cpus % (sizeof(unsigned int) * 8))
49 		size++;
50 
51 	mask = calloc(size, sizeof(unsigned int));
52 	if (!mask)
53 		return;
54 
55 	for (i = 0; i < max_cpus; ++i) {
56 		int mask_index, bit_index;
57 
58 		if (!CPU_ISSET_S(i, mask_size, cpu_mask))
59 			continue;
60 
61 		mask_index = i / (sizeof(unsigned int) * 8);
62 		bit_index = i % (sizeof(unsigned int) * 8);
63 		mask[mask_index] |= BIT(bit_index);
64 	}
65 
66 	curr_index = 0;
67 	for (i = size - 1; i >= 0; --i) {
68 		index = snprintf(&str[curr_index], str_len - curr_index, "%08x",
69 				 mask[i]);
70 		curr_index += index;
71 		if (curr_index >= str_len)
72 			break;
73 		if (i) {
74 			strncat(&str[curr_index], ",", str_len - curr_index);
75 			curr_index++;
76 		}
77 		if (curr_index >= str_len)
78 			break;
79 	}
80 
81 	free(mask);
82 }
83 
84 static void format_and_print_txt(FILE *outf, int level, char *header,
85 				 char *value)
86 {
87 	char *spaces = "  ";
88 	static char delimiters[256];
89 	int i, j = 0;
90 
91 	if (!level)
92 		return;
93 
94 	if (level == 1) {
95 		strcpy(delimiters, " ");
96 	} else {
97 		for (i = 0; i < level - 1; ++i)
98 			j += snprintf(&delimiters[j], sizeof(delimiters) - j,
99 				      "%s", spaces);
100 	}
101 
102 	if (header && value) {
103 		fprintf(outf, "%s", delimiters);
104 		fprintf(outf, "%s:%s\n", header, value);
105 	} else if (header) {
106 		fprintf(outf, "%s", delimiters);
107 		fprintf(outf, "%s\n", header);
108 	}
109 }
110 
111 static int last_level;
112 static void format_and_print(FILE *outf, int level, char *header, char *value)
113 {
114 	char *spaces = "  ";
115 	static char delimiters[256];
116 	int i;
117 
118 	if (!out_format_is_json()) {
119 		format_and_print_txt(outf, level, header, value);
120 		return;
121 	}
122 
123 	if (level == 0) {
124 		if (header)
125 			fprintf(outf, "{");
126 		else
127 			fprintf(outf, "\n}\n");
128 
129 	} else {
130 		int j = 0;
131 
132 		for (i = 0; i < level; ++i)
133 			j += snprintf(&delimiters[j], sizeof(delimiters) - j,
134 				      "%s", spaces);
135 
136 		if (last_level == level)
137 			fprintf(outf, ",\n");
138 
139 		if (value) {
140 			if (last_level != level)
141 				fprintf(outf, "\n");
142 
143 			fprintf(outf, "%s\"%s\": ", delimiters, header);
144 			fprintf(outf, "\"%s\"", value);
145 		} else {
146 			for (i = last_level - 1; i >= level; --i) {
147 				int k = 0;
148 
149 				for (j = i; j > 0; --j)
150 					k += snprintf(&delimiters[k],
151 						      sizeof(delimiters) - k,
152 						      "%s", spaces);
153 				if (i == level && header)
154 					fprintf(outf, "\n%s},", delimiters);
155 				else
156 					fprintf(outf, "\n%s}", delimiters);
157 			}
158 			if (abs(last_level - level) < 3)
159 				fprintf(outf, "\n");
160 			if (header)
161 				fprintf(outf, "%s\"%s\": {", delimiters,
162 					header);
163 		}
164 	}
165 
166 	last_level = level;
167 }
168 
169 static int print_package_info(int cpu, FILE *outf)
170 {
171 	char header[256];
172 
173 	if (out_format_is_json()) {
174 		snprintf(header, sizeof(header), "package-%d:die-%d:cpu-%d",
175 			 get_physical_package_id(cpu), get_physical_die_id(cpu),
176 			 cpu);
177 		format_and_print(outf, 1, header, NULL);
178 		return 1;
179 	}
180 	snprintf(header, sizeof(header), "package-%d",
181 		 get_physical_package_id(cpu));
182 	format_and_print(outf, 1, header, NULL);
183 	snprintf(header, sizeof(header), "die-%d", get_physical_die_id(cpu));
184 	format_and_print(outf, 2, header, NULL);
185 	snprintf(header, sizeof(header), "cpu-%d", cpu);
186 	format_and_print(outf, 3, header, NULL);
187 
188 	return 3;
189 }
190 
191 static void _isst_pbf_display_information(int cpu, FILE *outf, int level,
192 					  struct isst_pbf_info *pbf_info,
193 					  int disp_level)
194 {
195 	char header[256];
196 	char value[512];
197 
198 	snprintf(header, sizeof(header), "speed-select-base-freq-properties");
199 	format_and_print(outf, disp_level, header, NULL);
200 
201 	snprintf(header, sizeof(header), "high-priority-base-frequency(MHz)");
202 	snprintf(value, sizeof(value), "%d",
203 		 pbf_info->p1_high * DISP_FREQ_MULTIPLIER);
204 	format_and_print(outf, disp_level + 1, header, value);
205 
206 	snprintf(header, sizeof(header), "high-priority-cpu-mask");
207 	printcpumask(sizeof(value), value, pbf_info->core_cpumask_size,
208 		     pbf_info->core_cpumask);
209 	format_and_print(outf, disp_level + 1, header, value);
210 
211 	snprintf(header, sizeof(header), "high-priority-cpu-list");
212 	printcpulist(sizeof(value), value,
213 		     pbf_info->core_cpumask_size,
214 		     pbf_info->core_cpumask);
215 	format_and_print(outf, disp_level + 1, header, value);
216 
217 	snprintf(header, sizeof(header), "low-priority-base-frequency(MHz)");
218 	snprintf(value, sizeof(value), "%d",
219 		 pbf_info->p1_low * DISP_FREQ_MULTIPLIER);
220 	format_and_print(outf, disp_level + 1, header, value);
221 
222 	if (is_clx_n_platform())
223 		return;
224 
225 	snprintf(header, sizeof(header), "tjunction-temperature(C)");
226 	snprintf(value, sizeof(value), "%d", pbf_info->t_prochot);
227 	format_and_print(outf, disp_level + 1, header, value);
228 
229 	snprintf(header, sizeof(header), "thermal-design-power(W)");
230 	snprintf(value, sizeof(value), "%d", pbf_info->tdp);
231 	format_and_print(outf, disp_level + 1, header, value);
232 }
233 
234 static void _isst_fact_display_information(int cpu, FILE *outf, int level,
235 					   int fact_bucket, int fact_avx,
236 					   struct isst_fact_info *fact_info,
237 					   int base_level)
238 {
239 	struct isst_fact_bucket_info *bucket_info = fact_info->bucket_info;
240 	char header[256];
241 	char value[256];
242 	int print = 0, j;
243 
244 	for (j = 0; j < ISST_FACT_MAX_BUCKETS; ++j) {
245 		if (fact_bucket != 0xff && fact_bucket != j)
246 			continue;
247 
248 		if (!bucket_info[j].high_priority_cores_count)
249 			break;
250 
251 		print = 1;
252 	}
253 	if (!print) {
254 		fprintf(stderr, "Invalid bucket\n");
255 		return;
256 	}
257 
258 	snprintf(header, sizeof(header), "speed-select-turbo-freq-properties");
259 	format_and_print(outf, base_level, header, NULL);
260 	for (j = 0; j < ISST_FACT_MAX_BUCKETS; ++j) {
261 		if (fact_bucket != 0xff && fact_bucket != j)
262 			continue;
263 
264 		if (!bucket_info[j].high_priority_cores_count)
265 			break;
266 
267 		snprintf(header, sizeof(header), "bucket-%d", j);
268 		format_and_print(outf, base_level + 1, header, NULL);
269 
270 		snprintf(header, sizeof(header), "high-priority-cores-count");
271 		snprintf(value, sizeof(value), "%d",
272 			 bucket_info[j].high_priority_cores_count);
273 		format_and_print(outf, base_level + 2, header, value);
274 
275 		if (fact_avx & 0x01) {
276 			snprintf(header, sizeof(header),
277 				 "high-priority-max-frequency(MHz)");
278 			snprintf(value, sizeof(value), "%d",
279 				 bucket_info[j].sse_trl * DISP_FREQ_MULTIPLIER);
280 			format_and_print(outf, base_level + 2, header, value);
281 		}
282 
283 		if (fact_avx & 0x02) {
284 			snprintf(header, sizeof(header),
285 				 "high-priority-max-avx2-frequency(MHz)");
286 			snprintf(value, sizeof(value), "%d",
287 				 bucket_info[j].avx_trl * DISP_FREQ_MULTIPLIER);
288 			format_and_print(outf, base_level + 2, header, value);
289 		}
290 
291 		if (fact_avx & 0x04) {
292 			snprintf(header, sizeof(header),
293 				 "high-priority-max-avx512-frequency(MHz)");
294 			snprintf(value, sizeof(value), "%d",
295 				 bucket_info[j].avx512_trl *
296 					 DISP_FREQ_MULTIPLIER);
297 			format_and_print(outf, base_level + 2, header, value);
298 		}
299 	}
300 	snprintf(header, sizeof(header),
301 		 "speed-select-turbo-freq-clip-frequencies");
302 	format_and_print(outf, base_level + 1, header, NULL);
303 	snprintf(header, sizeof(header), "low-priority-max-frequency(MHz)");
304 	snprintf(value, sizeof(value), "%d",
305 		 fact_info->lp_clipping_ratio_license_sse *
306 			 DISP_FREQ_MULTIPLIER);
307 	format_and_print(outf, base_level + 2, header, value);
308 	snprintf(header, sizeof(header),
309 		 "low-priority-max-avx2-frequency(MHz)");
310 	snprintf(value, sizeof(value), "%d",
311 		 fact_info->lp_clipping_ratio_license_avx2 *
312 			 DISP_FREQ_MULTIPLIER);
313 	format_and_print(outf, base_level + 2, header, value);
314 	snprintf(header, sizeof(header),
315 		 "low-priority-max-avx512-frequency(MHz)");
316 	snprintf(value, sizeof(value), "%d",
317 		 fact_info->lp_clipping_ratio_license_avx512 *
318 			 DISP_FREQ_MULTIPLIER);
319 	format_and_print(outf, base_level + 2, header, value);
320 }
321 
322 void isst_ctdp_display_core_info(int cpu, FILE *outf, char *prefix,
323 				 unsigned int val, char *str0, char *str1)
324 {
325 	char header[256];
326 	char value[256];
327 	int level = 1;
328 
329 	if (out_format_is_json()) {
330 		snprintf(header, sizeof(header), "package-%d:die-%d:cpu-%d",
331 			 get_physical_package_id(cpu), get_physical_die_id(cpu),
332 			 cpu);
333 		format_and_print(outf, level++, header, NULL);
334 	} else {
335 		snprintf(header, sizeof(header), "package-%d",
336 			 get_physical_package_id(cpu));
337 		format_and_print(outf, level++, header, NULL);
338 		snprintf(header, sizeof(header), "die-%d",
339 			 get_physical_die_id(cpu));
340 		format_and_print(outf, level++, header, NULL);
341 		snprintf(header, sizeof(header), "cpu-%d", cpu);
342 		format_and_print(outf, level++, header, NULL);
343 	}
344 
345 	if (str0 && !val)
346 		snprintf(value, sizeof(value), "%s", str0);
347 	else if (str1 && val)
348 		snprintf(value, sizeof(value), "%s", str1);
349 	else
350 		snprintf(value, sizeof(value), "%u", val);
351 	format_and_print(outf, level, prefix, value);
352 
353 	format_and_print(outf, 1, NULL, NULL);
354 }
355 
356 void isst_ctdp_display_information(int cpu, FILE *outf, int tdp_level,
357 				   struct isst_pkg_ctdp *pkg_dev)
358 {
359 	char header[256];
360 	char value[512];
361 	static int level;
362 	int i;
363 
364 	if (pkg_dev->processed)
365 		level = print_package_info(cpu, outf);
366 
367 	for (i = 0; i <= pkg_dev->levels; ++i) {
368 		struct isst_pkg_ctdp_level_info *ctdp_level;
369 		int j;
370 
371 		ctdp_level = &pkg_dev->ctdp_level[i];
372 		if (!ctdp_level->processed)
373 			continue;
374 
375 		snprintf(header, sizeof(header), "perf-profile-level-%d",
376 			 ctdp_level->level);
377 		format_and_print(outf, level + 1, header, NULL);
378 
379 		snprintf(header, sizeof(header), "cpu-count");
380 		j = get_cpu_count(get_physical_die_id(cpu),
381 				  get_physical_die_id(cpu));
382 		snprintf(value, sizeof(value), "%d", j);
383 		format_and_print(outf, level + 2, header, value);
384 
385 		j = CPU_COUNT_S(ctdp_level->core_cpumask_size,
386 				ctdp_level->core_cpumask);
387 		if (j) {
388 			snprintf(header, sizeof(header), "enable-cpu-count");
389 			snprintf(value, sizeof(value), "%d", j);
390 			format_and_print(outf, level + 2, header, value);
391 		}
392 
393 		if (ctdp_level->core_cpumask_size) {
394 			snprintf(header, sizeof(header), "enable-cpu-mask");
395 			printcpumask(sizeof(value), value,
396 				     ctdp_level->core_cpumask_size,
397 				     ctdp_level->core_cpumask);
398 			format_and_print(outf, level + 2, header, value);
399 
400 			snprintf(header, sizeof(header), "enable-cpu-list");
401 			printcpulist(sizeof(value), value,
402 				     ctdp_level->core_cpumask_size,
403 				     ctdp_level->core_cpumask);
404 			format_and_print(outf, level + 2, header, value);
405 		}
406 
407 		snprintf(header, sizeof(header), "thermal-design-power-ratio");
408 		snprintf(value, sizeof(value), "%d", ctdp_level->tdp_ratio);
409 		format_and_print(outf, level + 2, header, value);
410 
411 		snprintf(header, sizeof(header), "base-frequency(MHz)");
412 		if (!ctdp_level->sse_p1)
413 			ctdp_level->sse_p1 = ctdp_level->tdp_ratio;
414 		snprintf(value, sizeof(value), "%d",
415 			  ctdp_level->sse_p1 * DISP_FREQ_MULTIPLIER);
416 		format_and_print(outf, level + 2, header, value);
417 
418 		if (ctdp_level->avx2_p1) {
419 			snprintf(header, sizeof(header), "base-frequency-avx2(MHz)");
420 			snprintf(value, sizeof(value), "%d",
421 				 ctdp_level->avx2_p1 * DISP_FREQ_MULTIPLIER);
422 			format_and_print(outf, level + 2, header, value);
423 		}
424 
425 		if (ctdp_level->avx512_p1) {
426 			snprintf(header, sizeof(header), "base-frequency-avx512(MHz)");
427 			snprintf(value, sizeof(value), "%d",
428 				 ctdp_level->avx512_p1 * DISP_FREQ_MULTIPLIER);
429 			format_and_print(outf, level + 2, header, value);
430 		}
431 
432 		if (ctdp_level->uncore_p1) {
433 			snprintf(header, sizeof(header), "uncore-frequency-min(MHz)");
434 			snprintf(value, sizeof(value), "%d",
435 				 ctdp_level->uncore_p1 * DISP_FREQ_MULTIPLIER);
436 			format_and_print(outf, level + 2, header, value);
437 		}
438 
439 		if (ctdp_level->uncore_p0) {
440 			snprintf(header, sizeof(header), "uncore-frequency-max(MHz)");
441 			snprintf(value, sizeof(value), "%d",
442 				 ctdp_level->uncore_p0 * DISP_FREQ_MULTIPLIER);
443 			format_and_print(outf, level + 2, header, value);
444 		}
445 
446 		if (ctdp_level->mem_freq) {
447 			snprintf(header, sizeof(header), "mem-frequency(MHz)");
448 			snprintf(value, sizeof(value), "%d",
449 				 ctdp_level->mem_freq * DISP_FREQ_MULTIPLIER);
450 			format_and_print(outf, level + 2, header, value);
451 		}
452 
453 		snprintf(header, sizeof(header),
454 			 "speed-select-turbo-freq");
455 		if (ctdp_level->fact_support) {
456 			if (ctdp_level->fact_enabled)
457 				snprintf(value, sizeof(value), "enabled");
458 			else
459 				snprintf(value, sizeof(value), "disabled");
460 		} else
461 			snprintf(value, sizeof(value), "unsupported");
462 		format_and_print(outf, level + 2, header, value);
463 
464 		snprintf(header, sizeof(header),
465 			 "speed-select-base-freq");
466 		if (ctdp_level->pbf_support) {
467 			if (ctdp_level->pbf_enabled)
468 				snprintf(value, sizeof(value), "enabled");
469 			else
470 				snprintf(value, sizeof(value), "disabled");
471 		} else
472 			snprintf(value, sizeof(value), "unsupported");
473 		format_and_print(outf, level + 2, header, value);
474 
475 		snprintf(header, sizeof(header),
476 			 "speed-select-core-power");
477 		if (ctdp_level->sst_cp_support) {
478 			if (ctdp_level->sst_cp_enabled)
479 				snprintf(value, sizeof(value), "enabled");
480 			else
481 				snprintf(value, sizeof(value), "disabled");
482 		} else
483 			snprintf(value, sizeof(value), "unsupported");
484 		format_and_print(outf, level + 2, header, value);
485 
486 		if (is_clx_n_platform()) {
487 			if (ctdp_level->pbf_support)
488 				_isst_pbf_display_information(cpu, outf,
489 							      tdp_level,
490 							  &ctdp_level->pbf_info,
491 							      level + 2);
492 			continue;
493 		}
494 
495 		if (ctdp_level->pkg_tdp) {
496 			snprintf(header, sizeof(header), "thermal-design-power(W)");
497 			snprintf(value, sizeof(value), "%d", ctdp_level->pkg_tdp);
498 			format_and_print(outf, level + 2, header, value);
499 		}
500 
501 		if (ctdp_level->t_proc_hot) {
502 			snprintf(header, sizeof(header), "tjunction-max(C)");
503 			snprintf(value, sizeof(value), "%d", ctdp_level->t_proc_hot);
504 			format_and_print(outf, level + 2, header, value);
505 		}
506 
507 		snprintf(header, sizeof(header), "turbo-ratio-limits-sse");
508 		format_and_print(outf, level + 2, header, NULL);
509 		for (j = 0; j < 8; ++j) {
510 			snprintf(header, sizeof(header), "bucket-%d", j);
511 			format_and_print(outf, level + 3, header, NULL);
512 
513 			snprintf(header, sizeof(header), "core-count");
514 			snprintf(value, sizeof(value), "%llu", (ctdp_level->buckets_info >> (j * 8)) & 0xff);
515 			format_and_print(outf, level + 4, header, value);
516 
517 			snprintf(header, sizeof(header),
518 				"max-turbo-frequency(MHz)");
519 			snprintf(value, sizeof(value), "%d",
520 				 ctdp_level->trl_sse_active_cores[j] *
521 				  DISP_FREQ_MULTIPLIER);
522 			format_and_print(outf, level + 4, header, value);
523 		}
524 
525 		if (ctdp_level->trl_avx_active_cores[0]) {
526 			snprintf(header, sizeof(header), "turbo-ratio-limits-avx2");
527 			format_and_print(outf, level + 2, header, NULL);
528 			for (j = 0; j < 8; ++j) {
529 				snprintf(header, sizeof(header), "bucket-%d", j);
530 				format_and_print(outf, level + 3, header, NULL);
531 
532 				snprintf(header, sizeof(header), "core-count");
533 				snprintf(value, sizeof(value), "%llu", (ctdp_level->buckets_info >> (j * 8)) & 0xff);
534 				format_and_print(outf, level + 4, header, value);
535 
536 				snprintf(header, sizeof(header), "max-turbo-frequency(MHz)");
537 				snprintf(value, sizeof(value), "%d", ctdp_level->trl_avx_active_cores[j] * DISP_FREQ_MULTIPLIER);
538 				format_and_print(outf, level + 4, header, value);
539 			}
540 		}
541 
542 		if (ctdp_level->trl_avx_512_active_cores[0]) {
543 			snprintf(header, sizeof(header), "turbo-ratio-limits-avx512");
544 			format_and_print(outf, level + 2, header, NULL);
545 			for (j = 0; j < 8; ++j) {
546 				snprintf(header, sizeof(header), "bucket-%d", j);
547 				format_and_print(outf, level + 3, header, NULL);
548 
549 				snprintf(header, sizeof(header), "core-count");
550 				snprintf(value, sizeof(value), "%llu", (ctdp_level->buckets_info >> (j * 8)) & 0xff);
551 				format_and_print(outf, level + 4, header, value);
552 
553 				snprintf(header, sizeof(header), "max-turbo-frequency(MHz)");
554 				snprintf(value, sizeof(value), "%d", ctdp_level->trl_avx_512_active_cores[j] * DISP_FREQ_MULTIPLIER);
555 				format_and_print(outf, level + 4, header, value);
556 			}
557 		}
558 
559 		if (ctdp_level->pbf_support)
560 			_isst_pbf_display_information(cpu, outf, i,
561 						      &ctdp_level->pbf_info,
562 						      level + 2);
563 		if (ctdp_level->fact_support)
564 			_isst_fact_display_information(cpu, outf, i, 0xff, 0xff,
565 						       &ctdp_level->fact_info,
566 						       level + 2);
567 	}
568 
569 	format_and_print(outf, 1, NULL, NULL);
570 }
571 
572 static int start;
573 void isst_ctdp_display_information_start(FILE *outf)
574 {
575 	last_level = 0;
576 	format_and_print(outf, 0, "start", NULL);
577 	start = 1;
578 }
579 
580 void isst_ctdp_display_information_end(FILE *outf)
581 {
582 	format_and_print(outf, 0, NULL, NULL);
583 	start = 0;
584 }
585 
586 void isst_pbf_display_information(int cpu, FILE *outf, int level,
587 				  struct isst_pbf_info *pbf_info)
588 {
589 	int _level;
590 
591 	_level = print_package_info(cpu, outf);
592 	_isst_pbf_display_information(cpu, outf, level, pbf_info, _level + 1);
593 	format_and_print(outf, 1, NULL, NULL);
594 }
595 
596 void isst_fact_display_information(int cpu, FILE *outf, int level,
597 				   int fact_bucket, int fact_avx,
598 				   struct isst_fact_info *fact_info)
599 {
600 	int _level;
601 
602 	_level = print_package_info(cpu, outf);
603 	_isst_fact_display_information(cpu, outf, level, fact_bucket, fact_avx,
604 				       fact_info, _level + 1);
605 	format_and_print(outf, 1, NULL, NULL);
606 }
607 
608 void isst_clos_display_information(int cpu, FILE *outf, int clos,
609 				   struct isst_clos_config *clos_config)
610 {
611 	char header[256];
612 	char value[256];
613 	int level;
614 
615 	level = print_package_info(cpu, outf);
616 
617 	snprintf(header, sizeof(header), "core-power");
618 	format_and_print(outf, level + 1, header, NULL);
619 
620 	snprintf(header, sizeof(header), "clos");
621 	snprintf(value, sizeof(value), "%d", clos);
622 	format_and_print(outf, level + 2, header, value);
623 
624 	snprintf(header, sizeof(header), "epp");
625 	snprintf(value, sizeof(value), "%d", clos_config->epp);
626 	format_and_print(outf, level + 2, header, value);
627 
628 	snprintf(header, sizeof(header), "clos-proportional-priority");
629 	snprintf(value, sizeof(value), "%d", clos_config->clos_prop_prio);
630 	format_and_print(outf, level + 2, header, value);
631 
632 	snprintf(header, sizeof(header), "clos-min");
633 	snprintf(value, sizeof(value), "%d MHz", clos_config->clos_min * DISP_FREQ_MULTIPLIER);
634 	format_and_print(outf, level + 2, header, value);
635 
636 	snprintf(header, sizeof(header), "clos-max");
637 	if (clos_config->clos_max == 0xff)
638 		snprintf(value, sizeof(value), "Max Turbo frequency");
639 	else
640 		snprintf(value, sizeof(value), "%d MHz", clos_config->clos_max * DISP_FREQ_MULTIPLIER);
641 	format_and_print(outf, level + 2, header, value);
642 
643 	snprintf(header, sizeof(header), "clos-desired");
644 	snprintf(value, sizeof(value), "%d MHz", clos_config->clos_desired * DISP_FREQ_MULTIPLIER);
645 	format_and_print(outf, level + 2, header, value);
646 
647 	format_and_print(outf, level, NULL, NULL);
648 }
649 
650 void isst_clos_display_clos_information(int cpu, FILE *outf,
651 					int clos_enable, int type,
652 					int state, int cap)
653 {
654 	char header[256];
655 	char value[256];
656 	int level;
657 
658 	level = print_package_info(cpu, outf);
659 
660 	snprintf(header, sizeof(header), "core-power");
661 	format_and_print(outf, level + 1, header, NULL);
662 
663 	snprintf(header, sizeof(header), "support-status");
664 	if (cap)
665 		snprintf(value, sizeof(value), "supported");
666 	else
667 		snprintf(value, sizeof(value), "unsupported");
668 	format_and_print(outf, level + 2, header, value);
669 
670 	snprintf(header, sizeof(header), "enable-status");
671 	if (state)
672 		snprintf(value, sizeof(value), "enabled");
673 	else
674 		snprintf(value, sizeof(value), "disabled");
675 	format_and_print(outf, level + 2, header, value);
676 
677 	snprintf(header, sizeof(header), "clos-enable-status");
678 	if (clos_enable)
679 		snprintf(value, sizeof(value), "enabled");
680 	else
681 		snprintf(value, sizeof(value), "disabled");
682 	format_and_print(outf, level + 2, header, value);
683 
684 	snprintf(header, sizeof(header), "priority-type");
685 	if (type)
686 		snprintf(value, sizeof(value), "ordered");
687 	else
688 		snprintf(value, sizeof(value), "proportional");
689 	format_and_print(outf, level + 2, header, value);
690 
691 	format_and_print(outf, level, NULL, NULL);
692 }
693 
694 void isst_clos_display_assoc_information(int cpu, FILE *outf, int clos)
695 {
696 	char header[256];
697 	char value[256];
698 	int level;
699 
700 	level = print_package_info(cpu, outf);
701 
702 	snprintf(header, sizeof(header), "get-assoc");
703 	format_and_print(outf, level + 1, header, NULL);
704 
705 	snprintf(header, sizeof(header), "clos");
706 	snprintf(value, sizeof(value), "%d", clos);
707 	format_and_print(outf, level + 2, header, value);
708 
709 	format_and_print(outf, level, NULL, NULL);
710 }
711 
712 void isst_display_result(int cpu, FILE *outf, char *feature, char *cmd,
713 			 int result)
714 {
715 	char header[256];
716 	char value[256];
717 	int level = 3;
718 
719 	if (cpu >= 0)
720 		level = print_package_info(cpu, outf);
721 
722 	snprintf(header, sizeof(header), "%s", feature);
723 	format_and_print(outf, level + 1, header, NULL);
724 	snprintf(header, sizeof(header), "%s", cmd);
725 	if (!result)
726 		snprintf(value, sizeof(value), "success");
727 	else
728 		snprintf(value, sizeof(value), "failed(error %d)", result);
729 	format_and_print(outf, level + 2, header, value);
730 
731 	format_and_print(outf, level, NULL, NULL);
732 }
733 
734 void isst_display_error_info_message(int error, char *msg, int arg_valid, int arg)
735 {
736 	FILE *outf = get_output_file();
737 	static int error_index;
738 	char header[256];
739 	char value[256];
740 
741 	if (!out_format_is_json()) {
742 		if (arg_valid)
743 			snprintf(value, sizeof(value), "%s %d", msg, arg);
744 		else
745 			snprintf(value, sizeof(value), "%s", msg);
746 
747 		if (error)
748 			fprintf(outf, "Error: %s\n", value);
749 		else
750 			fprintf(outf, "Information: %s\n", value);
751 		return;
752 	}
753 
754 	if (!start)
755 		format_and_print(outf, 0, "start", NULL);
756 
757 	if (error)
758 		snprintf(header, sizeof(header), "Error%d", error_index++);
759 	else
760 		snprintf(header, sizeof(header), "Information:%d", error_index++);
761 	format_and_print(outf, 1, header, NULL);
762 
763 	snprintf(header, sizeof(header), "message");
764 	if (arg_valid)
765 		snprintf(value, sizeof(value), "%s %d", msg, arg);
766 	else
767 		snprintf(value, sizeof(value), "%s", msg);
768 
769 	format_and_print(outf, 2, header, value);
770 	format_and_print(outf, 1, NULL, NULL);
771 	if (!start)
772 		format_and_print(outf, 0, NULL, NULL);
773 }
774 
775 void isst_trl_display_information(int cpu, FILE *outf, unsigned long long trl)
776 {
777 	char header[256];
778 	char value[256];
779 	int level;
780 
781 	level = print_package_info(cpu, outf);
782 
783 	snprintf(header, sizeof(header), "get-trl");
784 	format_and_print(outf, level + 1, header, NULL);
785 
786 	snprintf(header, sizeof(header), "trl");
787 	snprintf(value, sizeof(value), "0x%llx", trl);
788 	format_and_print(outf, level + 2, header, value);
789 
790 	format_and_print(outf, level, NULL, NULL);
791 }
792