drm/amdgpu: add helper function to query psp runtime db entry (v2)
[linux-2.6-microblaze.git] / drivers / xen / xen-pciback / conf_space_header.c
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * PCI Backend - Handles the virtual fields in the configuration space headers.
4  *
5  * Author: Ryan Wilson <hap9@epoch.ncsc.mil>
6  */
7
8 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
9 #define dev_fmt pr_fmt
10
11 #include <linux/kernel.h>
12 #include <linux/pci.h>
13 #include "pciback.h"
14 #include "conf_space.h"
15
16 struct pci_cmd_info {
17         u16 val;
18 };
19
20 struct pci_bar_info {
21         u32 val;
22         u32 len_val;
23         int which;
24 };
25
26 #define is_enable_cmd(value) ((value)&(PCI_COMMAND_MEMORY|PCI_COMMAND_IO))
27 #define is_master_cmd(value) ((value)&PCI_COMMAND_MASTER)
28
29 /* Bits guests are allowed to control in permissive mode. */
30 #define PCI_COMMAND_GUEST (PCI_COMMAND_MASTER|PCI_COMMAND_SPECIAL| \
31                            PCI_COMMAND_INVALIDATE|PCI_COMMAND_VGA_PALETTE| \
32                            PCI_COMMAND_WAIT|PCI_COMMAND_FAST_BACK)
33
34 static void *command_init(struct pci_dev *dev, int offset)
35 {
36         struct pci_cmd_info *cmd = kmalloc(sizeof(*cmd), GFP_KERNEL);
37         int err;
38
39         if (!cmd)
40                 return ERR_PTR(-ENOMEM);
41
42         err = pci_read_config_word(dev, PCI_COMMAND, &cmd->val);
43         if (err) {
44                 kfree(cmd);
45                 return ERR_PTR(err);
46         }
47
48         return cmd;
49 }
50
51 static int command_read(struct pci_dev *dev, int offset, u16 *value, void *data)
52 {
53         int ret = pci_read_config_word(dev, offset, value);
54         const struct pci_cmd_info *cmd = data;
55
56         *value &= PCI_COMMAND_GUEST;
57         *value |= cmd->val & ~PCI_COMMAND_GUEST;
58
59         return ret;
60 }
61
62 static int command_write(struct pci_dev *dev, int offset, u16 value, void *data)
63 {
64         struct xen_pcibk_dev_data *dev_data;
65         int err;
66         u16 val;
67         struct pci_cmd_info *cmd = data;
68
69         dev_data = pci_get_drvdata(dev);
70         if (!pci_is_enabled(dev) && is_enable_cmd(value)) {
71                 dev_dbg(&dev->dev, "enable\n");
72                 err = pci_enable_device(dev);
73                 if (err)
74                         return err;
75                 if (dev_data)
76                         dev_data->enable_intx = 1;
77         } else if (pci_is_enabled(dev) && !is_enable_cmd(value)) {
78                 dev_dbg(&dev->dev, "disable\n");
79                 pci_disable_device(dev);
80                 if (dev_data)
81                         dev_data->enable_intx = 0;
82         }
83
84         if (!dev->is_busmaster && is_master_cmd(value)) {
85                 dev_dbg(&dev->dev, "set bus master\n");
86                 pci_set_master(dev);
87         } else if (dev->is_busmaster && !is_master_cmd(value)) {
88                 dev_dbg(&dev->dev, "clear bus master\n");
89                 pci_clear_master(dev);
90         }
91
92         if (!(cmd->val & PCI_COMMAND_INVALIDATE) &&
93             (value & PCI_COMMAND_INVALIDATE)) {
94                 dev_dbg(&dev->dev, "enable memory-write-invalidate\n");
95                 err = pci_set_mwi(dev);
96                 if (err) {
97                         dev_warn(&dev->dev, "cannot enable memory-write-invalidate (%d)\n",
98                                 err);
99                         value &= ~PCI_COMMAND_INVALIDATE;
100                 }
101         } else if ((cmd->val & PCI_COMMAND_INVALIDATE) &&
102                    !(value & PCI_COMMAND_INVALIDATE)) {
103                 dev_dbg(&dev->dev, "disable memory-write-invalidate\n");
104                 pci_clear_mwi(dev);
105         }
106
107         if (dev_data && dev_data->allow_interrupt_control) {
108                 if ((cmd->val ^ value) & PCI_COMMAND_INTX_DISABLE) {
109                         if (value & PCI_COMMAND_INTX_DISABLE) {
110                                 pci_intx(dev, 0);
111                         } else {
112                                 /* Do not allow enabling INTx together with MSI or MSI-X. */
113                                 switch (xen_pcibk_get_interrupt_type(dev)) {
114                                 case INTERRUPT_TYPE_NONE:
115                                         pci_intx(dev, 1);
116                                         break;
117                                 case INTERRUPT_TYPE_INTX:
118                                         break;
119                                 default:
120                                         return PCIBIOS_SET_FAILED;
121                                 }
122                         }
123                 }
124         }
125
126         cmd->val = value;
127
128         if (!xen_pcibk_permissive && (!dev_data || !dev_data->permissive))
129                 return 0;
130
131         /* Only allow the guest to control certain bits. */
132         err = pci_read_config_word(dev, offset, &val);
133         if (err || val == value)
134                 return err;
135
136         value &= PCI_COMMAND_GUEST;
137         value |= val & ~PCI_COMMAND_GUEST;
138
139         return pci_write_config_word(dev, offset, value);
140 }
141
142 static int rom_write(struct pci_dev *dev, int offset, u32 value, void *data)
143 {
144         struct pci_bar_info *bar = data;
145
146         if (unlikely(!bar)) {
147                 dev_warn(&dev->dev, "driver data not found\n");
148                 return XEN_PCI_ERR_op_failed;
149         }
150
151         /* A write to obtain the length must happen as a 32-bit write.
152          * This does not (yet) support writing individual bytes
153          */
154         if ((value | ~PCI_ROM_ADDRESS_MASK) == ~0U)
155                 bar->which = 1;
156         else {
157                 u32 tmpval;
158                 pci_read_config_dword(dev, offset, &tmpval);
159                 if (tmpval != bar->val && value == bar->val) {
160                         /* Allow restoration of bar value. */
161                         pci_write_config_dword(dev, offset, bar->val);
162                 }
163                 bar->which = 0;
164         }
165
166         /* Do we need to support enabling/disabling the rom address here? */
167
168         return 0;
169 }
170
171 /* For the BARs, only allow writes which write ~0 or
172  * the correct resource information
173  * (Needed for when the driver probes the resource usage)
174  */
175 static int bar_write(struct pci_dev *dev, int offset, u32 value, void *data)
176 {
177         struct pci_bar_info *bar = data;
178         unsigned int pos = (offset - PCI_BASE_ADDRESS_0) / 4;
179         const struct resource *res = dev->resource;
180         u32 mask;
181
182         if (unlikely(!bar)) {
183                 dev_warn(&dev->dev, "driver data not found\n");
184                 return XEN_PCI_ERR_op_failed;
185         }
186
187         /* A write to obtain the length must happen as a 32-bit write.
188          * This does not (yet) support writing individual bytes
189          */
190         if (res[pos].flags & IORESOURCE_IO)
191                 mask = ~PCI_BASE_ADDRESS_IO_MASK;
192         else if (pos && (res[pos - 1].flags & IORESOURCE_MEM_64))
193                 mask = 0;
194         else
195                 mask = ~PCI_BASE_ADDRESS_MEM_MASK;
196         if ((value | mask) == ~0U)
197                 bar->which = 1;
198         else {
199                 u32 tmpval;
200                 pci_read_config_dword(dev, offset, &tmpval);
201                 if (tmpval != bar->val && value == bar->val) {
202                         /* Allow restoration of bar value. */
203                         pci_write_config_dword(dev, offset, bar->val);
204                 }
205                 bar->which = 0;
206         }
207
208         return 0;
209 }
210
211 static int bar_read(struct pci_dev *dev, int offset, u32 * value, void *data)
212 {
213         struct pci_bar_info *bar = data;
214
215         if (unlikely(!bar)) {
216                 dev_warn(&dev->dev, "driver data not found\n");
217                 return XEN_PCI_ERR_op_failed;
218         }
219
220         *value = bar->which ? bar->len_val : bar->val;
221
222         return 0;
223 }
224
225 static void *bar_init(struct pci_dev *dev, int offset)
226 {
227         unsigned int pos;
228         const struct resource *res = dev->resource;
229         struct pci_bar_info *bar = kzalloc(sizeof(*bar), GFP_KERNEL);
230
231         if (!bar)
232                 return ERR_PTR(-ENOMEM);
233
234         if (offset == PCI_ROM_ADDRESS || offset == PCI_ROM_ADDRESS1)
235                 pos = PCI_ROM_RESOURCE;
236         else {
237                 pos = (offset - PCI_BASE_ADDRESS_0) / 4;
238                 if (pos && (res[pos - 1].flags & IORESOURCE_MEM_64)) {
239                         bar->val = res[pos - 1].start >> 32;
240                         bar->len_val = -resource_size(&res[pos - 1]) >> 32;
241                         return bar;
242                 }
243         }
244
245         if (!res[pos].flags ||
246             (res[pos].flags & (IORESOURCE_DISABLED | IORESOURCE_UNSET |
247                                IORESOURCE_BUSY)))
248                 return bar;
249
250         bar->val = res[pos].start |
251                    (res[pos].flags & PCI_REGION_FLAG_MASK);
252         bar->len_val = -resource_size(&res[pos]) |
253                        (res[pos].flags & PCI_REGION_FLAG_MASK);
254
255         return bar;
256 }
257
258 static void bar_reset(struct pci_dev *dev, int offset, void *data)
259 {
260         struct pci_bar_info *bar = data;
261
262         bar->which = 0;
263 }
264
265 static void bar_release(struct pci_dev *dev, int offset, void *data)
266 {
267         kfree(data);
268 }
269
270 static int xen_pcibk_read_vendor(struct pci_dev *dev, int offset,
271                                u16 *value, void *data)
272 {
273         *value = dev->vendor;
274
275         return 0;
276 }
277
278 static int xen_pcibk_read_device(struct pci_dev *dev, int offset,
279                                u16 *value, void *data)
280 {
281         *value = dev->device;
282
283         return 0;
284 }
285
286 static int interrupt_read(struct pci_dev *dev, int offset, u8 * value,
287                           void *data)
288 {
289         *value = (u8) dev->irq;
290
291         return 0;
292 }
293
294 static int bist_write(struct pci_dev *dev, int offset, u8 value, void *data)
295 {
296         u8 cur_value;
297         int err;
298
299         err = pci_read_config_byte(dev, offset, &cur_value);
300         if (err)
301                 goto out;
302
303         if ((cur_value & ~PCI_BIST_START) == (value & ~PCI_BIST_START)
304             || value == PCI_BIST_START)
305                 err = pci_write_config_byte(dev, offset, value);
306
307 out:
308         return err;
309 }
310
311 static const struct config_field header_common[] = {
312         {
313          .offset    = PCI_VENDOR_ID,
314          .size      = 2,
315          .u.w.read  = xen_pcibk_read_vendor,
316         },
317         {
318          .offset    = PCI_DEVICE_ID,
319          .size      = 2,
320          .u.w.read  = xen_pcibk_read_device,
321         },
322         {
323          .offset    = PCI_COMMAND,
324          .size      = 2,
325          .init      = command_init,
326          .release   = bar_release,
327          .u.w.read  = command_read,
328          .u.w.write = command_write,
329         },
330         {
331          .offset    = PCI_INTERRUPT_LINE,
332          .size      = 1,
333          .u.b.read  = interrupt_read,
334         },
335         {
336          .offset    = PCI_INTERRUPT_PIN,
337          .size      = 1,
338          .u.b.read  = xen_pcibk_read_config_byte,
339         },
340         {
341          /* Any side effects of letting driver domain control cache line? */
342          .offset    = PCI_CACHE_LINE_SIZE,
343          .size      = 1,
344          .u.b.read  = xen_pcibk_read_config_byte,
345          .u.b.write = xen_pcibk_write_config_byte,
346         },
347         {
348          .offset    = PCI_LATENCY_TIMER,
349          .size      = 1,
350          .u.b.read  = xen_pcibk_read_config_byte,
351         },
352         {
353          .offset    = PCI_BIST,
354          .size      = 1,
355          .u.b.read  = xen_pcibk_read_config_byte,
356          .u.b.write = bist_write,
357         },
358         {}
359 };
360
361 #define CFG_FIELD_BAR(reg_offset)                       \
362         {                                               \
363         .offset     = reg_offset,                       \
364         .size       = 4,                                \
365         .init       = bar_init,                         \
366         .reset      = bar_reset,                        \
367         .release    = bar_release,                      \
368         .u.dw.read  = bar_read,                         \
369         .u.dw.write = bar_write,                        \
370         }
371
372 #define CFG_FIELD_ROM(reg_offset)                       \
373         {                                               \
374         .offset     = reg_offset,                       \
375         .size       = 4,                                \
376         .init       = bar_init,                         \
377         .reset      = bar_reset,                        \
378         .release    = bar_release,                      \
379         .u.dw.read  = bar_read,                         \
380         .u.dw.write = rom_write,                        \
381         }
382
383 static const struct config_field header_0[] = {
384         CFG_FIELD_BAR(PCI_BASE_ADDRESS_0),
385         CFG_FIELD_BAR(PCI_BASE_ADDRESS_1),
386         CFG_FIELD_BAR(PCI_BASE_ADDRESS_2),
387         CFG_FIELD_BAR(PCI_BASE_ADDRESS_3),
388         CFG_FIELD_BAR(PCI_BASE_ADDRESS_4),
389         CFG_FIELD_BAR(PCI_BASE_ADDRESS_5),
390         CFG_FIELD_ROM(PCI_ROM_ADDRESS),
391         {}
392 };
393
394 static const struct config_field header_1[] = {
395         CFG_FIELD_BAR(PCI_BASE_ADDRESS_0),
396         CFG_FIELD_BAR(PCI_BASE_ADDRESS_1),
397         CFG_FIELD_ROM(PCI_ROM_ADDRESS1),
398         {}
399 };
400
401 int xen_pcibk_config_header_add_fields(struct pci_dev *dev)
402 {
403         int err;
404
405         err = xen_pcibk_config_add_fields(dev, header_common);
406         if (err)
407                 goto out;
408
409         switch (dev->hdr_type) {
410         case PCI_HEADER_TYPE_NORMAL:
411                 err = xen_pcibk_config_add_fields(dev, header_0);
412                 break;
413
414         case PCI_HEADER_TYPE_BRIDGE:
415                 err = xen_pcibk_config_add_fields(dev, header_1);
416                 break;
417
418         default:
419                 err = -EINVAL;
420                 dev_err(&dev->dev, "Unsupported header type %d!\n",
421                         dev->hdr_type);
422                 break;
423         }
424
425 out:
426         return err;
427 }