이 질문은 Starting processes under specific credentials from a Windows service과 관련이 있지만 다른 문제입니다.Net.Tcp 포트 공유 서비스를 사용할 때 액세스가 거부되었습니다.
특정 자격 증명을 사용하여 시스템 세션 (0)의 Windows 서비스에서 프로세스를 시작했지만 포트 공유 URL을 수신 할 수 없습니다. Windows Server 2008 컴퓨터에서 "Worker"도메인 계정을 사용하고 있습니다.
내 SMSvcHost.exe.config 파일 : 나는뿐만 아니라 서비스 및 시스템을 다시 시작했지만, 여전히 나에게이 예외주고 http://pastie.org/private/jxed8bdft0eir5uc371pq
:
System.ServiceModel.CommunicationException: The service endpoint failed to listen on the URI 'net.tcp://localhost:5400/Agent/384' because access was denied. Verify that the current user is granted access in the appropriate allowAccounts section of SMSvcHost.exe.config. ---> System.ComponentModel.Win32Exception: Access is denied
at System.ServiceModel.Activation.SharedMemory.Read(String name, String& content)
at System.ServiceModel.Channels.SharedConnectionListener.SharedListenerProxy.ReadEndpoint(String sharedMemoryName, String& listenerEndpoint)
내 ProcessHelper을 프로세스를 시작하는 코드 : http://pastie.org/private/iytqehsdfujrgil1decda. StartAsUserFromService
메서드를 호출합니다.
config의 SID와 프로세스가 실행중인 계정 사이의 링크가 어떻게 든 생성되지 않는다고 가정합니다. 하지만 왜?
편집 :
은 내가 편집을 해요 설정 서비스가 사용되는 것을 재확인했습니다. System 계정과 Everyone을 명시 적으로 추가하려고 시도했지만 여전히 액세스 거부 오류가 발생합니다. 그것은 그 설정을 전혀 보지 않는 것과 같습니다.
누락 된 권한은 어디에서 찾을 수 있습니까?
편집 :
나는 기계와 모든 Windows 업데이트, 여전히 행운에 .NET 4.5.1을 다시 설치.
편집 :
이 사용자 토큰은 포트 공유를 사용할 수 있도록 복제의 올바른 방법이 있나요? 특히 SecurityDescriptor
비트?
private static ImpersonationResult ImpersonateUser(string domain, string username, string password)
{
IntPtr token = IntPtr.Zero;
IntPtr primaryToken = IntPtr.Zero;
try
{
// Get token
bool bImpersonated = LogonUser(
username,
domain,
password,
(int)LogonType.NetworkClearText,
(int)LogonProvider.Default,
ref token);
if (!bImpersonated)
{
throw new Exception(string.Format("Failed to impersonate identity. Error code: {0}", Marshal.GetLastWin32Error()));
}
SecurityDescriptor sd = new SecurityDescriptor();
IntPtr ptr = Marshal.AllocCoTaskMem(Marshal.SizeOf(sd));
Marshal.StructureToPtr(sd, ptr, false);
InitializeSecurityDescriptor(ptr, 1);
sd = (SecurityDescriptor)Marshal.PtrToStructure(ptr, typeof(SecurityDescriptor));
// Set up security
bool bDecriptorSet = SetSecurityDescriptorDacl(
ref sd,
true,
IntPtr.Zero,
false);
if (!bDecriptorSet)
{
throw new Exception(string.Format("Failed to set security descriptor. Error code: {0}", Marshal.GetLastWin32Error()));
}
SecurityAttributes processAttributes = new SecurityAttributes();
processAttributes.lpSecurityDescriptor = ptr;
processAttributes.nLength = (uint)Marshal.SizeOf(sd);
processAttributes.bInheritHandle = true;
// Duplicate token
bool bTokenDuplicated = DuplicateTokenEx(
token,
0,
ref processAttributes,
(int)SecurityImpersonationLevel.SecurityImpersonation,
(int)TokenType.TokenPrimary,
ref primaryToken);
if (!bTokenDuplicated)
{
throw new Exception(string.Format("Failed to duplicate identity token. Error code: {0}", Marshal.GetLastWin32Error()));
}
SecurityAttributes threadAttributes = new SecurityAttributes();
threadAttributes.lpSecurityDescriptor = IntPtr.Zero;
threadAttributes.nLength = 0;
threadAttributes.bInheritHandle = false;
// Got the token
return new ImpersonationResult()
{
Token = primaryToken,
ProcessAttributes = processAttributes,
ThreadAttributes = threadAttributes
};
}
finally
{
FreeToken(token);
}
}
private static void FreeToken(IntPtr token)
{
if (token != IntPtr.Zero)
{
CloseHandle(token);
}
}
편집 : http://pastie.org/private/nqqcwz8bvjb5fzp48yavbw : http://pastie.org/private/8ekqeps4d7rmo7hnktsw
여기 프로세스를 시작하는 서비스의의 app.config 비트입니다 :
여기에 포트 공유를 가능하게 내 프로세스의의 app.config 비트입니다. 시스템 계정에서 실행 중이기 때문에 포트 공유를 사용하는 데 문제가 없습니다.
포트 공유 서비스가 활성화되어 있으며 컴퓨터를 여러 번 다시 시작했다고 언급했습니다.
"응용 프로그램 서버"역할은 설치되어 있지 않지만 추가 할 때 TCP 포트 공유 역할은 이미 체크되어 회색으로 표시되어 있으므로 다른 기능이 설치되어 있어야합니다. .NET 4.5.1과 함께 제공됩니까?
조심해. 설정 파일에는 ''섹션이있다.이 섹션은 COMMENTED OUT이다. 메모장에서 편집하면 놓칠 수도 있습니다. 그 파일에서''을 찾아야한다. –
Menahem
내 설정이 정확합니다 : http://pastie.org/private/jxed8bdft0eir5uc371pq – Edgar
실제로 구성이 좋아 보입니다. 'localhost'에 바인드하지 않고 머신 이름을 바인딩하려 했습니까? – Menahem