Windows: Direct IO for AFS Redirector
[openafs.git] / src / WINNT / afsrdr / user / RDRInit.cpp
1 /*
2  * Copyright (c) 2008 Secure Endpoints, Inc.
3  * Copyright (c) 2009-2013 Your File System, Inc.
4  * All rights reserved.
5  *
6  * Redistribution and use in source and binary forms, with or without
7  * modification, are permitted provided that the following conditions are met:
8  *
9  * - Redistributions of source code must retain the above copyright notice,
10  *   this list of conditions and the following disclaimer.
11  * - Redistributions in binary form must reproduce the above copyright notice,
12  *   this list of conditions and the following disclaimer in the documentation
13  *   and/or other materials provided with the distribution.
14  * - Neither the name of Secure Endpoints Inc. nor the names of its contributors
15  *   may be used to endorse or promote products derived from this software without
16  *   specific prior written permission from Secure Endpoints, Inc. and
17  *   Your File System, Inc.
18  *
19  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
20  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
22  * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
23  * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
24  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
25  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
26  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
27  * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
28  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
29  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30  */
31
32 extern "C" {
33 #include <afsconfig.h>
34 #include <afs/param.h>
35 #include <afs/stds.h>
36 }
37
38 #ifndef _WIN32_WINNT
39 #define _WIN32_WINNT 0x0500
40 #endif
41 #define _CRT_SECURE_NO_DEPRECATE
42 #define _CRT_NON_CONFORMING_SWPRINTFS
43 #define UNICODE 1
44 #define STRSAFE_NO_DEPRECATE
45
46 #include <ntstatus.h>
47 #define WIN32_NO_STATUS
48 #include <windows.h>
49 typedef LONG NTSTATUS, *PNTSTATUS;      // not declared in ntstatus.h
50
51 #include <roken.h>
52
53 #include <devioctl.h>
54
55 #include <tchar.h>
56 #include <winbase.h>
57 #include <winreg.h>
58 #include <strsafe.h>
59
60 #include "..\\Common\\AFSUserDefines.h"
61 #include "..\\Common\\AFSUserIoctl.h"
62 #include "..\\Common\\AFSUserStructs.h"
63
64 extern "C" {
65 #include <osilog.h>
66 extern osi_log_t *afsd_logp;
67
68 #include <WINNT/afsreg.h>
69 #include <afs/cm_config.h>
70 #include <afs/cm_error.h>
71 #include <afs/cm_nls.h>
72 #include <afs/cm_user.h>
73 }
74 #include <RDRPrototypes.h>
75
76 static DWORD
77 RDR_SetFileStatus2( AFSFileID * pFileId,
78                     GUID *pAuthGroup,
79                     DWORD dwStatus);
80
81 #ifndef FlagOn
82 #define FlagOn(_F,_SF)        ((_F) & (_SF))
83 #endif
84
85 #ifndef BooleanFlagOn
86 #define BooleanFlagOn(F,SF)   ((BOOLEAN)(((F) & (SF)) != 0))
87 #endif
88
89 #ifndef SetFlag
90 #define SetFlag(_F,_SF)       ((_F) |= (_SF))
91 #endif
92
93 #ifndef ClearFlag
94 #define ClearFlag(_F,_SF)     ((_F) &= ~(_SF))
95 #endif
96
97 #define QuadAlign(Ptr) (                \
98     ((((ULONG)(Ptr)) + 7) & 0xfffffff8) \
99     )
100
101 #define MIN_WORKER_THREADS 5
102 #define MAX_WORKER_THREADS 512
103
104 typedef struct _worker_thread_info {
105
106     HANDLE hThread;
107
108     ULONG  Flags;
109
110     HANDLE hEvent;
111
112 } WorkerThreadInfo;
113
114 WorkerThreadInfo glWorkerThreadInfo[ MAX_WORKER_THREADS];
115
116 UINT   glThreadHandleIndex = 0;
117
118 HANDLE glDevHandle = INVALID_HANDLE_VALUE;
119
120 static DWORD Exit = false;
121
122 static DWORD ExitPending = false;
123
124 DWORD  dwOvEvIdx = 0;
125
126 extern "C" wchar_t RDR_UNCName[64]=L"AFS";
127
128 HANDLE RDR_SuspendEvent = INVALID_HANDLE_VALUE;
129
130 /* returns 0 on success */
131 extern "C" DWORD
132 RDR_Initialize(void)
133 {
134
135     DWORD dwRet = 0;
136     HKEY parmKey;
137     DWORD dummyLen;
138     DWORD numSvThreads = CM_CONFIGDEFAULT_SVTHREADS;
139
140     // Initialize the Suspend Event
141     RDR_SuspendEvent = CreateEvent( NULL,
142                                     TRUE, // manual reset event
143                                     TRUE, // signaled
144                                     NULL);
145
146     dwRet = RegOpenKeyEx(HKEY_LOCAL_MACHINE, AFSREG_CLT_SVC_PARAM_SUBKEY,
147                          0, KEY_QUERY_VALUE, &parmKey);
148     if (dwRet == ERROR_SUCCESS) {
149         dummyLen = sizeof(numSvThreads);
150         dwRet = RegQueryValueEx(parmKey, TEXT("ServerThreads"), NULL, NULL,
151                                 (BYTE *) &numSvThreads, &dummyLen);
152
153         dummyLen = sizeof(RDR_UNCName);
154         dwRet = RegQueryValueExW(parmKey, L"NetbiosName", NULL, NULL,
155                                  (BYTE *) RDR_UNCName, &dummyLen);
156
157         RegCloseKey (parmKey);
158     }
159
160     // Initialize the Thread local storage index for the overlapped i/o
161     // Event Handle
162     dwOvEvIdx = TlsAlloc();
163
164     Exit = false;
165
166     //
167     // Launch our workers down to the
168     // filters control device for processing requests
169     //
170
171     dwRet = RDR_ProcessWorkerThreads(numSvThreads);
172
173     if (dwRet == ERROR_SUCCESS) {
174
175         RDR_InitIoctl();
176         RDR_InitPipe();
177     }
178
179     return dwRet;
180 }
181
182 BOOL RDR_DeviceIoControl( HANDLE hDevice,
183                           DWORD dwIoControlCode,
184                           LPVOID lpInBuffer,
185                           DWORD nInBufferSize,
186                           LPVOID lpOutBuffer,
187                           DWORD nOutBufferSize,
188                           LPDWORD lpBytesReturned )
189 {
190     OVERLAPPED ov;
191     HANDLE hEvent;
192     BOOL rc = FALSE;
193     DWORD gle;
194
195     ZeroMemory(&ov, sizeof(OVERLAPPED));
196
197     hEvent = (HANDLE)TlsGetValue(dwOvEvIdx);
198     if (hEvent == NULL) {
199         hEvent = CreateEvent( NULL, TRUE, TRUE, NULL );
200         if (hEvent == INVALID_HANDLE_VALUE || hEvent == NULL)
201             return FALSE;
202         TlsSetValue( dwOvEvIdx, (LPVOID) hEvent );
203     }
204
205     ResetEvent( hEvent);
206     ov.hEvent = hEvent;
207     *lpBytesReturned = 0;
208
209     rc = DeviceIoControl( hDevice,
210                           dwIoControlCode,
211                           lpInBuffer,
212                           nInBufferSize,
213                           lpOutBuffer,
214                           nOutBufferSize,
215                           lpBytesReturned,
216                           &ov );
217     if ( !rc ) {
218         gle = GetLastError();
219
220         if ( gle == ERROR_IO_PENDING )
221             rc = GetOverlappedResult( hDevice, &ov, lpBytesReturned, TRUE );
222     }
223
224     return rc;
225 }
226
227 extern "C" DWORD
228 RDR_ShutdownFinal(void)
229 {
230
231     DWORD dwIndex = 0;
232
233     Exit = true;
234
235     //
236     // Close all the worker thread handles
237     //
238
239     while( dwIndex < glThreadHandleIndex)
240     {
241
242         CloseHandle( glWorkerThreadInfo[ dwIndex].hThread);
243
244         dwIndex++;
245     }
246
247     if( glDevHandle != INVALID_HANDLE_VALUE)
248     {
249
250         CloseHandle( glDevHandle);
251     }
252
253     return 0;
254 }
255
256 extern "C" DWORD
257 RDR_ShutdownNotify(void)
258 {
259
260     HANDLE hDevHandle = NULL;
261     DWORD bytesReturned;
262
263     //
264     // We use the global handle to the control device instance
265     //
266
267     hDevHandle = glDevHandle;
268
269
270     //
271     // First, notify the file system driver that
272     // we are shutting down.
273     //
274
275     ExitPending = true;
276
277     if( !RDR_DeviceIoControl( hDevHandle,
278                               IOCTL_AFS_SHUTDOWN,
279                               NULL,
280                               0,
281                               NULL,
282                               0,
283                               &bytesReturned ))
284     {
285         // log the error, nothing to do
286     }
287
288
289     RDR_ShutdownIoctl();
290     RDR_ShutdownPipe();
291
292     return 0;
293 }
294
295 //
296 // Here we launch the worker threads for the given volume
297 //
298
299 DWORD
300 RDR_ProcessWorkerThreads(DWORD numThreads)
301 {
302     DWORD WorkerID;
303     HANDLE hEvent;
304     DWORD index = 0;
305     DWORD bytesReturned = 0;
306     DWORD dwRedirInitInfo;
307     AFSRedirectorInitInfo * redirInitInfo = NULL;
308     DWORD dwErr;
309
310     if (dwErr = RDR_SetInitParams(&redirInitInfo, &dwRedirInitInfo))
311         return dwErr;
312
313     glDevHandle = CreateFile( AFS_SYMLINK_W,
314                               GENERIC_READ | GENERIC_WRITE,
315                               FILE_SHARE_READ | FILE_SHARE_WRITE,
316                               NULL,
317                               OPEN_EXISTING,
318                               FILE_FLAG_OVERLAPPED,
319                               NULL);
320
321     if( glDevHandle == INVALID_HANDLE_VALUE)
322     {
323         free(redirInitInfo);
324         return GetLastError();
325     }
326
327     //
328     // Now call down to initialize the pool.
329     //
330
331     if( !RDR_DeviceIoControl( glDevHandle,
332                               IOCTL_AFS_INITIALIZE_CONTROL_DEVICE,
333                               NULL,
334                               0,
335                               NULL,
336                               0,
337                               &bytesReturned ))
338     {
339
340         CloseHandle( glDevHandle);
341
342         glDevHandle = NULL;
343
344         free(redirInitInfo);
345
346         return GetLastError();
347     }
348
349     //
350     // OK, now launch the workers
351     //
352
353     hEvent = CreateEvent( NULL,
354                           TRUE,
355                           FALSE,
356                           NULL);
357
358     //
359     // Here we create a pool of worker threads but you can create the pool with as many requests
360     // as you want
361     //
362
363     if (numThreads < MIN_WORKER_THREADS)
364         numThreads = MIN_WORKER_THREADS;
365     else if (numThreads > MAX_WORKER_THREADS)
366         numThreads = MAX_WORKER_THREADS;
367
368     for (index = 0; index < numThreads; index++)
369     {
370         //
371         // 20% of worker threads should be reserved for release extent
372         // event processing
373         //
374         glWorkerThreadInfo[ glThreadHandleIndex].Flags =
375             (glThreadHandleIndex % 5) ? 0 : AFS_REQUEST_RELEASE_THREAD;
376         glWorkerThreadInfo[ glThreadHandleIndex].hEvent = hEvent;
377         glWorkerThreadInfo[ glThreadHandleIndex].hThread =
378             CreateThread( NULL,
379                           0,
380                           RDR_RequestWorkerThread,
381                           (void *)&glWorkerThreadInfo[ glThreadHandleIndex],
382                           0,
383                           &WorkerID);
384
385         if( glWorkerThreadInfo[ glThreadHandleIndex].hThread != NULL)
386         {
387
388             //
389             // Wait for the thread to signal it is ready for processing
390             //
391
392             WaitForSingleObject( hEvent,
393                                  INFINITE);
394
395             glThreadHandleIndex++;
396
397             ResetEvent( hEvent);
398         }
399         else
400         {
401
402             //
403             // Perform cleanup specific to your application
404             //
405
406         }
407     }
408
409     if( !RDR_DeviceIoControl( glDevHandle,
410                               IOCTL_AFS_INITIALIZE_REDIRECTOR_DEVICE,
411                               redirInitInfo,
412                               dwRedirInitInfo,
413                               NULL,
414                               0,
415                               &bytesReturned ))
416     {
417
418         CloseHandle( glDevHandle);
419
420         glDevHandle = NULL;
421
422         free(redirInitInfo);
423
424         return GetLastError();
425     }
426
427     free(redirInitInfo);
428
429     return 0;
430 }
431
432 //
433 // Entry point for the worker thread
434 //
435
436 DWORD
437 WINAPI
438 RDR_RequestWorkerThread( LPVOID lpParameter)
439 {
440
441     HANDLE hDevHandle = NULL;
442     DWORD bytesReturned;
443     AFSCommRequest *requestBuffer;
444     bool bError = false;
445     WorkerThreadInfo * pInfo = (WorkerThreadInfo *)lpParameter;
446
447     //
448     // We use the global handle to the control device instance
449     //
450
451     hDevHandle = glDevHandle;
452
453     //
454     // Allocate a request buffer.
455     //
456
457     requestBuffer = (AFSCommRequest *)malloc( sizeof( AFSCommRequest) + AFS_PAYLOAD_BUFFER_SIZE);
458
459     if( requestBuffer)
460     {
461
462         //
463         // Here we simply signal back to the main thread that we ahve started
464         //
465
466         SetEvent( pInfo->hEvent);
467
468         //
469         // Process requests until we are told to stop
470         //
471
472         while( !Exit)
473         {
474
475             memset( requestBuffer, '\0', sizeof( AFSCommRequest) + AFS_PAYLOAD_BUFFER_SIZE);
476
477             requestBuffer->RequestFlags = pInfo->Flags;
478
479             if( RDR_DeviceIoControl( hDevHandle,
480                                       IOCTL_AFS_PROCESS_IRP_REQUEST,
481                                       (void *)requestBuffer,
482                                       sizeof( AFSCommRequest),
483                                       (void *)requestBuffer,
484                                       sizeof( AFSCommRequest) + AFS_PAYLOAD_BUFFER_SIZE,
485                                       &bytesReturned ))
486             {
487
488                 WaitForSingleObject( RDR_SuspendEvent, INFINITE);
489
490                 //
491                 // Go process the request
492                 //
493
494                 if (!Exit)
495                     RDR_ProcessRequest( requestBuffer);
496             }
497             else
498             {
499
500                 if (afsd_logp->enabled) {
501                     WCHAR wchBuffer[256];
502                     DWORD gle = GetLastError();
503
504                     swprintf( wchBuffer,
505                               L"Failed to post IOCTL_AFS_IRP_REQUEST gle 0x%x", gle);
506                     osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
507                 }
508             }
509         }
510
511         free( requestBuffer);
512     }
513
514     ExitThread( 0);
515
516     return 0;
517 }
518
519 //
520 // This is the entry point for the worker threads to process the request from the TC Filter driver
521 //
522
523 void
524 RDR_ProcessRequest( AFSCommRequest *RequestBuffer)
525 {
526
527     DWORD               bytesReturned;
528     DWORD               result = 0;
529     ULONG               ulIndex = 0;
530     ULONG               ulCreateFlags = 0;
531     AFSCommResult *     pResultCB = NULL;
532     AFSCommResult       stResultCB;
533     DWORD               dwResultBufferLength = 0;
534     AFSSetFileExtentsCB * SetFileExtentsResultCB = NULL;
535     AFSSetByteRangeLockResultCB *SetByteRangeLockResultCB = NULL;
536     WCHAR               wchBuffer[1024];
537     char *pBuffer = (char *)wchBuffer;
538     DWORD gle;
539     cm_user_t *         userp = NULL;
540     BOOL                bWow64 = (RequestBuffer->RequestFlags & AFS_REQUEST_FLAG_WOW64) ? TRUE : FALSE;
541     BOOL                bFast  = (RequestBuffer->RequestFlags & AFS_REQUEST_FLAG_FAST_REQUEST) ? TRUE : FALSE;
542     BOOL                bHoldFid = (RequestBuffer->RequestFlags & AFS_REQUEST_FLAG_HOLD_FID) ? TRUE : FALSE;
543     BOOL                bFlushFile = (RequestBuffer->RequestFlags & AFS_REQUEST_FLAG_FLUSH_FILE) ? TRUE : FALSE;
544     BOOL                bDeleteFile = (RequestBuffer->RequestFlags & AFS_REQUEST_FLAG_FILE_DELETED) ? TRUE : FALSE;
545     BOOL                bUnlockFile = (RequestBuffer->RequestFlags & AFS_REQUEST_FLAG_BYTE_RANGE_UNLOCK_ALL) ? TRUE : FALSE;
546     BOOL                bCheckOnly = (RequestBuffer->RequestFlags & AFS_REQUEST_FLAG_CHECK_ONLY) ? TRUE : FALSE;
547     BOOL                bRetry = FALSE;
548     BOOL                bUnsupported = FALSE;
549     BOOL                bIsLocalSystem = (RequestBuffer->RequestFlags & AFS_REQUEST_LOCAL_SYSTEM_PAG) ? TRUE : FALSE;
550
551     userp = RDR_UserFromCommRequest(RequestBuffer);
552
553   retry:
554     //
555     // Build up the string to display based on the request type.
556     //
557
558     switch( RequestBuffer->RequestType)
559     {
560
561         case AFS_REQUEST_TYPE_DIR_ENUM:
562         {
563
564             AFSDirQueryCB *pQueryCB = (AFSDirQueryCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
565
566             if (afsd_logp->enabled) {
567                 swprintf( wchBuffer,
568                           L"ProcessRequest Processing AFS_REQUEST_TYPE_DIR_ENUM Index %08lX",
569                           RequestBuffer->RequestIndex);
570
571                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
572             }
573
574             //
575             // Here is where the content of the specific directory is enumerated.
576             //
577
578             RDR_EnumerateDirectory( userp, RequestBuffer->FileId,
579                                     pQueryCB, bWow64, bFast,
580                                     RequestBuffer->ResultBufferLength,
581                                     &pResultCB);
582             break;
583         }
584
585         case AFS_REQUEST_TYPE_EVAL_TARGET_BY_ID:
586         {
587             AFSEvalTargetCB *pEvalTargetCB = (AFSEvalTargetCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
588
589             if (afsd_logp->enabled) {
590                 swprintf( wchBuffer,
591                           L"ProcessRequest Processing AFS_REQUEST_TYPE_EVAL_TARGET_BY_ID Index %08lX",
592                           RequestBuffer->RequestIndex);
593
594                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
595             }
596             //
597             // Here is where the specified node is evaluated.
598             //
599
600             RDR_EvaluateNodeByID( userp, pEvalTargetCB->ParentId,
601                                   RequestBuffer->FileId,
602                                   bWow64, bFast, bHoldFid,
603                                   RequestBuffer->ResultBufferLength,
604                                   &pResultCB);
605             break;
606         }
607
608         case AFS_REQUEST_TYPE_EVAL_TARGET_BY_NAME:
609         {
610             AFSEvalTargetCB *pEvalTargetCB = (AFSEvalTargetCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
611
612             if (afsd_logp->enabled) {
613                 swprintf( wchBuffer,
614                           L"ProcessRequest Processing AFS_REQUEST_TYPE_EVAL_TARGET_BY_NAME Index %08lX",
615                           RequestBuffer->RequestIndex);
616
617                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
618             }
619             //
620             // Here is where the specified node is evaluated.
621             //
622
623             RDR_EvaluateNodeByName( userp, pEvalTargetCB->ParentId,
624                                     RequestBuffer->Name,
625                                     RequestBuffer->NameLength,
626                                     RequestBuffer->RequestFlags & AFS_REQUEST_FLAG_CASE_SENSITIVE ? TRUE : FALSE,
627                                     RequestBuffer->RequestFlags & AFS_REQUEST_FLAG_LAST_COMPONENT ? TRUE : FALSE,
628                                     bWow64, bFast, bHoldFid,
629                                     RequestBuffer->ResultBufferLength,
630                                     &pResultCB);
631             break;
632         }
633
634         case AFS_REQUEST_TYPE_CREATE_FILE:
635         {
636
637             AFSFileCreateCB *pCreateCB = (AFSFileCreateCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
638
639             WCHAR wchFileName[ 256];
640
641             if (afsd_logp->enabled) {
642                 memset( wchFileName, '\0', 256 * sizeof( WCHAR));
643
644                 memcpy( wchFileName,
645                         RequestBuffer->Name,
646                         RequestBuffer->NameLength);
647
648                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_CREATE_FILE Index %08lX File %S",
649                           RequestBuffer->RequestIndex, wchFileName);
650
651                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
652             }
653
654             RDR_CreateFileEntry( userp,
655                                  RequestBuffer->Name,
656                                  RequestBuffer->NameLength,
657                                  pCreateCB,
658                                  bWow64,
659                                  bHoldFid,
660                                  RequestBuffer->ResultBufferLength,
661                                  &pResultCB);
662
663             break;
664         }
665
666         case AFS_REQUEST_TYPE_UPDATE_FILE:
667         {
668
669             AFSFileUpdateCB *pUpdateCB = (AFSFileUpdateCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
670
671             if (afsd_logp->enabled) {
672                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_UPDATE_FILE Index %08lX File %08lX.%08lX.%08lX.%08lX",
673                           RequestBuffer->RequestIndex,
674                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
675                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
676
677                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
678             }
679
680             RDR_UpdateFileEntry( userp, RequestBuffer->FileId,
681                                  pUpdateCB,
682                                  bWow64,
683                                  RequestBuffer->ResultBufferLength,
684                                  &pResultCB);
685
686             break;
687         }
688
689         case AFS_REQUEST_TYPE_DELETE_FILE:
690         {
691
692             AFSFileDeleteCB *pDeleteCB = (AFSFileDeleteCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
693
694             if (afsd_logp->enabled) {
695                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_DELETE_FILE Index %08lX %08lX.%08lX.%08lX.%08lX CheckOnly %X",
696                           RequestBuffer->RequestIndex,
697                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
698                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique,
699                           bCheckOnly);
700
701                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
702             }
703
704             RDR_DeleteFileEntry( userp,
705                                  pDeleteCB->ParentId,
706                                  pDeleteCB->ProcessId,
707                                  RequestBuffer->Name,
708                                  RequestBuffer->NameLength,
709                                  bWow64,
710                                  bCheckOnly,
711                                  RequestBuffer->ResultBufferLength,
712                                  &pResultCB);
713
714             break;
715         }
716
717         case AFS_REQUEST_TYPE_RENAME_FILE:
718         {
719
720             AFSFileRenameCB *pFileRenameCB = (AFSFileRenameCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
721
722             if (afsd_logp->enabled) {
723                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_RENAME_FILE Index %08lX File %08lX.%08lX.%08lX.%08lX NameLength %08lX Name %*S TargetLength %08lX Target %*S",
724                           RequestBuffer->RequestIndex,
725                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
726                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique,
727                           RequestBuffer->NameLength, (int)RequestBuffer->NameLength, RequestBuffer->Name,
728                           pFileRenameCB->TargetNameLength, (int)pFileRenameCB->TargetNameLength, pFileRenameCB->TargetName);
729
730                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
731             }
732
733             RDR_RenameFileEntry( userp,
734                                  RequestBuffer->Name,
735                                  RequestBuffer->NameLength,
736                                  RequestBuffer->FileId,
737                                  pFileRenameCB,
738                                  bWow64,
739                                  RequestBuffer->ResultBufferLength,
740                                  &pResultCB);
741
742             break;
743         }
744
745         case AFS_REQUEST_TYPE_HARDLINK_FILE:
746         {
747
748             AFSFileHardLinkCB *pFileHardLinkCB = (AFSFileHardLinkCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
749
750             if (afsd_logp->enabled) {
751                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_HARDLINK_FILE Index %08lX File %08lX.%08lX.%08lX.%08lX NameLength %08lX Name %*S TargetLength %08lX Target %*S",
752                           RequestBuffer->RequestIndex,
753                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
754                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique,
755                           RequestBuffer->NameLength, (int)RequestBuffer->NameLength, RequestBuffer->Name,
756                           pFileHardLinkCB->TargetNameLength, (int)pFileHardLinkCB->TargetNameLength, pFileHardLinkCB->TargetName);
757
758                     osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
759                 }
760
761                 RDR_HardLinkFileEntry( userp,
762                                        RequestBuffer->Name,
763                                        RequestBuffer->NameLength,
764                                        RequestBuffer->FileId,
765                                        pFileHardLinkCB,
766                                        bWow64,
767                                        RequestBuffer->ResultBufferLength,
768                                        &pResultCB);
769
770             break;
771         }
772
773         case AFS_REQUEST_TYPE_REQUEST_FILE_EXTENTS:
774         {
775
776             AFSRequestExtentsCB *pFileRequestExtentsCB = (AFSRequestExtentsCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
777
778             if (afsd_logp->enabled) {
779                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_REQUEST_FILE_EXTENTS Index %08lX File %08lX.%08lX.%08lX.%08lX %S",
780                           RequestBuffer->RequestIndex,
781                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
782                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique,
783                           BooleanFlagOn( RequestBuffer->RequestFlags, AFS_REQUEST_FLAG_SYNCHRONOUS) ? L"Sync" : L"Async");
784
785                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
786             }
787
788             if (BooleanFlagOn( RequestBuffer->RequestFlags, AFS_REQUEST_FLAG_SYNCHRONOUS))
789                 osi_panic("SYNCHRONOUS AFS_REQUEST_TYPE_REQUEST_FILE_EXTENTS not supported",
790                           __FILE__, __LINE__);
791             else
792                 bRetry = RDR_RequestFileExtentsAsync( userp, RequestBuffer->FileId,
793                                                       pFileRequestExtentsCB,
794                                                       bWow64,
795                                                       &dwResultBufferLength,
796                                                       &SetFileExtentsResultCB );
797             break;
798         }
799
800         case AFS_REQUEST_TYPE_RELEASE_FILE_EXTENTS:
801         {
802
803             AFSReleaseExtentsCB *pFileReleaseExtentsCB = (AFSReleaseExtentsCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
804
805             if (afsd_logp->enabled) {
806                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_RELEASE_FILE_EXTENTS Index %08lX File %08lX.%08lX.%08lX.%08lX",
807                           RequestBuffer->RequestIndex,
808                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
809                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
810
811                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
812             }
813
814             RDR_ReleaseFileExtents( userp, RequestBuffer->FileId,
815                                     pFileReleaseExtentsCB,
816                                     bWow64,
817                                     RequestBuffer->ResultBufferLength,
818                                     &pResultCB);
819
820             break;
821         }
822
823         case AFS_REQUEST_TYPE_FLUSH_FILE:
824         {
825             if (afsd_logp->enabled) {
826                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_FLUSH_FILE Index %08lX File %08lX.%08lX.%08lX.%08lX",
827                           RequestBuffer->RequestIndex,
828                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
829                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
830
831                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
832             }
833
834             RDR_FlushFileEntry( userp, RequestBuffer->FileId,
835                                 bWow64,
836                                 RequestBuffer->ResultBufferLength,
837                                 &pResultCB);
838             break;
839         }
840
841         case AFS_REQUEST_TYPE_OPEN_FILE:
842         {
843             AFSFileOpenCB *pFileOpenCB = (AFSFileOpenCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
844
845             if (afsd_logp->enabled) {
846                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_OPEN_FILE Index %08lX File %08lX.%08lX.%08lX.%08lX",
847                           RequestBuffer->RequestIndex,
848                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
849                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
850
851                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
852             }
853
854             RDR_OpenFileEntry( userp, RequestBuffer->FileId,
855                                pFileOpenCB,
856                                bWow64,
857                                bHoldFid,
858                                RequestBuffer->ResultBufferLength,
859                                &pResultCB);
860
861             break;
862         }
863
864         case AFS_REQUEST_TYPE_RELEASE_FILE_ACCESS:
865         {
866             AFSFileAccessReleaseCB *pFileAccessReleaseCB = (AFSFileAccessReleaseCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
867
868             if (afsd_logp->enabled) {
869                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_RELEASE_FILE_ACCESS Index %08lX File %08lX.%08lX.%08lX.%08lX",
870                           RequestBuffer->RequestIndex,
871                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
872                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
873
874                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
875             }
876
877             RDR_ReleaseFileAccess( userp,
878                                    RequestBuffer->FileId,
879                                    pFileAccessReleaseCB,
880                                    bWow64,
881                                    RequestBuffer->ResultBufferLength,
882                                    &pResultCB);
883
884             break;
885         }
886
887         case AFS_REQUEST_TYPE_PIOCTL_OPEN:
888         {
889             AFSPIOCtlOpenCloseRequestCB *pPioctlCB = (AFSPIOCtlOpenCloseRequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
890
891             if (afsd_logp->enabled) {
892                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_PIOCTL_OPEN Index %08lX Parent %08lX.%08lX.%08lX.%08lX",
893                           RequestBuffer->RequestIndex,
894                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
895                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
896
897                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
898             }
899
900             RDR_PioctlOpen( userp,
901                             RequestBuffer->FileId,
902                             pPioctlCB,
903                             bWow64,
904                             RequestBuffer->ResultBufferLength,
905                             &pResultCB);
906             break;
907         }
908
909         case AFS_REQUEST_TYPE_PIOCTL_WRITE:
910         {
911             AFSPIOCtlIORequestCB *pPioctlCB = (AFSPIOCtlIORequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
912
913             if (afsd_logp->enabled) {
914                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_PIOCTL_WRITE Index %08lX Parent %08lX.%08lX.%08lX.%08lX",
915                           RequestBuffer->RequestIndex,
916                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
917                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
918
919                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
920             }
921
922             RDR_PioctlWrite( userp,
923                              RequestBuffer->FileId,
924                              pPioctlCB,
925                              bWow64,
926                              RequestBuffer->ResultBufferLength,
927                              &pResultCB);
928             break;
929         }
930
931         case AFS_REQUEST_TYPE_PIOCTL_READ:
932         {
933             AFSPIOCtlIORequestCB *pPioctlCB = (AFSPIOCtlIORequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
934
935             if (afsd_logp->enabled) {
936                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_PIOCTL_READ Index %08lX Parent %08lX.%08lX.%08lX.%08lX",
937                           RequestBuffer->RequestIndex,
938                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
939                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
940
941                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
942             }
943
944             RDR_PioctlRead( userp,
945                             RequestBuffer->FileId,
946                             pPioctlCB,
947                             bWow64,
948                             bIsLocalSystem,
949                             RequestBuffer->ResultBufferLength,
950                             &pResultCB);
951             break;
952         }
953
954         case AFS_REQUEST_TYPE_PIOCTL_CLOSE:
955         {
956             AFSPIOCtlOpenCloseRequestCB *pPioctlCB = (AFSPIOCtlOpenCloseRequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
957
958             if (afsd_logp->enabled) {
959                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_PIOCTL_CLOSE Index %08lX Parent %08lX.%08lX.%08lX.%08lX",
960                           RequestBuffer->RequestIndex,
961                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
962                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
963
964                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
965             }
966
967             RDR_PioctlClose( userp,
968                              RequestBuffer->FileId,
969                              pPioctlCB,
970                              bWow64,
971                              RequestBuffer->ResultBufferLength,
972                              &pResultCB);
973             break;
974         }
975
976
977         case AFS_REQUEST_TYPE_BYTE_RANGE_LOCK:
978         {
979             if (afsd_logp->enabled) {
980                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_BYTE_RANGE_LOCK Index %08lX File %08lX.%08lX.%08lX.%08lX %S",
981                           RequestBuffer->RequestIndex,
982                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
983                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique,
984                           BooleanFlagOn( RequestBuffer->RequestFlags, AFS_REQUEST_FLAG_SYNCHRONOUS) ? L"Sync" : L"Async");
985
986                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
987             }
988
989             AFSByteRangeLockRequestCB *pBRLRequestCB = (AFSByteRangeLockRequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
990
991             RDR_ByteRangeLockSync( userp,
992                                    RequestBuffer->FileId,
993                                    pBRLRequestCB,
994                                    bWow64,
995                                    RequestBuffer->ResultBufferLength,
996                                    &pResultCB);
997
998             break;
999         }
1000
1001         case AFS_REQUEST_TYPE_BYTE_RANGE_UNLOCK:
1002         {
1003             AFSByteRangeUnlockRequestCB *pBRURequestCB = (AFSByteRangeUnlockRequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
1004
1005             if (afsd_logp->enabled) {
1006                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_BYTE_RANGE_UNLOCK Index %08lX File %08lX.%08lX.%08lX.%08lX",
1007                           RequestBuffer->RequestIndex,
1008                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
1009                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
1010
1011                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1012             }
1013
1014             RDR_ByteRangeUnlock( userp,
1015                                  RequestBuffer->FileId,
1016                                  pBRURequestCB,
1017                                  bWow64,
1018                                  RequestBuffer->ResultBufferLength,
1019                                  &pResultCB);
1020             break;
1021         }
1022
1023         case AFS_REQUEST_TYPE_BYTE_RANGE_UNLOCK_ALL:
1024         {
1025             AFSByteRangeUnlockRequestCB *pBRURequestCB = (AFSByteRangeUnlockRequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
1026
1027             if (afsd_logp->enabled) {
1028                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_BYTE_RANGE_UNLOCK_ALL Index %08lX File %08lX.%08lX.%08lX.%08lX",
1029                           RequestBuffer->RequestIndex,
1030                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
1031                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
1032
1033                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1034             }
1035
1036             RDR_ByteRangeUnlockAll( userp,
1037                                     RequestBuffer->FileId,
1038                                     pBRURequestCB,
1039                                     bWow64,
1040                                     RequestBuffer->ResultBufferLength,
1041                                     &pResultCB);
1042             break;
1043         }
1044
1045         case AFS_REQUEST_TYPE_GET_VOLUME_INFO:
1046         {
1047             if (afsd_logp->enabled) {
1048                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_GET_VOLUME_INFO Index %08lX File %08lX.%08lX.%08lX.%08lX",
1049                           RequestBuffer->RequestIndex,
1050                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
1051                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
1052
1053                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1054             }
1055
1056             RDR_GetVolumeInfo( userp,
1057                                RequestBuffer->FileId,
1058                                bWow64,
1059                                RequestBuffer->ResultBufferLength,
1060                                &pResultCB);
1061             break;
1062         }
1063
1064         case AFS_REQUEST_TYPE_GET_VOLUME_SIZE_INFO:
1065         {
1066             if (afsd_logp->enabled) {
1067                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_GET_VOLUME_SIZE_INFO Index %08lX File %08lX.%08lX.%08lX.%08lX",
1068                           RequestBuffer->RequestIndex,
1069                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
1070                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
1071
1072                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1073             }
1074
1075             RDR_GetVolumeSizeInfo( userp,
1076                                    RequestBuffer->FileId,
1077                                    bWow64,
1078                                    RequestBuffer->ResultBufferLength,
1079                                    &pResultCB);
1080             break;
1081         }
1082
1083         case AFS_REQUEST_TYPE_HOLD_FID:
1084         {
1085
1086             AFSHoldFidRequestCB *pHoldFidCB = (AFSHoldFidRequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
1087
1088             if (afsd_logp->enabled) {
1089                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_HOLD_FID Index %08lX",
1090                           RequestBuffer->RequestIndex);
1091
1092                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1093             }
1094
1095             RDR_HoldFid( userp,
1096                          pHoldFidCB,
1097                          bFast,
1098                          RequestBuffer->ResultBufferLength,
1099                          &pResultCB);
1100
1101             break;
1102         }
1103
1104         case AFS_REQUEST_TYPE_RELEASE_FID:
1105         {
1106
1107             AFSReleaseFidRequestCB *pReleaseFidCB = (AFSReleaseFidRequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
1108
1109             if (afsd_logp->enabled) {
1110                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_RELEASE_FID Index %08lX",
1111                           RequestBuffer->RequestIndex);
1112
1113                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1114             }
1115
1116             RDR_ReleaseFid( userp,
1117                             pReleaseFidCB,
1118                             bFast,
1119                             RequestBuffer->ResultBufferLength,
1120                             &pResultCB);
1121
1122             break;
1123         }
1124
1125         case AFS_REQUEST_TYPE_CLEANUP_PROCESSING:
1126         {
1127
1128             AFSFileCleanupCB *pCleanupCB = (AFSFileCleanupCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
1129
1130             if (afsd_logp->enabled) {
1131                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_CLEANUP_FILE Index %08lX File %08lX.%08lX.%08lX.%08lX",
1132                           RequestBuffer->RequestIndex,
1133                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
1134                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
1135
1136                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1137             }
1138
1139             RDR_CleanupFileEntry( userp,
1140                                   RequestBuffer->FileId,
1141                                   RequestBuffer->Name,
1142                                   RequestBuffer->NameLength,
1143                                   pCleanupCB,
1144                                   bWow64,
1145                                   bFlushFile,
1146                                   bDeleteFile,
1147                                   bUnlockFile,
1148                                   RequestBuffer->ResultBufferLength,
1149                                   &pResultCB);
1150
1151             break;
1152         }
1153
1154         case AFS_REQUEST_TYPE_PIPE_OPEN:
1155         {
1156             AFSPipeOpenCloseRequestCB *pPipeCB = (AFSPipeOpenCloseRequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
1157
1158             if (afsd_logp->enabled) {
1159                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_PIPE_OPEN Index %08lX Parent %08lX.%08lX.%08lX.%08lX",
1160                           RequestBuffer->RequestIndex,
1161                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
1162                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
1163
1164                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1165             }
1166
1167             RDR_PipeOpen( userp,
1168                           RequestBuffer->FileId,
1169                           RequestBuffer->Name,
1170                           RequestBuffer->NameLength,
1171                           pPipeCB,
1172                           bWow64,
1173                           RequestBuffer->ResultBufferLength,
1174                           &pResultCB);
1175             break;
1176         }
1177
1178         case AFS_REQUEST_TYPE_PIPE_WRITE:
1179         {
1180             AFSPipeIORequestCB *pPipeCB = (AFSPipeIORequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
1181             BYTE *pPipeData = ((BYTE *)RequestBuffer->Name + RequestBuffer->DataOffset + sizeof(AFSPipeIORequestCB));
1182
1183             if (afsd_logp->enabled) {
1184                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_PIPE_WRITE Index %08lX Parent %08lX.%08lX.%08lX.%08lX",
1185                           RequestBuffer->RequestIndex,
1186                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
1187                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
1188
1189                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1190             }
1191
1192             RDR_PipeWrite( userp,
1193                            RequestBuffer->FileId,
1194                            pPipeCB,
1195                            pPipeData,
1196                            bWow64,
1197                            RequestBuffer->ResultBufferLength,
1198                            &pResultCB);
1199             break;
1200         }
1201
1202         case AFS_REQUEST_TYPE_PIPE_READ:
1203         {
1204             AFSPipeIORequestCB *pPipeCB = (AFSPipeIORequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
1205
1206             if (afsd_logp->enabled) {
1207                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_PIPE_READ Index %08lX Parent %08lX.%08lX.%08lX.%08lX",
1208                           RequestBuffer->RequestIndex,
1209                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
1210                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
1211
1212                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1213             }
1214
1215             RDR_PipeRead( userp,
1216                           RequestBuffer->FileId,
1217                           pPipeCB,
1218                           bWow64,
1219                           RequestBuffer->ResultBufferLength,
1220                           &pResultCB);
1221             break;
1222         }
1223
1224         case AFS_REQUEST_TYPE_PIPE_CLOSE:
1225         {
1226             AFSPipeOpenCloseRequestCB *pPipeCB = (AFSPipeOpenCloseRequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
1227
1228             if (afsd_logp->enabled) {
1229                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_PIPE_CLOSE Index %08lX Parent %08lX.%08lX.%08lX.%08lX",
1230                           RequestBuffer->RequestIndex,
1231                           RequestBuffer->FileId.Cell, RequestBuffer->FileId.Volume,
1232                           RequestBuffer->FileId.Vnode, RequestBuffer->FileId.Unique);
1233
1234                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1235             }
1236
1237             RDR_PipeClose( userp,
1238                            RequestBuffer->FileId,
1239                            pPipeCB,
1240                            bWow64,
1241                            RequestBuffer->ResultBufferLength,
1242                            &pResultCB);
1243             break;
1244         }
1245
1246
1247         case AFS_REQUEST_TYPE_PIPE_TRANSCEIVE:
1248         {
1249             AFSPipeIORequestCB *pPipeCB = (AFSPipeIORequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
1250             BYTE *pPipeData = ((BYTE *)RequestBuffer->Name + RequestBuffer->DataOffset + sizeof(AFSPipeIORequestCB));
1251
1252             if (afsd_logp->enabled) {
1253                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_PIPE_TRANSCEIVE Index %08lX",
1254                           RequestBuffer->RequestIndex);
1255
1256                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1257             }
1258
1259             RDR_PipeTransceive( userp,
1260                                 RequestBuffer->FileId,
1261                                 pPipeCB,
1262                                 pPipeData,
1263                                 bWow64,
1264                                 RequestBuffer->ResultBufferLength,
1265                                 &pResultCB);
1266             break;
1267         }
1268
1269         case AFS_REQUEST_TYPE_PIPE_QUERY_INFO:
1270         {
1271             AFSPipeInfoRequestCB *pPipeInfoCB = (AFSPipeInfoRequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
1272
1273             if (afsd_logp->enabled) {
1274                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_PIPE_QUERY_INFO Index %08lX",
1275                           RequestBuffer->RequestIndex);
1276
1277                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1278             }
1279
1280             RDR_PipeQueryInfo( userp,
1281                                RequestBuffer->FileId,
1282                                pPipeInfoCB,
1283                                bWow64,
1284                                RequestBuffer->ResultBufferLength,
1285                                &pResultCB);
1286             break;
1287         }
1288
1289         case AFS_REQUEST_TYPE_PIPE_SET_INFO:
1290         {
1291             AFSPipeInfoRequestCB *pPipeInfoCB = (AFSPipeInfoRequestCB *)((char *)RequestBuffer->Name + RequestBuffer->DataOffset);
1292             BYTE *pPipeData = ((BYTE *)RequestBuffer->Name + RequestBuffer->DataOffset + sizeof(AFSPipeInfoRequestCB));
1293
1294             if (afsd_logp->enabled) {
1295                 swprintf( wchBuffer, L"ProcessRequest Processing AFS_REQUEST_TYPE_PIPE_SET_INFO Index %08lX",
1296                           RequestBuffer->RequestIndex);
1297
1298                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1299             }
1300
1301             RDR_PipeSetInfo( userp,
1302                              RequestBuffer->FileId,
1303                              pPipeInfoCB,
1304                              pPipeData,
1305                              bWow64,
1306                              RequestBuffer->ResultBufferLength,
1307                              &pResultCB);
1308
1309             break;
1310         }
1311
1312         default:
1313             bUnsupported = TRUE;
1314
1315             if (afsd_logp->enabled) {
1316                 swprintf( wchBuffer, L"ProcessRequest Received unknown request type %08lX Index %08lX",
1317                           RequestBuffer->RequestType,
1318                           RequestBuffer->RequestIndex);
1319
1320                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1321             }
1322
1323             break;
1324     }
1325
1326     if( BooleanFlagOn( RequestBuffer->RequestFlags, AFS_REQUEST_FLAG_SYNCHRONOUS))
1327     {
1328
1329         if (pResultCB == NULL) {
1330             // We failed probably due to a memory allocation error
1331             // unless the unsupported flag was set.
1332             pResultCB = &stResultCB;
1333             memset(&stResultCB, 0, sizeof(stResultCB));
1334             if ( bUnsupported )
1335                 pResultCB->ResultStatus = STATUS_NOT_IMPLEMENTED;
1336             else
1337                 pResultCB->ResultStatus = STATUS_NO_MEMORY;
1338         }
1339
1340         if (userp) {
1341             pResultCB->Authenticated = cm_HaveToken( userp,
1342                                                      RequestBuffer->FileId.Cell);
1343         }
1344
1345         //
1346         // This is how the filter associates the response information passed in the IOCtl below to the
1347         // original call. This request index is setup by the filter and should not be modified, otherwise the
1348         // filter will not be able to locate the request in its internal queue and the blocking thread will
1349         // not be awakened
1350         //
1351
1352         pResultCB->RequestIndex = RequestBuffer->RequestIndex;
1353
1354         if (afsd_logp->enabled) {
1355             swprintf( wchBuffer,
1356                       L"ProcessRequest Responding to Index %08lX Length %08lX",
1357                       pResultCB->RequestIndex,
1358                       pResultCB->ResultBufferLength);
1359
1360             osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1361         }
1362
1363         //
1364         // Now post the result back to the driver.
1365         //
1366
1367         if( !RDR_DeviceIoControl( glDevHandle,
1368                                   IOCTL_AFS_PROCESS_IRP_RESULT,
1369                                   (void *)pResultCB,
1370                                   sizeof( AFSCommResult) + pResultCB->ResultBufferLength,
1371                                   (void *)NULL,
1372                                   0,
1373                                   &bytesReturned ))
1374         {
1375             char *pBuffer = (char *)wchBuffer;
1376             gle = GetLastError();
1377             if (afsd_logp->enabled) {
1378                 swprintf( wchBuffer,
1379                           L"Failed to post IOCTL_AFS_PROCESS_IRP_RESULT gle %X", gle);
1380                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1381             }
1382
1383             if (gle != ERROR_NOT_READY) {
1384                 sprintf( pBuffer,
1385                          "Failed to post IOCTL_AFS_PROCESS_IRP_RESULT gle %X",
1386                          GetLastError());
1387                 osi_panic(pBuffer, __FILE__, __LINE__);
1388             }
1389         }
1390
1391     }
1392     else if (RequestBuffer->RequestType == AFS_REQUEST_TYPE_REQUEST_FILE_EXTENTS) {
1393
1394         if (SetFileExtentsResultCB) {
1395
1396             if (1 || afsd_logp->enabled) {
1397                 if (SetFileExtentsResultCB->ResultStatus != 0)
1398                     swprintf( wchBuffer,
1399                           L"ProcessRequest Responding Asynchronously with FAILURE to REQUEST_FILE_EXTENTS Index %08lX Count %08lX Status %08lX",
1400                           RequestBuffer->RequestIndex, SetFileExtentsResultCB->ExtentCount, SetFileExtentsResultCB->ResultStatus);
1401                 else
1402                     swprintf( wchBuffer,
1403                           L"ProcessRequest Responding Asynchronously with SUCCESS to REQUEST_FILE_EXTENTS Index %08lX Count %08lX",
1404                           RequestBuffer->RequestIndex, SetFileExtentsResultCB->ExtentCount);
1405
1406                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1407             }
1408
1409             if( (SetFileExtentsResultCB->ExtentCount != 0 ||
1410                  SetFileExtentsResultCB->ResultStatus != 0) &&
1411                 !RDR_DeviceIoControl( glDevHandle,
1412                                        IOCTL_AFS_SET_FILE_EXTENTS,
1413                                       (void *)SetFileExtentsResultCB,
1414                                       dwResultBufferLength,
1415                                       (void *)NULL,
1416                                       0,
1417                                       &bytesReturned ))
1418             {
1419                 gle = GetLastError();
1420                 if (afsd_logp->enabled) {
1421                     swprintf( wchBuffer,
1422                               L"Failed to post IOCTL_AFS_SET_FILE_EXTENTS gle %X",
1423                               gle);
1424                     osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1425                 }
1426
1427                 // The file system returns an error when it can't find the FID
1428                 // This is a bug in the file system but we should try to avoid
1429                 // the crash and clean up our own memory space.
1430                 //
1431                 // Since we couldn't deliver the extents to the file system
1432                 // we should release them.
1433                 if ( SetFileExtentsResultCB->ExtentCount != 0)
1434                 {
1435                     RDR_ReleaseFailedSetFileExtents( userp,
1436                                                  SetFileExtentsResultCB,
1437                                                  dwResultBufferLength);
1438                 }
1439
1440                 if (gle != ERROR_GEN_FAILURE &&
1441                     gle != ERROR_NOT_READY) {
1442                     sprintf( pBuffer,
1443                              "Failed to post IOCTL_AFS_SET_FILE_EXTENTS gle %X",
1444                              gle);
1445                     osi_panic(pBuffer, __FILE__, __LINE__);
1446                 }
1447             }
1448
1449             free(SetFileExtentsResultCB);
1450
1451       } else {
1452           /* Must be out of memory */
1453           if (afsd_logp->enabled) {
1454               swprintf( wchBuffer,
1455                         L"ProcessRequest Responding Asynchronously STATUS_NO_MEMORY to REQUEST_FILE_EXTENTS Index %08lX",
1456                         RequestBuffer->RequestIndex);
1457
1458               osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1459           }
1460
1461           RDR_SetFileStatus2( &RequestBuffer->FileId, &RequestBuffer->AuthGroup, STATUS_NO_MEMORY);
1462        }
1463     }
1464     else if (RequestBuffer->RequestType == AFS_REQUEST_TYPE_BYTE_RANGE_LOCK) {
1465
1466         if (afsd_logp->enabled) {
1467             swprintf( wchBuffer,
1468                       L"ProcessRequest Responding Asynchronously to REQUEST_TYPE_BYTE_RANGELOCK Index %08lX",
1469                       RequestBuffer->RequestIndex);
1470
1471             osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1472         }
1473
1474
1475         if (SetByteRangeLockResultCB) {
1476
1477             if( !RDR_DeviceIoControl( glDevHandle,
1478                                   IOCTL_AFS_SET_BYTE_RANGE_LOCKS,
1479                                   (void *)SetByteRangeLockResultCB,
1480                                   dwResultBufferLength,
1481                                   (void *)NULL,
1482                                   0,
1483                                   &bytesReturned ))
1484             {
1485                 gle = GetLastError();
1486
1487                 if (afsd_logp->enabled) {
1488                     swprintf( wchBuffer,
1489                               L"Failed to post IOCTL_AFS_SET_BYTE_RANGE_LOCKS gle 0x%x", gle);
1490                     osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1491                 }
1492
1493
1494                 if (gle != ERROR_NOT_READY) {
1495                     // TODO - instead of a panic we should release the locks
1496                     sprintf( pBuffer,
1497                              "Failed to post IOCTL_AFS_SET_BYTE_RANGE_LOCKS gle %X", gle);
1498                     osi_panic(pBuffer, __FILE__, __LINE__);
1499                 }
1500             }
1501
1502             free(SetByteRangeLockResultCB);
1503         } else {
1504             /* Must be out of memory */
1505             AFSSetByteRangeLockResultCB SetByteRangeLockResultCB;
1506
1507             dwResultBufferLength = sizeof(AFSSetByteRangeLockResultCB);
1508             memset( &SetByteRangeLockResultCB, '\0', dwResultBufferLength );
1509             SetByteRangeLockResultCB.FileId = RequestBuffer->FileId;
1510             SetByteRangeLockResultCB.Result[0].Status = STATUS_NO_MEMORY;
1511
1512             if( !RDR_DeviceIoControl( glDevHandle,
1513                                       IOCTL_AFS_SET_BYTE_RANGE_LOCKS,
1514                                       (void *)&SetByteRangeLockResultCB,
1515                                       dwResultBufferLength,
1516                                       (void *)NULL,
1517                                       0,
1518                                       &bytesReturned ))
1519             {
1520                 gle = GetLastError();
1521
1522                 if (afsd_logp->enabled) {
1523                     swprintf( wchBuffer,
1524                               L"Failed to post IOCTL_AFS_SET_BYTE_RANGE_LOCKS gle 0x%x", gle);
1525                     osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1526                 }
1527
1528                 /* We were out of memory - nothing to do */
1529             }
1530         }
1531     }
1532     else {
1533
1534         if (afsd_logp->enabled) {
1535             swprintf( wchBuffer,
1536                       L"ProcessRequest Not responding to async Index %08lX",
1537                       RequestBuffer->RequestIndex);
1538
1539             osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1540         }
1541     }
1542
1543     if (bRetry)
1544         goto retry;
1545
1546     if (userp)
1547         RDR_ReleaseUser(userp);
1548
1549
1550     if( pResultCB && pResultCB != &stResultCB)
1551     {
1552
1553         free( pResultCB);
1554     }
1555     return;
1556 }
1557
1558
1559 extern "C" DWORD
1560 RDR_SetFileExtents( AFSSetFileExtentsCB *pSetFileExtentsResultCB,
1561                     DWORD dwResultBufferLength)
1562 {
1563     WCHAR wchBuffer[1024];
1564     DWORD bytesReturned;
1565     DWORD gle;
1566
1567     if (1 || afsd_logp->enabled) {
1568         if (pSetFileExtentsResultCB->ResultStatus != 0)
1569             swprintf( wchBuffer,
1570                L"RDR_SetFileExtents IOCTL_AFS_SET_FILE_EXTENTS FAILURE Count %08lX Status %08lX",
1571                pSetFileExtentsResultCB->ExtentCount, pSetFileExtentsResultCB->ResultStatus);
1572         else
1573             swprintf( wchBuffer,
1574                L"RDR_SetFileExtents IOCTL_AFS_SET_FILE_EXTENTS SUCCESS Count %08lX",
1575                pSetFileExtentsResultCB->ExtentCount);
1576
1577         osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1578     }
1579
1580     if( !RDR_DeviceIoControl( glDevHandle,
1581                               IOCTL_AFS_SET_FILE_EXTENTS,
1582                               (void *)pSetFileExtentsResultCB,
1583                               dwResultBufferLength,
1584                               (void *)NULL,
1585                               0,
1586                               &bytesReturned ))
1587     {
1588         gle = GetLastError();
1589         return gle;
1590     }
1591
1592     return 0;
1593 }
1594
1595
1596 extern "C" DWORD
1597 RDR_SetFileStatus( cm_fid_t *fidp,
1598                    GUID *pAuthGroup,
1599                    DWORD dwStatus)
1600 {
1601     WCHAR               wchBuffer[1024];
1602     AFSExtentFailureCB  SetFileStatusCB;
1603     DWORD               bytesReturned;
1604     DWORD               gle;
1605
1606     RDR_fid2FID(fidp, &SetFileStatusCB.FileId);
1607     memcpy(&SetFileStatusCB.AuthGroup, pAuthGroup, sizeof(GUID));
1608     SetFileStatusCB.FailureStatus = dwStatus;
1609
1610     if (afsd_logp->enabled) {
1611         swprintf( wchBuffer, L"RDR_SetFileStatus IOCTL_AFS_EXTENT_FAILURE_CB Fid %08lX.%08lX.%08lX.%08lX Status 0x%lX",
1612                   SetFileStatusCB.FileId.Cell, SetFileStatusCB.FileId.Volume,
1613                   SetFileStatusCB.FileId.Vnode, SetFileStatusCB.FileId.Unique,
1614                   dwStatus);
1615
1616         osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1617     }
1618
1619     if( !RDR_DeviceIoControl( glDevHandle,
1620                               IOCTL_AFS_SET_FILE_EXTENT_FAILURE,
1621                               (void *)&SetFileStatusCB,
1622                               sizeof(AFSExtentFailureCB),
1623                               (void *)NULL,
1624                               0,
1625                               &bytesReturned ))
1626     {
1627         gle = GetLastError();
1628         return gle;
1629     }
1630
1631     return 0;
1632 }
1633
1634 static DWORD
1635 RDR_SetFileStatus2( AFSFileID *pFileId,
1636                    GUID *pAuthGroup,
1637                    DWORD dwStatus)
1638 {
1639     WCHAR               wchBuffer[1024];
1640     AFSExtentFailureCB  SetFileStatusCB;
1641     DWORD               bytesReturned;
1642     DWORD               gle;
1643
1644     memcpy(&SetFileStatusCB.FileId, pFileId, sizeof(AFSFileID));
1645     memcpy(&SetFileStatusCB.AuthGroup, pAuthGroup, sizeof(GUID));
1646     SetFileStatusCB.FailureStatus = dwStatus;
1647
1648     if (afsd_logp->enabled) {
1649         swprintf( wchBuffer, L"RDR_SetFileStatus2 IOCTL_AFS_EXTENT_FAILURE_CB Fid %08lX.%08lX.%08lX.%08lX Status 0x%lX",
1650                   SetFileStatusCB.FileId.Cell, SetFileStatusCB.FileId.Volume,
1651                   SetFileStatusCB.FileId.Vnode, SetFileStatusCB.FileId.Unique,
1652                   dwStatus);
1653
1654         osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1655     }
1656
1657     if( !RDR_DeviceIoControl( glDevHandle,
1658                               IOCTL_AFS_SET_FILE_EXTENT_FAILURE,
1659                               (void *)&SetFileStatusCB,
1660                               sizeof(AFSExtentFailureCB),
1661                               (void *)NULL,
1662                               0,
1663                               &bytesReturned ))
1664     {
1665         gle = GetLastError();
1666         return gle;
1667     }
1668
1669     return 0;
1670 }
1671
1672 extern "C" DWORD
1673 RDR_RequestExtentRelease(cm_fid_t *fidp, LARGE_INTEGER numOfHeldExtents, DWORD numOfExtents, AFSFileExtentCB *extentList)
1674 {
1675
1676     HANDLE hDevHandle = NULL;
1677     DWORD bytesReturned;
1678     AFSReleaseFileExtentsCB *requestBuffer = NULL;
1679     AFSReleaseFileExtentsResultCB *responseBuffer = NULL;
1680     DWORD requestBufferLen, responseBufferLen;
1681     bool bError = false;
1682     DWORD rc = 0;
1683     WCHAR wchBuffer[256];
1684     DWORD gle;
1685
1686     if (ExitPending) {
1687         if (afsd_logp->enabled) {
1688             swprintf( wchBuffer,
1689                       L"IOCTL_AFS_RELEASE_FILE_EXTENTS request ignored due to shutdown pending");
1690
1691             osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1692         }
1693
1694         OutputDebugString(L"RDR_RequestExtentRequest ignored - shutdown pending\n");
1695         return CM_ERROR_WOULDBLOCK;
1696     }
1697
1698     if (afsd_logp->enabled) {
1699         swprintf( wchBuffer,
1700                   L"IOCTL_AFS_RELEASE_FILE_EXTENTS request - number %08lX",
1701                   numOfExtents);
1702
1703         osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1704     }
1705
1706     //
1707     // We use the global handle to the control device instance
1708     //
1709
1710     hDevHandle = glDevHandle;
1711
1712     //
1713     // Allocate a request buffer.
1714     //
1715
1716     requestBufferLen = sizeof( AFSReleaseFileExtentsCB) + sizeof(AFSFileExtentCB) * numOfExtents;
1717     requestBuffer = (AFSReleaseFileExtentsCB *)malloc( requestBufferLen);
1718     responseBufferLen = (sizeof( AFSReleaseFileExtentsResultCB) + sizeof( AFSReleaseFileExtentsResultFileCB)) * numOfExtents;
1719     responseBuffer = (AFSReleaseFileExtentsResultCB *)malloc( responseBufferLen);
1720
1721
1722     if( requestBuffer && responseBuffer)
1723     {
1724
1725         memset( requestBuffer, '\0', sizeof( AFSReleaseFileExtentsCB));
1726         memset( responseBuffer, '\0', responseBufferLen);
1727
1728         // If there is a FID provided, use it
1729         if (fidp && extentList)
1730         {
1731             RDR_fid2FID( fidp, &requestBuffer->FileId);
1732
1733             memcpy(&requestBuffer->FileExtents, extentList, numOfExtents * sizeof(AFSFileExtentCB));
1734
1735             requestBuffer->Flags = 0;
1736         } else {
1737
1738             requestBuffer->Flags = AFS_RELEASE_EXTENTS_FLAGS_RELEASE_ALL;
1739         }
1740
1741         // Set the number of extents to be freed
1742         // Leave the rest of the structure as zeros to indicate free anything
1743         requestBuffer->ExtentCount = numOfExtents;
1744
1745         requestBuffer->HeldExtentCount = numOfHeldExtents;
1746
1747         if( !RDR_DeviceIoControl( hDevHandle,
1748                                   IOCTL_AFS_RELEASE_FILE_EXTENTS,
1749                                   (void *)requestBuffer,
1750                                   requestBufferLen,
1751                                   (void *)responseBuffer,
1752                                   responseBufferLen,
1753                                   &bytesReturned ))
1754         {
1755             //
1756             // Error condition back from driver
1757             //
1758             if (afsd_logp->enabled) {
1759                 gle = GetLastError();
1760                 swprintf( wchBuffer,
1761                           L"Failed to post IOCTL_AFS_RELEASE_FILE_EXTENTS - gle 0x%x", gle);
1762                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1763             }
1764             rc = -1;
1765             goto cleanup;
1766         }
1767
1768         //
1769         // Go process the request
1770         //
1771
1772         if (afsd_logp->enabled) {
1773             swprintf( wchBuffer,
1774                       L"IOCTL_AFS_RELEASE_FILE_EXTENTS returns - serial number %08lX flags %lX FileCount %lX",
1775                       responseBuffer->SerialNumber, responseBuffer->Flags, responseBuffer->FileCount);
1776             osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1777         }
1778
1779         rc = RDR_ProcessReleaseFileExtentsResult( responseBuffer, bytesReturned);
1780     } else {
1781
1782         rc = ENOMEM;
1783     }
1784
1785   cleanup:
1786     if (requestBuffer)
1787         free( requestBuffer);
1788     if (responseBuffer)
1789         free( responseBuffer);
1790
1791     return rc;
1792 }
1793
1794
1795 extern "C" DWORD
1796 RDR_NetworkStatus(BOOLEAN status)
1797 {
1798
1799     HANDLE hDevHandle = NULL;
1800     DWORD bytesReturned;
1801     AFSNetworkStatusCB *requestBuffer = NULL;
1802     DWORD rc = 0;
1803     WCHAR wchBuffer[256];
1804     DWORD gle;
1805
1806     if (afsd_logp->enabled) {
1807         swprintf( wchBuffer,
1808                   L"IOCTL_AFS_NETWORK_STATUS request - status %d",
1809                   status);
1810
1811         osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1812     }
1813
1814     //
1815     // We use the global handle to the control device instance
1816     //
1817
1818     hDevHandle = glDevHandle;
1819
1820     //
1821     // Allocate a request buffer.
1822     //
1823
1824     requestBuffer = (AFSNetworkStatusCB *)malloc( sizeof( AFSNetworkStatusCB));
1825
1826
1827     if( requestBuffer)
1828     {
1829
1830         memset( requestBuffer, '\0', sizeof( AFSNetworkStatusCB));
1831
1832         // Set the number of extents to be freed
1833         // Leave the rest of the structure as zeros to indicate free anything
1834         requestBuffer->Online = status;
1835
1836         if( !RDR_DeviceIoControl( hDevHandle,
1837                                   IOCTL_AFS_NETWORK_STATUS,
1838                                   (void *)requestBuffer,
1839                                   sizeof( AFSNetworkStatusCB),
1840                                   NULL,
1841                                   0,
1842                                   &bytesReturned ))
1843         {
1844             //
1845             // Error condition back from driver
1846             //
1847             if (afsd_logp->enabled) {
1848                 gle = GetLastError();
1849                 swprintf( wchBuffer,
1850                           L"Failed to post IOCTL_AFS_NETWORK_STATUS gle 0x%x",
1851                           gle);
1852                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1853             }
1854
1855             rc = -1;
1856             goto cleanup;
1857         }
1858     } else
1859         rc = ENOMEM;
1860
1861   cleanup:
1862     if (requestBuffer)
1863         free( requestBuffer);
1864
1865     return rc;
1866 }
1867
1868
1869
1870 extern "C" DWORD
1871 RDR_VolumeStatus(ULONG cellID, ULONG volID, BOOLEAN online)
1872 {
1873
1874     HANDLE hDevHandle = NULL;
1875     DWORD bytesReturned;
1876     AFSVolumeStatusCB *requestBuffer = NULL;
1877     DWORD rc = 0;
1878     WCHAR wchBuffer[256];
1879     DWORD gle;
1880
1881     if (afsd_logp->enabled) {
1882         swprintf( wchBuffer,
1883                   L"IOCTL_AFS_VOLUME_STATUS request - cell 0x%x vol 0x%x online %d",
1884                   cellID, volID, online);
1885
1886         osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1887     }
1888
1889     //
1890     // We use the global handle to the control device instance
1891     //
1892
1893     hDevHandle = glDevHandle;
1894
1895     //
1896     // Allocate a request buffer.
1897     //
1898
1899     requestBuffer = (AFSVolumeStatusCB *)malloc( sizeof( AFSVolumeStatusCB));
1900
1901
1902     if( requestBuffer)
1903     {
1904
1905         memset( requestBuffer, '\0', sizeof( AFSVolumeStatusCB));
1906
1907         requestBuffer->FileID.Cell = cellID;
1908         requestBuffer->FileID.Volume = volID;
1909         requestBuffer->Online = online;
1910
1911         if( !RDR_DeviceIoControl( hDevHandle,
1912                                   IOCTL_AFS_VOLUME_STATUS,
1913                                   (void *)requestBuffer,
1914                                   sizeof( AFSVolumeStatusCB),
1915                                   NULL,
1916                                   0,
1917                                   &bytesReturned ))
1918         {
1919             //
1920             // Error condition back from driver
1921             //
1922
1923             if (afsd_logp->enabled) {
1924                 gle = GetLastError();
1925                 swprintf( wchBuffer,
1926                           L"Failed to post IOCTL_AFS_VOLUME_STATUS gle 0x%x", gle);
1927                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1928             }
1929
1930             rc = -1;
1931             goto cleanup;
1932         }
1933     } else
1934         rc = ENOMEM;
1935
1936   cleanup:
1937     if (requestBuffer)
1938         free( requestBuffer);
1939
1940     return rc;
1941 }
1942
1943 extern "C" DWORD
1944 RDR_NetworkAddrChange(void)
1945 {
1946     return 0;
1947 }
1948
1949
1950 extern "C" DWORD
1951 RDR_InvalidateVolume(ULONG cellID, ULONG volID, ULONG reason)
1952 {
1953
1954     HANDLE hDevHandle = NULL;
1955     DWORD bytesReturned;
1956     AFSInvalidateCacheCB *requestBuffer = NULL;
1957     DWORD rc = 0;
1958     WCHAR wchBuffer[256];
1959     DWORD gle;
1960
1961     if (afsd_logp->enabled) {
1962         swprintf( wchBuffer,
1963                   L"IOCTL_AFS_INVALIDATE_CACHE (vol) request - cell 0x%x vol 0x%x reason %d",
1964                   cellID, volID, reason);
1965
1966         osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
1967     }
1968
1969     //
1970     // We use the global handle to the control device instance
1971     //
1972
1973     hDevHandle = glDevHandle;
1974
1975     //
1976     // Allocate a request buffer.
1977     //
1978
1979     requestBuffer = (AFSInvalidateCacheCB *)malloc( sizeof( AFSInvalidateCacheCB));
1980
1981
1982     if( requestBuffer)
1983     {
1984
1985         memset( requestBuffer, '\0', sizeof( AFSInvalidateCacheCB));
1986
1987         requestBuffer->FileID.Cell = cellID;
1988         requestBuffer->FileID.Volume = volID;
1989         requestBuffer->WholeVolume = TRUE;
1990         requestBuffer->Reason = reason;
1991
1992         if( !RDR_DeviceIoControl( hDevHandle,
1993                                   IOCTL_AFS_INVALIDATE_CACHE,
1994                                   (void *)requestBuffer,
1995                                   sizeof( AFSInvalidateCacheCB),
1996                                   NULL,
1997                                   0,
1998                                   &bytesReturned ))
1999         {
2000             //
2001             // Error condition back from driver
2002             //
2003
2004             if (afsd_logp->enabled) {
2005                 gle = GetLastError();
2006                 swprintf( wchBuffer,
2007                           L"Failed to post IOCTL_AFS_INVALIDATE_VOLUME gle 0x%x", gle);
2008                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
2009             }
2010
2011             rc = -1;
2012             goto cleanup;
2013         }
2014     } else
2015         rc = ENOMEM;
2016
2017   cleanup:
2018     if (requestBuffer)
2019         free( requestBuffer);
2020
2021     return rc;
2022 }
2023
2024
2025 extern "C" DWORD
2026 RDR_InvalidateObject(ULONG cellID, ULONG volID, ULONG vnode, ULONG uniq, ULONG hash, ULONG fileType, ULONG reason)
2027 {
2028
2029     HANDLE hDevHandle = NULL;
2030     DWORD bytesReturned;
2031     AFSInvalidateCacheCB *requestBuffer = NULL;
2032     DWORD rc = 0;
2033     WCHAR wchBuffer[256];
2034     DWORD gle;
2035
2036     if (afsd_logp->enabled) {
2037         swprintf( wchBuffer,
2038                   L"IOCTL_AFS_INVALIDATE_CACHE (obj) request - cell 0x%x vol 0x%x vn 0x%x uniq 0x%x hash 0x%x type 0x%x reason %d",
2039                   cellID, volID, vnode, uniq, hash, fileType, reason);
2040
2041         osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
2042     }
2043
2044     //
2045     // We use the global handle to the control device instance
2046     //
2047
2048     hDevHandle = glDevHandle;
2049
2050     //
2051     // Allocate a request buffer.
2052     //
2053
2054     requestBuffer = (AFSInvalidateCacheCB *)malloc( sizeof( AFSInvalidateCacheCB));
2055
2056
2057     if( requestBuffer)
2058     {
2059
2060         memset( requestBuffer, '\0', sizeof( AFSInvalidateCacheCB));
2061
2062         requestBuffer->FileID.Cell = cellID;
2063         requestBuffer->FileID.Volume = volID;
2064         requestBuffer->FileID.Vnode = vnode;
2065         requestBuffer->FileID.Unique = uniq;
2066         requestBuffer->FileID.Hash = hash;
2067         requestBuffer->FileType = fileType;
2068         requestBuffer->WholeVolume = FALSE;
2069         requestBuffer->Reason = reason;
2070
2071         if( !RDR_DeviceIoControl( hDevHandle,
2072                                   IOCTL_AFS_INVALIDATE_CACHE,
2073                                   (void *)requestBuffer,
2074                                   sizeof( AFSInvalidateCacheCB),
2075                                   NULL,
2076                                   0,
2077                                   &bytesReturned ))
2078         {
2079             //
2080             // Error condition back from driver
2081             //
2082             if (afsd_logp->enabled) {
2083                 gle = GetLastError();
2084                 swprintf( wchBuffer,
2085                           L"Failed to post IOCTL_AFS_INVALIDATE_CACHE gle 0x%x", gle);
2086                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
2087             }
2088
2089             rc = -1;
2090             goto cleanup;
2091         }
2092     } else
2093         rc = ENOMEM;
2094
2095   cleanup:
2096     if (requestBuffer)
2097         free( requestBuffer);
2098
2099     return rc;
2100 }
2101
2102
2103
2104 extern "C" DWORD
2105 RDR_SysName(ULONG Architecture, ULONG Count, WCHAR **NameList)
2106 {
2107
2108     HANDLE hDevHandle = NULL;
2109     DWORD bytesReturned;
2110     AFSSysNameNotificationCB *requestBuffer = NULL;
2111     DWORD rc = 0;
2112     WCHAR wchBuffer[256];
2113     DWORD Length;
2114     DWORD gle;
2115
2116     if (afsd_logp->enabled) {
2117         swprintf( wchBuffer,
2118                   L"IOCTL_AFS_SYSNAME_NOTIFICATION request - Arch %d Count %d",
2119                   Architecture, Count);
2120
2121         osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
2122     }
2123
2124     if (Count <= 0 || NameList == NULL)
2125         return -1;
2126
2127     //
2128     // We use the global handle to the control device instance
2129     //
2130
2131     hDevHandle = glDevHandle;
2132
2133     //
2134     // Allocate a request buffer.
2135     //
2136
2137     Length = sizeof (AFSSysNameNotificationCB) + (Count - 1) * sizeof (AFSSysName);
2138     requestBuffer = (AFSSysNameNotificationCB *)malloc( Length );
2139
2140
2141     if( requestBuffer)
2142     {
2143         unsigned int i;
2144
2145         memset( requestBuffer, '\0', Length);
2146
2147         requestBuffer->Architecture = Architecture;
2148         requestBuffer->NumberOfNames = Count;
2149         for ( i=0 ; i<Count; i++) {
2150             size_t len = wcslen(NameList[i]);
2151             requestBuffer->SysNames[i].Length = (ULONG) (len * sizeof(WCHAR));
2152             StringCchCopyNW(requestBuffer->SysNames[i].String, AFS_MAX_SYSNAME_LENGTH,
2153                             NameList[i], len);
2154         }
2155
2156         if( !RDR_DeviceIoControl( hDevHandle,
2157                                   IOCTL_AFS_SYSNAME_NOTIFICATION,
2158                                   (void *)requestBuffer,
2159                                   Length,
2160                                   NULL,
2161                                   0,
2162                                   &bytesReturned ))
2163         {
2164             //
2165             // Error condition back from driver
2166             //
2167             if (afsd_logp->enabled) {
2168                 gle = GetLastError();
2169                 swprintf( wchBuffer,
2170                           L"Failed to post IOCTL_AFS_SYSNAME_NOTIFICATION gle 0x%x", gle);
2171                 osi_Log1(afsd_logp, "%S", osi_LogSaveStringW(afsd_logp, wchBuffer));
2172             }
2173
2174             rc = -1;
2175             goto cleanup;
2176         }
2177     } else
2178         rc = ENOMEM;
2179
2180   cleanup:
2181     if (requestBuffer)
2182         free( requestBuffer);
2183
2184     return rc;
2185 }
2186
2187 extern "C" VOID
2188 RDR_Suspend( VOID)
2189 {
2190     ResetEvent( RDR_SuspendEvent);
2191 }
2192
2193 extern "C" VOID
2194 RDR_Resume( VOID)
2195 {
2196     SetEvent( RDR_SuspendEvent);
2197 }