@@ -725,67 +725,84 @@ static void idxd_cleanup(struct idxd_device *idxd)
725
725
idxd_disable_sva (idxd -> pdev );
726
726
}
727
727
728
- static int idxd_pci_probe (struct pci_dev * pdev , const struct pci_device_id * id )
728
+ /*
729
+ * Probe idxd PCI device.
730
+ * If idxd is not given, need to allocate idxd and set up its data.
731
+ *
732
+ * If idxd is given, idxd was allocated and setup already. Just need to
733
+ * configure device without re-allocating and re-configuring idxd data.
734
+ * This is useful for recovering from FLR.
735
+ */
736
+ int idxd_pci_probe_alloc (struct idxd_device * idxd , struct pci_dev * pdev ,
737
+ const struct pci_device_id * id )
729
738
{
730
- struct device * dev = & pdev -> dev ;
731
- struct idxd_device * idxd ;
732
- struct idxd_driver_data * data = ( struct idxd_driver_data * ) id -> driver_data ;
739
+ bool alloc_idxd = idxd ? false : true ;
740
+ struct idxd_driver_data * data ;
741
+ struct device * dev ;
733
742
int rc ;
734
743
744
+ pdev = idxd ? idxd -> pdev : pdev ;
745
+ dev = & pdev -> dev ;
746
+ data = id ? (struct idxd_driver_data * )id -> driver_data : NULL ;
735
747
rc = pci_enable_device (pdev );
736
748
if (rc )
737
749
return rc ;
738
750
739
- dev_dbg (dev , "Alloc IDXD context\n" );
740
- idxd = idxd_alloc (pdev , data );
741
- if (!idxd ) {
742
- rc = - ENOMEM ;
743
- goto err_idxd_alloc ;
744
- }
751
+ if (alloc_idxd ) {
752
+ dev_dbg (dev , "Alloc IDXD context\n" );
753
+ idxd = idxd_alloc (pdev , data );
754
+ if (!idxd ) {
755
+ rc = - ENOMEM ;
756
+ goto err_idxd_alloc ;
757
+ }
745
758
746
- dev_dbg (dev , "Mapping BARs\n" );
747
- idxd -> reg_base = pci_iomap (pdev , IDXD_MMIO_BAR , 0 );
748
- if (!idxd -> reg_base ) {
749
- rc = - ENOMEM ;
750
- goto err_iomap ;
751
- }
759
+ dev_dbg (dev , "Mapping BARs\n" );
760
+ idxd -> reg_base = pci_iomap (pdev , IDXD_MMIO_BAR , 0 );
761
+ if (!idxd -> reg_base ) {
762
+ rc = - ENOMEM ;
763
+ goto err_iomap ;
764
+ }
752
765
753
- dev_dbg (dev , "Set DMA masks\n" );
754
- rc = dma_set_mask_and_coherent (& pdev -> dev , DMA_BIT_MASK (64 ));
755
- if (rc )
756
- goto err ;
766
+ dev_dbg (dev , "Set DMA masks\n" );
767
+ rc = dma_set_mask_and_coherent (& pdev -> dev , DMA_BIT_MASK (64 ));
768
+ if (rc )
769
+ goto err ;
770
+ }
757
771
758
772
dev_dbg (dev , "Set PCI master\n" );
759
773
pci_set_master (pdev );
760
774
pci_set_drvdata (pdev , idxd );
761
775
762
- idxd -> hw .version = ioread32 (idxd -> reg_base + IDXD_VER_OFFSET );
763
- rc = idxd_probe (idxd );
764
- if (rc ) {
765
- dev_err (dev , "Intel(R) IDXD DMA Engine init failed\n" );
766
- goto err ;
767
- }
776
+ if (alloc_idxd ) {
777
+ idxd -> hw .version = ioread32 (idxd -> reg_base + IDXD_VER_OFFSET );
778
+ rc = idxd_probe (idxd );
779
+ if (rc ) {
780
+ dev_err (dev , "Intel(R) IDXD DMA Engine init failed\n" );
781
+ goto err ;
782
+ }
768
783
769
- if (data -> load_device_defaults ) {
770
- rc = data -> load_device_defaults (idxd );
771
- if (rc )
772
- dev_warn (dev , "IDXD loading device defaults failed\n" );
773
- }
784
+ if (data -> load_device_defaults ) {
785
+ rc = data -> load_device_defaults (idxd );
786
+ if (rc )
787
+ dev_warn (dev , "IDXD loading device defaults failed\n" );
788
+ }
774
789
775
- rc = idxd_register_devices (idxd );
776
- if (rc ) {
777
- dev_err (dev , "IDXD sysfs setup failed\n" );
778
- goto err_dev_register ;
779
- }
790
+ rc = idxd_register_devices (idxd );
791
+ if (rc ) {
792
+ dev_err (dev , "IDXD sysfs setup failed\n" );
793
+ goto err_dev_register ;
794
+ }
780
795
781
- rc = idxd_device_init_debugfs (idxd );
782
- if (rc )
783
- dev_warn (dev , "IDXD debugfs failed to setup\n" );
796
+ rc = idxd_device_init_debugfs (idxd );
797
+ if (rc )
798
+ dev_warn (dev , "IDXD debugfs failed to setup\n" );
799
+ }
784
800
785
801
dev_info (& pdev -> dev , "Intel(R) Accelerator Device (v%x)\n" ,
786
802
idxd -> hw .version );
787
803
788
- idxd -> user_submission_safe = data -> user_submission_safe ;
804
+ if (data )
805
+ idxd -> user_submission_safe = data -> user_submission_safe ;
789
806
790
807
return 0 ;
791
808
@@ -800,6 +817,11 @@ static int idxd_pci_probe(struct pci_dev *pdev, const struct pci_device_id *id)
800
817
return rc ;
801
818
}
802
819
820
+ static int idxd_pci_probe (struct pci_dev * pdev , const struct pci_device_id * id )
821
+ {
822
+ return idxd_pci_probe_alloc (NULL , pdev , id );
823
+ }
824
+
803
825
void idxd_wqs_quiesce (struct idxd_device * idxd )
804
826
{
805
827
struct idxd_wq * wq ;
0 commit comments