brintos

brintos / linux-shallow public Read only

0
0
Text · 4.6 KiB · e0d17f0 Raw
218 lines · c
1// SPDX-License-Identifier: GPL-2.0-only2/*3 *  (C) 2004-2009  Dominik Brodowski <linux@dominikbrodowski.de>4 *  (C) 2010       Thomas Renninger <trenn@suse.de>5 */6 7 8#include <unistd.h>9#include <stdio.h>10#include <errno.h>11#include <stdlib.h>12#include <string.h>13#include <getopt.h>14 15#include <cpuidle.h>16 17#include "helpers/sysfs.h"18#include "helpers/helpers.h"19#include "helpers/bitmask.h"20 21#define LINE_LEN 1022 23static void cpuidle_cpu_output(unsigned int cpu, int verbose)24{25	unsigned int idlestates, idlestate;26	char *tmp;27 28	idlestates = cpuidle_state_count(cpu);29	if (idlestates == 0) {30		printf(_("CPU %u: No idle states\n"), cpu);31		return;32	}33 34	printf(_("Number of idle states: %d\n"), idlestates);35	printf(_("Available idle states:"));36	for (idlestate = 0; idlestate < idlestates; idlestate++) {37		tmp = cpuidle_state_name(cpu, idlestate);38		if (!tmp)39			continue;40		printf(" %s", tmp);41		free(tmp);42	}43	printf("\n");44 45	if (!verbose)46		return;47 48	for (idlestate = 0; idlestate < idlestates; idlestate++) {49		int disabled = cpuidle_is_state_disabled(cpu, idlestate);50		/* Disabled interface not supported on older kernels */51		if (disabled < 0)52			disabled = 0;53		tmp = cpuidle_state_name(cpu, idlestate);54		if (!tmp)55			continue;56		printf("%s%s:\n", tmp, (disabled) ? " (DISABLED) " : "");57		free(tmp);58 59		tmp = cpuidle_state_desc(cpu, idlestate);60		if (!tmp)61			continue;62		printf(_("Flags/Description: %s\n"), tmp);63		free(tmp);64 65		printf(_("Latency: %lu\n"),66		       cpuidle_state_latency(cpu, idlestate));67		printf(_("Residency: %lu\n"),68		       cpuidle_state_residency(cpu, idlestate));69		printf(_("Usage: %lu\n"),70		       cpuidle_state_usage(cpu, idlestate));71		printf(_("Duration: %llu\n"),72		       cpuidle_state_time(cpu, idlestate));73	}74}75 76static void cpuidle_general_output(void)77{78	char *tmp;79 80	tmp = cpuidle_get_driver();81	if (!tmp) {82		printf(_("Could not determine cpuidle driver\n"));83		return;84	}85 86	printf(_("CPUidle driver: %s\n"), tmp);87	free(tmp);88 89	tmp = cpuidle_get_governor();90	if (!tmp) {91		printf(_("Could not determine cpuidle governor\n"));92		return;93	}94 95	printf(_("CPUidle governor: %s\n"), tmp);96	free(tmp);97}98 99static void proc_cpuidle_cpu_output(unsigned int cpu)100{101	long max_allowed_cstate = 2000000000;102	unsigned int cstate, cstates;103 104	cstates = cpuidle_state_count(cpu);105	if (cstates == 0) {106		printf(_("CPU %u: No C-states info\n"), cpu);107		return;108	}109 110	printf(_("active state:            C0\n"));111	printf(_("max_cstate:              C%u\n"), cstates-1);112	printf(_("maximum allowed latency: %lu usec\n"), max_allowed_cstate);113	printf(_("states:\t\n"));114	for (cstate = 1; cstate < cstates; cstate++) {115		printf(_("    C%d:                  "116			 "type[C%d] "), cstate, cstate);117		printf(_("promotion[--] demotion[--] "));118		printf(_("latency[%03lu] "),119		       cpuidle_state_latency(cpu, cstate));120		printf(_("residency[%05lu] "),121		       cpuidle_state_residency(cpu, cstate));122		printf(_("usage[%08lu] "),123		       cpuidle_state_usage(cpu, cstate));124		printf(_("duration[%020Lu] \n"),125		       cpuidle_state_time(cpu, cstate));126	}127}128 129static struct option info_opts[] = {130	{"silent", no_argument, NULL, 's'},131	{"proc", no_argument, NULL, 'o'},132	{ },133};134 135static inline void cpuidle_exit(int fail)136{137	exit(EXIT_FAILURE);138}139 140int cmd_idle_info(int argc, char **argv)141{142	extern char *optarg;143	extern int optind, opterr, optopt;144	int ret = 0, cont = 1, output_param = 0, verbose = 1;145	unsigned int cpu = 0;146 147	do {148		ret = getopt_long(argc, argv, "os", info_opts, NULL);149		if (ret == -1)150			break;151		switch (ret) {152		case '?':153			output_param = '?';154			cont = 0;155			break;156		case 's':157			verbose = 0;158			break;159		case -1:160			cont = 0;161			break;162		case 'o':163			if (output_param) {164				output_param = -1;165				cont = 0;166				break;167			}168			output_param = ret;169			break;170		}171	} while (cont);172 173	switch (output_param) {174	case -1:175		printf(_("You can't specify more than one "176			 "output-specific argument\n"));177		cpuidle_exit(EXIT_FAILURE);178	case '?':179		printf(_("invalid or unknown argument\n"));180		cpuidle_exit(EXIT_FAILURE);181	}182 183	/* Default is: show output of base_cpu only */184	if (bitmask_isallclear(cpus_chosen))185		bitmask_setbit(cpus_chosen, base_cpu);186 187	if (output_param == 0)188		cpuidle_general_output();189 190	for (cpu = bitmask_first(cpus_chosen);191	     cpu <= bitmask_last(cpus_chosen); cpu++) {192 193		if (!bitmask_isbitset(cpus_chosen, cpu))194			continue;195 196		printf(_("analyzing CPU %d:\n"), cpu);197 198		if (sysfs_is_cpu_online(cpu) != 1) {199			printf(_(" *is offline\n"));200			printf("\n");201			continue;202		}203 204		switch (output_param) {205 206		case 'o':207			proc_cpuidle_cpu_output(cpu);208			break;209		case 0:210			printf("\n");211			cpuidle_cpu_output(cpu, verbose);212			break;213		}214		printf("\n");215	}216	return EXIT_SUCCESS;217}218