reactos操作系统实现(135)

时间:2021-12-13 14:28:29

 当从IO管理器里调用函数IopParseDevice来分析设备时,就可以找到相应的磁盘设备,并在这个函数里调用函数IopCheckVpbMounted来检查这个文件系统是否加载,如果没有加载,就会调用函数IopMountVolume来加载文件卷,那么在这个函数里就会构造一个IRP发送给文件系统驱动程序,驱动程序就收到主功能码为IRP_MJ_FILE_SYSTEM_CONTROL和次功能码为IRP_MN_MOUNT_VOLUMEIRP处理请求。在FAT文件系统里是通过函数VfatFileSystemControl来处理相应的功能码,具体实现如下:

#001  NTSTATUSVfatFileSystemControl(PVFAT_IRP_CONTEXT IrpContext)

#002  /*

#003   * FUNCTION: File systemcontrol

#004   */

#005  {

#006 

#007     NTSTATUS Status;

#008 

#009    DPRINT("VfatFileSystemControl(IrpContext %p)/n", IrpContext);

#010 

#011     ASSERT(IrpContext);

#012    ASSERT(IrpContext->Irp);

#013    ASSERT(IrpContext->Stack);

#014 

#015    IrpContext->Irp->IoStatus.Information = 0;

#016 

 

这里区分次功能码,并分派给不同的函数处理。

#017     switch(IrpContext->MinorFunction)

#018     {

#019        caseIRP_MN_USER_FS_REQUEST:

#020          switch(IrpContext->Stack->Parameters.DeviceIoControl.IoControlCode)

#021           {

#022              caseFSCTL_GET_VOLUME_BITMAP:

#023                 Status =VfatGetVolumeBitmap(IrpContext);

#024                 break;

#025              caseFSCTL_GET_RETRIEVAL_POINTERS:

#026                 Status =VfatGetRetrievalPointers(IrpContext);

#027                 break;

#028              case FSCTL_MOVE_FILE:

#029                 Status =VfatMoveFile(IrpContext);

#030                 break;

#031  #ifdef USE_ROS_CC_AND_FS

#032              caseFSCTL_ROS_QUERY_LCN_MAPPING:

#033                 Status =VfatRosQueryLcnMapping(IrpContext);

#034                 break;

#035  #endif

#036              caseFSCTL_IS_VOLUME_DIRTY:

#037                 Status =VfatIsVolumeDirty(IrpContext);

#038                 break;

#039              caseFSCTL_MARK_VOLUME_DIRTY:

#040                 Status =VfatMarkVolumeDirty(IrpContext);

#041                 break;

#042              default:

#043                 Status =STATUS_INVALID_DEVICE_REQUEST;

#044           }

#045           break;

#046 

 

这里就是实现加载文件卷的功能码处理。

#047        caseIRP_MN_MOUNT_VOLUME:

#048           Status = VfatMount(IrpContext);

#049           break;

#050 

#051        caseIRP_MN_VERIFY_VOLUME:

#052          DPRINT("VFATFS:IRP_MN_VERIFY_VOLUME/n");

#053           Status = VfatVerify(IrpContext);

#054           break;

#055 

#056        default:

#057             DPRINT("VFATFSC: MinorFunction %d/n", IrpContext->MinorFunction);

#058             Status =STATUS_INVALID_DEVICE_REQUEST;

#059             break;

#060     }

#061 

#062    IrpContext->Irp->IoStatus.Status = Status;

#063 

#064     IoCompleteRequest(IrpContext->Irp, IO_NO_INCREMENT);

#065    VfatFreeIrpContext(IrpContext);

#066     return (Status);

#067  }

#068