]> git.proxmox.com Git - mirror_edk2.git/blame - QuarkSocPkg/QuarkNorthCluster/QNCInit/Dxe/DxeQNCSmbus.c
QuarkSocPkg: Replace BSD License with BSD+Patent License
[mirror_edk2.git] / QuarkSocPkg / QuarkNorthCluster / QNCInit / Dxe / DxeQNCSmbus.c
CommitLineData
9b6bbcdb
MK
1/** @file\r
2Implementation for SMBus DXE driver entry point and SMBus Host\r
3Controller protocol.\r
4\r
5Copyright (c) 2013-2015 Intel Corporation.\r
6\r
c9f231d0 7SPDX-License-Identifier: BSD-2-Clause-Patent\r
9b6bbcdb
MK
8\r
9**/\r
10#include "CommonHeader.h"\r
11\r
12#include "DxeQNCSmbus.h"\r
13\r
14//\r
15// Interface defintion of SMBUS Host Controller Protocol.\r
16//\r
17EFI_SMBUS_HC_PROTOCOL mSmbusHc = {\r
18 SmbusExecute,\r
19 SmbusArpDevice,\r
20 SmbusGetArpMap,\r
21 SmbusNotify\r
22};\r
23\r
24//\r
25// Handle to install SMBus Host Controller protocol.\r
26//\r
27EFI_HANDLE mSmbusHcHandle = NULL;\r
28UINT8 mDeviceMapEntries = 0;\r
29EFI_SMBUS_DEVICE_MAP mDeviceMap[MAX_SMBUS_DEVICES];\r
30UINT8 mPlatformNumRsvd = 0;\r
31UINT8 *mPlatformAddrRsvd = NULL;\r
32\r
33//\r
34// These addresses are reserved by the SMBus 2.0 specification\r
35//\r
36UINT8 mReservedAddress[SMBUS_NUM_RESERVED] = {\r
37 0x00, 0x02, 0x04, 0x06, 0x08, 0x0A, 0x0C, 0x0E, 0x10, 0x18, 0x50, 0x6E, 0xC2,\r
38 0xF0, 0xF2, 0xF4, 0xF6, 0xF8, 0xFA, 0xFC, 0xFE\r
39};\r
40\r
41\r
42/**\r
43 Gets Io port base address of Smbus Host Controller.\r
44\r
45 This internal function depends on a feature flag named PcdIchSmbusFixedIoPortBaseAddress\r
46 to retrieve Smbus Io port base. If that feature flag is true, it will get Smbus Io port base\r
47 address from a preset Pcd entry named PcdIchSmbusIoPortBaseAddress; otherwise, it will always\r
48 read Pci configuration space to get that value in each Smbus bus transaction.\r
49\r
50 @return The Io port base address of Smbus host controller.\r
51\r
52**/\r
53UINTN\r
54GetSmbusIoPortBaseAddress (\r
55 VOID\r
56 )\r
57{\r
58 UINTN IoPortBaseAddress;\r
59\r
60 if (FeaturePcdGet (PcdSmbaIoBaseAddressFixed)) {\r
61 IoPortBaseAddress = (UINTN) PcdGet16 (PcdSmbaIoBaseAddress);\r
62 } else {\r
63 IoPortBaseAddress = (UINTN) LpcPciCfg32 (R_QNC_LPC_SMBUS_BASE) & B_QNC_LPC_SMBUS_BASE_MASK;\r
64 }\r
65\r
66 //\r
67 // Make sure that the IO port base address has been properly set.\r
68 //\r
69 ASSERT (IoPortBaseAddress != 0);\r
70\r
71 return IoPortBaseAddress;\r
72}\r
73\r
74\r
75VOID\r
76InitializeInternal (\r
77 )\r
78{\r
79 UINTN IoPortBaseAddress;\r
80\r
81 IoPortBaseAddress = GetSmbusIoPortBaseAddress ();\r
82\r
83 //\r
84 // Step1: Enable QNC SMBUS I/O space.\r
85 //\r
86 LpcPciCfg32Or(R_QNC_LPC_SMBUS_BASE, B_QNC_LPC_SMBUS_BASE_EN);\r
87\r
88 //\r
89 // Step2: Clear Status Register before anyone uses the interfaces.\r
90 //\r
91 IoWrite8 (IoPortBaseAddress + R_QNC_SMBUS_HSTS, B_QNC_SMBUS_HSTS_ALL);\r
92\r
93 //\r
94 // Step3: Program the correct smbus clock\r
95 //\r
96 IoWrite8 (IoPortBaseAddress + R_QNC_SMBUS_HCLK, V_QNC_SMBUS_HCLK_100KHZ);\r
97}\r
98\r
99\r
100\r
101\r
102BOOLEAN\r
103IsAddressAvailable (\r
104 IN EFI_SMBUS_DEVICE_ADDRESS SlaveAddress\r
105 )\r
106{\r
107 UINT8 Index;\r
108\r
109 //\r
110 // See if we have already assigned this address to a device\r
111 //\r
112 for (Index = 0; Index < mDeviceMapEntries; Index++) {\r
113 if (SlaveAddress.SmbusDeviceAddress ==\r
114 mDeviceMap[Index].SmbusDeviceAddress.SmbusDeviceAddress) {\r
115 return FALSE;\r
116 }\r
117 }\r
118\r
119 //\r
120 // See if this address is claimed by a platform non-ARP-capable device\r
121 //\r
122 for (Index = 0; Index < mPlatformNumRsvd; Index++) {\r
123 if ((SlaveAddress.SmbusDeviceAddress << 1) == mPlatformAddrRsvd[Index]) {\r
124 return FALSE;\r
125 }\r
126 }\r
127\r
128 //\r
129 // See if this is a reserved address\r
130 //\r
131 for (Index = 0; Index < SMBUS_NUM_RESERVED; Index++) {\r
132 if (SlaveAddress.SmbusDeviceAddress == (UINTN) mReservedAddress[Index]) {\r
133 return FALSE;\r
134 }\r
135 }\r
136\r
137 return TRUE;\r
138}\r
139\r
140\r
141EFI_STATUS\r
142GetNextAvailableAddress (\r
143 IN EFI_SMBUS_DEVICE_ADDRESS *SlaveAddress\r
144 )\r
145{\r
146 for (SlaveAddress->SmbusDeviceAddress = 0x03;\r
147 SlaveAddress->SmbusDeviceAddress < 0x7F;\r
148 SlaveAddress->SmbusDeviceAddress++\r
149 ) {\r
150 if (IsAddressAvailable (*SlaveAddress)) {\r
151 return EFI_SUCCESS;\r
152 }\r
153 }\r
154\r
155 return EFI_OUT_OF_RESOURCES;\r
156}\r
157\r
158EFI_STATUS\r
159SmbusPrepareToArp (\r
160 )\r
161{\r
162 EFI_SMBUS_DEVICE_ADDRESS SlaveAddress;\r
163 EFI_STATUS Status;\r
164 UINTN Length;\r
165 UINT8 Buffer;\r
166\r
167 SlaveAddress.SmbusDeviceAddress = SMBUS_ADDRESS_ARP;\r
168 Length = 1;\r
169 Buffer = SMBUS_DATA_PREPARE_TO_ARP;\r
170\r
171 Status = Execute (\r
172 SlaveAddress,\r
173 0,\r
174 EfiSmbusSendByte,\r
175 TRUE,\r
176 &Length,\r
177 &Buffer\r
178 );\r
179 return Status;\r
180}\r
181\r
182EFI_STATUS\r
183SmbusGetUdidGeneral (\r
184 IN OUT EFI_SMBUS_DEVICE_MAP *DeviceMap\r
185 )\r
186{\r
187 EFI_SMBUS_DEVICE_ADDRESS SlaveAddress;\r
188 EFI_STATUS Status;\r
189 UINTN Length;\r
190 UINT8 Buffer[SMBUS_GET_UDID_LENGTH];\r
191\r
192 SlaveAddress.SmbusDeviceAddress = SMBUS_ADDRESS_ARP;\r
193 Length = SMBUS_GET_UDID_LENGTH;\r
194\r
195 Status = Execute (\r
196 SlaveAddress,\r
197 SMBUS_DATA_GET_UDID_GENERAL,\r
198 EfiSmbusReadBlock,\r
199 TRUE,\r
200 &Length,\r
201 Buffer\r
202 );\r
203\r
204 if (!EFI_ERROR(Status)) {\r
205 if (Length == SMBUS_GET_UDID_LENGTH) {\r
206 DeviceMap->SmbusDeviceUdid.DeviceCapabilities = Buffer[0];\r
207 DeviceMap->SmbusDeviceUdid.VendorRevision = Buffer[1];\r
208 DeviceMap->SmbusDeviceUdid.VendorId = (UINT16)((Buffer[2] << 8) + Buffer[3]);\r
209 DeviceMap->SmbusDeviceUdid.DeviceId = (UINT16)((Buffer[4] << 8) + Buffer[5]);\r
210 DeviceMap->SmbusDeviceUdid.Interface = (UINT16)((Buffer[6] << 8) + Buffer[7]);\r
211 DeviceMap->SmbusDeviceUdid.SubsystemVendorId = (UINT16)((Buffer[8] << 8) + Buffer[9]);\r
212 DeviceMap->SmbusDeviceUdid.SubsystemDeviceId = (UINT16)((Buffer[10] << 8) + Buffer[11]);\r
213 DeviceMap->SmbusDeviceUdid.VendorSpecificId = (UINT32)((Buffer[12] << 24) + (Buffer[13] << 16) + (Buffer[14] << 8) + Buffer[15]);\r
214 DeviceMap->SmbusDeviceAddress.SmbusDeviceAddress = (UINT8)(Buffer[16] >> 1);\r
215 } else {\r
216 Status = EFI_DEVICE_ERROR;\r
217 }\r
218 }\r
219\r
220 return Status;\r
221}\r
222\r
223EFI_STATUS\r
224SmbusAssignAddress (\r
225 IN OUT EFI_SMBUS_DEVICE_MAP *DeviceMap\r
226 )\r
227{\r
228 EFI_SMBUS_DEVICE_ADDRESS SlaveAddress;\r
229 EFI_STATUS Status;\r
230 UINTN Length;\r
231 UINT8 Buffer[SMBUS_GET_UDID_LENGTH];\r
232\r
233 Buffer[0] = DeviceMap->SmbusDeviceUdid.DeviceCapabilities;\r
234 Buffer[1] = DeviceMap->SmbusDeviceUdid.VendorRevision;\r
235 Buffer[2] = (UINT8)(DeviceMap->SmbusDeviceUdid.VendorId >> 8);\r
236 Buffer[3] = (UINT8)(DeviceMap->SmbusDeviceUdid.VendorId);\r
237 Buffer[4] = (UINT8)(DeviceMap->SmbusDeviceUdid.DeviceId >> 8);\r
238 Buffer[5] = (UINT8)(DeviceMap->SmbusDeviceUdid.DeviceId);\r
239 Buffer[6] = (UINT8)(DeviceMap->SmbusDeviceUdid.Interface >> 8);\r
240 Buffer[7] = (UINT8)(DeviceMap->SmbusDeviceUdid.Interface);\r
241 Buffer[8] = (UINT8)(DeviceMap->SmbusDeviceUdid.SubsystemVendorId >> 8);\r
242 Buffer[9] = (UINT8)(DeviceMap->SmbusDeviceUdid.SubsystemVendorId);\r
243 Buffer[10] = (UINT8)(DeviceMap->SmbusDeviceUdid.SubsystemDeviceId >> 8);\r
244 Buffer[11] = (UINT8)(DeviceMap->SmbusDeviceUdid.SubsystemDeviceId);\r
245 Buffer[12] = (UINT8)(DeviceMap->SmbusDeviceUdid.VendorSpecificId >> 24);\r
246 Buffer[13] = (UINT8)(DeviceMap->SmbusDeviceUdid.VendorSpecificId >> 16);\r
247 Buffer[14] = (UINT8)(DeviceMap->SmbusDeviceUdid.VendorSpecificId >> 8);\r
248 Buffer[15] = (UINT8)(DeviceMap->SmbusDeviceUdid.VendorSpecificId);\r
249 Buffer[16] = (UINT8)(DeviceMap->SmbusDeviceAddress.SmbusDeviceAddress << 1);\r
250\r
251 SlaveAddress.SmbusDeviceAddress = SMBUS_ADDRESS_ARP;\r
252 Length = SMBUS_GET_UDID_LENGTH;\r
253\r
254 Status = Execute (\r
255 SlaveAddress,\r
256 SMBUS_DATA_ASSIGN_ADDRESS,\r
257 EfiSmbusWriteBlock,\r
258 TRUE,\r
259 &Length,\r
260 Buffer\r
261 );\r
262 return Status;\r
263}\r
264\r
265\r
266EFI_STATUS\r
267SmbusFullArp (\r
268 )\r
269{\r
270 EFI_STATUS Status;\r
271 EFI_SMBUS_DEVICE_MAP *CurrentDeviceMap;\r
272\r
273 Status = SmbusPrepareToArp ();\r
274 if (EFI_ERROR(Status)) {\r
275 if (Status == EFI_DEVICE_ERROR) {\r
276 //\r
277 // ARP is complete\r
278 //\r
279 return EFI_SUCCESS;\r
280 } else {\r
281 return Status;\r
282 }\r
283 }\r
284\r
285 //\r
286 // Main loop to ARP all ARP-capable devices\r
287 //\r
288 do {\r
289 CurrentDeviceMap = &mDeviceMap[mDeviceMapEntries];\r
290 Status = SmbusGetUdidGeneral (CurrentDeviceMap);\r
291 if (EFI_ERROR(Status)) {\r
292 break;\r
293 }\r
294\r
295 if (CurrentDeviceMap->SmbusDeviceAddress.SmbusDeviceAddress == (0xFF >> 1)) {\r
296 //\r
297 // If address is unassigned, assign it\r
298 //\r
299 Status = GetNextAvailableAddress (\r
300 &CurrentDeviceMap->SmbusDeviceAddress\r
301 );\r
302 if (EFI_ERROR(Status)) {\r
303 return EFI_OUT_OF_RESOURCES;\r
304 }\r
305 } else if (((CurrentDeviceMap->SmbusDeviceUdid.DeviceCapabilities) & 0xC0) != 0) {\r
306 //\r
307 // if address is not fixed, check if the current address is available\r
308 //\r
309 if (!IsAddressAvailable (\r
310 CurrentDeviceMap->SmbusDeviceAddress\r
311 )) {\r
312 //\r
313 // if currently assigned address is already used, get a new one\r
314 //\r
315 Status = GetNextAvailableAddress (\r
316 &CurrentDeviceMap->SmbusDeviceAddress\r
317 );\r
318 if (EFI_ERROR(Status)) {\r
319 return EFI_OUT_OF_RESOURCES;\r
320 }\r
321 }\r
322 }\r
323\r
324 Status = SmbusAssignAddress (CurrentDeviceMap);\r
325 if (EFI_ERROR(Status)) {\r
326 //\r
327 // If there was a device error, just continue on and try again.\r
328 // Other errors should be reported.\r
329 //\r
330 if (Status != EFI_DEVICE_ERROR) {\r
331 return Status;\r
332 }\r
333 } else {\r
334 //\r
335 // If there was no error, the address was assigned and we must update our\r
336 // records.\r
337 //\r
338 mDeviceMapEntries++;\r
339 }\r
340\r
341 } while (mDeviceMapEntries < MAX_SMBUS_DEVICES);\r
342\r
343 return EFI_SUCCESS;\r
344}\r
345\r
346\r
347EFI_STATUS\r
348SmbusDirectedArp (\r
349 IN EFI_SMBUS_UDID *SmbusUdid,\r
350 IN OUT EFI_SMBUS_DEVICE_ADDRESS *SlaveAddress\r
351 )\r
352{\r
353 EFI_STATUS Status;\r
354 EFI_SMBUS_DEVICE_MAP *CurrentDeviceMap;\r
355\r
356 if (mDeviceMapEntries >= MAX_SMBUS_DEVICES) {\r
357 return EFI_OUT_OF_RESOURCES;\r
358 }\r
359\r
360 CurrentDeviceMap = &mDeviceMap[mDeviceMapEntries];\r
361\r
362 //\r
363 // Find an available address to assign\r
364 //\r
365 Status = GetNextAvailableAddress (\r
366 &CurrentDeviceMap->SmbusDeviceAddress\r
367 );\r
368 if (EFI_ERROR(Status)) {\r
369 return EFI_OUT_OF_RESOURCES;\r
370 }\r
371\r
372 CurrentDeviceMap->SmbusDeviceUdid.DeviceCapabilities = SmbusUdid->DeviceCapabilities;\r
373 CurrentDeviceMap->SmbusDeviceUdid.DeviceId = SmbusUdid->DeviceId;\r
374 CurrentDeviceMap->SmbusDeviceUdid.Interface = SmbusUdid->Interface;\r
375 CurrentDeviceMap->SmbusDeviceUdid.SubsystemDeviceId = SmbusUdid->SubsystemDeviceId;\r
376 CurrentDeviceMap->SmbusDeviceUdid.SubsystemVendorId = SmbusUdid->SubsystemVendorId;\r
377 CurrentDeviceMap->SmbusDeviceUdid.VendorId = SmbusUdid->VendorId;\r
378 CurrentDeviceMap->SmbusDeviceUdid.VendorRevision = SmbusUdid->VendorRevision;\r
379 CurrentDeviceMap->SmbusDeviceUdid.VendorSpecificId = SmbusUdid->VendorSpecificId;\r
380\r
381 Status = SmbusAssignAddress (CurrentDeviceMap);\r
382 if (EFI_ERROR(Status)) {\r
383 return Status;\r
384 }\r
385\r
386 mDeviceMapEntries++;\r
387 SlaveAddress->SmbusDeviceAddress = CurrentDeviceMap->SmbusDeviceAddress.SmbusDeviceAddress;\r
388\r
389 return EFI_SUCCESS;\r
390}\r
391\r
392\r
393\r
394/**\r
395 Executes an SMBus operation to an SMBus controller. Returns when either the command has been\r
396 executed or an error is encountered in doing the operation.\r
397\r
398 The Execute() function provides a standard way to execute an operation as defined in the System\r
399 Management Bus (SMBus) Specification. The resulting transaction will be either that the SMBus\r
400 slave devices accept this transaction or that this function returns with error.\r
401\r
402 @param This A pointer to the EFI_SMBUS_HC_PROTOCOL instance.\r
403 @param SlaveAddress The SMBus slave address of the device with which to communicate.\r
404 @param Command This command is transmitted by the SMBus host controller to the\r
405 SMBus slave device and the interpretation is SMBus slave device\r
406 specific. It can mean the offset to a list of functions inside an\r
407 SMBus slave device. Not all operations or slave devices support\r
408 this command's registers.\r
409 @param Operation Signifies which particular SMBus hardware protocol instance that\r
410 it will use to execute the SMBus transactions. This SMBus\r
411 hardware protocol is defined by the SMBus Specification and is\r
412 not related to EFI.\r
413 @param PecCheck Defines if Packet Error Code (PEC) checking is required for this\r
414 operation.\r
415 @param Length Signifies the number of bytes that this operation will do. The\r
416 maximum number of bytes can be revision specific and operation\r
417 specific. This field will contain the actual number of bytes that\r
418 are executed for this operation. Not all operations require this\r
419 argument.\r
420 @param Buffer Contains the value of data to execute to the SMBus slave device.\r
421 Not all operations require this argument. The length of this\r
422 buffer is identified by Length.\r
423\r
424 @retval EFI_SUCCESS The last data that was returned from the access matched the poll\r
425 exit criteria.\r
426 @retval EFI_CRC_ERROR Checksum is not correct (PEC is incorrect).\r
427 @retval EFI_TIMEOUT Timeout expired before the operation was completed. Timeout is\r
428 determined by the SMBus host controller device.\r
429 @retval EFI_OUT_OF_RESOURCES The request could not be completed due to a lack of resources.\r
430 @retval EFI_DEVICE_ERROR The request was not completed because a failure that was\r
431 reflected in the Host Status Register bit. Device errors are a\r
432 result of a transaction collision, illegal command field,\r
433 unclaimed cycle (host initiated), or bus errors (collisions).\r
434 @retval EFI_INVALID_PARAMETER Operation is not defined in EFI_SMBUS_OPERATION.\r
435 @retval EFI_INVALID_PARAMETER Length/Buffer is NULL for operations except for EfiSmbusQuickRead\r
436 and EfiSmbusQuickWrite. Length is outside the range of valid\r
437 values.\r
438 @retval EFI_UNSUPPORTED The SMBus operation or PEC is not supported.\r
439 @retval EFI_BUFFER_TOO_SMALL Buffer is not sufficient for this operation.\r
440\r
441**/\r
442EFI_STATUS\r
443EFIAPI\r
444SmbusExecute (\r
445 IN CONST EFI_SMBUS_HC_PROTOCOL *This,\r
446 IN CONST EFI_SMBUS_DEVICE_ADDRESS SlaveAddress,\r
447 IN CONST EFI_SMBUS_DEVICE_COMMAND Command,\r
448 IN CONST EFI_SMBUS_OPERATION Operation,\r
449 IN CONST BOOLEAN PecCheck,\r
450 IN OUT UINTN *Length,\r
451 IN OUT VOID *Buffer\r
452 )\r
453{\r
454 InitializeInternal ();\r
455 return Execute (\r
456 SlaveAddress,\r
457 Command,\r
458 Operation,\r
459 PecCheck,\r
460 Length,\r
461 Buffer\r
462 );\r
463}\r
464\r
465/**\r
466 Sets the SMBus slave device addresses for the device with a given unique ID or enumerates the\r
467 entire bus.\r
468\r
469 The ArpDevice() function provides a standard way for a device driver to enumerate the entire\r
470 SMBus or specific devices on the bus.\r
471\r
472 @param This A pointer to the EFI_SMBUS_HC_PROTOCOL instance.\r
473 @param ArpAll A Boolean expression that indicates if the host drivers need to\r
474 enumerate all the devices or enumerate only the device that is\r
475 identified by SmbusUdid. If ArpAll is TRUE, SmbusUdid and\r
476 SlaveAddress are optional. If ArpAll is FALSE, ArpDevice will\r
477 enumerate SmbusUdid and the address will be at SlaveAddress.\r
478 @param SmbusUdid The Unique Device Identifier (UDID) that is associated with this\r
479 device.\r
480 @param SlaveAddress The SMBus slave address that is associated with an SMBus UDID.\r
481\r
482 @retval EFI_SUCCESS The last data that was returned from the access matched the poll\r
483 exit criteria.\r
484 @retval EFI_CRC_ERROR Checksum is not correct (PEC is incorrect).\r
485 @retval EFI_TIMEOUT Timeout expired before the operation was completed. Timeout is\r
486 determined by the SMBus host controller device.\r
487 @retval EFI_OUT_OF_RESOURCES The request could not be completed due to a lack of resources.\r
488 @retval EFI_DEVICE_ERROR The request was not completed because a failure that was\r
489 reflected in the Host Status Register bit. Device errors are a\r
490 result of a transaction collision, illegal command field,\r
491 unclaimed cycle (host initiated), or bus errors (collisions).\r
492 @retval EFI_UNSUPPORTED The corresponding SMBus operation is not supported.\r
493\r
494**/\r
495EFI_STATUS\r
496EFIAPI\r
497SmbusArpDevice (\r
498 IN CONST EFI_SMBUS_HC_PROTOCOL *This,\r
499 IN BOOLEAN ArpAll,\r
500 IN EFI_SMBUS_UDID *SmbusUdid, OPTIONAL\r
501 IN OUT EFI_SMBUS_DEVICE_ADDRESS *SlaveAddress OPTIONAL\r
502 )\r
503{\r
504 InitializeInternal ();\r
505\r
506 if (ArpAll) {\r
507 return SmbusFullArp ();\r
508 } else {\r
509 if ((SmbusUdid == NULL) || (SlaveAddress == NULL)) {\r
510 return EFI_INVALID_PARAMETER;\r
511 }\r
512 return SmbusDirectedArp ((EFI_SMBUS_UDID *)SmbusUdid, SlaveAddress);\r
513 }\r
514}\r
515\r
516/**\r
517 Returns a pointer to the Address Resolution Protocol (ARP) map that contains the ID/address pair\r
518 of the slave devices that were enumerated by the SMBus host controller driver.\r
519\r
520 The GetArpMap() function returns the mapping of all the SMBus devices that were enumerated by the\r
521 SMBus host driver.\r
522\r
523 @param This A pointer to the EFI_SMBUS_HC_PROTOCOL instance.\r
524 @param Length Size of the buffer that contains the SMBus device map.\r
525 @param SmbusDeviceMap The pointer to the device map as enumerated by the SMBus\r
526 controller driver.\r
527\r
528 @retval EFI_SUCCESS The SMBus returned the current device map.\r
529 @retval EFI_UNSUPPORTED The corresponding operation is not supported.\r
530\r
531**/\r
532EFI_STATUS\r
533EFIAPI\r
534SmbusGetArpMap (\r
535 IN CONST EFI_SMBUS_HC_PROTOCOL *This,\r
536 IN OUT UINTN *Length,\r
537 IN OUT EFI_SMBUS_DEVICE_MAP **SmbusDeviceMap\r
538 )\r
539{\r
540 *Length = mDeviceMapEntries;\r
541 *SmbusDeviceMap = mDeviceMap;\r
542 return EFI_SUCCESS;\r
543}\r
544\r
545\r
546/**\r
547 Allows a device driver to register for a callback when the bus driver detects a state that it\r
548 needs to propagate to other drivers that are registered for a callback.\r
549\r
550 The Notify() function registers all the callback functions to allow the bus driver to call these\r
551 functions when the SlaveAddress/Data pair happens.\r
552 If NotifyFunction is NULL, then ASSERT ().\r
553\r
554 @param This A pointer to the EFI_SMBUS_HC_PROTOCOL instance.\r
555 @param SlaveAddress The SMBUS hardware address to which the SMBUS device is\r
556 preassigned or allocated.\r
557 @param Data Data of the SMBus host notify command that the caller wants to be\r
558 called.\r
559 @param NotifyFunction The function to call when the bus driver detects the SlaveAddress\r
560 and Data pair.\r
561\r
562 @retval EFI_SUCCESS NotifyFunction was registered.\r
563 @retval EFI_UNSUPPORTED The corresponding operation is not supported.\r
564\r
565**/\r
566EFI_STATUS\r
567EFIAPI\r
568SmbusNotify (\r
569 IN CONST EFI_SMBUS_HC_PROTOCOL *This,\r
570 IN CONST EFI_SMBUS_DEVICE_ADDRESS SlaveAddress,\r
571 IN CONST UINTN Data,\r
572 IN CONST EFI_SMBUS_NOTIFY_FUNCTION NotifyFunction\r
573 )\r
574{\r
575 return EFI_UNSUPPORTED;\r
576}\r
577\r
578/**\r
579 Entry point to the DXE Driver that produces the SMBus Host Controller Protocol.\r
580\r
581 @param ImageHandle ImageHandle of the loaded driver.\r
582 @param SystemTable Pointer to the EFI System Table.\r
583\r
584 @retval EFI_SUCCESS The entry point of SMBus DXE driver is executed successfully.\r
585 @retval !EFI_SUCESS Some error occurs in the entry point of SMBus DXE driver.\r
586\r
587**/\r
588EFI_STATUS\r
589EFIAPI\r
590InitializeQNCSmbus (\r
591 IN EFI_HANDLE ImageHandle,\r
592 IN EFI_SYSTEM_TABLE *SystemTable\r
593 )\r
594{\r
595 EFI_STATUS Status;\r
596\r
597 mPlatformNumRsvd = (UINT8)PcdGet32 (PcdPlatformSmbusAddrNum);\r
598 mPlatformAddrRsvd = (UINT8 *)(UINTN) PcdGet64 (PcdPlatformSmbusAddrTable);\r
599\r
600 //\r
601 // Install SMBus Host Controller protocol interface.\r
602 //\r
603 Status = gBS->InstallMultipleProtocolInterfaces (\r
604 &mSmbusHcHandle,\r
605 &gEfiSmbusHcProtocolGuid,\r
606 &mSmbusHc,\r
607 NULL\r
608 );\r
609 ASSERT_EFI_ERROR (Status);\r
610\r
611 return Status;\r
612}\r