private void ParseAuditOperations(ref Rec rec, AuditInfo audit, StringBuilder buffer, StringBuilder domainBuffer, StringBuilder userBuffer, ref int sentItems) { try { if (string.IsNullOrEmpty(rec.Description)) return; using (var reader = new StringReader(rec.Description)) { string line; var state = -1; var mask = 0; var values = new string[9]; while ((line = reader.ReadLine()) != null) { Match m; switch (state) { case -1: m = RegLine.Match(line); if (m.Success) { for (state = 1; state < m.Groups.Count && !m.Groups[state].Success; ++state) { } if (state == m.Groups.Count) state = -1; else --state; } break; default: m = ((Regex)RegExps[state][0]).Match(line); if (m.Success) { //WriteLine(line); var i = 1; var ms = 1; while (i < m.Groups.Count) { if (m.Groups[i].Success) { values[i / 2] = m.Groups[i + 1].Value; mask |= ms; break; } i += 2; ms <<= 1; } if (mask == ((int)RegExps[state][1])) { var username = string.IsNullOrEmpty(values[1]) || string.IsNullOrEmpty(values[2]) ? UserWithDomain(values[0], buffer, domainBuffer, userBuffer) : values[1] + "\\" + values[2]; AuditLogonEnv env; if (!_handles.TryGetValue(values[3], out env)) { env = new AuditLogonEnv(values[3]); _handles[env.LogonId] = env; } try { switch (state) { case 0: AuditCloseHandle(ref rec, env, username, values[0], values[4], values[5], values[6], ref sentItems); return; case 1: AuditDuplicateHandle(ref rec, env, values[3], username, values[0], values[4], values[5], values[6], values[7], ref sentItems); return; case 2: if (audit.ObjectType == "File") AuditObjectRequestHandle(ref rec, env, values[3], username, values[0], values[5], values[6], values[8], values[4], values[7], ref sentItems); return; case 3: AuditDeleteHandle(ref rec, env, username, values[0], values[4], values[5], values[6], ref sentItems); return; } } finally { if (env.Handles.Count == 0) _handles.Remove(env.LogonId); //WriteLine("==================================================="); } } } break; } } } } catch (Exception e) { L.Log(LogType.FILE, LogLevel.ERROR, "Error while parsing audit operations:" + e); } }
private void AuditObjectRequestHandle(ref Rec rec, AuditLogonEnv env, string logonId, string username, string userSid, string handleId, string processId, string processName, string objectName, string accessMask, ref int sentItems) { var access = (uint)GetPid(accessMask); AuditHandle handle; if (!env.Handles.TryGetValue(handleId, out handle)) { handle = new AuditHandle() { Handle = handleId, Object = new AuditObject() }; env.Handles[handleId] = handle; } if (!string.IsNullOrEmpty(objectName)) { var kernel = RegKernelPath.Match(objectName); if (kernel.Success) objectName = QueryDosPath(kernel.Groups[1].Value, kernel.Groups[2].Value); } handle.Object.LogonId = logonId; handle.Object.Name = objectName; handle.Object.Owner = user; handle.Object.OwnerSid = userSid; handle.OwnerProcess[processId] = processName; handle.Object.Handles[handleId] = handle; handle.AccessType = (AccessMask)access; try { AuditHandle lastHandle; if (env.ProcessLastAudit.TryGetValue(processId, out lastHandle)) { if (lastHandle.Object.Name == handle.Object.Name) { lastHandle.AccessType |= handle.AccessType; env.Handles.Remove(handle.Handle); handle = lastHandle; return; } if ((lastHandle.AccessType & AccessMask.Delete) == AccessMask.Delete && (handle.AccessType & (AccessMask.WriteOrAddFile | AccessMask.AppendOrAddSubDir)) != AccessMask.None) { string customStr2; if ((handle.AccessType & AccessMask.WriteOrAddFile) == AccessMask.WriteOrAddFile) customStr2 = "File"; else customStr2 = "Directory"; env.Handles.Remove(lastHandle.Handle); int pid = GetPid(processId); var prevName = lastHandle.Object.Name; var op = "MOVE"; if (prevName != null) { var currName = handle.Object.Name; if (currName != null) { if (!currName.EndsWith("\\")) currName += "\\"; if (currName.Length < prevName.Length && prevName.StartsWith(currName) && prevName.IndexOf('\\', currName.Length) < 0) op = "RENAME"; } } SendData(ref rec, op, customStr2, lastHandle.Object.Name, userSid, username, processName, pid, accessMask, objectName); sentItems++; } } else if ((handle.AccessType & AccessMask.WriteDac) == AccessMask.WriteDac) { int pid = GetPid(processId); if ((handle.AccessType & FileMask) == FileMask) { SendData(ref rec, "NEW", "File", handle.Object.Name, userSid, user, processName, pid, accessMask, string.Empty); sentItems++; } else if ((handle.AccessType & DirectoryMask) == DirectoryMask) { SendData(ref rec, "NEW", "Directory", handle.Object.Name, userSid, user, processName, pid, accessMask, string.Empty); sentItems++; } } } finally { env.ProcessLastAudit[processId] = handle; } }
private void AuditDeleteHandle(ref Rec rec, AuditLogonEnv env, string user, string userSid, string handleId, string processId, string processName, ref int sentItems) { var pid = GetPid(processId); AuditHandle handle; if (env.Handles.TryGetValue(handleId, out handle)) { if ((handle.AccessType & AccessMask.Delete) == AccessMask.Delete) { env.Handles.Remove(handleId); SendData(ref rec, "DELETED", "File", handle.Object.Name, userSid, user, processName, pid, string.Format("{0:X}", handle.AccessType), string.Empty); sentItems++; } } }
private void AuditDuplicateHandle(ref Rec rec, AuditLogonEnv env, string logonId, string user, string userSid, string sourceHandleId, string sourceProcessId, string targetHandleId, string targetProcessId, ref int sentItems) { try { long pid = GetPid(targetProcessId); if (pid == 4) targetProcessId = sourceProcessId; AuditCloseHandle(ref rec, env, user, userSid, targetHandleId, targetProcessId, string.Empty, ref sentItems, false); AuditHandle handle; if (!env.Handles.TryGetValue(sourceHandleId, out handle)) { handle = new AuditHandle() { Handle = sourceHandleId, Object = new AuditObject() { LogonId = logonId, Owner = user, OwnerSid = userSid } }; env.Handles[sourceHandleId] = handle; } env.Handles[targetHandleId] = handle; handle.Object.Handles[sourceHandleId] = handle; handle.Object.Handles[targetHandleId] = handle; handle.OwnerProcess[sourceProcessId] = sourceProcessId; if (targetProcessId != sourceProcessId) handle.OwnerProcess[targetProcessId] = targetProcessId; } finally { env.ProcessLastAudit.Remove(sourceProcessId); } }
private void AuditCloseHandle(ref Rec rec, AuditLogonEnv env, string username, string userSid, string handleId, string processId, string processName, ref int sentItems, bool removeProcessLast = true) { try { AuditHandle handle; if (env.Handles.TryGetValue(handleId, out handle)) { if ((handle.AccessType & BeforeMoveMask) == BeforeMoveMask) return; handle.OwnerProcess.Remove(processId); if (handle.OwnerProcess.Keys.Count == 0) { if (handle.AccessType == AccessMask.Delete) { SendData(ref rec, "DELETED", "File", handle.Object.Name, userSid, username, processName, GetPid(processId), string.Format("{0:X}", handle.AccessType), string.Empty); sentItems++; } env.Handles.Remove(handleId); handle.Object.Handles.Remove(handleId); } } } finally { if (removeProcessLast) env.ProcessLastAudit.Remove(processId); } }