xref: /haiku/src/tests/add-ons/accelerants/intel_extreme/intel_reg.cpp (revision 85ea044bdb12bee80bb3604f46123b92ad9604b8)
1*85ea044bSJérôme Duval /*
2*85ea044bSJérôme Duval  * Copyright 2024, Haiku Inc. All rights reserved.
3*85ea044bSJérôme Duval  * Distributed under the terms of the MIT License.
4*85ea044bSJérôme Duval  *
5*85ea044bSJérôme Duval  * Authors:
6*85ea044bSJérôme Duval  * 		Jérôme Duval <jerome.duval@gmail.com>
7*85ea044bSJérôme Duval  */
8*85ea044bSJérôme Duval 
9*85ea044bSJérôme Duval 
10*85ea044bSJérôme Duval #include <errno.h>
11*85ea044bSJérôme Duval #include <stdint.h>
12*85ea044bSJérôme Duval #include <stdio.h>
13*85ea044bSJérôme Duval #include <stdlib.h>
14*85ea044bSJérôme Duval #include <string.h>
15*85ea044bSJérôme Duval 
16*85ea044bSJérôme Duval #include <OS.h>
17*85ea044bSJérôme Duval 
18*85ea044bSJérôme Duval 
19*85ea044bSJérôme Duval extern const char *__progname;
20*85ea044bSJérôme Duval static const char *kCommandName = __progname;
21*85ea044bSJérôme Duval 
22*85ea044bSJérôme Duval 
23*85ea044bSJérôme Duval // usage
24*85ea044bSJérôme Duval static const char *kUsage =
25*85ea044bSJérôme Duval "Usage: %s [ <options> ] [ command ] [ args ]\n"
26*85ea044bSJérôme Duval "\n"
27*85ea044bSJérôme Duval "Options:\n"
28*85ea044bSJérôme Duval "  --count <n>      - Read n registers.\n"
29*85ea044bSJérôme Duval ;
30*85ea044bSJérôme Duval 
31*85ea044bSJérôme Duval 
32*85ea044bSJérôme Duval static void
print_usage(bool error)33*85ea044bSJérôme Duval print_usage(bool error)
34*85ea044bSJérôme Duval {
35*85ea044bSJérôme Duval 	// print usage
36*85ea044bSJérôme Duval 	fprintf((error ? stderr : stdout), kUsage, kCommandName);
37*85ea044bSJérôme Duval }
38*85ea044bSJérôme Duval 
39*85ea044bSJérôme Duval 
40*85ea044bSJérôme Duval static void
print_usage_and_exit(bool error)41*85ea044bSJérôme Duval print_usage_and_exit(bool error)
42*85ea044bSJérôme Duval {
43*85ea044bSJérôme Duval 	print_usage(error);
44*85ea044bSJérôme Duval 	exit(error ? 1 : 0);
45*85ea044bSJérôme Duval }
46*85ea044bSJérôme Duval 
47*85ea044bSJérôme Duval 
48*85ea044bSJérôme Duval int
main(int argc,const char * const * argv)49*85ea044bSJérôme Duval main(int argc, const char *const *argv)
50*85ea044bSJérôme Duval {
51*85ea044bSJérôme Duval 	const char *const *programArgs = NULL;
52*85ea044bSJérôme Duval 	int32_t programArgCount = 0;
53*85ea044bSJérôme Duval 	uint32_t count = 1;
54*85ea044bSJérôme Duval 
55*85ea044bSJérôme Duval 	// parse arguments
56*85ea044bSJérôme Duval 	for (int argi = 1; argi < argc; argi++) {
57*85ea044bSJérôme Duval 		const char *arg = argv[argi];
58*85ea044bSJérôme Duval 		if (arg[0] == '-') {
59*85ea044bSJérôme Duval 			if (strcmp(arg, "-h") == 0 || strcmp(arg, "--help") == 0) {
60*85ea044bSJérôme Duval 				print_usage_and_exit(false);
61*85ea044bSJérôme Duval 			} else if (strcmp(arg, "--count") == 0) {
62*85ea044bSJérôme Duval 				count = strtol(argv[++argi], (char **)NULL, 10);
63*85ea044bSJérôme Duval 				if (count == 0 && errno != 0)
64*85ea044bSJérôme Duval 					print_usage_and_exit(true);
65*85ea044bSJérôme Duval 			} else {
66*85ea044bSJérôme Duval 				print_usage_and_exit(true);
67*85ea044bSJérôme Duval 			}
68*85ea044bSJérôme Duval 		} else {
69*85ea044bSJérôme Duval 			programArgs = argv + argi;
70*85ea044bSJérôme Duval 			programArgCount = argc - argi;
71*85ea044bSJérôme Duval 			break;
72*85ea044bSJérôme Duval 		}
73*85ea044bSJérôme Duval 	}
74*85ea044bSJérôme Duval 
75*85ea044bSJérôme Duval 	bool write = false;
76*85ea044bSJérôme Duval 	uint32 value = 0;
77*85ea044bSJérôme Duval 	if (programArgCount < 2) {
78*85ea044bSJérôme Duval 		print_usage_and_exit(true);
79*85ea044bSJérôme Duval 	}
80*85ea044bSJérôme Duval 	if (strcmp(programArgs[0], "read") == 0) {
81*85ea044bSJérôme Duval 		if (programArgCount >= 4) {
82*85ea044bSJérôme Duval 			const char *arg = programArgs[1];
83*85ea044bSJérôme Duval 			if (arg[0] == '-') {
84*85ea044bSJérôme Duval 				if (strcmp(arg, "--count") == 0) {
85*85ea044bSJérôme Duval 					count = strtol(programArgs[2], (char **)NULL, 10);
86*85ea044bSJérôme Duval 					if (count == 0 && errno != 0)
87*85ea044bSJérôme Duval 						print_usage_and_exit(true);
88*85ea044bSJérôme Duval 					programArgCount -= 2;
89*85ea044bSJérôme Duval 					programArgs += 2;
90*85ea044bSJérôme Duval 				} else {
91*85ea044bSJérôme Duval 					print_usage_and_exit(true);
92*85ea044bSJérôme Duval 				}
93*85ea044bSJérôme Duval 			}
94*85ea044bSJérôme Duval 		}
95*85ea044bSJérôme Duval 	} else if (strcmp(programArgs[0], "write") == 0) {
96*85ea044bSJérôme Duval 		write = true;
97*85ea044bSJérôme Duval 	} else
98*85ea044bSJérôme Duval 		print_usage_and_exit(true);
99*85ea044bSJérôme Duval 	programArgCount--;
100*85ea044bSJérôme Duval 	programArgs++;
101*85ea044bSJérôme Duval 
102*85ea044bSJérôme Duval 	area_id area = find_area("intel extreme mmio");
103*85ea044bSJérôme Duval 	if (area < 0) {
104*85ea044bSJérôme Duval 		fprintf(stderr, "couldn't find intel extreme mmio area\n");
105*85ea044bSJérôme Duval 		exit(1);
106*85ea044bSJérôme Duval 	}
107*85ea044bSJérôme Duval 
108*85ea044bSJérôme Duval 	void* regs;
109*85ea044bSJérôme Duval 	uint32 protection = B_READ_AREA | (write ? B_WRITE_AREA : 0);
110*85ea044bSJérôme Duval 	area_id clone = clone_area("clone regs", &regs, B_ANY_ADDRESS, protection, area);
111*85ea044bSJérôme Duval 	if (clone < B_OK) {
112*85ea044bSJérôme Duval 		fprintf(stderr, "couldn't clone intel extreme mmio area\n");
113*85ea044bSJérôme Duval 		exit(1);
114*85ea044bSJérôme Duval 	}
115*85ea044bSJérôme Duval 
116*85ea044bSJérôme Duval 	while (programArgCount > 0) {
117*85ea044bSJérôme Duval 		const char* arg = programArgs[0];
118*85ea044bSJérôme Duval 		programArgCount--;
119*85ea044bSJérôme Duval 		programArgs++;
120*85ea044bSJérôme Duval 		if (write) {
121*85ea044bSJérôme Duval 			if (programArgCount < 1)
122*85ea044bSJérôme Duval 				print_usage_and_exit(true);
123*85ea044bSJérôme Duval 			const char* val = programArgs[0];
124*85ea044bSJérôme Duval 			if (val[0] == '0' && (val[1] == 'x' || val[1] == 'X'))
125*85ea044bSJérôme Duval 				value = strtol(val + 2, (char **)NULL, 16);
126*85ea044bSJérôme Duval 			else
127*85ea044bSJérôme Duval 				value = strtol(val, (char **)NULL, 10);
128*85ea044bSJérôme Duval 			if (value == 0 && errno != 0)
129*85ea044bSJérôme Duval 				print_usage_and_exit(true);
130*85ea044bSJérôme Duval 			programArgCount--;
131*85ea044bSJérôme Duval 			programArgs++;
132*85ea044bSJérôme Duval 		}
133*85ea044bSJérôme Duval 		uint64_t address;
134*85ea044bSJérôme Duval 		if (arg[0] == '0' && (arg[1] == 'x' || arg[1] == 'X')) {
135*85ea044bSJérôme Duval 			address = strtol(arg + 2, (char **)NULL, 16);
136*85ea044bSJérôme Duval 		} else
137*85ea044bSJérôme Duval 			address = strtol(arg, (char **)NULL, 10);
138*85ea044bSJérôme Duval 		if (address == 0 && errno != 0)
139*85ea044bSJérôme Duval 			print_usage_and_exit(true);
140*85ea044bSJérôme Duval 
141*85ea044bSJérôme Duval 		for (uint32_t i = 0; i < count; i++) {
142*85ea044bSJérôme Duval 			addr_t addr = (addr_t)regs + address + i * sizeof(uint32);
143*85ea044bSJérôme Duval 			if (write) {
144*85ea044bSJérôme Duval 				*(uint32*)addr = value;
145*85ea044bSJérôme Duval 			} else {
146*85ea044bSJérôme Duval 				printf("(0x%08" B_PRIxADDR "): 0x%08" B_PRIx32 "\n", address + i * sizeof(uint32), *(uint32*)addr);
147*85ea044bSJérôme Duval 			}
148*85ea044bSJérôme Duval 		}
149*85ea044bSJérôme Duval 	}
150*85ea044bSJérôme Duval 
151*85ea044bSJérôme Duval 	delete_area(clone);
152*85ea044bSJérôme Duval 	exit(0);
153*85ea044bSJérôme Duval }
154