コード例 #1
0
ファイル: NtQueryKey.cs プロジェクト: rwrc/OpenSandbox
 public bool Handle(OffRegKey key)
 {
     // TODO: exceptions thrown from this function should use STATUS_* error codes set
     // instead of ERROR_*
     string name = key.Identity.GetSystemPath();
     KeyInfo info = key.QueryInfo();
     // TODO: either test the following error-prone code with offsets thoroughly
     // or replace it with safer alternative code
     int offset = 0;
     switch (KeyInformationClass_)
     {
         case Win32Api.KeyInformationClass.KeyBasicInformation:
             ResultLength_ = unchecked((uint)(16 + sizeof(char) * name.Length));
             if (Length_ < ResultLength_)
             {
                 throw Win32Exception.Create((int)Win32Api.Status.STATUS_BUFFER_TOO_SMALL);
             }
             if (KeyInformation_ != IntPtr.Zero)
             {
                 Marshal.StructureToPtr(info.LastWriteTime, KeyInformation_, false); offset += 8;
                 Marshal.WriteInt32(KeyInformation_, offset, 0); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, sizeof(char) * name.Length); offset += 4;
                 PInvokeHelper.CopyStringUni(name,
                     (IntPtr)((Int64)KeyInformation_ + offset), name.Length);
             }
             return true;
         case Win32Api.KeyInformationClass.KeyNodeInformation:
             ResultLength_ = unchecked((uint)(24 + sizeof(char) * (name.Length + info.Class.Length)));
             if (Length_ < ResultLength_)
             {
                 throw Win32Exception.Create((int)Win32Api.Status.STATUS_BUFFER_TOO_SMALL);
             }
             if (KeyInformation_ != IntPtr.Zero)
             {
                 // TODO: fill the parts of structures w/o strings using
                 // C# structures (until now I don't know solution for strings, but
                 // at least all other fields will be set carefully)
                 // do this throughout the function
                 Marshal.StructureToPtr(info.LastWriteTime, KeyInformation_, false); offset += 8;
                 Marshal.WriteInt32(KeyInformation_, offset, 0); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset,
                     24 + sizeof(char) * name.Length); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset,
                     sizeof(char) * info.Class.Length); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset,
                     sizeof(char) * name.Length); offset += 4;
                 PInvokeHelper.CopyStringUni(name,
                     (IntPtr)((Int64)KeyInformation_ + offset),
                     name.Length); offset += name.Length * sizeof(char);
                 PInvokeHelper.CopyStringUni(info.Class,
                     (IntPtr)((Int64)KeyInformation_ + offset),
                     info.Class.Length);
             }
             return true;
         case Win32Api.KeyInformationClass.KeyFullInformation:
             ResultLength_ = unchecked((uint)(44 + sizeof(char) * (info.Class.Length)));
             if (Length_ < ResultLength_)
             {
                 throw Win32Exception.Create((int)Win32Api.Status.STATUS_BUFFER_TOO_SMALL);
             }
             if (KeyInformation_ != IntPtr.Zero)
             {
                 Marshal.StructureToPtr(info.LastWriteTime, KeyInformation_, false); offset += 8;
                 Marshal.WriteInt32(KeyInformation_, offset, 0); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, 44); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset,
                     sizeof(char) * info.Class.Length); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, unchecked((int)info.SubKeysNumber)); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, unchecked((int)info.MaxSubKeyLength)); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, unchecked((int)info.MaxClassLength)); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, unchecked((int)info.ValuesNumber)); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, unchecked((int)info.MaxValueNameLength)); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, unchecked((int)info.MaxValueLength)); offset += 4;
                 PInvokeHelper.CopyStringUni(info.Class,
                     (IntPtr)((Int64)KeyInformation_ + offset),
                     info.Class.Length);
             }
             return true;
         case Win32Api.KeyInformationClass.KeyNameInformation:
             ResultLength_ = unchecked((uint)(4 + sizeof(char) * name.Length));
             if (Length_ < ResultLength_)
             {
                 throw Win32Exception.Create((int)Win32Api.Status.STATUS_BUFFER_TOO_SMALL);
             }
             if (KeyInformation_ != IntPtr.Zero)
             {
                 Marshal.WriteInt32(KeyInformation_, sizeof(char) * name.Length); offset += 4;
                 PInvokeHelper.CopyStringUni(name,
                     (IntPtr)((Int64)KeyInformation_ + offset), name.Length);
             }
             return true;
         case Win32Api.KeyInformationClass.KeyCachedInformation:
             ResultLength_ = 36;
             if (Length_ < ResultLength_)
             {
                 throw Win32Exception.Create((int)Win32Api.Status.STATUS_BUFFER_TOO_SMALL);
             }
             if (KeyInformation_ != IntPtr.Zero)
             {
                 Marshal.StructureToPtr(info.LastWriteTime, KeyInformation_, false); offset += 8;
                 Marshal.WriteInt32(KeyInformation_, offset, 0); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, unchecked((int)info.SubKeysNumber)); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, unchecked((int)info.MaxSubKeyLength)); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, unchecked((int)info.ValuesNumber)); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, unchecked((int)info.MaxValueNameLength)); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, unchecked((int)info.MaxValueLength)); offset += 4;
                 Marshal.WriteInt32(KeyInformation_, offset, name.Length);
             }
             return true;
         case Win32Api.KeyInformationClass.KeyFlagsInformation:
             // Reserved
             break;
         case Win32Api.KeyInformationClass.KeyVirtualizationInformation:
             // Not implemented
             break;
         case Win32Api.KeyInformationClass.KeyHandleTagsInformation:
             // Reserved
             break;
     }
     return false;
 }