00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00014 
00015 
00016 
00017 
00018 
00019 
00020 
00021 
00022 
00023 
00024 
#include    "cmp.h"
00025 
00026 
#ifdef ALLOC_PRAGMA
00027 
#pragma alloc_text(PAGE,HvCheckHive)
00028 
#pragma alloc_text(PAGE,HvCheckBin)
00029 
#endif
00030 
00031 
00032 
00033 
00034 
extern struct {
00035     PHHIVE      Hive;
00036     ULONG       
Status;
00037     ULONG       
Space;
00038     HCELL_INDEX MapPoint;
00039     PHBIN       BinPoint;
00040 } 
HvCheckHiveDebug;
00041 
00042 
extern struct {
00043     PHBIN       Bin;
00044     ULONG       
Status;
00045     PHCELL      CellPoint;
00046 } 
HvCheckBinDebug;
00047 
00048 
00049 
#if DBG
00050 
ULONG HvHiveChecking=0;
00051 
#endif
00052 
00053 ULONG
00054 HvCheckHive(
00055     
PHHIVE  Hive,
00056     PULONG  Storage OPTIONAL
00057     )
00058 
00059 
00060 
00061 
00062 
00063 
00064 
00065 
00066 
00067 
00068 
00069 
00070 
00071 
00072 
00073 
00074 
00075 
00076 
00077 
00078 
00079 
00080 {
00081     
HCELL_INDEX p;
00082     ULONG       Length;
00083     ULONG       localstorage = 0;
00084     
PHMAP_ENTRY t;
00085     
PHBIN       Bin;
00086     ULONG   i;
00087     ULONG   rc;
00088     
PFREE_HBIN  FreeBin;
00089 
00090     
HvCheckHiveDebug.Hive = 
Hive;
00091     
HvCheckHiveDebug.Status = 0;
00092     
HvCheckHiveDebug.Space = (ULONG)-1;
00093     
HvCheckHiveDebug.MapPoint = 
HCELL_NIL;
00094     
HvCheckHiveDebug.BinPoint = 0;
00095 
00096     p = 0;
00097 
00098 
00099     
00100     
00101     
00102     
for (i = 0; i <= 
Volatile; i++) {
00103         Length = 
Hive->Storage[i].Length;
00104 
00105         
00106         
00107         
00108         
while (p < Length) {
00109             
t = 
HvpGetCellMap(
Hive, p);
00110             
if (
t == 
NULL) {
00111                 KdPrint((
"HvCheckHive:"));
00112                 KdPrint((
"\tBin@:%08lx invalid\n", 
Bin));
00113                 
HvCheckHiveDebug.Status = 2005;
00114                 
HvCheckHiveDebug.Space = i;
00115                 
HvCheckHiveDebug.MapPoint = p;
00116                 
return 2005;
00117             }
00118 
00119 
00120             
if ((
t->BinAddress & 
HMAP_DISCARDABLE) == 0) {
00121 
00122                 
Bin = (
PHBIN)((
t->BinAddress) & 
HMAP_BASE);
00123 
00124                 
00125                 
00126                 
00127                 
if ( (
Bin->
Size > Length)                           ||
00128                      (
Bin->
Signature != 
HBIN_SIGNATURE)             ||
00129                      (
Bin->
FileOffset != p)
00130                    )
00131                 {
00132                     KdPrint((
"HvCheckHive:"));
00133                     KdPrint((
"\tBin@:%08lx invalid\n", 
Bin));
00134                     
HvCheckHiveDebug.Status = 2010;
00135                     
HvCheckHiveDebug.Space = i;
00136                     
HvCheckHiveDebug.MapPoint = p;
00137                     
HvCheckHiveDebug.BinPoint = 
Bin;
00138                     
return 2010;
00139                 }
00140 
00141                 
00142                 
00143                 
00144                 rc = 
HvCheckBin(
Hive, 
Bin, &localstorage);
00145                 
if (rc != 0) {
00146                     
HvCheckHiveDebug.Status = rc;
00147                     
HvCheckHiveDebug.Space = i;
00148                     
HvCheckHiveDebug.MapPoint = p;
00149                     
HvCheckHiveDebug.BinPoint = 
Bin;
00150                     
return rc;
00151                 }
00152 
00153                 p = (ULONG)p + 
Bin->
Size;
00154 
00155             } 
else {
00156                 
00157                 
00158                 
00159                 FreeBin = (
PFREE_HBIN)
t->BlockAddress;
00160                 p+=FreeBin->
Size;
00161             }
00162         }
00163 
00164         p = 0x80000000;     
00165     }
00166 
00167     
if (ARGUMENT_PRESENT(Storage)) {
00168         *Storage = localstorage;
00169     }
00170     
return 0;
00171 }
00172 
00173 
00174 ULONG
00175 HvCheckBin(
00176     
PHHIVE  Hive,
00177     
PHBIN   Bin,
00178     PULONG  Storage
00179     )
00180 
00181 
00182 
00183 
00184 
00185 
00186 
00187 
00188 
00189 
00190 
00191 
00192 
00193 
00194 
00195 
00196 
00197 
00198 
00199 
00200 
00201 
00202 {
00203     
PHCELL  p;
00204     
PHCELL  np;
00205     
PHCELL  lp;
00206     ULONG   freespace = 0
L;
00207     ULONG   allocated = 0
L;
00208     ULONG   userallocated = 0
L;
00209 
00210     
HvCheckBinDebug.Bin = 
Bin;
00211     
HvCheckBinDebug.Status = 0;
00212     
HvCheckBinDebug.CellPoint = 0;
00213 
00214     
00215     
00216     
00217     
00218     p = (
PHCELL)((PUCHAR)
Bin + 
sizeof(
HBIN));
00219     lp = p;
00220 
00221     
00222     
00223     
00224     
00225     
00226     
00227     
00228     
00229     
00230     
00231     
00232     
00233     
00234     
00235     
00236     
00237     
00238     
00239     
00240     
00241     
00242     
00243     
00244     
00245 
00246     
while (p < (
PHCELL)((PUCHAR)
Bin + 
Bin->
Size)) {
00247 
00248         
00249         
00250         
00251         
if (
USE_OLD_CELL(
Hive)) {
00252             
if (lp == p) {
00253                 
if (p->u.OldCell.Last != 
HBIN_NIL) {
00254                     KdPrint((
"HvCheckBin 20: First cell has wrong last pointer\n"));
00255                     KdPrint((
"Bin = %08lx\n", 
Bin));
00256                     
HvCheckBinDebug.Status = 20;
00257                     
HvCheckBinDebug.CellPoint = p;
00258                     
return 20;
00259                 }
00260             } 
else {
00261                 
if ((
PHCELL)(p->u.OldCell.Last + (PUCHAR)
Bin) != lp) {
00262                     KdPrint((
"HvCheckBin 30: incorrect last pointer\n"));
00263                     KdPrint((
"Bin = %08lx\n", 
Bin));
00264                     KdPrint((
"p = %08lx\n", (ULONG_PTR)p));
00265                     
HvCheckBinDebug.Status = 30;
00266                     
HvCheckBinDebug.CellPoint = p;
00267                     
return 30;
00268                 }
00269             }
00270         }
00271 
00272         
00273         
00274         
00275         
00276         
if (p->Size < 0) {
00277 
00278             
00279             
00280             
00281 
00282             
00283             
00284             
00285             
if ( ((ULONG)(p->Size * -1) > 
Bin->
Size)        ||
00286                  ( (
PHCELL)((p->Size * -1) + (PUCHAR)p) >
00287                    (
PHCELL)((PUCHAR)
Bin + 
Bin->
Size) )
00288                )
00289             {
00290                 KdPrint((
"HvCheckBin 40: impossible allocation\n"));
00291                 KdPrint((
"Bin = %08lx\n", 
Bin));
00292                 
HvCheckBinDebug.Status = 40;
00293                 
HvCheckBinDebug.CellPoint = p;
00294                 
return 40;
00295             }
00296 
00297             allocated += (p->Size * -1);
00298             
if (
USE_OLD_CELL(
Hive)) {
00299                 userallocated += (p->Size * -1) - FIELD_OFFSET(
HCELL, u.OldCell.u.UserData);
00300             } 
else {
00301                 userallocated += (p->Size * -1) - FIELD_OFFSET(
HCELL, u.NewCell.u.UserData);
00302             }
00303 
00304             
00305             
00306             
00307             
00308             
if (allocated > 
Bin->
Size) {
00309                 KdPrint((
"HvCheckBin 50: allocated exceeds available\n"));
00310                 KdPrint((
"Bin = %08lx\n", 
Bin));
00311                 
HvCheckBinDebug.Status = 50;
00312                 
HvCheckBinDebug.CellPoint = p;
00313                 
return 50;
00314             }
00315 
00316             np = (
PHCELL)((PUCHAR)p + (p->Size * -1));
00317 
00318 
00319 
00320         } 
else {
00321 
00322             
00323             
00324             
00325 
00326             
00327             
00328             
00329             
if ( ((ULONG)p->Size > 
Bin->
Size)               ||
00330                  ( (
PHCELL)(p->Size + (PUCHAR)p) >
00331                    (
PHCELL)((PUCHAR)
Bin + 
Bin->
Size) ) ||
00332                  (p->Size == 0) )
00333             {
00334                 KdPrint((
"HvCheckBin 60: impossible free block\n"));
00335                 KdPrint((
"Bin = %08lx\n", 
Bin));
00336                 
HvCheckBinDebug.Status = 60;
00337                 
HvCheckBinDebug.CellPoint = p;
00338                 
return 60;
00339             }
00340 
00341             freespace = freespace + p->Size;
00342 
00343             
00344             
00345             
00346             
00347             
if (freespace > 
Bin->
Size) {
00348                 KdPrint((
"HvCheckBin 70: free exceeds available\n"));
00349                 KdPrint((
"Bin = %08lx\n", 
Bin));
00350                 
HvCheckBinDebug.Status = 70;
00351                 
HvCheckBinDebug.CellPoint = p;
00352                 
return 70;
00353             }
00354 
00355             np = (
PHCELL)((PUCHAR)p + p->Size);
00356 
00357         }
00358 
00359         lp = p;
00360         p = np;
00361     }
00362 
00363     
00364     
00365     
00366     
00367     
if ((freespace + allocated + 
sizeof(
HBIN)) != 
Bin->
Size) {
00368         KdPrint((
"HvCheckBin 995: sizes do not add up\n"));
00369         KdPrint((
"Bin = %08lx\n", 
Bin));
00370         KdPrint((
"freespace = %08lx  ", freespace));
00371         KdPrint((
"allocated = %08lx  ", allocated));
00372         KdPrint((
"size = %08lx\n", 
Bin->
Size));
00373         
HvCheckBinDebug.Status = 995;
00374         
return 995;
00375     }
00376 
00377     
00378     
00379     
00380     
00381     
if (p != (
PHCELL)((PUCHAR)
Bin + 
Bin->
Size)) {
00382         KdPrint((
"HvCheckBin 1000: last cell points off the end\n"));
00383         KdPrint((
"Bin = %08lx\n", 
Bin));
00384         
HvCheckBinDebug.Status = 1000;
00385         
return 1000;
00386     }
00387 
00388     
if (ARGUMENT_PRESENT(Storage)) {
00389         *Storage += userallocated;
00390     }
00391     
return 0;
00392 }