xref: /aosp_15_r20/external/pciutils/lib/i386-io-haiku.h (revision c2e0c6b56a71da9abe8df5c8348fb3eb5c2c9251)
1 /*
2  *	The PCI Library -- Access to i386 I/O ports on Haiku
3  *
4  *	Copyright (c) 2009 Francois Revol <[email protected]>
5  *
6  *	Can be freely distributed and used under the terms of the GNU GPL v2+
7  *
8  *	SPDX-License-Identifier: GPL-2.0-or-later
9  */
10 
11 #include <Drivers.h>
12 #include <ISA.h>
13 #include <PCI.h>
14 
15 /* from haiku/trunk/headers/private/drivers/poke.h */
16 
17 #define POKE_DEVICE_NAME                "poke"
18 #define POKE_DEVICE_FULLNAME    "/dev/misc/poke"
19 #define POKE_SIGNATURE                  'wltp'  // "We Like To Poke"
20 
21 enum {
22 	POKE_PORT_READ = B_DEVICE_OP_CODES_END + 1,
23 	POKE_PORT_WRITE,
24 	POKE_PORT_INDEXED_READ,
25 	POKE_PORT_INDEXED_WRITE,
26 	POKE_PCI_READ_CONFIG,
27 	POKE_PCI_WRITE_CONFIG,
28 	POKE_GET_NTH_PCI_INFO,
29 	POKE_GET_PHYSICAL_ADDRESS,
30 	POKE_MAP_MEMORY,
31 	POKE_UNMAP_MEMORY
32 };
33 
34 
35 typedef struct {
36 	uint32		signature;
37 	uint8		index;
38 	pci_info*	info;
39 	status_t	status;
40 } pci_info_args;
41 
42 
43 typedef struct {
44 	uint32	signature;
45 	uint16	port;
46 	uint8	size;		// == index for POKE_PORT_INDEXED_*
47 	uint32	value;
48 } port_io_args;
49 
50 
51 typedef struct {
52 	uint32	signature;
53 	uint8	bus;
54 	uint8	device;
55 	uint8	function;
56 	uint8	size;
57 	uint8	offset;
58 	uint32	value;
59 } pci_io_args;
60 
61 
62 /* en poke.h*/
63 
64 static int poke_driver_fd;
65 
66 static int
intel_setup_io(struct pci_access * a UNUSED)67 intel_setup_io(struct pci_access *a UNUSED)
68 {
69   /*
70    * Opening poke device on systems with the linked change below
71    * automatically changes process IOPL to 3 and closing its file
72    * descriptor changes process IOPL back to 0, which give access
73    * to all x86 IO ports via x86 in/out instructions for this
74    * userspace process. To support also older systems without this
75    * change, access IO ports via ioctl() instead of x86 in/out.
76    * https://review.haiku-os.org/c/haiku/+/1077
77    */
78   poke_driver_fd = open(POKE_DEVICE_FULLNAME, O_RDWR);
79   return (poke_driver_fd < 0) ? 0 : 1;
80 }
81 
82 static inline void
intel_cleanup_io(struct pci_access * a UNUSED)83 intel_cleanup_io(struct pci_access *a UNUSED)
84 {
85   close(poke_driver_fd);
86 }
87 
88 static inline u8
intel_inb(u16 port)89 intel_inb (u16 port)
90 {
91   port_io_args args = { POKE_SIGNATURE, port, sizeof(u8), 0 };
92   if (ioctl(poke_driver_fd, POKE_PORT_READ, &args, sizeof(args)) < 0)
93     return 0;
94   return (u8)args.value;
95 }
96 
97 static inline u16
intel_inw(u16 port)98 intel_inw (u16 port)
99 {
100   port_io_args args = { POKE_SIGNATURE, port, sizeof(u16), 0 };
101   if (ioctl(poke_driver_fd, POKE_PORT_READ, &args, sizeof(args)) < 0)
102     return 0;
103   return (u16)args.value;
104 }
105 
106 static inline u32
intel_inl(u16 port)107 intel_inl (u16 port)
108 {
109   port_io_args args = { POKE_SIGNATURE, port, sizeof(u32), 0 };
110   if (ioctl(poke_driver_fd, POKE_PORT_READ, &args, sizeof(args)) < 0)
111     return 0;
112   return (u32)args.value;
113 }
114 
115 static inline void
intel_outb(u8 value,u16 port)116 intel_outb (u8 value, u16 port)
117 {
118   port_io_args args = { POKE_SIGNATURE, port, sizeof(u8), value };
119   ioctl(poke_driver_fd, POKE_PORT_WRITE, &args, sizeof(args));
120 }
121 
122 static inline void
intel_outw(u16 value,u16 port)123 intel_outw (u16 value, u16 port)
124 {
125   port_io_args args = { POKE_SIGNATURE, port, sizeof(u16), value };
126   ioctl(poke_driver_fd, POKE_PORT_WRITE, &args, sizeof(args));
127 }
128 
129 static inline void
intel_outl(u32 value,u16 port)130 intel_outl (u32 value, u16 port)
131 {
132   port_io_args args = { POKE_SIGNATURE, port, sizeof(u32), value };
133   ioctl(poke_driver_fd, POKE_PORT_WRITE, &args, sizeof(args));
134 }
135 
intel_io_lock(void)136 static inline void intel_io_lock(void)
137 {
138 }
139 
intel_io_unlock(void)140 static inline void intel_io_unlock(void)
141 {
142 }
143