diff options
-rw-r--r-- | drivers/scsi/isci/init.c | 7 | ||||
-rw-r--r-- | drivers/scsi/isci/probe_roms.c | 64 | ||||
-rw-r--r-- | drivers/scsi/isci/probe_roms.h | 2 |
3 files changed, 68 insertions, 5 deletions
diff --git a/drivers/scsi/isci/init.c b/drivers/scsi/isci/init.c index 65519321e1cc..13105294fbea 100644 --- a/drivers/scsi/isci/init.c +++ b/drivers/scsi/isci/init.c | |||
@@ -474,10 +474,9 @@ static int __devinit isci_pci_probe(struct pci_dev *pdev, const struct pci_devic | |||
474 | return -ENOMEM; | 474 | return -ENOMEM; |
475 | pci_set_drvdata(pdev, pci_info); | 475 | pci_set_drvdata(pdev, pci_info); |
476 | 476 | ||
477 | if (efi_enabled) { | 477 | if (efi_enabled) |
478 | /* do EFI parsing here */ | 478 | orom = isci_get_efi_var(pdev); |
479 | orom = NULL; | 479 | else |
480 | } else | ||
481 | orom = isci_request_oprom(pdev); | 480 | orom = isci_request_oprom(pdev); |
482 | 481 | ||
483 | if (!orom) { | 482 | if (!orom) { |
diff --git a/drivers/scsi/isci/probe_roms.c b/drivers/scsi/isci/probe_roms.c index 0b90e7c546c0..927feaddc04d 100644 --- a/drivers/scsi/isci/probe_roms.c +++ b/drivers/scsi/isci/probe_roms.c | |||
@@ -27,6 +27,7 @@ | |||
27 | #include <linux/kernel.h> | 27 | #include <linux/kernel.h> |
28 | #include <linux/firmware.h> | 28 | #include <linux/firmware.h> |
29 | #include <linux/uaccess.h> | 29 | #include <linux/uaccess.h> |
30 | #include <linux/efi.h> | ||
30 | #include <asm/probe_roms.h> | 31 | #include <asm/probe_roms.h> |
31 | 32 | ||
32 | #include "isci.h" | 33 | #include "isci.h" |
@@ -36,6 +37,15 @@ | |||
36 | #include "sci_environment.h" | 37 | #include "sci_environment.h" |
37 | #include "probe_roms.h" | 38 | #include "probe_roms.h" |
38 | 39 | ||
40 | struct efi_variable { | ||
41 | efi_char16_t VariableName[1024/sizeof(efi_char16_t)]; | ||
42 | efi_guid_t VendorGuid; | ||
43 | unsigned long DataSize; | ||
44 | __u8 Data[1024]; | ||
45 | efi_status_t Status; | ||
46 | __u32 Attributes; | ||
47 | } __attribute__((packed)); | ||
48 | |||
39 | struct isci_orom *isci_request_oprom(struct pci_dev *pdev) | 49 | struct isci_orom *isci_request_oprom(struct pci_dev *pdev) |
40 | { | 50 | { |
41 | void __iomem *oprom = pci_map_biosrom(pdev); | 51 | void __iomem *oprom = pci_map_biosrom(pdev); |
@@ -131,3 +141,57 @@ struct isci_orom *isci_request_firmware(struct pci_dev *pdev, const struct firmw | |||
131 | 141 | ||
132 | return orom; | 142 | return orom; |
133 | } | 143 | } |
144 | |||
145 | static struct efi *get_efi(void) | ||
146 | { | ||
147 | #ifdef CONFIG_EFI | ||
148 | return &efi; | ||
149 | #else | ||
150 | return NULL; | ||
151 | #endif | ||
152 | } | ||
153 | |||
154 | struct isci_orom *isci_get_efi_var(struct pci_dev *pdev) | ||
155 | { | ||
156 | struct efi_variable *evar; | ||
157 | efi_status_t status; | ||
158 | struct isci_orom *orom = NULL; | ||
159 | |||
160 | evar = devm_kzalloc(&pdev->dev, | ||
161 | sizeof(struct efi_variable), | ||
162 | GFP_KERNEL); | ||
163 | if (!evar) { | ||
164 | dev_warn(&pdev->dev, | ||
165 | "Unable to allocate memory for EFI var\n"); | ||
166 | return NULL; | ||
167 | } | ||
168 | |||
169 | evar->DataSize = 1024; | ||
170 | evar->VendorGuid = ISCI_EFI_VENDOR_GUID; | ||
171 | evar->Attributes = ISCI_EFI_ATTRIBUTES; | ||
172 | |||
173 | if (get_efi()) | ||
174 | status = get_efi()->get_variable(evar->VariableName, | ||
175 | &evar->VendorGuid, | ||
176 | &evar->Attributes, | ||
177 | &evar->DataSize, | ||
178 | evar->Data); | ||
179 | else | ||
180 | status = EFI_NOT_FOUND; | ||
181 | |||
182 | if (status == EFI_SUCCESS) | ||
183 | orom = (struct isci_orom *)evar->Data; | ||
184 | else | ||
185 | dev_warn(&pdev->dev, | ||
186 | "Unable to obtain EFI variable for OEM parms\n"); | ||
187 | |||
188 | if (orom && memcmp(orom->hdr.signature, ISCI_ROM_SIG, | ||
189 | strlen(ISCI_ROM_SIG)) != 0) | ||
190 | dev_warn(&pdev->dev, | ||
191 | "Verifying OROM signature failed\n"); | ||
192 | |||
193 | if (!orom) | ||
194 | devm_kfree(&pdev->dev, evar); | ||
195 | |||
196 | return orom; | ||
197 | } | ||
diff --git a/drivers/scsi/isci/probe_roms.h b/drivers/scsi/isci/probe_roms.h index 76651c01895a..96d8b9212457 100644 --- a/drivers/scsi/isci/probe_roms.h +++ b/drivers/scsi/isci/probe_roms.h | |||
@@ -69,7 +69,7 @@ enum sci_status isci_parse_oem_parameters( | |||
69 | struct isci_orom *orom, | 69 | struct isci_orom *orom, |
70 | int scu_index); | 70 | int scu_index); |
71 | struct isci_orom *isci_request_firmware(struct pci_dev *pdev, const struct firmware *fw); | 71 | struct isci_orom *isci_request_firmware(struct pci_dev *pdev, const struct firmware *fw); |
72 | int isci_get_efi_var(struct pci_dev *pdev); | 72 | struct isci_orom *isci_get_efi_var(struct pci_dev *pdev); |
73 | #else | 73 | #else |
74 | #define SCI_MAX_PORTS 4 | 74 | #define SCI_MAX_PORTS 4 |
75 | #define SCI_MAX_PHYS 4 | 75 | #define SCI_MAX_PHYS 4 |