1 /*
2  * This program is free software; you can redistribute it and/or modify it
3  * under the terms and conditions of the GNU General Public License,
4  * version 2, as published by the Free Software Foundation.
5  *
6  * This program is distributed in the hope it will be useful, but WITHOUT
7  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
8  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
9  * more details.
10  *
11  * You should have received a copy of the GNU General Public License along with
12  * this program; If not, see <http://www.gnu.org/licenses/>.
13  */
14 
15 #include <xen/sched.h>
16 #include <xen/iommu.h>
17 #include <xen/paging.h>
18 #include <xen/guest_access.h>
19 #include <xen/event.h>
20 #include <xen/param.h>
21 #include <xen/softirq.h>
22 #include <xen/keyhandler.h>
23 #include <xsm/xsm.h>
24 
25 static void iommu_dump_p2m_table(unsigned char key);
26 
27 unsigned int __read_mostly iommu_dev_iotlb_timeout = 1000;
28 integer_param("iommu_dev_iotlb_timeout", iommu_dev_iotlb_timeout);
29 
30 bool_t __initdata iommu_enable = 1;
31 bool_t __read_mostly iommu_enabled;
32 bool_t __read_mostly force_iommu;
33 bool_t __read_mostly iommu_verbose;
34 bool __read_mostly iommu_quarantine = true;
35 bool_t __read_mostly iommu_crash_disable;
36 
37 static bool __hwdom_initdata iommu_hwdom_none;
38 bool __hwdom_initdata iommu_hwdom_strict;
39 bool __read_mostly iommu_hwdom_passthrough;
40 bool __hwdom_initdata iommu_hwdom_inclusive;
41 int8_t __hwdom_initdata iommu_hwdom_reserved = -1;
42 
43 #ifndef iommu_hap_pt_share
44 bool __read_mostly iommu_hap_pt_share = true;
45 #endif
46 
47 bool_t __read_mostly iommu_debug;
48 bool_t __read_mostly amd_iommu_perdev_intremap = 1;
49 
50 DEFINE_PER_CPU(bool_t, iommu_dont_flush_iotlb);
51 
52 DEFINE_SPINLOCK(iommu_pt_cleanup_lock);
53 PAGE_LIST_HEAD(iommu_pt_cleanup_list);
54 static struct tasklet iommu_pt_cleanup_tasklet;
55 
parse_iommu_param(const char * s)56 static int __init parse_iommu_param(const char *s)
57 {
58     const char *ss;
59     int val, rc = 0;
60 
61     do {
62         ss = strchr(s, ',');
63         if ( !ss )
64             ss = strchr(s, '\0');
65 
66         if ( (val = parse_bool(s, ss)) >= 0 )
67             iommu_enable = val;
68         else if ( (val = parse_boolean("force", s, ss)) >= 0 ||
69                   (val = parse_boolean("required", s, ss)) >= 0 )
70             force_iommu = val;
71         else if ( (val = parse_boolean("quarantine", s, ss)) >= 0 )
72             iommu_quarantine = val;
73 #ifdef CONFIG_X86
74         else if ( (val = parse_boolean("igfx", s, ss)) >= 0 )
75             iommu_igfx = val;
76         else if ( (val = parse_boolean("qinval", s, ss)) >= 0 )
77             iommu_qinval = val;
78 #endif
79         else if ( (val = parse_boolean("verbose", s, ss)) >= 0 )
80             iommu_verbose = val;
81 #ifndef iommu_snoop
82         else if ( (val = parse_boolean("snoop", s, ss)) >= 0 )
83             iommu_snoop = val;
84 #endif
85 #ifndef iommu_intremap
86         else if ( (val = parse_boolean("intremap", s, ss)) >= 0 )
87             iommu_intremap = val ? iommu_intremap_full : iommu_intremap_off;
88 #endif
89 #ifndef iommu_intpost
90         else if ( (val = parse_boolean("intpost", s, ss)) >= 0 )
91             iommu_intpost = val;
92 #endif
93 #ifdef CONFIG_KEXEC
94         else if ( (val = parse_boolean("crash-disable", s, ss)) >= 0 )
95             iommu_crash_disable = val;
96 #endif
97         else if ( (val = parse_boolean("debug", s, ss)) >= 0 )
98         {
99             iommu_debug = val;
100             if ( val )
101                 iommu_verbose = 1;
102         }
103         else if ( (val = parse_boolean("amd-iommu-perdev-intremap", s, ss)) >= 0 )
104             amd_iommu_perdev_intremap = val;
105         else if ( (val = parse_boolean("dom0-passthrough", s, ss)) >= 0 )
106             iommu_hwdom_passthrough = val;
107         else if ( (val = parse_boolean("dom0-strict", s, ss)) >= 0 )
108             iommu_hwdom_strict = val;
109 #ifndef iommu_hap_pt_share
110         else if ( (val = parse_boolean("sharept", s, ss)) >= 0 )
111             iommu_hap_pt_share = val;
112 #endif
113         else
114             rc = -EINVAL;
115 
116         s = ss + 1;
117     } while ( *ss );
118 
119     return rc;
120 }
121 custom_param("iommu", parse_iommu_param);
122 
parse_dom0_iommu_param(const char * s)123 static int __init parse_dom0_iommu_param(const char *s)
124 {
125     const char *ss;
126     int rc = 0;
127 
128     do {
129         int val;
130 
131         ss = strchr(s, ',');
132         if ( !ss )
133             ss = strchr(s, '\0');
134 
135         if ( (val = parse_boolean("passthrough", s, ss)) >= 0 )
136             iommu_hwdom_passthrough = val;
137         else if ( (val = parse_boolean("strict", s, ss)) >= 0 )
138             iommu_hwdom_strict = val;
139         else if ( (val = parse_boolean("map-inclusive", s, ss)) >= 0 )
140             iommu_hwdom_inclusive = val;
141         else if ( (val = parse_boolean("map-reserved", s, ss)) >= 0 )
142             iommu_hwdom_reserved = val;
143         else if ( !cmdline_strcmp(s, "none") )
144             iommu_hwdom_none = true;
145         else
146             rc = -EINVAL;
147 
148         s = ss + 1;
149     } while ( *ss );
150 
151     return rc;
152 }
153 custom_param("dom0-iommu", parse_dom0_iommu_param);
154 
check_hwdom_reqs(struct domain * d)155 static void __hwdom_init check_hwdom_reqs(struct domain *d)
156 {
157     if ( iommu_hwdom_none || !is_hvm_domain(d) )
158         return;
159 
160     iommu_hwdom_passthrough = false;
161     iommu_hwdom_strict = true;
162 
163     arch_iommu_check_autotranslated_hwdom(d);
164 }
165 
iommu_domain_init(struct domain * d,unsigned int opts)166 int iommu_domain_init(struct domain *d, unsigned int opts)
167 {
168     struct domain_iommu *hd = dom_iommu(d);
169     int ret = 0;
170 
171     if ( is_hardware_domain(d) )
172         check_hwdom_reqs(d); /* may modify iommu_hwdom_strict */
173 
174     if ( !is_iommu_enabled(d) )
175         return 0;
176 
177 #ifdef CONFIG_NUMA
178     hd->node = NUMA_NO_NODE;
179 #endif
180 
181     ret = arch_iommu_domain_init(d);
182     if ( ret )
183         return ret;
184 
185     hd->platform_ops = iommu_get_ops();
186     ret = hd->platform_ops->init(d);
187     if ( ret || is_system_domain(d) )
188         return ret;
189 
190     /*
191      * Use shared page tables for HAP and IOMMU if the global option
192      * is enabled (from which we can infer the h/w is capable) and
193      * the domain options do not disallow it. HAP must, of course, also
194      * be enabled.
195      */
196     hd->hap_pt_share = hap_enabled(d) && iommu_hap_pt_share &&
197         !(opts & XEN_DOMCTL_IOMMU_no_sharept);
198 
199     /*
200      * NB: 'relaxed' h/w domains don't need the IOMMU mappings to be kept
201      *     in-sync with their assigned pages because all host RAM will be
202      *     mapped during hwdom_init().
203      */
204     if ( !is_hardware_domain(d) || iommu_hwdom_strict )
205         hd->need_sync = !iommu_use_hap_pt(d);
206 
207     ASSERT(!(hd->need_sync && hd->hap_pt_share));
208 
209     return 0;
210 }
211 
iommu_hwdom_init(struct domain * d)212 void __hwdom_init iommu_hwdom_init(struct domain *d)
213 {
214     struct domain_iommu *hd = dom_iommu(d);
215 
216     if ( !is_iommu_enabled(d) )
217         return;
218 
219     register_keyhandler('o', &iommu_dump_p2m_table, "dump iommu p2m table", 0);
220 
221     hd->platform_ops->hwdom_init(d);
222 }
223 
iommu_teardown(struct domain * d)224 static void iommu_teardown(struct domain *d)
225 {
226     struct domain_iommu *hd = dom_iommu(d);
227 
228     hd->platform_ops->teardown(d);
229     tasklet_schedule(&iommu_pt_cleanup_tasklet);
230 }
231 
iommu_domain_destroy(struct domain * d)232 void iommu_domain_destroy(struct domain *d)
233 {
234     if ( !is_iommu_enabled(d) )
235         return;
236 
237     iommu_teardown(d);
238 
239     arch_iommu_domain_destroy(d);
240 }
241 
iommu_map(struct domain * d,dfn_t dfn,mfn_t mfn,unsigned int page_order,unsigned int flags,unsigned int * flush_flags)242 int iommu_map(struct domain *d, dfn_t dfn, mfn_t mfn,
243               unsigned int page_order, unsigned int flags,
244               unsigned int *flush_flags)
245 {
246     const struct domain_iommu *hd = dom_iommu(d);
247     unsigned long i;
248     int rc = 0;
249 
250     if ( !is_iommu_enabled(d) )
251         return 0;
252 
253     ASSERT(IS_ALIGNED(dfn_x(dfn), (1ul << page_order)));
254     ASSERT(IS_ALIGNED(mfn_x(mfn), (1ul << page_order)));
255 
256     for ( i = 0; i < (1ul << page_order); i++ )
257     {
258         rc = iommu_call(hd->platform_ops, map_page, d, dfn_add(dfn, i),
259                         mfn_add(mfn, i), flags, flush_flags);
260 
261         if ( likely(!rc) )
262             continue;
263 
264         if ( !d->is_shutting_down && printk_ratelimit() )
265             printk(XENLOG_ERR
266                    "d%d: IOMMU mapping dfn %"PRI_dfn" to mfn %"PRI_mfn" failed: %d\n",
267                    d->domain_id, dfn_x(dfn_add(dfn, i)),
268                    mfn_x(mfn_add(mfn, i)), rc);
269 
270         while ( i-- )
271             /* if statement to satisfy __must_check */
272             if ( iommu_call(hd->platform_ops, unmap_page, d, dfn_add(dfn, i),
273                             flush_flags) )
274                 continue;
275 
276         if ( !is_hardware_domain(d) )
277             domain_crash(d);
278 
279         break;
280     }
281 
282     return rc;
283 }
284 
iommu_legacy_map(struct domain * d,dfn_t dfn,mfn_t mfn,unsigned int page_order,unsigned int flags)285 int iommu_legacy_map(struct domain *d, dfn_t dfn, mfn_t mfn,
286                      unsigned int page_order, unsigned int flags)
287 {
288     unsigned int flush_flags = 0;
289     int rc = iommu_map(d, dfn, mfn, page_order, flags, &flush_flags);
290 
291     if ( !this_cpu(iommu_dont_flush_iotlb) )
292     {
293         int err = iommu_iotlb_flush(d, dfn, (1u << page_order),
294                                     flush_flags);
295 
296         if ( !rc )
297             rc = err;
298     }
299 
300     return rc;
301 }
302 
iommu_unmap(struct domain * d,dfn_t dfn,unsigned int page_order,unsigned int * flush_flags)303 int iommu_unmap(struct domain *d, dfn_t dfn, unsigned int page_order,
304                 unsigned int *flush_flags)
305 {
306     const struct domain_iommu *hd = dom_iommu(d);
307     unsigned long i;
308     int rc = 0;
309 
310     if ( !is_iommu_enabled(d) )
311         return 0;
312 
313     ASSERT(IS_ALIGNED(dfn_x(dfn), (1ul << page_order)));
314 
315     for ( i = 0; i < (1ul << page_order); i++ )
316     {
317         int err = iommu_call(hd->platform_ops, unmap_page, d, dfn_add(dfn, i),
318                              flush_flags);
319 
320         if ( likely(!err) )
321             continue;
322 
323         if ( !d->is_shutting_down && printk_ratelimit() )
324             printk(XENLOG_ERR
325                    "d%d: IOMMU unmapping dfn %"PRI_dfn" failed: %d\n",
326                    d->domain_id, dfn_x(dfn_add(dfn, i)), err);
327 
328         if ( !rc )
329             rc = err;
330 
331         if ( !is_hardware_domain(d) )
332         {
333             domain_crash(d);
334             break;
335         }
336     }
337 
338     return rc;
339 }
340 
iommu_legacy_unmap(struct domain * d,dfn_t dfn,unsigned int page_order)341 int iommu_legacy_unmap(struct domain *d, dfn_t dfn, unsigned int page_order)
342 {
343     unsigned int flush_flags = 0;
344     int rc = iommu_unmap(d, dfn, page_order, &flush_flags);
345 
346     if ( !this_cpu(iommu_dont_flush_iotlb) )
347     {
348         int err = iommu_iotlb_flush(d, dfn, (1u << page_order),
349                                     flush_flags);
350 
351         if ( !rc )
352             rc = err;
353     }
354 
355     return rc;
356 }
357 
iommu_lookup_page(struct domain * d,dfn_t dfn,mfn_t * mfn,unsigned int * flags)358 int iommu_lookup_page(struct domain *d, dfn_t dfn, mfn_t *mfn,
359                       unsigned int *flags)
360 {
361     const struct domain_iommu *hd = dom_iommu(d);
362 
363     if ( !is_iommu_enabled(d) || !hd->platform_ops->lookup_page )
364         return -EOPNOTSUPP;
365 
366     return iommu_call(hd->platform_ops, lookup_page, d, dfn, mfn, flags);
367 }
368 
iommu_free_pagetables(void * unused)369 static void iommu_free_pagetables(void *unused)
370 {
371     do {
372         struct page_info *pg;
373 
374         spin_lock(&iommu_pt_cleanup_lock);
375         pg = page_list_remove_head(&iommu_pt_cleanup_list);
376         spin_unlock(&iommu_pt_cleanup_lock);
377         if ( !pg )
378             return;
379         iommu_vcall(iommu_get_ops(), free_page_table, pg);
380     } while ( !softirq_pending(smp_processor_id()) );
381 
382     tasklet_schedule_on_cpu(&iommu_pt_cleanup_tasklet,
383                             cpumask_cycle(smp_processor_id(), &cpu_online_map));
384 }
385 
iommu_iotlb_flush(struct domain * d,dfn_t dfn,unsigned int page_count,unsigned int flush_flags)386 int iommu_iotlb_flush(struct domain *d, dfn_t dfn, unsigned int page_count,
387                       unsigned int flush_flags)
388 {
389     const struct domain_iommu *hd = dom_iommu(d);
390     int rc;
391 
392     if ( !is_iommu_enabled(d) || !hd->platform_ops->iotlb_flush ||
393          !page_count || !flush_flags )
394         return 0;
395 
396     if ( dfn_eq(dfn, INVALID_DFN) )
397         return -EINVAL;
398 
399     rc = iommu_call(hd->platform_ops, iotlb_flush, d, dfn, page_count,
400                     flush_flags);
401     if ( unlikely(rc) )
402     {
403         if ( !d->is_shutting_down && printk_ratelimit() )
404             printk(XENLOG_ERR
405                    "d%d: IOMMU IOTLB flush failed: %d, dfn %"PRI_dfn", page count %u flags %x\n",
406                    d->domain_id, rc, dfn_x(dfn), page_count, flush_flags);
407 
408         if ( !is_hardware_domain(d) )
409             domain_crash(d);
410     }
411 
412     return rc;
413 }
414 
iommu_iotlb_flush_all(struct domain * d,unsigned int flush_flags)415 int iommu_iotlb_flush_all(struct domain *d, unsigned int flush_flags)
416 {
417     const struct domain_iommu *hd = dom_iommu(d);
418     int rc;
419 
420     if ( !is_iommu_enabled(d) || !hd->platform_ops->iotlb_flush_all ||
421          !flush_flags )
422         return 0;
423 
424     /*
425      * The operation does a full flush so we don't need to pass the
426      * flush_flags in.
427      */
428     rc = iommu_call(hd->platform_ops, iotlb_flush_all, d);
429     if ( unlikely(rc) )
430     {
431         if ( !d->is_shutting_down && printk_ratelimit() )
432             printk(XENLOG_ERR
433                    "d%d: IOMMU IOTLB flush all failed: %d\n",
434                    d->domain_id, rc);
435 
436         if ( !is_hardware_domain(d) )
437             domain_crash(d);
438     }
439 
440     return rc;
441 }
442 
iommu_quarantine_init(void)443 static int __init iommu_quarantine_init(void)
444 {
445     const struct domain_iommu *hd = dom_iommu(dom_io);
446     int rc;
447 
448     dom_io->options |= XEN_DOMCTL_CDF_iommu;
449 
450     rc = iommu_domain_init(dom_io, 0);
451     if ( rc )
452         return rc;
453 
454     if ( !hd->platform_ops->quarantine_init )
455         return 0;
456 
457     return hd->platform_ops->quarantine_init(dom_io);
458 }
459 
iommu_setup(void)460 int __init iommu_setup(void)
461 {
462     int rc = -ENODEV;
463     bool_t force_intremap = force_iommu && iommu_intremap;
464 
465     if ( iommu_hwdom_strict )
466         iommu_hwdom_passthrough = false;
467 
468     if ( iommu_enable )
469     {
470         rc = iommu_hardware_setup();
471         iommu_enabled = (rc == 0);
472     }
473 
474 #ifndef iommu_intremap
475     if ( !iommu_enabled )
476         iommu_intremap = iommu_intremap_off;
477 #endif
478 
479     if ( (force_iommu && !iommu_enabled) ||
480          (force_intremap && !iommu_intremap) )
481         panic("Couldn't enable %s and iommu=required/force\n",
482               !iommu_enabled ? "IOMMU" : "Interrupt Remapping");
483 
484 #ifndef iommu_intpost
485     if ( !iommu_intremap )
486         iommu_intpost = false;
487 #endif
488 
489     printk("I/O virtualisation %sabled\n", iommu_enabled ? "en" : "dis");
490     if ( !iommu_enabled )
491     {
492 #ifndef iommu_snoop
493         iommu_snoop = false;
494 #endif
495         iommu_hwdom_passthrough = false;
496         iommu_hwdom_strict = false;
497     }
498     else
499     {
500         if ( iommu_quarantine_init() )
501             panic("Could not set up quarantine\n");
502 
503         printk(" - Dom0 mode: %s\n",
504                iommu_hwdom_passthrough ? "Passthrough" :
505                iommu_hwdom_strict ? "Strict" : "Relaxed");
506 #ifndef iommu_intremap
507         printk("Interrupt remapping %sabled\n", iommu_intremap ? "en" : "dis");
508 #endif
509         tasklet_init(&iommu_pt_cleanup_tasklet, iommu_free_pagetables, NULL);
510     }
511 
512     return rc;
513 }
514 
iommu_suspend()515 int iommu_suspend()
516 {
517     if ( iommu_enabled )
518         return iommu_get_ops()->suspend();
519 
520     return 0;
521 }
522 
iommu_resume()523 void iommu_resume()
524 {
525     if ( iommu_enabled )
526         iommu_get_ops()->resume();
527 }
528 
iommu_do_domctl(struct xen_domctl * domctl,struct domain * d,XEN_GUEST_HANDLE_PARAM (xen_domctl_t)u_domctl)529 int iommu_do_domctl(
530     struct xen_domctl *domctl, struct domain *d,
531     XEN_GUEST_HANDLE_PARAM(xen_domctl_t) u_domctl)
532 {
533     int ret = -ENODEV;
534 
535     if ( !is_iommu_enabled(d) )
536         return -EOPNOTSUPP;
537 
538 #ifdef CONFIG_HAS_PCI
539     ret = iommu_do_pci_domctl(domctl, d, u_domctl);
540 #endif
541 
542 #ifdef CONFIG_HAS_DEVICE_TREE
543     if ( ret == -ENODEV )
544         ret = iommu_do_dt_domctl(domctl, d, u_domctl);
545 #endif
546 
547     return ret;
548 }
549 
iommu_share_p2m_table(struct domain * d)550 void iommu_share_p2m_table(struct domain* d)
551 {
552     ASSERT(hap_enabled(d));
553 
554     if ( iommu_use_hap_pt(d) )
555         iommu_get_ops()->share_p2m(d);
556 }
557 
iommu_crash_shutdown(void)558 void iommu_crash_shutdown(void)
559 {
560     if ( !iommu_crash_disable )
561         return;
562 
563     if ( iommu_enabled )
564         iommu_get_ops()->crash_shutdown();
565     iommu_enabled = false;
566 #ifndef iommu_intremap
567     iommu_intremap = iommu_intremap_off;
568 #endif
569 #ifndef iommu_intpost
570     iommu_intpost = false;
571 #endif
572 }
573 
iommu_get_reserved_device_memory(iommu_grdm_t * func,void * ctxt)574 int iommu_get_reserved_device_memory(iommu_grdm_t *func, void *ctxt)
575 {
576     const struct iommu_ops *ops;
577 
578     if ( !iommu_enabled )
579         return 0;
580 
581     ops = iommu_get_ops();
582     if ( !ops->get_reserved_device_memory )
583         return 0;
584 
585     return ops->get_reserved_device_memory(func, ctxt);
586 }
587 
iommu_has_feature(struct domain * d,enum iommu_feature feature)588 bool_t iommu_has_feature(struct domain *d, enum iommu_feature feature)
589 {
590     return is_iommu_enabled(d) && test_bit(feature, dom_iommu(d)->features);
591 }
592 
iommu_dump_p2m_table(unsigned char key)593 static void iommu_dump_p2m_table(unsigned char key)
594 {
595     struct domain *d;
596     const struct iommu_ops *ops;
597 
598     if ( !iommu_enabled )
599     {
600         printk("IOMMU not enabled!\n");
601         return;
602     }
603 
604     ops = iommu_get_ops();
605 
606     rcu_read_lock(&domlist_read_lock);
607 
608     for_each_domain(d)
609     {
610         if ( is_hardware_domain(d) || !is_iommu_enabled(d) )
611             continue;
612 
613         if ( iommu_use_hap_pt(d) )
614         {
615             printk("\ndomain%d IOMMU p2m table shared with MMU: \n", d->domain_id);
616             continue;
617         }
618 
619         printk("\ndomain%d IOMMU p2m table: \n", d->domain_id);
620         ops->dump_p2m_table(d);
621     }
622 
623     rcu_read_unlock(&domlist_read_lock);
624 }
625 
626 /*
627  * Local variables:
628  * mode: C
629  * c-file-style: "BSD"
630  * c-basic-offset: 4
631  * indent-tabs-mode: nil
632  * End:
633  */
634