TianoCore EDK2 master
Loading...
Searching...
No Matches
Statistics.c
Go to the documentation of this file.
1
9#include "Snp.h"
10
59EFIAPI
62 IN BOOLEAN Reset,
63 IN OUT UINTN *StatisticsSize OPTIONAL,
64 IN OUT EFI_NETWORK_STATISTICS *StatisticsTable OPTIONAL
65 )
66{
67 SNP_DRIVER *Snp;
69 UINT64 *Stp;
70 UINT64 Mask;
71 UINTN Size;
72 UINTN Index;
73 EFI_TPL OldTpl;
74 EFI_STATUS Status;
75
76 //
77 // Get pointer to SNP driver instance for *This.
78 //
79 if (This == NULL) {
80 return EFI_INVALID_PARAMETER;
81 }
82
83 Snp = EFI_SIMPLE_NETWORK_DEV_FROM_THIS (This);
84
85 OldTpl = gBS->RaiseTPL (TPL_CALLBACK);
86
87 //
88 // Return error if the SNP is not initialized.
89 //
90 switch (Snp->Mode.State) {
91 case EfiSimpleNetworkInitialized:
92 break;
93
94 case EfiSimpleNetworkStopped:
95 Status = EFI_NOT_STARTED;
96 goto ON_EXIT;
97
98 default:
99 Status = EFI_DEVICE_ERROR;
100 goto ON_EXIT;
101 }
102
103 //
104 // if we are not resetting the counters, we have to have a valid stat table
105 // with >0 size. if no reset, no table and no size, return success.
106 //
107 if (!Reset && (StatisticsSize == NULL)) {
108 Status = (StatisticsTable != NULL) ? EFI_INVALID_PARAMETER : EFI_SUCCESS;
109 goto ON_EXIT;
110 }
111
112 //
113 // Initialize UNDI Statistics CDB
114 //
115 Snp->Cdb.OpCode = PXE_OPCODE_STATISTICS;
116 Snp->Cdb.CPBsize = PXE_CPBSIZE_NOT_USED;
117 Snp->Cdb.CPBaddr = PXE_CPBADDR_NOT_USED;
118 Snp->Cdb.StatCode = PXE_STATCODE_INITIALIZE;
119 Snp->Cdb.StatFlags = PXE_STATFLAGS_INITIALIZE;
120 Snp->Cdb.IFnum = Snp->IfNum;
121 Snp->Cdb.Control = PXE_CONTROL_LAST_CDB_IN_LIST;
122
123 if (Reset) {
124 Snp->Cdb.OpFlags = PXE_OPFLAGS_STATISTICS_RESET;
125 Snp->Cdb.DBsize = PXE_DBSIZE_NOT_USED;
126 Snp->Cdb.DBaddr = PXE_DBADDR_NOT_USED;
127 Db = Snp->Db;
128 } else {
129 Snp->Cdb.OpFlags = PXE_OPFLAGS_STATISTICS_READ;
130 Snp->Cdb.DBsize = (UINT16)sizeof (PXE_DB_STATISTICS);
131 Snp->Cdb.DBaddr = (UINT64)(UINTN)(Db = Snp->Db);
132 }
133
134 //
135 // Issue UNDI command and check result.
136 //
137 DEBUG ((DEBUG_NET, "\nsnp->undi.statistics() "));
138
139 (*Snp->IssueUndi32Command)((UINT64)(UINTN)&Snp->Cdb);
140
141 switch (Snp->Cdb.StatCode) {
143 break;
144
145 case PXE_STATCODE_UNSUPPORTED:
146 DEBUG (
147 (DEBUG_ERROR,
148 "\nsnp->undi.statistics() %xh:%xh\n",
149 Snp->Cdb.StatFlags,
150 Snp->Cdb.StatCode)
151 );
152
153 Status = EFI_UNSUPPORTED;
154 goto ON_EXIT;
155
156 default:
157 DEBUG (
158 (DEBUG_ERROR,
159 "\nsnp->undi.statistics() %xh:%xh\n",
160 Snp->Cdb.StatFlags,
161 Snp->Cdb.StatCode)
162 );
163
164 Status = EFI_DEVICE_ERROR;
165 goto ON_EXIT;
166 }
167
168 if (Reset) {
169 Status = EFI_SUCCESS;
170 goto ON_EXIT;
171 }
172
173 if (StatisticsTable == NULL) {
174 *StatisticsSize = sizeof (EFI_NETWORK_STATISTICS);
175 Status = EFI_BUFFER_TOO_SMALL;
176 goto ON_EXIT;
177 }
178
179 //
180 // Convert the UNDI statistics information to SNP statistics
181 // information.
182 //
183 ZeroMem (StatisticsTable, *StatisticsSize);
184 Stp = (UINT64 *)StatisticsTable;
185 Size = 0;
186
187 for (Index = 0, Mask = 1; Index < 64; Index++, Mask = LShiftU64 (Mask, 1), Stp++) {
188 //
189 // There must be room for a full UINT64. Partial
190 // numbers will not be stored.
191 //
192 if ((Index + 1) * sizeof (UINT64) > *StatisticsSize) {
193 break;
194 }
195
196 if ((Db->Supported & Mask) != 0) {
197 *Stp = Db->Data[Index];
198 Size = Index + 1;
199 } else {
200 SetMem (Stp, sizeof (UINT64), 0xFF);
201 }
202 }
203
204 //
205 // Compute size up to last supported statistic.
206 //
207 while (++Index < 64) {
208 if ((Db->Supported & (Mask = LShiftU64 (Mask, 1))) != 0) {
209 Size = Index;
210 }
211 }
212
213 Size *= sizeof (UINT64);
214
215 if (*StatisticsSize >= Size) {
216 *StatisticsSize = Size;
217 Status = EFI_SUCCESS;
218 } else {
219 *StatisticsSize = Size;
220 Status = EFI_BUFFER_TOO_SMALL;
221 }
222
223ON_EXIT:
224 gBS->RestoreTPL (OldTpl);
225
226 return Status;
227}
UINT64 UINTN
UINT64 EFIAPI LShiftU64(IN UINT64 Operand, IN UINTN Count)
Definition: LShiftU64.c:28
VOID *EFIAPI SetMem(OUT VOID *Buffer, IN UINTN Length, IN UINT8 Value)
Definition: SetMemWrapper.c:38
VOID *EFIAPI ZeroMem(OUT VOID *Buffer, IN UINTN Length)
#define NULL
Definition: Base.h:319
#define IN
Definition: Base.h:279
#define OUT
Definition: Base.h:284
#define DEBUG(Expression)
Definition: DebugLib.h:434
EFI_STATUS EFIAPI SnpUndi32Statistics(IN EFI_SIMPLE_NETWORK_PROTOCOL *This, IN BOOLEAN Reset, IN OUT UINTN *StatisticsSize OPTIONAL, IN OUT EFI_NETWORK_STATISTICS *StatisticsTable OPTIONAL)
Definition: Statistics.c:60
RETURN_STATUS EFI_STATUS
Definition: UefiBaseType.h:29
UINTN EFI_TPL
Definition: UefiBaseType.h:41
#define EFI_SUCCESS
Definition: UefiBaseType.h:112
EFI_BOOT_SERVICES * gBS
#define PXE_CPBSIZE_NOT_USED
zero
Definition: UefiPxe.h:57
#define PXE_OPCODE_STATISTICS
Definition: UefiPxe.h:140
#define PXE_DBSIZE_NOT_USED
zero
Definition: UefiPxe.h:58
#define PXE_CPBADDR_NOT_USED
zero
Definition: UefiPxe.h:59
#define PXE_DBADDR_NOT_USED
zero
Definition: UefiPxe.h:60
#define PXE_OPFLAGS_STATISTICS_READ
Definition: UefiPxe.h:320
#define PXE_STATCODE_SUCCESS
Definition: UefiPxe.h:602
Definition: Snp.h:55
PXE_UINT64 Supported
Definition: UefiPxe.h:1366
PXE_UINT64 Data[64]
Definition: UefiPxe.h:1371