예제 #1
0
		public void GetBinaryForm ()
		{
			CommonSecurityDescriptor csd = new CommonSecurityDescriptor
				(false, false, ControlFlags.None, null, null, null, null);

			Assert.AreEqual (20, csd.BinaryLength);
			byte[] binaryForm = new byte[csd.BinaryLength];
			csd.GetBinaryForm (binaryForm, 0);

			Assert.AreEqual (ControlFlags.DiscretionaryAclPresent | ControlFlags.SelfRelative,
			                 csd.ControlFlags);

			// The default 'Allow Everyone Full Access' serializes as NOT having a
			// DiscretionaryAcl, as the above demonstrates (byte 3 is 0 not 4).
			Assert.AreEqual (new byte[20] {
				1, 0, 0, 128, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
			}, binaryForm);

			// Changing SystemAcl protection does nothing special.
			csd.SetSystemAclProtection (true, true);
			Assert.AreEqual (20, csd.BinaryLength);

			// Modifying the DiscretionaryAcl (even effective no-ops like this) causes serialization.
			csd.SetDiscretionaryAclProtection (false, true);
			Assert.AreEqual (48, csd.BinaryLength);
		}
예제 #2
0
 public byte[] GetSecurityDescriptorBinaryForm()
 {
     ReadLock();
     try {
         byte[] binaryForm = new byte[descriptor.BinaryLength];
         descriptor.GetBinaryForm(binaryForm, 0);
         return(binaryForm);
     } finally {
         ReadUnlock();
     }
 }
      public override byte[] GetAllowAllNodeAcl(string repositoryName, Guid domainId, Guid rootMapId)
      {
         // Return an empty Windows node ACL.
         SecurityIdentifier farmAccountSid = SPFarm.Local.DefaultServiceAccount.SecurityIdentifier;
         CommonSecurityDescriptor securityDescriptor = new CommonSecurityDescriptor(false, false, ControlFlags.None, farmAccountSid, null, null, null);
         securityDescriptor.SetDiscretionaryAclProtection(true, false);

         byte[] itemAcl = new byte[securityDescriptor.BinaryLength];
         securityDescriptor.GetBinaryForm(itemAcl, 0);

         return itemAcl;
      }
 public static byte[] ComputeHash(CommonSecurityDescriptor securityDescriptor)
 {
     if(securityDescriptor == null)
     {
         return null;
     }
     // Convert to binary form
     byte[] binaryForm = new byte[securityDescriptor.BinaryLength];
     securityDescriptor.GetBinaryForm(binaryForm, 0);
     using(var md5 = MD5CryptoServiceProvider.Create())
     {
         return md5.ComputeHash(binaryForm);
     }
 }
예제 #5
0
        /// <summary>
        /// 根据指定的二进制数据设置此 ObjectSecurity 对象的安全说明符。
        /// </summary>
        /// <returns></returns>
        public byte[] GetSecurityDescriptorBinaryForm()
        {
            ReadLock();

            try
            {
                byte[] result = new byte[_securityDescriptor.BinaryLength];

                _securityDescriptor.GetBinaryForm(result, 0);

                return(result);
            }
            finally
            {
                ReadUnlock();
            }
        }
예제 #6
0
        internal static IpcPort Create(String portName, CommonSecurityDescriptor securityDescriptor, bool exclusive)
        {
            if (Environment.OSVersion.Platform != PlatformID.Win32NT) {
                throw new NotSupportedException(CoreChannel.GetResourceString("Remoting_Ipc_Win9x"));
            }
            PipeHandle handle = null;
            // Add the prefix to the portName
            string pipeName = prefix + portName;
            SECURITY_ATTRIBUTES attr = new SECURITY_ATTRIBUTES();
            attr.nLength = (int)Marshal.SizeOf(attr);
            byte[] sd = null;
            // If no securityDescriptor was set by the user use the default
            if (securityDescriptor == null)
            {
                securityDescriptor = s_securityDescriptor;
            }

            sd = new byte[securityDescriptor.BinaryLength];
            // Get the binary form of the descriptor
            securityDescriptor.GetBinaryForm(sd, 0);
               
            GCHandle pinningHandle = GCHandle.Alloc(sd, GCHandleType.Pinned);
            // get the address of the security descriptor
            attr.lpSecurityDescriptor = Marshal.UnsafeAddrOfPinnedArrayElement(sd, 0);

            // Create the named pipe with the appropriate name
            handle = NativePipe.CreateNamedPipe(pipeName, 
                                      NativePipe.PIPE_ACCESS_DUPLEX  | NativePipe.FILE_FLAG_OVERLAPPED 
                                            | (exclusive ? NativePipe.FILE_FLAG_FIRST_PIPE_INSTANCE : 0x0), // Or exclusive flag 
                                      NativePipe.PIPE_TYPE_BYTE | NativePipe.PIPE_READMODE_BYTE | NativePipe.PIPE_WAIT,
                                      NativePipe.PIPE_UNLIMITED_INSTANCES,
                                      8192,
                                      8192,
                                      NativePipe.NMPWAIT_WAIT_FOREVER,
                                      attr); 

            pinningHandle.Free();
            if (handle.Handle.ToInt32() == NativePipe.INVALID_HANDLE_VALUE){
                int error = Marshal.GetLastWin32Error();
                throw new RemotingException(String.Format(CultureInfo.CurrentCulture, CoreChannel.GetResourceString("Remoting_Ipc_CreateIpcFailed"), GetMessage(error)));
            }

             return new IpcPort(portName, handle);   
        }
 private static byte[] FromSecurityIdentifiersFull(List<SecurityIdentifier> allowedSids, int accessRights)
 {
     int capacity = (allowedSids == null) ? 3 : (2 + allowedSids.Count);
     DiscretionaryAcl discretionaryAcl = new DiscretionaryAcl(false, false, capacity);
     discretionaryAcl.AddAccess(AccessControlType.Deny, new SecurityIdentifier(WellKnownSidType.NetworkSid, null), 0x10000000, InheritanceFlags.None, PropagationFlags.None);
     int accessMask = GenerateClientAccessRights(accessRights);
     if (allowedSids == null)
     {
         discretionaryAcl.AddAccess(AccessControlType.Allow, new SecurityIdentifier(WellKnownSidType.WorldSid, null), accessMask, InheritanceFlags.None, PropagationFlags.None);
     }
     else
     {
         for (int i = 0; i < allowedSids.Count; i++)
         {
             SecurityIdentifier sid = allowedSids[i];
             discretionaryAcl.AddAccess(AccessControlType.Allow, sid, accessMask, InheritanceFlags.None, PropagationFlags.None);
         }
     }
     discretionaryAcl.AddAccess(AccessControlType.Allow, GetProcessLogonSid(), accessRights, InheritanceFlags.None, PropagationFlags.None);
     CommonSecurityDescriptor descriptor = new CommonSecurityDescriptor(false, false, ControlFlags.None, null, null, null, discretionaryAcl);
     byte[] binaryForm = new byte[descriptor.BinaryLength];
     descriptor.GetBinaryForm(binaryForm, 0);
     return binaryForm;
 }
예제 #8
0
        private SafeFileHandle CreateNamedPipe(string pipeName)
        {
            CommonSecurityDescriptor sd = new CommonSecurityDescriptor(false, false, "D:(A;;GA;;;LS)(A;;GA;;;BA)(A;;GA;;;IU)");

            byte[] sdBytes = new byte[sd.BinaryLength];
            sd.GetBinaryForm(sdBytes, 0);
            GCHandle gcHandle = GCHandle.Alloc(sdBytes, GCHandleType.Pinned);

            Native.SECURITY_ATTRIBUTES securityAttributes = new Native.SECURITY_ATTRIBUTES();
            securityAttributes.nLength = Marshal.SizeOf(securityAttributes);
            securityAttributes.bInheritHandle = 0;
            securityAttributes.lpSecurityDescriptor = Marshal.UnsafeAddrOfPinnedArrayElement(sdBytes, 0);

            IntPtr handle = Native.CreateNamedPipe(
                pipeName,
                Native.PIPE_ACCESS_DUPLEX | Native.FILE_FLAG_OVERLAPPED | Native.FILE_FLAG_FIRST_PIPE_INSTANCE,
                Native.PIPE_TYPE_BYTE | Native.PIPE_READMODE_BYTE | Native.PIPE_WAIT,
                1,
                2048,
                2048,
                Native.NMPWAIT_USE_DEFAULT_WAIT,
                securityAttributes);

            gcHandle.Free();

            return new SafeFileHandle(handle, true);
        }
      protected byte[] GetNodeAclWorker(string mapDatabaseName, string repositoryName, Guid domainId, Guid rootMapId, bool isCacheEnabled)
      {
         SecurityIdentifier farmAccountSid = SPFarm.Local.DefaultServiceAccount.SecurityIdentifier;
         CommonSecurityDescriptor securityDescriptor = new CommonSecurityDescriptor(false, false, ControlFlags.None, farmAccountSid, null, null, null);
         securityDescriptor.SetDiscretionaryAclProtection(true, false);

         // Deny access to all users.
         SecurityIdentifier everyoneSid = new SecurityIdentifier(WellKnownSidType.WorldSid, null);
         securityDescriptor.DiscretionaryAcl.RemoveAccess(AccessControlType.Allow, everyoneSid, unchecked((int)0xffffffffL), InheritanceFlags.None, PropagationFlags.None);

         // Grant access to specified users.
         securityDescriptor.DiscretionaryAcl.AddAccess(AccessControlType.Allow, farmAccountSid, unchecked((int)0xffffffffL), InheritanceFlags.None, PropagationFlags.None);

         List<SpUserDetail> allowedUsers = GetAllowedUsers(mapDatabaseName, repositoryName, domainId, rootMapId);
         List<string> addedSids = new List<string>();
         foreach (SpUserDetail user in allowedUsers)
         {
            SecurityIdentifier userSid = null;
            if (!string.IsNullOrEmpty(user.Sid))
            {
               userSid = new SecurityIdentifier(user.Sid);
            }
            else
            {
               userSid = GetSidFromClaim(user.LoginName);
            }

            if (userSid != null && !addedSids.Contains(userSid.Value))
            {
               securityDescriptor.DiscretionaryAcl.AddAccess(AccessControlType.Allow, userSid, unchecked((int)0xffffffffL), InheritanceFlags.None, PropagationFlags.None);
               addedSids.Add(userSid.Value);
            }
         }

         byte[] itemAcl = new byte[securityDescriptor.BinaryLength];
         securityDescriptor.GetBinaryForm(itemAcl, 0);

         return itemAcl;
      }
 private static void EditKernelObjectSecurity(SafeCloseHandle kernelObject, List<SecurityIdentifier> accounts, SecurityIdentifier account, int right, bool add)
 {
     int num;
     if (!ListenerUnsafeNativeMethods.GetKernelObjectSecurity(kernelObject, 4, null, 0, out num))
     {
         int error = Marshal.GetLastWin32Error();
         if (error != 0x7a)
         {
             throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new Win32Exception(error));
         }
     }
     byte[] pSecurityDescriptor = new byte[num];
     if (!ListenerUnsafeNativeMethods.GetKernelObjectSecurity(kernelObject, 4, pSecurityDescriptor, pSecurityDescriptor.Length, out num))
     {
         throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new Win32Exception());
     }
     CommonSecurityDescriptor descriptor = new CommonSecurityDescriptor(false, false, pSecurityDescriptor, 0);
     DiscretionaryAcl discretionaryAcl = descriptor.DiscretionaryAcl;
     if (account != null)
     {
         EditDacl(discretionaryAcl, account, right, add);
     }
     else if (accounts != null)
     {
         foreach (SecurityIdentifier identifier in accounts)
         {
             EditDacl(discretionaryAcl, identifier, right, add);
         }
     }
     pSecurityDescriptor = new byte[descriptor.BinaryLength];
     descriptor.GetBinaryForm(pSecurityDescriptor, 0);
     if (!ListenerUnsafeNativeMethods.SetKernelObjectSecurity(kernelObject, 4, pSecurityDescriptor))
     {
         throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new Win32Exception());
     }
 }
예제 #11
0
		public void AefaRoundtrip ()
		{
			CommonSecurityDescriptor csd;

			csd = new CommonSecurityDescriptor (false, false, ControlFlags.None, null, null, null, null);
			Assert.AreEqual (20, csd.BinaryLength);

			byte[] binaryForm1 = new byte[csd.BinaryLength];
			csd.GetBinaryForm (binaryForm1, 0);

			csd = new CommonSecurityDescriptor (false, false, new RawSecurityDescriptor (binaryForm1, 0));

			byte[] binaryForm2 = new byte[csd.BinaryLength];
			csd.GetBinaryForm (binaryForm2, 0);

			Assert.AreEqual (binaryForm1, binaryForm2);
		}
예제 #12
0
		public void GetBinaryFormOffset ()
		{
			CommonSecurityDescriptor csd = new CommonSecurityDescriptor
				(false, false, ControlFlags.None, null, null, null, null);
			csd.GetBinaryForm (new byte[csd.BinaryLength], 1);
		}
예제 #13
0
        // Do not use this method unless you understand the consequnces of lack of synchronization
        static void EditKernelObjectSecurity(SafeCloseHandle kernelObject, List<SecurityIdentifier> accounts, SecurityIdentifier account, int right, bool add)
        {
            // take the SECURITY_DESCRIPTOR from the kernelObject
            int lpnLengthNeeded;
            bool success = ListenerUnsafeNativeMethods.GetKernelObjectSecurity(kernelObject, ListenerUnsafeNativeMethods.DACL_SECURITY_INFORMATION, null, 0, out lpnLengthNeeded);
            if (!success)
            {
                int errorCode = Marshal.GetLastWin32Error();
                if (errorCode != ListenerUnsafeNativeMethods.ERROR_INSUFFICIENT_BUFFER)
                {
                    throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new Win32Exception(errorCode));
                }
            }
            byte[] pSecurityDescriptor = new byte[lpnLengthNeeded];
#pragma warning suppress 56523 // Microsoft, Win32Exception ctor calls Marshal.GetLastWin32Error()
            success = ListenerUnsafeNativeMethods.GetKernelObjectSecurity(kernelObject, ListenerUnsafeNativeMethods.DACL_SECURITY_INFORMATION, pSecurityDescriptor, pSecurityDescriptor.Length, out lpnLengthNeeded);
            if (!success)
            {
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new Win32Exception());
            }
            CommonSecurityDescriptor securityDescriptor = new CommonSecurityDescriptor(false, false, pSecurityDescriptor, 0);
            DiscretionaryAcl dacl = securityDescriptor.DiscretionaryAcl;
            // add ACEs to the SECURITY_DESCRIPTOR of the kernelObject
            if (account != null)
            {
                EditDacl(dacl, account, right, add);
            }
            else if (accounts != null)
            {
                foreach (SecurityIdentifier accountInList in accounts)
                {
                    EditDacl(dacl, accountInList, right, add);
                }
            }
            lpnLengthNeeded = securityDescriptor.BinaryLength;
            pSecurityDescriptor = new byte[lpnLengthNeeded];
            securityDescriptor.GetBinaryForm(pSecurityDescriptor, 0);
            // set the SECURITY_DESCRIPTOR on the kernelObject
#pragma warning suppress 56523 // Microsoft, Win32Exception ctor calls Marshal.GetLastWin32Error()
            success = ListenerUnsafeNativeMethods.SetKernelObjectSecurity(kernelObject, ListenerUnsafeNativeMethods.DACL_SECURITY_INFORMATION, pSecurityDescriptor);
            if (!success)
            {
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new Win32Exception());
            }
        }
        internal override void AdjustRegKeyPermission()
        {
            const uint maxSecurityDescriptorSize = 40960;
            byte[] binarySecurityDescriptor;
            CommonSecurityDescriptor securityDescriptor = null;
            int ret;
            uint dwSize = 256;

            do
            {
                binarySecurityDescriptor = new byte[dwSize];
                ret = SafeNativeMethods.ClusterRegGetKeySecurity(hKey, SecurityInfos.DiscretionaryAcl, binarySecurityDescriptor, ref dwSize);
                if (ret == SafeNativeMethods.ERROR_SUCCESS)
                {
                    break;
                }
                else if (ret == SafeNativeMethods.ERROR_INSUFFICIENT_BUFFER)
                {
                    dwSize *= 2;
                }
                else
                {
                    throw registryExceptionHelper.CreateRegistryWriteException(null);
                }
            } while (dwSize <= maxSecurityDescriptorSize);

            if (dwSize > maxSecurityDescriptorSize)
            {
                throw registryExceptionHelper.CreateRegistryWriteException(null);
            }
                        
            try
            {
                securityDescriptor = new CommonSecurityDescriptor(false, false, binarySecurityDescriptor, 0);
                DiscretionaryAcl dacl = securityDescriptor.DiscretionaryAcl;
                if (dacl.Count == 1)
                {
                    CommonAce ace = dacl[0] as CommonAce;
                    if (ace != null && ace.AceType == AceType.AccessAllowed && ace.SecurityIdentifier.IsWellKnown(WellKnownSidType.WorldSid))
                    {
                        // This is the Allowed for everyone full access ACE that's automatically added by
                        // CommonSecurityDescriptor ctor; we should remove it
                        dacl.Purge(new SecurityIdentifier(WellKnownSidType.WorldSid, null));
                    }
                }

                // Add Read access for Authenticated Users account and Network Service account
                dacl.AddAccess(AccessControlType.Allow, new SecurityIdentifier(WellKnownSidType.AuthenticatedUserSid, null),
                    unchecked((int)0x80000000), InheritanceFlags.None, PropagationFlags.None);
                dacl.AddAccess(AccessControlType.Allow, new SecurityIdentifier(WellKnownSidType.NetworkServiceSid, null),
                    unchecked((int)0x80000000), InheritanceFlags.None, PropagationFlags.None);
            }
            #pragma warning suppress 56500
            catch (Exception e)
            {
                // MSDN does not have a spec of possible exceptions for the APIs used above.
                // To be safe, we should be a bit more generic in catching exceptions
                if (Utilities.IsCriticalException(e))
                {
                    throw;
                }
                throw registryExceptionHelper.CreateRegistryWriteException(e);
            }

            int dsNewSecDescSize = securityDescriptor.BinaryLength;
            byte[] newBinarySecurityDescriptor = new byte[dsNewSecDescSize];
            securityDescriptor.GetBinaryForm(newBinarySecurityDescriptor, 0);

            ret = SafeNativeMethods.ClusterRegSetKeySecurity(hKey, SecurityInfos.DiscretionaryAcl, newBinarySecurityDescriptor);
            if (ret != SafeNativeMethods.ERROR_SUCCESS)
            {
                throw registryExceptionHelper.CreateRegistryWriteException(null);
            }
        }
예제 #15
0
        /// <summary>
        /// Helper method to create a PowerShell transport named pipe via native API, along
        /// with a returned .Net NamedPipeServerStream object wrapping the named pipe.
        /// </summary>
        /// <param name="serverName">Named pipe server name.</param>
        /// <param name="namespaceName">Named pipe namespace name.</param>
        /// <param name="coreName">Named pipe core name.</param>
        /// <param name="securityDesc"></param>
        /// <returns>NamedPipeServerStream</returns>
        private NamedPipeServerStream CreateNamedPipe(
            string serverName,
            string namespaceName,
            string coreName,
            CommonSecurityDescriptor securityDesc)
        {
            if (serverName == null) { throw new PSArgumentNullException("serverName"); }
            if (namespaceName == null) { throw new PSArgumentNullException("namespaceName"); }
            if (coreName == null) { throw new PSArgumentNullException("coreName"); }

            string fullPipeName = @"\\" + serverName + @"\" + namespaceName + @"\" + coreName;

            // Create optional security attributes based on provided PipeSecurity.
            NamedPipeNative.SECURITY_ATTRIBUTES securityAttributes = null;
            GCHandle? securityDescHandle = null;
            if (securityDesc != null)
            {
                byte[] securityDescBuffer = new byte[securityDesc.BinaryLength];
                securityDesc.GetBinaryForm(securityDescBuffer, 0);
                securityDescHandle = GCHandle.Alloc(securityDescBuffer, GCHandleType.Pinned);
                securityAttributes = NamedPipeNative.GetSecurityAttributes(securityDescHandle.Value);
            }

            // Create named pipe.
            SafePipeHandle pipeHandle = NamedPipeNative.CreateNamedPipe(
                fullPipeName,
                NamedPipeNative.PIPE_ACCESS_DUPLEX | NamedPipeNative.FILE_FLAG_FIRST_PIPE_INSTANCE | NamedPipeNative.FILE_FLAG_OVERLAPPED,
                NamedPipeNative.PIPE_TYPE_MESSAGE | NamedPipeNative.PIPE_READMODE_MESSAGE,
                1,
                _namedPipeBufferSizeForRemoting,
                _namedPipeBufferSizeForRemoting,
                0,
                securityAttributes);

            int lastError = Marshal.GetLastWin32Error();
            if (securityDescHandle != null)
            {
                securityDescHandle.Value.Free();
            }

            if (pipeHandle.IsInvalid)
            {
                throw new PSInvalidOperationException(
                    StringUtil.Format(RemotingErrorIdStrings.CannotCreateNamedPipe, lastError));
            }

            // Create the .Net NamedPipeServerStream wrapper.
            try
            {
                return new NamedPipeServerStream(
                    PipeDirection.InOut,
                    true,                       // IsAsync
                    false,                      // IsConnected
                    pipeHandle);
            }
            catch (Exception e)
            {
                CommandProcessorBase.CheckForSevereException(e);
                pipeHandle.Dispose();
                throw;
            }
        }
예제 #16
0
        static byte[] FromSecurityIdentifiersFull(List<SecurityIdentifier> allowedSids, int accessRights)
        {
            int capacity = allowedSids == null ? 3 : 2 + allowedSids.Count;
            DiscretionaryAcl dacl = new DiscretionaryAcl(false, false, capacity);

            // add deny ACE first so that we don't get short circuited
            dacl.AddAccess(AccessControlType.Deny, new SecurityIdentifier(WellKnownSidType.NetworkSid, null),
                UnsafeNativeMethods.GENERIC_ALL, InheritanceFlags.None, PropagationFlags.None);

            // clients get different rights, since they shouldn't be able to listen
            int clientAccessRights = GenerateClientAccessRights(accessRights);

            if (allowedSids == null)
            {
                dacl.AddAccess(AccessControlType.Allow, new SecurityIdentifier(WellKnownSidType.WorldSid, null),
                    clientAccessRights, InheritanceFlags.None, PropagationFlags.None);
            }
            else
            {
                for (int i = 0; i < allowedSids.Count; i++)
                {
                    SecurityIdentifier allowedSid = allowedSids[i];
                    dacl.AddAccess(AccessControlType.Allow, allowedSid,
                        clientAccessRights, InheritanceFlags.None, PropagationFlags.None);
                }
            }

            dacl.AddAccess(AccessControlType.Allow, GetProcessLogonSid(), accessRights, InheritanceFlags.None, PropagationFlags.None);


            if (AppContainerInfo.IsRunningInAppContainer)
            {
                // NamedPipeBinding requires dacl with current AppContainer SID
                // to setup multiple NamedPipes in the BeginAccept loop.                
                dacl.AddAccess(
                            AccessControlType.Allow,
                            AppContainerInfo.GetCurrentAppContainerSid(),
                            accessRights,
                            InheritanceFlags.None,
                            PropagationFlags.None);
            }

            CommonSecurityDescriptor securityDescriptor =
                new CommonSecurityDescriptor(false, false, ControlFlags.None, null, null, null, dacl);
            byte[] binarySecurityDescriptor = new byte[securityDescriptor.BinaryLength];
            securityDescriptor.GetBinaryForm(binarySecurityDescriptor, 0);
            return binarySecurityDescriptor;
        }
예제 #17
0
		public void GetBinaryFormNull ()
		{
			CommonSecurityDescriptor csd = new CommonSecurityDescriptor
				(false, false, ControlFlags.None, null, null, null, null);
			csd.GetBinaryForm (null, 0);
		}
 internal static IpcPort Create(string portName, CommonSecurityDescriptor securityDescriptor, bool exclusive)
 {
     SECURITY_ATTRIBUTES security_attributes;
     if (Environment.OSVersion.Platform != PlatformID.Win32NT)
     {
         throw new NotSupportedException(CoreChannel.GetResourceString("Remoting_Ipc_Win9x"));
     }
     PipeHandle handle = null;
     string lpName = @"\\.\pipe\" + portName;
     security_attributes = new SECURITY_ATTRIBUTES {
         nLength = Marshal.SizeOf(security_attributes)
     };
     byte[] binaryForm = null;
     if (securityDescriptor == null)
     {
         securityDescriptor = s_securityDescriptor;
     }
     binaryForm = new byte[securityDescriptor.BinaryLength];
     securityDescriptor.GetBinaryForm(binaryForm, 0);
     GCHandle handle2 = GCHandle.Alloc(binaryForm, GCHandleType.Pinned);
     security_attributes.lpSecurityDescriptor = Marshal.UnsafeAddrOfPinnedArrayElement(binaryForm, 0);
     handle = NativePipe.CreateNamedPipe(lpName, (uint) (0x40000003 | (exclusive ? 0x80000 : 0)), 0, 0xff, 0x2000, 0x2000, uint.MaxValue, security_attributes);
     handle2.Free();
     if (handle.Handle.ToInt32() == -1)
     {
         int errorCode = Marshal.GetLastWin32Error();
         throw new RemotingException(string.Format(CultureInfo.CurrentCulture, CoreChannel.GetResourceString("Remoting_Ipc_CreateIpcFailed"), new object[] { GetMessage(errorCode) }));
     }
     return new IpcPort(portName, handle);
 }