private static uint ChangeGroupId(uint groupId) { var oldId = UnixInterop.setfsgid(groupId); if (oldId == groupId) { return(oldId); } // This will always fail and is required, because no // error status gets set by this function. var currentId = UnixInterop.setfsgid(uint.MaxValue); if (currentId != groupId) { if (currentId != oldId) { UnixInterop.setfsgid(oldId); } throw new InvalidOperationException(); } // Set again, because WSL seems to be buggy and accepts // uint.MaxValue even though it's not a valid group id. UnixInterop.setfsgid(groupId); return(oldId); }
/// <summary> /// Initializes a new instance of the <see cref="UnixFileSystemIdChanger"/> class. /// </summary> /// <param name="logger">The logger.</param> /// <param name="userId">The user identifier.</param> /// <param name="groupId">The group identifier.</param> /// <param name="defaultUserId">The user ID to restore.</param> /// <param name="defaultGroupId">The group ID to restore.</param> public UnixFileSystemIdChanger( ILogger?logger, long userId, long groupId, long defaultUserId, long defaultGroupId) { _logger = logger; _setUserId = (uint)userId; _setGroupId = (uint)groupId; _defaultUserId = (uint)defaultUserId; _defaultGroupId = (uint)defaultGroupId; _hasUserInfo = true; var oldGroupId = ChangeGroupId((uint)groupId); uint oldUserId; try { oldUserId = ChangeUserId((uint)userId); } catch { UnixInterop.setfsgid(oldGroupId); throw; } if (oldUserId != defaultUserId || oldGroupId != defaultGroupId) { logger?.LogWarning("Switched to user id={userId} (was: {oldUserId}) and group id={groupId} (was: {oldGroupId})", userId, oldUserId, groupId, oldGroupId); } }
private static bool TryGetDomainNameUnix(out string domainName, out string errorMessage) { unsafe { var domainNameBuffer = stackalloc byte[MaxDomainNameLength]; if (UnixInterop.GetDomainName(domainNameBuffer, MaxDomainNameLength) != 0) { // This should never happen. According to the man page, // the only possible errno for getdomainname is ENAMETOOLONG, // which should only happen if the buffer we supply isn't big // enough, and we're using a buffer size that the man page // says is the max for POSIX (and larger than the max for Linux). domainName = null; errorMessage = "GetDomainName function failed (POSIX violation)."; return(false); } domainName = Marshal.PtrToStringAnsi((IntPtr)domainNameBuffer); if (string.IsNullOrWhiteSpace(domainName)) { domainName = NoDomainName; } errorMessage = null; return(true); } }
/// <inheritdoc /> public void Dispose() { if (_hasUserInfo) { var restoreUid = _defaultUserId; var restoreGid = _defaultGroupId; var prevGid = UnixInterop.setfsgid(restoreGid); var prevUid = UnixInterop.setfsuid(restoreUid); if (prevUid != _setUserId || prevGid != _setGroupId) { _logger?.LogWarning( "Reverted to user id={oldUserId} (was set to: {prevUserId}) and group id={oldGroupId} (was set to: {prevGroupId})", restoreUid, prevUid, restoreGid, prevGid); } } }