ReactOS  0.4.13-dev-982-g9853eab
dirtree.cpp
Go to the documentation of this file.
1 // Copyright (C) Alexander Telyatnikov, Ivan Keliukh, Yegor Anchishkin, SKIF Software, 1999-2013. Kiev, Ukraine
3 // All rights reserved
4 // This file was released under the GPLv2 on June 2015.
6 /*
7  Module name:
8 
9  udf_info.cpp
10 
11  Abstract:
12 
13  This file contains filesystem-specific routines
14  for Directory tree & related structures support
15 
16 */
17 
18 #include "udf.h"
19 
20 #ifdef UDF_CHECK_UTIL
21  #include "..\namesup.h"
22 #else
23  #ifdef UDF_BUG_CHECK_ID
24  #undef UDF_BUG_CHECK_ID
25  #endif //UDF_BUG_CHECK_ID
26 #endif //UDF_CHECK_UTIL
27 
28 #define UDF_BUG_CHECK_ID UDF_FILE_UDF_INFO_DIR
29 
30 #define MEM_USDIRHASH_TAG "USDirHash"
31 
32 #define UDF_DUMP_DIRTREE
33 #ifdef UDF_DUMP_DIRTREE
34 #define DirPrint(x) UDFPrint(x)
35 #else
36 #define DirPrint(x) {;}
37 #endif
38 
39 /*
40  This routine initializes DirIndex array
41  */
44  IN uint_di i
45  )
46 {
47  uint_di j,k;
48  PDIR_INDEX_HDR hDirNdx;
49  PDIR_INDEX_ITEM* FrameList;
50 
51  if(!i)
52  return NULL;
53 #ifdef UDF_LIMIT_DIR_SIZE
55  return NULL;
56 #endif //UDF_LIMIT_DIR_SIZE
57 
59  i &= (UDF_DIR_INDEX_FRAME-1);
60 
62  if(!hDirNdx) return NULL;
63  RtlZeroMemory(hDirNdx, sizeof(DIR_INDEX_HDR));
64 
65  FrameList = (PDIR_INDEX_ITEM*)(hDirNdx+1);
66  for(k=0; k<j; k++, FrameList++) {
68  if(!(*FrameList)) {
69 free_hdi:
70  // item pointet by FrameList is NULL, it could not be allocated
71  while(k) {
72  k--;
73  FrameList--;
74  MyFreePool__(*FrameList);
75  }
76  MyFreePool__(hDirNdx);
77  return NULL;
78  }
79  RtlZeroMemory((*FrameList), UDF_DIR_INDEX_FRAME*sizeof(DIR_INDEX_ITEM));
80  }
81  if(i) {
83  if(!(*FrameList))
84  goto free_hdi;
85  RtlZeroMemory((*FrameList), i*sizeof(DIR_INDEX_ITEM));
86  }
87 
88  hDirNdx->FrameCount = j+(i!=0);
89  hDirNdx->LastFrameCount = i ? i : UDF_DIR_INDEX_FRAME;
90 
91  return hDirNdx;
92 } // UDFDirIndexAlloc()
93 
94 /*
95  This routine releases DirIndex array
96  */
97 void
99  PDIR_INDEX_HDR hDirNdx
100  )
101 {
102  uint32 k;
103  PDIR_INDEX_ITEM* FrameList;
104 
105  FrameList = (PDIR_INDEX_ITEM*)(hDirNdx+1);
106  if(!hDirNdx) return;
107  for(k=0; k<hDirNdx->FrameCount; k++, FrameList++) {
108  if(*FrameList) MyFreePool__(*FrameList);
109  }
110  MyFreePool__(hDirNdx);
111 } // UDFDirIndexFree();
112 
113 /*
114  This routine grows DirIndex array
115  */
116 OSSTATUS
118  IN PDIR_INDEX_HDR* _hDirNdx,
119  IN uint_di d // increment
120  )
121 {
122  uint_di j,k;
123  PDIR_INDEX_HDR hDirNdx = *_hDirNdx;
124  PDIR_INDEX_ITEM* FrameList;
125 
126  if(d > UDF_DIR_INDEX_FRAME)
128 
129  j = hDirNdx->LastFrameCount+d;
130 
131  if(j > UDF_DIR_INDEX_FRAME) {
132 #ifndef UDF_LIMIT_DIR_SIZE // release
133  // Grow header
134  k = hDirNdx->FrameCount;
135  if(!MyReallocPool__((int8*)hDirNdx, sizeof(DIR_INDEX_HDR) + k*sizeof(PDIR_INDEX_ITEM),
136  (int8**)(&hDirNdx), sizeof(DIR_INDEX_HDR) + (k+1)*sizeof(PDIR_INDEX_ITEM) ) )
138  FrameList = (PDIR_INDEX_ITEM*)(hDirNdx+1);
139  // Grow last frame
140  if(!MyReallocPool__((int8*)(FrameList[k-1]), AlignDirIndex(hDirNdx->LastFrameCount)*sizeof(DIR_INDEX_ITEM),
141  (int8**)(&(FrameList[k-1])), UDF_DIR_INDEX_FRAME*sizeof(DIR_INDEX_ITEM) ) )
143  RtlZeroMemory(&(FrameList[k-1][hDirNdx->LastFrameCount]),
144  (UDF_DIR_INDEX_FRAME-hDirNdx->LastFrameCount)*sizeof(DIR_INDEX_ITEM));
145  hDirNdx->LastFrameCount = UDF_DIR_INDEX_FRAME;
146  // Allocate new frame
148  if(!FrameList[k])
150  hDirNdx->FrameCount++;
151  RtlZeroMemory(FrameList[k], (j-UDF_DIR_INDEX_FRAME)*sizeof(DIR_INDEX_ITEM));
152  hDirNdx->LastFrameCount = j-UDF_DIR_INDEX_FRAME;
153  (*_hDirNdx) = hDirNdx;
154 #else // UDF_LIMIT_DIR_SIZE
156 #endif // UDF_LIMIT_DIR_SIZE
157  } else {
158  k = hDirNdx->FrameCount;
159  FrameList = (PDIR_INDEX_ITEM*)(hDirNdx+1);
160  if(!MyReallocPool__((int8*)(FrameList[k-1]), AlignDirIndex(hDirNdx->LastFrameCount)*sizeof(DIR_INDEX_ITEM),
161  (int8**)(&(FrameList[k-1])), AlignDirIndex(j)*sizeof(DIR_INDEX_ITEM) ) )
163  RtlZeroMemory(&(FrameList[k-1][hDirNdx->LastFrameCount]),
164  (j-hDirNdx->LastFrameCount)*sizeof(DIR_INDEX_ITEM));
165  hDirNdx->LastFrameCount = j;
166  }
167  return STATUS_SUCCESS;
168 } // end UDFDirIndexGrow()
169 
170 /*
171  Thisd routine truncates DirIndex array
172  */
173 OSSTATUS
175  IN PDIR_INDEX_HDR* _hDirNdx,
176  IN uint_di d // decrement
177  )
178 {
179  uint_di j,k;
180 
181  if(d > UDF_DIR_INDEX_FRAME) {
183  while(d) {
185  if(!OS_SUCCESS(status = UDFDirIndexTrunc(_hDirNdx, k))) {
186  return status;
187  }
188  d -= k;
189  }
190  return STATUS_SUCCESS;
191  }
192 
193  PDIR_INDEX_HDR hDirNdx = *_hDirNdx;
194  PDIR_INDEX_ITEM* FrameList;
195 
197  FrameList = (PDIR_INDEX_ITEM*)(hDirNdx+1);
198  k = hDirNdx->FrameCount-1;
199 
200  if(j <= UDF_DIR_INDEX_FRAME) {
201  // free last frame
202  if(!k && (j < 2)) {
203  // someone tries to trunc. residual entries...
205  }
206  MyFreePool__(FrameList[k]);
207  FrameList[k] = NULL;
209  hDirNdx->FrameCount--;
210  // Truncate new last frame
211  if(!MyReallocPool__((int8*)(FrameList[k-1]), UDF_DIR_INDEX_FRAME*sizeof(DIR_INDEX_ITEM),
212  (int8**)(&(FrameList[k-1])), AlignDirIndex(j)*sizeof(DIR_INDEX_ITEM) ) )
214  hDirNdx->LastFrameCount = j;
215  // Truncate header
216  if(!MyReallocPool__((int8*)hDirNdx, sizeof(DIR_INDEX_HDR) + (k+1)*sizeof(PDIR_INDEX_ITEM),
217  (int8**)(&hDirNdx), sizeof(DIR_INDEX_HDR) + k*sizeof(PDIR_INDEX_ITEM) ) )
219 
220  (*_hDirNdx) = hDirNdx;
221 
222  } else {
223 
225  if(!k && (j < 2)) {
226  // someone tries to trunc. residual entries...
228  }
229 
230  if(!MyReallocPool__((int8*)(FrameList[k]), AlignDirIndex(hDirNdx->LastFrameCount)*sizeof(DIR_INDEX_ITEM),
231  (int8**)(&(FrameList[k])), AlignDirIndex(j)*sizeof(DIR_INDEX_ITEM) ) )
233  hDirNdx->LastFrameCount = j;
234  }
235  return STATUS_SUCCESS;
236 } // end UDFDirIndexTrunc()
237 
238 #if defined _X86_ && !defined UDF_LIMIT_DIR_SIZE
239 #ifdef _MSC_VER
240 #pragma warning(disable:4035) // re-enable below
241 #endif
242 /*
243  This routine returns pointer to DirIndex item with index i.
244  */
245 #if defined(_MSC_VER) && !defined(__clang__)
246 __declspec (naked)
247 #endif
251  IN PDIR_INDEX_HDR hDirNdx, // ECX
252  IN uint32 i // EDX
253  )
254 {
255 #if defined(_MSC_VER) && !defined(__clang__)
256  __asm {
257  push ebx
258  push ecx
259  push edx
260 
261 // mov ebx,hDirNdx
262  mov ebx,ecx
263  mov ecx,edx
264  or ebx,ebx
265  jz EO_udi_err
266 
267  mov eax,ecx
268  shr ecx,UDF_DIR_INDEX_FRAME_SH ; ecx = j
269  mov edx,[ebx]hDirNdx.FrameCount ; edx = k
270  cmp ecx,edx
271  jae EO_udi_err
272 
273  and eax,(1 shl UDF_DIR_INDEX_FRAME_SH)-1 ; eax = i
274  dec edx
275  cmp ecx,edx
276  jb No_check
277 
278  cmp eax,[ebx].LastFrameCount
279  jae EO_udi_err
280 No_check:
281  add ebx,size DIR_INDEX_HDR ; ((PDIR_INDEX_ITEM*)(hDirNdx+1))...
282  mov ebx,[ebx+ecx*4] ; ...[j]...
284  mul edx ; ...[i]...
285  add eax,ebx ; &(...)
286  jmp udi_OK
287 EO_udi_err:
288  xor eax,eax
289 udi_OK:
290  pop edx
291  pop ecx
292  pop ebx
293 
294  ret
295  }
296 #else
297  /* FIXME ReactOS */
298  uint_di j, k;
299  if( hDirNdx &&
300  ((j = (i >> UDF_DIR_INDEX_FRAME_SH)) < (k = hDirNdx->FrameCount) ) &&
301  ((i = (i & (UDF_DIR_INDEX_FRAME-1))) < ((j < (k-1)) ? UDF_DIR_INDEX_FRAME : hDirNdx->LastFrameCount)) )
302  return &( (((PDIR_INDEX_ITEM*)(hDirNdx+1))[j])[i] );
303  return NULL;
304 #endif
305 }
306 #ifdef _MSC_VER
307 #pragma warning(default:4035)
308 #endif
309 #endif // _X86_
310 
311 /*
312  This routine returns pointer to DirIndex'es frame & index inside it
313  according to start Index parameter. It also initializes scan parameters
314  */
317  IN PDIR_INDEX_HDR hDirNdx,
318  IN uint32 Frame,
319  OUT uint32* FrameLen,
320  OUT uint_di* Index,
321  IN uint_di Rel
322  )
323 {
324  if(Frame >= hDirNdx->FrameCount)
325  return NULL;
326  if(Index) {
327 #ifdef UDF_LIMIT_DIR_SIZE
328  (*Index) = Rel;
329 // if(FrameLen)
330  (*FrameLen) = hDirNdx->LastFrameCount;
331 #else //UDF_LIMIT_DIR_SIZE
332  (*Index) = Frame*UDF_DIR_INDEX_FRAME+Rel;
333 // if(FrameLen)
334  (*FrameLen) = (Frame < (hDirNdx->FrameCount-1)) ? UDF_DIR_INDEX_FRAME :
335  hDirNdx->LastFrameCount;
336 #endif //UDF_LIMIT_DIR_SIZE
337  }
338  return ((PDIR_INDEX_ITEM*)(hDirNdx+1))[Frame]+Rel;
339 } // end UDFDirIndexGetFrame()
340 
341 /*
342  This routine initializes indexes for optimized DirIndex scan
343  according to start Index parameter
344  */
345 
346 BOOLEAN
348  IN PUDF_FILE_INFO DirInfo, //
351  )
352 {
353  Context->DirInfo = DirInfo;
354  Context->hDirNdx = DirInfo->Dloc->DirIndex;
355  if( (Context->frame = (Index >> UDF_DIR_INDEX_FRAME_SH)) >=
356  Context->hDirNdx->FrameCount) {
357  return FALSE;
358  }
359  if( (Context->j = Index & (UDF_DIR_INDEX_FRAME-1)) >=
360  ((Context->frame < (Context->hDirNdx->FrameCount-1))
361  ?
362  UDF_DIR_INDEX_FRAME : Context->hDirNdx->LastFrameCount) ) {
363  return FALSE;
364  }
365  Context->DirNdx = UDFDirIndexGetFrame(Context->hDirNdx,
366  Context->frame,
367  &(Context->d),
368  &(Context->i),
369  Context->j);
370  Context->i--;
371  Context->j--;
372  Context->DirNdx--;
373 
374  return TRUE;
375 } // end UDFDirIndexInitScan()
376 
380  PUDF_FILE_INFO* _FileInfo
381  )
382 {
384  PUDF_FILE_INFO ParFileInfo;
385 
386  Context->i++;
387  Context->j++;
388  Context->DirNdx++;
389 
390  if(Context->j >= Context->d) {
391  Context->j=0;
392  Context->frame++;
393  Context->DirNdx = UDFDirIndexGetFrame(Context->hDirNdx,
394  Context->frame,
395  &(Context->d),
396  &(Context->i),
397  Context->j);
398  }
399  if(!Context->DirNdx) {
400  if(_FileInfo)
401  (*_FileInfo) = NULL;
402  return NULL;
403  }
404 
405  if(_FileInfo) {
406  if((FileInfo = Context->DirNdx->FileInfo)) {
407  if(FileInfo->ParentFile != Context->DirInfo) {
408  ParFileInfo = UDFLocateParallelFI(Context->DirInfo,
409  Context->i,
410  FileInfo);
411 #ifdef UDF_DBG
412  if(ParFileInfo->ParentFile != Context->DirInfo) {
413  BrutePoint();
414  }
415 #endif // UDF_DBG
416  FileInfo = ParFileInfo;
417  }
418  }
419  (*_FileInfo) = FileInfo;
420  }
421 
422  return (Context->DirNdx);
423 } // end UDFDirIndexScan()
424 
425 /*
426  This routine calculates hashes for directory search
427  */
428 uint8
430  IN PVCB Vcb,
432  OUT PHASH_ENTRY hashes,
433  IN uint8 Mask
434  )
435 {
436  UNICODE_STRING UName;
437  WCHAR ShortNameBuffer[13];
438  uint8 RetFlags = 0;
439 
440  if(!Name->Buffer) return 0;
441 
442  if(Mask & HASH_POSIX)
443  hashes->hPosix = crc32((uint8*)(Name->Buffer), Name->Length);
444 
445  if(Mask & HASH_ULFN) {
446 /* if(OS_SUCCESS(MyInitUnicodeString(&UName, L"")) &&
447  OS_SUCCESS(MyAppendUnicodeStringToStringTag(&UName, Name, MEM_USDIRHASH_TAG))) {*/
448  if(OS_SUCCESS(MyCloneUnicodeString(&UName, Name))) {
449  RtlUpcaseUnicodeString(&UName, &UName, FALSE);
450  /* if(!RtlCompareUnicodeString(Name, &UName, FALSE)) {
451  RetFlags |= UDF_FI_FLAG_LFN;
452  }*/
453  hashes->hLfn = crc32((uint8*)(UName.Buffer), UName.Length);
454  } else {
455  BrutePoint();
456  }
457  MyFreePool__(UName.Buffer);
458  }
459 
460  if(Mask & HASH_DOS) {
461  UName.Buffer = (PWCHAR)(&ShortNameBuffer);
462  UName.MaximumLength = 13*sizeof(WCHAR);
463  UDFDOSName(Vcb, &UName, Name, (Mask & HASH_KEEP_NAME) ? TRUE : FALSE);
464  if(!RtlCompareUnicodeString(Name, &UName, TRUE)) {
465  RetFlags |= UDF_FI_FLAG_DOS;
466  }
467  hashes->hDos = crc32((uint8*)(UName.Buffer), UName.Length);
468  }
469  return RetFlags;
470 } // UDFBuildHashEntry()
471 
472 #ifdef UDF_CHECK_UTIL
473 uint32
475  IN int8* buff,
476  IN uint32 prevOffset,
478  )
479 {
480  PFILE_IDENT_DESC FileId;
481  while(prevOffset+sizeof(FILE_IDENT_DESC) < Length) {
482  prevOffset++;
483  FileId = (PFILE_IDENT_DESC)(buff+prevOffset);
484  if(FileId->descTag.tagIdent != TID_FILE_IDENT_DESC)
485  continue;
486  if(FileId->descTag.descVersion != 2 && FileId->descTag.descVersion != 3)
487  continue;
488  if(FileId->fileVersionNum != 1)
489  continue;
490  if(FileId->fileCharacteristics & (~0x1f))
491  continue;
492  if(prevOffset + ((FileId->lengthFileIdent + FileId->lengthOfImpUse + sizeof(FILE_IDENT_DESC) + 3) & (~((uint32)3))) <= Length) {
493  UDFPrint(("UDFFindNextFI OK: %x\n", prevOffset));
494  return prevOffset;
495  }
496  }
497  return 0;
498 } // end UDFFindNextFI()
499 #else //UDF_CHECK_UTIL
500 #define UDFFindNextFI(a,b,c) 0
501 #endif //UDF_CHECK_UTIL
502 
503 /*
504  This routine scans directory extent & builds index table for FileIdents
505  */
506 OSSTATUS
508  IN PVCB Vcb,
510  )
511 {
512  PDIR_INDEX_HDR hDirNdx;
513  PDIR_INDEX_ITEM DirNdx;
514  PFILE_IDENT_DESC FileId;
515  uint32 Offset = 0;
516 // uint32 prevOffset = 0;
517  uint_di Count = 0;
519  int8* buff;
520  PEXTENT_INFO ExtInfo; // Extent array for directory
521  uint16 PartNum;
523  uint16 valueCRC;
524 
527 
528  ExtInfo = &(FileInfo->Dloc->DataLoc);
529  FileInfo->Dloc->DirIndex = NULL;
530  UDFPrint(("UDF: scaning directory\n"));
531  // allocate buffer for the whole directory
532  ASSERT((uint32)(ExtInfo->Length));
533  if(!ExtInfo->Length)
535  buff = (int8*)DbgAllocatePool(PagedPool, (uint32)(ExtInfo->Length));
536  if(!buff)
538 
540 
541  // read FileIdents
542  status = UDFReadExtent(Vcb, ExtInfo, 0, (uint32)(ExtInfo->Length), FALSE, buff, &ReadBytes);
543  if(!OS_SUCCESS(status)) {
544  DbgFreePool(buff);
545  return status;
546  }
547  // scan Dir to get entry counter
548  FileId = (PFILE_IDENT_DESC)buff;
549  DirPrint((" ExtInfo->Length %x\n", ExtInfo->Length));
550 // prevOffset = 0;
551  while(Offset<ExtInfo->Length) {
552  DirPrint((" Offset %x\n", Offset));
553  if(!FileId->descTag.tagIdent) {
554  DirPrint((" term item\n"));
555  break;
556  }
557  if(FileId->descTag.tagIdent != TID_FILE_IDENT_DESC) {
558  DirPrint((" Inv. tag %x\n", FileId->descTag.tagIdent));
559  Offset = UDFFindNextFI(buff, prevOffset, (ULONG)(ExtInfo->Length));
560  if(!Offset) {
561  DirPrint((" can't find next\n"));
562  break;
563  } else {
564  DirPrint((" found next offs %x\n", Offset));
565  FileId = (PFILE_IDENT_DESC)((buff)+Offset);
566  }
567  }
568  if(((ULONG)Offset & (Vcb->LBlockSize-1)) > (Vcb->LBlockSize-sizeof(FILE_IDENT_DESC))) {
569  DirPrint((" badly aligned\n", Offset));
570  if(Vcb->Modified) {
571  DirPrint((" queue repack request\n"));
572  FileInfo->Dloc->DirIndex->DelCount = Vcb->PackDirThreshold+1;
573  }
574  }
575 // prevOffset = Offset;
576  Offset += (FileId->lengthFileIdent + FileId->lengthOfImpUse + sizeof(FILE_IDENT_DESC) + 3) & (~((uint32)3));
577  FileId = (PFILE_IDENT_DESC)((buff)+Offset);
578  Count++;
579  if(Offset+sizeof(FILE_IDENT_DESC) > ExtInfo->Length) {
580  if(Offset != ExtInfo->Length) {
581  UDFPrint((" Trash at the end of Dir\n"));
582  }
583 // BrutePoint();
584  break;
585  }
586  }
587  DirPrint((" final Offset %x\n", Offset));
588  if(Offset > ExtInfo->Length) {
589  BrutePoint();
590  UDFPrint((" Unexpected end of Dir\n"));
591  DbgFreePool(buff);
593  }
594  // allocate buffer for directory index & zero it
595  DirPrint((" Count %x\n", Count));
596  hDirNdx = UDFDirIndexAlloc(Count+1);
597  if(!hDirNdx) {
598  DbgFreePool(buff);
600  }
601 
602  Offset = Count = 0;
603  hDirNdx->DIFlags |= (ExtInfo->Offset ? UDF_DI_FLAG_INIT_IN_ICB : 0);
604  // add entry pointing to the directory itself
605  DirNdx = UDFDirIndex(hDirNdx,0);
606  ASSERT(FileInfo->Dloc->FELoc.Mapping[0].extLocation);
607  DirNdx->FileEntryLoc.partitionReferenceNum = PartNum =
608  (uint16)UDFGetPartNumByPhysLba(Vcb, FileInfo->Dloc->FELoc.Mapping[0].extLocation);
609  ASSERT(PartNum != -1);
610  DirNdx->FileEntryLoc.logicalBlockNum =
611  UDFPhysLbaToPart(Vcb, PartNum, FileInfo->Dloc->FELoc.Mapping[0].extLocation);
612  if(DirNdx->FileEntryLoc.logicalBlockNum == (ULONG)-1) {
613  DirPrint((" err: FileEntryLoc=-1\n"));
614  DbgFreePool(buff);
615  UDFDirIndexFree(hDirNdx);
617  }
618  DirNdx->FileCharacteristics = (FileInfo->FileIdent) ?
619  FileInfo->FileIdent->fileCharacteristics :
621 // DirNdx->Offset = 0;
622 // DirNdx->Length = 0;
623  RtlInitUnicodeString(&DirNdx->FName, L".");
624  DirNdx->FileInfo = FileInfo;
625  DirNdx->FI_Flags |= UDF_FI_FLAG_KEEP_NAME;
626  DirNdx->FI_Flags |= UDFBuildHashEntry(Vcb, &(DirNdx->FName), &(DirNdx->hashes),
628  Count++;
629  FileId = (PFILE_IDENT_DESC)buff;
631 // prevOffset = 0;
632  while((Offset<ExtInfo->Length) && FileId->descTag.tagIdent) {
633  // add new entry to index list
634  if(FileId->descTag.tagIdent != TID_FILE_IDENT_DESC) {
635  UDFPrint((" Invalid tagIdent %x (expected %x) offst %x\n", FileId->descTag.tagIdent, TID_FILE_IDENT_DESC, Offset));
636  DirPrint((" FileId: filen %x, iulen %x, charact %x\n",
637  FileId->lengthFileIdent, FileId->lengthOfImpUse, FileId->fileCharacteristics));
638  DirPrint((" loc: @%x\n", UDFExtentOffsetToLba(Vcb, ExtInfo->Mapping, Offset, NULL, NULL, NULL, NULL)));
639  KdDump(FileId, sizeof(FileId->descTag));
640  Offset = UDFFindNextFI(buff, prevOffset, (ULONG)(ExtInfo->Length));
641  if(!Offset) {
642  DbgFreePool(buff);
643  UDFDirIndexFree(hDirNdx);
645  } else {
646  DirPrint((" found next offs %x\n", Offset));
647  FileId = (PFILE_IDENT_DESC)((buff)+Offset);
648  }
649  }
650  DirNdx = UDFDirIndex(hDirNdx,Count);
651  // allocate buffer & fill it with decompressed unicode filename
652  if(FileId->fileCharacteristics & FILE_DELETED) {
653  DirPrint((" FILE_DELETED\n"));
654  hDirNdx->DelCount++;
655  }
656  DirPrint((" FileId: offs %x, filen %x, iulen %x\n", Offset, FileId->lengthFileIdent, FileId->lengthOfImpUse));
657  DirNdx->Length = (FileId->lengthFileIdent + FileId->lengthOfImpUse + sizeof(FILE_IDENT_DESC) + 3) & (~((uint32)3));
658  DirPrint((" DirNdx: Length %x, Charact %x\n", DirNdx->Length, FileId->fileCharacteristics));
659  if(FileId->fileCharacteristics & FILE_PARENT) {
660  DirPrint((" parent\n"));
661  // init 'parent' entry
662  // '..' points to Parent Object (if any),
663  // otherwise it points to the Dir itself
664  RtlInitUnicodeString(&DirNdx->FName, L"..");
665  DirNdx->FileInfo = (FileInfo->ParentFile) ?
666  FileInfo->ParentFile : FileInfo;
667  DirNdx->FI_Flags |= UDF_FI_FLAG_KEEP_NAME;
668  DirNdx->FI_Flags |= UDFBuildHashEntry(Vcb, &(DirNdx->FName), &(DirNdx->hashes), HASH_ALL | HASH_KEEP_NAME);
669  } else {
670  // init plain file/dir entry
671  ASSERT( (Offset+sizeof(FILE_IDENT_DESC)+FileId->lengthOfImpUse+FileId->lengthFileIdent) <=
672  ExtInfo->Length );
673  UDFDecompressUnicode(&(DirNdx->FName),
674  ((uint8*)(FileId+1)) + (FileId->lengthOfImpUse),
675  FileId->lengthFileIdent,
676  &valueCRC);
677  UDFNormalizeFileName(&(DirNdx->FName), valueCRC);
678  DirNdx->FI_Flags |= UDFBuildHashEntry(Vcb, &(DirNdx->FName), &(DirNdx->hashes), HASH_ALL);
679  }
680  if((FileId->fileCharacteristics & FILE_METADATA)
681  ||
682  !DirNdx->FName.Buffer
683  ||
684  ((DirNdx->FName.Length >= sizeof(UDF_RESERVED_NAME_HDR)-sizeof(WCHAR)) &&
685  (RtlCompareMemory(DirNdx->FName.Buffer, UDF_RESERVED_NAME_HDR, sizeof(UDF_RESERVED_NAME_HDR)-sizeof(WCHAR)) == sizeof(UDF_RESERVED_NAME_HDR)-sizeof(WCHAR)) )) {
686  DirPrint((" metadata\n"));
688  }
689 #if 0
690  UDFPrint(("%ws\n", DirNdx->FName.Buffer));
691 #endif
692  DirPrint(("%ws\n", DirNdx->FName.Buffer));
693  // remember FileEntry location...
694  DirNdx->FileEntryLoc = FileId->icb.extLocation;
695  // ... and some file characteristics
696  DirNdx->FileCharacteristics = FileId->fileCharacteristics;
697  DirNdx->Offset = Offset;
698 #ifdef UDF_CHECK_DISK_ALLOCATION
699  if(!(FileId->fileCharacteristics & FILE_DELETED) &&
701  UDFGetFreeBit(((uint32*)(Vcb->FSBM_Bitmap)), UDFPartLbaToPhys(Vcb, &(DirNdx->FileEntryLoc)) )) {
702 
703  AdPrint(("Ref to Discarded block %x\n",UDFPartLbaToPhys(Vcb, &(DirNdx->FileEntryLoc)) ));
704  BrutePoint();
706  } else
707  if(UDFPartLbaToPhys(Vcb, &(DirNdx->FileEntryLoc)) == LBA_OUT_OF_EXTENT) {
708  AdPrint(("Ref to Invalid block %x\n", UDFPartLbaToPhys(Vcb, &(DirNdx->FileEntryLoc)) ));
709  BrutePoint();
711  }
712 #endif // UDF_CHECK_DISK_ALLOCATION
713 // prevOffset = Offset;
714  Offset += DirNdx->Length;
715  FileId = (PFILE_IDENT_DESC)(((int8*)FileId)+DirNdx->Length);
716  Count++;
717  if(Offset+sizeof(FILE_IDENT_DESC) > ExtInfo->Length) {
718  if(Offset != ExtInfo->Length) {
719  UDFPrint((" Trash at the end of Dir (2)\n"));
720  }
721 // BrutePoint();
722  break;
723  }
724  } // while()
725  // we needn't writing terminator 'cause the buffer is already zero-filled
726  DbgFreePool(buff);
727  if(Count < 2) {
728  UDFDirIndexFree(hDirNdx);
729  UDFPrint((" Directory too short\n"));
731  }
732  // store index
733  FileInfo->Dloc->DirIndex = hDirNdx;
734  return status;
735 } // end UDFIndexDirectory()
736 
737 #ifndef UDF_READ_ONLY_BUILD
738 /*
739  This routine removes all DELETED entries from Dir & resizes it.
740  It must be called before closing, no files sould be opened.
741  */
742 OSSTATUS
744  IN PVCB Vcb,
745  IN OUT PUDF_FILE_INFO FileInfo // source (opened)
746  )
747 {
748 #ifdef UDF_PACK_DIRS
749  uint32 d, LBS;
750  uint_di i, j;
751  uint32 IUl, FIl, l;
752  uint32 DataLocOffset;
753  uint32 Offset, curOffset;
754  int8* Buf;
757  int8* storedFI;
758  PUDF_FILE_INFO curFileInfo;
759  PDIR_INDEX_ITEM DirNdx, DirNdx2;
760  UDF_DIR_SCAN_CONTEXT ScanContext;
761  uint_di dc=0;
762  uint16 PartNum;
763 #endif //UDF_PACK_DIRS
764 
766  PDIR_INDEX_HDR hDirNdx = FileInfo->Dloc->DirIndex;
767  if(!hDirNdx) return STATUS_NOT_A_DIRECTORY;
768 #ifndef UDF_PACK_DIRS
769  return STATUS_SUCCESS;
770 #else // UDF_PACK_DIRS
771 
772  // do not pack dirs on unchanged disks
773  if(!Vcb->Modified)
774  return STATUS_SUCCESS;
775  // start packing
776  LBS = Vcb->LBlockSize;
777  Buf = (int8*)DbgAllocatePool(PagedPool, LBS*2);
778  if(!Buf) return STATUS_INSUFFICIENT_RESOURCES;
779  // we shall never touch 1st entry 'cause it can't be deleted
780  Offset = UDFDirIndex(hDirNdx,2)->Offset;
781  DataLocOffset = FileInfo->Dloc->DataLoc.Offset;
782 
783  i=j=2;
784 
785  if(!UDFDirIndexInitScan(FileInfo, &ScanContext, i)) {
786  DbgFreePool(Buf);
787  return STATUS_SUCCESS;
788  }
789 
790  ASSERT(FileInfo->Dloc->FELoc.Mapping[0].extLocation);
791  PartNum = (uint16)UDFGetPartNumByPhysLba(Vcb, FileInfo->Dloc->FELoc.Mapping[0].extLocation);
792  ASSERT(PartNum != -1);
793 
794  while((DirNdx = UDFDirIndexScan(&ScanContext, NULL))) {
795 
796  if(UDFIsDeleted(DirNdx))
797  dc++;
798 
799  if(!UDFIsDeleted(DirNdx) ||
800  DirNdx->FileInfo) {
801  // move down valid entry
802  status = UDFReadFile__(Vcb, FileInfo, curOffset = DirNdx->Offset,
803  l = DirNdx->Length, FALSE, Buf, &ReadBytes);
804  if(!OS_SUCCESS(status)) {
805  DbgFreePool(Buf);
806  return status;
807  }
808  // remove ImpUse field
809  IUl = ((PFILE_IDENT_DESC)Buf)->lengthOfImpUse;
810  curFileInfo = DirNdx->FileInfo;
811  // align next entry
812  if((d = LBS - ((curOffset + (l - IUl) + DataLocOffset) & (LBS-1)) ) < sizeof(FILE_IDENT_DESC)) {
813 
814  // insufficient space at the end of last sector for
815  // next FileIdent's tag. fill it with ImpUse data
816 
817  // generally, all data should be DWORD-aligned, but if it is not so
818  // this opearation will help us to avoid glitches
819  d = (d+3) & ~(3);
820  if(d != IUl) {
821  l = l + d - IUl;
822  FIl = ((PFILE_IDENT_DESC)Buf)->lengthFileIdent;
823  // copy filename to upper addr
824  RtlMoveMemory(Buf+sizeof(FILE_IDENT_DESC)+d,
825  Buf+sizeof(FILE_IDENT_DESC)+IUl, FIl);
826  RtlZeroMemory(Buf+sizeof(FILE_IDENT_DESC), d);
827  ((PFILE_IDENT_DESC)Buf)->lengthOfImpUse = (uint16)d;
828 
829  if(curFileInfo && curFileInfo->FileIdent) {
830  // update stored FI if any
831  if(!MyReallocPool__((int8*)(curFileInfo->FileIdent), l,
832  (int8**)&(curFileInfo->FileIdent), (l+IUl-d) )) {
833  DbgFreePool(Buf);
835  }
836  storedFI = (int8*)(curFileInfo->FileIdent);
837  RtlMoveMemory(storedFI+sizeof(FILE_IDENT_DESC)+d,
838  storedFI+sizeof(FILE_IDENT_DESC)+IUl, FIl);
839  RtlZeroMemory(storedFI+sizeof(FILE_IDENT_DESC), d);
840  ((PFILE_IDENT_DESC)storedFI)->lengthOfImpUse = (uint16)d;
841  FileInfo->Dloc->FELoc.Modified = TRUE;
842  FileInfo->Dloc->FE_Flags |= UDF_FE_FLAG_FE_MODIFIED;
843  }
844  }
845  } else {
846  d = 0;
847  }
848  // write modified to new addr
849  if((d != IUl) ||
850  (curOffset != Offset)) {
851 
852  UDFSetUpTag(Vcb, (tag*)Buf, (uint16)l,
853  UDFPhysLbaToPart(Vcb, PartNum,
854  UDFExtentOffsetToLba(Vcb, FileInfo->Dloc->DataLoc.Mapping,
855  Offset, NULL, NULL, NULL, NULL)));
856 
858  if(!OS_SUCCESS(status)) {
859  DbgFreePool(Buf);
860  return status;
861  }
862  }
863  DirNdx2 = UDFDirIndex(hDirNdx, j);
864  *DirNdx2 = *DirNdx;
865  DirNdx2->Offset = Offset;
866  DirNdx2->Length = l;
867  if(curFileInfo) {
868  curFileInfo->Index = j;
869  DirNdx2->FI_Flags |= UDF_FI_FLAG_FI_MODIFIED;
870  }
871  Offset += l;
872  j++;
873  }
874  }
875  // resize DirIndex
876  DbgFreePool(Buf);
877  if(dc) {
878  if(!OS_SUCCESS(status = UDFDirIndexTrunc(&(FileInfo->Dloc->DirIndex), dc))) {
879  return status;
880  }
881  }
882  // terminator is set by UDFDirIndexTrunc()
883  FileInfo->Dloc->DirIndex->DelCount = 0;
884  ASSERT(FileInfo->Dloc->FELoc.Mapping[0].extLocation);
885 
886  // now Offset points to EOF. Let's truncate directory
888 #endif // UDF_PACK_DIRS
889 } // end UDFPackDirectory__()
890 
891 /*
892  This routine rebuilds tags for all entries from Dir.
893  */
894 OSSTATUS
896  IN PVCB Vcb,
897  IN OUT PUDF_FILE_INFO FileInfo // source (opened)
898  )
899 {
900  uint32 l;
901  uint32 Offset;
902  int8* Buf;
905  PUDF_FILE_INFO curFileInfo;
906  PDIR_INDEX_ITEM DirNdx;
907  UDF_DIR_SCAN_CONTEXT ScanContext;
908  uint16 PartNum;
909 
911  PDIR_INDEX_HDR hDirNdx = FileInfo->Dloc->DirIndex;
912  if(!hDirNdx) return STATUS_NOT_A_DIRECTORY;
913 
914  // do not pack dirs on unchanged disks
915  if(!Vcb->Modified)
916  return STATUS_SUCCESS;
917 
918  if( ((hDirNdx->DIFlags & UDF_DI_FLAG_INIT_IN_ICB) ? TRUE : FALSE) ==
919  ((FileInfo->Dloc->DataLoc.Offset) ? TRUE : FALSE) ) {
920  return STATUS_SUCCESS;
921  }
922 
923  // start packing
924  Buf = (int8*)DbgAllocatePool(PagedPool, Vcb->LBlockSize*2);
925  if(!Buf) return STATUS_INSUFFICIENT_RESOURCES;
926 
927  Offset = UDFDirIndex(hDirNdx,1)->Offset;
928 
929  if(!UDFDirIndexInitScan(FileInfo, &ScanContext, 1)) {
930  DbgFreePool(Buf);
931  return STATUS_SUCCESS;
932  }
933 
934  ASSERT(FileInfo->Dloc->FELoc.Mapping[0].extLocation);
935  PartNum = (uint16)UDFGetPartNumByPhysLba(Vcb, FileInfo->Dloc->FELoc.Mapping[0].extLocation);
936  ASSERT(PartNum != -1);
937 
938  while((DirNdx = UDFDirIndexScan(&ScanContext, NULL))) {
939 
941  l = DirNdx->Length, FALSE, Buf, &ReadBytes);
942  if(!OS_SUCCESS(status)) {
943  DbgFreePool(Buf);
944  return status;
945  }
946  curFileInfo = DirNdx->FileInfo;
947  // write modified
948  UDFSetUpTag(Vcb, (tag*)Buf, (uint16)l,
949  UDFPhysLbaToPart(Vcb, PartNum,
950  UDFExtentOffsetToLba(Vcb, FileInfo->Dloc->DataLoc.Mapping,
951  Offset, NULL, NULL, NULL, NULL)));
952 
953  if(curFileInfo && curFileInfo->FileIdent) {
954  FileInfo->Dloc->FELoc.Modified = TRUE;
955  FileInfo->Dloc->FE_Flags |= UDF_FE_FLAG_FE_MODIFIED;
956  }
957 
959  if(!OS_SUCCESS(status)) {
960  DbgFreePool(Buf);
961  return status;
962  }
963  if(curFileInfo) {
965  }
966  }
967  // resize DirIndex
968  DbgFreePool(Buf);
969 
970  hDirNdx->DIFlags &= ~UDF_DI_FLAG_INIT_IN_ICB;
971  hDirNdx->DIFlags |= (FileInfo->Dloc->DataLoc.Offset ? UDF_DI_FLAG_INIT_IN_ICB : 0);
972  return status;
973 
974 } // end UDFReTagDirectory()
975 #endif //UDF_READ_ONLY_BUILD
976 
977 /*
978  This routine performs search for specified file in specified directory &
979  returns corresponding offset in extent if found.
980  */
981 OSSTATUS
983  IN PVCB Vcb,
985  IN BOOLEAN NotDeleted,
987  IN PUDF_FILE_INFO DirInfo,
988  IN OUT uint_di* Index // IN:start index OUT:found file index
989  )
990 {
991 // PDIR_INDEX_HDR hDirIndex = DirInfo->Dloc->DirIndex;
993  WCHAR ShortNameBuffer[13];
994  PDIR_INDEX_ITEM DirNdx;
995  UDF_DIR_SCAN_CONTEXT ScanContext;
996  uint_di j=(-1), k=(-1);
997  HASH_ENTRY hashes;
998  BOOLEAN CanBe8d3;
999 
1001 
1002  if((CanBe8d3 = UDFCanNameBeA8dot3(Name))) {
1003  ShortName.MaximumLength = 13 * sizeof(WCHAR);
1004  ShortName.Buffer = (PWCHAR)&ShortNameBuffer;
1005  }
1006 
1007  if(!UDFDirIndexInitScan(DirInfo, &ScanContext, (*Index)))
1009 
1010  if(!IgnoreCase && !CanBe8d3) {
1011  // perform case sensetive sequential directory scan
1012 
1013  while((DirNdx = UDFDirIndexScan(&ScanContext, NULL))) {
1014  if( (DirNdx->hashes.hPosix == hashes.hPosix) &&
1015  DirNdx->FName.Buffer &&
1016  (!RtlCompareUnicodeString(&(DirNdx->FName), Name, FALSE)) &&
1017  ( (!UDFIsDeleted(DirNdx)) || (!NotDeleted) ) ) {
1018  (*Index) = ScanContext.i;
1019  return STATUS_SUCCESS;
1020  }
1021  }
1023  }
1024 
1025  if(hashes.hPosix == hashes.hLfn) {
1026 
1027  while((DirNdx = UDFDirIndexScan(&ScanContext, NULL))) {
1028  if(!DirNdx->FName.Buffer ||
1029  (NotDeleted && UDFIsDeleted(DirNdx)) )
1030  continue;
1031  if( (DirNdx->hashes.hLfn == hashes.hLfn) &&
1032  (!RtlCompareUnicodeString(&(DirNdx->FName), Name, IgnoreCase)) ) {
1033  (*Index) = ScanContext.i;
1034  return STATUS_SUCCESS;
1035  } else
1036  if( CanBe8d3 &&
1037  !(DirNdx->FI_Flags & UDF_FI_FLAG_DOS) &&
1038  (DirNdx->hashes.hDos == hashes.hLfn) &&
1039  (k == (uint_di)(-1))) {
1040  UDFDOSName(Vcb, &ShortName, &(DirNdx->FName), ScanContext.i < 2) ;
1042  k = ScanContext.i;
1043  }
1044  }
1045 
1046  } else {
1047 
1048  while((DirNdx = UDFDirIndexScan(&ScanContext, NULL))) {
1049  // perform sequential directory scan
1050  if(!DirNdx->FName.Buffer ||
1051  (NotDeleted && UDFIsDeleted(DirNdx)) )
1052  continue;
1053  if( (DirNdx->hashes.hPosix == hashes.hPosix) &&
1054  (!RtlCompareUnicodeString(&(DirNdx->FName), Name, FALSE)) ) {
1055  (*Index) = ScanContext.i;
1056  return STATUS_SUCCESS;
1057  } else
1058  if( (DirNdx->hashes.hLfn == hashes.hLfn) &&
1059  (j == (uint_di)(-1)) &&
1060  (!RtlCompareUnicodeString(&(DirNdx->FName), Name, IgnoreCase)) ) {
1061  j = ScanContext.i;
1062  } else
1063  if( CanBe8d3 &&
1064  !(DirNdx->FI_Flags & UDF_FI_FLAG_DOS) &&
1065  (DirNdx->hashes.hDos == hashes.hLfn) &&
1066  (k == (uint_di)(-1))) {
1067  UDFDOSName(Vcb, &ShortName, &(DirNdx->FName), ScanContext.i < 2 );
1069  k = ScanContext.i;
1070  }
1071  }
1072  }
1073  }
1074 
1075  if(j != (uint_di)(-1)) {
1076  (*Index) = j;
1077  return STATUS_SUCCESS;
1078  } else
1079  if(k != (uint_di)(-1)) {
1080  (*Index) = k;
1081  return STATUS_SUCCESS;
1082  }
1083 
1085 
1086 } // end UDFFindFile()
1087 
1088 /*
1089  This routine returns pointer to parent DirIndex
1090 */
1094  )
1095 {
1097 
1098  if(!FileInfo) {
1099  BrutePoint();
1100  return NULL;
1101  }
1102  if (FileInfo->ParentFile) {
1103  ValidateFileInfo(FileInfo->ParentFile);
1104 
1106  return NULL;
1107  if(FileInfo->ParentFile->Dloc)
1108  return FileInfo->ParentFile->Dloc->DirIndex;
1109  return NULL;
1110  }
1111  if(FileInfo->Dloc)
1112  return FileInfo->Dloc->DirIndex;
1113  return NULL;
1114 }
1115 
1116 /*
1117  File Data Location support routines (UDFXxxDloc)
1118  This group is responsible for caching FE locations
1119  If requested FE referenced by another FI the file is assumed to be linked
1120  All linked files reference to common Data Location (& attr) structure
1121  */
1122 
1123 /*
1124  Check if given FE is already in use
1125  */
1126 LONG
1128  IN PVCB Vcb,
1129  IN uint32 Lba
1130  )
1131 {
1132  PUDF_DATALOC_INDEX DlocList;
1133  uint32 l;
1134 
1135  if(!(DlocList = Vcb->DlocList) || !Lba) return (-1);
1136  // scan FE location cache
1137  l = Vcb->DlocCount;
1138  for(uint32 i=0; i<l; i++, DlocList++) {
1139  if(DlocList->Lba == Lba)
1140  return i;
1141  }
1142  return (-1);
1143 } // end UDFFindDloc()
1144 
1145 /*
1146  Check if given FE is already stored in memory
1147  */
1148 LONG
1150  IN PVCB Vcb,
1151  IN PUDF_DATALOC_INFO Dloc
1152  )
1153 {
1154  PUDF_DATALOC_INDEX DlocList;
1155  uint32 l;
1156 
1157  if(!(DlocList = Vcb->DlocList) || !Dloc) return (-1);
1158  // scan FE location cache
1159  l = Vcb->DlocCount;
1160  for(uint32 i=0; i<l; i++, DlocList++) {
1161  if(DlocList->Dloc == Dloc)
1162  return i;
1163  }
1164  return (-1);
1165 } // end UDFFindDlocInMem()
1166 
1167 /*
1168  Find free cache entry
1169  */
1170 LONG
1172  IN PVCB Vcb,
1173  IN uint32 Lba
1174  )
1175 {
1176  PUDF_DATALOC_INDEX DlocList;
1177  uint32 l;
1178 
1179  if(!Vcb->DlocList) {
1180  // init FE location cache
1182  return (-1);
1184  Vcb->DlocCount = DLOC_LIST_GRANULARITY;
1185  }
1186  // scan for free entry
1187  DlocList = Vcb->DlocList;
1188  l = Vcb->DlocCount;
1189  for(uint32 i=0; i<l; i++, DlocList++) {
1190  if(!DlocList->Dloc)
1191  return i;
1192  }
1193  // alloc some free entries
1194  if(!MyReallocPool__((int8*)(Vcb->DlocList), Vcb->DlocCount*sizeof(UDF_DATALOC_INDEX),
1195  (int8**)&(Vcb->DlocList), (Vcb->DlocCount+DLOC_LIST_GRANULARITY)*sizeof(UDF_DATALOC_INDEX))) {
1196  return (-1);
1197  }
1198  RtlZeroMemory(&(Vcb->DlocList[Vcb->DlocCount]), DLOC_LIST_GRANULARITY*sizeof(UDF_DATALOC_INDEX));
1199  Vcb->DlocCount += DLOC_LIST_GRANULARITY;
1200  return (Vcb->DlocCount - DLOC_LIST_GRANULARITY);
1201 } // end UDFFindFreeDloc()
1202 
1203 /*
1204  */
1205 OSSTATUS
1207  IN PVCB Vcb,
1208  IN PUDF_DATALOC_INFO Dloc
1209  )
1210 {
1211  UDFAcquireResourceExclusive(&(Vcb->DlocResource2),TRUE);
1212  if(Dloc->FE_Flags & UDF_FE_FLAG_UNDER_INIT) {
1213  UDFReleaseResource(&(Vcb->DlocResource2));
1214  return STATUS_SHARING_PAUSED;
1215  }
1216  Dloc->FE_Flags |= UDF_FE_FLAG_UNDER_INIT;
1217  UDFReleaseResource(&(Vcb->DlocResource2));
1218  return STATUS_SUCCESS;
1219 } // end UDFAcquireDloc()
1220 
1221 /*
1222  */
1223 OSSTATUS
1225  IN PVCB Vcb,
1226  IN PUDF_DATALOC_INFO Dloc
1227  )
1228 {
1229  UDFAcquireResourceExclusive(&(Vcb->DlocResource2),TRUE);
1230  Dloc->FE_Flags &= ~UDF_FE_FLAG_UNDER_INIT;
1231  UDFReleaseResource(&(Vcb->DlocResource2));
1232  return STATUS_SUCCESS;
1233 } // end UDFReleaseDloc()
1234 
1235 /*
1236  Try to store FE location in cache
1237  If it is already in use, caller will be informed about it
1238  */
1239 OSSTATUS
1241  IN PVCB Vcb,
1242  IN PUDF_FILE_INFO fi,
1243  IN uint32 Lba
1244  )
1245 {
1246  LONG i;
1247  PUDF_DATALOC_INFO Dloc;
1248 
1249  if(!Lba) return STATUS_INVALID_PARAMETER;
1250  if(Lba == (ULONG)-1) return STATUS_INVALID_PARAMETER;
1251 
1252  UDFAcquireResourceExclusive(&(Vcb->DlocResource),TRUE);
1253 
1254  // check if FE specified is already in use
1255  if((i = UDFFindDloc(Vcb, Lba)) == (-1)) {
1256  // not used
1257  if((i = UDFFindFreeDloc(Vcb, Lba)) == (-1)) {
1258  UDFReleaseResource(&(Vcb->DlocResource));
1260  }
1261  } else {
1262  if(!OS_SUCCESS(UDFAcquireDloc(Vcb, Dloc = Vcb->DlocList[i].Dloc))) {
1263  UDFReleaseResource(&(Vcb->DlocResource));
1264  return STATUS_SHARING_PAUSED;
1265  }
1266  // update caller's structures & exit
1267  fi->Dloc = Dloc;
1268  UDFReleaseDloc(Vcb, Dloc);
1269 #if defined UDF_DBG && !defined _CONSOLE
1270  if(fi->Dloc->CommonFcb) {
1271  ASSERT((uint32)(fi->Dloc->CommonFcb) != 0xDEADDA7A);
1272  ASSERT(fi->Dloc->CommonFcb->CommonFCBHeader.NodeTypeCode == UDF_NODE_TYPE_NT_REQ_FCB);
1273  }
1274 #endif // UDF_DBG
1275  UDFReleaseResource(&(Vcb->DlocResource));
1276  return STATUS_SUCCESS;
1277  }
1278  // allocate common DataLocation (Dloc) descriptor
1280  if(!Dloc) {
1281  UDFReleaseResource(&(Vcb->DlocResource));
1283  }
1284  Vcb->DlocList[i].Lba = Lba;
1285  Vcb->DlocList[i].Dloc = Dloc;
1286  RtlZeroMemory(Dloc, sizeof(UDF_DATALOC_INFO));
1287  Dloc->LinkedFileInfo = fi;
1288  UDFAcquireDloc(Vcb, Dloc);
1289  UDFReleaseResource(&(Vcb->DlocResource));
1290  return STATUS_SUCCESS;
1291 } // end UDFStoreDloc()
1292 
1293 /*
1294  Remove unreferenced FE location from cache & free allocated memory
1295  This routine must be invoked when there are no more opened files
1296  associated with given FE
1297  */
1298 OSSTATUS
1300  IN PVCB Vcb,
1301  IN PUDF_DATALOC_INFO Dloc
1302  )
1303 {
1304  LONG i;
1305 
1306  UDFAcquireResourceExclusive(&(Vcb->DlocResource),TRUE);
1307 
1308  if((i = UDFFindDlocInMem(Vcb, Dloc)) == (-1)) {
1309  // FE specified is not in cache. exit
1310  UDFReleaseResource(&(Vcb->DlocResource));
1311  return STATUS_INVALID_PARAMETER;
1312  }
1313  // remove from cache
1314  ASSERT(Vcb->DlocList);
1315  RtlZeroMemory(&(Vcb->DlocList[i]), sizeof(UDF_DATALOC_INDEX));
1316  UDFReleaseResource(&(Vcb->DlocResource));
1317  MyFreePool__(Dloc);
1318  return STATUS_SUCCESS;
1319 } // end UDFRemoveDloc()
1320 
1321 /*
1322  Remove unlinked FE location from cache & keep allocated memory
1323  This routine must be invoked when there are no more opened files
1324  associated with given FE
1325  */
1326 OSSTATUS
1328  IN PVCB Vcb,
1329  IN PUDF_DATALOC_INFO Dloc
1330  )
1331 {
1332  LONG i;
1333 
1334  UDFAcquireResourceExclusive(&(Vcb->DlocResource),TRUE);
1335 
1336  if((i = UDFFindDlocInMem(Vcb, Dloc)) == (-1)) {
1337  // FE specified is not in cache. exit
1338  UDFReleaseResource(&(Vcb->DlocResource));
1339  return STATUS_INVALID_PARAMETER;
1340  }
1341  // remove from cache
1342  ASSERT(Vcb->DlocList);
1343  RtlZeroMemory(&(Vcb->DlocList[i]), sizeof(UDF_DATALOC_INDEX));
1344  UDFReleaseResource(&(Vcb->DlocResource));
1345  return STATUS_SUCCESS;
1346 } // end UDFUnlinkDloc()
1347 
1348 /*
1349  This routine releases memory allocated for Dloc & removes it from
1350  cache (if it is still there)
1351  */
1352 void
1354  IN PVCB Vcb,
1355  IN PUDF_DATALOC_INFO Dloc
1356  )
1357 {
1358  LONG i;
1359 
1360  UDFAcquireResourceExclusive(&(Vcb->DlocResource),TRUE);
1361 
1362  if((i = UDFFindDlocInMem(Vcb, Dloc)) != (-1)) {
1363  ASSERT(Vcb->DlocList);
1364  RtlZeroMemory(&(Vcb->DlocList[i]), sizeof(UDF_DATALOC_INDEX));
1365  }
1366  UDFReleaseResource(&(Vcb->DlocResource));
1367  MyFreePool__(Dloc);
1368 } // end UDFFreeDloc()
1369 
1370 /*
1371  This routine updates Dloc LBA after relocation
1372  */
1373 void
1375  IN PVCB Vcb,
1376  IN PUDF_DATALOC_INFO Dloc,
1377  IN uint32 NewLba
1378  )
1379 {
1380  LONG i;
1381 
1382  UDFAcquireResourceExclusive(&(Vcb->DlocResource),TRUE);
1383 
1384  if((i = UDFFindDlocInMem(Vcb, Dloc)) != (-1)) {
1385  ASSERT(Vcb->DlocList);
1386  Vcb->DlocList[i].Lba = NewLba;
1387  }
1388  UDFReleaseResource(&(Vcb->DlocResource));
1389 
1390 } // end UDFRelocateDloc()
1391 
1392 /*
1393  Release FE cache
1394  */
1395 void
1397  IN PVCB Vcb
1398  )
1399 {
1400  if(!Vcb->DlocList) return;
1401  UDFAcquireResourceExclusive(&(Vcb->DlocResource),TRUE);
1402  for(uint32 i=0; i<Vcb->DlocCount; i++) {
1403  if(Vcb->DlocList[i].Dloc)
1404  MyFreePool__(Vcb->DlocList[i].Dloc);
1405  }
1406  MyFreePool__(Vcb->DlocList);
1407  Vcb->DlocList = NULL;
1408  Vcb->DlocCount = 0;
1409  UDFReleaseResource(&(Vcb->DlocResource));
1410 } // end UDFReleaseDlocList()
1411 
1412 /*
1413  This routine walks through Linked/Parallel FI chain and looks for
1414  FE with same Index & Parent File
1415  */
1418  PUDF_FILE_INFO di, // parent FileInfo
1419  uint_di i, // Index
1420  PUDF_FILE_INFO fi // FileInfo to start search from
1421  )
1422 {
1423  PUDF_FILE_INFO ParFileInfo = fi->NextLinkedFile;
1424 // PUDF_DATALOC_INFO Dloc = di->Dloc;
1425  while((ParFileInfo != fi) &&
1426  ((ParFileInfo->ParentFile != di) ||
1427  (ParFileInfo->Index != i)) ) {
1428  ParFileInfo = ParFileInfo->NextLinkedFile;
1429  }
1430  return ParFileInfo;
1431 // BrutePoint();
1432 } // end UDFLocateParallelFI()
1433 
1434 /*
1435  This routine walks through Linked/Parallel FI chain and looks for
1436  FE with same Index & Parent Dloc
1437  */
1440  PUDF_FILE_INFO fi // FileInfo to start search from
1441  )
1442 {
1443  if(!fi->ParentFile) {
1444  if(fi->NextLinkedFile == fi)
1445  return NULL;
1446  return fi->NextLinkedFile;
1447  }
1448  PUDF_FILE_INFO ParFileInfo = fi->NextLinkedFile;
1449  PUDF_DATALOC_INFO Dloc = fi->ParentFile->Dloc;
1450  uint_di i = fi->Index;
1451  BOOLEAN NotFound = TRUE;
1452  while((ParFileInfo != fi) &&
1453  (NotFound =
1454  ((ParFileInfo->Index != i) ||
1455  (ParFileInfo->ParentFile->Dloc != Dloc))) ) {
1456  ParFileInfo = ParFileInfo->NextLinkedFile;
1457  }
1458 /* if(NotFound) {
1459  if((ParFileInfo->Index == i) &&
1460  (ParFileInfo->ParentFile->Dloc == Dloc))
1461  return ParFileInfo;
1462  return NULL;
1463  }
1464  return ParFileInfo;*/
1465  return NotFound ? NULL : ParFileInfo;
1466 // BrutePoint();
1467 } // end UDFLocateAnyParallelFI()
1468 
1469 void
1471  PUDF_FILE_INFO fi, // FileInfo to be added to chain
1472  PUDF_FILE_INFO fi2 // any FileInfo fro the chain
1473  )
1474 {
1475  fi->NextLinkedFile = fi2->NextLinkedFile;
1476  fi->PrevLinkedFile = fi2;
1477  fi->NextLinkedFile->PrevLinkedFile =
1478  fi->PrevLinkedFile->NextLinkedFile = fi;
1479  return;
1480 } // end UDFInsertLinkedFile()
1481 
OSSTATUS UDFDirIndexGrow(IN PDIR_INDEX_HDR *_hDirNdx, IN uint_di d)
Definition: dirtree.cpp:117
IN PDCB IN POEM_STRING IN PUNICODE_STRING IN OUT POEM_STRING ShortName
Definition: fatprocs.h:1294
uint16 tagIdent
Definition: ecma_167.h:139
#define UDFAcquireResourceExclusive(Resource, CanWait)
Definition: env_spec_w32.h:656
#define DbgAllocatePool
Definition: env_spec_w32.h:332
int add
Definition: i386-dis.c:3122
PDIR_INDEX_HDR UDFDirIndexAlloc(IN uint_di i)
Definition: dirtree.cpp:43
UNICODE_STRING FName
Definition: udf_rel.h:173
void UDFFreeDloc(IN PVCB Vcb, IN PUDF_DATALOC_INFO Dloc)
Definition: dirtree.cpp:1353
struct _FILE_IDENT_DESC * PFILE_IDENT_DESC
#define IN
Definition: typedefs.h:38
#define UDFPrint(Args)
Definition: udffs.h:225
#define TRUE
Definition: types.h:120
#define HASH_DOS
Definition: udf_info.h:77
#define MEM_DLOC_INF_TAG
Definition: udf_rel.h:482
#define STATUS_INSUFFICIENT_RESOURCES
Definition: udferr_usr.h:158
NTSTATUS RtlUpcaseUnicodeString(PUNICODE_STRING dst, PUNICODE_STRING src, BOOLEAN Alloc)
Definition: string_lib.cpp:46
static void xor(unsigned char *dst, const unsigned char *a, const unsigned char *b, const int count)
Definition: crypt_des.c:251
#define AdPrint(_x_)
Definition: env_spec_w32.h:292
struct _UDF_FILE_INFO * LinkedFileInfo
Definition: udf_rel.h:313
OSSTATUS UDFIndexDirectory(IN PVCB Vcb, IN OUT PUDF_FILE_INFO FileInfo)
Definition: dirtree.cpp:507
uint8 UDFBuildHashEntry(IN PVCB Vcb, IN PUNICODE_STRING Name, OUT PHASH_ENTRY hashes, IN uint8 Mask)
Definition: dirtree.cpp:429
uint8 fileCharacteristics
Definition: ecma_167.h:428
#define KdDump(a, b)
Definition: env_spec_w32.h:312
struct _FILE_IDENT_DESC FILE_IDENT_DESC
USHORT MaximumLength
Definition: env_spec_w32.h:370
OSSTATUS UDFReadExtent(IN PVCB Vcb, IN PEXTENT_INFO ExtInfo, IN int64 Offset, IN SIZE_T Length, IN BOOLEAN Direct, OUT int8 *Buffer, OUT PSIZE_T ReadBytes)
Definition: extent.cpp:3021
PDIR_INDEX_ITEM UDFDirIndexGetFrame(IN PDIR_INDEX_HDR hDirNdx, IN uint32 Frame, OUT uint32 *FrameLen, OUT uint_di *Index, IN uint_di Rel)
Definition: dirtree.cpp:316
#define __fastcall
Definition: sync.c:41
#define STATUS_INVALID_PARAMETER
Definition: udferr_usr.h:135
void UDFInsertLinkedFile(PUDF_FILE_INFO fi, PUDF_FILE_INFO fi2)
Definition: dirtree.cpp:1470
unsigned int uint32
Definition: types.h:32
#define UDFReleaseResource(Resource)
Definition: env_spec_w32.h:661
ULONG MyReallocPool__(PCHAR addr, ULONG len, PCHAR *pnewaddr, ULONG newlen)
Definition: mem_tools.h:224
void UDFSetUpTag(IN PVCB Vcb, IN tag *Tag, IN uint16 DataLen, IN uint32 TagLoc)
Definition: udf_info.cpp:936
__inline PDIR_INDEX_ITEM UDFDirIndex(IN PDIR_INDEX_HDR hDirNdx, IN uint_di i)
Definition: udf_info.h:1105
#define UDF_FI_FLAG_KEEP_NAME
Definition: udf_rel.h:226
Definition: udf_rel.h:128
Definition: ecma_167.h:138
_Inout_ __drv_aliasesMem PSLIST_ENTRY _Inout_ PSLIST_ENTRY _In_ ULONG Count
Definition: exfuncs.h:1015
Definition: cdstruc.h:504
PUDF_FILE_INFO UDFLocateParallelFI(PUDF_FILE_INFO di, uint_di i, PUDF_FILE_INFO fi)
Definition: dirtree.cpp:1417
#define HASH_POSIX
Definition: udf_info.h:75
uint_di FrameCount
Definition: udf_rel.h:137
struct _EXCEPTION_POINTERS *_CRTIMP __declspec(noreturn) void __cdecl terminate(void)
Definition: eh.h:27
HDC dc
Definition: cylfrac.c:34
ios_base &_STLP_CALL dec(ios_base &__s)
Definition: _ios_base.h:321
UINT32 crc32
Definition: btrfs.c:3953
lb_addr extLocation
Definition: ecma_167.h:375
uint16_t * PWCHAR
Definition: typedefs.h:54
uint32 UDFExtentOffsetToLba(IN PVCB Vcb, IN PEXTENT_MAP Extent, IN int64 Offset, OUT uint32 *SectorOffset, OUT PSIZE_T AvailLength, OUT uint32 *Flags, OUT uint32 *Index)
Definition: extent.cpp:28
#define cmp(status, error)
Definition: error.c:114
#define UDF_FI_FLAG_FI_MODIFIED
FileIdent was modified & should be flushed.
Definition: udf_rel.h:217
lb_addr FileEntryLoc
Definition: udf_rel.h:178
int64 Length
Definition: udf_rel.h:67
static calc_node_t * pop(void)
Definition: rpn_ieee.c:90
void UDFReleaseDlocList(IN PVCB Vcb)
Definition: dirtree.cpp:1396
#define UDF_NODE_TYPE_NT_REQ_FCB
Definition: struct.h:57
#define RtlMoveMemory(Destination, Source, Length)
Definition: typedefs.h:263
uint32 uint_di
Definition: udf_rel.h:29
OSSTATUS UDFDirIndexTrunc(IN PDIR_INDEX_HDR *_hDirNdx, IN uint_di d)
Definition: dirtree.cpp:174
#define UDF_RESERVED_NAME_HDR
Definition: osta_misc.h:343
#define UDF_DATALOC_INFO_MT
Definition: udf_rel.h:228
PEXTENT_MAP Mapping
Definition: udf_rel.h:66
OSSTATUS UDFUnlinkDloc(IN PVCB Vcb, IN PUDF_DATALOC_INFO Dloc)
Definition: dirtree.cpp:1327
void UDFDirIndexFree(PDIR_INDEX_HDR hDirNdx)
Definition: dirtree.cpp:98
uint_di LastFrameCount
Definition: udf_rel.h:138
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
BOOLEAN __fastcall UDFCanNameBeA8dot3(IN PUNICODE_STRING Name)
Definition: namesup.cpp:266
#define STATUS_FILE_CORRUPT_ERROR
Definition: udferr_usr.h:168
#define STATUS_NOT_A_DIRECTORY
Definition: udferr_usr.h:169
uint_di DelCount
Definition: udf_rel.h:139
struct _UDF_FILE_INFO * NextLinkedFile
Definition: udf_rel.h:408
_In_ ULONG _In_ ULONG Offset
Definition: ntddpcm.h:101
PDIR_INDEX_HDR UDFGetDirIndexByFileInfo(IN PUDF_FILE_INFO FileInfo)
Definition: dirtree.cpp:1092
long LONG
Definition: pedump.c:60
OSSTATUS UDFPackDirectory__(IN PVCB Vcb, IN OUT PUDF_FILE_INFO FileInfo)
Definition: dirtree.cpp:743
struct _DIR_INDEX_HDR DIR_INDEX_HDR
uint32 __fastcall UDFPartLbaToPhys(IN PVCB Vcb, IN lb_addr *Addr)
Definition: alloc.cpp:114
#define OSSTATUS
Definition: env_spec_w32.h:57
#define DirPrint(x)
Definition: dirtree.cpp:34
#define UDF_DIR_INDEX_FRAME
Definition: udf_info.h:1089
#define MEM_DLOC_NDX_TAG
Definition: udf_rel.h:481
PUDF_FILE_INFO UDFLocateAnyParallelFI(PUDF_FILE_INFO fi)
Definition: dirtree.cpp:1439
unsigned char BOOLEAN
#define FILE_METADATA
Definition: ecma_167.h:442
uint8 FileCharacteristics
Definition: udf_rel.h:182
smooth NULL
Definition: ftsmooth.c:416
ULONG DIFlags
Definition: udf_rel.h:142
#define FILE_DELETED
Definition: ecma_167.h:440
#define DLOC_LIST_GRANULARITY
Definition: udf_common.h:654
OSSTATUS UDFStoreDloc(IN PVCB Vcb, IN PUDF_FILE_INFO fi, IN uint32 Lba)
Definition: dirtree.cpp:1240
#define UDF_FE_FLAG_FE_MODIFIED
Was modified & should be flushed.
Definition: udf_rel.h:323
#define FILE_PARENT
Definition: ecma_167.h:441
uint8 lengthFileIdent
Definition: ecma_167.h:429
static NTSTATUS ReadBytes(IN PDEVICE_OBJECT LowerDevice, OUT PUCHAR Buffer, IN ULONG BufferSize, OUT PULONG_PTR FilledBytes)
Definition: detect.c:67
#define UDFIsAStreamDir(FI)
Definition: udf_info.h:998
#define DbgFreePool
Definition: env_spec_w32.h:334
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint GLint GLint j
Definition: glfuncs.h:250
r l[0]
Definition: byte_order.h:167
#define UDFFindNextFI(a, b, c)
Definition: dirtree.cpp:500
void UDFRelocateDloc(IN PVCB Vcb, IN PUDF_DATALOC_INFO Dloc, IN uint32 NewLba)
Definition: dirtree.cpp:1374
GLsizeiptr size
Definition: glext.h:5919
#define d
Definition: ke_i.h:81
#define MEM_DIR_HDR_TAG
Definition: udf_rel.h:479
UCHAR Flags
Definition: udf_rel.h:69
ecx edi ebx edx edi decl ecx esi eax jecxz decl eax andl eax esi movl eax
Definition: synth_sse3d.h:85
NTSTATUS MyCloneUnicodeString(IN PUNICODE_STRING Str1, IN PUNICODE_STRING Str2)
__wchar_t WCHAR
Definition: xmlstorage.h:180
uint_di Index
Definition: udf_rel.h:392
struct _DIR_INDEX_ITEM * PDIR_INDEX_ITEM
HASH_ENTRY hashes
Definition: udf_rel.h:206
OSSTATUS UDFAcquireDloc(IN PVCB Vcb, IN PUDF_DATALOC_INFO Dloc)
Definition: dirtree.cpp:1206
#define Vcb
Definition: cdprocs.h:1425
#define MyFreePool__(addr)
Definition: mem_tools.h:152
struct _UDF_FILE_INFO * PrevLinkedFile
Definition: udf_rel.h:409
static const UCHAR Index[8]
Definition: usbohci.c:18
#define BrutePoint()
Definition: env_spec_w32.h:504
void __fastcall UDFDOSName(IN PVCB Vcb, IN OUT PUNICODE_STRING DosName, IN PUNICODE_STRING UdfName, IN BOOLEAN KeepIntact)
Definition: udf_info.cpp:427
unsigned char uint8
Definition: types.h:28
uint16 lengthOfImpUse
Definition: ecma_167.h:431
_In_ ULONG _In_ ULONG _In_ ULONG Length
Definition: ntddpcm.h:101
ecx edi ebx edx edi decl ecx esi eax jecxz decl eax andl ebx
Definition: synth_sse3d.h:83
struct _UDF_FILE_INFO * ParentFile
Definition: udf_rel.h:381
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
#define FILE_DIRECTORY
Definition: ecma_167.h:439
#define UDF_DI_FLAG_INIT_IN_ICB
Definition: udf_rel.h:147
OSSTATUS UDFFindFile(IN PVCB Vcb, IN BOOLEAN IgnoreCase, IN BOOLEAN NotDeleted, IN PUNICODE_STRING Name, IN PUDF_FILE_INFO DirInfo, IN OUT uint_di *Index)
Definition: dirtree.cpp:982
#define ValidateFileInfo(fi)
Definition: env_spec_w32.h:516
PDIR_INDEX_ITEM UDFDirIndexScan(PUDF_DIR_SCAN_CONTEXT Context, PUDF_FILE_INFO *_FileInfo)
Definition: dirtree.cpp:378
int ret
uint32 Offset
Definition: udf_rel.h:65
uint16 descVersion
Definition: ecma_167.h:140
#define UDF_DIR_INDEX_FRAME_SH
Definition: udf_info.h:1084
static const WCHAR L[]
Definition: oid.c:1250
ULONG RtlCompareUnicodeString(PUNICODE_STRING s1, PUNICODE_STRING s2, BOOLEAN UpCase)
Definition: string_lib.cpp:31
uint16 fileVersionNum
Definition: ecma_167.h:427
OSSTATUS UDFWriteFile__(IN PVCB Vcb, IN PUDF_FILE_INFO FileInfo, IN int64 Offset, IN SIZE_T Length, IN BOOLEAN Direct, IN int8 *Buffer, OUT PSIZE_T WrittenBytes)
Definition: udf_info.cpp:1605
#define OS_SUCCESS(a)
Definition: env_spec_w32.h:56
#define STATUS_SHARING_PAUSED
Definition: udferr_usr.h:165
PUDF_DATALOC_INFO Dloc
Definition: udf_rel.h:437
#define TID_FILE_IDENT_DESC
Definition: ecma_167.h:166
struct _UDF_DATALOC_INFO * PUDF_DATALOC_INFO
uint32 Offset
Definition: udf_rel.h:161
#define MyAllocatePoolTag__(type, size, tag)
Definition: mem_tools.h:150
OSSTATUS UDFRemoveDloc(IN PVCB Vcb, IN PUDF_DATALOC_INFO Dloc)
Definition: dirtree.cpp:1299
VOID UDFNormalizeFileName(IN PUNICODE_STRING FName, IN USHORT valueCRC)
__inline OSSTATUS UDFReadFile__(IN PVCB Vcb, IN PUDF_FILE_INFO FileInfo, IN int64 Offset, IN SIZE_T Length, IN BOOLEAN Direct, OUT int8 *Buffer, OUT PSIZE_T ReadBytes)
Definition: udf_info.h:666
uint32 hPosix
Definition: udf_rel.h:131
ULONG_PTR SIZE_T
Definition: typedefs.h:78
#define STATUS_OBJECT_NAME_NOT_FOUND
Definition: udferr_usr.h:149
#define IgnoreCase
Definition: cdprocs.h:464
#define UDF_FI_FLAG_FI_INTERNAL
Given entry represents the file used for internal FS purposes & must be invisible.
Definition: udf_rel.h:221
#define HASH_ULFN
Definition: udf_info.h:76
unsigned short uint16
Definition: types.h:30
#define HASH_KEEP_NAME
Definition: udf_info.h:79
OSSTATUS UDFResizeFile__(IN PVCB Vcb, IN OUT PUDF_FILE_INFO FileInfo, IN int64 NewLength)
Definition: udf_info.cpp:3468
void __fastcall UDFDecompressUnicode(IN OUT PUNICODE_STRING UName, IN uint8 *CS0, IN SIZE_T Length, OUT uint16 *valueCRC)
Definition: udf_info.cpp:170
struct _UDF_FILE_INFO * FileInfo
Definition: udf_rel.h:204
LONG UDFFindDlocInMem(IN PVCB Vcb, IN PUDF_DATALOC_INFO Dloc)
Definition: dirtree.cpp:1149
#define UDF_FI_FLAG_DOS
Definition: udf_rel.h:225
uint32 logicalBlockNum
Definition: ecma_167.h:362
PFILE_IDENT_DESC FileIdent
Definition: udf_rel.h:372
uint32 Length
Definition: udf_rel.h:168
uint16 partitionReferenceNum
Definition: ecma_167.h:363
#define OUT
Definition: typedefs.h:39
struct FileInfo FileInfo
BOOLEAN UDFDirIndexInitScan(IN PUDF_FILE_INFO DirInfo, OUT PUDF_DIR_SCAN_CONTEXT Context, IN uint_di Index)
Definition: dirtree.cpp:347
#define AlignDirIndex(n)
Definition: udf_info.h:1093
#define UDF_DIR_INDEX_MT
Definition: udf_rel.h:125
unsigned int ULONG
Definition: retypes.h:1
NTSYSAPI VOID NTAPI RtlInitUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:261
#define UDFGetFreeBit(arr, bit)
Definition: udf_info.h:1199
struct _DIR_INDEX_HDR * PDIR_INDEX_HDR
uint32 __fastcall UDFGetPartNumByPhysLba(IN PVCB Vcb, IN uint32 Lba)
Definition: alloc.cpp:201
OSSTATUS UDFReleaseDloc(IN PVCB Vcb, IN PUDF_DATALOC_INFO Dloc)
Definition: dirtree.cpp:1224
uint32 hDos
Definition: udf_rel.h:129
OSSTATUS UDFReTagDirectory(IN PVCB Vcb, IN OUT PUDF_FILE_INFO FileInfo)
Definition: dirtree.cpp:895
LONG UDFFindFreeDloc(IN PVCB Vcb, IN uint32 Lba)
Definition: dirtree.cpp:1171
#define UDF_FE_FLAG_UNDER_INIT
Dloc is being initialized, don't touch it now.
Definition: udf_rel.h:335
#define MEM_DIR_NDX_TAG
Definition: udf_rel.h:480
struct _DIR_INDEX_ITEM DIR_INDEX_ITEM
LONG UDFFindDloc(IN PVCB Vcb, IN uint32 Lba)
Definition: dirtree.cpp:1127
ecx edi ebx edx edi decl ecx esi eax jecxz decl eax andl eax esi movl edx
Definition: synth_sse3d.h:85
#define EXTENT_FLAG_ALLOC_SEQUENTIAL
Definition: udf_rel.h:77
static void push(calc_node_t *op)
Definition: rpn_ieee.c:113
uint32 hLfn
Definition: udf_rel.h:130
#define HASH_ALL
Definition: udf_info.h:78
uint8 FI_Flags
Definition: udf_rel.h:199
return STATUS_SUCCESS
Definition: btrfs.c:2777
#define mul(aa, bb)
Definition: mvAesAlg.c:25
static SERVICE_STATUS status
Definition: service.c:31
uint32 UDFPhysLbaToPart(IN PVCB Vcb, IN uint32 PartNum, IN uint32 Addr)
Definition: alloc.cpp:46
int k
Definition: mpi.c:3369
static unsigned char buff[32768]
Definition: fatten.c:17
#define UDFIsDeleted(DirNdx)
Definition: udf_info.h:788
#define RtlCompareMemory(s1, s2, l)
Definition: env_spec_w32.h:465
char int8
Definition: platform.h:10
#define LBA_OUT_OF_EXTENT
Definition: udf_rel.h:426
jmp_buf jmp
Definition: mach.c:36
Definition: ps.c:97